ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/staticperl/perl/lib/ExtUtils/MM_Any.pm
Revision: 1.1
Committed: Thu Jun 30 14:27:10 2005 UTC (21 years, 3 months ago) by root
Branch: MAIN
CVS Tags: PERL-5-8-7, HEAD
Branch point for: PERL
Log Message:
*** empty log message ***

File Contents

# User Rev Content
1 root 1.1 package ExtUtils::MM_Any;
2    
3     use strict;
4     use vars qw($VERSION @ISA);
5     $VERSION = 0.07;
6     @ISA = qw(File::Spec);
7    
8     use Config;
9     use File::Spec;
10    
11    
12     =head1 NAME
13    
14     ExtUtils::MM_Any - Platform-agnostic MM methods
15    
16     =head1 SYNOPSIS
17    
18     FOR INTERNAL USE ONLY!
19    
20     package ExtUtils::MM_SomeOS;
21    
22     # Temporarily, you have to subclass both. Put MM_Any first.
23     require ExtUtils::MM_Any;
24     require ExtUtils::MM_Unix;
25     @ISA = qw(ExtUtils::MM_Any ExtUtils::Unix);
26    
27     =head1 DESCRIPTION
28    
29     B<FOR INTERNAL USE ONLY!>
30    
31     ExtUtils::MM_Any is a superclass for the ExtUtils::MM_* set of
32     modules. It contains methods which are either inherently
33     cross-platform or are written in a cross-platform manner.
34    
35     Subclass off of ExtUtils::MM_Any I<and> ExtUtils::MM_Unix. This is a
36     temporary solution.
37    
38     B<THIS MAY BE TEMPORARY!>
39    
40     =head1 Inherently Cross-Platform Methods
41    
42     These are methods which are by their nature cross-platform and should
43     always be cross-platform.
44    
45     =over 4
46    
47     =item installvars
48    
49     my @installvars = $mm->installvars;
50    
51     A list of all the INSTALL* variables without the INSTALL prefix. Useful
52     for iteration or building related variable sets.
53    
54     =cut
55    
56     sub installvars {
57     return qw(PRIVLIB SITELIB VENDORLIB
58     ARCHLIB SITEARCH VENDORARCH
59     BIN SITEBIN VENDORBIN
60     SCRIPT
61     MAN1DIR SITEMAN1DIR VENDORMAN1DIR
62     MAN3DIR SITEMAN3DIR VENDORMAN3DIR
63     );
64     }
65    
66     =item os_flavor_is
67    
68     $mm->os_flavor_is($this_flavor);
69     $mm->os_flavor_is(@one_of_these_flavors);
70    
71     Checks to see if the current operating system is one of the given flavors.
72    
73     This is useful for code like:
74    
75     if( $mm->os_flavor_is('Unix') ) {
76     $out = `foo 2>&1`;
77     }
78     else {
79     $out = `foo`;
80     }
81    
82     =cut
83    
84     sub os_flavor_is {
85     my $self = shift;
86     my %flavors = map { ($_ => 1) } $self->os_flavor;
87     return (grep { $flavors{$_} } @_) ? 1 : 0;
88     }
89    
90     =back
91    
92     =head2 File::Spec wrappers
93    
94     ExtUtils::MM_Any is a subclass of File::Spec. The methods noted here
95     override File::Spec.
96    
97     =over 4
98    
99     =item catfile
100    
101     File::Spec <= 0.83 has a bug where the file part of catfile is not
102     canonicalized. This override fixes that bug.
103    
104     =cut
105    
106     sub catfile {
107     my $self = shift;
108     return $self->canonpath($self->SUPER::catfile(@_));
109     }
110    
111     =back
112    
113     =head1 Thought To Be Cross-Platform Methods
114    
115     These are methods which are thought to be cross-platform by virtue of
116     having been written in a way to avoid incompatibilities. They may
117     require partial overrides.
118    
119     =over 4
120    
121     =item B<split_command>
122    
123     my @cmds = $MM->split_command($cmd, @args);
124    
125     Most OS have a maximum command length they can execute at once. Large
126     modules can easily generate commands well past that limit. Its
127     necessary to split long commands up into a series of shorter commands.
128    
129     split_command() will return a series of @cmds each processing part of
130     the args. Collectively they will process all the arguments. Each
131     individual line in @cmds will not be longer than the
132     $self->max_exec_len being careful to take into account macro expansion.
133    
134     $cmd should include any switches and repeated initial arguments.
135    
136     If no @args are given, no @cmds will be returned.
137    
138     Pairs of arguments will always be preserved in a single command, this
139     is a heuristic for things like pm_to_blib and pod2man which work on
140     pairs of arguments. This makes things like this safe:
141    
142     $self->split_command($cmd, %pod2man);
143    
144    
145     =cut
146    
147     sub split_command {
148     my($self, $cmd, @args) = @_;
149    
150     my @cmds = ();
151     return(@cmds) unless @args;
152    
153     # If the command was given as a here-doc, there's probably a trailing
154     # newline.
155     chomp $cmd;
156    
157     # set aside 20% for macro expansion.
158     my $len_left = int($self->max_exec_len * 0.80);
159     $len_left -= length $self->_expand_macros($cmd);
160    
161     do {
162     my $arg_str = '';
163     my @next_args;
164     while( @next_args = splice(@args, 0, 2) ) {
165     # Two at a time to preserve pairs.
166     my $next_arg_str = "\t ". join ' ', @next_args, "\n";
167    
168     if( !length $arg_str ) {
169     $arg_str .= $next_arg_str
170     }
171     elsif( length($arg_str) + length($next_arg_str) > $len_left ) {
172     unshift @args, @next_args;
173     last;
174     }
175     else {
176     $arg_str .= $next_arg_str;
177     }
178     }
179     chop $arg_str;
180    
181     push @cmds, $self->escape_newlines("$cmd\n$arg_str");
182     } while @args;
183    
184     return @cmds;
185     }
186    
187    
188     sub _expand_macros {
189     my($self, $cmd) = @_;
190    
191     $cmd =~ s{\$\((\w+)\)}{
192     defined $self->{$1} ? $self->{$1} : "\$($1)"
193     }e;
194     return $cmd;
195     }
196    
197    
198     =item B<echo>
199    
200     my @commands = $MM->echo($text);
201     my @commands = $MM->echo($text, $file);
202     my @commands = $MM->echo($text, $file, $appending);
203    
204     Generates a set of @commands which print the $text to a $file.
205    
206     If $file is not given, output goes to STDOUT.
207    
208     If $appending is true the $file will be appended to rather than
209     overwritten.
210    
211     =cut
212    
213     sub echo {
214     my($self, $text, $file, $appending) = @_;
215     $appending ||= 0;
216    
217     my @cmds = map { '$(NOECHO) $(ECHO) '.$self->quote_literal($_) }
218     split /\n/, $text;
219     if( $file ) {
220     my $redirect = $appending ? '>>' : '>';
221     $cmds[0] .= " $redirect $file";
222     $_ .= " >> $file" foreach @cmds[1..$#cmds];
223     }
224    
225     return @cmds;
226     }
227    
228    
229     =item init_VERSION
230    
231     $mm->init_VERSION
232    
233     Initialize macros representing versions of MakeMaker and other tools
234    
235     MAKEMAKER: path to the MakeMaker module.
236    
237     MM_VERSION: ExtUtils::MakeMaker Version
238    
239     MM_REVISION: ExtUtils::MakeMaker version control revision (for backwards
240     compat)
241    
242     VERSION: version of your module
243    
244     VERSION_MACRO: which macro represents the version (usually 'VERSION')
245    
246     VERSION_SYM: like version but safe for use as an RCS revision number
247    
248     DEFINE_VERSION: -D line to set the module version when compiling
249    
250     XS_VERSION: version in your .xs file. Defaults to $(VERSION)
251    
252     XS_VERSION_MACRO: which macro represents the XS version.
253    
254     XS_DEFINE_VERSION: -D line to set the xs version when compiling.
255    
256     Called by init_main.
257    
258     =cut
259    
260     sub init_VERSION {
261     my($self) = shift;
262    
263     $self->{MAKEMAKER} = $ExtUtils::MakeMaker::Filename;
264     $self->{MM_VERSION} = $ExtUtils::MakeMaker::VERSION;
265     $self->{MM_REVISION}= $ExtUtils::MakeMaker::Revision;
266     $self->{VERSION_FROM} ||= '';
267    
268     if ($self->{VERSION_FROM}){
269     $self->{VERSION} = $self->parse_version($self->{VERSION_FROM});
270     if( $self->{VERSION} eq 'undef' ) {
271     require Carp;
272     Carp::carp("WARNING: Setting VERSION via file ".
273     "'$self->{VERSION_FROM}' failed\n");
274     }
275     }
276    
277     # strip blanks
278     if (defined $self->{VERSION}) {
279     $self->{VERSION} =~ s/^\s+//;
280     $self->{VERSION} =~ s/\s+$//;
281     }
282     else {
283     $self->{VERSION} = '';
284     }
285    
286    
287     $self->{VERSION_MACRO} = 'VERSION';
288     ($self->{VERSION_SYM} = $self->{VERSION}) =~ s/\W/_/g;
289     $self->{DEFINE_VERSION} = '-D$(VERSION_MACRO)=\"$(VERSION)\"';
290    
291    
292     # Graham Barr and Paul Marquess had some ideas how to ensure
293     # version compatibility between the *.pm file and the
294     # corresponding *.xs file. The bottomline was, that we need an
295     # XS_VERSION macro that defaults to VERSION:
296     $self->{XS_VERSION} ||= $self->{VERSION};
297    
298     $self->{XS_VERSION_MACRO} = 'XS_VERSION';
299     $self->{XS_DEFINE_VERSION} = '-D$(XS_VERSION_MACRO)=\"$(XS_VERSION)\"';
300    
301     }
302    
303     =item wraplist
304    
305     Takes an array of items and turns them into a well-formatted list of
306     arguments. In most cases this is simply something like:
307    
308     FOO \
309     BAR \
310     BAZ
311    
312     =cut
313    
314     sub wraplist {
315     my $self = shift;
316     return join " \\\n\t", @_;
317     }
318    
319     =item manifypods
320    
321     Defines targets and routines to translate the pods into manpages and
322     put them into the INST_* directories.
323    
324     =cut
325    
326     sub manifypods {
327     my $self = shift;
328    
329     my $POD2MAN_macro = $self->POD2MAN_macro();
330     my $manifypods_target = $self->manifypods_target();
331    
332     return <<END_OF_TARGET;
333    
334     $POD2MAN_macro
335    
336     $manifypods_target
337    
338     END_OF_TARGET
339    
340     }
341    
342    
343     =item manifypods_target
344    
345     my $manifypods_target = $self->manifypods_target;
346    
347     Generates the manifypods target. This target generates man pages from
348     all POD files in MAN1PODS and MAN3PODS.
349    
350     =cut
351    
352     sub manifypods_target {
353     my($self) = shift;
354    
355     my $man1pods = '';
356     my $man3pods = '';
357     my $dependencies = '';
358    
359     # populate manXpods & dependencies:
360     foreach my $name (keys %{$self->{MAN1PODS}}, keys %{$self->{MAN3PODS}}) {
361     $dependencies .= " \\\n\t$name";
362     }
363    
364     foreach my $name (keys %{$self->{MAN3PODS}}) {
365     $dependencies .= " \\\n\t$name"
366     }
367    
368     my $manify = <<END;
369     manifypods : pure_all $dependencies
370     END
371    
372     my @man_cmds;
373     foreach my $section (qw(1 3)) {
374     my $pods = $self->{"MAN${section}PODS"};
375     push @man_cmds, $self->split_command(<<CMD, %$pods);
376     \$(NOECHO) \$(POD2MAN) --section=$section --perm_rw=\$(PERM_RW)
377     CMD
378     }
379    
380     $manify .= "\t\$(NOECHO) \$(NOOP)\n" unless @man_cmds;
381     $manify .= join '', map { "$_\n" } @man_cmds;
382    
383     return $manify;
384     }
385    
386    
387     =item makemakerdflt_target
388    
389     my $make_frag = $mm->makemakerdflt_target
390    
391     Returns a make fragment with the makemakerdeflt_target specified.
392     This target is the first target in the Makefile, is the default target
393     and simply points off to 'all' just in case any make variant gets
394     confused or something gets snuck in before the real 'all' target.
395    
396     =cut
397    
398     sub makemakerdflt_target {
399     return <<'MAKE_FRAG';
400     makemakerdflt: all
401     $(NOECHO) $(NOOP)
402     MAKE_FRAG
403    
404     }
405    
406    
407     =item special_targets
408    
409     my $make_frag = $mm->special_targets
410    
411     Returns a make fragment containing any targets which have special
412     meaning to make. For example, .SUFFIXES and .PHONY.
413    
414     =cut
415    
416     sub special_targets {
417     my $make_frag = <<'MAKE_FRAG';
418     .SUFFIXES: .xs .c .C .cpp .i .s .cxx .cc $(OBJ_EXT)
419    
420     .PHONY: all config static dynamic test linkext manifest
421    
422     MAKE_FRAG
423    
424     $make_frag .= <<'MAKE_FRAG' if $ENV{CLEARCASE_ROOT};
425     .NO_CONFIG_REC: Makefile
426    
427     MAKE_FRAG
428    
429     return $make_frag;
430     }
431    
432     =item POD2MAN_macro
433    
434     my $pod2man_macro = $self->POD2MAN_macro
435    
436     Returns a definition for the POD2MAN macro. This is a program
437     which emulates the pod2man utility. You can add more switches to the
438     command by simply appending them on the macro.
439    
440     Typical usage:
441    
442     $(POD2MAN) --section=3 --perm_rw=$(PERM_RW) podfile1 man_page1 ...
443    
444     =cut
445    
446     sub POD2MAN_macro {
447     my $self = shift;
448    
449     # Need the trailing '--' so perl stops gobbling arguments and - happens
450     # to be an alternative end of line seperator on VMS so we quote it
451     return <<'END_OF_DEF';
452     POD2MAN_EXE = $(PERLRUN) "-MExtUtils::Command::MM" -e pod2man "--"
453     POD2MAN = $(POD2MAN_EXE)
454     END_OF_DEF
455     }
456    
457    
458     =item test_via_harness
459    
460     my $command = $mm->test_via_harness($perl, $tests);
461    
462     Returns a $command line which runs the given set of $tests with
463     Test::Harness and the given $perl.
464    
465     Used on the t/*.t files.
466    
467     =cut
468    
469     sub test_via_harness {
470     my($self, $perl, $tests) = @_;
471    
472     return qq{\t$perl "-MExtUtils::Command::MM" }.
473     qq{"-e" "test_harness(\$(TEST_VERBOSE), '\$(INST_LIB)', '\$(INST_ARCHLIB)')" $tests\n};
474     }
475    
476     =item test_via_script
477    
478     my $command = $mm->test_via_script($perl, $script);
479    
480     Returns a $command line which just runs a single test without
481     Test::Harness. No checks are done on the results, they're just
482     printed.
483    
484     Used for test.pl, since they don't always follow Test::Harness
485     formatting.
486    
487     =cut
488    
489     sub test_via_script {
490     my($self, $perl, $script) = @_;
491     return qq{\t$perl "-I\$(INST_LIB)" "-I\$(INST_ARCHLIB)" $script\n};
492     }
493    
494     =item libscan
495    
496     my $wanted = $self->libscan($path);
497    
498     Takes a path to a file or dir and returns an empty string if we don't
499     want to include this file in the library. Otherwise it returns the
500     the $path unchanged.
501    
502     Mainly used to exclude RCS, CVS, and SCCS directories from
503     installation.
504    
505     =cut
506    
507     sub libscan {
508     my($self,$path) = @_;
509     my($dirs,$file) = ($self->splitpath($path))[1,2];
510     return '' if grep /^(?:RCS|CVS|SCCS|\.svn)$/,
511     $self->splitdir($dirs), $file;
512    
513     return $path;
514     }
515    
516     =item tool_autosplit
517    
518     Defines a simple perl call that runs autosplit. May be deprecated by
519     pm_to_blib soon.
520    
521     =cut
522    
523     sub tool_autosplit {
524     my($self, %attribs) = @_;
525    
526     my $maxlen = $attribs{MAXLEN} ? '$$AutoSplit::Maxlen=$attribs{MAXLEN};'
527     : '';
528    
529     my $asplit = $self->oneliner(sprintf <<'PERL_CODE', $maxlen);
530     use AutoSplit; %s autosplit($$ARGV[0], $$ARGV[1], 0, 1, 1)
531     PERL_CODE
532    
533     return sprintf <<'MAKE_FRAG', $asplit;
534     # Usage: $(AUTOSPLITFILE) FileToSplit AutoDirToSplitInto
535     AUTOSPLITFILE = %s
536    
537     MAKE_FRAG
538    
539     }
540    
541    
542     =item all_target
543    
544     Generate the default target 'all'.
545    
546     =cut
547    
548     sub all_target {
549     my $self = shift;
550    
551     return <<'MAKE_EXT';
552     all :: pure_all
553     $(NOECHO) $(NOOP)
554     MAKE_EXT
555    
556     }
557    
558    
559     =item metafile_target
560    
561     my $target = $mm->metafile_target;
562    
563     Generate the metafile target.
564    
565     Writes the file META.yml, YAML encoded meta-data about the module. The
566     format follows Module::Build's as closely as possible. Additionally, we
567     include:
568    
569     version_from
570     installdirs
571    
572     =cut
573    
574     sub metafile_target {
575     my $self = shift;
576    
577     return <<'MAKE_FRAG' if $self->{NO_META};
578     metafile:
579     $(NOECHO) $(NOOP)
580     MAKE_FRAG
581    
582     my $prereq_pm = '';
583     foreach my $mod ( sort { lc $a cmp lc $b } keys %{$self->{PREREQ_PM}} ) {
584     my $ver = $self->{PREREQ_PM}{$mod};
585     $prereq_pm .= sprintf " %-30s %s\n", "$mod:", $ver;
586     }
587    
588     my $meta = <<YAML;
589     # http://module-build.sourceforge.net/META-spec.html
590     #XXXXXXX This is a prototype!!! It will change in the future!!! XXXXX#
591     name: $self->{DISTNAME}
592     version: $self->{VERSION}
593     version_from: $self->{VERSION_FROM}
594     installdirs: $self->{INSTALLDIRS}
595     requires:
596     $prereq_pm
597     distribution_type: module
598     generated_by: ExtUtils::MakeMaker version $ExtUtils::MakeMaker::VERSION
599     YAML
600    
601     my @write_meta = $self->echo($meta, 'META.yml');
602     return sprintf <<'MAKE_FRAG', join "\n\t", @write_meta;
603     metafile :
604     %s
605     MAKE_FRAG
606    
607     }
608    
609    
610     =item metafile_addtomanifest_target
611    
612     my $target = $mm->metafile_addtomanifest_target
613    
614     Adds the META.yml file to the MANIFEST.
615    
616     =cut
617    
618     sub metafile_addtomanifest_target {
619     my $self = shift;
620    
621     return <<'MAKE_FRAG' if $self->{NO_META};
622     metafile_addtomanifest:
623     $(NOECHO) $(NOOP)
624     MAKE_FRAG
625    
626     my $add_meta = $self->oneliner(<<'CODE', ['-MExtUtils::Manifest=maniadd']);
627     eval { maniadd({q{META.yml} => q{Module meta-data (added by MakeMaker)}}) }
628     or print "Could not add META.yml to MANIFEST: $${'@'}\n"
629     CODE
630    
631     return sprintf <<'MAKE_FRAG', $add_meta;
632     metafile_addtomanifest:
633     $(NOECHO) %s
634     MAKE_FRAG
635    
636     }
637    
638    
639     =back
640    
641     =head2 Abstract methods
642    
643     Methods which cannot be made cross-platform and each subclass will
644     have to do their own implementation.
645    
646     =over 4
647    
648     =item oneliner
649    
650     my $oneliner = $MM->oneliner($perl_code);
651     my $oneliner = $MM->oneliner($perl_code, \@switches);
652    
653     This will generate a perl one-liner safe for the particular platform
654     you're on based on the given $perl_code and @switches (a -e is
655     assumed) suitable for using in a make target. It will use the proper
656     shell quoting and escapes.
657    
658     $(PERLRUN) will be used as perl.
659    
660     Any newlines in $perl_code will be escaped. Leading and trailing
661     newlines will be stripped. Makes this idiom much easier:
662    
663     my $code = $MM->oneliner(<<'CODE', [...switches...]);
664     some code here
665     another line here
666     CODE
667    
668     Usage might be something like:
669    
670     # an echo emulation
671     $oneliner = $MM->oneliner('print "Foo\n"');
672     $make = '$oneliner > somefile';
673    
674     All dollar signs must be doubled in the $perl_code if you expect them
675     to be interpreted normally, otherwise it will be considered a make
676     macro. Also remember to quote make macros else it might be used as a
677     bareword. For example:
678    
679     # Assign the value of the $(VERSION_FROM) make macro to $vf.
680     $oneliner = $MM->oneliner('$$vf = "$(VERSION_FROM)"');
681    
682     Its currently very simple and may be expanded sometime in the figure
683     to include more flexible code and switches.
684    
685    
686     =item B<quote_literal>
687    
688     my $safe_text = $MM->quote_literal($text);
689    
690     This will quote $text so it is interpreted literally in the shell.
691    
692     For example, on Unix this would escape any single-quotes in $text and
693     put single-quotes around the whole thing.
694    
695    
696     =item B<escape_newlines>
697    
698     my $escaped_text = $MM->escape_newlines($text);
699    
700     Shell escapes newlines in $text.
701    
702    
703     =item max_exec_len
704    
705     my $max_exec_len = $MM->max_exec_len;
706    
707     Calculates the maximum command size the OS can exec. Effectively,
708     this is the max size of a shell command line.
709    
710     =for _private
711     $self->{_MAX_EXEC_LEN} is set by this method, but only for testing purposes.
712    
713     =item B<init_others>
714    
715     $MM->init_others();
716    
717     Initializes the macro definitions used by tools_other() and places them
718     in the $MM object.
719    
720     If there is no description, its the same as the parameter to
721     WriteMakefile() documented in ExtUtils::MakeMaker.
722    
723     Defines at least these macros.
724    
725     Macro Description
726    
727     NOOP Do nothing
728     NOECHO Tell make not to display the command itself
729    
730     MAKEFILE
731     FIRST_MAKEFILE
732     MAKEFILE_OLD
733     MAKE_APERL_FILE File used by MAKE_APERL
734    
735     SHELL Program used to run
736     shell commands
737    
738     ECHO Print text adding a newline on the end
739     RM_F Remove a file
740     RM_RF Remove a directory
741     TOUCH Update a file's timestamp
742     TEST_F Test for a file's existence
743     CP Copy a file
744     MV Move a file
745     CHMOD Change permissions on a
746     file
747    
748     UMASK_NULL Nullify umask
749     DEV_NULL Supress all command output
750    
751     =item init_DIRFILESEP
752    
753     $MM->init_DIRFILESEP;
754     my $dirfilesep = $MM->{DIRFILESEP};
755    
756     Initializes the DIRFILESEP macro which is the seperator between the
757     directory and filename in a filepath. ie. / on Unix, \ on Win32 and
758     nothing on VMS.
759    
760     For example:
761    
762     # instead of $(INST_ARCHAUTODIR)/extralibs.ld
763     $(INST_ARCHAUTODIR)$(DIRFILESEP)extralibs.ld
764    
765     Something of a hack but it prevents a lot of code duplication between
766     MM_* variants.
767    
768     Do not use this as a seperator between directories. Some operating
769     systems use different seperators between subdirectories as between
770     directories and filenames (for example: VOLUME:[dir1.dir2]file on VMS).
771    
772     =item init_linker
773    
774     $mm->init_linker;
775    
776     Initialize macros which have to do with linking.
777    
778     PERL_ARCHIVE: path to libperl.a equivalent to be linked to dynamic
779     extensions.
780    
781     PERL_ARCHIVE_AFTER: path to a library which should be put on the
782     linker command line I<after> the external libraries to be linked to
783     dynamic extensions. This may be needed if the linker is one-pass, and
784     Perl includes some overrides for C RTL functions, such as malloc().
785    
786     EXPORT_LIST: name of a file that is passed to linker to define symbols
787     to be exported.
788    
789     Some OSes do not need these in which case leave it blank.
790    
791    
792     =item init_platform
793    
794     $mm->init_platform
795    
796     Initialize any macros which are for platform specific use only.
797    
798     A typical one is the version number of your OS specific mocule.
799     (ie. MM_Unix_VERSION or MM_VMS_VERSION).
800    
801     =item platform_constants
802    
803     my $make_frag = $mm->platform_constants
804    
805     Returns a make fragment defining all the macros initialized in
806     init_platform() rather than put them in constants().
807    
808     =cut
809    
810     sub init_platform {
811     return '';
812     }
813    
814     sub platform_constants {
815     return '';
816     }
817    
818     =item os_flavor
819    
820     my @os_flavor = $mm->os_flavor;
821    
822     @os_flavor is the style of operating system this is, usually
823     corresponding to the MM_*.pm file we're using.
824    
825     The first element of @os_flavor is the major family (ie. Unix,
826     Windows, VMS, OS/2, MacOS, etc...) and the rest are sub families.
827    
828     Some examples:
829    
830     Cygwin98 ('Unix', 'Cygwin', 'Cygwin9x')
831     Windows NT ('Win32', 'WinNT')
832     Win98 ('Win32', 'Win9x')
833     Linux ('Unix', 'Linux')
834     MacOS Classic ('MacOS', 'MacOS Classic')
835     MacOS X ('Unix', 'Darwin', 'MacOS', 'MacOS X')
836     OS/2 ('OS/2')
837    
838     This is used to write code for styles of operating system.
839     See os_flavor_is() for use.
840    
841    
842     =back
843    
844     =head1 AUTHOR
845    
846     Michael G Schwern <schwern@pobox.com> and the denizens of
847     makemaker@perl.org with code from ExtUtils::MM_Unix and
848     ExtUtils::MM_Win32.
849    
850    
851     =cut
852    
853     1;