Integrate from macperl:
[p5sagit/p5-mst-13.2.git] / lib / ExtUtils / Constant.pm
CommitLineData
af6c647e 1package ExtUtils::Constant;
8ac27563 2use vars qw (@ISA $VERSION %XS_Constant %XS_TypeSet @EXPORT_OK %EXPORT_TAGS);
6557ab03 3$VERSION = '0.12';
af6c647e 4
5=head1 NAME
6
7ExtUtils::Constant - generate XS code to import C header constants
8
9=head1 SYNOPSIS
10
0552bf3a 11 use ExtUtils::Constant qw (WriteConstants);
12 WriteConstants(
13 NAME => 'Foo',
14 NAMES => [qw(FOO BAR BAZ)],
0552bf3a 15 );
16 # Generates wrapper code to make the values of the constants FOO BAR BAZ
17 # available to perl
af6c647e 18
19=head1 DESCRIPTION
20
21ExtUtils::Constant facilitates generating C and XS wrapper code to allow
22perl modules to AUTOLOAD constants defined in C library header files.
23It is principally used by the C<h2xs> utility, on which this code is based.
24It doesn't contain the routines to scan header files to extract these
25constants.
26
27=head1 USAGE
28
0552bf3a 29Generally one only needs to call the C<WriteConstants> function, and then
30
1cb0fb50 31 #include "const-c.inc"
0552bf3a 32
33in the C section of C<Foo.xs>
34
1cb0fb50 35 INCLUDE const-xs.inc
0552bf3a 36
37in the XS section of C<Foo.xs>.
38
39For greater flexibility use C<constant_types()>, C<C_constant> and
40C<XS_constant>, with which C<WriteConstants> is implemented.
af6c647e 41
42Currently this module understands the following types. h2xs may only know
43a subset. The sizes of the numeric types are chosen by the C<Configure>
44script at compile time.
45
46=over 4
47
48=item IV
49
50signed integer, at least 32 bits.
51
52=item UV
53
54unsigned integer, the same size as I<IV>
55
56=item NV
57
58floating point type, probably C<double>, possibly C<long double>
59
60=item PV
61
62NUL terminated string, length will be determined with C<strlen>
63
64=item PVN
65
66A fixed length thing, given as a [pointer, length] pair. If you know the
67length of a string at compile time you may use this instead of I<PV>
68
9a7df4f2 69=item SV
cea00dc5 70
71A B<mortal> SV.
72
3414cef0 73=item YES
74
75Truth. (C<PL_sv_yes>) The value is not needed (and ignored).
76
77=item NO
78
79Defined Falsehood. (C<PL_sv_no>) The value is not needed (and ignored).
80
81=item UNDEF
82
83C<undef>. The value of the macro is not needed.
84
af6c647e 85=back
86
87=head1 FUNCTIONS
88
89=over 4
90
91=cut
92
d7f97632 93if ($] >= 5.006) {
94 eval "use warnings; 1" or die $@;
95}
af6c647e 96use strict;
97use Carp;
98
99use Exporter;
af6c647e 100use Text::Wrap;
101$Text::Wrap::huge = 'overflow';
102$Text::Wrap::columns = 80;
103
104@ISA = 'Exporter';
af6c647e 105
106%EXPORT_TAGS = ( 'all' => [ qw(
107 XS_constant constant_types return_clause memEQ_clause C_stringify
9a7df4f2 108 C_constant autoload WriteConstants WriteMakefileSnippet
af6c647e 109) ] );
110
111@EXPORT_OK = ( @{ $EXPORT_TAGS{'all'} } );
112
6557ab03 113# '' is used as a flag to indicate non-ascii macro names, and hence the need
114# to pass in the utf8 on/off flag.
af6c647e 115%XS_Constant = (
6557ab03 116 '' => '',
cea00dc5 117 IV => 'PUSHi(iv)',
118 UV => 'PUSHu((UV)iv)',
119 NV => 'PUSHn(nv)',
120 PV => 'PUSHp(pv, strlen(pv))',
121 PVN => 'PUSHp(pv, iv)',
122 SV => 'PUSHs(sv)',
123 YES => 'PUSHs(&PL_sv_yes)',
124 NO => 'PUSHs(&PL_sv_no)',
19d75eda 125 UNDEF => '', # implicit undef
af6c647e 126);
127
128%XS_TypeSet = (
cea00dc5 129 IV => '*iv_return =',
130 UV => '*iv_return = (IV)',
131 NV => '*nv_return =',
132 PV => '*pv_return =',
133 PVN => ['*pv_return =', '*iv_return = (IV)'],
134 SV => '*sv_return = ',
19d75eda 135 YES => undef,
136 NO => undef,
137 UNDEF => undef,
af6c647e 138);
139
140
141=item C_stringify NAME
142
6557ab03 143A function which returns a 7 bit ASCII correctly \ escaped version of the
144string passed suitable for C's "" or ''. It will die if passed Unicode
145characters.
af6c647e 146
147=cut
148
149# Hopefully make a happy C identifier.
150sub C_stringify {
151 local $_ = shift;
6d79cad2 152 return unless defined $_;
6557ab03 153 confess "Wide character in '$_' intended as a C identifier" if tr/\0-\377//c;
af6c647e 154 s/\\/\\\\/g;
155 s/([\"\'])/\\$1/g; # Grr. fix perl mode.
6d79cad2 156 s/\n/\\n/g; # Ensure newlines don't end up in octal
157 s/\r/\\r/g;
3414cef0 158 s/\t/\\t/g;
159 s/\f/\\f/g;
160 s/\a/\\a/g;
6557ab03 161 s/([^\0-\177])/sprintf "\\%03o", ord $1/ge;
d7f97632 162 unless ($] < 5.006) {
6557ab03 163 # This will elicit a warning on 5.005_03 about [: :] being reserved unless
164 # I cheat
165 my $cheat = '([[:^print:]])';
166 s/$cheat/sprintf "\\%03o", ord $1/ge;
167 } else {
168 require POSIX;
169 s/([^A-Za-z0-9_])/POSIX::isprint($1) ? $1 : sprintf "\\%03o", ord $1/ge;
170 }
171 $_;
172}
173
174=item perl_stringify NAME
175
176A function which returns a 7 bit ASCII correctly \ escaped version of the
177string passed suitable for a perl "" string.
178
179=cut
180
181# Hopefully make a happy perl identifier.
182sub perl_stringify {
183 local $_ = shift;
184 return unless defined $_;
185 s/\\/\\\\/g;
186 s/([\"\'])/\\$1/g; # Grr. fix perl mode.
187 s/\n/\\n/g; # Ensure newlines don't end up in octal
188 s/\r/\\r/g;
189 s/\t/\\t/g;
190 s/\f/\\f/g;
191 s/\a/\\a/g;
192 s/([^\0-\177])/sprintf "\\x{%X}", ord $1/ge;
193 unless ($] < 5.006) {
194 # This will elicit a warning on 5.005_03 about [: :] being reserved unless
d7f97632 195 # I cheat
196 my $cheat = '([[:^print:]])';
197 s/$cheat/sprintf "\\%03o", ord $1/ge;
198 } else {
199 require POSIX;
200 s/([^A-Za-z0-9_])/POSIX::isprint($1) ? $1 : sprintf "\\%03o", ord $1/ge;
201 }
af6c647e 202 $_;
203}
204
205=item constant_types
206
207A function returning a single scalar with C<#define> definitions for the
208constants used internally between the generated C and XS functions.
209
210=cut
211
212sub constant_types () {
213 my $start = 1;
214 my @lines;
215 push @lines, "#define PERL_constant_NOTFOUND\t$start\n"; $start++;
216 push @lines, "#define PERL_constant_NOTDEF\t$start\n"; $start++;
217 foreach (sort keys %XS_Constant) {
6557ab03 218 next if $_ eq '';
af6c647e 219 push @lines, "#define PERL_constant_IS$_\t$start\n"; $start++;
220 }
221 push @lines, << 'EOT';
222
223#ifndef NVTYPE
224typedef double NV; /* 5.6 and later define NVTYPE, and typedef NV to it. */
225#endif
d7f97632 226#ifndef aTHX_
227#define aTHX_ /* 5.6 or later define this for threading support. */
228#endif
229#ifndef pTHX_
230#define pTHX_ /* 5.6 or later define this for threading support. */
231#endif
af6c647e 232EOT
233
234 return join '', @lines;
235}
236
237=item memEQ_clause NAME, CHECKED_AT, INDENT
238
239A function to return a suitable C C<if> statement to check whether I<NAME>
240is equal to the C variable C<name>. If I<CHECKED_AT> is defined, then it
241is used to avoid C<memEQ> for short names, or to generate a comment to
242highlight the position of the character in the C<switch> statement.
243
244=cut
245
246sub memEQ_clause {
247# if (memEQ(name, "thingy", 6)) {
248 # Which could actually be a character comparison or even ""
249 my ($name, $checked_at, $indent) = @_;
250 $indent = ' ' x ($indent || 4);
251 my $len = length $name;
252
253 if ($len < 2) {
254 return $indent . "{\n" if (defined $checked_at and $checked_at == 0);
255 # We didn't switch, drop through to the code for the 2 character string
256 $checked_at = 1;
257 }
258 if ($len < 3 and defined $checked_at) {
259 my $check;
260 if ($checked_at == 1) {
261 $check = 0;
262 } elsif ($checked_at == 0) {
263 $check = 1;
264 }
265 if (defined $check) {
266 my $char = C_stringify (substr $name, $check, 1);
267 return $indent . "if (name[$check] == '$char') {\n";
268 }
269 }
270 # Could optimise a memEQ on 3 to 2 single character checks here
271 $name = C_stringify ($name);
272 my $body = $indent . "if (memEQ(name, \"$name\", $len)) {\n";
273 $body .= $indent . "/* ". (' ' x $checked_at) . '^'
274 . (' ' x ($len - $checked_at + length $len)) . " */\n"
275 if defined $checked_at;
276 return $body;
277}
278
cea00dc5 279=item assign INDENT, TYPE, PRE, POST, VALUE...
6d79cad2 280
281A function to return a suitable assignment clause. If I<TYPE> is aggregate
282(eg I<PVN> expects both pointer and length) then there should be multiple
cea00dc5 283I<VALUE>s for the components. I<PRE> and I<POST> if defined give snippets
6557ab03 284of C code to proceed and follow the assignment. I<PRE> will be at the start
cea00dc5 285of a block, so variables may be defined in it.
6d79cad2 286
287=cut
288
289# Hmm. value undef to to NOTDEF? value () to do NOTFOUND?
290
291sub assign {
292 my $indent = shift;
293 my $type = shift;
cea00dc5 294 my $pre = shift;
295 my $post = shift || '';
6d79cad2 296 my $clause;
cea00dc5 297 my $close;
298 if ($pre) {
299 chomp $pre;
300 $clause = $indent . "{\n$pre";
301 $clause .= ";" unless $pre =~ /;$/;
302 $clause .= "\n";
303 $close = "$indent}\n";
304 $indent .= " ";
305 }
6557ab03 306 confess "undef \$type" unless defined $type;
307 confess "Can't generate code for type $type" unless exists $XS_TypeSet{$type};
3414cef0 308 my $typeset = $XS_TypeSet{$type};
6d79cad2 309 if (ref $typeset) {
310 die "Type $type is aggregate, but only single value given"
311 if @_ == 1;
312 foreach (0 .. $#$typeset) {
313 $clause .= $indent . "$typeset->[$_] $_[$_];\n";
314 }
3414cef0 315 } elsif (defined $typeset) {
6d79cad2 316 die "Aggregate value given for type $type"
317 if @_ > 1;
318 $clause .= $indent . "$typeset $_[0];\n";
319 }
cea00dc5 320 chomp $post;
321 if (length $post) {
322 $clause .= "$post";
323 $clause .= ";" unless $post =~ /;$/;
324 $clause .= "\n";
a2c454fa 325 }
6d79cad2 326 $clause .= "${indent}return PERL_constant_IS$type;\n";
cea00dc5 327 $clause .= $close if $close;
6d79cad2 328 return $clause;
329}
330
5dc6f178 331=item return_clause
332
6557ab03 333return_clause ITEM, INDENT
af6c647e 334
6557ab03 335A function to return a suitable C<#ifdef> clause. I<ITEM> is a hashref
336(as passed to C<C_constant> and C<match_clause>. I<INDENT> is the number
337of spaces to indent, defaulting to 6.
af6c647e 338
339=cut
340
6557ab03 341sub return_clause ($$) {
af6c647e 342##ifdef thingy
343# *iv_return = thingy;
344# return PERL_constant_ISIV;
345##else
346# return PERL_constant_NOTDEF;
347##endif
6557ab03 348 my ($item, $indent) = @_;
349
350 my ($name, $value, $macro, $default, $pre, $post, $def_pre, $def_post, $type)
351 = @$item{qw (name value macro default pre post def_pre def_post type)};
352 $value = $name unless defined $value;
353 $macro = $name unless defined $macro;
354
af6c647e 355 $macro = $value unless defined $macro;
356 $indent = ' ' x ($indent || 6);
6557ab03 357 unless ($type) {
358 # use Data::Dumper; print STDERR Dumper ($item);
359 confess "undef \$type";
360 }
af6c647e 361
6d79cad2 362 my $clause;
af6c647e 363
6d79cad2 364 ##ifdef thingy
365 if (ref $macro) {
366 $clause = $macro->[0];
72f7b9a1 367 } elsif ($macro ne "1") {
6d79cad2 368 $clause = "#ifdef $macro\n";
af6c647e 369 }
6d79cad2 370
371 # *iv_return = thingy;
372 # return PERL_constant_ISIV;
cea00dc5 373 $clause .= assign ($indent, $type, $pre, $post,
374 ref $value ? @$value : $value);
6d79cad2 375
72f7b9a1 376 if (ref $macro or $macro ne "1") {
377 ##else
378 $clause .= "#else\n";
a2c454fa 379
72f7b9a1 380 # return PERL_constant_NOTDEF;
381 if (!defined $default) {
382 $clause .= "${indent}return PERL_constant_NOTDEF;\n";
383 } else {
384 my @default = ref $default ? @$default : $default;
385 $type = shift @default;
386 $clause .= assign ($indent, $type, $def_pre, $def_post, @default);
387 }
6d79cad2 388
72f7b9a1 389 ##endif
390 if (ref $macro) {
391 $clause .= $macro->[1];
392 } else {
393 $clause .= "#endif\n";
394 }
6d79cad2 395 }
6557ab03 396 return $clause;
397}
398
399=pod
400
401XXX document me
402
403=cut
404
405sub match_clause {
406 # $offset defined if we have checked an offset.
407 my ($item, $offset, $indent) = @_;
408 $indent = ' ' x ($indent || 4);
409 my $body = '';
410 my ($no, $yes, $either, $name, $inner_indent);
411 if (ref $item eq 'ARRAY') {
412 ($yes, $no) = @$item;
413 $either = $yes || $no;
414 confess "$item is $either expecting hashref in [0] || [1]"
415 unless ref $either eq 'HASH';
416 $name = $either->{name};
417 } else {
418 confess "$item->{name} has utf8 flag '$item->{utf8}', should be false"
419 if $item->{utf8};
420 $name = $item->{name};
421 $inner_indent = $indent;
422 }
423
424 $body .= memEQ_clause ($name, $offset, length $indent);
425 if ($yes) {
426 $body .= $indent . " if (utf8) {\n";
427 } elsif ($no) {
428 $body .= $indent . " if (!utf8) {\n";
429 }
430 if ($either) {
431 $body .= return_clause ($either, 4 + length $indent);
432 if ($yes and $no) {
433 $body .= $indent . " } else {\n";
434 $body .= return_clause ($no, 4 + length $indent);
435 }
436 $body .= $indent . " }";
437 } else {
438 $body .= return_clause ($item, 2 + length $indent);
439 }
440 $body .= $indent . "}\n";
af6c647e 441}
442
8ac27563 443=item switch_clause INDENT, NAMELEN, ITEMHASH, ITEM...
444
445An internal function to generate a suitable C<switch> clause, called by
446C<C_constant> I<ITEM>s are in the hash ref format as given in the description
447of C<C_constant>, and must all have the names of the same length, given by
448I<NAMELEN> (This is not checked). I<ITEMHASH> is a reference to a hash,
449keyed by name, values being the hashrefs in the I<ITEM> list.
450(No parameters are modified, and there can be keys in the I<ITEMHASH> that
451are not in the list of I<ITEM>s without causing problems).
452
453=cut
454
455sub switch_clause {
456 my ($indent, $comment, $namelen, $items, @items) = @_;
457 $indent = ' ' x ($indent || 2);
a2c454fa 458
8ac27563 459 my @names = sort map {$_->{name}} @items;
460 my $leader = $indent . '/* ';
461 my $follower = ' ' x length $leader;
462 my $body = $indent . "/* Names all of length $namelen. */\n";
463 if ($comment) {
464 $body = wrap ($leader, $follower, $comment) . "\n";
465 $leader = $follower;
466 }
6557ab03 467 my @safe_names = @names;
468 foreach (@safe_names) {
469 next unless tr/A-Za-z0-9_//c;
470 $_ = '"' . perl_stringify ($_) . '"';
471 # Ensure that the enclosing C comment doesn't end
472 # by turning */ into *" . "/
473 s!\*\/!\*"."/!gs;
474 # gcc -Wall doesn't like finding /* inside a comment
475 s!\/\*!/"."\*!gs;
476 }
477 $body .= wrap ($leader, $follower, join (" ", @safe_names) . " */") . "\n";
8ac27563 478 # Figure out what to switch on.
479 # (RMS, Spread of jump table, Position, Hashref)
480 my @best = (1e38, ~0);
481 foreach my $i (0 .. ($namelen - 1)) {
482 my ($min, $max) = (~0, 0);
483 my %spread;
484 foreach (@names) {
485 my $char = substr $_, $i, 1;
486 my $ord = ord $char;
a2c454fa 487 $max = $ord if $ord > $max;
8ac27563 488 $min = $ord if $ord < $min;
489 push @{$spread{$char}}, $_;
490 # warn "$_ $char";
491 }
492 # I'm going to pick the character to split on that minimises the root
493 # mean square of the number of names in each case. Normally this should
494 # be the one with the most keys, but it may pick a 7 where the 8 has
495 # one long linear search. I'm not sure if RMS or just sum of squares is
496 # actually better.
497 # $max and $min are for the tie-breaker if the root mean squares match.
498 # Assuming that the compiler may be building a jump table for the
499 # switch() then try to minimise the size of that jump table.
500 # Finally use < not <= so that if it still ties the earliest part of
501 # the string wins. Because if that passes but the memEQ fails, it may
502 # only need the start of the string to bin the choice.
503 # I think. But I'm micro-optimising. :-)
504 my $ss;
505 $ss += @$_ * @$_ foreach values %spread;
506 my $rms = sqrt ($ss / keys %spread);
507 if ($rms < $best[0] || ($rms == $best[0] && ($max - $min) < $best[1])) {
508 @best = ($rms, $max - $min, $i, \%spread);
509 }
510 }
511 die "Internal error. Failed to pick a switch point for @names"
512 unless defined $best[2];
513 # use Data::Dumper; print Dumper (@best);
514 my ($offset, $best) = @best[2,3];
515 $body .= $indent . "/* Offset $offset gives the best switch position. */\n";
516 $body .= $indent . "switch (name[$offset]) {\n";
517 foreach my $char (sort keys %$best) {
518 $body .= $indent . "case '" . C_stringify ($char) . "':\n";
519 foreach my $name (sort @{$best->{$char}}) {
520 my $thisone = $items->{$name};
6557ab03 521 # warn "You are here";
522 $body .= match_clause ($thisone, $offset, 2 + length $indent);
8ac27563 523 }
524 $body .= $indent . " break;\n";
525 }
526 $body .= $indent . "}\n";
527 return $body;
528}
529
af6c647e 530=item params WHAT
531
532An internal function. I<WHAT> should be a hashref of types the constant
72f7b9a1 533function will return. I<params> returns a hashref keyed IV NV PV SV to show
534which combination of pointers will be needed in the C argument list.
af6c647e 535
536=cut
537
538sub params {
539 my $what = shift;
540 foreach (sort keys %$what) {
541 warn "ExtUtils::Constant doesn't know how to handle values of type $_" unless defined $XS_Constant{$_};
542 }
72f7b9a1 543 my $params = {};
6557ab03 544 $params->{''} = 1 if $what->{''};
72f7b9a1 545 $params->{IV} = 1 if $what->{IV} || $what->{UV} || $what->{PVN};
546 $params->{NV} = 1 if $what->{NV};
547 $params->{PV} = 1 if $what->{PV} || $what->{PVN};
548 $params->{SV} = 1 if $what->{SV};
549 return $params;
af6c647e 550}
551
a2c454fa 552=item dump_names
0addb26a 553
9a7df4f2 554dump_names DEFAULT_TYPE, TYPES, INDENT, OPTIONS, ITEM...
6d79cad2 555
556An internal function to generate the embedded perl code that will regenerate
9a7df4f2 557the constant subroutines. I<DEFAULT_TYPE>, I<TYPES> and I<ITEM>s are the
558same as for C_constant. I<INDENT> is treated as number of spaces to indent
559by. I<OPTIONS> is a hashref of options. Currently only C<declare_types> is
560recognised. If the value is true a C<$types> is always declared in the perl
561code generated, if defined and false never declared, and if undefined C<$types>
562is only declared if the values in I<TYPES> as passed in cannot be inferred from
563I<DEFAULT_TYPES> and the I<ITEM>s.
6d79cad2 564
565=cut
566
567sub dump_names {
9a7df4f2 568 my ($default_type, $what, $indent, $options, @items) = @_;
569 my $declare_types = $options->{declare_types};
570 $indent = ' ' x ($indent || 0);
571
572 my $result;
573 my (@simple, @complex, %used_types);
6d79cad2 574 foreach (@items) {
9a7df4f2 575 my $type;
576 if (ref $_) {
577 $type = $_->{type} || $default_type;
6557ab03 578 if ($_->{utf8}) {
579 # For simplicity always skip the bytes case, and reconstitute this entry
580 # from its utf8 twin.
581 next if $_->{utf8} eq 'no';
582 # Copy the hashref, as we don't want to mess with the caller's hashref.
583 $_ = {%$_};
584 utf8::decode ($_->{name});
585 delete $_->{utf8};
586 }
9a7df4f2 587 } else {
588 $_ = {name=>$_};
589 $type = $default_type;
590 }
591 $used_types{$type}++;
6d79cad2 592 if ($type eq $default_type and 0 == ($_->{name} =~ tr/A-Za-z0-9_//c)
593 and !defined ($_->{macro}) and !defined ($_->{value})
cea00dc5 594 and !defined ($_->{default}) and !defined ($_->{pre})
595 and !defined ($_->{post}) and !defined ($_->{def_pre})
596 and !defined ($_->{def_post})) {
6d79cad2 597 # It's the default type, and the name consists only of A-Za-z0-9_
598 push @simple, $_->{name};
599 } else {
600 push @complex, $_;
601 }
602 }
6d79cad2 603
9a7df4f2 604 if (!defined $declare_types) {
605 # Do they pass in any types we weren't already using?
606 foreach (keys %$what) {
607 next if $used_types{$_};
608 $declare_types++; # Found one in $what that wasn't used.
609 last; # And one is enough to terminate this loop
610 }
611 }
612 if ($declare_types) {
613 $result = $indent . 'my $types = {map {($_, 1)} qw('
614 . join (" ", sort keys %$what) . ")};\n";
615 }
616 $result .= wrap ($indent . "my \@names = (qw(",
617 $indent . " ", join (" ", sort @simple) . ")");
6d79cad2 618 if (@complex) {
619 foreach my $item (sort {$a->{name} cmp $b->{name}} @complex) {
6557ab03 620 my $name = perl_stringify $item->{name};
9a7df4f2 621 my $line = ",\n$indent {name=>\"$name\"";
6d79cad2 622 $line .= ", type=>\"$item->{type}\"" if defined $item->{type};
cea00dc5 623 foreach my $thing (qw (macro value default pre post def_pre def_post)) {
624 my $value = $item->{$thing};
625 if (defined $value) {
626 if (ref $value) {
627 $line .= ", $thing=>[\""
6557ab03 628 . join ('", "', map {perl_stringify $_} @$value) . '"]';
cea00dc5 629 } else {
6557ab03 630 $line .= ", $thing=>\"" . perl_stringify($value) . "\"";
cea00dc5 631 }
6d79cad2 632 }
633 }
634 $line .= "}";
635 # Ensure that the enclosing C comment doesn't end
636 # by turning */ into *" . "/
637 $line =~ s!\*\/!\*" . "/!gs;
3414cef0 638 # gcc -Wall doesn't like finding /* inside a comment
639 $line =~ s!\/\*!/" . "\*!gs;
6d79cad2 640 $result .= $line;
641 }
642 }
643 $result .= ");\n";
644
9a7df4f2 645 $result;
646}
647
648
649=item dogfood
650
651dogfood PACKAGE, SUBNAME, DEFAULT_TYPE, TYPES, INDENT, BREAKOUT, ITEM...
652
653An internal function to generate the embedded perl code that will regenerate
654the constant subroutines. Parameters are the same as for C_constant.
655
656=cut
657
658sub dogfood {
659 my ($package, $subname, $default_type, $what, $indent, $breakout, @items)
660 = @_;
661 my $result = <<"EOT";
662 /* When generated this function returned values for the list of names given
663 in this section of perl code. Rather than manually editing these functions
664 to add or remove constants, which would result in this comment and section
665 of code becoming inaccurate, we recommend that you edit this section of
666 code, and use it to regenerate a new set of constant functions which you
667 then use to replace the originals.
668
669 Regenerate these constant functions by feeding this entire source file to
670 perl -x
671
672#!$^X -w
673use ExtUtils::Constant qw (constant_types C_constant XS_constant);
674
675EOT
676 $result .= dump_names ($default_type, $what, 0, {declare_types=>1}, @items);
6d79cad2 677 $result .= <<'EOT';
678
679print constant_types(); # macro defs
680EOT
6557ab03 681 $package = perl_stringify($package);
6d79cad2 682 $result .=
683 "foreach (C_constant (\"$package\", '$subname', '$default_type', \$types, ";
684 # The form of the indent parameter isn't defined. (Yet)
685 if (defined $indent) {
686 require Data::Dumper;
687 $Data::Dumper::Terse=1;
8ac27563 688 $Data::Dumper::Terse=1; # Not used once. :-)
6d79cad2 689 chomp ($indent = Data::Dumper::Dumper ($indent));
690 $result .= $indent;
691 } else {
692 $result .= 'undef';
693 }
8ac27563 694 $result .= ", $breakout" . ', @names) ) {
6d79cad2 695 print $_, "\n"; # C constant subs
696}
697print "#### XS Section:\n";
698print XS_constant ("' . $package . '", $types);
699__END__
700 */
701
702';
a2c454fa 703
6d79cad2 704 $result;
705}
706
a2c454fa 707=item C_constant
0addb26a 708
8ac27563 709C_constant PACKAGE, SUBNAME, DEFAULT_TYPE, TYPES, INDENT, BREAKOUT, ITEM...
af6c647e 710
711A function that returns a B<list> of C subroutine definitions that return
712the value and type of constants when passed the name by the XS wrapper.
713I<ITEM...> gives a list of constant names. Each can either be a string,
714which is taken as a C macro name, or a reference to a hash with the following
715keys
716
717=over 8
718
719=item name
720
721The name of the constant, as seen by the perl code.
722
723=item type
724
725The type of the constant (I<IV>, I<NV> etc)
726
727=item value
728
729A C expression for the value of the constant, or a list of C expressions if
730the type is aggregate. This defaults to the I<name> if not given.
731
732=item macro
733
734The C pre-processor macro to use in the C<#ifdef>. This defaults to the
6d79cad2 735I<name>, and is mainly used if I<value> is an C<enum>. If a reference an
736array is passed then the first element is used in place of the C<#ifdef>
737line, and the second element in place of the C<#endif>. This allows
738pre-processor constructions such as
739
740 #if defined (foo)
741 #if !defined (bar)
742 ...
743 #endif
744 #endif
745
746to be used to determine if a constant is to be defined.
747
72f7b9a1 748A "macro" 1 signals that the constant is always defined, so the C<#if>/C<#endif>
749test is omitted.
750
6d79cad2 751=item default
752
753Default value to use (instead of C<croak>ing with "your vendor has not
754defined...") to return if the macro isn't defined. Specify a reference to
755an array with type followed by value(s).
af6c647e 756
cea00dc5 757=item pre
758
759C code to use before the assignment of the value of the constant. This allows
760you to use temporary variables to extract a value from part of a C<struct>
761and return this as I<value>. This C code is places at the start of a block,
762so you can declare variables in it.
763
764=item post
765
766C code to place between the assignment of value (to a temporary) and the
767return from the function. This allows you to clear up anything in I<pre>.
768Rarely needed.
769
770=item def_pre
771=item def_post
772
773Equivalents of I<pre> and I<post> for the default value.
774
6557ab03 775=item utf8
776
777Generated internally. Is zero or undefined if name is 7 bit ASCII,
778"no" if the name is 8 bit (and so should only match if SvUTF8() is false),
779"yes" if the name is utf8 encoded.
780
781The internals automatically clone any name with characters 128-255 but none
782256+ (ie one that could be either in bytes or utf8) into a second entry
783which is utf8 encoded.
784
af6c647e 785=back
786
6d79cad2 787I<PACKAGE> is the name of the package, and is only used in comments inside the
788generated C code.
789
790The next 5 arguments can safely be given as C<undef>, and are mainly used
af6c647e 791for recursion. I<SUBNAME> defaults to C<constant> if undefined.
792
793I<DEFAULT_TYPE> is the type returned by C<ITEM>s that don't specify their
794type. In turn it defaults to I<IV>. I<TYPES> should be given either as a comma
795separated list of types that the C subroutine C<constant> will generate or as
796a reference to a hash. I<DEFAULT_TYPE> will be added to the list if not
797present, as will any types given in the list of I<ITEM>s. The resultant list
798should be the same list of types that C<XS_constant> is given. [Otherwise
799C<XS_constant> and C<C_constant> may differ in the number of parameters to the
800constant function. I<INDENT> is currently unused and ignored. In future it may
801be used to pass in information used to change the C indentation style used.]
802The best way to maintain consistency is to pass in a hash reference and let
803this function update it.
804
8ac27563 805I<BREAKOUT> governs when child functions of I<SUBNAME> are generated. If there
806are I<BREAKOUT> or more I<ITEM>s with the same length of name, then the code
807to switch between them is placed into a function named I<SUBNAME>_I<LEN>, for
808example C<constant_5> for names 5 characters long. The default I<BREAKOUT> is
8093. A single C<ITEM> is always inlined.
af6c647e 810
811=cut
812
8ac27563 813# The parameter now BREAKOUT was previously documented as:
814#
815# I<NAMELEN> if defined signals that all the I<name>s of the I<ITEM>s are of
816# this length, and that the constant name passed in by perl is checked and
817# also of this length. It is used during recursion, and should be C<undef>
818# unless the caller has checked all the lengths during code generation, and
819# the generated subroutine is only to be called with a name of this length.
820#
821# As you can see it now performs this function during recursion by being a
822# scalar reference.
823
af6c647e 824sub C_constant {
8ac27563 825 my ($package, $subname, $default_type, $what, $indent, $breakout, @items)
826 = @_;
6d79cad2 827 $package ||= 'Foo';
af6c647e 828 $subname ||= 'constant';
829 # I'm not using this. But a hashref could be used for full formatting without
830 # breaking this API
6d79cad2 831 # $indent ||= 0;
72f7b9a1 832
833 my ($namelen, $items);
834 if (ref $breakout) {
835 # We are called recursively. We trust @items to be normalised, $what to
836 # be a hashref, and pinch %$items from our parent to save recalculation.
837 ($namelen, $items) = @$breakout;
838 } else {
839 $breakout ||= 3;
840 $default_type ||= 'IV';
841 if (!ref $what) {
842 # Convert line of the form IV,UV,NV to hash
843 $what = {map {$_ => 1} split /,\s*/, ($what || '')};
844 # Figure out what types we're dealing with, and assign all unknowns to the
845 # default type
af6c647e 846 }
6557ab03 847 my @new_items;
848 foreach my $orig (@items) {
849 my ($name, $item);
850 if (ref $orig) {
72f7b9a1 851 # Make a copy which is a normalised version of the ref passed in.
6557ab03 852 $name = $orig->{name};
853 my ($type, $macro, $value) = @$orig{qw (type macro value)};
72f7b9a1 854 $type ||= $default_type;
855 $what->{$type} = 1;
6557ab03 856 $item = {name=>$name, type=>$type};
72f7b9a1 857
858 undef $macro if defined $macro and $macro eq $name;
6557ab03 859 $item->{macro} = $macro if defined $macro;
72f7b9a1 860 undef $value if defined $value and $value eq $name;
6557ab03 861 $item->{value} = $value if defined $value;
72f7b9a1 862 foreach my $key (qw(default pre post def_pre def_post)) {
863 my $value = $orig->{$key};
6557ab03 864 $item->{$key} = $value if defined $value;
72f7b9a1 865 # warn "$key $value";
866 }
867 } else {
6557ab03 868 $name = $orig;
869 $item = {name=>$name, type=>$default_type};
72f7b9a1 870 $what->{$default_type} = 1;
871 }
6557ab03 872 warn "ExtUtils::Constant doesn't know how to handle values of type $_ used in macro $name" unless defined $XS_Constant{$item->{type}};
873 if ($name !~ tr/\0-\177//c) {
874 # No characters outside 7 bit ASCII.
875 if (exists $items->{$name}) {
876 die "Multiple definitions for macro $name";
877 }
878 $items->{$name} = $item;
879 } else {
880 # No characters outside 8 bit. This is hardest.
881 if (exists $items->{$name} and ref $items->{$name} ne 'ARRAY') {
882 confess "Unexpected ASCII definition for macro $name";
883 }
884 if ($name !~ tr/\0-\377//c) {
885 $item->{utf8} = 'no';
886 $items->{$name}[1] = $item;
887 push @new_items, $item;
888 # Copy item, to create the utf8 variant.
889 $item = {%$item};
890 }
891 # Encode the name as utf8 bytes.
892 utf8::encode($name);
893 if ($items->{$name}[0]) {
894 die "Multiple definitions for macro $name";
895 }
896 $item->{utf8} = 'yes';
897 $item->{name} = $name;
898 $items->{$name}[0] = $item;
899 # We have need for the utf8 flag.
900 $what->{''} = 1;
72f7b9a1 901 }
6557ab03 902 push @new_items, $item;
af6c647e 903 }
6557ab03 904 @items = @new_items;
905 # use Data::Dumper; print Dumper @items;
af6c647e 906 }
72f7b9a1 907 my $params = params ($what);
af6c647e 908
a2c454fa 909 my ($body, @subs) = "static int\n$subname (pTHX_ const char *name";
af6c647e 910 $body .= ", STRLEN len" unless defined $namelen;
6557ab03 911 $body .= ", int utf8" if $params->{''};
72f7b9a1 912 $body .= ", IV *iv_return" if $params->{IV};
913 $body .= ", NV *nv_return" if $params->{NV};
914 $body .= ", const char **pv_return" if $params->{PV};
915 $body .= ", SV **sv_return" if $params->{SV};
af6c647e 916 $body .= ") {\n";
917
6d79cad2 918 if (defined $namelen) {
919 # We are a child subroutine. Print the simple description
8ac27563 920 my $comment = 'When generated this function returned values for the list'
921 . ' of names given here. However, subsequent manual editing may have'
922 . ' added or removed some.';
72f7b9a1 923 $body .= switch_clause (2, $comment, $namelen, $items, @items);
af6c647e 924 } else {
925 # We are the top level.
926 $body .= " /* Initially switch on the length of the name. */\n";
9a7df4f2 927 $body .= dogfood ($package, $subname, $default_type, $what, $indent,
928 $breakout, @items);
af6c647e 929 $body .= " switch (len) {\n";
930 # Need to group names of the same length
931 my @by_length;
932 foreach (@items) {
933 push @{$by_length[length $_->{name}]}, $_;
934 }
935 foreach my $i (0 .. $#by_length) {
936 next unless $by_length[$i]; # None of this length
937 $body .= " case $i:\n";
938 if (@{$by_length[$i]} == 1) {
6557ab03 939 $body .= match_clause ($by_length[$i]->[0]);
8ac27563 940 } elsif (@{$by_length[$i]} < $breakout) {
72f7b9a1 941 $body .= switch_clause (4, '', $i, $items, @{$by_length[$i]});
af6c647e 942 } else {
72f7b9a1 943 # Only use the minimal set of parameters actually needed by the types
944 # of the names of this length.
945 my $what = {};
946 foreach (@{$by_length[$i]}) {
947 $what->{$_->{type}} = 1;
6557ab03 948 $what->{''} = 1 if $_->{utf8};
72f7b9a1 949 }
950 $params = params ($what);
951 push @subs, C_constant ($package, "${subname}_$i", $default_type, $what,
952 $indent, [$i, $items], @{$by_length[$i]});
a2c454fa 953 $body .= " return ${subname}_$i (aTHX_ name";
6557ab03 954 $body .= ", utf8" if $params->{''};
72f7b9a1 955 $body .= ", iv_return" if $params->{IV};
956 $body .= ", nv_return" if $params->{NV};
957 $body .= ", pv_return" if $params->{PV};
958 $body .= ", sv_return" if $params->{SV};
af6c647e 959 $body .= ");\n";
960 }
961 $body .= " break;\n";
962 }
963 $body .= " }\n";
964 }
965 $body .= " return PERL_constant_NOTFOUND;\n}\n";
966 return (@subs, $body);
967}
968
969=item XS_constant PACKAGE, TYPES, SUBNAME, C_SUBNAME
970
971A function to generate the XS code to implement the perl subroutine
972I<PACKAGE>::constant used by I<PACKAGE>::AUTOLOAD to load constants.
973This XS code is a wrapper around a C subroutine usually generated by
974C<C_constant>, and usually named C<constant>.
975
976I<TYPES> should be given either as a comma separated list of types that the
977C subroutine C<constant> will generate or as a reference to a hash. It should
978be the same list of types as C<C_constant> was given.
979[Otherwise C<XS_constant> and C<C_constant> may have different ideas about
980the number of parameters passed to the C function C<constant>]
981
982You can call the perl visible subroutine something other than C<constant> if
d1be9408 983you give the parameter I<SUBNAME>. The C subroutine it calls defaults to
af6c647e 984the name of the perl visible subroutine, unless you give the parameter
985I<C_SUBNAME>.
986
987=cut
988
989sub XS_constant {
990 my $package = shift;
991 my $what = shift;
992 my $subname = shift;
993 my $C_subname = shift;
994 $subname ||= 'constant';
995 $C_subname ||= $subname;
996
997 if (!ref $what) {
998 # Convert line of the form IV,UV,NV to hash
999 $what = {map {$_ => 1} split /,\s*/, ($what)};
1000 }
72f7b9a1 1001 my $params = params ($what);
af6c647e 1002 my $type;
1003
1004 my $xs = <<"EOT";
1005void
1006$subname(sv)
1007 PREINIT:
1008#ifdef dXSTARG
1009 dXSTARG; /* Faster if we have it. */
1010#else
1011 dTARGET;
1012#endif
1013 STRLEN len;
1014 int type;
1015EOT
1016
72f7b9a1 1017 if ($params->{IV}) {
af6c647e 1018 $xs .= " IV iv;\n";
1019 } else {
1020 $xs .= " /* IV\t\tiv;\tUncomment this if you need to return IVs */\n";
1021 }
72f7b9a1 1022 if ($params->{NV}) {
af6c647e 1023 $xs .= " NV nv;\n";
1024 } else {
1025 $xs .= " /* NV\t\tnv;\tUncomment this if you need to return NVs */\n";
1026 }
72f7b9a1 1027 if ($params->{PV}) {
af6c647e 1028 $xs .= " const char *pv;\n";
1029 } else {
1030 $xs .=
1031 " /* const char\t*pv;\tUncomment this if you need to return PVs */\n";
1032 }
1033
1034 $xs .= << 'EOT';
1035 INPUT:
1036 SV * sv;
1037 const char * s = SvPV(sv, len);
6557ab03 1038EOT
1039 if ($params->{''}) {
1040 $xs .= << 'EOT';
1041 INPUT:
1042 int utf8 = SvUTF8(sv);
1043EOT
1044 }
1045 $xs .= << 'EOT';
af6c647e 1046 PPCODE:
1047EOT
1048
72f7b9a1 1049 if ($params->{IV} xor $params->{NV}) {
af6c647e 1050 $xs .= << "EOT";
a2c454fa 1051 /* Change this to $C_subname(aTHX_ s, len, &iv, &nv);
af6c647e 1052 if you need to return both NVs and IVs */
1053EOT
1054 }
a2c454fa 1055 $xs .= " type = $C_subname(aTHX_ s, len";
6557ab03 1056 $xs .= ', utf8' if $params->{''};
72f7b9a1 1057 $xs .= ', &iv' if $params->{IV};
1058 $xs .= ', &nv' if $params->{NV};
1059 $xs .= ', &pv' if $params->{PV};
1060 $xs .= ', &sv' if $params->{SV};
af6c647e 1061 $xs .= ");\n";
1062
1063 $xs .= << "EOT";
1064 /* Return 1 or 2 items. First is error message, or undef if no error.
1065 Second, if present, is found value */
1066 switch (type) {
1067 case PERL_constant_NOTFOUND:
1068 sv = sv_2mortal(newSVpvf("%s is not a valid $package macro", s));
6d79cad2 1069 PUSHs(sv);
af6c647e 1070 break;
1071 case PERL_constant_NOTDEF:
1072 sv = sv_2mortal(newSVpvf(
8ac27563 1073 "Your vendor has not defined $package macro %s, used", s));
6d79cad2 1074 PUSHs(sv);
af6c647e 1075 break;
1076EOT
1077
1078 foreach $type (sort keys %XS_Constant) {
6557ab03 1079 # '' marks utf8 flag needed.
1080 next if $type eq '';
af6c647e 1081 $xs .= "\t/* Uncomment this if you need to return ${type}s\n"
1082 unless $what->{$type};
8ac27563 1083 $xs .= " case PERL_constant_IS$type:\n";
1084 if (length $XS_Constant{$type}) {
1085 $xs .= << "EOT";
af6c647e 1086 EXTEND(SP, 1);
1087 PUSHs(&PL_sv_undef);
1088 $XS_Constant{$type};
af6c647e 1089EOT
8ac27563 1090 } else {
1091 # Do nothing. return (), which will be correctly interpreted as
1092 # (undef, undef)
1093 }
1094 $xs .= " break;\n";
af6c647e 1095 unless ($what->{$type}) {
1096 chop $xs; # Yes, another need for chop not chomp.
1097 $xs .= " */\n";
1098 }
1099 }
1100 $xs .= << "EOT";
1101 default:
1102 sv = sv_2mortal(newSVpvf(
8ac27563 1103 "Unexpected return type %d while processing $package macro %s, used",
af6c647e 1104 type, s));
6d79cad2 1105 PUSHs(sv);
af6c647e 1106 }
1107EOT
1108
1109 return $xs;
1110}
1111
1112
6d79cad2 1113=item autoload PACKAGE, VERSION, AUTOLOADER
af6c647e 1114
1115A function to generate the AUTOLOAD subroutine for the module I<PACKAGE>
1116I<VERSION> is the perl version the code should be backwards compatible with.
6d79cad2 1117It defaults to the version of perl running the subroutine. If I<AUTOLOADER>
1118is true, the AUTOLOAD subroutine falls back on AutoLoader::AUTOLOAD for all
1119names that the constant() routine doesn't recognise.
af6c647e 1120
1121=cut
1122
6d79cad2 1123# ' # Grr. syntax highlighters that don't grok pod.
1124
af6c647e 1125sub autoload {
6d79cad2 1126 my ($module, $compat_version, $autoloader) = @_;
af6c647e 1127 $compat_version ||= $];
1128 croak "Can't maintain compatibility back as far as version $compat_version"
1129 if $compat_version < 5;
6d79cad2 1130 my $func = "sub AUTOLOAD {\n"
1131 . " # This AUTOLOAD is used to 'autoload' constants from the constant()\n"
1132 . " # XS function.";
1133 $func .= " If a constant is not found then control is passed\n"
1134 . " # to the AUTOLOAD in AutoLoader." if $autoloader;
1135
1136
1137 $func .= "\n\n"
1138 . " my \$constname;\n";
a2c454fa 1139 $func .=
6d79cad2 1140 " our \$AUTOLOAD;\n" if ($compat_version >= 5.006);
1141
1142 $func .= <<"EOT";
af6c647e 1143 (\$constname = \$AUTOLOAD) =~ s/.*:://;
1144 croak "&${module}::constant not defined" if \$constname eq 'constant';
1145 my (\$error, \$val) = constant(\$constname);
6d79cad2 1146EOT
1147
1148 if ($autoloader) {
1149 $func .= <<'EOT';
1150 if ($error) {
1151 if ($error =~ /is not a valid/) {
1152 $AutoLoader::AUTOLOAD = $AUTOLOAD;
af6c647e 1153 goto &AutoLoader::AUTOLOAD;
1154 } else {
6d79cad2 1155 croak $error;
af6c647e 1156 }
1157 }
6d79cad2 1158EOT
1159 } else {
1160 $func .=
1161 " if (\$error) { croak \$error; }\n";
1162 }
1163
1164 $func .= <<'END';
af6c647e 1165 {
1166 no strict 'refs';
1167 # Fixed between 5.005_53 and 5.005_61
6d79cad2 1168#XXX if ($] >= 5.00561) {
1169#XXX *$AUTOLOAD = sub () { $val };
af6c647e 1170#XXX }
1171#XXX else {
6d79cad2 1172 *$AUTOLOAD = sub { $val };
af6c647e 1173#XXX }
1174 }
6d79cad2 1175 goto &$AUTOLOAD;
af6c647e 1176}
1177
1178END
1179
6d79cad2 1180 return $func;
af6c647e 1181}
0552bf3a 1182
1183
9a7df4f2 1184=item WriteMakefileSnippet
1185
1186WriteMakefileSnippet ATTRIBUTE =E<gt> VALUE [, ...]
1187
d1be9408 1188A function to generate perl code for Makefile.PL that will regenerate
9a7df4f2 1189the constant subroutines. Parameters are named as passed to C<WriteConstants>,
1190with the addition of C<INDENT> to specify the number of leading spaces
1191(default 2).
1192
1193Currently only C<INDENT>, C<NAME>, C<DEFAULT_TYPE>, C<NAMES>, C<C_FILE> and
1194C<XS_FILE> are recognised.
1195
1196=cut
1197
1198sub WriteMakefileSnippet {
1199 my %args = @_;
1200 my $indent = $args{INDENT} || 2;
1201
1202 my $result = <<"EOT";
1203ExtUtils::Constant::WriteConstants(
1204 NAME => '$args{NAME}',
1205 NAMES => \\\@names,
1206 DEFAULT_TYPE => '$args{DEFAULT_TYPE}',
1207EOT
1208 foreach (qw (C_FILE XS_FILE)) {
1209 next unless exists $args{$_};
1210 $result .= sprintf " %-12s => '%s',\n",
1211 $_, $args{$_};
1212 }
1213 $result .= <<'EOT';
1214 );
1215EOT
1216
1217 $result =~ s/^/' 'x$indent/gem;
1218 return dump_names ($args{DEFAULT_TYPE}, undef, $indent, undef,
1219 @{$args{NAMES}})
1220 . $result;
1221}
1222
0552bf3a 1223=item WriteConstants ATTRIBUTE =E<gt> VALUE [, ...]
1224
1225Writes a file of C code and a file of XS code which you should C<#include>
1226and C<INCLUDE> in the C and XS sections respectively of your module's XS
1227code. You probaby want to do this in your C<Makefile.PL>, so that you can
1228easily edit the list of constants without touching the rest of your module.
1229The attributes supported are
1230
1231=over 4
1232
1233=item NAME
1234
1235Name of the module. This must be specified
1236
1237=item DEFAULT_TYPE
1238
1239The default type for the constants. If not specified C<IV> is assumed.
1240
1241=item BREAKOUT_AT
1242
1243The names of the constants are grouped by length. Generate child subroutines
1244for each group with this number or more names in.
1245
1246=item NAMES
1247
1248An array of constants' names, either scalars containing names, or hashrefs
1249as detailed in L<"C_constant">.
1250
1251=item C_FILE
1252
1253The name of the file to write containing the C code. The default is
1cb0fb50 1254C<const-c.inc>. The C<-> in the name ensures that the file can't be
1255mistaken for anything related to a legitimate perl package name, and
1256not naming the file C<.c> avoids having to override Makefile.PL's
1257C<.xs> to C<.c> rules.
0552bf3a 1258
1259=item XS_FILE
1260
1261The name of the file to write containing the XS code. The default is
1cb0fb50 1262C<const-xs.inc>.
0552bf3a 1263
1264=item SUBNAME
1265
1266The perl visible name of the XS subroutine generated which will return the
9a7df4f2 1267constants. The default is C<constant>.
0552bf3a 1268
1269=item C_SUBNAME
1270
1271The name of the C subroutine generated which will return the constants.
1272The default is I<SUBNAME>. Child subroutines have C<_> and the name
1273length appended, so constants with 10 character names would be in
1274C<constant_10> with the default I<XS_SUBNAME>.
1275
1276=back
1277
1278=cut
1279
1280sub WriteConstants {
1281 my %ARGS =
1282 ( # defaults
1cb0fb50 1283 C_FILE => 'const-c.inc',
1284 XS_FILE => 'const-xs.inc',
0552bf3a 1285 SUBNAME => 'constant',
1286 DEFAULT_TYPE => 'IV',
1287 @_);
1288
1289 $ARGS{C_SUBNAME} ||= $ARGS{SUBNAME}; # No-one sane will have C_SUBNAME eq '0'
1290
1291 croak "Module name not specified" unless length $ARGS{NAME};
1292
1293 open my $c_fh, ">$ARGS{C_FILE}" or die "Can't open $ARGS{C_FILE}: $!";
1294 open my $xs_fh, ">$ARGS{XS_FILE}" or die "Can't open $ARGS{XS_FILE}: $!";
1295
1296 # As this subroutine is intended to make code that isn't edited, there's no
1297 # need for the user to specify any types that aren't found in the list of
1298 # names.
1299 my $types = {};
1300
1301 print $c_fh constant_types(); # macro defs
1302 print $c_fh "\n";
1303
1304 # indent is still undef. Until anyone implents indent style rules with it.
1305 foreach (C_constant ($ARGS{NAME}, $ARGS{C_SUBNAME}, $ARGS{DEFAULT_TYPE},
1306 $types, undef, $ARGS{BREAKOUT_AT}, @{$ARGS{NAMES}})) {
1307 print $c_fh $_, "\n"; # C constant subs
1308 }
1309 print $xs_fh XS_constant ($ARGS{NAME}, $types, $ARGS{XS_SUBNAME},
1310 $ARGS{C_SUBNAME});
1311
1312 close $c_fh or warn "Error closing $ARGS{C_FILE}: $!";
1313 close $xs_fh or warn "Error closing $ARGS{XS_FILE}: $!";
1314}
1315
af6c647e 13161;
1317__END__
1318
1319=back
1320
1321=head1 AUTHOR
1322
1323Nicholas Clark <nick@ccl4.org> based on the code in C<h2xs> by Larry Wall and
1324others
1325
1326=cut