Sfoglia il codice sorgente

* create the recorddef at the start when building an anonymous recorddef,
so that we can already refer to its def while we are sill parsing
individual elements

git-svn-id: branches/hlcgllvm@28750 -

Jonas Maebe 10 anni fa
parent
commit
864b36fbe5
4 ha cambiato i file con 42 aggiunte e 29 eliminazioni
  1. 9 8
      compiler/aasmcnst.pas
  2. 4 1
      compiler/llvm/llvmdef.pas
  3. 12 9
      compiler/llvm/nllvmtcon.pas
  4. 17 11
      compiler/symdef.pas

+ 9 - 8
compiler/aasmcnst.pas

@@ -151,8 +151,8 @@ type
         b) the def of the record should be automatically constructed based on
         b) the def of the record should be automatically constructed based on
            the types of the emitted fields
            the types of the emitted fields
      }
      }
-     procedure begin_anonymous_record; virtual;
-     function end_anonymous_record(const optionalname: string; packrecords: shortint): trecorddef; virtual;
+     procedure begin_anonymous_record(const optionalname: string; packrecords: shortint); virtual;
+     function end_anonymous_record: trecorddef; virtual;
 
 
      { The next group of routines are for constructing complex expressions.
      { The next group of routines are for constructing complex expressions.
        While parsing a typed constant these operators are encountered from
        While parsing a typed constant these operators are encountered from
@@ -538,7 +538,7 @@ implementation
        current_asmdata.getdatalabel(result.lab);
        current_asmdata.getdatalabel(result.lab);
        startlab:=result.lab;
        startlab:=result.lab;
        result.ofs:=0;
        result.ofs:=0;
-       begin_anonymous_record;
+       begin_anonymous_record('$'+get_dynstring_rec_name(stringtype,false,len),sizeof(pint));
        string_symofs:=get_string_symofs(stringtype,false);
        string_symofs:=get_string_symofs(stringtype,false);
        { encoding }
        { encoding }
        emit_tai(tai_const.create_16bit(encoding),u16inttype);
        emit_tai(tai_const.create_16bit(encoding),u16inttype);
@@ -621,7 +621,7 @@ implementation
        datatcb.maybe_begin_aggregate(datadef);
        datatcb.maybe_begin_aggregate(datadef);
        datatcb.emit_tai(tai_string.create_pchar(s,len+1),datadef);
        datatcb.emit_tai(tai_string.create_pchar(s,len+1),datadef);
        datatcb.maybe_end_aggregate(datadef);
        datatcb.maybe_end_aggregate(datadef);
-       ansistrrecdef:=datatcb.end_anonymous_record('$'+get_dynstring_rec_name(st_ansistring,false,len),sizeof(pint));
+       ansistrrecdef:=datatcb.end_anonymous_record;
        if NewSection then
        if NewSection then
          sectype:=sec_rodata_norel
          sectype:=sec_rodata_norel
        else
        else
@@ -644,7 +644,7 @@ implementation
        strlength:=getlengthwidestring(pcompilerwidestring(data));
        strlength:=getlengthwidestring(pcompilerwidestring(data));
        if winlike then
        if winlike then
          begin
          begin
-           datatcb.begin_anonymous_record;
+           datatcb.begin_anonymous_record('$'+get_dynstring_rec_name(st_widestring,true,strlength),sizeof(pint));
            current_asmdata.getdatalabel(result.lab);
            current_asmdata.getdatalabel(result.lab);
            datatcb.emit_tai(Tai_const.Create_32bit(strlength*cwidechartype.size),s32inttype);
            datatcb.emit_tai(Tai_const.Create_32bit(strlength*cwidechartype.size),s32inttype);
            { can we optimise by placing the string constant label at the
            { can we optimise by placing the string constant label at the
@@ -672,7 +672,7 @@ implementation
            { ending #0 }
            { ending #0 }
            datatcb.emit_tai(Tai_const.Create_16bit(0),cwidechartype);
            datatcb.emit_tai(Tai_const.Create_16bit(0),cwidechartype);
            datatcb.maybe_end_aggregate(datadef);
            datatcb.maybe_end_aggregate(datadef);
-           uniwidestrrecdef:=datatcb.end_anonymous_record('$'+get_dynstring_rec_name(st_widestring,winlike,strlength),sizeof(pint));
+           uniwidestrrecdef:=datatcb.end_anonymous_record;
          end
          end
        else
        else
          { code generation for other sizes must be written }
          { code generation for other sizes must be written }
@@ -693,13 +693,14 @@ implementation
        { do nothing }
        { do nothing }
      end;
      end;
 
 
-   procedure ttai_lowleveltypedconstbuilder.begin_anonymous_record;
+
+   procedure ttai_lowleveltypedconstbuilder.begin_anonymous_record(const optionalname: string; packrecords: shortint);
      begin
      begin
        { do nothing }
        { do nothing }
      end;
      end;
 
 
 
 
-   function ttai_lowleveltypedconstbuilder.end_anonymous_record(const optionalname: string; packrecords: shortint): trecorddef;
+   function ttai_lowleveltypedconstbuilder.end_anonymous_record: trecorddef;
      begin
      begin
        { do nothing }
        { do nothing }
        result:=nil;
        result:=nil;

+ 4 - 1
compiler/llvm/llvmdef.pas

@@ -674,7 +674,10 @@ implementation
           internalerror(2014012002);
           internalerror(2014012002);
         res:=current_module.llvmdefs.FindOrAdd(@typename[1],length(typename));
         res:=current_module.llvmdefs.FindOrAdd(@typename[1],length(typename));
         if not assigned(res^.Data) then
         if not assigned(res^.Data) then
-          res^.Data:=crecorddef.create_global_from_deflist(typename,fieldtypes,packrecords);
+          begin
+            res^.Data:=crecorddef.create_global_internal(typename,packrecords);
+            trecorddef(res^.Data).add_fields_from_deflist(fieldtypes);
+          end;
         result:=trecorddef(res^.Data);
         result:=trecorddef(res^.Data);
       end;
       end;
 
 

+ 12 - 9
compiler/llvm/nllvmtcon.pas

@@ -61,8 +61,8 @@ interface
       procedure emit_tai_procvar2procdef(p: tai; pvdef: tprocvardef); override;
       procedure emit_tai_procvar2procdef(p: tai; pvdef: tprocvardef); override;
       procedure maybe_begin_aggregate(def: tdef); override;
       procedure maybe_begin_aggregate(def: tdef); override;
       procedure maybe_end_aggregate(def: tdef); override;
       procedure maybe_end_aggregate(def: tdef); override;
-      procedure begin_anonymous_record; override;
-      function end_anonymous_record(const optionalname: string; packrecords: shortint): trecorddef; override;
+      procedure begin_anonymous_record(const optionalname: string; packrecords: shortint); override;
+      function end_anonymous_record: trecorddef; override;
       procedure queue_init(todef: tdef); override;
       procedure queue_init(todef: tdef); override;
       procedure queue_vecn(def: tdef; const index: tconstexprint); override;
       procedure queue_vecn(def: tdef; const index: tconstexprint); override;
       procedure queue_subscriptn(def: tabstractrecorddef; vs: tfieldvarsym); override;
       procedure queue_subscriptn(def: tabstractrecorddef; vs: tfieldvarsym); override;
@@ -248,14 +248,17 @@ implementation
     end;
     end;
 
 
 
 
-  procedure tllvmtai_typedconstbuilder.begin_anonymous_record;
+  procedure tllvmtai_typedconstbuilder.begin_anonymous_record(const optionalname: string; packrecords: shortint);
+    var
+      recorddef: trecorddef;
     begin
     begin
       inherited;
       inherited;
-      begin_aggregate_intern(tck_record,nil);
+      recorddef:=crecorddef.create_global_internal(optionalname,packrecords);
+      begin_aggregate_intern(tck_record,recorddef);
     end;
     end;
 
 
 
 
-  function tllvmtai_typedconstbuilder.end_anonymous_record(const optionalname: string; packrecords: shortint): trecorddef;
+  function tllvmtai_typedconstbuilder.end_anonymous_record: trecorddef;
     var
     var
       agg: tai_aggregatetypedconst;
       agg: tai_aggregatetypedconst;
       ele: tai_abstracttypedconst;
       ele: tai_abstracttypedconst;
@@ -265,17 +268,17 @@ implementation
       if assigned(result) then
       if assigned(result) then
         exit;
         exit;
       if not assigned(faggregates) or
       if not assigned(faggregates) or
-         (faggregates.count=0) then
+         (faggregates.count=0) or
+         (tai_aggregatetypedconst(faggregates[faggregates.count-1]).def.typ<>recorddef) then
         internalerror(2014080201);
         internalerror(2014080201);
       agg:=tai_aggregatetypedconst(faggregates[faggregates.count-1]);
       agg:=tai_aggregatetypedconst(faggregates[faggregates.count-1]);
       defs:=tfplist.create;
       defs:=tfplist.create;
       for ele in agg do
       for ele in agg do
         defs.add(ele.def);
         defs.add(ele.def);
-      result:=crecorddef.create_global_from_deflist(optionalname,defs,packrecords);
-      agg.def:=result;
+      result:=trecorddef(agg.def);
+      result.add_fields_from_deflist(defs);
       { already added to the asmlist if necessary }
       { already added to the asmlist if necessary }
       faggregates.count:=faggregates.count-1;
       faggregates.count:=faggregates.count-1;
-      inherited;
     end;
     end;
 
 
 
 

+ 17 - 11
compiler/symdef.pas

@@ -298,7 +298,8 @@ interface
           variantrecdesc : pvariantrecdesc;
           variantrecdesc : pvariantrecdesc;
           isunion       : boolean;
           isunion       : boolean;
           constructor create(const n:string; p:TSymtable);virtual;
           constructor create(const n:string; p:TSymtable);virtual;
-          constructor create_global_from_deflist(n: string; fieldtypes: tfplist; packrecords: shortint); virtual;
+          constructor create_global_internal(n: string; packrecords: shortint); virtual;
+          procedure add_fields_from_deflist(fieldtypes: tfplist);
           constructor ppuload(ppufile:tcompilerppufile);
           constructor ppuload(ppufile:tcompilerppufile);
           destructor destroy;override;
           destructor destroy;override;
           function getcopy : tstoreddef;override;
           function getcopy : tstoreddef;override;
@@ -3945,11 +3946,8 @@ implementation
       end;
       end;
 
 
 
 
-    constructor trecorddef.create_global_from_deflist(n: string; fieldtypes: tfplist; packrecords: shortint);
+    constructor trecorddef.create_global_internal(n: string; packrecords: shortint);
       var
       var
-        i: longint;
-        hdef: tdef;
-        sym: tfieldvarsym;
         oldsymtablestack: tsymtablestack;
         oldsymtablestack: tsymtablestack;
         definedname: boolean;
         definedname: boolean;
       begin
       begin
@@ -3965,12 +3963,6 @@ implementation
         symtable:=trecordsymtable.create(n,packrecords);
         symtable:=trecordsymtable.create(n,packrecords);
         symtable.defowner:=self;
         symtable.defowner:=self;
         isunion:=false;
         isunion:=false;
-        for i:=0 to fieldtypes.count-1 do
-          begin
-            sym:=cfieldvarsym.create('$f'+tostr(i),vs_value,tdef(fieldtypes[i]),[]);
-            symtable.insert(sym);
-            trecordsymtable(symtable).addfield(sym,vis_hidden);
-          end;
         inherited create(n,recorddef);
         inherited create(n,recorddef);
         if assigned(current_module.localsymtable) then
         if assigned(current_module.localsymtable) then
           begin
           begin
@@ -3990,6 +3982,20 @@ implementation
       end;
       end;
 
 
 
 
+    procedure trecorddef.add_fields_from_deflist(fieldtypes: tfplist);
+      var
+        i: longint;
+        sym: tfieldvarsym;
+      begin
+        for i:=0 to fieldtypes.count-1 do
+          begin
+            sym:=cfieldvarsym.create('$f'+tostr(i),vs_value,tdef(fieldtypes[i]),[]);
+            symtable.insert(sym);
+            trecordsymtable(symtable).addfield(sym,vis_hidden);
+          end;
+      end;
+
+
     constructor trecorddef.ppuload(ppufile:tcompilerppufile);
     constructor trecorddef.ppuload(ppufile:tcompilerppufile);
 
 
       procedure readvariantrecdesc(var variantrecdesc : pvariantrecdesc);
       procedure readvariantrecdesc(var variantrecdesc : pvariantrecdesc);