Pārlūkot izejas kodu

remove `py_callcfunc`

blueloveTH 1 gadu atpakaļ
vecāks
revīzija
8eff9abfbc

+ 0 - 2
include/pocketpy/pocketpy.h

@@ -329,8 +329,6 @@ bool py_call(py_Ref f, int argc, py_Ref argv) PY_RAISE;
 /// The result will be set to `py_retval()`.
 /// The stack remains unchanged after the operation.
 bool py_callmethod(py_Ref self, py_Name name, int argc, py_Ref argv) PY_RAISE;
-/// Call a `py_CFunction` in a safe way.
-bool py_callcfunc(py_StackRef p0, py_CFunction cfunc, int argc, py_Ref argv) PY_RAISE;
 
 bool py_str(py_Ref val) PY_RAISE;
 bool py_repr(py_Ref val) PY_RAISE;

+ 8 - 8
src/interpreter/ceval.c

@@ -268,8 +268,8 @@ pk_FrameResult pk_VM__run_top_frame(pk_VM* self) {
                 py_Ref magic = py_tpfindmagic(SECOND()->type, __getitem__);
                 if(magic) {
                     if(magic->type == tp_nativefunc) {
-                        py_TValue* p0 = TOP();
-                        if(!py_callcfunc(p0, magic->_cfunc, 2, SECOND())) goto __ERROR;
+                        if(!magic->_cfunc(2, SECOND())) goto __ERROR;
+                        POP();
                         *TOP() = self->last_retval;
                     } else {
                         INSERT_THIRD();     // [?, a, b]
@@ -321,8 +321,8 @@ pk_FrameResult pk_VM__run_top_frame(pk_VM* self) {
                 if(magic) {
                     PUSH(THIRD());  // [val, a, b, val]
                     if(magic->type == tp_nativefunc) {
-                        py_TValue* p0 = FOURTH();
-                        if(!py_callcfunc(p0, magic->_cfunc, 3, THIRD())) goto __ERROR;
+                        if(!magic->_cfunc(3, THIRD())) goto __ERROR;
+                        STACK_SHRINK(4);
                     } else {
                         *FOURTH() = *magic;  // [__selitem__, a, b, val]
                         if(!py_vectorcall(2, 0)) goto __ERROR;
@@ -388,8 +388,8 @@ pk_FrameResult pk_VM__run_top_frame(pk_VM* self) {
                 py_Ref magic = py_tpfindmagic(SECOND()->type, __delitem__);
                 if(magic) {
                     if(magic->type == tp_nativefunc) {
-                        py_TValue* p0 = SECOND();
-                        if(!py_callcfunc(p0, magic->_cfunc, 2, SECOND())) goto __ERROR;
+                        if(!magic->_cfunc(2, SECOND())) goto __ERROR;
+                        STACK_SHRINK(2);
                     } else {
                         INSERT_THIRD();     // [?, a, b]
                         *THIRD() = *magic;  // [__delitem__, a, b]
@@ -528,8 +528,8 @@ pk_FrameResult pk_VM__run_top_frame(pk_VM* self) {
                 py_Ref magic = py_tpfindmagic(SECOND()->type, __contains__);
                 if(magic) {
                     if(magic->type == tp_nativefunc) {
-                        py_TValue* p0 = TOP();
-                        if(!py_callcfunc(p0, magic->_cfunc, 2, SECOND())) goto __ERROR;
+                        if(!magic->_cfunc(2, SECOND())) goto __ERROR;
+                        POP();
                         *TOP() = self->last_retval;
                     } else {
                         INSERT_THIRD();     // [?, b, a]

+ 6 - 4
src/interpreter/vm.c

@@ -347,8 +347,8 @@ static bool
                 c11_sv key_sv = py_name2sv(key);
                 py_newstrn(tmp, key_sv.data, key_sv.size);
                 py_dict__setitem(&buffer[decl->starred_kwarg], tmp, &p1[2 * j + 1]);
-                if(py_checkexc()) return false;
                 py_pop();
+                if(py_checkexc()) return false;
             }
         }
     }
@@ -401,7 +401,8 @@ pk_FrameResult pk_VM__vectorcall(pk_VM* self, uint16_t argc, uint16_t kwargc, bo
                     pk_VM__push_frame(self, Frame__new(co, &fn->module, p0, p0, argv, co));
                     return opcall ? RES_CALL : pk_VM__run_top_frame(self);
                 } else {
-                    bool ok = py_callcfunc(p0, fn->cfunc, co->nlocals, argv);
+                    bool ok = fn->cfunc(co->nlocals, argv);
+                    self->stack.sp = p0;
                     return ok ? RES_RETURN : RES_ERROR;
                 }
             }
@@ -440,8 +441,9 @@ pk_FrameResult pk_VM__vectorcall(pk_VM* self, uint16_t argc, uint16_t kwargc, bo
     }
 
     if(p0->type == tp_nativefunc) {
-        if(!py_callcfunc(p0, p0->_cfunc, p1 - argv, argv)) return RES_ERROR;
-        return RES_RETURN;
+        bool ok = p0->_cfunc(p1 - argv, argv);
+        self->stack.sp = p0;
+        return ok ? RES_RETURN : RES_ERROR;
     }
 
     if(p0->type == tp_type) {

+ 1 - 8
src/public/internal.c

@@ -203,8 +203,7 @@ bool py_exec(const char* source, const char* filename, enum py_CompileMode mode,
 
 bool py_call(py_Ref f, int argc, py_Ref argv) {
     if(f->type == tp_nativefunc) {
-        py_TValue* p0 = pk_current_vm->stack.sp;
-        return py_callcfunc(p0, f->_cfunc, argc, argv);
+        return f->_cfunc(argc, argv);
     } else {
         py_push(f);
         py_pushnil();
@@ -316,12 +315,6 @@ bool pk_callmagic(py_Name name, int argc, py_Ref argv) {
     return py_call(tmp, argc, argv);
 }
 
-bool py_callcfunc(py_StackRef p0, py_CFunction cfunc, int argc, py_Ref argv) {
-    bool ok = cfunc(argc, argv);
-    pk_current_vm->stack.sp = p0;
-    return ok;
-}
-
 bool StopIteration() {
     pk_VM* vm = pk_current_vm;
     assert(!vm->is_stopiteration);  // flag is already set

+ 22 - 11
src/public/modules.c

@@ -133,13 +133,13 @@ static bool _py_builtins__sorted(int argc, py_Ref argv) {
     PY_CHECK_ARGC(3);
     // convert _0 to list object
     if(!py_tpcall(tp_list, 1, py_arg(0))) return false;
-    py_push(py_retval());                       // duptop
-    py_push(py_retval());                       // [| <list>]
-    bool ok = py_pushmethod(py_name("sort"));   // [| list.sort, <list>]
+    py_push(py_retval());                      // duptop
+    py_push(py_retval());                      // [| <list>]
+    bool ok = py_pushmethod(py_name("sort"));  // [| list.sort, <list>]
     if(!ok) return false;
-    py_push(py_arg(1));                         // [| list.sort, <list>, key]
-    py_push(py_arg(2));                         // [| list.sort, <list>, key, reverse]
-    ok = py_vectorcall(2, 0);                   // [| ]
+    py_push(py_arg(1));        // [| list.sort, <list>, key]
+    py_push(py_arg(2));        // [| list.sort, <list>, key, reverse]
+    ok = py_vectorcall(2, 0);  // [| ]
     if(!ok) return false;
     py_assign(py_retval(), py_peek(-1));
     py_pop();
@@ -165,14 +165,25 @@ static bool _py_builtins__sum(int argc, py_Ref argv) {
     py_TValue* p = pk_arrayview(argv, &length);
     if(!p) return TypeError("sum() expects a list or tuple");
 
-    py_Ref tmp = py_pushtmp();
-    py_newint(tmp, 0);
+    py_i64 total_i64 = 0;
+    py_f64 total_f64 = 0.0;
+    bool is_float = false;
     for(int i = 0; i < length; i++) {
-        if(!py_binaryadd(tmp, &p[i])) return false;
-        *tmp = *py_retval();
+        switch(p[i].type) {
+            case tp_int: total_i64 += p[i]._i64; break;
+            case tp_float:
+                is_float = true;
+                total_f64 += p[i]._f64;
+                break;
+            default: return TypeError("sum() expects a list of numbers");
+        }
     }
 
-    *py_retval() = *tmp;
+    if(is_float) {
+        py_newfloat(py_retval(), total_f64 + total_i64);
+    } else {
+        py_newint(py_retval(), total_i64);
+    }
     return true;
 }
 

+ 6 - 5
src/public/py_list.c

@@ -120,14 +120,15 @@ static bool _py_list__new__(int argc, py_Ref argv) {
         py_newlist(list);
         while(true) {
             int res = py_next(iter);
-            if(res == -1) return false;
-            if(res) {
-                py_list__append(list, py_retval());
-            } else {
-                break;
+            if(res == -1){
+                py_shrink(2);
+                return false;
             }
+            if(!res) break;
+            py_list__append(list, py_retval());
         }
         *py_retval() = *list;
+        py_shrink(2);
         return true;
     }
     return TypeError("list() takes at most 1 argument");

+ 2 - 0
src/public/py_tuple.c

@@ -65,6 +65,7 @@ static bool _py_tuple__new__(int argc, py_Ref argv) {
         for(int i = 0; i < py_tuple__len(py_retval()); i++) {
             py_tuple__setitem(py_retval(), i, py_list__getitem(tmp, i));
         }
+        py_pop();
         return true;
     }
     return TypeError("tuple() takes at most 1 argument");
@@ -91,6 +92,7 @@ static bool _py_tuple__getitem__(int argc, py_Ref argv) {
         for(int i = 0; i < py_tuple__len(py_retval()); i++) {
             py_tuple__setitem(py_retval(), i, py_list__getitem(tmp, i));
         }
+        py_pop();
         return true;
     } else {
         return TypeError("tuple indices must be integers");