Configure: Add support for variables in build.info files
[openssl.git] / Configure
index 17de50e6897b5464ece653cec09b5737a26659e3..69a06d60622dd85404429316f377993830a69891 100755 (executable)
--- a/Configure
+++ b/Configure
@@ -1407,13 +1407,31 @@ unless ($disabled{asm}) {
     $target{bn_asm_src} =~ s/\w+-gf2m.c// if (defined($disabled{ec2m}));
 
     # bn-586 is the only one implementing bn_*_part_words
-    push @{$config{lib_defines}}, "OPENSSL_BN_ASM_PART_WORDS" if ($target{bn_asm_src} =~ /bn-586/);
-    push @{$config{lib_defines}}, "OPENSSL_IA32_SSE2" if (!$disabled{sse2} && $target{bn_asm_src} =~ /86/);
+    if ($target{bn_asm_src} =~ /bn-586/) {
+        push @{$config{lib_defines}}, "OPENSSL_BN_ASM_PART_WORDS";
+        push @{$config{module_defines}}, "OPENSSL_BN_ASM_PART_WORDS";
+    }
+    if (!$disabled{sse2} && $target{bn_asm_src} =~ /86/) {
+        push @{$config{lib_defines}}, "OPENSSL_IA32_SSE2";
+        push @{$config{module_defines}}, "OPENSSL_IA32_SSE2";
+    }
 
-    push @{$config{lib_defines}}, "OPENSSL_BN_ASM_MONT" if ($target{bn_asm_src} =~ /-mont/);
-    push @{$config{lib_defines}}, "OPENSSL_BN_ASM_MONT5" if ($target{bn_asm_src} =~ /-mont5/);
-    push @{$config{lib_defines}}, "OPENSSL_BN_ASM_GF2m" if ($target{bn_asm_src} =~ /-gf2m/);
-    push @{$config{lib_defines}}, "BN_DIV3W" if ($target{bn_asm_src} =~ /-div3w/);
+    if ($target{bn_asm_src} =~ /-mont/) {
+        push @{$config{lib_defines}}, "OPENSSL_BN_ASM_MONT";
+        push @{$config{module_defines}}, "OPENSSL_BN_ASM_MONT";
+    }
+    if ($target{bn_asm_src} =~ /-mont5/) {
+        push @{$config{lib_defines}}, "OPENSSL_BN_ASM_MONT5";
+        push @{$config{module_defines}}, "OPENSSL_BN_ASM_MONT5";
+    }
+    if ($target{bn_asm_src} =~ /-gf2m/) {
+        push @{$config{lib_defines}}, "OPENSSL_BN_ASM_GF2m";
+        push @{$config{module_defines}}, "OPENSSL_BN_ASM_GF2m";
+    }
+    if ($target{bn_asm_src} =~ /-div3w/) {
+        push @{$config{lib_defines}}, "BN_DIV3W";
+        push @{$config{module_defines}}, "BN_DIV3W";
+    }
 
     if ($target{sha1_asm_src}) {
         push @{$config{lib_defines}}, "SHA1_ASM"   if ($target{sha1_asm_src} =~ /sx86/ || $target{sha1_asm_src} =~ /sha1/);
@@ -1808,6 +1826,24 @@ if ($builder eq "unified") {
         my %depends = ();
         my %generate = ();
 
+        # Support for $variablename in build.info files.
+        # Embedded perl code is the ultimate master, still.  If its output
+        # contains a dollar sign, it had better be escaped, or it will be
+        # taken for a variable name prefix.
+        my %variables = ();
+        my $variable_re = qr/\$([[:alpha:]][[:alnum:]_]*)/;
+        my $expand_variables = sub {
+            my $value = '';
+            my $value_rest = shift;
+
+            while ($value_rest =~ /(?<!\\)${variable_re}/) {
+                $value .= $`;
+                $value .= $variables{$1};
+                $value_rest = $';
+            }
+            return $value . $value_rest;
+        };
+
         # We want to detect configdata.pm in the source tree, so we
         # don't use it if the build tree is different.
         my $src_configdata = cleanfile($srcdir, "configdata.pm", $blddir);
@@ -1863,10 +1899,16 @@ if ($builder eq "unified") {
             qr/^\s*ENDIF\s*$/
             => sub { die "ENDIF out of scope" if ! @skip;
                      pop @skip; },
+            qr/^\s*${variable_re}\s*=\s*(.*?)\s*$/
+            => sub {
+                if (!@skip || $skip[$#skip] > 0) {
+                    $variables{$1} = $2;
+                }
+            },
             qr/^\s*SUBDIRS\s*=\s*(.*)\s*$/
             => sub {
                 if (!@skip || $skip[$#skip] > 0) {
-                    foreach (tokenize($1)) {
+                    foreach (tokenize($expand_variables->($1))) {
                         push @build_dirs, [ @curd, splitdir($_, 1) ];
                     }
                 }
@@ -1875,7 +1917,7 @@ if ($builder eq "unified") {
             => sub {
                 if (!@skip || $skip[$#skip] > 0) {
                     my @a = tokenize($1, qr|\s*,\s*|);
-                    my @p = tokenize($2);
+                    my @p = tokenize($expand_variables->($2));
                     push @programs, @p;
                     foreach my $a (@a) {
                         my $ak = $a;
@@ -1894,7 +1936,7 @@ if ($builder eq "unified") {
             => sub {
                 if (!@skip || $skip[$#skip] > 0) {
                     my @a = tokenize($1, qr|\s*,\s*|);
-                    my @l = tokenize($2);
+                    my @l = tokenize($expand_variables->($2));
                     push @libraries, @l;
                     foreach my $a (@a) {
                         my $ak = $a;
@@ -1913,7 +1955,7 @@ if ($builder eq "unified") {
             => sub {
                 if (!@skip || $skip[$#skip] > 0) {
                     my @a = tokenize($1, qr|\s*,\s*|);
-                    my @m = tokenize($2);
+                    my @m = tokenize($expand_variables->($2));
                     push @modules, @m;
                     foreach my $a (@a) {
                         my $ak = $a;
@@ -1932,7 +1974,7 @@ if ($builder eq "unified") {
             => sub {
                 if (!@skip || $skip[$#skip] > 0) {
                     my @a = tokenize($1, qr|\s*,\s*|);
-                    my @s = tokenize($2);
+                    my @s = tokenize($expand_variables->($2));
                     push @scripts, @s;
                     foreach my $a (@a) {
                         my $ak = $a;
@@ -1949,22 +1991,23 @@ if ($builder eq "unified") {
             },
 
             qr/^\s*ORDINALS\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/,
-            => sub { push @{$ordinals{$1}}, tokenize($2)
+            => sub { push @{$ordinals{$1}}, tokenize($expand_variables->($2))
                          if !@skip || $skip[$#skip] > 0 },
             qr/^\s*SOURCE\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
-            => sub { push @{$sources{$1}}, tokenize($2)
+            => sub { push @{$sources{$1}}, tokenize($expand_variables->($2))
                          if !@skip || $skip[$#skip] > 0 },
             qr/^\s*SHARED_SOURCE\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
-            => sub { push @{$shared_sources{$1}}, tokenize($2)
+            => sub { push @{$shared_sources{$1}},
+                         tokenize($expand_variables->($2))
                          if !@skip || $skip[$#skip] > 0 },
             qr/^\s*INCLUDE\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
-            => sub { push @{$includes{$1}}, tokenize($2)
+            => sub { push @{$includes{$1}}, tokenize($expand_variables->($2))
                          if !@skip || $skip[$#skip] > 0 },
             qr/^\s*DEFINE\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
-            => sub { push @{$defines{$1}}, tokenize($2)
+            => sub { push @{$defines{$1}}, tokenize($expand_variables->($2))
                          if !@skip || $skip[$#skip] > 0 },
             qr/^\s*DEPEND\[((?:\\.|[^\\\]])*)\]\s*=\s*(.*)\s*$/
-            => sub { push @{$depends{$1}}, tokenize($2)
+            => sub { push @{$depends{$1}}, tokenize($expand_variables->($2))
                          if !@skip || $skip[$#skip] > 0 },
             qr/^\s*GENERATE\[((?:\\.|[^\\\]])+)\]\s*=\s*(.*)\s*$/
             => sub { push @{$generate{$1}}, $2
@@ -2191,6 +2234,34 @@ They are ignored and should be replaced with a combination of GENERATE,
 DEPEND and SHARED_SOURCE.
 EOF
 
+
+    # Go through the sources of all libraries and check that the same basename
+    # doesn't appear more than once.  Some static library archivers depend on
+    # them being unique.
+    {
+        my $err = 0;
+        foreach my $prod (keys %{$unified_info{libraries}}) {
+            my @prod_sources =
+                map { keys %{$unified_info{sources}->{$_}} }
+                keys %{$unified_info{sources}->{$prod}};
+            my %srccnt = ();
+
+            # Count how many times a given each source basename
+            # appears for each product.
+            foreach my $src (@prod_sources) {
+                $srccnt{basename $src}++;
+            }
+
+            foreach my $src (keys %srccnt) {
+                if ((my $cnt = $srccnt{$src}) > 1) {
+                    print STDERR "$src appears $cnt times for the product $prod\n";
+                    $err++
+                }
+            }
+        }
+        die if $err > 0;
+    }
+
     # Massage the result
 
     # If we depend on a header file or a perl module, add an inclusion of
@@ -2301,6 +2372,7 @@ EOF
             }
         }
     }
+
     # At this point, we have a number of sources with the value -1.  They
     # aren't part of the local build and are probably meant for a different
     # platform, and can therefore be cleaned away.  That happens when making