Configure et al: move the installation directory logic to Makefiles
[openssl.git] / Configure
1 #! /usr/bin/env perl
2 # -*- mode: perl; -*-
3
4 ##
5 ##  Configure -- OpenSSL source tree configuration script
6 ##  If editing this file, run this command before committing
7 ##      make -f Makefile.in TABLE
8 ##
9
10 require 5.000;
11 use strict;
12 use File::Basename;
13 use File::Spec::Functions qw/:DEFAULT abs2rel rel2abs/;
14 use File::Path qw/mkpath/;
15
16 # see INSTALL for instructions.
17
18 my $usage="Usage: Configure [no-<cipher> ...] [enable-<cipher> ...] [experimental-<cipher> ...] [-Dxxx] [-lxxx] [-Lxxx] [-fxxx] [-Kxxx] [no-hw-xxx|no-hw] [[no-]threads] [[no-]shared] [[no-]zlib|zlib-dynamic] [no-asm] [no-dso] [no-egd] [sctp] [386] [--prefix=DIR] [--openssldir=OPENSSLDIR] [--with-xxx[=vvv]] [--config=FILE] os/compiler[:flags]\n";
19
20 # Options:
21 #
22 # --config      add the given configuration file, which will be read after
23 #               any "Configurations*" files that are found in the same
24 #               directory as this script.
25 # --prefix      prefix for the OpenSSL installation, which includes the
26 #               directories bin, lib, include, share/man, share/doc/openssl
27 #               This becomes the value of INSTALLTOP in Makefile
28 #               (Default: /usr/local)
29 # --openssldir  OpenSSL data area, such as openssl.cnf, certificates and keys.
30 #               If it's a relative directory, it will be added on the directory
31 #               given with --prefix.
32 #               This becomes the value of OPENSSLDIR in Makefile and in C.
33 #               (Default: PREFIX/ssl)
34 #
35 # --install_prefix  Additional prefix for package builders (empty by
36 #               default).  This needn't be set in advance, you can
37 #               just as well use "make INSTALL_PREFIX=/whatever install".
38 #
39 # --cross-compile-prefix Add specified prefix to binutils components.
40 #
41 # --api         One of 0.9.8, 1.0.0 or 1.1.0.  Do not compile support for
42 #               interfaces deprecated as of the specified OpenSSL version.
43 #
44 # no-hw-xxx     do not compile support for specific crypto hardware.
45 #               Generic OpenSSL-style methods relating to this support
46 #               are always compiled but return NULL if the hardware
47 #               support isn't compiled.
48 # no-hw         do not compile support for any crypto hardware.
49 # [no-]threads  [don't] try to create a library that is suitable for
50 #               multithreaded applications (default is "threads" if we
51 #               know how to do it)
52 # [no-]shared   [don't] try to create shared libraries when supported.
53 # no-asm        do not use assembler
54 # no-dso        do not compile in any native shared-library methods. This
55 #               will ensure that all methods just return NULL.
56 # no-egd        do not compile support for the entropy-gathering daemon APIs
57 # [no-]zlib     [don't] compile support for zlib compression.
58 # zlib-dynamic  Like "zlib", but the zlib library is expected to be a shared
59 #               library and will be loaded in run-time by the OpenSSL library.
60 # sctp          include SCTP support
61 # 386           generate 80386 code
62 # no-sse2       disables IA-32 SSE2 code, above option implies no-sse2
63 # no-<cipher>   build without specified algorithm (rsa, idea, rc5, ...)
64 # -<xxx> +<xxx> compiler options are passed through
65 #
66 # DEBUG_SAFESTACK use type-safe stacks to enforce type-safety on stack items
67 #               provided to stack calls. Generates unique stack functions for
68 #               each possible stack type.
69 # BN_LLONG      use the type 'long long' in crypto/bn/bn.h
70 # RC4_CHAR      use 'char' instead of 'int' for RC4_INT in crypto/rc4/rc4.h
71 # Following are set automatically by this script
72 #
73 # MD5_ASM       use some extra md5 assember,
74 # SHA1_ASM      use some extra sha1 assember, must define L_ENDIAN for x86
75 # RMD160_ASM    use some extra ripemd160 assember,
76 # SHA256_ASM    sha256_block is implemented in assembler
77 # SHA512_ASM    sha512_block is implemented in assembler
78 # AES_ASM       ASE_[en|de]crypt is implemented in assembler
79
80 # Minimum warning options... any contributions to OpenSSL should at least get
81 # past these.
82
83 my $gcc_devteam_warn = "-Wall -pedantic -DPEDANTIC -Wno-long-long -Wsign-compare -Wmissing-prototypes -Wshadow -Wformat -Wtype-limits -Werror -DREF_CHECK -DDEBUG_UNUSED";
84
85 # These are used in addition to $gcc_devteam_warn when the compiler is clang.
86 # TODO(openssl-team): fix problems and investigate if (at least) the
87 # following warnings can also be enabled:
88 # -Wswitch-enum, -Wunused-macros, -Wmissing-field-initializers,
89 # -Wcast-align,
90 # -Wunreachable-code -Wunused-parameter -Wlanguage-extension-token
91 # -Wextended-offsetof
92 my $clang_devteam_warn = "-Wno-unused-parameter -Wno-missing-field-initializers -Wno-language-extension-token -Wno-extended-offsetof -Wconditional-uninitialized -Qunused-arguments -Wincompatible-pointer-types-discards-qualifiers -Wmissing-variable-declarations";
93
94 # Warn that "make depend" should be run?
95 my $warn_make_depend = 0;
96
97 # These are used in addition to $gcc_devteam_warn unless this is a mingw build.
98 # This adds backtrace information to the memory leak info.
99 my $memleak_devteam_backtrace = "-rdynamic -DCRYPTO_MDEBUG_BACKTRACE";
100
101 my $strict_warnings = 0;
102
103 # As for $BSDthreads. Idea is to maintain "collective" set of flags,
104 # which would cover all BSD flavors. -pthread applies to them all,
105 # but is treated differently. OpenBSD expands is as -D_POSIX_THREAD
106 # -lc_r, which is sufficient. FreeBSD 4.x expands it as -lc_r,
107 # which has to be accompanied by explicit -D_THREAD_SAFE and
108 # sometimes -D_REENTRANT. FreeBSD 5.x expands it as -lc_r, which
109 # seems to be sufficient?
110 my $BSDthreads="-pthread -D_THREAD_SAFE -D_REENTRANT";
111
112 #
113 # API compability name to version number mapping.
114 #
115 my $maxapi = "1.1.0";           # API for "no-deprecated" builds
116 my $apitable = {
117     "1.1.0" => "0x10100000L",
118     "1.0.0" => "0x10000000L",
119     "0.9.8" => "0x00908000L",
120 };
121
122 my $base_target = "BASE";   # The template that all other inherit from
123 our %table = ();
124 our %config = ();
125
126 # Forward declarations ###############################################
127
128 # read_config(filename)
129 #
130 # Reads a configuration file and populates %table with the contents
131 # (which the configuration file places in %targets).
132 sub read_config;
133
134 # resolve_config(target)
135 #
136 # Resolves all the late evalutations, inheritances and so on for the
137 # chosen target and any target it inherits from.
138 sub resolve_config;
139
140
141 # Information collection #############################################
142
143 # Unified build supports separate build dir
144 my $srcdir = catdir(absolutedir(dirname($0))); # catdir ensures local syntax
145 my $blddir = catdir(absolutedir("."));         # catdir ensures local syntax
146 my $dofile = abs2rel(catfile($srcdir, "util/dofile.pl"));
147
148 $config{sourcedir} = abs2rel($srcdir);
149 $config{builddir} = abs2rel($blddir);
150
151 # Collect version numbers
152 $config{version} = "unknown";
153 $config{version_num} = "unknown";
154 $config{shlib_version_number} = "unknown";
155 $config{shlib_version_history} = "unknown";
156
157 collect_information(
158     collect_from_file(catfile($srcdir,'include/openssl/opensslv.h')),
159     qr/OPENSSL.VERSION.TEXT.*OpenSSL (\S+) / => sub { $config{version} = $1; },
160     qr/OPENSSL.VERSION.NUMBER.*(0x\S+)/      => sub { $config{version_num}=$1 },
161     qr/SHLIB_VERSION_NUMBER *"([^"]+)"/      => sub { $config{shlib_version_number}=$1 },
162     qr/SHLIB_VERSION_HISTORY *"([^"]*)"/     => sub { $config{shlib_version_history}=$1 }
163     );
164 if ($config{shlib_version_history} ne "") { $config{shlib_version_history} .= ":"; }
165
166 ($config{major}, $config{minor})
167     = ($config{version} =~ /^([0-9]+)\.([0-9\.]+)/);
168 ($config{shlib_major}, $config{shlib_minor})
169     = ($config{shlib_version_number} =~ /^([0-9]+)\.([0-9\.]+)/);
170 die "erroneous version information in opensslv.h: ",
171     "$config{major}, $config{minor}, $config{shlib_major}, $config{shlib_minor}\n"
172     if ($config{major} eq "" || $config{minor} eq ""
173         || $config{shlib_major} eq "" ||  $config{shlib_minor} eq "");
174
175 # Collect target configurations
176
177 my $pattern = catfile(dirname($0), "Configurations", "*.conf");
178 foreach (sort glob($pattern) ) {
179     &read_config($_);
180 }
181
182
183 print "Configuring OpenSSL version $config{version} (0x$config{version_num})\n";
184
185 $config{perl};
186 $config{prefix}="";
187 $config{openssldir}="";
188 $config{processor}="";
189 $config{libdir}="";
190 $config{install_prefix}= "$ENV{'INSTALL_PREFIX'}";
191 $config{cross_compile_prefix}="";
192 $config{fipslibdir}="/usr/local/ssl/fips-2.0/lib/";
193 my $nofipscanistercheck=0;
194 $config{baseaddr}="0xFB00000";
195 my $no_threads=0;
196 my $threads=0;
197 $config{no_shared}=0; # but "no-shared" is default
198 my $zlib=1;      # but "no-zlib" is default
199 my $no_rfc3779=0;
200 my $no_asm=0;
201 my $no_dso=0;
202 my $default_ranlib;
203 $config{fips}=0;
204
205 # Top level directories to build
206 $config{dirs} = [ "crypto", "ssl", "engines", "apps", "test", "tools" ];
207 # crypto/ subdirectories to build
208 $config{sdirs} = [
209     "objects",
210     "md2", "md4", "md5", "sha", "mdc2", "hmac", "ripemd", "whrlpool", "poly1305",
211     "des", "aes", "rc2", "rc4", "rc5", "idea", "bf", "cast", "camellia", "seed", "chacha", "modes",
212     "bn", "ec", "rsa", "dsa", "dh", "dso", "engine",
213     "buffer", "bio", "stack", "lhash", "rand", "err",
214     "evp", "asn1", "pem", "x509", "x509v3", "conf", "txt_db", "pkcs7", "pkcs12", "comp", "ocsp", "ui",
215     "cms", "ts", "jpake", "srp", "cmac", "ct", "async", "kdf"
216     ];
217
218 # Known TLS and DTLS protocols
219 my @tls = qw(ssl3 tls1 tls1_1 tls1_2);
220 my @dtls = qw(dtls1 dtls1_2);
221
222 # Explicitelly known options that are possible to disable.  They can
223 # be regexps, and will be used like this: /^no-${option}$/
224 # For developers: keep it sorted alphabetically
225
226 my @disablables = (
227     "aes",
228     "asm",
229     "async",
230     "autoalginit",
231     "autoerrinit",
232     "bf",
233     "camellia",
234     "capieng",
235     "cast",
236     "chacha",
237     "cmac",
238     "cms",
239     "comp",
240     "crypto-mdebug",
241     "ct",
242     "deprecated",
243     "des",
244     "dgram",
245     "dh",
246     "dsa",
247     "dso",
248     "dtls",
249     "dynamic[-_]engine",
250     "ec",
251     "ec2m",
252     "ecdh",
253     "ecdsa",
254     "ec_nistp_64_gcc_128",
255     "egd",
256     "engine",
257     "err",                      # Really???
258     "heartbeats",
259     "hmac",
260     "hw(-.+)?",
261     "idea",
262     "jpake",
263     "locking",                  # Really???
264     "md2",
265     "md4",
266     "md5",
267     "mdc2",
268     "md[-_]ghost94",
269     "nextprotoneg",
270     "ocb",
271     "ocsp",
272     "poly1305",
273     "posix-io",
274     "psk",
275     "rc2",
276     "rc4",
277     "rc5",
278     "rdrand",
279     "rfc3779",
280     "rijndael",                 # Old AES name
281     "rmd160",
282     "rsa",
283     "scrypt",
284     "sct",
285     "sctp",
286     "seed",
287     "sha",
288     "shared",
289     "sock",
290     "srp",
291     "srtp",
292     "sse2",
293     "ssl",
294     "ssl-trace",
295     "static-engine",
296     "stdio",
297     "threads",
298     "tls",
299     "unit-test",
300     "whirlpool",
301     "zlib",
302     "zlib-dynamic",
303     );
304 foreach my $proto ((@tls, @dtls))
305         {
306         push(@disablables, $proto);
307         push(@disablables, "$proto-method");
308         }
309
310 # All of the following is disabled by default (RC5 was enabled before 0.9.8):
311
312 my %disabled = ( # "what"         => "comment" [or special keyword "experimental"]
313                  "ec_nistp_64_gcc_128" => "default",
314                  "egd"            => "default",
315                  "jpake"          => "experimental",
316                  "md2"            => "default",
317                  "rc5"            => "default",
318                  "sctp"           => "default",
319                  "shared"         => "default",
320                  "ssl-trace"      => "default",
321                  "unit-test"      => "default",
322                  "zlib"           => "default",
323                  "crypto-mdebug"  => "default",
324                );
325 my @experimental = ();
326
327 # Note: => pair form used for aesthetics, not to truly make a hash table
328 my @disable_cascades = (
329     # "what"            => [ "cascade", ... ]
330     sub { $config{processor} eq "386" }
331                         => [ "sse2" ],
332     "ssl"               => [ "ssl3" ],
333     "ssl3-method"       => [ "ssl3" ],
334     "zlib"              => [ "zlib-dynamic" ],
335     "rijndael"          => [ "aes" ],
336     "des"               => [ "mdc2" ],
337     "ec"                => [ "ecdsa", "ecdh" ],
338     "psk"               => [ "jpake" ],
339
340     "dgram"             => [ "dtls" ],
341     "dtls"              => [ @dtls ],
342
343     # SSL 3.0, (D)TLS 1.0 and TLS 1.1 require MD5 and SHA
344     "md5"               => [ "ssl", "tls1", "tls1_1", "dtls1" ],
345     "sha"               => [ "ssl", "tls1", "tls1_1", "dtls1" ],
346
347     # Additionally, SSL 3.0 requires either RSA or DSA+DH
348     sub { $disabled{rsa}
349           && ($disabled{dsa} || $disabled{dh}); }
350                         => [ "ssl" ],
351
352     # (D)TLS 1.0 and TLS 1.1 also require either RSA or DSA+DH
353     # or ECDSA + ECDH.  (D)TLS 1.2 has this requirement as well.
354     # (XXX: We don't support PSK-only builds).
355     sub { $disabled{rsa}
356           && ($disabled{dsa} || $disabled{dh})
357           && ($disabled{ecdsa} || $disabled{ecdh}); }
358                         => [ "tls1", "tls1_1", "tls1_2",
359                              "dtls1", "dtls1_2" ],
360
361     "tls"               => [ @tls ],
362
363     # SRP and HEARTBEATS require TLSEXT
364     "tlsext"            => [ "srp", "heartbeats" ],
365     );
366
367 # Avoid protocol support holes.  Also disable all versions below N, if version
368 # N is disabled while N+1 is enabled.
369 #
370 my @list = (reverse @tls);
371 while ((my $first, my $second) = (shift @list, shift @list)) {
372     last unless @list;
373     push @disable_cascades, ( sub { !$disabled{$first} && $disabled{$second} }
374                               => [ @list ] );
375     unshift @list, $second;
376 }
377 my @list = (reverse @dtls);
378 while ((my $first, my $second) = (shift @list, shift @list)) {
379     last unless @list;
380     push @disable_cascades, ( sub { !$disabled{$first} && $disabled{$second} }
381                               => [ @list ] );
382     unshift @list, $second;
383 }
384
385 # Construct the string of what $config{depdefines} should look like with
386 # the defaults from %disabled above.  (we need this to see if we should
387 # advise the user to run "make depend"):
388 my @default_depdefines =
389     map { my $x = $_; $x =~ tr{[a-z]-}{[A-Z]_}; "OPENSSL_NO_$x"; }
390     grep { $disabled{$_} !~ /\(no-depdefines\)$/ }
391     sort keys %disabled;
392
393 # Explicit "no-..." options will be collected in %disabled along with the defaults.
394 # To remove something from %disabled, use "enable-foo" (unless it's experimental).
395 # For symmetry, "disable-foo" is a synonym for "no-foo".
396
397 # For features called "experimental" here, a more explicit "experimental-foo" is needed to enable.
398 # We will collect such requests in @experimental.
399 # To avoid accidental use of experimental features, applications will have to use -DOPENSSL_EXPERIMENTAL_FOO.
400
401
402 my $no_sse2=0;
403
404 &usage if ($#ARGV < 0);
405
406 my $user_cflags="";
407 my @user_defines=();
408 $config{depdefines}=[];
409 $config{openssl_experimental_defines}=[];
410 $config{openssl_api_defines}=[];
411 $config{openssl_algorithm_defines}=[];
412 $config{openssl_thread_defines}=[];
413 $config{openssl_sys_defines}=[];
414 $config{openssl_other_defines}=[];
415 my $libs="";
416 my $target="";
417 $config{options}="";
418 my $make_depend=0;
419 my %withargs=();
420 my $build_prefix = "release_";
421
422 my @argvcopy=@ARGV;
423
424 if (grep /^reconf(igure)?$/, @argvcopy) {
425     if (-f "./configdata.pm") {
426         my $file = "./configdata.pm";
427         unless (my $return = do $file) {
428             die "couldn't parse $file: $@" if $@;
429             die "couldn't do $file: $!"    unless defined $return;
430             die "couldn't run $file"       unless $return;
431         }
432
433         @argvcopy = defined($configdata::config{perlargv}) ?
434             @{$configdata::config{perlargv}} : ();
435         die "Incorrect data to reconfigure, please do a normal configuration\n"
436             if (grep(/^reconf/,@argvcopy));
437         $ENV{CROSS_COMPILE} = $configdata::config{cross_compile_prefix}
438             if defined($configdata::config{cross_compile_prefix});
439         $ENV{CROSS_COMPILE} = $configdata::config{cc}
440             if defined($configdata::config{cc});
441
442         print "Reconfiguring with: ", join(" ",@argvcopy), "\n";
443         print "    CROSS_COMPILE = ",$ENV{CROSS_COMPILE},"\n"
444             if $ENV{CROSS_COMPILE};
445         print "    CC = ",$ENV{CC},"\n" if $ENV{CC};
446     } elsif (open IN, "<Makefile") {
447         #
448         # THIS SECTION IS TEMPORARY, it helps transitioning from Makefile
449         # centered information gathering the reading configdata.pm
450         #
451         while (<IN>) {
452             chomp;
453             if (/^CONFIGURE_ARGS=\s*(.*)\s*/) {
454                 # Older form, we split the string and hope for the best
455                 @argvcopy = split /\s+/, $_;
456                 die "Incorrect data to reconfigure, please do a normal configuration\n"
457                     if (grep(/^reconf/,@argvcopy));
458             } elsif (/^CROSS_COMPILE=\s*(.*)/) {
459                 $ENV{CROSS_COMPILE}=$1;
460             } elsif (/^CC=\s*(?:\$\(CROSS_COMPILE\))?(.*?)$/) {
461                 $ENV{CC}=$1;
462             }
463         }
464         #
465         # END OF TEMPORARY SECTION
466         #
467     } else {
468         die "Insufficient data to reconfigure, please do a normal configuration\n";
469     }
470 }
471
472 $config{perlargv} = [ @argvcopy ];
473
474 my %unsupported_options = ();
475 foreach (@argvcopy)
476         {
477         s /^-no-/no-/; # some people just can't read the instructions
478
479         # rewrite some options in "enable-..." form
480         s /^-?-?shared$/enable-shared/;
481         s /^sctp$/enable-sctp/;
482         s /^threads$/enable-threads/;
483         s /^zlib$/enable-zlib/;
484         s /^zlib-dynamic$/enable-zlib-dynamic/;
485
486         if (/^(no|disable|enable|experimental)-(.+)$/)
487                 {
488                 my $word = $2;
489                 if (!grep { $word =~ /^${_}$/ } @disablables)
490                         {
491                         $unsupported_options{$_} = 1;
492                         next;
493                         }
494                 }
495         if (/^no-(.+)$/ || /^disable-(.+)$/)
496                 {
497                 if (!($disabled{$1} eq "experimental"))
498                         {
499                         foreach my $proto ((@tls, @dtls))
500                                 {
501                                 if ($1 eq "$proto-method")
502                                         {
503                                         $disabled{"$proto"} = "option($proto-method)";
504                                         last;
505                                         }
506                                 }
507                         if ($1 eq "dtls")
508                                 {
509                                 foreach my $proto (@dtls)
510                                         {
511                                         $disabled{$proto} = "option(dtls)";
512                                         }
513                                 }
514                         elsif ($1 eq "ssl")
515                                 {
516                                 # Last one of its kind
517                                 $disabled{"ssl3"} = "option(ssl)";
518                                 }
519                         elsif ($1 eq "tls")
520                                 {
521                                 # XXX: Tests will fail if all SSL/TLS
522                                 # protocols are disabled.
523                                 foreach my $proto (@tls)
524                                         {
525                                         $disabled{$proto} = "option(tls)";
526                                         }
527                                 }
528                         else
529                                 {
530                                 $disabled{$1} = "option";
531                                 }
532                         }
533                 }
534         elsif (/^enable-(.+)$/ || /^experimental-(.+)$/)
535                 {
536                 my $algo = $1;
537                 if ($disabled{$algo} eq "experimental")
538                         {
539                         die "You are requesting an experimental feature; please say 'experimental-$algo' if you are sure\n"
540                                 unless (/^experimental-/);
541                         push @experimental, $algo;
542                         }
543                 delete $disabled{$algo};
544
545                 $threads = 1 if ($algo eq "threads");
546                 }
547         elsif (/^--strict-warnings$/)
548                 {
549                 $strict_warnings = 1;
550                 }
551         elsif (/^--debug$/)
552                 {
553                 $build_prefix = "debug_";
554                 }
555         elsif (/^--release$/)
556                 {
557                 $build_prefix = "release_";
558                 }
559         elsif (/^386$/)
560                 { $config{processor}=386; }
561         elsif (/^fips$/)
562                 {
563                 $config{fips}=1;
564                 }
565         elsif (/^rsaref$/)
566                 {
567                 # No RSAref support any more since it's not needed.
568                 # The check for the option is there so scripts aren't
569                 # broken
570                 }
571         elsif (/^nofipscanistercheck$/)
572                 {
573                 $config{fips} = 1;
574                 $nofipscanistercheck = 1;
575                 }
576         elsif (/^[-+]/)
577                 {
578                 if (/^--prefix=(.*)$/)
579                         {
580                         $config{prefix}=$1;
581                         die "Directory given with --prefix MUST be absolute\n"
582                                 unless file_name_is_absolute($config{prefix});
583                         }
584                 elsif (/^--api=(.*)$/)
585                         {
586                         $config{api}=$1;
587                         }
588                 elsif (/^--libdir=(.*)$/)
589                         {
590                         $config{libdir}=$1;
591                         }
592                 elsif (/^--openssldir=(.*)$/)
593                         {
594                         $config{openssldir}=$1;
595                         }
596                 elsif (/^--install.prefix=(.*)$/)
597                         {
598                         $config{install_prefix}=$1;
599                         }
600                 elsif (/^--with-zlib-lib=(.*)$/)
601                         {
602                         $withargs{zlib_lib}=$1;
603                         }
604                 elsif (/^--with-zlib-include=(.*)$/)
605                         {
606                         $withargs{zlib_include}="-I$1";
607                         }
608                 elsif (/^--with-fipslibdir=(.*)$/)
609                         {
610                         $config{fipslibdir}="$1/";
611                         }
612                 elsif (/^--with-baseaddr=(.*)$/)
613                         {
614                         $config{baseaddr}="$1";
615                         }
616                 elsif (/^--cross-compile-prefix=(.*)$/)
617                         {
618                         $config{cross_compile_prefix}=$1;
619                         }
620                 elsif (/^--config=(.*)$/)
621                         {
622                         read_config $1;
623                         }
624                 elsif (/^-[lL](.*)$/ or /^-Wl,/)
625                         {
626                         $libs.=$_." ";
627                         }
628                 elsif (/^-D(.*)$/)
629                         {
630                         push @user_defines, $1;
631                         }
632                 else    # common if (/^[-+]/), just pass down...
633                         {
634                         $_ =~ s/%([0-9a-f]{1,2})/chr(hex($1))/gei;
635                         $user_cflags.=$_." ";
636                         }
637                 }
638         elsif ($_ =~ /^([^:]+):(.+)$/)
639                 {
640                 eval "\$table{\$1} = \"$2\""; # allow $xxx constructs in the string
641                 $target=$1;
642                 }
643         else
644                 {
645                 die "target already defined - $target (offending arg: $_)\n" if ($target ne "");
646                 $target=$_;
647                 }
648         unless ($_ eq $target || /^no-/ || /^disable-/)
649                 {
650                 # "no-..." follows later after implied disactivations
651                 # have been derived.  (Don't take this too seroiusly,
652                 # we really only write OPTIONS to the Makefile out of
653                 # nostalgia.)
654
655                 if ($config{options} eq "")
656                         { $config{options} = $_; }
657                 else
658                         { $config{options} .= " ".$_; }
659                 }
660
661         if (defined($config{api}) && !exists $apitable->{$config{api}}) {
662                 die "***** Unsupported api compatibility level: $config{api}\n",
663         }
664
665         if (keys %unsupported_options)
666                 {
667                 die "***** Unsupported options: ",
668                         join(", ", keys %unsupported_options), "\n";
669                 }
670         }
671
672 if ($config{fips})
673         {
674         delete $disabled{"shared"} if ($disabled{"shared"} =~ /^default/);
675         }
676 else
677         {
678         @{$config{dirs}} = grep !/^fips$/, @{$config{dirs}};
679         }
680
681 my @tocheckfor = (keys %disabled);
682 while (@tocheckfor) {
683     my %new_tocheckfor = ();
684     my @cascade_copy = (@disable_cascades);
685     while (@cascade_copy) {
686         my ($test, $descendents) = (shift @cascade_copy, shift @cascade_copy);
687         if (ref($test) eq "CODE" ? $test->() : defined($disabled{$test})) {
688             map {
689                 $new_tocheckfor{$_} => 1; $disabled{$_} = "forced";
690             } grep { !defined($disabled{$_}) } @$descendents;
691         }
692     }
693     @tocheckfor = (keys %new_tocheckfor);
694 }
695
696 if ($target eq "TABLE") {
697     foreach (sort keys %table) {
698         print_table_entry($_, "TABLE");
699     }
700     exit 0;
701 }
702
703 if ($target eq "LIST") {
704     foreach (sort keys %table) {
705         print $_,"\n" unless $table{$_}->{template};
706     }
707     exit 0;
708 }
709
710 if ($target eq "HASH") {
711     print "%table = (\n";
712     foreach (sort keys %table) {
713         print_table_entry($_, "HASH");
714     }
715     exit 0;
716 }
717
718 # Backward compatibility?
719 if ($target =~ m/^CygWin32(-.*)$/) {
720     $target = "Cygwin".$1;
721 }
722
723 foreach (sort (keys %disabled))
724         {
725         $config{options} .= " no-$_";
726
727         printf "    no-%-12s %-10s", $_, "[$disabled{$_}]";
728
729         if (/^dso$/)
730                 { $no_dso = 1; }
731         elsif (/^threads$/)
732                 { $no_threads = 1; }
733         elsif (/^shared$/)
734                 { $config{no_shared} = 1; }
735         elsif (/^zlib$/)
736                 { $zlib = 0; }
737         elsif (/^static-engine$/)
738                 { }
739         elsif (/^zlib-dynamic$/)
740                 { }
741         elsif (/^sse2$/)
742                 { $no_sse2 = 1; }
743         elsif (/^engine$/)
744                 { @{$config{dirs}} = grep !/^engine$/, @{$config{dirs}}; }
745         else
746                 {
747                 my ($ALGO, $algo);
748                 ($ALGO = $algo = $_) =~ tr/[\-a-z]/[_A-Z]/;
749
750                 if (/^asm$/ || /^err$/ || /^hw$/ || /^hw-/ || /^async$/
751                                 || /^autoalginit/ || /^autoerrinit/)
752                         {
753                         push @{$config{openssl_other_defines}}, "OPENSSL_NO_$ALGO";
754                         print " OPENSSL_NO_$ALGO";
755
756                         if (/^err$/)    { push @user_defines, "OPENSSL_NO_ERR"; }
757                         elsif (/^asm$/) { $no_asm = 1; }
758                         }
759                 else
760                         {
761                         ($ALGO,$algo) = ("RMD160","rmd160") if ($algo eq "ripemd");
762
763                         push @{$config{openssl_algorithm_defines}}, "OPENSSL_NO_$ALGO";
764                         push @{$config{depdefines}}, "OPENSSL_NO_$ALGO";
765                         print " OPENSSL_NO_$ALGO";
766
767                         # fix-up crypto/directory name(s)
768                         $algo="whrlpool" if $algo eq "whirlpool";
769                         $algo="ripemd" if $algo eq "rmd160";
770                         @{$config{sdirs}} = grep { $_ ne $algo} @{$config{sdirs}};
771
772                         print " (skip dir)";
773                         }
774                 }
775
776         print "\n";
777         }
778
779 foreach (sort @experimental)
780         {
781         my $ALGO;
782         ($ALGO = $_) =~ tr/[a-z]/[A-Z]/;
783
784         # opensslconf.h will set OPENSSL_NO_... unless OPENSSL_EXPERIMENTAL_... is defined
785         push @{$config{openssl_experimental_defines}}, "OPENSSL_NO_$ALGO";
786         }
787
788 print "Configuring for $target\n";
789
790 # Support for legacy targets having a name starting with 'debug-'
791 my ($d, $t) = $target =~ m/^(debug-)?(.*)$/;
792 if ($d) {
793     $build_prefix = "debug_";
794
795     # If we do not find debug-foo in the table, the target is set to foo.
796     if (!$table{$target}) {
797         $target = $t;
798     }
799 }
800 $config{target} = $target;
801 delete $table{$base_target}->{template}; # or the next test will fail.
802 my %target = ( %{$table{$base_target}}, resolve_config($target) );
803
804 &usage if (!%target || $target{template});
805
806 $target{exe_extension}="";
807 $target{exe_extension}=".exe" if ($config{target} eq "Cygwin" || $config{target} eq "DJGPP" || $config{target} =~ /^mingw/);
808 $target{exe_extension}=".nlm" if ($config{target} =~ /netware/);
809 $target{exe_extension}=".pm"  if ($config{target} =~ /vos/);
810
811 $default_ranlib = which("ranlib") || "true";
812 $config{perl}   = $ENV{'PERL'} || which("perl5") || which("perl") || "perl";
813 my $make        = $ENV{'MAKE'} || "make";
814
815 $config{cross_compile_prefix} = $ENV{'CROSS_COMPILE'}
816     if $config{cross_compile_prefix} eq "";
817
818 # Allow environment CC to override compiler...
819 $target{cc} = $ENV{CC} || $target{cc};
820
821 # For cflags, lflags, plib_lflags, ex_libs and defines, add the debug_
822 # or release_ attributes.
823 # Do it in such a way that no spurious space is appended (hence the grep).
824 $config{defines} = [ @{$target{defines}},
825                      @{$target{$build_prefix."defines"}} ];
826 $config{cflags} = join(" ",
827                        grep { $_ ne "" } ($target{cflags},
828                                           $target{$build_prefix."cflags"}));
829 $config{lflags} = join(" ",
830                        grep { $_ ne "" } ($target{lflags},
831                                           $target{$build_prefix."lflags"}));
832 $config{plib_lflags} = join(" ",
833                             grep { $_  ne "" } ($target{plib_lflags},
834                                                 $target{$build_prefix."plib_lflags"}));
835 $config{ex_libs} = join(" ",
836                         grep { $_  ne "" } ($target{ex_libs},
837                                             $target{$build_prefix."ex_libs"}));
838
839 $target{ranlib} = $ENV{'RANLIB'} || $target{ranlib} || $default_ranlib;
840 $target{ar} = $ENV{'AR'} || "ar";
841 $target{arflags} = "" if !defined($target{arflags});
842 $target{nm} = "nm";
843 # Make sure build_scheme is consistent.
844 $target{build_scheme} = [ $target{build_scheme} ]
845     if ref($target{build_scheme}) ne "ARRAY";
846
847 my ($builder, $builder_platform, @builder_opts) =
848     @{$target{build_scheme}};
849
850 push @{$config{defines}},
851     map { (my $x = $_) =~ s/^OPENSSL_NO_/OPENSSL_EXPERIMENTAL_/; $x }
852         @{$config{openssl_experimental_defines}};
853
854 if ($target =~ /^mingw/ && `$target{cc} --target-help 2>&1` !~ m/-mno-cygwin/m)
855         {
856         $config{cflags} =~ s/-mno-cygwin\s*//;
857         $target{shared_ldflag} =~ s/-mno-cygwin\s*//;
858         }
859
860 if ($target =~ /linux.*-mips/ && !$no_asm && $user_cflags !~ /-m(ips|arch=)/) {
861         # minimally required architecture flags for assembly modules
862         $config{cflags}="-mips2 $config{cflags}" if ($target =~ /mips32/);
863         $config{cflags}="-mips3 $config{cflags}" if ($target =~ /mips64/);
864 }
865
866 my $no_shared_warn=0;
867 my $no_user_cflags=0;
868 my $no_user_defines=0;
869
870 if ($user_cflags ne "") { $config{cflags}="$user_cflags$config{cflags}"; }
871 else                    { $no_user_cflags=1;       }
872 if (@user_defines)      { $config{defines}=[ @user_defines, @{$config{defines}} ]; }
873 else                    { $no_user_defines=1;       }
874
875 # The DSO code currently always implements all functions so that no
876 # applications will have to worry about that from a compilation point
877 # of view. However, the "method"s may return zero unless that platform
878 # has support compiled in for them. Currently each method is enabled
879 # by a define "DSO_<name>" ... we translate the "dso_scheme" config
880 # string entry into using the following logic;
881 if (!$no_dso && $target{dso_scheme} ne "")
882         {
883         $target{dso_scheme} =~ tr/[a-z]/[A-Z]/;
884         if ($target{dso_scheme} eq "DLFCN")
885                 {
886                 $config{defines} = [ "DSO_DLFCN", "HAVE_DLFCN_H",
887                                      @{$config{defines}} ]
888                 }
889         elsif ($target{dso_scheme} eq "DLFCN_NO_H")
890                 {
891                 $config{defines} = [ "DSO_DLFCN", @{$config{defines}} ]
892                 }
893         else
894                 {
895                 $config{defines} = [ "DSO_$target{dso_scheme}",
896                                      @{$config{defines}} ]
897                 }
898         }
899
900 my $thread_cflags = "";
901 my @thread_defines;
902 if ($target{thread_cflag} ne "(unknown)" && !$no_threads)
903         {
904         # If we know how to do it, support threads by default.
905         $threads = 1;
906         }
907 if ($target{thread_cflag} eq "(unknown)" && $threads)
908         {
909         # If the user asked for "threads", [s]he is also expected to
910         # provide any system-dependent compiler options that are
911         # necessary.
912         if ($no_user_cflags && $no_user_defines)
913                 {
914                 print "You asked for multi-threading support, but didn't\n";
915                 print "provide any system-specific compiler options\n";
916                 exit(1);
917                 }
918         push @thread_defines, "OPENSSL_THREADS";
919         }
920 else
921         {
922         $thread_cflags=" $target{thread_cflag}";
923         push @thread_defines, @{$target{thread_defines}}, "OPENSSL_THREADS";
924         }
925
926 $config{ex_libs}="$libs$config{ex_libs}" if ($libs ne "");
927
928 if ($no_asm)
929         {
930         @{$config{defines}} = grep !/^[BL]_ENDIAN$/, @{$config{defines}}
931             if ($config{fips});
932         }
933
934 if ($threads)
935         {
936         $config{cflags} = "$thread_cflags $config{cflags}" if $thread_cflags;
937         push @{$config{defines}}, @thread_defines;
938         push @{$config{openssl_thread_defines}}, @thread_defines;
939         }
940
941 if ($zlib)
942         {
943         push @{$config{defines}}, "ZLIB";
944         if (defined($disabled{"zlib-dynamic"}))
945                 {
946                 if (defined($withargs{zlib_lib}))
947                         {
948                         $config{ex_libs} .= " -L" . $withargs{zlib_lib} . " -lz";
949                         }
950                 else
951                         {
952                         $config{ex_libs} .= " -lz";
953                         }
954                 }
955         else
956                 {
957                 push @{$config{defines}}, "ZLIB_SHARED";
958                 }
959         }
960
961 # With "deprecated" disable all deprecated features.
962 if (defined($disabled{"deprecated"})) {
963         $config{api} = $maxapi;
964 }
965
966 if ($target{shared_target} eq "")
967         {
968         $no_shared_warn = 1 if !$config{no_shared} && !$config{fips};
969         $config{no_shared} = 1;
970         }
971 if (!$config{no_shared})
972         {
973         if ($target{shared_cflag} ne "")
974                 {
975                 push @{$config{defines}}, "OPENSSL_PIC";
976                 $config{cflags} = "$target{shared_cflag} $config{cflags}";
977                 }
978         }
979
980 if ($builder ne "mk1mf")
981         {
982         # add {no-}static-engine to options to allow mkdef.pl to work without extra arguments
983         if ($config{no_shared})
984                 {
985                 push @{$config{openssl_other_defines}}, "OPENSSL_NO_DYNAMIC_ENGINE";
986                 $config{options}.=" static-engine";
987                 }
988         else
989                 {
990                 push @{$config{openssl_other_defines}}, "OPENSSL_NO_STATIC_ENGINE";
991                 $config{options}.=" no-static-engine";
992                 }
993         }
994
995 #
996 # Platform fix-ups
997 #
998 if ($target{sys_id} ne "")
999         {
1000         push @{$config{openssl_sys_defines}}, "OPENSSL_SYS_$target{sys_id}";
1001         }
1002
1003 if ($target{ranlib} eq "")
1004         {
1005         $target{ranlib} = $default_ranlib;
1006         }
1007
1008 if (!$no_asm) {
1009     $target{cpuid_asm_src}=$table{BASE}->{cpuid_asm_src} if ($config{processor} eq "386");
1010     $target{cpuid_asm_src}.=" uplink.c uplink-x86.s" if (grep { $_ eq "OPENSSL_USE_APPLINK"} @{$config{defines}});
1011
1012     $target{bn_asm_src} =~ s/\w+-gf2m.c// if (defined($disabled{ec2m}));
1013
1014     # bn-586 is the only one implementing bn_*_part_words
1015     push @{$config{defines}}, "OPENSSL_BN_ASM_PART_WORDS" if ($target{bn_asm_src} =~ /bn-586/);
1016     push @{$config{defines}}, "OPENSSL_IA32_SSE2" if (!$no_sse2 && $target{bn_asm_src} =~ /86/);
1017
1018     push @{$config{defines}}, "OPENSSL_BN_ASM_MONT" if ($target{bn_asm_src} =~ /-mont/);
1019     push @{$config{defines}}, "OPENSSL_BN_ASM_MONT5" if ($target{bn_asm_src} =~ /-mont5/);
1020     push @{$config{defines}}, "OPENSSL_BN_ASM_GF2m" if ($target{bn_asm_src} =~ /-gf2m/);
1021
1022     if ($config{fips}) {
1023         push @{$config{openssl_other_defines}}, "OPENSSL_FIPS";
1024     }
1025
1026     if ($target{sha1_asm_src}) {
1027         push @{$config{defines}}, "SHA1_ASM"   if ($target{sha1_asm_src} =~ /sx86/ || $target{sha1_asm_src} =~ /sha1/);
1028         push @{$config{defines}}, "SHA256_ASM" if ($target{sha1_asm_src} =~ /sha256/);
1029         push @{$config{defines}}, "SHA512_ASM" if ($target{sha1_asm_src} =~ /sha512/);
1030     }
1031     if ($target{md5_asm_src}) {
1032         push @{$config{defines}}, "MD5_ASM";
1033     }
1034     $target{cast_asm_src}=$table{BASE}->{cast_asm_src} if (!$config{no_shared}); # CAST assembler is not PIC
1035     if ($target{rmd160_asm_src}) {
1036         push @{$config{defines}}, "RMD160_ASM";
1037     }
1038     if ($target{aes_asm_src}) {
1039         push @{$config{defines}}, "AES_ASM" if ($target{aes_asm_src} =~ m/\baes-/);;
1040         # aes-ctr.fake is not a real file, only indication that assembler
1041         # module implements AES_ctr32_encrypt...
1042         push @{$config{defines}}, "AES_CTR_ASM" if ($target{aes_asm_src} =~ s/\s*aes-ctr\.fake//);
1043         # aes-xts.fake indicates presence of AES_xts_[en|de]crypt...
1044         push @{$config{defines}}, "AES_XTS_ASM" if ($target{aes_asm_src} =~ s/\s*aes-xts\.fake//);
1045         $target{aes_asm_src} =~ s/\s*(vpaes|aesni)-x86\.s//g if ($no_sse2);
1046         push @{$config{defines}}, "VPAES_ASM" if ($target{aes_asm_src} =~ m/vpaes/);
1047         push @{$config{defines}}, "BSAES_ASM" if ($target{aes_asm_src} =~ m/bsaes/);
1048     }
1049     if ($target{wp_asm_src} =~ /mmx/) {
1050         if ($config{processor} eq "386") {
1051             $target{wp_asm_src}=$table{BASE}->{wp_asm_src};
1052         } elsif (!$disabled{"whirlpool"}) {
1053             $config{cflags}.=" -DWHIRLPOOL_ASM";
1054         }
1055     }
1056     if ($target{modes_asm_src} =~ /ghash-/) {
1057         push @{$config{defines}}, "GHASH_ASM";
1058     }
1059     if ($target{ec_asm_src} =~ /ecp_nistz256/) {
1060         push @{$config{defines}}, "ECP_NISTZ256_ASM";
1061     }
1062     if ($target{poly1305_asm_src} ne "") {
1063         push @{$config{defines}}, "POLY1305_ASM";
1064     }
1065 }
1066
1067 # Is the compiler gcc or clang?  $ecc is used below to see if error-checking
1068 # can be turned on.
1069 my $ecc = $target{cc};
1070 my $ccpcc = "$config{cross_compile_prefix}$target{cc}";
1071 $config{makedepprog} = 'makedepend';
1072 open(PIPE, "$ccpcc --version 2>&1 | head -2 |");
1073 while ( <PIPE> ) {
1074     $config{makedepprog} = $ccpcc if /clang|gcc/;
1075     $ecc = "clang" if /clang/;
1076     $ecc = "gcc" if /gcc/;
1077 }
1078 close(PIPE);
1079
1080 $config{depflags} =~ s/^\s*//;
1081
1082
1083 # Deal with bn_ops ###################################################
1084
1085 $config{bn_ll}                  =0;
1086 $config{export_var_as_fn}       =0;
1087 my $def_int="unsigned int";
1088 $config{rc4_int}                =$def_int;
1089 ($config{b64l},$config{b64},$config{b32})=(0,0,1);
1090
1091 my $count = 0;
1092 foreach (sort split(/\s+/,$target{bn_ops})) {
1093     $count++ if /SIXTY_FOUR_BIT|SIXTY_FOUR_BIT_LONG|THIRTY_TWO_BIT/;
1094     $config{export_var_as_fn}=1                 if $_ eq 'EXPORT_VAR_AS_FN';
1095     $config{bn_ll}=1                            if $_ eq 'BN_LLONG';
1096     $config{rc4_int}="unsigned char"            if $_ eq 'RC4_CHAR';
1097     ($config{b64l},$config{b64},$config{b32})
1098         =(0,1,0)                                if $_ eq 'SIXTY_FOUR_BIT';
1099     ($config{b64l},$config{b64},$config{b32})
1100         =(1,0,0)                                if $_ eq 'SIXTY_FOUR_BIT_LONG';
1101     ($config{b64l},$config{b64},$config{b32})
1102         =(0,0,1)                                if $_ eq 'THIRTY_TWO_BIT';
1103 }
1104 die "Exactly one of SIXTY_FOUR_BIT|SIXTY_FOUR_BIT_LONG|THIRTY_TWO_BIT can be set in bn_ops\n"
1105     if $count > 1;
1106
1107
1108 # Hack cflags for better warnings (dev option) #######################
1109
1110 # "Stringify" the C flags string.  This permits it to be made part of a string
1111 # and works as well on command lines.
1112 $config{cflags} =~ s/([\\\"])/\\\1/g;
1113
1114 if (defined($config{api})) {
1115     $config{openssl_api_defines} = [ "OPENSSL_MIN_API=".$apitable->{$config{api}} ];
1116     my $apiflag = sprintf("OPENSSL_API_COMPAT=%s", $apitable->{$config{api}});
1117     push @default_depdefines, $apiflag;
1118     push @{$config{defines}}, $apiflag;
1119 }
1120
1121 if ($strict_warnings)
1122         {
1123         my $wopt;
1124         die "ERROR --strict-warnings requires gcc or clang"
1125             unless $ecc eq 'gcc' || $ecc eq 'clang';
1126         foreach $wopt (split /\s+/, $gcc_devteam_warn)
1127                 {
1128                 $config{cflags} .= " $wopt" unless ($config{cflags} =~ /(^|\s)$wopt(\s|$)/)
1129                 }
1130         if ($ecc eq "clang")
1131                 {
1132                 foreach $wopt (split /\s+/, $clang_devteam_warn)
1133                         {
1134                         $config{cflags} .= " $wopt" unless ($config{cflags} =~ /(^|\s)$wopt(\s|$)/)
1135                         }
1136                 }
1137         if ($target !~ /^mingw/)
1138                 {
1139                 foreach $wopt (split /\s+/, $memleak_devteam_backtrace)
1140                         {
1141                         $config{cflags} .= " $wopt" unless ($config{cflags} =~ /(^|\s)$wopt(\s|$)/)
1142                         }
1143                 if ($target =~ /^BSD-/)
1144                         {
1145                         $config{ex_libs} .= " -lexecinfo";
1146                         }
1147                 }
1148         }
1149
1150 # If we use the unified build, collect information from build.info files
1151 my %unified_info = ();
1152
1153 if ($builder eq "unified") {
1154     # Store the name of the template file we will build the build file from
1155     # in %config.  This may be useful for the build file itself.
1156     my $build_file_template =
1157         catfile($srcdir, "Configurations",
1158                 $builder_platform."-".$target{build_file}.".tmpl");
1159     $build_file_template =
1160         catfile($srcdir, "Configurations", $target{build_file}.".tmpl")
1161         if (! -f $build_file_template);
1162     $config{build_file_template} = $build_file_template;
1163
1164     use lib catdir(dirname(__FILE__),"util");
1165     use with_fallback qw(Text::Template);
1166
1167     sub cleandir {
1168         my $base = shift;
1169         my $dir = shift;
1170         my $relativeto = shift || ".";
1171
1172         $dir = catdir($base,$dir) unless isabsolute($dir);
1173
1174         # Make sure the directories we're building in exists
1175         mkpath($dir);
1176
1177         my $res = abs2rel(absolutedir($dir), rel2abs($relativeto));
1178         #print STDERR "DEBUG[cleandir]: $dir , $base => $res\n";
1179         return $res;
1180     }
1181
1182     sub cleanfile {
1183         my $base = shift;
1184         my $file = shift;
1185         my $relativeto = shift || ".";
1186
1187         $file = catfile($base,$file) unless isabsolute($file);
1188
1189         my $d = dirname($file);
1190         my $f = basename($file);
1191
1192         # Make sure the directories we're building in exists
1193         mkpath($d);
1194
1195         my $res = abs2rel(catfile(absolutedir($d), $f), rel2abs($relativeto));
1196         #print STDERR "DEBUG[cleanfile]: $d , $f => $res\n";
1197         return $res;
1198     }
1199
1200     my @build_infos = ( [ ".", "build.info" ] );
1201     foreach (@{$config{dirs}}) {
1202         push @build_infos, [ $_, "build.info" ]
1203             if (-f catfile($srcdir, $_, "build.info"));
1204     }
1205     foreach (@{$config{sdirs}}) {
1206         push @build_infos, [ catdir("crypto", $_), "build.info" ]
1207             if (-f catfile($srcdir, "crypto", $_, "build.info"));
1208     }
1209     foreach (@{$config{engdirs}}) {
1210         push @build_infos, [ catdir("engines", $_), "build.info" ]
1211             if (-f catfile($srcdir, "engines", $_, "build.info"));
1212     }
1213
1214     foreach (@build_infos) {
1215         my $sourced = catdir($srcdir, $_->[0]);
1216         my $buildd = catdir($blddir, $_->[0]);
1217
1218         mkpath($buildd);
1219
1220         my $f = $_->[1];
1221         # The basic things we're trying to build
1222         my @programs = ();
1223         my @libraries = ();
1224         my @engines = ();
1225         my @scripts = ();
1226         my @extra = ();
1227         my @intermediates = ();
1228         my @rawlines = ();
1229
1230         my %ordinals = ();
1231         my %sources = ();
1232         my %includes = ();
1233         my %depends = ();
1234         my %renames = ();
1235         my %sharednames = ();
1236
1237         my $template = Text::Template->new(TYPE => 'FILE',
1238                                            SOURCE => catfile($sourced, $f));
1239         die "Something went wrong with $sourced/$f: $!\n" unless $template;
1240         my @text =
1241             split /^/m,
1242             $template->fill_in(HASH => { config => \%config,
1243                                          target => \%target,
1244                                          builddir => abs2rel($buildd, $blddir),
1245                                          sourcedir => abs2rel($sourced, $blddir),
1246                                          buildtop => abs2rel($blddir, $blddir),
1247                                          sourcetop => abs2rel($srcdir, $blddir) },
1248                                DELIMITERS => [ "{-", "-}" ]);
1249
1250         # The top item of this stack has the following values
1251         # -2 positive already run and we found ELSE (following ELSIF should fail)
1252         # -1 positive already run (skip until ENDIF)
1253         # 0 negatives so far (if we're at a condition, check it)
1254         # 1 last was positive (don't skip lines until next ELSE, ELSIF or ENDIF)
1255         # 2 positive ELSE (following ELSIF should fail)
1256         my @skip = ();
1257         collect_information(
1258             collect_from_array([ @text ],
1259                                qr/\\$/ => sub { my $l1 = shift; my $l2 = shift;
1260                                                 $l1 =~ s/\\$//; $l1.$l2 }),
1261             # Info we're looking for
1262             qr/^\s*IF\[((?:\\.|[^\\\]])*)\]\s*$/
1263             => sub { push @skip, !! $1; },
1264             qr/^\s*ELSIF\[((?:\\.|[^\\\]])*)\]\s*$/
1265             => sub { die "ELSIF out of scope" if ! @skip;
1266                      die "ELSIF following ELSE" if abs($skip[$#skip]) == 2;
1267                      $skip[$#skip] = -1 if $skip[$#skip] != 0;
1268                      $skip[$#skip] = !! $1
1269                          if $skip[$#skip] == 0; },
1270             qr/^\s*ELSE\s*$/
1271             => sub { die "ELSE out of scope" if ! @skip;
1272                      $skip[$#skip] = -2 if $skip[$#skip] != 0;
1273                      $skip[$#skip] = 2 if $skip[$#skip] == 0; },
1274             qr/^\s*ENDIF\s*$/
1275             => sub { die "ENDIF out of scope" if ! @skip;
1276                      pop @skip; },
1277             qr/^\s*PROGRAMS\s*=\s*(.*)\s*$/
1278             => sub { push @programs, split(/\s+/, $1)
1279                          if !@skip || $skip[$#skip] > 0 },
1280             qr/^\s*LIBS\s*=\s*(.*)\s*$/
1281             => sub { push @libraries, split(/\s+/, $1)
1282                          if !@skip || $skip[$#skip] > 0 },
1283             qr/^\s*ENGINES\s*=\s*(.*)\s*$/
1284             => sub { push @engines, split(/\s+/, $1)
1285                          if !@skip || $skip[$#skip] > 0 },
1286             qr/^\s*SCRIPTS\s*=\s*(.*)\s*$/
1287             => sub { push @scripts, split(/\s+/, $1)
1288                          if !@skip || $skip[$#skip] > 0 },
1289             qr/^\s*EXTRA\s*=\s*(.*)\s*$/
1290             => sub { push @extra, split(/\s+/, $1)
1291                          if !@skip || $skip[$#skip] > 0 },
1292
1293             qr/^\s*ORDINALS\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/,
1294             => sub { push @{$ordinals{$1}}, split(/\s+/, $2)
1295                          if !@skip || $skip[$#skip] > 0 },
1296             qr/^\s*SOURCE\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
1297             => sub { push @{$sources{$1}}, split(/\s+/, $2)
1298                          if !@skip || $skip[$#skip] > 0 },
1299             qr/^\s*INCLUDE\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
1300             => sub { push @{$includes{$1}}, split(/\s+/, $2)
1301                          if !@skip || $skip[$#skip] > 0 },
1302             qr/^\s*DEPEND\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
1303             => sub { push @{$depends{$1}}, split(/\s+/, $2)
1304                          if !@skip || $skip[$#skip] > 0 },
1305             qr/^\s*RENAME\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
1306             => sub { push @{$renames{$1}}, split(/\s+/, $2)
1307                          if !@skip || $skip[$#skip] > 0 },
1308             qr/^\s*SHARED_NAME\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
1309             => sub { push @{$sharednames{$1}}, split(/\s+/, $2)
1310                          if !@skip || $skip[$#skip] > 0 },
1311             qr/^\s*BEGINRAW\[((?:\\.|[^\\\]])+)\]\s*$/
1312             => sub {
1313                 my $lineiterator = shift;
1314                 my $target_kind = $1;
1315                 while (defined $lineiterator->()) {
1316                     chomp;
1317                     if (/^\s*ENDRAW\[((?:\\.|[^\\\]])+)\]\s*$/) {
1318                         die "ENDRAW doesn't match BEGINRAW"
1319                             if $1 ne $target_kind;
1320                         last;
1321                     }
1322                     next if @skip && $skip[$#skip] <= 0;
1323                     push @rawlines,  $_
1324                         if ($target_kind eq $target{build_file}
1325                             || $target_kind eq $target{build_file}."(".$builder_platform.")");
1326                 }
1327             },
1328             qr/^(?:#.*|\s*)$/ => sub { },
1329             "OTHERWISE" => sub { die "Something wrong with this line:\n$_\nat $sourced/$f" }
1330             );
1331         die "runaway IF?" if (@skip);
1332
1333         foreach (keys %renames) {
1334             die "$_ renamed to more than one thing: "
1335                 ,join(" ", @{$renames{$_}}),"\n"
1336                 if scalar @{$renames{$_}} > 1;
1337             my $dest = cleanfile($buildd, $_, $blddir);
1338             my $to = cleanfile($buildd, $renames{$_}->[0], $blddir);
1339             die "$dest renamed to more than one thing: "
1340                 ,$unified_info{rename}->{$dest}, $to
1341                 unless !defined($unified_info{rename}->{$dest})
1342                 or $unified_info{rename}->{$dest} eq $to;
1343             $unified_info{rename}->{$dest} = $to;
1344         }
1345
1346         foreach (@programs) {
1347             my $program = cleanfile($buildd, $_, $blddir);
1348             if ($unified_info{rename}->{$program}) {
1349                 $program = $unified_info{rename}->{$program};
1350             }
1351             $unified_info{programs}->{$program} = 1;
1352         }
1353
1354         foreach (@libraries) {
1355             my $library = cleanfile($buildd, $_, $blddir);
1356             if ($unified_info{rename}->{$library}) {
1357                 $library = $unified_info{rename}->{$library};
1358             }
1359             $unified_info{libraries}->{$library} = 1;
1360         }
1361
1362         die <<"EOF" if $config{no_shared} && scalar @engines;
1363 ENGINES can only be used if configured with 'shared'.
1364 This is usually a fault in a build.info file.
1365 EOF
1366         foreach (@engines) {
1367             my $library = cleanfile($buildd, $_, $blddir);
1368             if ($unified_info{rename}->{$library}) {
1369                 $library = $unified_info{rename}->{$library};
1370             }
1371             $unified_info{engines}->{$library} = 1;
1372         }
1373
1374         foreach (@scripts) {
1375             my $script = cleanfile($buildd, $_, $blddir);
1376             if ($unified_info{rename}->{$script}) {
1377                 $script = $unified_info{rename}->{$script};
1378             }
1379             $unified_info{scripts}->{$script} = 1;
1380         }
1381
1382         foreach (@extra) {
1383             my $extra = cleanfile($buildd, $_, $blddir);
1384             $unified_info{extra}->{$extra} = 1;
1385         }
1386
1387         push @{$unified_info{rawlines}}, @rawlines;
1388
1389         if (!$config{no_shared}) {
1390             # Check sharednames.
1391             foreach (keys %sharednames) {
1392                 my $dest = cleanfile($buildd, $_, $blddir);
1393                 if ($unified_info{rename}->{$dest}) {
1394                     $dest = $unified_info{rename}->{$dest};
1395                 }
1396                 die "shared_name for $dest with multiple values: "
1397                     ,join(" ", @{$sharednames{$_}}),"\n"
1398                     if scalar @{$sharednames{$_}} > 1;
1399                 my $to = cleanfile($buildd, $sharednames{$_}->[0], $blddir);
1400                 die "shared_name found for a library $dest that isn't defined\n"
1401                     unless $unified_info{libraries}->{$dest};
1402                 die "shared_name for $dest with multiple values: "
1403                     ,$unified_info{sharednames}->{$dest}, ", ", $to
1404                     unless !defined($unified_info{sharednames}->{$dest})
1405                     or $unified_info{sharednames}->{$dest} eq $to;
1406                 $unified_info{sharednames}->{$dest} = $to;
1407             }
1408
1409             # Additionally, we set up sharednames for libraries that don't
1410             # have any, as themselves.
1411             foreach (keys %{$unified_info{libraries}}) {
1412                 if (!defined $unified_info{sharednames}->{$_}) {
1413                     $unified_info{sharednames}->{$_} = $_
1414                 }
1415             }
1416         }
1417
1418         foreach (keys %ordinals) {
1419             my $dest = $_;
1420             my $ddest = cleanfile($buildd, $_, $blddir);
1421             if ($unified_info{rename}->{$ddest}) {
1422                 $ddest = $unified_info{rename}->{$ddest};
1423             }
1424             foreach (@{$ordinals{$dest}}) {
1425                 my %known_ordinals =
1426                     (
1427                      crypto =>
1428                      cleanfile($sourced, catfile("util", "libeay.num"), $blddir),
1429                      ssl =>
1430                      cleanfile($sourced, catfile("util", "ssleay.num"), $blddir)
1431                     );
1432                 my $o = $known_ordinals{$_};
1433                 die "Ordinals for $ddest defined more than once\n"
1434                     if $unified_info{ordinals}->{$ddest};
1435                 $unified_info{ordinals}->{$ddest} = [ $_, $o ];
1436             }
1437         }
1438
1439         foreach (keys %sources) {
1440             my $dest = $_;
1441             my $ddest = cleanfile($buildd, $_, $blddir);
1442             if ($unified_info{rename}->{$ddest}) {
1443                 $ddest = $unified_info{rename}->{$ddest};
1444             }
1445             foreach (@{$sources{$dest}}) {
1446                 my $s = cleanfile($sourced, $_, $blddir);
1447
1448                 # If it isn't in the source tree, we assume it's generated
1449                 # in the build tree
1450                 if (! -f $s) {
1451                     $s = cleanfile($buildd, $_, $blddir);
1452                 }
1453                 # We recognise C and asm files
1454                 if ($s =~ /\.[csS]\b$/) {
1455                     (my $o = $_) =~ s/\.[csS]\b$/.o/;
1456                     $o = cleanfile($buildd, $o, $blddir);
1457                     $unified_info{sources}->{$ddest}->{$o} = 1;
1458                     $unified_info{sources}->{$o}->{$s} = 1;
1459                 } else {
1460                     $unified_info{sources}->{$ddest}->{$s} = 1;
1461                 }
1462             }
1463         }
1464
1465         foreach (keys %depends) {
1466             my $dest = $_;
1467             my $ddest = cleanfile($buildd, $_, $blddir);
1468             if ($unified_info{rename}->{$ddest}) {
1469                 $ddest = $unified_info{rename}->{$ddest};
1470             }
1471             foreach (@{$depends{$dest}}) {
1472                 my $d = cleanfile($sourced, $_, $blddir);
1473
1474                 # If it isn't found in the source, let's assume it's generated
1475                 # and that the Makefile template has the lines
1476                 if (! -f $d) {
1477                     $d = cleanfile($buildd, $_, $blddir);
1478                 }
1479                 # Take note if the file to depend on is being renamed
1480                 if ($unified_info{rename}->{$d}) {
1481                     $d = $unified_info{rename}->{$d};
1482                 }
1483                 $unified_info{depends}->{$ddest}->{$d} = 1;
1484                 # If we depend on a header file, let's make sure it
1485                 # can get included
1486                 if ($d =~ /\.h$/) {
1487                     my $i = dirname($d);
1488                     push @{$unified_info{includes}->{$ddest}}, $i
1489                         unless grep { $_ eq $i } @{$unified_info{includes}->{$ddest}};
1490                 }
1491             }
1492         }
1493
1494         foreach (keys %includes) {
1495             my $dest = $_;
1496             my $ddest = cleanfile($buildd, $_, $blddir);
1497             if ($unified_info{rename}->{$ddest}) {
1498                 $ddest = $unified_info{rename}->{$ddest};
1499             }
1500             foreach (@{$includes{$dest}}) {
1501                 my $i = cleandir($sourced, $_, $blddir);
1502                 push @{$unified_info{includes}->{$ddest}}, $i
1503                     unless grep { $_ eq $i } @{$unified_info{includes}->{$ddest}};
1504             }
1505         }
1506     }
1507
1508     ### Make unified_info a bit more efficient
1509     # One level structures
1510     foreach (("programs", "libraries", "engines", "scripts", "extra")) {
1511         $unified_info{$_} = [ sort keys %{$unified_info{$_}} ];
1512     }
1513     # Two level structures
1514     foreach my $l1 (("sources", "ldadd", "depends")) {
1515         foreach my $l2 (sort keys %{$unified_info{$l1}}) {
1516             $unified_info{$l1}->{$l2} =
1517                 [ sort keys %{$unified_info{$l1}->{$l2}} ];
1518         }
1519     }
1520 }
1521
1522 # For the schemes that need it, we provide the old *_obj configs
1523 # from the *_asm_obj ones
1524 foreach (grep /_asm_src$/, keys %target) {
1525     my $src = $_;
1526     (my $obj = $_) =~ s/_asm_src$/_obj/;
1527     ($target{$obj} = $target{$src}) =~ s/\.[csS]\b/.o/g;
1528 }
1529
1530 # Write down our configuration where it fits #########################
1531
1532 open(OUT,">configdata.pm") || die "unable to create configdata.pm: $!\n";
1533 print OUT <<"EOF";
1534 package configdata;
1535
1536 use strict;
1537 use warnings;
1538
1539 use Exporter;
1540 #use vars qw(\@ISA \@EXPORT);
1541 our \@ISA = qw(Exporter);
1542 our \@EXPORT = qw(\%config \%target %withargs %unified_info);
1543
1544 EOF
1545 print OUT "our %config = (\n";
1546 foreach (sort keys %config) {
1547     if (ref($config{$_}) eq "ARRAY") {
1548         print OUT "  ", $_, " => [ ", join(", ",
1549                                            map { quotify("perl", $_) }
1550                                            @{$config{$_}}), " ],\n";
1551     } else {
1552         print OUT "  ", $_, " => ", quotify("perl", $config{$_}), ",\n"
1553     }
1554 }
1555 print OUT <<"EOF";
1556 );
1557
1558 EOF
1559 print OUT "our %target = (\n";
1560 foreach (sort keys %target) {
1561     if (ref($target{$_}) eq "ARRAY") {
1562         print OUT "  ", $_, " => [ ", join(", ",
1563                                            map { quotify("perl", $_) }
1564                                            @{$target{$_}}), " ],\n";
1565     } else {
1566         print OUT "  ", $_, " => ", quotify("perl", $target{$_}), ",\n"
1567     }
1568 }
1569 print OUT <<"EOF";
1570 );
1571
1572 EOF
1573 print OUT "our \%available_protocols = (\n";
1574 print OUT "  tls => [ ", join(", ", map { quotify("perl", $_) } @tls), " ],\n";
1575 print OUT "  dtls => [ ", join(", ", map { quotify("perl", $_) } @dtls), " ],\n";
1576 print OUT <<"EOF";
1577 );
1578
1579 EOF
1580 print OUT "our \%disabled = (\n";
1581 foreach (sort keys %disabled) {
1582     print OUT "  ", quotify("perl", $_), " => ", quotify("perl", $disabled{$_}), ",\n";
1583 }
1584 print OUT <<"EOF";
1585 );
1586
1587 EOF
1588 print OUT "our %withargs = (\n";
1589 foreach (sort keys %withargs) {
1590     if (ref($withargs{$_}) eq "ARRAY") {
1591         print OUT "  ", $_, " => [ ", join(", ",
1592                                            map { quotify("perl", $_) }
1593                                            @{$withargs{$_}}), " ],\n";
1594     } else {
1595         print OUT "  ", $_, " => ", quotify("perl", $withargs{$_}), ",\n"
1596     }
1597 }
1598 print OUT <<"EOF";
1599 );
1600
1601 EOF
1602 if ($builder eq "unified") {
1603     my $recurse;
1604     $recurse = sub {
1605         my $indent = shift;
1606         foreach (@_) {
1607             if (ref $_ eq "ARRAY") {
1608                 print OUT " "x$indent, "[\n";
1609                 foreach (@$_) {
1610                     $recurse->($indent + 4, $_);
1611                 }
1612                 print OUT " "x$indent, "],\n";
1613             } elsif (ref $_ eq "HASH") {
1614                 my %h = %$_;
1615                 print OUT " "x$indent, "{\n";
1616                 foreach (sort keys %h) {
1617                     if (ref $h{$_} eq "") {
1618                         print OUT " "x($indent + 4), quotify("perl", $_), " => ", quotify("perl", $h{$_}), ",\n";
1619                     } else {
1620                         print OUT " "x($indent + 4), quotify("perl", $_), " =>\n";
1621                         $recurse->($indent + 8, $h{$_});
1622                     }
1623                 }
1624                 print OUT " "x$indent, "},\n";
1625             } else {
1626                 print OUT " "x$indent, quotify("perl", $_), ",\n";
1627             }
1628         }
1629     };
1630     print OUT "our %unified_info = (\n";
1631     foreach (sort keys %unified_info) {
1632         if (ref $unified_info{$_} eq "") {
1633             print OUT " "x4, quotify("perl", $_), " => ", quotify("perl", $unified_info{$_}), ",\n";
1634         } else {
1635             print OUT " "x4, quotify("perl", $_), " =>\n";
1636             $recurse->(8, $unified_info{$_});
1637         }
1638     }
1639     print OUT <<"EOF";
1640 );
1641
1642 EOF
1643 }
1644 print OUT "1;\n";
1645 close(OUT);
1646
1647 die <<"EOF" if $builder ne "unified" && $srcdir ne $blddir;
1648
1649 ***** Trying building anywhere else than in the source tree will not
1650 ***** work for target $config{target}.  To make it possible, it needs
1651 ***** to use the "unified" build scheme.
1652
1653 EOF
1654
1655 print "IsMK1MF       =", ($builder eq "mk1mf" ? "yes" : "no"), "\n";
1656 print "CC            =$target{cc}\n";
1657 print "CFLAG         =$config{cflags}\n";
1658 print "DEFINES       =",join(" ", @{$config{defines}}),"\n";
1659 print "LFLAG         =$config{lflags}\n";
1660 print "PLIB_LFLAG    =$config{plib_lflags}\n";
1661 print "EX_LIBS       =$config{ex_libs}\n";
1662 print "CPUID_OBJ     =$target{cpuid_obj}\n";
1663 print "BN_ASM        =$target{bn_obj}\n";
1664 print "EC_ASM        =$target{ec_obj}\n";
1665 print "DES_ENC       =$target{des_obj}\n";
1666 print "AES_ENC       =$target{aes_obj}\n";
1667 print "BF_ENC        =$target{bf_obj}\n";
1668 print "CAST_ENC      =$target{cast_obj}\n";
1669 print "RC4_ENC       =$target{rc4_obj}\n";
1670 print "RC5_ENC       =$target{rc5_obj}\n";
1671 print "MD5_OBJ_ASM   =$target{md5_obj}\n";
1672 print "SHA1_OBJ_ASM  =$target{sha1_obj}\n";
1673 print "RMD160_OBJ_ASM=$target{rmd160_obj}\n";
1674 print "CMLL_ENC      =$target{cmll_obj}\n";
1675 print "MODES_OBJ     =$target{modes_obj}\n";
1676 print "PADLOCK_OBJ   =$target{padlock_obj}\n";
1677 print "CHACHA_ENC    =$target{chacha_obj}\n";
1678 print "POLY1305_OBJ  =$target{poly1305_obj}\n";
1679 print "PROCESSOR     =$config{processor}\n";
1680 print "RANLIB        =$target{ranlib}\n";
1681 print "ARFLAGS       =$target{arflags}\n";
1682 print "PERL          =$config{perl}\n";
1683 print "\n";
1684 print "SIXTY_FOUR_BIT_LONG mode\n" if $config{b64l};
1685 print "SIXTY_FOUR_BIT mode\n" if $config{b64};
1686 print "THIRTY_TWO_BIT mode\n" if $config{b32};
1687 print "BN_LLONG mode\n" if $config{bn_ll};
1688 print "RC4 uses $config{rc4_int}\n" if $config{rc4_int} != $def_int;
1689
1690 mkpath(catdir($blddir, "include/openssl"));
1691 run_dofile(catfile($blddir, "include/openssl/opensslconf.h"),
1692            catfile($srcdir, "include/openssl/opensslconf.h.in"));
1693
1694 mkpath(catdir($blddir, "crypto/include/internal"));
1695 foreach my $alg ( 'bn' ) {
1696     run_dofile(catfile($blddir, "crypto/include/internal/${alg}_conf.h"),
1697                catfile($srcdir, "crypto/include/internal/${alg}_conf.h.in"));
1698 }
1699
1700 ###
1701 ### When the old "unixmake" scheme goes away, so does this function
1702 ###
1703 sub build_Makefile {
1704     run_dofile("Makefile","Makefile.in");
1705
1706     # Copy all Makefile.in to Makefile (except top-level)
1707     use File::Find;
1708     use IO::File;
1709     find(
1710         {
1711             preprocess => sub {
1712                 grep(!/^\./, @_);
1713             },
1714             wanted => sub {
1715                 return if ($_ ne "Makefile.in" || $File::Find::dir eq ".");
1716                 my $in = IO::File->new($_, "r") or
1717                     die sprintf "Error reading Makefile.in in %s: !$\n",
1718                     $File::Find::dir;
1719                 my $out = IO::File->new("Makefile", "w") or
1720                     die sprintf "Error writing Makefile in %s: !$\n",
1721                     $File::Find::dir;
1722                 print $out "# Generated from $_, do not edit\n";
1723                 while (my $line = <$in>) { print $out $line }
1724                 $in->close() or
1725                     die sprintf "Error reading Makefile.in in %s: !$\n",
1726                     $File::Find::dir;
1727                 $out->close() or
1728                     die sprintf "Error writing Makefile in %s: !$\n",
1729                     $File::Find::dir;
1730             },
1731         },
1732         ".");
1733 }
1734
1735 my %builders = (
1736     unified => sub {
1737         run_dofile(catfile($blddir, $target{build_file}),
1738                    $config{build_file_template},
1739                    catfile($srcdir, "Configurations", "common.tmpl"));
1740
1741         my $make_command = "$make PERL=\'$config{perl}\'";
1742         my $make_targets = "";
1743         my $need_make_depend =
1744             join(" ", @{$config{depdefines}}) ne join(" ", @default_depdefines);
1745         $make_targets .= " depend"
1746             if $need_make_depend && $make_depend;
1747
1748         (system $make_command.$make_targets) == 0
1749             or die "make $make_targets failed"
1750             if $make_targets ne "";
1751
1752         if ($need_make_depend && !$make_depend) {
1753             $warn_make_depend++;
1754         }
1755     },
1756     unixmake => sub {
1757         build_Makefile();
1758
1759         run_dofile("util/domd", "util/domd.in");
1760         chmod 0755, "util/domd";
1761
1762         my $make_command = "$make PERL=\'$config{perl}\'";
1763         my $make_targets = "";
1764         my $need_make_depend =
1765             join(" ", @{$config{depdefines}}) ne join(" ", @default_depdefines);
1766         $make_targets .= " depend"
1767             if $need_make_depend && $make_depend;
1768
1769         (system $make_command.$make_targets) == 0
1770             or die "make $make_targets failed"
1771             if $make_targets ne "";
1772
1773         if ($need_make_depend && !$make_depend) {
1774             $warn_make_depend++;
1775         }
1776     },
1777     mk1mf => sub {
1778         my $platform = shift;
1779         # The only reason we do this is to have something to build MINFO from
1780         build_Makefile();
1781
1782         open (OUT,">crypto/buildinf.h") || die "Can't open buildinf.h";
1783         printf OUT <<"EOF";
1784 #ifndef MK1MF_BUILD
1785   /* auto-generated by Configure for crypto/cversion.c:
1786    * for Unix builds, crypto/Makefile.ssl generates functional definitions;
1787    * Windows builds (and other mk1mf builds) compile cversion.c with
1788    * -DMK1MF_BUILD and use definitions added to this file by util/mk1mf.pl. */
1789   #error "Windows builds (PLATFORM=$target) use mk1mf.pl-created Makefiles"
1790 #endif
1791 EOF
1792         close(OUT);
1793
1794         # create the ms/version32.rc file if needed
1795         if ($platform ne "netware") {
1796             my ($v1, $v2, $v3, $v4);
1797             if ($config{version_num} =~ /^0x([0-9a-f]{1})([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{1})L$/i) {
1798                 $v1=hex $1;
1799                 $v2=hex $2;
1800                 $v3=hex $3;
1801                 $v4=hex $4;
1802             }
1803             open (OUT,">ms/version32.rc") || die "Can't open ms/version32.rc";
1804             print OUT <<"EOF";
1805 #include <winver.h>
1806
1807 LANGUAGE 0x09,0x01
1808
1809 1 VERSIONINFO
1810   FILEVERSION $v1,$v2,$v3,$v4
1811   PRODUCTVERSION $v1,$v2,$v3,$v4
1812   FILEFLAGSMASK 0x3fL
1813 #ifdef _DEBUG
1814   FILEFLAGS 0x01L
1815 #else
1816   FILEFLAGS 0x00L
1817 #endif
1818   FILEOS VOS__WINDOWS32
1819   FILETYPE VFT_DLL
1820   FILESUBTYPE 0x0L
1821 BEGIN
1822     BLOCK "StringFileInfo"
1823     BEGIN
1824         BLOCK "040904b0"
1825         BEGIN
1826             // Required:
1827             VALUE "CompanyName", "The OpenSSL Project, http://www.openssl.org/\\0"
1828             VALUE "FileDescription", "OpenSSL Shared Library\\0"
1829             VALUE "FileVersion", "$config{version}\\0"
1830 #if defined(CRYPTO)
1831             VALUE "InternalName", "libeay32\\0"
1832             VALUE "OriginalFilename", "libeay32.dll\\0"
1833 #elif defined(SSL)
1834             VALUE "InternalName", "ssleay32\\0"
1835             VALUE "OriginalFilename", "ssleay32.dll\\0"
1836 #endif
1837             VALUE "ProductName", "The OpenSSL Toolkit\\0"
1838             VALUE "ProductVersion", "$config{version}\\0"
1839             // Optional:
1840             //VALUE "Comments", "\\0"
1841             VALUE "LegalCopyright", "Copyright Â© 1998-2015 The OpenSSL Project. Copyright Â© 1995-1998 Eric A. Young, Tim J. Hudson. All rights reserved.\\0"
1842             //VALUE "LegalTrademarks", "\\0"
1843             //VALUE "PrivateBuild", "\\0"
1844             //VALUE "SpecialBuild", "\\0"
1845         END
1846     END
1847     BLOCK "VarFileInfo"
1848     BEGIN
1849         VALUE "Translation", 0x409, 0x4b0
1850     END
1851 END
1852 EOF
1853             close(OUT);
1854         }
1855     },
1856     );
1857
1858 $builders{$builder}->($builder_platform, @builder_opts);
1859
1860 print <<"EOF";
1861
1862 Configured for $target.
1863 EOF
1864
1865 print <<"EOF" if (!$no_threads && !$threads);
1866
1867 The library could not be configured for supporting multi-threaded
1868 applications as the compiler options required on this system are not known.
1869 See file INSTALL for details if you need multi-threading.
1870 EOF
1871
1872 print <<"EOF" if ($no_shared_warn);
1873
1874 You gave the option 'shared', which is not supported on this platform, so
1875 we will pretend you gave the option 'no-shared'.  If you know how to implement
1876 shared libraries, please let us know (but please first make sure you have
1877 tried with a current version of OpenSSL).
1878 EOF
1879
1880 print <<"EOF" if ($warn_make_depend);
1881
1882 *** Because of configuration changes, you MUST do the following before
1883 *** building:
1884
1885         make depend
1886 EOF
1887
1888 exit(0);
1889
1890 ######################################################################
1891 #
1892 # Helpers and utility functions
1893 #
1894
1895 # Configuration file reading #########################################
1896
1897 # Helper function to implement conditional inheritance depending on the
1898 # value of $no_asm.  Used in inherit_from values as follows:
1899 #
1900 #      inherit_from => [ "template", asm("asm_tmpl") ]
1901 #
1902 sub asm {
1903     my @x = @_;
1904     sub {
1905         $no_asm ? () : @x;
1906     }
1907 }
1908
1909 # Helper function to implement adding values to already existing configuration
1910 # values.  It handles elements that are ARRAYs, CODEs and scalars
1911 sub _add {
1912     my $separator = shift;
1913
1914     # If there's any ARRAY in the collection of values OR the separator
1915     # is undef, we will return an ARRAY of combined values, otherwise a
1916     # string of joined values with $separator as the separator.
1917     my $found_array = !defined($separator);
1918
1919     my @values =
1920         map {
1921             if (ref($_) eq "ARRAY") {
1922                 $found_array = 1;
1923                 @$_;
1924             } else {
1925                 $_;
1926             }
1927     } (@_);
1928
1929     if ($found_array) {
1930         [ @values ];
1931     } else {
1932         join($separator, @values);
1933     }
1934 }
1935 sub add_before {
1936     my $separator = shift;
1937     my @x = @_;
1938     sub { _add($separator, @x, @_) };
1939 }
1940 sub add {
1941     my $separator = shift;
1942     my @x = @_;
1943     sub { _add($separator, @_, @x) };
1944 }
1945
1946 # configuration reader, evaluates the input file as a perl script and expects
1947 # it to fill %targets with target configurations.  Those are then added to
1948 # %table.
1949 sub read_config {
1950     my $fname = shift;
1951     open(CONFFILE, "< $fname")
1952         or die "Can't open configuration file '$fname'!\n";
1953     my $x = $/;
1954     undef $/;
1955     my $content = <CONFFILE>;
1956     $/ = $x;
1957     close(CONFFILE);
1958     my %targets = ();
1959     {
1960         local %table = %::table;    # Protect %table from tampering
1961
1962         eval $content;
1963         warn $@ if $@;
1964     }
1965
1966     # For each target, check that it's configured with a hash table.
1967     foreach (keys %targets) {
1968         if (ref($targets{$_}) ne "HASH") {
1969             if (ref($targets{$_}) eq "") {
1970                 warn "Deprecated target configuration for $_, ignoring...\n";
1971             } else {
1972                 warn "Misconfigured target configuration for $_ (should be a hash table), ignoring...\n";
1973             }
1974             delete $targets{$_};
1975         }
1976     }
1977
1978     %table = (%table, %targets);
1979
1980 }
1981
1982 # configuration resolver.  Will only resolve all the lazy evalutation
1983 # codeblocks for the chozen target and all those it inherits from,
1984 # recursively
1985 sub resolve_config {
1986     my $target = shift;
1987     my @breadcrumbs = @_;
1988
1989     if (grep { $_ eq $target } @breadcrumbs) {
1990         die "inherit_from loop!  target backtrace:\n  "
1991             ,$target,"\n  ",join("\n  ", @breadcrumbs),"\n";
1992     }
1993
1994     if (!defined($table{$target})) {
1995         warn "Warning! target $target doesn't exist!\n";
1996         return ();
1997     }
1998     # Recurse through all inheritances.  They will be resolved on the
1999     # fly, so when this operation is done, they will all just be a
2000     # bunch of attributes with string values.
2001     # What we get here, though, are keys with references to lists of
2002     # the combined values of them all.  We will deal with lists after
2003     # this stage is done.
2004     my %combined_inheritance = ();
2005     if ($table{$target}->{inherit_from}) {
2006         my @inherit_from =
2007             map { ref($_) eq "CODE" ? $_->() : $_ } @{$table{$target}->{inherit_from}};
2008         foreach (@inherit_from) {
2009             my %inherited_config = resolve_config($_, $target, @breadcrumbs);
2010
2011             # 'template' is a marker that's considered private to
2012             # the config that had it.
2013             delete $inherited_config{template};
2014
2015             map {
2016                 if (!$combined_inheritance{$_}) {
2017                     $combined_inheritance{$_} = [];
2018                 }
2019                 push @{$combined_inheritance{$_}}, $inherited_config{$_};
2020             } keys %inherited_config;
2021         }
2022     }
2023
2024     # We won't need inherit_from in this target any more, since we've
2025     # resolved all the inheritances that lead to this
2026     delete $table{$target}->{inherit_from};
2027
2028     # Now is the time to deal with those lists.  Here's the place to
2029     # decide what shall be done with those lists, all based on the
2030     # values of the target we're currently dealing with.
2031     # - If a value is a coderef, it will be executed with the list of
2032     #   inherited values as arguments.
2033     # - If the corresponding key doesn't have a value at all or is the
2034     #   emoty string, the inherited value list will be run through the
2035     #   default combiner (below), and the result becomes this target's
2036     #   value.
2037     # - Otherwise, this target's value is assumed to be a string that
2038     #   will simply override the inherited list of values.
2039     my $default_combiner = add(" ");
2040
2041     my %all_keys =
2042         map { $_ => 1 } (keys %combined_inheritance,
2043                          keys %{$table{$target}});
2044     foreach (sort keys %all_keys) {
2045
2046         # Current target doesn't have a value for the current key?
2047         # Assign it the default combiner, the rest of this loop body
2048         # will handle it just like any other coderef.
2049         if (!exists $table{$target}->{$_}) {
2050             $table{$target}->{$_} = $default_combiner;
2051         }
2052
2053         my $valuetype = ref($table{$target}->{$_});
2054         if ($valuetype eq "CODE") {
2055             # CODE reference, execute it with the inherited values as
2056             # arguments.
2057             $table{$target}->{$_} =
2058                 $table{$target}->{$_}->(@{$combined_inheritance{$_}});
2059         } elsif ($valuetype eq "ARRAY" || $valuetype eq "") {
2060             # ARRAY or Scalar, just leave it as is.
2061         } else {
2062             # Some other type of reference that we don't handle.
2063             # Better to abort at this point.
2064             die "cannot handle reference type $valuetype,"
2065                 ," found in target $target -> $_\n";
2066         }
2067     }
2068
2069     # Finally done, return the result.
2070     return %{$table{$target}};
2071 }
2072
2073 sub usage
2074         {
2075         print STDERR $usage;
2076         print STDERR "\npick os/compiler from:\n";
2077         my $j=0;
2078         my $i;
2079         my $k=0;
2080         foreach $i (sort keys %table)
2081                 {
2082                 next if $table{$i}->{template};
2083                 next if $i =~ /^debug/;
2084                 $k += length($i) + 1;
2085                 if ($k > 78)
2086                         {
2087                         print STDERR "\n";
2088                         $k=length($i);
2089                         }
2090                 print STDERR $i . " ";
2091                 }
2092         foreach $i (sort keys %table)
2093                 {
2094                 next if $table{$i}->{template};
2095                 next if $i !~ /^debug/;
2096                 $k += length($i) + 1;
2097                 if ($k > 78)
2098                         {
2099                         print STDERR "\n";
2100                         $k=length($i);
2101                         }
2102                 print STDERR $i . " ";
2103                 }
2104         print STDERR "\n\nNOTE: If in doubt, on Unix-ish systems use './config'.\n";
2105         exit(1);
2106         }
2107
2108 sub run_dofile()
2109 {
2110     my $out = shift;
2111     my @templates = @_;
2112
2113     unlink $out || warn "Can't remove $out, $!"
2114         if -f $out;
2115     foreach (@templates) {
2116         die "Can't open $_, $!" unless -f $_;
2117     }
2118     my $cmd = "$config{perl} \"-I.\" \"-Mconfigdata\" $dofile -o\"Configure\" \"".join("\" \"",@templates)."\" > \"$out.new\"";
2119     #print STDERR "DEBUG[run_dofile]: \$cmd = $cmd\n";
2120     system($cmd);
2121     exit 1 if $? != 0;
2122     rename("$out.new", $out) || die "Can't rename $out.new, $!";
2123 }
2124
2125 # Configuration printer ##############################################
2126
2127 sub print_table_entry
2128 {
2129     my $target = shift;
2130     my %target = resolve_config($target);
2131     my $type = shift;
2132
2133     # Don't print the templates
2134     return if $target{template};
2135
2136     my @sequence = (
2137         "sys_id",
2138         "cc",
2139         "cflags",
2140         "defines",
2141         "debug_cflags",
2142         "debug_defines",
2143         "release_cflags",
2144         "release_defines",
2145         "thread_cflag",
2146         "unistd",
2147         "ld",
2148         "lflags",
2149         "plib_lflags",
2150         "ex_libs",
2151         "debug_lflags",
2152         "debug_plib_lflags",
2153         "debug_ex_libs",
2154         "release_lflags",
2155         "release_plib_lflags",
2156         "release_ex_libs",
2157         "bn_ops",
2158         "cpuid_obj",
2159         "bn_obj",
2160         "ec_obj",
2161         "des_obj",
2162         "aes_obj",
2163         "bf_obj",
2164         "md5_obj",
2165         "sha1_obj",
2166         "cast_obj",
2167         "rc4_obj",
2168         "rmd160_obj",
2169         "rc5_obj",
2170         "wp_obj",
2171         "cmll_obj",
2172         "modes_obj",
2173         "padlock_obj",
2174         "perlasm_scheme",
2175         "dso_scheme",
2176         "shared_target",
2177         "shared_cflag",
2178         "shared_ldflag",
2179         "shared_extension",
2180         "obj_extension",
2181         "exe_extension",
2182         "ranlib",
2183         "ar",
2184         "arflags",
2185         "multilib",
2186         "build_scheme",
2187         );
2188
2189     if ($type eq "TABLE") {
2190         print "\n";
2191         print "*** $target\n";
2192         printf "\$%-12s = %s\n", $_, $target{$_} foreach (@sequence);
2193     } elsif ($type eq "HASH") {
2194         my $largest =
2195             length((sort { length($a) <=> length($b) } @sequence)[-1]);
2196         print "    '$target' => {\n";
2197         foreach (@sequence) {
2198             if ($target{$_}) {
2199                 print "      '",$_,"'"," " x ($largest - length($_))," => '",$target{$_},"',\n";
2200             }
2201         }
2202         print "    },\n";
2203     }
2204 }
2205
2206 # Utility routines ###################################################
2207
2208 # On VMS, if the given file is a logical name, File::Spec::Functions
2209 # will consider it an absolute path.  There are cases when we want a
2210 # purely syntactic check without checking the environment.
2211 sub isabsolute {
2212     my $file = shift;
2213
2214     # On non-platforms, we just use file_name_is_absolute().
2215     return file_name_is_absolute($file) unless $^O eq "VMS";
2216
2217     # If the file spec includes a device or a directpry spec,
2218     # file_name_is_absolute() is perfectly safe.
2219     return file_name_is_absolute($file) if $file =~ m|[:\[]|;
2220
2221     # Here, we know the given file spec isn't absolute
2222     return 0;
2223 }
2224
2225 # Makes a directory absolute and cleans out /../ in paths like foo/../bar
2226 # On some platforms, this uses rel2abs(), while on others, realpath() is used.
2227 # realpath() requires that at least all path components except the last is an
2228 # existing directory.  On VMS, the last component of the directory spec must
2229 # exist.
2230 sub absolutedir {
2231     my $dir = shift;
2232
2233     # realpath() is quite buggy on VMS.  It uses LIB$FID_TO_NAME, which
2234     # will return the volume name for the device, no matter what.  Also,
2235     # it will return an incorrect directory spec if the argument is a
2236     # directory that doesn't exist.
2237     if ($^O eq "VMS") {
2238         return rel2abs($dir);
2239     }
2240
2241     # We use realpath() on Unix, since no other will properly clean out
2242     # a directory spec.
2243     use Cwd qw/realpath/;
2244
2245     return realpath($dir);
2246 }
2247
2248 sub which
2249         {
2250         my($name)=@_;
2251         my $path;
2252         foreach $path (split /:/, $ENV{PATH})
2253                 {
2254                 if (-f "$path/$name$target{exe_extension}" and -x _)
2255                         {
2256                         return "$path/$name$target{exe_extension}" unless ($name eq "perl" and
2257                          system("$path/$name$target{exe_extension} -e " . '\'exit($]<5.0);\''));
2258                         }
2259                 }
2260         }
2261
2262 sub quotify {
2263     my %processors = (
2264         perl    => sub { my $x = shift;
2265                          $x =~ s/([\\\$\@"])/\\$1/g;
2266                          return '"'.$x.'"'; },
2267         );
2268     my $for = shift;
2269     my $processor =
2270         defined($processors{$for}) ? $processors{$for} : sub { shift; };
2271
2272     map { $processor->($_); } @_;
2273 }
2274
2275 # collect_from_file($filename, $line_concat_cond_re, $line_concat)
2276 # $filename is a file name to read from
2277 # $line_concat_cond_re is a regexp detecting a line continuation ending
2278 # $line_concat is a CODEref that takes care of concatenating two lines
2279 sub collect_from_file {
2280     my $filename = shift;
2281     my $line_concat_cond_re = shift;
2282     my $line_concat = shift;
2283
2284     open my $fh, $filename || die "unable to read $filename: $!\n";
2285     return sub {
2286         my $saved_line = "";
2287         $_ = "";
2288         while (<$fh>) {
2289             chomp;
2290             if (defined $line_concat) {
2291                 $_ = $line_concat->($saved_line, $_);
2292                 $saved_line = "";
2293             }
2294             if (defined $line_concat_cond_re && /$line_concat_cond_re/) {
2295                 $saved_line = $_;
2296                 next;
2297             }
2298             return $_;
2299         }
2300         die "$filename ending with continuation line\n" if $_;
2301         close $fh;
2302         return undef;
2303     }
2304 }
2305
2306 # collect_from_array($array, $line_concat_cond_re, $line_concat)
2307 # $array is an ARRAYref of lines
2308 # $line_concat_cond_re is a regexp detecting a line continuation ending
2309 # $line_concat is a CODEref that takes care of concatenating two lines
2310 sub collect_from_array {
2311     my $array = shift;
2312     my $line_concat_cond_re = shift;
2313     my $line_concat = shift;
2314     my @array = (@$array);
2315
2316     return sub {
2317         my $saved_line = "";
2318         $_ = "";
2319         while (defined($_ = shift @array)) {
2320             chomp;
2321             if (defined $line_concat) {
2322                 $_ = $line_concat->($saved_line, $_);
2323                 $saved_line = "";
2324             }
2325             if (defined $line_concat_cond_re && /$line_concat_cond_re/) {
2326                 $saved_line = $_;
2327                 next;
2328             }
2329             return $_;
2330         }
2331         die "input text ending with continuation line\n" if $_;
2332         return undef;
2333     }
2334 }
2335
2336 # collect_information($lineiterator, $line_continue, $regexp => $CODEref, ...)
2337 # $lineiterator is a CODEref that delivers one line at a time.
2338 # All following arguments are regex/CODEref pairs, where the regexp detects a
2339 # line and the CODEref does something with the result of the regexp.
2340 sub collect_information {
2341     my $lineiterator = shift;
2342     my %collectors = @_;
2343
2344     while(defined($_ = $lineiterator->())) {
2345         chomp;
2346         my $found = 0;
2347         foreach my $re (keys %collectors) {
2348             if ($re ne "OTHERWISE" && /$re/) {
2349                 $collectors{$re}->($lineiterator);
2350                 $found = 1;
2351             };
2352         }
2353         if ($collectors{"OTHERWISE"}) {
2354             $collectors{"OTHERWISE"}->($lineiterator, $_)
2355                 unless $found || !defined $collectors{"OTHERWISE"};
2356         }
2357     }
2358 }