Commit | Line | Data |
---|---|---|
68dc0745 | 1 | package ExtUtils::MM_Win32; |
2 | ||
479d2113 MS |
3 | use strict; |
4 | ||
b75c8c73 | 5 | |
68dc0745 | 6 | =head1 NAME |
7 | ||
8 | ExtUtils::MM_Win32 - methods to override UN*X behaviour in ExtUtils::MakeMaker | |
9 | ||
10 | =head1 SYNOPSIS | |
11 | ||
12 | use ExtUtils::MM_Win32; # Done internally by ExtUtils::MakeMaker if needed | |
13 | ||
14 | =head1 DESCRIPTION | |
15 | ||
16 | See ExtUtils::MM_Unix for a documentation of the methods provided | |
17 | there. This package overrides the implementation of these methods, not | |
18 | the semantics. | |
19 | ||
68dc0745 | 20 | =cut |
21 | ||
7292dc67 | 22 | use ExtUtils::MakeMaker::Config; |
68dc0745 | 23 | use File::Basename; |
ecf68df6 | 24 | use File::Spec; |
f6d6199c | 25 | use ExtUtils::MakeMaker qw( neatvalue ); |
68dc0745 | 26 | |
f6d6199c MS |
27 | require ExtUtils::MM_Any; |
28 | require ExtUtils::MM_Unix; | |
a592ba15 | 29 | our @ISA = qw( ExtUtils::MM_Any ExtUtils::MM_Unix ); |
3d97da50 | 30 | our $VERSION = '6.56'; |
68dc0745 | 31 | |
32 | $ENV{EMXSHELL} = 'sh'; # to run `commands` | |
68dc0745 | 33 | |
a592ba15 | 34 | my $BORLAND = $Config{'cc'} =~ /^bcc/i ? 1 : 0; |
fa58a56f S |
35 | my $GCC = $Config{'cc'} =~ /\bgcc$/i ? 1 : 0; |
36 | my $DLLTOOL = $Config{'dlltool'} || 'dlltool'; | |
479d2113 MS |
37 | |
38 | ||
39 | =head2 Overridden methods | |
40 | ||
41 | =over 4 | |
42 | ||
43 | =item B<dlsyms> | |
44 | ||
45 | =cut | |
3e3baf6d | 46 | |
68dc0745 | 47 | sub dlsyms { |
48 | my($self,%attribs) = @_; | |
49 | ||
50 | my($funcs) = $attribs{DL_FUNCS} || $self->{DL_FUNCS} || {}; | |
51 | my($vars) = $attribs{DL_VARS} || $self->{DL_VARS} || []; | |
762efda7 | 52 | my($funclist) = $attribs{FUNCLIST} || $self->{FUNCLIST} || []; |
68dc0745 | 53 | my($imports) = $attribs{IMPORTS} || $self->{IMPORTS} || {}; |
54 | my(@m); | |
68dc0745 | 55 | |
56 | if (not $self->{SKIPHASH}{'dynamic'}) { | |
57 | push(@m," | |
58 | $self->{BASEEXT}.def: Makefile.PL | |
59 | ", | |
f6d6199c | 60 | q! $(PERLRUN) -MExtUtils::Mksymlists \\ |
5e687e55 NK |
61 | -e "Mksymlists('NAME'=>\"!, $self->{NAME}, |
62 | q!\", 'DLBASE' => '!,$self->{DLBASE}, | |
63 | # The above two lines quoted differently to work around | |
64 | # a bug in the 4DOS/4NT command line interpreter. The visible | |
65 | # result of the bug was files named q('extension_name',) *with the | |
66 | # single quotes and the comma* in the extension build directories. | |
68dc0745 | 67 | q!', 'DL_FUNCS' => !,neatvalue($funcs), |
762efda7 | 68 | q!, 'FUNCLIST' => !,neatvalue($funclist), |
68dc0745 | 69 | q!, 'IMPORTS' => !,neatvalue($imports), |
70 | q!, 'DL_VARS' => !, neatvalue($vars), q!);" | |
71 | !); | |
72 | } | |
73 | join('',@m); | |
74 | } | |
75 | ||
479d2113 MS |
76 | =item replace_manpage_separator |
77 | ||
78 | Changes the path separator with . | |
79 | ||
80 | =cut | |
81 | ||
68dc0745 | 82 | sub replace_manpage_separator { |
83 | my($self,$man) = @_; | |
84 | $man =~ s,/+,.,g; | |
85 | $man; | |
86 | } | |
87 | ||
479d2113 MS |
88 | |
89 | =item B<maybe_command> | |
90 | ||
91 | Since Windows has nothing as simple as an executable bit, we check the | |
92 | file extension. | |
93 | ||
94 | The PATHEXT env variable will be used to get a list of extensions that | |
95 | might indicate a command, otherwise .com, .exe, .bat and .cmd will be | |
96 | used by default. | |
97 | ||
98 | =cut | |
99 | ||
68dc0745 | 100 | sub maybe_command { |
101 | my($self,$file) = @_; | |
846f184a GS |
102 | my @e = exists($ENV{'PATHEXT'}) |
103 | ? split(/;/, $ENV{PATHEXT}) | |
104 | : qw(.com .exe .bat .cmd); | |
105 | my $e = ''; | |
106 | for (@e) { $e .= "\Q$_\E|" } | |
107 | chop $e; | |
108 | # see if file ends in one of the known extensions | |
2b2708c8 | 109 | if ($file =~ /($e)$/i) { |
846f184a GS |
110 | return $file if -e $file; |
111 | } | |
112 | else { | |
113 | for (@e) { | |
114 | return "$file$_" if -e "$file$_"; | |
115 | } | |
116 | } | |
68dc0745 | 117 | return; |
118 | } | |
119 | ||
68dc0745 | 120 | |
479d2113 MS |
121 | =item B<init_DIRFILESEP> |
122 | ||
123 | Using \ for Windows. | |
124 | ||
125 | =cut | |
126 | ||
127 | sub init_DIRFILESEP { | |
128 | my($self) = shift; | |
129 | ||
dedf98bc | 130 | # The ^ makes sure its not interpreted as an escape in nmake |
2e65e370 SH |
131 | $self->{DIRFILESEP} = $self->is_make_type('nmake') ? '^\\' : |
132 | $self->is_make_type('dmake') ? '\\\\' | |
133 | : '\\'; | |
68dc0745 | 134 | } |
135 | ||
479d2113 MS |
136 | =item B<init_others> |
137 | ||
138 | Override some of the Unix specific commands with portable | |
139 | ExtUtils::Command ones. | |
140 | ||
60537fc0 JH |
141 | Also provide defaults for LD and AR in case the %Config values aren't |
142 | set. | |
3e3baf6d | 143 | |
479d2113 | 144 | LDLOADLIBS's default is changed to $Config{libs}. |
3e3baf6d | 145 | |
479d2113 | 146 | Adjustments are made for Borland's quirks needing -L to come first. |
3e3baf6d TB |
147 | |
148 | =cut | |
149 | ||
479d2113 MS |
150 | sub init_others { |
151 | my ($self) = @_; | |
152 | ||
479d2113 | 153 | $self->{NOOP} ||= 'rem'; |
479d2113 MS |
154 | $self->{DEV_NULL} ||= '> NUL'; |
155 | ||
7292dc67 | 156 | $self->{FIXIN} ||= $self->{PERL_CORE} ? |
6383bd23 | 157 | "\$(PERLRUN) $self->{PERL_SRC}/win32/bin/pl2bat.pl" : |
7292dc67 RGS |
158 | 'pl2bat.bat'; |
159 | ||
5bdf71cc RGS |
160 | $self->{LD} ||= 'link'; |
161 | $self->{AR} ||= 'lib'; | |
479d2113 MS |
162 | |
163 | $self->SUPER::init_others; | |
164 | ||
dedf98bc MS |
165 | # Setting SHELL from $Config{sh} can break dmake. Its ok without it. |
166 | delete $self->{SHELL}; | |
167 | ||
479d2113 MS |
168 | $self->{LDLOADLIBS} ||= $Config{libs}; |
169 | # -Lfoo must come first for Borland, so we put it in LDDLFLAGS | |
170 | if ($BORLAND) { | |
171 | my $libs = $self->{LDLOADLIBS}; | |
172 | my $libpath = ''; | |
173 | while ($libs =~ s/(?:^|\s)(("?)-L.+?\2)(?:\s|$)/ /) { | |
174 | $libpath .= ' ' if length $libpath; | |
175 | $libpath .= $1; | |
176 | } | |
177 | $self->{LDLOADLIBS} = $libs; | |
178 | $self->{LDDLFLAGS} ||= $Config{lddlflags}; | |
179 | $self->{LDDLFLAGS} .= " $libpath"; | |
3e3baf6d TB |
180 | } |
181 | ||
479d2113 MS |
182 | return 1; |
183 | } | |
3e3baf6d | 184 | |
3e3baf6d | 185 | |
7292dc67 | 186 | =item init_platform |
3e3baf6d | 187 | |
479d2113 | 188 | Add MM_Win32_VERSION. |
3e3baf6d | 189 | |
7292dc67 | 190 | =item platform_constants |
3e3baf6d | 191 | |
479d2113 | 192 | =cut |
3e3baf6d | 193 | |
479d2113 MS |
194 | sub init_platform { |
195 | my($self) = shift; | |
3e3baf6d | 196 | |
479d2113 MS |
197 | $self->{MM_Win32_VERSION} = $VERSION; |
198 | } | |
3e3baf6d | 199 | |
479d2113 MS |
200 | sub platform_constants { |
201 | my($self) = shift; | |
202 | my $make_frag = ''; | |
3e3baf6d | 203 | |
479d2113 MS |
204 | foreach my $macro (qw(MM_Win32_VERSION)) |
205 | { | |
206 | next unless defined $self->{$macro}; | |
207 | $make_frag .= "$macro = $self->{$macro}\n"; | |
208 | } | |
3e3baf6d | 209 | |
479d2113 MS |
210 | return $make_frag; |
211 | } | |
3e3baf6d | 212 | |
3e3baf6d | 213 | |
7292dc67 | 214 | =item special_targets |
3e3baf6d | 215 | |
479d2113 | 216 | Add .USESHELL target for dmake. |
3e3baf6d | 217 | |
479d2113 | 218 | =cut |
3e3baf6d | 219 | |
479d2113 MS |
220 | sub special_targets { |
221 | my($self) = @_; | |
3e3baf6d | 222 | |
479d2113 | 223 | my $make_frag = $self->SUPER::special_targets; |
3e3baf6d | 224 | |
2e65e370 | 225 | $make_frag .= <<'MAKE_FRAG' if $self->is_make_type('dmake'); |
479d2113 MS |
226 | .USESHELL : |
227 | MAKE_FRAG | |
3e3baf6d | 228 | |
479d2113 | 229 | return $make_frag; |
3e3baf6d TB |
230 | } |
231 | ||
232 | ||
7292dc67 | 233 | =item static_lib |
68dc0745 | 234 | |
479d2113 MS |
235 | Changes how to run the linker. |
236 | ||
237 | The rest is duplicate code from MM_Unix. Should move the linker code | |
238 | to its own method. | |
68dc0745 | 239 | |
240 | =cut | |
241 | ||
242 | sub static_lib { | |
243 | my($self) = @_; | |
68dc0745 | 244 | return '' unless $self->has_link_code; |
245 | ||
246 | my(@m); | |
247 | push(@m, <<'END'); | |
7292dc67 | 248 | $(INST_STATIC): $(OBJECT) $(MYEXTLIB) $(INST_ARCHAUTODIR)$(DFSEP).exists |
68dc0745 | 249 | $(RM_RF) $@ |
250 | END | |
479d2113 | 251 | |
022735b4 | 252 | # If this extension has its own library (eg SDBM_File) |
68dc0745 | 253 | # then copy that to $(INST_STATIC) and add $(OBJECT) into it. |
479d2113 MS |
254 | push @m, <<'MAKE_FRAG' if $self->{MYEXTLIB}; |
255 | $(CP) $(MYEXTLIB) $@ | |
256 | MAKE_FRAG | |
68dc0745 | 257 | |
258 | push @m, | |
910dfcc8 GS |
259 | q{ $(AR) }.($BORLAND ? '$@ $(OBJECT:^"+")' |
260 | : ($GCC ? '-ru $@ $(OBJECT)' | |
261 | : '-out:$@ $(OBJECT)')).q{ | |
479d2113 MS |
262 | $(CHMOD) $(PERM_RWX) $@ |
263 | $(NOECHO) $(ECHO) "$(EXTRALIBS)" > $(INST_ARCHAUTODIR)\extralibs.ld | |
68dc0745 | 264 | }; |
265 | ||
479d2113 MS |
266 | # Old mechanism - still available: |
267 | push @m, <<'MAKE_FRAG' if $self->{PERL_SRC} && $self->{EXTRALIBS}; | |
268 | $(NOECHO) $(ECHO) "$(EXTRALIBS)" >> $(PERL_SRC)\ext.libs | |
269 | MAKE_FRAG | |
68dc0745 | 270 | |
479d2113 | 271 | join('', @m); |
68dc0745 | 272 | } |
273 | ||
68dc0745 | 274 | |
7292dc67 | 275 | =item dynamic_lib |
68dc0745 | 276 | |
479d2113 | 277 | Complicated stuff for Win32 that I don't understand. :( |
68dc0745 | 278 | |
279 | =cut | |
280 | ||
281 | sub dynamic_lib { | |
282 | my($self, %attribs) = @_; | |
283 | return '' unless $self->needs_linking(); #might be because of a subdir | |
284 | ||
285 | return '' unless $self->has_link_code; | |
286 | ||
3e3baf6d | 287 | my($otherldflags) = $attribs{OTHERLDFLAGS} || ($BORLAND ? 'c0d32.obj': ''); |
68dc0745 | 288 | my($inst_dynamic_dep) = $attribs{INST_DYNAMIC_DEP} || ""; |
289 | my($ldfrom) = '$(LDFROM)'; | |
290 | my(@m); | |
7a958ec3 | 291 | |
5db10396 GS |
292 | # one thing for GCC/Mingw32: |
293 | # we try to overcome non-relocateable-DLL problems by generating | |
7a958ec3 BS |
294 | # a (hopefully unique) image-base from the dll's name |
295 | # -- BKS, 10-19-1999 | |
296 | if ($GCC) { | |
7a958ec3 BS |
297 | my $dllname = $self->{BASEEXT} . "." . $self->{DLEXT}; |
298 | $dllname =~ /(....)(.{0,4})/; | |
299 | my $baseaddr = unpack("n", $1 ^ $2); | |
300 | $otherldflags .= sprintf("-Wl,--image-base,0x%x0000 ", $baseaddr); | |
301 | } | |
302 | ||
68dc0745 | 303 | push(@m,' |
304 | # This section creates the dynamically loadable $(INST_DYNAMIC) | |
305 | # from $(OBJECT) and possibly $(MYEXTLIB). | |
306 | OTHERLDFLAGS = '.$otherldflags.' | |
307 | INST_DYNAMIC_DEP = '.$inst_dynamic_dep.' | |
308 | ||
7292dc67 | 309 | $(INST_DYNAMIC): $(OBJECT) $(MYEXTLIB) $(BOOTSTRAP) $(INST_ARCHAUTODIR)$(DFSEP).exists $(EXPORT_LIST) $(PERL_ARCHIVE) $(INST_DYNAMIC_DEP) |
68dc0745 | 310 | '); |
5b0d9cbe NIS |
311 | if ($GCC) { |
312 | push(@m, | |
fa58a56f | 313 | q{ }.$DLLTOOL.q{ --def $(EXPORT_LIST) --output-exp dll.exp |
910dfcc8 | 314 | $(LD) -o $@ -Wl,--base-file -Wl,dll.base $(LDDLFLAGS) }.$ldfrom.q{ $(OTHERLDFLAGS) $(MYEXTLIB) $(PERL_ARCHIVE) $(LDLOADLIBS) dll.exp |
fa58a56f | 315 | }.$DLLTOOL.q{ --def $(EXPORT_LIST) --base-file dll.base --output-exp dll.exp |
5b0d9cbe | 316 | $(LD) -o $@ $(LDDLFLAGS) }.$ldfrom.q{ $(OTHERLDFLAGS) $(MYEXTLIB) $(PERL_ARCHIVE) $(LDLOADLIBS) dll.exp }); |
dc0d354b GS |
317 | } elsif ($BORLAND) { |
318 | push(@m, | |
319 | q{ $(LD) $(LDDLFLAGS) $(OTHERLDFLAGS) }.$ldfrom.q{,$@,,} | |
2e65e370 | 320 | .($self->is_make_type('dmake') |
2977d345 | 321 | ? q{$(PERL_ARCHIVE:s,/,\,) $(LDLOADLIBS:s,/,\,) } |
dc0d354b GS |
322 | .q{$(MYEXTLIB:s,/,\,),$(EXPORT_LIST:s,/,\,)} |
323 | : q{$(subst /,\,$(PERL_ARCHIVE)) $(subst /,\,$(LDLOADLIBS)) } | |
324 | .q{$(subst /,\,$(MYEXTLIB)),$(subst /,\,$(EXPORT_LIST))}) | |
325 | .q{,$(RESFILES)}); | |
326 | } else { # VC | |
327 | push(@m, | |
328 | q{ $(LD) -out:$@ $(LDDLFLAGS) }.$ldfrom.q{ $(OTHERLDFLAGS) } | |
329 | .q{$(MYEXTLIB) $(PERL_ARCHIVE) $(LDLOADLIBS) -def:$(EXPORT_LIST)}); | |
277189c8 | 330 | |
2f30d0d0 NC |
331 | # Embed the manifest file if it exists |
332 | push(@m, q{ | |
89f6f7bc SH |
333 | if exist $@.manifest mt -nologo -manifest $@.manifest -outputresource:$@;2 |
334 | if exist $@.manifest del $@.manifest}); | |
5b0d9cbe | 335 | } |
68dc0745 | 336 | push @m, ' |
479d2113 | 337 | $(CHMOD) $(PERM_RWX) $@ |
68dc0745 | 338 | '; |
339 | ||
68dc0745 | 340 | join('',@m); |
341 | } | |
342 | ||
7292dc67 | 343 | =item extra_clean_files |
479d2113 MS |
344 | |
345 | Clean out some extra dll.{base,exp} files which might be generated by | |
346 | gcc. Otherwise, take out all *.pdb files. | |
347 | ||
348 | =cut | |
349 | ||
7292dc67 RGS |
350 | sub extra_clean_files { |
351 | my $self = shift; | |
562c1c19 | 352 | |
7292dc67 | 353 | return $GCC ? (qw(dll.base dll.exp)) : ('*.pdb'); |
562c1c19 NIS |
354 | } |
355 | ||
479d2113 | 356 | =item init_linker |
562c1c19 | 357 | |
479d2113 | 358 | =cut |
562c1c19 | 359 | |
479d2113 MS |
360 | sub init_linker { |
361 | my $self = shift; | |
68dc0745 | 362 | |
479d2113 MS |
363 | $self->{PERL_ARCHIVE} = "\$(PERL_INC)\\$Config{libperl}"; |
364 | $self->{PERL_ARCHIVE_AFTER} = ''; | |
365 | $self->{EXPORT_LIST} = '$(BASEEXT).def'; | |
68dc0745 | 366 | } |
367 | ||
45bc4d3a | 368 | |
68dc0745 | 369 | =item perl_script |
370 | ||
479d2113 | 371 | Checks for the perl program under several common perl extensions. |
68dc0745 | 372 | |
373 | =cut | |
374 | ||
375 | sub perl_script { | |
376 | my($self,$file) = @_; | |
cae6c631 | 377 | return $file if -r $file && -f _; |
479d2113 MS |
378 | return "$file.pl" if -r "$file.pl" && -f _; |
379 | return "$file.plx" if -r "$file.plx" && -f _; | |
cae6c631 | 380 | return "$file.bat" if -r "$file.bat" && -f _; |
68dc0745 | 381 | return; |
382 | } | |
383 | ||
3e3baf6d | 384 | |
7292dc67 | 385 | =item xs_o |
68dc0745 | 386 | |
479d2113 | 387 | This target is stubbed out. Not sure why. |
68dc0745 | 388 | |
389 | =cut | |
390 | ||
479d2113 MS |
391 | sub xs_o { |
392 | return '' | |
68dc0745 | 393 | } |
394 | ||
68dc0745 | 395 | |
7292dc67 | 396 | =item pasthru |
68dc0745 | 397 | |
479d2113 MS |
398 | All we send is -nologo to nmake to prevent it from printing its damned |
399 | banner. | |
68dc0745 | 400 | |
401 | =cut | |
402 | ||
479d2113 | 403 | sub pasthru { |
68dc0745 | 404 | my($self) = shift; |
2e65e370 | 405 | return "PASTHRU = " . ($self->is_make_type('nmake') ? "-nologo" : ""); |
071e6b84 | 406 | } |
68dc0745 | 407 | |
3e3baf6d | 408 | |
5bdf71cc RGS |
409 | =item arch_check (override) |
410 | ||
411 | Normalize all arguments for consistency of comparison. | |
412 | ||
413 | =cut | |
414 | ||
415 | sub arch_check { | |
416 | my $self = shift; | |
417 | ||
c0956255 RGS |
418 | # Win32 is an XS module, minperl won't have it. |
419 | # arch_check() is not critical, so just fake it. | |
420 | return 1 unless $self->can_load_xs; | |
b6d6132c DM |
421 | return $self->SUPER::arch_check( map { $self->_normalize_path_name($_) } @_); |
422 | } | |
423 | ||
424 | sub _normalize_path_name { | |
425 | my $self = shift; | |
426 | my $file = shift; | |
c0956255 | 427 | |
5bdf71cc | 428 | require Win32; |
b6d6132c DM |
429 | my $short = Win32::GetShortPathName($file); |
430 | return defined $short ? lc $short : lc $file; | |
5bdf71cc RGS |
431 | } |
432 | ||
433 | ||
7292dc67 | 434 | =item oneliner |
3e3baf6d | 435 | |
479d2113 MS |
436 | These are based on what command.com does on Win98. They may be wrong |
437 | for other Windows shells, I don't know. | |
3e3baf6d TB |
438 | |
439 | =cut | |
440 | ||
479d2113 MS |
441 | sub oneliner { |
442 | my($self, $cmd, $switches) = @_; | |
443 | $switches = [] unless defined $switches; | |
3e3baf6d | 444 | |
479d2113 MS |
445 | # Strip leading and trailing newlines |
446 | $cmd =~ s{^\n+}{}; | |
447 | $cmd =~ s{\n+$}{}; | |
3e3baf6d | 448 | |
479d2113 MS |
449 | $cmd = $self->quote_literal($cmd); |
450 | $cmd = $self->escape_newlines($cmd); | |
3e3baf6d | 451 | |
479d2113 | 452 | $switches = join ' ', @$switches; |
3e3baf6d | 453 | |
2977d345 | 454 | return qq{\$(ABSPERLRUN) $switches -e $cmd --}; |
3e3baf6d TB |
455 | } |
456 | ||
68dc0745 | 457 | |
479d2113 MS |
458 | sub quote_literal { |
459 | my($self, $text) = @_; | |
68dc0745 | 460 | |
479d2113 MS |
461 | # I don't know if this is correct, but it seems to work on |
462 | # Win98's command.com | |
463 | $text =~ s{"}{\\"}g; | |
68dc0745 | 464 | |
dedf98bc MS |
465 | # dmake eats '{' inside double quotes and leaves alone { outside double |
466 | # quotes; however it transforms {{ into { either inside and outside double | |
467 | # quotes. It also translates }} into }. The escaping below is not | |
468 | # 100% correct. | |
2e65e370 | 469 | if( $self->is_make_type('dmake') ) { |
dedf98bc MS |
470 | $text =~ s/{/{{/g; |
471 | $text =~ s/}}/}}}/g; | |
472 | } | |
473 | ||
479d2113 | 474 | return qq{"$text"}; |
68dc0745 | 475 | } |
476 | ||
68dc0745 | 477 | |
479d2113 MS |
478 | sub escape_newlines { |
479 | my($self, $text) = @_; | |
68dc0745 | 480 | |
479d2113 MS |
481 | # Escape newlines |
482 | $text =~ s{\n}{\\\n}g; | |
68dc0745 | 483 | |
479d2113 | 484 | return $text; |
68dc0745 | 485 | } |
486 | ||
68dc0745 | 487 | |
7292dc67 RGS |
488 | =item cd |
489 | ||
490 | dmake can handle Unix style cd'ing but nmake (at least 1.5) cannot. It | |
491 | wants: | |
492 | ||
5bdf71cc | 493 | cd dir1\dir2 |
7292dc67 RGS |
494 | command |
495 | another_command | |
5bdf71cc | 496 | cd ..\.. |
7292dc67 RGS |
497 | |
498 | =cut | |
499 | ||
500 | sub cd { | |
501 | my($self, $dir, @cmds) = @_; | |
502 | ||
2e65e370 | 503 | return $self->SUPER::cd($dir, @cmds) unless $self->is_make_type('nmake'); |
7292dc67 RGS |
504 | |
505 | my $cmd = join "\n\t", map "$_", @cmds; | |
506 | ||
277189c8 SP |
507 | my $updirs = $self->catdir(map { $self->updir } $self->splitdir($dir)); |
508 | ||
7292dc67 | 509 | # No leading tab and no trailing newline makes for easier embedding. |
277189c8 | 510 | my $make_frag = sprintf <<'MAKE_FRAG', $dir, $cmd, $updirs; |
7292dc67 RGS |
511 | cd %s |
512 | %s | |
277189c8 | 513 | cd %s |
7292dc67 RGS |
514 | MAKE_FRAG |
515 | ||
516 | chomp $make_frag; | |
517 | ||
518 | return $make_frag; | |
519 | } | |
520 | ||
521 | ||
479d2113 | 522 | =item max_exec_len |
68dc0745 | 523 | |
2c91f887 | 524 | nmake 1.50 limits command length to 2048 characters. |
68dc0745 | 525 | |
526 | =cut | |
527 | ||
479d2113 MS |
528 | sub max_exec_len { |
529 | my $self = shift; | |
530 | ||
2c91f887 | 531 | return $self->{_MAX_EXEC_LEN} ||= 2 * 1024; |
68dc0745 | 532 | } |
533 | ||
534 | ||
dedf98bc MS |
535 | =item os_flavor |
536 | ||
537 | Windows is Win32. | |
538 | ||
539 | =cut | |
540 | ||
541 | sub os_flavor { | |
542 | return('Win32'); | |
543 | } | |
544 | ||
545 | ||
8b503b1a SH |
546 | =item cflags |
547 | ||
548 | Defines the PERLDLL symbol if we are configured for static building since all | |
549 | code destined for the perl5xx.dll must be compiled with the PERLDLL symbol | |
550 | defined. | |
551 | ||
552 | =cut | |
553 | ||
554 | sub cflags { | |
555 | my($self,$libperl)=@_; | |
556 | return $self->{CFLAGS} if $self->{CFLAGS}; | |
557 | return '' unless $self->needs_linking(); | |
558 | ||
559 | my $base = $self->SUPER::cflags($libperl); | |
560 | foreach (split /\n/, $base) { | |
561 | /^(\S*)\s*=\s*(\S*)$/ and $self->{$1} = $2; | |
562 | }; | |
563 | $self->{CCFLAGS} .= " -DPERLDLL" if ($self->{LINKTYPE} eq 'static'); | |
564 | ||
565 | return $self->{CFLAGS} = qq{ | |
566 | CCFLAGS = $self->{CCFLAGS} | |
567 | OPTIMIZE = $self->{OPTIMIZE} | |
568 | PERLTYPE = $self->{PERLTYPE} | |
569 | }; | |
570 | ||
571 | } | |
572 | ||
2e65e370 SH |
573 | sub is_make_type { |
574 | my($self, $type) = @_; | |
575 | return !! ($self->make =~ /\b$type(?:\.exe)?$/); | |
576 | } | |
577 | ||
68dc0745 | 578 | 1; |
579 | __END__ | |
580 | ||
581 | =back | |
582 | ||
583 | =cut | |
584 | ||
5b0d9cbe | 585 |