]> git.sur5r.net Git - cc65/commitdiff
Write imports out to the debug info file. Add the id of the corresponding
authoruz <uz@b7a2c559-68d2-44c3-8de9-860c34a00d81>
Tue, 16 Aug 2011 13:58:59 +0000 (13:58 +0000)
committeruz <uz@b7a2c559-68d2-44c3-8de9-860c34a00d81>
Tue, 16 Aug 2011 13:58:59 +0000 (13:58 +0000)
export.

git-svn-id: svn://svn.cc65.org/cc65/trunk@5186 b7a2c559-68d2-44c3-8de9-860c34a00d81

src/ld65/dbgsyms.c
src/ld65/dbgsyms.h
src/ld65/exports.c
src/ld65/exports.h
src/ld65/expr.c
src/ld65/objdata.c
src/ld65/objdata.h
src/ld65/objfile.c

index 445167818f5c647a200767b947f2c4cf7d5f36db..084e54592fc2df787e05b37675a88ff3ad4c3ff2 100644 (file)
@@ -44,6 +44,7 @@
 /* ld65 */
 #include "dbgsyms.h"
 #include "error.h"
+#include "exports.h"
 #include "expr.h"
 #include "fileio.h"
 #include "global.h"
 
 
 
+/* Definition of the debug symbol structure */
+struct DbgSym {
+    unsigned            Id;             /* Id of debug symbol */
+    DbgSym*                    Next;           /* Pool linear list link */
+    ObjData*                   Obj;            /* Object file that exports the name */
+    Collection          LineInfos;      /* Line infos of definition */
+    ExprNode*                  Expr;           /* Expression (0 if not def'd) */
+    unsigned            Size;           /* Symbol size if any */
+    unsigned            OwnerId;        /* Id of parent/owner */
+    unsigned            ImportId;       /* Id of import if this is one */
+    unsigned            Name;                  /* Name */
+    unsigned short      Type;          /* Type of symbol */
+    unsigned short      AddrSize;       /* Address size of symbol */
+};
+
 /* We will collect all debug symbols in the following array and remove
  * duplicates before outputing them.
  */
@@ -72,22 +88,25 @@ static DbgSym*      DbgSymPool[256];
 
 
 
