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
|
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include "oper.h"
#include "panic.h"
#include "slice.h"
static struct slice xmalloc(size_t size)
{
void *p = malloc(size);
if (!p) {
panicf("Out of memory!\n");
}
return (struct slice) {
.buf = p,
.size = size,
};
}
static struct slice xrealloc(void *ptr, size_t size)
{
void *p = realloc(ptr, size);
if (!p) {
panicf("Out of memory!\n");
}
return (struct slice) {
.buf = p,
.size = size,
};
}
void read_file(struct slice *out, char *filename)
{
FILE *f = fopen(filename, "r");
if (!f) {
panicf("File %s does not exit!\n", filename);
}
size_t offset = 0;
while (true) {
if (offset >= out->size) {
size_t new_size = 2 * out->size;
*out = xrealloc(out->buf, new_size);
}
size_t read_size = out->size - offset;
size_t n = fread(out->buf + offset, 1, read_size, f);
if (n < read_size) {
if (ferror(f)) {
panicf("Read error!\n");
}
out->size = offset + n;
return;
}
offset += n;
}
}
int main(int argc, char **argv)
{
if (argc < 2) {
printf("Usage error: need a filename.\n");
return 1;
}
struct slice program = xmalloc(1);
read_file(&program, argv[1]);
run(program);
free(program.buf);
}
|