Przeglądaj źródła

* overloading supported in child classes
* fixed parsing of classes with private and virtual and overloaded
so it is compatible with delphi

peter 24 lat temu
rodzic
commit
faf78ea813
9 zmienionych plików z 457 dodań i 365 usunięć
  1. 6 48
      compiler/cclasses.pas
  2. 44 45
      compiler/cutils.pas
  3. 80 1
      compiler/ncal.pas
  4. 170 170
      compiler/nobj.pas
  5. 33 29
      compiler/psystem.pas
  6. 70 3
      compiler/symdef.pas
  7. 19 52
      compiler/symsym.pas
  8. 19 16
      compiler/symtable.pas
  9. 16 1
      compiler/symtype.pas

+ 6 - 48
compiler/cclasses.pas

@@ -279,56 +279,9 @@ interface
        end;
 
 
-    { Speed/Hash value }
-    Function GetSpeedValue(Const s:String):cardinal;
-
-
 implementation
 
 
-{*****************************************************************************
-                               GetSpeedValue
-*****************************************************************************}
-
-{$ifdef ver1_0}
-  {$R-}
-{$endif}
-
-    var
-      Crc32Tbl : array[0..255] of cardinal;
-
-    procedure MakeCRC32Tbl;
-      var
-        crc : cardinal;
-        i,n : integer;
-      begin
-        for i:=0 to 255 do
-         begin
-           crc:=i;
-           for n:=1 to 8 do
-            if odd(longint(crc)) then
-             crc:=cardinal(crc shr 1) xor cardinal($edb88320)
-            else
-             crc:=cardinal(crc shr 1);
-           Crc32Tbl[i]:=crc;
-         end;
-      end;
-
-
-    Function GetSpeedValue(Const s:String):cardinal;
-      var
-        i : integer;
-        InitCrc : cardinal;
-      begin
-        if Crc32Tbl[1]=0 then
-         MakeCrc32Tbl;
-        InitCrc:=cardinal($ffffffff);
-        for i:=1 to Length(s) do
-         InitCrc:=Crc32Tbl[byte(InitCrc) xor ord(s[i])] xor (InitCrc shr 8);
-        GetSpeedValue:=InitCrc;
-      end;
-
-
 {*****************************************************************************
                                     Memory debug
 *****************************************************************************}
@@ -1775,7 +1728,12 @@ end;
 end.
 {
   $Log$
-  Revision 1.8  2001-11-05 14:16:25  jonas
+  Revision 1.9  2001-11-18 18:43:13  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.8  2001/11/05 14:16:25  jonas
     * reduced memory usage by about 10% and increased speed by about 15%
 
   Revision 1.7  2001/05/04 19:50:04  peter

+ 44 - 45
compiler/cutils.pas

@@ -89,7 +89,7 @@ uses
     function pstring2pchar(p : pstring) : pchar;
 
 { Speed/Hash value }
-function getspeedvalue(const s : string) : longint;
+    Function GetSpeedValue(Const s:String):cardinal;
 
 { Ansistring (pchar+length) support }
 procedure ansistringdispose(var p : pchar;length : longint);
@@ -633,49 +633,43 @@ uses
                                GetSpeedValue
 *****************************************************************************}
 
