1# Copyright (c) 2015, Google Inc. 2# 3# Permission to use, copy, modify, and/or distribute this software for any 4# purpose with or without fee is hereby granted, provided that the above 5# copyright notice and this permission notice appear in all copies. 6# 7# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY 10# SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION 12# OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN 13# CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 15"""Enumerates source files for consumption by various build systems.""" 16 17import optparse 18import os 19import subprocess 20import sys 21import json 22 23 24# OS_ARCH_COMBOS maps from OS and platform to the OpenSSL assembly "style" for 25# that platform and the extension used by asm files. 26OS_ARCH_COMBOS = [ 27 ('ios', 'arm', 'ios32', [], 'S'), 28 ('ios', 'aarch64', 'ios64', [], 'S'), 29 ('linux', 'arm', 'linux32', [], 'S'), 30 ('linux', 'aarch64', 'linux64', [], 'S'), 31 ('linux', 'ppc64le', 'linux64le', [], 'S'), 32 ('linux', 'x86', 'elf', ['-fPIC', '-DOPENSSL_IA32_SSE2'], 'S'), 33 ('linux', 'x86_64', 'elf', [], 'S'), 34 ('mac', 'x86', 'macosx', ['-fPIC', '-DOPENSSL_IA32_SSE2'], 'S'), 35 ('mac', 'x86_64', 'macosx', [], 'S'), 36 ('win', 'x86', 'win32n', ['-DOPENSSL_IA32_SSE2'], 'asm'), 37 ('win', 'x86_64', 'nasm', [], 'asm'), 38] 39 40# NON_PERL_FILES enumerates assembly files that are not processed by the 41# perlasm system. 42NON_PERL_FILES = { 43 ('linux', 'arm'): [ 44 'src/crypto/curve25519/asm/x25519-asm-arm.S', 45 'src/crypto/poly1305/poly1305_arm_asm.S', 46 ], 47 ('linux', 'x86_64'): [ 48 'src/crypto/hrss/asm/poly_rq_mul.S', 49 ], 50} 51 52PREFIX = None 53EMBED_TEST_DATA = True 54 55 56def PathOf(x): 57 return x if not PREFIX else os.path.join(PREFIX, x) 58 59 60class Android(object): 61 62 def __init__(self): 63 self.header = \ 64"""# Copyright (C) 2015 The Android Open Source Project 65# 66# Licensed under the Apache License, Version 2.0 (the "License"); 67# you may not use this file except in compliance with the License. 68# You may obtain a copy of the License at 69# 70# http://www.apache.org/licenses/LICENSE-2.0 71# 72# Unless required by applicable law or agreed to in writing, software 73# distributed under the License is distributed on an "AS IS" BASIS, 74# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 75# See the License for the specific language governing permissions and 76# limitations under the License. 77 78# This file is created by generate_build_files.py. Do not edit manually. 79""" 80 81 def PrintVariableSection(self, out, name, files): 82 out.write('%s := \\\n' % name) 83 for f in sorted(files): 84 out.write(' %s\\\n' % f) 85 out.write('\n') 86 87 def WriteFiles(self, files, asm_outputs): 88 # New Android.bp format 89 with open('sources.bp', 'w+') as blueprint: 90 blueprint.write(self.header.replace('#', '//')) 91 92 # Separate out BCM files to allow different compilation rules (specific to Android FIPS) 93 bcm_c_files = files['bcm_crypto'] 94 non_bcm_c_files = [file for file in files['crypto'] if file not in bcm_c_files] 95 non_bcm_asm = self.FilterBcmAsm(asm_outputs, False) 96 bcm_asm = self.FilterBcmAsm(asm_outputs, True) 97 98 self.PrintDefaults(blueprint, 'libcrypto_sources', non_bcm_c_files, non_bcm_asm) 99 self.PrintDefaults(blueprint, 'libcrypto_bcm_sources', bcm_c_files, bcm_asm) 100 self.PrintDefaults(blueprint, 'libssl_sources', files['ssl']) 101 self.PrintDefaults(blueprint, 'bssl_sources', files['tool']) 102 self.PrintDefaults(blueprint, 'boringssl_test_support_sources', files['test_support']) 103 self.PrintDefaults(blueprint, 'boringssl_crypto_test_sources', files['crypto_test']) 104 self.PrintDefaults(blueprint, 'boringssl_ssl_test_sources', files['ssl_test']) 105 106 # Legacy Android.mk format, only used by Trusty in new branches 107 with open('sources.mk', 'w+') as makefile: 108 makefile.write(self.header) 109 makefile.write('\n') 110 self.PrintVariableSection(makefile, 'crypto_sources', files['crypto']) 111 112 for ((osname, arch), asm_files) in asm_outputs: 113 if osname != 'linux': 114 continue 115 self.PrintVariableSection( 116 makefile, '%s_%s_sources' % (osname, arch), asm_files) 117 118 def PrintDefaults(self, blueprint, name, files, asm_outputs={}): 119 """Print a cc_defaults section from a list of C files and optionally assembly outputs""" 120 blueprint.write('\n') 121 blueprint.write('cc_defaults {\n') 122 blueprint.write(' name: "%s",\n' % name) 123 blueprint.write(' srcs: [\n') 124 for f in sorted(files): 125 blueprint.write(' "%s",\n' % f) 126 blueprint.write(' ],\n') 127 128 if asm_outputs: 129 blueprint.write(' target: {\n') 130 for ((osname, arch), asm_files) in asm_outputs: 131 if osname != 'linux' or arch == 'ppc64le': 132 continue 133 if arch == 'aarch64': 134 arch = 'arm64' 135 136 blueprint.write(' linux_%s: {\n' % arch) 137 blueprint.write(' srcs: [\n') 138 for f in sorted(asm_files): 139 blueprint.write(' "%s",\n' % f) 140 blueprint.write(' ],\n') 141 blueprint.write(' },\n') 142 blueprint.write(' },\n') 143 144 blueprint.write('}\n') 145 146 def FilterBcmAsm(self, asm, want_bcm): 147 """Filter a list of assembly outputs based on whether they belong in BCM 148 149 Args: 150 asm: Assembly file lists to filter 151 want_bcm: If true then include BCM files, otherwise do not 152 153 Returns: 154 A copy of |asm| with files filtered according to |want_bcm| 155 """ 156 return [(archinfo, filter(lambda p: ("/crypto/fipsmodule/" in p) == want_bcm, files)) 157 for (archinfo, files) in asm] 158 159 160class AndroidCMake(object): 161 162 def __init__(self): 163 self.header = \ 164"""# Copyright (C) 2019 The Android Open Source Project 165# 166# Licensed under the Apache License, Version 2.0 (the "License"); 167# you may not use this file except in compliance with the License. 168# You may obtain a copy of the License at 169# 170# http://www.apache.org/licenses/LICENSE-2.0 171# 172# Unless required by applicable law or agreed to in writing, software 173# distributed under the License is distributed on an "AS IS" BASIS, 174# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 175# See the License for the specific language governing permissions and 176# limitations under the License. 177 178# This file is created by generate_build_files.py. Do not edit manually. 179# To specify a custom path prefix, set BORINGSSL_ROOT before including this 180# file, or use list(TRANSFORM ... PREPEND) from CMake 3.12. 181 182""" 183 184 def PrintVariableSection(self, out, name, files): 185 out.write('set(%s\n' % name) 186 for f in sorted(files): 187 # Ideally adding the prefix would be the caller's job, but 188 # list(TRANSFORM ... PREPEND) is only available starting CMake 3.12. When 189 # sources.cmake is the source of truth, we can ask Android to either write 190 # a CMake function or update to 3.12. 191 out.write(' ${BORINGSSL_ROOT}%s\n' % f) 192 out.write(')\n') 193 194 def WriteFiles(self, files, asm_outputs): 195 # The Android emulator uses a custom CMake buildsystem. 196 # 197 # TODO(davidben): Move our various source lists into sources.cmake and have 198 # Android consume that directly. 199 with open('android-sources.cmake', 'w+') as out: 200 out.write(self.header) 201 202 self.PrintVariableSection(out, 'crypto_sources', files['crypto']) 203 self.PrintVariableSection(out, 'ssl_sources', files['ssl']) 204 self.PrintVariableSection(out, 'tool_sources', files['tool']) 205 self.PrintVariableSection(out, 'test_support_sources', 206 files['test_support']) 207 self.PrintVariableSection(out, 'crypto_test_sources', 208 files['crypto_test']) 209 self.PrintVariableSection(out, 'ssl_test_sources', files['ssl_test']) 210 211 for ((osname, arch), asm_files) in asm_outputs: 212 self.PrintVariableSection( 213 out, 'crypto_sources_%s_%s' % (osname, arch), asm_files) 214 215 216class Bazel(object): 217 """Bazel outputs files suitable for including in Bazel files.""" 218 219 def __init__(self): 220 self.firstSection = True 221 self.header = \ 222"""# This file is created by generate_build_files.py. Do not edit manually. 223 224""" 225 226 def PrintVariableSection(self, out, name, files): 227 if not self.firstSection: 228 out.write('\n') 229 self.firstSection = False 230 231 out.write('%s = [\n' % name) 232 for f in sorted(files): 233 out.write(' "%s",\n' % PathOf(f)) 234 out.write(']\n') 235 236 def WriteFiles(self, files, asm_outputs): 237 with open('BUILD.generated.bzl', 'w+') as out: 238 out.write(self.header) 239 240 self.PrintVariableSection(out, 'ssl_headers', files['ssl_headers']) 241 self.PrintVariableSection(out, 'fips_fragments', files['fips_fragments']) 242 self.PrintVariableSection( 243 out, 'ssl_internal_headers', files['ssl_internal_headers']) 244 self.PrintVariableSection(out, 'ssl_sources', files['ssl']) 245 self.PrintVariableSection(out, 'crypto_headers', files['crypto_headers']) 246 self.PrintVariableSection( 247 out, 'crypto_internal_headers', files['crypto_internal_headers']) 248 self.PrintVariableSection(out, 'crypto_sources', files['crypto']) 249 self.PrintVariableSection(out, 'tool_sources', files['tool']) 250 self.PrintVariableSection(out, 'tool_headers', files['tool_headers']) 251 252 for ((osname, arch), asm_files) in asm_outputs: 253 self.PrintVariableSection( 254 out, 'crypto_sources_%s_%s' % (osname, arch), asm_files) 255 256 with open('BUILD.generated_tests.bzl', 'w+') as out: 257 out.write(self.header) 258 259 out.write('test_support_sources = [\n') 260 for filename in sorted(files['test_support'] + 261 files['test_support_headers'] + 262 files['crypto_internal_headers'] + 263 files['ssl_internal_headers']): 264 if os.path.basename(filename) == 'malloc.cc': 265 continue 266 out.write(' "%s",\n' % PathOf(filename)) 267 268 out.write(']\n') 269 270 self.PrintVariableSection(out, 'crypto_test_sources', 271 files['crypto_test']) 272 self.PrintVariableSection(out, 'ssl_test_sources', files['ssl_test']) 273 self.PrintVariableSection(out, 'crypto_test_data', 274 files['crypto_test_data']) 275 self.PrintVariableSection(out, 'urandom_test_sources', 276 files['urandom_test']) 277 278 279class Eureka(object): 280 281 def __init__(self): 282 self.header = \ 283"""# Copyright (C) 2017 The Android Open Source Project 284# 285# Licensed under the Apache License, Version 2.0 (the "License"); 286# you may not use this file except in compliance with the License. 287# You may obtain a copy of the License at 288# 289# http://www.apache.org/licenses/LICENSE-2.0 290# 291# Unless required by applicable law or agreed to in writing, software 292# distributed under the License is distributed on an "AS IS" BASIS, 293# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 294# See the License for the specific language governing permissions and 295# limitations under the License. 296 297# This file is created by generate_build_files.py. Do not edit manually. 298 299""" 300 301 def PrintVariableSection(self, out, name, files): 302 out.write('%s := \\\n' % name) 303 for f in sorted(files): 304 out.write(' %s\\\n' % f) 305 out.write('\n') 306 307 def WriteFiles(self, files, asm_outputs): 308 # Legacy Android.mk format 309 with open('eureka.mk', 'w+') as makefile: 310 makefile.write(self.header) 311 312 self.PrintVariableSection(makefile, 'crypto_sources', files['crypto']) 313 self.PrintVariableSection(makefile, 'ssl_sources', files['ssl']) 314 self.PrintVariableSection(makefile, 'tool_sources', files['tool']) 315 316 for ((osname, arch), asm_files) in asm_outputs: 317 if osname != 'linux': 318 continue 319 self.PrintVariableSection( 320 makefile, '%s_%s_sources' % (osname, arch), asm_files) 321 322 323class GN(object): 324 325 def __init__(self): 326 self.firstSection = True 327 self.header = \ 328"""# Copyright (c) 2016 The Chromium Authors. All rights reserved. 329# Use of this source code is governed by a BSD-style license that can be 330# found in the LICENSE file. 331 332# This file is created by generate_build_files.py. Do not edit manually. 333 334""" 335 336 def PrintVariableSection(self, out, name, files): 337 if not self.firstSection: 338 out.write('\n') 339 self.firstSection = False 340 341 out.write('%s = [\n' % name) 342 for f in sorted(files): 343 out.write(' "%s",\n' % f) 344 out.write(']\n') 345 346 def WriteFiles(self, files, asm_outputs): 347 with open('BUILD.generated.gni', 'w+') as out: 348 out.write(self.header) 349 350 self.PrintVariableSection(out, 'crypto_sources', 351 files['crypto'] + 352 files['crypto_internal_headers']) 353 self.PrintVariableSection(out, 'crypto_headers', 354 files['crypto_headers']) 355 self.PrintVariableSection(out, 'ssl_sources', 356 files['ssl'] + files['ssl_internal_headers']) 357 self.PrintVariableSection(out, 'ssl_headers', files['ssl_headers']) 358 359 for ((osname, arch), asm_files) in asm_outputs: 360 self.PrintVariableSection( 361 out, 'crypto_sources_%s_%s' % (osname, arch), asm_files) 362 363 fuzzers = [os.path.splitext(os.path.basename(fuzzer))[0] 364 for fuzzer in files['fuzz']] 365 self.PrintVariableSection(out, 'fuzzers', fuzzers) 366 367 with open('BUILD.generated_tests.gni', 'w+') as out: 368 self.firstSection = True 369 out.write(self.header) 370 371 self.PrintVariableSection(out, 'test_support_sources', 372 files['test_support'] + 373 files['test_support_headers']) 374 self.PrintVariableSection(out, 'crypto_test_sources', 375 files['crypto_test']) 376 self.PrintVariableSection(out, 'crypto_test_data', 377 files['crypto_test_data']) 378 self.PrintVariableSection(out, 'ssl_test_sources', files['ssl_test']) 379 380 381class GYP(object): 382 383 def __init__(self): 384 self.header = \ 385"""# Copyright (c) 2016 The Chromium Authors. All rights reserved. 386# Use of this source code is governed by a BSD-style license that can be 387# found in the LICENSE file. 388 389# This file is created by generate_build_files.py. Do not edit manually. 390 391""" 392 393 def PrintVariableSection(self, out, name, files): 394 out.write(' \'%s\': [\n' % name) 395 for f in sorted(files): 396 out.write(' \'%s\',\n' % f) 397 out.write(' ],\n') 398 399 def WriteFiles(self, files, asm_outputs): 400 with open('boringssl.gypi', 'w+') as gypi: 401 gypi.write(self.header + '{\n \'variables\': {\n') 402 403 self.PrintVariableSection(gypi, 'boringssl_ssl_sources', 404 files['ssl'] + files['ssl_headers'] + 405 files['ssl_internal_headers']) 406 self.PrintVariableSection(gypi, 'boringssl_crypto_sources', 407 files['crypto'] + files['crypto_headers'] + 408 files['crypto_internal_headers']) 409 410 for ((osname, arch), asm_files) in asm_outputs: 411 self.PrintVariableSection(gypi, 'boringssl_%s_%s_sources' % 412 (osname, arch), asm_files) 413 414 gypi.write(' }\n}\n') 415 416 417def FindCMakeFiles(directory): 418 """Returns list of all CMakeLists.txt files recursively in directory.""" 419 cmakefiles = [] 420 421 for (path, _, filenames) in os.walk(directory): 422 for filename in filenames: 423 if filename == 'CMakeLists.txt': 424 cmakefiles.append(os.path.join(path, filename)) 425 426 return cmakefiles 427 428def OnlyFIPSFragments(path, dent, is_dir): 429 return is_dir or (path.startswith( 430 os.path.join('src', 'crypto', 'fipsmodule', '')) and 431 NoTests(path, dent, is_dir)) 432 433def NoTestsNorFIPSFragments(path, dent, is_dir): 434 return (NoTests(path, dent, is_dir) and 435 (is_dir or not OnlyFIPSFragments(path, dent, is_dir))) 436 437def NoTests(path, dent, is_dir): 438 """Filter function that can be passed to FindCFiles in order to remove test 439 sources.""" 440 if is_dir: 441 return dent != 'test' 442 return 'test.' not in dent 443 444 445def OnlyTests(path, dent, is_dir): 446 """Filter function that can be passed to FindCFiles in order to remove 447 non-test sources.""" 448 if is_dir: 449 return dent != 'test' 450 return '_test.' in dent 451 452 453def AllFiles(path, dent, is_dir): 454 """Filter function that can be passed to FindCFiles in order to include all 455 sources.""" 456 return True 457 458 459def NoTestRunnerFiles(path, dent, is_dir): 460 """Filter function that can be passed to FindCFiles or FindHeaderFiles in 461 order to exclude test runner files.""" 462 # NOTE(martinkr): This prevents .h/.cc files in src/ssl/test/runner, which 463 # are in their own subpackage, from being included in boringssl/BUILD files. 464 return not is_dir or dent != 'runner' 465 466 467def NotGTestSupport(path, dent, is_dir): 468 return 'gtest' not in dent and 'abi_test' not in dent 469 470 471def SSLHeaderFiles(path, dent, is_dir): 472 return dent in ['ssl.h', 'tls1.h', 'ssl23.h', 'ssl3.h', 'dtls1.h', 'srtp.h'] 473 474 475def FindCFiles(directory, filter_func): 476 """Recurses through directory and returns a list of paths to all the C source 477 files that pass filter_func.""" 478 cfiles = [] 479 480 for (path, dirnames, filenames) in os.walk(directory): 481 for filename in filenames: 482 if not filename.endswith('.c') and not filename.endswith('.cc'): 483 continue 484 if not filter_func(path, filename, False): 485 continue 486 cfiles.append(os.path.join(path, filename)) 487 488 for (i, dirname) in enumerate(dirnames): 489 if not filter_func(path, dirname, True): 490 del dirnames[i] 491 492 return cfiles 493 494 495def FindHeaderFiles(directory, filter_func): 496 """Recurses through directory and returns a list of paths to all the header files that pass filter_func.""" 497 hfiles = [] 498 499 for (path, dirnames, filenames) in os.walk(directory): 500 for filename in filenames: 501 if not filename.endswith('.h'): 502 continue 503 if not filter_func(path, filename, False): 504 continue 505 hfiles.append(os.path.join(path, filename)) 506 507 for (i, dirname) in enumerate(dirnames): 508 if not filter_func(path, dirname, True): 509 del dirnames[i] 510 511 return hfiles 512 513 514def ExtractPerlAsmFromCMakeFile(cmakefile): 515 """Parses the contents of the CMakeLists.txt file passed as an argument and 516 returns a list of all the perlasm() directives found in the file.""" 517 perlasms = [] 518 with open(cmakefile) as f: 519 for line in f: 520 line = line.strip() 521 if not line.startswith('perlasm('): 522 continue 523 if not line.endswith(')'): 524 raise ValueError('Bad perlasm line in %s' % cmakefile) 525 # Remove "perlasm(" from start and ")" from end 526 params = line[8:-1].split() 527 if len(params) < 2: 528 raise ValueError('Bad perlasm line in %s' % cmakefile) 529 perlasms.append({ 530 'extra_args': params[2:], 531 'input': os.path.join(os.path.dirname(cmakefile), params[1]), 532 'output': os.path.join(os.path.dirname(cmakefile), params[0]), 533 }) 534 535 return perlasms 536 537 538def ReadPerlAsmOperations(): 539 """Returns a list of all perlasm() directives found in CMake config files in 540 src/.""" 541 perlasms = [] 542 cmakefiles = FindCMakeFiles('src') 543 544 for cmakefile in cmakefiles: 545 perlasms.extend(ExtractPerlAsmFromCMakeFile(cmakefile)) 546 547 return perlasms 548 549 550def PerlAsm(output_filename, input_filename, perlasm_style, extra_args): 551 """Runs the a perlasm script and puts the output into output_filename.""" 552 base_dir = os.path.dirname(output_filename) 553 if not os.path.isdir(base_dir): 554 os.makedirs(base_dir) 555 subprocess.check_call( 556 ['perl', input_filename, perlasm_style] + extra_args + [output_filename]) 557 558 559def ArchForAsmFilename(filename): 560 """Returns the architectures that a given asm file should be compiled for 561 based on substrings in the filename.""" 562 563 if 'x86_64' in filename or 'avx2' in filename: 564 return ['x86_64'] 565 elif ('x86' in filename and 'x86_64' not in filename) or '586' in filename: 566 return ['x86'] 567 elif 'armx' in filename: 568 return ['arm', 'aarch64'] 569 elif 'armv8' in filename: 570 return ['aarch64'] 571 elif 'arm' in filename: 572 return ['arm'] 573 elif 'ppc' in filename: 574 return ['ppc64le'] 575 else: 576 raise ValueError('Unknown arch for asm filename: ' + filename) 577 578 579def WriteAsmFiles(perlasms): 580 """Generates asm files from perlasm directives for each supported OS x 581 platform combination.""" 582 asmfiles = {} 583 584 for osarch in OS_ARCH_COMBOS: 585 (osname, arch, perlasm_style, extra_args, asm_ext) = osarch 586 key = (osname, arch) 587 outDir = '%s-%s' % key 588 589 for perlasm in perlasms: 590 filename = os.path.basename(perlasm['input']) 591 output = perlasm['output'] 592 if not output.startswith('src'): 593 raise ValueError('output missing src: %s' % output) 594 output = os.path.join(outDir, output[4:]) 595 if output.endswith('-armx.${ASM_EXT}'): 596 output = output.replace('-armx', 597 '-armx64' if arch == 'aarch64' else '-armx32') 598 output = output.replace('${ASM_EXT}', asm_ext) 599 600 if arch in ArchForAsmFilename(filename): 601 PerlAsm(output, perlasm['input'], perlasm_style, 602 perlasm['extra_args'] + extra_args) 603 asmfiles.setdefault(key, []).append(output) 604 605 for (key, non_perl_asm_files) in NON_PERL_FILES.iteritems(): 606 asmfiles.setdefault(key, []).extend(non_perl_asm_files) 607 608 return asmfiles 609 610 611def ExtractVariablesFromCMakeFile(cmakefile): 612 """Parses the contents of the CMakeLists.txt file passed as an argument and 613 returns a dictionary of exported source lists.""" 614 variables = {} 615 in_set_command = False 616 set_command = [] 617 with open(cmakefile) as f: 618 for line in f: 619 if '#' in line: 620 line = line[:line.index('#')] 621 line = line.strip() 622 623 if not in_set_command: 624 if line.startswith('set('): 625 in_set_command = True 626 set_command = [] 627 elif line == ')': 628 in_set_command = False 629 if not set_command: 630 raise ValueError('Empty set command') 631 variables[set_command[0]] = set_command[1:] 632 else: 633 set_command.extend([c for c in line.split(' ') if c]) 634 635 if in_set_command: 636 raise ValueError('Unfinished set command') 637 return variables 638 639 640def main(platforms): 641 cmake = ExtractVariablesFromCMakeFile(os.path.join('src', 'sources.cmake')) 642 crypto_c_files = (FindCFiles(os.path.join('src', 'crypto'), NoTestsNorFIPSFragments) + 643 FindCFiles(os.path.join('src', 'third_party', 'fiat'), NoTestsNorFIPSFragments)) 644 fips_fragments = FindCFiles(os.path.join('src', 'crypto', 'fipsmodule'), OnlyFIPSFragments) 645 ssl_source_files = FindCFiles(os.path.join('src', 'ssl'), NoTests) 646 tool_c_files = FindCFiles(os.path.join('src', 'tool'), NoTests) 647 tool_h_files = FindHeaderFiles(os.path.join('src', 'tool'), AllFiles) 648 649 # third_party/fiat/p256.c lives in third_party/fiat, but it is a FIPS 650 # fragment, not a normal source file. 651 p256 = os.path.join('src', 'third_party', 'fiat', 'p256.c') 652 fips_fragments.append(p256) 653 crypto_c_files.remove(p256) 654 655 # BCM shared library C files 656 bcm_crypto_c_files = [ 657 os.path.join('src', 'crypto', 'fipsmodule', 'bcm.c') 658 ] 659 660 # Generate err_data.c 661 with open('err_data.c', 'w+') as err_data: 662 subprocess.check_call(['go', 'run', 'err_data_generate.go'], 663 cwd=os.path.join('src', 'crypto', 'err'), 664 stdout=err_data) 665 crypto_c_files.append('err_data.c') 666 667 test_support_c_files = FindCFiles(os.path.join('src', 'crypto', 'test'), 668 NotGTestSupport) 669 test_support_h_files = ( 670 FindHeaderFiles(os.path.join('src', 'crypto', 'test'), AllFiles) + 671 FindHeaderFiles(os.path.join('src', 'ssl', 'test'), NoTestRunnerFiles)) 672 673 crypto_test_files = [] 674 if EMBED_TEST_DATA: 675 # Generate crypto_test_data.cc 676 with open('crypto_test_data.cc', 'w+') as out: 677 subprocess.check_call( 678 ['go', 'run', 'util/embed_test_data.go'] + cmake['CRYPTO_TEST_DATA'], 679 cwd='src', 680 stdout=out) 681 crypto_test_files += ['crypto_test_data.cc'] 682 683 crypto_test_files += FindCFiles(os.path.join('src', 'crypto'), OnlyTests) 684 crypto_test_files += [ 685 'src/crypto/test/abi_test.cc', 686 'src/crypto/test/file_test_gtest.cc', 687 'src/crypto/test/gtest_main.cc', 688 ] 689 # urandom_test.cc is in a separate binary so that it can be test PRNG 690 # initialisation. 691 crypto_test_files = [ 692 file for file in crypto_test_files 693 if not file.endswith('/urandom_test.cc') 694 ] 695 696 ssl_test_files = FindCFiles(os.path.join('src', 'ssl'), OnlyTests) 697 ssl_test_files += [ 698 'src/crypto/test/abi_test.cc', 699 'src/crypto/test/gtest_main.cc', 700 ] 701 702 urandom_test_files = [ 703 'src/crypto/fipsmodule/rand/urandom_test.cc', 704 ] 705 706 fuzz_c_files = FindCFiles(os.path.join('src', 'fuzz'), NoTests) 707 708 ssl_h_files = ( 709 FindHeaderFiles( 710 os.path.join('src', 'include', 'openssl'), 711 SSLHeaderFiles)) 712 713 def NotSSLHeaderFiles(path, filename, is_dir): 714 return not SSLHeaderFiles(path, filename, is_dir) 715 crypto_h_files = ( 716 FindHeaderFiles( 717 os.path.join('src', 'include', 'openssl'), 718 NotSSLHeaderFiles)) 719 720 ssl_internal_h_files = FindHeaderFiles(os.path.join('src', 'ssl'), NoTests) 721 crypto_internal_h_files = ( 722 FindHeaderFiles(os.path.join('src', 'crypto'), NoTests) + 723 FindHeaderFiles(os.path.join('src', 'third_party', 'fiat'), NoTests)) 724 725 files = { 726 'bcm_crypto': bcm_crypto_c_files, 727 'crypto': crypto_c_files, 728 'crypto_headers': crypto_h_files, 729 'crypto_internal_headers': crypto_internal_h_files, 730 'crypto_test': sorted(crypto_test_files), 731 'crypto_test_data': sorted('src/' + x for x in cmake['CRYPTO_TEST_DATA']), 732 'fips_fragments': fips_fragments, 733 'fuzz': fuzz_c_files, 734 'ssl': ssl_source_files, 735 'ssl_headers': ssl_h_files, 736 'ssl_internal_headers': ssl_internal_h_files, 737 'ssl_test': sorted(ssl_test_files), 738 'tool': tool_c_files, 739 'tool_headers': tool_h_files, 740 'test_support': test_support_c_files, 741 'test_support_headers': test_support_h_files, 742 'urandom_test': sorted(urandom_test_files), 743 } 744 745 asm_outputs = sorted(WriteAsmFiles(ReadPerlAsmOperations()).iteritems()) 746 747 for platform in platforms: 748 platform.WriteFiles(files, asm_outputs) 749 750 return 0 751 752 753if __name__ == '__main__': 754 parser = optparse.OptionParser(usage='Usage: %prog [--prefix=<path>]' 755 ' [android|android-cmake|bazel|eureka|gn|gyp]') 756 parser.add_option('--prefix', dest='prefix', 757 help='For Bazel, prepend argument to all source files') 758 parser.add_option( 759 '--embed_test_data', type='choice', dest='embed_test_data', 760 action='store', default="true", choices=["true", "false"], 761 help='For Bazel or GN, don\'t embed data files in crypto_test_data.cc') 762 options, args = parser.parse_args(sys.argv[1:]) 763 PREFIX = options.prefix 764 EMBED_TEST_DATA = (options.embed_test_data == "true") 765 766 if not args: 767 parser.print_help() 768 sys.exit(1) 769 770 platforms = [] 771 for s in args: 772 if s == 'android': 773 platforms.append(Android()) 774 elif s == 'android-cmake': 775 platforms.append(AndroidCMake()) 776 elif s == 'bazel': 777 platforms.append(Bazel()) 778 elif s == 'eureka': 779 platforms.append(Eureka()) 780 elif s == 'gn': 781 platforms.append(GN()) 782 elif s == 'gyp': 783 platforms.append(GYP()) 784 else: 785 parser.print_help() 786 sys.exit(1) 787 788 sys.exit(main(platforms)) 789