Added a "fillval" attribute to the segment definition. When given, it

overrides the value from the memory area for all space that lies within the
segment itself.


git-svn-id: svn://svn.cc65.org/cc65/trunk@5823 b7a2c559-68d2-44c3-8de9-860c34a00d81
This commit is contained in:
uz
2012-09-09 19:00:43 +00:00
parent 1c77d3a6f0
commit 574c8fa273
5 changed files with 55 additions and 19 deletions

View File

@@ -6,7 +6,7 @@
/* */
/* */
/* */
/* (C) 1999-2011, Ullrich von Bassewitz */
/* (C) 1999-2012, Ullrich von Bassewitz */
/* Roemerstrasse 52 */
/* D-70794 Filderstadt */
/* EMail: uz@cc65.org */
@@ -142,7 +142,7 @@ static void BinWriteMem (BinDesc* D, MemoryArea* M)
/* Debugging: Check that the file offset is correct */
if (ftell (D->F) != (long)M->FileOffs) {
Internal ("Invalid file offset for memory area %s: %ld/%lu",
GetString (M->Name), ftell (D->F), M->FileOffs);
GetString (M->Name), ftell (D->F), M->FileOffs);
}
/* Walk over all segments in this memory area */
@@ -231,11 +231,10 @@ static void BinWriteMem (BinDesc* D, MemoryArea* M)
*/
if (DoWrite) {
unsigned long P = ftell (D->F);
S->Seg->FillVal = M->FillVal;
SegWrite (D->Filename, D->F, S->Seg, BinWriteExpr, D);
PrintNumVal ("Wrote", (unsigned long) (ftell (D->F) - P));
} else if (M->Flags & MF_FILL) {
WriteMult (D->F, M->FillVal, S->Seg->Size);
} else if (M->Flags & MF_FILL) {
WriteMult (D->F, S->Seg->FillVal, S->Seg->Size);
PrintNumVal ("Filled", (unsigned long) S->Seg->Size);
}

View File

@@ -118,6 +118,7 @@ static Collection SegDescList = STATIC_COLLECTION_INITIALIZER;
#define SA_OFFSET 0x0040
#define SA_START 0x0080
#define SA_OPTIONAL 0x0100
#define SA_FILLVAL 0x0200
/* Symbol types used in the CfgSymbol structure */
typedef enum {
@@ -353,6 +354,7 @@ static SegDesc* NewSegDesc (unsigned Name)
S->Seg = 0;
S->Attr = 0;
S->Flags = 0;
S->FillVal = 0;
S->RunAlignment = 1;
S->LoadAlignment = 1;
@@ -637,6 +639,7 @@ static void ParseSegments (void)
{ "ALIGN", CFGTOK_ALIGN },
{ "ALIGN_LOAD", CFGTOK_ALIGN_LOAD },
{ "DEFINE", CFGTOK_DEFINE },
{ "FILLVAL", CFGTOK_FILLVAL },
{ "LOAD", CFGTOK_LOAD },
{ "OFFSET", CFGTOK_OFFSET },
{ "OPTIONAL", CFGTOK_OPTIONAL },
@@ -706,6 +709,12 @@ static void ParseSegments (void)
CfgNextTok ();
break;
case CFGTOK_FILLVAL:
FlagAttr (&S->Attr, SA_FILLVAL, "FILLVAL");
S->FillVal = (unsigned char) CfgCheckedConstExpr (0, 0xFF);
S->Flags |= SF_FILLVAL;
break;
case CFGTOK_LOAD:
FlagAttr (&S->Attr, SA_LOAD, "LOAD");
S->Load = CfgGetMemory (GetStrBufId (&CfgSVal));
@@ -1561,22 +1570,22 @@ static void ProcessSegments (void)
while (I < CollCount (&SegDescList)) {
/* Get the next segment descriptor */
SegDesc* S = CollAtUnchecked (&SegDescList, I);
SegDesc* S = CollAtUnchecked (&SegDescList, I);
/* Search for the actual segment in the input files. The function may
* return NULL (no such segment), this is checked later.
*/
S->Seg = SegFind (S->Name);
/* If the segment is marked as BSS style, and if the segment exists
/* If the segment is marked as BSS style, and if the segment exists
* in any of the object file, check that there's no initialized data
* in the segment.
*/
if ((S->Flags & SF_BSS) != 0 && S->Seg != 0 && !IsBSSType (S->Seg)) {
*/
if ((S->Flags & SF_BSS) != 0 && S->Seg != 0 && !IsBSSType (S->Seg)) {
CfgWarning (GetSourcePos (S->LI),
"Segment `%s' with type `bss' contains initialized data",
GetString (S->Name));
}
GetString (S->Name));
}
/* If this segment does exist in any of the object files, insert the
* segment into the load/run memory areas. Otherwise print a warning
@@ -1592,6 +1601,9 @@ static void ProcessSegments (void)
MemoryInsert (S->Load, S);
}
/* Use the fill value from the config */
S->Seg->FillVal = S->FillVal;
/* Process the next segment descriptor in the next run */
++I;
@@ -1894,6 +1906,13 @@ unsigned CfgProcess (void)
}
/* If this is the load memory area and the segment doesn't have a
* fill value defined, use the one from the memory area.
*/
if (S->Load == M && (S->Flags & SF_FILLVAL) == 0) {
S->Seg->FillVal = M->FillVal;
}
/* Increment the fill level of the memory area and check for an
* overflow.
*/

