def generate(self, code_sink, wrapper_name=None, extra_wrapper_params=()): """ Generates the wrapper code code_sink -- a CodeSink instance that will receive the generated code method_name -- actual name the method will get extra_wrapper_params -- extra parameters the wrapper function should receive Returns the corresponding PyMethodDef entry string. """ if self.throw: # Bug #780945 self.return_value.REQUIRES_ASSIGNMENT_CONSTRUCTOR = False self.reset_code_generation_state() class_ = self.class_ #assert isinstance(class_, CppClass) tmp_sink = codesink.MemoryCodeSink() self.generate_body(tmp_sink, gen_call_params=[class_]) if wrapper_name is None: self.wrapper_actual_name = self.wrapper_base_name else: self.wrapper_actual_name = wrapper_name self.get_wrapper_signature(self.wrapper_actual_name, extra_wrapper_params) self.write_open_wrapper(code_sink)#, add_static=self.static_decl) tmp_sink.flush_to(code_sink) self.write_close_wrapper(code_sink)
def generate(self, code_sink, wrapper_name=None, extra_wrapper_params=()): """ Generates the wrapper code :param code_sink: a CodeSink instance that will receive the generated code :param wrapper_name: name of wrapper function """ if self.throw: # Bug #780945 self.return_value.REQUIRES_ASSIGNMENT_CONSTRUCTOR = False self.reset_code_generation_state() if wrapper_name is None: self.wrapper_actual_name = self.wrapper_base_name else: self.wrapper_actual_name = wrapper_name tmp_sink = codesink.MemoryCodeSink() self.generate_body(tmp_sink) flags = self.get_py_method_def_flags() self.wrapper_args = [] if 'METH_VARARGS' in flags: if self.self_parameter_pystruct is None: self_param = 'PyObject * PYBINDGEN_UNUSED(dummy)' else: self_param = '%s *self' % self.self_parameter_pystruct self.wrapper_args.append(self_param) self.wrapper_args.append("PyObject *args") if 'METH_KEYWORDS' in flags: self.wrapper_args.append("PyObject *kwargs") self.wrapper_args.extend(extra_wrapper_params) self.wrapper_return = "PyObject *" self.write_open_wrapper(code_sink) tmp_sink.flush_to(code_sink) self.write_close_wrapper(code_sink)
def generate(self, code_sink): """ :param code_sink: a CodeSink instance that will receive the generated code """ tmp_sink = codesink.MemoryCodeSink() self.generate_body(tmp_sink) code_sink.writeln("static PyObject* %s(%s *self, void * PYBINDGEN_UNUSED(closure))" % (self.c_function_name, self.class_.pystruct)) code_sink.writeln('{') code_sink.indent() tmp_sink.flush_to(code_sink) code_sink.unindent() code_sink.writeln('}')
def generate(self, code_sink): """ code_sink -- a CodeSink instance that will receive the generated code """ tmp_sink = codesink.MemoryCodeSink() self.generate_body(tmp_sink) code_sink.writeln("static PyObject* %s(%s *self)" % (self.c_function_name, self.container.iter_pystruct)) code_sink.writeln('{') code_sink.indent() tmp_sink.flush_to(code_sink) code_sink.unindent() code_sink.writeln('}')
def generate(self, code_sink, wrapper_name=None, extra_wrapper_params=()): """ Generates the wrapper code :param code_sink: a CodeSink instance that will receive the generated code :returns: the wrapper function name. """ if self.visibility == 'private': raise utils.SkipWrapper("Class %r has a private constructor ->" " cannot generate a constructor for it" % self._class.full_name) elif self.visibility == 'protected': if self._class.helper_class is None: raise utils.SkipWrapper("Class %r has a protected constructor and no helper class" " -> cannot generate a constructor for it" % self._class.full_name) #assert isinstance(class_, CppClass) tmp_sink = codesink.MemoryCodeSink() assert self._class is not None self.generate_body(tmp_sink, gen_call_params=[self._class]) assert ((self.parse_params.get_parameters() == ['""']) or self.parse_params.get_keywords() is not None), \ ("something went wrong with the type handlers;" " constructors need parameter names, " "yet no names were given for the class %s constructor" % self._class.name) if wrapper_name is None: self.wrapper_actual_name = self.wrapper_base_name else: self.wrapper_actual_name = wrapper_name self.wrapper_return = 'static int' self.wrapper_args = ["%s *self" % self._class.pystruct, "PyObject *args", "PyObject *kwargs"] self.wrapper_args.extend(extra_wrapper_params) self.write_open_wrapper(code_sink) tmp_sink.flush_to(code_sink) code_sink.writeln('return 0;') self.write_close_wrapper(code_sink)
cls_pp = mod.add_class('PythonScript', allow_subclassing=True, foreign_cpp_namespace='Python', custom_name='Plugin') """ PythonPlugin implements LoggingInterface for messaging to Tiled """ cls_logi = tiled.add_class('LoggingInterface', destructor_visibility='private') cls_logi.add_enum('OutputType', ('INFO', 'ERROR')) cls_logi.add_method('log', 'void', [('OutputType', 'type'), ('const QString', 'msg')], is_virtual=True) with open('pythonbind.cpp', 'w') as fh: import pybindgen.typehandlers.codesink as cs sink = cs.MemoryCodeSink() print >> fh, """ #ifdef __MINGW32__ #include <cmath> // included before Python.h to fix ::hypot not declared issue #endif """ mod.generate(fh) print >> fh, """ PyObject* _wrap_convert_c2py__Tiled__LoggingInterface(Tiled::LoggingInterface *cvalue) { PyObject *py_retval; PyTiledLoggingInterface *py_LoggingInterface;
def test(): code_out = codesink.FileCodeSink(sys.stdout) pybindgen.write_preamble(code_out) sys.stdout.write(""" #include <string> #include <stdint.h> """) ## Declare a dummy class sys.stdout.write(''' class Foo { std::string m_datum; public: Foo () : m_datum ("") {} Foo (std::string datum) : m_datum (datum) {} std::string get_datum () const { return m_datum; } Foo (Foo const & other) : m_datum (other.get_datum ()) {} }; ''') module = Module("foo") ## Register type handlers for the class Foo = module.add_class('Foo') Foo.add_constructor([Parameter.new("const Foo&", "foo")]) #Foo.full_name = Foo.name # normally adding the class to a module would take care of this Foo.generate_forward_declarations(code_out, module) wrapper_number = 0 ## test return type handlers of reverse wrappers for return_type, return_handler in list(typehandlers.base.return_type_matcher.items()): if type_blacklisted(return_type): continue if os.name == 'nt': if stdint_rx.search(return_type): continue # win32 does not support the u?int\d+_t types (defined in <stdint.h>) code_out.writeln("/* Test %s (%s) return type */" % (return_type, return_handler)) if issubclass(return_handler, (cppclass.CppClassPtrReturnValue, typehandlers.pyobjecttype.PyObjectReturnValue)): for caller_owns_return in True, False: retval = return_handler(return_type, caller_owns_return=caller_owns_return) wrapper = MyReverseWrapper(retval, []) wrapper_number += 1 try: wrapper.generate(code_out, '_test_wrapper_number_%i' % (wrapper_number,), ['static']) except NotImplementedError: sys.stderr.write("ReverseWrapper %s(void) (caller_owns_return=%r)" " could not be generated: not implemented\n" % (retval.ctype, caller_owns_return)) sys.stdout.write("\n") else: retval = return_handler(return_type) try: wrapper = MyReverseWrapper(retval, []) except NotSupportedError: continue except NotImplementedError: sys.stderr.write("ReverseWrapper %s(void) could not be generated: not implemented\n" % (retval.ctype)) continue wrapper_number += 1 memsink = codesink.MemoryCodeSink() try: wrapper.generate(memsink, '_test_wrapper_number_%i' % (wrapper_number,), ['static']) except NotImplementedError: sys.stderr.write("ReverseWrapper %s xxx (void) could not be generated: not implemented\n" % (retval.ctype,)) continue except NotSupportedError: continue else: memsink.flush_to(code_out) sys.stdout.write("\n") ## test parameter type handlers of reverse wrappers for param_type, param_handler in list(typehandlers.base.param_type_matcher.items()): if type_blacklisted(param_type): continue if os.name == 'nt': if stdint_rx.search(param_type): continue # win32 does not support the u?int\d+_t types (defined in <stdint.h>) for direction in param_handler.DIRECTIONS: if direction == (Parameter.DIRECTION_IN): param_name = 'param' elif direction == (Parameter.DIRECTION_IN|Parameter.DIRECTION_OUT): param_name = 'param_inout' elif direction == (Parameter.DIRECTION_OUT): param_name = 'param_out' def try_wrapper(param, wrapper_number): if 'const' in param.ctype and direction&Parameter.DIRECTION_OUT: return code_out.writeln("/* Test %s (%s) param type */" % (param_type, param_handler)) wrapper = MyReverseWrapper(ReturnValue.new('void'), [param]) try: wrapper.generate(code_out, '_test_wrapper_number_%i' % (wrapper_number,), ['static']) except NotImplementedError: sys.stderr.write("ReverseWrapper void(%s) could not be generated: not implemented" % (param.ctype)) sys.stdout.write("\n") if issubclass(param_handler, (cppclass.CppClassPtrParameter, typehandlers.pyobjecttype.PyObjectParam)): for transfer_ownership in True, False: try: param = param_handler(param_type, param_name, transfer_ownership=transfer_ownership) except TypeError: sys.stderr.write("ERROR -----> param_handler(param_type=%r, " "transfer_ownership=%r, is_const=%r)\n" % (param_type, transfer_ownership, is_const)) wrapper_number += 1 try_wrapper(param, wrapper_number) else: param = param_handler(param_type, param_name, direction) wrapper_number += 1 try_wrapper(param, wrapper_number) ## test generic forward wrappers, and module for return_type, return_handler in list(typehandlers.base.return_type_matcher.items()): if type_blacklisted(return_type): continue if os.name == 'nt': if stdint_rx.search(return_type): continue # win32 does not support the u?int\d+_t types (defined in <stdint.h>) wrapper_number += 1 function_name = 'foo_function_%i' % (wrapper_number,) ## declare a fake prototype sys.stdout.write("%s %s(void);\n\n" % (return_type, function_name)) if issubclass(return_handler, (cppclass.CppClassPtrReturnValue, typehandlers.pyobjecttype.PyObjectReturnValue)): retval = return_handler(return_type, caller_owns_return=True) else: retval = return_handler(return_type) module.add_function(function_name, retval, []) for param_type, param_handler in list(typehandlers.base.param_type_matcher.items()): if type_blacklisted(param_type): continue if os.name == 'nt': if stdint_rx.search(param_type): continue # win32 does not support the u?int\d+_t types (defined in <stdint.h>) for is_const in [True, False]: for direction in param_handler.DIRECTIONS: if direction == (Parameter.DIRECTION_IN): param_name = 'param' elif direction == (Parameter.DIRECTION_IN|Parameter.DIRECTION_OUT): param_name = 'param_inout' elif direction == (Parameter.DIRECTION_OUT): param_name = 'param_out' if is_const and direction & Parameter.DIRECTION_OUT: continue # const and output parameter makes no sense if is_const: if '&' in param_type: # const references not allowed continue param_type_with_const = "const %s" % (param_type,) else: param_type_with_const = param_type if issubclass(param_handler, (cppclass.CppClassPtrParameter, typehandlers.pyobjecttype.PyObjectParam)): for transfer_ownership in True, False: name = param_name + (transfer_ownership and '_transfer' or '_notransfer') try: param = param_handler(param_type, name, transfer_ownership=transfer_ownership) except TypeError: sys.stderr.write("ERROR -----> param_handler(param_type=%r, " "name=%r, transfer_ownership=%r, is_const=%r)\n" % (param_type, name, transfer_ownership, is_const)) wrapper_number += 1 function_name = 'foo_function_%i' % (wrapper_number,) ## declare a fake prototype sys.stdout.write("void %s(%s %s);\n\n" % (function_name, param_type_with_const, name)) module.add_function(function_name, ReturnValue.new('void'), [param]) else: param = param_handler(param_type, param_name, direction) wrapper_number += 1 function_name = 'foo_function_%i' % (wrapper_number,) ## declare a fake prototype sys.stdout.write("void %s(%s);\n\n" % (function_name, param_type_with_const)) module.add_function(function_name, ReturnValue.new('void'), [param]) module.generate(code_out)