From 20154ba51994a547221ed348be5c2a69386701eb Mon Sep 17 00:00:00 2001 From: "K. Lange" Date: Tue, 28 Feb 2023 15:45:36 +0900 Subject: [PATCH] New opcodes to support *-expansion in collection expressions --- src/opcodes.h | 8 ++++++++ src/vm.c | 55 +++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 63 insertions(+) diff --git a/src/opcodes.h b/src/opcodes.h index 5ef88ac..1093c10 100644 --- a/src/opcodes.h +++ b/src/opcodes.h @@ -110,3 +110,11 @@ OPERAND(OP_EXPAND_ARGS,EXPAND_ARGS_MORE) JUMP(OP_CALL_ITER,+) JUMP(OP_JUMP_IF_TRUE_OR_POP,+) OPERAND(OP_MISSING_KW, NOOP) + +SIMPLE(OP_LIST_EXTEND_TOP) +SIMPLE(OP_LIST_APPEND_TOP) +SIMPLE(OP_DICT_UPDATE_TOP) +SIMPLE(OP_DICT_SET_TOP) +SIMPLE(OP_SET_UPDATE_TOP) +SIMPLE(OP_SET_ADD_TOP) +SIMPLE(OP_TUPLE_FROM_LIST) diff --git a/src/vm.c b/src/vm.c index 23cf995..5e30a5a 100644 --- a/src/vm.c +++ b/src/vm.c @@ -1979,6 +1979,9 @@ extern KrkValue krk_int_op_sub(krk_integer_type a, krk_integer_type b); extern FUNC_SIG(list,append); extern FUNC_SIG(dict,__setitem__); extern FUNC_SIG(set,add); +extern FUNC_SIG(list,extend); +extern FUNC_SIG(dict,update); +extern FUNC_SIG(set,update); static inline void makeCollection(NativeFn func, size_t count) { KrkValue collection = krk_callNativeOnStack(count, &krk_currentThread.stackTop[-count], 0, func); @@ -2372,6 +2375,58 @@ _finishReturn: (void)0; break; } + case OP_LIST_APPEND_TOP: { + KrkValue list = krk_peek(1); + FUNC_NAME(list,append)(2,(KrkValue[]){list,krk_peek(0)},0); + krk_pop(); + break; + } + case OP_DICT_SET_TOP: { + KrkValue dict = krk_peek(2); + FUNC_NAME(dict,__setitem__)(3,(KrkValue[]){dict,krk_peek(1),krk_peek(0)},0); + krk_pop(); + krk_pop(); + break; + } + case OP_SET_ADD_TOP: { + KrkValue set = krk_peek(1); + FUNC_NAME(set,add)(2,(KrkValue[]){set,krk_peek(0)},0); + krk_pop(); + break; + } + + case OP_LIST_EXTEND_TOP: { + KrkValue list = krk_peek(1); + FUNC_NAME(list,extend)(2,(KrkValue[]){list,krk_peek(0)},0); + krk_pop(); + break; + } + case OP_DICT_UPDATE_TOP: { + KrkValue dict = krk_peek(1); + FUNC_NAME(dict,update)(2,(KrkValue[]){dict,krk_peek(0)},0); + krk_pop(); + break; + } + case OP_SET_UPDATE_TOP: { + KrkValue set = krk_peek(1); + FUNC_NAME(set,update)(2,(KrkValue[]){set,krk_peek(0)},0); + krk_pop(); + break; + } + + case OP_TUPLE_FROM_LIST: { + KrkValue list = krk_peek(0); + size_t count = AS_LIST(list)->count; + KrkValue tuple = OBJECT_VAL(krk_newTuple(count)); + krk_push(tuple); + for (size_t i = 0; i < count; ++i) { + AS_TUPLE(tuple)->values.values[AS_TUPLE(tuple)->values.count++] = AS_LIST(list)->values[i]; + } + krk_swap(1); + krk_pop(); + break; + } + /* * Two-byte operands */