1##
2## Makefile for OpenSSL
3##
4## {- join("\n## ", @autowarntext) -}
5{-
6     use OpenSSL::Util;
7
8     our $makedep_scheme = $config{makedep_scheme};
9     our $makedepcmd = platform->makedepcmd();
10
11     sub windowsdll { $config{target} =~ /^(?:Cygwin|mingw)/ }
12
13     # Shared AIX support is special. We put libcrypto[64].so.ver into
14     # libcrypto.a and use libcrypto_a.a as static one, unless using
15     # shared_target style aix-solib.  In that mode, create
16     # libcrypto.so as a link-import library that inserts runtime
17     # dependencies on libcrypto.so.ver, and the static library is
18     # named libcrypto.a.
19     sub sharedaix  { !$disabled{shared} && $target{shared_target} =~ /^aix(?!-solib$)/ }
20     sub sharedaix_solib  { !$disabled{shared} && $target{shared_target} =~ /^aix-solib$/ }
21
22     our $sover_dirname = platform->shlib_version_as_filename();
23
24     # This makes sure things get built in the order they need
25     # to. You're welcome.
26     sub dependmagic {
27         my $target = shift;
28         my $help = shift;
29
30         return "$target: build_generated ## $help\n\t\"\$(MAKE)\" depend && \"\$(MAKE)\" _$target\n_$target";
31     }
32
33     our $COLUMNS = $ENV{COLUMNS};
34     if ($COLUMNS =~ /^\d+$/) {
35         $COLUMNS = int($COLUMNS) - 2; # 2 to leave space for ending ' \'
36     } else {
37         $COLUMNS = 76;
38     }
39
40     sub fill_lines {
41         my $item_sep = shift;                  # string
42         my $line_length = shift;               # number of chars
43
44         my @result = ();
45         my $resultpos = 0;
46
47         foreach (@_) {
48             my $fill_line = $result[$resultpos] // '';
49             my $newline =
50                 ($fill_line eq '' ? '' : $fill_line . $item_sep) . $_;
51
52             if (length($newline) > $line_length) {
53                 # If this is a single item and the intended result line
54                 # is empty, we put it there anyway
55                 if ($fill_line eq '') {
56                     $result[$resultpos++] = $newline;
57                 } else {
58                     $result[++$resultpos] = $_;
59                 }
60             } else {
61                 $result[$resultpos] = $newline;
62             }
63         }
64         return @result;
65     }
66     '';
67-}
68PLATFORM={- $config{target} -}
69OPTIONS={- $config{options} -}
70CONFIGURE_ARGS=({- join(", ",quotify_l(@{$config{perlargv}})) -})
71SRCDIR={- $config{sourcedir} -}
72BLDDIR={- $config{builddir} -}
73FIPSKEY={- $config{FIPSKEY} -}
74
75VERSION={- "$config{full_version}" -}
76VERSION_NUMBER={- "$config{version}" -}
77MAJOR={- $config{major} -}
78MINOR={- $config{minor} -}
79SHLIB_VERSION_NUMBER={- $config{shlib_version} -}
80SHLIB_TARGET={- $target{shared_target} -}
81
82LIBS={- join(" \\\n" . ' ' x 5,
83             fill_lines(" ", $COLUMNS - 5,
84                        map { platform->staticlib($_) // () }
85                        @{$unified_info{libraries}})) -}
86SHLIBS={- join(" \\\n" . ' ' x 7,
87               fill_lines(" ", $COLUMNS - 7,
88                          map { platform->sharedlib($_) // () }
89                          @{$unified_info{libraries}})) -}
90SHLIB_INFO={- join(" \\\n" . ' ' x 11,
91                   fill_lines(" ", $COLUMNS - 11,
92                          map { my $x = platform->sharedlib($_);
93                                my $y = platform->sharedlib_simple($_) // '';
94                                my $z = platform->sharedlib_import($_) // '';
95                                $x ? "\"$x;$y;$z\"" : () }
96                          @{$unified_info{libraries}})) -}
97MODULES={- join(" \\\n" . ' ' x 8,
98                fill_lines(" ", $COLUMNS - 8,
99                           map { platform->dso($_) }
100                           # Drop all modules that are dependencies, they will
101                           # be processed through their dependents
102                           grep { my $x = $_;
103                                  !grep { grep { $_ eq $x } @$_ }
104                                        values %{$unified_info{depends}} }
105                           @{$unified_info{modules}})) -}
106FIPSMODULE={- # We do some extra checking here, as there should be only one
107              use File::Basename;
108              our @fipsmodules =
109                  grep { !$unified_info{attributes}->{modules}->{$_}->{noinst}
110                         && $unified_info{attributes}->{modules}->{$_}->{fips} }
111                  @{$unified_info{modules}};
112              die "More that one FIPS module" if scalar @fipsmodules > 1;
113              join(" ", map { platform->dso($_) } @fipsmodules) -}
114FIPSMODULENAME={- die "More that one FIPS module" if scalar @fipsmodules > 1;
115                  join(" ", map { basename(platform->dso($_)) } @fipsmodules) -}
116
117PROGRAMS={- join(" \\\n" . ' ' x 9,
118                 fill_lines(" ", $COLUMNS - 9,
119                            map { platform->bin($_) }
120                            @{$unified_info{programs}})) -}
121SCRIPTS={- join(" \\\n" . ' ' x 8,
122                fill_lines(" ", $COLUMNS - 8, @{$unified_info{scripts}})) -}
123{- output_off() if $disabled{makedepend}; "" -}
124DEPS={- join(" \\\n" . ' ' x 5,
125             fill_lines(" ", $COLUMNS - 5,
126                        map { platform->isobj($_) ? platform->dep($_) : () }
127                        grep { $unified_info{sources}->{$_}->[0] =~ /\.c$/ }
128                        keys %{$unified_info{sources}})); -}
129{- output_on() if $disabled{makedepend}; "" -}
130GENERATED_MANDATORY={- join(" \\\n" . ' ' x 20,
131                            fill_lines(" ", $COLUMNS - 20,
132                                       @{$unified_info{depends}->{""}})) -}
133GENERATED_PODS={- # common0.tmpl provides @generated
134                  join(" \\\n" . ' ' x 15,
135                       fill_lines(" ", $COLUMNS - 15,
136                                  map { my $x = $_;
137                                        (
138                                          grep {
139                                                 $unified_info{attributes}->{depends}
140                                                 ->{$x}->{$_}->{pod} // 0
141                                               }
142                                              keys %{$unified_info{attributes}->{depends}->{$x}}
143                                        ) ? $x : ();
144                                      }
145                                      @generated)) -}
146GENERATED={- # common0.tmpl provides @generated
147             join(" \\\n" . ' ' x 5,
148                  fill_lines(" ", $COLUMNS - 5,
149                             map { platform->convertext($_) } @generated )) -}
150
151INSTALL_LIBS={-
152        join(" \\\n" . ' ' x 13,
153             fill_lines(" ", $COLUMNS - 13,
154                        map { platform->staticlib($_) // () }
155                        grep { !$unified_info{attributes}->{libraries}->{$_}->{noinst} }
156                        @{$unified_info{libraries}}))
157-}
158INSTALL_SHLIBS={-
159        join(" \\\n" . ' ' x 15,
160             fill_lines(" ", $COLUMNS - 15,
161                        map { platform->sharedlib($_) // () }
162                        grep { !$unified_info{attributes}->{libraries}->{$_}->{noinst} }
163                        @{$unified_info{libraries}}))
164-}
165INSTALL_SHLIB_INFO={-
166        join(" \\\n" . ' ' x 19,
167             fill_lines(" ", $COLUMNS - 19,
168                        map { my $x = platform->sharedlib($_);
169                              my $y = platform->sharedlib_simple($_) // '';
170                              my $z = platform->sharedlib_import($_) // '';
171                              $x ? "\"$x;$y;$z\"" : () }
172                        grep { !$unified_info{attributes}->{libraries}->{$_}->{noinst} }
173                        @{$unified_info{libraries}}))
174-}
175INSTALL_ENGINES={-
176        join(" \\\n" . ' ' x 16,
177             fill_lines(" ", $COLUMNS - 16,
178                        map { platform->dso($_) }
179                        grep { !$unified_info{attributes}->{modules}->{$_}->{noinst}
180                               && $unified_info{attributes}->{modules}->{$_}->{engine} }
181                        @{$unified_info{modules}}))
182-}
183INSTALL_MODULES={-
184        join(" \\\n" . ' ' x 16,
185             fill_lines(" ", $COLUMNS - 16,
186                        map { platform->dso($_) }
187                        grep { !$unified_info{attributes}->{modules}->{$_}->{noinst}
188                               && !$unified_info{attributes}->{modules}->{$_}->{engine}
189                               && !$unified_info{attributes}->{modules}->{$_}->{fips} }
190                        @{$unified_info{modules}}))
191-}
192INSTALL_FIPSMODULE={-
193        join(" \\\n" . ' ' x 16,
194             fill_lines(" ", $COLUMNS - 16,
195                        map { platform->dso($_) }
196                        grep { !$unified_info{attributes}->{modules}->{$_}->{noinst}
197                               && $unified_info{attributes}->{modules}->{$_}->{fips} }
198                        @{$unified_info{modules}}))
199-}
200INSTALL_FIPSMODULECONF=providers/fipsmodule.cnf
201INSTALL_PROGRAMS={-
202        join(" \\\n" . ' ' x 16,
203             fill_lines(" ", $COLUMNS - 16, map { platform->bin($_) }
204                        grep { !$unified_info{attributes}->{programs}->{$_}->{noinst} }
205                        @{$unified_info{programs}}))
206-}
207INSTALL_EXPORTERS_PKGCONFIG={-
208        join(" \\\n" . ' ' x 28,
209             fill_lines(" ", $COLUMNS - 28,
210                        grep { $unified_info{attributes}->{generate}->{$_}->{exporter} eq 'pkg-config'}
211                        sort keys %{$unified_info{generate}}))
212-}
213INSTALL_EXPORTERS_CMAKE={-
214        join(" \\\n" . ' ' x 24,
215             fill_lines(" ", $COLUMNS - 24,
216                        grep { $unified_info{attributes}->{generate}->{$_}->{exporter} eq 'cmake'}
217                        sort keys %{$unified_info{generate}}))
218-}
219BIN_SCRIPTS={-
220        join(" \\\n" . ' ' x 12,
221             fill_lines(" ", $COLUMNS - 12,
222                        map { my $x = $unified_info{attributes}->{scripts}->{$_}->{linkname};
223                              $x ? "$_:$x" : $_ }
224                        grep { !$unified_info{attributes}->{scripts}->{$_}->{noinst}
225                               && !$unified_info{attributes}->{scripts}->{$_}->{misc} }
226                        @{$unified_info{scripts}}))
227-}
228MISC_SCRIPTS={-
229        join(" \\\n" . ' ' x 13,
230             fill_lines(" ", $COLUMNS - 13,
231                        map { my $x = $unified_info{attributes}->{scripts}->{$_}->{linkname};
232                              $x ? "$_:$x" : $_ }
233                        grep { !$unified_info{attributes}->{scripts}->{$_}->{noinst}
234                               && $unified_info{attributes}->{scripts}->{$_}->{misc} }
235                        @{$unified_info{scripts}}))
236-}
237IMAGEDOCS1={-
238        join(" \\\n" . ' ' x 10,
239             fill_lines(" ", $COLUMNS - 10,
240                        @{$unified_info{imagedocs}->{man1}})) -}
241IMAGEDOCS3={-
242        join(" \\\n" . ' ' x 10,
243             fill_lines(" ", $COLUMNS - 10,
244                        @{$unified_info{imagedocs}->{man3}})) -}
245IMAGEDOCS5={-
246        join(" \\\n" . ' ' x 10,
247             fill_lines(" ", $COLUMNS - 10,
248                        @{$unified_info{imagedocs}->{man5}})) -}
249IMAGEDOCS7={-
250        join(" \\\n" . ' ' x 10,
251             fill_lines(" ", $COLUMNS - 10,
252                        @{$unified_info{imagedocs}->{man7}})) -}
253HTMLDOCS1={-
254        join(" \\\n" . ' ' x 10,
255             fill_lines(" ", $COLUMNS - 10,
256                        @{$unified_info{htmldocs}->{man1}})) -}
257HTMLDOCS3={-
258        join(" \\\n" . ' ' x 10,
259             fill_lines(" ", $COLUMNS - 10,
260                        @{$unified_info{htmldocs}->{man3}})) -}
261HTMLDOCS5={-
262        join(" \\\n" . ' ' x 10,
263             fill_lines(" ", $COLUMNS - 10,
264                        @{$unified_info{htmldocs}->{man5}})) -}
265HTMLDOCS7={-
266        join(" \\\n" . ' ' x 10,
267             fill_lines(" ", $COLUMNS - 10,
268                        @{$unified_info{htmldocs}->{man7}})) -}
269MANDOCS1={-
270        join(" \\\n" . ' ' x 9,
271             fill_lines(" ", $COLUMNS - 9,
272                        @{$unified_info{mandocs}->{man1}})) -}
273MANDOCS3={-
274        join(" \\\n" . ' ' x 9,
275             fill_lines(" ", $COLUMNS - 9,
276                        @{$unified_info{mandocs}->{man3}})) -}
277MANDOCS5={-
278        join(" \\\n" . ' ' x 9,
279             fill_lines(" ", $COLUMNS - 9,
280                        @{$unified_info{mandocs}->{man5}})) -}
281MANDOCS7={-
282        join(" \\\n" . ' ' x 9,
283             fill_lines(" ", $COLUMNS - 9,
284                        @{$unified_info{mandocs}->{man7}})) -}
285
286APPS_OPENSSL="{- use File::Spec::Functions;
287                 catfile("apps","openssl") -}"
288
289# DESTDIR is for package builders so that they can configure for, say,
290# /usr/ and yet have everything installed to /tmp/somedir/usr/.
291# Normally it is left empty.
292DESTDIR=
293
294# Do not edit these manually. Use Configure with --prefix or --openssldir
295# to change this!  Short explanation in the top comment in Configure
296INSTALLTOP={- # $prefix is used in the OPENSSLDIR perl snippet
297	      #
298	      our $prefix = $config{prefix} || "/usr/local";
299              $prefix -}
300OPENSSLDIR={- #
301	      # The logic here is that if no --openssldir was given,
302	      # OPENSSLDIR will get the value from $prefix plus "/ssl".
303	      # If --openssldir was given and the value is an absolute
304	      # path, OPENSSLDIR will get its value without change.
305	      # If the value from --openssldir is a relative path,
306	      # OPENSSLDIR will get $prefix with the --openssldir
307	      # value appended as a subdirectory.
308	      #
309              use File::Spec::Functions;
310              our $openssldir =
311                  $config{openssldir} ?
312                      (file_name_is_absolute($config{openssldir}) ?
313                           $config{openssldir}
314                           : catdir($prefix, $config{openssldir}))
315                      : catdir($prefix, "ssl");
316              $openssldir -}
317LIBDIR={- our $libdir = $config{libdir};
318          unless ($libdir) {
319              $libdir = "lib$target{multilib}";
320          }
321          file_name_is_absolute($libdir) ? "" : $libdir -}
322# $(libdir) is chosen to be compatible with the GNU coding standards
323libdir={- file_name_is_absolute($libdir)
324          ? $libdir : '$(INSTALLTOP)/$(LIBDIR)' -}
325ENGINESDIR=$(libdir)/engines-{- $sover_dirname -}
326MODULESDIR=$(libdir)/ossl-modules
327
328# Convenience variable for those who want to set the rpath in shared
329# libraries and applications
330LIBRPATH=$(libdir)
331
332BINDIR={- our $bindir = $config{bindir};
333          unless ($bindir) {
334              $bindir = "bin$target{multibin}";
335          }
336          file_name_is_absolute($bindir) ? "" : $bindir -}
337bindir={- file_name_is_absolute($bindir)
338          ? $bindir : '$(INSTALLTOP)/$(BINDIR)' -}
339
340PKGCONFIGDIR=$(libdir)/pkgconfig
341CMAKECONFIGDIR=$(libdir)/cmake/OpenSSL
342
343MANDIR=$(INSTALLTOP)/share/man
344DOCDIR=$(INSTALLTOP)/share/doc/$(BASENAME)
345HTMLDIR=$(DOCDIR)/html
346
347# MANSUFFIX is for the benefit of anyone who may want to have a suffix
348# appended after the manpage file section number.  "ssl" is popular,
349# resulting in files such as config.5ssl rather than config.5.
350MANSUFFIX=ossl
351HTMLSUFFIX=html
352
353# For "optional" echo messages, to get "real" silence
354ECHO = echo
355
356##### User defined commands and flags ################################
357
358# We let the C compiler driver to take care of .s files. This is done in
359# order to be excused from maintaining a separate set of architecture
360# dependent assembler flags. E.g. if you throw -mcpu=ultrasparc at SPARC
361# gcc, then the driver will automatically translate it to -xarch=v8plus
362# and pass it down to assembler.  In any case, we do not define AS or
363# ASFLAGS for this reason.
364
365CROSS_COMPILE={- $config{CROSS_COMPILE} -}
366CC=$(CROSS_COMPILE){- $config{CC} -}
367CXX={- $config{CXX} ? "\$(CROSS_COMPILE)$config{CXX}" : '' -}
368CPPFLAGS={- our $cppflags1 = join(" ",
369                                  (map { "-D".$_} @{$config{CPPDEFINES}}),
370                                  (map { "-I".$_} @{$config{CPPINCLUDES}}),
371                                  @{$config{CPPFLAGS}}) -}
372CFLAGS={- join(' ', @{$config{CFLAGS}}) -}
373CXXFLAGS={- join(' ', @{$config{CXXFLAGS}}) -}
374LDFLAGS= {- join(' ', @{$config{LDFLAGS}}) -}
375EX_LIBS= {- join(' ', @{$config{LDLIBS}}) -}
376OBJCOPY={- $config{OBJCOPY} -}
377
378MAKEDEPEND={- $config{makedepcmd} -}
379
380PERL={- $config{PERL} -}
381
382AR=$(CROSS_COMPILE){- $config{AR} -}
383ARFLAGS= {- join(' ', @{$config{ARFLAGS}}) -}
384RANLIB={- $config{RANLIB} ? "\$(CROSS_COMPILE)$config{RANLIB}" : "true"; -}
385RC= $(CROSS_COMPILE){- $config{RC} -}
386RCFLAGS={- join(' ', @{$config{RCFLAGS}}) -} {- $target{shared_rcflag} -}
387
388RM= rm -f
389RMDIR= rmdir
390TAR= {- $target{TAR} || "tar" -}
391TARFLAGS= {- $target{TARFLAGS} -}
392
393BASENAME=       openssl
394NAME=           $(BASENAME)-$(VERSION)
395# Relative to $(SRCDIR)
396TARFILE=        ../$(NAME).tar
397
398##### Project flags ##################################################
399
400# Variables starting with CNF_ are common variables for all product types
401
402CNF_CPPFLAGS={- our $cppflags2 =
403                    join(' ', $target{cppflags} || (),
404                              (map { "-D".$_} @{$target{defines}},
405                                              @{$config{defines}}),
406                              (map { "-I".$_} @{$target{includes}},
407                                              @{$config{includes}}),
408                              @{$config{cppflags}}) -}
409CNF_CFLAGS={- join(' ', $target{cflags} || (),
410                        @{$config{cflags}}) -}
411CNF_CXXFLAGS={- join(' ', $target{cxxflags} || (),
412                          @{$config{cxxflags}}) -}
413CNF_LDFLAGS={- join(' ', $target{lflags} || (),
414                         @{$config{lflags}}) -}
415CNF_EX_LIBS={- join(' ', $target{ex_libs} || (),
416                         @{$config{ex_libs}}) -}
417
418# Variables starting with LIB_ are used to build library object files
419# and shared libraries.
420# Variables starting with DSO_ are used to build DSOs and their object files.
421# Variables starting with BIN_ are used to build programs and their object
422# files.
423
424LIB_CPPFLAGS={- our $lib_cppflags =
425                join(' ', $target{lib_cppflags} || (),
426                          $target{shared_cppflag} || (),
427                          (map { '-D'.$_ }
428                               @{$target{lib_defines} || ()},
429                               @{$target{shared_defines} || ()},
430                               @{$config{lib_defines} || ()},
431                               @{$config{shared_defines} || ()}),
432                          (map { '-I'.quotify1($_) }
433                               @{$target{lib_includes}},
434                               @{$target{shared_includes}},
435                               @{$config{lib_includes}},
436                               @{$config{shared_includes}}),
437                          @{$config{lib_cppflags}},
438                          @{$config{shared_cppflag}});
439                join(' ', $lib_cppflags,
440                          (map { '-D'.$_ }
441                               'OPENSSLDIR="\"$(OPENSSLDIR)\""',
442                               'ENGINESDIR="\"$(ENGINESDIR)\""',
443                               'MODULESDIR="\"$(MODULESDIR)\""'),
444                          '$(CNF_CPPFLAGS)', '$(CPPFLAGS)') -}
445LIB_CFLAGS={- join(' ', $target{lib_cflags} || (),
446                        $target{shared_cflag} || (),
447                        @{$config{lib_cflags}},
448                        @{$config{shared_cflag}},
449                        '$(CNF_CFLAGS)', '$(CFLAGS)') -}
450LIB_CXXFLAGS={- join(' ', $target{lib_cxxflags} || (),
451                          $target{shared_cxxflag} || (),
452                          @{$config{lib_cxxflags}},
453                          @{$config{shared_cxxflag}},
454                          '$(CNF_CXXFLAGS)', '$(CXXFLAGS)') -}
455LIB_LDFLAGS={- join(' ', $target{shared_ldflag} || (),
456                         $config{shared_ldflag} || (),
457                         '$(CNF_LDFLAGS)', '$(LDFLAGS)') -}
458LIB_EX_LIBS=$(CNF_EX_LIBS) $(EX_LIBS)
459DSO_CPPFLAGS={- join(' ', $target{dso_cppflags} || (),
460                          $target{module_cppflags} || (),
461                          (map { '-D'.$_ }
462                               @{$target{dso_defines}},
463                               @{$target{module_defines}},
464                               @{$config{dso_defines} || ()},
465                               @{$config{module_defines} || ()}),
466                          (map { '-I'.quotify1($_) }
467                               @{$target{dso_includes}},
468                               @{$target{module_includes}},
469                               @{$config{dso_includes}},
470                               @{$config{module_includes}}),
471                          @{$config{dso_cppflags}},
472                          @{$config{module_cppflags}},
473                          '$(CNF_CPPFLAGS)', '$(CPPFLAGS)') -}
474DSO_CFLAGS={- join(' ', $target{dso_cflags} || (),
475                        $target{module_cflags} || (),
476                        @{$config{dso_cflags}},
477                        @{$config{module_cflags}},
478                        '$(CNF_CFLAGS)', '$(CFLAGS)') -}
479DSO_CXXFLAGS={- join(' ', $target{dso_cxxflags} || (),
480                          $target{module_cxxflags} || (),
481                          @{$config{dso_cxxflags}},
482                          @{$config{module_cxxflag}},
483                          '$(CNF_CXXFLAGS)', '$(CXXFLAGS)') -}
484DSO_LDFLAGS={- join(' ', $target{dso_ldflags} || (),
485                         $target{module_ldflags} || (),
486                         @{$config{dso_ldflags}},
487                         @{$config{module_ldflags}},
488                         '$(CNF_LDFLAGS)', '$(LDFLAGS)') -}
489DSO_EX_LIBS=$(CNF_EX_LIBS) $(EX_LIBS)
490BIN_CPPFLAGS={- join(' ', $target{bin_cppflags} || (),
491                          (map { '-D'.$_ } @{$config{bin_defines} || ()}),
492                          @{$config{bin_cppflags}},
493                          '$(CNF_CPPFLAGS)', '$(CPPFLAGS)') -}
494BIN_CFLAGS={- join(' ', $target{bin_cflags} || (),
495                        @{$config{bin_cflags}},
496                        '$(CNF_CFLAGS)', '$(CFLAGS)') -}
497BIN_CXXFLAGS={- join(' ', $target{bin_cxxflags} || (),
498                          @{$config{bin_cxxflags}},
499                          '$(CNF_CXXFLAGS)', '$(CXXFLAGS)') -}
500BIN_LDFLAGS={- join(' ', $target{bin_lflags} || (),
501                         @{$config{bin_lflags}},
502                         '$(CNF_LDFLAGS)', '$(LDFLAGS)') -}
503BIN_EX_LIBS=$(CNF_EX_LIBS) $(EX_LIBS)
504
505# CPPFLAGS_Q is used for one thing only: to build up buildinf.h
506CPPFLAGS_Q={- $cppflags1 =~ s|([\\"])|\\$1|g;
507              $cppflags2 =~ s|([\\"])|\\$1|g;
508              $lib_cppflags =~ s|([\\"])|\\$1|g;
509              join(' ', $lib_cppflags || (), $cppflags2 || (),
510                        $cppflags1 || ()) -}
511
512PERLASM_SCHEME= {- $target{perlasm_scheme} -}
513
514# For x86 assembler: Set PROCESSOR to 386 if you want to support
515# the 80386.
516PROCESSOR= {- $config{processor} -}
517
518# We want error [and other] messages in English. Trouble is that make(1)
519# doesn't pass macros down as environment variables unless there already
520# was corresponding variable originally set. In other words we can only
521# reassign environment variables, but not set new ones, not in portable
522# manner that is. That's why we reassign several, just to be sure...
523LC_ALL=C
524LC_MESSAGES=C
525LANG=C
526
527# The main targets ###################################################
528
529##@ Software
530
531{- dependmagic('build_sw', 'Build all the software (default target)'); -}: build_libs_nodep build_modules_nodep build_programs_nodep link-utils
532{- dependmagic('build_libs', 'Build the libraries libssl and libcrypto'); -}: build_libs_nodep
533{- dependmagic('build_modules', 'Build the modules (i.e. providers and engines)'); -}: build_modules_nodep
534{- dependmagic('build_programs', 'Build the openssl executables and scripts'); -}: build_programs_nodep
535
536all: build_sw {- "build_docs" if !$disabled{docs}; -} ## Build software and documentation
537debuginfo: $(SHLIBS)
538	@set -e; for i in $(SHLIBS); do \
539		$(OBJCOPY) --only-keep-debug $$i $$i.debug; \
540		$(OBJCOPY) --strip-debug --add-gnu-debuglink=$$i.debug $$i; \
541	done;
542
543cov-report: $(SHLIBS)
544	@set -e; gcovr -r . --txt-metric=branch --html --html-details -o openssl-metrics.html
545
546##@ Documentation
547build_generated_pods: $(GENERATED_PODS)
548build_docs: build_man_docs build_html_docs ## Create documentation
549build_man_docs: $(MANDOCS1) $(MANDOCS3) $(MANDOCS5) $(MANDOCS7) ## Create manpages
550build_html_docs: $(HTMLDOCS1) $(HTMLDOCS3) $(HTMLDOCS5) $(HTMLDOCS7) ## Create HTML documentation
551
552build_generated: $(GENERATED_MANDATORY)
553build_libs_nodep: $(LIBS) {- join(" ",map { platform->sharedlib_simple($_) // platform->sharedlib_import($_) // platform->sharedlib($_) // () } @{$unified_info{libraries}}) -}
554build_modules_nodep: $(MODULES)
555build_programs_nodep: $(PROGRAMS) $(SCRIPTS)
556
557# Kept around for backward compatibility
558build_apps build_tests: build_programs
559
560# Convenience target to prebuild all generated files, not just the mandatory
561# ones
562build_all_generated: $(GENERATED_MANDATORY) $(GENERATED) build_docs
563	@ : {- output_off() if $disabled{makedepend}; "" -}
564	@echo "Warning: consider configuring with no-makedepend, because if"
565	@echo "         target system doesn't have $(PERL),"
566	@echo "         then make will fail..."
567	@ : {- output_on() if $disabled{makedepend}; "" -}
568
569##@ Help
570.PHONY: help
571help: ## Show this help screen
572	@$(PERL) $(SRCDIR)/util/help.pl $(BLDDIR)/Makefile
573
574##@ Testing
575test: tests ## Run tests (alias of "tests")
576{- dependmagic('tests', 'Run tests'); -}: build_programs_nodep build_modules_nodep link-utils
577	"$(MAKE)" run_tests
578run_tests: FORCE
579	@ : {- output_off() if $disabled{tests}; "" -}
580	( SRCTOP=$(SRCDIR) \
581	  BLDTOP=$(BLDDIR) \
582	  PERL="$(PERL)" \
583	  FIPSKEY="$(FIPSKEY)" \
584	  EXE_EXT={- platform->binext() -} \
585	  $(PERL) $(SRCDIR)/test/run_tests.pl $(TESTS) )
586	@ : {- if ($disabled{tests}) { output_on(); } else { output_off(); } "" -}
587	@echo "Tests are not supported with your chosen Configure options"
588	@ : {- output_on() if !$disabled{tests}; "" -}
589
590list-tests: ## List available tests that can be invoked via "make test TESTS=<name>"
591	@ : {- output_off() if $disabled{tests}; "" -}
592	"$(MAKE)" run_tests TESTS=list
593	@ : {- if ($disabled{tests}) { output_on(); } else { output_off(); } "" -}
594	@echo "Tests are not supported with your chosen Configure options"
595	@ : {- output_on() if !$disabled{tests}; "" -}
596
597##@ Workspace cleaning
598
599libclean:
600	@set -e; for s in $(SHLIB_INFO); do \
601		if [ "$$s" = ";" ]; then continue; fi; \
602		s1=`echo "$$s" | cut -f1 -d";"`; \
603		s2=`echo "$$s" | cut -f2 -d";"`; \
604		s3=`echo "$$s" | cut -f3 -d";"`; \
605		$(ECHO) $(RM) $$s1; {- output_off() unless windowsdll(); "" -}\
606		$(RM) apps/$$s1; \
607		$(RM) test/$$s1; \
608		$(RM) fuzz/$$s1; {- output_on() unless windowsdll(); "" -}\
609		$(RM) $$s1; \
610		if [ "$$s2" != "" ]; then \
611			$(ECHO) $(RM) $$s2; \
612			$(RM) $$s2; \
613		fi; \
614		if [ "$$s3" != "" ]; then \
615			$(ECHO) $(RM) $$s3; \
616			$(RM) $$s3; \
617		fi; \
618	done
619	$(RM) $(LIBS)
620	$(RM) *{- platform->defext() -}
621
622clean: libclean ## Clean the workspace, keep the configuration
623	$(RM) $(HTMLDOCS1)
624	$(RM) $(HTMLDOCS3)
625	$(RM) $(HTMLDOCS5)
626	$(RM) $(HTMLDOCS7)
627	$(RM) $(MANDOCS1)
628	$(RM) $(MANDOCS3)
629	$(RM) $(MANDOCS5)
630	$(RM) $(MANDOCS7)
631	$(RM) $(PROGRAMS) $(TESTPROGS) $(MODULES) $(FIPSMODULE) $(SCRIPTS)
632	$(RM) $(GENERATED_MANDATORY) $(GENERATED)
633	-find . -name '*{- platform->depext() -}' \! -name '.*' \! -type d -exec $(RM) {} \;
634	-find . -name '*{- platform->objext() -}' \! -name '.*' \! -type d -exec $(RM) {} \;
635	$(RM) core
636	$(RM) tags TAGS doc-nits md-nits
637	$(RM) -r test/test-runs
638	$(RM) providers/fips*.new
639	-find . -type l \! -name '.*' \! -wholename './pkcs11-provider/*' -exec $(RM) {} \;
640
641distclean: clean ## Clean and remove the configuration
642	$(RM) include/openssl/configuration.h
643	$(RM) configdata.pm
644	$(RM) Makefile
645
646# We check if any depfile is newer than Makefile and decide to
647# concatenate only if that is true.
648depend: Makefile
649	@: {- output_off() if $disabled{makedepend}; "" -}
650	@$(PERL) $(SRCDIR)/util/add-depends.pl "{- $makedep_scheme -}"
651	@: {- output_on() if $disabled{makedepend}; "" -}
652
653# Install helper targets #############################################
654##@ Installation
655
656install: Makefile ## Install software and documentation, create OpenSSL directories
657	$(MAKE) install_sw
658	$(MAKE) install_ssldirs
659	{- "\$(MAKE) install_docs" if !$disabled{docs} -}
660	{- "\$(MAKE) install_fips" if !$disabled{fips} -}
661
662uninstall: {- "uninstall_docs" if !$disabled{docs}; -} uninstall_sw {- $disabled{fips} ? "" : "uninstall_fips" -} ## Uninstall software and documentation
663
664install_sw: install_dev install_engines install_modules install_runtime ## Install just the software and libraries
665
666uninstall_sw: uninstall_runtime uninstall_modules uninstall_engines uninstall_dev ## Uninstall the software and libraries
667
668install_docs: install_man_docs install_html_docs ## Install manpages and HTML documentation
669
670uninstall_docs: uninstall_man_docs uninstall_html_docs ## Uninstall manpages and HTML documentation
671	$(RM) -r "$(DESTDIR)$(DOCDIR)"
672
673{- output_off() if $disabled{fips}; "" -}
674install_fips: build_sw $(INSTALL_FIPSMODULECONF)
675	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
676	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(MODULESDIR)"
677	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(OPENSSLDIR)"
678	@$(ECHO) "*** Installing FIPS module"
679	@$(ECHO) "install $(INSTALL_FIPSMODULE) -> $(DESTDIR)$(MODULESDIR)/$(FIPSMODULENAME)"
680	@cp "$(INSTALL_FIPSMODULE)" "$(DESTDIR)$(MODULESDIR)/$(FIPSMODULENAME).new"
681	@chmod 755 "$(DESTDIR)$(MODULESDIR)/$(FIPSMODULENAME).new"
682	@mv -f "$(DESTDIR)$(MODULESDIR)/$(FIPSMODULENAME).new" \
683	       "$(DESTDIR)$(MODULESDIR)/$(FIPSMODULENAME)"
684	@$(ECHO) "*** Installing FIPS module configuration"
685	@$(ECHO) "install $(INSTALL_FIPSMODULECONF) -> $(DESTDIR)$(OPENSSLDIR)/fipsmodule.cnf"
686	@cp $(INSTALL_FIPSMODULECONF) "$(DESTDIR)$(OPENSSLDIR)/fipsmodule.cnf"
687
688uninstall_fips:
689	@$(ECHO) "*** Uninstalling FIPS module configuration"
690	$(RM) "$(DESTDIR)$(OPENSSLDIR)/fipsmodule.cnf"
691	@$(ECHO) "*** Uninstalling FIPS module"
692	$(RM) "$(DESTDIR)$(MODULESDIR)/$(FIPSMODULENAME)"
693{- if ($disabled{fips}) { output_on(); } else { output_off(); } "" -}
694install_fips:
695	@$(ECHO) "The 'install_fips' target requires the 'enable-fips' option"
696
697uninstall_fips:
698	@$(ECHO) "The 'uninstall_fips' target requires the 'enable-fips' option"
699{- output_on() if !$disabled{fips}; "" -}
700
701
702install_ssldirs:
703	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(OPENSSLDIR)/certs"
704	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(OPENSSLDIR)/private"
705	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(OPENSSLDIR)/misc"
706	@set -e; for x in dummy $(MISC_SCRIPTS); do \
707		if [ "$$x" = "dummy" ]; then continue; fi; \
708		x1=`echo "$$x" | cut -f1 -d:`; \
709		x2=`echo "$$x" | cut -f2 -d:`; \
710		fn=`basename $$x1`; \
711		$(ECHO) "install $$x1 -> $(DESTDIR)$(OPENSSLDIR)/misc/$$fn"; \
712		cp $$x1 "$(DESTDIR)$(OPENSSLDIR)/misc/$$fn.new"; \
713		chmod 755 "$(DESTDIR)$(OPENSSLDIR)/misc/$$fn.new"; \
714		mv -f "$(DESTDIR)$(OPENSSLDIR)/misc/$$fn.new" \
715		      "$(DESTDIR)$(OPENSSLDIR)/misc/$$fn"; \
716		if [ "$$x1" != "$$x2" ]; then \
717			ln=`basename "$$x2"`; \
718			: {- output_off() unless windowsdll(); "" -}; \
719			$(ECHO) "copy $(DESTDIR)$(OPENSSLDIR)/misc/$$ln -> $(DESTDIR)$(OPENSSLDIR)/misc/$$fn"; \
720			cp "$(DESTDIR)$(OPENSSLDIR)/misc/$$fn" "$(DESTDIR)$(OPENSSLDIR)/misc/$$ln"; \
721			: {- output_on() unless windowsdll();
722			     output_off() if windowsdll(); "" -}; \
723			$(ECHO) "link $(DESTDIR)$(OPENSSLDIR)/misc/$$ln -> $(DESTDIR)$(OPENSSLDIR)/misc/$$fn"; \
724			ln -sf $$fn "$(DESTDIR)$(OPENSSLDIR)/misc/$$ln"; \
725			: {- output_on() if windowsdll(); "" -}; \
726		fi; \
727	done
728	@$(ECHO) "install $(SRCDIR)/apps/openssl.cnf -> $(DESTDIR)$(OPENSSLDIR)/openssl.cnf.dist"
729	@cp $(SRCDIR)/apps/openssl.cnf "$(DESTDIR)$(OPENSSLDIR)/openssl.cnf.new"
730	@chmod 644 "$(DESTDIR)$(OPENSSLDIR)/openssl.cnf.new"
731	@mv -f  "$(DESTDIR)$(OPENSSLDIR)/openssl.cnf.new" "$(DESTDIR)$(OPENSSLDIR)/openssl.cnf.dist"
732	@if [ ! -f "$(DESTDIR)$(OPENSSLDIR)/openssl.cnf" ]; then \
733		$(ECHO) "install $(SRCDIR)/apps/openssl.cnf -> $(DESTDIR)$(OPENSSLDIR)/openssl.cnf"; \
734		cp $(SRCDIR)/apps/openssl.cnf "$(DESTDIR)$(OPENSSLDIR)/openssl.cnf"; \
735		chmod 644 "$(DESTDIR)$(OPENSSLDIR)/openssl.cnf"; \
736	fi
737	@$(ECHO) "install $(SRCDIR)/apps/ct_log_list.cnf -> $(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf.dist"
738	@cp $(SRCDIR)/apps/ct_log_list.cnf "$(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf.new"
739	@chmod 644 "$(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf.new"
740	@mv -f  "$(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf.new" "$(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf.dist"
741	@if [ ! -f "$(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf" ]; then \
742		$(ECHO) "install $(SRCDIR)/apps/ct_log_list.cnf -> $(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf"; \
743		cp $(SRCDIR)/apps/ct_log_list.cnf "$(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf"; \
744		chmod 644 "$(DESTDIR)$(OPENSSLDIR)/ct_log_list.cnf"; \
745	fi
746
747install_dev: install_runtime_libs
748	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
749	@$(ECHO) "*** Installing development files"
750	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(INSTALLTOP)/include/openssl"
751	@ : {- output_off() if $disabled{uplink}; "" -}
752	@$(ECHO) "install $(SRCDIR)/ms/applink.c -> $(DESTDIR)$(INSTALLTOP)/include/openssl/applink.c"
753	@cp $(SRCDIR)/ms/applink.c "$(DESTDIR)$(INSTALLTOP)/include/openssl/applink.c"
754	@chmod 644 "$(DESTDIR)$(INSTALLTOP)/include/openssl/applink.c"
755	@ : {- output_on() if $disabled{uplink}; "" -}
756	@set -e; for i in $(SRCDIR)/include/openssl/*.h \
757			  $(BLDDIR)/include/openssl/*.h; do \
758		fn=`basename $$i`; \
759		$(ECHO) "install $$i -> $(DESTDIR)$(INSTALLTOP)/include/openssl/$$fn"; \
760		cp $$i "$(DESTDIR)$(INSTALLTOP)/include/openssl/$$fn"; \
761		chmod 644 "$(DESTDIR)$(INSTALLTOP)/include/openssl/$$fn"; \
762	done
763	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(libdir)"
764	@set -e; for l in $(INSTALL_LIBS); do \
765		fn=`basename $$l`; \
766		$(ECHO) "install $$l -> $(DESTDIR)$(libdir)/$$fn"; \
767		cp $$l "$(DESTDIR)$(libdir)/$$fn.new"; \
768		$(RANLIB) "$(DESTDIR)$(libdir)/$$fn.new"; \
769		chmod 644 "$(DESTDIR)$(libdir)/$$fn.new"; \
770		mv -f "$(DESTDIR)$(libdir)/$$fn.new" \
771		      "$(DESTDIR)$(libdir)/$$fn"; \
772	done
773	@ : {- output_off() if $disabled{shared}; "" -}
774	@set -e; for s in $(INSTALL_SHLIB_INFO); do \
775		s1=`echo "$$s" | cut -f1 -d";"`; \
776		s2=`echo "$$s" | cut -f2 -d";"`; \
777		s3=`echo "$$s" | cut -f3 -d";"`; \
778		fn1=`basename "$$s1"`; \
779		fn2=`basename "$$s2"`; \
780		fn3=`basename "$$s3"`; \
781		: {- output_off(); output_on() unless windowsdll() or sharedaix() or sharedaix_solib(); "" -}; \
782		if [ "$$fn2" != "" ]; then \
783			$(ECHO) "link $(DESTDIR)$(libdir)/$$fn2 -> $(DESTDIR)$(libdir)/$$fn1"; \
784			ln -sf $$fn1 "$(DESTDIR)$(libdir)/$$fn2"; \
785		fi; \
786		: {- output_off() unless windowsdll() or sharedaix() or sharedaix_solib(); output_on() if windowsdll() or sharedaix_solib(); "" -}; \
787		if [ "$$fn3" != "" ]; then \
788			$(ECHO) "install $$s3 -> $(DESTDIR)$(libdir)/$$fn3"; \
789			cp $$s3 "$(DESTDIR)$(libdir)/$$fn3.new"; \
790			chmod 755 "$(DESTDIR)$(libdir)/$$fn3.new"; \
791			mv -f "$(DESTDIR)$(libdir)/$$fn3.new" \
792			      "$(DESTDIR)$(libdir)/$$fn3"; \
793		fi; \
794		: {- output_off() if windowsdll() or sharedaix_solib(); output_on() if sharedaix(); "" -}; \
795		a="$(DESTDIR)$(libdir)/$$fn2"; \
796		$(ECHO) "install $$s1 -> $$a"; \
797		if [ -f $$a ]; then ( trap "rm -rf /tmp/ar.$$$$" INT 0; \
798			mkdir /tmp/ar.$$$$; ( cd /tmp/ar.$$$$; \
799			cp -f $$a $$a.new; \
800			for so in `$(AR) t $$a`; do \
801				$(AR) x $$a $$so; \
802				chmod u+w $$so; \
803				strip -X32_64 -e $$so; \
804				$(AR) r $$a.new $$so; \
805			done; \
806		)); fi; \
807		$(AR) r $$a.new $$s1; \
808		mv -f $$a.new $$a; \
809		: {- output_off() if sharedaix(); output_on(); "" -}; \
810	done
811	@ : {- output_on() if $disabled{shared}; "" -}
812	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(PKGCONFIGDIR)"
813	@for e in $(INSTALL_EXPORTERS_PKGCONFIG); do \
814		fn=`basename $$e`; \
815		$(ECHO) "install $$e -> $(DESTDIR)$(PKGCONFIGDIR)/$$fn"; \
816		cp $$e "$(DESTDIR)$(PKGCONFIGDIR)/$$fn"; \
817		chmod 644 "$(DESTDIR)$(PKGCONFIGDIR)/$$fn"; \
818	done
819	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(CMAKECONFIGDIR)"
820	@for e in $(INSTALL_EXPORTERS_CMAKE); do \
821		fn=`basename $$e`; \
822		$(ECHO) "install $$e -> $(DESTDIR)$(CMAKECONFIGDIR)/$$fn"; \
823		cp $$e "$(DESTDIR)$(CMAKECONFIGDIR)/$$fn"; \
824		chmod 644 "$(DESTDIR)$(CMAKECONFIGDIR)/$$fn"; \
825	done
826
827uninstall_dev: uninstall_runtime_libs
828	@$(ECHO) "*** Uninstalling development files"
829	@ : {- output_off() if $disabled{uplink}; "" -}
830	@$(ECHO) "$(RM) $(DESTDIR)$(INSTALLTOP)/include/openssl/applink.c"
831	@$(RM) "$(DESTDIR)$(INSTALLTOP)/include/openssl/applink.c"
832	@ : {- output_on() if $disabled{uplink}; "" -}
833	@set -e; for i in $(SRCDIR)/include/openssl/*.h \
834			  $(BLDDIR)/include/openssl/*.h; do \
835		fn=`basename $$i`; \
836		$(ECHO) "$(RM) $(DESTDIR)$(INSTALLTOP)/include/openssl/$$fn"; \
837		$(RM) "$(DESTDIR)$(INSTALLTOP)/include/openssl/$$fn"; \
838	done
839	-$(RMDIR) "$(DESTDIR)$(INSTALLTOP)/include/openssl"
840	-$(RMDIR) "$(DESTDIR)$(INSTALLTOP)/include"
841	@set -e; for l in $(INSTALL_LIBS); do \
842		fn=`basename $$l`; \
843		$(ECHO) "$(RM) $(DESTDIR)$(libdir)/$$fn"; \
844		$(RM) "$(DESTDIR)$(libdir)/$$fn"; \
845	done
846	@ : {- output_off() if $disabled{shared}; "" -}
847	@set -e; for s in $(INSTALL_SHLIB_INFO); do \
848		s1=`echo "$$s" | cut -f1 -d";"`; \
849		s2=`echo "$$s" | cut -f2 -d";"`; \
850		s3=`echo "$$s" | cut -f3 -d";"`; \
851		fn1=`basename "$$s1"`; \
852		fn2=`basename "$$s2"`; \
853		fn3=`basename "$$s3"`; \
854		: {- output_off() if windowsdll(); "" -}; \
855		$(ECHO) "$(RM) $(DESTDIR)$(libdir)/$$fn1"; \
856		$(RM) "$(DESTDIR)$(libdir)/$$fn1"; \
857		if [ -n "$$fn2" ]; then \
858			$(ECHO) "$(RM) $(DESTDIR)$(libdir)/$$fn2"; \
859			$(RM) "$(DESTDIR)$(libdir)/$$fn2"; \
860		fi; \
861		: {- output_on() if windowsdll(); "" -}{- output_off() unless windowsdll(); "" -}; \
862		if [ -n "$$fn3" ]; then \
863			$(ECHO) "$(RM) $(DESTDIR)$(libdir)/$$fn3"; \
864			$(RM) "$(DESTDIR)$(libdir)/$$fn3"; \
865		fi; \
866		: {- output_on() unless windowsdll(); "" -}; \
867	done
868	@ : {- output_on() if $disabled{shared}; "" -}
869	@for e in $(INSTALL_EXPORTERS_PKGCONFIG); do \
870		fn=`basename "$$e"`; \
871		$(RM) "$(DESTDIR)$(PKGCONFIGDIR)/$$fn"; \
872	done
873	@for e in $(INSTALL_EXPORTERS_CMAKE); do \
874		fn=`basename "$$e"`; \
875		$(RM) "$(DESTDIR)$(CMAKECONFIGDIR)/$$fn"; \
876	done
877	-$(RMDIR) "$(DESTDIR)$(PKGCONFIGDIR)"
878	-$(RMDIR) "$(DESTDIR)$(CMAKECONFIGDIR)"
879	-$(RMDIR) "$(DESTDIR)$(libdir)"
880
881_install_modules_deps: install_runtime_libs build_modules
882
883install_engines: _install_modules_deps
884	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
885	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(ENGINESDIR)/"
886	@$(ECHO) "*** Installing engines"
887	@set -e; for e in dummy $(INSTALL_ENGINES); do \
888		if [ "$$e" = "dummy" ]; then continue; fi; \
889		fn=`basename $$e`; \
890		$(ECHO) "install $$e -> $(DESTDIR)$(ENGINESDIR)/$$fn"; \
891		cp $$e "$(DESTDIR)$(ENGINESDIR)/$$fn.new"; \
892		chmod 755 "$(DESTDIR)$(ENGINESDIR)/$$fn.new"; \
893		mv -f "$(DESTDIR)$(ENGINESDIR)/$$fn.new" \
894		      "$(DESTDIR)$(ENGINESDIR)/$$fn"; \
895	done
896
897uninstall_engines:
898	@$(ECHO) "*** Uninstalling engines"
899	@set -e; for e in dummy $(INSTALL_ENGINES); do \
900		if [ "$$e" = "dummy" ]; then continue; fi; \
901		fn=`basename $$e`; \
902		$(ECHO) "$(RM) $(DESTDIR)$(ENGINESDIR)/$$fn"; \
903		$(RM) "$(DESTDIR)$(ENGINESDIR)/$$fn"; \
904	done
905	-$(RMDIR) "$(DESTDIR)$(ENGINESDIR)"
906
907install_modules: _install_modules_deps
908	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
909	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(MODULESDIR)/"
910	@$(ECHO) "*** Installing modules"
911	@set -e; for e in dummy $(INSTALL_MODULES); do \
912		if [ "$$e" = "dummy" ]; then continue; fi; \
913		fn=`basename $$e`; \
914		$(ECHO) "install $$e -> $(DESTDIR)$(MODULESDIR)/$$fn"; \
915		cp $$e "$(DESTDIR)$(MODULESDIR)/$$fn.new"; \
916		chmod 755 "$(DESTDIR)$(MODULESDIR)/$$fn.new"; \
917		mv -f "$(DESTDIR)$(MODULESDIR)/$$fn.new" \
918		      "$(DESTDIR)$(MODULESDIR)/$$fn"; \
919	done
920
921uninstall_modules:
922	@$(ECHO) "*** Uninstalling modules"
923	@set -e; for e in dummy $(INSTALL_MODULES); do \
924		if [ "$$e" = "dummy" ]; then continue; fi; \
925		fn=`basename $$e`; \
926		$(ECHO) "$(RM) $(DESTDIR)$(MODULESDIR)/$$fn"; \
927		$(RM) "$(DESTDIR)$(MODULESDIR)/$$fn"; \
928	done
929	-$(RMDIR) "$(DESTDIR)$(MODULESDIR)"
930
931install_runtime: install_programs
932
933install_runtime_libs: build_libs
934	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
935	@ : {- output_off() if windowsdll(); "" -}
936	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(libdir)"
937	@ : {- output_on() if windowsdll(); output_off() unless windowsdll(); "" -}
938	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(bindir)/"
939	@ : {- output_on() unless windowsdll(); "" -}
940	@$(ECHO) "*** Installing runtime libraries"
941	@set -e; for s in dummy $(INSTALL_SHLIBS); do \
942		if [ "$$s" = "dummy" ]; then continue; fi; \
943		fn=`basename $$s`; \
944		: {- output_off() unless windowsdll(); "" -}; \
945		$(ECHO) "install $$s -> $(DESTDIR)$(bindir)/$$fn"; \
946		cp $$s "$(DESTDIR)$(bindir)/$$fn.new"; \
947		chmod 755 "$(DESTDIR)$(bindir)/$$fn.new"; \
948		mv -f "$(DESTDIR)$(bindir)/$$fn.new" \
949		      "$(DESTDIR)$(bindir)/$$fn"; \
950		: {- output_on() unless windowsdll(); "" -}{- output_off() if windowsdll(); "" -}; \
951		$(ECHO) "install $$s -> $(DESTDIR)$(libdir)/$$fn"; \
952		cp $$s "$(DESTDIR)$(libdir)/$$fn.new"; \
953		chmod 755 "$(DESTDIR)$(libdir)/$$fn.new"; \
954		mv -f "$(DESTDIR)$(libdir)/$$fn.new" \
955		      "$(DESTDIR)$(libdir)/$$fn"; \
956		: {- output_on() if windowsdll(); "" -}; \
957	done
958
959install_programs: install_runtime_libs build_programs
960	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
961	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(bindir)"
962	@$(ECHO) "*** Installing runtime programs"
963	@set -e; for x in dummy $(INSTALL_PROGRAMS); do \
964		if [ "$$x" = "dummy" ]; then continue; fi; \
965		fn=`basename $$x`; \
966		$(ECHO) "install $$x -> $(DESTDIR)$(bindir)/$$fn"; \
967		cp $$x "$(DESTDIR)$(bindir)/$$fn.new"; \
968		chmod 755 "$(DESTDIR)$(bindir)/$$fn.new"; \
969		mv -f "$(DESTDIR)$(bindir)/$$fn.new" \
970		      "$(DESTDIR)$(bindir)/$$fn"; \
971	done
972	@set -e; for x in dummy $(BIN_SCRIPTS); do \
973		if [ "$$x" = "dummy" ]; then continue; fi; \
974		fn=`basename $$x`; \
975		$(ECHO) "install $$x -> $(DESTDIR)$(bindir)/$$fn"; \
976		cp $$x "$(DESTDIR)$(bindir)/$$fn.new"; \
977		chmod 755 "$(DESTDIR)$(bindir)/$$fn.new"; \
978		mv -f "$(DESTDIR)$(bindir)/$$fn.new" \
979		      "$(DESTDIR)$(bindir)/$$fn"; \
980	done
981
982uninstall_runtime: uninstall_programs uninstall_runtime_libs
983
984uninstall_programs:
985	@$(ECHO) "*** Uninstalling runtime programs"
986	@set -e; for x in dummy $(INSTALL_PROGRAMS); \
987	do  \
988		if [ "$$x" = "dummy" ]; then continue; fi; \
989		fn=`basename $$x`; \
990		$(ECHO) "$(RM) $(DESTDIR)$(bindir)/$$fn"; \
991		$(RM) "$(DESTDIR)$(bindir)/$$fn"; \
992	done;
993	@set -e; for x in dummy $(BIN_SCRIPTS); \
994	do  \
995		if [ "$$x" = "dummy" ]; then continue; fi; \
996		fn=`basename $$x`; \
997		$(ECHO) "$(RM) $(DESTDIR)$(bindir)/$$fn"; \
998		$(RM) "$(DESTDIR)$(bindir)/$$fn"; \
999	done
1000	-$(RMDIR) "$(DESTDIR)$(bindir)"
1001
1002uninstall_runtime_libs:
1003	@$(ECHO) "*** Uninstalling runtime libraries"
1004	@ : {- output_off() unless windowsdll(); "" -}
1005	@set -e; for s in dummy $(INSTALL_SHLIBS); do \
1006		if [ "$$s" = "dummy" ]; then continue; fi; \
1007		fn=`basename $$s`; \
1008		$(ECHO) "$(RM) $(DESTDIR)$(bindir)/$$fn"; \
1009		$(RM) "$(DESTDIR)$(bindir)/$$fn"; \
1010	done
1011	@ : {- output_on() unless windowsdll(); "" -}
1012
1013
1014install_man_docs: build_man_docs
1015	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
1016	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(MANDIR)/man1"
1017	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(MANDIR)/man3"
1018	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(MANDIR)/man5"
1019	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(MANDIR)/man7"
1020	@$(ECHO) "*** Installing manpages"
1021	@set -e; for x in dummy $(MANDOCS1); do \
1022		if [ "$$x" = "dummy" ]; then continue; fi; \
1023		fn=`basename $$x`; \
1024		$(ECHO) "install $$x -> $(DESTDIR)$(MANDIR)/man1/$${fn}$(MANSUFFIX)"; \
1025		cp $$x "$(DESTDIR)$(MANDIR)/man1/$${fn}$(MANSUFFIX)"; \
1026		chmod 644 "$(DESTDIR)$(MANDIR)/man1/$${fn}$(MANSUFFIX)"; \
1027		$(PERL) $(SRCDIR)/util/write-man-symlinks install $(SRCDIR)/doc/man1 $(BLDDIR)/doc/man1 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man1"; \
1028	done
1029	@set -e; for x in dummy $(MANDOCS3); do \
1030		if [ "$$x" = "dummy" ]; then continue; fi; \
1031		fn=`basename $$x`; \
1032		$(ECHO) "install $$x -> $(DESTDIR)$(MANDIR)/man3/$${fn}$(MANSUFFIX)"; \
1033		cp $$x "$(DESTDIR)$(MANDIR)/man3/$${fn}$(MANSUFFIX)"; \
1034		chmod 644 "$(DESTDIR)$(MANDIR)/man3/$${fn}$(MANSUFFIX)"; \
1035		$(PERL) $(SRCDIR)/util/write-man-symlinks install $(SRCDIR)/doc/man3 $(BLDDIR)/doc/man3 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man3"; \
1036	done
1037	@set -e; for x in dummy $(MANDOCS5); do \
1038		if [ "$$x" = "dummy" ]; then continue; fi; \
1039		fn=`basename $$x`; \
1040		$(ECHO) "install $$x -> $(DESTDIR)$(MANDIR)/man5/$${fn}$(MANSUFFIX)"; \
1041		cp $$x "$(DESTDIR)$(MANDIR)/man5/$${fn}$(MANSUFFIX)"; \
1042		chmod 644 "$(DESTDIR)$(MANDIR)/man5/$${fn}$(MANSUFFIX)"; \
1043		$(PERL) $(SRCDIR)/util/write-man-symlinks install $(SRCDIR)/doc/man5 $(BLDDIR)/doc/man5 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man5"; \
1044	done
1045	@set -e; for x in dummy $(MANDOCS7); do \
1046		if [ "$$x" = "dummy" ]; then continue; fi; \
1047		fn=`basename $$x`; \
1048		$(ECHO) "install $$x -> $(DESTDIR)$(MANDIR)/man7/$${fn}$(MANSUFFIX)"; \
1049		cp $$x "$(DESTDIR)$(MANDIR)/man7/$${fn}$(MANSUFFIX)"; \
1050		chmod 644 "$(DESTDIR)$(MANDIR)/man7/$${fn}$(MANSUFFIX)"; \
1051		$(PERL) $(SRCDIR)/util/write-man-symlinks install $(SRCDIR)/doc/man7 $(BLDDIR)/doc/man7 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man7"; \
1052	done
1053
1054uninstall_man_docs: build_man_docs
1055	@$(ECHO) "*** Uninstalling manpages"
1056	@set -e; for x in dummy $(MANDOCS1); do \
1057		if [ "$$x" = "dummy" ]; then continue; fi; \
1058		fn=`basename $$x`; \
1059		$(ECHO) "$(RM) $(DESTDIR)$(MANDIR)/man1/$${fn}$(MANSUFFIX)"; \
1060		$(RM) "$(DESTDIR)$(MANDIR)/man1/$${fn}$(MANSUFFIX)"; \
1061		$(PERL) $(SRCDIR)/util/write-man-symlinks uninstall $(SRCDIR)/doc/man1 $(BLDDIR)/doc/man1 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man1"; \
1062	done
1063	@set -e; for x in dummy $(MANDOCS3); do \
1064		if [ "$$x" = "dummy" ]; then continue; fi; \
1065		fn=`basename $$x`; \
1066		$(ECHO) "$(RM) $(DESTDIR)$(MANDIR)/man3/$${fn}$(MANSUFFIX)"; \
1067		$(RM) "$(DESTDIR)$(MANDIR)/man3/$${fn}$(MANSUFFIX)"; \
1068		$(PERL) $(SRCDIR)/util/write-man-symlinks uninstall $(SRCDIR)/doc/man3 $(BLDDIR)/doc/man3 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man3"; \
1069	done
1070	@set -e; for x in dummy $(MANDOCS5); do \
1071		if [ "$$x" = "dummy" ]; then continue; fi; \
1072		fn=`basename $$x`; \
1073		$(ECHO) "$(RM) $(DESTDIR)$(MANDIR)/man5/$${fn}$(MANSUFFIX)"; \
1074		$(RM) "$(DESTDIR)$(MANDIR)/man5/$${fn}$(MANSUFFIX)"; \
1075		$(PERL) $(SRCDIR)/util/write-man-symlinks uninstall $(SRCDIR)/doc/man5 $(BLDDIR)/doc/man5 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man5"; \
1076	done
1077	@set -e; for x in dummy $(MANDOCS7); do \
1078		if [ "$$x" = "dummy" ]; then continue; fi; \
1079		fn=`basename $$x`; \
1080		$(ECHO) "$(RM) $(DESTDIR)$(MANDIR)/man7/$${fn}$(MANSUFFIX)"; \
1081		$(RM) "$(DESTDIR)$(MANDIR)/man7/$${fn}$(MANSUFFIX)"; \
1082		$(PERL) $(SRCDIR)/util/write-man-symlinks uninstall $(SRCDIR)/doc/man7 $(BLDDIR)/doc/man7 $${fn}$(MANSUFFIX) "$(DESTDIR)$(MANDIR)/man7"; \
1083	done
1084
1085install_html_docs: install_image_docs build_html_docs
1086	@[ -n "$(INSTALLTOP)" ] || (echo INSTALLTOP should not be empty; exit 1)
1087	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(HTMLDIR)/man1"
1088	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(HTMLDIR)/man3"
1089	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(HTMLDIR)/man5"
1090	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(HTMLDIR)/man7"
1091	@$(ECHO) "*** Installing HTML manpages"
1092	@set -e; for x in dummy $(HTMLDOCS1); do \
1093		if [ "$$x" = "dummy" ]; then continue; fi; \
1094		fn=`basename $$x`; \
1095		$(ECHO) "install $$x -> $(DESTDIR)$(HTMLDIR)/man1/$$fn"; \
1096		cp $$x "$(DESTDIR)$(HTMLDIR)/man1/$$fn"; \
1097		chmod 644 "$(DESTDIR)$(HTMLDIR)/man1/$$fn"; \
1098	done
1099	@set -e; for x in dummy $(HTMLDOCS3); do \
1100		if [ "$$x" = "dummy" ]; then continue; fi; \
1101		fn=`basename $$x`; \
1102		$(ECHO) "install $$x -> $(DESTDIR)$(HTMLDIR)/man3/$$fn"; \
1103		cp $$x "$(DESTDIR)$(HTMLDIR)/man3/$$fn"; \
1104		chmod 644 "$(DESTDIR)$(HTMLDIR)/man3/$$fn"; \
1105	done
1106	@set -e; for x in dummy $(HTMLDOCS5); do \
1107		if [ "$$x" = "dummy" ]; then continue; fi; \
1108		fn=`basename $$x`; \
1109		$(ECHO) "install $$x -> $(DESTDIR)$(HTMLDIR)/man5/$$fn"; \
1110		cp $$x "$(DESTDIR)$(HTMLDIR)/man5/$$fn"; \
1111		chmod 644 "$(DESTDIR)$(HTMLDIR)/man5/$$fn"; \
1112	done
1113	@set -e; for x in dummy $(HTMLDOCS7); do \
1114		if [ "$$x" = "dummy" ]; then continue; fi; \
1115		fn=`basename $$x`; \
1116		$(ECHO) "install $$x -> $(DESTDIR)$(HTMLDIR)/man7/$$fn"; \
1117		cp $$x "$(DESTDIR)$(HTMLDIR)/man7/$$fn"; \
1118		chmod 644 "$(DESTDIR)$(HTMLDIR)/man7/$$fn"; \
1119	done
1120
1121uninstall_html_docs: uninstall_image_docs
1122	@$(ECHO) "*** Uninstalling HTML manpages"
1123	@set -e; for x in dummy $(HTMLDOCS1); do \
1124		if [ "$$x" = "dummy" ]; then continue; fi; \
1125		fn=`basename $$x`; \
1126		$(ECHO) "$(RM) $(DESTDIR)$(HTMLDIR)/man1/$$fn"; \
1127		$(RM) "$(DESTDIR)$(HTMLDIR)/man1/$$fn"; \
1128	done
1129	@set -e; for x in dummy $(HTMLDOCS3); do \
1130		if [ "$$x" = "dummy" ]; then continue; fi; \
1131		fn=`basename $$x`; \
1132		$(ECHO) "$(RM) $(DESTDIR)$(HTMLDIR)/man3/$$fn"; \
1133		$(RM) "$(DESTDIR)$(HTMLDIR)/man3/$$fn"; \
1134	done
1135	@set -e; for x in dummy $(HTMLDOCS5); do \
1136		if [ "$$x" = "dummy" ]; then continue; fi; \
1137		fn=`basename $$x`; \
1138		$(ECHO) "$(RM) $(DESTDIR)$(HTMLDIR)/man5/$$fn"; \
1139		$(RM) "$(DESTDIR)$(HTMLDIR)/man5/$$fn"; \
1140	done
1141	@set -e; for x in dummy $(HTMLDOCS7); do \
1142		if [ "$$x" = "dummy" ]; then continue; fi; \
1143		fn=`basename $$x`; \
1144		$(ECHO) "$(RM) $(DESTDIR)$(HTMLDIR)/man7/$$fn"; \
1145		$(RM) "$(DESTDIR)$(HTMLDIR)/man7/$$fn"; \
1146	done
1147
1148install_image_docs:
1149	@$(PERL) $(SRCDIR)/util/mkdir-p.pl "$(DESTDIR)$(HTMLDIR)/man7/img"
1150	@set -e; for x in dummy $(IMAGEDOCS7); do \
1151		if [ "$$x" = "dummy" ]; then continue; fi; \
1152		fn=`basename $$x`; \
1153		$(ECHO) "install $$x -> $(DESTDIR)$(HTMLDIR)/man7/img/$$fn"; \
1154		cp $(SRCDIR)/$$x "$(DESTDIR)$(HTMLDIR)/man7/img/$$fn"; \
1155		chmod 644 "$(DESTDIR)$(HTMLDIR)/man7/img/$$fn"; \
1156	done
1157
1158uninstall_image_docs:
1159	@set -e; for x in dummy $(IMAGEDOCS7); do \
1160		if [ "$$x" = "dummy" ]; then continue; fi; \
1161		fn=`basename $$x`; \
1162		$(ECHO) "$(RM) $(DESTDIR)$(HTMLDIR)/man7/img/$$fn"; \
1163		$(RM) "$(DESTDIR)$(HTMLDIR)/man7/img/$$fn"; \
1164	done
1165
1166# Developer targets (note: these are only available on Unix) #########
1167##@ Code maintenance
1168
1169# It's important that generate_buildinfo comes after ordinals, as ordinals
1170# is sensitive to build.info changes.
1171update: generate errors ordinals generate_buildinfo ## Update errors, ordinals and build info
1172
1173.PHONY: generate generate_apps generate_crypto_bn generate_crypto_objects \
1174          generate_crypto_conf generate_crypto_asn1 generate_fuzz_oids
1175generate: generate_apps generate_crypto_bn generate_crypto_objects \
1176          generate_crypto_conf generate_crypto_asn1 generate_fuzz_oids
1177
1178.PHONY: generate_buildinfo generate_doc_buildinfo
1179generate_buildinfo: generate_doc_buildinfo
1180
1181.PHONY: doc-nits md-nits
1182doc-nits: build_generated_pods ## Evaluate OpenSSL documentation
1183	$(PERL) $(SRCDIR)/util/find-doc-nits -c -n -l -e -i -a
1184
1185# This uses "mdl", the markdownlint application, which is written in ruby.
1186# The source is at https://github.com/markdownlint/markdownlint
1187# If you have ruby installed, "gem install mdl" should work.
1188# Another option is at https://snapcraft.io/install/mdl/debian
1189# Finally, there's a Node.js version, which we haven't tried, that
1190# can be found at https://github.com/DavidAnson/markdownlint
1191md-nits: ## Evaluate markdown files via "mdl"
1192	mdl -s $(SRCDIR)/util/markdownlint.rb .
1193
1194# Test coverage is a good idea for the future
1195#coverage: $(PROGRAMS) $(TESTPROGRAMS)
1196#	...
1197
1198.PHONY: lint
1199lint: ## Evaluate C code via "splint"
1200	@( cd $(SRCDIR); \
1201           echo splint -DLINT -posixlib -preproc -D__gnuc_va_list=void \
1202	   -I. -Iinclude -Iapps/include $(CRYPTOHEADERS) $(SSLHEADERS) $(SRCS) )
1203
1204.PHONY: check-format
1205check-format: ## Evaluate C code according to OpenSSL coding standards
1206	( cd $(SRCDIR); $(PERL) util/check-format.pl \
1207			$(SRCS) \$(CRYPTOHEADERS) $(SSLHEADERS) )
1208
1209generate_apps:
1210	( cd $(SRCDIR); $(PERL) VMS/VMSify-conf.pl \
1211				< apps/openssl.cnf > apps/openssl-vms.cnf )
1212
1213generate_crypto_bn:
1214	( cd $(SRCDIR); $(PERL) crypto/bn/bn_prime.pl > crypto/bn/bn_prime.h )
1215
1216generate_crypto_objects:
1217	( cd $(SRCDIR); $(PERL) crypto/objects/objects.pl -n \
1218				crypto/objects/objects.txt \
1219				crypto/objects/obj_mac.num \
1220				> crypto/objects/obj_mac.new && \
1221	    mv crypto/objects/obj_mac.new crypto/objects/obj_mac.num )
1222	( cd $(SRCDIR); $(PERL) crypto/objects/objects.pl \
1223				crypto/objects/objects.txt \
1224				crypto/objects/obj_mac.num \
1225				> include/openssl/obj_mac.h )
1226	( cd $(SRCDIR); $(PERL) crypto/objects/obj_dat.pl \
1227				include/openssl/obj_mac.h \
1228				> crypto/objects/obj_dat.h )
1229	( cd $(SRCDIR); $(PERL) crypto/objects/objxref.pl \
1230				crypto/objects/obj_mac.num \
1231				crypto/objects/obj_xref.txt \
1232				> crypto/objects/obj_xref.h )
1233	( cd $(SRCDIR);	sed -e '1,8d' crypto/objects/obj_compat.h >> include/openssl/obj_mac.h )
1234
1235generate_crypto_conf:
1236	( cd $(SRCDIR); $(PERL) crypto/conf/keysets.pl \
1237			        > crypto/conf/conf_def.h )
1238
1239generate_crypto_asn1:
1240	( cd $(SRCDIR); $(PERL) crypto/asn1/charmap.pl \
1241			        > crypto/asn1/charmap.h )
1242
1243generate_fuzz_oids:
1244	( cd $(SRCDIR); $(PERL) fuzz/mkfuzzoids.pl \
1245				crypto/objects/obj_dat.h \
1246				> fuzz/oids.txt )
1247
1248generate_doc_buildinfo:
1249	( $(PERL) -I$(BLDDIR) -Mconfigdata \
1250                $(SRCDIR)/util/dofile.pl -o Makefile \
1251                        $(SRCDIR)/doc/build.info.in \
1252                        > $(SRCDIR)/doc/build.info.new; \
1253          if ( test -e $(SRCDIR)/doc/build.info \
1254               && cmp $(SRCDIR)/doc/build.info.new $(SRCDIR)/doc/build.info \
1255                  > /dev/null ); \
1256          then \
1257                rm $(SRCDIR)/doc/build.info.new; \
1258          else \
1259                mv $(SRCDIR)/doc/build.info.new $(SRCDIR)/doc/build.info; \
1260          fi )
1261
1262generate_fips_sources: providers/fips.module.sources.new
1263providers/fips.module.sources.new: configdata.pm
1264	rm -rf sources-tmp
1265	mkdir sources-tmp
1266	( \
1267	  srcdir=`cd $(SRCDIR); pwd`; \
1268	  cd sources-tmp \
1269	  && $$srcdir/Configure --banner=Configured enable-fips -O0 \
1270	  && ./configdata.pm --query 'get_sources("providers/fips")' > sources1 \
1271	  && "$(MAKE)" -sj 4 build_generated providers/fips.so \
1272	  && find . -name '*.d' | xargs cat > dep1 \
1273          && "$(MAKE)" distclean \
1274	  && $$srcdir/Configure --banner=Configured enable-fips no-asm -O0 \
1275	  && ./configdata.pm --query 'get_sources("providers/fips")' > sources2 \
1276	  && "$(MAKE)" -sj 4 build_generated providers/fips.so \
1277	  && find . -name '*.d' | xargs cat > dep2 \
1278	  && cat sources1 sources2 \
1279	     | grep -v ' : \\$$' | grep -v util/providers.num \
1280	     | sed -e 's/^ *//' -e 's/ *\\$$//' \
1281	     | sort | uniq > sources \
1282	  && cat dep1 dep2 \
1283	     | $(PERL) -p -e 's/\\\n//' \
1284	     | sed -e 's/^.*: *//' -e 's/  */ /g' \
1285	     | fgrep -f sources \
1286	     | tr ' ' '\n' \
1287	     | sort | uniq > deps.raw \
1288	  && cat deps.raw \
1289	     | xargs ./configdata.pm --query 'get_sources(@ARGV)' \
1290	     | $(PERL) -p -e 's/\\\n//' \
1291	     | sed -e 's/\./\\\./g' -e 's/ : */:/' -e 's/^/s:/' -e 's/$$/:/' \
1292	     > deps.sed \
1293	  && cat deps.raw | sed -f deps.sed > deps \
1294	)
1295	( \
1296	  cat sources-tmp/sources sources-tmp/deps \
1297	     | $(PERL) -p -e 's:^ *\Q../\E:: ;' \
1298			  -e 's:^\Q$(SRCDIR)/\E:: if "$(SRCDIR)" ne "." ;' \
1299			  -e 'my $$x; do { $$x = $$_; s:(^|/)((?!\Q../\E)[^/]*/)\Q..\E($$|/):$$1: } while ($$x ne $$_) ;' ; \
1300	  cd $(SRCDIR); \
1301	  for x in crypto/bn/asm/*.pl crypto/bn/asm/*.S \
1302		   crypto/aes/asm/*.pl crypto/aes/asm/*.S \
1303		   crypto/ec/asm/*.pl \
1304		   crypto/modes/asm/*.pl \
1305		   crypto/sha/asm/*.pl \
1306		   crypto/*cpuid.pl crypto/*cpuid.S \
1307		   crypto/*cap.c; do \
1308	    echo "$$x"; \
1309	  done \
1310	) | grep -v sm2p256 | sort | uniq > providers/fips.module.sources.new
1311	rm -rf sources-tmp
1312
1313# Set to -force to force a rebuild
1314ERROR_REBUILD=
1315errors:
1316	( b=`pwd`; set -e; cd $(SRCDIR); \
1317          $(PERL) util/ck_errf.pl -strict -internal; \
1318          $(PERL) -I$$b util/mkerr.pl $(ERROR_REBUILD) -internal )
1319	( b=`pwd`; set -e; cd $(SRCDIR)/engines; \
1320          for E in *.ec ; do \
1321              $(PERL) ../util/ck_errf.pl -strict \
1322                -conf $$E `basename $$E .ec`.c; \
1323              $(PERL) -I$$b ../util/mkerr.pl $(ERROR_REBUILD) -static \
1324                -conf $$E `basename $$E .ec`.c ; \
1325          done )
1326
1327{- use File::Basename;
1328
1329   my @sslheaders_tmpl =
1330       qw( include/openssl/ssl.h
1331           include/openssl/ssl2.h
1332           include/openssl/ssl3.h
1333           include/openssl/sslerr.h
1334           include/openssl/tls1.h
1335           include/openssl/dtls1.h
1336           include/openssl/srtp.h
1337           include/openssl/quic.h
1338           include/openssl/sslerr_legacy.h );
1339   my @cryptoheaders_tmpl =
1340       qw( include/internal/dso.h
1341           include/internal/o_dir.h
1342           include/internal/err.h
1343           include/internal/evp.h
1344           include/internal/pem.h
1345           include/internal/asn1.h
1346           include/internal/sslconf.h );
1347   my @cryptoskipheaders = ( @sslheaders_tmpl,
1348       qw( include/openssl/conf_api.h
1349           include/openssl/ebcdic.h
1350           include/openssl/opensslconf.h
1351           include/openssl/symhacks.h ) );
1352   our %cryptoheaders = ();
1353   our %sslheaders = ();
1354   foreach my $d ( qw( include/openssl include/internal ) ) {
1355       my @header_patterns =
1356           map { catfile($config{sourcedir}, $d, $_) } ( '*.h', '*.h.in' );
1357       foreach my $f ( map { glob($_) } @header_patterns ) {
1358           my $base = basename($f);
1359           my $base_in = basename($f, '.in');
1360           my $dir = catfile($config{sourcedir}, $d);
1361           if ($base ne $base_in) {
1362               # We have a .h.in file, which means the header file is in the
1363               # build tree.
1364               $base = $base_in;
1365               $dir = catfile($config{builddir}, $d);
1366           }
1367           my $new_f = catfile($dir, $base);
1368           my $fn = "$d/$base";
1369           # The logic to add files to @cryptoheaders is a bit complex.  The
1370           # file to be added must be either in the public header directory
1371           # or one of the pre-declared internal headers, and must under no
1372           # circumstances be one of those that must be skipped.
1373           $cryptoheaders{$new_f} = 1
1374               if (($d eq 'include/openssl'
1375                    || ( grep { $_ eq $fn } @cryptoheaders_tmpl ))
1376                   && !( grep { $_ eq $fn } @cryptoskipheaders ));
1377           # The logic to add files to @sslheaders is much simpler...
1378           $sslheaders{$new_f} = 1 if grep { $_ eq $fn } @sslheaders_tmpl;
1379       }
1380   }
1381   "";
1382-}
1383SRCS={-
1384sub uniq { my %seen; grep !$seen{$_}++, @_; }
1385sub flat(@) { return map { ref eq 'ARRAY' ? @$_ : $_ } @_; }
1386join(" \\\n" . ' ' x 5, fill_lines(" ", $COLUMNS - 5,
1387     uniq(grep /\.(c|cc|cpp)$/,
1388          flat (map { $unified_info{sources}->{$_} }
1389                (sort keys %{$unified_info{sources}})))))
1390-}
1391CRYPTOHEADERS={- join(" \\\n" . ' ' x 14,
1392                      fill_lines(" ", $COLUMNS - 14, sort keys %cryptoheaders)) -}
1393SSLHEADERS={- join(" \\\n" . ' ' x 11,
1394                   fill_lines(" ", $COLUMNS - 11, sort keys %sslheaders)) -}
1395
1396renumber: build_generated
1397	$(PERL) $(SRCDIR)/util/mknum.pl --version $(VERSION_NUMBER) --no-warnings \
1398                --ordinals $(SRCDIR)/util/libcrypto.num \
1399                --symhacks $(SRCDIR)/include/openssl/symhacks.h \
1400                --renumber \
1401                $(CRYPTOHEADERS)
1402	$(PERL) $(SRCDIR)/util/mknum.pl --version $(VERSION_NUMBER) --no-warnings \
1403                --ordinals $(SRCDIR)/util/libssl.num \
1404                --symhacks $(SRCDIR)/include/openssl/symhacks.h \
1405                --renumber \
1406                $(SSLHEADERS)
1407
1408.PHONY: ordinals
1409ordinals: build_generated
1410	$(PERL) $(SRCDIR)/util/mknum.pl --version $(VERSION_NUMBER) --no-warnings \
1411                --ordinals $(SRCDIR)/util/libcrypto.num \
1412                --symhacks $(SRCDIR)/include/openssl/symhacks.h \
1413                $(CRYPTOHEADERS)
1414	$(PERL) $(SRCDIR)/util/mknum.pl --version $(VERSION_NUMBER) --no-warnings \
1415                --ordinals $(SRCDIR)/util/libssl.num \
1416                --symhacks $(SRCDIR)/include/openssl/symhacks.h \
1417                $(SSLHEADERS)
1418
1419test_ordinals:
1420	"$(MAKE)" run_tests TESTS=test_ordinals
1421
1422tags TAGS: FORCE build_generated
1423	rm -f TAGS tags
1424	-( cd $(SRCDIR); util/ctags.sh )
1425	-etags `find . -name '*.[ch]' -o -name '*.pm' -o -name '*.inc'`
1426
1427providers/fips.checksum.new: providers/fips.module.sources.new
1428	@which unifdef > /dev/null || \
1429	( echo >&2 "ERROR: unifdef not in your \$$PATH, FIPS checksums not calculated"; \
1430	  false )
1431	( sources=`pwd`/providers/fips.module.sources.new; \
1432	  cd $(SRCDIR) \
1433	  && cat $$sources \
1434	         | xargs ./util/fips-checksums.sh ) \
1435	         > providers/fips-sources.checksums.new \
1436	&& sha256sum providers/fips-sources.checksums.new \
1437	     | sed -e 's|\.new||' > providers/fips.checksum.new
1438
1439fips-checksums: providers/fips.checksum.new
1440
1441$(SRCDIR)/providers/fips.checksum: providers/fips.checksum.new
1442	cp -p providers/fips.module.sources.new $(SRCDIR)/providers/fips.module.sources
1443	cp -p providers/fips-sources.checksums.new $(SRCDIR)/providers/fips-sources.checksums
1444	cp -p providers/fips.checksum.new $(SRCDIR)/providers/fips.checksum
1445
1446update-fips-checksums: $(SRCDIR)/providers/fips.checksum
1447
1448diff-fips-checksums: fips-checksums
1449	diff -u $(SRCDIR)/providers/fips.module.sources providers/fips.module.sources.new
1450	diff -u $(SRCDIR)/providers/fips-sources.checksums providers/fips-sources.checksums.new
1451	diff -u $(SRCDIR)/providers/fips.checksum providers/fips.checksum.new
1452
1453# Release targets (note: only available on Unix) #####################
1454
1455tar:
1456	(cd $(SRCDIR); ./util/mktar.sh --name='$(NAME)' --tarfile='$(TARFILE)')
1457
1458# Helper targets #####################################################
1459
1460link-utils: $(BLDDIR)/util/opensslwrap.sh $(BLDDIR)/apps/openssl.cnf
1461
1462$(BLDDIR)/util/opensslwrap.sh: Makefile
1463	@if [ "$(SRCDIR)" != "$(BLDDIR)" ]; then \
1464	    mkdir -p "$(BLDDIR)/util"; \
1465	    ln -sf "../$(SRCDIR)/util/`basename "$@"`" "$(BLDDIR)/util"; \
1466	fi
1467
1468$(BLDDIR)/apps/openssl.cnf: Makefile
1469	@if [ "$(SRCDIR)" != "$(BLDDIR)" ]; then \
1470	    mkdir -p "$(BLDDIR)/apps"; \
1471	    ln -sf "../$(SRCDIR)/apps/`basename "$@"`" "$(BLDDIR)/apps"; \
1472	fi
1473
1474FORCE:
1475
1476# Building targets ###################################################
1477
1478Makefile: configdata.pm \
1479          {- join(" \\\n" . ' ' x 10,
1480                  fill_lines(" ", $COLUMNS - 10,
1481                             @{$config{build_file_templates}})) -}
1482	@echo "Detected changed: $?"
1483	$(PERL) configdata.pm
1484	@echo "**************************************************"
1485	@echo "***                                            ***"
1486	@echo "***   Please run the same make command again   ***"
1487	@echo "***                                            ***"
1488	@echo "**************************************************"
1489	@false
1490
1491configdata.pm: $(SRCDIR)/Configure $(SRCDIR)/config \
1492               {- join(" \\\n" . ' ' x 15,
1493                       fill_lines(" ", $COLUMNS - 15,
1494                                  @{$config{build_infos}},
1495                                  @{$config{conf_files}})) -}
1496	@echo "Detected changed: $?"
1497	$(PERL) configdata.pm -r
1498	@echo "**************************************************"
1499	@echo "***                                            ***"
1500	@echo "***   Please run the same make command again   ***"
1501	@echo "***                                            ***"
1502	@echo "**************************************************"
1503	@false
1504
1505reconfigure reconf:
1506	$(PERL) configdata.pm -r
1507
1508{-
1509  use File::Basename;
1510  use File::Spec::Functions qw/:DEFAULT abs2rel rel2abs/;
1511
1512  # Helper function to convert dependencies in platform agnostic form to
1513  # dependencies in platform form.
1514  sub compute_platform_depends {
1515      map { my $x = $_;
1516
1517            grep { $x eq $_ } @{$unified_info{programs}} and platform->bin($x)
1518            or grep { $x eq $_ } @{$unified_info{modules}} and platform->dso($x)
1519            or grep { $x eq $_ } @{$unified_info{libraries}} and platform->lib($x)
1520            or platform->convertext($x); } @_;
1521  }
1522
1523  # Helper function to figure out dependencies on libraries
1524  # It takes a list of library names and outputs a list of dependencies
1525  sub compute_lib_depends {
1526      # Depending on shared libraries:
1527      # On Windows POSIX layers, we depend on {libname}.dll.a
1528      # On Unix platforms, we depend on {shlibname}.so
1529      return map { platform->sharedlib_simple($_)
1530                   // platform->sharedlib_import($_)
1531                   // platform->sharedlib($_)
1532                   // platform->staticlib($_)
1533                 } @_;
1534  }
1535
1536  sub generatetarget {
1537      my %args = @_;
1538      my $deps = join(" ", compute_platform_depends(@{$args{deps}}));
1539      return <<"EOF";
1540$args{target}: $deps
1541EOF
1542  }
1543
1544  sub generatesrc {
1545      my %args = @_;
1546      my $gen0 = $args{generator}->[0];
1547      my $gen_args = join('', map { " $_" }
1548                              @{$args{generator}}[1..$#{$args{generator}}]);
1549      my $gen_incs = join("", map { " -I".$_ } @{$args{generator_incs}});
1550      my $incs = join("", map { " -I".$_ } @{$args{incs}});
1551      my $defs = join("", map { " -D".$_ } @{$args{defs}});
1552      my $deps = join(" ", compute_platform_depends(@{$args{generator_deps}},
1553                                                    @{$args{deps}}));
1554
1555      if ($args{src} =~ /\.html$/) {
1556          #
1557          # HTML generator
1558          #
1559          my $title = basename($args{src}, ".html");
1560          my $pod = $gen0;
1561          return <<"EOF";
1562$args{src}: $pod
1563	\$(PERL) \$(SRCDIR)/util/mkpod2html.pl -i "$pod" -o \$\@ -t "$title" -r "\$(SRCDIR)/doc"
1564EOF
1565      } elsif ($args{src} =~ /\.(\d)$/) {
1566          #
1567          # Man-page generator
1568          #
1569          my $section = $1;
1570          my $name = uc basename($args{src}, ".$section");
1571          my $pod = $gen0;
1572          return <<"EOF";
1573$args{src}: $pod
1574	pod2man --name=$name --section=$section\$(MANSUFFIX) --center=OpenSSL \\
1575		--release=\$(VERSION) $pod >\$\@
1576EOF
1577      } elsif (platform->isdef($args{src})) {
1578          #
1579          # Linker script-ish generator
1580          #
1581          my $target = platform->def($args{src});
1582          (my $mkdef_os = $target{shared_target}) =~ s|-shared$||;
1583          my $ord_ver = $args{intent} eq 'lib' ? ' --version $(VERSION_NUMBER)' : '';
1584          my $ord_name = $args{generator}->[1] || $args{product};
1585          return <<"EOF";
1586$target: $gen0 $deps \$(SRCDIR)/util/mkdef.pl
1587	\$(PERL) \$(SRCDIR)/util/mkdef.pl$ord_ver --type $args{intent} --ordinals $gen0  --name $ord_name --OS $mkdef_os > $target
1588EOF
1589      } elsif (platform->isasm($args{src})
1590               || platform->iscppasm($args{src})) {
1591          #
1592          # Assembler generator
1593          #
1594          my $cppflags = {
1595              shlib => '$(LIB_CFLAGS) $(LIB_CPPFLAGS)',
1596              lib => '$(LIB_CFLAGS) $(LIB_CPPFLAGS)',
1597              dso => '$(DSO_CFLAGS) $(DSO_CPPFLAGS)',
1598              bin => '$(BIN_CFLAGS) $(BIN_CPPFLAGS)'
1599          } -> {$args{intent}};
1600
1601          my $generator;
1602          if ($gen0 =~ /\.pl$/) {
1603              $generator = 'CC="$(CC)" $(PERL)'.$gen_incs.' '.$gen0.$gen_args
1604                  .' "$(PERLASM_SCHEME)"'.$incs.' '.$cppflags.$defs.' $(PROCESSOR)';
1605          } elsif ($gen0 =~ /\.m4$/) {
1606              $generator = 'm4 -B 8192'.$gen_incs.' '.$gen0.$gen_args.' >'
1607          } elsif ($gen0 =~ /\.S$/) {
1608              $generator = undef;
1609          } else {
1610              die "Generator type for $args{src} unknown: $gen0\n";
1611          }
1612
1613          if (defined($generator)) {
1614              return <<"EOF";
1615$args{src}: $gen0 $deps
1616	$generator \$@
1617EOF
1618          }
1619          return <<"EOF";
1620$args{src}: $gen0 $deps
1621	\$(CC) $incs $cppflags $defs -E $gen0 | \\
1622	\$(PERL) -ne '/^#(line)?\\s*[0-9]+/ or print' > \$@
1623EOF
1624      } elsif ($gen0 =~ m|^.*\.in$|) {
1625          #
1626          # "dofile" generator (file.in -> file)
1627          #
1628          my $dofile = abs2rel(rel2abs(catfile($config{sourcedir},
1629                                               "util", "dofile.pl")),
1630                               rel2abs($config{builddir}));
1631          my @perlmodules = ();
1632          my %perlmoduleincs = ();
1633          my %perlmoduledeps = ();
1634          foreach my $x (('configdata.pm', @{$args{deps}})) {
1635              # Compute (i)nclusion directory, (m)odule name and (d)ependency
1636              my $i, $m, $d;
1637              if ($x =~ /\|/) {
1638                  $i = $`;
1639                  $d = $';
1640
1641                  # Massage the module part to become a real perl module spec
1642                  $m = $d;
1643                  $m =~ s|\.pm$||;
1644                  # Directory specs are :: in perl package names
1645                  $m =~ s|/|::|g;
1646
1647                  # Full file name of the dependency
1648                  $d = catfile($i, $d) if $i;
1649              } elsif ($x =~ /\.pm$/) {
1650                  $i = dirname($x);
1651                  $m = basename($x, '.pm');
1652                  $d = $x;
1653              } else {
1654                  # All other dependencies are simply collected
1655                  $d = $x;
1656              }
1657              push @perlmodules, '"-M'.$m.'"' if $m;
1658              $perlmoduledeps{$d} = 1;
1659              $perlmoduleincs{'"-I'.$i.'"'} = 1 if $i;
1660          }
1661
1662          # Because of the special treatment of dependencies, we need to
1663          # recompute $deps completely
1664          my $deps
1665              = join(" ", compute_platform_depends(@{$args{generator_deps}},
1666                                                   sort keys %perlmoduledeps));
1667          my $perlmodules = join(' ', '', ( sort keys %perlmoduleincs ), @perlmodules);
1668
1669          return <<"EOF";
1670$args{src}: $gen0 $deps
1671	\$(PERL)$perlmodules "$dofile" "-o$target{build_file}" $gen0$gen_args > \$@
1672EOF
1673      } elsif (grep { $_ eq $gen0 } @{$unified_info{programs}}) {
1674          #
1675          # Generic generator using OpenSSL programs
1676          #
1677
1678          # Redo $gen0, to ensure that we have the proper extension where
1679          # necessary.
1680          $gen0 = platform->bin($gen0);
1681          # Use $(PERL) to execute wrap.pl directly to avoid calling env
1682          return <<"EOF";
1683$args{src}: $gen0 $deps \$(BLDDIR)/util/wrap.pl
1684	\$(PERL) \$(BLDDIR)/util/wrap.pl $gen0$gen_args > \$@
1685EOF
1686      } else {
1687          #
1688          # Generic generator using Perl
1689          #
1690          return <<"EOF";
1691$args{src}: $gen0 $deps
1692	\$(PERL)$gen_incs $gen0$gen_args > \$@
1693EOF
1694      }
1695  }
1696
1697  # Should one wonder about the end of the Perl snippet, it's because this
1698  # second regexp eats up line endings as well, if the removed path is the
1699  # last in the line.  We may therefore need to put back a line ending.
1700  sub src2obj {
1701      my %args = @_;
1702      my $obj = platform->convertext($args{obj});
1703      my $dep = platform->dep($args{obj});
1704      my @srcs = @{$args{srcs}};
1705      my $srcs = join(" ",  @srcs);
1706      my $deps = join(" ", @srcs, @{$args{deps}});
1707      my $incs = join("", map { " -I".$_ } @{$args{incs}});
1708      my $defs = join("", map { " -D".$_ } @{$args{defs}});
1709      my $cmd;
1710      my $cmdflags;
1711      my $cmdcompile;
1712      if (grep /\.rc$/, @srcs) {
1713          $cmd = '$(RC)';
1714          $cmdflags = '$(RCFLAGS)';
1715          $cmdcompile = '';
1716      } elsif (grep /\.(cc|cpp)$/, @srcs) {
1717          $cmd = '$(CXX)';
1718          $cmdcompile = ' -c';
1719          $cmdflags = {
1720              shlib => '$(LIB_CXXFLAGS) $(LIB_CPPFLAGS)',
1721              lib => '$(LIB_CXXFLAGS) $(LIB_CPPFLAGS)',
1722              dso => '$(DSO_CXXFLAGS) $(DSO_CPPFLAGS)',
1723              bin => '$(BIN_CXXFLAGS) $(BIN_CPPFLAGS)'
1724          } -> {$args{intent}};
1725      } else {
1726          $cmd = '$(CC)';
1727          $cmdcompile = ' -c';
1728          $cmdflags = {
1729              shlib => '$(LIB_CFLAGS) $(LIB_CPPFLAGS)',
1730              lib => '$(LIB_CFLAGS) $(LIB_CPPFLAGS)',
1731              dso => '$(DSO_CFLAGS) $(DSO_CPPFLAGS)',
1732              bin => '$(BIN_CFLAGS) $(BIN_CPPFLAGS)'
1733          } -> {$args{intent}};
1734      }
1735      my $recipe;
1736      # extension-specific rules
1737      if (grep /\.s$/, @srcs) {
1738          $recipe .= <<"EOF";
1739$obj: $deps
1740	$cmd $cmdflags -c -o \$\@ $srcs
1741EOF
1742      } elsif (grep /\.S$/, @srcs) {
1743          # Originally there was multi-step rule with $(CC) -E file.S
1744          # followed by $(CC) -c file.s. It compensated for one of
1745          # legacy platform compiler's inability to handle .S files.
1746          # The platform is long discontinued by vendor so there is
1747          # hardly a point to drag it along...
1748          $recipe .= <<"EOF";
1749$obj: $deps
1750	$cmd $incs $defs $cmdflags -c -o \$\@ $srcs
1751EOF
1752      } elsif ($makedep_scheme eq 'gcc' && !grep /\.rc$/, @srcs) {
1753          $recipe .= <<"EOF";
1754$obj: $deps
1755	$cmd $incs $defs $cmdflags -MMD -MF $dep.tmp -c -o \$\@ $srcs
1756	\@touch $dep.tmp
1757	\@if cmp $dep.tmp $dep > /dev/null 2> /dev/null; then \\
1758		rm -f $dep.tmp; \\
1759	else \\
1760		mv $dep.tmp $dep; \\
1761	fi
1762EOF
1763      } else {
1764          $recipe .= <<"EOF";
1765$obj: $deps
1766	$cmd $incs $defs $cmdflags $cmdcompile -o \$\@ $srcs
1767EOF
1768          if ($makedep_scheme eq 'makedepend') {
1769              $recipe .= <<"EOF";
1770	\$(MAKEDEPEND) -f- -Y -- $incs $cmdflags -- $srcs 2>/dev/null \\
1771	    > $dep
1772EOF
1773          }
1774      }
1775      return $recipe;
1776  }
1777  # We *know* this routine is only called when we've configure 'shared'.
1778  sub obj2shlib {
1779      my %args = @_;
1780      my @linkdirs = ();
1781      my @linklibs = ();
1782      foreach (@{$args{deps}}) {
1783          if (platform->isstaticlib($_)) {
1784              push @linklibs, platform->convertext($_);
1785          } else {
1786              my $d = "-L" . dirname($_);
1787              my $l = basename($_);
1788              $l =~ s/^lib//;
1789              $l = "-l" . $l;
1790              push @linklibs, $l;
1791              push @linkdirs, $d unless grep { $d eq $_ } @linkdirs;
1792          }
1793      }
1794      my $linkflags = join("", map { $_." " } @linkdirs);
1795      my $linklibs = join("", map { $_." " } @linklibs);
1796      my @objs = map { platform->convertext($_) }
1797                 grep { !platform->isdef($_) }
1798                 @{$args{objs}};
1799      my @defs = map { platform->def($_) }
1800                 grep { platform->isdef($_) }
1801                 @{$args{objs}};
1802      my @deps = compute_lib_depends(@{$args{deps}});
1803      die "More than one exported symbol map" if scalar @defs > 1;
1804
1805      my $full = platform->sharedlib($args{lib});
1806      # $import is for Windows and subsystems thereof, where static import
1807      # libraries for DLLs are a thing.  On platforms that have this mechanism,
1808      # $import has the name of this import library.  On platforms that don't
1809      # have this mechanism, $import will be |undef|.
1810      # It's also used on AIX in solib mode, which creates import libraries
1811      # for the shared libraries.
1812      my $import = platform->sharedlib_import($args{lib});
1813      # $simple is for platforms where full shared library names include the
1814      # shared library version, and there's a simpler name that doesn't include
1815      # that version.  On such platforms, $simple has the simpler name.  On
1816      # other platforms, it will be |undef|.
1817      my $simple = platform->sharedlib_simple($args{lib});
1818
1819      my $argfile = defined $target{shared_argfileflag} ? $full.".args" : undef;
1820      my $shared_soname = "";
1821      $shared_soname .= ' '.$target{shared_sonameflag}.basename($full)
1822          if defined $target{shared_sonameflag};
1823      my $shared_imp = "";
1824      $shared_imp .= ' '.$target{shared_impflag}.basename($import)
1825          if defined $target{shared_impflag} && defined $import;
1826      my $shared_def = join("", map { ' '.$target{shared_defflag}.$_ } @defs);
1827
1828      # There is at least one platform where the compiler-as-linker needs to
1829      # have one object file directly on the command line.  That won't hurt
1830      # any other platform, so we do that for everyone when there's an argfile
1831      # to be had.  This depends heavily on splice, which removes elements from
1832      # the given array, and returns them so they can be captured.
1833      my @argfileobjs = $argfile
1834          ? splice(@objs, 1)
1835          : ();
1836      my $argfilecmds = $argfile
1837          ? join("\n\t", map { "echo $_ >> $argfile" } @argfileobjs)
1838          : undef;
1839      my $argfiledeps = $argfile
1840          ? join(" \\\n" . ' ' x (length($argfile) + 2),
1841                 fill_lines(' ', $COLUMNS - length($full) - 2, @argfileobjs))
1842          : undef;
1843      my @fulldeps = (@objs, ($argfile ? $argfile : ()), @defs, @deps);
1844      my @fullobjs = (
1845          @objs,
1846          ($argfile ? $target{shared_argfileflag}.$argfile : ())
1847      );
1848      my $fulldeps =
1849          join(" \\\n" . ' ' x (length($full) + 2),
1850               fill_lines(' ', $COLUMNS - length($full) - 2, @fulldeps));
1851      my $fullobjs =
1852          join(" \\\n\t\t", fill_lines(' ', $COLUMNS - 16, @fullobjs));
1853
1854      my $recipe = '';
1855
1856      if (defined $simple && $simple ne $full) {
1857          if (sharedaix()) {
1858              $recipe .= <<"EOF";
1859$simple: $full
1860	rm -f $simple && \\
1861	\$(AR) r $simple $full
1862EOF
1863          } else {
1864              $recipe .= <<"EOF";
1865$simple: $full
1866	rm -f $simple && \\
1867	ln -s $full $simple
1868EOF
1869          }
1870      }
1871      if (defined $import) {
1872          if (sharedaix_solib()) {
1873              $recipe .= <<"EOF";
1874$import: $full $defs[0]
1875	rm -f $import && \\
1876	echo \\#!$full > $import && \\
1877        cat $defs[0] >>$import
1878EOF
1879          } else {
1880      $recipe .= <<"EOF";
1881$import: $full
1882EOF
1883          }
1884      }
1885      $recipe .= <<"EOF";
1886$full: $fulldeps
1887	\$(CC) \$(LIB_CFLAGS) $linkflags\$(LIB_LDFLAGS)$shared_soname$shared_imp \\
1888		-o $full$shared_def \\
1889		$fullobjs \\
1890		$linklibs \$(LIB_EX_LIBS)
1891EOF
1892      if (windowsdll()) {
1893          $recipe .= <<"EOF";
1894	rm -f apps/$full
1895	rm -f fuzz/$full
1896	cp -p $full apps/
1897	cp -p $full fuzz/
1898EOF
1899          if (!$disabled{tests}) {
1900            $recipe .= <<"EOF";
1901	rm -f test/$full
1902	cp -p $full test/
1903EOF
1904          }
1905      }
1906      $recipe .= <<"EOF" if defined $argfile;
1907$argfile: $argfiledeps
1908	\$(RM) $argfile
1909	$argfilecmds
1910EOF
1911      return $recipe;
1912  }
1913  sub obj2dso {
1914      my %args = @_;
1915      my $dso = platform->dso($args{module});
1916      my @linkdirs = ();
1917      my @linklibs = ();
1918      foreach (@{$args{deps}}) {
1919          next unless defined $_;
1920          if (platform->isstaticlib($_)) {
1921              push @linklibs, platform->convertext($_);
1922          } else {
1923              my $d = "-L" . dirname($_);
1924              my $l = basename($_);
1925              $l =~ s/^lib//;
1926              $l = "-l" . $l;
1927              push @linklibs, $l;
1928              push @linkdirs, $d unless grep { $d eq $_ } @linkdirs;
1929          }
1930      }
1931      my $linkflags = join("", map { $_." " } @linkdirs);
1932      my $linklibs = join("", map { $_." " } @linklibs);
1933      my @objs = map { platform->convertext($_) }
1934                 grep { !platform->isdef($_) }
1935                 @{$args{objs}};
1936      my @defs = map { platform->def($_) }
1937                 grep { platform->isdef($_) }
1938                 @{$args{objs}};
1939      my @deps = compute_lib_depends(@{$args{deps}});
1940      my $shared_def = join("", map { ' '.$target{shared_defflag}.$_ } @defs);
1941      # Next line needs to become "less magic" (see PR #11950)
1942      $shared_def .= ' '.$target{shared_fipsflag} if (defined $target{shared_fipsflag} && $shared_def =~ m/providers\/fips/);
1943      my $objs = join(" \\\n\t\t", fill_lines(' ', $COLUMNS - 16, @objs));
1944      my $deps = join(" \\\n" . ' ' x (length($dso) + 2),
1945                      fill_lines(' ', $COLUMNS - length($dso) - 2,
1946                                 @objs, @defs, @deps));
1947
1948      return <<"EOF";
1949$dso: $deps
1950	\$(CC) \$(DSO_CFLAGS) $linkflags\$(DSO_LDFLAGS) \\
1951		-o $dso$shared_def \\
1952		$objs \\
1953		$linklibs\$(DSO_EX_LIBS)
1954EOF
1955  }
1956  sub obj2lib {
1957      my %args = @_;
1958      my $lib = platform->staticlib($args{lib});
1959      my @objs = map { platform->obj($_) } @{$args{objs}};
1960      my $deps = join(" \\\n" . ' ' x (length($lib) + 2),
1961                      fill_lines(' ', $COLUMNS - length($lib) - 2, @objs));
1962      my $max_per_call = 500;
1963      my @objs_grouped;
1964      push @objs_grouped, join(" ", splice @objs, 0, $max_per_call) while @objs;
1965      my $fill_lib =
1966          join("\n\t", (map { "\$(AR) \$(ARFLAGS) $lib $_" } @objs_grouped));
1967      return <<"EOF";
1968$lib: $deps
1969	\$(RM) $lib
1970	$fill_lib
1971	\$(RANLIB) \$\@ || echo Never mind.
1972EOF
1973  }
1974  sub obj2bin {
1975      my %args = @_;
1976      my $bin = platform->bin($args{bin});
1977      my @objs = map { platform->obj($_) } @{$args{objs}};
1978      my @deps = compute_lib_depends(@{$args{deps}});
1979      my $objs = join(" \\\n" . ' ' x (length($bin) + 2),
1980                      fill_lines(' ', $COLUMNS - length($bin) - 2, @objs));
1981      my @linkdirs = ();
1982      my @linklibs = ();
1983      foreach (@{$args{deps}}) {
1984          next unless defined $_;
1985          if (platform->isstaticlib($_)) {
1986              push @linklibs, platform->convertext($_);
1987          } else {
1988              my $d = "-L" . dirname($_);
1989              my $l = basename($_);
1990              $l =~ s/^lib//;
1991              $l = "-l" . $l;
1992              push @linklibs, $l;
1993              push @linkdirs, $d unless grep { $d eq $_ } @linkdirs;
1994          }
1995      }
1996      my $linkflags = join("", map { $_." " } @linkdirs);
1997      my $linklibs = join("", map { $_." " } @linklibs);
1998      my $cmd = '$(CC)';
1999      my $cmdflags = '$(BIN_CFLAGS)';
2000      if (grep /_cc\.o$/, @{$args{objs}}) {
2001          $cmd = '$(CXX)';
2002          $cmdflags = '$(BIN_CXXFLAGS)';
2003      }
2004
2005      my $objs = join(" \\\n\t\t", fill_lines(' ', $COLUMNS - 16, @objs));
2006      my $deps = join(" \\\n" . ' ' x (length($bin) + 2),
2007                      fill_lines(' ', $COLUMNS - length($bin) - 2,
2008                                 @objs, @deps));
2009
2010      return <<"EOF";
2011$bin: $deps
2012	rm -f $bin
2013	\$\${LDCMD:-$cmd} $cmdflags $linkflags\$(BIN_LDFLAGS) \\
2014		-o $bin \\
2015		$objs \\
2016		$linklibs\$(BIN_EX_LIBS)
2017EOF
2018  }
2019  sub in2script {
2020      my %args = @_;
2021      my $script = $args{script};
2022      my $sources = join(" ", @{$args{sources}});
2023      my $dofile = abs2rel(rel2abs(catfile($config{sourcedir},
2024                                           "util", "dofile.pl")),
2025                           rel2abs($config{builddir}));
2026      return <<"EOF";
2027$script: $sources configdata.pm
2028	\$(RM) "$script"
2029	\$(PERL) "-I\$(BLDDIR)" -Mconfigdata "$dofile" \\
2030	    "-o$target{build_file}" $sources > "$script"
2031	chmod a+x $script
2032EOF
2033  }
2034  sub generatedir {
2035      my %args = @_;
2036      my $dir = $args{dir};
2037      my @deps = compute_platform_depends(@{$args{deps}});
2038      my @comments = ();
2039
2040      # We already have a 'test' target, and the top directory is just plain
2041      # silly
2042      return if $dir eq "test" || $dir eq ".";
2043
2044      foreach my $type (("dso", "lib", "bin", "script")) {
2045          next unless defined($unified_info{dirinfo}->{$dir}->{products}->{$type});
2046          # For lib object files, we could update the library.  However, it
2047          # was decided that it's enough to build the directory local object
2048          # files, so we don't need to add any actions, and the dependencies
2049          # are already taken care of.
2050          if ($type ne "lib") {
2051              foreach my $prod (@{$unified_info{dirinfo}->{$dir}->{products}->{$type}}) {
2052                  if (dirname($prod) eq $dir) {
2053                      push @deps, compute_platform_depends($prod);
2054                  } else {
2055                      push @comments, "# No support to produce $type ".join(", ", @{$unified_info{dirinfo}->{$dir}->{products}->{$type}});
2056                  }
2057              }
2058          }
2059      }
2060
2061      my $target = "$dir $dir/";
2062      my $deps = join(" \\\n\t",
2063                      fill_lines(' ', $COLUMNS - 8, @deps));
2064      my $comments = join("\n", "", @comments);
2065      return <<"EOF";
2066$target: \\
2067	$deps$comments
2068EOF
2069  }
2070  ""    # Important!  This becomes part of the template result.
2071-}
2072