View File

@@ -6,7 +6,7 @@
/* */
/* */
/* */
/* (C) 1998-2011, Ullrich von Bassewitz */
/* (C) 1998-2012, Ullrich von Bassewitz */
/* Roemerstrasse 52 */
/* D-70794 Filderstadt */
/* EMail: uz@cc65.org */
@@ -75,6 +75,7 @@ struct SegDesc {
Segment* Seg; /* Pointer to segment structure */
unsigned Attr; /* Attributes for segment */
unsigned Flags; /* Set of bitmapped flags */
unsigned char FillVal; /* Fill value for this segment */
struct MemoryArea* Load; /* Load memory section */
struct MemoryArea* Run; /* Run memory section */
unsigned long Addr; /* Start address or offset into segment */
@@ -94,6 +95,7 @@ struct SegDesc {
#define SF_OPTIONAL 0x0100 /* Segment is optional (must not exist) */
#define SF_RUN_DEF 0x0200 /* RUN symbols already defined */
#define SF_LOAD_DEF 0x0400 /* LOAD symbols already defined */
#define SF_FILLVAL 0x0800 /* Segment has separate fill value */

View File

@@ -464,16 +464,22 @@ void SegWrite (const char* TgtName, FILE* Tgt, Segment* S, SegWriteFunc F, void*
/* Loop over all sections in this segment */
for (I = 0; I < CollCount (&S->Sections); ++I) {
Section* Sec = CollAtUnchecked (&S->Sections, I);
Fragment* Frag;
Section* Sec = CollAtUnchecked (&S->Sections, I);
Fragment* Frag;
unsigned char FillVal;
/* Output were this section is from */
Print (stdout, 2, " Section from \"%s\"\n", GetObjFileName (Sec->Obj));
/* If we have fill bytes, write them now */
/* If we have fill bytes, write them now. Beware: If this is the
* first section, the fill value is not considered part of the segment
* and therefore taken from the memory area.
*/
FillVal = (I == 0)? S->MemArea->FillVal : S->FillVal;
Print (stdout, 2, " Filling 0x%lx bytes with 0x%02x\n",
Sec->Fill, S->FillVal);
WriteMult (Tgt, S->FillVal, Sec->Fill);
Sec->Fill, FillVal);
WriteMult (Tgt, FillVal, Sec->Fill);
Offs += Sec->Fill;
/* Loop over all fragments in this section */