defcmp.pas 46 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150
  1. {
  2. $Id$
  3. Copyright (c) 1998-2002 by Florian Klaempfl
  4. Compare definitions and parameter lists
  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 defcmp;
  19. {$i fpcdefs.inc}
  20. interface
  21. uses
  22. cclasses,
  23. cpuinfo,
  24. globals,
  25. node,
  26. symconst,symbase,symtype,symdef;
  27. type
  28. { The order is from low priority to high priority,
  29. Note: the operators > and < are used on this list }
  30. tequaltype = (
  31. te_incompatible,
  32. te_convert_operator,
  33. te_convert_l2,
  34. te_convert_l1,
  35. te_equal,
  36. te_exact
  37. );
  38. { if acp is cp_all the var const or nothing are considered equal }
  39. compare_type = ( cp_none, cp_value_equal_const, cp_all,cp_procvar);
  40. tconverttype = (
  41. tc_equal,
  42. tc_not_possible,
  43. tc_string_2_string,
  44. tc_char_2_string,
  45. tc_char_2_chararray,
  46. tc_pchar_2_string,
  47. tc_cchar_2_pchar,
  48. tc_cstring_2_pchar,
  49. tc_ansistring_2_pchar,
  50. tc_string_2_chararray,
  51. tc_chararray_2_string,
  52. tc_array_2_pointer,
  53. tc_pointer_2_array,
  54. tc_int_2_int,
  55. tc_int_2_bool,
  56. tc_bool_2_bool,
  57. tc_bool_2_int,
  58. tc_real_2_real,
  59. tc_int_2_real,
  60. tc_proc_2_procvar,
  61. tc_arrayconstructor_2_set,
  62. tc_load_smallset,
  63. tc_cord_2_pointer,
  64. tc_intf_2_string,
  65. tc_intf_2_guid,
  66. tc_class_2_intf,
  67. tc_char_2_char,
  68. tc_normal_2_smallset,
  69. tc_dynarray_2_openarray,
  70. tc_pwchar_2_string
  71. );
  72. function compare_defs_ext(def_from,def_to : tdef;
  73. fromtreetype : tnodetype;
  74. explicit : boolean;
  75. check_operator : boolean;
  76. var doconv : tconverttype;
  77. var operatorpd : tprocdef):tequaltype;
  78. { Returns if the type def_from can be converted to def_to or if both types are equal }
  79. function compare_defs(def_from,def_to:tdef;fromtreetype:tnodetype):tequaltype;
  80. { Returns true, if def1 and def2 are semantically the same }
  81. function equal_defs(def_from,def_to:tdef):boolean;
  82. { Checks for type compatibility (subgroups of type)
  83. used for case statements... probably missing stuff
  84. to use on other types }
  85. function is_subequal(def1, def2: tdef): boolean;
  86. function assignment_overloaded(from_def,to_def : tdef) : tprocdef;
  87. {# true, if two parameter lists are equal
  88. if acp is cp_none, all have to match exactly
  89. if acp is cp_value_equal_const call by value
  90. and call by const parameter are assumed as
  91. equal
  92. allowdefaults indicates if default value parameters
  93. are allowed (in this case, the search order will first
  94. search for a routine with default parameters, before
  95. searching for the same definition with no parameters)
  96. }
  97. function compare_paras(paralist1,paralist2 : TLinkedList; acp : compare_type;allowdefaults:boolean):tequaltype;
  98. { True if a function can be assigned to a procvar }
  99. { changed first argument type to pabstractprocdef so that it can also be }
  100. { used to test compatibility between two pprocvardefs (JM) }
  101. function proc_to_procvar_equal(def1:tabstractprocdef;def2:tprocvardef):tequaltype;
  102. implementation
  103. uses
  104. globtype,tokens,
  105. verbose,systems,
  106. symsym,symtable,
  107. defutil,symutil;
  108. function assignment_overloaded(from_def,to_def:tdef):tprocdef;
  109. begin
  110. if assigned(overloaded_operators[_ASSIGNMENT]) then
  111. assignment_overloaded:=overloaded_operators[_ASSIGNMENT].search_procdef_assignment_operator(from_def,to_def)
  112. else
  113. assignment_overloaded:=nil;
  114. end;
  115. function compare_defs_ext(def_from,def_to : tdef;
  116. fromtreetype : tnodetype;
  117. explicit : boolean;
  118. check_operator : boolean;
  119. var doconv : tconverttype;
  120. var operatorpd : tprocdef):tequaltype;
  121. { Tbasetype:
  122. uvoid,
  123. u8bit,u16bit,u32bit,u64bit,
  124. s8bit,s16bit,s32bit,s64bit,
  125. bool8bit,bool16bit,bool32bit,
  126. uchar,uwidechar }
  127. type
  128. tbasedef=(bvoid,bchar,bint,bbool);
  129. const
  130. basedeftbl:array[tbasetype] of tbasedef =
  131. (bvoid,
  132. bint,bint,bint,bint,
  133. bint,bint,bint,bint,
  134. bbool,bbool,bbool,
  135. bchar,bchar);
  136. basedefconvertsimplicit : array[tbasedef,tbasedef] of tconverttype =
  137. { void, char, int, bool }
  138. ((tc_not_possible,tc_not_possible,tc_not_possible,tc_not_possible),
  139. (tc_not_possible,tc_char_2_char,tc_not_possible,tc_not_possible),
  140. (tc_not_possible,tc_not_possible,tc_int_2_int,tc_int_2_bool),
  141. (tc_not_possible,tc_not_possible,tc_bool_2_int,tc_bool_2_bool));
  142. basedefconvertsexplicit : array[tbasedef,tbasedef] of tconverttype =
  143. { void, char, int, bool }
  144. ((tc_not_possible,tc_not_possible,tc_not_possible,tc_not_possible),
  145. (tc_not_possible,tc_char_2_char,tc_int_2_int,tc_int_2_bool),
  146. (tc_not_possible,tc_int_2_int,tc_int_2_int,tc_int_2_bool),
  147. (tc_not_possible,tc_bool_2_int,tc_bool_2_int,tc_bool_2_bool));
  148. var
  149. eq,b : tequaltype;
  150. hd1,hd2 : tdef;
  151. hct : tconverttype;
  152. hd3 : tobjectdef;
  153. hpd : tprocdef;
  154. begin
  155. { safety check }
  156. if not(assigned(def_from) and assigned(def_to)) then
  157. begin
  158. compare_defs_ext:=te_incompatible;
  159. exit;
  160. end;
  161. { same def? then we've an exact match }
  162. if def_from=def_to then
  163. begin
  164. compare_defs_ext:=te_exact;
  165. exit;
  166. end;
  167. { tp7 procvar def support, in tp7 a procvar is always called, if the
  168. procvar is passed explicit a addrn would be there }
  169. if (m_tp_procvar in aktmodeswitches) and
  170. (def_from.deftype=procvardef) and
  171. (fromtreetype=loadn) and
  172. { only if the procvar doesn't require any paramters }
  173. (tprocvardef(def_from).minparacount = 0) then
  174. begin
  175. def_from:=tprocvardef(def_from).rettype.def;
  176. end;
  177. { we walk the wanted (def_to) types and check then the def_from
  178. types if there is a conversion possible }
  179. b:=te_incompatible;
  180. doconv:=tc_not_possible;
  181. case def_to.deftype of
  182. orddef :
  183. begin
  184. case def_from.deftype of
  185. orddef :
  186. begin
  187. if (torddef(def_from).typ=torddef(def_to).typ) then
  188. begin
  189. case torddef(def_from).typ of
  190. u8bit,u16bit,u32bit,u64bit,
  191. s8bit,s16bit,s32bit,s64bit:
  192. begin
  193. if (torddef(def_from).low=torddef(def_to).low) and
  194. (torddef(def_from).high=torddef(def_to).high) then
  195. b:=te_equal
  196. else
  197. b:=te_convert_l1;
  198. end;
  199. uvoid,uchar,uwidechar,
  200. bool8bit,bool16bit,bool32bit:
  201. b:=te_equal;
  202. else
  203. internalerror(200210061);
  204. end;
  205. end
  206. else
  207. begin
  208. if explicit then
  209. doconv:=basedefconvertsexplicit[basedeftbl[torddef(def_from).typ],basedeftbl[torddef(def_to).typ]]
  210. else
  211. doconv:=basedefconvertsimplicit[basedeftbl[torddef(def_from).typ],basedeftbl[torddef(def_to).typ]];
  212. if (doconv=tc_not_possible) then
  213. b:=te_incompatible
  214. else
  215. { "punish" bad type conversions :) (JM) }
  216. if (not is_in_limit(def_from,def_to)) and
  217. (def_from.size > def_to.size) then
  218. b:=te_convert_l2
  219. else
  220. b:=te_convert_l1;
  221. end;
  222. end;
  223. enumdef :
  224. begin
  225. { needed for char(enum) }
  226. if explicit then
  227. begin
  228. doconv:=tc_int_2_int;
  229. b:=te_convert_l1;
  230. end;
  231. end;
  232. pointerdef :
  233. begin
  234. if explicit and
  235. (fromtreetype=niln) then
  236. begin
  237. { will be handled by the constant folding }
  238. doconv:=tc_equal;
  239. b:=te_convert_l1;
  240. end;
  241. end;
  242. end;
  243. end;
  244. stringdef :
  245. begin
  246. case def_from.deftype of
  247. stringdef :
  248. begin
  249. if (tstringdef(def_from).string_typ=tstringdef(def_to).string_typ) and
  250. ((tstringdef(def_from).string_typ<>st_shortstring) or
  251. (tstringdef(def_from).len=tstringdef(def_to).len)) then
  252. b:=te_equal
  253. else
  254. begin
  255. doconv:=tc_string_2_string;
  256. b:=te_convert_l1;
  257. end;
  258. end;
  259. orddef :
  260. begin
  261. { char to string}
  262. if is_char(def_from) or
  263. is_widechar(def_from) then
  264. begin
  265. doconv:=tc_char_2_string;
  266. b:=te_convert_l1;
  267. end;
  268. end;
  269. arraydef :
  270. begin
  271. { array of char to string, the length check is done by the firstpass of this node }
  272. if is_chararray(def_from) or
  273. (is_char(tarraydef(def_from).elementtype.def) and
  274. is_open_array(def_from)) then
  275. begin
  276. doconv:=tc_chararray_2_string;
  277. if is_open_array(def_from) or
  278. (is_shortstring(def_to) and
  279. (def_from.size <= 255)) or
  280. (is_ansistring(def_to) and
  281. (def_from.size > 255)) then
  282. b:=te_convert_l1
  283. else
  284. b:=te_convert_l2;
  285. end;
  286. end;
  287. pointerdef :
  288. begin
  289. { pchar can be assigned to short/ansistrings,
  290. but not in tp7 compatible mode }
  291. if not(m_tp7 in aktmodeswitches) then
  292. begin
  293. if is_pchar(def_from) then
  294. begin
  295. doconv:=tc_pchar_2_string;
  296. { trefer ansistrings because pchars can overflow shortstrings, }
  297. { but only if ansistrings are the default (JM) }
  298. if (is_shortstring(def_to) and
  299. not(cs_ansistrings in aktlocalswitches)) or
  300. (is_ansistring(def_to) and
  301. (cs_ansistrings in aktlocalswitches)) then
  302. b:=te_convert_l1
  303. else
  304. b:=te_convert_l2;
  305. end
  306. else if is_pwidechar(def_from) then
  307. begin
  308. doconv:=tc_pwchar_2_string;
  309. { trefer ansistrings because pchars can overflow shortstrings, }
  310. { but only if ansistrings are the default (JM) }
  311. if is_widestring(def_to) then
  312. b:=te_convert_l1
  313. else
  314. b:=te_convert_l2;
  315. end;
  316. end;
  317. end;
  318. end;
  319. end;
  320. floatdef :
  321. begin
  322. case def_from.deftype of
  323. orddef :
  324. begin { ordinal to real }
  325. if is_integer(def_from) then
  326. begin
  327. doconv:=tc_int_2_real;
  328. b:=te_convert_l1;
  329. end;
  330. end;
  331. floatdef :
  332. begin
  333. if tfloatdef(def_from).typ=tfloatdef(def_to).typ then
  334. b:=te_equal
  335. else
  336. begin
  337. doconv:=tc_real_2_real;
  338. b:=te_convert_l1;
  339. end;
  340. end;
  341. end;
  342. end;
  343. enumdef :
  344. begin
  345. case def_from.deftype of
  346. enumdef :
  347. begin
  348. if explicit then
  349. begin
  350. b:=te_convert_l1;
  351. doconv:=tc_int_2_int;
  352. end
  353. else
  354. begin
  355. hd1:=def_from;
  356. while assigned(tenumdef(hd1).basedef) do
  357. hd1:=tenumdef(hd1).basedef;
  358. hd2:=def_to;
  359. while assigned(tenumdef(hd2).basedef) do
  360. hd2:=tenumdef(hd2).basedef;
  361. if (hd1=hd2) then
  362. begin
  363. b:=te_convert_l1;
  364. { because of packenum they can have different sizes! (JM) }
  365. doconv:=tc_int_2_int;
  366. end;
  367. end;
  368. end;
  369. orddef :
  370. begin
  371. if explicit then
  372. begin
  373. b:=te_convert_l1;
  374. doconv:=tc_int_2_int;
  375. end;
  376. end;
  377. end;
  378. end;
  379. arraydef :
  380. begin
  381. { open array is also compatible with a single element of its base type }
  382. if is_open_array(def_to) and
  383. equal_defs(def_from,tarraydef(def_to).elementtype.def) then
  384. begin
  385. doconv:=tc_equal;
  386. b:=te_convert_l1;
  387. end
  388. else
  389. begin
  390. case def_from.deftype of
  391. arraydef :
  392. begin
  393. { to dynamic array }
  394. if is_dynamic_array(def_to) then
  395. begin
  396. { dynamic array -> dynamic array }
  397. if is_dynamic_array(def_from) and
  398. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  399. b:=te_equal;
  400. end
  401. else
  402. { to open array }
  403. if is_open_array(def_to) then
  404. begin
  405. { array constructor -> open array }
  406. if is_array_constructor(def_from) then
  407. begin
  408. if is_void(tarraydef(def_from).elementtype.def) then
  409. begin
  410. doconv:=tc_equal;
  411. b:=te_convert_l1;
  412. end
  413. else
  414. begin
  415. eq:=compare_defs_ext(tarraydef(def_from).elementtype.def,
  416. tarraydef(def_to).elementtype.def,
  417. arrayconstructorn,false,true,hct,hpd);
  418. if (eq>=te_equal) then
  419. begin
  420. doconv:=tc_equal;
  421. b:=te_convert_l1;
  422. end
  423. else
  424. if (eq>te_incompatible) then
  425. begin
  426. doconv:=hct;
  427. b:=te_convert_l2;
  428. end;
  429. end;
  430. end
  431. else
  432. { dynamic array -> open array }
  433. if is_dynamic_array(def_from) and
  434. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  435. begin
  436. doconv:=tc_dynarray_2_openarray;
  437. b:=te_convert_l2;
  438. end
  439. else
  440. { array -> open array }
  441. if equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  442. b:=te_equal;
  443. end
  444. else
  445. { to array of const }
  446. if is_array_of_const(def_to) then
  447. begin
  448. if is_array_of_const(def_from) or
  449. is_array_constructor(def_from) then
  450. begin
  451. b:=te_equal;
  452. end
  453. else
  454. { array of tvarrec -> array of const }
  455. if equal_defs(tarraydef(def_to).elementtype.def,tarraydef(def_from).elementtype.def) then
  456. begin
  457. doconv:=tc_equal;
  458. b:=te_convert_l1;
  459. end;
  460. end
  461. else
  462. { other arrays }
  463. begin
  464. { open array -> array }
  465. if is_open_array(def_from) and
  466. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  467. begin
  468. b:=te_equal
  469. end
  470. else
  471. { array -> array }
  472. if not(m_tp7 in aktmodeswitches) and
  473. not(m_delphi in aktmodeswitches) and
  474. (tarraydef(def_from).lowrange=tarraydef(def_to).lowrange) and
  475. (tarraydef(def_from).highrange=tarraydef(def_to).highrange) and
  476. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) and
  477. equal_defs(tarraydef(def_from).rangetype.def,tarraydef(def_to).rangetype.def) then
  478. begin
  479. b:=te_equal
  480. end;
  481. end;
  482. end;
  483. pointerdef :
  484. begin
  485. { nil is compatible with dyn. arrays }
  486. if is_dynamic_array(def_to) and
  487. (fromtreetype=niln) then
  488. begin
  489. doconv:=tc_equal;
  490. b:=te_convert_l1;
  491. end
  492. else
  493. if is_zero_based_array(def_to) and
  494. equal_defs(tpointerdef(def_from).pointertype.def,tarraydef(def_to).elementtype.def) then
  495. begin
  496. doconv:=tc_pointer_2_array;
  497. b:=te_convert_l1;
  498. end;
  499. end;
  500. stringdef :
  501. begin
  502. { string to char array }
  503. if (not is_special_array(def_to)) and
  504. is_char(tarraydef(def_to).elementtype.def) then
  505. begin
  506. doconv:=tc_string_2_chararray;
  507. b:=te_convert_l1;
  508. end;
  509. end;
  510. orddef:
  511. begin
  512. if is_chararray(def_to) and
  513. is_char(def_from) then
  514. begin
  515. doconv:=tc_char_2_chararray;
  516. b:=te_convert_l2;
  517. end;
  518. end;
  519. recorddef :
  520. begin
  521. { tvarrec -> array of const }
  522. if is_array_of_const(def_to) and
  523. equal_defs(def_from,tarraydef(def_to).elementtype.def) then
  524. begin
  525. doconv:=tc_equal;
  526. b:=te_convert_l1;
  527. end;
  528. end;
  529. end;
  530. end;
  531. end;
  532. pointerdef :
  533. begin
  534. case def_from.deftype of
  535. stringdef :
  536. begin
  537. { string constant (which can be part of array constructor)
  538. to zero terminated string constant }
  539. if (fromtreetype in [arrayconstructorn,stringconstn]) and
  540. (is_pchar(def_to) or is_pwidechar(def_to)) then
  541. begin
  542. doconv:=tc_cstring_2_pchar;
  543. b:=te_convert_l1;
  544. end
  545. else
  546. if explicit then
  547. begin
  548. { pchar(ansistring) }
  549. if is_pchar(def_to) and
  550. is_ansistring(def_from) then
  551. begin
  552. doconv:=tc_ansistring_2_pchar;
  553. b:=te_convert_l1;
  554. end
  555. else
  556. { pwidechar(ansistring) }
  557. if is_pwidechar(def_to) and
  558. is_widestring(def_from) then
  559. begin
  560. doconv:=tc_ansistring_2_pchar;
  561. b:=te_convert_l1;
  562. end;
  563. end;
  564. end;
  565. orddef :
  566. begin
  567. { char constant to zero terminated string constant }
  568. if (fromtreetype=ordconstn) then
  569. begin
  570. if is_char(def_from) and
  571. is_pchar(def_to) then
  572. begin
  573. doconv:=tc_cchar_2_pchar;
  574. b:=te_convert_l1;
  575. end
  576. else
  577. if is_integer(def_from) then
  578. begin
  579. doconv:=tc_cord_2_pointer;
  580. b:=te_convert_l1;
  581. end;
  582. end;
  583. if (b=te_incompatible) and
  584. explicit and
  585. (m_delphi in aktmodeswitches) then
  586. begin
  587. doconv:=tc_int_2_int;
  588. b:=te_convert_l1;
  589. end;
  590. end;
  591. arraydef :
  592. begin
  593. { chararray to pointer }
  594. if is_zero_based_array(def_from) and
  595. equal_defs(tarraydef(def_from).elementtype.def,tpointerdef(def_to).pointertype.def) then
  596. begin
  597. doconv:=tc_array_2_pointer;
  598. b:=te_convert_l1;
  599. end;
  600. end;
  601. pointerdef :
  602. begin
  603. { check for far pointers }
  604. if (tpointerdef(def_from).is_far<>tpointerdef(def_to).is_far) then
  605. begin
  606. b:=te_incompatible;
  607. end
  608. else
  609. { the types can be forward type, handle before normal type check !! }
  610. if assigned(def_to.typesym) and
  611. (tpointerdef(def_to).pointertype.def.deftype=forwarddef) then
  612. begin
  613. if (def_from.typesym=def_to.typesym) then
  614. b:=te_equal
  615. end
  616. else
  617. { same types }
  618. if (tpointerdef(def_from).pointertype.def=tpointerdef(def_to).pointertype.def) then
  619. begin
  620. b:=te_equal
  621. end
  622. else
  623. { child class pointer can be assigned to anchestor pointers }
  624. if (
  625. (tpointerdef(def_from).pointertype.def.deftype=objectdef) and
  626. (tpointerdef(def_to).pointertype.def.deftype=objectdef) and
  627. tobjectdef(tpointerdef(def_from).pointertype.def).is_related(
  628. tobjectdef(tpointerdef(def_to).pointertype.def))
  629. ) or
  630. { all pointers can be assigned to/from void-pointer }
  631. is_void(tpointerdef(def_to).pointertype.def) or
  632. is_void(tpointerdef(def_from).pointertype.def) then
  633. begin
  634. doconv:=tc_equal;
  635. b:=te_convert_l1;
  636. end;
  637. end;
  638. procvardef :
  639. begin
  640. { procedure variable can be assigned to an void pointer }
  641. { Not anymore. Use the @ operator now.}
  642. if not(m_tp_procvar in aktmodeswitches) and
  643. (tpointerdef(def_to).pointertype.def.deftype=orddef) and
  644. (torddef(tpointerdef(def_to).pointertype.def).typ=uvoid) then
  645. begin
  646. doconv:=tc_equal;
  647. b:=te_convert_l1;
  648. end;
  649. end;
  650. classrefdef,
  651. objectdef :
  652. begin
  653. { class types and class reference type
  654. can be assigned to void pointers }
  655. if (
  656. is_class_or_interface(def_from) or
  657. (def_from.deftype=classrefdef)
  658. ) and
  659. (tpointerdef(def_to).pointertype.def.deftype=orddef) and
  660. (torddef(tpointerdef(def_to).pointertype.def).typ=uvoid) then
  661. begin
  662. doconv:=tc_equal;
  663. b:=te_convert_l1;
  664. end;
  665. end;
  666. end;
  667. end;
  668. setdef :
  669. begin
  670. case def_from.deftype of
  671. setdef :
  672. begin
  673. if assigned(tsetdef(def_from).elementtype.def) and
  674. assigned(tsetdef(def_to).elementtype.def) then
  675. begin
  676. { sets with the same element base type are equal }
  677. if is_subequal(tsetdef(def_from).elementtype.def,tsetdef(def_to).elementtype.def) then
  678. b:=te_equal;
  679. end
  680. else
  681. { empty set is compatible with everything }
  682. b:=te_equal;
  683. end;
  684. arraydef :
  685. begin
  686. { automatic arrayconstructor -> set conversion }
  687. if is_array_constructor(def_from) then
  688. begin
  689. doconv:=tc_arrayconstructor_2_set;
  690. b:=te_convert_l1;
  691. end;
  692. end;
  693. end;
  694. end;
  695. procvardef :
  696. begin
  697. case def_from.deftype of
  698. procdef :
  699. begin
  700. { proc -> procvar }
  701. if (m_tp_procvar in aktmodeswitches) then
  702. begin
  703. b:=proc_to_procvar_equal(tprocdef(def_from),tprocvardef(def_to));
  704. if b>te_incompatible then
  705. begin
  706. doconv:=tc_proc_2_procvar;
  707. b:=te_convert_l1;
  708. end;
  709. end;
  710. end;
  711. procvardef :
  712. begin
  713. { procvar -> procvar }
  714. b:=proc_to_procvar_equal(tprocvardef(def_from),tprocvardef(def_to));
  715. end;
  716. pointerdef :
  717. begin
  718. { nil is compatible with procvars }
  719. if (fromtreetype=niln) then
  720. begin
  721. doconv:=tc_equal;
  722. b:=te_convert_l1;
  723. end
  724. else
  725. { for example delphi allows the assignement from pointers }
  726. { to procedure variables }
  727. if (m_pointer_2_procedure in aktmodeswitches) and
  728. (tpointerdef(def_from).pointertype.def.deftype=orddef) and
  729. (torddef(tpointerdef(def_from).pointertype.def).typ=uvoid) then
  730. begin
  731. doconv:=tc_equal;
  732. b:=te_convert_l1;
  733. end;
  734. end;
  735. end;
  736. end;
  737. objectdef :
  738. begin
  739. { object pascal objects }
  740. if (def_from.deftype=objectdef) and
  741. tobjectdef(def_from).is_related(tobjectdef(def_to)) then
  742. begin
  743. doconv:=tc_equal;
  744. b:=te_convert_l1;
  745. end
  746. else
  747. { Class/interface specific }
  748. if is_class_or_interface(def_to) then
  749. begin
  750. { void pointer also for delphi mode }
  751. if (m_delphi in aktmodeswitches) and
  752. is_voidpointer(def_from) then
  753. begin
  754. doconv:=tc_equal;
  755. b:=te_convert_l1;
  756. end
  757. else
  758. { nil is compatible with class instances and interfaces }
  759. if (fromtreetype=niln) then
  760. begin
  761. doconv:=tc_equal;
  762. b:=te_convert_l1;
  763. end
  764. { classes can be assigned to interfaces }
  765. else if is_interface(def_to) and
  766. is_class(def_from) and
  767. assigned(tobjectdef(def_from).implementedinterfaces) then
  768. begin
  769. { we've to search in parent classes as well }
  770. hd3:=tobjectdef(def_from);
  771. while assigned(hd3) do
  772. begin
  773. if hd3.implementedinterfaces.searchintf(def_to)<>-1 then
  774. begin
  775. doconv:=tc_class_2_intf;
  776. b:=te_convert_l1;
  777. break;
  778. end;
  779. hd3:=hd3.childof;
  780. end;
  781. end
  782. { Interface 2 GUID handling }
  783. else if (def_to=tdef(rec_tguid)) and
  784. (fromtreetype=typen) and
  785. is_interface(def_from) and
  786. assigned(tobjectdef(def_from).iidguid) then
  787. begin
  788. b:=te_convert_l1;
  789. doconv:=tc_equal;
  790. end;
  791. end;
  792. end;
  793. classrefdef :
  794. begin
  795. { similar to pointerdef wrt forwards }
  796. if assigned(def_to.typesym) and
  797. (tclassrefdef(def_to).pointertype.def.deftype=forwarddef) then
  798. begin
  799. if (def_from.typesym=def_to.typesym) then
  800. b:=te_equal;
  801. end
  802. else
  803. { class reference types }
  804. if (def_from.deftype=classrefdef) then
  805. begin
  806. if equal_defs(tclassrefdef(def_from).pointertype.def,tclassrefdef(def_to).pointertype.def) then
  807. begin
  808. b:=te_equal;
  809. end
  810. else
  811. begin
  812. doconv:=tc_equal;
  813. if tobjectdef(tclassrefdef(def_from).pointertype.def).is_related(
  814. tobjectdef(tclassrefdef(def_to).pointertype.def)) then
  815. b:=te_convert_l1;
  816. end;
  817. end
  818. else
  819. { nil is compatible with class references }
  820. if (fromtreetype=niln) then
  821. begin
  822. doconv:=tc_equal;
  823. b:=te_convert_l1;
  824. end;
  825. end;
  826. filedef :
  827. begin
  828. { typed files are all equal to the abstract file type
  829. name TYPEDFILE in system.pp in is_equal in types.pas
  830. the problem is that it sholud be also compatible to FILE
  831. but this would leed to a problem for ASSIGN RESET and REWRITE
  832. when trying to find the good overloaded function !!
  833. so all file function are doubled in system.pp
  834. this is not very beautiful !!}
  835. if (def_from.deftype=filedef) then
  836. begin
  837. if (tfiledef(def_from).filetyp=tfiledef(def_to).filetyp) then
  838. begin
  839. if
  840. (
  841. (tfiledef(def_from).typedfiletype.def=nil) and
  842. (tfiledef(def_to).typedfiletype.def=nil)
  843. ) or
  844. (
  845. (tfiledef(def_from).typedfiletype.def<>nil) and
  846. (tfiledef(def_to).typedfiletype.def<>nil) and
  847. equal_defs(tfiledef(def_from).typedfiletype.def,tfiledef(def_to).typedfiletype.def)
  848. ) or
  849. (
  850. (tfiledef(def_from).filetyp = ft_typed) and
  851. (tfiledef(def_to).filetyp = ft_typed) and
  852. (
  853. (tfiledef(def_from).typedfiletype.def = tdef(voidtype.def)) or
  854. (tfiledef(def_to).typedfiletype.def = tdef(voidtype.def))
  855. )
  856. ) then
  857. begin
  858. b:=te_equal;
  859. end;
  860. end
  861. else
  862. if ((tfiledef(def_from).filetyp = ft_untyped) and
  863. (tfiledef(def_to).filetyp = ft_typed)) or
  864. ((tfiledef(def_from).filetyp = ft_typed) and
  865. (tfiledef(def_to).filetyp = ft_untyped)) then
  866. begin
  867. doconv:=tc_equal;
  868. b:=te_convert_l1;
  869. end;
  870. end;
  871. end;
  872. recorddef :
  873. begin
  874. { interface -> guid }
  875. if is_interface(def_from) and
  876. (def_to=rec_tguid) then
  877. begin
  878. doconv:=tc_intf_2_guid;
  879. b:=te_convert_l1;
  880. end
  881. else
  882. begin
  883. { assignment overwritten ?? }
  884. if check_operator then
  885. begin
  886. operatorpd:=assignment_overloaded(def_from,def_to);
  887. if assigned(operatorpd) then
  888. b:=te_convert_operator;
  889. end;
  890. end;
  891. end;
  892. formaldef :
  893. begin
  894. if (def_from.deftype=formaldef) then
  895. b:=te_equal
  896. else
  897. { Just about everything can be converted to a formaldef...}
  898. if not (def_from.deftype in [abstractdef,errordef]) then
  899. b:=te_convert_l1
  900. else
  901. begin
  902. { assignment overwritten ?? }
  903. if check_operator then
  904. begin
  905. operatorpd:=assignment_overloaded(def_from,def_to);
  906. if assigned(operatorpd) then
  907. b:=te_convert_operator;
  908. end;
  909. end;
  910. end;
  911. end;
  912. { if we didn't find an appropriate type conversion yet, we try the overloaded := operator }
  913. { This is done for variants only yet, maybe we should do this for other types as well (FK) }
  914. if (b=te_incompatible) and
  915. check_operator and
  916. ((def_from.deftype in [variantdef]) or
  917. (def_to.deftype in [variantdef])) then
  918. begin
  919. operatorpd:=assignment_overloaded(def_from,def_to);
  920. if assigned(operatorpd) then
  921. b:=te_convert_operator;
  922. end;
  923. compare_defs_ext:=b;
  924. end;
  925. function equal_defs(def_from,def_to:tdef):boolean;
  926. var
  927. convtyp : tconverttype;
  928. pd : tprocdef;
  929. begin
  930. { Compare defs with nothingn and no explicit typecasts and
  931. searching for overloaded operators is not needed }
  932. equal_defs:=(compare_defs_ext(def_from,def_to,nothingn,false,false,convtyp,pd)>=te_equal);
  933. end;
  934. function compare_defs(def_from,def_to:tdef;fromtreetype:tnodetype):tequaltype;
  935. var
  936. doconv : tconverttype;
  937. pd : tprocdef;
  938. begin
  939. compare_defs:=compare_defs_ext(def_from,def_to,fromtreetype,false,true,doconv,pd);
  940. end;
  941. function is_subequal(def1, def2: tdef): boolean;
  942. var
  943. basedef1,basedef2 : tenumdef;
  944. Begin
  945. is_subequal := false;
  946. if assigned(def1) and assigned(def2) then
  947. Begin
  948. if (def1.deftype = orddef) and (def2.deftype = orddef) then
  949. Begin
  950. { see p.47 of Turbo Pascal 7.01 manual for the separation of types }
  951. { range checking for case statements is done with testrange }
  952. case torddef(def1).typ of
  953. u8bit,u16bit,u32bit,u64bit,
  954. s8bit,s16bit,s32bit,s64bit :
  955. is_subequal:=(torddef(def2).typ in [s64bit,u64bit,s32bit,u32bit,u8bit,s8bit,s16bit,u16bit]);
  956. bool8bit,bool16bit,bool32bit :
  957. is_subequal:=(torddef(def2).typ in [bool8bit,bool16bit,bool32bit]);
  958. uchar :
  959. is_subequal:=(torddef(def2).typ=uchar);
  960. uwidechar :
  961. is_subequal:=(torddef(def2).typ=uwidechar);
  962. end;
  963. end
  964. else
  965. Begin
  966. { Check if both basedefs are equal }
  967. if (def1.deftype=enumdef) and (def2.deftype=enumdef) then
  968. Begin
  969. { get both basedefs }
  970. basedef1:=tenumdef(def1);
  971. while assigned(basedef1.basedef) do
  972. basedef1:=basedef1.basedef;
  973. basedef2:=tenumdef(def2);
  974. while assigned(basedef2.basedef) do
  975. basedef2:=basedef2.basedef;
  976. is_subequal:=(basedef1=basedef2);
  977. end;
  978. end;
  979. end;
  980. end;
  981. function compare_paras(paralist1,paralist2 : TLinkedList; acp : compare_type;allowdefaults:boolean):tequaltype;
  982. var
  983. def1,def2 : TParaItem;
  984. eq,lowesteq : tequaltype;
  985. begin
  986. compare_paras:=te_incompatible;
  987. { we need to parse the list from left-right so the
  988. not-default parameters are checked first }
  989. lowesteq:=high(tequaltype);
  990. def1:=TParaItem(paralist1.last);
  991. def2:=TParaItem(paralist2.last);
  992. while (assigned(def1)) and (assigned(def2)) do
  993. begin
  994. eq:=te_incompatible;
  995. case acp of
  996. cp_value_equal_const :
  997. begin
  998. if (
  999. (def1.paratyp<>def2.paratyp) and
  1000. ((def1.paratyp in [vs_var,vs_out]) or
  1001. (def2.paratyp in [vs_var,vs_out]))
  1002. ) then
  1003. exit;
  1004. end;
  1005. cp_all,cp_procvar :
  1006. begin
  1007. if (def1.paratyp<>def2.paratyp) then
  1008. exit;
  1009. end;
  1010. end;
  1011. { check type }
  1012. eq:=compare_defs(def1.paratype.def,def2.paratype.def,nothingn);
  1013. if eq=te_incompatible then
  1014. exit;
  1015. if eq<lowesteq then
  1016. lowesteq:=eq;
  1017. { also check default value if both have it declared }
  1018. if assigned(def1.defaultvalue) and
  1019. assigned(def2.defaultvalue) then
  1020. begin
  1021. if not equal_constsym(tconstsym(def1.defaultvalue),tconstsym(def2.defaultvalue)) then
  1022. exit;
  1023. end;
  1024. def1:=TParaItem(def1.previous);
  1025. def2:=TParaItem(def2.previous);
  1026. end;
  1027. { when both lists are empty then the parameters are equal. Also
  1028. when one list is empty and the other has a parameter with default
  1029. value assigned then the parameters are also equal }
  1030. if ((def1=nil) and (def2=nil)) or
  1031. (allowdefaults and
  1032. ((assigned(def1) and assigned(def1.defaultvalue)) or
  1033. (assigned(def2) and assigned(def2.defaultvalue)))) then
  1034. compare_paras:=lowesteq;
  1035. end;
  1036. function proc_to_procvar_equal(def1:tabstractprocdef;def2:tprocvardef):tequaltype;
  1037. const
  1038. po_comp = po_compatibility_options-[po_methodpointer,po_classmethod];
  1039. var
  1040. ismethod : boolean;
  1041. begin
  1042. proc_to_procvar_equal:=te_incompatible;
  1043. if not(assigned(def1)) or not(assigned(def2)) then
  1044. exit;
  1045. { check for method pointer }
  1046. if def1.deftype=procvardef then
  1047. begin
  1048. ismethod:=(po_methodpointer in def1.procoptions);
  1049. end
  1050. else
  1051. begin
  1052. ismethod:=assigned(def1.owner) and
  1053. (def1.owner.symtabletype=objectsymtable);
  1054. end;
  1055. if (ismethod and not (po_methodpointer in def2.procoptions)) or
  1056. (not(ismethod) and (po_methodpointer in def2.procoptions)) then
  1057. begin
  1058. Message(type_e_no_method_and_procedure_not_compatible);
  1059. exit;
  1060. end;
  1061. { check return value and options, methodpointer is already checked }
  1062. if ((po_comp * def1.procoptions)= (po_comp * def2.procoptions)) and
  1063. equal_defs(def1.rettype.def,def2.rettype.def) and
  1064. (def1.para_size(target_info.alignment.paraalign)=def2.para_size(target_info.alignment.paraalign)) then
  1065. begin
  1066. { return equal type based on the parameters }
  1067. proc_to_procvar_equal:=compare_paras(def1.para,def2.para,cp_procvar,false);
  1068. end;
  1069. end;
  1070. function is_equal(def1,def2 : tdef) : boolean;
  1071. var
  1072. doconv : tconverttype;
  1073. hpd : tprocdef;
  1074. begin
  1075. is_equal:=(compare_defs_ext(def1,def2,nothingn,false,true,doconv,hpd)>=te_equal);
  1076. end;
  1077. function equal_paras(paralist1,paralist2 : TLinkedList; acp : compare_type;allowdefaults:boolean) : boolean;
  1078. begin
  1079. equal_paras:=(compare_paras(paralist1,paralist2,acp,allowdefaults)>=te_equal);
  1080. end;
  1081. end.
  1082. {
  1083. $Log$
  1084. Revision 1.1 2002-11-25 17:43:16 peter
  1085. * splitted defbase in defutil,symutil,defcmp
  1086. * merged isconvertable and is_equal into compare_defs(_ext)
  1087. * made operator search faster by walking the list only once
  1088. }