1# MM_MacOS.pm 2# MakeMaker default methods for MacOS 3# This package is inserted into @ISA of MakeMaker's MM before the 4# built-in ExtUtils::MM_Unix methods if MakeMaker.pm is run under MacOS. 5# 6# Author: Matthias Neeracher <neeracher@mac.com> 7# Maintainer: Chris Nandor <pudge@pobox.com> 8 9package ExtUtils::MM_MacOS; 10require ExtUtils::MM_Any; 11require ExtUtils::MM_Unix; 12@ISA = qw( ExtUtils::MM_Any ExtUtils::MM_Unix ); 13 14use vars qw($VERSION); 15$VERSION = '1.07'; 16 17use Config; 18use Cwd 'cwd'; 19require Exporter; 20use File::Basename; 21use vars qw(%make_data); 22 23my $Mac_FS = eval { require Mac::FileSpec::Unixish }; 24 25use ExtUtils::MakeMaker qw($Verbose &neatvalue); 26 27=head1 NAME 28 29ExtUtils::MM_MacOS - methods to override UN*X behaviour in ExtUtils::MakeMaker 30 31=head1 SYNOPSIS 32 33 use ExtUtils::MM_MacOS; # Done internally by ExtUtils::MakeMaker if needed 34 35=head1 DESCRIPTION 36 37MM_MacOS currently only produces an approximation to the correct Makefile. 38 39=over 4 40 41=cut 42 43sub new { 44 my($class,$self) = @_; 45 my($key); 46 my($cwd) = cwd(); 47 48 print STDOUT "Mac MakeMaker (v$ExtUtils::MakeMaker::VERSION)\n" if $Verbose; 49 if (-f "MANIFEST" && ! -f "Makefile.mk"){ 50 ExtUtils::MakeMaker::check_manifest(); 51 } 52 53 mkdir("Obj", 0777) unless -d "Obj"; 54 55 $self = {} unless defined $self; 56 57 check_hints($self); 58 59 my(%initial_att) = %$self; # record initial attributes 60 61 if (defined $self->{CONFIGURE}) { 62 if (ref $self->{CONFIGURE} eq 'CODE') { 63 $self = { %$self, %{&{$self->{CONFIGURE}}}}; 64 } else { 65 require Carp; 66 Carp::croak("Attribute 'CONFIGURE' to WriteMakefile() not a code reference\n"); 67 } 68 } 69 70 my $newclass = ++$ExtUtils::MakeMaker::PACKNAME; 71 local @ExtUtils::MakeMaker::Parent = @ExtUtils::MakeMaker::Parent; # Protect against non-local exits 72 { 73 no strict 'refs'; 74 print "Blessing Object into class [$newclass]\n" if $Verbose>=2; 75 ExtUtils::MakeMaker::mv_all_methods("MY",$newclass); 76 bless $self, $newclass; 77 push @Parent, $self; 78 require ExtUtils::MY; 79 @{"$newclass\:\:ISA"} = 'MM'; 80 } 81 82 $ExtUtils::MakeMaker::Recognized_Att_Keys{$_} = 1 83 for map { $_ . 'Optimize' } qw(MWC MWCPPC MWC68K MPW MRC MRC SC); 84 85 if (defined $ExtUtils::MakeMaker::Parent[-2]){ 86 $self->{PARENT} = $ExtUtils::MakeMaker::Parent[-2]; 87 my $key; 88 for $key (@ExtUtils::MakeMaker::Prepend_parent) { 89 next unless defined $self->{PARENT}{$key}; 90 $self->{$key} = $self->{PARENT}{$key}; 91 if ($key !~ /PERL$/) { 92 $self->{$key} = $self->catdir("..",$self->{$key}) 93 unless $self->file_name_is_absolute($self->{$key}); 94 } else { 95 # PERL or FULLPERL will be a command verb or even a 96 # command with an argument instead of a full file 97 # specification under VMS. So, don't turn the command 98 # into a filespec, but do add a level to the path of 99 # the argument if not already absolute. 100 my @cmd = split /\s+/, $self->{$key}; 101 $cmd[1] = $self->catfile('[-]',$cmd[1]) 102 unless (@cmd < 2) || $self->file_name_is_absolute($cmd[1]); 103 $self->{$key} = join(' ', @cmd); 104 } 105 } 106 if ($self->{PARENT}) { 107 $self->{PARENT}->{CHILDREN}->{$newclass} = $self; 108 foreach my $opt (qw(POLLUTE PERL_CORE)) { 109 if (exists $self->{PARENT}->{$opt} 110 and not exists $self->{$opt}) 111 { 112 # inherit, but only if already unspecified 113 $self->{$opt} = $self->{PARENT}->{$opt}; 114 } 115 } 116 } 117 my @fm = grep /^FIRST_MAKEFILE=/, @ARGV; 118 $self->parse_args(@fm) if @fm; 119 } else { 120 $self->parse_args(split(' ', $ENV{PERL_MM_OPT} || ''),@ARGV); 121 } 122 123 $self->{NAME} ||= $self->guess_name; 124 125 ($self->{NAME_SYM} = $self->{NAME}) =~ s/\W+/_/g; 126 127 $self->init_main(); 128 $self->init_dirscan(); 129 $self->init_others(); 130 131 push @{$self->{RESULT}}, <<END; 132# This Makefile is for the $self->{NAME} extension to perl. 133# 134# It was generated automatically by MakeMaker version 135# $ExtUtils::MakeMaker::VERSION (Revision: $ExtUtils::MakeMaker::Revision) from the contents of 136# Makefile.PL. Don't edit this file, edit Makefile.PL instead. 137# 138# ANY CHANGES MADE HERE WILL BE LOST! 139# 140# MakeMaker Parameters: 141END 142 143 foreach $key (sort keys %initial_att){ 144 my($v) = neatvalue($initial_att{$key}); 145 $v =~ s/(CODE|HASH|ARRAY|SCALAR)\([\dxa-f]+\)/$1\(...\)/; 146 $v =~ tr/\n/ /s; 147 push @{$self->{RESULT}}, "# $key => $v"; 148 } 149 150 # turn the SKIP array into a SKIPHASH hash 151 my (%skip,$skip); 152 for $skip (@{$self->{SKIP} || []}) { 153 $self->{SKIPHASH}{$skip} = 1; 154 } 155 delete $self->{SKIP}; # free memory 156 157 # We skip many sections for MacOS, but we don't say anything about it in the Makefile 158 for (qw/ const_config tool_autosplit 159 tool_xsubpp tools_other dist macro depend post_constants 160 pasthru c_o xs_c xs_o top_targets linkext 161 dynamic_bs dynamic_lib static_lib manifypods 162 installbin subdirs dist_basics dist_core 163 distdir dist_test dist_ci install force perldepend makefile 164 staticmake test pm_to_blib selfdocument 165 const_loadlibs const_cccmd 166 /) 167 { 168 $self->{SKIPHASH}{$_} = 2; 169 } 170 push @ExtUtils::MakeMaker::MM_Sections, "rulez" 171 unless grep /rulez/, @ExtUtils::MakeMaker::MM_Sections; 172 173 if ($self->{PARENT}) { 174 for (qw/install dist dist_basics dist_core distdir dist_test dist_ci/) { 175 $self->{SKIPHASH}{$_} = 1; 176 } 177 } 178 179 # We run all the subdirectories now. They don't have much to query 180 # from the parent, but the parent has to query them: if they need linking! 181 unless ($self->{NORECURS}) { 182 $self->eval_in_subdirs if @{$self->{DIR}}; 183 } 184 185 my $section; 186 foreach $section ( @ExtUtils::MakeMaker::MM_Sections ){ 187 next if defined $self->{SKIPHASH}{$section} && 188 $self->{SKIPHASH}{$section} == 2; 189 print "Processing Makefile '$section' section\n" if ($Verbose >= 2); 190 $self->{ABSTRACT_FROM} = macify($self->{ABSTRACT_FROM}) 191 if $self->{ABSTRACT_FROM}; 192 my($skipit) = $self->skipcheck($section); 193 if ($skipit){ 194 push @{$self->{RESULT}}, "\n# --- MakeMaker $section section $skipit."; 195 } else { 196 my(%a) = %{$self->{$section} || {}}; 197 push @{$self->{RESULT}}, "\n# --- MakeMaker $section section:"; 198 push @{$self->{RESULT}}, "# " . join ", ", %a if $Verbose && %a; 199 push @{$self->{RESULT}}, $self->nicetext($self->$section( %a )); 200 } 201 } 202 203 push @{$self->{RESULT}}, "\n# End."; 204 pop @Parent; 205 206 $ExtUtils::MM_MacOS::make_data{$cwd} = $self; 207 $self; 208} 209 210sub skipcheck { 211 my($self) = shift; 212 my($section) = @_; 213 return 'skipped' if $self->{SKIPHASH}{$section}; 214 return ''; 215} 216 217=item maybe_command 218 219Returns true, if the argument is likely to be a command. 220 221=cut 222 223sub maybe_command { 224 my($self,$file) = @_; 225 return $file if ! -d $file; 226 return; 227} 228 229=item guess_name 230 231Guess the name of this package by examining the working directory's 232name. MakeMaker calls this only if the developer has not supplied a 233NAME attribute. 234 235=cut 236 237sub guess_name { 238 my($self) = @_; 239 my $name = cwd(); 240 $name =~ s/.*:// unless ($name =~ s/^.*:ext://); 241 $name =~ s#:#::#g; 242 $name =~ s#[\-_][\d.\-]+$##; # this is new with MM 5.00 243 $name; 244} 245 246=item macify 247 248Translate relative Unix filepaths into Mac names. 249 250=cut 251 252sub macify { 253 my($unix) = @_; 254 my(@mac); 255 256 foreach (split(/[ \t\n]+/, $unix)) { 257 if (m|/|) { 258 if ($Mac_FS) { # should always be true 259 $_ = Mac::FileSpec::Unixish::nativize($_); 260 } else { 261 s|^\./||; 262 s|/|:|g; 263 $_ = ":$_"; 264 } 265 } 266 push(@mac, $_); 267 } 268 269 return "@mac"; 270} 271 272=item patternify 273 274Translate Unix filepaths and shell globs to Mac style. 275 276=cut 277 278sub patternify { 279 my($unix) = @_; 280 my(@mac); 281 use ExtUtils::MakeMaker::bytes; # Non-UTF-8 high bytes below. 282 283 foreach (split(/[ \t\n]+/, $unix)) { 284 if (m|/|) { 285 $_ = ":$_"; 286 s|/|:|g; 287 s|\*|�|g; 288 $_ = "'$_'" if /[?�]/; 289 push(@mac, $_); 290 } 291 } 292 293 return "@mac"; 294} 295 296=item init_main 297 298Initializes some of NAME, FULLEXT, BASEEXT, DLBASE, PERL_SRC, 299PERL_LIB, PERL_ARCHLIB, PERL_INC, INSTALLDIRS, INST_*, INSTALL*, 300PREFIX, CONFIG, AR, AR_STATIC_ARGS, LD, OBJ_EXT, LIB_EXT, MAP_TARGET, 301LIBPERL_A, VERSION_FROM, VERSION, DISTNAME, VERSION_SYM. 302 303=cut 304 305sub init_main { 306 my($self) = @_; 307 308 # --- Initialize Module Name and Paths 309 310 # NAME = The perl module name for this extension (eg DBD::Oracle). 311 # FULLEXT = Pathname for extension directory (eg DBD/Oracle). 312 # BASEEXT = Basename part of FULLEXT. May be just equal FULLEXT. 313 ($self->{FULLEXT} = 314 $self->{NAME}) =~ s!::!:!g ; #eg. BSD:Foo:Socket 315 ($self->{BASEEXT} = 316 $self->{NAME}) =~ s!.*::!! ; #eg. Socket 317 318 # --- Initialize PERL_LIB, INST_LIB, PERL_SRC 319 320 # *Real* information: where did we get these two from? ... 321 my $inc_config_dir = dirname($INC{'Config.pm'}); 322 my $inc_carp_dir = dirname($INC{'Carp.pm'}); 323 324 unless ($self->{PERL_SRC}){ 325 my($dir); 326 foreach $dir (qw(:: ::: :::: ::::: ::::::)){ 327 if (-f "${dir}perl.h") { 328 $self->{PERL_SRC}=$dir ; 329 last; 330 } 331 } 332 if (!$self->{PERL_SRC} && -f "$ENV{MACPERL}CORE:perl:perl.h") { 333 # Mac pathnames may be very nasty, so we'll install symlinks 334 unlink(":PerlCore", ":PerlLib"); 335 symlink("$ENV{MACPERL}CORE:", "PerlCore"); 336 symlink("$ENV{MACPERL}lib:", "PerlLib"); 337 $self->{PERL_SRC} = ":PerlCore:perl:" ; 338 $self->{PERL_LIB} = ":PerlLib:"; 339 } 340 } 341 if ($self->{PERL_SRC}){ 342 $self->{PERL_LIB} ||= $self->catdir("$self->{PERL_SRC}","lib"); 343 $self->{PERL_ARCHLIB} = $self->{PERL_LIB}; 344 $self->{PERL_INC} = $self->{PERL_SRC}; 345 } else { 346# hmmmmmmm ... ? 347 $self->{PERL_LIB} ||= "$ENV{MACPERL}site_perl"; 348 $self->{PERL_ARCHLIB} = $self->{PERL_LIB}; 349 $self->{PERL_INC} = $ENV{MACPERL}; 350 $self->{PERL_SRC} = ''; 351 } 352 353 $self->{INSTALLDIRS} = "perl"; 354 $self->{INST_LIB} = $self->{INST_ARCHLIB} = $self->{PERL_LIB}; 355 $self->{INST_MAN1DIR} = $self->{INSTALLMAN1DIR} = "none"; 356 $self->{MAN1EXT} ||= $Config::Config{man1ext}; 357 $self->{INST_MAN3DIR} = $self->{INSTALLMAN3DIR} = "none"; 358 $self->{MAN3EXT} ||= $Config::Config{man3ext}; 359 $self->{MAP_TARGET} ||= "perl"; 360 361 # make a simple check if we find Exporter 362 # hm ... do we really care? at all? 363# warn "Warning: PERL_LIB ($self->{PERL_LIB}) seems not to be a perl library directory 364# (Exporter.pm not found)" 365# unless -f $self->catfile("$self->{PERL_LIB}","Exporter.pm") || 366# $self->{NAME} eq "ExtUtils::MakeMaker"; 367 368 # Determine VERSION and VERSION_FROM 369 ($self->{DISTNAME}=$self->{NAME}) =~ s#(::)#-#g unless $self->{DISTNAME}; 370 if ($self->{VERSION_FROM}){ 371 # XXX replace with parse_version() override 372 local *FH; 373 open(FH,macify($self->{VERSION_FROM})) or 374 die "Could not open '$self->{VERSION_FROM}' (attribute VERSION_FROM): $!"; 375 while (<FH>) { 376 chop; 377 next unless /\$([\w:]*\bVERSION)\b.*=/; 378 local $ExtUtils::MakeMaker::module_version_variable = $1; 379 my($eval) = "$_;"; 380 eval $eval; 381 die "Could not eval '$eval': $@" if $@; 382 if ($self->{VERSION} = $ {$ExtUtils::MakeMaker::module_version_variable}){ 383 print "$self->{NAME} VERSION is $self->{VERSION} (from $self->{VERSION_FROM})\n" if $Verbose; 384 } else { 385 # XXX this should probably croak 386 print "WARNING: Setting VERSION via file '$self->{VERSION_FROM}' failed\n"; 387 } 388 last; 389 } 390 close FH; 391 } 392 393 if ($self->{VERSION}) { 394 $self->{VERSION} =~ s/^\s+//; 395 $self->{VERSION} =~ s/\s+$//; 396 } 397 398 $self->{VERSION} = "0.10" unless $self->{VERSION}; 399 ($self->{VERSION_SYM} = $self->{VERSION}) =~ s/\W/_/g; 400 401 402 # Graham Barr and Paul Marquess had some ideas how to ensure 403 # version compatibility between the *.pm file and the 404 # corresponding *.xs file. The bottomline was, that we need an 405 # XS_VERSION macro that defaults to VERSION: 406 $self->{XS_VERSION} ||= $self->{VERSION}; 407 408 409 $self->{DEFINE} .= " \$(XS_DEFINE_VERSION) \$(DEFINE_VERSION)"; 410 411 # Preprocessor definitions may be useful 412 $self->{DEFINE} =~ s/-D/-d /g; 413 414 # UN*X includes probably are not useful 415 $self->{DEFINE} =~ s/-I\S+/_include($1)/eg; 416 417 418 if ($self->{INC}) { 419 # UN*X includes probably are not useful 420 $self->{INC} =~ s/-I(\S+)/_include($1)/eg; 421 } 422 423 424 # --- Initialize Perl Binary Locations 425 426 # Find Perl 5. The only contract here is that both 'PERL' and 'FULLPERL' 427 # will be working versions of perl 5. miniperl has priority over perl 428 # for PERL to ensure that $(PERL) is usable while building ./ext/* 429 my ($component,@defpath); 430 foreach $component ($self->{PERL_SRC}, $self->path(), $Config::Config{binexp}) { 431 push @defpath, $component if defined $component; 432 } 433 $self->{PERL} = "$self->{PERL_SRC}miniperl"; 434} 435 436=item init_others 437 438Initializes LDLOADLIBS, LIBS 439 440=cut 441 442sub init_others { # --- Initialize Other Attributes 443 my($self) = shift; 444 445 if ( !$self->{OBJECT} ) { 446 # init_dirscan should have found out, if we have C files 447 $self->{OBJECT} = ""; 448 $self->{OBJECT} = "$self->{BASEEXT}.c" if @{$self->{C}||[]}; 449 } else { 450 $self->{OBJECT} =~ s/\$\(O_FILES\)/@{$self->{C}||[]}/; 451 } 452 my($src); 453 foreach (split(/[ \t\n]+/, $self->{OBJECT})) { 454 if (/^$self->{BASEEXT}\.o(bj)?$/) { 455 $src .= " $self->{BASEEXT}.c"; 456 } elsif (/^(.*\..*)\.o$/) { 457 $src .= " $1"; 458 } elsif (/^(.*)(\.o(bj)?|\$\(OBJ_EXT\))$/) { 459 if (-f "$1.cp") { 460 $src .= " $1.cp"; 461 } else { 462 $src .= " $1.c"; 463 } 464 } else { 465 $src .= " $_"; 466 } 467 } 468 $self->{SOURCE} = $src; 469 $self->{FULLPERL} = "$self->{PERL_SRC}perl"; 470 $self->{MAKEFILE} = "Makefile.mk"; 471 $self->{FIRST_MAKEFILE} = $self->{MAKEFILE}; 472 $self->{MAKEFILE_OLD} = $self->{MAKEFILE}.'.old'; 473 474 $self->{'DEV_NULL'} ||= ' \xB3 Dev:Null'; 475 476 return 1; 477} 478 479=item init_platform 480 481Add MACPERL_SRC MACPERL_LIB 482 483=item platform_constants 484 485Add MACPERL_SRC MACPERL_LIB MACLIBS_68K MACLIBS_PPC MACLIBS_SC MACLIBS_MRC 486MACLIBS_ALL_68K MACLIBS_ALL_PPC MACLIBS_SHARED 487 488XXX Few are initialized. How many of these are ever used? 489 490=cut 491 492sub init_platform { 493 my $self = shift; 494 495 $self->{MACPERL_SRC} = $self->catdir("$self->{PERL_SRC}","macos:"); 496 $self->{MACPERL_LIB} ||= $self->catdir("$self->{MACPERL_SRC}","lib"); 497 $self->{MACPERL_INC} = $self->{MACPERL_SRC}; 498} 499 500 501 502sub platform_constants { 503 my $self = shift; 504 505 foreach my $macro (qw(MACPERL_SRC MACPERL_LIB MACLIBS_68K MACLIBS_PPC 506 MACLIBS_SC MACLIBS_MRC MACLIBS_ALL_68K 507 MACLIBS_ALL_PPC MACLIBS_SHARED)) 508 { 509 next unless defined $self->{$macro}; 510 $make_frag .= "$macro = $self->{$macro}\n"; 511 } 512 513 return $make_frag; 514} 515 516 517=item init_dirscan 518 519Initializes DIR, XS, PM, C, O_FILES, H, PL_FILES, MAN*PODS, EXE_FILES. 520 521=cut 522 523sub init_dirscan { # --- File and Directory Lists (.xs .pm .pod etc) 524 my($self) = @_; 525 my($name, %dir, %xs, %c, %h, %ignore, %pl_files, %manifypods); 526 local(%pm); #the sub in find() has to see this hash 527 528 # in case we don't find it below! 529 if ($self->{VERSION_FROM}) { 530 my $version_from = macify($self->{VERSION_FROM}); 531 $pm{$version_from} = $self->catfile('$(INST_LIBDIR)', 532 $version_from); 533 } 534 535 $ignore{'test.pl'} = 1; 536 foreach $name ($self->lsdir(":")){ 537 next if ($name =~ /^\./ or $ignore{$name}); 538 next unless $self->libscan($name); 539 if (-d $name){ 540 next if $self->{NORECURS}; 541 $dir{$name} = $name if (-f ":$name:Makefile.PL"); 542 } elsif ($name =~ /\.xs$/){ 543 my($c); ($c = $name) =~ s/\.xs$/.c/; 544 $xs{$name} = $c; 545 $c{$c} = 1; 546 } elsif ($name =~ /\.c(p|pp|xx|c)?$/i){ # .c .C .cpp .cxx .cc .cp 547 $c{$name} = 1 548 unless $name =~ m/perlmain\.c/; # See MAP_TARGET 549 } elsif ($name =~ /\.h$/i){ 550 $h{$name} = 1; 551 } elsif ($name =~ /\.(p[ml]|pod)$/){ 552 $pm{$name} = $self->catfile('$(INST_LIBDIR)',$name); 553 } elsif ($name =~ /\.PL$/ && $name ne "Makefile.PL") { 554 ($pl_files{$name} = $name) =~ s/\.PL$// ; 555 } 556 } 557 558 # Some larger extensions often wish to install a number of *.pm/pl 559 # files into the library in various locations. 560 561 # The attribute PMLIBDIRS holds an array reference which lists 562 # subdirectories which we should search for library files to 563 # install. PMLIBDIRS defaults to [ 'lib', $self->{BASEEXT} ]. We 564 # recursively search through the named directories (skipping any 565 # which don't exist or contain Makefile.PL files). 566 567 # For each *.pm or *.pl file found $self->libscan() is called with 568 # the default installation path in $_[1]. The return value of 569 # libscan defines the actual installation location. The default 570 # libscan function simply returns the path. The file is skipped 571 # if libscan returns false. 572 573 # The default installation location passed to libscan in $_[1] is: 574 # 575 # ./*.pm => $(INST_LIBDIR)/*.pm 576 # ./xyz/... => $(INST_LIBDIR)/xyz/... 577 # ./lib/... => $(INST_LIB)/... 578 # 579 # In this way the 'lib' directory is seen as the root of the actual 580 # perl library whereas the others are relative to INST_LIBDIR 581 # This is a subtle distinction but one that's important for nested 582 # modules. 583 584 $self->{PMLIBDIRS} = ['lib', $self->{BASEEXT}] 585 unless $self->{PMLIBDIRS}; 586 587 #only existing directories that aren't in $dir are allowed 588 589 my (@pmlibdirs) = map { macify ($_) } @{$self->{PMLIBDIRS}}; 590 my ($pmlibdir); 591 @{$self->{PMLIBDIRS}} = (); 592 foreach $pmlibdir (@pmlibdirs) { 593 -d $pmlibdir && !$dir{$pmlibdir} && push @{$self->{PMLIBDIRS}}, $pmlibdir; 594 } 595 596 if (@{$self->{PMLIBDIRS}}){ 597 print "Searching PMLIBDIRS: @{$self->{PMLIBDIRS}}\n" 598 if ($Verbose >= 2); 599 require File::Find; 600 File::Find::find(sub { 601 if (-d $_){ 602 unless ($self->libscan($_)){ 603 $File::Find::prune = 1; 604 } 605 return; 606 } 607 my($path, $prefix) = ($File::Find::name, '$(INST_LIBDIR)'); 608 my($striplibpath,$striplibname); 609 $prefix = '$(INST_LIB)' if (($striplibpath = $path) =~ s:^(\W*)lib\W:$1:); 610 ($striplibname,$striplibpath) = fileparse($striplibpath); 611 my($inst) = $self->catfile($prefix,$striplibpath,$striplibname); 612 local($_) = $inst; # for backwards compatibility 613 $inst = $self->libscan($inst); 614 print "libscan($path) => '$inst'\n" if ($Verbose >= 2); 615 return unless $inst; 616 $pm{$path} = $inst; 617 }, @{$self->{PMLIBDIRS}}); 618 } 619 620 $self->{DIR} = [sort keys %dir] unless $self->{DIR}; 621 $self->{XS} = \%xs unless $self->{XS}; 622 $self->{PM} = \%pm unless $self->{PM}; 623 $self->{C} = [sort keys %c] unless $self->{C}; 624 $self->{H} = [sort keys %h] unless $self->{H}; 625 $self->{PL_FILES} = \%pl_files unless $self->{PL_FILES}; 626 627 # Set up names of manual pages to generate from pods 628 unless ($self->{MAN1PODS}) { 629 $self->{MAN1PODS} = {}; 630 } 631 unless ($self->{MAN3PODS}) { 632 $self->{MAN3PODS} = {}; 633 } 634} 635 636 637=item init_VERSION (o) 638 639Change DEFINE_VERSION and XS_DEFINE_VERSION 640 641=cut 642 643sub init_VERSION { 644 my $self = shift; 645 646 $self->SUPER::init_VERSION; 647 648 $self->{DEFINE_VERSION} = '-d $(VERSION_MACRO)="�"$(VERSION)�""'; 649 $self->{XS_DEFINE_VERSION} = '-d $(XS_VERSION_MACRO)="�"$(XS_VERSION)�""'; 650} 651 652 653=item special_targets (o) 654 655Add .INCLUDE 656 657=cut 658 659sub special_targets { 660 my $self = shift; 661 662 my $make_frag = $self->SUPER::special_targets; 663 664 return $make_frag . <<'MAKE_FRAG'; 665.INCLUDE : $(MACPERL_SRC)BuildRules.mk $(MACPERL_SRC)ExtBuildRules.mk 666 667MAKE_FRAG 668 669} 670 671=item static (o) 672 673Defines the static target. 674 675=cut 676 677sub static { 678# --- Static Loading Sections --- 679 680 my($self) = shift; 681 my($extlib) = $self->{MYEXTLIB} ? "\nstatic :: myextlib\n" : ""; 682 ' 683all :: static 684 685install :: do_install_static 686 687install_static :: do_install_static 688' . $extlib; 689} 690 691=item dlsyms (o) 692 693Used by MacOS to define DL_FUNCS and DL_VARS and write the *.exp 694files. 695 696=cut 697 698sub dlsyms { 699 my($self,%attribs) = @_; 700 701 return '' unless !$self->{SKIPHASH}{'dynamic'}; 702 703 my($funcs) = $attribs{DL_FUNCS} || $self->{DL_FUNCS} || {}; 704 my($vars) = $attribs{DL_VARS} || $self->{DL_VARS} || []; 705 my(@m); 706 707 push(@m," 708dynamic :: $self->{BASEEXT}.exp 709 710") unless $self->{SKIPHASH}{'dynamic'}; 711 712 my($extlib) = $self->{MYEXTLIB} ? " myextlib" : ""; 713 714 push(@m," 715$self->{BASEEXT}.exp: Makefile.PL$extlib 716", qq[\t\$(PERL) "-I\$(PERL_LIB)" -e 'use ExtUtils::Mksymlists; ], 717 'Mksymlists("NAME" => "',$self->{NAME},'", "DL_FUNCS" => ', 718 neatvalue($funcs),', "DL_VARS" => ', neatvalue($vars), ');\' 719'); 720 721 join('',@m); 722} 723 724=item dynamic (o) 725 726Defines the dynamic target. 727 728=cut 729 730sub dynamic { 731# --- dynamic Loading Sections --- 732 733 my($self) = shift; 734 ' 735all :: dynamic 736 737install :: do_install_dynamic 738 739install_dynamic :: do_install_dynamic 740'; 741} 742 743 744=item clean (o) 745 746Defines the clean target. 747 748=cut 749 750sub clean { 751# --- Cleanup and Distribution Sections --- 752 753 my($self, %attribs) = @_; 754 my(@m,$dir); 755 push(@m, ' 756# Delete temporary files but do not touch installed files. We don\'t delete 757# the Makefile here so a later make realclean still has a makefile to use. 758 759clean :: clean_subdirs 760'); 761 762 my(@otherfiles) = values %{$self->{XS}}; # .c files from *.xs files 763 push(@otherfiles, patternify($attribs{FILES})) if $attribs{FILES}; 764 push @m, "\t\$(RM_RF) @otherfiles\n"; 765 # See realclean and ext/utils/make_ext for usage of Makefile.old 766 push(@m, 767 "\t\$(MV) \$(FIRST_MAKEFILE) \$(MAKEFILE_OLD)\n"); 768 push(@m, 769 "\t$attribs{POSTOP}\n") if $attribs{POSTOP}; 770 join("", @m); 771} 772 773=item clean_subdirs_target 774 775MacOS semantics for changing directories and checking for existence 776very different than everyone else. 777 778=cut 779 780sub clean_subdirs_target { 781 my($self) = shift; 782 783 # No subdirectories, no cleaning. 784 return <<'NOOP_FRAG' unless @{$self->{DIR}}; 785clean_subdirs : 786 $(NOECHO)$(NOOP) 787NOOP_FRAG 788 789 790 my $clean = "clean_subdirs :\n"; 791 792 for my $dir (@{$self->{DIR}}) { 793 $clean .= sprintf <<'MAKE_FRAG', $dir; 794 Set OldEcho {Echo} 795 Set Echo 0 796 Directory %s 797 If "`Exists -f $(FIRST_MAKEFILE)`" != "" 798 $(MAKE) clean 799 End 800 Set Echo {OldEcho} 801 802MAKE_FRAG 803 } 804 805 return $clean; 806} 807 808 809=item realclean (o) 810 811Defines the realclean target. 812 813=cut 814 815sub realclean { 816 my($self, %attribs) = @_; 817 my(@m); 818 push(@m,' 819# Delete temporary files (via clean) and also delete installed files 820realclean purge :: clean 821'); 822 823 my(@otherfiles) = ('$(FIRST_MAKEFILE)', '$(MAKEFILE_OLD)'); # Makefiles last 824 push(@otherfiles, patternify($attribs{FILES})) if $attribs{FILES}; 825 push(@m, "\t\$(RM_RF) @otherfiles\n") if @otherfiles; 826 push(@m, "\t$attribs{POSTOP}\n") if $attribs{POSTOP}; 827 join("", @m); 828} 829 830 831=item realclean_subdirs_target 832 833MacOS semantics for changing directories and checking for existence 834very different than everyone else. 835 836=cut 837 838sub realclean_subdirs_target { 839 my $self = shift; 840 841 return <<'NOOP_FRAG' unless @{$self->{DIR}}; 842realclean_subdirs : 843 $(NOECHO)$(NOOP) 844NOOP_FRAG 845 846 my $rclean = "realclean_subdirs :\n"; 847 848 foreach my $dir (@{$self->{DIR}}){ 849 $rclean .= sprintf <<'RCLEAN', $dir, 850 Set OldEcho \{Echo\} 851 Set Echo 0 852 Directory %s 853 If \"\`Exists -f $(FIRST_MAKEFILE)\`\" != \"\" 854 \$(MAKE) realclean 855 End 856 Set Echo \{OldEcho\} 857 858RCLEAN 859 860 } 861 862 return $rclean; 863} 864 865 866=item rulez (o) 867 868=cut 869 870sub rulez { 871 my($self) = shift; 872 qq' 873install install_static install_dynamic :: 874\t\$(MACPERL_SRC)PerlInstall -l \$(PERL_LIB) 875 876.INCLUDE : \$(MACPERL_SRC)BulkBuildRules.mk 877'; 878} 879 880 881=item processPL (o) 882 883Defines targets to run *.PL files. 884 885=cut 886 887sub processPL { 888 my($self) = shift; 889 return "" unless $self->{PL_FILES}; 890 my(@m, $plfile); 891 foreach $plfile (sort keys %{$self->{PL_FILES}}) { 892 my $list = ref($self->{PL_FILES}->{$plfile}) 893 ? $self->{PL_FILES}->{$plfile} 894 : [$self->{PL_FILES}->{$plfile}]; 895 foreach $target (@$list) { 896 push @m, " 897ProcessPL :: $target 898\t$(NOECHO)\$(NOOP) 899 900$target :: $plfile 901\t\$(PERL) -I\$(MACPERL_LIB) -I\$(PERL_LIB) $plfile $target 902"; 903 } 904 } 905 join "", @m; 906} 907 908sub cflags { 909 my($self,$libperl) = @_; 910 my $optimize = ''; 911 912 for (map { $_ . "Optimize" } qw(MWC MWCPPC MWC68K MPW MRC MRC SC)) { 913 $optimize .= "$_ = $self->{$_}" if exists $self->{$_}; 914 } 915 916 return $self->{CFLAGS} = $optimize; 917} 918 919 920sub _include { # for Unix-style includes, with -I instead of -i 921 my($inc) = @_; 922 require File::Spec::Unix; 923 924 # allow only relative paths 925 if (File::Spec::Unix->file_name_is_absolute($inc)) { 926 return ''; 927 } else { 928 return '-i ' . macify($inc); 929 } 930} 931 932=item os_flavor 933 934MacOS Classic is MacOS and MacOS Classic. 935 936=cut 937 938sub os_flavor { 939 return('MacOS', 'MacOS Classic'); 940} 941 942=back 943 944=cut 945 9461; 947