-
Notifications
You must be signed in to change notification settings - Fork 6
/
Copy pathmain.c
100 lines (81 loc) · 2.55 KB
/
main.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
#include "include/syscall.h"
/**
Simple subset of C.
- All types are 32-bit unsigned integer, C types may be specified but are ignored
- No varargs
- Any variable may be dereferenced, indexed, or called like a function
- All #defines must have a single numerical value
- Simple assignment only (does not support -= += ++ -- etc)
- No forward declarations, but symbol resolution is two-pass
- Simplistic cast expression support:
- (char)... is equivalent to (... & 0xff)
- (struct ...*|unsigned|unsigned *|int|int *|void *) are elided as used only for compatibility w/full compilers
Stdlib limits:
- malloc (but no free)
- alloca (freed on function return)
*/
#define OPEN_READ 0
#define OPEN_WRITE 1
char* newline = "\n";
int input_handle;
int output_handle;
/***********************************************************************/
/* Utility routines */
/***********************************************************************/
void fatal(char* error) {
syscall(SC_WRITE, 2, error, strlen(error));
syscall(SC_WRITE, 2, newline, 1);
syscall(SC_EXIT, 1);
}
/***********************************************************************/
/* String routines */
/***********************************************************************/
void memset(char* buffer, int value, int length) {
char* ptr = buffer;
while (length > 0) {
*ptr = value;
ptr = ptr + 1;
length = length - 1;
}
}
void strlen(char* string) {
char* ptr = string;
int length = 0;
while (*ptr != 0) {
ptr = ptr + 1;
length = length + 1;
}
return length;
}
/***********************************************************************/
/* Syscall routines */
/***********************************************************************/
int open(char* filename, int mode) {
int handle;
if (mode == OPEN_READ) {
handle = syscall(SC_OPEN, filename, O_RDONLY);
} else {
handle = syscall(SC_OPEN, filename, O_RDWR | O_TRUNC | O_CREAT);
}
if ((handle + 1) == 0) {
fatal("Failed to open file");
}
return handle;
}
char* getargv(int index) {
/* Returns a buffer that is still technically on the stack but it'll work alright */
int* buffer = alloca(0x1000);
syscall(SC_GETARGV, buffer, 0x1000);
char* s = buffer[index + 1];
return s;
}
/***********************************************************************/
/* Main */
/***********************************************************************/
int main() {
if (getargv(1) == 0 || getargv(2) == 0) {
error("Usage: bootstrap5 [input] [output]");
}
input_handle = open(getargv(1), OPEN_READ);
output_handle = open(getargv(2), OPEN_WRITE);
}