22
33#include "third-party/quickjs.h"
44
5- static PyObject * JSException = NULL ;
6- static PyObject * quickjs_to_python (JSContext * context , JSValue value );
7-
8- //
9- // Object type
10- //
5+ typedef struct {
6+ PyObject_HEAD JSRuntime * runtime ;
7+ JSContext * context ;
8+ } ContextData ;
119
1210typedef struct {
1311 PyObject_HEAD ;
14- JSContext * context ;
12+ ContextData * context ;
1513 JSValue object ;
1614} ObjectData ;
1715
16+ static PyObject * JSException = NULL ;
17+ static PyObject * quickjs_to_python (ContextData * context_obj , JSValue value );
18+
19+ //
20+ // Object type
21+ //
1822static PyObject * object_new (PyTypeObject * type , PyObject * args , PyObject * kwds ) {
1923 ObjectData * self ;
2024 self = (ObjectData * )type -> tp_alloc (type , 0 );
@@ -26,27 +30,30 @@ static PyObject *object_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2630
2731static void object_dealloc (ObjectData * self ) {
2832 if (self -> context ) {
29- JS_FreeValue (self -> context , self -> object );
33+ JS_FreeValue (self -> context -> context , self -> object );
34+ Py_DECREF (self -> context );
3035 }
3136 Py_TYPE (self )-> tp_free ((PyObject * )self );
3237}
3338
3439static PyObject * object_call (ObjectData * self , PyObject * args , PyObject * kwds );
3540
3641static PyObject * object_json (ObjectData * self ) {
37- JSValue global = JS_GetGlobalObject (self -> context );
38- JSValue JSON = JS_GetPropertyStr (self -> context , global , "JSON" );
39- JSValue stringify = JS_GetPropertyStr (self -> context , JSON , "stringify" );
42+ JSContext * context = self -> context -> context ;
43+ JSValue global = JS_GetGlobalObject (context );
44+ JSValue JSON = JS_GetPropertyStr (context , global , "JSON" );
45+ JSValue stringify = JS_GetPropertyStr (context , JSON , "stringify" );
4046 JSValueConst args [1 ] = {self -> object };
41- JSValue json_string = JS_Call (self -> context , stringify , JSON , 1 , args );
42- JS_FreeValue (self -> context , global );
43- JS_FreeValue (self -> context , JSON );
44- JS_FreeValue (self -> context , stringify );
47+ JSValue json_string = JS_Call (context , stringify , JSON , 1 , args );
48+ JS_FreeValue (context , global );
49+ JS_FreeValue (context , JSON );
50+ JS_FreeValue (context , stringify );
4551 return quickjs_to_python (self -> context , json_string );
4652}
4753
4854static PyMethodDef object_methods [] = {
49- {"json" , object_json , METH_NOARGS , "Converts to a JSON string." }, {NULL } /* Sentinel */
55+ {"json" , (PyCFunction )object_json , METH_NOARGS , "Converts to a JSON string." },
56+ {NULL } /* Sentinel */
5057};
5158
5259static PyTypeObject Object = {PyVarObject_HEAD_INIT (NULL , 0 ).tp_name = "_quickjs.Object" ,
@@ -68,7 +75,7 @@ static PyObject *object_call(ObjectData *self, PyObject *args, PyObject *kwds) {
6875 PyObject * item = PyTuple_GetItem (args , i );
6976 if (PyLong_Check (item )) {
7077 } else if (PyUnicode_Check (item )) {
71- } else if (PyObject_IsInstance (item , (PyObject * )& Object )) {
78+ } else if (PyObject_IsInstance (item , (PyObject * )& Object )) {
7279 } else {
7380 PyErr_Format (PyExc_ValueError , "Unsupported type when calling quickjs object" );
7481 return NULL ;
@@ -80,20 +87,21 @@ static PyObject *object_call(ObjectData *self, PyObject *args, PyObject *kwds) {
8087 if (PyLong_Check (item )) {
8188 jsargs [i ] = JS_MKVAL (JS_TAG_INT , PyLong_AsLong (item ));
8289 } else if (PyUnicode_Check (item )) {
83- jsargs [i ] = JS_NewString (self -> context , PyUnicode_AsUTF8 (item ));
84- } else if (PyObject_IsInstance (item , (PyObject * )& Object )) {
85- jsargs [i ] = JS_DupValue (self -> context , ((ObjectData * )item )-> object );
90+ jsargs [i ] = JS_NewString (self -> context -> context , PyUnicode_AsUTF8 (item ));
91+ } else if (PyObject_IsInstance (item , (PyObject * )& Object )) {
92+ jsargs [i ] = JS_DupValue (self -> context -> context , ((ObjectData * )item )-> object );
8693 }
8794 }
88- JSValue value = JS_Call (self -> context , self -> object , JS_NULL , nargs , jsargs );
95+ JSValue value = JS_Call (self -> context -> context , self -> object , JS_NULL , nargs , jsargs );
8996 for (int i = 0 ; i < nargs ; ++ i ) {
90- JS_FreeValue (self -> context , jsargs [i ]);
97+ JS_FreeValue (self -> context -> context , jsargs [i ]);
9198 }
9299 free (jsargs );
93100 return quickjs_to_python (self -> context , value );
94101}
95102
96- static PyObject * quickjs_to_python (JSContext * context , JSValue value ) {
103+ static PyObject * quickjs_to_python (ContextData * context_obj , JSValue value ) {
104+ JSContext * context = context_obj -> context ;
97105 int tag = JS_VALUE_GET_TAG (value );
98106 PyObject * return_value = NULL ;
99107
@@ -122,7 +130,8 @@ static PyObject *quickjs_to_python(JSContext *context, JSValue value) {
122130 } else if (tag == JS_TAG_OBJECT ) {
123131 return_value = PyObject_CallObject ((PyObject * )& Object , NULL );
124132 ObjectData * object = (ObjectData * )return_value ;
125- object -> context = context ;
133+ Py_INCREF (context_obj );
134+ object -> context = context_obj ;
126135 object -> object = JS_DupValue (context , value );
127136 } else {
128137 PyErr_Format (PyExc_ValueError , "Unknown quickjs tag: %d" , tag );
@@ -144,11 +153,6 @@ struct module_state {};
144153//
145154// Context type
146155//
147- typedef struct {
148- PyObject_HEAD JSRuntime * runtime ;
149- JSContext * context ;
150- } ContextData ;
151-
152156static PyObject * context_new (PyTypeObject * type , PyObject * args , PyObject * kwds ) {
153157 ContextData * self ;
154158 self = (ContextData * )type -> tp_alloc (type , 0 );
@@ -171,7 +175,7 @@ static PyObject *context_eval(ContextData *self, PyObject *args) {
171175 return NULL ;
172176 }
173177 JSValue value = JS_Eval (self -> context , code , strlen (code ), "<input>" , JS_EVAL_TYPE_GLOBAL );
174- return quickjs_to_python (self -> context , value );
178+ return quickjs_to_python (self , value );
175179}
176180
177181static PyObject * context_get (ContextData * self , PyObject * args ) {
@@ -182,7 +186,7 @@ static PyObject *context_get(ContextData *self, PyObject *args) {
182186 JSValue global = JS_GetGlobalObject (self -> context );
183187 JSValue value = JS_GetPropertyStr (self -> context , global , name );
184188 JS_FreeValue (self -> context , global );
185- return quickjs_to_python (self -> context , value );
189+ return quickjs_to_python (self , value );
186190}
187191
188192static PyMethodDef context_methods [] = {
0 commit comments