defcmp.pas 56 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367
  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. globtype,globals,
  24. node,
  25. symconst,symtype,symdef;
  26. type
  27. { if acp is cp_all the var const or nothing are considered equal }
  28. tcompare_paras_type = ( cp_none, cp_value_equal_const, cp_all,cp_procvar);
  29. tcompare_paras_option = (cpo_allowdefaults,cpo_ignorehidden,cpo_allowconvert,cpo_comparedefaultvalue);
  30. tcompare_paras_options = set of tcompare_paras_option;
  31. tcompare_defs_option = (cdo_internal,cdo_explicit,cdo_check_operator,cdo_allow_variant);
  32. tcompare_defs_options = set of tcompare_defs_option;
  33. tconverttype = (
  34. tc_equal,
  35. tc_not_possible,
  36. tc_string_2_string,
  37. tc_char_2_string,
  38. tc_char_2_chararray,
  39. tc_pchar_2_string,
  40. tc_cchar_2_pchar,
  41. tc_cstring_2_pchar,
  42. tc_ansistring_2_pchar,
  43. tc_string_2_chararray,
  44. tc_chararray_2_string,
  45. tc_array_2_pointer,
  46. tc_pointer_2_array,
  47. tc_int_2_int,
  48. tc_int_2_bool,
  49. tc_bool_2_bool,
  50. tc_bool_2_int,
  51. tc_real_2_real,
  52. tc_int_2_real,
  53. tc_real_2_currency,
  54. tc_proc_2_procvar,
  55. tc_arrayconstructor_2_set,
  56. tc_load_smallset,
  57. tc_cord_2_pointer,
  58. tc_intf_2_string,
  59. tc_intf_2_guid,
  60. tc_class_2_intf,
  61. tc_char_2_char,
  62. tc_normal_2_smallset,
  63. tc_dynarray_2_openarray,
  64. tc_pwchar_2_string,
  65. tc_variant_2_dynarray,
  66. tc_dynarray_2_variant,
  67. tc_variant_2_enum,
  68. tc_enum_2_variant
  69. );
  70. function compare_defs_ext(def_from,def_to : tdef;
  71. fromtreetype : tnodetype;
  72. var doconv : tconverttype;
  73. var operatorpd : tprocdef;
  74. cdoptions:tcompare_defs_options):tequaltype;
  75. { Returns if the type def_from can be converted to def_to or if both types are equal }
  76. function compare_defs(def_from,def_to:tdef;fromtreetype:tnodetype):tequaltype;
  77. { Returns true, if def1 and def2 are semantically the same }
  78. function equal_defs(def_from,def_to:tdef):boolean;
  79. { Checks for type compatibility (subgroups of type)
  80. used for case statements... probably missing stuff
  81. to use on other types }
  82. function is_subequal(def1, def2: tdef): boolean;
  83. {# true, if two parameter lists are equal
  84. if acp is cp_none, all have to match exactly
  85. if acp is cp_value_equal_const call by value
  86. and call by const parameter are assumed as
  87. equal
  88. allowdefaults indicates if default value parameters
  89. are allowed (in this case, the search order will first
  90. search for a routine with default parameters, before
  91. searching for the same definition with no parameters)
  92. }
  93. function compare_paras(para1,para2 : tlist; acp : tcompare_paras_type; cpoptions: tcompare_paras_options):tequaltype;
  94. { True if a function can be assigned to a procvar }
  95. { changed first argument type to pabstractprocdef so that it can also be }
  96. { used to test compatibility between two pprocvardefs (JM) }
  97. function proc_to_procvar_equal(def1:tabstractprocdef;def2:tprocvardef;methoderr:boolean):tequaltype;
  98. implementation
  99. uses
  100. verbose,systems,
  101. symtable,symsym,
  102. defutil,symutil;
  103. function compare_defs_ext(def_from,def_to : tdef;
  104. fromtreetype : tnodetype;
  105. var doconv : tconverttype;
  106. var operatorpd : tprocdef;
  107. cdoptions:tcompare_defs_options):tequaltype;
  108. { Tbasetype:
  109. uvoid,
  110. u8bit,u16bit,u32bit,u64bit,
  111. s8bit,s16bit,s32bit,s64bit,
  112. bool8bit,bool16bit,bool32bit,
  113. uchar,uwidechar }
  114. type
  115. tbasedef=(bvoid,bchar,bint,bbool);
  116. const
  117. basedeftbl:array[tbasetype] of tbasedef =
  118. (bvoid,
  119. bint,bint,bint,bint,
  120. bint,bint,bint,bint,
  121. bbool,bbool,bbool,
  122. bchar,bchar,bint);
  123. basedefconvertsimplicit : array[tbasedef,tbasedef] of tconverttype =
  124. { void, char, int, bool }
  125. ((tc_not_possible,tc_not_possible,tc_not_possible,tc_not_possible),
  126. (tc_not_possible,tc_char_2_char,tc_not_possible,tc_not_possible),
  127. (tc_not_possible,tc_not_possible,tc_int_2_int,tc_not_possible),
  128. (tc_not_possible,tc_not_possible,tc_not_possible,tc_bool_2_bool));
  129. basedefconvertsexplicit : array[tbasedef,tbasedef] of tconverttype =
  130. { void, char, int, bool }
  131. ((tc_not_possible,tc_not_possible,tc_not_possible,tc_not_possible),
  132. (tc_not_possible,tc_char_2_char,tc_int_2_int,tc_int_2_bool),
  133. (tc_not_possible,tc_int_2_int,tc_int_2_int,tc_int_2_bool),
  134. (tc_not_possible,tc_bool_2_int,tc_bool_2_int,tc_bool_2_bool));
  135. var
  136. subeq,eq : tequaltype;
  137. hd1,hd2 : tdef;
  138. hct : tconverttype;
  139. hd3 : tobjectdef;
  140. hpd : tprocdef;
  141. begin
  142. { safety check }
  143. if not(assigned(def_from) and assigned(def_to)) then
  144. begin
  145. compare_defs_ext:=te_incompatible;
  146. exit;
  147. end;
  148. { same def? then we've an exact match }
  149. if def_from=def_to then
  150. begin
  151. compare_defs_ext:=te_exact;
  152. exit;
  153. end;
  154. { we walk the wanted (def_to) types and check then the def_from
  155. types if there is a conversion possible }
  156. eq:=te_incompatible;
  157. doconv:=tc_not_possible;
  158. case def_to.deftype of
  159. orddef :
  160. begin
  161. case def_from.deftype of
  162. orddef :
  163. begin
  164. if (torddef(def_from).typ=torddef(def_to).typ) then
  165. begin
  166. case torddef(def_from).typ of
  167. uchar,uwidechar,
  168. u8bit,u16bit,u32bit,u64bit,
  169. s8bit,s16bit,s32bit,s64bit:
  170. begin
  171. if (torddef(def_from).low=torddef(def_to).low) and
  172. (torddef(def_from).high=torddef(def_to).high) then
  173. eq:=te_equal
  174. else
  175. begin
  176. doconv:=tc_int_2_int;
  177. eq:=te_convert_l1;
  178. end;
  179. end;
  180. uvoid,
  181. bool8bit,bool16bit,bool32bit:
  182. eq:=te_equal;
  183. else
  184. internalerror(200210061);
  185. end;
  186. end
  187. else
  188. begin
  189. if cdo_explicit in cdoptions then
  190. doconv:=basedefconvertsexplicit[basedeftbl[torddef(def_from).typ],basedeftbl[torddef(def_to).typ]]
  191. else
  192. doconv:=basedefconvertsimplicit[basedeftbl[torddef(def_from).typ],basedeftbl[torddef(def_to).typ]];
  193. if (doconv=tc_not_possible) then
  194. eq:=te_incompatible
  195. else
  196. { "punish" bad type conversions :) (JM) }
  197. if (not is_in_limit(def_from,def_to)) and
  198. (def_from.size > def_to.size) then
  199. eq:=te_convert_l3
  200. else
  201. eq:=te_convert_l1;
  202. end;
  203. end;
  204. enumdef :
  205. begin
  206. { needed for char(enum) }
  207. if cdo_explicit in cdoptions then
  208. begin
  209. doconv:=tc_int_2_int;
  210. eq:=te_convert_l1;
  211. end;
  212. end;
  213. floatdef :
  214. begin
  215. if is_currency(def_to) then
  216. begin
  217. doconv:=tc_real_2_currency;
  218. eq:=te_convert_l2;
  219. end;
  220. end;
  221. classrefdef,
  222. procvardef,
  223. pointerdef :
  224. begin
  225. if cdo_explicit in cdoptions then
  226. begin
  227. eq:=te_convert_l1;
  228. if (fromtreetype=niln) then
  229. begin
  230. { will be handled by the constant folding }
  231. doconv:=tc_equal;
  232. end
  233. else
  234. doconv:=tc_int_2_int;
  235. end;
  236. end;
  237. end;
  238. end;
  239. stringdef :
  240. begin
  241. case def_from.deftype of
  242. stringdef :
  243. begin
  244. { Constant string }
  245. if (fromtreetype=stringconstn) then
  246. begin
  247. if (tstringdef(def_from).string_typ=tstringdef(def_to).string_typ) then
  248. eq:=te_equal
  249. else
  250. begin
  251. doconv:=tc_string_2_string;
  252. { Don't prefer conversions from widestring to a
  253. normal string as we can loose information }
  254. if tstringdef(def_from).string_typ=st_widestring then
  255. eq:=te_convert_l1
  256. else
  257. begin
  258. if tstringdef(def_to).string_typ=st_widestring then
  259. eq:=te_convert_l1
  260. else
  261. eq:=te_equal; { we can change the stringconst node }
  262. end;
  263. end;
  264. end
  265. else
  266. { Same string type, for shortstrings also the length must match }
  267. if (tstringdef(def_from).string_typ=tstringdef(def_to).string_typ) and
  268. ((tstringdef(def_from).string_typ<>st_shortstring) or
  269. (tstringdef(def_from).len=tstringdef(def_to).len)) then
  270. eq:=te_equal
  271. else
  272. begin
  273. doconv:=tc_string_2_string;
  274. { Prefer conversions to shortstring over other
  275. conversions. This is compatible with Delphi (PFV) }
  276. if tstringdef(def_to).string_typ=st_shortstring then
  277. eq:=te_convert_l2
  278. else
  279. eq:=te_convert_l3;
  280. end;
  281. end;
  282. orddef :
  283. begin
  284. { char to string}
  285. if is_char(def_from) or
  286. is_widechar(def_from) then
  287. begin
  288. doconv:=tc_char_2_string;
  289. eq:=te_convert_l1;
  290. end;
  291. end;
  292. arraydef :
  293. begin
  294. { array of char to string, the length check is done by the firstpass of this node }
  295. if is_chararray(def_from) or
  296. (is_char(tarraydef(def_from).elementtype.def) and
  297. is_open_array(def_from)) then
  298. begin
  299. doconv:=tc_chararray_2_string;
  300. if is_open_array(def_from) or
  301. (is_shortstring(def_to) and
  302. (def_from.size <= 255)) or
  303. (is_ansistring(def_to) and
  304. (def_from.size > 255)) then
  305. eq:=te_convert_l1
  306. else
  307. eq:=te_convert_l2;
  308. end;
  309. end;
  310. pointerdef :
  311. begin
  312. { pchar can be assigned to short/ansistrings,
  313. but not in tp7 compatible mode }
  314. if not(m_tp7 in aktmodeswitches) then
  315. begin
  316. if is_pchar(def_from) then
  317. begin
  318. doconv:=tc_pchar_2_string;
  319. { prefer ansistrings because pchars can overflow shortstrings, }
  320. { but only if ansistrings are the default (JM) }
  321. if (is_shortstring(def_to) and
  322. not(cs_ansistrings in aktlocalswitches)) or
  323. (is_ansistring(def_to) and
  324. (cs_ansistrings in aktlocalswitches)) then
  325. eq:=te_convert_l1
  326. else
  327. eq:=te_convert_l2;
  328. end
  329. else if is_pwidechar(def_from) then
  330. begin
  331. doconv:=tc_pwchar_2_string;
  332. { prefer ansistrings because pchars can overflow shortstrings, }
  333. { but only if ansistrings are the default (JM) }
  334. if is_widestring(def_to) then
  335. eq:=te_convert_l1
  336. else
  337. eq:=te_convert_l3;
  338. end;
  339. end;
  340. end;
  341. end;
  342. end;
  343. floatdef :
  344. begin
  345. case def_from.deftype of
  346. orddef :
  347. begin { ordinal to real }
  348. if is_integer(def_from) or
  349. (is_currency(def_from) and
  350. (s64currencytype.def.deftype = floatdef)) then
  351. begin
  352. doconv:=tc_int_2_real;
  353. eq:=te_convert_l1;
  354. end
  355. else if is_currency(def_from)
  356. { and (s64currencytype.def.deftype = orddef)) } then
  357. begin
  358. { prefer conversion to orddef in this case, unless }
  359. { the orddef < currency (then it will get convert l3, }
  360. { and conversion to float is favoured) }
  361. doconv:=tc_int_2_real;
  362. eq:=te_convert_l2;
  363. end;
  364. end;
  365. floatdef :
  366. begin
  367. if tfloatdef(def_from).typ=tfloatdef(def_to).typ then
  368. eq:=te_equal
  369. else
  370. begin
  371. if (fromtreetype=realconstn) or
  372. not((cdo_explicit in cdoptions) and
  373. (m_delphi in aktmodeswitches)) then
  374. begin
  375. doconv:=tc_real_2_real;
  376. { do we loose precision? }
  377. if def_to.size<def_from.size then
  378. eq:=te_convert_l2
  379. else
  380. eq:=te_convert_l1;
  381. end;
  382. end;
  383. end;
  384. end;
  385. end;
  386. enumdef :
  387. begin
  388. case def_from.deftype of
  389. enumdef :
  390. begin
  391. if cdo_explicit in cdoptions then
  392. begin
  393. eq:=te_convert_l1;
  394. doconv:=tc_int_2_int;
  395. end
  396. else
  397. begin
  398. hd1:=def_from;
  399. while assigned(tenumdef(hd1).basedef) do
  400. hd1:=tenumdef(hd1).basedef;
  401. hd2:=def_to;
  402. while assigned(tenumdef(hd2).basedef) do
  403. hd2:=tenumdef(hd2).basedef;
  404. if (hd1=hd2) then
  405. begin
  406. eq:=te_convert_l1;
  407. { because of packenum they can have different sizes! (JM) }
  408. doconv:=tc_int_2_int;
  409. end;
  410. end;
  411. end;
  412. orddef :
  413. begin
  414. if cdo_explicit in cdoptions then
  415. begin
  416. eq:=te_convert_l1;
  417. doconv:=tc_int_2_int;
  418. end;
  419. end;
  420. variantdef :
  421. begin
  422. eq:=te_convert_l1;
  423. doconv:=tc_variant_2_enum;
  424. end;
  425. end;
  426. end;
  427. arraydef :
  428. begin
  429. { open array is also compatible with a single element of its base type }
  430. if is_open_array(def_to) and
  431. equal_defs(def_from,tarraydef(def_to).elementtype.def) then
  432. begin
  433. doconv:=tc_equal;
  434. eq:=te_convert_l1;
  435. end
  436. else
  437. begin
  438. case def_from.deftype of
  439. arraydef :
  440. begin
  441. { to dynamic array }
  442. if is_dynamic_array(def_to) then
  443. begin
  444. { dynamic array -> dynamic array }
  445. if is_dynamic_array(def_from) and
  446. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  447. eq:=te_equal;
  448. end
  449. else
  450. { to open array }
  451. if is_open_array(def_to) then
  452. begin
  453. { array constructor -> open array }
  454. if is_array_constructor(def_from) then
  455. begin
  456. if is_void(tarraydef(def_from).elementtype.def) then
  457. begin
  458. doconv:=tc_equal;
  459. eq:=te_convert_l1;
  460. end
  461. else
  462. begin
  463. subeq:=compare_defs_ext(tarraydef(def_from).elementtype.def,
  464. tarraydef(def_to).elementtype.def,
  465. arrayconstructorn,hct,hpd,[cdo_check_operator]);
  466. if (subeq>=te_equal) then
  467. begin
  468. doconv:=tc_equal;
  469. eq:=te_convert_l1;
  470. end
  471. else
  472. if (subeq>te_incompatible) then
  473. begin
  474. doconv:=hct;
  475. eq:=te_convert_l2;
  476. end;
  477. end;
  478. end
  479. else
  480. { dynamic array -> open array }
  481. if is_dynamic_array(def_from) and
  482. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  483. begin
  484. doconv:=tc_dynarray_2_openarray;
  485. eq:=te_convert_l2;
  486. end
  487. else
  488. { array -> open array }
  489. if equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  490. eq:=te_equal;
  491. end
  492. else
  493. { to array of const }
  494. if is_array_of_const(def_to) then
  495. begin
  496. if is_array_of_const(def_from) or
  497. is_array_constructor(def_from) then
  498. begin
  499. eq:=te_equal;
  500. end
  501. else
  502. { array of tvarrec -> array of const }
  503. if equal_defs(tarraydef(def_to).elementtype.def,tarraydef(def_from).elementtype.def) then
  504. begin
  505. doconv:=tc_equal;
  506. eq:=te_convert_l1;
  507. end;
  508. end
  509. else
  510. { other arrays }
  511. begin
  512. { open array -> array }
  513. if is_open_array(def_from) and
  514. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) then
  515. begin
  516. eq:=te_equal
  517. end
  518. else
  519. { array -> array }
  520. if not(m_tp7 in aktmodeswitches) and
  521. not(m_delphi in aktmodeswitches) and
  522. (tarraydef(def_from).lowrange=tarraydef(def_to).lowrange) and
  523. (tarraydef(def_from).highrange=tarraydef(def_to).highrange) and
  524. equal_defs(tarraydef(def_from).elementtype.def,tarraydef(def_to).elementtype.def) and
  525. equal_defs(tarraydef(def_from).rangetype.def,tarraydef(def_to).rangetype.def) then
  526. begin
  527. eq:=te_equal
  528. end;
  529. end;
  530. end;
  531. pointerdef :
  532. begin
  533. { nil and voidpointers are compatible with dyn. arrays }
  534. if is_dynamic_array(def_to) and
  535. ((fromtreetype=niln) or
  536. is_voidpointer(def_from)) then
  537. begin
  538. doconv:=tc_equal;
  539. eq:=te_convert_l1;
  540. end
  541. else
  542. if is_zero_based_array(def_to) and
  543. equal_defs(tpointerdef(def_from).pointertype.def,tarraydef(def_to).elementtype.def) then
  544. begin
  545. doconv:=tc_pointer_2_array;
  546. eq:=te_convert_l1;
  547. end;
  548. end;
  549. stringdef :
  550. begin
  551. { string to char array }
  552. if (not is_special_array(def_to)) and
  553. is_char(tarraydef(def_to).elementtype.def) then
  554. begin
  555. doconv:=tc_string_2_chararray;
  556. eq:=te_convert_l1;
  557. end;
  558. end;
  559. orddef:
  560. begin
  561. if is_chararray(def_to) and
  562. is_char(def_from) then
  563. begin
  564. doconv:=tc_char_2_chararray;
  565. eq:=te_convert_l2;
  566. end;
  567. end;
  568. recorddef :
  569. begin
  570. { tvarrec -> array of const }
  571. if is_array_of_const(def_to) and
  572. equal_defs(def_from,tarraydef(def_to).elementtype.def) then
  573. begin
  574. doconv:=tc_equal;
  575. eq:=te_convert_l1;
  576. end;
  577. end;
  578. variantdef :
  579. begin
  580. if is_dynamic_array(def_to) then
  581. begin
  582. doconv:=tc_variant_2_dynarray;
  583. eq:=te_convert_l1;
  584. end;
  585. end;
  586. end;
  587. end;
  588. end;
  589. variantdef :
  590. begin
  591. if (cdo_allow_variant in cdoptions) then
  592. begin
  593. case def_from.deftype of
  594. enumdef :
  595. begin
  596. doconv:=tc_enum_2_variant;
  597. eq:=te_convert_l1;
  598. end;
  599. arraydef :
  600. begin
  601. if is_dynamic_array(def_from) then
  602. begin
  603. doconv:=tc_dynarray_2_variant;
  604. eq:=te_convert_l1;
  605. end;
  606. end;
  607. end;
  608. end;
  609. end;
  610. pointerdef :
  611. begin
  612. case def_from.deftype of
  613. stringdef :
  614. begin
  615. { string constant (which can be part of array constructor)
  616. to zero terminated string constant }
  617. if (fromtreetype in [arrayconstructorn,stringconstn]) and
  618. (is_pchar(def_to) or is_pwidechar(def_to)) then
  619. begin
  620. doconv:=tc_cstring_2_pchar;
  621. eq:=te_convert_l1;
  622. end
  623. else
  624. if cdo_explicit in cdoptions then
  625. begin
  626. { pchar(ansistring) }
  627. if is_pchar(def_to) and
  628. is_ansistring(def_from) then
  629. begin
  630. doconv:=tc_ansistring_2_pchar;
  631. eq:=te_convert_l1;
  632. end
  633. else
  634. { pwidechar(ansistring) }
  635. if is_pwidechar(def_to) and
  636. is_widestring(def_from) then
  637. begin
  638. doconv:=tc_ansistring_2_pchar;
  639. eq:=te_convert_l1;
  640. end;
  641. end;
  642. end;
  643. orddef :
  644. begin
  645. { char constant to zero terminated string constant }
  646. if (fromtreetype=ordconstn) then
  647. begin
  648. if is_char(def_from) and
  649. is_pchar(def_to) then
  650. begin
  651. doconv:=tc_cchar_2_pchar;
  652. eq:=te_convert_l1;
  653. end
  654. else
  655. if (m_delphi in aktmodeswitches) and is_integer(def_from) then
  656. begin
  657. doconv:=tc_cord_2_pointer;
  658. eq:=te_convert_l1;
  659. end;
  660. end;
  661. { delphi compatible, allow explicit typecasts from
  662. ordinals to pointer.
  663. It is also used by the compiler internally for inc(pointer,ordinal) }
  664. if (eq=te_incompatible) and
  665. not is_void(def_from) and
  666. (
  667. (
  668. (m_delphi in aktmodeswitches) and
  669. (cdo_explicit in cdoptions)
  670. ) or
  671. (cdo_internal in cdoptions)
  672. ) then
  673. begin
  674. doconv:=tc_int_2_int;
  675. eq:=te_convert_l1;
  676. end;
  677. end;
  678. arraydef :
  679. begin
  680. { chararray to pointer }
  681. if is_zero_based_array(def_from) and
  682. equal_defs(tarraydef(def_from).elementtype.def,tpointerdef(def_to).pointertype.def) then
  683. begin
  684. doconv:=tc_array_2_pointer;
  685. eq:=te_convert_l1;
  686. end
  687. else
  688. { dynamic array to pointer, delphi only }
  689. if (m_delphi in aktmodeswitches) and
  690. is_dynamic_array(def_from) then
  691. begin
  692. eq:=te_equal;
  693. end;
  694. end;
  695. pointerdef :
  696. begin
  697. { check for far pointers }
  698. if (tpointerdef(def_from).is_far<>tpointerdef(def_to).is_far) then
  699. begin
  700. eq:=te_incompatible;
  701. end
  702. else
  703. { the types can be forward type, handle before normal type check !! }
  704. if assigned(def_to.typesym) and
  705. (tpointerdef(def_to).pointertype.def.deftype=forwarddef) then
  706. begin
  707. if (def_from.typesym=def_to.typesym) then
  708. eq:=te_equal
  709. end
  710. else
  711. { same types }
  712. if equal_defs(tpointerdef(def_from).pointertype.def,tpointerdef(def_to).pointertype.def) then
  713. begin
  714. eq:=te_equal
  715. end
  716. else
  717. { child class pointer can be assigned to anchestor pointers }
  718. if (
  719. (tpointerdef(def_from).pointertype.def.deftype=objectdef) and
  720. (tpointerdef(def_to).pointertype.def.deftype=objectdef) and
  721. tobjectdef(tpointerdef(def_from).pointertype.def).is_related(
  722. tobjectdef(tpointerdef(def_to).pointertype.def))
  723. ) then
  724. begin
  725. doconv:=tc_equal;
  726. eq:=te_convert_l1;
  727. end
  728. else
  729. { all pointers can be assigned to void-pointer }
  730. if is_void(tpointerdef(def_to).pointertype.def) then
  731. begin
  732. doconv:=tc_equal;
  733. { give pwidechar,pchar a penalty so it prefers
  734. conversion to ansistring }
  735. if is_pchar(def_from) or
  736. is_pwidechar(def_from) then
  737. eq:=te_convert_l2
  738. else
  739. eq:=te_convert_l1;
  740. end
  741. else
  742. { all pointers can be assigned from void-pointer }
  743. if is_void(tpointerdef(def_from).pointertype.def) then
  744. begin
  745. doconv:=tc_equal;
  746. { give pwidechar a penalty so it prefers
  747. conversion to pchar }
  748. if is_pwidechar(def_to) then
  749. eq:=te_convert_l2
  750. else
  751. eq:=te_convert_l1;
  752. end;
  753. end;
  754. procvardef :
  755. begin
  756. { procedure variable can be assigned to an void pointer }
  757. { Not anymore. Use the @ operator now.}
  758. if not(m_tp_procvar in aktmodeswitches) and
  759. { method pointers can't be assigned to void pointers
  760. not(tprocvardef(def_from).is_methodpointer) and }
  761. (tpointerdef(def_to).pointertype.def.deftype=orddef) and
  762. (torddef(tpointerdef(def_to).pointertype.def).typ=uvoid) then
  763. begin
  764. doconv:=tc_equal;
  765. eq:=te_convert_l1;
  766. end;
  767. end;
  768. classrefdef,
  769. objectdef :
  770. begin
  771. { class types and class reference type
  772. can be assigned to void pointers, but it is less
  773. preferred than assigning to a related objectdef }
  774. if (
  775. is_class_or_interface(def_from) or
  776. (def_from.deftype=classrefdef)
  777. ) and
  778. (tpointerdef(def_to).pointertype.def.deftype=orddef) and
  779. (torddef(tpointerdef(def_to).pointertype.def).typ=uvoid) then
  780. begin
  781. doconv:=tc_equal;
  782. eq:=te_convert_l2;
  783. end;
  784. end;
  785. end;
  786. end;
  787. setdef :
  788. begin
  789. case def_from.deftype of
  790. setdef :
  791. begin
  792. if assigned(tsetdef(def_from).elementtype.def) and
  793. assigned(tsetdef(def_to).elementtype.def) then
  794. begin
  795. { sets with the same element base type are equal }
  796. if is_subequal(tsetdef(def_from).elementtype.def,tsetdef(def_to).elementtype.def) then
  797. eq:=te_equal;
  798. end
  799. else
  800. { empty set is compatible with everything }
  801. eq:=te_equal;
  802. end;
  803. arraydef :
  804. begin
  805. { automatic arrayconstructor -> set conversion }
  806. if is_array_constructor(def_from) then
  807. begin
  808. doconv:=tc_arrayconstructor_2_set;
  809. eq:=te_convert_l1;
  810. end;
  811. end;
  812. end;
  813. end;
  814. procvardef :
  815. begin
  816. case def_from.deftype of
  817. procdef :
  818. begin
  819. { proc -> procvar }
  820. if (m_tp_procvar in aktmodeswitches) then
  821. begin
  822. subeq:=proc_to_procvar_equal(tprocdef(def_from),tprocvardef(def_to),true);
  823. if subeq>te_incompatible then
  824. begin
  825. doconv:=tc_proc_2_procvar;
  826. eq:=te_convert_l1;
  827. end;
  828. end;
  829. end;
  830. procvardef :
  831. begin
  832. { procvar -> procvar }
  833. eq:=proc_to_procvar_equal(tprocvardef(def_from),tprocvardef(def_to),false);
  834. end;
  835. pointerdef :
  836. begin
  837. { nil is compatible with procvars }
  838. if (fromtreetype=niln) then
  839. begin
  840. doconv:=tc_equal;
  841. eq:=te_convert_l1;
  842. end
  843. else
  844. { for example delphi allows the assignement from pointers }
  845. { to procedure variables }
  846. if (m_pointer_2_procedure in aktmodeswitches) and
  847. (tpointerdef(def_from).pointertype.def.deftype=orddef) and
  848. (torddef(tpointerdef(def_from).pointertype.def).typ=uvoid) then
  849. begin
  850. doconv:=tc_equal;
  851. eq:=te_convert_l1;
  852. end;
  853. end;
  854. end;
  855. end;
  856. objectdef :
  857. begin
  858. { object pascal objects }
  859. if (def_from.deftype=objectdef) and
  860. (tobjectdef(def_from).is_related(tobjectdef(def_to))) then
  861. begin
  862. doconv:=tc_equal;
  863. eq:=te_convert_l1;
  864. end
  865. else
  866. { Class/interface specific }
  867. if is_class_or_interface(def_to) then
  868. begin
  869. { void pointer also for delphi mode }
  870. if (m_delphi in aktmodeswitches) and
  871. is_voidpointer(def_from) then
  872. begin
  873. doconv:=tc_equal;
  874. { prefer pointer-pointer assignments }
  875. eq:=te_convert_l2;
  876. end
  877. else
  878. { nil is compatible with class instances and interfaces }
  879. if (fromtreetype=niln) then
  880. begin
  881. doconv:=tc_equal;
  882. eq:=te_convert_l1;
  883. end
  884. { classes can be assigned to interfaces }
  885. else if is_interface(def_to) and
  886. is_class(def_from) and
  887. assigned(tobjectdef(def_from).implementedinterfaces) then
  888. begin
  889. { we've to search in parent classes as well }
  890. hd3:=tobjectdef(def_from);
  891. while assigned(hd3) do
  892. begin
  893. if hd3.implementedinterfaces.searchintf(def_to)<>-1 then
  894. begin
  895. doconv:=tc_class_2_intf;
  896. eq:=te_convert_l1;
  897. break;
  898. end;
  899. hd3:=hd3.childof;
  900. end;
  901. end
  902. { Interface 2 GUID handling }
  903. else if (def_to=tdef(rec_tguid)) and
  904. (fromtreetype=typen) and
  905. is_interface(def_from) and
  906. assigned(tobjectdef(def_from).iidguid) then
  907. begin
  908. eq:=te_convert_l1;
  909. doconv:=tc_equal;
  910. end;
  911. end;
  912. end;
  913. classrefdef :
  914. begin
  915. { similar to pointerdef wrt forwards }
  916. if assigned(def_to.typesym) and
  917. (tclassrefdef(def_to).pointertype.def.deftype=forwarddef) then
  918. begin
  919. if (def_from.typesym=def_to.typesym) then
  920. eq:=te_equal;
  921. end
  922. else
  923. { class reference types }
  924. if (def_from.deftype=classrefdef) then
  925. begin
  926. if equal_defs(tclassrefdef(def_from).pointertype.def,tclassrefdef(def_to).pointertype.def) then
  927. begin
  928. eq:=te_equal;
  929. end
  930. else
  931. begin
  932. doconv:=tc_equal;
  933. if (cdo_explicit in cdoptions) or
  934. tobjectdef(tclassrefdef(def_from).pointertype.def).is_related(
  935. tobjectdef(tclassrefdef(def_to).pointertype.def)) then
  936. eq:=te_convert_l1;
  937. end;
  938. end
  939. else
  940. { nil is compatible with class references }
  941. if (fromtreetype=niln) then
  942. begin
  943. doconv:=tc_equal;
  944. eq:=te_convert_l1;
  945. end;
  946. end;
  947. filedef :
  948. begin
  949. { typed files are all equal to the abstract file type
  950. name TYPEDFILE in system.pp in is_equal in types.pas
  951. the problem is that it sholud be also compatible to FILE
  952. but this would leed to a problem for ASSIGN RESET and REWRITE
  953. when trying to find the good overloaded function !!
  954. so all file function are doubled in system.pp
  955. this is not very beautiful !!}
  956. if (def_from.deftype=filedef) then
  957. begin
  958. if (tfiledef(def_from).filetyp=tfiledef(def_to).filetyp) then
  959. begin
  960. if
  961. (
  962. (tfiledef(def_from).typedfiletype.def=nil) and
  963. (tfiledef(def_to).typedfiletype.def=nil)
  964. ) or
  965. (
  966. (tfiledef(def_from).typedfiletype.def<>nil) and
  967. (tfiledef(def_to).typedfiletype.def<>nil) and
  968. equal_defs(tfiledef(def_from).typedfiletype.def,tfiledef(def_to).typedfiletype.def)
  969. ) or
  970. (
  971. (tfiledef(def_from).filetyp = ft_typed) and
  972. (tfiledef(def_to).filetyp = ft_typed) and
  973. (
  974. (tfiledef(def_from).typedfiletype.def = tdef(voidtype.def)) or
  975. (tfiledef(def_to).typedfiletype.def = tdef(voidtype.def))
  976. )
  977. ) then
  978. begin
  979. eq:=te_equal;
  980. end;
  981. end
  982. else
  983. if ((tfiledef(def_from).filetyp = ft_untyped) and
  984. (tfiledef(def_to).filetyp = ft_typed)) or
  985. ((tfiledef(def_from).filetyp = ft_typed) and
  986. (tfiledef(def_to).filetyp = ft_untyped)) then
  987. begin
  988. doconv:=tc_equal;
  989. eq:=te_convert_l1;
  990. end;
  991. end;
  992. end;
  993. recorddef :
  994. begin
  995. { interface -> guid }
  996. if is_interface(def_from) and
  997. (def_to=rec_tguid) then
  998. begin
  999. doconv:=tc_intf_2_guid;
  1000. eq:=te_convert_l1;
  1001. end;
  1002. end;
  1003. formaldef :
  1004. begin
  1005. doconv:=tc_equal;
  1006. if (def_from.deftype=formaldef) then
  1007. eq:=te_equal
  1008. else
  1009. { Just about everything can be converted to a formaldef...}
  1010. if not (def_from.deftype in [abstractdef,errordef]) then
  1011. eq:=te_convert_l1;
  1012. end;
  1013. end;
  1014. { if we didn't find an appropriate type conversion yet
  1015. then we search also the := operator }
  1016. if (eq=te_incompatible) and
  1017. (
  1018. { Check for variants? }
  1019. (
  1020. (cdo_allow_variant in cdoptions) and
  1021. ((def_from.deftype=variantdef) or (def_to.deftype=variantdef))
  1022. ) or
  1023. { Check for operators? }
  1024. (
  1025. (cdo_check_operator in cdoptions) and
  1026. ((def_from.deftype in [objectdef,recorddef,arraydef,stringdef,variantdef]) or
  1027. (def_to.deftype in [objectdef,recorddef,arraydef,stringdef,variantdef]))
  1028. )
  1029. ) then
  1030. begin
  1031. operatorpd:=search_assignment_operator(def_from,def_to);
  1032. if assigned(operatorpd) then
  1033. eq:=te_convert_operator;
  1034. end;
  1035. { update convtype for te_equal when it is not yet set }
  1036. if (eq=te_equal) and
  1037. (doconv=tc_not_possible) then
  1038. doconv:=tc_equal;
  1039. compare_defs_ext:=eq;
  1040. end;
  1041. function equal_defs(def_from,def_to:tdef):boolean;
  1042. var
  1043. convtyp : tconverttype;
  1044. pd : tprocdef;
  1045. begin
  1046. { Compare defs with nothingn and no explicit typecasts and
  1047. searching for overloaded operators is not needed }
  1048. equal_defs:=(compare_defs_ext(def_from,def_to,nothingn,convtyp,pd,[])>=te_equal);
  1049. end;
  1050. function compare_defs(def_from,def_to:tdef;fromtreetype:tnodetype):tequaltype;
  1051. var
  1052. doconv : tconverttype;
  1053. pd : tprocdef;
  1054. begin
  1055. compare_defs:=compare_defs_ext(def_from,def_to,fromtreetype,doconv,pd,[cdo_check_operator,cdo_allow_variant]);
  1056. end;
  1057. function is_subequal(def1, def2: tdef): boolean;
  1058. var
  1059. basedef1,basedef2 : tenumdef;
  1060. Begin
  1061. is_subequal := false;
  1062. if assigned(def1) and assigned(def2) then
  1063. Begin
  1064. if (def1.deftype = orddef) and (def2.deftype = orddef) then
  1065. Begin
  1066. { see p.47 of Turbo Pascal 7.01 manual for the separation of types }
  1067. { range checking for case statements is done with testrange }
  1068. case torddef(def1).typ of
  1069. u8bit,u16bit,u32bit,u64bit,
  1070. s8bit,s16bit,s32bit,s64bit :
  1071. is_subequal:=(torddef(def2).typ in [s64bit,u64bit,s32bit,u32bit,u8bit,s8bit,s16bit,u16bit]);
  1072. bool8bit,bool16bit,bool32bit :
  1073. is_subequal:=(torddef(def2).typ in [bool8bit,bool16bit,bool32bit]);
  1074. uchar :
  1075. is_subequal:=(torddef(def2).typ=uchar);
  1076. uwidechar :
  1077. is_subequal:=(torddef(def2).typ=uwidechar);
  1078. end;
  1079. end
  1080. else
  1081. Begin
  1082. { Check if both basedefs are equal }
  1083. if (def1.deftype=enumdef) and (def2.deftype=enumdef) then
  1084. Begin
  1085. { get both basedefs }
  1086. basedef1:=tenumdef(def1);
  1087. while assigned(basedef1.basedef) do
  1088. basedef1:=basedef1.basedef;
  1089. basedef2:=tenumdef(def2);
  1090. while assigned(basedef2.basedef) do
  1091. basedef2:=basedef2.basedef;
  1092. is_subequal:=(basedef1=basedef2);
  1093. end;
  1094. end;
  1095. end;
  1096. end;
  1097. function compare_paras(para1,para2 : tlist; acp : tcompare_paras_type; cpoptions: tcompare_paras_options):tequaltype;
  1098. var
  1099. currpara1,
  1100. currpara2 : tparavarsym;
  1101. eq,lowesteq : tequaltype;
  1102. hpd : tprocdef;
  1103. convtype : tconverttype;
  1104. cdoptions : tcompare_defs_options;
  1105. i1,i2 : byte;
  1106. begin
  1107. compare_paras:=te_incompatible;
  1108. cdoptions:=[cdo_check_operator,cdo_allow_variant];
  1109. { we need to parse the list from left-right so the
  1110. not-default parameters are checked first }
  1111. lowesteq:=high(tequaltype);
  1112. i1:=0;
  1113. i2:=0;
  1114. if cpo_ignorehidden in cpoptions then
  1115. begin
  1116. while (i1<para1.count) and
  1117. (vo_is_hidden_para in tparavarsym(para1[i1]).varoptions) do
  1118. inc(i1);
  1119. while (i2<para2.count) and
  1120. (vo_is_hidden_para in tparavarsym(para2[i2]).varoptions) do
  1121. inc(i2);
  1122. end;
  1123. while (i1<para1.count) and (i2<para2.count) do
  1124. begin
  1125. eq:=te_incompatible;
  1126. currpara1:=tparavarsym(para1[i1]);
  1127. currpara2:=tparavarsym(para2[i2]);
  1128. { Unique types must match exact }
  1129. if ((df_unique in currpara1.vartype.def.defoptions) or (df_unique in currpara2.vartype.def.defoptions)) and
  1130. (currpara1.vartype.def<>currpara2.vartype.def) then
  1131. exit;
  1132. { Handle hidden parameters separately, because self is
  1133. defined as voidpointer for methodpointers }
  1134. if (vo_is_hidden_para in currpara1.varoptions) or
  1135. (vo_is_hidden_para in currpara2.varoptions) then
  1136. begin
  1137. { both must be hidden }
  1138. if (vo_is_hidden_para in currpara1.varoptions)<>(vo_is_hidden_para in currpara2.varoptions) then
  1139. exit;
  1140. eq:=te_equal;
  1141. if not(vo_is_self in currpara1.varoptions) and
  1142. not(vo_is_self in currpara2.varoptions) then
  1143. begin
  1144. if (currpara1.varspez<>currpara2.varspez) then
  1145. exit;
  1146. eq:=compare_defs_ext(currpara1.vartype.def,currpara2.vartype.def,nothingn,
  1147. convtype,hpd,cdoptions);
  1148. end;
  1149. end
  1150. else
  1151. begin
  1152. case acp of
  1153. cp_value_equal_const :
  1154. begin
  1155. if (
  1156. (currpara1.varspez<>currpara2.varspez) and
  1157. ((currpara1.varspez in [vs_var,vs_out]) or
  1158. (currpara2.varspez in [vs_var,vs_out]))
  1159. ) then
  1160. exit;
  1161. eq:=compare_defs_ext(currpara1.vartype.def,currpara2.vartype.def,nothingn,
  1162. convtype,hpd,cdoptions);
  1163. end;
  1164. cp_all :
  1165. begin
  1166. if (currpara1.varspez<>currpara2.varspez) then
  1167. exit;
  1168. eq:=compare_defs_ext(currpara1.vartype.def,currpara2.vartype.def,nothingn,
  1169. convtype,hpd,cdoptions);
  1170. end;
  1171. cp_procvar :
  1172. begin
  1173. if (currpara1.varspez<>currpara2.varspez) then
  1174. exit;
  1175. eq:=compare_defs_ext(currpara1.vartype.def,currpara2.vartype.def,nothingn,
  1176. convtype,hpd,cdoptions);
  1177. { Parameters must be at least equal otherwise the are incompatible }
  1178. if (eq<te_equal) then
  1179. eq:=te_incompatible;
  1180. end;
  1181. else
  1182. eq:=compare_defs_ext(currpara1.vartype.def,currpara2.vartype.def,nothingn,
  1183. convtype,hpd,cdoptions);
  1184. end;
  1185. end;
  1186. { check type }
  1187. if eq=te_incompatible then
  1188. exit;
  1189. if eq<lowesteq then
  1190. lowesteq:=eq;
  1191. { also check default value if both have it declared }
  1192. if (cpo_comparedefaultvalue in cpoptions) and
  1193. assigned(currpara1.defaultconstsym) and
  1194. assigned(currpara2.defaultconstsym) then
  1195. begin
  1196. if not equal_constsym(tconstsym(currpara1.defaultconstsym),tconstsym(currpara2.defaultconstsym)) then
  1197. exit;
  1198. end;
  1199. inc(i1);
  1200. inc(i2);
  1201. if cpo_ignorehidden in cpoptions then
  1202. begin
  1203. while (i1<para1.count) and
  1204. (vo_is_hidden_para in tparavarsym(para1[i1]).varoptions) do
  1205. inc(i1);
  1206. while (i2<para2.count) and
  1207. (vo_is_hidden_para in tparavarsym(para2[i2]).varoptions) do
  1208. inc(i2);
  1209. end;
  1210. end;
  1211. { when both lists are empty then the parameters are equal. Also
  1212. when one list is empty and the other has a parameter with default
  1213. value assigned then the parameters are also equal }
  1214. if ((i1>=para1.count) and (i2>=para2.count)) or
  1215. ((cpo_allowdefaults in cpoptions) and
  1216. (((i1<para1.count) and assigned(tparavarsym(para1[i1]).defaultconstsym)) or
  1217. ((i2<para2.count) and assigned(tparavarsym(para2[i2]).defaultconstsym)))) then
  1218. compare_paras:=lowesteq;
  1219. end;
  1220. function proc_to_procvar_equal(def1:tabstractprocdef;def2:tprocvardef;methoderr:boolean):tequaltype;
  1221. var
  1222. eq : tequaltype;
  1223. po_comp : tprocoptions;
  1224. begin
  1225. proc_to_procvar_equal:=te_incompatible;
  1226. if not(assigned(def1)) or not(assigned(def2)) then
  1227. exit;
  1228. { check for method pointer }
  1229. if (def1.is_methodpointer xor def2.is_methodpointer) or
  1230. (def1.is_addressonly xor def2.is_addressonly) then
  1231. begin
  1232. if methoderr then
  1233. Message(type_e_no_method_and_procedure_not_compatible);
  1234. exit;
  1235. end;
  1236. { check return value and options, methodpointer is already checked }
  1237. po_comp:=[po_staticmethod,po_interrupt,
  1238. po_iocheck,po_varargs];
  1239. if (m_delphi in aktmodeswitches) then
  1240. exclude(po_comp,po_varargs);
  1241. if (def1.proccalloption=def2.proccalloption) and
  1242. ((po_comp * def1.procoptions)= (po_comp * def2.procoptions)) and
  1243. equal_defs(def1.rettype.def,def2.rettype.def) then
  1244. begin
  1245. { return equal type based on the parameters, but a proc->procvar
  1246. is never exact, so map an exact match of the parameters to
  1247. te_equal }
  1248. eq:=compare_paras(def1.paras,def2.paras,cp_procvar,[]);
  1249. if eq=te_exact then
  1250. eq:=te_equal;
  1251. proc_to_procvar_equal:=eq;
  1252. end;
  1253. end;
  1254. end.
  1255. {
  1256. $Log$
  1257. Revision 1.61 2004-11-29 17:32:56 peter
  1258. * prevent some IEs with delphi methodpointers
  1259. Revision 1.60 2004/11/26 22:33:54 peter
  1260. * don't allow pointer(ordinal) typecast in fpc mode, only allow it
  1261. for delphi and for internal use
  1262. Revision 1.59 2004/11/15 23:35:31 peter
  1263. * tparaitem removed, use tparavarsym instead
  1264. * parameter order is now calculated from paranr value in tparavarsym
  1265. Revision 1.58 2004/11/08 22:09:58 peter
  1266. * tvarsym splitted
  1267. Revision 1.57 2004/11/01 10:31:48 peter
  1268. * procvar arguments need to be at least equal
  1269. Revision 1.56 2004/11/01 08:02:26 peter
  1270. * remove previous patch
  1271. Revision 1.55 2004/10/31 22:05:25 peter
  1272. * only allow ordinal-pointer for same size
  1273. Revision 1.54 2004/10/31 21:45:02 peter
  1274. * generic tlocation
  1275. * move tlocation to cgutils
  1276. Revision 1.53 2004/09/21 15:52:35 peter
  1277. * prefer pchar-string over pchar-pointer
  1278. Revision 1.52 2004/09/16 16:32:44 peter
  1279. * dynarr-pointer is allowed under delphi
  1280. Revision 1.51 2004/06/20 08:55:29 florian
  1281. * logs truncated
  1282. Revision 1.50 2004/04/12 11:26:10 peter
  1283. * voidpointer can be converted to dynarray
  1284. Revision 1.49 2004/03/04 17:22:32 peter
  1285. * use defs_equal when comparing pointer types
  1286. Revision 1.48 2004/03/03 22:02:16 peter
  1287. * also compare calling convention in proc_to_procvar_equal
  1288. Revision 1.47 2004/02/24 16:12:39 peter
  1289. * operator overload chooses rewrite
  1290. * overload choosing is now generic and moved to htypechk
  1291. Revision 1.46 2004/02/15 12:18:22 peter
  1292. * allow real_2_real conversion for realconstn, fixes 2971
  1293. }