stage0 修复部分问题
This commit is contained in:
1 parent
5073c2b3ea
commit
a1e684f6d4
3 files changed
+57
-43
No files matched your search
+5
-4
@@ -19,6 +19,7 @@ void spl_prog_init(spl_prog_t *prog) {
|
|||||||
vec_init(prog->natives);
|
vec_init(prog->natives);
|
||||||
vec_init(prog->strtab);
|
vec_init(prog->strtab);
|
||||||
vec_init(prog->gdata);
|
vec_init(prog->gdata);
|
||||||
|
vec_push(prog->gdata, (spl_vm_gdata_t){0});
|
||||||
map_init(prog->symtab, MAP_HASH_STR, MAP_CMP_STR);
|
map_init(prog->symtab, MAP_HASH_STR, MAP_CMP_STR);
|
||||||
prog->debug = NULL;
|
prog->debug = NULL;
|
||||||
}
|
}
|
||||||
@@ -296,7 +297,7 @@ int spl_prog_store_to_file(const char *fname, spl_prog_t *prog) {
|
|||||||
ninsns = vec_size(prog->insns);
|
ninsns = vec_size(prog->insns);
|
||||||
nnatives = vec_size(prog->natives);
|
nnatives = vec_size(prog->natives);
|
||||||
nstrs = vec_size(prog->strtab);
|
nstrs = vec_size(prog->strtab);
|
||||||
ndata = vec_size(prog->gdata);
|
ndata = vec_size(prog->gdata) - 1; /* jump 0 node */
|
||||||
|
|
||||||
/* Calculate total size */
|
/* Calculate total size */
|
||||||
total = 8 /* magic */
|
total = 8 /* magic */
|
||||||
@@ -325,7 +326,7 @@ int spl_prog_store_to_file(const char *fname, spl_prog_t *prog) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* gdata */
|
/* gdata */
|
||||||
for (i = 0; i < ndata; i++) {
|
for (i = 1; i < vec_size(prog->gdata); i++) {
|
||||||
usize dsize = vec_at(prog->gdata, i).size;
|
usize dsize = vec_at(prog->gdata, i).size;
|
||||||
total += 8 + ALIGN8(dsize); /* dsize + data(pad) */
|
total += 8 + ALIGN8(dsize); /* dsize + data(pad) */
|
||||||
}
|
}
|
||||||
@@ -398,7 +399,7 @@ int spl_prog_store_to_file(const char *fname, spl_prog_t *prog) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* ---- global data ---- */
|
/* ---- global data ---- */
|
||||||
for (i = 0; i < ndata; i++) {
|
for (i = 1; i <= ndata; i++) {
|
||||||
spl_vm_gdata_t *entry = &vec_at(prog->gdata, i);
|
spl_vm_gdata_t *entry = &vec_at(prog->gdata, i);
|
||||||
pad = ALIGN8(entry->size) - entry->size;
|
pad = ALIGN8(entry->size) - entry->size;
|
||||||
wr64(&p, entry->size);
|
wr64(&p, entry->size);
|
||||||
@@ -452,7 +453,7 @@ int spl_prog_add_data(spl_prog_t *prog, void *ptr, usize size) {
|
|||||||
memcpy(entry.data, ptr, size);
|
memcpy(entry.data, ptr, size);
|
||||||
entry.size = size;
|
entry.size = size;
|
||||||
vec_push(prog->gdata, entry);
|
vec_push(prog->gdata, entry);
|
||||||
return vec_size(prog->gdata);
|
return (int)(vec_size(prog->gdata) - 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
spl_vm_func_t *spl_prog_get_func(spl_prog_t *prog, const char *name) {
|
spl_vm_func_t *spl_prog_get_func(spl_prog_t *prog, const char *name) {
|
||||||
|
|||||||
+44
-37
@@ -168,63 +168,70 @@ SYSCALL_2(vm_strcmp, const char *, const char *, strcmp(a1, a2))
|
|||||||
SYSCALL_3(vm_memcpy, void *, const void *, size_t, (memcpy(a1, a2, a3), (uintptr_t)a1))
|
SYSCALL_3(vm_memcpy, void *, const void *, size_t, (memcpy(a1, a2, a3), (uintptr_t)a1))
|
||||||
|
|
||||||
static spl_vm_val_t vm_printf(int nargs, spl_vm_val_t *args) {
|
static spl_vm_val_t vm_printf(int nargs, spl_vm_val_t *args) {
|
||||||
(void)args;
|
if (nargs <= 0)
|
||||||
if (nargs <= 0) {
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
/* args[0] 是 SPL 的 []u8 format 参数。VM 里 slice 作为参数传递时,
|
||||||
|
栈上压的是"指向 slice 结构体的指针",结构为 {ptr:*u8, len:u64} */
|
||||||
|
const spl_vm_val_t *fmt_slice = (const spl_vm_val_t *)args[0];
|
||||||
|
const char *fmt = (const char *)fmt_slice[0];
|
||||||
|
usize fmt_len = (usize)fmt_slice[1];
|
||||||
|
|
||||||
|
if (nargs <= 1) {
|
||||||
|
fwrite(fmt, 1, fmt_len, stdout);
|
||||||
|
return (spl_vm_val_t)nargs;
|
||||||
}
|
}
|
||||||
const char *fmt = (const char *)args[0];
|
|
||||||
usize fmt_len = strlen(fmt);
|
|
||||||
typedef VEC(char) string_builder_t;
|
typedef VEC(char) string_builder_t;
|
||||||
string_builder_t buffer;
|
string_builder_t buffer;
|
||||||
vec_init(buffer);
|
vec_init(buffer);
|
||||||
if (nargs <= 1) {
|
|
||||||
printf("%s", fmt);
|
int arg_idx = 1; /* 0 是 format */
|
||||||
return nargs;
|
|
||||||
}
|
|
||||||
int arg_idx = 0;
|
|
||||||
char tmp_buf[32];
|
char tmp_buf[32];
|
||||||
memset(tmp_buf, 0, sizeof(tmp_buf));
|
|
||||||
for (usize i = 0; i < fmt_len; ++i) {
|
for (usize i = 0; i < fmt_len; ++i) {
|
||||||
if (fmt[i] != '%') {
|
if (fmt[i] != '%') {
|
||||||
vec_push(buffer, fmt[i]);
|
vec_push(buffer, fmt[i]);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
arg_idx += 1;
|
if (++i >= fmt_len)
|
||||||
if (++i >= fmt_len) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
switch (fmt[i]) {
|
|
||||||
case '.': {
|
|
||||||
Assert(i + 2 < fmt_len && arg_idx + 1 <= nargs && fmt[i + 1] == '*' &&
|
|
||||||
fmt[i + 2] == 's');
|
|
||||||
for (usize j = 0; j < args[arg_idx]; ++j) {
|
|
||||||
vec_push(buffer, ((const char *)args[arg_idx + 1])[j]);
|
|
||||||
}
|
|
||||||
arg_idx += 1; /* %.*s 消耗 2 个实参(len, data),遇 % 已 +1,这里补 1 */
|
|
||||||
i += 2;
|
|
||||||
} break;
|
|
||||||
case 'd':
|
|
||||||
snprintf(tmp_buf, sizeof(tmp_buf), "%zd", args[arg_idx]);
|
|
||||||
for (usize j = 0; j < strlen(tmp_buf); ++j) {
|
|
||||||
vec_push(buffer, tmp_buf[j]);
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
if (arg_idx >= nargs)
|
||||||
|
break;
|
||||||
|
|
||||||
|
switch (fmt[i]) {
|
||||||
|
case 'd': {
|
||||||
|
memset(tmp_buf, 0, sizeof(tmp_buf));
|
||||||
|
snprintf(tmp_buf, sizeof(tmp_buf), "%zd", (isize)args[arg_idx]);
|
||||||
|
for (usize j = 0; tmp_buf[j] != '\0'; ++j)
|
||||||
|
vec_push(buffer, tmp_buf[j]);
|
||||||
|
arg_idx++;
|
||||||
|
break;
|
||||||
|
}
|
||||||
case 'c':
|
case 'c':
|
||||||
vec_push(buffer, (char)args[arg_idx]);
|
vec_push(buffer, (char)args[arg_idx]);
|
||||||
|
arg_idx++;
|
||||||
break;
|
break;
|
||||||
case 's':
|
case 's': {
|
||||||
for (usize j = 0; j < strlen((const char *)args[arg_idx]); ++j) {
|
const spl_vm_val_t *s = (const spl_vm_val_t *)args[arg_idx];
|
||||||
vec_push(buffer, ((const char *)args[arg_idx])[j]);
|
const char *p = (const char *)s[0];
|
||||||
}
|
usize l = (usize)s[1];
|
||||||
|
for (usize j = 0; j < l; ++j)
|
||||||
|
vec_push(buffer, p[j]);
|
||||||
|
arg_idx++;
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
default:
|
default:
|
||||||
continue;
|
vec_push(buffer, '%');
|
||||||
|
vec_push(buffer, fmt[i]);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
vec_push(buffer, '\0');
|
|
||||||
printf("%s", buffer.data);
|
if (vec_size(buffer) > 0)
|
||||||
|
fwrite(buffer.data, 1, vec_size(buffer), stdout);
|
||||||
vec_free(buffer);
|
vec_free(buffer);
|
||||||
return nargs;
|
return (spl_vm_val_t)nargs;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* =================================================================
|
/* =================================================================
|
||||||
|
|||||||
+8
-2
@@ -328,6 +328,9 @@ static int spl_type_size(spl_vm_kind_t t) {
|
|||||||
_r = _da OP _db; \
|
_r = _da OP _db; \
|
||||||
break; \
|
break; \
|
||||||
} \
|
} \
|
||||||
|
case SPL_BOOL: \
|
||||||
|
_r = (uint8_t)_a OP(uint8_t) _b; \
|
||||||
|
break; \
|
||||||
default: \
|
default: \
|
||||||
_r = 0; \
|
_r = 0; \
|
||||||
break; \
|
break; \
|
||||||
@@ -1018,9 +1021,12 @@ int spl_vm_run_once(spl_vm_t *vm) {
|
|||||||
|
|
||||||
case SPL_GADDR: {
|
case SPL_GADDR: {
|
||||||
spl_vm_val_t _idx = ins->imm;
|
spl_vm_val_t _idx = ins->imm;
|
||||||
if (_idx >= vec_size(prog->gdata))
|
if (_idx == 0 || _idx >= vec_size(prog->gdata))
|
||||||
VM_ERROR("GADDR: global data index out of range");
|
VM_ERROR("GADDR: global data index out of range");
|
||||||
PUSH((spl_vm_val_t)(uintptr_t)vec_at(prog->gdata, _idx).data);
|
spl_vm_gdata_t *gd = &vec_at(prog->gdata, _idx);
|
||||||
|
if (!gd->data)
|
||||||
|
VM_ERROR("GADDR: null gdata entry");
|
||||||
|
PUSH((spl_vm_val_t)(uintptr_t)gd->data);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in new issue
Block a user