abort under automated testing if we can't find threads support code
[imager.git] / Makefile.PL
1 #!perl -w
2 use strict;
3 use ExtUtils::MakeMaker;
4 use Cwd;
5 use Config;
6 use File::Spec;
7 use Getopt::Long;
8 use ExtUtils::Manifest qw(maniread);
9 use ExtUtils::Liblist;
10 use vars qw(%formats $VERBOSE $INCPATH $LIBPATH $NOLOG $DEBUG_MALLOC $MANUAL $CFLAGS $LFLAGS $DFLAGS);
11 use lib 'inc';
12 use Devel::CheckLib;
13
14 # EU::MM runs Makefile.PL all in the same process, so sub-modules will
15 # see this
16 our $BUILDING_IMAGER = 1;
17
18 # used to display a summary after we've probed the world
19 our %IMAGER_LIBS;
20
21 #
22 # IM_INCPATH      colon seperated list of paths to extra include paths
23 # IM_LIBPATH      colon seperated list of paths to extra library paths
24 #
25 # IM_VERBOSE      turns on verbose mode for the library finding and such
26 # IM_MANUAL       to manually select which libraries are used and which not
27 # IM_ENABLE       to programmatically select which libraries are used
28 #                 and which are not
29 # IM_NOLOG        if true logging will not be compiled into the module
30 # IM_DEBUG_MALLOC if true malloc debbuging will be compiled into the module
31 #                 do not use IM_DEBUG_MALLOC in production - this slows
32 #                 everything down by alot
33 # IM_CFLAGS       Extra flags to pass to the compiler
34 # IM_LFLAGS       Extra flags to pass to the linker
35 # IM_DFLAGS       Extra flags to pass to the preprocessor
36
37 my $KEEP_FILES = $ENV{IMAGER_KEEP_FILES};
38
39 getenv();     # get environment variables
40
41 my $lext=$Config{'so'};   # Get extensions of libraries
42 my $aext=$Config{'_a'};
43
44 my $help; # display help if set
45 my @enable; # list of drivers to enable
46 my @disable; # or list of drivers to disable
47 my @incpaths; # places to look for headers
48 my @libpaths; # places to look for libraries
49 my $coverage; # build for coverage testing
50 my $assert; # build with assertions
51 my $trace_context; # trace context management to stderr
52 GetOptions("help" => \$help,
53            "enable=s" => \@enable,
54            "disable=s" => \@disable,
55            "incpath=s", \@incpaths,
56            "libpath=s" => \@libpaths,
57            "verbose|v" => \$VERBOSE,
58            "nolog" => \$NOLOG,
59            'coverage' => \$coverage,
60            "assert|a" => \$assert,
61            "tracecontext" => \$trace_context);
62
63 setenv();
64
65 if ($ENV{AUTOMATED_TESTING}) {
66   $assert = 1;
67 }
68
69 if ($VERBOSE) { 
70   print "Verbose mode\n"; 
71   require Data::Dumper; 
72   import Data::Dumper qw(Dumper);
73 }
74
75 if ($help) {
76   usage();
77 }
78
79 my @defines;
80
81 if ($NOLOG)   { print "Logging not compiled into module\n"; }
82 else { 
83   push @defines, [ IMAGER_LOG => 1, "Logging system" ];
84 }
85
86 if ($assert) {
87   push @defines, [ IM_ASSERT => 1, "im_assert() are effective" ];
88 }
89
90 if ($DEBUG_MALLOC) {
91   push @defines, [ IMAGER_DEBUG_MALLOC => 1, "Use Imager's DEBUG malloc()" ];
92   print "Malloc debugging enabled\n";
93 }
94
95 if (@enable && @disable) {
96   print STDERR "Only --enable or --disable can be used, not both, try --help\n";
97   exit 1;
98 }
99
100 my %definc;
101 my %deflib;
102 my @incs; # all the places to look for headers
103 my @libs; # all the places to look for libraries
104
105 init();       # initialize global data
106 pathcheck();  # Check if directories exist
107
108 if (exists $ENV{IM_ENABLE}) {
109   my %en = map { $_, 1 } split ' ', $ENV{IM_ENABLE};
110   for my $key (keys %formats) {
111     delete $formats{$key} unless $en{$key};
112   }
113 }
114 if (@enable) {
115   my %en = map { $_ => 1 } map { split /,/ } @enable;
116   for my $key (keys %formats) {
117     delete $formats{$key} unless $en{$key};
118   }
119 }
120 elsif (@disable) {
121   delete @formats{map { split /,/ } @disable};
122 }
123
124 # Pick what libraries are used
125 if ($MANUAL) {
126   manual();
127 } else {
128   automatic();
129 }
130
131 my $lib_cflags = '';
132 my $lib_lflags = '';
133 my $F_LIBS = '';
134 my $F_OBJECT = '';
135 for my $frmkey (sort { $formats{$a}{order} <=> $formats{$b}{order} } keys %formats) {
136   my $frm = $formats{$frmkey};
137   push @defines, [ $frm->{def}, 1, "$frmkey available" ];
138   $F_OBJECT .= ' '  .$frm->{objfiles};
139   if ($frm->{cflags}) {
140     $lib_cflags   .= ' '  .$frm->{cflags};
141     ++$definc{$_} for map { /^-I(.*)$/ ? ($1) : () }
142       grep /^-I./, split ' ', $frm->{cflags};
143   }
144   if ($frm->{lflags}) {
145     $lib_lflags .= ' ' . $frm->{lflags};
146   }
147   else {
148     $F_LIBS   .= ' '  .$frm->{libfiles};
149   }
150
151 }
152
153 my $F_INC  = join ' ', map "-I$_", map / / ? qq{"$_"} : $_, 
154   grep !$definc{$_}, @incs;
155 $F_LIBS = join(' ',map "-L$_", map / / ? qq{"$_"} : $_, 
156                grep !$deflib{$_}++, @libs) . $F_LIBS;
157
158 my $OSLIBS = '';
159 my $OSDEF  = "-DOS_$^O";
160
161 if ($^O eq 'hpux')                { $OSLIBS .= ' -ldld'; }
162 if (defined $Config{'d_dlsymun'}) { $OSDEF  .= ' -DDLSYMUN'; }
163
164 my @objs = qw(Imager.o context.o draw.o polygon.o image.o io.o iolayer.o
165               log.o gaussian.o conv.o pnm.o raw.o feat.o combine.o
166               filters.o dynaload.o stackmach.o datatypes.o
167               regmach.o trans2.o quant.o error.o convert.o
168               map.o tags.o palimg.o maskimg.o img8.o img16.o rotate.o
169               bmp.o tga.o color.o fills.o imgdouble.o limits.o hlines.o
170               imext.o scale.o rubthru.o render.o paste.o compose.o flip.o);
171
172 if ($Config{useithreads}) {
173   if ($Config{i_pthread}) {
174     print "POSIX threads\n";
175     push @objs, "mutexpthr.o";
176   }
177   elsif ($^O eq 'MSWin32') {
178     print "Win32 threads\n";
179     push @objs, "mutexwin.o";
180   }
181   else {
182     print "Unsupported threading model\n";
183     push @objs, "mutexnull.o";
184     if ($ENV{AUTOMATED_TESTING}) {
185       die "OS unsupported: no threading support code for this platform\n";
186     }
187   }
188 }
189 else {
190   print "No threads\n";
191   push @objs, "mutexnull.o";
192 }
193
194 my @typemaps = qw(typemap.local typemap);
195 if ($] < 5.008) {
196     unshift @typemaps, "typemap.oldperl";
197 }
198
199 if ($trace_context) {
200   $CFLAGS .= " -DIMAGER_TRACE_CONTEXT";
201 }
202
203 my %opts=
204   (
205    'NAME'         => 'Imager',
206    'VERSION_FROM' => 'Imager.pm',
207    'LIBS'         => "$LFLAGS -lm $lib_lflags $OSLIBS $F_LIBS",
208    'DEFINE'       => "$OSDEF $CFLAGS",
209    'INC'          => "$lib_cflags $DFLAGS $F_INC",
210    'OBJECT'       => join(' ', @objs, $F_OBJECT),
211    clean          => { FILES=>'testout rubthru.c scale.c conv.c  filters.c gaussian.c render.c rubthru.c' },
212    PM             => gen_PM(),
213    PREREQ_PM      =>
214    { 
215     'Test::More' => 0.47,
216     'Scalar::Util' => 1.00,
217     'XSLoader'    => 0,
218    },
219    TYPEMAPS       => \@typemaps,
220   );
221
222 if ($coverage) {
223     if ($Config{gccversion}) {
224         push @ARGV, 'OPTIMIZE=-ftest-coverage -fprofile-arcs -g';
225         $opts{dynamic_lib} = { OTHERLDFLAGS => '-ftest-coverage -fprofile-arcs' };
226     }
227     else {
228         die "Don't know the coverage C flags for your compiler\n";
229     }
230 }
231
232 # eval to prevent warnings about versions with _ in them
233 my $MM_ver = eval $ExtUtils::MakeMaker::VERSION;
234 if ($MM_ver > 6.06) {
235   $opts{AUTHOR} = 'Tony Cook <tonyc@cpan.org>, Arnar M. Hrafnkelsson';
236   $opts{ABSTRACT} = 'Perl extension for Generating 24 bit Images';
237 }
238
239 if ($MM_ver >= 6.46) {
240   $opts{META_MERGE} =
241     {
242      recommends =>
243      {
244       "Parse::RecDescent" => 0
245      },
246      license => "perl",
247      dynamic_config => 1,
248      no_index =>
249      {
250       directory =>
251       [
252        "PNG",
253        "GIF",
254        "TIFF",
255        "JPEG",
256        "W32",
257        "FT2",
258        "T1",
259       ],
260      },
261      resources =>
262      {
263       homepage => "http://imager.perl.org/",
264       repository => "git://git.imager.perl.org/imager.git",
265       bugtracker => "http://rt.cpan.org/NoAuth/Bugs.html?Dist=Imager",
266      },
267     };
268 }
269
270 make_imconfig(\@defines);
271
272 if ($VERBOSE) { print Dumper(\%opts); }
273 mkdir('testout',0777); # since we cannot include it in the archive.
274
275 -d "probe" and rmdir "probe";
276
277 WriteMakefile(%opts);
278
279 my @good;
280 my @bad;
281 for my $name (sort { lc $a cmp lc $b } keys %IMAGER_LIBS) {
282   if ($IMAGER_LIBS{$name}) {
283     push @good, $name;
284   }
285   else {
286     push @bad, $name;
287   }
288 }
289
290 print "\n";
291 print "Libraries found:\n" if @good;
292 print "  $_\n" for @good;
293 print "Libraries *not* found:\n" if @bad;
294 print "  $_\n" for @bad;
295
296 exit;
297
298
299 sub MY::postamble {
300     my $self = shift;
301     my $perl = $self->{PERLRUN} ? '$(PERLRUN)' : '$(PERL)';
302     my $mani = maniread;
303
304     my @ims = grep /\.im$/, keys %$mani;
305 '
306 dyntest.$(MYEXTLIB) : dynfilt/Makefile
307         cd dynfilt && $(MAKE) $(PASTHRU)
308
309 lib/Imager/Regops.pm : regmach.h regops.perl
310         $(PERL) regops.perl regmach.h lib/Imager/Regops.pm
311
312 imconfig.h : Makefile.PL
313         $(ECHO) "imconfig.h out-of-date with respect to $?"
314         $(PERLRUN) Makefile.PL
315         $(ECHO) "==> Your Makefile has been rebuilt - re-run your make command <=="
316 '.qq!
317 lib/Imager/APIRef.pod : \$(C_FILES) \$(H_FILES) apidocs.perl
318         $perl apidocs.perl lib/Imager/APIRef.pod
319
320 !.join('', map _im_rule($perl, $_), @ims)
321
322 }
323
324 sub _im_rule {
325   my ($perl, $im) = @_;
326
327   (my $c = $im) =~ s/\.im$/.c/;
328   return <<MAKE;
329
330 $c: $im lib/Imager/Preprocess.pm
331         $perl -Ilib -MImager::Preprocess -epreprocess $im $c
332
333 MAKE
334
335 }
336
337 # manual configuration of helper libraries
338
339 sub manual {
340   print <<EOF;
341
342       Please answer the following questions about
343       which formats are avaliable on your computer
344
345 press <return> to continue
346 EOF
347
348   <STDIN>; # eat one return
349
350   for my $frm(sort { $formats{$b}{order} <=> $formats{$a}{order} } keys %formats) {
351   SWX:
352     if ($formats{$frm}{docs}) { print "\n",$formats{$frm}{docs},"\n\n"; }
353     print "Enable $frm support: ";
354     my $gz = <STDIN>;
355     chomp($gz);
356     if ($gz =~ m/^(y|yes|n|no)/i) {
357       $gz=substr(lc($gz),0,1);
358       if ($gz eq 'n') {
359         delete $formats{$frm};
360       }
361     } else { goto SWX; }
362   }
363 }
364
365
366 # automatic configuration of helper libraries
367
368 sub automatic {
369   print "Automatic probing:\n" if $VERBOSE;
370   for my $frm (sort { $formats{$a}{order} <=> $formats{$b}{order} } keys %formats) {
371     delete $formats{$frm} if !checkformat($frm);        
372   }
373 }
374
375 sub grep_directory {
376   my($path, $chk)=@_;
377
378 #    print "checking path $path\n";
379   if ( !opendir(DH,$path) ) {
380     warn "Cannot open dir $path: $!\n";
381     return;
382   }
383   my @l=grep { $chk->($_) } readdir(DH);
384   #    print @l;
385   close(DH);
386   return map $path, @l;
387 }
388
389 sub _probe_default {
390   my ($format, $frm) = @_;
391
392   my $lib_check=$formats{$frm}{'libcheck'};
393   my $inc_check=$formats{$frm}{'inccheck'};
394
395   if ($lib_check) {
396     my @l;
397     for my $lp (@libs) {
398       push(@l, grep_directory($lp,$lib_check));
399     }
400     
401     my @i;
402     for my $ip (@incs) {
403       push(@i, $ip) if $inc_check->($ip,$frm);
404     }
405     
406     printf("%10s: includes %s - libraries %s\n",$frm,(@i?'found':'not found'),(@l?'found':'not found'));
407     $formats{$frm}{incdir} = \@i;
408     $formats{$frm}{libdir} = \@l;
409     return 1 if scalar(@i && @l);
410   }
411   else {
412     printf("%10s: not available\n", $frm);
413   }
414
415   return 0;
416 }
417
418 sub checkformat {
419   my $frm=shift;
420
421   print "  checkformat($frm)\n" if $VERBOSE;
422   
423   my $format = $formats{$frm};
424
425   my @probes;
426   if (my $code = $format->{'code'}) {
427     if (ref $code eq 'ARRAY') {
428       push @probes, @$code;
429     }
430     else {
431       push @probes, $code;
432     }
433   }
434   push @probes, \&_probe_default;
435
436   print "    Calling probe function\n" if $VERBOSE;
437   my $found;
438   for my $func (@probes) {
439     if ($func->($format, $frm)) {
440       ++$found;
441       last;
442     }
443   }
444
445   $found or return;
446
447   if ($format->{postcheck}) {
448     print "    Calling postcheck function\n" if $VERBOSE;
449     $format->{postcheck}->($format, $frm)
450       or return;
451   }
452
453   return 1;
454 }
455
456
457 sub pathcheck {
458   if ($VERBOSE) {
459     print "pathcheck\n";
460     print "  Include paths:\n";
461     for (@incs) { print $_,"\n"; }
462   }
463   @incs=grep { -d $_ && -r _ && -x _ or ( print("  $_ doesnt exist or is unaccessible - removed.\n"),0) } @incs;
464
465   if ($VERBOSE) {
466     print "\nLibrary paths:\n";
467     for (@libs) { print $_,"\n"; }
468   }
469   @libs=grep { -d $_ && -r _ && -x _ or ( print("  $_ doesnt exist or is unaccessible - removed.\n"),0) } @libs;
470   print "\ndone.\n";
471 }
472
473
474 # Format data initialization
475
476 # format definition is:
477 # defines needed
478 # default include path
479 # files needed for include (boolean perl code)
480 # default lib path
481 # libs needed
482 # files needed for link (boolean perl code)
483 # object files needed for the format
484
485
486 sub init {
487
488   my @definc = qw(/usr/include);
489   @definc{@definc}=(1) x @definc;
490   @incs=
491     (
492      split(/\Q$Config{path_sep}/, $INCPATH),
493      map _tilde_expand($_), map { split /\Q$Config{path_sep}/ } @incpaths 
494     );
495   if ($Config{locincpth}) {
496     push @incs, grep -d, split ' ', $Config{locincpth};
497   }
498   if ($^O =~ /win32/i && $Config{cc} =~ /\bcl\b/i) {
499     push(@incs, split /;/, $ENV{INCLUDE}) if exists $ENV{INCLUDE};
500   }
501   if ($Config{incpath}) {
502     push @incs, grep -d, split /\Q$Config{path_sep}/, $Config{incpath};
503   }
504   push @incs, grep -d,
505       qw(/sw/include 
506          /usr/include/freetype2
507          /usr/local/include/freetype2
508          /usr/local/include/freetype1/freetype
509          /usr/include /usr/local/include /usr/include/freetype
510          /usr/local/include/freetype);
511   if ($Config{ccflags}) {
512     my @hidden = map { /^-I(.*)$/ ? ($1) : () } split ' ', $Config{ccflags};
513     push @incs, @hidden;
514     @definc{@hidden} = (1) x @hidden;
515   }
516
517   @libs= ( split(/\Q$Config{path_sep}/,$LIBPATH),
518     map _tilde_expand($_), map { split /\Q$Config{path_sep}/} @libpaths );
519   if ($Config{loclibpth}) {
520     push @libs, grep -d, split ' ', $Config{loclibpth};
521   }
522   
523   push @libs, grep -d, qw(/sw/lib),  split(/ /, $Config{'libpth'});
524   push @libs, grep -d, split / /, $Config{libspath} if $Config{libspath};
525   if ($^O =~ /win32/i && $Config{cc} =~ /\bcl\b/i) {
526     push(@libs, split /;/, $ENV{LIB}) if exists $ENV{LIB};
527   }
528   if ($^O eq 'cygwin') {
529     push(@libs, '/usr/lib/w32api') if -d '/usr/lib/w32api';
530     push(@incs, '/usr/include/w32api') if -d '/usr/include/w32api';
531   }
532   if ($Config{ldflags}) {
533     # some builds of perl put -Ldir into ldflags without putting it in
534     # loclibpth, let's extract them
535     my @hidden = grep -d, map { /^-L(.*)$/ ? ($1) : () }
536       split ' ', $Config{ldflags};
537     push @libs, @hidden;
538     # don't mark them as seen - EU::MM will remove any libraries
539     # it can't find and it doesn't look for -L in ldflags
540     #@deflib{@hidden} = @hidden;
541   }
542   push @libs, grep -d, qw(/usr/local/lib);
543
544   $formats{'TT-fonts'}=
545     {
546      order=>'31',
547      def=>'HAVE_LIBTT',
548      inccheck=>sub { -e catfile($_[0], 'freetype.h')
549                        && !-e catfile($_[0], 'fterrors.h') },
550      libcheck=>sub { $_[0] eq "libttf$aext" or $_[0] eq "libttf.$lext" },
551      libfiles=>'-lttf',
552      objfiles=>'fontft1.o',
553      code => \&freetype1_probe,
554      docs=>q{
555 Truetype fonts are scalable fonts. They can include 
556 kerning and hinting information and generally yield good
557 visual quality esp on low resultions. The freetype library is
558 used to rasterize for us. The only drawback is that there
559 are alot of badly designed fonts out there.}
560                        };
561   # Make fix indent
562   for (keys %formats) { $formats{$_}->{docs} =~ s/^\s+/  /mg; }
563 }
564
565
566
567 sub gen {
568   my $V = $ENV{$_[0]};
569   defined($V) ? $V : "";
570 }
571
572
573 # Get information from environment variables
574
575 sub getenv {
576
577   ($VERBOSE,
578    $INCPATH,
579    $LIBPATH,
580    $NOLOG,
581    $DEBUG_MALLOC,
582    $MANUAL,
583    $CFLAGS,
584    $LFLAGS,
585    $DFLAGS) = map { gen $_ } qw(IM_VERBOSE
586                                 IM_INCPATH
587                                 IM_LIBPATH
588                                 IM_NOLOG
589                                 IM_DEBUG_MALLOC
590                                 IM_MANUAL
591                                 IM_CFLAGS
592                                 IM_LFLAGS
593                                 IM_DFLAGS);
594
595 }
596
597 # populate the environment so that sub-modules get the same info
598 sub setenv {
599   $ENV{IM_VERBOSE} = 1 if $VERBOSE;
600   $ENV{IM_INCPATH} = join $Config{path_sep}, @incpaths if @incpaths;
601   $ENV{IM_LIBPATH} = join $Config{path_sep}, @libpaths if @libpaths;
602 }
603
604 sub make_imconfig {
605   my ($defines) = @_;
606
607   open CONFIG, "> imconfig.h"
608     or die "Cannot create imconfig.h: $!\n";
609   print CONFIG <<EOS;
610 /* This file is automatically generated by Makefile.PL.
611    Don't edit this file, since any changes will be lost */
612
613 #ifndef IMAGER_IMCONFIG_H
614 #define IMAGER_IMCONFIG_H
615 EOS
616   for my $define (@$defines) {
617     if ($define->[2]) {
618       print CONFIG "\n/*\n  $define->[2]\n*/\n\n";
619     }
620     print CONFIG "#define $define->[0] $define->[1]\n";
621   }
622   if ($Config{gccversion} && $Config{gccversion} =~ /^([0-9]+)/ && $1 > 3) {
623     print CONFIG <<EOS;
624 /*
625
626 Compiler supports the GCC __attribute__((format...)) syntax.
627
628 */
629
630 #define IMAGER_FORMAT_ATTR 1
631
632 EOS
633   }
634
635   if ($Config{d_snprintf}) {
636     print CONFIG <<EOS;
637 /* We can use snprintf() */
638 #define IMAGER_SNPRINTF 1
639
640 EOS
641   }
642
643   if ($Config{d_vsnprintf}) {
644     print CONFIG <<EOS;
645 /* We can use vsnprintf() */
646 #define IMAGER_VSNPRINTF 1
647
648 EOS
649   }
650
651   print CONFIG <<EOS;
652 /*
653  Type and format code for formatted output as with printf.
654
655  This is intended for formatting i_img_dim values.
656 */
657 typedef $Config{ivtype} i_dim_format_t;
658 #define i_DF $Config{ivdformat}
659 EOS
660
661   print CONFIG "\n#endif\n";
662   close CONFIG;
663 }
664
665 # probes for freetype1 by scanning @incs for the includes and 
666 # @libs for the libs.  This is done separately because freetype's headers
667 # are stored in a freetype or freetype1 directory under PREFIX/include.
668 #
669 # we could find the files with the existing mechanism, but it won't set
670 # -I flags correctly.
671 #
672 # This could be extended to freetype2 too, but freetype-config catches
673 # that
674 sub freetype1_probe {
675   my ($frm, $frmkey) = @_;
676
677   my $found_inc;
678  INCS:
679   for my $inc (@incs) {
680     for my $subdir (qw/freetype freetype1/) {
681       my $path = File::Spec->catfile($inc, $subdir, 'freetype.h');
682       -e $path or next;
683       $path = File::Spec->catfile($inc, $subdir, 'fterrors.h');
684       -e $path and next;
685
686       $found_inc = File::Spec->catdir($inc, $subdir);
687       last INCS;
688     }
689   }
690
691   my $found_lib;
692  LIBS:
693   for my $lib (@libs) {
694     my $a_path = File::Spec->catfile($lib, "libttf$aext");
695     my $l_path = File::Spec->catfile($lib, "libttf.$lext");
696     if (-e $a_path || -e $l_path) {
697       $found_lib = $lib;
698       last LIBS;
699     }
700   }
701
702   return unless $found_inc && $found_lib;
703   printf("%10s: includes %s - libraries %s\n", $frmkey,
704          ($found_inc ? 'found' : 'not found'), 
705          ($found_lib ? 'found' : 'not found'));
706
707   $frm->{cflags} = "-I$found_inc";
708   $frm->{libfiles} = "-lttf";
709
710   return 1;
711 }
712
713 sub catfile {
714   return File::Spec->catfile(@_);
715 }
716
717 sub usage {
718   print STDERR <<EOS;
719 Usage: $0 [--enable feature1,feature2,...] [other options]
720        $0 [--disable feature1,feature2,...]  [other options]
721        $0 --help
722 Possible feature names are:
723   T1-fonts
724 Other options:
725   --verbose | -v
726     Verbose library probing (or set IM_VERBOSE in the environment)
727   --nolog
728     Disable logging (or set IM_NOLOG in the environment)
729   --incpath dir
730     Add to the include search path
731   --libpath dir
732     Add to the library search path
733   --coverage
734     Build for coverage testing.
735   --assert
736     Build with assertions active.
737 EOS
738   exit 1;
739
740 }
741
742 # generate the PM MM argument
743 # I'd prefer to modify the public version, but there doesn't seem to be 
744 # a public API to do that
745 sub gen_PM {
746   my %pm;
747   my $instbase = '$(INST_LIBDIR)';
748
749   # first the basics, .pm and .pod files
750   $pm{"Imager.pm"} = "$instbase/Imager.pm";
751
752   my $mani = maniread();
753
754   for my $filename (keys %$mani) {
755     if ($filename =~ m!^lib/! && $filename =~ /\.(pm|pod)$/) {
756       (my $work = $filename) =~ s/^lib//;
757       $pm{$filename} = $instbase . $work;
758     }
759   }
760
761   # need the typemap
762   $pm{typemap} = $instbase . '/Imager/typemap';
763
764   # and the core headers
765   for my $filename (keys %$mani) {
766     if ($filename =~ /^\w+\.h$/) {
767       $pm{$filename} = $instbase . '/Imager/include/' . $filename;
768     }
769   }
770
771   # and the generated header
772   $pm{"imconfig.h"} = $instbase . '/Imager/include/imconfig.h';
773
774   \%pm;
775 }
776
777 my $home;
778 sub _tilde_expand {
779   my ($path) = @_;
780
781   if ($path =~ m!^~[/\\]!) {
782     defined $home or $home = $ENV{HOME};
783     if (!defined $home && $^O eq 'MSWin32'
784        && defined $ENV{HOMEDRIVE} && defined $ENV{HOMEPATH}) {
785       $home = $ENV{HOMEDRIVE} . $ENV{HOMEPATH};
786     }
787     unless (defined $home) {
788       $home = eval { (getpwuid($<))[7] };
789     }
790     defined $home or die "You supplied $path, but I can't find your home directory\n";
791     $path =~ s/^~//;
792     $path = File::Spec->catdir($home, $path);
793   }
794
795   $path;
796 }
797
798 1;