-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathrv32im.c
80 lines (65 loc) · 1.58 KB
/
rv32im.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
#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
#include "../arch.h"
#ifndef JTAG_BASE
#define JTAG_BASE 0x100000
#endif
#ifndef MEM_BASE
#define MEM_BASE 0x300000
#endif
#ifndef MEM_SIZE
#define MEM_SIZE 0x100000
#endif
#ifndef STACK_WORDS
#define STACK_WORDS 0x1000
#endif
#define JTAG ((volatile uint32_t *const) JTAG_BASE)
#define JTF_READY (1<<15)
#define JTF_CHAR (0x7f)
void arch_fflush(unsigned long _) {}
void arch_fputc(unsigned long hdl, char c) {
if(hdl == STDOUT || hdl == STDERR) {
*JTAG = JTF_CHAR & c;
}
}
int arch_fgetc(unsigned long hdl) {
uint32_t value;
if(hdl != STDIN) return EOF;
while(1) {
value = *JTAG;
if(value & JTF_READY) return JTF_CHAR & value;
}
}
void arch_halt(int _) { while(1); }
static int arch_heap_was_init = 0;
void arch_new_heap(size_t min_sz, void **region, size_t *sz) {
if(!arch_heap_was_init) {
arch_heap_was_init = 1;
*region = (void *)MEM_BASE;
*sz = MEM_SIZE;
fprintf(stderr, "%s: gave heap %p len %p\n", __func__, *region, *sz);
} else {
fprintf(stderr, "%s: no more heap\n", __func__);
}
}
void arch_release_heap(void *region, size_t sz) {
if(arch_heap_was_init)
fprintf(stderr, "%s: released heap at %p size %p\n", __func__, region, sz);
else
fprintf(stderr, "%s: double-free at %p size %p\n", __func__, region, sz);
arch_heap_was_init = 0;
}
uint32_t stack[STACK_WORDS];
uint32_t *stack_top = stack + STACK_WORDS;
int main();
__asm__(
".global _start\n"
".section begin\n"
"_start:\n"
" la sp, stack_top\n"
" mv fp, zero\n"
" call main\n"
" li a0, 0\n"
" call arch_halt\n"
);