tccal.pas 40 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960
  1. {
  2. $Id$
  3. Copyright (c) 1993-98 by Florian Klaempfl
  4. Type checking and register allocation for call 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 tccal;
  19. interface
  20. uses
  21. symtable,tree;
  22. procedure firstcallparan(var p : ptree;defcoll : pdefcoll);
  23. procedure firstcalln(var p : ptree);
  24. procedure firstprocinline(var p : ptree);
  25. implementation
  26. uses
  27. cobjects,verbose,globals,systems,
  28. aasm,types,
  29. hcodegen,htypechk,pass_1
  30. {$ifdef i386}
  31. ,i386,tgeni386
  32. {$endif}
  33. {$ifdef m68k}
  34. ,m68k,tgen68k
  35. {$endif}
  36. {$ifdef UseBrowser}
  37. ,browser
  38. {$endif UseBrowser}
  39. ;
  40. {*****************************************************************************
  41. FirstCallParaN
  42. *****************************************************************************}
  43. procedure firstcallparan(var p : ptree;defcoll : pdefcoll);
  44. var
  45. old_array_constructor : boolean;
  46. store_valid : boolean;
  47. oldtype : pdef;
  48. {convtyp : tconverttype;}
  49. begin
  50. inc(parsing_para_level);
  51. if assigned(p^.right) then
  52. begin
  53. if defcoll=nil then
  54. firstcallparan(p^.right,nil)
  55. else
  56. firstcallparan(p^.right,defcoll^.next);
  57. p^.registers32:=p^.right^.registers32;
  58. p^.registersfpu:=p^.right^.registersfpu;
  59. {$ifdef SUPPORT_MMX}
  60. p^.registersmmx:=p^.right^.registersmmx;
  61. {$endif}
  62. end;
  63. if defcoll=nil then
  64. begin
  65. old_array_constructor:=allow_array_constructor;
  66. allow_array_constructor:=true;
  67. if not(assigned(p^.resulttype)) or
  68. (p^.left^.treetype=typeconvn) then
  69. firstpass(p^.left);
  70. allow_array_constructor:=old_array_constructor;
  71. if codegenerror then
  72. begin
  73. dec(parsing_para_level);
  74. exit;
  75. end;
  76. p^.resulttype:=p^.left^.resulttype;
  77. end
  78. { if we know the routine which is called, then the type }
  79. { conversions are inserted }
  80. else
  81. begin
  82. if count_ref then
  83. begin
  84. store_valid:=must_be_valid;
  85. if (defcoll^.paratyp=vs_var) then
  86. test_protected(p^.left);
  87. if (defcoll^.paratyp<>vs_var) then
  88. must_be_valid:=true
  89. else
  90. must_be_valid:=false;
  91. { here we must add something for the implicit type }
  92. { conversion from array of char to pchar }
  93. { if isconvertable(p^.left^.resulttype,defcoll^.data,convtyp,
  94. p^.left^.treetype,false) then
  95. if convtyp=tc_array_to_pointer then
  96. must_be_valid:=false; }
  97. { only process typeconvn, else it will break other trees }
  98. old_array_constructor:=allow_array_constructor;
  99. allow_array_constructor:=true;
  100. if (p^.left^.treetype=typeconvn) then
  101. firstpass(p^.left);
  102. allow_array_constructor:=old_array_constructor;
  103. must_be_valid:=store_valid;
  104. end;
  105. if not(is_shortstring(p^.left^.resulttype) and
  106. is_shortstring(defcoll^.data)) and
  107. (defcoll^.data^.deftype<>formaldef) then
  108. begin
  109. if (defcoll^.paratyp=vs_var) and
  110. { allows conversion from word to integer and
  111. byte to shortint }
  112. (not(
  113. (p^.left^.resulttype^.deftype=orddef) and
  114. (defcoll^.data^.deftype=orddef) and
  115. (p^.left^.resulttype^.size=defcoll^.data^.size)
  116. ) and
  117. { an implicit pointer conversion is allowed }
  118. not(
  119. (p^.left^.resulttype^.deftype=pointerdef) and
  120. (defcoll^.data^.deftype=pointerdef)
  121. ) and
  122. { child classes can be also passed }
  123. not(
  124. (p^.left^.resulttype^.deftype=objectdef) and
  125. (defcoll^.data^.deftype=objectdef) and
  126. pobjectdef(p^.left^.resulttype)^.isrelated(pobjectdef(defcoll^.data))
  127. ) and
  128. { passing a single element to a openarray of the same type }
  129. not(
  130. (is_open_array(defcoll^.data) and
  131. is_equal(parraydef(defcoll^.data)^.definition,p^.left^.resulttype))
  132. ) and
  133. { an implicit file conversion is also allowed }
  134. { from a typed file to an untyped one }
  135. not(
  136. (p^.left^.resulttype^.deftype=filedef) and
  137. (defcoll^.data^.deftype=filedef) and
  138. (pfiledef(defcoll^.data)^.filetype = ft_untyped) and
  139. (pfiledef(p^.left^.resulttype)^.filetype = ft_typed)
  140. ) and
  141. not(is_equal(p^.left^.resulttype,defcoll^.data))) then
  142. CGMessage(parser_e_call_by_ref_without_typeconv);
  143. { don't generate an type conversion for open arrays }
  144. { else we loss the ranges }
  145. if is_open_array(defcoll^.data) then
  146. begin
  147. oldtype:=p^.left^.resulttype;
  148. p^.left:=gentypeconvnode(p^.left,defcoll^.data);
  149. firstpass(p^.left);
  150. p^.left^.resulttype:=oldtype;
  151. end
  152. else
  153. begin
  154. p^.left:=gentypeconvnode(p^.left,defcoll^.data);
  155. firstpass(p^.left);
  156. end;
  157. if codegenerror then
  158. begin
  159. dec(parsing_para_level);
  160. exit;
  161. end;
  162. end;
  163. { check var strings }
  164. if (cs_strict_var_strings in aktlocalswitches) and
  165. is_shortstring(p^.left^.resulttype) and
  166. is_shortstring(defcoll^.data) and
  167. (defcoll^.paratyp=vs_var) and
  168. not(is_equal(p^.left^.resulttype,defcoll^.data)) then
  169. CGMessage(type_e_strict_var_string_violation);
  170. { Variablen, die call by reference �bergeben werden, }
  171. { k”nnen nicht in ein Register kopiert werden }
  172. { is this usefull here ? }
  173. { this was missing in formal parameter list }
  174. if defcoll^.paratyp=vs_var then
  175. begin
  176. set_unique(p^.left);
  177. make_not_regable(p^.left);
  178. end;
  179. p^.resulttype:=defcoll^.data;
  180. end;
  181. if p^.left^.registers32>p^.registers32 then
  182. p^.registers32:=p^.left^.registers32;
  183. if p^.left^.registersfpu>p^.registersfpu then
  184. p^.registersfpu:=p^.left^.registersfpu;
  185. {$ifdef SUPPORT_MMX}
  186. if p^.left^.registersmmx>p^.registersmmx then
  187. p^.registersmmx:=p^.left^.registersmmx;
  188. {$endif SUPPORT_MMX}
  189. dec(parsing_para_level);
  190. end;
  191. {*****************************************************************************
  192. FirstCallN
  193. *****************************************************************************}
  194. procedure firstcalln(var p : ptree);
  195. type
  196. pprocdefcoll = ^tprocdefcoll;
  197. tprocdefcoll = record
  198. data : pprocdef;
  199. nextpara : pdefcoll;
  200. firstpara : pdefcoll;
  201. next : pprocdefcoll;
  202. end;
  203. var
  204. hp,procs,hp2 : pprocdefcoll;
  205. pd : pprocdef;
  206. actprocsym : pprocsym;
  207. nextprocsym : pprocsym;
  208. def_from,def_to,conv_to : pdef;
  209. pt,inlinecode : ptree;
  210. exactmatch,inlined : boolean;
  211. paralength,l : longint;
  212. pdc : pdefcoll;
  213. {$ifdef TEST_PROCSYMS}
  214. symt : psymtable;
  215. {$endif TEST_PROCSYMS}
  216. { only Dummy }
  217. hcvt : tconverttype;
  218. regi : tregister;
  219. store_valid, old_count_ref : boolean;
  220. { types.is_equal can't handle a formaldef ! }
  221. function is_equal(def1,def2 : pdef) : boolean;
  222. begin
  223. { safety check }
  224. if not (assigned(def1) or assigned(def2)) then
  225. begin
  226. is_equal:=false;
  227. exit;
  228. end;
  229. { all types can be passed to a formaldef }
  230. is_equal:=(def1^.deftype=formaldef) or
  231. (types.is_equal(def1,def2))
  232. { to support ansi/long/wide strings in a proper way }
  233. { string and string[10] are assumed as equal }
  234. { when searching the correct overloaded procedure }
  235. or
  236. (
  237. (def1^.deftype=stringdef) and (def2^.deftype=stringdef) and
  238. (pstringdef(def1)^.string_typ=pstringdef(def2)^.string_typ)
  239. )
  240. { set can also be a not yet converted array constructor }
  241. or
  242. (
  243. (def1^.deftype=setdef) and (def2^.deftype=arraydef) and
  244. (parraydef(def2)^.IsConstructor) and not(parraydef(def2)^.IsVariant)
  245. )
  246. ;
  247. end;
  248. function is_in_limit(def_from,def_to : pdef) : boolean;
  249. begin
  250. is_in_limit:=(def_from^.deftype = orddef) and
  251. (def_to^.deftype = orddef) and
  252. (porddef(def_from)^.low>porddef(def_to)^.low) and
  253. (porddef(def_from)^.high<porddef(def_to)^.high);
  254. end;
  255. var
  256. is_const : boolean;
  257. begin
  258. { release registers! }
  259. { if procdefinition<>nil then we called firstpass already }
  260. { it seems to be bad because of the registers }
  261. { at least we can avoid the overloaded search !! }
  262. procs:=nil;
  263. { made this global for disposing !! }
  264. store_valid:=must_be_valid;
  265. must_be_valid:=false;
  266. inlined:=false;
  267. if assigned(p^.procdefinition) and
  268. ((p^.procdefinition^.options and poinline)<>0) then
  269. begin
  270. inlinecode:=p^.right;
  271. if assigned(inlinecode) then
  272. begin
  273. inlined:=true;
  274. p^.procdefinition^.options:=p^.procdefinition^.options and (not poinline);
  275. end;
  276. p^.right:=nil;
  277. end;
  278. { procedure variable ? }
  279. if assigned(p^.right) then
  280. begin
  281. { procedure does a call }
  282. procinfo.flags:=procinfo.flags or pi_do_call;
  283. { calc the correture value for the register }
  284. {$ifdef i386}
  285. for regi:=R_EAX to R_EDI do
  286. inc(reg_pushes[regi],t_times*2);
  287. {$endif}
  288. {$ifdef m68k}
  289. for regi:=R_D0 to R_A6 do
  290. inc(reg_pushes[regi],t_times*2);
  291. {$endif}
  292. { calculate the type of the parameters }
  293. if assigned(p^.left) then
  294. begin
  295. old_count_ref:=count_ref;
  296. count_ref:=false;
  297. firstcallparan(p^.left,nil);
  298. count_ref:=old_count_ref;
  299. if codegenerror then
  300. exit;
  301. end;
  302. firstpass(p^.right);
  303. { check the parameters }
  304. pdc:=pprocvardef(p^.right^.resulttype)^.para1;
  305. pt:=p^.left;
  306. while assigned(pdc) and assigned(pt) do
  307. begin
  308. pt:=pt^.right;
  309. pdc:=pdc^.next;
  310. end;
  311. if assigned(pt) or assigned(pdc) then
  312. CGMessage(parser_e_illegal_parameter_list);
  313. { insert type conversions }
  314. if assigned(p^.left) then
  315. begin
  316. old_count_ref:=count_ref;
  317. count_ref:=true;
  318. firstcallparan(p^.left,pprocvardef(p^.right^.resulttype)^.para1);
  319. count_ref:=old_count_ref;
  320. if codegenerror then
  321. exit;
  322. end;
  323. p^.resulttype:=pprocvardef(p^.right^.resulttype)^.retdef;
  324. { this was missing, leads to a bug below if
  325. the procvar is a function }
  326. p^.procdefinition:=pprocdef(p^.right^.resulttype);
  327. end
  328. else
  329. { not a procedure variable }
  330. begin
  331. { determine the type of the parameters }
  332. if assigned(p^.left) then
  333. begin
  334. old_count_ref:=count_ref;
  335. count_ref:=false;
  336. store_valid:=must_be_valid;
  337. must_be_valid:=false;
  338. firstcallparan(p^.left,nil);
  339. count_ref:=old_count_ref;
  340. must_be_valid:=store_valid;
  341. if codegenerror then
  342. exit;
  343. end;
  344. { do we know the procedure to call ? }
  345. if not(assigned(p^.procdefinition)) then
  346. begin
  347. actprocsym:=pprocsym(p^.symtableprocentry);
  348. {$ifdef TEST_PROCSYMS}
  349. if (p^.unit_specific) or
  350. assigned(p^.methodpointer) then
  351. nextprocsym:=nil
  352. else while not assigned(procs) do
  353. begin
  354. symt:=p^.symtableproc;
  355. srsym:=nil;
  356. while assigned(symt^.next) and not assigned(srsym) do
  357. begin
  358. symt:=symt^.next;
  359. getsymonlyin(symt,actprocsym^.name);
  360. if assigned(srsym) then
  361. if srsym^.typ<>procsym then
  362. begin
  363. { reject all that is not a procedure }
  364. srsym:=nil;
  365. { don't search elsewhere }
  366. while assigned(symt^.next) do
  367. symt:=symt^.next;
  368. end;
  369. end;
  370. nextprocsym:=srsym;
  371. end;
  372. {$else TEST_PROCSYMS}
  373. nextprocsym:=nil;
  374. {$endif TEST_PROCSYMS}
  375. { determine length of parameter list }
  376. pt:=p^.left;
  377. paralength:=0;
  378. while assigned(pt) do
  379. begin
  380. inc(paralength);
  381. pt:=pt^.right;
  382. end;
  383. { link all procedures which have the same # of parameters }
  384. pd:=actprocsym^.definition;
  385. while assigned(pd) do
  386. begin
  387. { we should also check that the overloaded function
  388. has been declared in a unit that is in the uses !! }
  389. { pd^.owner should be in the symtablestack !! }
  390. { Laenge der deklarierten Parameterliste feststellen: }
  391. { not necessary why nextprocsym field }
  392. {st:=symtablestack;
  393. if (pd^.owner^.symtabletype<>objectsymtable) then
  394. while assigned(st) do
  395. begin
  396. if (st=pd^.owner) then break;
  397. st:=st^.next;
  398. end;
  399. if assigned(st) then }
  400. begin
  401. pdc:=pd^.para1;
  402. l:=0;
  403. while assigned(pdc) do
  404. begin
  405. inc(l);
  406. pdc:=pdc^.next;
  407. end;
  408. { only when the # of parameter are equal }
  409. if l=paralength then
  410. begin
  411. new(hp);
  412. hp^.data:=pd;
  413. hp^.next:=procs;
  414. hp^.nextpara:=pd^.para1;
  415. hp^.firstpara:=pd^.para1;
  416. procs:=hp;
  417. end;
  418. end;
  419. pd:=pd^.nextoverloaded;
  420. end;
  421. { no procedures found? then there is something wrong
  422. with the parameter size }
  423. if not assigned(procs) and
  424. ((parsing_para_level=0) or assigned(p^.left)) and
  425. (nextprocsym=nil) then
  426. begin
  427. CGMessage(parser_e_wrong_parameter_size);
  428. actprocsym^.write_parameter_lists;
  429. exit;
  430. end;
  431. { now we can compare parameter after parameter }
  432. pt:=p^.left;
  433. while assigned(pt) do
  434. begin
  435. { matches a parameter of one procedure exact ? }
  436. exactmatch:=false;
  437. hp:=procs;
  438. while assigned(hp) do
  439. begin
  440. if is_equal(hp^.nextpara^.data,pt^.resulttype) then
  441. begin
  442. if hp^.nextpara^.data=pt^.resulttype then
  443. begin
  444. pt^.exact_match_found:=true;
  445. hp^.nextpara^.argconvtyp:=act_exact;
  446. end
  447. else
  448. hp^.nextpara^.argconvtyp:=act_equal;
  449. exactmatch:=true;
  450. end
  451. else
  452. hp^.nextpara^.argconvtyp:=act_convertable;
  453. hp:=hp^.next;
  454. end;
  455. { .... if yes, del all the other procedures }
  456. if exactmatch then
  457. begin
  458. { the first .... }
  459. while (assigned(procs)) and not(is_equal(procs^.nextpara^.data,pt^.resulttype)) do
  460. begin
  461. hp:=procs^.next;
  462. dispose(procs);
  463. procs:=hp;
  464. end;
  465. { and the others }
  466. hp:=procs;
  467. while (assigned(hp)) and assigned(hp^.next) do
  468. begin
  469. if not(is_equal(hp^.next^.nextpara^.data,pt^.resulttype)) then
  470. begin
  471. hp2:=hp^.next^.next;
  472. dispose(hp^.next);
  473. hp^.next:=hp2;
  474. end
  475. else
  476. hp:=hp^.next;
  477. end;
  478. end
  479. { when a parameter matches exact, remove all procs
  480. which need typeconvs }
  481. else
  482. begin
  483. { the first... }
  484. while (assigned(procs)) and
  485. not(isconvertable(pt^.resulttype,procs^.nextpara^.data,
  486. hcvt,pt^.left^.treetype,false)) do
  487. begin
  488. hp:=procs^.next;
  489. dispose(procs);
  490. procs:=hp;
  491. end;
  492. { and the others }
  493. hp:=procs;
  494. while (assigned(hp)) and assigned(hp^.next) do
  495. begin
  496. if not(isconvertable(pt^.resulttype,hp^.next^.nextpara^.data,
  497. hcvt,pt^.left^.treetype,false)) then
  498. begin
  499. hp2:=hp^.next^.next;
  500. dispose(hp^.next);
  501. hp^.next:=hp2;
  502. end
  503. else
  504. hp:=hp^.next;
  505. end;
  506. end;
  507. { update nextpara for all procedures }
  508. hp:=procs;
  509. while assigned(hp) do
  510. begin
  511. hp^.nextpara:=hp^.nextpara^.next;
  512. hp:=hp^.next;
  513. end;
  514. { load next parameter }
  515. pt:=pt^.right;
  516. end;
  517. if not assigned(procs) then
  518. begin
  519. { there is an error, must be wrong type, because
  520. wrong size is already checked (PFV) }
  521. if ((parsing_para_level=0) or (p^.left<>nil)) and
  522. (nextprocsym=nil) then
  523. begin
  524. CGMessage(parser_e_wrong_parameter_type);
  525. actprocsym^.write_parameter_lists;
  526. exit;
  527. end
  528. else
  529. begin
  530. { try to convert to procvar }
  531. p^.treetype:=loadn;
  532. p^.resulttype:=pprocsym(p^.symtableprocentry)^.definition;
  533. p^.symtableentry:=p^.symtableprocentry;
  534. p^.is_first:=false;
  535. p^.disposetyp:=dt_nothing;
  536. firstpass(p);
  537. exit;
  538. end;
  539. end;
  540. { if there are several choices left then for orddef }
  541. { if a type is totally included in the other }
  542. { we don't fear an overflow , }
  543. { so we can do as if it is an exact match }
  544. { this will convert integer to longint }
  545. { rather than to words }
  546. { conversion of byte to integer or longint }
  547. {would still not be solved }
  548. if assigned(procs) and assigned(procs^.next) then
  549. begin
  550. hp:=procs;
  551. while assigned(hp) do
  552. begin
  553. hp^.nextpara:=hp^.firstpara;
  554. hp:=hp^.next;
  555. end;
  556. pt:=p^.left;
  557. while assigned(pt) do
  558. begin
  559. { matches a parameter of one procedure exact ? }
  560. exactmatch:=false;
  561. def_from:=pt^.resulttype;
  562. hp:=procs;
  563. while assigned(hp) do
  564. begin
  565. if not is_equal(hp^.nextpara^.data,pt^.resulttype) then
  566. begin
  567. def_to:=hp^.nextpara^.data;
  568. if ((def_from^.deftype=orddef) and (def_to^.deftype=orddef)) and
  569. (is_in_limit(def_from,def_to) or
  570. ((hp^.nextpara^.paratyp=vs_var) and
  571. (def_from^.size=def_to^.size))) then
  572. begin
  573. exactmatch:=true;
  574. conv_to:=def_to;
  575. end;
  576. end;
  577. hp:=hp^.next;
  578. end;
  579. { .... if yes, del all the other procedures }
  580. if exactmatch then
  581. begin
  582. { the first .... }
  583. while (assigned(procs)) and not(is_in_limit(def_from,procs^.nextpara^.data)) do
  584. begin
  585. hp:=procs^.next;
  586. dispose(procs);
  587. procs:=hp;
  588. end;
  589. { and the others }
  590. hp:=procs;
  591. while (assigned(hp)) and assigned(hp^.next) do
  592. begin
  593. if not(is_in_limit(def_from,hp^.next^.nextpara^.data)) then
  594. begin
  595. hp2:=hp^.next^.next;
  596. dispose(hp^.next);
  597. hp^.next:=hp2;
  598. end
  599. else
  600. begin
  601. def_to:=hp^.next^.nextpara^.data;
  602. if (conv_to^.size>def_to^.size) or
  603. ((porddef(conv_to)^.low<porddef(def_to)^.low) and
  604. (porddef(conv_to)^.high>porddef(def_to)^.high)) then
  605. begin
  606. hp2:=procs;
  607. procs:=hp;
  608. conv_to:=def_to;
  609. dispose(hp2);
  610. end
  611. else
  612. hp:=hp^.next;
  613. end;
  614. end;
  615. end;
  616. { update nextpara for all procedures }
  617. hp:=procs;
  618. while assigned(hp) do
  619. begin
  620. hp^.nextpara:=hp^.nextpara^.next;
  621. hp:=hp^.next;
  622. end;
  623. pt:=pt^.right;
  624. end;
  625. end;
  626. { let's try to eliminate equal is exact is there }
  627. {if assigned(procs^.next) then
  628. begin
  629. pt:=p^.left;
  630. while assigned(pt) do
  631. begin
  632. if pt^.exact_match_found then
  633. begin
  634. hp:=procs;
  635. while (assigned(procs)) and (procs^.nextpara^.data<>pt^.resulttype) do
  636. begin
  637. hp:=procs^.next;
  638. dispose(procs);
  639. procs:=hp;
  640. end;
  641. end;
  642. pt:=pt^.right;
  643. end;
  644. end; }
  645. if assigned(procs^.next) then
  646. begin
  647. CGMessage(cg_e_cant_choose_overload_function);
  648. actprocsym^.write_parameter_lists;
  649. end;
  650. {$ifdef TEST_PROCSYMS}
  651. if (procs=nil) and assigned(nextprocsym) then
  652. begin
  653. p^.symtableprocentry:=nextprocsym;
  654. p^.symtableproc:=symt;
  655. end;
  656. end ; { of while assigned(p^.symtableprocentry) do }
  657. {$endif TEST_PROCSYMS}
  658. {$ifdef UseBrowser}
  659. if make_ref then
  660. begin
  661. procs^.data^.lastref:=new(pref,init(procs^.data^.lastref,@p^.fileinfo));
  662. if procs^.data^.defref=nil then
  663. procs^.data^.defref:=procs^.data^.lastref;
  664. end;
  665. {$endif UseBrowser}
  666. p^.procdefinition:=procs^.data;
  667. p^.resulttype:=procs^.data^.retdef;
  668. { big error for with statements
  669. p^.symtableproc:=p^.procdefinition^.owner; }
  670. p^.location.loc:=LOC_MEM;
  671. {$ifdef CHAINPROCSYMS}
  672. { object with method read;
  673. call to read(x) will be a usual procedure call }
  674. if assigned(p^.methodpointer) and
  675. (p^.procdefinition^._class=nil) then
  676. begin
  677. { not ok for extended }
  678. case p^.methodpointer^.treetype of
  679. typen,hnewn : fatalerror(no_para_match);
  680. end;
  681. disposetree(p^.methodpointer);
  682. p^.methodpointer:=nil;
  683. end;
  684. {$endif CHAINPROCSYMS}
  685. end;{ end of procedure to call determination }
  686. is_const:=((p^.procdefinition^.options and pointernconst)<>0) and
  687. ((block_type=bt_const) or
  688. (assigned(p^.left) and (p^.left^.left^.treetype in [realconstn,ordconstn])));
  689. { handle predefined procedures }
  690. if ((p^.procdefinition^.options and pointernproc)<>0) or is_const then
  691. begin
  692. if assigned(p^.left) then
  693. begin
  694. { settextbuf needs two args }
  695. if assigned(p^.left^.right) then
  696. pt:=geninlinenode(pprocdef(p^.procdefinition)^.extnumber,is_const,p^.left)
  697. else
  698. begin
  699. pt:=geninlinenode(pprocdef(p^.procdefinition)^.extnumber,is_const,p^.left^.left);
  700. putnode(p^.left);
  701. end;
  702. end
  703. else
  704. begin
  705. pt:=geninlinenode(pprocdef(p^.procdefinition)^.extnumber,is_const,nil);
  706. end;
  707. putnode(p);
  708. firstpass(pt);
  709. p:=pt;
  710. must_be_valid:=store_valid;
  711. if codegenerror then
  712. exit;
  713. dispose(procs);
  714. exit;
  715. end
  716. else
  717. { no intern procedure => we do a call }
  718. { calc the correture value for the register }
  719. { handle predefined procedures }
  720. if (p^.procdefinition^.options and poinline)<>0 then
  721. begin
  722. if assigned(p^.methodpointer) then
  723. CGMessage(cg_e_unable_inline_object_methods);
  724. if assigned(p^.right) and (p^.right^.treetype<>procinlinen) then
  725. CGMessage(cg_e_unable_inline_procvar);
  726. { p^.treetype:=procinlinen; }
  727. if not assigned(p^.right) then
  728. begin
  729. if assigned(p^.procdefinition^.code) then
  730. inlinecode:=genprocinlinenode(p,ptree(p^.procdefinition^.code))
  731. else
  732. CGMessage(cg_e_no_code_for_inline_stored);
  733. if assigned(inlinecode) then
  734. begin
  735. { consider it has not inlined if called
  736. again inside the args }
  737. p^.procdefinition^.options:=p^.procdefinition^.options and (not poinline);
  738. firstpass(inlinecode);
  739. inlined:=true;
  740. end;
  741. end;
  742. end
  743. else
  744. procinfo.flags:=procinfo.flags or pi_do_call;
  745. { work trough all parameters to insert the type conversions }
  746. { !!! done now after internproc !! (PM) }
  747. if assigned(p^.left) then
  748. begin
  749. old_count_ref:=count_ref;
  750. count_ref:=true;
  751. firstcallparan(p^.left,p^.procdefinition^.para1);
  752. count_ref:=old_count_ref;
  753. end;
  754. {$ifdef i386}
  755. for regi:=R_EAX to R_EDI do
  756. begin
  757. if (p^.procdefinition^.usedregisters and ($80 shr word(regi)))<>0 then
  758. inc(reg_pushes[regi],t_times*2);
  759. end;
  760. {$endif}
  761. {$ifdef m68k}
  762. for regi:=R_D0 to R_A6 do
  763. begin
  764. if (p^.procdefinition^.usedregisters and ($800 shr word(regi)))<>0 then
  765. inc(reg_pushes[regi],t_times*2);
  766. end;
  767. {$endif}
  768. end;
  769. { ensure that the result type is set }
  770. p^.resulttype:=p^.procdefinition^.retdef;
  771. { get a register for the return value }
  772. if (p^.resulttype<>pdef(voiddef)) then
  773. begin
  774. if (p^.procdefinition^.options and poconstructor)<>0 then
  775. begin
  776. { extra handling of classes }
  777. { p^.methodpointer should be assigned! }
  778. if assigned(p^.methodpointer) and assigned(p^.methodpointer^.resulttype) and
  779. (p^.methodpointer^.resulttype^.deftype=classrefdef) then
  780. begin
  781. p^.location.loc:=LOC_REGISTER;
  782. p^.registers32:=1;
  783. { the result type depends on the classref }
  784. p^.resulttype:=pclassrefdef(p^.methodpointer^.resulttype)^.definition;
  785. end
  786. { a object constructor returns the result with the flags }
  787. else
  788. p^.location.loc:=LOC_FLAGS;
  789. end
  790. else
  791. begin
  792. {$ifdef SUPPORT_MMX}
  793. if (cs_mmx in aktlocalswitches) and
  794. is_mmx_able_array(p^.resulttype) then
  795. begin
  796. p^.location.loc:=LOC_MMXREGISTER;
  797. p^.registersmmx:=1;
  798. end
  799. else
  800. {$endif SUPPORT_MMX}
  801. if ret_in_acc(p^.resulttype) then
  802. begin
  803. p^.location.loc:=LOC_REGISTER;
  804. p^.registers32:=1;
  805. end
  806. else if (p^.resulttype^.deftype=floatdef) then
  807. begin
  808. p^.location.loc:=LOC_FPU;
  809. p^.registersfpu:=1;
  810. end
  811. end;
  812. end;
  813. { a fpu can be used in any procedure !! }
  814. p^.registersfpu:=p^.procdefinition^.fpu_used;
  815. { if this is a call to a method calc the registers }
  816. if (p^.methodpointer<>nil) then
  817. begin
  818. case p^.methodpointer^.treetype of
  819. { but only, if this is not a supporting node }
  820. typen,hnewn : ;
  821. else
  822. begin
  823. { R.Assign is not a constructor !!! }
  824. { but for R^.Assign, R must be valid !! }
  825. if ((p^.procdefinition^.options and poconstructor) <> 0) or
  826. ((p^.methodpointer^.treetype=loadn) and
  827. ((pobjectdef(p^.methodpointer^.resulttype)^.options and oo_hasvirtual) = 0)) then
  828. must_be_valid:=false
  829. else
  830. must_be_valid:=true;
  831. firstpass(p^.methodpointer);
  832. p^.registersfpu:=max(p^.methodpointer^.registersfpu,p^.registersfpu);
  833. p^.registers32:=max(p^.methodpointer^.registers32,p^.registers32);
  834. {$ifdef SUPPORT_MMX}
  835. p^.registersmmx:=max(p^.methodpointer^.registersmmx,p^.registersmmx);
  836. {$endif SUPPORT_MMX}
  837. end;
  838. end;
  839. end;
  840. if inlined then
  841. begin
  842. p^.right:=inlinecode;
  843. p^.procdefinition^.options:=p^.procdefinition^.options or poinline;
  844. end;
  845. { determine the registers of the procedure variable }
  846. { is this OK for inlined procs also ?? (PM) }
  847. if assigned(p^.right) then
  848. begin
  849. p^.registersfpu:=max(p^.right^.registersfpu,p^.registersfpu);
  850. p^.registers32:=max(p^.right^.registers32,p^.registers32);
  851. {$ifdef SUPPORT_MMX}
  852. p^.registersmmx:=max(p^.right^.registersmmx,p^.registersmmx);
  853. {$endif SUPPORT_MMX}
  854. end;
  855. { determine the registers of the procedure }
  856. if assigned(p^.left) then
  857. begin
  858. p^.registersfpu:=max(p^.left^.registersfpu,p^.registersfpu);
  859. p^.registers32:=max(p^.left^.registers32,p^.registers32);
  860. {$ifdef SUPPORT_MMX}
  861. p^.registersmmx:=max(p^.left^.registersmmx,p^.registersmmx);
  862. {$endif SUPPORT_MMX}
  863. end;
  864. if assigned(procs) then
  865. dispose(procs);
  866. must_be_valid:=store_valid;
  867. end;
  868. {*****************************************************************************
  869. FirstProcInlineN
  870. *****************************************************************************}
  871. procedure firstprocinline(var p : ptree);
  872. begin
  873. { left contains the code in tree form }
  874. { but it has already been firstpassed }
  875. { so firstpass(p^.left); does not seem required }
  876. { might be required later if we change the arg handling !! }
  877. end;
  878. end.
  879. {
  880. $Log$
  881. Revision 1.9 1998-10-28 18:26:22 pierre
  882. * removed some erros after other errors (introduced by useexcept)
  883. * stabs works again correctly (for how long !)
  884. Revision 1.8 1998/10/09 16:36:09 pierre
  885. * some memory leaks specific to usebrowser define fixed
  886. * removed tmodule.implsymtable (was like tmodule.localsymtable)
  887. Revision 1.7 1998/10/06 20:49:09 peter
  888. * m68k compiler compiles again
  889. Revision 1.6 1998/10/02 09:24:22 peter
  890. * more constant expression evaluators
  891. Revision 1.5 1998/09/28 11:22:17 pierre
  892. * did not compile for browser
  893. * merge from fixes
  894. Revision 1.4 1998/09/27 10:16:24 florian
  895. * type casts pchar<->ansistring fixed
  896. * ansistring[..] calls does now an unique call
  897. Revision 1.3 1998/09/24 14:27:40 peter
  898. * some better support for openarray
  899. Revision 1.2 1998/09/24 09:02:16 peter
  900. * rewritten isconvertable to use case
  901. * array of .. and single variable are compatible
  902. Revision 1.1 1998/09/23 20:42:24 peter
  903. * splitted pass_1
  904. }