167 lines
		
	
	
		
			7.7 KiB
		
	
	
	
		
			Python
		
	
	
			
		
		
	
	
			167 lines
		
	
	
		
			7.7 KiB
		
	
	
	
		
			Python
		
	
	
| import textwrap
 | |
| 
 | |
| 
 | |
| class WrapperTemplate:
 | |
|     """Class to encapsulate string templates for use in wrapper generation"""
 | |
|     boost_headers = textwrap.dedent("""
 | |
|             #include <boost/archive/text_iarchive.hpp>
 | |
|             #include <boost/archive/text_oarchive.hpp>
 | |
|             #include <boost/serialization/export.hpp>
 | |
|         """)
 | |
| 
 | |
|     typdef_collectors = textwrap.dedent('''\
 | |
|                 typedef std::set<boost::shared_ptr<{class_name_sep}>*> Collector_{class_name};
 | |
|                 static Collector_{class_name} collector_{class_name};
 | |
|             ''')
 | |
| 
 | |
|     delete_obj = textwrap.indent(textwrap.dedent('''\
 | |
|                 {{ for(Collector_{class_name}::iterator iter = collector_{class_name}.begin();
 | |
|                     iter != collector_{class_name}.end(); ) {{
 | |
|                   delete *iter;
 | |
|                   collector_{class_name}.erase(iter++);
 | |
|                   anyDeleted = true;
 | |
|                 }} }}
 | |
|             '''),
 | |
|                                  prefix='  ')
 | |
| 
 | |
|     delete_all_objects = textwrap.dedent('''
 | |
|             void _deleteAllObjects()
 | |
|             {{
 | |
|               mstream mout;
 | |
|               std::streambuf *outbuf = std::cout.rdbuf(&mout);\n
 | |
|               bool anyDeleted = false;
 | |
|             {delete_objs}
 | |
|               if(anyDeleted)
 | |
|                 cout <<
 | |
|                   "WARNING:  Wrap modules with variables in the workspace have been reloaded due to\\n"
 | |
|                   "calling destructors, call \'clear all\' again if you plan to now recompile a wrap\\n"
 | |
|                   "module, so that your recompiled module is used instead of the old one." << endl;
 | |
|               std::cout.rdbuf(outbuf);
 | |
|             }}
 | |
|         ''')
 | |
| 
 | |
|     rtti_register = textwrap.dedent('''\
 | |
|             void _{module_name}_RTTIRegister() {{
 | |
|               const mxArray *alreadyCreated = mexGetVariablePtr("global", "gtsam_{module_name}_rttiRegistry_created");
 | |
|               if(!alreadyCreated) {{
 | |
|                 std::map<std::string, std::string> types;
 | |
| 
 | |
|             {rtti_classes}
 | |
| 
 | |
|                 mxArray *registry = mexGetVariable("global", "gtsamwrap_rttiRegistry");
 | |
|                 if(!registry)
 | |
|                   registry = mxCreateStructMatrix(1, 1, 0, NULL);
 | |
|                 typedef std::pair<std::string, std::string> StringPair;
 | |
|                 for(const StringPair& rtti_matlab: types) {{
 | |
|                   int fieldId = mxAddField(registry, rtti_matlab.first.c_str());
 | |
|                   if(fieldId < 0) {{
 | |
|                     mexErrMsgTxt("gtsam wrap:  Error indexing RTTI types, inheritance will not work correctly");
 | |
|                   }}
 | |
|                   mxArray *matlabName = mxCreateString(rtti_matlab.second.c_str());
 | |
|                   mxSetFieldByNumber(registry, 0, fieldId, matlabName);
 | |
|                 }}
 | |
|                 if(mexPutVariable("global", "gtsamwrap_rttiRegistry", registry) != 0) {{
 | |
|                   mexErrMsgTxt("gtsam wrap:  Error indexing RTTI types, inheritance will not work correctly");
 | |
|                 }}
 | |
|                 mxDestroyArray(registry);
 | |
| 
 | |
|                 mxArray *newAlreadyCreated = mxCreateNumericMatrix(0, 0, mxINT8_CLASS, mxREAL);
 | |
|                 if(mexPutVariable("global", "gtsam_geometry_rttiRegistry_created", newAlreadyCreated) != 0) {{
 | |
|                   mexErrMsgTxt("gtsam wrap:  Error indexing RTTI types, inheritance will not work correctly");
 | |
|                 }}
 | |
|                 mxDestroyArray(newAlreadyCreated);
 | |
|               }}
 | |
|             }}
 | |
|         ''')
 | |
| 
 | |
