=head1 NAME Inline::SLang - Write Perl subroutines in S-Lang. =head1 SYNOPSIS use Inline SLang; print "9 + 16 = ", add(9,16), "\n"; print "9 - 16 = ", subtract(9,16), "\n"; print JAxH('Inline'), "\n"; __END__ __SLang__ define add (a,b) { return a + b; } define subtract (a,b) { return a - b; } define JAxH () { variable type = (); return sprintf( "Just Another %S Hacker!", type ); } =head1 DESCRIPTION # # Version 0.20 adds support for the Perl Data Language. # However the way this is implemented *AND* some details of # how PDL is supported (mainly the support for non 1D arrays/piddles) # is not finalised. # # This support does not work on Linux and OS-X machines so it # has been turned off by default in version 0.21 # The C<Inline::SLang> module lets you write Perl subroutines in S-Lang. It dynamically translates the parameters and return values into native data types for both languages (or into Perl classes that are used to represent S-Lang types with no direct translation to Perl). This allows you to write a Perl script and take advantage of S-Lang whenever you wish: perhaps there is a S-Lang I<module> that you wish to use, or you want to take advantage of a S-Lang function that you have written. The module sets up an in-process S-Lang interpreter, runs your code, and then examines the interpreter's symbol table, looking for things to bind to Perl. The process of interrogating the S-Lang interpreter only occurs the first time you run your S-Lang code. The namespaces are cached, and subsequent calls use the cached version (which is hidden in the F<_Inline> directory; see the L<Inline documentation|Inline> for details of how the code is cached). Of course, your S-Lang code must still be run every time your run the Perl script -- but Inline::S-Lang already knows the results of running it. =head1 What is S-Lang? From the S-Lang library home page at L<http://www.s-lang.org/> S-Lang is a multi-platform programmer's library designed to allow a developer to create robust multi-platform software. It provides facilities required by interactive applications such as display/screen management, keyboard input, keymaps, and so on. The most exciting feature of the library is the slang interpreter that may be easily embedded into a program to make it extensible. For our purposes it is the S-Lang interpreter that we are interested in. See the L<Term::Slang|Term::Slang> module (on CPAN) if you want an interface to the terminal library provided by S-Lang. =head1 Using the Inline::SLang Module Using Inline::SLang will seem very similar to using any other Inline language, thanks to Inline's consistent look and feel. This section will explain the different ways to use Inline::SLang. Further details on configuring the behaviour of C<Inline::SLang> can be found in L<Inline::SLang::Config>. For more details on C<Inline>, see L<Inline> or C<perldoc Inline>. =head2 S-Lang Functions Using functions defined in S-Lang is just like using Perl subroutines. You just supply the source code to Inline::SLang - see the L<Inline manual|Inline> for the various ways of doing this - and then use them in your Perl code. For example: # set up a S-Lang function use Inline SLang => <<'END'; define doit() { vmessage("Printing from S-Lang"); } END # now call the S-Lang function from Perl doit; By default all S-Lang functions - other than S-Lang intrinsic functions (the functions defined by the S-Lang interpreter, such as C<array_map()> and C<assoc_get_keys()>) - in the default namespace ("Global") are bound to Perl. The Perl functions are available in the C<main> package. The C<BIND_NS> configuration option can be used to change the list of S-Lang namespaces bound to Perl. If you have need of an intrinsic S-Lang function then you can either write a wrapper routine or use the C<BIND_SLFUNCS> option. See L<Inline::SLang::Config> for more details. Note that there are no checks that a S-Lang symbol, when mapped to Perl, does not clobber an existing value (or is a Perl built-in function so can not be over-ridden). So I<beware> when you define a S-Lang function called C<open()>! =head3 But all I want to do is use a S-Lang module? If you have a S-Lang module that you want to use directly from Perl, it's as easy as the following (assuming the module is importable and called C<funkymodule>): use Inline 'SLang' => 'import("funkymodule");'; and then you can start using the functions defined by the module. You use a similar technique if you have a file containing S-Lang code that needs to be loaded via C<evalfile>. =head2 S-Lang Variables We currently do not bind any S-Lang variables to Perl. To access variables you have to write S-Lang routines that read/write the variable, as shown by the C<foo()> and C<bar()> routines below: variable foobar = "a string"; define foo() { return foobar; } define bar(x) { foobar = x; } It I<should> be possible to also bind variables, but this is not a high priority (and may never be). =head2 Supported Data Types Inline::S-Lang attempts to seamlessly convert between Perl and S-Lang data types. For "simple" types - for example strings - where there is a direct match between S-Lang and Perl, the conversion is not noticeable. For more complicated types - such as complex numbers - S-Lang variables are converted to Perl objects. Where possible a I<perl-like> interface is retained. See L<Inline::SLang::Types> for more information on how the various data types are supported. The module currently B<requires> that yor S-Lang library has been compiled with support for both floating-point and complex numbers. =head2 Perl routines The module provides several utility functions which are discussed below. By default they are only available using fully-qualified names - e.g. C<Inline::SLang::sl_eval()> - although the C<EXPORT> L<configuration option|Inline::SLang::Config/EXPORT> can be used to change this. =head3 Inline::SLang::sl_array2perl =head4 Usage: $val = Inline::SLang::sl_array2perl(); $val = Inline::SLang::sl_array2perl( $newval ); Sets/Gets the current status of the "how do we convert a S-Lang array into Perl" flag. Returns the status. We list the possible values of the flag below. For further details on array support in C<Inline::SLang> see L<Inline::SLang::Array>. =head4 With no PDL support If PDL support was not compiled in to the module then the flag can either be 0 or 1, where =over 3 =item Value = B<0> All arrays are converted to a Perl array reference. =item Value = B<1> All arrays are converted to a Perl C<Array_Type> object =back =head4 With PDL support If PDL support is available then there are four options: =over 3 =item Value = B<0> All arrays are converted to a Perl array reference. =item Value = B<1> All arrays are converted to a Perl C<Array_Type> object =item Value = B<2> Numeric arrays are converted to piddles and non-numeric arrays are converted to a Perl array reference. =item Value = B<3> Numeric arrays are converted to piddles and non-numeric arrays are converted to a Perl C<Array_Type> object. =back =head3 Inline::SLang::sl_array =head4 Usage: $sl = Inline::SLang::sl_array( $aref ); $sl = Inline::SLang::sl_array( $aref, $adims ); $sl = Inline::SLang::sl_array( $aref, $atype ); $sl = Inline::SLang::sl_array( $aref, $adims, $atype ); This is a wrapper around the C<Array_Type> constructor and is intended to make it easy to ensure that a Perl array reference is converted into a S-Lang array of the correct type, dimensionality, and size. The data is stored in C<$aref>, a Perl array reference. If no other parameters are supplied then the array dimensions, size, and type are I<guessed> from C<$aref>. Since Perl has such a flexible type system the routine can sometimes make a surprising choice for the data type of the array, so it may well be worth supplying the array type as C<$atype> - which can be either a string containing the name of the S-Lang datatype, such as C<"Int_Type">, or a C<DataType_Type> object. If you know the array dimensions then it's probably faster to supply them as the C<$adims> argument, which should be an array reference. Note that there is limited error checking in this routine: if C<$aref> is a 2x3 array but you send in C<$adims> as C<[3,2]> - or C<[24]> say - then expect I<weird behaviour> (at the very least). =head4 Example: use Inline 'SLang' => Config => EXPORT => [ "sl_array" ]; use Inline 'SLang'; ... some_slang_func( sl_array([[1.0,0.0],[0.0,1.0]],"Double_Type") ); For numeric types I expect most people to use piddles. This routine is more useful for arrays of non-numeric data types. =head3 Inline::SLang::sl_eval =head4 Usage [ retval(s) = ] Inline::SLang::sl_eval( $str ); This function evaluates the supplied S-Lang code (in C<$str>) and converts any return values to Perl. In general this will not be needed, since you can always call S-Lang's C<eval()> function via a wrapper function (or by binding it to a different function name in Perl). =head4 Example: my $foo = Inline::SLang::sl_eval("23+4"); print "S-Lang thinks 23+4 is $foo\n"; A more flexible solution is to write a S-lang wrapper around the S-Lang C<eval()> function (perhaps this functionality should be moved into C<sl_eval>?): % Call as myeval( "slang code" [, var1, var2, ... ] ); % where varX are variables that placed onto the S-Lang % stack before calling the S-Lang code define myeval() { % pop off the slang code from the stack, leave the rest there variable slcode; if ( _NARGS > 1 ) { _stk_reverse(_NARGS); slcode = (); _stk_reverse(_NARGS-1); } else slcode = (); eval( slcode ); } =head3 Inline::SLang::sl_have_pdl =head4 Usage: $flag = Inline::SLang::sl_have_pdl(); Returns C<1> if the module was compiled with support for L<PDL|PDL::Intro>, and C<0> otherwise. =head3 Inline::SLang::sl_typeof =head4 Usage: $type = Inline::SLang::sl_typeof( $var ); Returns the S-Lang type of the data stored in the Perl variable C<$var>. This should be more efficient than using S-Lang's C<typeof()> command since it does not require the conversion of the whole variable to S-Lang (normally not a big issue but it can be if C<$var> contains a large array or a complicated structure). The return value is an object of the C<DataType_Type> class; see L<PDL::Types|PDL::Types> for more information on how S-Lang variables are represented in Perl. =head4 Example: my $foo = some_slang_function(); my $type = Inline::SLang::sl_typeof($foo); print "The function returned a $type variable\n"; Note that all objects used to represent S-Lang data types - other than C<Math::Complex> objects - have a C<typeof()> method which can be used to find the type of the object. =head3 Inline::SLang::sl_version =head4 Usage: $ver = Inline::SLang::sl_version(); Returns, as a string, the version of S-Lang against which the module was compiled, with a format of "a.b.c". You can use C<sl_eval("_slang_version_string")> to find out what version of the library you are using. =head2 What happens when there is a S-Lang error? The module will refuse to build if there is an error in the S-Lang code compiled when your program is first run. If an error occurs in the S-Lang interpreter - such as calling a function that expects an argument with none - then the S-Lang error is transformed into a Perl error (as a call to C<croak>) and the S-Lang interpreter is restarted. This means that these errors can be handled by using Perl's C<eval> statement. =head1 CHANGES =over 2 =item v0.23 Wed Apr 7 21:32:07 EDT 2004 This is a bug-fix for C<make test> in version 0.22, which failed on systems which did not already have C<Inline::SLang> installed. =item v0.22 Wed Apr 7 16:29:05 EDT 2004 The build process has been changed to use L<Inline::C> to embed C code within F<Makefile.PL>, rather than having it in a separate file which we have to compile ourselves. This should hopefully make the build process a bit more portable. =item v0.21 Mon Apr 5 15:15:51 EDT 2004 This release will now build on OS-X machines. The support for PDL has been turned off by default - even if PDL is installed on your system - since it does not work on Linux and OS-X machines. The main changes are behind the scenes, and involve splitting the code up and making a tad more modular. =item v0.20 Wed May 21 00:37:07 EDT 2003 This release begins support for the L<Perl Data Language|PDL::Intro> in C<Inline::SLang>. Please note that it is a work-in-progress. =over 2 =item * requires v2.4.0 of PDL which isn't actually released (a fairly-recent CVS build should do the trick) =item * conversion betweed 1D arrays and piddles works =item * should 0D piddles be converted to a scalar or a 1-element 1D array? (currently the code croaks) =item * > 1D arrays is a mess since a 2x3 array in S-Lang maps to a 3x2 piddle. The first time this happens a warning is printed to STDERR as a precaution. Not sure what the best approach is. =item * It has not been tested on non 32-bit machines. =back =item v0.12 Sun May 11 23:33:38 EDT 2003 This is a minor upgrade in functionality to version 0.11; the changes are made to help support the inclusion of PDL in a future release. The changes are: =over 2 =item * Added support to the C<DataType_Type> class for numeric types that are - or may be - synonyms of the "base" types. The added types are: C<Int16_Type>, C<Int32_Type>, their unsigned versions, C<Float32_Type>, C<Float64_Type>, and - if they are not a "base" type - C<Short_Type> and C<Long_Type>. =item * The build process now checks that the S-Lang library was built with support for floating-point and complex numbers. If it was not then it should stop. =item * Added a brief section to this document describing how S-Lang errors are handled. =back =item v0.11 Wed May 7 00:39:17 EDT 2003 This release makes a couple of improvements to version I<0.10> and includes infrastructure changes to support L<PDL|PDL::Intro> (although piddles are still not supported). The major changes are: =over 2 =item * S-Lang arrays can now be converted to the Perl C<Array_Type> object as well as array references. The behaviour is controlled by the C<Inline::SLang::sl_array2perl()> function, described in L<Inline::SLang|Inline::SLang>. =item * It is now easier to create Perl scalars that contain a C<DataType_Type> object: use the functions C<< Inline::SLang::<datatype name>() >> instead of C<< DataType_Type->new( "<datatype name>" ); >>. Use C<'!types'> in the C<EXPORT> configuration option to import all these functions. =item * C<DataType_Type> objects can now be compared for equality (C<==>, C<eq>) and inequality (C<!=>, C<ne>). =back =item v0.10 Sat May 3 19:39:00 EDT 2003 There have been a number of significant enhancements and changes in this release, which is why the release number has been bumped-up to the lofty heights of I<0.10>. The really-short summary is that all variables should now be supported and the support for S-Lang's associative arrays, normal arrays, and structures has been made much -more Perl like. =over 2 =item * Support for S-Lang libraries earlier than 1.4.7 has been discontinued. =item * Perl class names have been changed from C<Inline::SLang::XXX> to C<XXX>. =item * S-Lang structs (both C<Struct_Type> and named structs) are stored using a Perl object (also called C<Struct_Type>) which can be treated as a hash reference. As an example, if the S-Lang structure has a field C<x> and it is stored in the Perl variable C<$foo> then you can access the field as C<$$foo{x}>. =item * S-Lang C<Assoc_Type> arrays are now converted to the Perl C<Assoc_Type> class (and vice-versa). This object can be treated as a hash reference. When calling S-Lang functions, hash references are converted to S-Lang as an C<Assoc_Type [Any_Type]> array. =item * Arrays can now be converted between Perl (array references or Perl C<Array_Type> objects) and S-Lang (C<Array_Type> variables) for any S-Lang data type. Any dimension of array supported by S-Lang is now available (in previous only one and two dimensional arrays could be used). Support for piddles is I<not yet available> (planned soon). =item * Several Inline::SLang::XXX routines can now be exported to Perl's main package by use of the EXPORT configuration option (rather than the standard Perl way of using 'use foo qw( ... );'. This can be looked at as something of a hack. =item * Handling of S-Lang errors has been improved: they are now caught and then converted into Perl errors (i.e. calls to C<croak>). This means that calling DataType_Type->new() with an unknown type name no longer results in S-Lang error messages printed to STDERR (which it did in 0.06). =item * fixed mem leak when converting structs from Perl to S-Lang. Note that the code used *may* trigger a mem leak in the S-Lang library if you are using a version < 1.4.9. =back =item v0.06 Thu Apr 3 22:36:54 EST 2003 Notable changes are: =over 2 =item * Essentially all S-Lang I<scalars> can now be converted to Perl. Those without a direct translation to a native Perl type are converted to "opaque" Perl objects, with classes called C<Inline::SLang::XXX> where C<XXX> equals the name of their S-Lang data type. Essentially all you can do with these objects is pass them back to S-Lang routines. However, it does mean you can now call routines that return module-defined types. Currently the S-Lang file types (so C<File_Type> and C<FD_Type>) are converted using this scheme, which means you can I<not> use them with Perl I/O commands. I need to read up a lot more on Perl's I/O mechanism before I can change this (if it's possible). =item * "Named" structures - e.g. C<Foo_Type> created by C<< typedef struct {...} Foo_Type; >> - are now handled as C<Inline::SLang::XXX> objects, where C<XXX> matches the structure type (so C<Foo_Type> in this example). These classes are sub-classes of C<Inline::SLang::Struct_Type>. =item * Fixed handling of BIND_NS =E<gt> "All". =item * Added an examples/ directory to the distribution, which contains simple examples (mainly from L<Inline::SLang::Types>). Note that these files are I<not> installed into the Perl tree by 'make install'. =back =item v0.05 Fri Mar 14 11:57:31 EST 2003 Notable changes are: =over 2 =item * Handling of 'foreign' S-Lang types - those for which we have introduced special classes such as C<DataType_Type> variables - has been changed to use a scheme in which the Perl class name is formed from the concatanation of C<Inline::SLang::> and the S-Lang type (so C<Inline::SLang::struct> has been renamed to C<Inline::SLang::Struct_Type>). The classes are also more uniform in that they have a number of common functions and, where possible, the method names are similar to S-Lang functions with the same functionality. =item * Ref_Type variables are now supported (scalars only) via the C<Inline::SLang::Ref_Type> class. Unfortunately this requires use of function/types that are not part of the public interface of the S-Lang library. =item * The BIND_NS option only works for v1.4.3 and higher of S-Lang. The option has been enhanced to allow namespace "renaming" and the use of "All" to specify all known namespaces (this only works for v1.4.7 and higher of S-Lang). The only valid string options are now "Global(=...)" and "All". =item * The BIND_SLFUNCS option has been added to allow you to use slected S-Lang intrinsic functions directly from Perl (i.e. without having to write a S-Lang wrapper function around it). To help avoid nameclashes you can chose your own name for the function in Perl. =item * Documentation on S-Lang specific configuration options has been moved to L<Inline::SLang::Config>. =back =item v0.04 Fri Mar 7 00:14:47 EST 2003 Notable changes are: =over 2 =item * License changed to GNU GPL and copyright holder to SAO. =item * Now binds all functions (other than S-Lang intrinsic functions) in the Global namespace. Added the C<BIND_NS> configuration option to allow functions in other namespaces to be bound as well. Use the Inline '-MInline=INFO' option to find out what functions have been bound. =item * S-Lang C<Struct_Type> variables are converted to C<Inline::SLang::struct> objects. There are memory leaks! =item * Fixed memory leaks when converting C<Assoc_Type> arrays to Perl. =item * S-Lang C<Struct_Type> variables are converted to C<Inline::SLang::struct> objects. =back =item v0.03 Tue Jan 28 12:01:49 EST 2003 Initial public release =back =head1 SUPPORTED PLATFORMS =over 2 =item * S-Lang library >= 1.4.7 =item * The S-Lang library must have been compiled with support for floating-point and complex numbers. The module could be made to work without these numbers/types but I do not have the time to do this. =item * The only tested operating systems are Solaris, Linux, and OS-X (10.3.3). It should compile on UNIX-like systems (no promises though), and I will be surprised if it works without tweaking on other operating systems. =item * Perl >= 5.6.0 =back =head1 BUGS AND DEFICIENCIES The code has not been widely tested so I can not guarantee what will happen if you try to use it (not that I could offer any sort of guarantee even if it had been tested across multiple platforms). Please use the CPAN Resource Tracker at http://rt.cpan.org/NoAuth/Bugs.html?Dist=Inline-SLang to check for bugs, report new ones, and request new features. =head1 SEE ALSO L<Inline::SLang::Config>, L<Inline::SLang::Types>, L<Term::Slang> For information about using C<Inline>, see L<Inline>. For information about other Inline languages, see L<Inline-Support>. For information about S-Lang see L<http://www.s-lang.org/>. =head1 ACKNOWLEDGEMENTS John Davis (for S-Lang), Brian Ingerson (for the Inline framework), and Neil Watkiss since I based much of this module on his L<Inline::Python> and L<Inline::Ruby> modules. However, please do not assume that any errors in this module are in any way related to the above people. =head1 AUTHOR Doug Burke <djburke@cpan.org> =head1 COPYRIGHT This software is Copyright (C) 2003, 2004 Smithsonian Astrophysical Observatory. All rights are reserved. It is released under the GNU General Public License. You may find a copy of this licence in the file LICENSE within the source distribution or at L<http://www.fsf.org/copyleft/gpl.html> Prior to version 0.04 the module was distributed under the same terms as Perl. =head1 WARRANTY There is no warranty. Please see the GNU General Public License for more details.