-static DbgSym* NewDbgSym (unsigned Type, unsigned char AddrSize, ObjData* O)
+static DbgSym* NewDbgSym (unsigned Id, unsigned Type, unsigned char AddrSize,
+                          ObjData* O)
 /* Create a new DbgSym and return it */
 {
     /* Allocate memory */
-    DbgSym* D    = xmalloc (sizeof (DbgSym));
+    DbgSym* D     = xmalloc (sizeof (DbgSym));
 
     /* Initialize the fields */
-    D->Next      = 0;
-    D->Obj       = O;
-    D->LineInfos = EmptyCollection;
-    D->Expr             = 0;
-    D->Size      = 0;
-    D->OwnerId   = ~0U;
-    D->Name     = 0;
-    D->Type             = Type;
-    D->AddrSize  = AddrSize;
+    D->Id         = Id;
+    D->Next       = 0;
+    D->Obj        = O;
+    D->LineInfos  = EmptyCollection;
+    D->Expr              = 0;
+    D->Size       = 0;
+    D->OwnerId    = ~0U;
+    D->ImportId   = ~0U;
+    D->Name      = 0;
+    D->Type              = Type;
+    D->AddrSize   = AddrSize;
 
     /* Return the new entry */
     return D;
@@ -141,7 +160,7 @@ static void InsertDbgSym (DbgSym* D, long Val)
 
 
 
-DbgSym* ReadDbgSym (FILE* F, ObjData* O)
+DbgSym* ReadDbgSym (FILE* F, ObjData* O, unsigned Id)
 /* Read a debug symbol from a file, insert and return it */
 {
     /* Read the type and address size */
@@ -149,7 +168,7 @@ DbgSym* ReadDbgSym (FILE* F, ObjData* O)
     unsigned char AddrSize = Read8 (F);
 
     /* Create a new debug symbol */
-    DbgSym* D = NewDbgSym (Type, AddrSize, O);
+    DbgSym* D = NewDbgSym (Id, Type, AddrSize, O);
 
     /* Read the id of the owner scope/symbol */
     D->OwnerId = ReadVar (F);
@@ -169,6 +188,19 @@ DbgSym* ReadDbgSym (FILE* F, ObjData* O)
         D->Size = ReadVar (F);
     }
 
+    /* If this is an import, the file contains its id */
+    if (SYM_IS_IMPORT (D->Type)) {
+        D->ImportId = ReadVar (F);
+    }
+
+    /* If its an exports, there's also the export id, but we don't remember
+     * it but use it to let the export point back to us.
+     */
+    if (SYM_IS_EXPORT (D->Type)) {
+        /* Get the export from the export id, then set the our id */
+        GetObjExport (O, ReadVar (F))->DbgSymId = Id;
+    }
+
     /* Last is the list of line infos for this symbol */
     ReadLineInfoList (F, O, &D->LineInfos);
 
@@ -195,7 +227,7 @@ void ClearDbgSymTable (void)
 
 
 
-long GetDbgSymVal (const DbgSym* D)
+static long GetDbgSymVal (const DbgSym* D)
 /* Get the value of this symbol */
 {
     CHECK (D->Expr != 0);
@@ -203,7 +235,7 @@ long GetDbgSymVal (const DbgSym* D)
 }
 
 
-             
+
 void PrintDbgSyms (FILE* F)
 /* Print the debug symbols in a debug file */
 {
@@ -212,40 +244,56 @@ void PrintDbgSyms (FILE* F)
     for (I = 0; I < CollCount (&ObjDataList); ++I) {
 
         /* Get the object file */
-        const ObjData* O = CollAtUnchecked (&ObjDataList, I);
+        ObjData* O = CollAtUnchecked (&ObjDataList, I);
 
         /* Walk through all debug symbols in this module */
         for (J = 0; J < CollCount (&O->DbgSyms); ++J) {
 
-            long Val;
-            SegExprDesc D;
-
             /* Get the next debug symbol */
             const DbgSym* S = CollConstAt (&O->DbgSyms, J);
 
-            /* Get the symbol value */
-            Val = GetDbgSymVal (S);
-
             /* Emit the base data for the entry */
             fprintf (F,
-                     "sym\tid=%u,name=\"%s\",val=0x%lX,addrsize=%s,type=%s",
+                     "sym\tid=%u,name=\"%s\",addrsize=%s,type=%s",
                      O->SymBaseId + J,
                      GetString (S->Name),
-                     Val,
                      AddrSizeToStr (S->AddrSize),
                      SYM_IS_LABEL (S->Type)? "lab" : "equ");
 
-            /* Emit the size only if we know it */
-            if (S->Size != 0) {
-                fprintf (F, ",size=%lu", S->Size);
+            /* If this is not an import, output its value and - if we have
+             * it - the segment.
+             */
+            if (!SYM_IS_IMPORT (S->Type)) {
+
+                SegExprDesc D;
+
+                /* Get the symbol value */
+                long Val = GetDbgSymVal (S);
+
+                /* Output it */
+                fprintf (F, ",val=0x%lX", Val);
+
+                /* Check for a segmented expression and add the segment id to
+                 * the debug info if we have one.
+                 */
+                GetSegExprVal (S->Expr, &D);
+                if (!D.TooComplex && D.Seg != 0) {
+                    fprintf (F, ",seg=%u", D.Seg->Id);
+                }
+
+                /* Output the type */
+                fprintf (F, ",type=%s", SYM_IS_LABEL (S->Type)? "lab" : "equ");
+
+            } else {
+
+                /* Output the type */
+                fputs (",type=imp", F);
+
             }
 
-            /* Check for a segmented expression and add the segment id to the
-             * debug info if we have one.
-             */
-            GetSegExprVal (S->Expr, &D);
-            if (!D.TooComplex && D.Seg != 0) {
-                fprintf (F, ",seg=%u", D.Seg->Id);
+            /* Emit the size only if we know it */
+            if (S->Size != 0) {
+                fprintf (F, ",size=%u", S->Size);
             }
 
             /* For cheap local symbols, add the owner symbol, for others,
@@ -257,6 +305,23 @@ void PrintDbgSyms (FILE* F)
                 fprintf (F, ",parent=%u", O->SymBaseId + S->OwnerId);
             }
 
+            /* If this is an import, output the id of the matching export */
+            if (SYM_IS_IMPORT (S->Type)) {
+
+                /* Get the import */
+                const Import* Imp = GetObjImport (O, S->ImportId);
+
+                /* Get the export from the import */
+                const Export* Exp = Imp->Exp;
+
+                /* If this is not a linker generated symbol, output the debug
+                 * symbol id for the export
+                 */
+                if (Exp->Obj) {
+                    fprintf (F, ",exp=%u", Exp->Obj->SymBaseId + Exp->DbgSymId);
+                }
+            }
+
             /* Terminate the output line */
             fputc ('\n', F);
         }
@@ -278,25 +343,25 @@ void PrintDbgSymLabels (ObjData* O, FILE* F)
        /* Get the next debug symbol */
        DbgSym* D = CollAt (&O->DbgSyms, I);
 
-        /* Emit this symbol only if it is a label (ignore equates) */
-        if (SYM_IS_EQUATE (D->Type)) {
+        /* Emit this symbol only if it is a label (ignore equates and imports) */
+        if (SYM_IS_EQUATE (D->Type) || SYM_IS_IMPORT (D->Type)) {
             continue;
         }
 
-       /* Get the symbol value */
-       Val = GetDbgSymVal (D);
+               /* Get the symbol value */
+               Val = GetDbgSymVal (D);
 
-       /* Lookup this symbol in the table. If it is found in the table, it was
-        * already written to the file, so don't emit it twice. If it is not in
-        * the table, insert and output it.
-        */
+               /* Lookup this symbol in the table. If it is found in the table, it was
+                * already written to the file, so don't emit it twice. If it is not in
+                * the table, insert and output it.
+                */
                if (GetDbgSym (D, Val) == 0) {
 
-           /* Emit the VICE label line */
+                   /* Emit the VICE label line */
                    fprintf (F, "al %06lX .%s\n", Val, GetString (D->Name));
 
-           /* Insert the symbol into the table */
-           InsertDbgSym (D, Val);
+                   /* Insert the symbol into the table */
+                   InsertDbgSym (D, Val);
                }
     }
 }
index 209d78f4a1afabca0bdfc68228996c4ee661de3d..fd6b9a37dbb16fe1b760dc193e480d968aa27922 100644 (file)
 /* Forwards */
 struct Scope;
 
-/* Debug symbol structure */
+/* Opaque debug symbol structure */
 typedef struct DbgSym DbgSym;
-struct DbgSym {
-    DbgSym*                    Next;           /* Pool linear list link */
-    ObjData*                   Obj;            /* Object file that exports the name */
-    Collection          LineInfos;      /* Line infos of definition */
-    ExprNode*                  Expr;           /* Expression (0 if not def'd) */
-    unsigned            Size;           /* Symbol size if any */
-    unsigned            OwnerId;        /* Id of parent/owner */
-    unsigned            Name;                  /* Name */
-    unsigned short      Type;          /* Type of symbol */
-    unsigned short      AddrSize;       /* Address size of symbol */
-};
 
 
 
 /*****************************************************************************/
-/*                                          Code                                    */
+/*                                          Code                                    */
 /*****************************************************************************/
 
 
 
-DbgSym* ReadDbgSym (FILE* F, ObjData* Obj);
+DbgSym* ReadDbgSym (FILE* F, ObjData* Obj, unsigned Id);
 /* Read a debug symbol from a file, insert and return it */
 
-long GetDbgSymVal (const DbgSym* D);
-/* Get the value of this symbol */
-
 void ClearDbgSymTable (void);
 /* Clear the debug symbol table. Must be called before outputting debug syms
  * or debug labels the first time.
index 9be4e22fb5f1bcf7ec817fd45cd4fa8d13955642..e1571d782beab90b9216d22b2d2f701e7e0e2c06 100644 (file)
@@ -41,6 +41,7 @@
 #include "addrsize.h"
 #include "check.h"
 #include "hashfunc.h"
+#include "lidefs.h"
 #include "symdefs.h"
 #include "xmalloc.h"
 
@@ -232,7 +233,7 @@ Import* InsertImport (Import* I)
     if (HashTab[Hash] == 0) {
        /* The slot is empty, we need to insert a dummy export */
                E = HashTab[Hash] = NewExport (0, ADDR_SIZE_DEFAULT, Name, 0);
-       ++ExpCount;
+               ++ExpCount;
     } else {
        E = HashTab [Hash];
        while (1) {
@@ -274,11 +275,21 @@ Import* InsertImport (Import* I)
 
 
 
-const LineInfo* GetImportPos (const Import* I)
+const LineInfo* GetImportPos (const Import* Imp)
 /* Return the basic line info of an import */
 {
-    /* Source file position is always in slot zero */
-    return CollConstAt (&I->LineInfos, 0);
+    unsigned I;
+
+    /* Search for a line info of LI_TYPE_ASM */
+    for (I = 0; I < CollCount (&Imp->LineInfos); ++I) {
+        const LineInfo* LI = CollConstAt (&Imp->LineInfos, I);
+        if (LI_GET_TYPE (LI->Type) == LI_TYPE_ASM) {
+            return LI;
+        }
+    }
+
+    /* Not found - return the one in slot zero */
+    return CollConstAt (&Imp->LineInfos, 0);
 }
 
 
@@ -306,6 +317,7 @@ static Export* NewExport (unsigned Type, unsigned char AddrSize,
     E->Expr             = 0;
     E->Size      = 0;
     E->LineInfos = EmptyCollection;
+    E->DbgSymId  = ~0U;
     E->Type             = Type | SYM_EXPORT;
     E->AddrSize  = AddrSize;
     memset (E->ConDes, 0, sizeof (E->ConDes));
index 535e7b24c876ae0d5a8de18f1e97df52fc12a23b..d71e5d53318f985612c10eb848ef93a4b557bc17 100644 (file)
@@ -85,6 +85,7 @@ struct Export {
     ExprNode*                  Expr;           /* Expression (0 if not def'd) */
     unsigned            Size;           /* Size of the symbol if any */
     Collection          LineInfos;      /* Line info of definition */
+    unsigned            DbgSymId;       /* Id of debug symbol for this export */
     unsigned short      Type;          /* Type of export */
     unsigned short      AddrSize;       /* Address size of export */
     unsigned char      ConDes[CD_TYPE_COUNT];  /* Constructor/destructor decls */
index c6d3c7ef3a63563a138c1949c0910cdb10d6e973..d671914b7a091fe824ec7c7ab0a6f50f73a421cf 100644 (file)
@@ -201,8 +201,8 @@ Import* GetExprImport (ExprNode* Expr)
      * import pointer.
      */
     if (Expr->Obj) {
-       /* Return the export */
-               return CollAt (&Expr->Obj->Imports, Expr->V.ImpNum);
+       /* Return the Import */
+               return GetObjImport (Expr->Obj, Expr->V.ImpNum);
     } else {
        return Expr->V.Imp;
     }
index 21b75e1e89045cb090a8fe443ae0734d59b4d2ed..b0a17d0e98192c1a8ffd32d1c51da4cd52c3b9fd 100644 (file)
@@ -211,6 +211,30 @@ struct Section* GetObjSection (ObjData* O, unsigned Id)
 
 
 
+struct Import* GetObjImport (ObjData* O, unsigned Id)
+/* Get an import from an object file checking for a valid index */
+{
+    if (Id >= CollCount (&O->Imports)) {
+        Error ("Invalid import index (%u) in module `%s'",
+               Id, GetObjFileName (O));
+    }
+    return CollAtUnchecked (&O->Imports, Id);
+}
+
+
+
+struct Export* GetObjExport (ObjData* O, unsigned Id)
+/* Get an export from an object file checking for a valid index */
+{
+    if (Id >= CollCount (&O->Exports)) {
+        Error ("Invalid export index (%u) in module `%s'",
+               Id, GetObjFileName (O));
+    }
+    return CollAtUnchecked (&O->Exports, Id);
+}
+
+
+
 struct Scope* GetObjScope (ObjData* O, unsigned Id)
 /* Get a scope from an object file checking for a valid index */
 {
index b892f9f6e7f03bb8fa5a40d899fb6ae37d21f56b..77d75f064dcd4a4766656bf546eeb37748d91de3 100644 (file)
@@ -52,6 +52,8 @@
 
 
 /* Forwards */
+struct Export;
+struct Import;
 struct Library;
 struct Scope;
 struct Section;
@@ -144,6 +146,12 @@ INLINE int ObjHasFiles (const ObjData* O)
 struct Section* GetObjSection (ObjData* Obj, unsigned Id);
 /* Get a section from an object file checking for a valid index */
 
+struct Import* GetObjImport (ObjData* Obj, unsigned Id);
+/* Get an import from an object file checking for a valid index */
+
+struct Export* GetObjExport (ObjData* Obj, unsigned Id);
+/* Get an export from an object file checking for a valid index */
+
 struct Scope* GetObjScope (ObjData* Obj, unsigned Id);
 /* Get a scope from an object file checking for a valid index */
 
index 8b85e2cfa385b162a8674703981d4ab7b1930b8d..66bcc64fefc1a8cf3ea96514dd0cdd9dd75bc9ff 100644 (file)
@@ -200,7 +200,7 @@ void ObjReadDbgSyms (FILE* F, unsigned long Pos, ObjData* O)
     DbgSymCount = ReadVar (F);
     CollGrow (&O->DbgSyms, DbgSymCount);
     for (I = 0; I < DbgSymCount; ++I) {
-       CollAppend (&O->DbgSyms, ReadDbgSym (F, O));
+       CollAppend (&O->DbgSyms, ReadDbgSym (F, O, I));
     }
 }
 
@@ -276,7 +276,7 @@ void ObjReadScopes (FILE* F, unsigned long Pos, ObjData* O)
     CollGrow (&O->Scopes, ScopeCount);
     for (I = 0; I < ScopeCount; ++I) {
         CollAppend (&O->Scopes,  ReadScope (F, O, I));
-    }   
+    }
 }