1
0
mirror of https://github.com/cc65/cc65.git synced 2024-12-27 15:29:46 +00:00

Rename SegRange to span. Write out the size instead of the end offset so we

can save some bytes in the object file.


git-svn-id: svn://svn.cc65.org/cc65/trunk@5113 b7a2c559-68d2-44c3-8de9-860c34a00d81
This commit is contained in:
uz 2011-08-04 12:49:59 +00:00
parent f04d65a662
commit 31d2fff060
6 changed files with 84 additions and 88 deletions

View File

@ -56,8 +56,8 @@ OBJS = anonname.o \
repeat.o \ repeat.o \
scanner.o \ scanner.o \
segment.o \ segment.o \
segrange.o \
sizeof.o \ sizeof.o \
span.o \
spool.o \ spool.o \
struct.o \ struct.o \
studyexpr.o \ studyexpr.o \

View File

@ -89,8 +89,8 @@ OBJS = anonname.obj \
repeat.obj \ repeat.obj \
scanner.obj \ scanner.obj \
segment.obj \ segment.obj \
segrange.obj \
sizeof.obj \ sizeof.obj \
span.obj \
spool.obj \ spool.obj \
struct.obj \ struct.obj \
studyexpr.obj \ studyexpr.obj \

View File

@ -1,8 +1,8 @@
/*****************************************************************************/ /*****************************************************************************/
/* */ /* */
/* segrange.c */ /* span.c */
/* */ /* */
/* A segment range */ /* A span of data within a segment */
/* */ /* */
/* */ /* */
/* */ /* */
@ -39,7 +39,7 @@
/* ca65 */ /* ca65 */
#include "objfile.h" #include "objfile.h"
#include "segment.h" #include "segment.h"
#include "segrange.h" #include "span.h"
@ -49,42 +49,41 @@
SegRange* NewSegRange (struct Segment* Seg) Span* NewSpan (struct Segment* Seg)
/* Create a new segment range. The segment is set to Seg, Start and End are /* Create a new span. The segment is set to Seg, Start and End are set to the
* set to the current PC of the segment. * current PC of the segment.
*/ */
{ {
/* Allocate memory */ /* Allocate memory */
SegRange* R = xmalloc (sizeof (SegRange)); Span* S = xmalloc (sizeof (Span));
/* Initialize the struct */ /* Initialize the struct */
R->Seg = Seg; S->Seg = Seg;
R->Start = Seg->PC; S->Start = Seg->PC;
R->End = Seg->PC; S->End = Seg->PC;
/* Return the new struct */ /* Return the new struct */
return R; return S;
} }
void AddSegRanges (Collection* Ranges) void AddSpans (Collection* Spans)
/* Add a segment range for all existing segments to the given collection of /* Add a span for all existing segments to the given collection of spans. The
* ranges. The currently active segment will be inserted first with all others * currently active segment will be inserted first with all others following.
* following.
*/ */
{ {
Segment* Seg; Segment* Seg;
/* Add the currently active segment */ /* Add the currently active segment */
CollAppend (Ranges, NewSegRange (ActiveSeg)); CollAppend (Spans, NewSpan (ActiveSeg));
/* Walk through the segment list and add all other segments */ /* Walk through the segment list and add all other segments */
Seg = SegmentList; Seg = SegmentList;
while (Seg) { while (Seg) {
/* Be sure to skip the active segment, since it was already added */ /* Be sure to skip the active segment, since it was already added */
if (Seg != ActiveSeg) { if (Seg != ActiveSeg) {
CollAppend (Ranges, NewSegRange (Seg)); CollAppend (Spans, NewSpan (Seg));
} }
Seg = Seg->List; Seg = Seg->List;
} }
@ -92,59 +91,60 @@ void AddSegRanges (Collection* Ranges)
void CloseSegRanges (Collection* Ranges) void CloseSpans (Collection* Spans)
/* Close all open segment ranges by setting PC to the current PC for the /* Close all open spans by setting PC to the current PC for the segment. */
* segment.
*/
{ {
unsigned I; unsigned I;
/* Walk over the segment list */ /* Walk over the segment list */
for (I = 0; I < CollCount (Ranges); ++I) { for (I = 0; I < CollCount (Spans); ++I) {
/* Get the next segment range */ /* Get the next segment range */
SegRange* R = CollAtUnchecked (Ranges, I); Span* S = CollAtUnchecked (Spans, I);
/* Set the end offset */ /* Set the end offset */
R->End = R->Seg->PC; S->End = S->Seg->PC;
} }
} }
void WriteSegRanges (const Collection* Ranges) void WriteSpans (const Collection* Spans)
/* Write a list of segment ranges to the output file */ /* Write a list of spans to the output file */
{ {
unsigned I; unsigned I;
unsigned Count; unsigned Count;
/* Determine how many of the segments contain actual data */ /* Determine how many of the segments contain actual data */
Count = 0; Count = 0;
for (I = 0; I < CollCount (Ranges); ++I) { for (I = 0; I < CollCount (Spans); ++I) {
/* Get next range */ /* Get next range */
const SegRange* R = CollConstAt (Ranges, I); const Span* S = CollConstAt (Spans, I);
/* Is this segment range empty? */ /* Is this segment range empty? */
if (R->Start != R->End) { if (S->Start != S->End) {
++Count; ++Count;
} }
} }
/* Write the number of ranges with data */ /* Write the number of spans with data */
ObjWriteVar (Count); ObjWriteVar (Count);
/* Write the ranges */ /* Write the spans */
for (I = 0; I < CollCount (Ranges); ++I) { for (I = 0; I < CollCount (Spans); ++I) {
/* Get next range */ /* Get next range */
const SegRange* R = CollConstAt (Ranges, I); const Span* S = CollConstAt (Spans, I);
/* Write data for non empty ranges */ /* Write data for non empty spans. We will write the size instead of
if (R->Start != R->End) { * the end offset to save some bytes, since most spans are expected
ObjWriteVar (R->Seg->Num); * to be rather small.
ObjWriteVar (R->Start); */
ObjWriteVar (R->End); if (S->Start != S->End) {
ObjWriteVar (S->Seg->Num);
ObjWriteVar (S->Start);
ObjWriteVar (S->End - S->Start);
} }
} }
} }

View File

@ -1,8 +1,8 @@
/*****************************************************************************/ /*****************************************************************************/
/* */ /* */
/* segrange.h */ /* span.h */
/* */ /* */
/* A segment range */ /* A span of data within a segment */
/* */ /* */
/* */ /* */
/* */ /* */
@ -33,8 +33,8 @@
#ifndef SEGRANGE_H #ifndef SPAN_H
#define SEGRANGE_H #define SPAN_H
@ -50,9 +50,9 @@
/* Segment range definition */ /* Span definition */
typedef struct SegRange SegRange; typedef struct Span Span;
struct SegRange{ struct Span{
struct Segment* Seg; /* Pointer to segment */ struct Segment* Seg; /* Pointer to segment */
unsigned long Start; /* Start of range */ unsigned long Start; /* Start of range */
unsigned long End; /* End of range */ unsigned long End; /* End of range */
@ -66,41 +66,37 @@ struct SegRange{
SegRange* NewSegRange (struct Segment* Seg); Span* NewSpan (struct Segment* Seg);
/* Create a new segment range. The segment is set to Seg, Start and End are /* Create a new span. The segment is set to Seg, Start and End are set to the
* set to the current PC of the segment. * current PC of the segment.
*/ */
#if defined(HAVE_INLINE) #if defined(HAVE_INLINE)
INLINE unsigned long GetSegRangeSize (const SegRange* R) INLINE unsigned long GetSpanSize (const Span* R)
/* Return the segment range size in bytes */ /* Return the span size in bytes */
{ {
return (R->End - R->Start); return (R->End - R->Start);
} }
#else #else
# define GetSegRangeSize(R) ((R)->End - (R)->Start) # define GetSpanSize(R) ((R)->End - (R)->Start)
#endif #endif
void AddSegRanges (Collection* Ranges); void AddSpans (Collection* Spans);
/* Add a segment range for all existing segments to the given collection of /* Add a span for all existing segments to the given collection of spans. The
* ranges. The currently active segment will be inserted first with all others * currently active segment will be inserted first with all others following.
* following.
*/ */
void CloseSegRanges (Collection* Ranges); void CloseSpans (Collection* Spans);
/* Close all open segment ranges by setting PC to the current PC for the /* Close all open spans by setting PC to the current PC for the segment. */
* segment.
*/
void WriteSegRanges (const Collection* Ranges); void WriteSpans (const Collection* Spans);
/* Write a list of segment ranges to the output file */ /* Write a list of spans to the output file */
/* End of segrange.h */ /* End of span.h */
#endif #endif

View File

@ -52,6 +52,7 @@
#include "scanner.h" #include "scanner.h"
#include "segment.h" #include "segment.h"
#include "sizeof.h" #include "sizeof.h"
#include "span.h"
#include "spool.h" #include "spool.h"
#include "studyexpr.h" #include "studyexpr.h"
#include "symtab.h" #include "symtab.h"
@ -116,7 +117,7 @@ static SymTable* NewSymTable (SymTable* Parent, const StrBuf* Name)
S->Right = 0; S->Right = 0;
S->Childs = 0; S->Childs = 0;
S->OwnerSym = 0; S->OwnerSym = 0;
S->SegRanges = AUTO_COLLECTION_INITIALIZER; S->Spans = AUTO_COLLECTION_INITIALIZER;
S->Id = ScopeCount++; S->Id = ScopeCount++;
S->Flags = ST_NONE; S->Flags = ST_NONE;
S->AddrSize = ADDR_SIZE_DEFAULT; S->AddrSize = ADDR_SIZE_DEFAULT;
@ -215,14 +216,14 @@ void SymEnterLevel (const StrBuf* ScopeName, unsigned char Type,
CurrentScope->Type = Type; CurrentScope->Type = Type;
CurrentScope->OwnerSym = OwnerSym; CurrentScope->OwnerSym = OwnerSym;
/* If this is a scope that allows to emit data into segments, add segment /* If this is a scope that allows to emit data into segments, add spans
* ranges for all currently existing segments. Doing this for just a few * for all currently existing segments. Doing this for just a few scope
* scope types is not really necessary but an optimization, because it * types is not really necessary but an optimization, because it does not
* does not allocate memory for useless data (unhandled types here don't * allocate memory for useless data (unhandled types here don't occupy
* occupy space in any segment). * space in any segment).
*/ */
if (CurrentScope->Type <= SCOPE_HAS_DATA) { if (CurrentScope->Type <= SCOPE_HAS_DATA) {
AddSegRanges (&CurrentScope->SegRanges); AddSpans (&CurrentScope->Spans);
} }
} }
@ -231,19 +232,19 @@ void SymEnterLevel (const StrBuf* ScopeName, unsigned char Type,
void SymLeaveLevel (void) void SymLeaveLevel (void)
/* Leave the current lexical level */ /* Leave the current lexical level */
{ {
/* Close the segment ranges. We don't care about the scope type here, /* Close the spans. We don't care about the scope type here, since types
* since types without segment ranges will just have an empty list. * without spans will just have an empty list.
*/ */
CloseSegRanges (&CurrentScope->SegRanges); CloseSpans (&CurrentScope->Spans);
/* If we have segment ranges, the first one is the segment that was /* If we have spans, the first one is the segment that was active, when the
* active, when the scope was opened. Set the size of the scope to the * scope was opened. Set the size of the scope to the number of data bytes
* number of data bytes emitted into this segment. If we have an owner * emitted into this segment. If we have an owner symbol set the size of
* symbol set the size of this symbol, too. * this symbol, too.
*/ */
if (CollCount (&CurrentScope->SegRanges) > 0) { if (CollCount (&CurrentScope->Spans) > 0) {
const SegRange* R = CollAtUnchecked (&CurrentScope->SegRanges, 0); const Span* S = CollAtUnchecked (&CurrentScope->Spans, 0);
unsigned long Size = GetSegRangeSize (R); unsigned long Size = GetSpanSize (S);
DefSizeOfScope (CurrentScope, Size); DefSizeOfScope (CurrentScope, Size);
if (CurrentScope->OwnerSym) { if (CurrentScope->OwnerSym) {
DefSizeOfSymbol (CurrentScope->OwnerSym, Size); DefSizeOfSymbol (CurrentScope->OwnerSym, Size);
@ -940,8 +941,8 @@ void WriteScopes (void)
ObjWriteVar (Size); ObjWriteVar (Size);
} }
/* Segment ranges for this scope */ /* Spans for this scope */
WriteSegRanges (&S->SegRanges); WriteSpans (&S->Spans);
/* Next scope */ /* Next scope */
S = S->Next; S = S->Next;

View File

@ -45,7 +45,6 @@
#include "inline.h" #include "inline.h"
/* ca65 */ /* ca65 */
#include "segrange.h"
#include "symentry.h" #include "symentry.h"
@ -69,7 +68,7 @@ struct SymTable {
SymTable* Parent; /* Link to enclosing scope if any */ SymTable* Parent; /* Link to enclosing scope if any */
SymTable* Childs; /* Pointer to child scopes */ SymTable* Childs; /* Pointer to child scopes */
SymEntry* OwnerSym; /* Symbol that "owns" the scope */ SymEntry* OwnerSym; /* Symbol that "owns" the scope */
Collection SegRanges; /* Segment ranges for this scope */ Collection Spans; /* Spans for this scope */
unsigned Id; /* Scope id */ unsigned Id; /* Scope id */
unsigned short Flags; /* Symbol table flags */ unsigned short Flags; /* Symbol table flags */
unsigned char AddrSize; /* Address size */ unsigned char AddrSize; /* Address size */