InlineX::CPP2XS - Convert from Inline C++ code to XS.
#USAGE: #cpp2xs($module_name, $package_name [, $build_dir] [, $config_opts]) use InlineX::CPP2XS qw(cpp2xs); my $module_name = 'MY::XS_MOD'; my $package_name = 'MY::XS_MOD'; # $build_dir is an optional third arg. # If omitted it defaults to '.' (the cwd). my $build_dir = '/some/where/else'; # $config_opts is an optional fourth arg (hash reference) my $config_opts = {'WRITE_PM' => 1, #'WRITE_MAKEFILE_PL' => 1, # non portable files 'WRITE_MAKEFILE_PL' => 'p', # portable files 'VERSION' => 0.42, }; # Create /some/where/else/XS_MOD.xs from ./src/XS_MOD.cpp # Will also create the typemap file /some/where/else/CPP.map # if that file is going to be needed to build the module: cpp2xs($module_name, $package_name, $build_dir); # Alternatively create XS_MOD.xs (and CPP.map, if needed) in # the cwd: cpp2xs($module_name, $package_name); # Or Create /some/where/else/XS_MOD.xs from $code $code = 'void foo() {printf("Hello World\n");}' . "\n\n"; cpp2xs($module_name, $package_name, $build_dir, {CODE => $code}); # Or Create /some/where/else/XS_MOD.xs from the C code that's in # ./otherplace/otherfile.ext $loc = './otherplace/otherfile.ext'; cpp2xs($module_name, $package_name, $build_dir, {SRC_LOCATION => $loc}); The optional fourth arg (a reference to a hash) is to enable the passing of additional information and configuration options that Inline may need - and also to enable the creation of the Makefile.PL and .pm file(if desired). See the "Recognised Hash Keys" section below. # Create XS_MOD.xs in the cwd, and generate the Makefile.PL # and XS_MOD.pm : cpp2xs($module_name, $package_name, $config_opts); NOTE: If you wish to supply the $config_opts argument, but not the $build_dir argument then you simply omit the $build_dir argument. That is, the following are equivalent: cpp2xs($module_name, $package_name, '.', $config_opts); cpp2xs($module_name, $package_name, $config_opts); If a third argument is given, it's deemed to be the build directory unless it's a hash reference (in which case it's deemed to be the hash reference containing the additional config options). As of version 0.19, a cpp2xs utility is also provided. It's just an Inline::CPP2XS wrapper - see 'cpp2xs --help'. See also the cpp2xs demos in demos/cpp2xs_utility/README (in the InlineX::CPP2XS source distro).
Don't feed an actual Inline::CPP script to this module - it won't be able to parse it. It is capable of parsing correctly only that CPP code that is suitable for inclusion in an Inline::CPP script. For example, here is a simple Inline::CPP script: use warnings; use Inline CPP => Config => BUILD_NOISY => 1, CLEAN_AFTER_BUILD => 0; use Inline CPP => <<'EOC'; #include <stdio.h> void greet() { printf("Hello world\n"); } EOC greet(); __END__ The CPP file that InlineX::CPP2XS needs to find would contain only that code that's between the opening 'EOC' and the closing 'EOC' - namely: #include <stdio.h> void greet() { printf("Hello world\n"); } If the CPP code is not provided by either the CODE or SRC_LOCATION keys, InlineX::CPP2XS looks for the source file in ./src directory - expecting that the filename will be the same as what appears after the final '::' in the module name (with a '.cpp' extension). ie if your module is called My::Next::Mod the cpp2xs() function looks for a file ./src/Mod.cpp, and creates a file named Mod.xs. Also created (by the cpp2xs function, is the file 'INLINE.h' - but only if that file is needed. The generated xs file (and INLINE.h) will be written to the cwd unless a third argument (specifying a valid directory) is provided to the cpp2xs function. The created XS file, when packaged with the '.pm' file, an appropriate 'Makefile.PL' (which can also be auto-generated by setting the WRITE_MAKEFILE_PL hash key), and 'INLINE.h' (if it's needed), can be used to build the module in the usual way - without any dependence upon the Inline::CPP module. The cpp2xs() function may also produce a typemap file ('CPP.map'). That file, if produced, is also needed for a successful build. See the demos/cpp folder in the InlineX::CPP2XS source for an example of what's required.
As regards the optional fourth argument to cpp2xs(), the following hash keys/values are recognised: AUTO_INCLUDE The value specified is automatically inserted into the generated XS file. (Also, the specified include will be parsed and used iff AUTOWRAP is set to a true value.) eg: AUTO_INCLUDE => '#include <my_header.h>', ---- AUTOWRAP Set this to a true value to enable Inline::CPP's AUTOWRAP capability. eg: AUTOWRAP => 1, ---- BOOT Specifies C/CPP code to be executed in the XS BOOT section. Corresponds to the XS parameter. eg: BOOT => 'printf("Hello .. from bootstrap\n");', ---- BOOT_F Specifies a file containing C/CPP code to be executed in the XS BOOT section. eg: BOOT_F => '/home/me/boot_code.ext', ---- BUILD_NOISY Is set to a true value, by default. Setting to a false value will mean that progress messages generated by Inline::CPP are suppressed. eg: BUILD_NOISY => 0, ---- CC Specify the compiler you want to use. It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: CC => 'g++', ---- CCFLAGS Specify which compiler flags to use. (Existing value gets clobbered, so you'll probably want to re-specify it.) It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: CCFLAGS => $Config{ccflags} . ' -DMY_DEFINE', ---- DIST If set, sets WRITE_MAKEFILE_PL => 'p', WRITE_PM => 1, MANIF => 1. eg: DIST => 1, ---- CCFLAGSEX Add compiler flags to existing flags. It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: CCFLAGSEX => '-DMY_DEFINE', ---- CODE A string containing the CPP code. eg: CODE => 'void foo() {printf("Hello World\n");}' . "\n\n", ---- EXPORT_ALL Makes no sense to use this unless WRITE_PM has been set. Places all XSubs except those beginning with a *single* underscore (but not multiple underscores) in @EXPORT in the generated .pm file. eg: EXPORT_ALL => 1, ---- EXPORT_OK_ALL Makes no sense to use this unless WRITE_PM has been set. Places all XSubs except those beginning with a *single* underscore (but not multiple underscores) in @EXPORT_OK in the generated .pm file. eg: EXPORT_OK_ALL => 1, ---- EXPORT_TAGS_ALL Makes no sense to use this unless WRITE_PM has been set. In the generated .pm file, creates an EXPORT_TAGS tag named 'name' (where 'name' is whatever you have specified), and places all XSubs except those beginning with a *single* underscore (but not multiple underscores) in 'name'. Also places same subs in @EXPORT_OK. eg, the following creates and fills a tag named 'all': EXPORT_TAGS_ALL => 'all', ---- INC The value specified is added to the includes search path. It makes sense to assign this key only when AUTOWRAP and/or WRITE_MAKEFILE_PL are set to a true value. eg: INC => '-I/my/includes/dir -I/other/includes/dir', INC => ['-I/my/includes/dir', '-I/other/includes/dir'], ---- LD Specify the linker you want to use.It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: LD => 'g++', ---- LDDLFLAGS Specify which linker flags to use. (Existing value gets clobbered, so you'll probably want to re-specify it.) It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: LDDLFLAGS => "$my_ldopts " . $Config{lddlflags}, ---- LIBS The value(s) specified become the LIBS search path. It makes sense to assign this key only if WRITE_MAKEFILE_PL is set to a true value. eg: LIBS => '-L/somewhere -lsomelib -L/elsewhere -lotherlib', LIBS => ['-L/somewhere -lsomelib', '-L/elsewhere -lotherlib'], ---- MAKE Specify the make utility you want to use. It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: MAKE => 'pmake', # I have no idea whether that will work :-) ---- MANIF If true, the MANIFEST file will be written. (It will include all created files.) eg: MANIF => 1, ---- MYEXTLIB Specifies a user compiled object that should be linked in. Corresponds to the MakeMaker parameter. It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: MYEXTLIB => '/your/path/yourmodule.so', ---- OPTIMIZE This controls the MakeMaker OPTIMIZE setting.It makes sense to assign this key only when WRITE_MAKEFILE_PL is set to a true value. eg: OPTIMIZE => '-g', ---- PREFIX Specifies a prefix that will be automatically stripped from C functions when they are bound to Perl. eg: PREFIX => 'FOO_', ---- PRE_HEAD Specifies code that will precede the inclusion of all files specified in AUTO_INCLUDE (ie EXTERN.h, perl.h, XSUB.h, INLINE.h and anything else that might have been added to AUTO_INCLUDE by the user). If the specified value identifies a file, the contents of that file will be inserted, otherwise the specified value is inserted. If the specified value is a string of code, then since that string ends in "\n" (as all code *should* terminate with at least one "\n"), you will get a warning about an "Unsuccessful stat on filename containing newline" when the test for the existence of a file that matches the PRE_HEAD value is conducted. PRE_HEAD => $code_or_filename; ---- PREREQ_PM Makes sense to specify this only if WRITE_MAKEFILE_PL is set to true. The string to which PREREQ_PM is set will be reproduced as is in the generated Makefile.PL. That is, if you specify: PREREQ_PM => "{'Some::Mod' => '1.23', 'Nother::Mod' => '3.21'}", then the WriteMakefile hash in the generated Makefile.PL will contain: PREREQ_PM => {'Some::Mod' => '1.23', 'Nother::Mod' => '3.21'}, ---- SRC_LOCATION Specifies a C file that contains the CPP source code. eg: SRC_LOCATION => '/home/me/source.ext', ---- T Is false by default but, When set to true will write a basic t/00load.t test script in the build directory. eg: T => 1, ---- TYPEMAPS The value(s) specified are added to the list of typemaps. eg: TYPEMAPS =>['my_typemap', 'my_other_typemap'], TYPEMAPS =>'my_typemap my_other_typemap', ---- USE Must be an array reference, listing the modules that the autogenerated pm file needs to load (use). Makes no sense to assign this key if WRITE_PM is not set to a true value. eg: USE => ['Digest::MD5', 'LWP::Simple']; ---- USING With Inline::C, enables use of an alternative parser. But with Inline::CPP, there is currently no alternative parser available. USING => ['ParseRegExp'], # fails on Inline::CPP & InlineX::CPP2XS. or USING => 'ParseRegExp', # fails on Inline::CPP & InlineX::CPP2XS. ---- VERSION Set this to the version number of the module. It makes sense to assign this key only if WRITE_MAKEFILE_PL and/or WRITE_PM is set to a true value. eg: VERSION => 0.42, ---- WRITE_MAKEFILE_PL Set this to to a true value if you want the Makefile.PL to be generated. (You should also assign the 'VERSION' key to the correct value when WRITE_MAKEFILE_PL is set.) eg: WRITE_MAKEFILE_PL => 1, # Makefile.PL and xs file may not work on # a different machine. WRITE_MAKEFILE_PL => 'p', # Makefile.PL and xs file should be portable ---- WRITE_PM Set this to a true value if you want a .pm file to be generated. You'll also need to assign the 'VERSION' key appropriately. Note that it's a fairly simplistic .pm file - no POD, no perl subroutines, no exported subs (unless EXPORT_ALL or EXPORT_OK_ALL has been set), no warnings - but it will allow the utilisation of all of the XSubs in the XS file. eg: WRITE_PM => 1, ----
None known - patches/rewrites/enhancements welcome. Send to sisyphus at cpan dot org
This program is free software; you may redistribute it and/or modify it under the same terms as Perl itself. Copyright 2006-2009, 2010-12, Sisyphus
Sisyphus <sisyphus at(@) cpan dot (.) org>
To install InlineX::CPP2XS, copy and paste the appropriate command in to your terminal.
cpanm
cpanm InlineX::CPP2XS
CPAN shell
perl -MCPAN -e shell install InlineX::CPP2XS
For more information on module installation, please visit the detailed CPAN module installation guide.