Fixed several obvious omissions. Allow specifying a start address.
git-svn-id: svn://svn.cc65.org/cc65/trunk@570 b7a2c559-68d2-44c3-8de9-860c34a00d81
This commit is contained in:
parent
b2b7fb4b33
commit
61a1fa52c4
7 changed files with 89 additions and 11 deletions
|
@ -69,6 +69,7 @@ void LoadCode (const char* Name, unsigned long StartAddress)
|
||||||
/* Load the code from the given file */
|
/* Load the code from the given file */
|
||||||
{
|
{
|
||||||
unsigned Count, MaxCount;
|
unsigned Count, MaxCount;
|
||||||
|
long Size;
|
||||||
FILE* F;
|
FILE* F;
|
||||||
|
|
||||||
|
|
||||||
|
@ -83,14 +84,32 @@ void LoadCode (const char* Name, unsigned long StartAddress)
|
||||||
Error ("Cannot open `%s': %s", Name, strerror (errno));
|
Error ("Cannot open `%s': %s", Name, strerror (errno));
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Read from the file and remember the number of bytes read */
|
/* Seek to the end to get the size of the file */
|
||||||
Count = fread (CodeBuf + StartAddress, 1, MaxCount, F);
|
if (fseek (F, 0, SEEK_END) != 0) {
|
||||||
if (ferror (F)) {
|
Error ("Cannot seek on file `%s': %s", Name, strerror (errno));
|
||||||
Error ("Error reading from `%s': %s", Name, strerror (errno));
|
|
||||||
}
|
}
|
||||||
if (Count == 0) {
|
Size = ftell (F);
|
||||||
|
rewind (F);
|
||||||
|
|
||||||
|
/* Check if the size is larger than what we can read */
|
||||||
|
if (Size == 0) {
|
||||||
Error ("File `%s' contains no data", Name);
|
Error ("File `%s' contains no data", Name);
|
||||||
}
|
}
|
||||||
|
if (Size > MaxCount) {
|
||||||
|
Warning ("File `%s' is too large, ignoring %ld bytes",
|
||||||
|
Name, Size - MaxCount);
|
||||||
|
} else if (MaxCount > Size) {
|
||||||
|
MaxCount = (unsigned) Size;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Read from the file and remember the number of bytes read */
|
||||||
|
Count = fread (CodeBuf + StartAddress, 1, MaxCount, F);
|
||||||
|
if (ferror (F) || Count != MaxCount) {
|
||||||
|
Error ("Error reading from `%s': %s", Name, strerror (errno));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Close the file */
|
||||||
|
fclose (F);
|
||||||
|
|
||||||
/* Set the buffer variables */
|
/* Set the buffer variables */
|
||||||
CodeStart = PC = StartAddress;
|
CodeStart = PC = StartAddress;
|
||||||
|
|
|
@ -68,6 +68,7 @@ static void GlobalSection (void)
|
||||||
{ "INPUTNAME", CFGTOK_INPUTNAME },
|
{ "INPUTNAME", CFGTOK_INPUTNAME },
|
||||||
{ "OUTPUTNAME", CFGTOK_OUTPUTNAME },
|
{ "OUTPUTNAME", CFGTOK_OUTPUTNAME },
|
||||||
{ "PAGELENGTH", CFGTOK_PAGELENGTH },
|
{ "PAGELENGTH", CFGTOK_PAGELENGTH },
|
||||||
|
{ "STARTADDR", CFGTOK_STARTADDR },
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Skip the token */
|
/* Skip the token */
|
||||||
|
@ -114,6 +115,15 @@ static void GlobalSection (void)
|
||||||
PageLength = CfgIVal;
|
PageLength = CfgIVal;
|
||||||
CfgNextTok ();
|
CfgNextTok ();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case CFGTOK_STARTADDR:
|
||||||
|
CfgNextTok ();
|
||||||
|
CfgAssureInt ();
|
||||||
|
CfgRangeCheck (0x0000, 0xFFFF);
|
||||||
|
StartAddr = CfgIVal;
|
||||||
|
CfgNextTok ();
|
||||||
|
break;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Directive is followed by a semicolon */
|
/* Directive is followed by a semicolon */
|
||||||
|
|
|
@ -154,7 +154,10 @@ unsigned AddrTable (void)
|
||||||
/* Count how many bytes may be output. */
|
/* Count how many bytes may be output. */
|
||||||
unsigned Count = GetSpan (atAddrTab);
|
unsigned Count = GetSpan (atAddrTab);
|
||||||
|
|
||||||
/* Need to handle Count == 1 here!!! ### */
|
/* Handle Count == 1 ### */
|
||||||
|
if (Count == 1) {
|
||||||
|
ByteTable ();
|
||||||
|
}
|
||||||
|
|
||||||
/* Make the given number even */
|
/* Make the given number even */
|
||||||
Count &= ~1U;
|
Count &= ~1U;
|
||||||
|
|
|
@ -55,6 +55,7 @@ const char CfgExt[] = ".cfg"; /* Config file extension */
|
||||||
unsigned char Verbosity = 4; /* Verbosity of the output file */
|
unsigned char Verbosity = 4; /* Verbosity of the output file */
|
||||||
unsigned char FormFeeds = 0; /* Add form feeds to the output? */
|
unsigned char FormFeeds = 0; /* Add form feeds to the output? */
|
||||||
unsigned char PassCount = 2; /* How many passed do we do? */
|
unsigned char PassCount = 2; /* How many passed do we do? */
|
||||||
|
unsigned long StartAddr = 0xC000; /* Start/load address of the program */
|
||||||
|
|
||||||
/* Stuff needed by many routines */
|
/* Stuff needed by many routines */
|
||||||
unsigned char Pass = 0; /* Disassembler pass */
|
unsigned char Pass = 0; /* Disassembler pass */
|
||||||
|
|
|
@ -56,6 +56,8 @@ extern const char CfgExt[]; /* Config file extension */
|
||||||
extern unsigned char Verbosity; /* Verbosity of the output file */
|
extern unsigned char Verbosity; /* Verbosity of the output file */
|
||||||
extern unsigned char FormFeeds; /* Add form feeds to the output? */
|
extern unsigned char FormFeeds; /* Add form feeds to the output? */
|
||||||
extern unsigned char PassCount; /* How many passed do we do? */
|
extern unsigned char PassCount; /* How many passed do we do? */
|
||||||
|
extern unsigned long StartAddr; /* Start/load address of the program */
|
||||||
|
|
||||||
|
|
||||||
/* Stuff needed by many routines */
|
/* Stuff needed by many routines */
|
||||||
extern unsigned char Pass; /* Disassembler pass */
|
extern unsigned char Pass; /* Disassembler pass */
|
||||||
|
|
|
@ -76,20 +76,49 @@ static void Usage (void)
|
||||||
" -o name\t\tName the output file\n"
|
" -o name\t\tName the output file\n"
|
||||||
" -v\t\t\tIncrease verbosity\n"
|
" -v\t\t\tIncrease verbosity\n"
|
||||||
" -F\t\t\tAdd formfeeds to the output\n"
|
" -F\t\t\tAdd formfeeds to the output\n"
|
||||||
" -V\t\t\tPrint the assembler version\n"
|
" -S addr\t\tSet the start/load address\n"
|
||||||
|
" -V\t\t\tPrint the disassembler version\n"
|
||||||
"\n"
|
"\n"
|
||||||
"Long options:\n"
|
"Long options:\n"
|
||||||
" --cpu type\t\tSet cpu type\n"
|
" --cpu type\t\tSet cpu type\n"
|
||||||
" --formfeeds\t\tAdd formfeeds to the output\n"
|
" --formfeeds\t\tAdd formfeeds to the output\n"
|
||||||
" --help\t\tHelp (this text)\n"
|
" --help\t\tHelp (this text)\n"
|
||||||
" --pagelength n\tSet the page length for the listing\n"
|
" --pagelength n\tSet the page length for the listing\n"
|
||||||
|
" --start-addr addr\tSet the start/load address\n"
|
||||||
" --verbose\t\tIncrease verbosity\n"
|
" --verbose\t\tIncrease verbosity\n"
|
||||||
" --version\t\tPrint the assembler version\n",
|
" --version\t\tPrint the disassembler version\n",
|
||||||
ProgName);
|
ProgName);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
static unsigned long CvtNumber (const char* Arg, const char* Number)
|
||||||
|
/* Convert a number from a string. Allow '$' and '0x' prefixes for hex
|
||||||
|
* numbers.
|
||||||
|
*/
|
||||||
|
{
|
||||||
|
unsigned long Val;
|
||||||
|
int Converted;
|
||||||
|
|
||||||
|
/* Convert */
|
||||||
|
if (*Number == '$') {
|
||||||
|
++Number;
|
||||||
|
Converted = sscanf (Number, "%lx", &Val);
|
||||||
|
} else {
|
||||||
|
Converted = sscanf (Number, "%li", (long*)&Val);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Check if we do really have a number */
|
||||||
|
if (Converted != 1) {
|
||||||
|
Error ("Invalid number given in argument: %s\n", Arg);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Return the result */
|
||||||
|
return Val;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static void OptCPU (const char* Opt, const char* Arg)
|
static void OptCPU (const char* Opt, const char* Arg)
|
||||||
/* Handle the --cpu option */
|
/* Handle the --cpu option */
|
||||||
{
|
{
|
||||||
|
@ -146,6 +175,14 @@ static void OptPageLength (const char* Opt, const char* Arg)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
static void OptStartAddr (const char* Opt, const char* Arg)
|
||||||
|
/* Set the default start address */
|
||||||
|
{
|
||||||
|
StartAddr = CvtNumber (Opt, Arg);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static void OptVerbose (const char* Opt, const char* Arg)
|
static void OptVerbose (const char* Opt, const char* Arg)
|
||||||
/* Increase verbosity */
|
/* Increase verbosity */
|
||||||
{
|
{
|
||||||
|
@ -280,6 +317,7 @@ int main (int argc, char* argv [])
|
||||||
{ "--formfeeds", 0, OptFormFeeds },
|
{ "--formfeeds", 0, OptFormFeeds },
|
||||||
{ "--help", 0, OptHelp },
|
{ "--help", 0, OptHelp },
|
||||||
{ "--pagelength", 1, OptPageLength },
|
{ "--pagelength", 1, OptPageLength },
|
||||||
|
{ "--start-addr", 1, OptStartAddr },
|
||||||
{ "--verbose", 0, OptVerbose },
|
{ "--verbose", 0, OptVerbose },
|
||||||
{ "--version", 0, OptVersion },
|
{ "--version", 0, OptVersion },
|
||||||
};
|
};
|
||||||
|
@ -316,6 +354,10 @@ int main (int argc, char* argv [])
|
||||||
OptVerbose (Arg, 0);
|
OptVerbose (Arg, 0);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case 'S':
|
||||||
|
OptStartAddr (Arg, GetArg (&I, 2));
|
||||||
|
break;
|
||||||
|
|
||||||
case 'V':
|
case 'V':
|
||||||
OptVersion (Arg, 0);
|
OptVersion (Arg, 0);
|
||||||
break;
|
break;
|
||||||
|
@ -359,7 +401,7 @@ int main (int argc, char* argv [])
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Load the input file */
|
/* Load the input file */
|
||||||
LoadCode (InFile, 0xE000); /* ### */
|
LoadCode (InFile, StartAddr);
|
||||||
|
|
||||||
/* Open the output file */
|
/* Open the output file */
|
||||||
OpenOutput (OutFile);
|
OpenOutput (OutFile);
|
||||||
|
|
|
@ -68,6 +68,7 @@ typedef enum token_t {
|
||||||
CFGTOK_INPUTNAME,
|
CFGTOK_INPUTNAME,
|
||||||
CFGTOK_OUTPUTNAME,
|
CFGTOK_OUTPUTNAME,
|
||||||
CFGTOK_PAGELENGTH,
|
CFGTOK_PAGELENGTH,
|
||||||
|
CFGTOK_STARTADDR,
|
||||||
|
|
||||||
/* Range section */
|
/* Range section */
|
||||||
CFGTOK_START,
|
CFGTOK_START,
|
||||||
|
|
Loading…
Add table
Reference in a new issue