htypechk.pas 82 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205
  1. {
  2. $Id$
  3. Copyright (c) 1998-2000 by Florian Klaempfl
  4. This unit exports some help routines for the type checking
  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 htypechk;
  19. {$i defines.inc}
  20. interface
  21. uses
  22. tokens,
  23. {$ifdef cg11}
  24. node,
  25. {$else cg11}
  26. tree,
  27. {$endif cg11}
  28. symtable;
  29. type
  30. {$ifdef cg11}
  31. Ttok2nodeRec=record
  32. tok : ttoken;
  33. nod : tnodetype;
  34. op_overloading_supported : boolean;
  35. {$else cg11}
  36. Ttok2nodeRec=record
  37. tok : ttoken;
  38. nod : ttreetyp;
  39. op_overloading_supported : boolean;
  40. {$endif cg11}
  41. end;
  42. const
  43. tok2nodes=25;
  44. tok2node:array[1..tok2nodes] of ttok2noderec=(
  45. (tok:_PLUS ;nod:addn;op_overloading_supported:true), { binary overloading supported }
  46. (tok:_MINUS ;nod:subn;op_overloading_supported:true), { binary and unary overloading supported }
  47. (tok:_STAR ;nod:muln;op_overloading_supported:true), { binary overloading supported }
  48. (tok:_SLASH ;nod:slashn;op_overloading_supported:true), { binary overloading supported }
  49. (tok:_EQUAL ;nod:equaln;op_overloading_supported:true), { binary overloading supported }
  50. (tok:_GT ;nod:gtn;op_overloading_supported:true), { binary overloading supported }
  51. (tok:_LT ;nod:ltn;op_overloading_supported:true), { binary overloading supported }
  52. (tok:_GTE ;nod:gten;op_overloading_supported:true), { binary overloading supported }
  53. (tok:_LTE ;nod:lten;op_overloading_supported:true), { binary overloading supported }
  54. (tok:_SYMDIF ;nod:symdifn;op_overloading_supported:true), { binary overloading supported }
  55. (tok:_STARSTAR;nod:starstarn;op_overloading_supported:true), { binary overloading supported }
  56. (tok:_OP_AS ;nod:asn;op_overloading_supported:false), { binary overloading NOT supported }
  57. (tok:_OP_IN ;nod:inn;op_overloading_supported:false), { binary overloading NOT supported }
  58. (tok:_OP_IS ;nod:isn;op_overloading_supported:false), { binary overloading NOT supported }
  59. (tok:_OP_OR ;nod:orn;op_overloading_supported:true), { binary overloading supported }
  60. (tok:_OP_AND ;nod:andn;op_overloading_supported:true), { binary overloading supported }
  61. (tok:_OP_DIV ;nod:divn;op_overloading_supported:true), { binary overloading supported }
  62. (tok:_OP_NOT ;nod:notn;op_overloading_supported:true), { unary overloading supported }
  63. (tok:_OP_MOD ;nod:modn;op_overloading_supported:true), { binary overloading supported }
  64. (tok:_OP_SHL ;nod:shln;op_overloading_supported:true), { binary overloading supported }
  65. (tok:_OP_SHR ;nod:shrn;op_overloading_supported:true), { binary overloading supported }
  66. (tok:_OP_XOR ;nod:xorn;op_overloading_supported:true), { binary overloading supported }
  67. (tok:_ASSIGNMENT;nod:assignn;op_overloading_supported:true), { unary overloading supported }
  68. (tok:_CARET ;nod:caretn;op_overloading_supported:false), { binary overloading NOT supported }
  69. (tok:_UNEQUAL ;nod:unequaln;op_overloading_supported:false) { binary overloading NOT supported overload = instead }
  70. );
  71. const
  72. { firstcallparan without varspez we don't count the ref }
  73. {$ifdef extdebug}
  74. count_ref : boolean = true;
  75. {$endif def extdebug}
  76. get_para_resulttype : boolean = false;
  77. allow_array_constructor : boolean = false;
  78. {$ifdef cg11}
  79. { if someones has a lot of time he might change this into methods }
  80. { tnode and its decendends }
  81. { Conversion }
  82. function isconvertable(def_from,def_to : pdef;
  83. var doconv : tconverttype;fromtreetype : tnodetype;
  84. explicit : boolean) : byte;
  85. { is overloading of this operator allowed for this
  86. binary operator }
  87. function isbinaryoperatoroverloadable(ld, rd,dd : pdef;
  88. treetyp : tnodetype) : boolean;
  89. { is overloading of this operator allowed for this
  90. unary operator }
  91. function isunaryoperatoroverloadable(rd,dd : pdef;
  92. treetyp : tnodetype) : boolean;
  93. { check operator args and result type }
  94. function isoperatoracceptable(pf : pprocdef; optoken : ttoken) : boolean;
  95. { Register Allocation }
  96. procedure make_not_regable(p : tnode);
  97. procedure calcregisters(p : tbinarynode;r32,fpu,mmx : word);
  98. { subroutine handling }
  99. procedure test_protected_sym(sym : psym);
  100. procedure test_protected(p : tnode);
  101. function valid_for_formal_var(p : tnode) : boolean;
  102. function valid_for_formal_const(p : tnode) : boolean;
  103. function is_procsym_load(p:tnode):boolean;
  104. function is_procsym_call(p:tnode):boolean;
  105. function assignment_overloaded(from_def,to_def : pdef) : pprocdef;
  106. procedure test_local_to_procvar(from_def:pprocvardef;to_def:pdef);
  107. function valid_for_assign(p:tnode;allowprop:boolean):boolean;
  108. {$else cg11}
  109. { Conversion }
  110. function isconvertable(def_from,def_to : pdef;
  111. var doconv : tconverttype;fromtreetype : ttreetyp;
  112. explicit : boolean) : byte;
  113. { is overloading of this operator allowed for this
  114. binary operator }
  115. function isbinaryoperatoroverloadable(ld, rd,dd : pdef;
  116. treetyp : ttreetyp) : boolean;
  117. { is overloading of this operator allowed for this
  118. unary operator }
  119. function isunaryoperatoroverloadable(rd,dd : pdef;
  120. treetyp : ttreetyp) : boolean;
  121. { check operator args and result type }
  122. function isoperatoracceptable(pf : pprocdef; optoken : ttoken) : boolean;
  123. { Register Allocation }
  124. procedure make_not_regable(p : ptree);
  125. procedure left_right_max(p : ptree);
  126. procedure calcregisters(p : ptree;r32,fpu,mmx : word);
  127. { subroutine handling }
  128. procedure test_protected_sym(sym : psym);
  129. procedure test_protected(p : ptree);
  130. function valid_for_formal_var(p : ptree) : boolean;
  131. function valid_for_formal_const(p : ptree) : boolean;
  132. function is_procsym_load(p:Ptree):boolean;
  133. function is_procsym_call(p:Ptree):boolean;
  134. function assignment_overloaded(from_def,to_def : pdef) : pprocdef;
  135. procedure test_local_to_procvar(from_def:pprocvardef;to_def:pdef);
  136. function valid_for_assign(p:ptree;allowprop:boolean):boolean;
  137. {$endif cg11}
  138. implementation
  139. uses
  140. globtype,systems,
  141. cutils,cobjects,verbose,globals,
  142. symconst,
  143. types,pass_1,cpubase,ncnv,nld,
  144. nmem,ncal,
  145. {$ifdef newcg}
  146. cgbase
  147. {$else}
  148. hcodegen
  149. {$endif}
  150. ;
  151. {$ifdef cg11}
  152. {****************************************************************************
  153. Convert
  154. ****************************************************************************}
  155. { Returns:
  156. 0 - Not convertable
  157. 1 - Convertable
  158. 2 - Convertable, but not first choice }
  159. function isconvertable(def_from,def_to : pdef;
  160. var doconv : tconverttype;fromtreetype : tnodetype;
  161. explicit : boolean) : byte;
  162. { Tbasetype: uauto,uvoid,uchar,
  163. u8bit,u16bit,u32bit,
  164. s8bit,s16bit,s32,
  165. bool8bit,bool16bit,bool32bit,
  166. u64bit,s64bitint }
  167. type
  168. tbasedef=(bvoid,bchar,bint,bbool);
  169. const
  170. basedeftbl:array[tbasetype] of tbasedef =
  171. (bvoid,bvoid,bchar,
  172. bint,bint,bint,
  173. bint,bint,bint,
  174. bbool,bbool,bbool,bint,bint,bchar);
  175. basedefconverts : array[tbasedef,tbasedef] of tconverttype =
  176. ((tc_not_possible,tc_not_possible,tc_not_possible,tc_not_possible),
  177. (tc_not_possible,tc_equal,tc_not_possible,tc_not_possible),
  178. (tc_not_possible,tc_not_possible,tc_int_2_int,tc_int_2_bool),
  179. (tc_not_possible,tc_not_possible,tc_bool_2_int,tc_bool_2_bool));
  180. var
  181. b : byte;
  182. hd1,hd2 : pdef;
  183. hct : tconverttype;
  184. begin
  185. { safety check }
  186. if not(assigned(def_from) and assigned(def_to)) then
  187. begin
  188. isconvertable:=0;
  189. exit;
  190. end;
  191. { tp7 procvar def support, in tp7 a procvar is always called, if the
  192. procvar is passed explicit a addrn would be there }
  193. if (m_tp_procvar in aktmodeswitches) and
  194. (def_from^.deftype=procvardef) and
  195. (fromtreetype=loadn) then
  196. begin
  197. def_from:=pprocvardef(def_from)^.rettype.def;
  198. end;
  199. { we walk the wanted (def_to) types and check then the def_from
  200. types if there is a conversion possible }
  201. b:=0;
  202. case def_to^.deftype of
  203. orddef :
  204. begin
  205. case def_from^.deftype of
  206. orddef :
  207. begin
  208. doconv:=basedefconverts[basedeftbl[porddef(def_from)^.typ],basedeftbl[porddef(def_to)^.typ]];
  209. b:=1;
  210. if (doconv=tc_not_possible) or
  211. ((doconv=tc_int_2_bool) and
  212. (not explicit) and
  213. (not is_boolean(def_from))) or
  214. ((doconv=tc_bool_2_int) and
  215. (not explicit) and
  216. (not is_boolean(def_to))) then
  217. b:=0;
  218. end;
  219. enumdef :
  220. begin
  221. { needed for char(enum) }
  222. if explicit then
  223. begin
  224. doconv:=tc_int_2_int;
  225. b:=1;
  226. end;
  227. end;
  228. end;
  229. end;
  230. stringdef :
  231. begin
  232. case def_from^.deftype of
  233. stringdef :
  234. begin
  235. doconv:=tc_string_2_string;
  236. b:=1;
  237. end;
  238. orddef :
  239. begin
  240. { char to string}
  241. if is_char(def_from) then
  242. begin
  243. doconv:=tc_char_2_string;
  244. b:=1;
  245. end;
  246. end;
  247. arraydef :
  248. begin
  249. { array of char to string, the length check is done by the firstpass of this node }
  250. if is_chararray(def_from) then
  251. begin
  252. doconv:=tc_chararray_2_string;
  253. if (not(cs_ansistrings in aktlocalswitches) and
  254. is_shortstring(def_to)) or
  255. ((cs_ansistrings in aktlocalswitches) and
  256. is_ansistring(def_to)) then
  257. b:=1
  258. else
  259. b:=2;
  260. end;
  261. end;
  262. pointerdef :
  263. begin
  264. { pchar can be assigned to short/ansistrings,
  265. but not in tp7 compatible mode }
  266. if is_pchar(def_from) and not(m_tp7 in aktmodeswitches) then
  267. begin
  268. doconv:=tc_pchar_2_string;
  269. b:=1;
  270. end;
  271. end;
  272. end;
  273. end;
  274. floatdef :
  275. begin
  276. case def_from^.deftype of
  277. orddef :
  278. begin { ordinal to real }
  279. if is_integer(def_from) then
  280. begin
  281. if pfloatdef(def_to)^.typ=f32bit then
  282. doconv:=tc_int_2_fix
  283. else
  284. doconv:=tc_int_2_real;
  285. b:=1;
  286. end;
  287. end;
  288. floatdef :
  289. begin { 2 float types ? }
  290. if pfloatdef(def_from)^.typ=pfloatdef(def_to)^.typ then
  291. doconv:=tc_equal
  292. else
  293. begin
  294. if pfloatdef(def_from)^.typ=f32bit then
  295. doconv:=tc_fix_2_real
  296. else
  297. if pfloatdef(def_to)^.typ=f32bit then
  298. doconv:=tc_real_2_fix
  299. else
  300. doconv:=tc_real_2_real;
  301. end;
  302. b:=1;
  303. end;
  304. end;
  305. end;
  306. enumdef :
  307. begin
  308. if (def_from^.deftype=enumdef) then
  309. begin
  310. hd1:=def_from;
  311. while assigned(penumdef(hd1)^.basedef) do
  312. hd1:=penumdef(hd1)^.basedef;
  313. hd2:=def_to;
  314. while assigned(penumdef(hd2)^.basedef) do
  315. hd2:=penumdef(hd2)^.basedef;
  316. if (hd1=hd2) then
  317. begin
  318. b:=1;
  319. { because of packenum they can have different sizes! (JM) }
  320. doconv:=tc_int_2_int;
  321. end;
  322. end;
  323. end;
  324. arraydef :
  325. begin
  326. { open array is also compatible with a single element of its base type }
  327. if is_open_array(def_to) and
  328. is_equal(parraydef(def_to)^.elementtype.def,def_from) then
  329. begin
  330. doconv:=tc_equal;
  331. b:=1;
  332. end
  333. else
  334. begin
  335. case def_from^.deftype of
  336. arraydef :
  337. begin
  338. { array constructor -> open array }
  339. if is_open_array(def_to) and
  340. is_array_constructor(def_from) then
  341. begin
  342. if is_void(parraydef(def_from)^.elementtype.def) or
  343. is_equal(parraydef(def_to)^.elementtype.def,parraydef(def_from)^.elementtype.def) then
  344. begin
  345. doconv:=tc_equal;
  346. b:=1;
  347. end
  348. else
  349. if isconvertable(parraydef(def_from)^.elementtype.def,
  350. parraydef(def_to)^.elementtype.def,hct,arrayconstructn,false)<>0 then
  351. begin
  352. doconv:=hct;
  353. b:=2;
  354. end;
  355. end;
  356. end;
  357. pointerdef :
  358. begin
  359. if is_zero_based_array(def_to) and
  360. is_equal(ppointerdef(def_from)^.pointertype.def,parraydef(def_to)^.elementtype.def) then
  361. begin
  362. doconv:=tc_pointer_2_array;
  363. b:=1;
  364. end;
  365. end;
  366. stringdef :
  367. begin
  368. { string to array of char}
  369. if (not(is_special_array(def_to)) or is_open_array(def_to)) and
  370. is_equal(parraydef(def_to)^.elementtype.def,cchardef) then
  371. begin
  372. doconv:=tc_string_2_chararray;
  373. b:=1;
  374. end;
  375. end;
  376. end;
  377. end;
  378. end;
  379. pointerdef :
  380. begin
  381. case def_from^.deftype of
  382. stringdef :
  383. begin
  384. { string constant (which can be part of array constructor)
  385. to zero terminated string constant }
  386. if (fromtreetype in [arrayconstructn,stringconstn]) and
  387. is_pchar(def_to) then
  388. begin
  389. doconv:=tc_cstring_2_pchar;
  390. b:=1;
  391. end;
  392. end;
  393. orddef :
  394. begin
  395. { char constant to zero terminated string constant }
  396. if (fromtreetype=ordconstn) then
  397. begin
  398. if is_equal(def_from,cchardef) and
  399. is_pchar(def_to) then
  400. begin
  401. doconv:=tc_cchar_2_pchar;
  402. b:=1;
  403. end
  404. else
  405. if is_integer(def_from) then
  406. begin
  407. doconv:=tc_cord_2_pointer;
  408. b:=1;
  409. end;
  410. end;
  411. end;
  412. arraydef :
  413. begin
  414. { chararray to pointer }
  415. if is_zero_based_array(def_from) and
  416. is_equal(parraydef(def_from)^.elementtype.def,ppointerdef(def_to)^.pointertype.def) then
  417. begin
  418. doconv:=tc_array_2_pointer;
  419. b:=1;
  420. end;
  421. end;
  422. pointerdef :
  423. begin
  424. { child class pointer can be assigned to anchestor pointers }
  425. if (
  426. (ppointerdef(def_from)^.pointertype.def^.deftype=objectdef) and
  427. (ppointerdef(def_to)^.pointertype.def^.deftype=objectdef) and
  428. pobjectdef(ppointerdef(def_from)^.pointertype.def)^.is_related(
  429. pobjectdef(ppointerdef(def_to)^.pointertype.def))
  430. ) or
  431. { all pointers can be assigned to void-pointer }
  432. is_equal(ppointerdef(def_to)^.pointertype.def,voiddef) or
  433. { in my opnion, is this not clean pascal }
  434. { well, but it's handy to use, it isn't ? (FK) }
  435. is_equal(ppointerdef(def_from)^.pointertype.def,voiddef) then
  436. begin
  437. doconv:=tc_equal;
  438. b:=1;
  439. end;
  440. end;
  441. procvardef :
  442. begin
  443. { procedure variable can be assigned to an void pointer }
  444. { Not anymore. Use the @ operator now.}
  445. if not(m_tp_procvar in aktmodeswitches) and
  446. (ppointerdef(def_to)^.pointertype.def^.deftype=orddef) and
  447. (porddef(ppointerdef(def_to)^.pointertype.def)^.typ=uvoid) then
  448. begin
  449. doconv:=tc_equal;
  450. b:=1;
  451. end;
  452. end;
  453. classrefdef,
  454. objectdef :
  455. begin
  456. { class types and class reference type
  457. can be assigned to void pointers }
  458. if (
  459. ((def_from^.deftype=objectdef) and pobjectdef(def_from)^.is_class) or
  460. (def_from^.deftype=classrefdef)
  461. ) and
  462. (ppointerdef(def_to)^.pointertype.def^.deftype=orddef) and
  463. (porddef(ppointerdef(def_to)^.pointertype.def)^.typ=uvoid) then
  464. begin
  465. doconv:=tc_equal;
  466. b:=1;
  467. end;
  468. end;
  469. end;
  470. end;
  471. setdef :
  472. begin
  473. { automatic arrayconstructor -> set conversion }
  474. if is_array_constructor(def_from) then
  475. begin
  476. doconv:=tc_arrayconstructor_2_set;
  477. b:=1;
  478. end;
  479. end;
  480. procvardef :
  481. begin
  482. { proc -> procvar }
  483. if (def_from^.deftype=procdef) then
  484. begin
  485. doconv:=tc_proc_2_procvar;
  486. if proc_to_procvar_equal(pprocdef(def_from),pprocvardef(def_to)) then
  487. b:=1;
  488. end
  489. else
  490. { for example delphi allows the assignement from pointers }
  491. { to procedure variables }
  492. if (m_pointer_2_procedure in aktmodeswitches) and
  493. (def_from^.deftype=pointerdef) and
  494. (ppointerdef(def_from)^.pointertype.def^.deftype=orddef) and
  495. (porddef(ppointerdef(def_from)^.pointertype.def)^.typ=uvoid) then
  496. begin
  497. doconv:=tc_equal;
  498. b:=1;
  499. end
  500. else
  501. { nil is compatible with procvars }
  502. if (fromtreetype=niln) then
  503. begin
  504. doconv:=tc_equal;
  505. b:=1;
  506. end;
  507. end;
  508. objectdef :
  509. begin
  510. { object pascal objects }
  511. if (def_from^.deftype=objectdef) {and
  512. pobjectdef(def_from)^.isclass and pobjectdef(def_to)^.isclass }then
  513. begin
  514. doconv:=tc_equal;
  515. if pobjectdef(def_from)^.is_related(pobjectdef(def_to)) then
  516. b:=1;
  517. end
  518. else
  519. { Class specific }
  520. if (pobjectdef(def_to)^.is_class) then
  521. begin
  522. { void pointer also for delphi mode }
  523. if (m_delphi in aktmodeswitches) and
  524. is_voidpointer(def_from) then
  525. begin
  526. doconv:=tc_equal;
  527. b:=1;
  528. end
  529. else
  530. { nil is compatible with class instances }
  531. if (fromtreetype=niln) and (pobjectdef(def_to)^.is_class) then
  532. begin
  533. doconv:=tc_equal;
  534. b:=1;
  535. end;
  536. end;
  537. end;
  538. classrefdef :
  539. begin
  540. { class reference types }
  541. if (def_from^.deftype=classrefdef) then
  542. begin
  543. doconv:=tc_equal;
  544. if pobjectdef(pclassrefdef(def_from)^.pointertype.def)^.is_related(
  545. pobjectdef(pclassrefdef(def_to)^.pointertype.def)) then
  546. b:=1;
  547. end
  548. else
  549. { nil is compatible with class references }
  550. if (fromtreetype=niln) then
  551. begin
  552. doconv:=tc_equal;
  553. b:=1;
  554. end;
  555. end;
  556. filedef :
  557. begin
  558. { typed files are all equal to the abstract file type
  559. name TYPEDFILE in system.pp in is_equal in types.pas
  560. the problem is that it sholud be also compatible to FILE
  561. but this would leed to a problem for ASSIGN RESET and REWRITE
  562. when trying to find the good overloaded function !!
  563. so all file function are doubled in system.pp
  564. this is not very beautiful !!}
  565. if (def_from^.deftype=filedef) and
  566. (
  567. (
  568. (pfiledef(def_from)^.filetyp = ft_typed) and
  569. (pfiledef(def_to)^.filetyp = ft_typed) and
  570. (
  571. (pfiledef(def_from)^.typedfiletype.def = pdef(voiddef)) or
  572. (pfiledef(def_to)^.typedfiletype.def = pdef(voiddef))
  573. )
  574. ) or
  575. (
  576. (
  577. (pfiledef(def_from)^.filetyp = ft_untyped) and
  578. (pfiledef(def_to)^.filetyp = ft_typed)
  579. ) or
  580. (
  581. (pfiledef(def_from)^.filetyp = ft_typed) and
  582. (pfiledef(def_to)^.filetyp = ft_untyped)
  583. )
  584. )
  585. ) then
  586. begin
  587. doconv:=tc_equal;
  588. b:=1;
  589. end
  590. end;
  591. else
  592. begin
  593. { assignment overwritten ?? }
  594. if assignment_overloaded(def_from,def_to)<>nil then
  595. b:=2;
  596. end;
  597. end;
  598. isconvertable:=b;
  599. end;
  600. { ld is the left type definition
  601. rd the right type definition
  602. dd the result type definition or voiddef if unkown }
  603. function isbinaryoperatoroverloadable(ld, rd, dd : pdef;
  604. treetyp : tnodetype) : boolean;
  605. begin
  606. isbinaryoperatoroverloadable:=
  607. (treetyp=starstarn) or
  608. (ld^.deftype=recorddef) or
  609. (rd^.deftype=recorddef) or
  610. ((rd^.deftype=pointerdef) and
  611. not(is_pchar(rd) and
  612. (is_chararray(ld) or
  613. (ld^.deftype=stringdef) or
  614. (treetyp=addn))) and
  615. (not(ld^.deftype in [pointerdef,objectdef,classrefdef,procvardef]) or
  616. not (treetyp in [equaln,unequaln,gtn,gten,ltn,lten,subn])
  617. ) and
  618. (not is_integer(ld) or not (treetyp in [addn,subn]))
  619. ) or
  620. ((ld^.deftype=pointerdef) and
  621. not(is_pchar(ld) and
  622. (is_chararray(rd) or
  623. (rd^.deftype=stringdef) or
  624. (treetyp=addn))) and
  625. (not(rd^.deftype in [stringdef,pointerdef,objectdef,classrefdef,procvardef]) and
  626. ((not is_integer(rd) and (rd^.deftype<>objectdef)
  627. and (rd^.deftype<>classrefdef)) or
  628. not (treetyp in [equaln,unequaln,gtn,gten,ltn,lten,addn,subn])
  629. )
  630. )
  631. ) or
  632. { array def, but not mmx or chararray+[char,string,chararray] }
  633. ((ld^.deftype=arraydef) and
  634. not((cs_mmx in aktlocalswitches) and
  635. is_mmx_able_array(ld)) and
  636. not(is_chararray(ld) and
  637. (is_char(rd) or
  638. is_pchar(rd) or
  639. (rd^.deftype=stringdef) or
  640. is_chararray(rd)))
  641. ) or
  642. ((rd^.deftype=arraydef) and
  643. not((cs_mmx in aktlocalswitches) and
  644. is_mmx_able_array(rd)) and
  645. not(is_chararray(rd) and
  646. (is_char(ld) or
  647. is_pchar(ld) or
  648. (ld^.deftype=stringdef) or
  649. is_chararray(ld)))
  650. ) or
  651. { <> and = are defined for classes }
  652. ((ld^.deftype=objectdef) and
  653. (not(pobjectdef(ld)^.is_class) or
  654. not(treetyp in [equaln,unequaln])
  655. )
  656. ) or
  657. ((rd^.deftype=objectdef) and
  658. (not(pobjectdef(rd)^.is_class) or
  659. not(treetyp in [equaln,unequaln])
  660. )
  661. or
  662. { allow other operators that + on strings }
  663. (
  664. (is_char(rd) or
  665. is_pchar(rd) or
  666. (rd^.deftype=stringdef) or
  667. is_chararray(rd) or
  668. is_char(ld) or
  669. is_pchar(ld) or
  670. (ld^.deftype=stringdef) or
  671. is_chararray(ld)
  672. ) and
  673. not(treetyp in [addn,equaln,unequaln,gtn,gten,ltn,lten]) and
  674. not(is_pchar(ld) and
  675. (is_integer(rd) or (rd^.deftype=pointerdef)) and
  676. (treetyp=subn)
  677. )
  678. )
  679. );
  680. end;
  681. function isunaryoperatoroverloadable(rd,dd : pdef;
  682. treetyp : tnodetype) : boolean;
  683. begin
  684. isunaryoperatoroverloadable:=false;
  685. { what assignment overloading should be allowed ?? }
  686. if (treetyp=assignn) then
  687. begin
  688. isunaryoperatoroverloadable:=true;
  689. { this already get tbs0261 to fail
  690. isunaryoperatoroverloadable:=not is_equal(rd,dd); PM }
  691. end
  692. { should we force that rd and dd are equal ?? }
  693. else if (treetyp=subn { unaryminusn }) then
  694. begin
  695. isunaryoperatoroverloadable:=
  696. not is_integer(rd) and not (rd^.deftype=floatdef)
  697. {$ifdef SUPPORT_MMX}
  698. and not ((cs_mmx in aktlocalswitches) and
  699. is_mmx_able_array(rd))
  700. {$endif SUPPORT_MMX}
  701. ;
  702. end
  703. else if (treetyp=notn) then
  704. begin
  705. isunaryoperatoroverloadable:=not is_integer(rd) and not is_boolean(rd)
  706. {$ifdef SUPPORT_MMX}
  707. and not ((cs_mmx in aktlocalswitches) and
  708. is_mmx_able_array(rd))
  709. {$endif SUPPORT_MMX}
  710. ;
  711. end;
  712. end;
  713. function isoperatoracceptable(pf : pprocdef; optoken : ttoken) : boolean;
  714. var
  715. ld,rd,dd : pdef;
  716. i : longint;
  717. begin
  718. case pf^.parast^.symindex^.count of
  719. 2 : begin
  720. isoperatoracceptable:=false;
  721. for i:=1 to tok2nodes do
  722. if tok2node[i].tok=optoken then
  723. begin
  724. ld:=pvarsym(pf^.parast^.symindex^.first)^.vartype.def;
  725. rd:=pvarsym(pf^.parast^.symindex^.first^.indexnext)^.vartype.def;
  726. dd:=pf^.rettype.def;
  727. isoperatoracceptable:=
  728. tok2node[i].op_overloading_supported and
  729. isbinaryoperatoroverloadable(ld,rd,dd,tok2node[i].nod);
  730. break;
  731. end;
  732. end;
  733. 1 : begin
  734. rd:=pvarsym(pf^.parast^.symindex^.first)^.vartype.def;
  735. dd:=pf^.rettype.def;
  736. for i:=1 to tok2nodes do
  737. if tok2node[i].tok=optoken then
  738. begin
  739. isoperatoracceptable:=
  740. tok2node[i].op_overloading_supported and
  741. isunaryoperatoroverloadable(rd,dd,tok2node[i].nod);
  742. break;
  743. end;
  744. end;
  745. else
  746. isoperatoracceptable:=false;
  747. end;
  748. end;
  749. {****************************************************************************
  750. Register Calculation
  751. ****************************************************************************}
  752. { marks an lvalue as "unregable" }
  753. procedure make_not_regable(p : tnode);
  754. begin
  755. case p.nodetype of
  756. typeconvn :
  757. make_not_regable(ttypeconvnode(p).left);
  758. loadn :
  759. if tloadnode(p).symtableentry^.typ=varsym then
  760. pvarsym(tloadnode(p).symtableentry)^.varoptions:=pvarsym(tloadnode(p).symtableentry)^.varoptions-[vo_regable,vo_fpuregable];
  761. end;
  762. end;
  763. { calculates the needed registers for a binary operator }
  764. procedure calcregisters(p : tbinarynode;r32,fpu,mmx : word);
  765. begin
  766. p.left_right_max;
  767. { Only when the difference between the left and right registers < the
  768. wanted registers allocate the amount of registers }
  769. if assigned(p.left) then
  770. begin
  771. if assigned(p.right) then
  772. begin
  773. if (abs(p.left.registers32-p.right.registers32)<r32) then
  774. inc(p.registers32,r32);
  775. if (abs(p.left.registersfpu-p.right.registersfpu)<fpu) then
  776. inc(p.registersfpu,fpu);
  777. {$ifdef SUPPORT_MMX}
  778. if (abs(p.left.registersmmx-p.right.registersmmx)<mmx) then
  779. inc(p.registersmmx,mmx);
  780. {$endif SUPPORT_MMX}
  781. { the following is a little bit guessing but I think }
  782. { it's the only way to solve same internalerrors: }
  783. { if the left and right node both uses registers }
  784. { and return a mem location, but the current node }
  785. { doesn't use an integer register we get probably }
  786. { trouble when restoring a node }
  787. if (p.left.registers32=p.right.registers32) and
  788. (p.registers32=p.left.registers32) and
  789. (p.registers32>0) and
  790. (p.left.location.loc in [LOC_REFERENCE,LOC_MEM]) and
  791. (p.right.location.loc in [LOC_REFERENCE,LOC_MEM]) then
  792. inc(p.registers32);
  793. end
  794. else
  795. begin
  796. if (p.left.registers32<r32) then
  797. inc(p.registers32,r32);
  798. if (p.left.registersfpu<fpu) then
  799. inc(p.registersfpu,fpu);
  800. {$ifdef SUPPORT_MMX}
  801. if (p.left.registersmmx<mmx) then
  802. inc(p.registersmmx,mmx);
  803. {$endif SUPPORT_MMX}
  804. end;
  805. end;
  806. { error CGMessage, if more than 8 floating point }
  807. { registers are needed }
  808. if p.registersfpu>8 then
  809. CGMessage(cg_e_too_complex_expr);
  810. end;
  811. {****************************************************************************
  812. Subroutine Handling
  813. ****************************************************************************}
  814. { protected field handling
  815. protected field can not appear in
  816. var parameters of function !!
  817. this can only be done after we have determined the
  818. overloaded function
  819. this is the reason why it is not in the parser, PM }
  820. procedure test_protected_sym(sym : psym);
  821. begin
  822. if (sp_protected in sym^.symoptions) and
  823. ((sym^.owner^.symtabletype=unitsymtable) or
  824. ((sym^.owner^.symtabletype=objectsymtable) and
  825. (pobjectdef(sym^.owner^.defowner)^.owner^.symtabletype=unitsymtable))
  826. ) then
  827. CGMessage(parser_e_cant_access_protected_member);
  828. end;
  829. procedure test_protected(p : tnode);
  830. begin
  831. case p.nodetype of
  832. loadn : test_protected_sym(tloadnode(p).symtableentry);
  833. typeconvn : test_protected(ttypeconvnode(p).left);
  834. derefn : test_protected(tderefnode(p).left);
  835. subscriptn : begin
  836. { test_protected(p.left);
  837. Is a field of a protected var
  838. also protected ??? PM }
  839. test_protected_sym(tsubscriptnode(p).vs);
  840. end;
  841. end;
  842. end;
  843. function valid_for_formal_var(p : tnode) : boolean;
  844. var
  845. v : boolean;
  846. begin
  847. case p.nodetype of
  848. loadn :
  849. v:=(tloadnode(p).symtableentry^.typ in [typedconstsym,varsym]);
  850. typeconvn :
  851. v:=valid_for_formal_var(ttypeconvnode(p).left);
  852. derefn,
  853. subscriptn,
  854. vecn,
  855. funcretn,
  856. selfn :
  857. v:=true;
  858. calln : { procvars are callnodes first }
  859. v:=assigned(tcallnode(p).right) and not assigned(tcallnode(p).left);
  860. addrn :
  861. begin
  862. { addrn is not allowed as this generate a constant value,
  863. but a tp procvar are allowed (PFV) }
  864. if nf_procvarload in p.flags then
  865. v:=true
  866. else
  867. v:=false;
  868. end;
  869. else
  870. v:=false;
  871. end;
  872. valid_for_formal_var:=v;
  873. end;
  874. function valid_for_formal_const(p : tnode) : boolean;
  875. var
  876. v : boolean;
  877. begin
  878. { p must have been firstpass'd before }
  879. { accept about anything but not a statement ! }
  880. case p.nodetype of
  881. calln,
  882. statementn,
  883. addrn :
  884. begin
  885. { addrn is not allowed as this generate a constant value,
  886. but a tp procvar are allowed (PFV) }
  887. if nf_procvarload in p.flags then
  888. v:=true
  889. else
  890. v:=false;
  891. end;
  892. else
  893. v:=true;
  894. end;
  895. valid_for_formal_const:=v;
  896. end;
  897. function is_procsym_load(p:tnode):boolean;
  898. begin
  899. is_procsym_load:=((p.nodetype=loadn) and (tloadnode(p).symtableentry^.typ=procsym)) or
  900. ((p.nodetype=addrn) and (taddrnode(p).left.nodetype=loadn)
  901. and (tloadnode(taddrnode(p).left).symtableentry^.typ=procsym)) ;
  902. end;
  903. { change a proc call to a procload for assignment to a procvar }
  904. { this can only happen for proc/function without arguments }
  905. function is_procsym_call(p:tnode):boolean;
  906. begin
  907. is_procsym_call:=(p.nodetype=calln) and (tcallnode(p).left=nil) and
  908. (((tcallnode(p).symtableprocentry^.typ=procsym) and (tcallnode(p).right=nil)) or
  909. (assigned(tcallnode(p).right) and (tcallnode(tcallnode(p).right).symtableprocentry^.typ=varsym)));
  910. end;
  911. function assignment_overloaded(from_def,to_def : pdef) : pprocdef;
  912. var
  913. passproc : pprocdef;
  914. convtyp : tconverttype;
  915. begin
  916. assignment_overloaded:=nil;
  917. if assigned(overloaded_operators[_assignment]) then
  918. passproc:=overloaded_operators[_assignment]^.definition
  919. else
  920. exit;
  921. while passproc<>nil do
  922. begin
  923. if is_equal(passproc^.rettype.def,to_def) and
  924. (is_equal(pparaitem(passproc^.para^.first)^.paratype.def,from_def) or
  925. (isconvertable(from_def,pparaitem(passproc^.para^.first)^.paratype.def,convtyp,ordconstn,false)=1)) then
  926. begin
  927. assignment_overloaded:=passproc;
  928. break;
  929. end;
  930. passproc:=passproc^.nextoverloaded;
  931. end;
  932. end;
  933. { local routines can't be assigned to procvars }
  934. procedure test_local_to_procvar(from_def:pprocvardef;to_def:pdef);
  935. begin
  936. if (from_def^.symtablelevel>1) and (to_def^.deftype=procvardef) then
  937. CGMessage(type_e_cannot_local_proc_to_procvar);
  938. end;
  939. function valid_for_assign(p:tnode;allowprop:boolean):boolean;
  940. var
  941. hp : tnode;
  942. gotwith,
  943. gotsubscript,
  944. gotpointer,
  945. gotclass,
  946. gotderef : boolean;
  947. begin
  948. valid_for_assign:=false;
  949. gotsubscript:=false;
  950. gotderef:=false;
  951. gotclass:=false;
  952. gotpointer:=false;
  953. gotwith:=false;
  954. hp:=p;
  955. while assigned(hp) do
  956. begin
  957. { property allowed? calln has a property check itself }
  958. if (not allowprop) and
  959. (nf_isproperty in hp.flags) and
  960. (hp.nodetype<>calln) then
  961. begin
  962. CGMessagePos(hp.fileinfo,type_e_argument_cant_be_assigned);
  963. exit;
  964. end;
  965. case hp.nodetype of
  966. derefn :
  967. begin
  968. gotderef:=true;
  969. hp:=tderefnode(hp).left;
  970. end;
  971. typeconvn :
  972. begin
  973. case hp.resulttype^.deftype of
  974. pointerdef :
  975. gotpointer:=true;
  976. objectdef :
  977. gotclass:=pobjectdef(hp.resulttype)^.is_class;
  978. classrefdef :
  979. gotclass:=true;
  980. arraydef :
  981. begin
  982. { pointer -> array conversion is done then we need to see it
  983. as a deref, because a ^ is then not required anymore }
  984. if (ttypeconvnode(hp).left.resulttype^.deftype=pointerdef) then
  985. gotderef:=true;
  986. end;
  987. end;
  988. hp:=ttypeconvnode(hp).left;
  989. end;
  990. vecn,
  991. asn :
  992. hp:=tunarynode(hp).left;
  993. subscriptn :
  994. begin
  995. gotsubscript:=true;
  996. hp:=tsubscriptnode(hp).left;
  997. end;
  998. subn,
  999. addn :
  1000. begin
  1001. { Allow add/sub operators on a pointer, or an integer
  1002. and a pointer typecast and deref has been found }
  1003. if (hp.resulttype^.deftype=pointerdef) or
  1004. (is_integer(hp.resulttype) and gotpointer and gotderef) then
  1005. valid_for_assign:=true
  1006. else
  1007. CGMessagePos(hp.fileinfo,type_e_variable_id_expected);
  1008. exit;
  1009. end;
  1010. addrn :
  1011. begin
  1012. if not(gotderef) and
  1013. not(nf_procvarload in hp.flags) then
  1014. CGMessagePos(hp.fileinfo,type_e_no_assign_to_addr);
  1015. exit;
  1016. end;
  1017. selfn,
  1018. funcretn :
  1019. begin
  1020. valid_for_assign:=true;
  1021. exit;
  1022. end;
  1023. calln :
  1024. begin
  1025. { check return type }
  1026. case hp.resulttype^.deftype of
  1027. pointerdef :
  1028. gotpointer:=true;
  1029. objectdef :
  1030. gotclass:=pobjectdef(hp.resulttype)^.is_class;
  1031. recorddef, { handle record like class it needs a subscription }
  1032. classrefdef :
  1033. gotclass:=true;
  1034. end;
  1035. { 1. if it returns a pointer and we've found a deref,
  1036. 2. if it returns a class or record and a subscription or with is found,
  1037. 3. property is allowed }
  1038. if (gotpointer and gotderef) or
  1039. (gotclass and (gotsubscript or gotwith)) or
  1040. ((nf_isproperty in hp.flags) and allowprop) then
  1041. valid_for_assign:=true
  1042. else
  1043. CGMessagePos(hp.fileinfo,type_e_argument_cant_be_assigned);
  1044. exit;
  1045. end;
  1046. loadn :
  1047. begin
  1048. case tloadnode(hp).symtableentry^.typ of
  1049. absolutesym,
  1050. varsym :
  1051. begin
  1052. if (pvarsym(tloadnode(hp).symtableentry)^.varspez=vs_const) then
  1053. begin
  1054. { allow p^:= constructions with p is const parameter }
  1055. if gotderef then
  1056. valid_for_assign:=true
  1057. else
  1058. CGMessagePos(tloadnode(hp).fileinfo,type_e_no_assign_to_const);
  1059. exit;
  1060. end;
  1061. { Are we at a with symtable, then we need to process the
  1062. withrefnode also to check for maybe a const load }
  1063. if (tloadnode(hp).symtable^.symtabletype=withsymtable) then
  1064. begin
  1065. { continue with processing the withref node }
  1066. hp:=tnode(pwithsymtable(tloadnode(hp).symtable)^.withrefnode);
  1067. gotwith:=true;
  1068. end
  1069. else
  1070. begin
  1071. { set the assigned flag for varsyms }
  1072. if (pvarsym(tloadnode(hp).symtableentry)^.varstate=vs_declared) then
  1073. pvarsym(tloadnode(hp).symtableentry)^.varstate:=vs_assigned;
  1074. valid_for_assign:=true;
  1075. exit;
  1076. end;
  1077. end;
  1078. funcretsym,
  1079. typedconstsym :
  1080. begin
  1081. valid_for_assign:=true;
  1082. exit;
  1083. end;
  1084. end;
  1085. end;
  1086. else
  1087. begin
  1088. CGMessagePos(hp.fileinfo,type_e_variable_id_expected);
  1089. exit;
  1090. end;
  1091. end;
  1092. end;
  1093. end;
  1094. {$else cg11}
  1095. {****************************************************************************
  1096. Convert
  1097. ****************************************************************************}
  1098. { Returns:
  1099. 0 - Not convertable
  1100. 1 - Convertable
  1101. 2 - Convertable, but not first choice }
  1102. function isconvertable(def_from,def_to : pdef;
  1103. var doconv : tconverttype;fromtreetype : ttreetyp;
  1104. explicit : boolean) : byte;
  1105. { Tbasetype: uauto,uvoid,uchar,
  1106. u8bit,u16bit,u32bit,
  1107. s8bit,s16bit,s32,
  1108. bool8bit,bool16bit,bool32bit,
  1109. u64bit,s64bitint }
  1110. type
  1111. tbasedef=(bvoid,bchar,bint,bbool);
  1112. const
  1113. basedeftbl:array[tbasetype] of tbasedef =
  1114. (bvoid,bvoid,bchar,
  1115. bint,bint,bint,
  1116. bint,bint,bint,
  1117. bbool,bbool,bbool,bint,bint,bchar);
  1118. basedefconverts : array[tbasedef,tbasedef] of tconverttype =
  1119. ((tc_not_possible,tc_not_possible,tc_not_possible,tc_not_possible),
  1120. (tc_not_possible,tc_equal,tc_not_possible,tc_not_possible),
  1121. (tc_not_possible,tc_not_possible,tc_int_2_int,tc_int_2_bool),
  1122. (tc_not_possible,tc_not_possible,tc_bool_2_int,tc_bool_2_bool));
  1123. var
  1124. b : byte;
  1125. hd1,hd2 : pdef;
  1126. hct : tconverttype;
  1127. begin
  1128. { safety check }
  1129. if not(assigned(def_from) and assigned(def_to)) then
  1130. begin
  1131. isconvertable:=0;
  1132. exit;
  1133. end;
  1134. { tp7 procvar def support, in tp7 a procvar is always called, if the
  1135. procvar is passed explicit a addrn would be there }
  1136. if (m_tp_procvar in aktmodeswitches) and
  1137. (def_from^.deftype=procvardef) and
  1138. (fromtreetype=loadn) then
  1139. begin
  1140. def_from:=pprocvardef(def_from)^.rettype.def;
  1141. end;
  1142. { we walk the wanted (def_to) types and check then the def_from
  1143. types if there is a conversion possible }
  1144. b:=0;
  1145. case def_to^.deftype of
  1146. orddef :
  1147. begin
  1148. case def_from^.deftype of
  1149. orddef :
  1150. begin
  1151. doconv:=basedefconverts[basedeftbl[porddef(def_from)^.typ],basedeftbl[porddef(def_to)^.typ]];
  1152. b:=1;
  1153. if (doconv=tc_not_possible) or
  1154. ((doconv=tc_int_2_bool) and
  1155. (not explicit) and
  1156. (not is_boolean(def_from))) or
  1157. ((doconv=tc_bool_2_int) and
  1158. (not explicit) and
  1159. (not is_boolean(def_to))) then
  1160. b:=0;
  1161. end;
  1162. enumdef :
  1163. begin
  1164. { needed for char(enum) }
  1165. if explicit then
  1166. begin
  1167. doconv:=tc_int_2_int;
  1168. b:=1;
  1169. end;
  1170. end;
  1171. end;
  1172. end;
  1173. stringdef :
  1174. begin
  1175. case def_from^.deftype of
  1176. stringdef :
  1177. begin
  1178. doconv:=tc_string_2_string;
  1179. b:=1;
  1180. end;
  1181. orddef :
  1182. begin
  1183. { char to string}
  1184. if is_char(def_from) then
  1185. begin
  1186. doconv:=tc_char_2_string;
  1187. b:=1;
  1188. end;
  1189. end;
  1190. arraydef :
  1191. begin
  1192. { array of char to string, the length check is done by the firstpass of this node }
  1193. if is_chararray(def_from) then
  1194. begin
  1195. doconv:=tc_chararray_2_string;
  1196. if (not(cs_ansistrings in aktlocalswitches) and
  1197. is_shortstring(def_to)) or
  1198. ((cs_ansistrings in aktlocalswitches) and
  1199. is_ansistring(def_to)) then
  1200. b:=1
  1201. else
  1202. b:=2;
  1203. end;
  1204. end;
  1205. pointerdef :
  1206. begin
  1207. { pchar can be assigned to short/ansistrings,
  1208. but not in tp7 compatible mode }
  1209. if is_pchar(def_from) and not(m_tp7 in aktmodeswitches) then
  1210. begin
  1211. doconv:=tc_pchar_2_string;
  1212. b:=1;
  1213. end;
  1214. end;
  1215. end;
  1216. end;
  1217. floatdef :
  1218. begin
  1219. case def_from^.deftype of
  1220. orddef :
  1221. begin { ordinal to real }
  1222. if is_integer(def_from) then
  1223. begin
  1224. if pfloatdef(def_to)^.typ=f32bit then
  1225. doconv:=tc_int_2_fix
  1226. else
  1227. doconv:=tc_int_2_real;
  1228. b:=1;
  1229. end;
  1230. end;
  1231. floatdef :
  1232. begin { 2 float types ? }
  1233. if pfloatdef(def_from)^.typ=pfloatdef(def_to)^.typ then
  1234. doconv:=tc_equal
  1235. else
  1236. begin
  1237. if pfloatdef(def_from)^.typ=f32bit then
  1238. doconv:=tc_fix_2_real
  1239. else
  1240. if pfloatdef(def_to)^.typ=f32bit then
  1241. doconv:=tc_real_2_fix
  1242. else
  1243. doconv:=tc_real_2_real;
  1244. end;
  1245. b:=1;
  1246. end;
  1247. end;
  1248. end;
  1249. enumdef :
  1250. begin
  1251. if (def_from^.deftype=enumdef) then
  1252. begin
  1253. hd1:=def_from;
  1254. while assigned(penumdef(hd1)^.basedef) do
  1255. hd1:=penumdef(hd1)^.basedef;
  1256. hd2:=def_to;
  1257. while assigned(penumdef(hd2)^.basedef) do
  1258. hd2:=penumdef(hd2)^.basedef;
  1259. if (hd1=hd2) then
  1260. begin
  1261. b:=1;
  1262. { because of packenum they can have different sizes! (JM) }
  1263. doconv:=tc_int_2_int;
  1264. end;
  1265. end;
  1266. end;
  1267. arraydef :
  1268. begin
  1269. { open array is also compatible with a single element of its base type }
  1270. if is_open_array(def_to) and
  1271. is_equal(parraydef(def_to)^.elementtype.def,def_from) then
  1272. begin
  1273. doconv:=tc_equal;
  1274. b:=1;
  1275. end
  1276. else
  1277. begin
  1278. case def_from^.deftype of
  1279. arraydef :
  1280. begin
  1281. { array constructor -> open array }
  1282. if is_open_array(def_to) and
  1283. is_array_constructor(def_from) then
  1284. begin
  1285. if is_void(parraydef(def_from)^.elementtype.def) or
  1286. is_equal(parraydef(def_to)^.elementtype.def,parraydef(def_from)^.elementtype.def) then
  1287. begin
  1288. doconv:=tc_equal;
  1289. b:=1;
  1290. end
  1291. else
  1292. if isconvertable(parraydef(def_from)^.elementtype.def,
  1293. parraydef(def_to)^.elementtype.def,hct,arrayconstructn,false)<>0 then
  1294. begin
  1295. doconv:=hct;
  1296. b:=2;
  1297. end;
  1298. end;
  1299. end;
  1300. pointerdef :
  1301. begin
  1302. if is_zero_based_array(def_to) and
  1303. is_equal(ppointerdef(def_from)^.pointertype.def,parraydef(def_to)^.elementtype.def) then
  1304. begin
  1305. doconv:=tc_pointer_2_array;
  1306. b:=1;
  1307. end;
  1308. end;
  1309. stringdef :
  1310. begin
  1311. { string to array of char}
  1312. if (not(is_special_array(def_to)) or is_open_array(def_to)) and
  1313. is_equal(parraydef(def_to)^.elementtype.def,cchardef) then
  1314. begin
  1315. doconv:=tc_string_2_chararray;
  1316. b:=1;
  1317. end;
  1318. end;
  1319. end;
  1320. end;
  1321. end;
  1322. pointerdef :
  1323. begin
  1324. case def_from^.deftype of
  1325. stringdef :
  1326. begin
  1327. { string constant (which can be part of array constructor)
  1328. to zero terminated string constant }
  1329. if (fromtreetype in [arrayconstructn,stringconstn]) and
  1330. is_pchar(def_to) then
  1331. begin
  1332. doconv:=tc_cstring_2_pchar;
  1333. b:=1;
  1334. end;
  1335. end;
  1336. orddef :
  1337. begin
  1338. { char constant to zero terminated string constant }
  1339. if (fromtreetype=ordconstn) then
  1340. begin
  1341. if is_equal(def_from,cchardef) and
  1342. is_pchar(def_to) then
  1343. begin
  1344. doconv:=tc_cchar_2_pchar;
  1345. b:=1;
  1346. end
  1347. else
  1348. if is_integer(def_from) then
  1349. begin
  1350. doconv:=tc_cord_2_pointer;
  1351. b:=1;
  1352. end;
  1353. end;
  1354. end;
  1355. arraydef :
  1356. begin
  1357. { chararray to pointer }
  1358. if is_zero_based_array(def_from) and
  1359. is_equal(parraydef(def_from)^.elementtype.def,ppointerdef(def_to)^.pointertype.def) then
  1360. begin
  1361. doconv:=tc_array_2_pointer;
  1362. b:=1;
  1363. end;
  1364. end;
  1365. pointerdef :
  1366. begin
  1367. { child class pointer can be assigned to anchestor pointers }
  1368. if (
  1369. (ppointerdef(def_from)^.pointertype.def^.deftype=objectdef) and
  1370. (ppointerdef(def_to)^.pointertype.def^.deftype=objectdef) and
  1371. pobjectdef(ppointerdef(def_from)^.pointertype.def)^.is_related(
  1372. pobjectdef(ppointerdef(def_to)^.pointertype.def))
  1373. ) or
  1374. { all pointers can be assigned to void-pointer }
  1375. is_equal(ppointerdef(def_to)^.pointertype.def,voiddef) or
  1376. { in my opnion, is this not clean pascal }
  1377. { well, but it's handy to use, it isn't ? (FK) }
  1378. is_equal(ppointerdef(def_from)^.pointertype.def,voiddef) then
  1379. begin
  1380. doconv:=tc_equal;
  1381. b:=1;
  1382. end;
  1383. end;
  1384. procvardef :
  1385. begin
  1386. { procedure variable can be assigned to an void pointer }
  1387. { Not anymore. Use the @ operator now.}
  1388. if not(m_tp_procvar in aktmodeswitches) and
  1389. (ppointerdef(def_to)^.pointertype.def^.deftype=orddef) and
  1390. (porddef(ppointerdef(def_to)^.pointertype.def)^.typ=uvoid) then
  1391. begin
  1392. doconv:=tc_equal;
  1393. b:=1;
  1394. end;
  1395. end;
  1396. classrefdef,
  1397. objectdef :
  1398. begin
  1399. { class types and class reference type
  1400. can be assigned to void pointers }
  1401. if (
  1402. ((def_from^.deftype=objectdef) and pobjectdef(def_from)^.is_class) or
  1403. (def_from^.deftype=classrefdef)
  1404. ) and
  1405. (ppointerdef(def_to)^.pointertype.def^.deftype=orddef) and
  1406. (porddef(ppointerdef(def_to)^.pointertype.def)^.typ=uvoid) then
  1407. begin
  1408. doconv:=tc_equal;
  1409. b:=1;
  1410. end;
  1411. end;
  1412. end;
  1413. end;
  1414. setdef :
  1415. begin
  1416. { automatic arrayconstructor -> set conversion }
  1417. if is_array_constructor(def_from) then
  1418. begin
  1419. doconv:=tc_arrayconstructor_2_set;
  1420. b:=1;
  1421. end;
  1422. end;
  1423. procvardef :
  1424. begin
  1425. { proc -> procvar }
  1426. if (def_from^.deftype=procdef) then
  1427. begin
  1428. doconv:=tc_proc_2_procvar;
  1429. if proc_to_procvar_equal(pprocdef(def_from),pprocvardef(def_to)) then
  1430. b:=1;
  1431. end
  1432. else
  1433. { for example delphi allows the assignement from pointers }
  1434. { to procedure variables }
  1435. if (m_pointer_2_procedure in aktmodeswitches) and
  1436. (def_from^.deftype=pointerdef) and
  1437. (ppointerdef(def_from)^.pointertype.def^.deftype=orddef) and
  1438. (porddef(ppointerdef(def_from)^.pointertype.def)^.typ=uvoid) then
  1439. begin
  1440. doconv:=tc_equal;
  1441. b:=1;
  1442. end
  1443. else
  1444. { nil is compatible with procvars }
  1445. if (fromtreetype=niln) then
  1446. begin
  1447. doconv:=tc_equal;
  1448. b:=1;
  1449. end;
  1450. end;
  1451. objectdef :
  1452. begin
  1453. { object pascal objects }
  1454. if (def_from^.deftype=objectdef) {and
  1455. pobjectdef(def_from)^.isclass and pobjectdef(def_to)^.isclass }then
  1456. begin
  1457. doconv:=tc_equal;
  1458. if pobjectdef(def_from)^.is_related(pobjectdef(def_to)) then
  1459. b:=1;
  1460. end
  1461. else
  1462. { Class specific }
  1463. if (pobjectdef(def_to)^.is_class) then
  1464. begin
  1465. { void pointer also for delphi mode }
  1466. if (m_delphi in aktmodeswitches) and
  1467. is_voidpointer(def_from) then
  1468. begin
  1469. doconv:=tc_equal;
  1470. b:=1;
  1471. end
  1472. else
  1473. { nil is compatible with class instances }
  1474. if (fromtreetype=niln) and (pobjectdef(def_to)^.is_class) then
  1475. begin
  1476. doconv:=tc_equal;
  1477. b:=1;
  1478. end;
  1479. end;
  1480. end;
  1481. classrefdef :
  1482. begin
  1483. { class reference types }
  1484. if (def_from^.deftype=classrefdef) then
  1485. begin
  1486. doconv:=tc_equal;
  1487. if pobjectdef(pclassrefdef(def_from)^.pointertype.def)^.is_related(
  1488. pobjectdef(pclassrefdef(def_to)^.pointertype.def)) then
  1489. b:=1;
  1490. end
  1491. else
  1492. { nil is compatible with class references }
  1493. if (fromtreetype=niln) then
  1494. begin
  1495. doconv:=tc_equal;
  1496. b:=1;
  1497. end;
  1498. end;
  1499. filedef :
  1500. begin
  1501. { typed files are all equal to the abstract file type
  1502. name TYPEDFILE in system.pp in is_equal in types.pas
  1503. the problem is that it sholud be also compatible to FILE
  1504. but this would leed to a problem for ASSIGN RESET and REWRITE
  1505. when trying to find the good overloaded function !!
  1506. so all file function are doubled in system.pp
  1507. this is not very beautiful !!}
  1508. if (def_from^.deftype=filedef) and
  1509. (
  1510. (
  1511. (pfiledef(def_from)^.filetyp = ft_typed) and
  1512. (pfiledef(def_to)^.filetyp = ft_typed) and
  1513. (
  1514. (pfiledef(def_from)^.typedfiletype.def = pdef(voiddef)) or
  1515. (pfiledef(def_to)^.typedfiletype.def = pdef(voiddef))
  1516. )
  1517. ) or
  1518. (
  1519. (
  1520. (pfiledef(def_from)^.filetyp = ft_untyped) and
  1521. (pfiledef(def_to)^.filetyp = ft_typed)
  1522. ) or
  1523. (
  1524. (pfiledef(def_from)^.filetyp = ft_typed) and
  1525. (pfiledef(def_to)^.filetyp = ft_untyped)
  1526. )
  1527. )
  1528. ) then
  1529. begin
  1530. doconv:=tc_equal;
  1531. b:=1;
  1532. end
  1533. end;
  1534. else
  1535. begin
  1536. { assignment overwritten ?? }
  1537. if assignment_overloaded(def_from,def_to)<>nil then
  1538. b:=2;
  1539. end;
  1540. end;
  1541. isconvertable:=b;
  1542. end;
  1543. { ld is the left type definition
  1544. rd the right type definition
  1545. dd the result type definition or voiddef if unkown }
  1546. function isbinaryoperatoroverloadable(ld, rd, dd : pdef;
  1547. treetyp : ttreetyp) : boolean;
  1548. begin
  1549. isbinaryoperatoroverloadable:=
  1550. (treetyp=starstarn) or
  1551. (ld^.deftype=recorddef) or
  1552. (rd^.deftype=recorddef) or
  1553. ((rd^.deftype=pointerdef) and
  1554. not(is_pchar(rd) and
  1555. (is_chararray(ld) or
  1556. (ld^.deftype=stringdef) or
  1557. (treetyp=addn))) and
  1558. (not(ld^.deftype in [pointerdef,objectdef,classrefdef,procvardef]) or
  1559. not (treetyp in [equaln,unequaln,gtn,gten,ltn,lten,subn])
  1560. ) and
  1561. (not is_integer(ld) or not (treetyp in [addn,subn]))
  1562. ) or
  1563. ((ld^.deftype=pointerdef) and
  1564. not(is_pchar(ld) and
  1565. (is_chararray(rd) or
  1566. (rd^.deftype=stringdef) or
  1567. (treetyp=addn))) and
  1568. (not(rd^.deftype in [stringdef,pointerdef,objectdef,classrefdef,procvardef]) and
  1569. ((not is_integer(rd) and (rd^.deftype<>objectdef)
  1570. and (rd^.deftype<>classrefdef)) or
  1571. not (treetyp in [equaln,unequaln,gtn,gten,ltn,lten,addn,subn])
  1572. )
  1573. )
  1574. ) or
  1575. { array def, but not mmx or chararray+[char,string,chararray] }
  1576. ((ld^.deftype=arraydef) and
  1577. not((cs_mmx in aktlocalswitches) and
  1578. is_mmx_able_array(ld)) and
  1579. not(is_chararray(ld) and
  1580. (is_char(rd) or
  1581. is_pchar(rd) or
  1582. (rd^.deftype=stringdef) or
  1583. is_chararray(rd)))
  1584. ) or
  1585. ((rd^.deftype=arraydef) and
  1586. not((cs_mmx in aktlocalswitches) and
  1587. is_mmx_able_array(rd)) and
  1588. not(is_chararray(rd) and
  1589. (is_char(ld) or
  1590. is_pchar(ld) or
  1591. (ld^.deftype=stringdef) or
  1592. is_chararray(ld)))
  1593. ) or
  1594. { <> and = are defined for classes }
  1595. ((ld^.deftype=objectdef) and
  1596. (not(pobjectdef(ld)^.is_class) or
  1597. not(treetyp in [equaln,unequaln])
  1598. )
  1599. ) or
  1600. ((rd^.deftype=objectdef) and
  1601. (not(pobjectdef(rd)^.is_class) or
  1602. not(treetyp in [equaln,unequaln])
  1603. )
  1604. or
  1605. { allow other operators that + on strings }
  1606. (
  1607. (is_char(rd) or
  1608. is_pchar(rd) or
  1609. (rd^.deftype=stringdef) or
  1610. is_chararray(rd) or
  1611. is_char(ld) or
  1612. is_pchar(ld) or
  1613. (ld^.deftype=stringdef) or
  1614. is_chararray(ld)
  1615. ) and
  1616. not(treetyp in [addn,equaln,unequaln,gtn,gten,ltn,lten]) and
  1617. not(is_pchar(ld) and
  1618. (is_integer(rd) or (rd^.deftype=pointerdef)) and
  1619. (treetyp=subn)
  1620. )
  1621. )
  1622. );
  1623. end;
  1624. function isunaryoperatoroverloadable(rd,dd : pdef;
  1625. treetyp : ttreetyp) : boolean;
  1626. begin
  1627. isunaryoperatoroverloadable:=false;
  1628. { what assignment overloading should be allowed ?? }
  1629. if (treetyp=assignn) then
  1630. begin
  1631. isunaryoperatoroverloadable:=true;
  1632. { this already get tbs0261 to fail
  1633. isunaryoperatoroverloadable:=not is_equal(rd,dd); PM }
  1634. end
  1635. { should we force that rd and dd are equal ?? }
  1636. else if (treetyp=subn { unaryminusn }) then
  1637. begin
  1638. isunaryoperatoroverloadable:=
  1639. not is_integer(rd) and not (rd^.deftype=floatdef)
  1640. {$ifdef SUPPORT_MMX}
  1641. and not ((cs_mmx in aktlocalswitches) and
  1642. is_mmx_able_array(rd))
  1643. {$endif SUPPORT_MMX}
  1644. ;
  1645. end
  1646. else if (treetyp=notn) then
  1647. begin
  1648. isunaryoperatoroverloadable:=not is_integer(rd) and not is_boolean(rd)
  1649. {$ifdef SUPPORT_MMX}
  1650. and not ((cs_mmx in aktlocalswitches) and
  1651. is_mmx_able_array(rd))
  1652. {$endif SUPPORT_MMX}
  1653. ;
  1654. end;
  1655. end;
  1656. function isoperatoracceptable(pf : pprocdef; optoken : ttoken) : boolean;
  1657. var
  1658. ld,rd,dd : pdef;
  1659. i : longint;
  1660. begin
  1661. case pf^.parast^.symindex^.count of
  1662. 2 : begin
  1663. isoperatoracceptable:=false;
  1664. for i:=1 to tok2nodes do
  1665. if tok2node[i].tok=optoken then
  1666. begin
  1667. ld:=pvarsym(pf^.parast^.symindex^.first)^.vartype.def;
  1668. rd:=pvarsym(pf^.parast^.symindex^.first^.indexnext)^.vartype.def;
  1669. dd:=pf^.rettype.def;
  1670. isoperatoracceptable:=
  1671. tok2node[i].op_overloading_supported and
  1672. isbinaryoperatoroverloadable(ld,rd,dd,tok2node[i].nod);
  1673. break;
  1674. end;
  1675. end;
  1676. 1 : begin
  1677. rd:=pvarsym(pf^.parast^.symindex^.first)^.vartype.def;
  1678. dd:=pf^.rettype.def;
  1679. for i:=1 to tok2nodes do
  1680. if tok2node[i].tok=optoken then
  1681. begin
  1682. isoperatoracceptable:=
  1683. tok2node[i].op_overloading_supported and
  1684. isunaryoperatoroverloadable(rd,dd,tok2node[i].nod);
  1685. break;
  1686. end;
  1687. end;
  1688. else
  1689. isoperatoracceptable:=false;
  1690. end;
  1691. end;
  1692. {****************************************************************************
  1693. Register Calculation
  1694. ****************************************************************************}
  1695. { marks an lvalue as "unregable" }
  1696. procedure make_not_regable(p : ptree);
  1697. begin
  1698. case p^.treetype of
  1699. typeconvn :
  1700. make_not_regable(p^.left);
  1701. loadn :
  1702. if p^.symtableentry^.typ=varsym then
  1703. pvarsym(p^.symtableentry)^.varoptions:=pvarsym(p^.symtableentry)^.varoptions-[vo_regable,vo_fpuregable];
  1704. end;
  1705. end;
  1706. procedure left_right_max(p : ptree);
  1707. begin
  1708. if assigned(p^.left) then
  1709. begin
  1710. if assigned(p^.right) then
  1711. begin
  1712. p^.registers32:=max(p^.left^.registers32,p^.right^.registers32);
  1713. p^.registersfpu:=max(p^.left^.registersfpu,p^.right^.registersfpu);
  1714. {$ifdef SUPPORT_MMX}
  1715. p^.registersmmx:=max(p^.left^.registersmmx,p^.right^.registersmmx);
  1716. {$endif SUPPORT_MMX}
  1717. end
  1718. else
  1719. begin
  1720. p^.registers32:=p^.left^.registers32;
  1721. p^.registersfpu:=p^.left^.registersfpu;
  1722. {$ifdef SUPPORT_MMX}
  1723. p^.registersmmx:=p^.left^.registersmmx;
  1724. {$endif SUPPORT_MMX}
  1725. end;
  1726. end;
  1727. end;
  1728. { calculates the needed registers for a binary operator }
  1729. procedure calcregisters(p : ptree;r32,fpu,mmx : word);
  1730. begin
  1731. left_right_max(p);
  1732. { Only when the difference between the left and right registers < the
  1733. wanted registers allocate the amount of registers }
  1734. if assigned(p^.left) then
  1735. begin
  1736. if assigned(p^.right) then
  1737. begin
  1738. if (abs(p^.left^.registers32-p^.right^.registers32)<r32) then
  1739. inc(p^.registers32,r32);
  1740. if (abs(p^.left^.registersfpu-p^.right^.registersfpu)<fpu) then
  1741. inc(p^.registersfpu,fpu);
  1742. {$ifdef SUPPORT_MMX}
  1743. if (abs(p^.left^.registersmmx-p^.right^.registersmmx)<mmx) then
  1744. inc(p^.registersmmx,mmx);
  1745. {$endif SUPPORT_MMX}
  1746. { the following is a little bit guessing but I think }
  1747. { it's the only way to solve same internalerrors: }
  1748. { if the left and right node both uses registers }
  1749. { and return a mem location, but the current node }
  1750. { doesn't use an integer register we get probably }
  1751. { trouble when restoring a node }
  1752. if (p^.left^.registers32=p^.right^.registers32) and
  1753. (p^.registers32=p^.left^.registers32) and
  1754. (p^.registers32>0) and
  1755. (p^.left^.location.loc in [LOC_REFERENCE,LOC_MEM]) and
  1756. (p^.right^.location.loc in [LOC_REFERENCE,LOC_MEM]) then
  1757. inc(p^.registers32);
  1758. end
  1759. else
  1760. begin
  1761. if (p^.left^.registers32<r32) then
  1762. inc(p^.registers32,r32);
  1763. if (p^.left^.registersfpu<fpu) then
  1764. inc(p^.registersfpu,fpu);
  1765. {$ifdef SUPPORT_MMX}
  1766. if (p^.left^.registersmmx<mmx) then
  1767. inc(p^.registersmmx,mmx);
  1768. {$endif SUPPORT_MMX}
  1769. end;
  1770. end;
  1771. { error CGMessage, if more than 8 floating point }
  1772. { registers are needed }
  1773. if p^.registersfpu>8 then
  1774. CGMessage(cg_e_too_complex_expr);
  1775. end;
  1776. {****************************************************************************
  1777. Subroutine Handling
  1778. ****************************************************************************}
  1779. { protected field handling
  1780. protected field can not appear in
  1781. var parameters of function !!
  1782. this can only be done after we have determined the
  1783. overloaded function
  1784. this is the reason why it is not in the parser, PM }
  1785. procedure test_protected_sym(sym : psym);
  1786. begin
  1787. if (sp_protected in sym^.symoptions) and
  1788. ((sym^.owner^.symtabletype=unitsymtable) or
  1789. ((sym^.owner^.symtabletype=objectsymtable) and
  1790. (pobjectdef(sym^.owner^.defowner)^.owner^.symtabletype=unitsymtable))
  1791. ) then
  1792. CGMessage(parser_e_cant_access_protected_member);
  1793. end;
  1794. procedure test_protected(p : ptree);
  1795. begin
  1796. case p^.treetype of
  1797. loadn : test_protected_sym(p^.symtableentry);
  1798. typeconvn : test_protected(p^.left);
  1799. derefn : test_protected(p^.left);
  1800. subscriptn : begin
  1801. { test_protected(p^.left);
  1802. Is a field of a protected var
  1803. also protected ??? PM }
  1804. test_protected_sym(p^.vs);
  1805. end;
  1806. end;
  1807. end;
  1808. function valid_for_formal_var(p : ptree) : boolean;
  1809. var
  1810. v : boolean;
  1811. begin
  1812. case p^.treetype of
  1813. loadn :
  1814. v:=(p^.symtableentry^.typ in [typedconstsym,varsym]);
  1815. typeconvn :
  1816. v:=valid_for_formal_var(p^.left);
  1817. derefn,
  1818. subscriptn,
  1819. vecn,
  1820. funcretn,
  1821. selfn :
  1822. v:=true;
  1823. calln : { procvars are callnodes first }
  1824. v:=assigned(p^.right) and not assigned(p^.left);
  1825. addrn :
  1826. begin
  1827. { addrn is not allowed as this generate a constant value,
  1828. but a tp procvar are allowed (PFV) }
  1829. if p^.procvarload then
  1830. v:=true
  1831. else
  1832. v:=false;
  1833. end;
  1834. else
  1835. v:=false;
  1836. end;
  1837. valid_for_formal_var:=v;
  1838. end;
  1839. function valid_for_formal_const(p : ptree) : boolean;
  1840. var
  1841. v : boolean;
  1842. begin
  1843. { p must have been firstpass'd before }
  1844. { accept about anything but not a statement ! }
  1845. case p^.treetype of
  1846. calln,
  1847. statementn,
  1848. addrn :
  1849. begin
  1850. { addrn is not allowed as this generate a constant value,
  1851. but a tp procvar are allowed (PFV) }
  1852. if p^.procvarload then
  1853. v:=true
  1854. else
  1855. v:=false;
  1856. end;
  1857. else
  1858. v:=true;
  1859. end;
  1860. valid_for_formal_const:=v;
  1861. end;
  1862. function is_procsym_load(p:Ptree):boolean;
  1863. begin
  1864. is_procsym_load:=((p^.treetype=loadn) and (p^.symtableentry^.typ=procsym)) or
  1865. ((p^.treetype=addrn) and (p^.left^.treetype=loadn)
  1866. and (p^.left^.symtableentry^.typ=procsym)) ;
  1867. end;
  1868. { change a proc call to a procload for assignment to a procvar }
  1869. { this can only happen for proc/function without arguments }
  1870. function is_procsym_call(p:Ptree):boolean;
  1871. begin
  1872. is_procsym_call:=(p^.treetype=calln) and (p^.left=nil) and
  1873. (((p^.symtableprocentry^.typ=procsym) and (p^.right=nil)) or
  1874. ((p^.right<>nil) and (p^.right^.symtableprocentry^.typ=varsym)));
  1875. end;
  1876. function assignment_overloaded(from_def,to_def : pdef) : pprocdef;
  1877. var
  1878. passproc : pprocdef;
  1879. convtyp : tconverttype;
  1880. begin
  1881. assignment_overloaded:=nil;
  1882. if assigned(overloaded_operators[_assignment]) then
  1883. passproc:=overloaded_operators[_assignment]^.definition
  1884. else
  1885. exit;
  1886. while passproc<>nil do
  1887. begin
  1888. if is_equal(passproc^.rettype.def,to_def) and
  1889. (is_equal(pparaitem(passproc^.para^.first)^.paratype.def,from_def) or
  1890. (isconvertable(from_def,pparaitem(passproc^.para^.first)^.paratype.def,convtyp,ordconstn,false)=1)) then
  1891. begin
  1892. assignment_overloaded:=passproc;
  1893. break;
  1894. end;
  1895. passproc:=passproc^.nextoverloaded;
  1896. end;
  1897. end;
  1898. { local routines can't be assigned to procvars }
  1899. procedure test_local_to_procvar(from_def:pprocvardef;to_def:pdef);
  1900. begin
  1901. if (from_def^.symtablelevel>1) and (to_def^.deftype=procvardef) then
  1902. CGMessage(type_e_cannot_local_proc_to_procvar);
  1903. end;
  1904. function valid_for_assign(p:ptree;allowprop:boolean):boolean;
  1905. var
  1906. hp : ptree;
  1907. gotwith,
  1908. gotsubscript,
  1909. gotpointer,
  1910. gotclass,
  1911. gotderef : boolean;
  1912. begin
  1913. valid_for_assign:=false;
  1914. gotsubscript:=false;
  1915. gotderef:=false;
  1916. gotclass:=false;
  1917. gotpointer:=false;
  1918. gotwith:=false;
  1919. hp:=p;
  1920. while assigned(hp) do
  1921. begin
  1922. { property allowed? calln has a property check itself }
  1923. if (not allowprop) and
  1924. (hp^.isproperty) and
  1925. (hp^.treetype<>calln) then
  1926. begin
  1927. CGMessagePos(hp^.fileinfo,type_e_argument_cant_be_assigned);
  1928. exit;
  1929. end;
  1930. case hp^.treetype of
  1931. derefn :
  1932. begin
  1933. gotderef:=true;
  1934. hp:=hp^.left;
  1935. end;
  1936. typeconvn :
  1937. begin
  1938. case hp^.resulttype^.deftype of
  1939. pointerdef :
  1940. gotpointer:=true;
  1941. objectdef :
  1942. gotclass:=pobjectdef(hp^.resulttype)^.is_class;
  1943. classrefdef :
  1944. gotclass:=true;
  1945. arraydef :
  1946. begin
  1947. { pointer -> array conversion is done then we need to see it
  1948. as a deref, because a ^ is then not required anymore }
  1949. if (hp^.left^.resulttype^.deftype=pointerdef) then
  1950. gotderef:=true;
  1951. end;
  1952. end;
  1953. hp:=hp^.left;
  1954. end;
  1955. vecn,
  1956. asn :
  1957. hp:=hp^.left;
  1958. subscriptn :
  1959. begin
  1960. gotsubscript:=true;
  1961. hp:=hp^.left;
  1962. end;
  1963. subn,
  1964. addn :
  1965. begin
  1966. { Allow add/sub operators on a pointer, or an integer
  1967. and a pointer typecast and deref has been found }
  1968. if (hp^.resulttype^.deftype=pointerdef) or
  1969. (is_integer(hp^.resulttype) and gotpointer and gotderef) then
  1970. valid_for_assign:=true
  1971. else
  1972. CGMessagePos(hp^.fileinfo,type_e_variable_id_expected);
  1973. exit;
  1974. end;
  1975. addrn :
  1976. begin
  1977. if not(gotderef) and
  1978. not(hp^.procvarload) then
  1979. CGMessagePos(hp^.fileinfo,type_e_no_assign_to_addr);
  1980. exit;
  1981. end;
  1982. selfn,
  1983. funcretn :
  1984. begin
  1985. valid_for_assign:=true;
  1986. exit;
  1987. end;
  1988. calln :
  1989. begin
  1990. { check return type }
  1991. case hp^.resulttype^.deftype of
  1992. pointerdef :
  1993. gotpointer:=true;
  1994. objectdef :
  1995. gotclass:=pobjectdef(hp^.resulttype)^.is_class;
  1996. recorddef, { handle record like class it needs a subscription }
  1997. classrefdef :
  1998. gotclass:=true;
  1999. end;
  2000. { 1. if it returns a pointer and we've found a deref,
  2001. 2. if it returns a class or record and a subscription or with is found,
  2002. 3. property is allowed }
  2003. if (gotpointer and gotderef) or
  2004. (gotclass and (gotsubscript or gotwith)) or
  2005. (hp^.isproperty and allowprop) then
  2006. valid_for_assign:=true
  2007. else
  2008. CGMessagePos(hp^.fileinfo,type_e_argument_cant_be_assigned);
  2009. exit;
  2010. end;
  2011. loadn :
  2012. begin
  2013. case hp^.symtableentry^.typ of
  2014. absolutesym,
  2015. varsym :
  2016. begin
  2017. if (pvarsym(hp^.symtableentry)^.varspez=vs_const) then
  2018. begin
  2019. { allow p^:= constructions with p is const parameter }
  2020. if gotderef then
  2021. valid_for_assign:=true
  2022. else
  2023. CGMessagePos(hp^.fileinfo,type_e_no_assign_to_const);
  2024. exit;
  2025. end;
  2026. { Are we at a with symtable, then we need to process the
  2027. withrefnode also to check for maybe a const load }
  2028. if (hp^.symtable^.symtabletype=withsymtable) then
  2029. begin
  2030. { continue with processing the withref node }
  2031. hp:=ptree(pwithsymtable(hp^.symtable)^.withrefnode);
  2032. gotwith:=true;
  2033. end
  2034. else
  2035. begin
  2036. { set the assigned flag for varsyms }
  2037. if (pvarsym(hp^.symtableentry)^.varstate=vs_declared) then
  2038. pvarsym(hp^.symtableentry)^.varstate:=vs_assigned;
  2039. valid_for_assign:=true;
  2040. exit;
  2041. end;
  2042. end;
  2043. funcretsym,
  2044. typedconstsym :
  2045. begin
  2046. valid_for_assign:=true;
  2047. exit;
  2048. end;
  2049. end;
  2050. end;
  2051. else
  2052. begin
  2053. CGMessagePos(hp^.fileinfo,type_e_variable_id_expected);
  2054. exit;
  2055. end;
  2056. end;
  2057. end;
  2058. end;
  2059. {$endif cg11}
  2060. end.
  2061. {
  2062. $Log$
  2063. Revision 1.9 2000-09-28 19:49:51 florian
  2064. *** empty log message ***
  2065. Revision 1.8 2000/09/27 18:14:31 florian
  2066. * fixed a lot of syntax errors in the n*.pas stuff
  2067. Revision 1.7 2000/09/26 20:06:13 florian
  2068. * hmm, still a lot of work to get things compilable
  2069. Revision 1.6 2000/09/24 15:06:17 peter
  2070. * use defines.inc
  2071. Revision 1.5 2000/08/27 16:11:51 peter
  2072. * moved some util functions from globals,cobjects to cutils
  2073. * splitted files into finput,fmodule
  2074. Revision 1.4 2000/08/16 18:33:53 peter
  2075. * splitted namedobjectitem.next into indexnext and listnext so it
  2076. can be used in both lists
  2077. * don't allow "word = word" type definitions (merged)
  2078. Revision 1.3 2000/08/07 11:31:04 jonas
  2079. * fixed bug in type conversions between enum subranges (it didn't take
  2080. the packenum directive into account)
  2081. + define PACKENUMFIXED symbol in options.pas
  2082. (merged from fixes branch)
  2083. Revision 1.2 2000/07/13 11:32:41 michael
  2084. + removed logs
  2085. }