This commit is contained in:
dzaima 2022-06-19 21:05:05 +03:00
parent 0232cda412
commit 43b8b5e2a0
4 changed files with 32 additions and 7 deletions

View File

@ -32,6 +32,10 @@ Erase the specified variable name.
Not a system function because it only clears the variables value (previous code `↩`ing it will still be able to), and to allow it to be executed even when the VM is completely out of memory such that it can't even parse REPL input BQN.
## `)escaped "escaped expr"`
Parse `\`-escapes and execute as REPL input. Primarily for external tools to be able to execute multiline input.
## `)mem`
Get statistics on memory usage.

View File

@ -506,7 +506,7 @@ static void freed_visit(Value* x) {
static void empty_free(Value* x) { err("FREEING EMPTY\n"); }
static void builtin_free(Value* x) { err("FREEING BUILTIN\n"); }
DEF_FREE(def) { }
static void def_visit(Value* x) { printf("(no visit for %d=%s)\n", x->type, type_repr(x->type)); }
static void def_visit(Value* x) { err("undefined visit for object\n"); }
static void def_print(FILE* f, B x) { fprintf(f, "(%d=%s)", v(x)->type, type_repr(v(x)->type)); }
static bool def_canStore(B x) { return false; }
static B def_identity(B f) { return bi_N; }
@ -646,6 +646,7 @@ void base_init() { // very first init function
TIi(t_empty,getU) = empty_getU;
#endif
TIi(t_shape,visit) = noop_visit;
TIi(t_temp,visit) = noop_visit;
TIi(t_funBI,visit) = TIi(t_md1BI,visit) = TIi(t_md2BI,visit) = noop_visit;
TIi(t_funBI,freeO) = TIi(t_md1BI,freeO) = TIi(t_md2BI,freeO) = builtin_free;
TIi(t_funBI,freeF) = TIi(t_md1BI,freeF) = TIi(t_md2BI,freeF) = builtin_free;

View File

@ -2,6 +2,7 @@
#include "vm.h"
#include "ns.h"
#include "utils/utf.h"
#include "utils/talloc.h"
#include "utils/file.h"
#include "utils/time.h"
#include "utils/interrupt.h"
@ -46,6 +47,15 @@ void profiler_free(void);
void profiler_displayResults(void);
void clearImportCache(void);
static B escape_parser;
B simple_unescape(B x) {
if (RARE(escape_parser.u==0)) {
escape_parser = bqn_exec(utf8Decode0("{m←\"Expected surrounding quotes\" ⋄ m!2≤≠𝕩 ⋄ m!\"\"\"\"\"\"≡0‿¯1⊏𝕩 ⋄ s←¬e←<`'\\'=𝕩 ⋄ i‿o←\"\\\"\"nr\"\"\\\"\"\"∾@+10‿13 ⋄ 1↓¯1↓{n←i⊐𝕩\"Unknown escape\"!∧´n≠≠i ⋄ n⊏o}⌾((s/»e)⊸/) s/𝕩}"), bi_N, bi_N);
gc_add(escape_parser);
}
return c1(escape_parser, x);
}
i64 readInt(char** p) {
char* c = *p;
i64 am = 0;
@ -58,7 +68,6 @@ i64 readInt(char** p) {
}
void cbqn_runLine0(char* ln, i64 read) {
if (ln[0]==10) return;
if (ln[read-1]==10) ln[--read] = 0;
B code;
int output; // 0-no; 1-formatter; 2-internal
@ -74,6 +83,16 @@ void cbqn_runLine0(char* ln, i64 read) {
} else if (isCmd(cmdS, &cmdE, "r ")) {
code = utf8Decode0(cmdE);
output = 0;
} else if (isCmd(cmdS, &cmdE, "escaped ")) {
B u = simple_unescape(utf8Decode0(cmdE));
u64 len = utf8lenB(u);
TALLOC(char, ascii, len+1);
toUTF8(u, ascii);
dec(u);
ascii[len] = '\0';
cbqn_runLine0(ascii, len+1);
TFREE(ascii);
return;
} else if (isCmd(cmdS, &cmdE, "t ") || isCmd(cmdS, &cmdE, "time ")) {
code = utf8Decode0(cmdE);
time = -1;
@ -234,10 +253,6 @@ void cbqn_runLine0(char* ln, i64 read) {
}
} else dec(res);
#ifdef HEAP_VERIFY
heapVerify();
#endif
gc_maybeGC();
}
void cbqn_runLine(char* ln, i64 len) {
@ -254,6 +269,10 @@ void cbqn_runLine(char* ln, i64 len) {
}
cbqn_takeInterrupts(true);
cbqn_runLine0(ln, len);
#ifdef HEAP_VERIFY
heapVerify();
#endif
gc_maybeGC();
cbqn_takeInterrupts(false);
popCatch();
}
@ -396,6 +415,7 @@ int main(int argc, char* argv[]) {
size_t gl = 0;
i64 read = getline(&ln, &gl, stdin);
if (read<=0 || ln[0]==0) { if(!silentREPL) putchar('\n'); break; }
if (ln[read-1]==10) ln[--read] = 0;
cbqn_runLine(ln, read);
free(ln);
}

View File

@ -33,7 +33,7 @@ static void gc_tryFree(Value* v) {
if (t==t_freed) err("GC found t_freed\n");
#endif
if (t!=t_empty && !(v->mmInfo&0x80)) {
if (t==t_shape) return;
if (t==t_shape || t==t_temp) return;
#ifdef DONT_FREE
v->flags = t;
#else