Browse Source

+ implemented writing of the LNAMES omf record(s)

git-svn-id: trunk@30398 -
nickysn 10 years ago
parent
commit
72bfe8d2c4
2 changed files with 143 additions and 0 deletions
  1. 41 0
      compiler/ogomf.pas
  2. 102 0
      compiler/omfbase.pas

+ 41 - 0
compiler/ogomf.pas

@@ -47,10 +47,14 @@ interface
       end;
       end;
 
 
       TOmfObjOutput = class(tObjOutput)
       TOmfObjOutput = class(tObjOutput)
+      private
+        FLNames: TOmfOrderedNameCollection;
+        property LNames: TOmfOrderedNameCollection read FLNames;
       protected
       protected
         function writeData(Data:TObjData):boolean;override;
         function writeData(Data:TObjData):boolean;override;
       public
       public
         constructor create(AWriter:TObjectWriter);override;
         constructor create(AWriter:TObjectWriter);override;
+        destructor Destroy;override;
       end;
       end;
 
 
       TOmfAssembler = class(tinternalassembler)
       TOmfAssembler = class(tinternalassembler)
@@ -89,6 +93,7 @@ implementation
         RawRecord: TOmfRawRecord;
         RawRecord: TOmfRawRecord;
         Header: TOmfRecord_THEADR;
         Header: TOmfRecord_THEADR;
         Translator_COMENT: TOmfRecord_COMENT;
         Translator_COMENT: TOmfRecord_COMENT;
+        LNamesRec: TOmfRecord_LNAMES;
       begin
       begin
         { write header record }
         { write header record }
         RawRecord:=TOmfRawRecord.Create;
         RawRecord:=TOmfRawRecord.Create;
@@ -107,6 +112,35 @@ implementation
         RawRecord.WriteTo(FWriter);
         RawRecord.WriteTo(FWriter);
         Translator_COMENT.Free;
         Translator_COMENT.Free;
 
 
+        { dummy: let's add some names }
+        LNames.Clear;
+        LNames.Add('');
+        LNames.Add('text');
+        LNames.Add('code');
+        LNames.Add('rodata');
+        LNames.Add('data');
+        LNames.Add('data');
+        LNames.Add('data');
+        LNames.Add('fpc');
+        LNames.Add('data');
+        LNames.Add('bss');
+        LNames.Add('bss');
+        LNames.Add('stack');
+        LNames.Add('stack');
+        LNames.Add('heap');
+        LNames.Add('heap');
+        LNames.Add('dgroup');
+
+        { write LNAMES record(s) }
+        LNamesRec:=TOmfRecord_LNAMES.Create;
+        LNamesRec.Names:=LNames;
+        while LNamesRec.NextIndex<=LNames.Count do
+          begin
+            LNamesRec.EncodeTo(RawRecord);
+            RawRecord.WriteTo(FWriter);
+          end;
+        LNamesRec.Free;
+
         RawRecord.Free;
         RawRecord.Free;
         result:=true;
         result:=true;
       end;
       end;
@@ -115,6 +149,13 @@ implementation
       begin
       begin
         inherited create(AWriter);
         inherited create(AWriter);
         cobjdata:=TOmfObjData;
         cobjdata:=TOmfObjData;
+        FLNames:=TOmfOrderedNameCollection.Create;
+      end;
+
+    destructor TOmfObjOutput.Destroy;
+      begin
+        FLNames.Free;
+        inherited Destroy;
       end;
       end;
 
 
 {****************************************************************************
 {****************************************************************************

+ 102 - 0
compiler/omfbase.pas

@@ -27,6 +27,7 @@ unit omfbase;
 interface
 interface
 {$H+}
 {$H+}
   uses
   uses
+    cclasses,
     owbase;
     owbase;
 
 
   const
   const
@@ -100,6 +101,21 @@ interface
 
 
   type
   type
 
 
+    { TOmfOrderedNameCollection }
+
+    TOmfOrderedNameCollection = class
+    private
+      FStringList: array of string;
+      function GetCount: Integer;
+      function GetString(Index: Integer): string;
+      procedure SetString(Index: Integer; AValue: string);
+    public
+      function Add(const S: string): Integer;
+      procedure Clear;
+      property Strings [Index: Integer]: string read GetString write SetString; default;
+      property Count: Integer read GetCount;
+    end;
+
     { TOmfRawRecord }
     { TOmfRawRecord }
 
 
     TOmfRawRecord = class
     TOmfRawRecord = class
@@ -168,11 +184,56 @@ interface
       property NoList: Boolean read GetNoList write SetNoList;
       property NoList: Boolean read GetNoList write SetNoList;
     end;
     end;
 
 
+    { TOmfRecord_LNAMES }
+
+    TOmfRecord_LNAMES = class(TOmfParsedRecord)
+    private
+      FNames: TOmfOrderedNameCollection;
+      FNextIndex: Integer;
+    public
+      constructor Create;
+
+      procedure DecodeFrom(RawRecord: TOmfRawRecord);override;
+      procedure EncodeTo(RawRecord: TOmfRawRecord);override;
+
+      property Names: TOmfOrderedNameCollection read FNames write FNames;
+      property NextIndex: Integer read FNextIndex write FNextIndex;
+    end;
+
 implementation
 implementation
 
 
   uses
   uses
     verbose;
     verbose;
 
 
+  { TOmfOrderedNameCollection }
+
+  function TOmfOrderedNameCollection.GetString(Index: Integer): string;
+    begin
+      Result:=FStringList[Index-1];
+    end;
+
+  function TOmfOrderedNameCollection.GetCount: Integer;
+    begin
+      Result:=Length(FStringList);
+    end;
+
+  procedure TOmfOrderedNameCollection.SetString(Index: Integer; AValue: string);
+    begin
+      FStringList[Index-1]:=AValue;
+    end;
+
+  function TOmfOrderedNameCollection.Add(const S: string): Integer;
+    begin
+      Result:=Length(FStringList)+1;
+      SetLength(FStringList,Result);
+      FStringList[Result-1]:=S;
+    end;
+
+  procedure TOmfOrderedNameCollection.Clear;
+    begin
+      SetLength(FStringList,0);
+    end;
+
   { TOmfRawRecord }
   { TOmfRawRecord }
 
 
   function TOmfRawRecord.GetRecordType: Byte;
   function TOmfRawRecord.GetRecordType: Byte;
@@ -339,4 +400,45 @@ implementation
       RawRecord.CalculateChecksumByte;
       RawRecord.CalculateChecksumByte;
     end;
     end;
 
 
+  { TOmfRecord_LNAMES }
+
+  constructor TOmfRecord_LNAMES.Create;
+    begin
+      FNextIndex:=1;
+    end;
+
+  procedure TOmfRecord_LNAMES.DecodeFrom(RawRecord: TOmfRawRecord);
+    begin
+      {TODO: implement}
+      internalerror(2015040101);
+    end;
+
+  procedure TOmfRecord_LNAMES.EncodeTo(RawRecord: TOmfRawRecord);
+    const
+      RecordLengthLimit = 1024;
+    var
+      Len,LastIncludedIndex,NextOfs,I: Integer;
+    begin
+      RawRecord.RecordType:=RT_LNAMES;
+
+      { find out how many strings can we include until we reach the length limit }
+      Len:=1;
+      LastIncludedIndex:=NextIndex-1;
+      repeat
+        Inc(LastIncludedIndex);
+        Inc(Len,Length(Names[LastIncludedIndex])+1);
+      until (LastIncludedIndex>=Names.Count) or ((Len+Length(Names[LastIncludedIndex+1])+1)>=RecordLengthLimit);
+
+      { write the strings... }
+      NextOfs:=0;
+      for I:=NextIndex to LastIncludedIndex do
+        NextOfs:=RawRecord.WriteStringAt(NextOfs,Names[I]);
+      RawRecord.RecordLength:=Len;
+      RawRecord.CalculateChecksumByte;
+
+      { update NextIndex }
+      NextIndex:=LastIncludedIndex+1;
+    end;
+
+
 end.
 end.