1
0
mirror of https://github.com/cc65/cc65.git synced 2024-07-01 08:29:37 +00:00

Merge pull request #99 from groessler/something_to_pull

Make ld65 command line arguments position independent.
This commit is contained in:
Oliver Schmidt 2014-03-28 17:37:02 +02:00
commit 435fd06bc6

View File

@ -80,6 +80,24 @@
static unsigned ObjFiles = 0; /* Count of object files linked */
static unsigned LibFiles = 0; /* Count of library files linked */
/* struct InputFile.Type definitions */
#define INPUT_FILES_FILE 0 /* Entry is a file (unknown type) */
#define INPUT_FILES_FILE_OBJ 1 /* Entry is a object file */
#define INPUT_FILES_FILE_LIB 2 /* Entry is a library file */
#define INPUT_FILES_SGROUP 3 /* Entry is 'StartGroup' */
#define INPUT_FILES_EGROUP 4 /* Entry is 'EndGroup' */
#define MAX_INPUTFILES 256
/* Array of inputs (libraries and object files) */
static struct InputFile {
const char *FileName;
unsigned Type;
} *InputFiles;
static unsigned InputFilesCount = 0;
static const char *CmdlineCfgFile = NULL,
*CmdlineTarget = NULL;
/*****************************************************************************/
@ -390,7 +408,10 @@ static void OptHelp (const char* Opt attribute ((unused)),
static void OptLib (const char* Opt attribute ((unused)), const char* Arg)
/* Link a library */
{
LinkFile (Arg, FILETYPE_LIB);
InputFiles[InputFilesCount].Type = INPUT_FILES_FILE_LIB;
InputFiles[InputFilesCount].FileName = Arg;
if (++InputFilesCount >= MAX_INPUTFILES)
Error ("Too many input files");
}
@ -406,6 +427,9 @@ static void OptLibPath (const char* Opt attribute ((unused)), const char* Arg)
static void OptMapFile (const char* Opt attribute ((unused)), const char* Arg)
/* Give the name of the map file */
{
if (MapFileName) {
Error ("Cannot use -m twice");
}
MapFileName = Arg;
}
@ -426,7 +450,10 @@ static void OptModuleId (const char* Opt, const char* Arg)
static void OptObj (const char* Opt attribute ((unused)), const char* Arg)
/* Link an object file */
{
LinkFile (Arg, FILETYPE_OBJ);
InputFiles[InputFilesCount].Type = INPUT_FILES_FILE_OBJ;
InputFiles[InputFilesCount].FileName = Arg;
if (++InputFilesCount >= MAX_INPUTFILES)
Error ("Too many input files");
}
@ -439,16 +466,14 @@ static void OptObjPath (const char* Opt attribute ((unused)), const char* Arg)
static void OptOutputName (const char* Opt, const char* Arg)
static void OptOutputName (const char* Opt attribute ((unused)), const char* Arg)
/* Give the name of the output file */
{
/* If the name of the output file has been used in the config before
* (by using %O) we're actually changing it later, which - in most cases -
* gives unexpected results, so emit a warning in this case.
*/
if (OutputNameUsed) {
Warning ("Option `%s' should precede options `-t' or `-C'", Opt);
static int OutputNameSeen = 0;
if (OutputNameSeen) {
Error ("Cannot use -o twice");
}
OutputNameSeen = 1;
OutputName = Arg;
}
@ -457,6 +482,9 @@ static void OptOutputName (const char* Opt, const char* Arg)
static void OptStartAddr (const char* Opt, const char* Arg)
/* Set the default start address */
{
if (HaveStartAddr) {
Error ("Cannot use -S twice");
}
StartAddr = CvtNumber (Opt, Arg);
HaveStartAddr = 1;
}
@ -520,16 +548,61 @@ static void OptVersion (const char* Opt attribute ((unused)),
int main (int argc, char* argv [])
/* Assembler main program */
static void CmdlOptStartGroup (const char* Opt attribute ((unused)),
const char* Arg attribute ((unused)))
/* Remember 'start group' occurrence in input files array */
{
InputFiles[InputFilesCount].Type = INPUT_FILES_SGROUP;
InputFiles[InputFilesCount].FileName = Arg; /* Unused */
if (++InputFilesCount >= MAX_INPUTFILES)
Error ("Too many input files");
}
static void CmdlOptEndGroup (const char* Opt attribute ((unused)),
const char* Arg attribute ((unused)))
/* Remember 'end group' occurrence in input files array */
{
InputFiles[InputFilesCount].Type = INPUT_FILES_EGROUP;
InputFiles[InputFilesCount].FileName = Arg; /* Unused */
if (++InputFilesCount >= MAX_INPUTFILES)
Error ("Too many input files");
}
static void CmdlOptConfig (const char* Opt attribute ((unused)), const char* Arg)
/* Set 'config file' command line parameter */
{
if (CmdlineCfgFile || CmdlineTarget) {
Error ("Cannot use -C/-t twice");
}
CmdlineCfgFile = Arg;
}
static void CmdlOptTarget (const char* Opt attribute ((unused)), const char* Arg)
/* Set 'target' command line parameter */
{
if (CmdlineCfgFile || CmdlineTarget) {
Error ("Cannot use -C/-t twice");
}
CmdlineTarget = Arg;
}
static void ParseCommandLine(void)
{
/* Program long options */
static const LongOpt OptTab[] = {
{ "--cfg-path", 1, OptCfgPath },
{ "--config", 1, OptConfig },
{ "--config", 1, CmdlOptConfig },
{ "--dbgfile", 1, OptDbgFile },
{ "--define", 1, OptDefine },
{ "--end-group", 0, OptEndGroup },
{ "--end-group", 0, CmdlOptEndGroup },
{ "--force-import", 1, OptForceImport },
{ "--help", 0, OptHelp },
{ "--lib", 1, OptLib },
@ -539,27 +612,18 @@ int main (int argc, char* argv [])
{ "--obj", 1, OptObj },
{ "--obj-path", 1, OptObjPath },
{ "--start-addr", 1, OptStartAddr },
{ "--start-group", 0, OptStartGroup },
{ "--target", 1, OptTarget },
{ "--start-group", 0, CmdlOptStartGroup },
{ "--target", 1, CmdlOptTarget },
{ "--version", 0, OptVersion },
};
unsigned I;
unsigned MemoryAreaOverflows;
unsigned LabelFileGiven = 0;
/* Initialize the cmdline module */
InitCmdLine (&argc, &argv, "ld65");
/* Allocate memory for input file array */
InputFiles = xmalloc (MAX_INPUTFILES * sizeof (struct InputFile));
/* Initialize the input file search paths */
InitSearchPaths ();
/* Initialize the string pool */
InitStrPool ();
/* Initialize the type pool */
InitTypePool ();
/* Check the parameters */
/* Defer setting of config/target and input files until all options are parsed */
I = 1;
while (I < ArgCount) {
@ -577,11 +641,11 @@ int main (int argc, char* argv [])
break;
case '(':
OptStartGroup (Arg, 0);
CmdlOptStartGroup (Arg, 0);
break;
case ')':
OptEndGroup (Arg, 0);
CmdlOptEndGroup (Arg, 0);
break;
case 'h':
@ -594,14 +658,11 @@ int main (int argc, char* argv [])
break;
case 'o':
OptOutputName (Arg, GetArg (&I, 2));
OptOutputName (NULL, GetArg (&I, 2));
break;
case 't':
if (CfgAvail ()) {
Error ("Cannot use -C/-t twice");
}
OptTarget (Arg, GetArg (&I, 2));
CmdlOptTarget (Arg, GetArg (&I, 2));
break;
case 'u':
@ -617,7 +678,7 @@ int main (int argc, char* argv [])
break;
case 'C':
OptConfig (Arg, GetArg (&I, 2));
CmdlOptConfig (Arg, GetArg (&I, 2));
break;
case 'D':
@ -626,9 +687,17 @@ int main (int argc, char* argv [])
case 'L':
switch (Arg [2]) {
/* ## The first one is obsolete and will go */
case 'n': LabelFileName = GetArg (&I, 3); break;
default: OptLibPath (Arg, GetArg (&I, 2)); break;
case 'n':
/* ## This one is obsolete and will go */
if (LabelFileGiven) {
Error ("Cannot use -Ln twice");
}
LabelFileGiven = 1;
LabelFileName = GetArg (&I, 3);
break;
default:
OptLibPath (Arg, InputFiles[I].FileName);
break;
}
break;
@ -648,7 +717,10 @@ int main (int argc, char* argv [])
} else {
/* A filename */
LinkFile (Arg, FILETYPE_UNKNOWN);
InputFiles[InputFilesCount].Type = INPUT_FILES_FILE;
InputFiles[InputFilesCount].FileName = Arg;
if (++InputFilesCount >= MAX_INPUTFILES)
Error ("Too many input files");
}
@ -656,6 +728,61 @@ int main (int argc, char* argv [])
++I;
}
if (CmdlineTarget) {
OptTarget (NULL, CmdlineTarget);
} else if (CmdlineCfgFile) {
OptConfig (NULL, CmdlineCfgFile);
}
/* Process input files */
for (I = 0; I < InputFilesCount; ++I) {
switch (InputFiles[I].Type) {
case INPUT_FILES_FILE:
LinkFile (InputFiles[I].FileName, FILETYPE_UNKNOWN);
break;
case INPUT_FILES_FILE_LIB:
LinkFile (InputFiles[I].FileName, FILETYPE_LIB);
break;
case INPUT_FILES_FILE_OBJ:
LinkFile (InputFiles[I].FileName, FILETYPE_OBJ);
break;
case INPUT_FILES_SGROUP:
OptStartGroup (NULL, 0);
break;
case INPUT_FILES_EGROUP:
OptEndGroup (NULL, 0);
break;
default:
abort ();
}
}
/* Free memory used for input file array */
xfree (InputFiles);
}
int main (int argc, char* argv [])
/* Linker main program */
{
unsigned MemoryAreaOverflows;
/* Initialize the cmdline module */
InitCmdLine (&argc, &argv, "ld65");
/* Initialize the input file search paths */
InitSearchPaths ();
/* Initialize the string pool */
InitStrPool ();
/* Initialize the type pool */
InitTypePool ();
/* Parse the command line */
ParseCommandLine ();
/* Check if we had any object files */
if (ObjFiles == 0) {
Error ("No object files to link");