tcmem.pas 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755
  1. {
  2. $Id$
  3. Copyright (c) 1993-98 by Florian Klaempfl
  4. Type checking and register allocation for memory related nodes
  5. This program is free software; you can redistribute it and/or modify
  6. it under the terms of the GNU General Public License as published by
  7. the Free Software Foundation; either version 2 of the License, or
  8. (at your option) any later version.
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. GNU General Public License for more details.
  13. You should have received a copy of the GNU General Public License
  14. along with this program; if not, write to the Free Software
  15. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  16. ****************************************************************************
  17. }
  18. unit tcmem;
  19. interface
  20. uses
  21. tree;
  22. procedure firstloadvmt(var p : ptree);
  23. procedure firsthnew(var p : ptree);
  24. procedure firstnew(var p : ptree);
  25. procedure firsthdispose(var p : ptree);
  26. procedure firstsimplenewdispose(var p : ptree);
  27. procedure firstaddr(var p : ptree);
  28. procedure firstdoubleaddr(var p : ptree);
  29. procedure firstderef(var p : ptree);
  30. procedure firstsubscript(var p : ptree);
  31. procedure firstvec(var p : ptree);
  32. procedure firstself(var p : ptree);
  33. procedure firstwith(var p : ptree);
  34. implementation
  35. uses
  36. globtype,systems,
  37. cobjects,verbose,globals,
  38. symconst,symtable,aasm,types,
  39. hcodegen,htypechk,pass_1,cpubase;
  40. {*****************************************************************************
  41. FirstLoadVMT
  42. *****************************************************************************}
  43. procedure firstloadvmt(var p : ptree);
  44. begin
  45. p^.registers32:=1;
  46. p^.location.loc:=LOC_REGISTER;
  47. end;
  48. {*****************************************************************************
  49. FirstHNew
  50. *****************************************************************************}
  51. procedure firsthnew(var p : ptree);
  52. begin
  53. end;
  54. {*****************************************************************************
  55. FirstNewN
  56. *****************************************************************************}
  57. procedure firstnew(var p : ptree);
  58. begin
  59. { Standardeinleitung }
  60. if assigned(p^.left) then
  61. firstpass(p^.left);
  62. if codegenerror then
  63. exit;
  64. if assigned(p^.left) then
  65. begin
  66. p^.registers32:=p^.left^.registers32;
  67. p^.registersfpu:=p^.left^.registersfpu;
  68. {$ifdef SUPPORT_MMX}
  69. p^.registersmmx:=p^.left^.registersmmx;
  70. {$endif SUPPORT_MMX}
  71. end;
  72. { result type is already set }
  73. procinfo^.flags:=procinfo^.flags or pi_do_call;
  74. if assigned(p^.left) then
  75. p^.location.loc:=LOC_REGISTER
  76. else
  77. p^.location.loc:=LOC_REFERENCE;
  78. end;
  79. {*****************************************************************************
  80. FirstDispose
  81. *****************************************************************************}
  82. procedure firsthdispose(var p : ptree);
  83. begin
  84. firstpass(p^.left);
  85. if codegenerror then
  86. exit;
  87. p^.registers32:=p^.left^.registers32;
  88. p^.registersfpu:=p^.left^.registersfpu;
  89. {$ifdef SUPPORT_MMX}
  90. p^.registersmmx:=p^.left^.registersmmx;
  91. {$endif SUPPORT_MMX}
  92. if p^.registers32<1 then
  93. p^.registers32:=1;
  94. {
  95. if p^.left^.location.loc<>LOC_REFERENCE then
  96. CGMessage(cg_e_illegal_expression);
  97. }
  98. if p^.left^.location.loc=LOC_CREGISTER then
  99. inc(p^.registers32);
  100. p^.location.loc:=LOC_REFERENCE;
  101. p^.resulttype:=ppointerdef(p^.left^.resulttype)^.definition;
  102. end;
  103. {*****************************************************************************
  104. FirstSimpleNewDispose
  105. *****************************************************************************}
  106. procedure firstsimplenewdispose(var p : ptree);
  107. begin
  108. { this cannot be in a register !! }
  109. make_not_regable(p^.left);
  110. firstpass(p^.left);
  111. if codegenerror then
  112. exit;
  113. { check the type }
  114. if p^.left^.resulttype=nil then
  115. p^.left^.resulttype:=generrordef;
  116. if (p^.left^.resulttype^.deftype<>pointerdef) then
  117. CGMessage1(type_e_pointer_type_expected,p^.left^.resulttype^.typename);
  118. if (p^.left^.location.loc<>LOC_REFERENCE) {and
  119. (p^.left^.location.loc<>LOC_CREGISTER)} then
  120. CGMessage(cg_e_illegal_expression);
  121. p^.registers32:=p^.left^.registers32;
  122. p^.registersfpu:=p^.left^.registersfpu;
  123. {$ifdef SUPPORT_MMX}
  124. p^.registersmmx:=p^.left^.registersmmx;
  125. {$endif SUPPORT_MMX}
  126. p^.resulttype:=voiddef;
  127. procinfo^.flags:=procinfo^.flags or pi_do_call;
  128. end;
  129. {*****************************************************************************
  130. FirstAddr
  131. *****************************************************************************}
  132. procedure firstaddr(var p : ptree);
  133. var
  134. hp : ptree;
  135. hp2 : pdefcoll;
  136. store_valid : boolean;
  137. hp3 : pabstractprocdef;
  138. begin
  139. make_not_regable(p^.left);
  140. if not(assigned(p^.resulttype)) then
  141. begin
  142. { tp @procvar support (type of @procvar is a void pointer)
  143. Note: we need to leave the addrn in the tree,
  144. else we can't see the difference between @procvar and procvar.
  145. we set the procvarload flag so a secondpass does nothing for
  146. this node (PFV) }
  147. if (m_tp_procvar in aktmodeswitches) then
  148. begin
  149. hp:=p^.left;
  150. case hp^.treetype of
  151. calln :
  152. begin
  153. { is it a procvar? }
  154. hp:=hp^.right;
  155. if assigned(hp) then
  156. begin
  157. { remove calln node }
  158. putnode(p^.left);
  159. p^.left:=hp;
  160. firstpass(hp);
  161. p^.procvarload:=true;
  162. end;
  163. end;
  164. loadn,
  165. vecn,
  166. derefn :
  167. begin
  168. firstpass(hp);
  169. if codegenerror then
  170. exit;
  171. if hp^.resulttype^.deftype=procvardef then
  172. begin
  173. p^.procvarload:=true;
  174. end;
  175. end;
  176. end;
  177. end;
  178. if p^.procvarload then
  179. begin
  180. p^.registers32:=p^.left^.registers32;
  181. p^.registersfpu:=p^.left^.registersfpu;
  182. {$ifdef SUPPORT_MMX}
  183. p^.registersmmx:=p^.left^.registersmmx;
  184. {$endif SUPPORT_MMX}
  185. if p^.registers32<1 then
  186. p^.registers32:=1;
  187. p^.location.loc:=p^.left^.location.loc;
  188. p^.resulttype:=voidpointerdef;
  189. exit;
  190. end;
  191. { proc 2 procvar ? }
  192. if p^.left^.treetype=calln then
  193. begin
  194. { generate a methodcallnode or proccallnode }
  195. { we shouldn't convert things like @tcollection.load }
  196. if (p^.left^.symtableprocentry^.owner^.symtabletype=objectsymtable) and
  197. not(assigned(p^.left^.methodpointer) and (p^.left^.methodpointer^.treetype=typen)) then
  198. begin
  199. hp:=genloadmethodcallnode(pprocsym(p^.left^.symtableprocentry),p^.left^.symtableproc,
  200. getcopy(p^.left^.methodpointer));
  201. disposetree(p);
  202. firstpass(hp);
  203. p:=hp;
  204. exit;
  205. end
  206. else
  207. hp:=genloadcallnode(pprocsym(p^.left^.symtableprocentry),p^.left^.symtableproc);
  208. { result is a procedure variable }
  209. { No, to be TP compatible, you must return a pointer to
  210. the procedure that is stored in the procvar.}
  211. if not(m_tp_procvar in aktmodeswitches) then
  212. begin
  213. p^.resulttype:=new(pprocvardef,init);
  214. { it could also be a procvar, not only pprocsym ! }
  215. if p^.left^.symtableprocentry^.typ=varsym then
  216. hp3:=pabstractprocdef(pvarsym(p^.left^.symtableentry)^.definition)
  217. else
  218. hp3:=pabstractprocdef(pprocsym(p^.left^.symtableprocentry)^.definition);
  219. pprocvardef(p^.resulttype)^.proctypeoption:=hp3^.proctypeoption;
  220. pprocvardef(p^.resulttype)^.proccalloptions:=hp3^.proccalloptions;
  221. pprocvardef(p^.resulttype)^.procoptions:=hp3^.procoptions;
  222. pprocvardef(p^.resulttype)^.retdef:=hp3^.retdef;
  223. pprocvardef(p^.resulttype)^.symtablelevel:=hp3^.symtablelevel;
  224. { method ? then set the methodpointer flag }
  225. if (hp3^.owner^.symtabletype=objectsymtable) and
  226. (pobjectdef(hp3^.owner^.defowner)^.is_class) then
  227. {$ifdef INCLUDEOK}
  228. include(pprocvardef(p^.resulttype)^.procoptions,po_methodpointer);
  229. {$else}
  230. pprocvardef(p^.resulttype)^.procoptions:=pprocvardef(p^.resulttype)^.procoptions+[po_methodpointer];
  231. {$endif}
  232. hp2:=hp3^.para1;
  233. while assigned(hp2) do
  234. begin
  235. pprocvardef(p^.resulttype)^.concatdef(hp2^.data,hp2^.paratyp);
  236. hp2:=hp2^.next;
  237. end;
  238. end
  239. else
  240. p^.resulttype:=voidpointerdef;
  241. disposetree(p^.left);
  242. p^.left:=hp;
  243. end
  244. else
  245. begin
  246. { what are we getting the address from an absolute sym? }
  247. hp:=p^.left;
  248. while assigned(hp) and (hp^.treetype in [vecn,subscriptn]) do
  249. hp:=hp^.left;
  250. if assigned(hp) and (hp^.treetype=loadn) and
  251. ((hp^.symtableentry^.typ=absolutesym) and
  252. pabsolutesym(hp^.symtableentry)^.absseg) then
  253. begin
  254. if not(cs_typed_addresses in aktlocalswitches) then
  255. p^.resulttype:=voidfarpointerdef
  256. else
  257. p^.resulttype:=new(ppointerdef,initfar(p^.left^.resulttype));
  258. end
  259. else
  260. begin
  261. if not(cs_typed_addresses in aktlocalswitches) then
  262. p^.resulttype:=voidpointerdef
  263. else
  264. p^.resulttype:=new(ppointerdef,init(p^.left^.resulttype));
  265. end;
  266. end;
  267. end;
  268. store_valid:=must_be_valid;
  269. must_be_valid:=false;
  270. firstpass(p^.left);
  271. must_be_valid:=store_valid;
  272. if codegenerror then
  273. exit;
  274. { don't allow constants }
  275. if is_constnode(p^.left) then
  276. begin
  277. aktfilepos:=p^.left^.fileinfo;
  278. CGMessage(type_e_no_addr_of_constant);
  279. end
  280. else
  281. begin
  282. { we should allow loc_mem for @string }
  283. if not(p^.left^.location.loc in [LOC_MEM,LOC_REFERENCE]) then
  284. begin
  285. aktfilepos:=p^.left^.fileinfo;
  286. CGMessage(cg_e_illegal_expression);
  287. end;
  288. end;
  289. p^.registers32:=p^.left^.registers32;
  290. p^.registersfpu:=p^.left^.registersfpu;
  291. {$ifdef SUPPORT_MMX}
  292. p^.registersmmx:=p^.left^.registersmmx;
  293. {$endif SUPPORT_MMX}
  294. if p^.registers32<1 then
  295. p^.registers32:=1;
  296. p^.location.loc:=LOC_REGISTER;
  297. end;
  298. {*****************************************************************************
  299. FirstDoubleAddr
  300. *****************************************************************************}
  301. procedure firstdoubleaddr(var p : ptree);
  302. begin
  303. make_not_regable(p^.left);
  304. firstpass(p^.left);
  305. if p^.resulttype=nil then
  306. p^.resulttype:=voidpointerdef;
  307. if codegenerror then
  308. exit;
  309. if (p^.left^.resulttype^.deftype)<>procvardef then
  310. CGMessage(cg_e_illegal_expression);
  311. if (p^.left^.location.loc<>LOC_REFERENCE) then
  312. CGMessage(cg_e_illegal_expression);
  313. p^.registers32:=p^.left^.registers32;
  314. p^.registersfpu:=p^.left^.registersfpu;
  315. {$ifdef SUPPORT_MMX}
  316. p^.registersmmx:=p^.left^.registersmmx;
  317. {$endif SUPPORT_MMX}
  318. if p^.registers32<1 then
  319. p^.registers32:=1;
  320. p^.location.loc:=LOC_REGISTER;
  321. end;
  322. {*****************************************************************************
  323. FirstDeRef
  324. *****************************************************************************}
  325. procedure firstderef(var p : ptree);
  326. begin
  327. firstpass(p^.left);
  328. if codegenerror then
  329. begin
  330. p^.resulttype:=generrordef;
  331. exit;
  332. end;
  333. p^.registers32:=max(p^.left^.registers32,1);
  334. p^.registersfpu:=p^.left^.registersfpu;
  335. {$ifdef SUPPORT_MMX}
  336. p^.registersmmx:=p^.left^.registersmmx;
  337. {$endif SUPPORT_MMX}
  338. if p^.left^.resulttype^.deftype<>pointerdef then
  339. CGMessage(cg_e_invalid_qualifier);
  340. p^.resulttype:=ppointerdef(p^.left^.resulttype)^.definition;
  341. p^.location.loc:=LOC_REFERENCE;
  342. end;
  343. {*****************************************************************************
  344. FirstSubScript
  345. *****************************************************************************}
  346. procedure firstsubscript(var p : ptree);
  347. begin
  348. firstpass(p^.left);
  349. if codegenerror then
  350. begin
  351. p^.resulttype:=generrordef;
  352. exit;
  353. end;
  354. p^.resulttype:=p^.vs^.definition;
  355. { this must be done in the parser
  356. if count_ref and not must_be_valid then
  357. if (p^.vs^.properties and sp_protected)<>0 then
  358. CGMessage(parser_e_cant_write_protected_member);
  359. }
  360. p^.registers32:=p^.left^.registers32;
  361. p^.registersfpu:=p^.left^.registersfpu;
  362. {$ifdef SUPPORT_MMX}
  363. p^.registersmmx:=p^.left^.registersmmx;
  364. {$endif SUPPORT_MMX}
  365. { classes must be dereferenced implicit }
  366. if (p^.left^.resulttype^.deftype=objectdef) and
  367. pobjectdef(p^.left^.resulttype)^.is_class then
  368. begin
  369. if p^.registers32=0 then
  370. p^.registers32:=1;
  371. p^.location.loc:=LOC_REFERENCE;
  372. end
  373. else
  374. begin
  375. if (p^.left^.location.loc<>LOC_MEM) and
  376. (p^.left^.location.loc<>LOC_REFERENCE) then
  377. CGMessage(cg_e_illegal_expression);
  378. set_location(p^.location,p^.left^.location);
  379. end;
  380. end;
  381. {*****************************************************************************
  382. FirstVec
  383. *****************************************************************************}
  384. procedure firstvec(var p : ptree);
  385. var
  386. harr : pdef;
  387. ct : tconverttype;
  388. {$ifdef consteval}
  389. tcsym : ptypedconstsym;
  390. {$endif}
  391. begin
  392. firstpass(p^.left);
  393. firstpass(p^.right);
  394. if codegenerror then
  395. exit;
  396. { range check only for arrays }
  397. if (p^.left^.resulttype^.deftype=arraydef) then
  398. begin
  399. if (isconvertable(p^.right^.resulttype,parraydef(p^.left^.resulttype)^.rangedef,
  400. ct,ordconstn,false)=0) and
  401. not(is_equal(p^.right^.resulttype,parraydef(p^.left^.resulttype)^.rangedef)) then
  402. CGMessage(type_e_mismatch);
  403. end;
  404. { Never convert a boolean or a char !}
  405. { maybe type conversion }
  406. if (p^.right^.resulttype^.deftype<>enumdef) and
  407. not(is_char(p^.right^.resulttype)) and
  408. not(is_boolean(p^.right^.resulttype)) then
  409. begin
  410. p^.right:=gentypeconvnode(p^.right,s32bitdef);
  411. firstpass(p^.right);
  412. if codegenerror then
  413. exit;
  414. end;
  415. { determine return type }
  416. if not assigned(p^.resulttype) then
  417. if p^.left^.resulttype^.deftype=arraydef then
  418. p^.resulttype:=parraydef(p^.left^.resulttype)^.definition
  419. else if (p^.left^.resulttype^.deftype=pointerdef) then
  420. begin
  421. { convert pointer to array }
  422. harr:=new(parraydef,init(0,$7fffffff,s32bitdef));
  423. parraydef(harr)^.definition:=ppointerdef(p^.left^.resulttype)^.definition;
  424. p^.left:=gentypeconvnode(p^.left,harr);
  425. firstpass(p^.left);
  426. if codegenerror then
  427. exit;
  428. p^.resulttype:=parraydef(harr)^.definition
  429. end
  430. else if p^.left^.resulttype^.deftype=stringdef then
  431. begin
  432. { indexed access to strings }
  433. case pstringdef(p^.left^.resulttype)^.string_typ of
  434. {
  435. st_widestring : p^.resulttype:=cwchardef;
  436. }
  437. st_ansistring : p^.resulttype:=cchardef;
  438. st_longstring : p^.resulttype:=cchardef;
  439. st_shortstring : p^.resulttype:=cchardef;
  440. end;
  441. end
  442. else
  443. CGMessage(type_e_mismatch);
  444. { the register calculation is easy if a const index is used }
  445. if p^.right^.treetype=ordconstn then
  446. begin
  447. {$ifdef consteval}
  448. { constant evaluation }
  449. if (p^.left^.treetype=loadn) and
  450. (p^.left^.symtableentry^.typ=typedconstsym) then
  451. begin
  452. tcsym:=ptypedconstsym(p^.left^.symtableentry);
  453. if tcsym^.defintion^.typ=stringdef then
  454. begin
  455. end;
  456. end;
  457. {$endif}
  458. p^.registers32:=p^.left^.registers32;
  459. { for ansi/wide strings, we need at least one register }
  460. if is_ansistring(p^.left^.resulttype) or
  461. is_widestring(p^.left^.resulttype) then
  462. p^.registers32:=max(p^.registers32,1);
  463. end
  464. else
  465. begin
  466. { this rules are suboptimal, but they should give }
  467. { good results }
  468. p^.registers32:=max(p^.left^.registers32,p^.right^.registers32);
  469. { for ansi/wide strings, we need at least one register }
  470. if is_ansistring(p^.left^.resulttype) or
  471. is_widestring(p^.left^.resulttype) then
  472. p^.registers32:=max(p^.registers32,1);
  473. { need we an extra register when doing the restore ? }
  474. if (p^.left^.registers32<=p^.right^.registers32) and
  475. { only if the node needs less than 3 registers }
  476. { two for the right node and one for the }
  477. { left address }
  478. (p^.registers32<3) then
  479. inc(p^.registers32);
  480. { need we an extra register for the index ? }
  481. if (p^.right^.location.loc<>LOC_REGISTER)
  482. { only if the right node doesn't need a register }
  483. and (p^.right^.registers32<1) then
  484. inc(p^.registers32);
  485. { not correct, but what works better ?
  486. if p^.left^.registers32>0 then
  487. p^.registers32:=max(p^.registers32,2)
  488. else
  489. min. one register
  490. p^.registers32:=max(p^.registers32,1);
  491. }
  492. end;
  493. p^.registersfpu:=max(p^.left^.registersfpu,p^.right^.registersfpu);
  494. {$ifdef SUPPORT_MMX}
  495. p^.registersmmx:=max(p^.left^.registersmmx,p^.right^.registersmmx);
  496. {$endif SUPPORT_MMX}
  497. if p^.left^.location.loc in [LOC_CREGISTER,LOC_REFERENCE] then
  498. p^.location.loc:=LOC_REFERENCE
  499. else
  500. p^.location.loc:=LOC_MEM;
  501. end;
  502. {*****************************************************************************
  503. FirstSelf
  504. *****************************************************************************}
  505. procedure firstself(var p : ptree);
  506. begin
  507. if (p^.resulttype^.deftype=classrefdef) or
  508. ((p^.resulttype^.deftype=objectdef)
  509. and pobjectdef(p^.resulttype)^.is_class
  510. ) then
  511. p^.location.loc:=LOC_CREGISTER
  512. else
  513. p^.location.loc:=LOC_REFERENCE;
  514. end;
  515. {*****************************************************************************
  516. FirstWithN
  517. *****************************************************************************}
  518. procedure firstwith(var p : ptree);
  519. var
  520. symtable : pwithsymtable;
  521. i : longint;
  522. begin
  523. if assigned(p^.left) and assigned(p^.right) then
  524. begin
  525. firstpass(p^.left);
  526. if codegenerror then
  527. exit;
  528. symtable:=p^.withsymtable;
  529. for i:=1 to p^.tablecount do
  530. begin
  531. if (p^.left^.treetype=loadn) and
  532. (p^.left^.symtable=aktprocsym^.definition^.localst) then
  533. symtable^.direct_with:=true;
  534. symtable^.withnode:=p;
  535. symtable:=pwithsymtable(symtable^.next);
  536. end;
  537. firstpass(p^.right);
  538. if codegenerror then
  539. exit;
  540. left_right_max(p);
  541. p^.resulttype:=voiddef;
  542. end
  543. else
  544. begin
  545. { optimization }
  546. disposetree(p);
  547. p:=nil;
  548. end;
  549. end;
  550. end.
  551. {
  552. $Log$
  553. Revision 1.29 1999-09-27 23:45:02 peter
  554. * procinfo is now a pointer
  555. * support for result setting in sub procedure
  556. Revision 1.28 1999/09/17 17:14:12 peter
  557. * @procvar fixes for tp mode
  558. * @<id>:= gives now an error
  559. Revision 1.27 1999/09/11 11:10:39 florian
  560. * fix of my previous commit, make cycle was broken
  561. Revision 1.26 1999/09/11 09:08:34 florian
  562. * fixed bug 596
  563. * fixed some problems with procedure variables and procedures of object,
  564. especially in TP mode. Procedure of object doesn't apply only to classes,
  565. it is also allowed for objects !!
  566. Revision 1.25 1999/08/23 23:34:15 pierre
  567. * one more register needed if hnewn with CREGISTER
  568. Revision 1.24 1999/08/05 16:53:25 peter
  569. * V_Fatal=1, all other V_ are also increased
  570. * Check for local procedure when assigning procvar
  571. * fixed comment parsing because directives
  572. * oldtp mode directives better supported
  573. * added some messages to errore.msg
  574. Revision 1.23 1999/08/04 00:23:44 florian
  575. * renamed i386asm and i386base to cpuasm and cpubase
  576. Revision 1.22 1999/08/03 22:03:35 peter
  577. * moved bitmask constants to sets
  578. * some other type/const renamings
  579. Revision 1.21 1999/07/16 10:04:39 peter
  580. * merged
  581. Revision 1.20 1999/07/05 20:25:41 peter
  582. * merged
  583. Revision 1.19 1999/07/05 16:24:17 peter
  584. * merged
  585. Revision 1.18.2.4 1999/07/16 09:54:59 peter
  586. * @procvar support in tp7 mode works again
  587. Revision 1.18.2.3 1999/07/05 20:06:47 peter
  588. * give error instead of warning for ln(0) and sqrt(0)
  589. Revision 1.18.2.2 1999/07/05 16:22:56 peter
  590. * error if @constant
  591. Revision 1.18.2.1 1999/06/28 00:33:53 pierre
  592. * better error position bug0269
  593. Revision 1.18 1999/06/03 09:34:12 peter
  594. * better methodpointer check for proc->procvar
  595. Revision 1.17 1999/05/27 19:45:24 peter
  596. * removed oldasm
  597. * plabel -> pasmlabel
  598. * -a switches to source writing automaticly
  599. * assembler readers OOPed
  600. * asmsymbol automaticly external
  601. * jumptables and other label fixes for asm readers
  602. Revision 1.16 1999/05/18 09:52:21 peter
  603. * procedure of object and addrn fixes
  604. Revision 1.15 1999/05/17 23:51:46 peter
  605. * with temp vars now use a reference with a persistant temp instead
  606. of setting datasize
  607. Revision 1.14 1999/05/01 13:24:57 peter
  608. * merged nasm compiler
  609. * old asm moved to oldasm/
  610. Revision 1.13 1999/04/26 18:30:05 peter
  611. * farpointerdef moved into pointerdef.is_far
  612. Revision 1.12 1999/03/02 18:24:24 peter
  613. * fixed overloading of array of char
  614. Revision 1.11 1999/02/22 02:15:54 peter
  615. * updates for ag386bin
  616. Revision 1.10 1999/02/04 11:44:47 florian
  617. * fixed indexed access of ansistrings to temp. ansistring, i.e.
  618. c:=(s1+s2)[i], the temp is now correctly remove and the generated
  619. code is also fixed
  620. Revision 1.9 1999/01/22 12:18:34 pierre
  621. * with bug introduced with DIRECTWITH removed
  622. Revision 1.8 1999/01/21 16:41:08 pierre
  623. * fix for constructor inside with statements
  624. Revision 1.7 1998/12/30 22:15:59 peter
  625. + farpointer type
  626. * absolutesym now also stores if its far
  627. Revision 1.6 1998/12/15 17:16:02 peter
  628. * fixed const s : ^string
  629. * first things for const pchar : @string[1]
  630. Revision 1.5 1998/12/11 00:03:57 peter
  631. + globtype,tokens,version unit splitted from globals
  632. Revision 1.4 1998/11/25 19:12:53 pierre
  633. * var:=new(pointer_type) support added
  634. Revision 1.3 1998/09/26 15:03:05 florian
  635. * small problems with DOM and excpetions fixed (code generation
  636. of raise was wrong and self was sometimes destroyed :()
  637. Revision 1.2 1998/09/24 23:49:24 peter
  638. + aktmodeswitches
  639. Revision 1.1 1998/09/23 20:42:24 peter
  640. * splitted pass_1
  641. }