[pygccxml-commit] SF.net SVN: pygccxml:[1786] pyplusplus_dev
Brought to you by:
mbaas,
roman_yakovenko
From: <rom...@us...> - 2009-12-27 20:43:42
|
Revision: 1786 http://pygccxml.svn.sourceforge.net/pygccxml/?rev=1786&view=rev Author: roman_yakovenko Date: 2009-12-27 20:43:34 +0000 (Sun, 27 Dec 2009) Log Message: ----------- add ability to treat char* as a pointer to a binary data Modified Paths: -------------- pyplusplus_dev/pyplusplus/code_creators/calldef_ctypes.py pyplusplus_dev/pyplusplus/code_creators/ctypes_formatter.py pyplusplus_dev/pyplusplus/code_creators/global_variable.py pyplusplus_dev/pyplusplus/code_creators/member_variable.py pyplusplus_dev/pyplusplus/code_creators/module.py pyplusplus_dev/pyplusplus/code_creators/typedef_as_pyvar.py pyplusplus_dev/unittests/ctypes_tester.py pyplusplus_dev/unittests/sconstruct Added Paths: ----------- pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/ pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.cpp pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.h pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/sconscript Removed Paths: ------------- pyplusplus_dev/pyplusplus/code_creators/ctypes_module.py Modified: pyplusplus_dev/pyplusplus/code_creators/calldef_ctypes.py =================================================================== --- pyplusplus_dev/pyplusplus/code_creators/calldef_ctypes.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/pyplusplus/code_creators/calldef_ctypes.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -66,14 +66,15 @@ def restype_code(self): if not declarations.is_void( self.ftype.return_type ): - return ctypes_formatter.as_ctype( self.ftype.return_type ) + return ctypes_formatter.as_ctype( self.ftype.return_type, self.top_parent.treat_char_ptr_as_binary_data ) else: return '' def argtypes_code(self, group_in_list=True): if not self.ftype.arguments_types: return '' - args = map( ctypes_formatter.as_ctype, self.ftype.arguments_types ) + args = map( lambda type_: ctypes_formatter.as_ctype( type_, self.top_parent.treat_char_ptr_as_binary_data ) + , self.ftype.arguments_types ) return self.join_arguments( args, group_in_list ) def _get_system_files_impl( self ): Modified: pyplusplus_dev/pyplusplus/code_creators/ctypes_formatter.py =================================================================== --- pyplusplus_dev/pyplusplus/code_creators/ctypes_formatter.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/pyplusplus/code_creators/ctypes_formatter.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -16,11 +16,15 @@ All functions within this class should be redefined in derived classes. """ - def __init__(self, type_, decl_formatter): + def __init__(self, type_, treat_char_ptr_as_binary_data, decl_formatter=algorithm.complete_py_name): declarations.type_visitor_t.__init__(self) self.user_type = type_ self.decl_formatter = decl_formatter + self.treat_char_ptr_as_binary_data = treat_char_ptr_as_binary_data + def create_converter( self, type_): + return type_converter_t( type_, self.treat_char_ptr_as_binary_data, self.decl_formatter ) + def visit_void( self ): return "None" @@ -75,23 +79,23 @@ #skip complex and jxxx types def visit_volatile( self ): - base_visitor = type_converter_t( self.user_type.base, self.decl_formatter ) + base_visitor = self.create_converter( self.user_type.base ) return declarations.apply_visitor( base_visitor, base_visitor.user_type ) def visit_const( self ): - base_visitor = type_converter_t( self.user_type.base, self.decl_formatter ) + base_visitor = self.create_converter( self.user_type.base ) return declarations.apply_visitor( base_visitor, base_visitor.user_type ) def visit_pointer( self ): no_ptr = declarations.remove_const( declarations.remove_pointer( self.user_type ) ) - if declarations.is_same( declarations.char_t(), no_ptr ): + if declarations.is_same( declarations.char_t(), no_ptr ) and self.treat_char_ptr_as_binary_data == False: return "ctypes.c_char_p" - elif declarations.is_same( declarations.wchar_t(), no_ptr ): + elif declarations.is_same( declarations.wchar_t(), no_ptr ) and self.treat_char_ptr_as_binary_data == False: return "ctypes.c_wchar_p" elif declarations.is_same( declarations.void_t(), no_ptr ): return "ctypes.c_void_p" else: - base_visitor = type_converter_t( self.user_type.base, self.decl_formatter ) + base_visitor = self.create_converter( self.user_type.base ) internal_type_str = declarations.apply_visitor( base_visitor, base_visitor.user_type ) if declarations.is_calldef_pointer( self.user_type ): return internal_type_str @@ -107,13 +111,12 @@ elif declarations.is_same( declarations.void_t(), no_ref ): return "ctypes.c_void_p" else: - base_visitor = type_converter_t( self.user_type.base, self.decl_formatter ) + base_visitor = self.create_converter( self.user_type.base ) internal_type_str = declarations.apply_visitor( base_visitor, base_visitor.user_type ) return "ctypes.POINTER( %s )" % internal_type_str def visit_array( self ): - item_visitor = type_converter_t( declarations.array_item_type(self.user_type) - , self.decl_formatter ) + item_visitor = self.create_converter( declarations.array_item_type(self.user_type) ) item_type = declarations.apply_visitor( item_visitor, item_visitor.user_type ) size = declarations.array_size( self.user_type ) if size == declarations.array_t.SIZE_UNKNOWN: @@ -121,11 +124,11 @@ return "( %s * %d )" % ( item_type, size ) def visit_free_function_type( self ): - return_visitor = type_converter_t( self.user_type.return_type, self.decl_formatter ) - return_type = declarations.apply_visitor(return_visitor, self.user_type.return_type) + return_visitor = self.create_converter( self.user_type.return_type ) + return_type = declarations.apply_visitor( return_visitor, self.user_type.return_type ) argtypes = [] for arg in self.user_type.arguments_types: - arg_visitor = type_converter_t( arg, self.decl_formatter ) + arg_visitor = self.create_converter( arg ) argtypes.append( declarations.apply_visitor(arg_visitor, arg) ) return declarations.call_invocation.join( "ctypes.CFUNCTYPE", [return_type] + argtypes ) @@ -138,19 +141,19 @@ def visit_declarated( self ): #TODO: the follwoing code removes typedefs if isinstance( self.user_type.declaration, declarations.typedef_t ): - base_visitor = type_converter_t( self.user_type.declaration.type, self.decl_formatter ) + base_visitor = self.create_converter( self.user_type.declaration.type ) return declarations.apply_visitor( base_visitor, base_visitor.user_type ) else: return self.decl_formatter( self.user_type.declaration ) def visit_restrict( self ): - base_visitor = type_converter_t( self.user_type.base, self.decl_formatter ) + base_visitor = self.create_converter( self.user_type.base ) return declarations.apply_visitor( base_visitor, base_visitor.user_type ) def visit_ellipsis( self ): return '' -def as_ctype( type_, decl_formatter=algorithm.complete_py_name ): - v = type_converter_t( type_, decl_formatter ) +def as_ctype( type_, treat_char_ptr_as_binary_data=False): + v = type_converter_t( type_, treat_char_ptr_as_binary_data ) return declarations.apply_visitor( v, type_ ) Deleted: pyplusplus_dev/pyplusplus/code_creators/ctypes_module.py =================================================================== --- pyplusplus_dev/pyplusplus/code_creators/ctypes_module.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/pyplusplus/code_creators/ctypes_module.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -1,30 +0,0 @@ -# Copyright 2004-2008 Roman Yakovenko. -# Distributed under the Boost Software License, Version 1.0. (See -# accompanying file LICENSE_1_0.txt or copy at -# http://www.boost.org/LICENSE_1_0.txt) - -import os -import module -import library_reference -from pygccxml import utils - -class ctypes_module_t(module.module_t): - """This class represents the source code for the entire extension module. - - The root of the code creator tree is always a module_t object. - """ - def __init__(self, global_ns): - """Constructor. - """ - module.module_t.__init__(self, global_ns, ctypes_module_t.CODE_GENERATOR_TYPES.CTYPES) - - def _create_impl(self): - return self.create_internal_code( self.creators, indent_code=False ) - - @utils.cached - def library_var_name(self): - for creator in self.creators: - if isinstance( creator, library_reference.library_reference_t ): - return creator.library_var_name - else: - raise RuntimeError( "Internal Error: library_reference_t creator was not created" ) Modified: pyplusplus_dev/pyplusplus/code_creators/global_variable.py =================================================================== --- pyplusplus_dev/pyplusplus/code_creators/global_variable.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/pyplusplus/code_creators/global_variable.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -192,7 +192,7 @@ def _create_impl( self ): return '%(alias)s = %(type)s.in_dll( %(library_var_name)s, %(library_var_name)s.undecorated_names["%(undecorated_decl_name)s"] )' \ % dict( alias=self.alias - , type=ctypes_formatter.as_ctype( self.declaration.type ) + , type=ctypes_formatter.as_ctype( self.declaration.type, self.top_parent.treat_char_ptr_as_binary_data ) , library_var_name=self.top_parent.library_var_name , undecorated_decl_name=self.undecorated_decl_name ) Modified: pyplusplus_dev/pyplusplus/code_creators/member_variable.py =================================================================== --- pyplusplus_dev/pyplusplus/code_creators/member_variable.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/pyplusplus/code_creators/member_variable.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -736,7 +736,7 @@ vars.sort( key=lambda d: d.location.line ) for v in vars: tmp = None - type_as_str = ctypes_formatter.as_ctype( v.type ) + type_as_str = ctypes_formatter.as_ctype( v.type, self.top_parent.treat_char_ptr_as_binary_data ) if v.bits != None: tmp = '("%(name)s", %(type)s, %(bits)d),' \ % dict( name=v.alias, type=type_as_str, bits=v.bits ) Modified: pyplusplus_dev/pyplusplus/code_creators/module.py =================================================================== --- pyplusplus_dev/pyplusplus/code_creators/module.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/pyplusplus/code_creators/module.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -237,7 +237,8 @@ """Constructor. """ module_t.__init__(self, global_ns, ctypes_module_t.CODE_GENERATOR_TYPES.CTYPES) - + self.treat_char_ptr_as_binary_data = False + def _create_impl(self): return self.create_internal_code( self.creators, indent_code=False ) Modified: pyplusplus_dev/pyplusplus/code_creators/typedef_as_pyvar.py =================================================================== --- pyplusplus_dev/pyplusplus/code_creators/typedef_as_pyvar.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/pyplusplus/code_creators/typedef_as_pyvar.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -16,7 +16,7 @@ def _create_impl(self): return "%(complete_py_name)s = %(type)s" \ % dict( complete_py_name=self.complete_py_name - , type=ctypes_formatter.as_ctype( self.declaration.type ) ) + , type=ctypes_formatter.as_ctype( self.declaration.type, self.top_parent.treat_char_ptr_as_binary_data ) ) def _get_system_files_impl( self ): return [] Modified: pyplusplus_dev/unittests/ctypes_tester.py =================================================================== --- pyplusplus_dev/unittests/ctypes_tester.py 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/unittests/ctypes_tester.py 2009-12-27 20:43:34 UTC (rev 1786) @@ -49,6 +49,9 @@ def customize(self, mb ): pass + def customize_cc( self, mb ): + pass + def __build_scons_cmd( self ): cmd = autoconfig.scons.cmd_build + ' ' + self.base_name if autoconfig.cxx_parsers_cfg.gccxml.compiler == 'msvc71': @@ -66,8 +69,9 @@ autoconfig.scons_config.compile( self.__build_scons_cmd(), cwd=autoconfig.this_module_dir_path ) mb = ctypes_module_builder_t( [self.header], self.symbols_file, autoconfig.cxx_parsers_cfg.gccxml ) - self.customize( mb ) + self.customize( mb ) mb.build_code_creator( self.library_file ) + self.customize_cc( mb ) mb.write_module( os.path.join( self.project_dir, 'binaries', self.base_name + '.py' ) ) sys.path.insert( 0, os.path.join( self.project_dir, 'binaries' ) ) __import__( self.base_name ) @@ -212,6 +216,23 @@ #TODO: sort structs and classes by dependencies pass #just test that module could be loaded + +class char_ptr_as_binary_data_tester_t( ctypes_base_tester_t ): + def __init__( self, *args, **keywd ): + ctypes_base_tester_t.__init__( self, 'char_ptr_as_binary_data', *args, **keywd ) + + def customize_cc( self, mb ): + mb.code_creator.treat_char_ptr_as_binary_data = True + + def test(self): + data = self.module_ref.get_empty() + self.failUnless( data.contents.size == 0 ) + self.failUnless( not data.contents.bytes ) + + data = self.module_ref.get_hello_world() + self.failUnless( data.contents.size == len( "hello world" ) ) + self.failUnless( data.contents.bytes[0:data.contents.size + 1] == "hello\0world\0" ) + def create_suite(): #part of this functionality is going to be deprecated suite = unittest.TestSuite() @@ -223,6 +244,7 @@ suite.addTest( unittest.makeSuite(varargs_tester_t)) suite.addTest( unittest.makeSuite(circular_references_tester_t)) suite.addTest( unittest.makeSuite(function_ptr_as_variable_tester_t)) + suite.addTest( unittest.makeSuite(char_ptr_as_binary_data_tester_t)) return suite def run_suite(): Added: pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.cpp =================================================================== --- pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.cpp (rev 0) +++ pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.cpp 2009-12-27 20:43:34 UTC (rev 1786) @@ -0,0 +1,15 @@ +#include "char_ptr_as_binary_data.h" + +EXPORT_SYMBOL data_t* get_empty(){ + data_t* x = new data_t(); + x->size = 0; + x->bytes = 0; + return x; +} + +EXPORT_SYMBOL data_t* get_hello_world(){ + data_t* x = new data_t(); + x->size = 11; + x->bytes = "hello\0world"; + return x; +} Added: pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.h =================================================================== --- pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.h (rev 0) +++ pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/char_ptr_as_binary_data.h 2009-12-27 20:43:34 UTC (rev 1786) @@ -0,0 +1,11 @@ +#include "libconfig.h" + +struct EXPORT_SYMBOL data_t{ + unsigned int size; + char const * bytes; +}; + +EXPORT_SYMBOL data_t* get_empty(); +EXPORT_SYMBOL data_t* get_hello_world(); + + Added: pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/sconscript =================================================================== --- pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/sconscript (rev 0) +++ pyplusplus_dev/unittests/data/ctypes/char_ptr_as_binary_data/sconscript 2009-12-27 20:43:34 UTC (rev 1786) @@ -0,0 +1,7 @@ +Import('*') + +target_name = 'char_ptr_as_binary_data' +shlib = env.SharedLibrary( target=target_name + , source=[ target_name + '.cpp' ] + , CPPPATH=['#data'] ) +env.Alias( target_name, shlib ) Modified: pyplusplus_dev/unittests/sconstruct =================================================================== --- pyplusplus_dev/unittests/sconstruct 2009-12-26 20:13:12 UTC (rev 1785) +++ pyplusplus_dev/unittests/sconstruct 2009-12-27 20:43:34 UTC (rev 1786) @@ -33,7 +33,8 @@ , 'varargs' , 'templates' , 'circular_references' - , 'function_ptr_as_variable' ] + , 'function_ptr_as_variable' + , 'char_ptr_as_binary_data' ] for s in scripts: SConscript( 'data/ctypes/%s/sconscript' % s This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |