Changes in tools/autotool.py [2660ee3:a35b458] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
tools/autotool.py
r2660ee3 ra35b458 93 93 def read_config(fname, config): 94 94 "Read HelenOS build configuration" 95 95 96 96 inf = open(fname, 'r') 97 97 98 98 for line in inf: 99 99 res = re.match(r'^(?:#!# )?([^#]\w*)\s*=\s*(.*?)\s*$', line) 100 100 if (res): 101 101 config[res.group(1)] = res.group(2) 102 102 103 103 inf.close() 104 104 105 105 def print_error(msg): 106 106 "Print a bold error message" 107 107 108 108 sys.stderr.write("\n") 109 109 sys.stderr.write("######################################################################\n") … … 113 113 sys.stderr.write("######################################################################\n") 114 114 sys.stderr.write("\n") 115 115 116 116 sys.exit(1) 117 117 118 118 def print_warning(msg): 119 119 "Print a bold error message" 120 120 121 121 sys.stderr.write("\n") 122 122 sys.stderr.write("######################################################################\n") … … 126 126 sys.stderr.write("######################################################################\n") 127 127 sys.stderr.write("\n") 128 128 129 129 time.sleep(5) 130 130 131 131 def sandbox_enter(): 132 132 "Create a temporal sandbox directory for running tests" 133 133 134 134 if (os.path.exists(SANDBOX)): 135 135 if (os.path.isdir(SANDBOX)): … … 141 141 print_error(["Please inspect and remove unexpected directory,", 142 142 "entry \"%s\"." % SANDBOX]) 143 143 144 144 try: 145 145 os.mkdir(SANDBOX) 146 146 except: 147 147 print_error(["Unable to create sandbox directory \"%s\"." % SANDBOX]) 148 148 149 149 owd = os.getcwd() 150 150 os.chdir(SANDBOX) 151 151 152 152 return owd 153 153 154 154 def sandbox_leave(owd): 155 155 "Leave the temporal sandbox directory" 156 156 157 157 os.chdir(owd) 158 158 159 159 def check_config(config, key): 160 160 "Check whether the configuration key exists" 161 161 162 162 if (not key in config): 163 163 print_error(["Build configuration of HelenOS does not contain %s." % key, … … 167 167 def check_common(common, key): 168 168 "Check whether the common key exists" 169 169 170 170 if (not key in common): 171 171 print_error(["Failed to determine the value %s." % key, … … 178 178 target = None 179 179 cc_args = [] 180 180 181 181 if (config['PLATFORM'] == "abs32le"): 182 182 check_config(config, "CROSS_TARGET") 183 183 platform = config['CROSS_TARGET'] 184 184 185 185 if (config['CROSS_TARGET'] == "arm32"): 186 186 gnu_target = "arm-linux-gnueabi" 187 187 helenos_target = "arm-helenos-gnueabi" 188 188 189 189 if (config['CROSS_TARGET'] == "ia32"): 190 190 gnu_target = "i686-pc-linux-gnu" 191 191 helenos_target = "i686-pc-helenos" 192 192 193 193 if (config['CROSS_TARGET'] == "mips32"): 194 194 cc_args.append("-mabi=32") 195 195 gnu_target = "mipsel-linux-gnu" 196 196 helenos_target = "mipsel-helenos" 197 197 198 198 if (config['PLATFORM'] == "amd64"): 199 199 platform = config['PLATFORM'] 200 200 gnu_target = "amd64-unknown-elf" 201 201 helenos_target = "amd64-helenos" 202 202 203 203 if (config['PLATFORM'] == "arm32"): 204 204 platform = config['PLATFORM'] 205 205 gnu_target = "arm-linux-gnueabi" 206 206 helenos_target = "arm-helenos-gnueabi" 207 207 208 208 if (config['PLATFORM'] == "ia32"): 209 209 platform = config['PLATFORM'] 210 210 gnu_target = "i686-pc-linux-gnu" 211 211 helenos_target = "i686-pc-helenos" 212 212 213 213 if (config['PLATFORM'] == "ia64"): 214 214 platform = config['PLATFORM'] 215 215 gnu_target = "ia64-pc-linux-gnu" 216 216 helenos_target = "ia64-pc-helenos" 217 217 218 218 if (config['PLATFORM'] == "mips32"): 219 219 check_config(config, "MACHINE") 220 220 cc_args.append("-mabi=32") 221 221 222 222 if ((config['MACHINE'] == "msim") or (config['MACHINE'] == "lmalta")): 223 223 platform = config['PLATFORM'] 224 224 gnu_target = "mipsel-linux-gnu" 225 225 helenos_target = "mipsel-helenos" 226 226 227 227 if ((config['MACHINE'] == "bmalta")): 228 228 platform = "mips32eb" 229 229 gnu_target = "mips-linux-gnu" 230 230 helenos_target = "mips-helenos" 231 231 232 232 if (config['PLATFORM'] == "mips64"): 233 233 check_config(config, "MACHINE") 234 234 cc_args.append("-mabi=64") 235 235 236 236 if (config['MACHINE'] == "msim"): 237 237 platform = config['PLATFORM'] 238 238 gnu_target = "mips64el-linux-gnu" 239 239 helenos_target = "mips64el-helenos" 240 240 241 241 if (config['PLATFORM'] == "ppc32"): 242 242 platform = config['PLATFORM'] 243 243 gnu_target = "ppc-linux-gnu" 244 244 helenos_target = "ppc-helenos" 245 245 246 246 if (config['PLATFORM'] == "riscv64"): 247 247 platform = config['PLATFORM'] 248 248 gnu_target = "riscv64-unknown-linux-gnu" 249 249 helenos_target = "riscv64-helenos" 250 250 251 251 if (config['PLATFORM'] == "sparc64"): 252 252 platform = config['PLATFORM'] 253 253 gnu_target = "sparc64-linux-gnu" 254 254 helenos_target = "sparc64-helenos" 255 255 256 256 if (config['COMPILER'] == "gcc_helenos"): 257 257 target = helenos_target 258 258 else: 259 259 target = gnu_target 260 260 261 261 return (platform, cc_args, target) 262 262 263 263 def check_app(args, name, details): 264 264 "Check whether an application can be executed" 265 265 266 266 try: 267 267 sys.stderr.write("Checking for %s ... " % args[0]) … … 273 273 "Execution of \"%s\" has failed. Please make sure that it" % " ".join(args), 274 274 "is installed in your system (%s)." % details]) 275 275 276 276 sys.stderr.write("ok\n") 277 277 278 278 def check_app_alternatives(alts, args, name, details): 279 279 "Check whether an application can be executed (use several alternatives)" 280 280 281 281 tried = [] 282 282 found = None 283 283 284 284 for alt in alts: 285 285 working = True 286 286 cmdline = [alt] + args 287 287 tried.append(" ".join(cmdline)) 288 288 289 289 try: 290 290 sys.stderr.write("Checking for %s ... " % alt) … … 293 293 sys.stderr.write("failed\n") 294 294 working = False 295 295 296 296 if (working): 297 297 sys.stderr.write("ok\n") 298 298 found = alt 299 299 break 300 300 301 301 if (found is None): 302 302 print_error(["%s is missing." % name, … … 306 306 "", 307 307 "The following alternatives were tried:"] + tried) 308 308 309 309 return found 310 310 311 311 def check_clang(path, prefix, common, details): 312 312 "Check for clang" 313 313 314 314 common['CLANG'] = "%sclang" % prefix 315 315 316 316 if (not path is None): 317 317 common['CLANG'] = "%s/%s" % (path, common['CLANG']) 318 318 319 319 check_app([common['CLANG'], "--version"], "clang", details) 320 320 321 321 def check_gcc(path, prefix, common, details): 322 322 "Check for GCC" 323 323 324 324 common['GCC'] = "%sgcc" % prefix 325 325 326 326 if (not path is None): 327 327 common['GCC'] = "%s/%s" % (path, common['GCC']) 328 328 329 329 check_app([common['GCC'], "--version"], "GNU GCC", details) 330 330 331 331 def check_binutils(path, prefix, common, details): 332 332 "Check for binutils toolchain" 333 333 334 334 common['AS'] = "%sas" % prefix 335 335 common['LD'] = "%sld" % prefix … … 338 338 common['OBJDUMP'] = "%sobjdump" % prefix 339 339 common['STRIP'] = "%sstrip" % prefix 340 340 341 341 if (not path is None): 342 342 for key in ["AS", "LD", "AR", "OBJCOPY", "OBJDUMP", "STRIP"]: 343 343 common[key] = "%s/%s" % (path, common[key]) 344 344 345 345 check_app([common['AS'], "--version"], "GNU Assembler", details) 346 346 check_app([common['LD'], "--version"], "GNU Linker", details) … … 352 352 def check_python(): 353 353 "Check for Python dependencies" 354 354 355 355 try: 356 356 sys.stderr.write("Checking for PyYAML ... ") … … 361 361 "Please make sure that it is installed in your", 362 362 "system (usually part of PyYAML package)."]) 363 363 364 364 sys.stderr.write("ok\n") 365 365 366 366 def decode_value(value): 367 367 "Decode integer value" 368 368 369 369 base = 10 370 370 371 371 if ((value.startswith('$')) or (value.startswith('#'))): 372 372 value = value[1:] 373 373 374 374 if (value.startswith('0x')): 375 375 value = value[2:] 376 376 base = 16 377 377 378 378 return int(value, base) 379 379 380 380 def probe_compiler(common, typesizes): 381 381 "Generate, compile and parse probing source" 382 382 383 383 check_common(common, "CC") 384 384 385 385 outf = open(PROBE_SOURCE, 'w') 386 386 outf.write(PROBE_HEAD) 387 387 388 388 for typedef in typesizes: 389 389 if 'def' in typedef: … … 392 392 if 'def' in typedef: 393 393 outf.write("#endif\n") 394 394 395 395 outf.write(PROBE_TAIL) 396 396 outf.close() 397 397 398 398 args = common['CC_AUTOGEN'].split(' ') 399 399 args.extend(["-S", "-o", PROBE_OUTPUT, PROBE_SOURCE]) 400 400 401 401 try: 402 402 sys.stderr.write("Checking compiler properties ... ") … … 406 406 print_error(["Error executing \"%s\"." % " ".join(args), 407 407 "Make sure that the compiler works properly."]) 408 408 409 409 if (not os.path.isfile(PROBE_OUTPUT)): 410 410 sys.stderr.write("failed\n") … … 415 415 output[0], 416 416 output[1]]) 417 417 418 418 sys.stderr.write("ok\n") 419 419 420 420 inf = open(PROBE_OUTPUT, 'r') 421 421 lines = inf.readlines() 422 422 inf.close() 423 423 424 424 builtins = {} 425 425 426 426 for j in range(len(lines)): 427 427 tokens = lines[j].strip().split("\t") 428 428 429 429 if (len(tokens) > 0): 430 430 if (tokens[0] == "AUTOTOOL_DECLARE"): 431 431 if (len(tokens) < 8): 432 432 print_error(["Malformed declaration in \"%s\" on line %s." % (PROBE_OUTPUT, j), COMPILER_FAIL]) 433 433 434 434 category = tokens[1] 435 435 tag = tokens[2] … … 439 439 size = tokens[6] 440 440 compatible = tokens[7] 441 441 442 442 try: 443 443 compatible_int = decode_value(compatible) … … 445 445 except: 446 446 print_error(["Integer value expected in \"%s\" on line %s." % (PROBE_OUTPUT, j), COMPILER_FAIL]) 447 447 448 448 if (compatible_int == 1): 449 449 builtins[tag] = { … … 454 454 'size': size_int, 455 455 } 456 456 457 457 for typedef in typesizes: 458 458 if not typedef['tag'] in builtins: … … 461 461 if 'sname' in typedef: 462 462 builtins[typedef['tag']]['sname'] = typedef['sname'] 463 463 464 464 return builtins 465 465 … … 490 490 def detect_sizes(probe): 491 491 "Detect properties of builtin types" 492 492 493 493 macros = {} 494 494 495 495 for type in probe.values(): 496 496 macros['__SIZEOF_%s__' % type['tag']] = type['size'] 497 497 498 498 if ('sname' in type): 499 499 macros['__%s_TYPE__' % type['sname']] = type['name'] … … 502 502 macros['__%s_C_SUFFIX__' % type['sname']] = get_suffix(type) 503 503 macros['__%s_MAX__' % type['sname']] = "%d%s" % (get_max(type), get_suffix(type)) 504 504 505 505 if (probe['SIZE_T']['sign'] != 'unsigned'): 506 506 print_error(['The type size_t is not unsigned.', COMPILER_FAIL]) 507 507 508 508 return macros 509 509 510 510 def create_makefile(mkname, common): 511 511 "Create makefile output" 512 512 513 513 outmk = open(mkname, 'w') 514 514 515 515 outmk.write('#########################################\n') 516 516 outmk.write('## AUTO-GENERATED FILE, DO NOT EDIT!!! ##\n') 517 517 outmk.write('## Generated by: tools/autotool.py ##\n') 518 518 outmk.write('#########################################\n\n') 519 519 520 520 for key, value in common.items(): 521 521 if (type(value) is list): … … 523 523 else: 524 524 outmk.write('%s = %s\n' % (key, value)) 525 525 526 526 outmk.close() 527 527 528 528 def create_header(hdname, macros): 529 529 "Create header output" 530 530 531 531 outhd = open(hdname, 'w') 532 532 533 533 outhd.write('/***************************************\n') 534 534 outhd.write(' * AUTO-GENERATED FILE, DO NOT EDIT!!! *\n') 535 535 outhd.write(' * Generated by: tools/autotool.py *\n') 536 536 outhd.write(' ***************************************/\n\n') 537 537 538 538 outhd.write('#ifndef %s\n' % GUARD) 539 539 outhd.write('#define %s\n\n' % GUARD) 540 540 541 541 for macro in sorted(macros): 542 542 outhd.write('#ifndef %s\n' % macro) 543 543 outhd.write('#define %s %s\n' % (macro, macros[macro])) 544 544 outhd.write('#endif\n\n') 545 545 546 546 outhd.write('\n#endif\n') 547 547 outhd.close() … … 550 550 config = {} 551 551 common = {} 552 552 553 553 # Read and check configuration 554 554 if os.path.exists(CONFIG): … … 558 558 "configuration phase of HelenOS build went OK. Try running", 559 559 "\"make config\" again."]) 560 560 561 561 check_config(config, "PLATFORM") 562 562 check_config(config, "COMPILER") 563 563 check_config(config, "BARCH") 564 564 565 565 # Cross-compiler prefix 566 566 if ('CROSS_PREFIX' in os.environ): … … 568 568 else: 569 569 cross_prefix = "/usr/local/cross" 570 570 571 571 # HelenOS cross-compiler prefix 572 572 if ('CROSS_HELENOS_PREFIX' in os.environ): … … 574 574 else: 575 575 cross_helenos_prefix = "/usr/local/cross-helenos" 576 576 577 577 # Prefix binutils tools on Solaris 578 578 if (os.uname()[0] == "SunOS"): … … 580 580 else: 581 581 binutils_prefix = "" 582 582 583 583 owd = sandbox_enter() 584 584 585 585 try: 586 586 # Common utilities … … 593 593 check_app(["make", "--version"], "Make utility", "preferably GNU Make") 594 594 check_app(["unzip"], "unzip utility", "usually part of zip/unzip utilities") 595 595 596 596 platform, cc_args, target = get_target(config) 597 597 598 598 if (platform is None) or (target is None): 599 599 print_error(["Unsupported compiler target.", 600 600 "Please contact the developers of HelenOS."]) 601 601 602 602 path = "%s/%s/bin" % (cross_prefix, target) 603 603 604 604 # Compatibility with earlier toolchain paths. 605 605 if not os.path.exists(path): … … 614 614 print_error(["Toolchain for target is not installed, or CROSS_PREFIX is not set correctly."]) 615 615 path = "%s/%s/bin" % (cross_prefix, platform) 616 616 617 617 common['TARGET'] = target 618 618 prefix = "%s-" % target 619 619 620 620 # Compiler 621 621 if (config['COMPILER'] == "gcc_cross" or config['COMPILER'] == "gcc_helenos"): 622 622 check_gcc(path, prefix, common, PACKAGE_CROSS) 623 623 check_binutils(path, prefix, common, PACKAGE_CROSS) 624 624 625 625 check_common(common, "GCC") 626 626 common['CC'] = " ".join([common['GCC']] + cc_args) 627 627 common['CC_AUTOGEN'] = common['CC'] 628 628 629 629 if (config['COMPILER'] == "gcc_native"): 630 630 check_gcc(None, "", common, PACKAGE_GCC) 631 631 check_binutils(None, binutils_prefix, common, PACKAGE_BINUTILS) 632 632 633 633 check_common(common, "GCC") 634 634 common['CC'] = common['GCC'] 635 635 common['CC_AUTOGEN'] = common['CC'] 636 636 637 637 if (config['COMPILER'] == "clang"): 638 638 check_binutils(path, prefix, common, PACKAGE_CROSS) 639 639 check_clang(path, prefix, common, PACKAGE_CLANG) 640 640 641 641 check_common(common, "CLANG") 642 642 common['CC'] = " ".join([common['CLANG']] + cc_args) 643 643 common['CC_AUTOGEN'] = common['CC'] + " -no-integrated-as" 644 644 645 645 if (config['INTEGRATED_AS'] == "yes"): 646 646 common['CC'] += " -integrated-as" 647 647 648 648 if (config['INTEGRATED_AS'] == "no"): 649 649 common['CC'] += " -no-integrated-as" 650 650 651 651 check_python() 652 652 653 653 # Platform-specific utilities 654 654 if ((config['BARCH'] == "amd64") or (config['BARCH'] == "ia32") or (config['BARCH'] == "ppc32") or (config['BARCH'] == "sparc64")): … … 656 656 if common['GENISOIMAGE'] == 'xorriso': 657 657 common['GENISOIMAGE'] += ' -as genisoimage' 658 658 659 659 probe = probe_compiler(common, 660 660 [ … … 675 675 ] 676 676 ) 677 677 678 678 macros = detect_sizes(probe) 679 679 680 680 finally: 681 681 sandbox_leave(owd) 682 682 683 683 common['AUTOGEN'] = "%s/autogen.py" % os.path.dirname(os.path.abspath(sys.argv[0])) 684 684 685 685 create_makefile(MAKEFILE, common) 686 686 create_header(HEADER, macros) 687 687 688 688 return 0 689 689
Note:
See TracChangeset
for help on using the changeset viewer.