comparison oct-py-eval.cc @ 404:aef165ff92b0

Adopt pytave::python_object where objects are local or created and returned * __py_struct_from_dict__.cc, exceptions.cc, oct-py-eval.cc, oct-py-types.cc, pycall.cc: Use pytave::python_object in place of PyObject where objects are created locally and destroyed or returned to the caller.
author Mike Miller <mtmiller@octave.org>
date Fri, 28 Apr 2017 16:21:39 -0700
parents 3644df6564bc
children 3613ffbd52b2
comparison
equal deleted inserted replaced
403:3644df6564bc 404:aef165ff92b0
28 #include <boost/python.hpp> 28 #include <boost/python.hpp>
29 #include <octave/ov.h> 29 #include <octave/ov.h>
30 #include <octave/ovl.h> 30 #include <octave/ovl.h>
31 31
32 #include "oct-py-eval.h" 32 #include "oct-py-eval.h"
33 #include "oct-py-object.h"
33 #include "oct-py-util.h" 34 #include "oct-py-util.h"
34 #include "octave_to_python.h" 35 #include "octave_to_python.h"
35 36
36 namespace pytave 37 namespace pytave
37 { 38 {
38 39
39 PyObject * 40 PyObject *
40 py_call_function (const std::string& func, const octave_value_list& args) 41 py_call_function (const std::string& func, const octave_value_list& args)
41 { 42 {
42 PyObject *func_obj = py_find_function (func); 43 python_object func_obj = py_find_function (func);
43 PyObject *retval = py_call_function (func_obj, args); 44 python_object retval = py_call_function (func_obj, args);
44 Py_DECREF (func_obj); 45 return retval.release ();
45 return retval;
46 } 46 }
47 47
48 PyObject * 48 PyObject *
49 py_call_function (const std::string& func, PyObject *args, PyObject *kwargs) 49 py_call_function (const std::string& func, PyObject *args, PyObject *kwargs)
50 { 50 {
51 PyObject *func_obj = py_find_function (func); 51 python_object func_obj = py_find_function (func);
52 PyObject *retval = py_call_function (func_obj, args, kwargs); 52 python_object retval = py_call_function (func_obj, args, kwargs);
53 Py_DECREF (func_obj); 53 return retval.release ();
54 return retval;
55 } 54 }
56 55
57 PyObject * 56 PyObject *
58 py_call_function (PyObject *callable, const octave_value_list& args) 57 py_call_function (PyObject *callable, const octave_value_list& args)
59 { 58 {
60 PyObject *kwargs = nullptr; 59 python_object kwargs;
61 PyObject *args_list = PyList_New (0); 60 python_object args_list = PyList_New (0);
62 if (! args_list) 61 if (! args_list)
63 octave_throw_bad_alloc (); 62 octave_throw_bad_alloc ();
64 63
65 for (int i = 0; i < args.length (); ++i) 64 for (int i = 0; i < args.length (); ++i)
66 { 65 {
75 Py_INCREF (obj); 74 Py_INCREF (obj);
76 PyList_Append (args_list, obj); 75 PyList_Append (args_list, obj);
77 } 76 }
78 } 77 }
79 78
80 PyObject *args_tuple = PyList_AsTuple (args_list); 79 python_object args_tuple = PyList_AsTuple (args_list);
81 Py_DECREF (args_list);
82 80
83 PyObject *retval = py_call_function (callable, args_tuple, kwargs); 81 python_object retval = py_call_function (callable, args_tuple, kwargs);
84 Py_DECREF (args_tuple);
85 Py_XDECREF (kwargs);
86 82
87 return retval; 83 return retval.release ();
88 } 84 }
89 85
90 PyObject * 86 PyObject *
91 py_call_function (PyObject *callable, PyObject *args, PyObject *kwargs) 87 py_call_function (PyObject *callable, PyObject *args, PyObject *kwargs)
92 { 88 {
93 PyObject *retval = PyEval_CallObjectWithKeywords (callable, args, kwargs); 89 python_object retval = PyEval_CallObjectWithKeywords (callable, args, kwargs);
94 if (! retval) 90 if (! retval)
95 throw boost::python::error_already_set (); 91 throw boost::python::error_already_set ();
96 92
97 return retval; 93 return retval.release ();
98 } 94 }
99 95
100 PyObject * 96 PyObject *
101 py_run_string_safe (const std::string& expr, int start, PyObject *globals, 97 py_run_string_safe (const std::string& expr, int start, PyObject *globals,
102 PyObject *locals) 98 PyObject *locals)
103 { 99 {
104 bool alloc = false; 100 bool alloc = false;
105 101
106 if (! globals || (globals == Py_None)) 102 if (! globals || (globals == Py_None))
107 { 103 {
108 PyObject *main = py_import_module ("__main__"); 104 python_object main = py_import_module ("__main__");
109 globals = PyModule_GetDict (main); 105 globals = PyModule_GetDict (main);
110 Py_DECREF (main);
111 if (! globals) 106 if (! globals)
112 { 107 {
113 globals = PyDict_New (); 108 globals = PyDict_New ();
114 alloc = true; 109 alloc = true;
115 } 110 }
119 locals = globals; 114 locals = globals;
120 115
121 // Evaluate all expressions under "from __future__ import print_function" 116 // Evaluate all expressions under "from __future__ import print_function"
122 PyCompilerFlags flags { CO_FUTURE_PRINT_FUNCTION }; 117 PyCompilerFlags flags { CO_FUTURE_PRINT_FUNCTION };
123 118
124 PyObject *retval = PyRun_StringFlags (expr.c_str (), start, globals, locals, 119 python_object retval = PyRun_StringFlags (expr.c_str (), start, globals, locals,
125 &flags); 120 &flags);
126 121
127 if (alloc) 122 if (alloc)
128 Py_DECREF (globals); 123 Py_DECREF (globals);
129 124
130 if (! retval) 125 if (! retval)
131 throw boost::python::error_already_set (); 126 throw boost::python::error_already_set ();
132 127
133 return retval; 128 return retval.release ();
134 } 129 }
135 130
136 PyObject * 131 PyObject *
137 py_eval_string (const std::string& expr, PyObject *globals, PyObject *locals) 132 py_eval_string (const std::string& expr, PyObject *globals, PyObject *locals)
138 { 133 {