X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=src%2Fcc65%2Fsymentry.c;h=18cc026ea6b4ec9e250bb16fd6c31c8fd475541a;hb=HEAD;hp=578c6c0054d38ef9e11e20fbc5197a83e7a77d7f;hpb=83e73742c80662af07124bbc0e6361a7361418d9;p=cc65 diff --git a/src/cc65/symentry.c b/src/cc65/symentry.c index 578c6c005..18cc026ea 100644 --- a/src/cc65/symentry.c +++ b/src/cc65/symentry.c @@ -1,15 +1,15 @@ /*****************************************************************************/ /* */ -/* symentry.c */ +/* symentry.c */ /* */ -/* Symbol table entries for the cc65 C compiler */ +/* Symbol table entries for the cc65 C compiler */ /* */ /* */ /* */ -/* (C) 2000-2002 Ullrich von Bassewitz */ -/* Wacholderweg 14 */ -/* D-70597 Stuttgart */ -/* EMail: uz@cc65.org */ +/* (C) 2000-2013, Ullrich von Bassewitz */ +/* Roemerstrasse 52 */ +/* D-70794 Filderstadt */ +/* EMail: uz@cc65.org */ /* */ /* */ /* This software is provided 'as-is', without any expressed or implied */ @@ -39,12 +39,15 @@ #include "xmalloc.h" /* cc65 */ +#include "anonname.h" +#include "declare.h" +#include "error.h" #include "symentry.h" /*****************************************************************************/ -/* Code */ +/* Code */ /*****************************************************************************/ @@ -59,14 +62,16 @@ SymEntry* NewSymEntry (const char* Name, unsigned Flags) SymEntry* E = xmalloc (sizeof (SymEntry) + Len); /* Initialize the entry */ - E->NextHash = 0; - E->PrevSym = 0; - E->NextSym = 0; - E->Link = 0; - E->Owner = 0; - E->Flags = Flags; - E->Type = 0; + E->NextHash = 0; + E->PrevSym = 0; + E->NextSym = 0; + E->Link = 0; + E->Owner = 0; + E->Flags = Flags; + E->Type = 0; + E->Attr = 0; E->AsmName = 0; + E->V.BssName = 0; memcpy (E->Name, Name, Len+1); /* Return the new entry */ @@ -78,8 +83,19 @@ SymEntry* NewSymEntry (const char* Name, unsigned Flags) void FreeSymEntry (SymEntry* E) /* Free a symbol entry */ { + unsigned i; + TypeFree (E->Type); xfree (E->AsmName); + + if (E->Flags & SC_LABEL) { + for (i = 0; i < CollCount (E->V.L.DefsOrRefs); i++) { + xfree (CollAt (E->V.L.DefsOrRefs, i)); + } + + DoneCollection (E->V.L.DefsOrRefs); + } + xfree (E); } @@ -89,26 +105,28 @@ void DumpSymEntry (FILE* F, const SymEntry* E) /* Dump the given symbol table entry to the file in readable form */ { static const struct { - const char* Name; - unsigned Val; + const char* Name; + unsigned Val; } Flags [] = { - /* Beware: Order is important! */ - { "SC_TYPEDEF", SC_TYPEDEF }, - { "SC_SFLD", SC_SFLD }, - { "SC_STRUCT", SC_STRUCT }, - { "SC_AUTO", SC_AUTO }, - { "SC_REGISTER", SC_REGISTER }, - { "SC_STATIC", SC_STATIC }, - { "SC_EXTERN", SC_EXTERN }, - { "SC_ENUM", SC_ENUM }, - { "SC_CONST", SC_CONST }, - { "SC_LABEL", SC_LABEL }, - { "SC_PARAM", SC_PARAM }, - { "SC_FUNC", SC_FUNC }, - { "SC_STORAGE", SC_STORAGE }, - { "SC_DEF", SC_DEF }, - { "SC_REF", SC_REF }, - { "SC_ZEROPAGE", SC_ZEROPAGE }, + /* Beware: Order is important! */ + { "SC_TYPEDEF", SC_TYPEDEF }, + { "SC_BITFIELD", SC_BITFIELD }, + { "SC_STRUCTFIELD", SC_STRUCTFIELD }, + { "SC_UNION", SC_UNION }, + { "SC_STRUCT", SC_STRUCT }, + { "SC_AUTO", SC_AUTO }, + { "SC_REGISTER", SC_REGISTER }, + { "SC_STATIC", SC_STATIC }, + { "SC_EXTERN", SC_EXTERN }, + { "SC_ENUM", SC_ENUM }, + { "SC_CONST", SC_CONST }, + { "SC_LABEL", SC_LABEL }, + { "SC_PARAM", SC_PARAM }, + { "SC_FUNC", SC_FUNC }, + { "SC_STORAGE", SC_STORAGE }, + { "SC_DEF", SC_DEF }, + { "SC_REF", SC_REF }, + { "SC_ZEROPAGE", SC_ZEROPAGE }, }; unsigned I; @@ -124,49 +142,126 @@ void DumpSymEntry (FILE* F, const SymEntry* E) /* Print the flags */ SymFlags = E->Flags; - fprintf (F, " Flags: "); + fprintf (F, " Flags:"); for (I = 0; I < sizeof (Flags) / sizeof (Flags[0]) && SymFlags != 0; ++I) { - if ((SymFlags & Flags[I].Val) == Flags[I].Val) { - SymFlags &= ~Flags[I].Val; - fprintf (F, "%s ", Flags[I].Name); - } + if ((SymFlags & Flags[I].Val) == Flags[I].Val) { + SymFlags &= ~Flags[I].Val; + fprintf (F, " %s", Flags[I].Name); + } } if (SymFlags != 0) { - fprintf (F, "%04X", SymFlags); + fprintf (F, " 0x%05X", SymFlags); } fprintf (F, "\n"); /* Print the type */ fprintf (F, " Type: "); if (E->Type) { - PrintType (F, E->Type); + PrintType (F, E->Type); } else { - fprintf (F, "(none)"); + fprintf (F, "(none)"); } fprintf (F, "\n"); } -int IsTypeDef (const SymEntry* E) -/* Return true if the given entry is a typedef entry */ +int SymIsOutputFunc (const SymEntry* Sym) +/* Return true if this is a function that must be output */ +{ + /* Symbol must be a function which is defined and either extern or + ** static and referenced. + */ + return IsTypeFunc (Sym->Type) && + SymIsDef (Sym) && + (Sym->Flags & (SC_REF | SC_EXTERN)); +} + + + +const DeclAttr* SymGetAttr (const SymEntry* Sym, DeclAttrType AttrType) +/* Return an attribute for this symbol or NULL if the attribute does not exist */ +{ + /* Beware: We may not even have a collection */ + if (Sym->Attr) { + unsigned I; + for (I = 0; I < CollCount (Sym->Attr); ++I) { + + /* Get the next attribute */ + const DeclAttr* A = CollConstAt (Sym->Attr, I); + + /* If this is the one we're searching for, return it */ + if (A->AttrType == AttrType) { + return A; + } + } + } + + /* Not found */ + return 0; +} + + + +void SymUseAttr (SymEntry* Sym, struct Declaration* D) +/* Use the attributes from the declaration for this symbol */ { - return ((E->Flags & SC_TYPEDEF) == SC_TYPEDEF); + /* We cannot specify attributes twice */ + if ((Sym->Flags & SC_HAVEATTR) != 0) { + if (D->Attributes != 0) { + Error ("Attributes must be specified in the first declaration"); + } + return; + } + + /* Move the attributes */ + Sym->Attr = D->Attributes; + D->Attributes = 0; + Sym->Flags |= SC_HAVEATTR; +} + + + +void SymSetAsmName (SymEntry* Sym) +/* Set the assembler name for an external symbol from the name of the symbol */ +{ + unsigned Len; + + /* Cannot be used to change the name */ + PRECONDITION (Sym->AsmName == 0); + + /* The assembler name starts with an underline */ + Len = strlen (Sym->Name); + Sym->AsmName = xmalloc (Len + 2); + Sym->AsmName[0] = '_'; + memcpy (Sym->AsmName+1, Sym->Name, Len+1); } -void ChangeSymType (SymEntry* Entry, type* Type) +void CvtRegVarToAuto (SymEntry* Sym) +/* Convert a register variable to an auto variable */ +{ + /* Change the storage class */ + Sym->Flags = (Sym->Flags & ~(SC_REGISTER | SC_STATIC | SC_EXTERN)) | SC_AUTO; + + /* Transfer the stack offset from register save area to actual offset */ + Sym->V.Offs = Sym->V.R.SaveOffs; +} + + + +void ChangeSymType (SymEntry* Entry, Type* T) /* Change the type of the given symbol */ { TypeFree (Entry->Type); - Entry->Type = TypeDup (Type); + Entry->Type = TypeDup (T); } void ChangeAsmName (SymEntry* Entry, const char* NewAsmName) -/* Change the assembler name of the symbol */ +/* Change the assembler name of the symbol */ { xfree (Entry->AsmName); Entry->AsmName = xstrdup (NewAsmName); @@ -174,3 +269,8 @@ void ChangeAsmName (SymEntry* Entry, const char* NewAsmName) +int HasAnonName (const SymEntry* Entry) +/* Return true if the symbol entry has an anonymous name */ +{ + return IsAnonName (Entry->Name); +}