A much less wasteful envp setup
This commit is contained in:
parent
f4caad6ea6
commit
b76123326e
9
cc.c
9
cc.c
|
@ -51,6 +51,7 @@ int main(int argc, char** argv, char** envp)
|
||||||
PREPROCESSOR_MODE = FALSE;
|
PREPROCESSOR_MODE = FALSE;
|
||||||
STDIO_USED = FALSE;
|
STDIO_USED = FALSE;
|
||||||
DIRTY_MODE = FALSE;
|
DIRTY_MODE = FALSE;
|
||||||
|
Architecture = NULL;
|
||||||
|
|
||||||
/* Our fun locals */
|
/* Our fun locals */
|
||||||
int debug_flag = TRUE;
|
int debug_flag = TRUE;
|
||||||
|
@ -108,6 +109,13 @@ int main(int argc, char** argv, char** envp)
|
||||||
fputc('\n', stderr);
|
fputc('\n', stderr);
|
||||||
i+= 2;
|
i+= 2;
|
||||||
}
|
}
|
||||||
|
else if(match(argv[i], "-A") || match(argv[i], "--architecture"))
|
||||||
|
{
|
||||||
|
hold = argv[i+1];
|
||||||
|
require(NULL != hold, "--architecture needs to be passed an architecture\n");
|
||||||
|
Architecture = hold;
|
||||||
|
i += 2;
|
||||||
|
}
|
||||||
else if(match(argv[i], "-f") || match(argv[i], "--file"))
|
else if(match(argv[i], "-f") || match(argv[i], "--file"))
|
||||||
{
|
{
|
||||||
if(NULL == hold_string)
|
if(NULL == hold_string)
|
||||||
|
@ -138,6 +146,7 @@ int main(int argc, char** argv, char** envp)
|
||||||
else if(match(argv[i], "-o") || match(argv[i], "--output"))
|
else if(match(argv[i], "-o") || match(argv[i], "--output"))
|
||||||
{
|
{
|
||||||
destination_name = argv[i + 1];
|
destination_name = argv[i + 1];
|
||||||
|
require(NULL != destination_name, "--output option requires a filename to follow\n");
|
||||||
destination_file = fopen(destination_name, "w");
|
destination_file = fopen(destination_name, "w");
|
||||||
if(NULL == destination_file)
|
if(NULL == destination_file)
|
||||||
{
|
{
|
||||||
|
|
233
cc_env.c
233
cc_env.c
|
@ -21,41 +21,57 @@
|
||||||
|
|
||||||
void init_macro_env(char* sym, char* value, char* source, int num);
|
void init_macro_env(char* sym, char* value, char* source, int num);
|
||||||
char* env_lookup(char* variable);
|
char* env_lookup(char* variable);
|
||||||
|
void clear_string(char* s);
|
||||||
|
|
||||||
void setup_env()
|
void setup_env()
|
||||||
{
|
{
|
||||||
if(2 <= DEBUG_LEVEL) fputs("Starting setup_env\n", stderr);
|
if(2 <= DEBUG_LEVEL) fputs("Starting setup_env\n", stderr);
|
||||||
char* ARCH = NULL;
|
char* ARCH;
|
||||||
struct utsname* unameData = calloc(1, sizeof(struct utsname));
|
if(NULL != Architecture)
|
||||||
require(NULL != unameData, "unameData calloc failed\n");
|
|
||||||
uname(unameData);
|
|
||||||
if(3 <= DEBUG_LEVEL) fputs("obtained architecture details\n", stderr);
|
|
||||||
if(4 <= DEBUG_LEVEL)
|
|
||||||
{
|
{
|
||||||
fputs("utsname details: ", stderr);
|
ARCH = Architecture;
|
||||||
fputs(unameData->machine, stderr);
|
}
|
||||||
fputc('\n', stderr);
|
else
|
||||||
|
{
|
||||||
|
ARCH = NULL;
|
||||||
|
struct utsname* unameData = calloc(1, sizeof(struct utsname));
|
||||||
|
require(NULL != unameData, "unameData calloc failed\n");
|
||||||
|
uname(unameData);
|
||||||
|
if(4 <= DEBUG_LEVEL)
|
||||||
|
{
|
||||||
|
fputs("utsname details: ", stderr);
|
||||||
|
fputs(unameData->machine, stderr);
|
||||||
|
fputc('\n', stderr);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(match("i386", unameData->machine) ||
|
||||||
|
match("i486", unameData->machine) ||
|
||||||
|
match("i586", unameData->machine) ||
|
||||||
|
match("i686", unameData->machine) ||
|
||||||
|
match("i686-pae", unameData->machine)) ARCH = "x86";
|
||||||
|
else if(match("x86_64", unameData->machine)) ARCH = "amd64";
|
||||||
|
else ARCH = unameData->machine;
|
||||||
|
if(3 <= DEBUG_LEVEL)
|
||||||
|
{
|
||||||
|
fputs("Architecture selected: ", stderr);
|
||||||
|
fputs(ARCH, stderr);
|
||||||
|
fputc('\n', stderr);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Check for override */
|
||||||
|
char* hold = env_lookup("ARCHITECTURE_OVERRIDE");
|
||||||
|
if(NULL != hold)
|
||||||
|
{
|
||||||
|
ARCH = hold;
|
||||||
|
if(3 <= DEBUG_LEVEL)
|
||||||
|
{
|
||||||
|
fputs("environmental override for ARCH: ", stderr);
|
||||||
|
fputs(ARCH, stderr);
|
||||||
|
fputc('\n', stderr);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(match("i386", unameData->machine) ||
|
|
||||||
match("i486", unameData->machine) ||
|
|
||||||
match("i586", unameData->machine) ||
|
|
||||||
match("i686", unameData->machine) ||
|
|
||||||
match("i686-pae", unameData->machine)) ARCH = "x86";
|
|
||||||
else if(match("x86_64", unameData->machine)) ARCH = "amd64";
|
|
||||||
else ARCH = unameData->machine;
|
|
||||||
if(3 <= DEBUG_LEVEL)
|
|
||||||
{
|
|
||||||
fputs("Architecture selected: ", stderr);
|
|
||||||
fputs(ARCH, stderr);
|
|
||||||
fputc('\n', stderr);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* Check for override */
|
|
||||||
char* hold = env_lookup("ARCHITECTURE_OVERRIDE");
|
|
||||||
if(NULL != hold) ARCH = hold;
|
|
||||||
if(3 <= DEBUG_LEVEL) fputs("override?\n", stderr);
|
|
||||||
|
|
||||||
/* Set desired architecture */
|
/* Set desired architecture */
|
||||||
WORDSIZE = 32;
|
WORDSIZE = 32;
|
||||||
|
@ -63,22 +79,26 @@ void setup_env()
|
||||||
BASEADDRESS = "0x0";
|
BASEADDRESS = "0x0";
|
||||||
if(match("knight-native", ARCH))
|
if(match("knight-native", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using knight-native architecture\n", stderr);
|
||||||
ENDIAN = TRUE;
|
ENDIAN = TRUE;
|
||||||
Architecture = "knight-native";
|
Architecture = "knight-native";
|
||||||
}
|
}
|
||||||
else if(match("knight-posix", ARCH))
|
else if(match("knight-posix", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using knight-posix architecture\n", stderr);
|
||||||
ENDIAN = TRUE;
|
ENDIAN = TRUE;
|
||||||
Architecture = "knight-posix";
|
Architecture = "knight-posix";
|
||||||
}
|
}
|
||||||
else if(match("x86", ARCH))
|
else if(match("x86", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using x86 architecture\n", stderr);
|
||||||
BASEADDRESS = "0x8048000";
|
BASEADDRESS = "0x8048000";
|
||||||
Architecture = "x86";
|
Architecture = "x86";
|
||||||
init_macro_env("__i386__", "1", "--architecture", 0);
|
init_macro_env("__i386__", "1", "--architecture", 0);
|
||||||
}
|
}
|
||||||
else if(match("amd64", ARCH))
|
else if(match("amd64", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using amd64 architecture\n", stderr);
|
||||||
BASEADDRESS = "0x00600000";
|
BASEADDRESS = "0x00600000";
|
||||||
Architecture = "amd64";
|
Architecture = "amd64";
|
||||||
WORDSIZE = 64;
|
WORDSIZE = 64;
|
||||||
|
@ -86,12 +106,14 @@ void setup_env()
|
||||||
}
|
}
|
||||||
else if(match("armv7l", ARCH))
|
else if(match("armv7l", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using armv7l architecture\n", stderr);
|
||||||
BASEADDRESS = "0x10000";
|
BASEADDRESS = "0x10000";
|
||||||
Architecture = "armv7l";
|
Architecture = "armv7l";
|
||||||
init_macro_env("__arm__", "1", "--architecture", 0);
|
init_macro_env("__arm__", "1", "--architecture", 0);
|
||||||
}
|
}
|
||||||
else if(match("aarch64", ARCH))
|
else if(match("aarch64", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using aarch64 architecture\n", stderr);
|
||||||
BASEADDRESS = "0x400000";
|
BASEADDRESS = "0x400000";
|
||||||
Architecture = "aarch64";
|
Architecture = "aarch64";
|
||||||
WORDSIZE = 64;
|
WORDSIZE = 64;
|
||||||
|
@ -99,14 +121,15 @@ void setup_env()
|
||||||
}
|
}
|
||||||
else if(match("riscv32", ARCH))
|
else if(match("riscv32", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using riscv32 architecture\n", stderr);
|
||||||
BASEADDRESS = "0x600000";
|
BASEADDRESS = "0x600000";
|
||||||
Architecture = "riscv32";
|
Architecture = "riscv32";
|
||||||
WORDSIZE = 64;
|
|
||||||
init_macro_env("__riscv", "1", "--architecture", 0);
|
init_macro_env("__riscv", "1", "--architecture", 0);
|
||||||
init_macro_env("__riscv_xlen", "32", "--architecture", 1);
|
init_macro_env("__riscv_xlen", "32", "--architecture", 1);
|
||||||
}
|
}
|
||||||
else if(match("riscv64", ARCH))
|
else if(match("riscv64", ARCH))
|
||||||
{
|
{
|
||||||
|
if(4 <= DEBUG_LEVEL) fputs("Using riscv64 architecture\n", stderr);
|
||||||
BASEADDRESS = "0x600000";
|
BASEADDRESS = "0x600000";
|
||||||
Architecture = "riscv64";
|
Architecture = "riscv64";
|
||||||
WORDSIZE = 64;
|
WORDSIZE = 64;
|
||||||
|
@ -159,14 +182,26 @@ int array_length(char** array)
|
||||||
/* Search for a variable in the token linked-list */
|
/* Search for a variable in the token linked-list */
|
||||||
char* token_lookup(char* variable, struct Token* token)
|
char* token_lookup(char* variable, struct Token* token)
|
||||||
{
|
{
|
||||||
|
if(6 <= DEBUG_LEVEL)
|
||||||
|
{
|
||||||
|
fputs("in token_lookup\nLooking for: ", stderr);
|
||||||
|
fputs(variable, stderr);
|
||||||
|
fputc('\n', stderr);
|
||||||
|
}
|
||||||
/* Start at the head */
|
/* Start at the head */
|
||||||
struct Token* n = token;
|
struct Token* n = token;
|
||||||
|
|
||||||
/* Loop over the linked-list */
|
/* Loop over the linked-list */
|
||||||
while(n != NULL)
|
while(n != NULL)
|
||||||
{
|
{
|
||||||
|
if(15 <= DEBUG_LEVEL)
|
||||||
|
{
|
||||||
|
fputs(n->var, stderr);
|
||||||
|
fputc('\n', stderr);
|
||||||
|
}
|
||||||
if(match(variable, n->var))
|
if(match(variable, n->var))
|
||||||
{
|
{
|
||||||
|
if(6 <= DEBUG_LEVEL) fputs("match found in token_lookup\n", stderr);
|
||||||
/* We have found the correct node */
|
/* We have found the correct node */
|
||||||
return n->value; /* Done */
|
return n->value; /* Done */
|
||||||
}
|
}
|
||||||
|
@ -185,6 +220,67 @@ char* env_lookup(char* variable)
|
||||||
return token_lookup(variable, env);
|
return token_lookup(variable, env);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
char* envp_hold;
|
||||||
|
int envp_index;
|
||||||
|
|
||||||
|
void reset_envp_hold()
|
||||||
|
{
|
||||||
|
clear_string(envp_hold);
|
||||||
|
envp_index = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void push_env_byte(int c)
|
||||||
|
{
|
||||||
|
envp_hold[envp_index] = c;
|
||||||
|
envp_index = envp_index + 1;
|
||||||
|
require(4096 > envp_index, "Token exceeded 4096 char envp limit\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
struct Token* process_env_variable(char* envp_line, struct Token* n)
|
||||||
|
{
|
||||||
|
struct Token* node = calloc(1, sizeof(struct Token));
|
||||||
|
require(node != NULL, "Memory initialization of node failed\n");
|
||||||
|
reset_envp_hold();
|
||||||
|
int i = 0;
|
||||||
|
|
||||||
|
while(envp_line[i] != '=')
|
||||||
|
{
|
||||||
|
/* Copy over everything up to = to var */
|
||||||
|
push_env_byte(envp_line[i]);
|
||||||
|
i = i + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
node->var = calloc(i + 2, sizeof(char));
|
||||||
|
require(node->var != NULL, "Memory initialization of n->var in population of env failed\n");
|
||||||
|
strcpy(node->var, envp_hold);
|
||||||
|
|
||||||
|
i = i + 1; /* Skip over = */
|
||||||
|
|
||||||
|
reset_envp_hold();
|
||||||
|
while(envp_line[i] != 0)
|
||||||
|
{
|
||||||
|
/* Copy everything else to value */
|
||||||
|
push_env_byte(envp_line[i]);
|
||||||
|
i = i + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Sometimes, we get lines like VAR=, indicating nothing is in the variable */
|
||||||
|
if(0 == strlen(envp_hold))
|
||||||
|
{
|
||||||
|
node->value = "";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
/* but looks like we got something so, lets use it */
|
||||||
|
node->value = calloc(strlen(envp_hold) + 2, sizeof(char));
|
||||||
|
require(node->value != NULL, "Memory initialization of n->var in population of env failed\n");
|
||||||
|
strcpy(node->value, envp_hold);
|
||||||
|
}
|
||||||
|
|
||||||
|
node->next = n;
|
||||||
|
return node;
|
||||||
|
}
|
||||||
|
|
||||||
void populate_env(char** envp)
|
void populate_env(char** envp)
|
||||||
{
|
{
|
||||||
if(2 <= DEBUG_LEVEL) fputs("populate_env started\n", stderr);
|
if(2 <= DEBUG_LEVEL) fputs("populate_env started\n", stderr);
|
||||||
|
@ -205,82 +301,51 @@ void populate_env(char** envp)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Initialize env and n */
|
/* Initialize env and n */
|
||||||
env = calloc(1, sizeof(struct Token));
|
env = NULL;
|
||||||
require(env != NULL, "Memory initialization of env failed\n");
|
|
||||||
struct Token* n;
|
|
||||||
n = env;
|
|
||||||
int i;
|
int i;
|
||||||
int j;
|
envp_hold = calloc(4096, sizeof(char));
|
||||||
int k;
|
require(envp_hold != NULL, "Memory initialization of envp_hold in population of env failed\n");
|
||||||
char* envp_line;
|
char* envp_line = calloc(4096, sizeof(char));
|
||||||
|
require(envp_line != NULL, "Memory initialization of envp_line in population of env failed\n");
|
||||||
|
|
||||||
if(3 <= DEBUG_LEVEL) fputs("starting env loop\n", stderr);
|
if(3 <= DEBUG_LEVEL) fputs("starting env loop\n", stderr);
|
||||||
for(i = 0; i < max; i = i + 1)
|
for(i = 0; i < max; i = i + 1)
|
||||||
{
|
{
|
||||||
n->var = calloc(MAX_STRING, sizeof(char));
|
|
||||||
require(n->var != NULL, "Memory initialization of n->var in population of env failed\n");
|
|
||||||
n->value = calloc(MAX_STRING, sizeof(char));
|
|
||||||
require(n->value != NULL, "Memory initialization of n->var in population of env failed\n");
|
|
||||||
j = 0;
|
|
||||||
/*
|
/*
|
||||||
* envp is weird.
|
* envp is weird.
|
||||||
* When referencing envp[i]'s characters directly, they were all jumbled.
|
* When referencing envp[i]'s characters directly, they were all jumbled.
|
||||||
* So just copy envp[i] to envp_line, and work with that - that seems
|
* So just copy envp[i] to envp_line, and work with that - that seems
|
||||||
* to fix it.
|
* to fix it.
|
||||||
*/
|
*/
|
||||||
envp_line = calloc(MAX_STRING, sizeof(char));
|
clear_string(envp_line);
|
||||||
require(envp_line != NULL, "Memory initialization of envp_line in population of env failed\n");
|
require(4096 > strlen(envp[i]), "envp line exceeds 4096byte limit\n");
|
||||||
strcpy(envp_line, envp[i]);
|
strcpy(envp_line, envp[i]);
|
||||||
|
|
||||||
while(envp_line[j] != '=')
|
if(4 <= DEBUG_LEVEL)
|
||||||
{
|
{
|
||||||
/* Copy over everything up to = to var */
|
fputs("trying envp_line: ", stderr);
|
||||||
n->var[j] = envp_line[j];
|
fputs(envp_line, stderr);
|
||||||
j = j + 1;
|
fputc('\n', stderr);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* If we get strange input, we need to ignore it */
|
env = process_env_variable(envp_line, env);
|
||||||
if(n->var == NULL)
|
|
||||||
|
if(8 <= DEBUG_LEVEL)
|
||||||
{
|
{
|
||||||
continue;
|
fputs("got var of: ", stderr);
|
||||||
|
fputs(env->var, stderr);
|
||||||
|
fputs("\nAnd value of: ", stderr);
|
||||||
|
fputs(env->value, stderr);
|
||||||
|
fputc('\n', stderr);
|
||||||
}
|
}
|
||||||
|
|
||||||
j = j + 1; /* Skip over = */
|
|
||||||
k = 0; /* As envp[i] will continue as j but n->value begins at 0 */
|
|
||||||
|
|
||||||
while(envp_line[j] != 0)
|
|
||||||
{
|
|
||||||
/* Copy everything else to value */
|
|
||||||
n->value[k] = envp_line[j];
|
|
||||||
j = j + 1;
|
|
||||||
k = k + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Sometimes, we get lines like VAR=, indicating nothing is in the variable */
|
|
||||||
if(n->value == NULL)
|
|
||||||
{
|
|
||||||
n->value = "";
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Advance to next part of linked list */
|
|
||||||
n->next = calloc(1, sizeof(struct Token));
|
|
||||||
require(n->next != NULL, "Memory initialization of n->next in population of env failed\n");
|
|
||||||
n = n->next;
|
|
||||||
}
|
}
|
||||||
if(3 <= DEBUG_LEVEL) fputs("env loop successful\n", stderr);
|
if(3 <= DEBUG_LEVEL)
|
||||||
|
|
||||||
/* Get rid of node on the end */
|
|
||||||
n = NULL;
|
|
||||||
/* Also destroy the n->next reference */
|
|
||||||
n = env;
|
|
||||||
|
|
||||||
require(NULL != n, "can't have an empty environment from the creation of a non-null environment\n");
|
|
||||||
require(NULL != n->next, "should have an extra node at the end of the env\n");
|
|
||||||
while(n->next->var != NULL)
|
|
||||||
{
|
{
|
||||||
n = n->next;
|
fputs("\n\nenv loop successful\n", stderr);
|
||||||
|
fputs(int2str(i, 10, FALSE), stderr);
|
||||||
|
fputs(" envp records processed\n\n", stderr);
|
||||||
}
|
}
|
||||||
|
|
||||||
n->next = NULL;
|
require(NULL != env, "can't have an empty environment from the creation of a non-null environment\n");
|
||||||
if(2 <= DEBUG_LEVEL) fputs("populate_env successful\n", stderr);
|
if(2 <= DEBUG_LEVEL) fputs("populate_env successful\n", stderr);
|
||||||
}
|
}
|
||||||
|
|
26
cc_reader.c
26
cc_reader.c
|
@ -59,11 +59,16 @@ int grab_byte()
|
||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
|
|
||||||
int consume_byte(int c)
|
void push_byte(int c)
|
||||||
{
|
{
|
||||||
hold_string[string_index] = c;
|
hold_string[string_index] = c;
|
||||||
string_index = string_index + 1;
|
string_index = string_index + 1;
|
||||||
require(MAX_STRING > string_index, "Token exceeded MAX_STRING char limit\nuse --max-string number to increase\n");
|
require(MAX_STRING > string_index, "Token exceeded MAX_STRING char limit\nuse --max-string number to increase\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
int consume_byte(int c)
|
||||||
|
{
|
||||||
|
push_byte(c);
|
||||||
return grab_byte();
|
return grab_byte();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -104,17 +109,24 @@ int preserve_keyword(int c, char* S)
|
||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void clear_string(char* s)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
while(0 != s[i])
|
||||||
|
{
|
||||||
|
s[i] = 0;
|
||||||
|
i = i + 1;
|
||||||
|
require(i < MAX_STRING, "string exceeded max string size while clearing string\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void reset_hold_string()
|
void reset_hold_string()
|
||||||
{
|
{
|
||||||
int i = MAX_STRING;
|
clear_string(hold_string);
|
||||||
while(0 <= i)
|
|
||||||
{
|
|
||||||
hold_string[i] = 0;
|
|
||||||
i = i - 1;
|
|
||||||
}
|
|
||||||
string_index = 0;
|
string_index = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* note if this is the first token in the list, head needs fixing up */
|
/* note if this is the first token in the list, head needs fixing up */
|
||||||
struct token_list* eat_token(struct token_list* token)
|
struct token_list* eat_token(struct token_list* token)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in New Issue