|     collector_function_upcast_from_void = textwrap.dedent('''\
 | |
|             void {class_name}_upcastFromVoid_{id}(int nargout, mxArray *out[], int nargin, const mxArray *in[]) {{
 | |
|               mexAtExit(&_deleteAllObjects);
 | |
|               typedef boost::shared_ptr<{cpp_name}> Shared;
 | |
|               boost::shared_ptr<void> *asVoid = *reinterpret_cast<boost::shared_ptr<void>**> (mxGetData(in[0]));
 | |
|               out[0] = mxCreateNumericMatrix(1, 1, mxUINT32OR64_CLASS, mxREAL);
 | |
|               Shared *self = new Shared(boost::static_pointer_cast<{cpp_name}>(*asVoid));
 | |
|               *reinterpret_cast<Shared**>(mxGetData(out[0])) = self;
 | |
|             }}\n
 | |
|         ''')
 | |
| 
 | |
|     class_serialize_method = textwrap.dedent('''\
 | |
|             function varargout = string_serialize(this, varargin)
 | |
|               % STRING_SERIALIZE usage: string_serialize() : returns string
 | |
|               % Doxygen can be found at https://gtsam.org/doxygen/
 | |
|               if length(varargin) == 0
 | |
|                 varargout{{1}} = {wrapper}({wrapper_id}, this, varargin{{:}});
 | |
|               else
 | |
|                 error('Arguments do not match any overload of function {class_name}.string_serialize');
 | |
|               end
 | |
|             end\n
 | |
|             function sobj = saveobj(obj)
 | |
|               % SAVEOBJ Saves the object to a matlab-readable format
 | |
|               sobj = obj.string_serialize();
 | |
|             end
 | |
|         ''')
 | |
| 
 | |
|     collector_function_serialize = textwrap.indent(textwrap.dedent("""\
 | |
|             typedef boost::shared_ptr<{full_name}> Shared;
 | |
|             checkArguments("string_serialize",nargout,nargin-1,0);
 | |
|             Shared obj = unwrap_shared_ptr<{full_name}>(in[0], "ptr_{namespace}{class_name}");
 | |
|             ostringstream out_archive_stream;
 | |
|             boost::archive::text_oarchive out_archive(out_archive_stream);
 | |
|             out_archive << *obj;
 | |
|             out[0] = wrap< string >(out_archive_stream.str());
 | |
|         """),
 | |
|                                                    prefix='  ')
 | |
| 
 | |
|     collector_function_deserialize = textwrap.indent(textwrap.dedent("""\
 | |
|             typedef boost::shared_ptr<{full_name}> Shared;
 | |
|             checkArguments("{namespace}{class_name}.string_deserialize",nargout,nargin,1);
 | |
|             string serialized = unwrap< string >(in[0]);
 | |
|             istringstream in_archive_stream(serialized);
 | |
|             boost::archive::text_iarchive in_archive(in_archive_stream);
 | |
|             Shared output(new {full_name}());
 | |
|             in_archive >> *output;
 | |
|             out[0] = wrap_shared_ptr(output,"{namespace}.{class_name}", false);
 | |
|         """),
 | |
|                                                      prefix='  ')
 | |
| 
 | |
|     mex_function = textwrap.dedent('''
 | |
|             void mexFunction(int nargout, mxArray *out[], int nargin, const mxArray *in[])
 | |
|             {{
 | |
|               mstream mout;
 | |
|               std::streambuf *outbuf = std::cout.rdbuf(&mout);\n
 | |
|               _{module_name}_RTTIRegister();\n
 | |
|               int id = unwrap<int>(in[0]);\n
 | |
|               try {{
 | |
|                 switch(id) {{
 | |
|             {cases}    }}
 | |
|               }} catch(const std::exception& e) {{
 | |
|                 mexErrMsgTxt(("Exception from gtsam:\\n" + std::string(e.what()) + "\\n").c_str());
 | |
|               }}\n
 | |
|               std::cout.rdbuf(outbuf);
 | |
|             }}
 | |
|         ''')
 | |
| 
 | |
|     collector_function_shared_return = textwrap.indent(textwrap.dedent('''\
 | |
|             {{
 | |
|             boost::shared_ptr<{name}> shared({shared_obj});
 | |
|             out[{id}] = wrap_shared_ptr(shared,"{name}");
 | |
|             }}{new_line}'''),
 | |
|                                                        prefix='  ')
 | |
| 
 | |
|     matlab_deserialize = textwrap.indent(textwrap.dedent("""\
 | |
|                 function varargout = string_deserialize(varargin)
 | |
|                   % STRING_DESERIALIZE usage: string_deserialize() : returns {class_name}
 | |
|                   % Doxygen can be found at https://gtsam.org/doxygen/
 | |
|                   if length(varargin) == 1
 | |
|                     varargout{{1}} = {wrapper}({id}, varargin{{:}});
 | |
|                   else
 | |
|                     error('Arguments do not match any overload of function {class_name}.string_deserialize');
 | |
|                   end
 | |
|                 end\n
 | |
|                 function obj = loadobj(sobj)
 | |
|                   % LOADOBJ Saves the object to a matlab-readable format
 | |
|                   obj = {class_name}.string_deserialize(sobj);
 | |
|                 end
 | |
|             """),
 | |
|                                          prefix='  ')
 |