argra****@users*****
argra****@users*****
2007年 11月 19日 (月) 04:20:26 JST
Index: docs/perl/5.8.8/perlxstut.pod diff -u docs/perl/5.8.8/perlxstut.pod:1.1 docs/perl/5.8.8/perlxstut.pod:1.2 --- docs/perl/5.8.8/perlxstut.pod:1.1 Sun Nov 18 04:16:13 2007 +++ docs/perl/5.8.8/perlxstut.pod Mon Nov 19 04:20:26 2007 @@ -45,6 +45,10 @@ =end original +This tutorial was written from a Unix point of view. Where I know them +to be otherwise different for other platforms (e.g. Win32), I will list +them. If you find something that was missed, please let me know. +(TBT) =head1 SPECIAL NOTES @@ -59,6 +63,11 @@ =end original +This tutorial assumes that the make program that Perl is configured to +use is called C<make>. Instead of running "make" in the examples that +follow, you may have to substitute whatever make program Perl has been +configured to use. Running B<perl -V:make> should tell you what it is. +(TBT) =head2 Version caveat @@ -72,6 +81,12 @@ =end original +When writing a Perl extension for general consumption, one should expect that +the extension will be used with versions of Perl different from the +version available on your machine. Since you are reading this document, +the version of Perl on your machine is probably 5.005 or later, but the users +of your extension may have more ancient versions. +(TBT) =begin original @@ -81,6 +96,10 @@ =end original +To understand what kinds of incompatibilities one may expect, and in the rare +case that the version of Perl on your machine is older than this document, +see the section on "Troubleshooting these Examples" for more information. +(TBT) =begin original @@ -92,6 +111,12 @@ =end original +If your extension uses some features of Perl which are not available on older +releases of Perl, your users would appreciate an early meaningful warning. +You would probably put this information into the F<README> file, but nowadays +installation of extensions may be performed automatically, guided by F<CPAN.pm> +module or other tools. +(TBT) =begin original @@ -101,6 +126,10 @@ =end original +In MakeMaker-based installations, F<Makefile.PL> provides the earliest +opportunity to perform version checks. One can put something like this +in F<Makefile.PL> for this purpose: +(TBT) eval { require 5.007 } or die <<EOD; @@ -175,12 +204,15 @@ =head1 TUTORIAL +(チュートリアル) + =begin original Now let's go on with the show! =end original +では、見ていきましょう! =head2 EXAMPLE 1 @@ -281,6 +313,9 @@ =end original +The rest of the .pm file contains sample code for providing documentation for +the extension. +(TBT) =begin original @@ -317,6 +352,10 @@ =end original +It is okay for the lines starting at the "CODE:" line to not be indented. +However, for readability purposes, it is suggested that you indent CODE: +one level and the lines following one more level. +(TBT) =begin original @@ -367,6 +406,9 @@ =end original +You can safely ignore the line about "prototyping behavior" - it is +explained in the section "The PROTOTYPES: Keyword" in L<perlxs>. +(TBT) =begin original @@ -380,6 +422,14 @@ =end original +If you are on a Win32 system, and the build process fails with linker +errors for functions in the C library, check if your Perl is configured +to use PerlCRT (running B<perl -V:libc> should show you if this is the +case). If Perl is configured to use PerlCRT, you have to make sure +PerlCRT.lib is copied to the same location that msvcrt.lib lives in, +so that the compiler can find it on its own. msvcrt.lib is usually +found in the Visual C compiler's lib directory (e.g. C:/DevStudio/VC/lib). +(TBT) =begin original @@ -841,8 +891,8 @@ =end original -“C<make test>”を実行すると、Perl は致命的エラーを起こして終了して -しまいます。 +“C<make test>”を実行すると、Perl は致命的エラーを起こして +終了してしまいます。 Perl は、定数値を変更することをさせないのです! =head2 What's new here? @@ -1155,6 +1205,11 @@ =end original +Make sure you use a tab and not spaces on the lines beginning with "$(AR)" +and "$(RANLIB)". Make will not function properly if you use spaces. +It has also been reported that the "cr" argument to $(AR) is unnecessary +on Win32 systems. +(TBT) =begin original @@ -1457,6 +1512,9 @@ =end original +The .xs file of L<"EXAMPLE 4"> contained some new elements. To understand +the meaning of these elements, pay attention to the line which reads +(TBT) MODULE = Mytest2 PACKAGE = Mytest2 @@ -1469,6 +1527,11 @@ =end original +Anything before this line is plain C code which describes which headers +to include, and defines some convenience functions. No translations are +performed on this part, apart from having embedded POD documentation +skipped over (see L<perlpod>) it goes into the generated output C file as is. +(TBT) =begin original @@ -1479,6 +1542,11 @@ =end original +Anything after this line is the description of XSUB functions. +These descriptions are translated by B<xsubpp> into C code which +implements these functions using Perl calling conventions, and which +makes these functions visible from Perl interpreter. +(TBT) =begin original @@ -1489,6 +1557,11 @@ =end original +Pay a special attention to the function C<constant>. This name appears +twice in the generated .xs file: once in the first part, as a static C +function, then another time in the second part, when an XSUB interface to +this static C function is defined. +(TBT) =begin original @@ -1502,6 +1575,14 @@ =end original +This is quite typical for .xs files: usually the .xs file provides +an interface to an existing C function. Then this C function is defined +somewhere (either in an external library, or in the first part of .xs file), +and a Perl interface to this function (i.e. "Perl glue") is described in the +second part of .xs file. The situation in L<"EXAMPLE 1">, L<"EXAMPLE 2">, +and L<"EXAMPLE 3">, when all the work is done inside the "Perl glue", is +somewhat of an exception rather than the rule. +(TBT) =head2 Getting the fat out of XSUBs @@ -1512,6 +1593,9 @@ =end original +In L<"EXAMPLE 4"> the second part of .xs file contained the following +description of an XSUB: +(TBT) double foo(a,b,c) @@ -1530,6 +1614,11 @@ =end original +Note that in contrast with L<"EXAMPLE 1">, L<"EXAMPLE 2"> and L<"EXAMPLE 3">, +this description does not contain the actual I<code> for what is done +is done during a call to Perl function foo(). To understand what is going +on here, one can add a CODE section to this XSUB: +(TBT) double foo(a,b,c) @@ -1554,6 +1643,15 @@ =end original +However, these two XSUBs provide almost identical generated C code: B<xsubpp> +compiler is smart enough to figure out the C<CODE:> section from the first +two lines of the description of XSUB. What about C<OUTPUT:> section? In +fact, that is absolutely the same! The C<OUTPUT:> section can be removed +as well, I<as far as C<CODE:> section or C<PPCODE:> section> is not +specified: B<xsubpp> can see that it needs to generate a function call +section, and will autogenerate the OUTPUT section too. Thus one can +shortcut the XSUB to become: +(TBT) double foo(a,b,c) @@ -1567,6 +1665,7 @@ =end original +同じことを L<"EXAMPLE 2"> の XSUB: int is_even(input) @@ -1584,6 +1683,11 @@ =end original +で出来るでしょうか? +To do this, one needs to define a C function C<int +is_even(int input)>. As we saw in L<Anatomy of .xs file>, a proper place +for this definition is in the first part of .xs file. In fact a C function +(TBT) int is_even(int arg) @@ -1598,6 +1702,9 @@ =end original +is probably overkill for this. Something as simple as a C<#define> will +do too: +(TBT) #define is_even(arg) ((arg) % 2 == 0) @@ -1608,6 +1715,9 @@ =end original +After having this in the first part of .xs file, the "Perl glue" part becomes +as simple as +(TBT) int is_even(input) @@ -1625,6 +1735,14 @@ =end original +This technique of separation of the glue part from the workhorse part has +obvious tradeoffs: if you want to change a Perl interface, you need to +change two places in your code. However, it removes a lot of clutter, +and makes the workhorse part independent from idiosyncrasies of Perl calling +convention. (In fact, there is nothing Perl-specific in the above description, +a different version of B<xsubpp> might have translated this to TCL glue or +Python glue as well.) +(TBT) =head2 More about XSUB arguments @@ -1669,6 +1787,11 @@ =end original +While Perl passes arguments to functions by reference, +C passes arguments by value; to implement a C function which modifies data +of one of the "arguments", the actual argument of this C function would be +a pointer to the data. Thus two C functions with declarations +(TBT) int string_length(char *s); int upper_case_char(char *cp); @@ -1683,6 +1806,12 @@ =end original +may have completely different semantics: the first one may inspect an array +of chars pointed by s, and the second one may immediately dereference C<cp> +and manipulate C<*cp> only (using the return value as, say, a success +indicator). From Perl one would use these functions in +a completely different manner. +(TBT) =begin original @@ -1692,6 +1821,10 @@ =end original +One conveys this info to B<xsubpp> by replacing C<*> before the +argument by C<&>. C<&> means that the argument should be passed to a library +function by its address. The above two function may be XSUB-ified as +(TBT) int string_length(s) @@ -1707,6 +1840,7 @@ =end original +例として、次のものを考えます: int foo(a,b) @@ -1816,6 +1950,12 @@ =end original +The actual values on the argument stack are pointers to the values passed +in. When an argument is listed as being an OUTPUT value, its corresponding +value on the stack (i.e., ST(0) if it was the first argument) is changed. +You can verify this by looking at the C code generated for Example 3. +The code for the round() XSUB routine contains lines that look like this: +(TBT) double arg = (double)SvNV(ST(0)); /* Round the contents of the variable arg */ @@ -1828,6 +1968,9 @@ =end original +The arg variable is initially set by taking the value from ST(0), then is +stored back into ST(0) at the end of the routine. +(TBT) =begin original @@ -1837,6 +1980,10 @@ =end original +XSUBs are also allowed to return lists, not just scalars. This must be +done by manipulating stack values ST(0), ST(1), etc, in a subtly +different way. See L<perlxs> for details. +(TBT) =begin original @@ -1849,6 +1996,13 @@ =end original +XSUBs are also allowed to avoid automatic conversion of Perl function arguments +to C function arguments. See L<perlxs> for details. Some people prefer +manual conversion by inspecting C<ST(i)> even in the cases when automatic +conversion will do, arguing that this makes the logic of an XSUB call clearer. +Compare with L<"Getting the fat out of XSUBs"> for a similar tradeoff of +a complete separation of "Perl glue" and "workhorse" parts of an XSUB. +(TBT) =begin original @@ -1860,6 +2014,12 @@ =end original +While experts may argue about these idioms, a novice to Perl guts may +prefer a way which is as little Perl-guts-specific as possible, meaning +automatic conversion and automatic call generation, as in +L<"Getting the fat out of XSUBs">. This approach has the additional +benefit of protecting the XSUB writer from future changes to the Perl API. +(TBT) =head2 Extending your Extension @@ -1957,6 +2117,13 @@ =end original +Alternately, you can specify the exact directory to place the extension's +files by placing a "PREFIX=/destination/directory" after the make install. +(or in between the make and install if you have a brain-dead version of make). +This can be very useful if you are building an extension that will eventually +be distributed to multiple systems. You can then just archive the files in +the destination directory and distribute them to your destination systems. +(TBT) =head2 EXAMPLE 5 @@ -1968,6 +2135,10 @@ =end original +In this example, we'll do some more work with the argument stack. The +previous examples have all returned only a single value. We'll now +create an extension that returns an array. +(TBT) =begin original @@ -1980,6 +2151,13 @@ =end original +This extension is very Unix-oriented (struct statfs and the statfs system +call). If you are not running on a Unix system, you can substitute for +statfs any other function that returns multiple values, you can hard-code +values to be returned to the caller (although this will be a bit harder +to test the error case), or you can simply not do this example. If you +change the XSUB, be sure to fix the test cases to match the changes. +(TBT) =begin original @@ -1988,6 +2166,9 @@ =end original +Return to the Mytest directory and add the following code to the end of +Mytest.xs: +(TBT) void statfs(path) @@ -2019,6 +2200,9 @@ =end original +You'll also need to add the following code to the top of the .xs file, just +after the include of "XSUB.h": +(TBT) #include <sys/vfs.h> @@ -2029,6 +2213,9 @@ =end original +Also add the following code segment to test.pl while incrementing the "1..9" +string in the BEGIN block to "1..11": +(TBT) @a = &Mytest::statfs("/blech"); print ((scalar(@a) == 1 && $a[0] == 2) ? "ok 10\n" : "not ok 10\n"); @@ -2043,6 +2230,8 @@ =end original +This example added quite a few new concepts. We'll take them one at a time. +(TBT) =over 4 @@ -2059,6 +2248,13 @@ =end original +The INIT: directive contains code that will be placed immediately after +the argument stack is decoded. C does not allow variable declarations at +arbitrary locations inside a function, +so this is usually the best way to declare local variables needed by the XSUB. +(Alternatively, one could put the whole C<PPCODE:> section into braces, and +put these declarations on top.) +(TBT) =item * @@ -2073,6 +2269,13 @@ =end original +This routine also returns a different number of arguments depending on the +success or failure of the call to statfs. If there is an error, the error +number is returned as a single-element array. If the call is successful, +then a 9-element array is returned. Since only one argument is passed into +this function, we need room on the stack to hold the 9 values which may be +returned. +(TBT) =begin original @@ -2082,6 +2285,10 @@ =end original +We do this by using the PPCODE: directive, rather than the CODE: directive. +This tells B<xsubpp> that we will be managing the return values that will be +put on the argument stack by ourselves. +(TBT) =item * @@ -2096,6 +2303,13 @@ =end original +When we want to place values to be returned to the caller onto the stack, +we use the series of macros that begin with "XPUSH". There are five +different versions, for placing integers, unsigned integers, doubles, +strings, and Perl scalars on the stack. In our example, we placed a +Perl scalar onto the stack. (In fact this is the only macro which +can be used to return multiple values.) +(TBT) =begin original @@ -2105,6 +2319,10 @@ =end original +The XPUSH* macros will automatically extend the return stack to prevent +it from being overrun. You push values onto the stack in the order you +want them seen by the calling program. +(TBT) =item * @@ -2118,6 +2336,12 @@ =end original +The values pushed onto the return stack of the XSUB are actually mortal SV's. +They are made mortal so that once the values are copied by the calling +program, the SV's that held the returned values can be deallocated. +If they were not mortal, then they would continue to exist after the XSUB +routine returned, but would not be accessible. This is a memory leak. +(TBT) =item * @@ -2129,6 +2353,10 @@ =end original +If we were interested in performance, not in code compactness, in the success +branch we would not use C<XPUSHs> macros, but C<PUSHs> macros, and would +pre-extend the stack before pushing the return values: +(TBT) EXTEND(SP, 9); @@ -2140,6 +2368,10 @@ =end original +The tradeoff is that one needs to calculate the number of return values +in advance (though overextending the stack will not typically hurt +anything but memory consumption). +(TBT) =begin original @@ -2149,6 +2381,10 @@ =end original +Similarly, in the failure branch we could use C<PUSHs> I<without> extending +the stack: the Perl function reference comes to an XSUB on the stack, thus +the stack is I<always> large enough to take one return value. +(TBT) =back @@ -2162,6 +2398,10 @@ =end original +In this example, we will accept a reference to an array as an input +parameter, and return a reference to an array of hashes. This will +demonstrate manipulation of complex Perl data types from an XSUB. +(TBT) =begin original @@ -2173,6 +2413,12 @@ =end original +This extension is somewhat contrived. It is based on the code in +the previous example. It calls the statfs function multiple times, +accepting a reference to an array of filenames as input, and returning +a reference to an array of hashes containing the data for each of the +filesystems. +(TBT) =begin original @@ -2181,6 +2427,9 @@ =end original +Return to the Mytest directory and add the following code to the end of +Mytest.xs: +(TBT) SV * multi_statfs(paths) @@ -2233,6 +2482,9 @@ =end original +And add the following code to test.pl, while incrementing the "1..11" +string in the BEGIN block to "1..13": +(TBT) $results = Mytest::multi_statfs([ '/', '/blech' ]); print ((ref $results->[0]) ? "ok 12\n" : "not ok 12\n"); @@ -2246,6 +2498,8 @@ =end original +There are a number of new concepts introduced here, described below: +(TBT) =over 4 @@ -2261,6 +2515,12 @@ =end original +This function does not use a typemap. Instead, we declare it as accepting +one SV* (scalar) parameter, and returning an SV* value, and we take care of +populating these scalars within the code. Because we are only returning +one value, we don't need a C<PPCODE:> directive - instead, we use C<CODE:> +and C<OUTPUT:> directives. +(TBT) =item * @@ -2278,6 +2538,16 @@ =end original +When dealing with references, it is important to handle them with caution. +The C<INIT:> block first checks that +C<SvROK> returns true, which indicates that paths is a valid reference. It +then verifies that the object referenced by paths is an array, using C<SvRV> +to dereference paths, and C<SvTYPE> to discover its type. As an added test, +it checks that the array referenced by paths is non-empty, using the C<av_len> +function (which returns -1 if the array is empty). The XSRETURN_UNDEF macro +is used to abort the XSUB and return the undefined value whenever all three of +these conditions are not met. +(TBT) =item * @@ -2292,6 +2562,13 @@ =end original +We manipulate several arrays in this XSUB. Note that an array is represented +internally by an AV* pointer. The functions and macros for manipulating +arrays are similar to the functions in Perl: C<av_len> returns the highest +index in an AV*, much like $#array; C<av_fetch> fetches a single scalar value +from an array, given its index; C<av_push> pushes a scalar value onto the +end of the array, automatically extending the array as necessary. +(TBT) =begin original @@ -2304,6 +2581,13 @@ =end original +Specifically, we read pathnames one at a time from the input array, and +store the results in an output array (results) in the same order. If +statfs fails, the element pushed onto the return array is the value of +errno after the failure. If statfs succeeds, though, the value pushed +onto the return array is a reference to a hash containing some of the +information in the statfs structure. +(TBT) =begin original @@ -2313,6 +2597,10 @@ =end original +As with the return stack, it would be possible (and a small performance win) +to pre-extend the return array before pushing data into it, since we know +how many elements we will return: +(TBT) av_extend(results, numpaths); @@ -2328,6 +2616,12 @@ =end original +We are performing only one hash operation in this function, which is storing +a new scalar under a key using C<hv_store>. A hash is represented by an HV* +pointer. Like arrays, the functions for manipulating hashes from an XSUB +mirror the functionality available from Perl. See L<perlguts> and L<perlapi> +for details. +(TBT) =item * @@ -2342,6 +2636,13 @@ =end original +To create a reference, we use the C<newRV> function. Note that you can +cast an AV* or an HV* to type SV* in this case (and many others). This +allows you to take references to arrays, hashes and scalars with the same +function. Conversely, the C<SvRV> function always returns an SV*, which may +need to be cast to the appropriate type if it is something other than a +scalar (check with C<SvTYPE>). +(TBT) =item * @@ -2352,6 +2653,9 @@ =end original +At this point, xsubpp is doing very little work - the differences between +Mytest.xs and Mytest.c are minimal. +(TBT) =back @@ -2363,6 +2667,8 @@ =end original +XPUSH args AND set RETVAL AND assign return value to array +(TBT) =head2 EXAMPLE 8 (Coming Soon) @@ -2372,6 +2678,8 @@ =end original +Setting $! +(TBT) =head2 EXAMPLE 9 Passing open files to XSes @@ -2382,6 +2690,9 @@ =end original +You would think passing files to an XS is difficult, with all the +typeglobs and stuff. Well, it isn't. +(TBT) =begin original @@ -2390,6 +2701,9 @@ =end original +Suppose that for some strange reason we need a wrapper around the +standard C library function C<fputs()>. This is all we need: +(TBT) #define PERLIO_NOT_STDIO 0 #include "EXTERN.h" @@ -2409,6 +2723,8 @@ =end original +The real work is done in the standard typemap. +(TBT) =begin original @@ -2417,6 +2733,9 @@ =end original +B<But> you loose all the fine stuff done by the perlio layers. This +calls the stdio function C<fputs()>, which knows nothing about them. +(TBT) =begin original @@ -2429,6 +2748,13 @@ =end original +The standard typemap offers three variants of PerlIO *: +C<InputStream> (T_IN), C<InOutStream> (T_INOUT) and C<OutputStream> +(T_OUT). A bare C<PerlIO *> is considered a T_INOUT. If it matters +in your code (see below for why it might) #define or typedef +one of the specific names and use that as the argument or result +type in your XS file. +(TBT) =begin original @@ -2438,6 +2764,10 @@ =end original +The standard typemap does not contain PerlIO * before perl 5.7, +but it has the three stream variants. Using a PerlIO * directly +is not backwards compatible unless you provide your own typemap. +(TBT) =begin original @@ -2447,6 +2777,10 @@ =end original +For streams coming I<from> perl the main difference is that +C<OutputStream> will get the output PerlIO * - which may make +a difference on a socket. Like in our example... +(TBT) =begin original @@ -2459,6 +2793,13 @@ =end original +For streams being handed I<to> perl a new file handle is created +(i.e. a reference to a new glob) and associated with the PerlIO * +provided. If the read/write state of the PerlIO * is not correct then you +may get errors or warnings from when the file handle is used. +So if you opened the PerlIO * as "w" it should really be an +C<OutputStream> if open as "r" it should be an C<InputStream>. +(TBT) =begin original @@ -2467,6 +2808,9 @@ =end original +Now, suppose you want to use perlio layers in your XS. We'll use the +perlio C<PerlIO_puts()> function as an example. +(TBT) =begin original @@ -2475,6 +2819,9 @@ =end original +In the C part of the XS file (above the first MODULE line) you +have +(TBT) #define OutputStream PerlIO * or @@ -2487,6 +2834,8 @@ =end original +And this is the XS code: +(TBT) int perlioputs(s, stream) @@ -2504,6 +2853,9 @@ =end original +We have to use a C<CODE> section because C<PerlIO_puts()> has the arguments +reversed compared to C<fputs()>, and we want to keep the arguments the same. +(TBT) =begin original @@ -2513,6 +2865,10 @@ =end original +Wanting to explore this thoroughly, we want to use the stdio C<fputs()> +on a PerlIO *. This means we have to ask the perlio system for a stdio +C<FILE *>: +(TBT) int perliofputs(s, stream) @@ -2541,6 +2897,14 @@ =end original +Note: C<PerlIO_findFILE()> will search the layers for a stdio +layer. If it can't find one, it will call C<PerlIO_exportFILE()> to +generate a new stdio C<FILE>. Please only call C<PerlIO_exportFILE()> if +you want a I<new> C<FILE>. It will generate one on each call and push a +new stdio layer. So don't call it repeatedly on the same +file. C<PerlIO()>_findFILE will retrieve the stdio layer once it has been +generated by C<PerlIO_exportFILE()>. +(TBT) =begin original @@ -2549,6 +2913,9 @@ =end original +This applies to the perlio system only. For versions before 5.7, +C<PerlIO_exportFILE()> is equivalent to C<PerlIO_findFILE()>. +(TBT) =head2 Troubleshooting these Examples @@ -2559,6 +2926,9 @@ =end original +As mentioned at the top of this document, if you are having problems with +these example extensions, you might see if any of these help you. +(TBT) =over 4 @@ -2656,6 +3026,8 @@ =end original +Dean Roehrich, Ilya Zakharevich, Andreas Koenig, Tim Bunce によるレビューと +助力を受けました。 =begin original @@ -2664,6 +3036,8 @@ =end original +PerlIO の素材は Lupe Christoph によって提供され、Nick Ing-Simmons によって +明確化されたものです。 =head2 Last Changed @@ -2675,3 +3049,11 @@ 2002/05/08 + +=begin meta + +Created: KIMURA Koichi +Updated: Kentaro Shirakata <argra****@ub32*****> + +=end meta +