Finally became self-hosting
This commit is contained in:
parent
35c9d4036f
commit
426a92ab09
141
cc.c
141
cc.c
|
@ -14,9 +14,10 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "cc.h"
|
||||
#include <getopt.h>
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
#include<string.h>
|
||||
#include"cc.h"
|
||||
|
||||
/* The core functions */
|
||||
void initialize_types();
|
||||
|
@ -24,84 +25,77 @@ struct token_list* read_all_tokens(FILE* a, struct token_list* current);
|
|||
struct token_list* reverse_list(struct token_list* head);
|
||||
struct token_list* program(struct token_list* out);
|
||||
void recursive_output(struct token_list* i, FILE* out);
|
||||
int match(char* a, char* b);
|
||||
void file_print(char* s, FILE* f);
|
||||
char* parse_string(char* string);
|
||||
|
||||
#if !__MESC__
|
||||
static
|
||||
#endif
|
||||
struct option long_options[] = {
|
||||
{"file", required_argument, 0, 'f'},
|
||||
{"output", required_argument, 0, 'o'},
|
||||
{"help", no_argument, 0, 'h'},
|
||||
{"version", no_argument, 0, 'V'},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
|
||||
/* Our essential organizer */
|
||||
int main(int argc, char **argv)
|
||||
void test0(struct token_list* l, FILE* o)
|
||||
{
|
||||
global_token = NULL;
|
||||
|
||||
int c;
|
||||
FILE* source_file;
|
||||
FILE* destination_file = stdout;
|
||||
int option_index = 0;
|
||||
while ((c = getopt_long(argc, argv, "f:h:o:V", long_options, &option_index)) != -1)
|
||||
while(NULL != l)
|
||||
{
|
||||
switch(c)
|
||||
if(l->s[0] == 34)
|
||||
{
|
||||
case 0: break;
|
||||
case 'h':
|
||||
{
|
||||
file_print("Usage: M2-Planet -f FILENAME1 {-f FILENAME2} -o OUTPUT\n", stderr);
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
case 'f':
|
||||
{
|
||||
#if __MESC__
|
||||
source_file = open(optarg, O_RDONLY);
|
||||
#else
|
||||
source_file = fopen(optarg, "r");
|
||||
#endif
|
||||
file_print(parse_string(l->s), o);
|
||||
}
|
||||
else
|
||||
{
|
||||
file_print(l->s, o);
|
||||
}
|
||||
fputc(10, o);
|
||||
l = l->next;
|
||||
}
|
||||
}
|
||||
|
||||
if(NULL == source_file)
|
||||
{
|
||||
file_print("The file: ", stderr);
|
||||
file_print(optarg, stderr);
|
||||
file_print(" can not be opened!\n", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
global_token = read_all_tokens(source_file, global_token);
|
||||
break;
|
||||
}
|
||||
case 'o':
|
||||
int main(int argc, char** argv)
|
||||
{
|
||||
FILE* in = stdin;
|
||||
FILE* destination_file = stdout;
|
||||
int i = 1;
|
||||
while(i <= argc)
|
||||
{
|
||||
if(NULL == argv[i])
|
||||
{
|
||||
i = i + 1;
|
||||
}
|
||||
else if(match(argv[i], "-f"))
|
||||
{
|
||||
in = fopen(argv[i + 1], "r");
|
||||
if(NULL == in)
|
||||
{
|
||||
#if __MESC__
|
||||
destination_file = open(optarg, O_CREAT|O_TRUNC|O_WRONLY, S_IRUSR|S_IWUSR);
|
||||
#else
|
||||
destination_file = fopen(optarg, "w");
|
||||
#endif
|
||||
|
||||
if(NULL == destination_file)
|
||||
{
|
||||
file_print("The file: ", stderr);
|
||||
file_print(optarg, stderr);
|
||||
file_print(" can not be opened!\n", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case 'V':
|
||||
{
|
||||
file_print("M2-Planet 0.1\n", stdout);
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
default:
|
||||
{
|
||||
file_print("Unknown option\n", stderr);
|
||||
file_print("Unable to open for reading file: ", stderr);
|
||||
file_print(argv[i + 1], stderr);
|
||||
file_print("\x0A Aborting to avoid problems\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
global_token = read_all_tokens(in, global_token);
|
||||
i = i + 2;
|
||||
}
|
||||
else if(match(argv[i], "-o"))
|
||||
{
|
||||
destination_file = fopen(argv[i + 1], "w");
|
||||
if(NULL == destination_file)
|
||||
{
|
||||
file_print("Unable to open for writing file: ", stderr);
|
||||
file_print(argv[i + 1], stderr);
|
||||
file_print("\x0A Aborting to avoid problems\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
i = i + 2;
|
||||
}
|
||||
else if(match(argv[i], "--help"))
|
||||
{
|
||||
file_print(" -f input file\x0A -o output file\x0A --help for this message\x0A --version for file version\x0A", stdout);
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
else if(match(argv[i], "--version"))
|
||||
{
|
||||
file_print("Basic test version 0.0.0.1a\x0A", stderr);
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
else
|
||||
{
|
||||
file_print("UNKNOWN ARGUMENT\x0A", stdout);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -122,5 +116,6 @@ int main(int argc, char **argv)
|
|||
recursive_output(globals_list, destination_file);
|
||||
file_print("\n# Program strings\n\n", destination_file);
|
||||
recursive_output(strings_list, destination_file);
|
||||
file_print("\n:ELF_end\n", destination_file);
|
||||
return EXIT_SUCCESS;
|
||||
}
|
||||
|
|
2
cc.h
2
cc.h
|
@ -25,6 +25,8 @@
|
|||
// CONSTANT FALSE 0
|
||||
#define TRUE 1
|
||||
// CONSTANT TRUE 1
|
||||
#define LF 10
|
||||
// CONSTANT LF 10
|
||||
|
||||
void file_print(char* s, FILE* f);
|
||||
int match(char* a, char* b);
|
||||
|
|
316
cc_core.c
316
cc_core.c
|
@ -30,6 +30,11 @@ char* break_target;
|
|||
|
||||
/* Imported functions */
|
||||
char* parse_string(char* string);
|
||||
char* numerate_number(int a);
|
||||
char* postpend_char(char* s, char a);
|
||||
char* prepend_char(char a, char* s);
|
||||
char* prepend_string(char* add, char* base);
|
||||
void require_match(char* message, char* required);
|
||||
|
||||
struct token_list* emit(char *s, struct token_list* head)
|
||||
{
|
||||
|
@ -39,105 +44,6 @@ struct token_list* emit(char *s, struct token_list* head)
|
|||
return t;
|
||||
}
|
||||
|
||||
char* numerate_number(int a)
|
||||
{
|
||||
char* result = calloc(16, sizeof(char));
|
||||
int i = 0;
|
||||
|
||||
/* Deal with Zero case */
|
||||
if(0 == a)
|
||||
{
|
||||
result[0] = '0';
|
||||
result[1] = '\n';
|
||||
return result;
|
||||
}
|
||||
|
||||
/* Deal with negatives */
|
||||
if(0 > a)
|
||||
{
|
||||
result[0] = '-';
|
||||
i = 1;
|
||||
a = a * -1;
|
||||
}
|
||||
|
||||
/* Using the largest 10^n number possible in 32bits */
|
||||
int divisor = 0x3B9ACA00;
|
||||
/* Skip leading Zeros */
|
||||
while(0 == (a / divisor)) divisor = divisor / 10;
|
||||
|
||||
/* Now simply collect numbers until divisor is gone */
|
||||
while(0 < divisor)
|
||||
{
|
||||
result[i] = ((a / divisor) + 48);
|
||||
a = a % divisor;
|
||||
divisor = divisor / 10;
|
||||
i = i + 1;
|
||||
}
|
||||
|
||||
result[i] = '\n';
|
||||
return result;
|
||||
}
|
||||
|
||||
int match(char* a, char* b)
|
||||
{
|
||||
int i = -1;
|
||||
do
|
||||
{
|
||||
i = i + 1;
|
||||
if(a[i] != b[i])
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
} while((0 != a[i]) && (0 !=b[i]));
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
char* postpend_char(char* s, char a)
|
||||
{
|
||||
int i = 0;
|
||||
while(0 != s[i])
|
||||
{
|
||||
i = i + 1;
|
||||
}
|
||||
s[i] = a;
|
||||
return s;
|
||||
}
|
||||
|
||||
char* prepend_char(char a, char* s)
|
||||
{
|
||||
int hold = a;
|
||||
int prev;
|
||||
int i = 0;
|
||||
do
|
||||
{
|
||||
prev = hold;
|
||||
hold = s[i];
|
||||
s[i] = prev;
|
||||
i = i + 1;
|
||||
} while(0 != hold);
|
||||
return s;
|
||||
}
|
||||
|
||||
char* prepend_string(char* add, char* base)
|
||||
{
|
||||
char* ret = calloc(MAX_STRING, sizeof(char));
|
||||
int i = 0;
|
||||
while(0 != add[i])
|
||||
{
|
||||
ret[i] = add[i];
|
||||
i = i + 1;
|
||||
}
|
||||
|
||||
int j = 0;
|
||||
while(0 != base[j])
|
||||
{
|
||||
ret[i] = base[j];
|
||||
i = i + 1;
|
||||
j = j + 1;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
struct token_list* sym_declare(char *s, struct type* t, struct token_list* list)
|
||||
{
|
||||
struct token_list* a = calloc(1, sizeof(struct token_list));
|
||||
|
@ -172,14 +78,22 @@ int stack_index(struct token_list* a, struct token_list* function)
|
|||
|
||||
for(i = function->arguments; NULL != i; i = i->next)
|
||||
{
|
||||
if(i == a) return depth;
|
||||
if(i == a)
|
||||
{
|
||||
if(match("main", function->s))
|
||||
{
|
||||
if(match("argc", i->s)) return (depth - 4);
|
||||
else if(match("argv", i->s)) return (depth + 4);
|
||||
}
|
||||
return depth;
|
||||
}
|
||||
else depth = depth + 4;
|
||||
}
|
||||
|
||||
file_print(a->s,stderr);
|
||||
file_print(" does not exist in function ", stderr);
|
||||
file_print(function->s,stderr);
|
||||
file_print("\n",stderr);
|
||||
file_print("\x0A",stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
|
@ -189,7 +103,7 @@ struct token_list* sym_get_value(char *s, struct token_list* out, struct token_l
|
|||
struct token_list* a = sym_lookup(s, global_constant_list);
|
||||
if(NULL != a)
|
||||
{
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_eax %", postpend_char(a->arguments->s, '\n')), out); return out;
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_eax %", postpend_char(a->arguments->s, LF)), out); return out;
|
||||
}
|
||||
|
||||
a= sym_lookup(s, global_function_list);
|
||||
|
@ -202,8 +116,8 @@ struct token_list* sym_get_value(char *s, struct token_list* out, struct token_l
|
|||
if(NULL != a)
|
||||
{
|
||||
current_target = a->type;
|
||||
out = emit(prepend_string("LOAD_EFFECTIVE_ADDRESS %", postpend_char(numerate_number(stack_index(a, function)), '\n')), out);
|
||||
if(!match("=", global_token->s)) out = emit("LOAD_INTEGER\n", out);
|
||||
out = emit(prepend_string("LOAD_EFFECTIVE_ADDRESS %", postpend_char(numerate_number(stack_index(a, function)), LF)), out);
|
||||
if(!match("=", global_token->s)) out = emit("LOAD_INTEGER\x0A", out);
|
||||
return out;
|
||||
}
|
||||
a = sym_lookup(s, function->arguments);
|
||||
|
@ -211,8 +125,8 @@ struct token_list* sym_get_value(char *s, struct token_list* out, struct token_l
|
|||
if(NULL != a)
|
||||
{
|
||||
current_target = a->type;
|
||||
out = emit(prepend_string("LOAD_EFFECTIVE_ADDRESS %", postpend_char(numerate_number(stack_index(a, function)), '\n')), out);
|
||||
if(!match("=", global_token->s)) out = emit("LOAD_INTEGER\n", out);
|
||||
out = emit(prepend_string("LOAD_EFFECTIVE_ADDRESS %", postpend_char(numerate_number(stack_index(a, function)), LF)), out);
|
||||
if(!match("=", global_token->s) && !match("argv", s)) out = emit("LOAD_INTEGER\x0A", out);
|
||||
return out;
|
||||
}
|
||||
|
||||
|
@ -220,26 +134,16 @@ struct token_list* sym_get_value(char *s, struct token_list* out, struct token_l
|
|||
if(NULL != a)
|
||||
{
|
||||
current_target = a->type;
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_eax &GLOBAL_", postpend_char(s, '\n')), out);
|
||||
if(!match("=", global_token->s)) out = emit("LOAD_INTEGER\n", out);
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_eax &GLOBAL_", postpend_char(s, LF)), out);
|
||||
if(!match("=", global_token->s)) out = emit("LOAD_INTEGER\x0A", out);
|
||||
return out;
|
||||
}
|
||||
|
||||
file_print(s ,stderr);
|
||||
file_print(" is not a defined symbol\n", stderr);
|
||||
file_print(" is not a defined symbol\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
void require_match(char* message, char* required)
|
||||
{
|
||||
if(!match(global_token->s, required))
|
||||
{
|
||||
file_print(message, stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
global_token = global_token->next;
|
||||
}
|
||||
|
||||
struct token_list* expression(struct token_list* out, struct token_list* function);
|
||||
|
||||
/*
|
||||
|
@ -253,7 +157,7 @@ struct token_list* primary_expr(struct token_list* out, struct token_list* funct
|
|||
{
|
||||
if(('0' <= global_token->s[0]) & (global_token->s[0] <= '9'))
|
||||
{
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_eax %", postpend_char(global_token->s, '\n')), out);
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_eax %", postpend_char(global_token->s, LF)), out);
|
||||
global_token = global_token->next;
|
||||
}
|
||||
else if((('a' <= global_token->s[0]) & (global_token->s[0] <= 'z')) | (('A' <= global_token->s[0]) & (global_token->s[0] <= 'Z')))
|
||||
|
@ -264,7 +168,7 @@ struct token_list* primary_expr(struct token_list* out, struct token_list* funct
|
|||
{
|
||||
global_token = global_token->next;
|
||||
out = expression(out, function);
|
||||
require_match("Error in Primary expression\nDidn't get )\n", ")");
|
||||
require_match("Error in Primary expression\nDidn't get )\x0A", ")");
|
||||
}
|
||||
else if(global_token->s[0] == 39)
|
||||
{ /* 39 == ' */
|
||||
|
@ -292,7 +196,7 @@ struct token_list* primary_expr(struct token_list* out, struct token_list* funct
|
|||
{
|
||||
file_print("Recieved ", stderr);
|
||||
file_print(global_token->s, stderr);
|
||||
file_print(" in primary_expr\n", stderr);
|
||||
file_print(" in primary_expr\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
|
@ -309,26 +213,26 @@ struct token_list* process_expression_list(struct token_list* out, struct token_
|
|||
if(global_token->s[0] != ')')
|
||||
{
|
||||
out = expression(out, function);
|
||||
out = emit("PUSH_eax\t#_process_expression1\n", out);
|
||||
out = emit("PUSH_eax\t#_process_expression1\x0A", out);
|
||||
function->temps = function->temps + 1;
|
||||
|
||||
while(global_token->s[0] == ',')
|
||||
{
|
||||
global_token = global_token->next;
|
||||
out = expression(out, function);
|
||||
out = emit("PUSH_eax\t#_process_expression2\n", out);
|
||||
out = emit("PUSH_eax\t#_process_expression2\x0A", out);
|
||||
function->temps = function->temps + 1;
|
||||
}
|
||||
require_match("ERROR in process_expression_list\nNo ) was found\n", ")");
|
||||
require_match("ERROR in process_expression_list\nNo ) was found\x0A", ")");
|
||||
}
|
||||
else global_token = global_token->next;
|
||||
|
||||
out = emit(prepend_string("CALL_IMMEDIATE %FUNCTION_", postpend_char(func, '\n')), out);
|
||||
out = emit(prepend_string("CALL_IMMEDIATE %FUNCTION_", postpend_char(func, LF)), out);
|
||||
|
||||
int i;
|
||||
for(i = function->temps - temp; 0 != i; i = i - 1)
|
||||
{
|
||||
out = emit("POP_ebx\t# _process_expression_locals\n", out);
|
||||
out = emit("POP_ebx\t# _process_expression_locals\x0A", out);
|
||||
}
|
||||
|
||||
function->temps = temp;
|
||||
|
@ -339,7 +243,7 @@ struct token_list* process_expression_list(struct token_list* out, struct token_
|
|||
struct token_list* pre_recursion(struct token_list* out, struct token_list* func)
|
||||
{
|
||||
global_token = global_token->next;
|
||||
out = emit("PUSH_eax\t#_common_recursion\n", out);
|
||||
out = emit("PUSH_eax\t#_common_recursion\x0A", out);
|
||||
func->temps = func->temps + 1;
|
||||
return out;
|
||||
}
|
||||
|
@ -347,7 +251,7 @@ struct token_list* pre_recursion(struct token_list* out, struct token_list* func
|
|||
struct token_list* post_recursion(struct token_list* out, struct token_list* func)
|
||||
{
|
||||
func->temps = func->temps - 1;
|
||||
out = emit("POP_ebx\t# _common_recursion\n", out);
|
||||
out = emit("POP_ebx\t# _common_recursion\x0A", out);
|
||||
return out;
|
||||
}
|
||||
|
||||
|
@ -395,21 +299,21 @@ struct token_list* postfix_expr(struct token_list* out, struct token_list* funct
|
|||
out = emit(prepend_string("SAL_eax_Immediate8 !", numerate_number(ceil_log2(a->indirect->size))), out);
|
||||
}
|
||||
|
||||
out = emit("ADD_ebx_to_eax\n", out);
|
||||
out = emit("ADD_ebx_to_eax\x0A", out);
|
||||
current_target = target;
|
||||
|
||||
if(!match("=", global_token->next->s))
|
||||
{
|
||||
if( 4 == a->indirect->size)
|
||||
{
|
||||
out = emit("LOAD_INTEGER\n", out);
|
||||
out = emit("LOAD_INTEGER\x0A", out);
|
||||
}
|
||||
else
|
||||
{
|
||||
out = emit("LOAD_BYTE\n", out);
|
||||
out = emit("LOAD_BYTE\x0A", out);
|
||||
}
|
||||
}
|
||||
require_match("ERROR in postfix_expr\nMissing ]\n", "]");
|
||||
require_match("ERROR in postfix_expr\nMissing ]\x0A", "]");
|
||||
}
|
||||
else if(global_token->s[0] == '(')
|
||||
{
|
||||
|
@ -417,7 +321,7 @@ struct token_list* postfix_expr(struct token_list* out, struct token_list* funct
|
|||
}
|
||||
else if(match("->", global_token->s))
|
||||
{
|
||||
out = emit("# looking up offset\n", out);
|
||||
out = emit("# looking up offset\x0A", out);
|
||||
global_token = global_token->next;
|
||||
struct type* i;
|
||||
for(i = current_target->members; NULL != i; i = i->members)
|
||||
|
@ -430,18 +334,18 @@ struct token_list* postfix_expr(struct token_list* out, struct token_list* funct
|
|||
file_print(current_target->name, stderr);
|
||||
file_print("->", stderr);
|
||||
file_print(global_token->s, stderr);
|
||||
file_print(" does not exist\n", stderr);
|
||||
file_print(" does not exist\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
if(0 != i->offset)
|
||||
{
|
||||
out = emit("# -> offset calculation\n", out);
|
||||
out = emit("# -> offset calculation\x0A", out);
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_ebx %", numerate_number(i->offset)), out);
|
||||
out = emit("ADD_ebx_to_eax\n", out);
|
||||
out = emit("ADD_ebx_to_eax\x0A", out);
|
||||
}
|
||||
if(!match("=", global_token->next->s))
|
||||
{
|
||||
out = emit("LOAD_INTEGER\n", out);
|
||||
out = emit("LOAD_INTEGER\x0A", out);
|
||||
}
|
||||
current_target = i->type;
|
||||
global_token = global_token->next;
|
||||
|
@ -462,26 +366,26 @@ struct token_list* unary_expr(struct token_list* out, struct token_list* functio
|
|||
{
|
||||
if(match("-", global_token->s))
|
||||
{
|
||||
out = emit("LOAD_IMMEDIATE_eax %0\n", out);
|
||||
out = emit("LOAD_IMMEDIATE_eax %0\x0A", out);
|
||||
out = pre_recursion(out, function);
|
||||
out = postfix_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("SUBTRACT_eax_from_ebx_into_ebx\nMOVE_ebx_to_eax\n", out);
|
||||
out = emit("SUBTRACT_eax_from_ebx_into_ebx\nMOVE_ebx_to_eax\x0A", out);
|
||||
}
|
||||
else if(match("!", global_token->s))
|
||||
{
|
||||
out = emit("LOAD_IMMEDIATE_eax %1\n", out);
|
||||
out = emit("LOAD_IMMEDIATE_eax %1\x0A", out);
|
||||
out = pre_recursion(out, function);
|
||||
out = postfix_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("XOR_ebx_eax_into_eax\n", out);
|
||||
out = emit("XOR_ebx_eax_into_eax\x0A", out);
|
||||
}
|
||||
else if(match("sizeof", global_token->s))
|
||||
{
|
||||
global_token = global_token->next;
|
||||
require_match("ERROR in unary_expr\nMissing (\n", "(");
|
||||
require_match("ERROR in unary_expr\nMissing (\x0A", "(");
|
||||
struct type* a = type_name();
|
||||
require_match("ERROR in unary_expr\nMissing )\n", ")");
|
||||
require_match("ERROR in unary_expr\nMissing )\x0A", ")");
|
||||
|
||||
out = emit(prepend_string("LOAD_IMMEDIATE_eax %", numerate_number(a->size)), out);
|
||||
}
|
||||
|
@ -510,35 +414,35 @@ struct token_list* additive_expr(struct token_list* out, struct token_list* func
|
|||
out = pre_recursion(out, function);
|
||||
out = unary_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("ADD_ebx_to_eax\n", out);
|
||||
out = emit("ADD_ebx_to_eax\x0A", out);
|
||||
}
|
||||
else if(match("-", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = unary_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("SUBTRACT_eax_from_ebx_into_ebx\nMOVE_ebx_to_eax\n", out);
|
||||
out = emit("SUBTRACT_eax_from_ebx_into_ebx\nMOVE_ebx_to_eax\x0A", out);
|
||||
}
|
||||
else if(match("*", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = unary_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("MULTIPLY_eax_by_ebx_into_eax\n", out);
|
||||
out = emit("MULTIPLY_eax_by_ebx_into_eax\x0A", out);
|
||||
}
|
||||
else if(match("/", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = unary_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("DIVIDE_eax_by_ebx_into_eax\n", out);
|
||||
out = emit("XCHG_eax_ebx\nLOAD_IMMEDIATE_edx %0\nDIVIDE_eax_by_ebx_into_eax\x0A", out);
|
||||
}
|
||||
else if(match("%", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = unary_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("MODULUS_eax_from_ebx_into_ebx\nMOVE_ebx_to_eax\n", out);
|
||||
out = emit("XCHG_eax_ebx\nLOAD_IMMEDIATE_edx %0\nMODULUS_eax_from_ebx_into_ebx\nMOVE_edx_to_eax\x0A", out);
|
||||
}
|
||||
else return out;
|
||||
}
|
||||
|
@ -564,7 +468,7 @@ struct token_list* shift_expr(struct token_list* out, struct token_list* functio
|
|||
/* Ugly hack to Work around flaw in x86 */
|
||||
struct token_list* old = out->next;
|
||||
free(out);
|
||||
out = emit("COPY_eax_to_ecx\nPOP_eax\nSAL_eax_cl\n", old);
|
||||
out = emit("COPY_eax_to_ecx\nPOP_eax\nSAL_eax_cl\x0A", old);
|
||||
}
|
||||
else if(match(">>", global_token->s))
|
||||
{
|
||||
|
@ -574,7 +478,7 @@ struct token_list* shift_expr(struct token_list* out, struct token_list* functio
|
|||
/* Ugly hack to Work around flaw in x86 */
|
||||
struct token_list* old = out->next;
|
||||
free(out);
|
||||
out = emit("COPY_eax_to_ecx\nPOP_eax\nSAR_eax_cl\n", old);
|
||||
out = emit("COPY_eax_to_ecx\nPOP_eax\nSAR_eax_cl\x0A", old);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -602,28 +506,28 @@ struct token_list* relational_expr(struct token_list* out, struct token_list* fu
|
|||
out = pre_recursion(out, function);
|
||||
out = shift_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("CMP\nSETL\nMOVEZBL\n", out);
|
||||
out = emit("CMP\nSETL\nMOVEZBL\x0A", out);
|
||||
}
|
||||
else if(match("<=", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = shift_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("CMP\nSETLE\nMOVEZBL\n", out);
|
||||
out = emit("CMP\nSETLE\nMOVEZBL\x0A", out);
|
||||
}
|
||||
else if(match(">=", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = shift_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("CMP\nSETGE\nMOVEZBL\n", out);
|
||||
out = emit("CMP\nSETGE\nMOVEZBL\x0A", out);
|
||||
}
|
||||
else if(match(">", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = shift_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("CMP\nSETG\nMOVEZBL\n", out);
|
||||
out = emit("CMP\nSETG\nMOVEZBL\x0A", out);
|
||||
}
|
||||
else return out;
|
||||
}
|
||||
|
@ -646,14 +550,14 @@ struct token_list* equality_expr(struct token_list* out, struct token_list* func
|
|||
out = pre_recursion(out, function);
|
||||
out = relational_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("CMP\nSETE\nMOVEZBL\n", out);
|
||||
out = emit("CMP\nSETE\nMOVEZBL\x0A", out);
|
||||
}
|
||||
else if(match("!=", global_token->s))
|
||||
{
|
||||
out = pre_recursion(out, function);
|
||||
out = relational_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("CMP\nSETNE\nMOVEZBL\n", out);
|
||||
out = emit("CMP\nSETNE\nMOVEZBL\x0A", out);
|
||||
}
|
||||
else return out;
|
||||
}
|
||||
|
@ -673,7 +577,7 @@ struct token_list* bitwise_and_expr(struct token_list* out, struct token_list* f
|
|||
out = pre_recursion(out, function);
|
||||
out = equality_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("AND_eax_ebx\n", out);
|
||||
out = emit("AND_eax_ebx\x0A", out);
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
@ -692,7 +596,7 @@ struct token_list* bitwise_or_expr(struct token_list* out, struct token_list* fu
|
|||
out = pre_recursion(out, function);
|
||||
out = bitwise_and_expr(out, function);
|
||||
out = post_recursion(out, function);
|
||||
out = emit("OR_eax_ebx\n", out);
|
||||
out = emit("OR_eax_ebx\x0A", out);
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
@ -716,15 +620,15 @@ struct token_list* expression(struct token_list* out, struct token_list* functio
|
|||
|
||||
if(member)
|
||||
{
|
||||
if(1 == target->indirect->size) out = emit("STORE_CHAR\n", out);
|
||||
if(1 == target->indirect->size) out = emit("STORE_CHAR\x0A", out);
|
||||
else if(4 == target->indirect->size)
|
||||
{
|
||||
out = emit("STORE_INTEGER\n", out);
|
||||
out = emit("STORE_INTEGER\x0A", out);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
out = emit("STORE_INTEGER\n", out);
|
||||
out = emit("STORE_INTEGER\x0A", out);
|
||||
}
|
||||
}
|
||||
return out;
|
||||
|
@ -735,7 +639,7 @@ struct token_list* expression(struct token_list* out, struct token_list* functio
|
|||
struct token_list* collect_local(struct token_list* out, struct token_list* function)
|
||||
{
|
||||
struct type* type_size = type_name();
|
||||
out = emit(prepend_string("# Defining local ", prepend_string(global_token->s, "\n")), out);
|
||||
out = emit(prepend_string("# Defining local ", prepend_string(global_token->s, "\x0A")), out);
|
||||
|
||||
struct token_list* a = sym_declare(global_token->s, type_size, function->locals);
|
||||
function->locals = a;
|
||||
|
@ -749,9 +653,9 @@ struct token_list* collect_local(struct token_list* out, struct token_list* func
|
|||
}
|
||||
function->temps = function->temps + 1;
|
||||
|
||||
require_match("ERROR in collect_local\nMissing ;\n", ";");
|
||||
require_match("ERROR in collect_local\nMissing ;\x0A", ";");
|
||||
|
||||
out = emit(prepend_string("PUSH_eax\t#", prepend_string(a->s, "\n")), out);
|
||||
out = emit(prepend_string("PUSH_eax\t#", prepend_string(a->s, "\x0A")), out);
|
||||
return out;
|
||||
}
|
||||
|
||||
|
@ -767,12 +671,12 @@ struct token_list* process_if(struct token_list* out, struct token_list* functio
|
|||
out = emit(prepend_string("# IF_", number_string), out);
|
||||
|
||||
global_token = global_token->next;
|
||||
require_match("ERROR in process_if\nMISSING (\n", "(");
|
||||
require_match("ERROR in process_if\nMISSING (\x0A", "(");
|
||||
out = expression(out, function);
|
||||
|
||||
out = emit(prepend_string("TEST\nJUMP_EQ %ELSE_", number_string), out);
|
||||
|
||||
require_match("ERROR in process_if\nMISSING )\n", ")");
|
||||
require_match("ERROR in process_if\nMISSING )\x0A", ")");
|
||||
out = statement(out, function);
|
||||
|
||||
out = emit(prepend_string("JUMP %_END_IF_", number_string), out);
|
||||
|
@ -802,25 +706,25 @@ struct token_list* process_for(struct token_list* out, struct token_list* functi
|
|||
|
||||
global_token = global_token->next;
|
||||
|
||||
require_match("ERROR in process_for\nMISSING (\n", "(");
|
||||
require_match("ERROR in process_for\nMISSING (\x0A", "(");
|
||||
out = expression(out, function);
|
||||
|
||||
out = emit(prepend_string(":FOR_", number_string), out);
|
||||
|
||||
require_match("ERROR in process_for\nMISSING ;1\n", ";");
|
||||
require_match("ERROR in process_for\nMISSING ;1\x0A", ";");
|
||||
out = expression(out, function);
|
||||
|
||||
out = emit(prepend_string("TEST\nJUMP_EQ %FOR_END_", number_string), out);
|
||||
out = emit(prepend_string("JUMP %FOR_THEN_", number_string), out);
|
||||
out = emit(prepend_string(":FOR_ITER_", number_string), out);
|
||||
|
||||
require_match("ERROR in process_for\nMISSING ;2\n", ";");
|
||||
require_match("ERROR in process_for\nMISSING ;2\x0A", ";");
|
||||
out = expression(out, function);
|
||||
|
||||
out = emit(prepend_string("JUMP %FOR_", number_string), out);
|
||||
out = emit(prepend_string(":FOR_THEN_", number_string), out);
|
||||
|
||||
require_match("ERROR in process_for\nMISSING )\n", ")");
|
||||
require_match("ERROR in process_for\nMISSING )\x0A", ")");
|
||||
out = statement(out, function);
|
||||
|
||||
out = emit(prepend_string("JUMP %FOR_ITER_", number_string), out);
|
||||
|
@ -835,15 +739,15 @@ struct token_list* process_for(struct token_list* out, struct token_list* functi
|
|||
struct token_list* process_asm(struct token_list* out)
|
||||
{
|
||||
global_token = global_token->next;
|
||||
require_match("ERROR in process_asm\nMISSING (\n", "(");
|
||||
require_match("ERROR in process_asm\nMISSING (\x0A", "(");
|
||||
while(34 == global_token->s[0])
|
||||
{/* 34 == " */
|
||||
out = emit((global_token->s + 1), out);
|
||||
out = emit("\n", out);
|
||||
out = emit("\x0A", out);
|
||||
global_token = global_token->next;
|
||||
}
|
||||
require_match("ERROR in process_asm\nMISSING )\n", ")");
|
||||
require_match("ERROR in process_asm\nMISSING ;\n", ";");
|
||||
require_match("ERROR in process_asm\nMISSING )\x0A", ")");
|
||||
require_match("ERROR in process_asm\nMISSING ;\x0A", ";");
|
||||
return out;
|
||||
}
|
||||
|
||||
|
@ -864,11 +768,11 @@ struct token_list* process_do(struct token_list* out, struct token_list* functio
|
|||
global_token = global_token->next;
|
||||
out = statement(out, function);
|
||||
|
||||
require_match("ERROR in process_do\nMISSING while\n", "while");
|
||||
require_match("ERROR in process_do\nMISSING (\n", "(");
|
||||
require_match("ERROR in process_do\nMISSING while\x0A", "while");
|
||||
require_match("ERROR in process_do\nMISSING (\x0A", "(");
|
||||
out = expression(out, function);
|
||||
require_match("ERROR in process_do\nMISSING )\n", ")");
|
||||
require_match("ERROR in process_do\nMISSING ;\n", ";");
|
||||
require_match("ERROR in process_do\nMISSING )\x0A", ")");
|
||||
require_match("ERROR in process_do\nMISSING ;\x0A", ";");
|
||||
|
||||
out = emit(prepend_string("TEST\nJUMP_NE %DO_", number_string), out);
|
||||
out = emit(prepend_string(":DO_END_", number_string), out);
|
||||
|
@ -895,13 +799,13 @@ struct token_list* process_while(struct token_list* out, struct token_list* func
|
|||
out = emit(prepend_string(":WHILE_", number_string), out);
|
||||
|
||||
global_token = global_token->next;
|
||||
require_match("ERROR in process_while\nMISSING (\n", "(");
|
||||
require_match("ERROR in process_while\nMISSING (\x0A", "(");
|
||||
out = expression(out, function);
|
||||
|
||||
out = emit(prepend_string("TEST\nJUMP_EQ %END_WHILE_", number_string), out);
|
||||
out = emit(prepend_string("# THEN_while_", number_string), out);
|
||||
|
||||
require_match("ERROR in process_while\nMISSING )\n", ")");
|
||||
require_match("ERROR in process_while\nMISSING )\x0A", ")");
|
||||
out = statement(out, function);
|
||||
|
||||
out = emit(prepend_string("JUMP %WHILE_", number_string), out);
|
||||
|
@ -918,14 +822,14 @@ struct token_list* return_result(struct token_list* out, struct token_list* func
|
|||
global_token = global_token->next;
|
||||
if(global_token->s[0] != ';') out = expression(out, function);
|
||||
|
||||
require_match("ERROR in return_result\nMISSING ;\n", ";");
|
||||
require_match("ERROR in return_result\nMISSING ;\x0A", ";");
|
||||
|
||||
struct token_list* i;
|
||||
for(i = function->locals; NULL != i; i = i->next)
|
||||
{
|
||||
out = emit("POP_ebx\t# _return_result_locals\n", out);
|
||||
out = emit("POP_ebx\t# _return_result_locals\x0A", out);
|
||||
}
|
||||
out = emit("RETURN\n", out);
|
||||
out = emit("RETURN\x0A", out);
|
||||
return out;
|
||||
}
|
||||
|
||||
|
@ -946,9 +850,9 @@ struct token_list* recursive_statement(struct token_list* out, struct token_list
|
|||
struct token_list* i;
|
||||
for(i = function->locals; frame != i; i = i->next)
|
||||
{
|
||||
if(!match("RETURN\n", out->s))
|
||||
if(!match("RETURN\x0A", out->s))
|
||||
{
|
||||
out = emit( "POP_ebx\t# _recursive_statement_locals\n", out);
|
||||
out = emit( "POP_ebx\t# _recursive_statement_locals\x0A", out);
|
||||
}
|
||||
function->locals = function->locals->next;
|
||||
}
|
||||
|
@ -984,7 +888,7 @@ struct token_list* statement(struct token_list* out, struct token_list* function
|
|||
else if(':' == global_token->s[0])
|
||||
{
|
||||
out = emit(global_token->s, out);
|
||||
out = emit("\t#C goto label\n", out);
|
||||
out = emit("\t#C goto label\x0A", out);
|
||||
global_token = global_token->next;
|
||||
}
|
||||
else if((NULL != lookup_type(global_token->s)) || match("struct", global_token->s))
|
||||
|
@ -1014,9 +918,9 @@ struct token_list* statement(struct token_list* out, struct token_list* function
|
|||
else if(match("goto", global_token->s))
|
||||
{
|
||||
global_token = global_token->next;
|
||||
out = emit(prepend_string("JUMP %", prepend_string(global_token->s, "\n")), out);
|
||||
out = emit(prepend_string("JUMP %", prepend_string(global_token->s, "\x0A")), out);
|
||||
global_token = global_token->next;
|
||||
require_match("ERROR in statement\nMissing ;\n", ";");
|
||||
require_match("ERROR in statement\nMissing ;\x0A", ";");
|
||||
}
|
||||
else if(match("return", global_token->s))
|
||||
{
|
||||
|
@ -1033,17 +937,17 @@ struct token_list* statement(struct token_list* out, struct token_list* function
|
|||
while(i != break_locals)
|
||||
{
|
||||
if(NULL == i) break;
|
||||
out = emit("POP_ebx\t# break_cleanup_locals\n", out);
|
||||
out = emit("POP_ebx\t# break_cleanup_locals\x0A", out);
|
||||
i = i->next;
|
||||
}
|
||||
global_token = global_token->next;
|
||||
out = emit(prepend_string("JUMP %", prepend_string(break_target, "\n")), out);
|
||||
require_match("ERROR in statement\nMissing ;\n", ";");
|
||||
out = emit(prepend_string("JUMP %", prepend_string(break_target, "\x0A")), out);
|
||||
require_match("ERROR in statement\nMissing ;\x0A", ";");
|
||||
}
|
||||
else
|
||||
{
|
||||
out = expression(out, function);
|
||||
require_match("ERROR in statement\nMISSING ;\n", ";");
|
||||
require_match("ERROR in statement\nMISSING ;\x0A", ";");
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
@ -1091,14 +995,14 @@ struct token_list* declare_function(struct token_list* out, struct type* type)
|
|||
if(global_token->s[0] == ';') global_token = global_token->next;
|
||||
else
|
||||
{
|
||||
out = emit(prepend_string("# Defining function ", prepend_string(essential, "\n")), out);
|
||||
out = emit(prepend_string(":FUNCTION_", prepend_string(essential, "\n")), out);
|
||||
out = emit(prepend_string("# Defining function ", prepend_string(essential, "\x0A")), out);
|
||||
out = emit(prepend_string(":FUNCTION_", prepend_string(essential, "\x0A")), out);
|
||||
out = statement(out, func);
|
||||
|
||||
/* Prevent duplicate RETURNS */
|
||||
if(!match("RETURN\n", out->s))
|
||||
if(!match("RETURN\x0A", out->s))
|
||||
{
|
||||
out = emit("RETURN\n", out);
|
||||
out = emit("RETURN\x0A", out);
|
||||
}
|
||||
}
|
||||
return out;
|
||||
|
@ -1124,6 +1028,7 @@ struct token_list* declare_function(struct token_list* out, struct type* type)
|
|||
*/
|
||||
struct token_list* program(struct token_list* out)
|
||||
{
|
||||
struct type* type_size;
|
||||
while(NULL != global_token)
|
||||
{
|
||||
new_type:
|
||||
|
@ -1135,7 +1040,7 @@ new_type:
|
|||
}
|
||||
else
|
||||
{
|
||||
struct type* type_size = type_name();
|
||||
type_size = type_name();
|
||||
if(NULL == type_size)
|
||||
{
|
||||
goto new_type;
|
||||
|
@ -1147,8 +1052,8 @@ new_type:
|
|||
global_symbol_list = sym_declare(global_token->prev->s, type_size, global_symbol_list);
|
||||
|
||||
/* Ensure 4 bytes are allocated for the global */
|
||||
globals_list = emit(prepend_string(":GLOBAL_", prepend_string(global_token->prev->s, "\n")), globals_list);
|
||||
globals_list = emit("NOP\n", globals_list);
|
||||
globals_list = emit(prepend_string(":GLOBAL_", prepend_string(global_token->prev->s, "\x0A")), globals_list);
|
||||
globals_list = emit("NOP\x0A", globals_list);
|
||||
|
||||
global_token = global_token->next;
|
||||
}
|
||||
|
@ -1157,7 +1062,7 @@ new_type:
|
|||
{
|
||||
file_print("Recieved ", stderr);
|
||||
file_print(global_token->s, stderr);
|
||||
file_print(" in program\n", stderr);
|
||||
file_print(" in program\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
@ -1171,12 +1076,3 @@ void recursive_output(struct token_list* i, FILE* out)
|
|||
recursive_output(i->next, out);
|
||||
file_print(i->s, out);
|
||||
}
|
||||
|
||||
void file_print(char* s, FILE* f)
|
||||
{
|
||||
while(0 != s[0])
|
||||
{
|
||||
fputc(s[0], f);
|
||||
s = s + 1;
|
||||
}
|
||||
}
|
||||
|
|
34
cc_strings.c
34
cc_strings.c
|
@ -81,6 +81,14 @@ int weird(char* string)
|
|||
else if('F' == string[2]) return TRUE;
|
||||
else return weird(string+3);
|
||||
}
|
||||
else if('n' == string[1])
|
||||
{
|
||||
return weird(string+2);
|
||||
}
|
||||
else if('t' == string[1])
|
||||
{
|
||||
return weird(string+2);
|
||||
}
|
||||
else
|
||||
{
|
||||
return weird(string+3);
|
||||
|
@ -107,6 +115,16 @@ char* collect_regular_string(char* string)
|
|||
message[i] = t1 + t2;
|
||||
j = j + 4;
|
||||
}
|
||||
else if((string[j] == '\\') & (string[j + 1] == 'n'))
|
||||
{
|
||||
message[i] = 10;
|
||||
j = j + 2;
|
||||
}
|
||||
else if((string[j] == '\\') & (string[j + 1] == 't'))
|
||||
{
|
||||
message[i] = 9;
|
||||
j = j + 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
message[i] = string[j];
|
||||
|
@ -117,7 +135,7 @@ char* collect_regular_string(char* string)
|
|||
}
|
||||
|
||||
message[i] = 34;
|
||||
message[i + 1] = '\n';
|
||||
message[i + 1] = LF;
|
||||
return message;
|
||||
}
|
||||
|
||||
|
@ -141,6 +159,18 @@ char* collect_weird_string(char* string)
|
|||
hold[k + 2] = upcase(string[j + 3]);
|
||||
j = j + 4;
|
||||
}
|
||||
else if((string[j] == '\\') & (string[j + 1] == 'n'))
|
||||
{
|
||||
hold[k + 1] = '0';
|
||||
hold[k + 2] = 'A';
|
||||
j = j + 2;
|
||||
}
|
||||
else if((string[j] == '\\') & (string[j + 1] == 't'))
|
||||
{
|
||||
hold[k + 1] = '0';
|
||||
hold[k + 2] = '9';
|
||||
j = j + 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
hold[k + 1] = table[(string[j] >> 4)];
|
||||
|
@ -155,7 +185,7 @@ char* collect_weird_string(char* string)
|
|||
hold[k + 1] = '0';
|
||||
hold[k + 2] = '0';
|
||||
hold[k + 3] = 39;
|
||||
hold[k + 4] = '\n';
|
||||
hold[k + 4] = LF;
|
||||
return hold;
|
||||
}
|
||||
|
||||
|
|
|
@ -95,7 +95,7 @@ void create_struct()
|
|||
global_types = head;
|
||||
global_token = global_token->next;
|
||||
i->size = 4;
|
||||
require_match("ERROR in create_struct\nMissing {\n", "{");
|
||||
require_match("ERROR in create_struct\x0A Missing {\x0A", "{");
|
||||
struct type* last = NULL;
|
||||
while('}' != global_token->s[0])
|
||||
{
|
||||
|
@ -108,12 +108,12 @@ void create_struct()
|
|||
i->offset = offset;
|
||||
offset = offset + member_type->size;
|
||||
global_token = global_token->next;
|
||||
require_match("ERROR in create_struct\nMissing ;\n", ";");
|
||||
require_match("ERROR in create_struct\x0A Missing ;\x0A", ";");
|
||||
last = i;
|
||||
}
|
||||
|
||||
global_token = global_token->next;
|
||||
require_match("ERROR in create_struct\nMissing ;\n", ";");
|
||||
require_match("ERROR in create_struct\x0A Missing ;\x0A", ";");
|
||||
|
||||
head->size = offset;
|
||||
head->members = last;
|
||||
|
@ -145,7 +145,7 @@ struct type* type_name()
|
|||
{
|
||||
file_print("Unknown type ", stderr);
|
||||
file_print(global_token->s, stderr);
|
||||
file_print("\n", stderr);
|
||||
file_print("\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
else if(NULL == ret)
|
||||
|
|
|
@ -0,0 +1,27 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include "../cc.h"
|
||||
|
||||
void require_match(char* message, char* required)
|
||||
{
|
||||
if(!match(global_token->s, required))
|
||||
{
|
||||
file_print(message, stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
global_token = global_token->next;
|
||||
}
|
72
libc.c
72
libc.c
|
@ -1,72 +0,0 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "cc.h"
|
||||
// CONSTANT NULL 0
|
||||
// CONSTANT EXIT_FAILURE 1
|
||||
// CONSTANT EXIT_SUCCESS 0
|
||||
// CONSTANT stdin 0
|
||||
// CONSTANT stdout 1
|
||||
// CONSTANT stderr 2
|
||||
|
||||
int fgetc(FILE* f);
|
||||
void fputc(char s, FILE* f);
|
||||
FILE* fopen(char* filename, char* mode);
|
||||
int fclose(FILE* file);
|
||||
void* malloc(int size)
|
||||
{
|
||||
asm("STORE_eax_into_ESP_IMMEDIATE8 !4"
|
||||
"PUSH_eax"
|
||||
"LOAD_IMMEDIATE_eax %45"
|
||||
"LOAD_IMMEDIATE_ebx %0"
|
||||
"INT_80"
|
||||
"POP_ebx"
|
||||
"ADD_eax_to_ebx"
|
||||
"PUSH_eax"
|
||||
"PUSH_ebx"
|
||||
"LOAD_IMMEDIATE_eax %45"
|
||||
"INT_80"
|
||||
"POP_ebx"
|
||||
"CMP"
|
||||
"POP_eax"
|
||||
"JUMP_EQ8 !FUNCTION_malloc_Done"
|
||||
"LOAD_IMMEDIATE_eax %-1"
|
||||
":FUNCTION_malloc_Done"
|
||||
"RETURN");
|
||||
}
|
||||
void* calloc(int count, int size)
|
||||
{
|
||||
char* ret = malloc(count * size);
|
||||
int i;
|
||||
for(i = (count * size); i >= 0; i = i - 1)
|
||||
{
|
||||
ret[i] = 0;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
void free(void* pointer)
|
||||
{
|
||||
return;
|
||||
}
|
||||
void exit(int value)
|
||||
{
|
||||
asm("POP_ebx"
|
||||
"POP_ebx"
|
||||
"LOAD_IMMEDIATE_eax %1"
|
||||
"INT_80");
|
||||
}
|
49
makefile
49
makefile
|
@ -6,12 +6,27 @@ all: M2-Planet
|
|||
CC=gcc
|
||||
CFLAGS=-D_GNU_SOURCE -O0 -std=c99 -ggdb
|
||||
|
||||
M2-Planet: cc_reader.c cc_strings.c cc_core.c cc.c cc_types.c cc.h | bin
|
||||
$(CC) $(CFLAGS) cc_reader.c cc_strings.c cc_core.c cc.c cc_types.c cc.h -o bin/M2-Planet
|
||||
M2-Planet-gcc: cc_reader.c cc_strings.c cc_core.c cc.c cc_types.c cc.h | bin
|
||||
$(CC) $(CFLAGS) \
|
||||
test/functions/match.c \
|
||||
test/functions/numerate_number.c \
|
||||
test/functions/file_print.c \
|
||||
test/functions/string.c \
|
||||
functions/require_match.c \
|
||||
cc_reader.c \
|
||||
cc_strings.c \
|
||||
cc_types.c \
|
||||
cc_core.c \
|
||||
cc.c \
|
||||
cc.h \
|
||||
-o bin/M2-Planet-gcc
|
||||
|
||||
M2-Planet-minimal: cc_reader.c cc_strings.c cc_core.c cc-minimal.c cc_types.c cc.h | bin
|
||||
$(CC) $(CFLAGS) cc_reader.c cc_strings.c cc_core.c cc-minimal.c cc_types.c cc.h -o bin/M2-Planet-minimal
|
||||
|
||||
M2-Planet: M2-Planet-gcc | bin results
|
||||
./test/test100/hello.sh
|
||||
|
||||
# Clean up after ourselves
|
||||
.PHONY: clean
|
||||
clean:
|
||||
|
@ -30,6 +45,12 @@ clean:
|
|||
./test/test11/cleanup.sh
|
||||
./test/test12/cleanup.sh
|
||||
./test/test13/cleanup.sh
|
||||
./test/test14/cleanup.sh
|
||||
./test/test15/cleanup.sh
|
||||
./test/test16/cleanup.sh
|
||||
./test/test17/cleanup.sh
|
||||
./test/test18/cleanup.sh
|
||||
./test/test19/cleanup.sh
|
||||
./test/test99/cleanup.sh
|
||||
|
||||
# Directories
|
||||
|
@ -54,6 +75,12 @@ test: test00-binary \
|
|||
test11-binary \
|
||||
test12-binary \
|
||||
test13-binary \
|
||||
test14-binary \
|
||||
test15-binary \
|
||||
test16-binary \
|
||||
test17-binary \
|
||||
test18-binary \
|
||||
test19-binary \
|
||||
test99-binary | results
|
||||
sha256sum -c test/test.answers
|
||||
|
||||
|
@ -99,6 +126,24 @@ test12-binary: M2-Planet | results
|
|||
test13-binary: M2-Planet | results
|
||||
test/test13/hello.sh
|
||||
|
||||
test14-binary: M2-Planet | results
|
||||
test/test14/hello.sh
|
||||
|
||||
test15-binary: M2-Planet | results
|
||||
test/test15/hello.sh
|
||||
|
||||
test16-binary: M2-Planet | results
|
||||
test/test16/hello.sh
|
||||
|
||||
test17-binary: M2-Planet | results
|
||||
test/test17/hello.sh
|
||||
|
||||
test18-binary: M2-Planet | results
|
||||
test/test18/hello.sh
|
||||
|
||||
test19-binary: M2-Planet | results
|
||||
test/test19/hello.sh
|
||||
|
||||
test99-binary: M2-Planet | results
|
||||
test/test99/hello.sh
|
||||
|
||||
|
|
|
@ -15,9 +15,20 @@
|
|||
### You should have received a copy of the GNU General Public License
|
||||
### along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
### stage0's hex2 format for x86
|
||||
### !<label> 1 byte relative
|
||||
### $<label> 2 byte address
|
||||
### @<label> 2 byte relative
|
||||
### &<label> 4 byte address
|
||||
### %<label> 4 byte relative
|
||||
### local_<label> function-local
|
||||
### string_<index> string #<index>
|
||||
|
||||
### elf32.hex2: 32 bit elf header in hex2
|
||||
|
||||
## ELF Header
|
||||
|
||||
:ELF_base
|
||||
7F 45 4C 46 # e_ident[EI_MAG0-3] ELF's magic number
|
||||
|
||||
01 # e_ident[EI_CLASS] Indicating 32 bit
|
||||
|
@ -28,15 +39,17 @@
|
|||
00 # e_ident[EI_ABIVERSION] See above
|
||||
|
||||
00 00 00 00 00 00 00 # e_ident[EI_PAD]
|
||||
|
||||
02 00 # e_type Indicating Executable
|
||||
03 00 # e_machine Indicating 32bit x86
|
||||
01 00 00 00 # e_version Indicating original elf
|
||||
|
||||
54 80 04 08 # e_entry Address of the entry point
|
||||
34 00 00 00 # e_phoff Address of program header table
|
||||
00 00 00 00 # e_shoff Address of section header table
|
||||
&ELF_text # e_entry Address of the entry point
|
||||
%ELF_program_headers>ELF_base # e_phoff Address of program header table
|
||||
00 00 00 00 # e_shoff Address of section header table
|
||||
|
||||
00 00 00 00 # e_flags
|
||||
|
||||
34 00 # e_ehsize Indicating our 52 Byte header
|
||||
|
||||
20 00 # e_phentsize size of a program header table
|
||||
|
@ -48,14 +61,18 @@
|
|||
00 00 # e_shstrndx index of the section names
|
||||
|
||||
## Program Header
|
||||
:ELF_program_headers
|
||||
:ELF_program_header__text
|
||||
01 00 00 00 # p_type
|
||||
00 00 00 00 # p_offset
|
||||
|
||||
00 80 04 08 # p_vaddr
|
||||
00 80 04 08 # p_physaddr
|
||||
&ELF_base # p_vaddr
|
||||
&ELF_base # p_physaddr
|
||||
|
||||
2A 36 00 00 # p_filesz
|
||||
2A 36 00 00 # p_memsz
|
||||
%ELF_end>ELF_base # p_filesz
|
||||
%ELF_end>ELF_base # p_memsz
|
||||
|
||||
07 00 00 00 # p_flags
|
||||
01 00 00 00 # alignmen
|
||||
|
||||
:ELF_text
|
||||
|
|
|
@ -25,6 +25,7 @@ DEFINE COPY_eax_to_ebx 89C3
|
|||
DEFINE COPY_eax_to_ecx 89C1
|
||||
DEFINE COPY_ebx_to_edx 89DA
|
||||
DEFINE COPY_esp_to_ecx 89E1
|
||||
DEFINE DIVIDE_eax_by_ebx_into_eax F7FB
|
||||
DEFINE INT_80 CD80
|
||||
DEFINE JUMP E9
|
||||
DEFINE JUMP_EQ 0F84
|
||||
|
@ -33,14 +34,23 @@ DEFINE JUMP_EQ8 74
|
|||
DEFINE JUMP_NE8 75
|
||||
DEFINE LOAD_BYTE 0FBE00
|
||||
DEFINE LOAD_EFFECTIVE_ADDRESS 8D8424
|
||||
DEFINE LOAD_EFFECTIVE_ADDRESS_ecx 8D4C24
|
||||
DEFINE LOAD_EFFECTIVE_ADDRESS_ebx 8D9C24
|
||||
DEFINE LOAD_EFFECTIVE_ADDRESS_ecx 8D8C24
|
||||
DEFINE LOAD_EFFECTIVE_ADDRESS_edx 8D9424
|
||||
DEFINE LOAD_ESP_IMMEDIATE_into_eax 8B8424
|
||||
DEFINE LOAD_IMMEDIATE_eax B8
|
||||
DEFINE LOAD_IMMEDIATE_ebx BB
|
||||
DEFINE LOAD_IMMEDIATE_edx BA
|
||||
DEFINE LOAD_INTEGER 8B00
|
||||
DEFINE LOAD_INTEGER_ebx 8B1B
|
||||
DEFINE LOAD_INTEGER_ecx 8B09
|
||||
DEFINE LOAD_INTEGER_edx 8B12
|
||||
DEFINE MODULUS_eax_from_ebx_into_ebx F7FB
|
||||
DEFINE MOVEZBL 0FB6C0
|
||||
DEFINE MOVE_ebx_to_eax 89D8
|
||||
DEFINE MOVE_ecx_to_eax 89C8
|
||||
DEFINE MOVE_edx_to_eax 89D0
|
||||
DEFINE MULTIPLY_eax_by_ebx_into_eax F7E3
|
||||
DEFINE NOP 00000000
|
||||
DEFINE NOT_eax F7D0
|
||||
DEFINE OR_eax_ebx 09D8
|
||||
|
@ -64,4 +74,5 @@ DEFINE STORE_INTEGER 8903
|
|||
DEFINE SUBTRACT_eax_from_ebx_into_ebx 29C3
|
||||
DEFINE MOVE_ebx_to_eax 89D8
|
||||
DEFINE TEST 85C0
|
||||
DEFINE XCHG_eax_ebx 93
|
||||
DEFINE XOR_ebx_eax_into_eax 31D8
|
||||
|
|
|
@ -0,0 +1,38 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
void* memset(void* ptr, int value, int num)
|
||||
{
|
||||
char* s;
|
||||
for(s = ptr; 0 < num; num = num - 1)
|
||||
{
|
||||
s[0] = value;
|
||||
s = s + 1;
|
||||
}
|
||||
}
|
||||
|
||||
void* calloc(int count, int size)
|
||||
{
|
||||
void* ret = malloc(count * size);
|
||||
memset(ret, 0, (count * size));
|
||||
return ret;
|
||||
}
|
||||
|
||||
void free(void* l)
|
||||
{
|
||||
return;
|
||||
}
|
|
@ -0,0 +1,25 @@
|
|||
## Copyright (C) 2016 Jeremiah Orians
|
||||
## This file is part of stage0.
|
||||
##
|
||||
## stage0 is free software: you an redistribute it and/or modify
|
||||
## it under the terms of the GNU General Public License as published by
|
||||
## the Free Software Foundation, either version 3 of the License, or
|
||||
## (at your option) any later version.
|
||||
##
|
||||
## stage0 is distributed in the hope that it will be useful,
|
||||
## but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
## GNU General Public License for more details.
|
||||
##
|
||||
## You should have received a copy of the GNU General Public License
|
||||
## along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
// CONSTANT EXIT_FAILURE 1
|
||||
// CONSTANT EXIT_SUCCESS 0
|
||||
|
||||
void exit(int value)
|
||||
{
|
||||
asm("POP_ebx"
|
||||
"POP_ebx"
|
||||
"LOAD_IMMEDIATE_eax %1"
|
||||
"INT_80");
|
||||
}
|
|
@ -0,0 +1,90 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// CONSTANT stdin 0
|
||||
// CONSTANT stdout 1
|
||||
// CONSTANT stderr 2
|
||||
|
||||
int fgetc(FILE* f)
|
||||
{
|
||||
asm("LOAD_IMMEDIATE_eax %3"
|
||||
"LOAD_EFFECTIVE_ADDRESS_ebx %4"
|
||||
"LOAD_INTEGER_ebx"
|
||||
"PUSH_ebx"
|
||||
"COPY_esp_to_ecx"
|
||||
"LOAD_IMMEDIATE_edx %1"
|
||||
"INT_80"
|
||||
"TEST"
|
||||
"POP_eax"
|
||||
"JUMP_NE8 !FUNCTION_fgetc_Done"
|
||||
"LOAD_IMMEDIATE_eax %-1"
|
||||
":FUNCTION_fgetc_Done");
|
||||
}
|
||||
|
||||
void fputc(char s, FILE* f)
|
||||
{
|
||||
asm("LOAD_IMMEDIATE_eax %4"
|
||||
"LOAD_EFFECTIVE_ADDRESS_ebx %4"
|
||||
"LOAD_INTEGER_ebx"
|
||||
"LOAD_EFFECTIVE_ADDRESS_ecx %8"
|
||||
"LOAD_IMMEDIATE_edx %1"
|
||||
"INT_80");
|
||||
}
|
||||
|
||||
/* Important values needed for open
|
||||
* O_RDONLY => 0
|
||||
* O_WRONLY => 1
|
||||
* O_RDWR => 2
|
||||
* O_CREAT => 64
|
||||
* O_TRUNC => 512
|
||||
* S_IRWXU => 00700
|
||||
* S_IXUSR => 00100
|
||||
* S_IWUSR => 00200
|
||||
* S_IRUSR => 00400
|
||||
*/
|
||||
|
||||
FILE* open(char* name, int flag, int mode)
|
||||
{
|
||||
asm("LOAD_EFFECTIVE_ADDRESS_ebx %12"
|
||||
"LOAD_INTEGER_ebx"
|
||||
"LOAD_EFFECTIVE_ADDRESS_ecx %8"
|
||||
"LOAD_INTEGER_ecx"
|
||||
"LOAD_EFFECTIVE_ADDRESS_edx %4"
|
||||
"LOAD_INTEGER_edx"
|
||||
"LOAD_IMMEDIATE_eax %5"
|
||||
"INT_80");
|
||||
}
|
||||
|
||||
FILE* fopen(char* filename, char* mode)
|
||||
{
|
||||
FILE* f;
|
||||
if('w' == mode[0])
|
||||
{ /* 577 is O_WRONLY|O_CREAT|O_TRUNC, 384 is 600 in octal */
|
||||
f = open(filename, 577 , 384);
|
||||
}
|
||||
else
|
||||
{ /* Everything else is a read */
|
||||
f = open(filename, 0, 0);
|
||||
}
|
||||
|
||||
/* Negative numbers are error codes */
|
||||
if(0 > f)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
return f;
|
||||
}
|
|
@ -0,0 +1,26 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdio.h>
|
||||
|
||||
void file_print(char* s, FILE* f)
|
||||
{
|
||||
while(0 != s[0])
|
||||
{
|
||||
fputc(s[0], f);
|
||||
s = s + 1;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,30 @@
|
|||
## Copyright (C) 2016 Jeremiah Orians
|
||||
## This file is part of stage0.
|
||||
##
|
||||
## stage0 is free software: you an redistribute it and/or modify
|
||||
## it under the terms of the GNU General Public License as published by
|
||||
## the Free Software Foundation, either version 3 of the License, or
|
||||
## (at your option) any later version.
|
||||
##
|
||||
## stage0 is distributed in the hope that it will be useful,
|
||||
## but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
## GNU General Public License for more details.
|
||||
##
|
||||
## You should have received a copy of the GNU General Public License
|
||||
## along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
int getchar()
|
||||
{
|
||||
asm("LOAD_IMMEDIATE_eax %3"
|
||||
"LOAD_IMMEDIATE_ebx %0"
|
||||
"PUSH_ebx"
|
||||
"COPY_esp_to_ecx"
|
||||
"LOAD_IMMEDIATE_edx %1"
|
||||
"INT_80"
|
||||
"TEST"
|
||||
"POP_eax"
|
||||
"JUMP_NE8 !FUNCTION_getchar_Done"
|
||||
"LOAD_IMMEDIATE_eax %-1"
|
||||
":FUNCTION_getchar_Done");
|
||||
}
|
|
@ -19,51 +19,3 @@
|
|||
COPY_eax_to_ebx
|
||||
LOAD_IMMEDIATE_eax %1
|
||||
INT_80
|
||||
|
||||
:FUNCTION_exit
|
||||
POP_ebx
|
||||
POP_ebx
|
||||
LOAD_IMMEDIATE_eax %1
|
||||
INT_80
|
||||
|
||||
:FUNCTION_getchar
|
||||
LOAD_IMMEDIATE_eax %3
|
||||
LOAD_IMMEDIATE_ebx %0
|
||||
PUSH_ebx
|
||||
COPY_esp_to_ecx
|
||||
LOAD_IMMEDIATE_edx %1
|
||||
INT_80
|
||||
TEST
|
||||
POP_eax
|
||||
JUMP_NE8 !FUNCTION_getchar_Done
|
||||
LOAD_IMMEDIATE_eax %-1
|
||||
:FUNCTION_getchar_Done
|
||||
RETURN
|
||||
|
||||
:FUNCTION_malloc
|
||||
STORE_eax_into_ESP_IMMEDIATE8 !4
|
||||
PUSH_eax
|
||||
LOAD_IMMEDIATE_eax %45
|
||||
LOAD_IMMEDIATE_ebx %0
|
||||
INT_80
|
||||
POP_ebx
|
||||
ADD_eax_to_ebx
|
||||
PUSH_eax
|
||||
PUSH_ebx
|
||||
LOAD_IMMEDIATE_eax %45
|
||||
INT_80
|
||||
POP_ebx
|
||||
CMP
|
||||
POP_eax
|
||||
JUMP_EQ8 !FUNCTION_malloc_Done
|
||||
LOAD_IMMEDIATE_eax %-1
|
||||
:FUNCTION_malloc_Done
|
||||
RETURN
|
||||
|
||||
:FUNCTION_putchar
|
||||
LOAD_IMMEDIATE_eax %4
|
||||
LOAD_IMMEDIATE_ebx %1
|
||||
LOAD_EFFECTIVE_ADDRESS_ecx !4
|
||||
COPY_ebx_to_edx
|
||||
INT_80
|
||||
RETURN
|
|
@ -0,0 +1,37 @@
|
|||
## Copyright (C) 2016 Jeremiah Orians
|
||||
## This file is part of stage0.
|
||||
##
|
||||
## stage0 is free software: you an redistribute it and/or modify
|
||||
## it under the terms of the GNU General Public License as published by
|
||||
## the Free Software Foundation, either version 3 of the License, or
|
||||
## (at your option) any later version.
|
||||
##
|
||||
## stage0 is distributed in the hope that it will be useful,
|
||||
## but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
## GNU General Public License for more details.
|
||||
##
|
||||
## You should have received a copy of the GNU General Public License
|
||||
## along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
// CONSTANT NULL 0
|
||||
|
||||
void* malloc(int size)
|
||||
{
|
||||
asm("STORE_eax_into_ESP_IMMEDIATE8 !4"
|
||||
"PUSH_eax"
|
||||
"LOAD_IMMEDIATE_eax %45"
|
||||
"LOAD_IMMEDIATE_ebx %0"
|
||||
"INT_80"
|
||||
"POP_ebx"
|
||||
"ADD_eax_to_ebx"
|
||||
"PUSH_eax"
|
||||
"PUSH_ebx"
|
||||
"LOAD_IMMEDIATE_eax %45"
|
||||
"INT_80"
|
||||
"POP_ebx"
|
||||
"CMP"
|
||||
"POP_eax"
|
||||
"JUMP_EQ8 !FUNCTION_malloc_Done"
|
||||
"LOAD_IMMEDIATE_eax %-1"
|
||||
":FUNCTION_malloc_Done");
|
||||
}
|
|
@ -0,0 +1,35 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define FALSE 0
|
||||
// CONSTANT FALSE 0
|
||||
#define TRUE 1
|
||||
// CONSTANT TRUE 1
|
||||
|
||||
int match(char* a, char* b)
|
||||
{
|
||||
int i = -1;
|
||||
do
|
||||
{
|
||||
i = i + 1;
|
||||
if(a[i] != b[i])
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
} while((0 != a[i]) && (0 !=b[i]));
|
||||
return TRUE;
|
||||
}
|
|
@ -0,0 +1,58 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdlib.h>
|
||||
#include<string.h>
|
||||
|
||||
char* numerate_number(int a)
|
||||
{
|
||||
char* result = malloc(16);
|
||||
memset(result, 0, 16);
|
||||
int i = 0;
|
||||
|
||||
/* Deal with Zero case */
|
||||
if(0 == a)
|
||||
{
|
||||
result[0] = '0';
|
||||
result[1] = 10;
|
||||
return result;
|
||||
}
|
||||
|
||||
/* Deal with negatives */
|
||||
if(0 > a)
|
||||
{
|
||||
result[0] = '-';
|
||||
i = 1;
|
||||
a = a * -1;
|
||||
}
|
||||
|
||||
/* Using the largest 10^n number possible in 32bits */
|
||||
int divisor = 0x3B9ACA00;
|
||||
/* Skip leading Zeros */
|
||||
while(0 == (a / divisor)) divisor = divisor / 10;
|
||||
|
||||
/* Now simply collect numbers until divisor is gone */
|
||||
while(0 < divisor)
|
||||
{
|
||||
result[i] = ((a / divisor) + 48);
|
||||
a = a % divisor;
|
||||
divisor = divisor / 10;
|
||||
i = i + 1;
|
||||
}
|
||||
|
||||
result[i] = 10;
|
||||
return result;
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
## Copyright (C) 2016 Jeremiah Orians
|
||||
## This file is part of stage0.
|
||||
##
|
||||
## stage0 is free software: you an redistribute it and/or modify
|
||||
## it under the terms of the GNU General Public License as published by
|
||||
## the Free Software Foundation, either version 3 of the License, or
|
||||
## (at your option) any later version.
|
||||
##
|
||||
## stage0 is distributed in the hope that it will be useful,
|
||||
## but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
## GNU General Public License for more details.
|
||||
##
|
||||
## You should have received a copy of the GNU General Public License
|
||||
## along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
void putchar(int c)
|
||||
{
|
||||
asm("LOAD_IMMEDIATE_eax %4"
|
||||
"LOAD_IMMEDIATE_ebx %1"
|
||||
"LOAD_EFFECTIVE_ADDRESS_ecx %4"
|
||||
"COPY_ebx_to_edx"
|
||||
"INT_80");
|
||||
}
|
|
@ -0,0 +1,64 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdlib.h>
|
||||
#define MAX_STRING 4096
|
||||
|
||||
char* postpend_char(char* s, char a)
|
||||
{
|
||||
int i = 0;
|
||||
while(0 != s[i])
|
||||
{
|
||||
i = i + 1;
|
||||
}
|
||||
s[i] = a;
|
||||
return s;
|
||||
}
|
||||
|
||||
char* prepend_char(char a, char* s)
|
||||
{
|
||||
int hold = a;
|
||||
int prev;
|
||||
int i = 0;
|
||||
do
|
||||
{
|
||||
prev = hold;
|
||||
hold = s[i];
|
||||
s[i] = prev;
|
||||
i = i + 1;
|
||||
} while(0 != hold);
|
||||
return s;
|
||||
}
|
||||
|
||||
char* prepend_string(char* add, char* base)
|
||||
{
|
||||
char* ret = calloc(MAX_STRING, sizeof(char));
|
||||
int i = 0;
|
||||
while(0 != add[i])
|
||||
{
|
||||
ret[i] = add[i];
|
||||
i = i + 1;
|
||||
}
|
||||
|
||||
int j = 0;
|
||||
while(0 != base[j])
|
||||
{
|
||||
ret[i] = base[j];
|
||||
i = i + 1;
|
||||
j = j + 1;
|
||||
}
|
||||
return ret;
|
||||
}
|
|
@ -1,15 +1,21 @@
|
|||
646164d0e3de386d0c534cc5abd415e331c4bfa289e5755688b0ac15b082b8e3 test/results/test00-binary
|
||||
117b1837f95ca77de4a30b2b0428472ce60433ea82b0ca6d2e5f57316ef20c9a test/results/test01-binary
|
||||
3de3e1eabc6b808fbe172c7bb5a4e677a272fcbec7f73f2f896090051280d95a test/results/test02-binary
|
||||
97c9a95f88b63cf318b8caae963abc899004dc17c9695d7f5a2b0f7d4cf7dcb8 test/results/test03-binary
|
||||
e20f8dbbfaf58b3706e7b445dcb63ee8ff071d0efb6bfc00c89ed9365d5555eb test/results/test04-binary
|
||||
e55762fc05b6fca351c0e49a3951810f7361d3516768bd2235ad29a0227564c5 test/results/test05-binary
|
||||
9d26baf5537e489ba73c24feb229d863e356d4796a876f6dc773cc191bc0ce99 test/results/test06-binary
|
||||
c3d09cbcb5d7be5e0cb97dd8592fe20d8ef6799eb4812dce44728d6f1771da48 test/results/test07-binary
|
||||
d236657797c77ded168092a64629bf7f4ed4ff04dbda995ac3550bc3877c8e0e test/results/test08-binary
|
||||
2832ac2466f13aa63f2ccafd1a132b82dbb8d421c9c81ffaa5adaee13cd1b00b test/results/test09-binary
|
||||
04e3f14f5f4dfa18a0674798c16bb0a64842a240576f0841dcb799a94ab8ca49 test/results/test10-binary
|
||||
900d7467cc32fdce1c74289590a00a6fca4fba672e6179f78eed788c3f6b09d0 test/results/test11-binary
|
||||
511b056ea02c6544fdbae3f878a0f4f4f4a7297301f4c199c0fa64807c67025e test/results/test12-binary
|
||||
dfd63f9bb0704b56908b9c8c01bc741443012ef17d0425db3399f4f4000f6a86 test/results/test13-binary
|
||||
44188322e8272196652061d1d0fa2b2403593f51ddd7aa896c8a199740c53d71 test/results/test99-binary
|
||||
c359c568a0c31a0559ed2a9a8232d3d8f439903066e31dac843908b1d79008c6 test/results/test00-binary
|
||||
85db8b71becd83c68331561eb565b7a187cf40019bb84dcd4142371901569489 test/results/test01-binary
|
||||
968dca052b05c2b2e82eec4b0b453de1acd81e4a0a6d5178334a3212ee91db13 test/results/test02-binary
|
||||
53501e16b035f635c68bd3202ac7d815e0a5d9ba7e1c3b76a6e25b6badf58ca5 test/results/test03-binary
|
||||
fc50b56e4115369438187fa3e31a7ae7a20040e033afe0a3159b9e8e69205f7e test/results/test04-binary
|
||||
bda47233fdac376fbd558e4917281d0f717bea4ed3f84f79244a78752e8d2192 test/results/test05-binary
|
||||
a2c36f93cc736a5bc352c74d55bc3f029b8522f83a8422a06a3916a742ca5a2c test/results/test06-binary
|
||||
d27eb315d694324650b11a421d6990eee60ac5921a5625bbccb43d806f09e156 test/results/test07-binary
|
||||
8cc38294fb1261843cfc3956fad5a451c95bbc2ed687435d4e2d59df2c4a8567 test/results/test08-binary
|
||||
cc8f252877a85c0d7832094ff574d7173ac33940917bc1591358b8970651a81c test/results/test09-binary
|
||||
3857aee4183de41bd00b014d616a5d73f4bfc57aa60a6073bb4113d6ff2fb8d5 test/results/test10-binary
|
||||
dce2f0b35323cf6a2b01f74a9335100f2d8626028af545832dbdb503573db0e5 test/results/test11-binary
|
||||
88602970fa07b5da7a42b4f2b2486fe03accc6796e05453c4ab934e986790bef test/results/test12-binary
|
||||
c85a57b5b1d65288efd47a3b12c6fca1efade9e7ec91e65efda5531d2c40d293 test/results/test13-binary
|
||||
ef2b0fd3acd8f478f5f1ea51ab165503e2f22a4c330e5db134e162cf8b624cf8 test/results/test14-binary
|
||||
c432555f7b121e07ae80f6216128b0420bc158293048bc29259d6adb94a05cb4 test/results/test15-binary
|
||||
b1de0d8c35068420d8f15d2fea74496e4f86c905f7c1b8601d569cd5c61d2796 test/results/test16-binary
|
||||
15f1fc51d559b74d7515d3e978a835f7edc765f0763fdbae328f4b03a6b2b92b test/results/test17-binary
|
||||
f2245dea4a08a26f1f63383acedd5a67e918b8c9d8e484f037aee7b71c7f8a50 test/results/test18-binary
|
||||
6f1331ad820cdf9d45506eaac3053b80f4357fe955c30a113d1ec2bf829d79a2 test/results/test19-binary
|
||||
ba3d9623c6512bc327cf934d994e5327e5fad3f7500896e2d8458467fae9b9e9 test/results/test99-binary
|
||||
|
|
|
@ -1,9 +1,17 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test00/return.c -o test/test00/return.M1 || exit 1
|
||||
bin/M2-Planet -f test/test00/return.c \
|
||||
-o test/test00/return.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test00/return.M1 --LittleEndian --Architecture 1 -o test/test00/return.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test00/return.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test00/return.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test00/return.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test00-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test01/library_call.c -o test/test01/library_call.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test01/library_call.c \
|
||||
-o test/test01/library_call.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test01/library_call.M1 --LittleEndian --Architecture 1 -o test/test01/library_call.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test01/library_call.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test01/library_call.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test01/library_call.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test01-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
*/
|
||||
|
||||
/* Ensure that C library calls function correctly */
|
||||
|
||||
#include <stdio.h>
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test02/if.c -o test/test02/if.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test02/if.c \
|
||||
-o test/test02/if.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test02/if.M1 --LittleEndian --Architecture 1 -o test/test02/if.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test02/if.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test02/if.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test02/if.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test02-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that IF statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
|
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that constant statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
#define TRUE 1
|
||||
#define FALSE 0
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test03/constant.c -o test/test03/constant.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test03/constant.c \
|
||||
-o test/test03/constant.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test03/constant.M1 --LittleEndian --Architecture 1 -o test/test03/constant.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test03/constant.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test03/constant.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test03/constant.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test03-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that call statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
#define TRUE 1
|
||||
#define FALSE 0
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test04/call.c -o test/test04/call.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test04/call.c \
|
||||
-o test/test04/call.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test04/call.M1 --LittleEndian --Architecture 1 -o test/test04/call.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test04/call.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test04/call.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test04/call.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test04-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test05/string.c -o test/test05/string.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test05/string.c \
|
||||
-o test/test05/string.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test05/string.M1 --LittleEndian --Architecture 1 -o test/test05/string.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test05/string.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test05/string.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test05/string.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test05-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -14,10 +14,7 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that string statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdio.h>
|
||||
|
||||
void printc(char* s, int a)
|
||||
{
|
||||
|
|
|
@ -16,7 +16,6 @@
|
|||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
int putchar(int);
|
||||
|
||||
int main()
|
||||
{
|
||||
|
|
|
@ -1,9 +1,18 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test06/for.c -o test/test06/for.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/test06/for.c \
|
||||
-o test/test06/for.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test06/for.M1 --LittleEndian --Architecture 1 -o test/test06/for.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test06/for.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test06/for.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test06/for.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test06-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that call statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test07/do.c -o test/test07/do.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test07/do.c \
|
||||
-o test/test07/do.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test07/do.M1 --LittleEndian --Architecture 1 -o test/test07/do.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test07/do.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test07/do.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test07/do.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test07-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -1,9 +1,20 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test08/struct.c -o test/test08/struct.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/functions/malloc.c \
|
||||
-f test/test08/struct.c \
|
||||
-o test/test08/struct.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test08/struct.M1 --LittleEndian --Architecture 1 -o test/test08/struct.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test08/struct.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test08/struct.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test08/struct.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test08-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -15,10 +15,8 @@
|
|||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that call statements behave correctly */
|
||||
void *malloc(int);
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
struct foo
|
||||
{
|
||||
|
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that call statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
void printstring(char* s)
|
||||
{
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test09/goto.c -o test/test09/goto.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test09/goto.c \
|
||||
-o test/test09/goto.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test09/goto.M1 --LittleEndian --Architecture 1 -o test/test09/goto.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test09/goto.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test09/goto.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test09/goto.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test09-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -1,9 +1,20 @@
|
|||
#! /bin/sh
|
||||
set -x
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test10/nested_struct.c -o test/test10/nested_struct.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/functions/malloc.c \
|
||||
-f test/test10/nested_struct.c \
|
||||
-o test/test10/nested_struct.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test10/nested_struct.M1 --LittleEndian --Architecture 1 -o test/test10/nested_struct.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test10/nested_struct.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test10/nested_struct.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test10/nested_struct.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test10-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -14,11 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that nested struct statements behave correctly */
|
||||
void *malloc(int);
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
struct bar
|
||||
{
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
# Ignore the files created by script
|
||||
*.M1
|
||||
*.hex2
|
||||
proof
|
||||
|
||||
# A place to put a good run for comparison
|
||||
actual.M1
|
|
@ -0,0 +1,5 @@
|
|||
#! /bin/sh
|
||||
rm -f test/test100/cc.M1
|
||||
rm -f test/test100/cc.hex2
|
||||
rm -f test/test100/proof
|
||||
exit 0
|
|
@ -0,0 +1,59 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet-gcc -f test/functions/file.c \
|
||||
-f test/functions/malloc.c \
|
||||
-f test/functions/calloc.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/functions/match.c \
|
||||
-f test/functions/numerate_number.c \
|
||||
-f test/functions/file_print.c \
|
||||
-f cc.h \
|
||||
-f test/functions/string.c \
|
||||
-f cc_reader.c \
|
||||
-f cc_strings.c \
|
||||
-f cc_types.c \
|
||||
-f functions/require_match.c \
|
||||
-f cc_core.c \
|
||||
-f cc.c \
|
||||
-o test/test100/cc.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test100/cc.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test100/cc.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test100/cc.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test100-binary --exec_enable || exit 3
|
||||
|
||||
# Ensure binary works if host machine supports test
|
||||
if [ "$(get_machine)" = "x86_64" ]
|
||||
then
|
||||
# Verify that the resulting file works
|
||||
./test/results/test100-binary -f test/functions/file.c \
|
||||
-f test/functions/malloc.c \
|
||||
-f test/functions/calloc.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/functions/match.c \
|
||||
-f test/functions/numerate_number.c \
|
||||
-f test/functions/file_print.c \
|
||||
-f cc.h \
|
||||
-f test/functions/string.c \
|
||||
-f cc_reader.c \
|
||||
-f cc_strings.c \
|
||||
-f cc_types.c \
|
||||
-f functions/require_match.c \
|
||||
-f cc_core.c \
|
||||
-f cc.c \
|
||||
-o test/test100/proof || exit 4
|
||||
|
||||
out=$(sha256sum -c test/test100/proof.answer)
|
||||
[ "$out" = "test/test100/proof: OK" ] || exit 5
|
||||
cp test/results/test100-binary bin/M2-Planet
|
||||
else
|
||||
cp bin/M2-Planet-gcc bin/M2-Planet
|
||||
fi
|
||||
exit 0
|
|
@ -0,0 +1 @@
|
|||
380db88d937c29f6f177daf592df473b97ff2c1dcee4adf82e99cdfb825fbc3e test/test100/proof
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that call statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test11/break-do.c -o test/test11/break-do.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test11/break-do.c \
|
||||
-o test/test11/break-do.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test11/break-do.M1 --LittleEndian --Architecture 1 -o test/test11/break-do.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test11/break-do.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test11/break-do.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test11/break-do.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test11-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that call statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test12/break-for.c -o test/test12/break-for.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test12/break-for.c \
|
||||
-o test/test12/break-for.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test12/break-for.M1 --LittleEndian --Architecture 1 -o test/test12/break-for.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test12/break-for.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test12/break-for.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test12/break-for.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test12-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -14,10 +14,8 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Validate that call statements behave correctly */
|
||||
int putchar(int);
|
||||
void exit(int);
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
|
|
|
@ -1,9 +1,19 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test13/break-while.c -o test/test13/break-while.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/test13/break-while.c \
|
||||
-o test/test13/break-while.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test13/break-while.M1 --LittleEndian --Architecture 1 -o test/test13/break-while.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test13/break-while.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test13/break-while.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test13/break-while.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test13-binary --exec_enable || exit 3
|
||||
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
# Ignore the files created by script
|
||||
*.M1
|
||||
*.hex2
|
||||
proof
|
||||
|
||||
# A place to put a good run for comparison
|
||||
actual.M1
|
|
@ -0,0 +1,39 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
void write_string(char* a)
|
||||
{
|
||||
while(0 != a[0])
|
||||
{
|
||||
putchar(a[0]);
|
||||
a = a + 1;
|
||||
}
|
||||
putchar(10);
|
||||
}
|
||||
|
||||
int main(int argc, char** argv)
|
||||
{
|
||||
int i = 0;
|
||||
while(i < argc)
|
||||
{
|
||||
write_string(argv[i]);
|
||||
i = i + 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
#! /bin/sh
|
||||
rm -f test/test14/basic_args.M1
|
||||
rm -f test/test14/basic_args.hex2
|
||||
rm -f test/test14/proof
|
||||
exit 0
|
|
@ -0,0 +1,27 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/test14/basic_args.c \
|
||||
-o test/test14/basic_args.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test14/basic_args.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test14/basic_args.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test14/basic_args.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test14-binary --exec_enable || exit 3
|
||||
|
||||
# Ensure binary works if host machine supports test
|
||||
if [ "$(get_machine)" = "x86_64" ]
|
||||
then
|
||||
# Verify that the resulting file works
|
||||
./test/results/test14-binary 314 1 5926 5 35897 932384626 43 383279 50288 419 71693 99375105 820974944 >| test/test14/proof || exit 4
|
||||
out=$(sha256sum -c test/test14/proof.answer)
|
||||
[ "$out" = "test/test14/proof: OK" ] || exit 5
|
||||
fi
|
||||
exit 0
|
|
@ -0,0 +1 @@
|
|||
036eed868520c4eb4ebd1c2cfcce3f5fed6618184f151cd26b4e95234ff73115 test/test14/proof
|
|
@ -0,0 +1,7 @@
|
|||
# Ignore the files created by script
|
||||
*.M1
|
||||
*.hex2
|
||||
proof
|
||||
|
||||
# A place to put a good run for comparison
|
||||
actual.M1
|
|
@ -0,0 +1,5 @@
|
|||
#! /bin/sh
|
||||
rm -f test/test15/file_read.M1
|
||||
rm -f test/test15/file_read.hex2
|
||||
rm -f test/test15/proof
|
||||
exit 0
|
|
@ -0,0 +1,37 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdio.h>
|
||||
|
||||
void write_string(FILE* f)
|
||||
{
|
||||
int a = fgetc(f);
|
||||
while(-1 != a)
|
||||
{
|
||||
putchar(a);
|
||||
a = fgetc(f);
|
||||
}
|
||||
}
|
||||
|
||||
int main(int argc, char** argv)
|
||||
{
|
||||
if(2 == argc)
|
||||
{
|
||||
FILE* f = fopen(argv[1], "r");
|
||||
write_string(f);
|
||||
}
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,28 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/functions/file.c \
|
||||
-f test/functions/putchar.c \
|
||||
-f test/test15/file_read.c \
|
||||
-o test/test15/file_read.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test15/file_read.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test15/file_read.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test15/file_read.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test15-binary --exec_enable || exit 3
|
||||
|
||||
# Ensure binary works if host machine supports test
|
||||
if [ "$(get_machine)" = "x86_64" ]
|
||||
then
|
||||
# Verify that the resulting file works
|
||||
./test/results/test15-binary test/test15/file_read.c >| test/test15/proof || exit 4
|
||||
out=$(sha256sum -c test/test15/proof.answer)
|
||||
[ "$out" = "test/test15/proof: OK" ] || exit 5
|
||||
fi
|
||||
exit 0
|
|
@ -0,0 +1 @@
|
|||
65efe46ad54a84cdace0b618447a7aedb72068f9e18a32cbd7643fe46a250f13 test/test15/proof
|
|
@ -0,0 +1,7 @@
|
|||
# Ignore the files created by script
|
||||
*.M1
|
||||
*.hex2
|
||||
proof
|
||||
|
||||
# A place to put a good run for comparison
|
||||
actual.M1
|
|
@ -0,0 +1,5 @@
|
|||
#! /bin/sh
|
||||
rm -f test/test16/file_write.M1
|
||||
rm -f test/test16/file_write.hex2
|
||||
rm -f test/test16/proof
|
||||
exit 0
|
|
@ -0,0 +1,44 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdio.h>
|
||||
|
||||
void write_string(FILE* f)
|
||||
{
|
||||
int i = 65;
|
||||
do
|
||||
{
|
||||
int j = i;
|
||||
do
|
||||
{
|
||||
fputc(j, f);
|
||||
j = j + 1;
|
||||
} while (j <= 90);
|
||||
i = i + 1;
|
||||
fputc(10, f);
|
||||
} while (i <= 90);
|
||||
}
|
||||
|
||||
int main(int argc, char** argv)
|
||||
{
|
||||
FILE* f = stdout;
|
||||
if(2 == argc)
|
||||
{
|
||||
f = fopen(argv[1], "w");
|
||||
}
|
||||
write_string(f);
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,28 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/functions/file.c \
|
||||
-f test/functions/putchar.c \
|
||||
-f test/test16/file_write.c \
|
||||
-o test/test16/file_write.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test16/file_write.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test16/file_write.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test16/file_write.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test16-binary --exec_enable || exit 3
|
||||
|
||||
# Ensure binary works if host machine supports test
|
||||
if [ "$(get_machine)" = "x86_64" ]
|
||||
then
|
||||
# Verify that the resulting file works
|
||||
./test/results/test16-binary test/test16/proof || exit 4
|
||||
out=$(sha256sum -c test/test16/proof.answer)
|
||||
[ "$out" = "test/test16/proof: OK" ] || exit 5
|
||||
fi
|
||||
exit 0
|
|
@ -0,0 +1 @@
|
|||
7dc238b12da104224bdb3d64edea5b5e150964faf868556bbc05d346590e3664 test/test16/proof
|
|
@ -0,0 +1,7 @@
|
|||
# Ignore the files created by script
|
||||
*.M1
|
||||
*.hex2
|
||||
proof
|
||||
|
||||
# A place to put a good run for comparison
|
||||
actual.M1
|
|
@ -0,0 +1,5 @@
|
|||
#! /bin/sh
|
||||
rm -f test/test17/memset.M1
|
||||
rm -f test/test17/memset.hex2
|
||||
rm -f test/test17/proof
|
||||
exit 0
|
|
@ -0,0 +1,29 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/functions/malloc.c \
|
||||
-f test/functions/calloc.c \
|
||||
-f test/functions/putchar.c \
|
||||
-f test/test17/memset.c \
|
||||
-o test/test17/memset.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test17/memset.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test17/memset.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test17/memset.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test17-binary --exec_enable || exit 3
|
||||
|
||||
# Ensure binary works if host machine supports test
|
||||
if [ "$(get_machine)" = "x86_64" ]
|
||||
then
|
||||
# Verify that the resulting file works
|
||||
./test/results/test17-binary >| test/test17/proof || exit 4
|
||||
out=$(sha256sum -c test/test17/proof.answer)
|
||||
[ "$out" = "test/test17/proof: OK" ] || exit 5
|
||||
fi
|
||||
exit 0
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1 @@
|
|||
17bdd78dfd87cb05d15ad1da129e0d1684287dc1c3d8ae5a8f3e1935871eb5ce test/test17/proof
|
|
@ -0,0 +1,7 @@
|
|||
# Ignore the files created by script
|
||||
*.M1
|
||||
*.hex2
|
||||
proof
|
||||
|
||||
# A place to put a good run for comparison
|
||||
actual.M1
|
|
@ -0,0 +1,5 @@
|
|||
#! /bin/sh
|
||||
rm -f test/test18/math.M1
|
||||
rm -f test/test18/math.hex2
|
||||
rm -f test/test18/proof
|
||||
exit 0
|
|
@ -0,0 +1,29 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/functions/file.c \
|
||||
-f test/functions/malloc.c \
|
||||
-f test/functions/calloc.c \
|
||||
-f test/test18/math.c \
|
||||
-o test/test18/math.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test18/math.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test18/math.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test18/math.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test18-binary --exec_enable || exit 3
|
||||
|
||||
# Ensure binary works if host machine supports test
|
||||
if [ "$(get_machine)" = "x86_64" ]
|
||||
then
|
||||
# Verify that the resulting file works
|
||||
./test/results/test18-binary >| test/test18/proof || exit 4
|
||||
out=$(sha256sum -c test/test18/proof.answer)
|
||||
[ "$out" = "test/test18/proof: OK" ] || exit 5
|
||||
fi
|
||||
exit 0
|
|
@ -0,0 +1,76 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
#include<string.h>
|
||||
|
||||
char* numerate_number(int a)
|
||||
{
|
||||
char* result = malloc(16);
|
||||
memset(result, 0, 16);
|
||||
int i = 0;
|
||||
|
||||
/* Deal with Zero case */
|
||||
if(0 == a)
|
||||
{
|
||||
result[0] = '0';
|
||||
result[1] = 10;
|
||||
return result;
|
||||
}
|
||||
|
||||
/* Deal with negatives */
|
||||
if(0 > a)
|
||||
{
|
||||
result[0] = '-';
|
||||
i = 1;
|
||||
a = a * -1;
|
||||
}
|
||||
|
||||
/* Using the largest 10^n number possible in 32bits */
|
||||
int divisor = 0x3B9ACA00;
|
||||
/* Skip leading Zeros */
|
||||
while(0 == (a / divisor)) divisor = divisor / 10;
|
||||
|
||||
/* Now simply collect numbers until divisor is gone */
|
||||
while(0 < divisor)
|
||||
{
|
||||
result[i] = ((a / divisor) + 48);
|
||||
a = a % divisor;
|
||||
divisor = divisor / 10;
|
||||
i = i + 1;
|
||||
}
|
||||
|
||||
result[i] = 10;
|
||||
return result;
|
||||
}
|
||||
|
||||
void write_string(char* s, FILE* f)
|
||||
{
|
||||
while(0 != s[0])
|
||||
{
|
||||
fputc(s[0], f);
|
||||
s = s + 1;
|
||||
}
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
write_string(numerate_number(1248), stdout);
|
||||
write_string(numerate_number(0), stdout);
|
||||
write_string(numerate_number(-1248), stdout);
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
daadb01014c1eac7d257c7b0c8acfd27e383f6e6ca94c798c4ecb7d4b48e8337 test/test18/proof
|
|
@ -0,0 +1,7 @@
|
|||
# Ignore the files created by script
|
||||
*.M1
|
||||
*.hex2
|
||||
proof
|
||||
|
||||
# A place to put a good run for comparison
|
||||
actual.M1
|
|
@ -0,0 +1,5 @@
|
|||
#! /bin/sh
|
||||
rm -f test/test19/getopt.M1
|
||||
rm -f test/test19/getopt.hex2
|
||||
rm -f test/test19/proof
|
||||
exit 0
|
|
@ -0,0 +1,107 @@
|
|||
/* Copyright (C) 2016 Jeremiah Orians
|
||||
* This file is part of stage0.
|
||||
*
|
||||
* stage0 is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* stage0 is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with stage0. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include<stdlib.h>
|
||||
#include<stdio.h>
|
||||
|
||||
int char2int(char c)
|
||||
{
|
||||
if((48 <= c) && (57>= c))
|
||||
{
|
||||
return (c - 48);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void write_string(char* c, FILE* f)
|
||||
{
|
||||
while(0 != c[0])
|
||||
{
|
||||
fputc(c[0], f);
|
||||
c = c + 1;
|
||||
}
|
||||
}
|
||||
|
||||
char* numerate_number(int a);
|
||||
void sum_file(FILE* input, FILE* output)
|
||||
{
|
||||
int c = fgetc(input);
|
||||
int sum = 0;
|
||||
while(0 <= c)
|
||||
{
|
||||
sum = sum + char2int(c);
|
||||
c = fgetc(input);
|
||||
}
|
||||
|
||||
write_string(numerate_number(sum), output);
|
||||
}
|
||||
|
||||
int match(char* a, char* b);
|
||||
int main(int argc, char** argv)
|
||||
{
|
||||
FILE* in = stdin;
|
||||
FILE* out = stdout;
|
||||
int i = 1;
|
||||
while(i <= argc)
|
||||
{
|
||||
if(NULL == argv[i])
|
||||
{
|
||||
i = i + 1;
|
||||
}
|
||||
else if(match(argv[i], "-f"))
|
||||
{
|
||||
in = fopen(argv[i + 1], "r");
|
||||
if(NULL == in)
|
||||
{
|
||||
write_string("Unable to open for reading file: ", stderr);
|
||||
write_string(argv[i + 1], stderr);
|
||||
write_string("\x0A Aborting to avoid problems\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
i = i + 2;
|
||||
}
|
||||
else if(match(argv[i], "-o"))
|
||||
{
|
||||
out = fopen(argv[i + 1], "w");
|
||||
if(NULL == out)
|
||||
{
|
||||
write_string("Unable to open for writing file: ", stderr);
|
||||
write_string(argv[i + 1], stderr);
|
||||
write_string("\x0A Aborting to avoid problems\x0A", stderr);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
i = i + 2;
|
||||
}
|
||||
else if(match(argv[i], "--help"))
|
||||
{
|
||||
write_string(" -f input file\x0A -o output file\x0A --help for this message\x0A --version for file version\x0A", stdout);
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
else if(match(argv[i], "--version"))
|
||||
{
|
||||
write_string("Basic test version 0.0.0.1a\x0A", stderr);
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
else
|
||||
{
|
||||
write_string("UNKNOWN ARGUMENT\x0A", stdout);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
sum_file(in, out);
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,32 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/functions/file.c \
|
||||
-f test/functions/malloc.c \
|
||||
-f test/functions/calloc.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/functions/match.c \
|
||||
-f test/functions/numerate_number.c \
|
||||
-f test/test19/getopt.c \
|
||||
-o test/test19/getopt.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test19/getopt.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test19/getopt.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test19/getopt.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test19-binary --exec_enable || exit 3
|
||||
|
||||
# Ensure binary works if host machine supports test
|
||||
if [ "$(get_machine)" = "x86_64" ]
|
||||
then
|
||||
# Verify that the resulting file works
|
||||
./test/results/test19-binary -f test/test19/input -o test/test19/proof || exit 4
|
||||
out=$(sha256sum -c test/test19/proof.answer)
|
||||
[ "$out" = "test/test19/proof: OK" ] || exit 5
|
||||
fi
|
||||
exit 0
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1 @@
|
|||
62deae9018fab41292bfd3234d4d46b2f2d91af0121550ebb3aa4ada04c118b2 test/test19/proof
|
|
@ -1,9 +1,21 @@
|
|||
#! /bin/sh
|
||||
set -ex
|
||||
# Build the test
|
||||
bin/M2-Planet -f test/test99/cc500.c -o test/test99/cc0.M1 || exit 1
|
||||
bin/M2-Planet -f test/functions/putchar.c \
|
||||
-f test/functions/getchar.c \
|
||||
-f test/functions/exit.c \
|
||||
-f test/functions/malloc.c \
|
||||
-f test/test99/cc500.c \
|
||||
-o test/test99/cc0.M1 || exit 1
|
||||
|
||||
# Macro assemble with libc written in M1-Macro
|
||||
M1 -f test/common_x86/x86_defs.M1 -f test/common_x86/libc.M1 -f test/test99/cc0.M1 --LittleEndian --Architecture 1 -o test/test99/cc0.hex2 || exit 2
|
||||
M1 -f test/common_x86/x86_defs.M1 \
|
||||
-f test/functions/libc-core.M1 \
|
||||
-f test/test99/cc0.M1 \
|
||||
--LittleEndian \
|
||||
--Architecture 1 \
|
||||
-o test/test99/cc0.hex2 || exit 2
|
||||
|
||||
# Resolve all linkages
|
||||
hex2 -f test/common_x86/ELF-i386.hex2 -f test/test99/cc0.hex2 --LittleEndian --Architecture 1 --BaseAddress 0x8048000 -o test/results/test99-binary --exec_enable || exit 3
|
||||
|
||||
|
|
Loading…
Reference in New Issue