mirror of
https://github.com/nunuhara/xsystem4.git
synced 2026-10-08 22:59:57 +03:00
Implement DUP_U2, SP_INC, DELETE, R_ASSIGN
Reference assignment.
This commit is contained in:
@@ -79,6 +79,23 @@ enum ain_data_type {
|
||||
case AIN_ARRAY_LONG_INT: \
|
||||
case AIN_ARRAY_DELEGATE
|
||||
|
||||
#define AIN_REF_TYPE \
|
||||
AIN_REF_INT: \
|
||||
case AIN_REF_FLOAT: \
|
||||
case AIN_REF_STRING: \
|
||||
case AIN_REF_STRUCT: \
|
||||
case AIN_REF_ARRAY_INT: \
|
||||
case AIN_REF_ARRAY_FLOAT: \
|
||||
case AIN_REF_ARRAY_STRING: \
|
||||
case AIN_REF_ARRAY_STRUCT: \
|
||||
case AIN_REF_FUNC_TYPE: \
|
||||
case AIN_REF_ARRAY_FUNC_TYPE: \
|
||||
case AIN_REF_BOOL: \
|
||||
case AIN_REF_ARRAY_BOOL: \
|
||||
case AIN_REF_LONG_INT: \
|
||||
case AIN_REF_ARRAY_LONG_INT: \
|
||||
case AIN_REF_ARRAY_DELEGATE
|
||||
|
||||
struct ain_variable {
|
||||
char *name;
|
||||
int32_t data_type;
|
||||
|
||||
+5
-5
@@ -155,9 +155,9 @@ const struct instruction instructions[NR_OPCODES] = {
|
||||
OP(I_STRING, 0),
|
||||
JMP(CALLFUNC2, 0),
|
||||
OP(DUP2_X1, 0),
|
||||
OP(R_ASSIGN, 0), // TODO
|
||||
OP(R_ASSIGN, 0),
|
||||
OP(FT_ASSIGNS, 0), // TODO
|
||||
OP(ASSERT, 0), // TODO
|
||||
OP(ASSERT, 0),
|
||||
OP(S_LT, 0),
|
||||
OP(S_GT, 0),
|
||||
OP(S_LTE, 0),
|
||||
@@ -165,12 +165,12 @@ const struct instruction instructions[NR_OPCODES] = {
|
||||
OP(S_LENGTH2, 0), // TODO
|
||||
OP(S_LENGTHBYTE2, 0), // TODO
|
||||
OP(NEW, 0), // TODO
|
||||
OP(DELETE, 0), // TODO
|
||||
OP(DELETE, 0),
|
||||
OP(CHECKUDO, 0), // TODO
|
||||
OP(A_REF, 0),
|
||||
OP(DUP, 0),
|
||||
OP(DUP_U2, 0), // TODO
|
||||
OP(SP_INC, 0), // TODO
|
||||
OP(DUP_U2, 0),
|
||||
OP(SP_INC, 0),
|
||||
OP(SP_DEC, 0), // TODO
|
||||
OP(ENDFUNC, 1, INSTR_FUN),
|
||||
OP(R_EQUALE, 0), // TODO
|
||||
|
||||
@@ -90,6 +90,13 @@ int test_string_switch_default(string s)
|
||||
return -1;
|
||||
}
|
||||
|
||||
ref int gi;
|
||||
|
||||
void set_page_ref(int v)
|
||||
{
|
||||
gi <- v;
|
||||
}
|
||||
|
||||
void test_lang(void)
|
||||
{
|
||||
int i;
|
||||
@@ -112,4 +119,5 @@ void test_lang(void)
|
||||
test_equal("string switch", test_string_switch("b"), 1);
|
||||
test_equal("string switch (no default)", test_string_switch("d"), 100);
|
||||
test_equal("string switch (default)", test_string_switch_default("d"), 100);
|
||||
test_equal("local ref escape", (set_page_ref(42), gi), 42);
|
||||
}
|
||||
|
||||
@@ -210,7 +210,7 @@ static union vm_value *stack_pop_var(void)
|
||||
int32_t page_index = stack_pop().i;
|
||||
int32_t heap_index = stack_pop().i;
|
||||
if (!heap[heap_index].page || page_index >= heap[heap_index].page->nr_vars)
|
||||
EXECUTION_ERROR("Out of bounds page index");
|
||||
EXECUTION_ERROR("Out of bounds page index: %d/%d", heap_index, page_index);
|
||||
return &heap[heap_index].page->values[page_index];
|
||||
}
|
||||
|
||||
@@ -320,6 +320,10 @@ static void system_call(int32_t code)
|
||||
case 0x0: // system.Exit(int nResult)
|
||||
sys_exit(stack_pop().i);
|
||||
break;
|
||||
case 0x3: // system.LockPeek()
|
||||
case 0x4: // system.UnlockPeek()
|
||||
stack_push(1);
|
||||
break;
|
||||
case 0x6: // system.Output(string szText)
|
||||
str = stack_peek_string(0);
|
||||
utf = sjis2utf(str->text, str->size);
|
||||
@@ -432,11 +436,18 @@ static void execute_instruction(int16_t opcode)
|
||||
stack_push(b);
|
||||
stack_push(c);
|
||||
break;
|
||||
case DUP_U2:
|
||||
// AB -> ABA
|
||||
stack_push(stack_peek(1).i);
|
||||
break;
|
||||
case SWAP:
|
||||
a = stack_peek(1).i;
|
||||
stack_set(1, stack_peek(0));
|
||||
stack_set(0, a);
|
||||
break;
|
||||
//
|
||||
// --- Variables ---
|
||||
//
|
||||
case PUSHGLOBALPAGE:
|
||||
stack_push(0);
|
||||
break;
|
||||
@@ -481,6 +492,23 @@ static void execute_instruction(int16_t opcode)
|
||||
case SH_LOCALCREATE: // VARNO, STRUCTNO
|
||||
create_struct(get_argument(1), local_ptr(get_argument(0)));
|
||||
break;
|
||||
case R_ASSIGN:
|
||||
varno = stack_pop().i;
|
||||
pageno = stack_pop().i;
|
||||
dst_i = stack_pop().i;
|
||||
dst = stack_pop().i;
|
||||
heap[dst].page->values[dst_i].i = pageno;
|
||||
heap[dst].page->values[dst_i+1].i = varno;
|
||||
stack_push(pageno);
|
||||
stack_push(varno);
|
||||
break;
|
||||
case DELETE:
|
||||
if ((slot = stack_pop().i) != -1)
|
||||
heap_unref(slot);
|
||||
break;
|
||||
case SP_INC:
|
||||
heap_ref(stack_pop().i);
|
||||
break;
|
||||
//
|
||||
// --- Control Flow ---
|
||||
//
|
||||
@@ -1028,6 +1056,8 @@ void vm_execute_ain(struct ain *program)
|
||||
case AIN_STRING:
|
||||
heap[0].page->values[i].i = heap_alloc_slot(VM_STRING);
|
||||
break;
|
||||
case AIN_REF_TYPE:
|
||||
heap[0].page->values[i].i = -1;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user