OLD | NEW |
(Empty) | |
| 1 # -*- python -*- |
| 2 # Copyright 2010 The Native Client Authors. All rights reserved. Use |
| 3 # of this source code is governed by a BSD-style license that can be |
| 4 # found in the LICENSE file. |
| 5 |
| 6 Import('env') |
| 7 |
| 8 # So far, all tests involve native assembler |
| 9 |
| 10 HALT_SLED_SIZE=32 |
| 11 |
| 12 |
| 13 # ---------------------------------------------------------- |
| 14 # Tests that require a NaCl module |
| 15 # ---------------------------------------------------------- |
| 16 |
| 17 if env['TARGET_ARCHITECTURE'] == 'x86': |
| 18 arch_dir = ('arch/' + env['TARGET_ARCHITECTURE'] + |
| 19 '_' + env['TARGET_SUBARCH']) |
| 20 nacl_text_pad_asm = (arch_dir + |
| 21 '/nacl_text_pad_test.S') |
| 22 elif env['TARGET_ARCHITECTURE'] == 'arm': |
| 23 arch_dir = 'arch/' + env['TARGET_ARCHITECTURE'] |
| 24 nacl_text_pad_asm = ( arch_dir + |
| 25 '/nacl_text_pad_test.S') |
| 26 else: |
| 27 raise Exception, 'unknown architecture' |
| 28 |
| 29 def NewAsmEnv(env, *alist, **kwarg): |
| 30 asm_env = env.Clone() |
| 31 if ARGUMENTS.get('bitcode'): |
| 32 asm_env.Replace(CC=env['CC_NATIVE']) |
| 33 if env['TARGET_ARCHITECTURE'] == 'x86': |
| 34 if env['TARGET_SUBARCH'] == '32': |
| 35 asm_env['LINKCOM'] = ('${LD} -melf_nacl -e _start ${RO_START}' + |
| 36 ' ${RW_START} -o ${TARGET} ${SOURCES}') |
| 37 elif env['TARGET_SUBARCH'] == '64': |
| 38 asm_env['LINKCOM'] = ('${LD} -melf64_nacl -e _start ${RO_START}' + |
| 39 ' ${RW_START} -o ${TARGET} ${SOURCES}') |
| 40 else: |
| 41 raise Exception, 'new subarchtecture for x86?!?' |
| 42 elif env['TARGET_ARCHITECTURE'] == 'arm': |
| 43 asm_env['LINKCOM'] = ('${LD} --native-client -e _start -Ttext 0x20000' + |
| 44 ' -nostdlib -static' + |
| 45 ' ${RO_START} ${RW_START} -o ${TARGET} ${SOURCES}' + |
| 46 ' && ${PYTHON}' + |
| 47 ' ${SCONSTRUCT_DIR}/tools/elf_patcher.py' + |
| 48 ' -a 16 -h ${SCONSTRUCT_DIR}/src/include/nacl_elf.h' + |
| 49 ' ${TARGET}') |
| 50 else: |
| 51 raise Exception, 'unknown architecture' |
| 52 |
| 53 asm_env.Append(CPPDEFINES = [ |
| 54 ['NACL_BLOCK_SHIFT', 5], |
| 55 ['NACL_BLOCK_SIZE', 32], |
| 56 ['NACL_BUILD_ARCH', '${BUILD_ARCHITECTURE}' ], |
| 57 ['NACL_BUILD_SUBARCH', '${BUILD_SUBARCH}' ], |
| 58 ['NACL_TARGET_ARCH', '${TARGET_ARCHITECTURE}' ], |
| 59 ['NACL_TARGET_SUBARCH', '${TARGET_SUBARCH}' ], |
| 60 ]) |
| 61 asm_env.Append(*alist, **kwarg) |
| 62 return asm_env |
| 63 |
| 64 |
| 65 if (env['TARGET_ARCHITECTURE'] == env['BUILD_ARCHITECTURE']): |
| 66 ALLOCATION_SIZE = 0x10000 |
| 67 START_OF_TEXT = 0x20000 |
| 68 TEXT_SIZE_BOUND = 0x10000 # estimate of test code size |
| 69 RODATA_SIZE_BOUND = 0x10000 |
| 70 RWDATA_SIZE = 0x4 # if we have rwdata, we must use exactly one word! |
| 71 |
| 72 def EndOfText(text_end_modulus): |
| 73 return START_OF_TEXT + text_end_modulus |
| 74 |
| 75 def RoundUpToAllocSize(size): |
| 76 return (size + ALLOCATION_SIZE - 1) & ~(ALLOCATION_SIZE - 1) |
| 77 |
| 78 def TextGap(text_end): |
| 79 end_of_text = EndOfText(text_end) |
| 80 rounded_end_of_text = RoundUpToAllocSize(end_of_text) |
| 81 text_gap = rounded_end_of_text - end_of_text |
| 82 return text_gap |
| 83 |
| 84 def NaturalRodataStart(text_end): |
| 85 extra = 0 |
| 86 text_gap = TextGap(text_end) |
| 87 if text_gap < HALT_SLED_SIZE: |
| 88 extra = ALLOCATION_SIZE |
| 89 return RoundUpToAllocSize(START_OF_TEXT + TEXT_SIZE_BOUND + extra) |
| 90 |
| 91 def ExpectedBreak(text_end, rodata_addr, rwdata_addr, rwdata_size): |
| 92 if rwdata_addr is None: |
| 93 if rodata_addr is None: |
| 94 break_addr = NaturalRodataStart(text_end) |
| 95 else: |
| 96 break_addr = RoundUpToAllocSize(rodata_addr + RODATA_SIZE_BOUND) |
| 97 else: |
| 98 break_addr = rwdata_addr + rwdata_size |
| 99 return break_addr |
| 100 |
| 101 test_specs = [ (0x10000, 'no'), |
| 102 (0x10000 - 32, 'small'), |
| 103 ( 0x8000, 'large'), |
| 104 (0x10000 - 28, 'too_small') ] |
| 105 |
| 106 rwdata_address = None # none for now |
| 107 |
| 108 for text_end, variant in test_specs: |
| 109 for rodata_address, name_modifier in [ (None, ''), |
| 110 (0, '_ro'), |
| 111 (0x100000, '_ro_dyn') ]: |
| 112 # rodata_address is None when no .rodata section should appear |
| 113 # in the generated nexe, and is 0 when it should appear in the |
| 114 # natural location (as defined by the linker script); when it |
| 115 # has a non-zero numeric value, then the .rodata section is |
| 116 # forced to start at that address. |
| 117 |
| 118 expected_exit_status = '0' |
| 119 |
| 120 # arm assembler misplaces the text section when --section-start |
| 121 # directive is used, so none of the tests that leaves room for |
| 122 # dynamic code can run. |
| 123 |
| 124 if (rodata_address is not None and rodata_address != 0 and |
| 125 env['TARGET_ARCHITECTURE'] == 'arm'): |
| 126 continue |
| 127 |
| 128 # arm assembler does not ensure there is enough space for |
| 129 # halt sled, and manually setting rodata's start location |
| 130 # is currently broken (moves text too). |
| 131 if (rodata_address == 0 and |
| 132 env['TARGET_ARCHITECTURE'] == 'arm' and |
| 133 variant == 'too_small'): |
| 134 expected_exit_status = 'trusted_sigabrt' |
| 135 |
| 136 if rodata_address == 0: |
| 137 use_rodata_address = NaturalRodataStart(text_end) |
| 138 else: |
| 139 use_rodata_address = rodata_address |
| 140 # use_rodata_address is None or a non-zero integer |
| 141 |
| 142 break_address = ExpectedBreak(text_end, use_rodata_address, |
| 143 rwdata_address, RWDATA_SIZE) |
| 144 |
| 145 defines=[] |
| 146 for (symbol, value) in [('TEXT_EXTEND', text_end), |
| 147 ('EXPECTED_BREAK', break_address), |
| 148 ('EXPECTED_RODATA', use_rodata_address), |
| 149 ('EXPECTED_RWDATA', rwdata_address)]: |
| 150 if value is not None: |
| 151 defines += [[symbol, str(value)]] |
| 152 |
| 153 asm_env = NewAsmEnv(env, |
| 154 CPPDEFINES=defines) |
| 155 |
| 156 for (linkcom_symbol, section_name, address) in [ |
| 157 ('RO_START', '.rodata', rodata_address), |
| 158 ('RW_START', '.data', rwdata_address)]: |
| 159 # on the arm, we *must* leave out the --section-start directive |
| 160 # when we use the "natural" address, since otherwise the linker |
| 161 # gets confused and misplaces the text section! |
| 162 if address is not None and address != 0: |
| 163 asm_env[linkcom_symbol] = ('--section-start=' + section_name + |
| 164 '=' + hex(address)) |
| 165 |
| 166 base_name = ('nacl_text_' + variant + '_pad' |
| 167 + name_modifier + '_test') |
| 168 obj = asm_env.ComponentObject(base_name + '.o', |
| 169 nacl_text_pad_asm) |
| 170 nexe_name = base_name + '.nexe' |
| 171 |
| 172 asm_env.ComponentProgram(nexe_name, |
| 173 [obj]) |
| 174 node = env.CommandSelLdrTestNacl( |
| 175 base_name + '.out', |
| 176 command=[env.File(nexe_name)], |
| 177 exit_status=expected_exit_status) |
| 178 env.AddNodeToTestSuite(node, ['sel_ldr_sled_tests'], 'run_' + base_name) |
OLD | NEW |