-var
-  Crc32Tbl : array[0..255] of longint;
-
-procedure MakeCRC32Tbl;
-var
-  crc : longint;
-  i,n : byte;
-begin
-  for i:=0 to 255 do
-   begin
-     crc:=i;
-     for n:=1 to 8 do
-      if odd(crc) then
-       crc:=(crc shr 1) xor longint($edb88320)
-      else
-       crc:=crc shr 1;
-     Crc32Tbl[i]:=crc;
-   end;
-end;
-
-
-{$ifopt R+}
-  {$define Range_check_on}
-{$endif opt R+}
-
-{$R- needed here }
-{CRC 32}
-Function GetSpeedValue(Const s:String):longint;
-var
-  i,InitCrc : longint;
-begin
-  if Crc32Tbl[1]=0 then
-   MakeCrc32Tbl;
-  InitCrc:=-1;
-  for i:=1 to Length(s) do
-   InitCrc:=Crc32Tbl[byte(InitCrc) xor ord(s[i])] xor (InitCrc shr 8);
-  GetSpeedValue:=InitCrc;
-end;
-
-{$ifdef Range_check_on}
-  {$R+}
-  {$undef Range_check_on}
-{$endif Range_check_on}
+{$ifdef ver1_0}
+  {$R-}
+{$endif}
+
+    var
+      Crc32Tbl : array[0..255] of cardinal;
+
+    procedure MakeCRC32Tbl;
+      var
+        crc : cardinal;
+        i,n : integer;
+      begin
+        for i:=0 to 255 do
+         begin
+           crc:=i;
+           for n:=1 to 8 do
+            if odd(longint(crc)) then
+             crc:=cardinal(crc shr 1) xor cardinal($edb88320)
+            else
+             crc:=cardinal(crc shr 1);
+           Crc32Tbl[i]:=crc;
+         end;
+      end;
+
+
+    Function GetSpeedValue(Const s:String):cardinal;
+      var
+        i : integer;
+        InitCrc : cardinal;
+      begin
+        if Crc32Tbl[1]=0 then
+         MakeCrc32Tbl;
+        InitCrc:=cardinal($ffffffff);
+        for i:=1 to Length(s) do
+         InitCrc:=Crc32Tbl[byte(InitCrc) xor ord(s[i])] xor (InitCrc shr 8);
+        GetSpeedValue:=InitCrc;
+      end;
 
 
 {*****************************************************************************
@@ -756,7 +750,12 @@ initialization
 end.
 {
   $Log$
-  Revision 1.11  2001-09-05 15:20:26  jonas
+  Revision 1.12  2001-11-18 18:43:13  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.11  2001/09/05 15:20:26  jonas
     * ispowerf2 now works with 64bit ints and should be faster
 
   Revision 1.10  2001/08/04 11:06:30  peter

+ 80 - 1
compiler/ncal.pas

@@ -147,6 +147,66 @@ implementation
       end;
 
 
+    procedure search_class_overloads(aprocsym : tprocsym);
+    { searches n in symtable of pd and all anchestors }
+      var
+        speedvalue : cardinal;
+        srsym      : tprocsym;
+        s          : string;
+        found      : boolean;
+        srpdl,pdl  : pprocdeflist;
+        objdef     : tobjectdef;
+      begin
+        if aprocsym.overloadchecked then
+         exit;
+        aprocsym.overloadchecked:=true;
+        if (aprocsym.owner.symtabletype<>objectsymtable) then
+         internalerror(200111021);
+        objdef:=tobjectdef(aprocsym.owner.defowner);
+        { we start in the parent }
+        if not assigned(objdef.childof) then
+         exit;
+        objdef:=objdef.childof;
+        s:=aprocsym.name;
+        speedvalue:=getspeedvalue(s);
+        while assigned(objdef) do
+         begin
+           srsym:=tprocsym(objdef.symtable.speedsearch(s,speedvalue));
+           if assigned(srsym) then
+            begin
+              if (srsym.typ<>procsym) then
+               internalerror(200111022);
+              if srsym.check_private then
+               begin
+                 srpdl:=srsym.defs;
+                 while assigned(srpdl) do
+                  begin
+                    found:=false;
+                    pdl:=aprocsym.defs;
+                    while assigned(pdl) do
+                     begin
+                       if equal_paras(pdl^.def.para,srpdl^.def.para,cp_all) then
+                        begin
+                          found:=true;
+                          break;
+                        end;
+                       pdl:=pdl^.next;
+                     end;
+                    if not found then
+                     aprocsym.addprocdef(srpdl^.def);
+                    srpdl:=srpdl^.next;
+                  end;
+                 { we can stop if the overloads were already added
+                  for the found symbol }
+                 if srsym.overloadchecked then
+                  break;
+               end;
+            end;
+           { next parent }
+           objdef:=objdef.childof;
+         end;
+      end;
+
 
 {****************************************************************************
                              TCALLPARANODE
@@ -801,6 +861,20 @@ implementation
               { do we know the procedure to call ? }
               if not(assigned(procdefinition)) then
                 begin
+                   { when the definition has overload directive set, we search for
+                      overloaded definitions }
+                   if (not symtableprocentry.overloadchecked) and
+                      (
+                       (m_fpc in aktmodeswitches) or
+                       ((po_overload in symtableprocentry.defs^.def.procoptions) and
+                        (m_delphi in aktmodeswitches))
+                      ) then
+                    begin
+                      { for methods search in the class tree }
+                      if (symtableprocentry.owner.symtabletype=objectsymtable) then
+                        search_class_overloads(symtableprocentry);
+                    end;
+
                    { link all procedures which have the same # of parameters }
                    pd:=symtableprocentry.defs;
                    while assigned(pd) do
@@ -1693,7 +1767,12 @@ begin
 end.
 {
   $Log$
-  Revision 1.55  2001-11-02 23:16:50  peter
+  Revision 1.56  2001-11-18 18:43:13  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.55  2001/11/02 23:16:50  peter
     * removed obsolete chainprocsym and test_procsym code
 
   Revision 1.54  2001/11/02 22:58:01  peter

+ 170 - 170
compiler/nobj.pas

@@ -42,6 +42,7 @@ interface
       pprocdefcoll = ^tprocdefcoll;
       tprocdefcoll = record
          data : tprocdef;
+         hidden : boolean;
          next : pprocdefcoll;
       end;
 
@@ -221,7 +222,6 @@ implementation
       var
          hp : pprocdeflist;
          pt : pprocdeftree;
-
       begin
          if tsym(p).typ=procsym then
            begin
@@ -505,208 +505,203 @@ implementation
          hp : pprocdeflist;
          symcoll : psymcoll;
          _name : string;
-         stored : boolean;
-
-      { creates a new entry in the procsym list }
-      procedure newentry;
-
-        begin
-           { if not, generate a new symbol item }
-           new(symcoll);
-           symcoll^.name:=stringdup(sym.name);
-           symcoll^.next:=wurzel;
-           symcoll^.data:=nil;
-           wurzel:=symcoll;
-
-           { inserts all definitions }
-           hp:=tprocsym(sym).defs;
-           while assigned(hp) do
-             begin
-                new(procdefcoll);
-                procdefcoll^.data:=hp^.def;
-                procdefcoll^.next:=symcoll^.data;
-                symcoll^.data:=procdefcoll;
-
-                { if it's a virtual method }
-                if (po_virtualmethod in hp^.def.procoptions) then
-                  begin
-                     { then it gets a number ... }
-                     hp^.def.extnumber:=nextvirtnumber;
-                     { and we inc the number }
-                     inc(nextvirtnumber);
-                     has_virtual_method:=true;
-                  end;
-
-                if (hp^.def.proctypeoption=potype_constructor) then
-                  has_constructor:=true;
-
-                { check, if a method should be overridden }
-                if (po_overridingmethod in hp^.def.procoptions) then
-                  MessagePos1(hp^.def.fileinfo,parser_e_nothing_to_be_overridden,_class.objname^+'.'+_name+hp^.def.demangled_paras);
-                { next overloaded method }
-                hp:=hp^.next;
-             end;
-        end;
-
-      procedure newdefentry;
 
+      procedure newdefentry(pd:tprocdef);
         begin
            new(procdefcoll);
-           procdefcoll^.data:=hp^.def;
+           procdefcoll^.data:=pd;
            procdefcoll^.next:=symcoll^.data;
            symcoll^.data:=procdefcoll;
 
            { if it's a virtual method }
-           if (po_virtualmethod in hp^.def.procoptions) then
+           if (po_virtualmethod in pd.procoptions) then
              begin
                 { then it gets a number ... }
-                hp^.def.extnumber:=nextvirtnumber;
+                pd.extnumber:=nextvirtnumber;
                 { and we inc the number }
                 inc(nextvirtnumber);
                 has_virtual_method:=true;
              end;
 
-           if (hp^.def.proctypeoption=potype_constructor) then
+           if (pd.proctypeoption=potype_constructor) then
              has_constructor:=true;
 
            { check, if a method should be overridden }
-           if (po_overridingmethod in hp^.def.procoptions) then
-             MessagePos1(hp^.def.fileinfo,parser_e_nothing_to_be_overridden,_class.objname^+'.'+_name+hp^.def.demangled_paras);
+           if (pd._class=_class) and
+              (po_overridingmethod in pd.procoptions) then
+             MessagePos1(pd.fileinfo,parser_e_nothing_to_be_overridden,pd.fullprocname);
+        end;
+
+      { creates a new entry in the procsym list }
+      procedure newentry;
+        begin
+           { if not, generate a new symbol item }
+           new(symcoll);
+           symcoll^.name:=stringdup(sym.name);
+           symcoll^.next:=wurzel;
+           symcoll^.data:=nil;
+           wurzel:=symcoll;
+
+           { inserts all definitions }
+           hp:=tprocsym(sym).defs;
+           while assigned(hp) do
+             begin
+                newdefentry(hp^.def);
+                hp:=hp^.next;
+             end;
         end;
 
       label
          handlenextdef;
-
+      var
+         pd : tprocdef;
+         pdoverload : boolean;
       begin
          { put only sub routines into the VMT }
          if tsym(sym).typ=procsym then
            begin
+              { skip private symbols that can not been seen }
+              if not tsym(sym).check_private then
+               exit;
+
+              { check the current list of symbols }
               _name:=sym.name;
               symcoll:=wurzel;
               while assigned(symcoll) do
-                begin
-                   { does the symbol already exist in the list ? }
-                   if _name=symcoll^.name^ then
+               begin
+                 { does the symbol already exist in the list ? }
+                 if _name=symcoll^.name^ then
+                  begin
+                    { walk through all defs of the symbol }
+                    hp:=tprocsym(sym).defs;
+                    while assigned(hp) do
                      begin
-                        { walk through all defs of the symbol }
-                        hp:=tprocsym(sym).defs;
-                        while assigned(hp) do
-                          begin
-                             { compare with all stored definitions }
-                             procdefcoll:=symcoll^.data;
-                             stored:=false;
-                             while assigned(procdefcoll) do
-                               begin
-                                  { compare parameters }
-                                  if equal_paras(procdefcoll^.data.para,hp^.def.para,cp_all) and
-                                     (
-                                       (po_virtualmethod in procdefcoll^.data.procoptions) or
-                                       (po_virtualmethod in hp^.def.procoptions)
-                                     ) then
-                                    begin { same parameters }
-                                       { wenn sie gleich sind }
-                                       { und eine davon virtual deklariert ist }
-                                       { Fehler falls nur eine VIRTUAL }
-                                       if (po_virtualmethod in procdefcoll^.data.procoptions)<>
-                                          (po_virtualmethod in hp^.def.procoptions) then
+                       pd:=hp^.def;
+                       if pd.procsym=sym then
+                        begin
+                          pdoverload:=(po_overload in pd.procoptions) or
+                                      (m_fpc in aktmodeswitches);
+
+                          { compare with all stored definitions }
+                          procdefcoll:=symcoll^.data;
+                          while assigned(procdefcoll) do
+                            begin
+                               { compare only if the definition is not hidden }
+                               if not procdefcoll^.hidden then
+                                begin
+                                  { check if one of the two methods has virtual }
+                                  if (po_virtualmethod in procdefcoll^.data.procoptions) or
+                                     (po_virtualmethod in pd.procoptions) then
+                                   begin
+                                     { if the current definition has no virtual then hide the
+                                       old virtual if the new definition has the same arguments or
+                                       has no overload directive }
+                                     if not(po_virtualmethod in pd.procoptions) then
+                                      begin
+                                        if not pdoverload or
+                                           equal_paras(procdefcoll^.data.para,pd.para,cp_all) then
                                          begin
-                                            { in classes, we hide the old method }
-                                            if is_class(_class) then
-                                              begin
-                                                 { warn only if it is the first time,
-                                                   we hide the method }
-                                                 if _class=hp^.def._class then
-                                                   Message1(parser_w_should_use_override,hp^.def.fullprocname);
-                                              end
-                                            else
-                                              if _class=hp^.def._class then
-                                                begin
-                                                   if (po_virtualmethod in procdefcoll^.data.procoptions) then
-                                                     Message1(parser_w_overloaded_are_not_both_virtual,
-                                                              hp^.def.fullprocname)
-                                                   else
-                                                     Message1(parser_w_overloaded_are_not_both_non_virtual,
-                                                              hp^.def.fullprocname);
-                                                end;
-                                            { was newentry; exit; (FK) }
-                                            newdefentry;
-                                            goto handlenextdef;
+                                           procdefcoll^.hidden:=true;
+                                           if _class=pd._class then
+                                             MessagePos1(pd.fileinfo,parser_w_should_use_override,pd.fullprocname);
+                                         end;
+                                      end
+                                     { if both are virtual we check the header }
+                                     else if (po_virtualmethod in pd.procoptions) and
+                                             (po_virtualmethod in procdefcoll^.data.procoptions) then
+                                      begin
+                                        { new one has not override }
+                                        if is_class(_class) and
+                                           not(po_overridingmethod in pd.procoptions) then
+                                         begin
+                                           { we start a new virtual tree, hide the old }
+                                           if not pdoverload or
+                                              equal_paras(procdefcoll^.data.para,pd.para,cp_all) then
+                                            begin
+                                              procdefcoll^.hidden:=true;
+                                              if _class=pd._class then
+                                                MessagePos1(pd.fileinfo,parser_w_should_use_override,pd.fullprocname);
+                                            end;
+                                         end
+                                        { same parameters }
+                                        else if (equal_paras(procdefcoll^.data.para,pd.para,cp_all)) then
+                                         begin
+                                           { overload is inherited }
+                                           if (po_overload in procdefcoll^.data.procoptions) then
+                                            include(pd.procoptions,po_overload);
+
+                                           { the flags have to match except abstract and override }
+                                           { only if both are virtual !!  }
+                                           if (procdefcoll^.data.proccalloption<>pd.proccalloption) or
+                                               (procdefcoll^.data.proctypeoption<>pd.proctypeoption) or
+                                               ((procdefcoll^.data.procoptions-
+                                                   [po_abstractmethod,po_overridingmethod,po_assembler,po_overload])<>
+                                                (pd.procoptions-[po_abstractmethod,po_overridingmethod,po_assembler,po_overload])) then
+                                              MessagePos1(pd.fileinfo,parser_e_header_dont_match_forward,pd.fullprocname);
+
+                                           { error, if the return types aren't equal }
+                                           if not(is_equal(procdefcoll^.data.rettype.def,pd.rettype.def)) and
+                                              not((procdefcoll^.data.rettype.def.deftype=objectdef) and
+                                               (pd.rettype.def.deftype=objectdef) and
+                                               is_class(procdefcoll^.data.rettype.def) and
+                                               is_class(pd.rettype.def) and
+                                               (tobjectdef(pd.rettype.def).is_related(
+                                                   tobjectdef(procdefcoll^.data.rettype.def)))) then
+                                             Message2(parser_e_overridden_methods_not_same_ret,pd.fullprocnamewithret,
+                                                      procdefcoll^.data.fullprocnamewithret);
+
+                                           { now set the number }
+                                           pd.extnumber:=procdefcoll^.data.extnumber;
+                                           { and exchange }
+                                           procdefcoll^.data:=pd;
+                                           goto handlenextdef;
                                          end
-                                       else
-                                       { the flags have to match      }
-                                       { except abstract and override }
-                                       { only if both are virtual !!  }
-                                       if (procdefcoll^.data.proccalloption<>hp^.def.proccalloption) or
-                                          (procdefcoll^.data.proctypeoption<>hp^.def.proctypeoption) or
-                                          ((procdefcoll^.data.procoptions-
-                                              [po_abstractmethod,po_overridingmethod,po_assembler,po_overload])<>
-                                           (hp^.def.procoptions-[po_abstractmethod,po_overridingmethod,po_assembler,po_overload])) then
-                                         Message1(parser_e_header_dont_match_forward,hp^.def.fullprocname);
-
-                                       { check, if the overridden directive is set }
-                                       { (povirtualmethod is set! }
-
-                                       { class ? }
-                                       if is_class(_class) and
-                                          not(po_overridingmethod in hp^.def.procoptions) then
+                                        { different parameters }
+                                        else
                                          begin
-                                            { warn only if it is the first time,
-                                              we hide the method }
-                                            if _class=hp^.def._class then
-                                              Message1(parser_w_should_use_override,hp^.def.fullprocname);
-                                            { was newentry; (FK) }
-                                            newdefentry;
-                                            exit;
+                                           { when we got an override directive then can search futher for
+                                             the procedure to override.
+                                             If we are starting a new virtual tree then hide the old tree }
+                                           if not(po_overridingmethod in pd.procoptions) and
+                                              not pdoverload then
+                                            begin
+                                              procdefcoll^.hidden:=true;
+                                              if _class=pd._class then
+                                                MessagePos1(pd.fileinfo,parser_w_should_use_override,pd.fullprocname);
+                                            end;
                                          end;
-
-                                       { error, if the return types aren't equal }
-                                       if not(is_equal(procdefcoll^.data.rettype.def,hp^.def.rettype.def)) and
-                                         not((procdefcoll^.data.rettype.def.deftype=objectdef) and
-                                           (hp^.def.rettype.def.deftype=objectdef) and
-                                           is_class(procdefcoll^.data.rettype.def) and
-                                           is_class(hp^.def.rettype.def) and
-                                           (tobjectdef(hp^.def.rettype.def).is_related(
-                                               tobjectdef(procdefcoll^.data.rettype.def)))) then
-                                         Message2(parser_e_overridden_methods_not_same_ret,hp^.def.fullprocnamewithret,
-                                           procdefcoll^.data.fullprocnamewithret);
-
-
-                                       { now set the number }
-                                       hp^.def.extnumber:=procdefcoll^.data.extnumber;
-                                       { and exchange }
-                                       procdefcoll^.data:=hp^.def;
-                                       stored:=true;
-                                       goto handlenextdef;
-                                    end;  { same parameters }
-                                  procdefcoll:=procdefcoll^.next;
-                               end;
-                             { if it isn't saved in the list }
-                             { we create a new entry         }
-                             if not(stored) then
-                               begin
-                                  new(procdefcoll);
-                                  procdefcoll^.data:=hp^.def;
-                                  procdefcoll^.next:=symcoll^.data;
-                                  symcoll^.data:=procdefcoll;
-                                  { if the method is virtual ... }
-                                  if (po_virtualmethod in hp^.def.procoptions) then
-                                    begin
-                                       { ... it will get a number }
-                                       hp^.def.extnumber:=nextvirtnumber;
-                                       inc(nextvirtnumber);
-                                    end;
-                                  { check, if a method should be overridden }
-                                  if (po_overridingmethod in hp^.def.procoptions) then
-                                   MessagePos1(hp^.def.fileinfo,parser_e_nothing_to_be_overridden,
-                                     hp^.def.fullprocname);
-                               end;
-                          handlenextdef:
-                             hp:=hp^.next;
-                          end;
-                        exit;
+                                      end
+                                     else
+                                      begin
+                                        { the new definition is virtual and the old static, we hide the old one
+                                          if the new defintion has not the overload directive }
+                                        if not pdoverload or
+                                           equal_paras(procdefcoll^.data.para,pd.para,cp_all) then
+                                         procdefcoll^.hidden:=true;
+                                      end;
+                                   end
+                                  else
+                                   begin
+                                     { both are static, we hide the old one if the new defintion
+                                       has not the overload directive }
+                                     if equal_paras(procdefcoll^.data.para,pd.para,cp_all) or
+                                        not pdoverload then
+                                      procdefcoll^.hidden:=true;
+                                   end;
+                                end; { not hidden }
+                               procdefcoll:=procdefcoll^.next;
+                            end;
+
+                          { if it isn't saved in the list we create a new entry }
+                          newdefentry(pd);
+                        end;
+                     handlenextdef:
+                       hp:=hp^.next;
                      end;
-                   symcoll:=symcoll^.next;
-                end;
+                    exit;
+                  end;
+                 symcoll:=symcoll^.next;
+               end;
              newentry;
            end;
       end;
@@ -1281,7 +1276,12 @@ initialization
 end.
 {
   $Log$
-  Revision 1.8  2001-11-02 22:58:02  peter
+  Revision 1.9  2001-11-18 18:43:14  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.8  2001/11/02 22:58:02  peter
     * procsym definition rewrite
 
   Revision 1.7  2001/10/25 21:22:35  peter

+ 33 - 29
compiler/psystem.pas

@@ -109,6 +109,32 @@ var
   vmtarraytype : ttype;
   vmtsymtable  : tsymtable;
 begin
+{ Normal types }
+  addtype('Single',s32floattype);
+  addtype('Double',s64floattype);
+  addtype('Extended',s80floattype);
+  addtype('Real',s64floattype);
+{$ifdef i386}
+  adddef('Comp',tfloatdef.create(s64comp));
+{$endif}
+  addtype('Pointer',voidpointertype);
+  addtype('FarPointer',voidfarpointertype);
+  addtype('ShortString',cshortstringtype);
+  addtype('LongString',clongstringtype);
+  addtype('AnsiString',cansistringtype);
+  addtype('WideString',cwidestringtype);
+  addtype('Boolean',booltype);
+  addtype('ByteBool',booltype);
+  adddef('WordBool',torddef.create(bool16bit,0,1));
+  adddef('LongBool',torddef.create(bool32bit,0,1));
+  addtype('Char',cchartype);
+  addtype('WideChar',cwidechartype);
+  adddef('Text',tfiledef.createtext);
+  addtype('Cardinal',u32bittype);
+  addtype('QWord',cu64bittype);
+  addtype('Int64',cs64bittype);
+  adddef('TypedFile',tfiledef.createtyped(voidtype));
+  addtype('Variant',cvarianttype);
 { Internal types }
   addtype('$formal',cformaltype);
   addtype('$void',voidtype);
@@ -135,8 +161,7 @@ begin
   addtype('$s32real',s32floattype);
   addtype('$s64real',s64floattype);
   addtype('$s80real',s80floattype);
-  { Add a type for virtual method tables in lowercase }
-  { so it isn't reachable!                            }
+{ Add a type for virtual method tables }
   vmtsymtable:=trecordsymtable.create;
   vmttype.setdef(trecorddef.create(vmtsymtable));
   pvmttype.setdef(tpointerdef.create(vmttype));
@@ -153,32 +178,6 @@ begin
   addtype('$vtblarray',vmtarraytype);
 { Add functions that require compiler magic }
   insertinternsyms(p);
-{ Normal types }
-  addtype('Single',s32floattype);
-  addtype('Double',s64floattype);
-  addtype('Extended',s80floattype);
-  addtype('Real',s64floattype);
-{$ifdef i386}
-  adddef('Comp',tfloatdef.create(s64comp));
-{$endif}
-  addtype('Pointer',voidpointertype);
-  addtype('FarPointer',voidfarpointertype);
-  addtype('ShortString',cshortstringtype);
-  addtype('LongString',clongstringtype);
-  addtype('AnsiString',cansistringtype);
-  addtype('WideString',cwidestringtype);
-  addtype('Boolean',booltype);
-  addtype('ByteBool',booltype);
-  adddef('WordBool',torddef.create(bool16bit,0,1));
-  adddef('LongBool',torddef.create(bool32bit,0,1));
-  addtype('Char',cchartype);
-  addtype('WideChar',cwidechartype);
-  adddef('Text',tfiledef.createtext);
-  addtype('Cardinal',u32bittype);
-  addtype('QWord',cu64bittype);
-  addtype('Int64',cs64bittype);
-  adddef('TypedFile',tfiledef.createtyped(voidtype));
-  addtype('Variant',cvarianttype);
 end;
 
 
@@ -277,7 +276,12 @@ end;
 end.
 {
   $Log$
-  Revision 1.20  2001-10-24 11:51:39  marco
+  Revision 1.21  2001-11-18 18:43:14  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.20  2001/10/24 11:51:39  marco
    * Make new/dispose system functions instead of keywords
 
   Revision 1.19  2001/08/30 20:13:53  peter

+ 70 - 3
compiler/symdef.pas

@@ -458,6 +458,9 @@ interface
        tprocdef = class(tabstractprocdef)
        private
           _mangledname : pstring;
+{$ifdef GDB}
+          isstabwritten : boolean;
+{$endif GDB}
        public
           extnumber  : longint;
           messageinf : tmessageinf;
@@ -3269,6 +3272,9 @@ implementation
          regvarinfo := nil;
          count:=false;
          is_used:=false;
+{$ifdef GDB}
+         isstabwritten := false;
+{$endif GDB}
       end;
 
 
@@ -3334,6 +3340,9 @@ implementation
          refcount:=0;
          count:=true;
          is_used:=false;
+{$ifdef GDB}
+         isstabwritten := false;
+{$endif GDB}
       end;
 
 
@@ -3587,6 +3596,8 @@ implementation
 
 
 {$ifdef GDB}
+
+{$ifdef unused}
 {    procedure addparaname(p : tsym);
       var vs : char;
       begin
@@ -3630,11 +3641,62 @@ implementation
       stabstring := strnew(stabrecstring);
       freemem(stabrecstring,1024);
       end;
+{$endif unused}
 
+    function tprocdef.stabstring: pchar;
+     Var RType : Char;
+         Obj,Info : String;
+         stabsstr : string;
+         p : pchar;
+    begin
+      obj := procsym.name;
+      info := '';
+      if tprocsym(procsym).is_global then
+       RType := 'F'
+      else
+       RType := 'f';
+     if assigned(owner) then
+      begin
+        if (owner.symtabletype = objectsymtable) then
+         obj := upper(owner.name^)+'__'+procsym.name;
+        { this code was correct only as long as the local symboltable
+          of the parent had the same name as the function
+          but this is no true anymore !! PM
+        if (owner.symtabletype=localsymtable) and assigned(owner.name) then
+         info := ','+name+','+owner.name^;  }
+        if (owner.symtabletype=localsymtable) and
+           assigned(owner.defowner) and
+           assigned(tprocdef(owner.defowner).procsym) then
+          info := ','+procsym.name+','+tprocdef(owner.defowner).procsym.name;
+      end;
+     stabsstr:=mangledname;
+     getmem(p,length(stabsstr)+255);
+     strpcopy(p,'"'+obj+':'+RType
+           +tstoreddef(rettype.def).numberstring+info+'",'+tostr(n_function)
+           +',0,'+
+           tostr(fileinfo.line)
+           +',');
+     strpcopy(strend(p),stabsstr);
+     stabstring:=strnew(p);
+     freemem(p,length(stabsstr)+255);
+    end;
 
     procedure tprocdef.concatstabto(asmlist : taasmoutput);
-      begin
-      end;
+    begin
+      if (proccalloption=pocall_internproc) then
+        exit;
+      if not isstabwritten then
+        asmList.concat(Tai_stabs.Create(stabstring));
+      isstabwritten := true;
+      if assigned(parast) then
+        tstoredsymtable(parast).concatstabto(asmlist);
+      { local type defs and vars should not be written
+        inside the main proc stab }
+      if assigned(localst) and
+         (lexlevel>main_program_level) then
+        tstoredsymtable(localst).concatstabto(asmlist);
+      is_def_stab_written := written;
+    end;
 {$endif GDB}
 
 
@@ -5396,7 +5458,12 @@ implementation
 end.
 {
   $Log$
-  Revision 1.56  2001-11-18 18:27:57  florian
+  Revision 1.57  2001-11-18 18:43:14  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.56  2001/11/18 18:27:57  florian
     * publishing of qword, int64 and widechar properties is now possible
 
   Revision 1.55  2001/11/02 22:58:06  peter

+ 19 - 52
compiler/symsym.pas

@@ -100,6 +100,7 @@ interface
        tprocsym = class(tstoredsym)
           defs      : pprocdeflist; { linked list of overloaded procdefs }
           is_global : boolean;
+          overloadchecked : boolean;
           constructor create(const n : string);
           constructor load(ppufile:tcompilerppufile);
           destructor destroy;override;
@@ -678,7 +679,8 @@ implementation
          typ:=procsym;
          defs:=nil;
          owner:=nil;
-         is_global := false;
+         is_global:=false;
+         overloadchecked:=false;
       end;
 
 
@@ -695,7 +697,8 @@ implementation
             break;
            addprocdef(pd);
          until false;
-         is_global := false;
+         is_global:=false;
+         overloadchecked:=false;
       end;
 
 
@@ -770,7 +773,10 @@ implementation
          p:=defs;
          while assigned(p) do
            begin
-             ppufile.putderef(p^.def);
+             { only write the proc definitions that belong
+               to this procsym }
+             if (p^.def.procsym=self) then
+              ppufile.putderef(p^.def);
              p:=p^.next;
            end;
          ppufile.putderef(nil);
@@ -836,57 +842,13 @@ implementation
 
 {$ifdef GDB}
     function tprocsym.stabstring : pchar;
-     Var RetType : Char;
-         Obj,Info : String;
-         stabsstr : string;
-         p : pchar;
-    begin
-      obj := name;
-      info := '';
-      if is_global then
-       RetType := 'F'
-      else
-       RetType := 'f';
-     if assigned(owner) then
-      begin
-        if (owner.symtabletype = objectsymtable) then
-         obj := upper(owner.name^)+'__'+name;
-        { this code was correct only as long as the local symboltable
-          of the parent had the same name as the function
-          but this is no true anymore !! PM
-        if (owner.symtabletype=localsymtable) and assigned(owner.name) then
-         info := ','+name+','+owner.name^;  }
-        if (owner.symtabletype=localsymtable) and
-           assigned(owner.defowner) and
-           assigned(tprocdef(owner.defowner).procsym) then
-          info := ','+name+','+tprocdef(owner.defowner).procsym.name;
-      end;
-     stabsstr:=defs^.def.mangledname;
-     getmem(p,length(stabsstr)+255);
-     strpcopy(p,'"'+obj+':'+RetType
-           +tstoreddef(defs^.def.rettype.def).numberstring+info+'",'+tostr(n_function)
-           +',0,'+
-           tostr(aktfilepos.line)
-           +',');
-     strpcopy(strend(p),stabsstr);
-     stabstring:=strnew(p);
-     freemem(p,length(stabsstr)+255);
-    end;
+      begin
+        internalerror(200111171);
+      end;
 
     procedure tprocsym.concatstabto(asmlist : taasmoutput);
     begin
-      if (defs^.def.proccalloption=pocall_internproc) then exit;
-      if not isstabwritten then
-        asmList.concat(Tai_stabs.Create(stabstring));
-      isstabwritten := true;
-      if assigned(defs^.def.parast) then
-        tstoredsymtable(defs^.def.parast).concatstabto(asmlist);
-      { local type defs and vars should not be written
-        inside the main proc stab }
-      if assigned(defs^.def.localst) and
-         (lexlevel>main_program_level) then
-        tstoredsymtable(defs^.def.localst).concatstabto(asmlist);
-      defs^.def.is_def_stab_written := written;
+      internalerror(200111172);
     end;
 {$endif GDB}
 
@@ -2477,7 +2439,12 @@ implementation
 end.
 {
   $Log$
-  Revision 1.26  2001-11-02 22:58:08  peter
+  Revision 1.27  2001-11-18 18:43:16  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.26  2001/11/02 22:58:08  peter
     * procsym definition rewrite
 
   Revision 1.25  2001/10/25 21:22:40  peter

+ 19 - 16
compiler/symtable.pas

@@ -1103,8 +1103,7 @@ implementation
               { but private ids can be reused }
               hsym:=search_class_member(tobjectdef(defowner),sym.name);
               if assigned(hsym) and
-                (not(sp_private in hsym.symoptions) or
-                 (hsym.owner.defowner.owner.unitid=0)) then
+                 hsym.check_private then
                begin
                  DuplicateSym(hsym);
                  exit;
@@ -1269,20 +1268,19 @@ implementation
            (sym.typ <> funcretsym) then
            begin
               hsym:=search_class_member(procinfo^._class,sym.name);
+              { private ids can be reused }
               if assigned(hsym) and
-                { private ids can be reused }
-                (not(sp_private in hsym.symoptions) or
-                 (hsym.owner.defowner.owner.unitid=0)) then
-                begin
-                   { delphi allows to reuse the names in a class, but not
-                     in object (tp7 compatible) }
-                   if not((m_delphi in aktmodeswitches) and
-                          is_class(procinfo^._class)) then
-                    begin
-                      DuplicateSym(hsym);
-                      exit;
-                    end;
-                end;
+                 hsym.check_private then
+               begin
+                 { delphi allows to reuse the names in a class, but not
+                   in object (tp7 compatible) }
+                 if not((m_delphi in aktmodeswitches) and
+                        is_class(procinfo^._class)) then
+                  begin
+                    DuplicateSym(hsym);
+                    exit;
+                  end;
+               end;
            end;
 
          inherited insert(sym);
@@ -2047,7 +2045,12 @@ implementation
 end.
 {
   $Log$
-  Revision 1.49  2001-11-02 23:16:52  peter
+  Revision 1.50  2001-11-18 18:43:17  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.49  2001/11/02 23:16:52  peter
     * removed obsolete chainprocsym and test_procsym code
 
   Revision 1.48  2001/11/02 22:58:08  peter

+ 16 - 1
compiler/symtype.pas

@@ -91,6 +91,7 @@ interface
          function  realname:string;
          procedure deref;virtual;abstract;
          function  gettypedef:tdef;virtual;
+         function  check_private:boolean;
       end;
 
 {************************************************
@@ -221,6 +222,15 @@ implementation
       end;
 
 
+    function tsym.check_private:boolean;
+      begin
+        { private symbols are allowed when we are in the same
+          module as they are defined }
+        check_private:=not(sp_private in symoptions) or
+                       (owner.defowner.owner.unitid=0);
+      end;
+
+
 {****************************************************************************
                                TRef
 ****************************************************************************}
@@ -517,7 +527,12 @@ implementation
 end.
 {
   $Log$
-  Revision 1.11  2001-11-02 22:58:08  peter
+  Revision 1.12  2001-11-18 18:43:18  peter
+    * overloading supported in child classes
+    * fixed parsing of classes with private and virtual and overloaded
+      so it is compatible with delphi
+
+  Revision 1.11  2001/11/02 22:58:08  peter
     * procsym definition rewrite
 
   Revision 1.10  2001/10/21 12:33:07  peter