*
This commit is contained in:
parent
b98af7bdde
commit
5991d9fef3
6 changed files with 52 additions and 2 deletions
1
README
1
README
|
|
@ -12,4 +12,5 @@
|
|||
|
||||
TODO:
|
||||
- [o] "#load" pragma
|
||||
- [o better dip/keep (avoid using the retain stack for them)
|
||||
- [ ] hand-rolled parser
|
||||
|
|
|
|||
11
examples/cat.grr
Normal file
11
examples/cat.grr
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
#load("std.grr")
|
||||
|
||||
def while {
|
||||
swap dup bury >r >r
|
||||
if: call dup
|
||||
[r> dup >r call r> r> swap while]
|
||||
[drop r> drop r> drop];
|
||||
}
|
||||
|
||||
while: [stdin fgetline]
|
||||
[print];
|
||||
37
src/file.c
37
src/file.c
|
|
@ -1,5 +1,8 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "src/gc.h"
|
||||
#include "src/object.h"
|
||||
#include "string.h"
|
||||
#include "userdata.h"
|
||||
#include "vm.h"
|
||||
|
|
@ -13,6 +16,11 @@ Ut userdata_file = {
|
|||
};
|
||||
// clang-format on
|
||||
|
||||
I prim_file_stdin(Vm *vm) {
|
||||
vm_push(vm, vm->stdin);
|
||||
return 0;
|
||||
}
|
||||
|
||||
I prim_file_stdout(Vm *vm) {
|
||||
vm_push(vm, vm->stdout);
|
||||
return 0;
|
||||
|
|
@ -29,13 +37,13 @@ I prim_file_fprint(Vm *vm) {
|
|||
|
||||
Ud *file_ud = userdata_unwrap(file_obj, &userdata_file);
|
||||
if (file_ud == NULL) {
|
||||
fprintf(stderr, "expected file object");
|
||||
fprintf(stderr, "expected file object\n");
|
||||
return VM_ERR_TYPE;
|
||||
};
|
||||
|
||||
Str *str = string_unwrap(string_obj);
|
||||
if (str == NULL) {
|
||||
fprintf(stderr, "expected string");
|
||||
fprintf(stderr, "expected string\n");
|
||||
return VM_ERR_TYPE;
|
||||
}
|
||||
|
||||
|
|
@ -43,6 +51,31 @@ I prim_file_fprint(Vm *vm) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
I prim_file_fgetline(Vm *vm) {
|
||||
O file_obj = vm_pop(vm);
|
||||
I mark = gc_mark(&vm->gc);
|
||||
gc_addroot(&vm->gc, &file_obj);
|
||||
|
||||
Ud *file_ud = userdata_unwrap(file_obj, &userdata_file);
|
||||
if (file_ud == NULL) {
|
||||
fprintf(stderr, "expected file object\n");
|
||||
return VM_ERR_TYPE;
|
||||
}
|
||||
|
||||
char *lineptr = NULL;
|
||||
size_t size;
|
||||
I len = getline(&lineptr, &size, (FILE *)file_ud->data);
|
||||
if (len == -1) {
|
||||
vm_push(vm, NIL);
|
||||
} else {
|
||||
vm_push(vm, string_make(vm, lineptr, len));
|
||||
}
|
||||
free(lineptr);
|
||||
|
||||
gc_reset(&vm->gc, mark);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static V finalizer(V *data) {
|
||||
FILE *f = (FILE *)data;
|
||||
if (f && f != stdin && f != stdout && f != stderr)
|
||||
|
|
|
|||
|
|
@ -2,6 +2,8 @@
|
|||
|
||||
extern Ut userdata_file;
|
||||
|
||||
I prim_file_stdin(Vm *);
|
||||
I prim_file_stdout(Vm *);
|
||||
I prim_file_stderr(Vm *);
|
||||
I prim_file_fprint(Vm *);
|
||||
I prim_file_fgetline(Vm *vm);
|
||||
|
|
|
|||
|
|
@ -28,9 +28,11 @@ static I prim_printstack(Vm *vm) {
|
|||
Pr primitives_table[] = {
|
||||
{".", prim_pprint},
|
||||
{".s", prim_printstack},
|
||||
{"stdin", prim_file_stdin},
|
||||
{"stdout", prim_file_stdout},
|
||||
{"stderr", prim_file_stderr},
|
||||
{"fprint", prim_file_fprint},
|
||||
{"fgetline", prim_file_fgetline},
|
||||
{NULL, NULL},
|
||||
};
|
||||
// clang-format on
|
||||
|
|
|
|||
|
|
@ -21,6 +21,7 @@ V print(O o) {
|
|||
printf("<quotation>");
|
||||
break;
|
||||
case OBJ_STR: {
|
||||
// TODO: make this binary safe
|
||||
Str *s = string_unwrap(o);
|
||||
char *escaped = malloc(s->len + 1);
|
||||
memcpy(escaped, s->data, s->len);
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue