Unified · Split
| @@ -24,9 +24,9 @@ · 23 unmodified lines | ||
| 24 | 24 | #define CONFIG_TCC_ASM |
| 25 | 25 | #define NB_ASM_REGS 16 |
| 26 | 26 | |
| 27 | −ST_FUNC void g(int c); | |
| 28 | −ST_FUNC void gen_le16(int c); | |
| 29 | −ST_FUNC void gen_le32(int c); | |
| 27 | +ST_FUNC void g(TCCState* S, int c); | |
| 28 | +ST_FUNC void gen_le16(TCCState* S, int c); | |
| 29 | +ST_FUNC void gen_le32(TCCState* S, int c); | |
| 30 | 30 | |
| 31 | 31 | /*************************************************************/ |
| 32 | 32 | #else |
| @@ -92,7 +92,7 @@ static int asm_parse_vfp_status_regvar(int t) · 59 unmodified lines | ||
| 92 | 92 | } |
| 93 | 93 | |
| 94 | 94 | /* Parse a text containing operand and store the result in OP */ |
| 95 | −static void parse_operand(TCCState *s1, Operand *op) | |
| 95 | +static void parse_operand(TCCState *S, Operand *op) | |
| 96 | 96 | { |
| 97 | 97 | ExprValue e; |
| 98 | 98 | int8_t reg; |
| @@ -100,54 +100,54 @@ static void parse_operand(TCCState *s1, Operand *op) · 1 unmodified line | ||
| 100 | 100 | |
| 101 | 101 | op->type = 0; |
| 102 | 102 | |
| 103 | − if (tok == '{') { // regset literal | |
| 104 | − next(); // skip '{' | |
| 105 | − while (tok != '}' && tok != TOK_EOF) { | |
| 106 | − reg = asm_parse_regvar(tok); | |
| 103 | + if (S->tccpp_tok == '{') { // regset literal | |
| 104 | + next(S); // skip '{' | |
| 105 | + while (S->tccpp_tok != '}' && S->tccpp_tok != TOK_EOF) { | |
| 106 | + reg = asm_parse_regvar(S, S->tccpp_tok); | |
| 107 | 107 | if (reg == -1) { |
| 108 | − expect("register"); | |
| 108 | + expect(S, "register"); | |
| 109 | 109 | return; |
| 110 | 110 | } else |
| 111 | − next(); // skip register name | |
| 111 | + next(S); // skip register name | |
| 112 | 112 | |
| 113 | 113 | if ((1 << reg) < regset) |
| 114 | − tcc_warning("registers will be processed in ascending order by hardware--but are not specified in ascending order here"); | |
| 114 | + tcc_warning(S, "registers will be processed in ascending order by hardware--but are not specified in ascending order here"); | |
| 115 | 115 | regset |= 1 << reg; |
| 116 | − if (tok != ',') | |
| 116 | + if (S->tccpp_tok != ',') | |
| 117 | 117 | break; |
| 118 | − next(); // skip ',' | |
| 118 | + next(S); // skip ',' | |
| 119 | 119 | } |
| 120 | − if (tok != '}') | |
| 121 | − expect("'}'"); | |
| 122 | − next(); // skip '}' | |
| 120 | + if (S->tccpp_tok != '}') | |
| 121 | + expect(S, "'}'"); | |
| 122 | + next(S); // skip '}' | |
| 123 | 123 | if (regset == 0) { |
| 124 | 124 | // ARM instructions don't support empty regset. |
| 125 | − tcc_error("empty register list is not supported"); | |
| 125 | + tcc_error(S, "empty register list is not supported"); | |
| 126 | 126 | } else { |
| 127 | 127 | op->type = OP_REGSET32; |
| 128 | 128 | op->regset = regset; |
| 129 | 129 | } |
| 130 | 130 | return; |
| 131 | − } else if ((reg = asm_parse_regvar(tok)) != -1) { | |
| 132 | − next(); // skip register name | |
| 131 | + } else if ((reg = asm_parse_regvar(S, S->tccpp_tok)) != -1) { | |
| 132 | + next(S); // skip register name | |
| 133 | 133 | op->type = OP_REG32; |
| 134 | 134 | op->reg = (uint8_t) reg; |
| 135 | 135 | return; |
| 136 | − } else if ((reg = asm_parse_vfp_regvar(tok, 0)) != -1) { | |
| 137 | − next(); // skip register name | |
| 136 | + } else if ((reg = asm_parse_vfp_regvar(S->tccpp_tok, 0)) != -1) { | |
| 137 | + next(S); // skip register name | |
| 138 | 138 | op->type = OP_VREG32; |
| 139 | 139 | op->reg = (uint8_t) reg; |
| 140 | 140 | return; |
| 141 | − } else if ((reg = asm_parse_vfp_regvar(tok, 1)) != -1) { | |
| 142 | − next(); // skip register name | |
| 141 | + } else if ((reg = asm_parse_vfp_regvar(S->tccpp_tok, 1)) != -1) { | |
| 142 | + next(S); // skip register name | |
| 143 | 143 | op->type = OP_VREG64; |
| 144 | 144 | op->reg = (uint8_t) reg; |
| 145 | 145 | return; |
| 146 | − } else if (tok == '#' || tok == '$') { | |
| 146 | + } else if (S->tccpp_tok == '#' || S->tccpp_tok == '$') { | |
| 147 | 147 | /* constant value */ |
| 148 | − next(); // skip '#' or '$' | |
| 148 | + next(S); // skip '#' or '$' | |
| 149 | 149 | } |
| 150 | − asm_expr(s1, &e); | |
| 150 | + asm_expr(S, &e); | |
| 151 | 151 | op->type = OP_IM32; |
| 152 | 152 | op->e = e; |
| 153 | 153 | if (!op->e.sym) { |
| @@ -156,64 +156,64 @@ static void parse_operand(TCCState *s1, Operand *op) · 2 unmodified lines | ||
| 156 | 156 | else if (op->e.v == (uint8_t)op->e.v) |
| 157 | 157 | op->type = OP_IM8; |
| 158 | 158 | } else |
| 159 | − expect("operand"); | |
| 159 | + expect(S, "operand"); | |
| 160 | 160 | } |
| 161 | 161 | |
| 162 | 162 | /* XXX: make it faster ? */ |
| 163 | −ST_FUNC void g(int c) | |
| 163 | +ST_FUNC void g(TCCState* S, int c) | |
| 164 | 164 | { |
| 165 | 165 | int ind1; |
| 166 | − if (nocode_wanted) | |
| 166 | + if (S->tccgen_nocode_wanted) | |
| 167 | 167 | return; |
| 168 | − ind1 = ind + 1; | |
| 168 | + ind1 = S->tccgen_ind + 1; | |
| 169 | 169 | if (ind1 > cur_text_section->data_allocated) |
| 170 | − section_realloc(cur_text_section, ind1); | |
| 171 | − cur_text_section->data[ind] = c; | |
| 172 | − ind = ind1; | |
| 170 | + section_realloc(S, cur_text_section, ind1); | |
| 171 | + cur_text_section->data[S->tccgen_ind] = c; | |
| 172 | + S->tccgen_ind = ind1; | |
| 173 | 173 | } |
| 174 | 174 | |
| 175 | −ST_FUNC void gen_le16 (int i) | |
| 175 | +ST_FUNC void gen_le16 (TCCState* S, int i) | |
| 176 | 176 | { |
| 177 | − g(i); | |
| 178 | − g(i>>8); | |
| 177 | + g(S, i); | |
| 178 | + g(S, i>>8); | |
| 179 | 179 | } |
| 180 | 180 | |
| 181 | −ST_FUNC void gen_le32 (int i) | |
| 181 | +ST_FUNC void gen_le32 (TCCState* S, int i) | |
| 182 | 182 | { |
| 183 | 183 | int ind1; |
| 184 | − if (nocode_wanted) | |
| 184 | + if (S->tccgen_nocode_wanted) | |
| 185 | 185 | return; |
| 186 | − ind1 = ind + 4; | |
| 186 | + ind1 = S->tccgen_ind + 4; | |
| 187 | 187 | if (ind1 > cur_text_section->data_allocated) |
| 188 | − section_realloc(cur_text_section, ind1); | |
| 189 | − cur_text_section->data[ind++] = i & 0xFF; | |
| 190 | − cur_text_section->data[ind++] = (i >> 8) & 0xFF; | |
| 191 | − cur_text_section->data[ind++] = (i >> 16) & 0xFF; | |
| 192 | − cur_text_section->data[ind++] = (i >> 24) & 0xFF; | |
| 188 | + section_realloc(S, cur_text_section, ind1); | |
| 189 | + cur_text_section->data[S->tccgen_ind++] = i & 0xFF; | |
| 190 | + cur_text_section->data[S->tccgen_ind++] = (i >> 8) & 0xFF; | |
| 191 | + cur_text_section->data[S->tccgen_ind++] = (i >> 16) & 0xFF; | |
| 192 | + cur_text_section->data[S->tccgen_ind++] = (i >> 24) & 0xFF; | |
| 193 | 193 | } |
| 194 | 194 | |
| 195 | −ST_FUNC void gen_expr32(ExprValue *pe) | |
| 195 | +ST_FUNC void gen_expr32(TCCState* S, ExprValue *pe) | |
| 196 | 196 | { |
| 197 | − gen_le32(pe->v); | |
| 197 | + gen_le32(S, pe->v); | |
| 198 | 198 | } |
| 199 | 199 | |
| 200 | −static uint32_t condition_code_of_token(int token) { | |
| 200 | +static uint32_t condition_code_of_token(TCCState* S, int token) { | |
| 201 | 201 | if (token < TOK_ASM_nopeq) { |
| 202 | − expect("condition-enabled instruction"); | |
| 202 | + expect(S, "condition-enabled instruction"); | |
| 203 | 203 | return 0; |
| 204 | 204 | } else |
| 205 | 205 | return (token - TOK_ASM_nopeq) & 15; |
| 206 | 206 | } |
| 207 | 207 | |
| 208 | −static void asm_emit_opcode(int token, uint32_t opcode) { | |
| 209 | − gen_le32((condition_code_of_token(token) << 28) | opcode); | |
| 208 | +static void asm_emit_opcode(TCCState* S, int token, uint32_t opcode) { | |
| 209 | + gen_le32(S, (condition_code_of_token(S, token) << 28) | opcode); | |
| 210 | 210 | } |
| 211 | 211 | |
| 212 | −static void asm_emit_unconditional_opcode(uint32_t opcode) { | |
| 213 | − gen_le32(opcode); | |
| 212 | +static void asm_emit_unconditional_opcode(TCCState* S, uint32_t opcode) { | |
| 213 | + gen_le32(S, opcode); | |
| 214 | 214 | } |
| 215 | 215 | |
| 216 | −static void asm_emit_coprocessor_opcode(uint32_t high_nibble, uint8_t cp_number, uint8_t cp_opcode, uint8_t cp_destination_register, uint8_t cp_n_operand_register, uint8_t cp_m_operand_register, uint8_t cp_opcode2, int inter_processor_transfer) | |
| 216 | +static void asm_emit_coprocessor_opcode(TCCState* S, uint32_t high_nibble, uint8_t cp_number, uint8_t cp_opcode, uint8_t cp_destination_register, uint8_t cp_n_operand_register, uint8_t cp_m_operand_register, uint8_t cp_opcode2, int inter_processor_transfer) | |
| 217 | 217 | { |
| 218 | 218 | uint32_t opcode = 0xe000000; |
| 219 | 219 | if (inter_processor_transfer) |
| @@ -230,69 +230,69 @@ static void asm_emit_coprocessor_opcode(uint32_t high_nibble, uint8_t cp_number, · 10 unmodified lines | ||
| 230 | 230 | opcode |= cp_opcode2 << 5; |
| 231 | 231 | //assert(cp_m_operand_register < 16); |
| 232 | 232 | opcode |= cp_m_operand_register; |
| 233 | − asm_emit_unconditional_opcode((high_nibble << 28) | opcode); | |
| 233 | + asm_emit_unconditional_opcode(S, (high_nibble << 28) | opcode); | |
| 234 | 234 | } |
| 235 | 235 | |
| 236 | −static void asm_nullary_opcode(int token) | |
| 236 | +static void asm_nullary_opcode(TCCState* S, int token) | |
| 237 | 237 | { |
| 238 | 238 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 239 | 239 | case TOK_ASM_nopeq: |
| 240 | − asm_emit_opcode(token, 0xd << 21); // mov r0, r0 | |
| 240 | + asm_emit_opcode(S, token, 0xd << 21); // mov r0, r0 | |
| 241 | 241 | break; |
| 242 | 242 | case TOK_ASM_wfeeq: |
| 243 | − asm_emit_opcode(token, 0x320f002); | |
| 243 | + asm_emit_opcode(S, token, 0x320f002); | |
| 244 | 244 | case TOK_ASM_wfieq: |
| 245 | − asm_emit_opcode(token, 0x320f003); | |
| 245 | + asm_emit_opcode(S, token, 0x320f003); | |
| 246 | 246 | break; |
| 247 | 247 | default: |
| 248 | − expect("nullary instruction"); | |
| 248 | + expect(S, "nullary instruction"); | |
| 249 | 249 | } |
| 250 | 250 | } |
| 251 | 251 | |
| 252 | −static void asm_unary_opcode(TCCState *s1, int token) | |
| 252 | +static void asm_unary_opcode(TCCState *S, int token) | |
| 253 | 253 | { |
| 254 | 254 | Operand op; |
| 255 | − parse_operand(s1, &op); | |
| 255 | + parse_operand(S, &op); | |
| 256 | 256 | |
| 257 | 257 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 258 | 258 | case TOK_ASM_swieq: |
| 259 | 259 | case TOK_ASM_svceq: |
| 260 | 260 | if (op.type != OP_IM8) |
| 261 | − expect("immediate 8-bit unsigned integer"); | |
| 261 | + expect(S, "immediate 8-bit unsigned integer"); | |
| 262 | 262 | else { |
| 263 | 263 | /* Note: Dummy operand (ignored by processor): ARM ref documented 0...255, ARM instruction set documented 24 bit */ |
| 264 | − asm_emit_opcode(token, (0xf << 24) | op.e.v); | |
| 264 | + asm_emit_opcode(S, token, (0xf << 24) | op.e.v); | |
| 265 | 265 | } |
| 266 | 266 | break; |
| 267 | 267 | default: |
| 268 | − expect("unary instruction"); | |
| 268 | + expect(S, "unary instruction"); | |
| 269 | 269 | } |
| 270 | 270 | } |
| 271 | 271 | |
| 272 | −static void asm_binary_opcode(TCCState *s1, int token) | |
| 272 | +static void asm_binary_opcode(TCCState *S, int token) | |
| 273 | 273 | { |
| 274 | 274 | Operand ops[2]; |
| 275 | 275 | Operand rotation; |
| 276 | 276 | uint32_t encoded_rotation = 0; |
| 277 | 277 | uint64_t amount; |
| 278 | − parse_operand(s1, &ops[0]); | |
| 279 | − if (tok == ',') | |
| 280 | − next(); | |
| 278 | + parse_operand(S, &ops[0]); | |
| 279 | + if (S->tccpp_tok == ',') | |
| 280 | + next(S); | |
| 281 | 281 | else |
| 282 | − expect("','"); | |
| 283 | − parse_operand(s1, &ops[1]); | |
| 282 | + expect(S, "','"); | |
| 283 | + parse_operand(S, &ops[1]); | |
| 284 | 284 | if (ops[0].type != OP_REG32) { |
| 285 | − expect("(destination operand) register"); | |
| 285 | + expect(S, "(destination operand) register"); | |
| 286 | 286 | return; |
| 287 | 287 | } |
| 288 | 288 | |
| 289 | 289 | if (ops[0].reg == 15) { |
| 290 | − tcc_error("'%s' does not support 'pc' as operand", get_tok_str(token, NULL)); | |
| 290 | + tcc_error(S, "'%s' does not support 'pc' as operand", get_tok_str(S, token, NULL)); | |
| 291 | 291 | return; |
| 292 | 292 | } |
| 293 | 293 | |
| 294 | 294 | if (ops[0].reg == 13) |
| 295 | − tcc_warning("Using 'sp' as operand with '%s' is deprecated by ARM", get_tok_str(token, NULL)); | |
| 295 | + tcc_warning(S, "Using 'sp' as operand with '%s' is deprecated by ARM", get_tok_str(S, token, NULL)); | |
| 296 | 296 | |
| 297 | 297 | if (ops[1].type != OP_REG32) { |
| 298 | 298 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| @@ -303,38 +303,38 @@ static void asm_binary_opcode(TCCState *s1, int token) · 4 unmodified lines | ||
| 303 | 303 | uint16_t immediate_value = ops[1].e.v; |
| 304 | 304 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 305 | 305 | case TOK_ASM_movteq: |
| 306 | − asm_emit_opcode(token, 0x3400000 | (ops[0].reg << 12) | (immediate_value & 0xF000) << 4 | (immediate_value & 0xFFF)); | |
| 306 | + asm_emit_opcode(S, token, 0x3400000 | (ops[0].reg << 12) | (immediate_value & 0xF000) << 4 | (immediate_value & 0xFFF)); | |
| 307 | 307 | break; |
| 308 | 308 | case TOK_ASM_movweq: |
| 309 | − asm_emit_opcode(token, 0x3000000 | (ops[0].reg << 12) | (immediate_value & 0xF000) << 4 | (immediate_value & 0xFFF)); | |
| 309 | + asm_emit_opcode(S, token, 0x3000000 | (ops[0].reg << 12) | (immediate_value & 0xF000) << 4 | (immediate_value & 0xFFF)); | |
| 310 | 310 | break; |
| 311 | 311 | } |
| 312 | 312 | } else |
| 313 | − expect("(source operand) immediate 16 bit value"); | |
| 313 | + expect(S, "(source operand) immediate 16 bit value"); | |
| 314 | 314 | } else |
| 315 | − expect("(source operand) immediate"); | |
| 315 | + expect(S, "(source operand) immediate"); | |
| 316 | 316 | break; |
| 317 | 317 | default: |
| 318 | − expect("(source operand) register"); | |
| 318 | + expect(S, "(source operand) register"); | |
| 319 | 319 | } |
| 320 | 320 | return; |
| 321 | 321 | } |
| 322 | 322 | |
| 323 | 323 | if (ops[1].reg == 15) { |
| 324 | − tcc_error("'%s' does not support 'pc' as operand", get_tok_str(token, NULL)); | |
| 324 | + tcc_error(S, "'%s' does not support 'pc' as operand", get_tok_str(S, token, NULL)); | |
| 325 | 325 | return; |
| 326 | 326 | } |
| 327 | 327 | |
| 328 | 328 | if (ops[1].reg == 13) |
| 329 | − tcc_warning("Using 'sp' as operand with '%s' is deprecated by ARM", get_tok_str(token, NULL)); | |
| 329 | + tcc_warning(S, "Using 'sp' as operand with '%s' is deprecated by ARM", get_tok_str(S, token, NULL)); | |
| 330 | 330 | |
| 331 | − if (tok == ',') { | |
| 332 | − next(); // skip ',' | |
| 333 | − if (tok == TOK_ASM_ror) { | |
| 334 | − next(); // skip 'ror' | |
| 335 | − parse_operand(s1, &rotation); | |
| 331 | + if (S->tccpp_tok == ',') { | |
| 332 | + next(S); // skip ',' | |
| 333 | + if (S->tccpp_tok == TOK_ASM_ror) { | |
| 334 | + next(S); // skip 'ror' | |
| 335 | + parse_operand(S, &rotation); | |
| 336 | 336 | if (rotation.type != OP_IM8) { |
| 337 | − expect("immediate value for rotation"); | |
| 337 | + expect(S, "immediate value for rotation"); | |
| 338 | 338 | return; |
| 339 | 339 | } else { |
| 340 | 340 | amount = rotation.e.v; |
| @@ -349,7 +349,7 @@ static void asm_binary_opcode(TCCState *s1, int token) · 8 unmodified lines | ||
| 349 | 349 | encoded_rotation = 3 << 10; |
| 350 | 350 | break; |
| 351 | 351 | default: |
| 352 | − expect("'8' or '16' or '24'"); | |
| 352 | + expect(S, "'8' or '16' or '24'"); | |
| 353 | 353 | return; |
| 354 | 354 | } |
| 355 | 355 | } |
| @@ -358,27 +358,27 @@ static void asm_binary_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 358 | 358 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 359 | 359 | case TOK_ASM_clzeq: |
| 360 | 360 | if (encoded_rotation) |
| 361 | − tcc_error("clz does not support rotation"); | |
| 362 | − asm_emit_opcode(token, 0x16f0f10 | (ops[0].reg << 12) | ops[1].reg); | |
| 361 | + tcc_error(S, "clz does not support rotation"); | |
| 362 | + asm_emit_opcode(S, token, 0x16f0f10 | (ops[0].reg << 12) | ops[1].reg); | |
| 363 | 363 | break; |
| 364 | 364 | case TOK_ASM_sxtbeq: |
| 365 | − asm_emit_opcode(token, 0x6af0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 365 | + asm_emit_opcode(S, token, 0x6af0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 366 | 366 | break; |
| 367 | 367 | case TOK_ASM_sxtheq: |
| 368 | − asm_emit_opcode(token, 0x6bf0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 368 | + asm_emit_opcode(S, token, 0x6bf0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 369 | 369 | break; |
| 370 | 370 | case TOK_ASM_uxtbeq: |
| 371 | − asm_emit_opcode(token, 0x6ef0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 371 | + asm_emit_opcode(S, token, 0x6ef0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 372 | 372 | break; |
| 373 | 373 | case TOK_ASM_uxtheq: |
| 374 | − asm_emit_opcode(token, 0x6ff0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 374 | + asm_emit_opcode(S, token, 0x6ff0070 | (ops[0].reg << 12) | ops[1].reg | encoded_rotation); | |
| 375 | 375 | break; |
| 376 | 376 | default: |
| 377 | − expect("binary instruction"); | |
| 377 | + expect(S, "binary instruction"); | |
| 378 | 378 | } |
| 379 | 379 | } |
| 380 | 380 | |
| 381 | −static void asm_coprocessor_opcode(TCCState *s1, int token) { | |
| 381 | +static void asm_coprocessor_opcode(TCCState *S, int token) { | |
| 382 | 382 | uint8_t coprocessor; |
| 383 | 383 | Operand opcode1; |
| 384 | 384 | Operand opcode2; |
| @@ -387,70 +387,70 @@ static void asm_coprocessor_opcode(TCCState *s1, int token) { · 2 unmodified lines | ||
| 387 | 387 | uint8_t high_nibble; |
| 388 | 388 | uint8_t mrc = 0; |
| 389 | 389 | |
| 390 | − if (tok >= TOK_ASM_p0 && tok <= TOK_ASM_p15) { | |
| 391 | − coprocessor = tok - TOK_ASM_p0; | |
| 392 | − next(); | |
| 390 | + if (S->tccpp_tok >= TOK_ASM_p0 && S->tccpp_tok <= TOK_ASM_p15) { | |
| 391 | + coprocessor = S->tccpp_tok - TOK_ASM_p0; | |
| 392 | + next(S); | |
| 393 | 393 | } else { |
| 394 | − expect("'p<number>'"); | |
| 394 | + expect(S, "'p<number>'"); | |
| 395 | 395 | return; |
| 396 | 396 | } |
| 397 | 397 | |
| 398 | − if (tok == ',') | |
| 399 | − next(); | |
| 398 | + if (S->tccpp_tok == ',') | |
| 399 | + next(S); | |
| 400 | 400 | else |
| 401 | − expect("','"); | |
| 401 | + expect(S, "','"); | |
| 402 | 402 | |
| 403 | − parse_operand(s1, &opcode1); | |
| 403 | + parse_operand(S, &opcode1); | |
| 404 | 404 | if (opcode1.type != OP_IM8 || opcode1.e.v > 15) { |
| 405 | − tcc_error("opcode1 of instruction '%s' must be an immediate value between 0 and 15", get_tok_str(token, NULL)); | |
| 405 | + tcc_error(S, "opcode1 of instruction '%s' must be an immediate value between 0 and 15", get_tok_str(S, token, NULL)); | |
| 406 | 406 | return; |
| 407 | 407 | } |
| 408 | 408 | |
| 409 | 409 | for (i = 0; i < 3; ++i) { |
| 410 | − if (tok == ',') | |
| 411 | − next(); | |
| 410 | + if (S->tccpp_tok == ',') | |
| 411 | + next(S); | |
| 412 | 412 | else |
| 413 | − expect("','"); | |
| 413 | + expect(S, "','"); | |
| 414 | 414 | if (i == 0 && token != TOK_ASM_cdp2 && (ARM_INSTRUCTION_GROUP(token) == TOK_ASM_mrceq || ARM_INSTRUCTION_GROUP(token) == TOK_ASM_mcreq)) { |
| 415 | − if (tok >= TOK_ASM_r0 && tok <= TOK_ASM_r15) { | |
| 416 | − registers[i] = tok - TOK_ASM_r0; | |
| 417 | − next(); | |
| 415 | + if (S->tccpp_tok >= TOK_ASM_r0 && S->tccpp_tok <= TOK_ASM_r15) { | |
| 416 | + registers[i] = S->tccpp_tok - TOK_ASM_r0; | |
| 417 | + next(S); | |
| 418 | 418 | } else { |
| 419 | − expect("'r<number>'"); | |
| 419 | + expect(S, "'r<number>'"); | |
| 420 | 420 | return; |
| 421 | 421 | } |
| 422 | 422 | } else { |
| 423 | − if (tok >= TOK_ASM_c0 && tok <= TOK_ASM_c15) { | |
| 424 | − registers[i] = tok - TOK_ASM_c0; | |
| 425 | − next(); | |
| 423 | + if (S->tccpp_tok >= TOK_ASM_c0 && S->tccpp_tok <= TOK_ASM_c15) { | |
| 424 | + registers[i] = S->tccpp_tok - TOK_ASM_c0; | |
| 425 | + next(S); | |
| 426 | 426 | } else { |
| 427 | − expect("'c<number>'"); | |
| 427 | + expect(S, "'c<number>'"); | |
| 428 | 428 | return; |
| 429 | 429 | } |
| 430 | 430 | } |
| 431 | 431 | } |
| 432 | − if (tok == ',') { | |
| 433 | − next(); | |
| 434 | − parse_operand(s1, &opcode2); | |
| 432 | + if (S->tccpp_tok == ',') { | |
| 433 | + next(S); | |
| 434 | + parse_operand(S, &opcode2); | |
| 435 | 435 | } else { |
| 436 | 436 | opcode2.type = OP_IM8; |
| 437 | 437 | opcode2.e.v = 0; |
| 438 | 438 | } |
| 439 | 439 | if (opcode2.type != OP_IM8 || opcode2.e.v > 15) { |
| 440 | − tcc_error("opcode2 of instruction '%s' must be an immediate value between 0 and 15", get_tok_str(token, NULL)); | |
| 440 | + tcc_error(S, "opcode2 of instruction '%s' must be an immediate value between 0 and 15", get_tok_str(S, token, NULL)); | |
| 441 | 441 | return; |
| 442 | 442 | } |
| 443 | 443 | |
| 444 | 444 | if (token == TOK_ASM_cdp2) { |
| 445 | 445 | high_nibble = 0xF; |
| 446 | − asm_emit_coprocessor_opcode(high_nibble, coprocessor, opcode1.e.v, registers[0], registers[1], registers[2], opcode2.e.v, 0); | |
| 446 | + asm_emit_coprocessor_opcode(S, high_nibble, coprocessor, opcode1.e.v, registers[0], registers[1], registers[2], opcode2.e.v, 0); | |
| 447 | 447 | return; |
| 448 | 448 | } else |
| 449 | − high_nibble = condition_code_of_token(token); | |
| 449 | + high_nibble = condition_code_of_token(S, token); | |
| 450 | 450 | |
| 451 | 451 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 452 | 452 | case TOK_ASM_cdpeq: |
| 453 | − asm_emit_coprocessor_opcode(high_nibble, coprocessor, opcode1.e.v, registers[0], registers[1], registers[2], opcode2.e.v, 0); | |
| 453 | + asm_emit_coprocessor_opcode(S, high_nibble, coprocessor, opcode1.e.v, registers[0], registers[1], registers[2], opcode2.e.v, 0); | |
| 454 | 454 | break; |
| 455 | 455 | case TOK_ASM_mrceq: |
| 456 | 456 | // opcode1 encoding changes! highest and lowest bit gone. |
| @@ -459,13 +459,13 @@ static void asm_coprocessor_opcode(TCCState *s1, int token) { · 2 unmodified lines | ||
| 459 | 459 | case TOK_ASM_mcreq: |
| 460 | 460 | // opcode1 encoding changes! highest and lowest bit gone. |
| 461 | 461 | if (opcode1.e.v > 7) { |
| 462 | − tcc_error("opcode1 of instruction '%s' must be an immediate value between 0 and 7", get_tok_str(token, NULL)); | |
| 462 | + tcc_error(S, "opcode1 of instruction '%s' must be an immediate value between 0 and 7", get_tok_str(S, token, NULL)); | |
| 463 | 463 | return; |
| 464 | 464 | } |
| 465 | − asm_emit_coprocessor_opcode(high_nibble, coprocessor, (opcode1.e.v << 1) | mrc, registers[0], registers[1], registers[2], opcode2.e.v, 1); | |
| 465 | + asm_emit_coprocessor_opcode(S, high_nibble, coprocessor, (opcode1.e.v << 1) | mrc, registers[0], registers[1], registers[2], opcode2.e.v, 1); | |
| 466 | 466 | break; |
| 467 | 467 | default: |
| 468 | − expect("known instruction"); | |
| 468 | + expect(S, "known instruction"); | |
| 469 | 469 | } |
| 470 | 470 | } |
| 471 | 471 | |
| @@ -486,27 +486,27 @@ static void asm_coprocessor_opcode(TCCState *s1, int token) { · 14 unmodified lines | ||
| 486 | 486 | #define ENCODE_BARREL_SHIFTER_REGISTER(register_index) ((register_index) << 8) |
| 487 | 487 | #define ENCODE_BARREL_SHIFTER_IMMEDIATE(value) ((value) << 7) |
| 488 | 488 | |
| 489 | −static void asm_block_data_transfer_opcode(TCCState *s1, int token) | |
| 489 | +static void asm_block_data_transfer_opcode(TCCState *S, int token) | |
| 490 | 490 | { |
| 491 | 491 | uint32_t opcode; |
| 492 | 492 | int op0_exclam = 0; |
| 493 | 493 | Operand ops[2]; |
| 494 | 494 | int nb_ops = 1; |
| 495 | − parse_operand(s1, &ops[0]); | |
| 496 | − if (tok == '!') { | |
| 495 | + parse_operand(S, &ops[0]); | |
| 496 | + if (S->tccpp_tok == '!') { | |
| 497 | 497 | op0_exclam = 1; |
| 498 | − next(); // skip '!' | |
| 498 | + next(S); // skip '!' | |
| 499 | 499 | } |
| 500 | − if (tok == ',') { | |
| 501 | − next(); // skip comma | |
| 502 | − parse_operand(s1, &ops[1]); | |
| 500 | + if (S->tccpp_tok == ',') { | |
| 501 | + next(S); // skip comma | |
| 502 | + parse_operand(S, &ops[1]); | |
| 503 | 503 | ++nb_ops; |
| 504 | 504 | } |
| 505 | 505 | if (nb_ops < 1) { |
| 506 | − expect("at least one operand"); | |
| 506 | + expect(S, "at least one operand"); | |
| 507 | 507 | return; |
| 508 | 508 | } else if (ops[nb_ops - 1].type != OP_REGSET32) { |
| 509 | − expect("(last operand) register list"); | |
| 509 | + expect(S, "(last operand) register list"); | |
| 510 | 510 | return; |
| 511 | 511 | } |
| 512 | 512 | |
| @@ -522,9 +522,9 @@ static void asm_block_data_transfer_opcode(TCCState *s1, int token) · 9 unmodified lines | ||
| 522 | 522 | // Rn: base register |
| 523 | 523 | // Register List: bits 15...0 |
| 524 | 524 | if (nb_ops != 1) |
| 525 | − expect("exactly one operand"); | |
| 525 | + expect(S, "exactly one operand"); | |
| 526 | 526 | else |
| 527 | − asm_emit_opcode(token, (0x92d << 16) | ops[0].regset); // TODO: base register ? | |
| 527 | + asm_emit_opcode(S, token, (0x92d << 16) | ops[0].regset); // TODO: base register ? | |
| 528 | 528 | break; |
| 529 | 529 | case TOK_ASM_popeq: // TODO: Optimize 1-register case to: ldr ?, [sp], #4 |
| 530 | 530 | // Instruction: 1 I=0 P=0 U=1 S=0 W=0 L=1 << 20, op 1101 |
| @@ -532,9 +532,9 @@ static void asm_block_data_transfer_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 532 | 532 | // Rn: base register |
| 533 | 533 | // Register List: bits 15...0 |
| 534 | 534 | if (nb_ops != 1) |
| 535 | − expect("exactly one operand"); | |
| 535 | + expect(S, "exactly one operand"); | |
| 536 | 536 | else |
| 537 | − asm_emit_opcode(token, (0x8bd << 16) | ops[0].regset); // TODO: base register ? | |
| 537 | + asm_emit_opcode(S, token, (0x8bd << 16) | ops[0].regset); // TODO: base register ? | |
| 538 | 538 | break; |
| 539 | 539 | case TOK_ASM_stmdaeq: |
| 540 | 540 | case TOK_ASM_ldmdaeq: |
| @@ -574,23 +574,23 @@ static void asm_block_data_transfer_opcode(TCCState *s1, int token) · 33 unmodified lines | ||
| 574 | 574 | opcode = 0x99 << 20; |
| 575 | 575 | break; |
| 576 | 576 | default: |
| 577 | − tcc_error("internal error: This place should not be reached (fallback in asm_block_data_transfer_opcode)"); | |
| 577 | + tcc_error(S, "internal error: This place should not be reached (fallback in asm_block_data_transfer_opcode)"); | |
| 578 | 578 | } |
| 579 | 579 | // operands: |
| 580 | 580 | // Rn: first operand |
| 581 | 581 | // Register List: lower bits |
| 582 | 582 | if (nb_ops != 2) |
| 583 | − expect("exactly two operands"); | |
| 583 | + expect(S, "exactly two operands"); | |
| 584 | 584 | else if (ops[0].type != OP_REG32) |
| 585 | − expect("(first operand) register"); | |
| 585 | + expect(S, "(first operand) register"); | |
| 586 | 586 | else { |
| 587 | 587 | if (op0_exclam) |
| 588 | 588 | opcode |= 1 << 21; // writeback |
| 589 | − asm_emit_opcode(token, opcode | ENCODE_RN(ops[0].reg) | ops[1].regset); | |
| 589 | + asm_emit_opcode(S, token, opcode | ENCODE_RN(ops[0].reg) | ops[1].regset); | |
| 590 | 590 | } |
| 591 | 591 | break; |
| 592 | 592 | default: |
| 593 | − expect("block data transfer instruction"); | |
| 593 | + expect(S, "block data transfer instruction"); | |
| 594 | 594 | } |
| 595 | 595 | } |
| 596 | 596 | |
| @@ -600,17 +600,17 @@ static void asm_block_data_transfer_opcode(TCCState *s1, int token) · 3 unmodified lines | ||
| 600 | 600 | |
| 601 | 601 | NB_SHIFT: will be set to 1 iff SHIFT is filled. Note that for rrx, there's no need to fill SHIFT. |
| 602 | 602 | SHIFT: will be filled in with the shift operand to use, if any. */ |
| 603 | −static uint32_t asm_parse_optional_shift(TCCState* s1, int* nb_shift, Operand* shift) | |
| 603 | +static uint32_t asm_parse_optional_shift(TCCState* S, int* nb_shift, Operand* shift) | |
| 604 | 604 | { |
| 605 | 605 | uint32_t opcode = 0; |
| 606 | 606 | *nb_shift = 0; |
| 607 | − switch (tok) { | |
| 607 | + switch (S->tccpp_tok) { | |
| 608 | 608 | case TOK_ASM_asl: |
| 609 | 609 | case TOK_ASM_lsl: |
| 610 | 610 | case TOK_ASM_asr: |
| 611 | 611 | case TOK_ASM_lsr: |
| 612 | 612 | case TOK_ASM_ror: |
| 613 | − switch (tok) { | |
| 613 | + switch (S->tccpp_tok) { | |
| 614 | 614 | case TOK_ASM_asl: |
| 615 | 615 | /* fallthrough */ |
| 616 | 616 | case TOK_ASM_lsl: |
| @@ -626,26 +626,26 @@ static uint32_t asm_parse_optional_shift(TCCState* s1, int* nb_shift, Operand* s · 9 unmodified lines | ||
| 626 | 626 | opcode = ENCODE_BARREL_SHIFTER_MODE_ROR; |
| 627 | 627 | break; |
| 628 | 628 | } |
| 629 | − next(); | |
| 630 | − parse_operand(s1, shift); | |
| 629 | + next(S); | |
| 630 | + parse_operand(S, shift); | |
| 631 | 631 | *nb_shift = 1; |
| 632 | 632 | break; |
| 633 | 633 | case TOK_ASM_rrx: |
| 634 | − next(); | |
| 634 | + next(S); | |
| 635 | 635 | opcode = ENCODE_BARREL_SHIFTER_MODE_ROR; |
| 636 | 636 | break; |
| 637 | 637 | } |
| 638 | 638 | return opcode; |
| 639 | 639 | } |
| 640 | 640 | |
| 641 | −static uint32_t asm_encode_shift(Operand* shift) | |
| 641 | +static uint32_t asm_encode_shift(TCCState *S, Operand* shift) | |
| 642 | 642 | { |
| 643 | 643 | uint64_t amount; |
| 644 | 644 | uint32_t operands = 0; |
| 645 | 645 | switch (shift->type) { |
| 646 | 646 | case OP_REG32: |
| 647 | 647 | if (shift->reg == 15) |
| 648 | − tcc_error("r15 cannot be used as a shift count"); | |
| 648 | + tcc_error(S, "r15 cannot be used as a shift count"); | |
| 649 | 649 | else { |
| 650 | 650 | operands = ENCODE_BARREL_SHIFTER_SHIFT_BY_REGISTER; |
| 651 | 651 | operands |= ENCODE_BARREL_SHIFTER_REGISTER(shift->reg); |
| @@ -656,15 +656,15 @@ static uint32_t asm_encode_shift(Operand* shift) · 4 unmodified lines | ||
| 656 | 656 | if (amount > 0 && amount < 32) |
| 657 | 657 | operands = ENCODE_BARREL_SHIFTER_IMMEDIATE(amount); |
| 658 | 658 | else |
| 659 | − tcc_error("shift count out of range"); | |
| 659 | + tcc_error(S, "shift count out of range"); | |
| 660 | 660 | break; |
| 661 | 661 | default: |
| 662 | − tcc_error("unknown shift amount"); | |
| 662 | + tcc_error(S, "unknown shift amount"); | |
| 663 | 663 | } |
| 664 | 664 | return operands; |
| 665 | 665 | } |
| 666 | 666 | |
| 667 | −static void asm_data_processing_opcode(TCCState *s1, int token) | |
| 667 | +static void asm_data_processing_opcode(TCCState *S, int token) | |
| 668 | 668 | { |
| 669 | 669 | Operand ops[3]; |
| 670 | 670 | int nb_ops; |
| @@ -677,31 +677,31 @@ static void asm_data_processing_opcode(TCCState *s1, int token) · 6 unmodified lines | ||
| 677 | 677 | uint32_t opcode_nos = opcode_idx >> 1; // without "s"; "OpCode" in ARM docs |
| 678 | 678 | |
| 679 | 679 | for (nb_ops = 0; nb_ops < sizeof(ops)/sizeof(ops[0]); ) { |
| 680 | − if (tok == TOK_ASM_asl || tok == TOK_ASM_lsl || tok == TOK_ASM_lsr || tok == TOK_ASM_asr || tok == TOK_ASM_ror || tok == TOK_ASM_rrx) | |
| 680 | + if (S->tccpp_tok == TOK_ASM_asl || S->tccpp_tok == TOK_ASM_lsl || S->tccpp_tok == TOK_ASM_lsr || S->tccpp_tok == TOK_ASM_asr || S->tccpp_tok == TOK_ASM_ror || S->tccpp_tok == TOK_ASM_rrx) | |
| 681 | 681 | break; |
| 682 | − parse_operand(s1, &ops[nb_ops]); | |
| 682 | + parse_operand(S, &ops[nb_ops]); | |
| 683 | 683 | ++nb_ops; |
| 684 | − if (tok != ',') | |
| 684 | + if (S->tccpp_tok != ',') | |
| 685 | 685 | break; |
| 686 | − next(); // skip ',' | |
| 686 | + next(S); // skip ',' | |
| 687 | 687 | } |
| 688 | − if (tok == ',') | |
| 689 | − next(); | |
| 690 | − operands |= asm_parse_optional_shift(s1, &nb_shift, &shift); | |
| 688 | + if (S->tccpp_tok == ',') | |
| 689 | + next(S); | |
| 690 | + operands |= asm_parse_optional_shift(S, &nb_shift, &shift); | |
| 691 | 691 | if (nb_ops < 2) |
| 692 | − expect("at least two operands"); | |
| 692 | + expect(S, "at least two operands"); | |
| 693 | 693 | else if (nb_ops == 2) { |
| 694 | 694 | memcpy(&ops[2], &ops[1], sizeof(ops[1])); // move ops[2] |
| 695 | 695 | memcpy(&ops[1], &ops[0], sizeof(ops[0])); // ops[1] was implicit |
| 696 | 696 | nb_ops = 3; |
| 697 | 697 | } else if (nb_ops == 3) { |
| 698 | 698 | if (opcode_nos == 0xd || opcode_nos == 0xf || opcode_nos == 0xa || opcode_nos == 0xb || opcode_nos == 0x8 || opcode_nos == 0x9) { // mov, mvn, cmp, cmn, tst, teq |
| 699 | − tcc_error("'%s' cannot be used with three operands", get_tok_str(token, NULL)); | |
| 699 | + tcc_error(S, "'%s' cannot be used with three operands", get_tok_str(S, token, NULL)); | |
| 700 | 700 | return; |
| 701 | 701 | } |
| 702 | 702 | } |
| 703 | 703 | if (nb_ops != 3) { |
| 704 | − expect("two or three operands"); | |
| 704 | + expect(S, "two or three operands"); | |
| 705 | 705 | return; |
| 706 | 706 | } else { |
| 707 | 707 | uint32_t opcode = 0; |
| @@ -710,7 +710,7 @@ static void asm_data_processing_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 710 | 710 | if (nb_shift && shift.type == OP_REG32) { |
| 711 | 711 | if ((ops[0].type == OP_REG32 && ops[0].reg == 15) || |
| 712 | 712 | (ops[1].type == OP_REG32 && ops[1].reg == 15)) { |
| 713 | − tcc_error("Using the 'pc' register in data processing instructions that have a register-controlled shift is not implemented by ARM"); | |
| 713 | + tcc_error(S, "Using the 'pc' register in data processing instructions that have a register-controlled shift is not implemented by ARM"); | |
| 714 | 714 | return; |
| 715 | 715 | } |
| 716 | 716 | } |
| @@ -726,13 +726,13 @@ static void asm_data_processing_opcode(TCCState *s1, int token) · 9 unmodified lines | ||
| 726 | 726 | /* operations in the token list are ordered by opcode */ |
| 727 | 727 | opcode = opcode_nos << 21; // drop "s" |
| 728 | 728 | if (ops[0].type != OP_REG32) |
| 729 | − expect("(destination operand) register"); | |
| 729 | + expect(S, "(destination operand) register"); | |
| 730 | 730 | else if (opcode_nos == 0xa || opcode_nos == 0xb || opcode_nos == 0x8 || opcode_nos == 0x9) // cmp, cmn, tst, teq |
| 731 | 731 | operands |= ENCODE_SET_CONDITION_CODES; // force S set, otherwise it's a completely different instruction. |
| 732 | 732 | else |
| 733 | 733 | operands |= ENCODE_RD(ops[0].reg); |
| 734 | 734 | if (ops[1].type != OP_REG32) |
| 735 | − expect("(first source operand) register"); | |
| 735 | + expect(S, "(first source operand) register"); | |
| 736 | 736 | else if (!(opcode_nos == 0xd || opcode_nos == 0xf)) // not: mov, mvn (those have only one source operand) |
| 737 | 737 | operands |= ENCODE_RN(ops[1].reg); |
| 738 | 738 | switch (ops[2].type) { |
| @@ -809,7 +809,7 @@ static void asm_data_processing_opcode(TCCState *s1, int token) · 70 unmodified lines | ||
| 809 | 809 | immediate_value = ~immediate_value; |
| 810 | 810 | break; |
| 811 | 811 | default: |
| 812 | − tcc_error("cannot use '%s' with a negative immediate value", get_tok_str(token, NULL)); | |
| 812 | + tcc_error(S, "cannot use '%s' with a negative immediate value", get_tok_str(S, token, NULL)); | |
| 813 | 813 | } |
| 814 | 814 | for (half_immediate_rotation = 0; half_immediate_rotation < 16; ++half_immediate_rotation) { |
| 815 | 815 | if (immediate_value >= 0x00 && immediate_value < 0x100) |
| @@ -819,30 +819,30 @@ static void asm_data_processing_opcode(TCCState *s1, int token) · 3 unmodified lines | ||
| 819 | 819 | } |
| 820 | 820 | if (half_immediate_rotation >= 16) { |
| 821 | 821 | immediate_value = ops[2].e.v; |
| 822 | − tcc_error("immediate value 0x%X cannot be encoded into ARM immediate", (unsigned) immediate_value); | |
| 822 | + tcc_error(S, "immediate value 0x%X cannot be encoded into ARM immediate", (unsigned) immediate_value); | |
| 823 | 823 | return; |
| 824 | 824 | } |
| 825 | 825 | operands |= immediate_value; |
| 826 | 826 | operands |= half_immediate_rotation << 8; |
| 827 | 827 | break; |
| 828 | 828 | default: |
| 829 | − expect("(second source operand) register or immediate value"); | |
| 829 | + expect(S, "(second source operand) register or immediate value"); | |
| 830 | 830 | } |
| 831 | 831 | |
| 832 | 832 | if (nb_shift) { |
| 833 | 833 | if (operands & ENCODE_IMMEDIATE_FLAG) |
| 834 | − tcc_error("immediate rotation not implemented"); | |
| 834 | + tcc_error(S, "immediate rotation not implemented"); | |
| 835 | 835 | else |
| 836 | − operands |= asm_encode_shift(&shift); | |
| 836 | + operands |= asm_encode_shift(S, &shift); | |
| 837 | 837 | } |
| 838 | 838 | |
| 839 | 839 | /* S=0 and S=1 entries alternate one after another, in that order */ |
| 840 | 840 | opcode |= (opcode_idx & 1) ? ENCODE_SET_CONDITION_CODES : 0; |
| 841 | − asm_emit_opcode(token, opcode | operands); | |
| 841 | + asm_emit_opcode(S, token, opcode | operands); | |
| 842 | 842 | } |
| 843 | 843 | } |
| 844 | 844 | |
| 845 | −static void asm_shift_opcode(TCCState *s1, int token) | |
| 845 | +static void asm_shift_opcode(TCCState *S, int token) | |
| 846 | 846 | { |
| 847 | 847 | Operand ops[3]; |
| 848 | 848 | int nb_ops; |
| @@ -851,20 +851,20 @@ static void asm_shift_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 851 | 851 | uint32_t operands = 0; |
| 852 | 852 | |
| 853 | 853 | for (nb_ops = 0; nb_ops < sizeof(ops)/sizeof(ops[0]); ++nb_ops) { |
| 854 | − parse_operand(s1, &ops[nb_ops]); | |
| 855 | − if (tok != ',') { | |
| 854 | + parse_operand(S, &ops[nb_ops]); | |
| 855 | + if (S->tccpp_tok != ',') { | |
| 856 | 856 | ++nb_ops; |
| 857 | 857 | break; |
| 858 | 858 | } |
| 859 | − next(); // skip ',' | |
| 859 | + next(S); // skip ',' | |
| 860 | 860 | } |
| 861 | 861 | if (nb_ops < 2) { |
| 862 | − expect("at least two operands"); | |
| 862 | + expect(S, "at least two operands"); | |
| 863 | 863 | return; |
| 864 | 864 | } |
| 865 | 865 | |
| 866 | 866 | if (ops[0].type != OP_REG32) { |
| 867 | − expect("(destination operand) register"); | |
| 867 | + expect(S, "(destination operand) register"); | |
| 868 | 868 | return; |
| 869 | 869 | } else |
| 870 | 870 | operands |= ENCODE_RD(ops[0].reg); |
| @@ -878,9 +878,9 @@ static void asm_shift_opcode(TCCState *s1, int token) · 7 unmodified lines | ||
| 878 | 878 | if (ops[1].type == OP_REG32) { |
| 879 | 879 | operands |= ops[1].reg; |
| 880 | 880 | operands |= ENCODE_BARREL_SHIFTER_MODE_ROR; |
| 881 | − asm_emit_opcode(token, opcode | operands); | |
| 881 | + asm_emit_opcode(S, token, opcode | operands); | |
| 882 | 882 | } else |
| 883 | − tcc_error("(first source operand) register"); | |
| 883 | + tcc_error(S, "(first source operand) register"); | |
| 884 | 884 | return; |
| 885 | 885 | default: |
| 886 | 886 | memcpy(&ops[2], &ops[1], sizeof(ops[1])); // move ops[2] |
| @@ -889,7 +889,7 @@ static void asm_shift_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 889 | 889 | } |
| 890 | 890 | } |
| 891 | 891 | if (nb_ops != 3) { |
| 892 | − expect("two or three operands"); | |
| 892 | + expect(S, "two or three operands"); | |
| 893 | 893 | return; |
| 894 | 894 | } |
| 895 | 895 | |
| @@ -909,7 +909,7 @@ static void asm_shift_opcode(TCCState *s1, int token) · 13 unmodified lines | ||
| 909 | 909 | case OP_IM8: |
| 910 | 910 | operands |= ENCODE_IMMEDIATE_FLAG; |
| 911 | 911 | operands |= ops[1].e.v; |
| 912 | − tcc_error("Using an immediate value as the source operand is not possible with '%s' instruction on ARM", get_tok_str(token, NULL)); | |
| 912 | + tcc_error(S, "Using an immediate value as the source operand is not possible with '%s' instruction on ARM", get_tok_str(S, token, NULL)); | |
| 913 | 913 | return; |
| 914 | 914 | } |
| 915 | 915 | |
| @@ -917,13 +917,13 @@ static void asm_shift_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 917 | 917 | case OP_REG32: |
| 918 | 918 | if ((ops[0].type == OP_REG32 && ops[0].reg == 15) || |
| 919 | 919 | (ops[1].type == OP_REG32 && ops[1].reg == 15)) { |
| 920 | − tcc_error("Using the 'pc' register in data processing instructions that have a register-controlled shift is not implemented by ARM"); | |
| 920 | + tcc_error(S, "Using the 'pc' register in data processing instructions that have a register-controlled shift is not implemented by ARM"); | |
| 921 | 921 | } |
| 922 | − operands |= asm_encode_shift(&ops[2]); | |
| 922 | + operands |= asm_encode_shift(S, &ops[2]); | |
| 923 | 923 | break; |
| 924 | 924 | case OP_IM8: |
| 925 | 925 | if (ops[2].e.v) |
| 926 | − operands |= asm_encode_shift(&ops[2]); | |
| 926 | + operands |= asm_encode_shift(S, &ops[2]); | |
| 927 | 927 | else |
| 928 | 928 | definitely_neutral = 1; |
| 929 | 929 | break; |
| @@ -947,28 +947,28 @@ static void asm_shift_opcode(TCCState *s1, int token) · 17 unmodified lines | ||
| 947 | 947 | operands |= ENCODE_BARREL_SHIFTER_MODE_ROR; |
| 948 | 948 | break; |
| 949 | 949 | default: |
| 950 | − expect("shift instruction"); | |
| 950 | + expect(S, "shift instruction"); | |
| 951 | 951 | return; |
| 952 | 952 | } |
| 953 | − asm_emit_opcode(token, opcode | operands); | |
| 953 | + asm_emit_opcode(S, token, opcode | operands); | |
| 954 | 954 | } |
| 955 | 955 | |
| 956 | −static void asm_multiplication_opcode(TCCState *s1, int token) | |
| 956 | +static void asm_multiplication_opcode(TCCState *S, int token) | |
| 957 | 957 | { |
| 958 | 958 | Operand ops[4]; |
| 959 | 959 | int nb_ops = 0; |
| 960 | 960 | uint32_t opcode = 0x90; |
| 961 | 961 | |
| 962 | 962 | for (nb_ops = 0; nb_ops < sizeof(ops)/sizeof(ops[0]); ++nb_ops) { |
| 963 | − parse_operand(s1, &ops[nb_ops]); | |
| 964 | − if (tok != ',') { | |
| 963 | + parse_operand(S, &ops[nb_ops]); | |
| 964 | + if (S->tccpp_tok != ',') { | |
| 965 | 965 | ++nb_ops; |
| 966 | 966 | break; |
| 967 | 967 | } |
| 968 | − next(); // skip ',' | |
| 968 | + next(S); // skip ',' | |
| 969 | 969 | } |
| 970 | 970 | if (nb_ops < 2) |
| 971 | − expect("at least two operands"); | |
| 971 | + expect(S, "at least two operands"); | |
| 972 | 972 | else if (nb_ops == 2) { |
| 973 | 973 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 974 | 974 | case TOK_ASM_mulseq: |
| @@ -976,7 +976,7 @@ static void asm_multiplication_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 976 | 976 | memcpy(&ops[2], &ops[0], sizeof(ops[1])); // ARM is actually like this! |
| 977 | 977 | break; |
| 978 | 978 | default: |
| 979 | − expect("at least three operands"); | |
| 979 | + expect(S, "at least three operands"); | |
| 980 | 980 | return; |
| 981 | 981 | } |
| 982 | 982 | nb_ops = 3; |
| @@ -992,20 +992,20 @@ static void asm_multiplication_opcode(TCCState *s1, int token) · 9 unmodified lines | ||
| 992 | 992 | if (ops[0].type == OP_REG32) |
| 993 | 993 | opcode |= ops[0].reg << 16; |
| 994 | 994 | else |
| 995 | − expect("(destination operand) register"); | |
| 995 | + expect(S, "(destination operand) register"); | |
| 996 | 996 | if (ops[1].type == OP_REG32) |
| 997 | 997 | opcode |= ops[1].reg; |
| 998 | 998 | else |
| 999 | − expect("(first source operand) register"); | |
| 999 | + expect(S, "(first source operand) register"); | |
| 1000 | 1000 | if (ops[2].type == OP_REG32) |
| 1001 | 1001 | opcode |= ops[2].reg << 8; |
| 1002 | 1002 | else |
| 1003 | − expect("(second source operand) register"); | |
| 1003 | + expect(S, "(second source operand) register"); | |
| 1004 | 1004 | if (nb_ops > 3) { |
| 1005 | 1005 | if (ops[3].type == OP_REG32) |
| 1006 | 1006 | opcode |= ops[3].reg << 12; |
| 1007 | 1007 | else |
| 1008 | − expect("(third source operand) register"); | |
| 1008 | + expect(S, "(third source operand) register"); | |
| 1009 | 1009 | } |
| 1010 | 1010 | |
| 1011 | 1011 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| @@ -1014,9 +1014,9 @@ static void asm_multiplication_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 1014 | 1014 | /* fallthrough */ |
| 1015 | 1015 | case TOK_ASM_muleq: |
| 1016 | 1016 | if (nb_ops != 3) |
| 1017 | − expect("three operands"); | |
| 1017 | + expect(S, "three operands"); | |
| 1018 | 1018 | else { |
| 1019 | − asm_emit_opcode(token, opcode); | |
| 1019 | + asm_emit_opcode(S, token, opcode); | |
| 1020 | 1020 | } |
| 1021 | 1021 | break; |
| 1022 | 1022 | case TOK_ASM_mlaseq: |
| @@ -1024,33 +1024,33 @@ static void asm_multiplication_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 1024 | 1024 | /* fallthrough */ |
| 1025 | 1025 | case TOK_ASM_mlaeq: |
| 1026 | 1026 | if (nb_ops != 4) |
| 1027 | − expect("four operands"); | |
| 1027 | + expect(S, "four operands"); | |
| 1028 | 1028 | else { |
| 1029 | 1029 | opcode |= 1 << 21; // Accumulate |
| 1030 | − asm_emit_opcode(token, opcode); | |
| 1030 | + asm_emit_opcode(S, token, opcode); | |
| 1031 | 1031 | } |
| 1032 | 1032 | break; |
| 1033 | 1033 | default: |
| 1034 | − expect("known multiplication instruction"); | |
| 1034 | + expect(S, "known multiplication instruction"); | |
| 1035 | 1035 | } |
| 1036 | 1036 | } |
| 1037 | 1037 | |
| 1038 | −static void asm_long_multiplication_opcode(TCCState *s1, int token) | |
| 1038 | +static void asm_long_multiplication_opcode(TCCState *S, int token) | |
| 1039 | 1039 | { |
| 1040 | 1040 | Operand ops[4]; |
| 1041 | 1041 | int nb_ops = 0; |
| 1042 | 1042 | uint32_t opcode = 0x90 | (1 << 23); |
| 1043 | 1043 | |
| 1044 | 1044 | for (nb_ops = 0; nb_ops < sizeof(ops)/sizeof(ops[0]); ++nb_ops) { |
| 1045 | − parse_operand(s1, &ops[nb_ops]); | |
| 1046 | − if (tok != ',') { | |
| 1045 | + parse_operand(S, &ops[nb_ops]); | |
| 1046 | + if (S->tccpp_tok != ',') { | |
| 1047 | 1047 | ++nb_ops; |
| 1048 | 1048 | break; |
| 1049 | 1049 | } |
| 1050 | − next(); // skip ',' | |
| 1050 | + next(S); // skip ',' | |
| 1051 | 1051 | } |
| 1052 | 1052 | if (nb_ops != 4) { |
| 1053 | − expect("four operands"); | |
| 1053 | + expect(S, "four operands"); | |
| 1054 | 1054 | return; |
| 1055 | 1055 | } |
| 1056 | 1056 | |
| @@ -1064,19 +1064,19 @@ static void asm_long_multiplication_opcode(TCCState *s1, int token) · 7 unmodified lines | ||
| 1064 | 1064 | if (ops[0].type == OP_REG32) |
| 1065 | 1065 | opcode |= ops[0].reg << 12; |
| 1066 | 1066 | else |
| 1067 | − expect("(destination lo accumulator) register"); | |
| 1067 | + expect(S, "(destination lo accumulator) register"); | |
| 1068 | 1068 | if (ops[1].type == OP_REG32) |
| 1069 | 1069 | opcode |= ops[1].reg << 16; |
| 1070 | 1070 | else |
| 1071 | − expect("(destination hi accumulator) register"); | |
| 1071 | + expect(S, "(destination hi accumulator) register"); | |
| 1072 | 1072 | if (ops[2].type == OP_REG32) |
| 1073 | 1073 | opcode |= ops[2].reg; |
| 1074 | 1074 | else |
| 1075 | − expect("(first source operand) register"); | |
| 1075 | + expect(S, "(first source operand) register"); | |
| 1076 | 1076 | if (ops[3].type == OP_REG32) |
| 1077 | 1077 | opcode |= ops[3].reg << 8; |
| 1078 | 1078 | else |
| 1079 | − expect("(second source operand) register"); | |
| 1079 | + expect(S, "(second source operand) register"); | |
| 1080 | 1080 | |
| 1081 | 1081 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 1082 | 1082 | case TOK_ASM_smullseq: |
| @@ -1084,13 +1084,13 @@ static void asm_long_multiplication_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 1084 | 1084 | /* fallthrough */ |
| 1085 | 1085 | case TOK_ASM_smulleq: |
| 1086 | 1086 | opcode |= 1 << 22; // signed |
| 1087 | − asm_emit_opcode(token, opcode); | |
| 1087 | + asm_emit_opcode(S, token, opcode); | |
| 1088 | 1088 | break; |
| 1089 | 1089 | case TOK_ASM_umullseq: |
| 1090 | 1090 | opcode |= 1 << 20; // Status |
| 1091 | 1091 | /* fallthrough */ |
| 1092 | 1092 | case TOK_ASM_umulleq: |
| 1093 | − asm_emit_opcode(token, opcode); | |
| 1093 | + asm_emit_opcode(S, token, opcode); | |
| 1094 | 1094 | break; |
| 1095 | 1095 | case TOK_ASM_smlalseq: |
| 1096 | 1096 | opcode |= 1 << 20; // Status |
| @@ -1098,21 +1098,21 @@ static void asm_long_multiplication_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 1098 | 1098 | case TOK_ASM_smlaleq: |
| 1099 | 1099 | opcode |= 1 << 22; // signed |
| 1100 | 1100 | opcode |= 1 << 21; // Accumulate |
| 1101 | − asm_emit_opcode(token, opcode); | |
| 1101 | + asm_emit_opcode(S, token, opcode); | |
| 1102 | 1102 | break; |
| 1103 | 1103 | case TOK_ASM_umlalseq: |
| 1104 | 1104 | opcode |= 1 << 20; // Status |
| 1105 | 1105 | /* fallthrough */ |
| 1106 | 1106 | case TOK_ASM_umlaleq: |
| 1107 | 1107 | opcode |= 1 << 21; // Accumulate |
| 1108 | − asm_emit_opcode(token, opcode); | |
| 1108 | + asm_emit_opcode(S, token, opcode); | |
| 1109 | 1109 | break; |
| 1110 | 1110 | default: |
| 1111 | − expect("known long multiplication instruction"); | |
| 1111 | + expect(S, "known long multiplication instruction"); | |
| 1112 | 1112 | } |
| 1113 | 1113 | } |
| 1114 | 1114 | |
| 1115 | −static void asm_single_data_transfer_opcode(TCCState *s1, int token) | |
| 1115 | +static void asm_single_data_transfer_opcode(TCCState *S, int token) | |
| 1116 | 1116 | { |
| 1117 | 1117 | Operand ops[3]; |
| 1118 | 1118 | Operand strex_operand; |
| @@ -1126,67 +1126,67 @@ static void asm_single_data_transfer_opcode(TCCState *s1, int token) · 7 unmodified lines | ||
| 1126 | 1126 | // Note: ldr r0, [r4, #4]! ; pre-indexed: r0 = *(int*)(r4+4); r4 = r4+4 |
| 1127 | 1127 | // Note: ldr r0, [r4], #4 ; post-indexed: r0 = *(int*)(r4+0); r4 = r4+4 |
| 1128 | 1128 | |
| 1129 | − parse_operand(s1, &ops[0]); | |
| 1129 | + parse_operand(S, &ops[0]); | |
| 1130 | 1130 | if (ops[0].type == OP_REG32) |
| 1131 | 1131 | opcode |= ENCODE_RD(ops[0].reg); |
| 1132 | 1132 | else { |
| 1133 | − expect("(destination operand) register"); | |
| 1133 | + expect(S, "(destination operand) register"); | |
| 1134 | 1134 | return; |
| 1135 | 1135 | } |
| 1136 | − if (tok != ',') | |
| 1137 | − expect("at least two arguments"); | |
| 1136 | + if (S->tccpp_tok != ',') | |
| 1137 | + expect(S, "at least two arguments"); | |
| 1138 | 1138 | else |
| 1139 | − next(); // skip ',' | |
| 1139 | + next(S); // skip ',' | |
| 1140 | 1140 | |
| 1141 | 1141 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 1142 | 1142 | case TOK_ASM_strexbeq: |
| 1143 | 1143 | case TOK_ASM_strexeq: |
| 1144 | − parse_operand(s1, &strex_operand); | |
| 1144 | + parse_operand(S, &strex_operand); | |
| 1145 | 1145 | if (strex_operand.type != OP_REG32) { |
| 1146 | − expect("register"); | |
| 1146 | + expect(S, "register"); | |
| 1147 | 1147 | return; |
| 1148 | 1148 | } |
| 1149 | − if (tok != ',') | |
| 1150 | − expect("at least three arguments"); | |
| 1149 | + if (S->tccpp_tok != ',') | |
| 1150 | + expect(S, "at least three arguments"); | |
| 1151 | 1151 | else |
| 1152 | − next(); // skip ',' | |
| 1152 | + next(S); // skip ',' | |
| 1153 | 1153 | break; |
| 1154 | 1154 | } |
| 1155 | 1155 | |
| 1156 | − if (tok != '[') | |
| 1157 | − expect("'['"); | |
| 1156 | + if (S->tccpp_tok != '[') | |
| 1157 | + expect(S, "'['"); | |
| 1158 | 1158 | else |
| 1159 | − next(); // skip '[' | |
| 1159 | + next(S); // skip '[' | |
| 1160 | 1160 | |
| 1161 | − parse_operand(s1, &ops[1]); | |
| 1161 | + parse_operand(S, &ops[1]); | |
| 1162 | 1162 | if (ops[1].type == OP_REG32) |
| 1163 | 1163 | opcode |= ENCODE_RN(ops[1].reg); |
| 1164 | 1164 | else { |
| 1165 | − expect("(first source operand) register"); | |
| 1165 | + expect(S, "(first source operand) register"); | |
| 1166 | 1166 | return; |
| 1167 | 1167 | } |
| 1168 | − if (tok == ']') { | |
| 1169 | − next(); | |
| 1168 | + if (S->tccpp_tok == ']') { | |
| 1169 | + next(S); | |
| 1170 | 1170 | closed_bracket = 1; |
| 1171 | 1171 | // exclam = 1; // implicit in hardware; don't do it in software |
| 1172 | 1172 | } |
| 1173 | − if (tok == ',') { | |
| 1174 | − next(); // skip ',' | |
| 1175 | − if (tok == '-') { | |
| 1173 | + if (S->tccpp_tok == ',') { | |
| 1174 | + next(S); // skip ',' | |
| 1175 | + if (S->tccpp_tok == '-') { | |
| 1176 | 1176 | op2_minus = 1; |
| 1177 | − next(); | |
| 1177 | + next(S); | |
| 1178 | 1178 | } |
| 1179 | − parse_operand(s1, &ops[2]); | |
| 1179 | + parse_operand(S, &ops[2]); | |
| 1180 | 1180 | if (ops[2].type == OP_REG32) { |
| 1181 | 1181 | if (ops[2].reg == 15) { |
| 1182 | − tcc_error("Using 'pc' for register offset in '%s' is not implemented by ARM", get_tok_str(token, NULL)); | |
| 1182 | + tcc_error(S, "Using 'pc' for register offset in '%s' is not implemented by ARM", get_tok_str(S, token, NULL)); | |
| 1183 | 1183 | return; |
| 1184 | 1184 | } |
| 1185 | − if (tok == ',') { | |
| 1186 | − next(); | |
| 1187 | − opcode |= asm_parse_optional_shift(s1, &nb_shift, &shift); | |
| 1185 | + if (S->tccpp_tok == ',') { | |
| 1186 | + next(S); | |
| 1187 | + opcode |= asm_parse_optional_shift(S, &nb_shift, &shift); | |
| 1188 | 1188 | if (opcode == 0) |
| 1189 | − expect("shift directive, or no comma"); | |
| 1189 | + expect(S, "shift directive, or no comma"); | |
| 1190 | 1190 | } |
| 1191 | 1191 | } |
| 1192 | 1192 | } else { |
| @@ -1196,14 +1196,14 @@ static void asm_single_data_transfer_opcode(TCCState *s1, int token) · 3 unmodified lines | ||
| 1196 | 1196 | opcode |= 1 << 24; // add offset before transfer |
| 1197 | 1197 | } |
| 1198 | 1198 | if (!closed_bracket) { |
| 1199 | − if (tok != ']') | |
| 1200 | − expect("']'"); | |
| 1199 | + if (S->tccpp_tok != ']') | |
| 1200 | + expect(S, "']'"); | |
| 1201 | 1201 | else |
| 1202 | − next(); // skip ']' | |
| 1202 | + next(S); // skip ']' | |
| 1203 | 1203 | opcode |= 1 << 24; // add offset before transfer |
| 1204 | − if (tok == '!') { | |
| 1204 | + if (S->tccpp_tok == '!') { | |
| 1205 | 1205 | exclam = 1; |
| 1206 | − next(); // skip '!' | |
| 1206 | + next(S); // skip '!' | |
| 1207 | 1207 | } |
| 1208 | 1208 | } |
| 1209 | 1209 | |
| @@ -1224,16 +1224,16 @@ static void asm_single_data_transfer_opcode(TCCState *s1, int token) · 14 unmodified lines | ||
| 1224 | 1224 | if (ops[2].type == OP_IM32 || ops[2].type == OP_IM8 || ops[2].type == OP_IM8N) { |
| 1225 | 1225 | int v = ops[2].e.v; |
| 1226 | 1226 | if (op2_minus) |
| 1227 | − tcc_error("minus before '#' not supported for immediate values"); | |
| 1227 | + tcc_error(S, "minus before '#' not supported for immediate values"); | |
| 1228 | 1228 | if (v >= 0) { |
| 1229 | 1229 | opcode |= 1 << 23; // up |
| 1230 | 1230 | if (v >= 0x1000) |
| 1231 | − tcc_error("offset out of range for '%s'", get_tok_str(token, NULL)); | |
| 1231 | + tcc_error(S, "offset out of range for '%s'", get_tok_str(S, token, NULL)); | |
| 1232 | 1232 | else |
| 1233 | 1233 | opcode |= v; |
| 1234 | 1234 | } else { // down |
| 1235 | 1235 | if (v <= -0x1000) |
| 1236 | − tcc_error("offset out of range for '%s'", get_tok_str(token, NULL)); | |
| 1236 | + tcc_error(S, "offset out of range for '%s'", get_tok_str(S, token, NULL)); | |
| 1237 | 1237 | else |
| 1238 | 1238 | opcode |= -v; |
| 1239 | 1239 | } |
| @@ -1243,7 +1243,7 @@ static void asm_single_data_transfer_opcode(TCCState *s1, int token) · 3 unmodified lines | ||
| 1243 | 1243 | opcode |= ENCODE_IMMEDIATE_FLAG; /* if set, it means it's NOT immediate */ |
| 1244 | 1244 | opcode |= ops[2].reg; |
| 1245 | 1245 | } else |
| 1246 | − expect("register"); | |
| 1246 | + expect(S, "register"); | |
| 1247 | 1247 | |
| 1248 | 1248 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 1249 | 1249 | case TOK_ASM_strbeq: |
| @@ -1252,8 +1252,8 @@ static void asm_single_data_transfer_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 1252 | 1252 | case TOK_ASM_streq: |
| 1253 | 1253 | opcode |= 1 << 26; // Load/Store |
| 1254 | 1254 | if (nb_shift) |
| 1255 | − opcode |= asm_encode_shift(&shift); | |
| 1256 | − asm_emit_opcode(token, opcode); | |
| 1255 | + opcode |= asm_encode_shift(S, &shift); | |
| 1256 | + asm_emit_opcode(S, token, opcode); | |
| 1257 | 1257 | break; |
| 1258 | 1258 | case TOK_ASM_ldrbeq: |
| 1259 | 1259 | opcode |= 1 << 22; // B |
| @@ -1262,56 +1262,56 @@ static void asm_single_data_transfer_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 1262 | 1262 | opcode |= 1 << 20; // L |
| 1263 | 1263 | opcode |= 1 << 26; // Load/Store |
| 1264 | 1264 | if (nb_shift) |
| 1265 | − opcode |= asm_encode_shift(&shift); | |
| 1266 | − asm_emit_opcode(token, opcode); | |
| 1265 | + opcode |= asm_encode_shift(S, &shift); | |
| 1266 | + asm_emit_opcode(S, token, opcode); | |
| 1267 | 1267 | break; |
| 1268 | 1268 | case TOK_ASM_strexbeq: |
| 1269 | 1269 | opcode |= 1 << 22; // B |
| 1270 | 1270 | /* fallthrough */ |
| 1271 | 1271 | case TOK_ASM_strexeq: |
| 1272 | 1272 | if ((opcode & 0xFFF) || nb_shift) { |
| 1273 | − tcc_error("neither offset nor shift allowed with 'strex'"); | |
| 1273 | + tcc_error(S, "neither offset nor shift allowed with 'strex'"); | |
| 1274 | 1274 | return; |
| 1275 | 1275 | } else if (opcode & ENCODE_IMMEDIATE_FLAG) { // if set, it means it's NOT immediate |
| 1276 | − tcc_error("offset not allowed with 'strex'"); | |
| 1276 | + tcc_error(S, "offset not allowed with 'strex'"); | |
| 1277 | 1277 | return; |
| 1278 | 1278 | } |
| 1279 | 1279 | if ((opcode & (1 << 24)) == 0) { // add offset after transfer |
| 1280 | − tcc_error("adding offset after transfer not allowed with 'strex'"); | |
| 1280 | + tcc_error(S, "adding offset after transfer not allowed with 'strex'"); | |
| 1281 | 1281 | return; |
| 1282 | 1282 | } |
| 1283 | 1283 | |
| 1284 | 1284 | opcode |= 0xf90; // Used to mean: barrel shifter is enabled, barrel shift register is r15, mode is LSL |
| 1285 | 1285 | opcode |= strex_operand.reg; |
| 1286 | − asm_emit_opcode(token, opcode); | |
| 1286 | + asm_emit_opcode(S, token, opcode); | |
| 1287 | 1287 | break; |
| 1288 | 1288 | case TOK_ASM_ldrexbeq: |
| 1289 | 1289 | opcode |= 1 << 22; // B |
| 1290 | 1290 | /* fallthrough */ |
| 1291 | 1291 | case TOK_ASM_ldrexeq: |
| 1292 | 1292 | if ((opcode & 0xFFF) || nb_shift) { |
| 1293 | − tcc_error("neither offset nor shift allowed with 'ldrex'"); | |
| 1293 | + tcc_error(S, "neither offset nor shift allowed with 'ldrex'"); | |
| 1294 | 1294 | return; |
| 1295 | 1295 | } else if (opcode & ENCODE_IMMEDIATE_FLAG) { // if set, it means it's NOT immediate |
| 1296 | − tcc_error("offset not allowed with 'ldrex'"); | |
| 1296 | + tcc_error(S, "offset not allowed with 'ldrex'"); | |
| 1297 | 1297 | return; |
| 1298 | 1298 | } |
| 1299 | 1299 | if ((opcode & (1 << 24)) == 0) { // add offset after transfer |
| 1300 | − tcc_error("adding offset after transfer not allowed with 'ldrex'"); | |
| 1300 | + tcc_error(S, "adding offset after transfer not allowed with 'ldrex'"); | |
| 1301 | 1301 | return; |
| 1302 | 1302 | } |
| 1303 | 1303 | opcode |= 1 << 20; // L |
| 1304 | 1304 | opcode |= 0x00f; |
| 1305 | 1305 | opcode |= 0xf90; // Used to mean: barrel shifter is enabled, barrel shift register is r15, mode is LSL |
| 1306 | − asm_emit_opcode(token, opcode); | |
| 1306 | + asm_emit_opcode(S, token, opcode); | |
| 1307 | 1307 | break; |
| 1308 | 1308 | default: |
| 1309 | − expect("data transfer instruction"); | |
| 1309 | + expect(S, "data transfer instruction"); | |
| 1310 | 1310 | } |
| 1311 | 1311 | } |
| 1312 | 1312 | |
| 1313 | 1313 | // Note: Only call this using a VFP register if you know exactly what you are doing (i.e. cp_number is 10 or 11 and you are doing a vmov) |
| 1314 | −static void asm_emit_coprocessor_data_transfer(uint32_t high_nibble, uint8_t cp_number, uint8_t CRd, const Operand* Rn, const Operand* offset, int offset_minus, int preincrement, int writeback, int long_transfer, int load) { | |
| 1314 | +static void asm_emit_coprocessor_data_transfer(TCCState *S, uint32_t high_nibble, uint8_t cp_number, uint8_t CRd, const Operand* Rn, const Operand* offset, int offset_minus, int preincrement, int writeback, int long_transfer, int load) { | |
| 1315 | 1315 | uint32_t opcode = 0x0; |
| 1316 | 1316 | opcode |= 1 << 26; // Load/Store |
| 1317 | 1317 | opcode |= 1 << 27; // coprocessor |
| @@ -1328,7 +1328,7 @@ static void asm_emit_coprocessor_data_transfer(uint32_t high_nibble, uint8_t cp_ · 10 unmodified lines | ||
| 1328 | 1328 | opcode |= ENCODE_RD(CRd); |
| 1329 | 1329 | |
| 1330 | 1330 | if (Rn->type != OP_REG32) { |
| 1331 | − expect("register"); | |
| 1331 | + expect(S, "register"); | |
| 1332 | 1332 | return; |
| 1333 | 1333 | } |
| 1334 | 1334 | //assert(Rn->reg < 16); |
| @@ -1342,18 +1342,18 @@ static void asm_emit_coprocessor_data_transfer(uint32_t high_nibble, uint8_t cp_ · 7 unmodified lines | ||
| 1342 | 1342 | if (offset->type == OP_IM8 || offset->type == OP_IM8N || offset->type == OP_IM32) { |
| 1343 | 1343 | int v = offset->e.v; |
| 1344 | 1344 | if (offset_minus) |
| 1345 | − tcc_error("minus before '#' not supported for immediate values"); | |
| 1345 | + tcc_error(S, "minus before '#' not supported for immediate values"); | |
| 1346 | 1346 | if (offset->type == OP_IM8N || v < 0) |
| 1347 | 1347 | v = -v; |
| 1348 | 1348 | else |
| 1349 | 1349 | opcode |= 1 << 23; // up |
| 1350 | 1350 | if (v & 3) { |
| 1351 | − tcc_error("immediate offset must be a multiple of 4"); | |
| 1351 | + tcc_error(S, "immediate offset must be a multiple of 4"); | |
| 1352 | 1352 | return; |
| 1353 | 1353 | } |
| 1354 | 1354 | v >>= 2; |
| 1355 | 1355 | if (v > 255) { |
| 1356 | − tcc_error("immediate offset must be between -1020 and 1020"); | |
| 1356 | + tcc_error(S, "immediate offset must be between -1020 and 1020"); | |
| 1357 | 1357 | return; |
| 1358 | 1358 | } |
| 1359 | 1359 | opcode |= v; |
| @@ -1362,20 +1362,20 @@ static void asm_emit_coprocessor_data_transfer(uint32_t high_nibble, uint8_t cp_ · 2 unmodified lines | ||
| 1362 | 1362 | opcode |= 1 << 23; // up |
| 1363 | 1363 | opcode |= ENCODE_IMMEDIATE_FLAG; /* if set, it means it's NOT immediate */ |
| 1364 | 1364 | opcode |= offset->reg; |
| 1365 | − tcc_error("Using register offset to register address is not possible here"); | |
| 1365 | + tcc_error(S, "Using register offset to register address is not possible here"); | |
| 1366 | 1366 | return; |
| 1367 | 1367 | } else if (offset->type == OP_VREG64) { |
| 1368 | 1368 | opcode |= 16; |
| 1369 | 1369 | opcode |= offset->reg; |
| 1370 | 1370 | } else |
| 1371 | − expect("immediate or register"); | |
| 1371 | + expect(S, "immediate or register"); | |
| 1372 | 1372 | |
| 1373 | − asm_emit_unconditional_opcode((high_nibble << 28) | opcode); | |
| 1373 | + asm_emit_unconditional_opcode(S, (high_nibble << 28) | opcode); | |
| 1374 | 1374 | } |
| 1375 | 1375 | |
| 1376 | 1376 | // Almost exactly the same as asm_single_data_transfer_opcode. |
| 1377 | 1377 | // Difference: Offsets are smaller and multiples of 4; no shifts, no STREX, ENCODE_IMMEDIATE_FLAG is inverted again. |
| 1378 | −static void asm_coprocessor_data_transfer_opcode(TCCState *s1, int token) | |
| 1378 | +static void asm_coprocessor_data_transfer_opcode(TCCState *S, int token) | |
| 1379 | 1379 | { |
| 1380 | 1380 | Operand ops[3]; |
| 1381 | 1381 | uint8_t coprocessor; |
| @@ -1389,61 +1389,61 @@ static void asm_coprocessor_data_transfer_opcode(TCCState *s1, int token) · 7 unmodified lines | ||
| 1389 | 1389 | // Note: ldc p2, c0, [r4, #4]! ; pre-indexed: r0 = *(int*)(r4+4); r4 = r4+4 |
| 1390 | 1390 | // Note: ldc p3, c0, [r4], #4 ; post-indexed: r0 = *(int*)(r4+0); r4 = r4+4 |
| 1391 | 1391 | |
| 1392 | − if (tok >= TOK_ASM_p0 && tok <= TOK_ASM_p15) { | |
| 1393 | − coprocessor = tok - TOK_ASM_p0; | |
| 1394 | − next(); | |
| 1392 | + if (S->tccpp_tok >= TOK_ASM_p0 && S->tccpp_tok <= TOK_ASM_p15) { | |
| 1393 | + coprocessor = S->tccpp_tok - TOK_ASM_p0; | |
| 1394 | + next(S); | |
| 1395 | 1395 | } else { |
| 1396 | − expect("'c<number>'"); | |
| 1396 | + expect(S, "'c<number>'"); | |
| 1397 | 1397 | return; |
| 1398 | 1398 | } |
| 1399 | 1399 | |
| 1400 | − if (tok == ',') | |
| 1401 | − next(); | |
| 1400 | + if (S->tccpp_tok == ',') | |
| 1401 | + next(S); | |
| 1402 | 1402 | else |
| 1403 | − expect("','"); | |
| 1403 | + expect(S, "','"); | |
| 1404 | 1404 | |
| 1405 | − if (tok >= TOK_ASM_c0 && tok <= TOK_ASM_c15) { | |
| 1406 | − coprocessor_destination_register = tok - TOK_ASM_c0; | |
| 1407 | − next(); | |
| 1405 | + if (S->tccpp_tok >= TOK_ASM_c0 && S->tccpp_tok <= TOK_ASM_c15) { | |
| 1406 | + coprocessor_destination_register = S->tccpp_tok - TOK_ASM_c0; | |
| 1407 | + next(S); | |
| 1408 | 1408 | } else { |
| 1409 | − expect("'c<number>'"); | |
| 1409 | + expect(S, "'c<number>'"); | |
| 1410 | 1410 | return; |
| 1411 | 1411 | } |
| 1412 | 1412 | |
| 1413 | − if (tok == ',') | |
| 1414 | − next(); | |
| 1413 | + if (S->tccpp_tok == ',') | |
| 1414 | + next(S); | |
| 1415 | 1415 | else |
| 1416 | − expect("','"); | |
| 1416 | + expect(S, "','"); | |
| 1417 | 1417 | |
| 1418 | − if (tok != '[') | |
| 1419 | − expect("'['"); | |
| 1418 | + if (S->tccpp_tok != '[') | |
| 1419 | + expect(S, "'['"); | |
| 1420 | 1420 | else |
| 1421 | − next(); // skip '[' | |
| 1421 | + next(S); // skip '[' | |
| 1422 | 1422 | |
| 1423 | − parse_operand(s1, &ops[1]); | |
| 1423 | + parse_operand(S, &ops[1]); | |
| 1424 | 1424 | if (ops[1].type != OP_REG32) { |
| 1425 | − expect("(first source operand) register"); | |
| 1425 | + expect(S, "(first source operand) register"); | |
| 1426 | 1426 | return; |
| 1427 | 1427 | } |
| 1428 | − if (tok == ']') { | |
| 1429 | − next(); | |
| 1428 | + if (S->tccpp_tok == ']') { | |
| 1429 | + next(S); | |
| 1430 | 1430 | closed_bracket = 1; |
| 1431 | 1431 | // exclam = 1; // implicit in hardware; don't do it in software |
| 1432 | 1432 | } |
| 1433 | − if (tok == ',') { | |
| 1434 | − next(); // skip ',' | |
| 1435 | − if (tok == '-') { | |
| 1433 | + if (S->tccpp_tok == ',') { | |
| 1434 | + next(S); // skip ',' | |
| 1435 | + if (S->tccpp_tok == '-') { | |
| 1436 | 1436 | op2_minus = 1; |
| 1437 | − next(); | |
| 1437 | + next(S); | |
| 1438 | 1438 | } |
| 1439 | − parse_operand(s1, &ops[2]); | |
| 1439 | + parse_operand(S, &ops[2]); | |
| 1440 | 1440 | if (ops[2].type == OP_REG32) { |
| 1441 | 1441 | if (ops[2].reg == 15) { |
| 1442 | − tcc_error("Using 'pc' for register offset in '%s' is not implemented by ARM", get_tok_str(token, NULL)); | |
| 1442 | + tcc_error(S, "Using 'pc' for register offset in '%s' is not implemented by ARM", get_tok_str(S, token, NULL)); | |
| 1443 | 1443 | return; |
| 1444 | 1444 | } |
| 1445 | 1445 | } else if (ops[2].type == OP_VREG64) { |
| 1446 | − tcc_error("'%s' does not support VFP register operand", get_tok_str(token, NULL)); | |
| 1446 | + tcc_error(S, "'%s' does not support VFP register operand", get_tok_str(S, token, NULL)); | |
| 1447 | 1447 | return; |
| 1448 | 1448 | } |
| 1449 | 1449 | } else { |
| @@ -1453,14 +1453,14 @@ static void asm_coprocessor_data_transfer_opcode(TCCState *s1, int token) · 3 unmodified lines | ||
| 1453 | 1453 | preincrement = 1; // add offset before transfer |
| 1454 | 1454 | } |
| 1455 | 1455 | if (!closed_bracket) { |
| 1456 | − if (tok != ']') | |
| 1457 | − expect("']'"); | |
| 1456 | + if (S->tccpp_tok != ']') | |
| 1457 | + expect(S, "']'"); | |
| 1458 | 1458 | else |
| 1459 | − next(); // skip ']' | |
| 1459 | + next(S); // skip ']' | |
| 1460 | 1460 | preincrement = 1; // add offset before transfer |
| 1461 | − if (tok == '!') { | |
| 1461 | + if (S->tccpp_tok == '!') { | |
| 1462 | 1462 | exclam = 1; |
| 1463 | − next(); // skip '!' | |
| 1463 | + next(S); // skip '!' | |
| 1464 | 1464 | } |
| 1465 | 1465 | } |
| 1466 | 1466 | |
| @@ -1472,13 +1472,13 @@ static void asm_coprocessor_data_transfer_opcode(TCCState *s1, int token) · 5 unmodified lines | ||
| 1472 | 1472 | long_transfer = 1; // long transfer |
| 1473 | 1473 | /* fallthrough */ |
| 1474 | 1474 | case TOK_ASM_ldc2: |
| 1475 | − asm_emit_coprocessor_data_transfer(0xF, coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 1); | |
| 1475 | + asm_emit_coprocessor_data_transfer(S, 0xF, coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 1); | |
| 1476 | 1476 | break; |
| 1477 | 1477 | case TOK_ASM_stc2l: |
| 1478 | 1478 | long_transfer = 1; // long transfer |
| 1479 | 1479 | /* fallthrough */ |
| 1480 | 1480 | case TOK_ASM_stc2: |
| 1481 | − asm_emit_coprocessor_data_transfer(0xF, coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 0); | |
| 1481 | + asm_emit_coprocessor_data_transfer(S, 0xF, coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 0); | |
| 1482 | 1482 | break; |
| 1483 | 1483 | } |
| 1484 | 1484 | } else switch (ARM_INSTRUCTION_GROUP(token)) { |
| @@ -1486,16 +1486,16 @@ static void asm_coprocessor_data_transfer_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 1486 | 1486 | long_transfer = 1; |
| 1487 | 1487 | /* fallthrough */ |
| 1488 | 1488 | case TOK_ASM_stceq: |
| 1489 | − asm_emit_coprocessor_data_transfer(condition_code_of_token(token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 0); | |
| 1489 | + asm_emit_coprocessor_data_transfer(S, condition_code_of_token(S, token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 0); | |
| 1490 | 1490 | break; |
| 1491 | 1491 | case TOK_ASM_ldcleq: |
| 1492 | 1492 | long_transfer = 1; |
| 1493 | 1493 | /* fallthrough */ |
| 1494 | 1494 | case TOK_ASM_ldceq: |
| 1495 | − asm_emit_coprocessor_data_transfer(condition_code_of_token(token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 1); | |
| 1495 | + asm_emit_coprocessor_data_transfer(S, condition_code_of_token(S, token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], op2_minus, preincrement, exclam, long_transfer, 1); | |
| 1496 | 1496 | break; |
| 1497 | 1497 | default: |
| 1498 | − expect("coprocessor data transfer instruction"); | |
| 1498 | + expect(S, "coprocessor data transfer instruction"); | |
| 1499 | 1499 | } |
| 1500 | 1500 | } |
| 1501 | 1501 | |
| @@ -1503,7 +1503,7 @@ static void asm_coprocessor_data_transfer_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 1503 | 1503 | #define CP_SINGLE_PRECISION_FLOAT 10 |
| 1504 | 1504 | #define CP_DOUBLE_PRECISION_FLOAT 11 |
| 1505 | 1505 | |
| 1506 | −static void asm_floating_point_single_data_transfer_opcode(TCCState *s1, int token) | |
| 1506 | +static void asm_floating_point_single_data_transfer_opcode(TCCState *S, int token) | |
| 1507 | 1507 | { |
| 1508 | 1508 | Operand ops[3]; |
| 1509 | 1509 | uint8_t coprocessor = 0; |
| @@ -1513,7 +1513,7 @@ static void asm_floating_point_single_data_transfer_opcode(TCCState *s1, int tok · 3 unmodified lines | ||
| 1513 | 1513 | // Note: Not allowed: vldr p2, c0, [r4, #4]! ; pre-indexed: r0 = *(int*)(r4+4); r4 = r4+4 |
| 1514 | 1514 | // Note: Not allowed: vldr p3, c0, [r4], #4 ; post-indexed: r0 = *(int*)(r4+0); r4 = r4+4 |
| 1515 | 1515 | |
| 1516 | − parse_operand(s1, &ops[0]); | |
| 1516 | + parse_operand(S, &ops[0]); | |
| 1517 | 1517 | if (ops[0].type == OP_VREG32) { |
| 1518 | 1518 | coprocessor = CP_SINGLE_PRECISION_FLOAT; |
| 1519 | 1519 | coprocessor_destination_register = ops[0].reg; |
| @@ -1522,32 +1522,32 @@ static void asm_floating_point_single_data_transfer_opcode(TCCState *s1, int tok · 2 unmodified lines | ||
| 1522 | 1522 | } else if (ops[0].type == OP_VREG64) { |
| 1523 | 1523 | coprocessor = CP_DOUBLE_PRECISION_FLOAT; |
| 1524 | 1524 | coprocessor_destination_register = ops[0].reg; |
| 1525 | − next(); | |
| 1525 | + next(S); | |
| 1526 | 1526 | } else { |
| 1527 | − expect("floating point register"); | |
| 1527 | + expect(S, "floating point register"); | |
| 1528 | 1528 | return; |
| 1529 | 1529 | } |
| 1530 | 1530 | |
| 1531 | − if (tok == ',') | |
| 1532 | − next(); | |
| 1531 | + if (S->tccpp_tok == ',') | |
| 1532 | + next(S); | |
| 1533 | 1533 | else |
| 1534 | − expect("','"); | |
| 1534 | + expect(S, "','"); | |
| 1535 | 1535 | |
| 1536 | − if (tok != '[') | |
| 1537 | − expect("'['"); | |
| 1536 | + if (S->tccpp_tok != '[') | |
| 1537 | + expect(S, "'['"); | |
| 1538 | 1538 | else |
| 1539 | − next(); // skip '[' | |
| 1539 | + next(S); // skip '[' | |
| 1540 | 1540 | |
| 1541 | − parse_operand(s1, &ops[1]); | |
| 1541 | + parse_operand(S, &ops[1]); | |
| 1542 | 1542 | if (ops[1].type != OP_REG32) { |
| 1543 | − expect("(first source operand) register"); | |
| 1543 | + expect(S, "(first source operand) register"); | |
| 1544 | 1544 | return; |
| 1545 | 1545 | } |
| 1546 | − if (tok == ',') { | |
| 1547 | − next(); // skip ',' | |
| 1548 | − parse_operand(s1, &ops[2]); | |
| 1546 | + if (S->tccpp_tok == ',') { | |
| 1547 | + next(S); // skip ',' | |
| 1548 | + parse_operand(S, &ops[2]); | |
| 1549 | 1549 | if (ops[2].type != OP_IM8 && ops[2].type != OP_IM8N) { |
| 1550 | − expect("immediate offset"); | |
| 1550 | + expect(S, "immediate offset"); | |
| 1551 | 1551 | return; |
| 1552 | 1552 | } |
| 1553 | 1553 | } else { |
| @@ -1555,24 +1555,24 @@ static void asm_floating_point_single_data_transfer_opcode(TCCState *s1, int tok · 1 unmodified line | ||
| 1555 | 1555 | ops[2].type = OP_IM8; |
| 1556 | 1556 | ops[2].e.v = 0; |
| 1557 | 1557 | } |
| 1558 | − if (tok != ']') | |
| 1559 | − expect("']'"); | |
| 1558 | + if (S->tccpp_tok != ']') | |
| 1559 | + expect(S, "']'"); | |
| 1560 | 1560 | else |
| 1561 | − next(); // skip ']' | |
| 1561 | + next(S); // skip ']' | |
| 1562 | 1562 | |
| 1563 | 1563 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 1564 | 1564 | case TOK_ASM_vldreq: |
| 1565 | − asm_emit_coprocessor_data_transfer(condition_code_of_token(token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], 0, 1, 0, long_transfer, 1); | |
| 1565 | + asm_emit_coprocessor_data_transfer(S, condition_code_of_token(S, token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], 0, 1, 0, long_transfer, 1); | |
| 1566 | 1566 | break; |
| 1567 | 1567 | case TOK_ASM_vstreq: |
| 1568 | − asm_emit_coprocessor_data_transfer(condition_code_of_token(token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], 0, 1, 0, long_transfer, 0); | |
| 1568 | + asm_emit_coprocessor_data_transfer(S, condition_code_of_token(S, token), coprocessor, coprocessor_destination_register, &ops[1], &ops[2], 0, 1, 0, long_transfer, 0); | |
| 1569 | 1569 | break; |
| 1570 | 1570 | default: |
| 1571 | − expect("floating point data transfer instruction"); | |
| 1571 | + expect(S, "floating point data transfer instruction"); | |
| 1572 | 1572 | } |
| 1573 | 1573 | } |
| 1574 | 1574 | |
| 1575 | −static void asm_floating_point_block_data_transfer_opcode(TCCState *s1, int token) | |
| 1575 | +static void asm_floating_point_block_data_transfer_opcode(TCCState *S, int token) | |
| 1576 | 1576 | { |
| 1577 | 1577 | uint8_t coprocessor = 0; |
| 1578 | 1578 | int first_regset_register; |
| @@ -1592,56 +1592,56 @@ static void asm_floating_point_block_data_transfer_opcode(TCCState *s1, int toke · 13 unmodified lines | ||
| 1592 | 1592 | op0_exclam = 1; |
| 1593 | 1593 | break; |
| 1594 | 1594 | default: |
| 1595 | − parse_operand(s1, &ops[0]); | |
| 1596 | − if (tok == '!') { | |
| 1595 | + parse_operand(S, &ops[0]); | |
| 1596 | + if (S->tccpp_tok == '!') { | |
| 1597 | 1597 | op0_exclam = 1; |
| 1598 | − next(); // skip '!' | |
| 1598 | + next(S); // skip '!' | |
| 1599 | 1599 | } |
| 1600 | − if (tok == ',') | |
| 1601 | − next(); // skip comma | |
| 1600 | + if (S->tccpp_tok == ',') | |
| 1601 | + next(S); // skip comma | |
| 1602 | 1602 | else { |
| 1603 | − expect("','"); | |
| 1603 | + expect(S, "','"); | |
| 1604 | 1604 | return; |
| 1605 | 1605 | } |
| 1606 | 1606 | } |
| 1607 | 1607 | |
| 1608 | − if (tok != '{') { | |
| 1609 | − expect("'{'"); | |
| 1608 | + if (S->tccpp_tok != '{') { | |
| 1609 | + expect(S, "'{'"); | |
| 1610 | 1610 | return; |
| 1611 | 1611 | } |
| 1612 | − next(); // skip '{' | |
| 1613 | − first_regset_register = asm_parse_vfp_regvar(tok, 1); | |
| 1614 | − if ((first_regset_register = asm_parse_vfp_regvar(tok, 1)) != -1) { | |
| 1612 | + next(S); // skip '{' | |
| 1613 | + first_regset_register = asm_parse_vfp_regvar(S->tccpp_tok, 1); | |
| 1614 | + if ((first_regset_register = asm_parse_vfp_regvar(S->tccpp_tok, 1)) != -1) { | |
| 1615 | 1615 | coprocessor = CP_DOUBLE_PRECISION_FLOAT; |
| 1616 | − next(); | |
| 1617 | − } else if ((first_regset_register = asm_parse_vfp_regvar(tok, 0)) != -1) { | |
| 1616 | + next(S); | |
| 1617 | + } else if ((first_regset_register = asm_parse_vfp_regvar(S->tccpp_tok, 0)) != -1) { | |
| 1618 | 1618 | coprocessor = CP_SINGLE_PRECISION_FLOAT; |
| 1619 | − next(); | |
| 1619 | + next(S); | |
| 1620 | 1620 | } else { |
| 1621 | − expect("floating-point register"); | |
| 1621 | + expect(S, "floating-point register"); | |
| 1622 | 1622 | return; |
| 1623 | 1623 | } |
| 1624 | 1624 | |
| 1625 | − if (tok == '-') { | |
| 1626 | − next(); | |
| 1627 | − if ((last_regset_register = asm_parse_vfp_regvar(tok, coprocessor == CP_DOUBLE_PRECISION_FLOAT)) != -1) | |
| 1628 | − next(); | |
| 1625 | + if (S->tccpp_tok == '-') { | |
| 1626 | + next(S); | |
| 1627 | + if ((last_regset_register = asm_parse_vfp_regvar(S->tccpp_tok, coprocessor == CP_DOUBLE_PRECISION_FLOAT)) != -1) | |
| 1628 | + next(S); | |
| 1629 | 1629 | else { |
| 1630 | − expect("floating-point register"); | |
| 1630 | + expect(S, "floating-point register"); | |
| 1631 | 1631 | return; |
| 1632 | 1632 | } |
| 1633 | 1633 | } else |
| 1634 | 1634 | last_regset_register = first_regset_register; |
| 1635 | 1635 | |
| 1636 | 1636 | if (last_regset_register < first_regset_register) { |
| 1637 | − tcc_error("registers will be processed in ascending order by hardware--but are not specified in ascending order here"); | |
| 1637 | + tcc_error(S, "registers will be processed in ascending order by hardware--but are not specified in ascending order here"); | |
| 1638 | 1638 | return; |
| 1639 | 1639 | } |
| 1640 | − if (tok != '}') { | |
| 1641 | − expect("'}'"); | |
| 1640 | + if (S->tccpp_tok != '}') { | |
| 1641 | + expect(S, "'}'"); | |
| 1642 | 1642 | return; |
| 1643 | 1643 | } |
| 1644 | − next(); // skip '}' | |
| 1644 | + next(S); // skip '}' | |
| 1645 | 1645 | |
| 1646 | 1646 | // Note: 0 (one down) is not implemented by us regardless. |
| 1647 | 1647 | regset_item_count = last_regset_register - first_regset_register + 1; |
| @@ -1672,23 +1672,23 @@ static void asm_floating_point_block_data_transfer_opcode(TCCState *s1, int toke · 24 unmodified lines | ||
| 1672 | 1672 | preincrement = 1; |
| 1673 | 1673 | break; |
| 1674 | 1674 | default: |
| 1675 | − expect("floating point block data transfer instruction"); | |
| 1675 | + expect(S, "floating point block data transfer instruction"); | |
| 1676 | 1676 | return; |
| 1677 | 1677 | } |
| 1678 | 1678 | if (ops[0].type != OP_REG32) |
| 1679 | − expect("(first operand) register"); | |
| 1679 | + expect(S, "(first operand) register"); | |
| 1680 | 1680 | else if (ops[0].reg == 15) |
| 1681 | − tcc_error("'%s' does not support 'pc' as operand", get_tok_str(token, NULL)); | |
| 1681 | + tcc_error(S, "'%s' does not support 'pc' as operand", get_tok_str(S, token, NULL)); | |
| 1682 | 1682 | else if (!op0_exclam && ARM_INSTRUCTION_GROUP(token) != TOK_ASM_vldmeq && ARM_INSTRUCTION_GROUP(token) != TOK_ASM_vldmiaeq && ARM_INSTRUCTION_GROUP(token) != TOK_ASM_vstmeq && ARM_INSTRUCTION_GROUP(token) != TOK_ASM_vstmiaeq) |
| 1683 | − tcc_error("first operand of '%s' should have an exclamation mark", get_tok_str(token, NULL)); | |
| 1683 | + tcc_error(S, "first operand of '%s' should have an exclamation mark", get_tok_str(S, token, NULL)); | |
| 1684 | 1684 | else |
| 1685 | − asm_emit_coprocessor_data_transfer(condition_code_of_token(token), coprocessor, first_regset_register, &ops[0], &offset, 0, preincrement, op0_exclam, extra_register_bit, load); | |
| 1685 | + asm_emit_coprocessor_data_transfer(S, condition_code_of_token(S, token), coprocessor, first_regset_register, &ops[0], &offset, 0, preincrement, op0_exclam, extra_register_bit, load); | |
| 1686 | 1686 | } |
| 1687 | 1687 | |
| 1688 | 1688 | #define VMOV_FRACTIONAL_DIGITS 7 |
| 1689 | 1689 | #define VMOV_ONE 10000000 /* pow(10, VMOV_FRACTIONAL_DIGITS) */ |
| 1690 | 1690 | |
| 1691 | −static uint32_t vmov_parse_fractional_part(const char* s) | |
| 1691 | +static uint32_t vmov_parse_fractional_part(TCCState* S, const char* s) | |
| 1692 | 1692 | { |
| 1693 | 1693 | uint32_t result = 0; |
| 1694 | 1694 | int i; |
| @@ -1701,7 +1701,7 @@ static uint32_t vmov_parse_fractional_part(const char* s) · 6 unmodified lines | ||
| 1701 | 1701 | } |
| 1702 | 1702 | } |
| 1703 | 1703 | if (*s) |
| 1704 | − expect("decimal numeral"); | |
| 1704 | + expect(S, "decimal numeral"); | |
| 1705 | 1705 | return result; |
| 1706 | 1706 | } |
| 1707 | 1707 | |
| @@ -1720,34 +1720,34 @@ static int vmov_linear_approx_index(uint32_t beginning, uint32_t end, uint32_t v · 12 unmodified lines | ||
| 1720 | 1720 | return -1; |
| 1721 | 1721 | } |
| 1722 | 1722 | |
| 1723 | −static uint32_t vmov_parse_immediate_value() { | |
| 1723 | +static uint32_t vmov_parse_immediate_value(TCCState* S) { | |
| 1724 | 1724 | uint32_t value; |
| 1725 | 1725 | unsigned long integral_value; |
| 1726 | 1726 | const char *p; |
| 1727 | 1727 | |
| 1728 | − if (tok != TOK_PPNUM) { | |
| 1729 | − expect("immediate value"); | |
| 1728 | + if (S->tccpp_tok != TOK_PPNUM) { | |
| 1729 | + expect(S, "immediate value"); | |
| 1730 | 1730 | return 0; |
| 1731 | 1731 | } |
| 1732 | − p = tokc.str.data; | |
| 1732 | + p = S->tccpp_tokc.str.data; | |
| 1733 | 1733 | errno = 0; |
| 1734 | 1734 | integral_value = strtoul(p, (char **)&p, 0); |
| 1735 | 1735 | |
| 1736 | 1736 | if (errno || integral_value >= 32) { |
| 1737 | − tcc_error("invalid floating-point immediate value"); | |
| 1737 | + tcc_error(S, "invalid floating-point immediate value"); | |
| 1738 | 1738 | return 0; |
| 1739 | 1739 | } |
| 1740 | 1740 | |
| 1741 | 1741 | value = (uint32_t) integral_value * VMOV_ONE; |
| 1742 | 1742 | if (*p == '.') { |
| 1743 | 1743 | ++p; |
| 1744 | − value += vmov_parse_fractional_part(p); | |
| 1744 | + value += vmov_parse_fractional_part(S, p); | |
| 1745 | 1745 | } |
| 1746 | − next(); | |
| 1746 | + next(S); | |
| 1747 | 1747 | return value; |
| 1748 | 1748 | } |
| 1749 | 1749 | |
| 1750 | −static uint8_t vmov_encode_immediate_value(uint32_t value) | |
| 1750 | +static uint8_t vmov_encode_immediate_value(TCCState* S, uint32_t value) | |
| 1751 | 1751 | { |
| 1752 | 1752 | uint32_t limit; |
| 1753 | 1753 | uint32_t end = 0; |
| @@ -1767,7 +1767,7 @@ static uint8_t vmov_encode_immediate_value(uint32_t value) · 13 unmodified lines | ||
| 1767 | 1767 | limit >>= 1; |
| 1768 | 1768 | } |
| 1769 | 1769 | if (r == -1 || value < beginning || value > end) { |
| 1770 | − tcc_error("invalid decimal number for vmov: %d", value); | |
| 1770 | + tcc_error(S, "invalid decimal number for vmov: %d", value); | |
| 1771 | 1771 | return 0; |
| 1772 | 1772 | } |
| 1773 | 1773 | n = vmov_linear_approx_index(beginning, end, value); |
| @@ -1775,7 +1775,7 @@ static uint8_t vmov_encode_immediate_value(uint32_t value) · 1 unmodified line | ||
| 1775 | 1775 | } |
| 1776 | 1776 | |
| 1777 | 1777 | // Not standalone. |
| 1778 | −static void asm_floating_point_immediate_data_processing_opcode_tail(TCCState *s1, int token, uint8_t coprocessor, uint8_t CRd) { | |
| 1778 | +static void asm_floating_point_immediate_data_processing_opcode_tail(TCCState *S, int token, uint8_t coprocessor, uint8_t CRd) { | |
| 1779 | 1779 | uint8_t opcode1 = 0; |
| 1780 | 1780 | uint8_t opcode2 = 0; |
| 1781 | 1781 | uint8_t operands[3] = {0, 0, 0}; |
| @@ -1785,14 +1785,14 @@ static void asm_floating_point_immediate_data_processing_opcode_tail(TCCState *s · 3 unmodified lines | ||
| 1785 | 1785 | |
| 1786 | 1786 | operands[0] = CRd; |
| 1787 | 1787 | |
| 1788 | − if (tok == '#' || tok == '$') { | |
| 1789 | − next(); | |
| 1788 | + if (S->tccpp_tok == '#' || S->tccpp_tok == '$') { | |
| 1789 | + next(S); | |
| 1790 | 1790 | } |
| 1791 | − if (tok == '-') { | |
| 1791 | + if (S->tccpp_tok == '-') { | |
| 1792 | 1792 | op_minus = 1; |
| 1793 | − next(); | |
| 1793 | + next(S); | |
| 1794 | 1794 | } |
| 1795 | − immediate_value = vmov_parse_immediate_value(); | |
| 1795 | + immediate_value = vmov_parse_immediate_value(S); | |
| 1796 | 1796 | |
| 1797 | 1797 | opcode1 = 11; // "Other" instruction |
| 1798 | 1798 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| @@ -1801,7 +1801,7 @@ static void asm_floating_point_immediate_data_processing_opcode_tail(TCCState *s · 2 unmodified lines | ||
| 1801 | 1801 | opcode2 = 2; |
| 1802 | 1802 | operands[1] = 5; |
| 1803 | 1803 | if (immediate_value) { |
| 1804 | − expect("Immediate value 0"); | |
| 1804 | + expect(S, "Immediate value 0"); | |
| 1805 | 1805 | return; |
| 1806 | 1806 | } |
| 1807 | 1807 | break; |
| @@ -1810,7 +1810,7 @@ static void asm_floating_point_immediate_data_processing_opcode_tail(TCCState *s · 2 unmodified lines | ||
| 1810 | 1810 | opcode2 = 6; |
| 1811 | 1811 | operands[1] = 5; |
| 1812 | 1812 | if (immediate_value) { |
| 1813 | − expect("Immediate value 0"); | |
| 1813 | + expect(S, "Immediate value 0"); | |
| 1814 | 1814 | return; |
| 1815 | 1815 | } |
| 1816 | 1816 | break; |
| @@ -1821,12 +1821,12 @@ static void asm_floating_point_immediate_data_processing_opcode_tail(TCCState *s · 4 unmodified lines | ||
| 1821 | 1821 | operands[1] = 0x8; |
| 1822 | 1822 | else |
| 1823 | 1823 | operands[1] = 0x0; |
| 1824 | − code = vmov_encode_immediate_value(immediate_value); | |
| 1824 | + code = vmov_encode_immediate_value(S, immediate_value); | |
| 1825 | 1825 | operands[1] |= code >> 4; |
| 1826 | 1826 | operands[2] = code & 0xF; |
| 1827 | 1827 | break; |
| 1828 | 1828 | default: |
| 1829 | − expect("known floating point with immediate instruction"); | |
| 1829 | + expect(S, "known floating point with immediate instruction"); | |
| 1830 | 1830 | return; |
| 1831 | 1831 | } |
| 1832 | 1832 | |
| @@ -1836,17 +1836,17 @@ static void asm_floating_point_immediate_data_processing_opcode_tail(TCCState *s · 3 unmodified lines | ||
| 1836 | 1836 | operands[0] >>= 1; |
| 1837 | 1837 | } |
| 1838 | 1838 | |
| 1839 | − asm_emit_coprocessor_opcode(condition_code_of_token(token), coprocessor, opcode1, operands[0], operands[1], operands[2], opcode2, 0); | |
| 1839 | + asm_emit_coprocessor_opcode(S, condition_code_of_token(S, token), coprocessor, opcode1, operands[0], operands[1], operands[2], opcode2, 0); | |
| 1840 | 1840 | } |
| 1841 | 1841 | |
| 1842 | −static void asm_floating_point_reg_arm_reg_transfer_opcode_tail(TCCState *s1, int token, int coprocessor, int nb_arm_regs, int nb_ops, Operand ops[3]) { | |
| 1842 | +static void asm_floating_point_reg_arm_reg_transfer_opcode_tail(TCCState *S, int token, int coprocessor, int nb_arm_regs, int nb_ops, Operand ops[3]) { | |
| 1843 | 1843 | uint8_t opcode1 = 0; |
| 1844 | 1844 | uint8_t opcode2 = 0; |
| 1845 | 1845 | switch (coprocessor) { |
| 1846 | 1846 | case CP_SINGLE_PRECISION_FLOAT: |
| 1847 | 1847 | // "vmov.f32 r2, s3" or "vmov.f32 s3, r2" |
| 1848 | 1848 | if (nb_ops != 2 || nb_arm_regs != 1) { |
| 1849 | − tcc_error("vmov.f32 only implemented for one VFP register operand and one ARM register operands"); | |
| 1849 | + tcc_error(S, "vmov.f32 only implemented for one VFP register operand and one ARM register operands"); | |
| 1850 | 1850 | return; |
| 1851 | 1851 | } |
| 1852 | 1852 | if (ops[0].type != OP_REG32) { // determine mode: load or store |
| @@ -1869,11 +1869,11 @@ static void asm_floating_point_reg_arm_reg_transfer_opcode_tail(TCCState *s1, in · 16 unmodified lines | ||
| 1869 | 1869 | ops[0].reg >>= 1; |
| 1870 | 1870 | } |
| 1871 | 1871 | |
| 1872 | − asm_emit_coprocessor_opcode(condition_code_of_token(token), coprocessor, opcode1, ops[0].reg, (ops[1].type == OP_IM8) ? ops[1].e.v : ops[1].reg, 0x10, opcode2, 0); | |
| 1872 | + asm_emit_coprocessor_opcode(S, condition_code_of_token(S, token), coprocessor, opcode1, ops[0].reg, (ops[1].type == OP_IM8) ? ops[1].e.v : ops[1].reg, 0x10, opcode2, 0); | |
| 1873 | 1873 | break; |
| 1874 | 1874 | case CP_DOUBLE_PRECISION_FLOAT: |
| 1875 | 1875 | if (nb_ops != 3 || nb_arm_regs != 2) { |
| 1876 | − tcc_error("vmov.f32 only implemented for one VFP register operand and two ARM register operands"); | |
| 1876 | + tcc_error(S, "vmov.f32 only implemented for one VFP register operand and two ARM register operands"); | |
| 1877 | 1877 | return; |
| 1878 | 1878 | } |
| 1879 | 1879 | // Determine whether it's a store into a VFP register (vmov "d1, r2, r3") rather than "vmov r2, r3, d1" |
| @@ -1886,23 +1886,23 @@ static void asm_floating_point_reg_arm_reg_transfer_opcode_tail(TCCState *s1, in · 6 unmodified lines | ||
| 1886 | 1886 | memcpy(&ops[1], &ops[2], sizeof(ops[1])); |
| 1887 | 1887 | memcpy(&ops[2], &temp, sizeof(ops[2])); |
| 1888 | 1888 | } else { |
| 1889 | − tcc_error("vmov.f64 only implemented for one VFP register operand and two ARM register operands"); | |
| 1889 | + tcc_error(S, "vmov.f64 only implemented for one VFP register operand and two ARM register operands"); | |
| 1890 | 1890 | return; |
| 1891 | 1891 | } |
| 1892 | 1892 | } else if (ops[0].type != OP_REG32 || ops[1].type != OP_REG32 || ops[2].type != OP_VREG64) { |
| 1893 | − tcc_error("vmov.f64 only implemented for one VFP register operand and two ARM register operands"); | |
| 1893 | + tcc_error(S, "vmov.f64 only implemented for one VFP register operand and two ARM register operands"); | |
| 1894 | 1894 | return; |
| 1895 | 1895 | } else { |
| 1896 | 1896 | opcode1 |= 1; |
| 1897 | 1897 | } |
| 1898 | − asm_emit_coprocessor_data_transfer(condition_code_of_token(token), coprocessor, ops[0].reg, &ops[1], &ops[2], 0, 0, 0, 1, opcode1); | |
| 1898 | + asm_emit_coprocessor_data_transfer(S, condition_code_of_token(S, token), coprocessor, ops[0].reg, &ops[1], &ops[2], 0, 0, 0, 1, opcode1); | |
| 1899 | 1899 | break; |
| 1900 | 1900 | default: |
| 1901 | − tcc_internal_error("unknown coprocessor"); | |
| 1901 | + tcc_internal_error(S, "unknown coprocessor"); | |
| 1902 | 1902 | } |
| 1903 | 1903 | } |
| 1904 | 1904 | |
| 1905 | −static void asm_floating_point_vcvt_data_processing_opcode(TCCState *s1, int token) { | |
| 1905 | +static void asm_floating_point_vcvt_data_processing_opcode(TCCState *S, int token) { | |
| 1906 | 1906 | uint8_t coprocessor = 0; |
| 1907 | 1907 | Operand ops[3]; |
| 1908 | 1908 | uint8_t opcode1 = 11; |
| @@ -1928,11 +1928,11 @@ static void asm_floating_point_vcvt_data_processing_opcode(TCCState *s1, int tok · 19 unmodified lines | ||
| 1928 | 1928 | coprocessor = CP_SINGLE_PRECISION_FLOAT; |
| 1929 | 1929 | break; |
| 1930 | 1930 | default: |
| 1931 | − tcc_error("Unknown coprocessor for instruction '%s'", get_tok_str(token, NULL)); | |
| 1931 | + tcc_error(S, "Unknown coprocessor for instruction '%s'", get_tok_str(S, token, NULL)); | |
| 1932 | 1932 | return; |
| 1933 | 1933 | } |
| 1934 | 1934 | |
| 1935 | − parse_operand(s1, &ops[0]); | |
| 1935 | + parse_operand(S, &ops[0]); | |
| 1936 | 1936 | ops[1].type = OP_IM8; |
| 1937 | 1937 | ops[1].e.v = 8; |
| 1938 | 1938 | /* floating-point -> integer */ |
| @@ -1956,11 +1956,11 @@ static void asm_floating_point_vcvt_data_processing_opcode(TCCState *s1, int tok · 17 unmodified lines | ||
| 1956 | 1956 | break; |
| 1957 | 1957 | } |
| 1958 | 1958 | |
| 1959 | − if (tok == ',') | |
| 1960 | − next(); | |
| 1959 | + if (S->tccpp_tok == ',') | |
| 1960 | + next(S); | |
| 1961 | 1961 | else |
| 1962 | − expect("','"); | |
| 1963 | − parse_operand(s1, &ops[2]); | |
| 1962 | + expect(S, "','"); | |
| 1963 | + parse_operand(S, &ops[2]); | |
| 1964 | 1964 | |
| 1965 | 1965 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 1966 | 1966 | /* floating-point -> integer */ |
| @@ -1990,7 +1990,7 @@ static void asm_floating_point_vcvt_data_processing_opcode(TCCState *s1, int tok · 23 unmodified lines | ||
| 1990 | 1990 | case TOK_ASM_vcvteq_f64_f32: |
| 1991 | 1991 | if (ops[0].type == OP_VREG64 && ops[2].type == OP_VREG32) { |
| 1992 | 1992 | } else { |
| 1993 | − expect("d<number>, s<number>"); | |
| 1993 | + expect(S, "d<number>, s<number>"); | |
| 1994 | 1994 | return; |
| 1995 | 1995 | } |
| 1996 | 1996 | break; |
| @@ -1998,13 +1998,13 @@ static void asm_floating_point_vcvt_data_processing_opcode(TCCState *s1, int tok · 1 unmodified line | ||
| 1998 | 1998 | if (coprocessor == CP_SINGLE_PRECISION_FLOAT) { |
| 1999 | 1999 | if (ops[0].type == OP_VREG32 && ops[2].type == OP_VREG32) { |
| 2000 | 2000 | } else { |
| 2001 | − expect("s<number>, s<number>"); | |
| 2001 | + expect(S, "s<number>, s<number>"); | |
| 2002 | 2002 | return; |
| 2003 | 2003 | } |
| 2004 | 2004 | } else if (coprocessor == CP_DOUBLE_PRECISION_FLOAT) { |
| 2005 | 2005 | if (ops[0].type == OP_VREG32 && ops[2].type == OP_VREG64) { |
| 2006 | 2006 | } else { |
| 2007 | − expect("s<number>, d<number>"); | |
| 2007 | + expect(S, "s<number>, d<number>"); | |
| 2008 | 2008 | return; |
| 2009 | 2009 | } |
| 2010 | 2010 | } |
| @@ -2020,10 +2020,10 @@ static void asm_floating_point_vcvt_data_processing_opcode(TCCState *s1, int tok · 9 unmodified lines | ||
| 2020 | 2020 | opcode1 |= 4; |
| 2021 | 2021 | ops[0].reg >>= 1; |
| 2022 | 2022 | } |
| 2023 | − asm_emit_coprocessor_opcode(condition_code_of_token(token), coprocessor, opcode1, ops[0].reg, (ops[1].type == OP_IM8) ? ops[1].e.v : ops[1].reg, (ops[2].type == OP_IM8) ? ops[2].e.v : ops[2].reg, opcode2, 0); | |
| 2023 | + asm_emit_coprocessor_opcode(S, condition_code_of_token(S, token), coprocessor, opcode1, ops[0].reg, (ops[1].type == OP_IM8) ? ops[1].e.v : ops[1].reg, (ops[2].type == OP_IM8) ? ops[2].e.v : ops[2].reg, opcode2, 0); | |
| 2024 | 2024 | } |
| 2025 | 2025 | |
| 2026 | −static void asm_floating_point_data_processing_opcode(TCCState *s1, int token) { | |
| 2026 | +static void asm_floating_point_data_processing_opcode(TCCState *S, int token) { | |
| 2027 | 2027 | uint8_t coprocessor = CP_SINGLE_PRECISION_FLOAT; |
| 2028 | 2028 | uint8_t opcode1 = 0; |
| 2029 | 2029 | uint8_t opcode2 = 0; // (0 || 2) | register selection |
| @@ -2078,30 +2078,30 @@ static void asm_floating_point_data_processing_opcode(TCCState *s1, int token) { · 48 unmodified lines | ||
| 2078 | 2078 | |
| 2079 | 2079 | for (nb_ops = 0; nb_ops < 3; ) { |
| 2080 | 2080 | // Note: Necessary because parse_operand can't parse decimal numerals. |
| 2081 | − if (nb_ops == 1 && (tok == '#' || tok == '$' || tok == TOK_PPNUM || tok == '-')) { | |
| 2082 | − asm_floating_point_immediate_data_processing_opcode_tail(s1, token, coprocessor, ops[0].reg); | |
| 2081 | + if (nb_ops == 1 && (S->tccpp_tok == '#' || S->tccpp_tok == '$' || S->tccpp_tok == TOK_PPNUM || S->tccpp_tok == '-')) { | |
| 2082 | + asm_floating_point_immediate_data_processing_opcode_tail(S, token, coprocessor, ops[0].reg); | |
| 2083 | 2083 | return; |
| 2084 | 2084 | } |
| 2085 | − parse_operand(s1, &ops[nb_ops]); | |
| 2085 | + parse_operand(S, &ops[nb_ops]); | |
| 2086 | 2086 | if (vmov && ops[nb_ops].type == OP_REG32) { |
| 2087 | 2087 | ++nb_arm_regs; |
| 2088 | 2088 | } else if (ops[nb_ops].type == OP_VREG32) { |
| 2089 | 2089 | if (coprocessor != CP_SINGLE_PRECISION_FLOAT) { |
| 2090 | − expect("'s<number>'"); | |
| 2090 | + expect(S, "'s<number>'"); | |
| 2091 | 2091 | return; |
| 2092 | 2092 | } |
| 2093 | 2093 | } else if (ops[nb_ops].type == OP_VREG64) { |
| 2094 | 2094 | if (coprocessor != CP_DOUBLE_PRECISION_FLOAT) { |
| 2095 | − expect("'d<number>'"); | |
| 2095 | + expect(S, "'d<number>'"); | |
| 2096 | 2096 | return; |
| 2097 | 2097 | } |
| 2098 | 2098 | } else { |
| 2099 | − expect("floating point register"); | |
| 2099 | + expect(S, "floating point register"); | |
| 2100 | 2100 | return; |
| 2101 | 2101 | } |
| 2102 | 2102 | ++nb_ops; |
| 2103 | − if (tok == ',') | |
| 2104 | − next(); | |
| 2103 | + if (S->tccpp_tok == ',') | |
| 2104 | + next(S); | |
| 2105 | 2105 | else |
| 2106 | 2106 | break; |
| 2107 | 2107 | } |
| @@ -2113,7 +2113,7 @@ static void asm_floating_point_data_processing_opcode(TCCState *s1, int token) { · 5 unmodified lines | ||
| 2113 | 2113 | nb_ops = 3; |
| 2114 | 2114 | } |
| 2115 | 2115 | if (nb_ops < 3) { |
| 2116 | − tcc_error("Not enough operands for '%s' (%u)", get_tok_str(token, NULL), nb_ops); | |
| 2116 | + tcc_error(S, "Not enough operands for '%s' (%u)", get_tok_str(S, token, NULL), nb_ops); | |
| 2117 | 2117 | return; |
| 2118 | 2118 | } |
| 2119 | 2119 | } |
| @@ -2202,7 +2202,7 @@ static void asm_floating_point_data_processing_opcode(TCCState *s1, int token) { · 82 unmodified lines | ||
| 2202 | 2202 | case TOK_ASM_vmoveq_f32: |
| 2203 | 2203 | case TOK_ASM_vmoveq_f64: |
| 2204 | 2204 | if (nb_arm_regs > 0) { // vmov.f32 r2, s3 or similar |
| 2205 | − asm_floating_point_reg_arm_reg_transfer_opcode_tail(s1, token, coprocessor, nb_arm_regs, nb_ops, ops); | |
| 2205 | + asm_floating_point_reg_arm_reg_transfer_opcode_tail(S, token, coprocessor, nb_arm_regs, nb_ops, ops); | |
| 2206 | 2206 | return; |
| 2207 | 2207 | } else { |
| 2208 | 2208 | opcode1 = 11; // "Other" instruction |
| @@ -2212,7 +2212,7 @@ static void asm_floating_point_data_processing_opcode(TCCState *s1, int token) { · 3 unmodified lines | ||
| 2212 | 2212 | } |
| 2213 | 2213 | break; |
| 2214 | 2214 | default: |
| 2215 | − expect("known floating point instruction"); | |
| 2215 | + expect(S, "known floating point instruction"); | |
| 2216 | 2216 | return; |
| 2217 | 2217 | } |
| 2218 | 2218 | |
| @@ -2236,10 +2236,10 @@ static void asm_floating_point_data_processing_opcode(TCCState *s1, int token) { · 17 unmodified lines | ||
| 2236 | 2236 | } |
| 2237 | 2237 | } |
| 2238 | 2238 | |
| 2239 | − asm_emit_coprocessor_opcode(condition_code_of_token(token), coprocessor, opcode1, ops[0].reg, (ops[1].type == OP_IM8) ? ops[1].e.v : ops[1].reg, (ops[2].type == OP_IM8) ? ops[2].e.v : ops[2].reg, opcode2, 0); | |
| 2239 | + asm_emit_coprocessor_opcode(S, condition_code_of_token(S, token), coprocessor, opcode1, ops[0].reg, (ops[1].type == OP_IM8) ? ops[1].e.v : ops[1].reg, (ops[2].type == OP_IM8) ? ops[2].e.v : ops[2].reg, opcode2, 0); | |
| 2240 | 2240 | } |
| 2241 | 2241 | |
| 2242 | −static void asm_floating_point_status_register_opcode(TCCState* s1, int token) | |
| 2242 | +static void asm_floating_point_status_register_opcode(TCCState* S, int token) | |
| 2243 | 2243 | { |
| 2244 | 2244 | uint8_t coprocessor = CP_SINGLE_PRECISION_FLOAT; |
| 2245 | 2245 | uint8_t opcode; |
| @@ -2248,61 +2248,61 @@ static void asm_floating_point_status_register_opcode(TCCState* s1, int token) · 2 unmodified lines | ||
| 2248 | 2248 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 2249 | 2249 | case TOK_ASM_vmrseq: |
| 2250 | 2250 | opcode = 0xf; |
| 2251 | − if (tok == TOK_ASM_apsr_nzcv) { | |
| 2251 | + if (S->tccpp_tok == TOK_ASM_apsr_nzcv) { | |
| 2252 | 2252 | arm_operand.type = OP_REG32; |
| 2253 | 2253 | arm_operand.reg = 15; // not PC |
| 2254 | − next(); // skip apsr_nzcv | |
| 2254 | + next(S); // skip apsr_nzcv | |
| 2255 | 2255 | } else { |
| 2256 | − parse_operand(s1, &arm_operand); | |
| 2256 | + parse_operand(S, &arm_operand); | |
| 2257 | 2257 | if (arm_operand.type == OP_REG32 && arm_operand.reg == 15) { |
| 2258 | − tcc_error("'%s' does not support 'pc' as operand", get_tok_str(token, NULL)); | |
| 2258 | + tcc_error(S, "'%s' does not support 'pc' as operand", get_tok_str(S, token, NULL)); | |
| 2259 | 2259 | return; |
| 2260 | 2260 | } |
| 2261 | 2261 | } |
| 2262 | 2262 | |
| 2263 | − if (tok != ',') | |
| 2264 | − expect("','"); | |
| 2263 | + if (S->tccpp_tok != ',') | |
| 2264 | + expect(S, "','"); | |
| 2265 | 2265 | else |
| 2266 | − next(); // skip ',' | |
| 2267 | − vfp_sys_reg = asm_parse_vfp_status_regvar(tok); | |
| 2268 | − next(); // skip vfp sys reg | |
| 2266 | + next(S); // skip ',' | |
| 2267 | + vfp_sys_reg = asm_parse_vfp_status_regvar(S->tccpp_tok); | |
| 2268 | + next(S); // skip vfp sys reg | |
| 2269 | 2269 | if (arm_operand.type == OP_REG32 && arm_operand.reg == 15 && vfp_sys_reg != 1) { |
| 2270 | − tcc_error("'%s' only supports the variant 'vmrs apsr_nzcv, fpscr' here", get_tok_str(token, NULL)); | |
| 2270 | + tcc_error(S, "'%s' only supports the variant 'vmrs apsr_nzcv, fpscr' here", get_tok_str(S, token, NULL)); | |
| 2271 | 2271 | return; |
| 2272 | 2272 | } |
| 2273 | 2273 | break; |
| 2274 | 2274 | case TOK_ASM_vmsreq: |
| 2275 | 2275 | opcode = 0xe; |
| 2276 | − vfp_sys_reg = asm_parse_vfp_status_regvar(tok); | |
| 2277 | − next(); // skip vfp sys reg | |
| 2278 | − if (tok != ',') | |
| 2279 | − expect("','"); | |
| 2276 | + vfp_sys_reg = asm_parse_vfp_status_regvar(S->tccpp_tok); | |
| 2277 | + next(S); // skip vfp sys reg | |
| 2278 | + if (S->tccpp_tok != ',') | |
| 2279 | + expect(S, "','"); | |
| 2280 | 2280 | else |
| 2281 | − next(); // skip ',' | |
| 2282 | − parse_operand(s1, &arm_operand); | |
| 2281 | + next(S); // skip ',' | |
| 2282 | + parse_operand(S, &arm_operand); | |
| 2283 | 2283 | if (arm_operand.type == OP_REG32 && arm_operand.reg == 15) { |
| 2284 | − tcc_error("'%s' does not support 'pc' as operand", get_tok_str(token, NULL)); | |
| 2284 | + tcc_error(S, "'%s' does not support 'pc' as operand", get_tok_str(S, token, NULL)); | |
| 2285 | 2285 | return; |
| 2286 | 2286 | } |
| 2287 | 2287 | break; |
| 2288 | 2288 | default: |
| 2289 | − expect("floating point status register instruction"); | |
| 2289 | + expect(S, "floating point status register instruction"); | |
| 2290 | 2290 | return; |
| 2291 | 2291 | } |
| 2292 | 2292 | if (vfp_sys_reg == -1) { |
| 2293 | − expect("VFP system register"); | |
| 2293 | + expect(S, "VFP system register"); | |
| 2294 | 2294 | return; |
| 2295 | 2295 | } |
| 2296 | 2296 | if (arm_operand.type != OP_REG32) { |
| 2297 | − expect("ARM register"); | |
| 2297 | + expect(S, "ARM register"); | |
| 2298 | 2298 | return; |
| 2299 | 2299 | } |
| 2300 | − asm_emit_coprocessor_opcode(condition_code_of_token(token), coprocessor, opcode, arm_operand.reg, vfp_sys_reg, 0x10, 0, 0); | |
| 2300 | + asm_emit_coprocessor_opcode(S, condition_code_of_token(S, token), coprocessor, opcode, arm_operand.reg, vfp_sys_reg, 0x10, 0, 0); | |
| 2301 | 2301 | } |
| 2302 | 2302 | |
| 2303 | 2303 | #endif |
| 2304 | 2304 | |
| 2305 | −static void asm_misc_single_data_transfer_opcode(TCCState *s1, int token) | |
| 2305 | +static void asm_misc_single_data_transfer_opcode(TCCState *S, int token) | |
| 2306 | 2306 | { |
| 2307 | 2307 | Operand ops[3]; |
| 2308 | 2308 | int exclam = 0; |
| @@ -2322,42 +2322,42 @@ static void asm_misc_single_data_transfer_opcode(TCCState *s1, int token) · 13 unmodified lines | ||
| 2322 | 2322 | // Here: 0 0 0 P U I W L << 20 |
| 2323 | 2323 | // [compare single data transfer: 0 1 I P U B W L << 20] |
| 2324 | 2324 | |
| 2325 | − parse_operand(s1, &ops[0]); | |
| 2325 | + parse_operand(S, &ops[0]); | |
| 2326 | 2326 | if (ops[0].type == OP_REG32) |
| 2327 | 2327 | opcode |= ENCODE_RD(ops[0].reg); |
| 2328 | 2328 | else { |
| 2329 | − expect("(destination operand) register"); | |
| 2329 | + expect(S, "(destination operand) register"); | |
| 2330 | 2330 | return; |
| 2331 | 2331 | } |
| 2332 | − if (tok != ',') | |
| 2333 | − expect("at least two arguments"); | |
| 2332 | + if (S->tccpp_tok != ',') | |
| 2333 | + expect(S, "at least two arguments"); | |
| 2334 | 2334 | else |
| 2335 | − next(); // skip ',' | |
| 2335 | + next(S); // skip ',' | |
| 2336 | 2336 | |
| 2337 | − if (tok != '[') | |
| 2338 | − expect("'['"); | |
| 2337 | + if (S->tccpp_tok != '[') | |
| 2338 | + expect(S, "'['"); | |
| 2339 | 2339 | else |
| 2340 | − next(); // skip '[' | |
| 2340 | + next(S); // skip '[' | |
| 2341 | 2341 | |
| 2342 | − parse_operand(s1, &ops[1]); | |
| 2342 | + parse_operand(S, &ops[1]); | |
| 2343 | 2343 | if (ops[1].type == OP_REG32) |
| 2344 | 2344 | opcode |= ENCODE_RN(ops[1].reg); |
| 2345 | 2345 | else { |
| 2346 | − expect("(first source operand) register"); | |
| 2346 | + expect(S, "(first source operand) register"); | |
| 2347 | 2347 | return; |
| 2348 | 2348 | } |
| 2349 | − if (tok == ']') { | |
| 2350 | − next(); | |
| 2349 | + if (S->tccpp_tok == ']') { | |
| 2350 | + next(S); | |
| 2351 | 2351 | closed_bracket = 1; |
| 2352 | 2352 | // exclam = 1; // implicit in hardware; don't do it in software |
| 2353 | 2353 | } |
| 2354 | − if (tok == ',') { | |
| 2355 | − next(); // skip ',' | |
| 2356 | − if (tok == '-') { | |
| 2354 | + if (S->tccpp_tok == ',') { | |
| 2355 | + next(S); // skip ',' | |
| 2356 | + if (S->tccpp_tok == '-') { | |
| 2357 | 2357 | op2_minus = 1; |
| 2358 | − next(); | |
| 2358 | + next(S); | |
| 2359 | 2359 | } |
| 2360 | − parse_operand(s1, &ops[2]); | |
| 2360 | + parse_operand(S, &ops[2]); | |
| 2361 | 2361 | } else { |
| 2362 | 2362 | // end of input expression in brackets--assume 0 offset |
| 2363 | 2363 | ops[2].type = OP_IM8; |
| @@ -2365,20 +2365,20 @@ static void asm_misc_single_data_transfer_opcode(TCCState *s1, int token) · 1 unmodified line | ||
| 2365 | 2365 | opcode |= 1 << 24; // add offset before transfer |
| 2366 | 2366 | } |
| 2367 | 2367 | if (!closed_bracket) { |
| 2368 | − if (tok != ']') | |
| 2369 | − expect("']'"); | |
| 2368 | + if (S->tccpp_tok != ']') | |
| 2369 | + expect(S, "']'"); | |
| 2370 | 2370 | else |
| 2371 | − next(); // skip ']' | |
| 2371 | + next(S); // skip ']' | |
| 2372 | 2372 | opcode |= 1 << 24; // add offset before transfer |
| 2373 | − if (tok == '!') { | |
| 2373 | + if (S->tccpp_tok == '!') { | |
| 2374 | 2374 | exclam = 1; |
| 2375 | − next(); // skip '!' | |
| 2375 | + next(S); // skip '!' | |
| 2376 | 2376 | } |
| 2377 | 2377 | } |
| 2378 | 2378 | |
| 2379 | 2379 | if (exclam) { |
| 2380 | 2380 | if ((opcode & (1 << 24)) == 0) { |
| 2381 | − tcc_error("result of '%s' would be unpredictable here", get_tok_str(token, NULL)); | |
| 2381 | + tcc_error(S, "result of '%s' would be unpredictable here", get_tok_str(S, token, NULL)); | |
| 2382 | 2382 | return; |
| 2383 | 2383 | } |
| 2384 | 2384 | opcode |= 1 << 21; // write offset back into register |
| @@ -2387,11 +2387,11 @@ static void asm_misc_single_data_transfer_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 2387 | 2387 | if (ops[2].type == OP_IM32 || ops[2].type == OP_IM8 || ops[2].type == OP_IM8N) { |
| 2388 | 2388 | int v = ops[2].e.v; |
| 2389 | 2389 | if (op2_minus) |
| 2390 | − tcc_error("minus before '#' not supported for immediate values"); | |
| 2390 | + tcc_error(S, "minus before '#' not supported for immediate values"); | |
| 2391 | 2391 | if (v >= 0) { |
| 2392 | 2392 | opcode |= 1 << 23; // up |
| 2393 | 2393 | if (v >= 0x100) |
| 2394 | − tcc_error("offset out of range for '%s'", get_tok_str(token, NULL)); | |
| 2394 | + tcc_error(S, "offset out of range for '%s'", get_tok_str(S, token, NULL)); | |
| 2395 | 2395 | else { |
| 2396 | 2396 | // bits 11...8: immediate hi nibble |
| 2397 | 2397 | // bits 3...0: immediate lo nibble |
| @@ -2400,7 +2400,7 @@ static void asm_misc_single_data_transfer_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 2400 | 2400 | } |
| 2401 | 2401 | } else { // down |
| 2402 | 2402 | if (v <= -0x100) |
| 2403 | − tcc_error("offset out of range for '%s'", get_tok_str(token, NULL)); | |
| 2403 | + tcc_error(S, "offset out of range for '%s'", get_tok_str(S, token, NULL)); | |
| 2404 | 2404 | else { |
| 2405 | 2405 | v = -v; |
| 2406 | 2406 | // bits 11...8: immediate hi nibble |
| @@ -2415,7 +2415,7 @@ static void asm_misc_single_data_transfer_opcode(TCCState *s1, int token) · 8 unmodified lines | ||
| 2415 | 2415 | opcode |= 1 << 23; // up |
| 2416 | 2416 | opcode |= ops[2].reg; |
| 2417 | 2417 | } else |
| 2418 | − expect("register"); | |
| 2418 | + expect(S, "register"); | |
| 2419 | 2419 | |
| 2420 | 2420 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 2421 | 2421 | case TOK_ASM_ldrsheq: |
| @@ -2424,34 +2424,34 @@ static void asm_misc_single_data_transfer_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 2424 | 2424 | case TOK_ASM_ldrsbeq: |
| 2425 | 2425 | opcode |= 1 << 6; // sign extend |
| 2426 | 2426 | opcode |= 1 << 20; // L |
| 2427 | − asm_emit_opcode(token, opcode); | |
| 2427 | + asm_emit_opcode(S, token, opcode); | |
| 2428 | 2428 | break; |
| 2429 | 2429 | case TOK_ASM_ldrheq: |
| 2430 | 2430 | opcode |= 1 << 5; // halfword, not byte |
| 2431 | 2431 | opcode |= 1 << 20; // L |
| 2432 | − asm_emit_opcode(token, opcode); | |
| 2432 | + asm_emit_opcode(S, token, opcode); | |
| 2433 | 2433 | break; |
| 2434 | 2434 | case TOK_ASM_strheq: |
| 2435 | 2435 | opcode |= 1 << 5; // halfword, not byte |
| 2436 | − asm_emit_opcode(token, opcode); | |
| 2436 | + asm_emit_opcode(S, token, opcode); | |
| 2437 | 2437 | break; |
| 2438 | 2438 | } |
| 2439 | 2439 | } |
| 2440 | 2440 | |
| 2441 | 2441 | /* Note: almost dupe of encbranch in arm-gen.c */ |
| 2442 | −static uint32_t encbranchoffset(int pos, int addr, int fail) | |
| 2442 | +static uint32_t encbranchoffset(TCCState* S, int pos, int addr, int fail) | |
| 2443 | 2443 | { |
| 2444 | 2444 | addr-=pos+8; |
| 2445 | 2445 | addr/=4; |
| 2446 | 2446 | if(addr>=0x7fffff || addr<-0x800000) { |
| 2447 | 2447 | if(fail) |
| 2448 | − tcc_error("branch offset is too far"); | |
| 2448 | + tcc_error(S, "branch offset is too far"); | |
| 2449 | 2449 | return 0; |
| 2450 | 2450 | } |
| 2451 | 2451 | return /*not 0x0A000000|*/(addr&0xffffff); |
| 2452 | 2452 | } |
| 2453 | 2453 | |
| 2454 | −static void asm_branch_opcode(TCCState *s1, int token) | |
| 2454 | +static void asm_branch_opcode(TCCState *S, int token) | |
| 2455 | 2455 | { |
| 2456 | 2456 | int jmp_disp = 0; |
| 2457 | 2457 | Operand op; |
| @@ -2461,63 +2461,63 @@ static void asm_branch_opcode(TCCState *s1, int token) · 3 unmodified lines | ||
| 2461 | 2461 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 2462 | 2462 | case TOK_ASM_beq: |
| 2463 | 2463 | case TOK_ASM_bleq: |
| 2464 | − asm_expr(s1, &e); | |
| 2465 | − esym = elfsym(e.sym); | |
| 2464 | + asm_expr(S, &e); | |
| 2465 | + esym = elfsym(S, e.sym); | |
| 2466 | 2466 | if (!esym || esym->st_shndx != cur_text_section->sh_num) { |
| 2467 | − tcc_error("invalid branch target"); | |
| 2467 | + tcc_error(S, "invalid branch target"); | |
| 2468 | 2468 | return; |
| 2469 | 2469 | } |
| 2470 | − jmp_disp = encbranchoffset(ind, e.v + esym->st_value, 1); | |
| 2470 | + jmp_disp = encbranchoffset(S, S->tccgen_ind, e.v + esym->st_value, 1); | |
| 2471 | 2471 | break; |
| 2472 | 2472 | default: |
| 2473 | − parse_operand(s1, &op); | |
| 2473 | + parse_operand(S, &op); | |
| 2474 | 2474 | break; |
| 2475 | 2475 | } |
| 2476 | 2476 | switch (ARM_INSTRUCTION_GROUP(token)) { |
| 2477 | 2477 | case TOK_ASM_beq: |
| 2478 | − asm_emit_opcode(token, (0xa << 24) | (jmp_disp & 0xffffff)); | |
| 2478 | + asm_emit_opcode(S, token, (0xa << 24) | (jmp_disp & 0xffffff)); | |
| 2479 | 2479 | break; |
| 2480 | 2480 | case TOK_ASM_bleq: |
| 2481 | − asm_emit_opcode(token, (0xb << 24) | (jmp_disp & 0xffffff)); | |
| 2481 | + asm_emit_opcode(S, token, (0xb << 24) | (jmp_disp & 0xffffff)); | |
| 2482 | 2482 | break; |
| 2483 | 2483 | case TOK_ASM_bxeq: |
| 2484 | 2484 | if (op.type != OP_REG32) |
| 2485 | − expect("register"); | |
| 2485 | + expect(S, "register"); | |
| 2486 | 2486 | else |
| 2487 | − asm_emit_opcode(token, (0x12fff1 << 4) | op.reg); | |
| 2487 | + asm_emit_opcode(S, token, (0x12fff1 << 4) | op.reg); | |
| 2488 | 2488 | break; |
| 2489 | 2489 | case TOK_ASM_blxeq: |
| 2490 | 2490 | if (op.type != OP_REG32) |
| 2491 | − expect("register"); | |
| 2491 | + expect(S, "register"); | |
| 2492 | 2492 | else |
| 2493 | − asm_emit_opcode(token, (0x12fff3 << 4) | op.reg); | |
| 2493 | + asm_emit_opcode(S, token, (0x12fff3 << 4) | op.reg); | |
| 2494 | 2494 | break; |
| 2495 | 2495 | default: |
| 2496 | − expect("branch instruction"); | |
| 2496 | + expect(S, "branch instruction"); | |
| 2497 | 2497 | } |
| 2498 | 2498 | } |
| 2499 | 2499 | |
| 2500 | −ST_FUNC void asm_opcode(TCCState *s1, int token) | |
| 2500 | +ST_FUNC void asm_opcode(TCCState *S, int token) | |
| 2501 | 2501 | { |
| 2502 | 2502 | while (token == TOK_LINEFEED) { |
| 2503 | − next(); | |
| 2504 | − token = tok; | |
| 2503 | + next(S); | |
| 2504 | + token = S->tccpp_tok; | |
| 2505 | 2505 | } |
| 2506 | 2506 | if (token == TOK_EOF) |
| 2507 | 2507 | return; |
| 2508 | 2508 | if (token < TOK_ASM_nopeq) { // no condition code |
| 2509 | 2509 | switch (token) { |
| 2510 | 2510 | case TOK_ASM_cdp2: |
| 2511 | − asm_coprocessor_opcode(s1, token); | |
| 2511 | + asm_coprocessor_opcode(S, token); | |
| 2512 | 2512 | return; |
| 2513 | 2513 | case TOK_ASM_ldc2: |
| 2514 | 2514 | case TOK_ASM_ldc2l: |
| 2515 | 2515 | case TOK_ASM_stc2: |
| 2516 | 2516 | case TOK_ASM_stc2l: |
| 2517 | − asm_coprocessor_data_transfer_opcode(s1, token); | |
| 2517 | + asm_coprocessor_data_transfer_opcode(S, token); | |
| 2518 | 2518 | return; |
| 2519 | 2519 | default: |
| 2520 | − expect("instruction"); | |
| 2520 | + expect(S, "instruction"); | |
| 2521 | 2521 | return; |
| 2522 | 2522 | } |
| 2523 | 2523 | } |
| @@ -2535,22 +2535,22 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 11 unmodified lines | ||
| 2535 | 2535 | case TOK_ASM_ldmdbeq: |
| 2536 | 2536 | case TOK_ASM_stmibeq: |
| 2537 | 2537 | case TOK_ASM_ldmibeq: |
| 2538 | − asm_block_data_transfer_opcode(s1, token); | |
| 2538 | + asm_block_data_transfer_opcode(S, token); | |
| 2539 | 2539 | return; |
| 2540 | 2540 | case TOK_ASM_nopeq: |
| 2541 | 2541 | case TOK_ASM_wfeeq: |
| 2542 | 2542 | case TOK_ASM_wfieq: |
| 2543 | − asm_nullary_opcode(token); | |
| 2543 | + asm_nullary_opcode(S, token); | |
| 2544 | 2544 | return; |
| 2545 | 2545 | case TOK_ASM_swieq: |
| 2546 | 2546 | case TOK_ASM_svceq: |
| 2547 | − asm_unary_opcode(s1, token); | |
| 2547 | + asm_unary_opcode(S, token); | |
| 2548 | 2548 | return; |
| 2549 | 2549 | case TOK_ASM_beq: |
| 2550 | 2550 | case TOK_ASM_bleq: |
| 2551 | 2551 | case TOK_ASM_bxeq: |
| 2552 | 2552 | case TOK_ASM_blxeq: |
| 2553 | − asm_branch_opcode(s1, token); | |
| 2553 | + asm_branch_opcode(S, token); | |
| 2554 | 2554 | return; |
| 2555 | 2555 | case TOK_ASM_clzeq: |
| 2556 | 2556 | case TOK_ASM_sxtbeq: |
| @@ -2559,7 +2559,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 2559 | 2559 | case TOK_ASM_uxtheq: |
| 2560 | 2560 | case TOK_ASM_movteq: |
| 2561 | 2561 | case TOK_ASM_movweq: |
| 2562 | − asm_binary_opcode(s1, token); | |
| 2562 | + asm_binary_opcode(S, token); | |
| 2563 | 2563 | return; |
| 2564 | 2564 | |
| 2565 | 2565 | case TOK_ASM_ldreq: |
| @@ -2570,14 +2570,14 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 4 unmodified lines | ||
| 2570 | 2570 | case TOK_ASM_ldrexbeq: |
| 2571 | 2571 | case TOK_ASM_strexeq: |
| 2572 | 2572 | case TOK_ASM_strexbeq: |
| 2573 | − asm_single_data_transfer_opcode(s1, token); | |
| 2573 | + asm_single_data_transfer_opcode(S, token); | |
| 2574 | 2574 | return; |
| 2575 | 2575 | |
| 2576 | 2576 | case TOK_ASM_ldrheq: |
| 2577 | 2577 | case TOK_ASM_ldrsheq: |
| 2578 | 2578 | case TOK_ASM_ldrsbeq: |
| 2579 | 2579 | case TOK_ASM_strheq: |
| 2580 | − asm_misc_single_data_transfer_opcode(s1, token); | |
| 2580 | + asm_misc_single_data_transfer_opcode(S, token); | |
| 2581 | 2581 | return; |
| 2582 | 2582 | |
| 2583 | 2583 | case TOK_ASM_andeq: |
| @@ -2612,7 +2612,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 28 unmodified lines | ||
| 2612 | 2612 | case TOK_ASM_movseq: |
| 2613 | 2613 | case TOK_ASM_bicseq: |
| 2614 | 2614 | case TOK_ASM_mvnseq: |
| 2615 | − asm_data_processing_opcode(s1, token); | |
| 2615 | + asm_data_processing_opcode(S, token); | |
| 2616 | 2616 | return; |
| 2617 | 2617 | |
| 2618 | 2618 | case TOK_ASM_lsleq: |
| @@ -2625,14 +2625,14 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 6 unmodified lines | ||
| 2625 | 2625 | case TOK_ASM_rorseq: |
| 2626 | 2626 | case TOK_ASM_rrxseq: |
| 2627 | 2627 | case TOK_ASM_rrxeq: |
| 2628 | − asm_shift_opcode(s1, token); | |
| 2628 | + asm_shift_opcode(S, token); | |
| 2629 | 2629 | return; |
| 2630 | 2630 | |
| 2631 | 2631 | case TOK_ASM_muleq: |
| 2632 | 2632 | case TOK_ASM_mulseq: |
| 2633 | 2633 | case TOK_ASM_mlaeq: |
| 2634 | 2634 | case TOK_ASM_mlaseq: |
| 2635 | − asm_multiplication_opcode(s1, token); | |
| 2635 | + asm_multiplication_opcode(S, token); | |
| 2636 | 2636 | return; |
| 2637 | 2637 | |
| 2638 | 2638 | case TOK_ASM_smulleq: |
| @@ -2643,26 +2643,26 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 4 unmodified lines | ||
| 2643 | 2643 | case TOK_ASM_smlalseq: |
| 2644 | 2644 | case TOK_ASM_umlaleq: |
| 2645 | 2645 | case TOK_ASM_umlalseq: |
| 2646 | − asm_long_multiplication_opcode(s1, token); | |
| 2646 | + asm_long_multiplication_opcode(S, token); | |
| 2647 | 2647 | return; |
| 2648 | 2648 | |
| 2649 | 2649 | case TOK_ASM_cdpeq: |
| 2650 | 2650 | case TOK_ASM_mcreq: |
| 2651 | 2651 | case TOK_ASM_mrceq: |
| 2652 | − asm_coprocessor_opcode(s1, token); | |
| 2652 | + asm_coprocessor_opcode(S, token); | |
| 2653 | 2653 | return; |
| 2654 | 2654 | |
| 2655 | 2655 | case TOK_ASM_ldceq: |
| 2656 | 2656 | case TOK_ASM_ldcleq: |
| 2657 | 2657 | case TOK_ASM_stceq: |
| 2658 | 2658 | case TOK_ASM_stcleq: |
| 2659 | − asm_coprocessor_data_transfer_opcode(s1, token); | |
| 2659 | + asm_coprocessor_data_transfer_opcode(S, token); | |
| 2660 | 2660 | return; |
| 2661 | 2661 | |
| 2662 | 2662 | #if defined(TCC_ARM_VFP) |
| 2663 | 2663 | case TOK_ASM_vldreq: |
| 2664 | 2664 | case TOK_ASM_vstreq: |
| 2665 | − asm_floating_point_single_data_transfer_opcode(s1, token); | |
| 2665 | + asm_floating_point_single_data_transfer_opcode(S, token); | |
| 2666 | 2666 | return; |
| 2667 | 2667 | |
| 2668 | 2668 | case TOK_ASM_vmlaeq_f32: |
| @@ -2695,7 +2695,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 26 unmodified lines | ||
| 2695 | 2695 | case TOK_ASM_vcmpeq_f64: |
| 2696 | 2696 | case TOK_ASM_vcmpeeq_f64: |
| 2697 | 2697 | case TOK_ASM_vmoveq_f64: |
| 2698 | − asm_floating_point_data_processing_opcode(s1, token); | |
| 2698 | + asm_floating_point_data_processing_opcode(S, token); | |
| 2699 | 2699 | return; |
| 2700 | 2700 | |
| 2701 | 2701 | case TOK_ASM_vcvtreq_s32_f32: |
| @@ -2712,7 +2712,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 10 unmodified lines | ||
| 2712 | 2712 | case TOK_ASM_vcvteq_f32_u32: |
| 2713 | 2713 | case TOK_ASM_vcvteq_f64_f32: |
| 2714 | 2714 | case TOK_ASM_vcvteq_f32_f64: |
| 2715 | − asm_floating_point_vcvt_data_processing_opcode(s1, token); | |
| 2715 | + asm_floating_point_vcvt_data_processing_opcode(S, token); | |
| 2716 | 2716 | return; |
| 2717 | 2717 | |
| 2718 | 2718 | case TOK_ASM_vpusheq: |
| @@ -2723,21 +2723,21 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 4 unmodified lines | ||
| 2723 | 2723 | case TOK_ASM_vstmeq: |
| 2724 | 2724 | case TOK_ASM_vstmiaeq: |
| 2725 | 2725 | case TOK_ASM_vstmdbeq: |
| 2726 | − asm_floating_point_block_data_transfer_opcode(s1, token); | |
| 2726 | + asm_floating_point_block_data_transfer_opcode(S, token); | |
| 2727 | 2727 | return; |
| 2728 | 2728 | |
| 2729 | 2729 | case TOK_ASM_vmsreq: |
| 2730 | 2730 | case TOK_ASM_vmrseq: |
| 2731 | − asm_floating_point_status_register_opcode(s1, token); | |
| 2731 | + asm_floating_point_status_register_opcode(S, token); | |
| 2732 | 2732 | return; |
| 2733 | 2733 | #endif |
| 2734 | 2734 | |
| 2735 | 2735 | default: |
| 2736 | − expect("known instruction"); | |
| 2736 | + expect(S, "known instruction"); | |
| 2737 | 2737 | } |
| 2738 | 2738 | } |
| 2739 | 2739 | |
| 2740 | −ST_FUNC void subst_asm_operand(CString *add_str, SValue *sv, int modifier) | |
| 2740 | +ST_FUNC void subst_asm_operand(TCCState* S, CString *add_str, SValue *sv, int modifier) | |
| 2741 | 2741 | { |
| 2742 | 2742 | int r, reg, size, val; |
| 2743 | 2743 | char buf[64]; |
| @@ -2746,45 +2746,45 @@ ST_FUNC void subst_asm_operand(CString *add_str, SValue *sv, int modifier) · 2 unmodified lines | ||
| 2746 | 2746 | if ((r & VT_VALMASK) == VT_CONST) { |
| 2747 | 2747 | if (!(r & VT_LVAL) && modifier != 'c' && modifier != 'n' && |
| 2748 | 2748 | modifier != 'P') |
| 2749 | − cstr_ccat(add_str, '#'); | |
| 2749 | + cstr_ccat(S, add_str, '#'); | |
| 2750 | 2750 | if (r & VT_SYM) { |
| 2751 | − const char *name = get_tok_str(sv->sym->v, NULL); | |
| 2751 | + const char *name = get_tok_str(S, sv->sym->v, NULL); | |
| 2752 | 2752 | if (sv->sym->v >= SYM_FIRST_ANOM) { |
| 2753 | 2753 | /* In case of anonymous symbols ("L.42", used |
| 2754 | 2754 | for static data labels) we can't find them |
| 2755 | 2755 | in the C symbol table when later looking up |
| 2756 | 2756 | this name. So enter them now into the asm label |
| 2757 | 2757 | list when we still know the symbol. */ |
| 2758 | − get_asm_sym(tok_alloc(name, strlen(name))->tok, sv->sym); | |
| 2758 | + get_asm_sym(S, tok_alloc(S, name, strlen(name))->tok, sv->sym); | |
| 2759 | 2759 | } |
| 2760 | − if (tcc_state->leading_underscore) | |
| 2761 | − cstr_ccat(add_str, '_'); | |
| 2762 | − cstr_cat(add_str, name, -1); | |
| 2760 | + if (S->leading_underscore) | |
| 2761 | + cstr_ccat(S, add_str, '_'); | |
| 2762 | + cstr_cat(S, add_str, name, -1); | |
| 2763 | 2763 | if ((uint32_t) sv->c.i == 0) |
| 2764 | 2764 | goto no_offset; |
| 2765 | − cstr_ccat(add_str, '+'); | |
| 2765 | + cstr_ccat(S, add_str, '+'); | |
| 2766 | 2766 | } |
| 2767 | 2767 | val = sv->c.i; |
| 2768 | 2768 | if (modifier == 'n') |
| 2769 | 2769 | val = -val; |
| 2770 | 2770 | snprintf(buf, sizeof(buf), "%d", (int) sv->c.i); |
| 2771 | − cstr_cat(add_str, buf, -1); | |
| 2771 | + cstr_cat(S, add_str, buf, -1); | |
| 2772 | 2772 | no_offset:; |
| 2773 | 2773 | } else if ((r & VT_VALMASK) == VT_LOCAL) { |
| 2774 | 2774 | snprintf(buf, sizeof(buf), "[fp,#%d]", (int) sv->c.i); |
| 2775 | − cstr_cat(add_str, buf, -1); | |
| 2775 | + cstr_cat(S, add_str, buf, -1); | |
| 2776 | 2776 | } else if (r & VT_LVAL) { |
| 2777 | 2777 | reg = r & VT_VALMASK; |
| 2778 | 2778 | if (reg >= VT_CONST) |
| 2779 | − tcc_internal_error(""); | |
| 2779 | + tcc_internal_error(S, ""); | |
| 2780 | 2780 | snprintf(buf, sizeof(buf), "[%s]", |
| 2781 | − get_tok_str(TOK_ASM_r0 + reg, NULL)); | |
| 2782 | − cstr_cat(add_str, buf, -1); | |
| 2781 | + get_tok_str(S, TOK_ASM_r0 + reg, NULL)); | |
| 2782 | + cstr_cat(S, add_str, buf, -1); | |
| 2783 | 2783 | } else { |
| 2784 | 2784 | /* register case */ |
| 2785 | 2785 | reg = r & VT_VALMASK; |
| 2786 | 2786 | if (reg >= VT_CONST) |
| 2787 | − tcc_internal_error(""); | |
| 2787 | + tcc_internal_error(S, ""); | |
| 2788 | 2788 | |
| 2789 | 2789 | /* choose register operand size */ |
| 2790 | 2790 | if ((sv->type.t & VT_BTYPE) == VT_BYTE || |
| @@ -2808,13 +2808,13 @@ ST_FUNC void subst_asm_operand(CString *add_str, SValue *sv, int modifier) · 17 unmodified lines | ||
| 2808 | 2808 | reg = TOK_ASM_r0 + reg; |
| 2809 | 2809 | break; |
| 2810 | 2810 | } |
| 2811 | − snprintf(buf, sizeof(buf), "%s", get_tok_str(reg, NULL)); | |
| 2812 | − cstr_cat(add_str, buf, -1); | |
| 2811 | + snprintf(buf, sizeof(buf), "%s", get_tok_str(S, reg, NULL)); | |
| 2812 | + cstr_cat(S, add_str, buf, -1); | |
| 2813 | 2813 | } |
| 2814 | 2814 | } |
| 2815 | 2815 | |
| 2816 | 2816 | /* generate prolog and epilog code for asm statement */ |
| 2817 | −ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, | |
| 2817 | +ST_FUNC void asm_gen_code(TCCState* S, ASMOperand *operands, int nb_operands, | |
| 2818 | 2818 | int nb_outputs, int is_output, |
| 2819 | 2819 | uint8_t *clobber_regs, |
| 2820 | 2820 | int out_reg) |
| @@ -2844,7 +2844,7 @@ ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, · 23 unmodified lines | ||
| 2844 | 2844 | if (!is_output) { // prolog |
| 2845 | 2845 | /* generate reg save code */ |
| 2846 | 2846 | if (saved_regset) |
| 2847 | − gen_le32(0xe92d0000 | saved_regset); // push {...} | |
| 2847 | + gen_le32(S, 0xe92d0000 | saved_regset); // push {...} | |
| 2848 | 2848 | |
| 2849 | 2849 | /* generate load code */ |
| 2850 | 2850 | for(i = 0; i < nb_operands; i++) { |
| @@ -2858,12 +2858,12 @@ ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, · 7 unmodified lines | ||
| 2858 | 2858 | sv = *op->vt; |
| 2859 | 2859 | sv.r = (sv.r & ~VT_VALMASK) | VT_LOCAL | VT_LVAL; |
| 2860 | 2860 | sv.type.t = VT_PTR; |
| 2861 | − load(op->reg, &sv); | |
| 2861 | + load(S, op->reg, &sv); | |
| 2862 | 2862 | } else if (i >= nb_outputs || op->is_rw) { // not write-only |
| 2863 | 2863 | /* load value in register */ |
| 2864 | − load(op->reg, op->vt); | |
| 2864 | + load(S, op->reg, op->vt); | |
| 2865 | 2865 | if (op->is_llong) |
| 2866 | − tcc_error("long long not implemented"); | |
| 2866 | + tcc_error(S, "long long not implemented"); | |
| 2867 | 2867 | } |
| 2868 | 2868 | } |
| 2869 | 2869 | } |
| @@ -2878,29 +2878,29 @@ ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, · 8 unmodified lines | ||
| 2878 | 2878 | sv = *op->vt; |
| 2879 | 2879 | sv.r = (sv.r & ~VT_VALMASK) | VT_LOCAL; |
| 2880 | 2880 | sv.type.t = VT_PTR; |
| 2881 | − load(out_reg, &sv); | |
| 2881 | + load(S, out_reg, &sv); | |
| 2882 | 2882 | |
| 2883 | 2883 | sv = *op->vt; |
| 2884 | 2884 | sv.r = (sv.r & ~VT_VALMASK) | out_reg; |
| 2885 | − store(op->reg, &sv); | |
| 2885 | + store(S, op->reg, &sv); | |
| 2886 | 2886 | } |
| 2887 | 2887 | } else { |
| 2888 | − store(op->reg, op->vt); | |
| 2888 | + store(S, op->reg, op->vt); | |
| 2889 | 2889 | if (op->is_llong) |
| 2890 | − tcc_error("long long not implemented"); | |
| 2890 | + tcc_error(S, "long long not implemented"); | |
| 2891 | 2891 | } |
| 2892 | 2892 | } |
| 2893 | 2893 | } |
| 2894 | 2894 | |
| 2895 | 2895 | /* generate reg restore code */ |
| 2896 | 2896 | if (saved_regset) |
| 2897 | − gen_le32(0xe8bd0000 | saved_regset); // pop {...} | |
| 2897 | + gen_le32(S, 0xe8bd0000 | saved_regset); // pop {...} | |
| 2898 | 2898 | } |
| 2899 | 2899 | } |
| 2900 | 2900 | |
| 2901 | 2901 | /* return the constraint priority (we allocate first the lowest |
| 2902 | 2902 | numbered constraints) */ |
| 2903 | −static inline int constraint_priority(const char *str) | |
| 2903 | +static inline int constraint_priority(TCCState* S, const char *str) | |
| 2904 | 2904 | { |
| 2905 | 2905 | int priority, c, pr; |
| 2906 | 2906 | |
| @@ -2927,7 +2927,7 @@ static inline int constraint_priority(const char *str) · 20 unmodified lines | ||
| 2927 | 2927 | pr = 4; |
| 2928 | 2928 | break; |
| 2929 | 2929 | default: |
| 2930 | − tcc_error("unknown constraint '%c'", c); | |
| 2930 | + tcc_error(S, "unknown constraint '%c'", c); | |
| 2931 | 2931 | pr = 0; |
| 2932 | 2932 | } |
| 2933 | 2933 | if (pr > priority) |
| @@ -2956,7 +2956,7 @@ static const char *skip_constraint_modifiers(const char *p) · 22 unmodified lines | ||
| 2956 | 2956 | |
| 2957 | 2957 | #define is_reg_allocated(reg) (regs_allocated[reg] & reg_mask) |
| 2958 | 2958 | |
| 2959 | −ST_FUNC void asm_compute_constraints(ASMOperand *operands, | |
| 2959 | +ST_FUNC void asm_compute_constraints(TCCState* S, ASMOperand *operands, | |
| 2960 | 2960 | int nb_operands, int nb_outputs, |
| 2961 | 2961 | const uint8_t *clobber_regs, |
| 2962 | 2962 | int *pout_reg) |
| @@ -3009,13 +3009,13 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 46 unmodified lines | ||
| 3009 | 3009 | str = skip_constraint_modifiers(str); |
| 3010 | 3010 | if (isnum(*str) || *str == '[') { |
| 3011 | 3011 | /* this is a reference to another constraint */ |
| 3012 | − k = find_constraint(operands, nb_operands, str, NULL); | |
| 3012 | + k = find_constraint(S, operands, nb_operands, str, NULL); | |
| 3013 | 3013 | if ((unsigned) k >= i || i < nb_outputs) |
| 3014 | − tcc_error("invalid reference in constraint %d ('%s')", | |
| 3014 | + tcc_error(S, "invalid reference in constraint %d ('%s')", | |
| 3015 | 3015 | i, str); |
| 3016 | 3016 | op->ref_index = k; |
| 3017 | 3017 | if (operands[k].input_index >= 0) |
| 3018 | − tcc_error("cannot reference twice the same operand"); | |
| 3018 | + tcc_error(S, "cannot reference twice the same operand"); | |
| 3019 | 3019 | operands[k].input_index = i; |
| 3020 | 3020 | op->priority = 5; |
| 3021 | 3021 | } else if ((op->vt->r & VT_VALMASK) == VT_LOCAL |
| @@ -3024,7 +3024,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 2 unmodified lines | ||
| 3024 | 3024 | op->priority = 1; |
| 3025 | 3025 | op->reg = reg; |
| 3026 | 3026 | } else { |
| 3027 | − op->priority = constraint_priority(str); | |
| 3027 | + op->priority = constraint_priority(S, str); | |
| 3028 | 3028 | } |
| 3029 | 3029 | } |
| 3030 | 3030 | |
| @@ -3073,7 +3073,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 42 unmodified lines | ||
| 3073 | 3073 | if (op->reg >= 0) { |
| 3074 | 3074 | if (is_reg_allocated(op->reg)) |
| 3075 | 3075 | tcc_error |
| 3076 | − ("asm regvar requests register that's taken already"); | |
| 3076 | + (S, "asm regvar requests register that's taken already"); | |
| 3077 | 3077 | reg = op->reg; |
| 3078 | 3078 | goto reg_found; |
| 3079 | 3079 | } |
| @@ -3087,7 +3087,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 7 unmodified lines | ||
| 3087 | 3087 | /* FALL THRU */ |
| 3088 | 3088 | case '&': // Operand is clobbered before the instruction is done using the input operands |
| 3089 | 3089 | if (j >= nb_outputs) |
| 3090 | − tcc_error("'%c' modifier can only be applied to outputs", | |
| 3090 | + tcc_error(S, "'%c' modifier can only be applied to outputs", | |
| 3091 | 3091 | c); |
| 3092 | 3092 | reg_mask = REG_IN_MASK | REG_OUT_MASK; |
| 3093 | 3093 | goto try_next; |
| @@ -3147,7 +3147,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 53 unmodified lines | ||
| 3147 | 3147 | } |
| 3148 | 3148 | break; |
| 3149 | 3149 | default: |
| 3150 | − tcc_error("asm constraint %d ('%s') could not be satisfied", | |
| 3150 | + tcc_error(S, "asm constraint %d ('%s') could not be satisfied", | |
| 3151 | 3151 | j, op->constraint); |
| 3152 | 3152 | break; |
| 3153 | 3153 | } |
| @@ -3169,7 +3169,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 15 unmodified lines | ||
| 3169 | 3169 | if (!(regs_allocated[reg] & REG_OUT_MASK)) |
| 3170 | 3170 | goto reg_found2; |
| 3171 | 3171 | } |
| 3172 | − tcc_error("could not find free output register for reloading"); | |
| 3172 | + tcc_error(S, "could not find free output register for reloading"); | |
| 3173 | 3173 | reg_found2: |
| 3174 | 3174 | *pout_reg = reg; |
| 3175 | 3175 | break; |
| @@ -3183,7 +3183,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 7 unmodified lines | ||
| 3183 | 3183 | op = &operands[j]; |
| 3184 | 3184 | printf("%%%d [%s]: \"%s\" r=0x%04x reg=%d\n", |
| 3185 | 3185 | j, |
| 3186 | − op->id ? get_tok_str(op->id, NULL) : "", | |
| 3186 | + op->id ? get_tok_str(S, op->id, NULL) : "", | |
| 3187 | 3187 | op->constraint, op->vt->r, op->reg); |
| 3188 | 3188 | } |
| 3189 | 3189 | if (*pout_reg >= 0) |
| @@ -3191,7 +3191,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 1 unmodified line | ||
| 3191 | 3191 | #endif |
| 3192 | 3192 | } |
| 3193 | 3193 | |
| 3194 | −ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str) | |
| 3194 | +ST_FUNC void asm_clobber(TCCState* S, uint8_t *clobber_regs, const char *str) | |
| 3195 | 3195 | { |
| 3196 | 3196 | int reg; |
| 3197 | 3197 | TokenSym *ts; |
| @@ -3200,17 +3200,17 @@ ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str) · 2 unmodified lines | ||
| 3200 | 3200 | !strcmp(str, "cc") || |
| 3201 | 3201 | !strcmp(str, "flags")) |
| 3202 | 3202 | return; |
| 3203 | − ts = tok_alloc(str, strlen(str)); | |
| 3204 | − reg = asm_parse_regvar(ts->tok); | |
| 3203 | + ts = tok_alloc(S, str, strlen(str)); | |
| 3204 | + reg = asm_parse_regvar(S, ts->tok); | |
| 3205 | 3205 | if (reg == -1) { |
| 3206 | − tcc_error("invalid clobber register '%s'", str); | |
| 3206 | + tcc_error(S, "invalid clobber register '%s'", str); | |
| 3207 | 3207 | } |
| 3208 | 3208 | clobber_regs[reg] = 1; |
| 3209 | 3209 | } |
| 3210 | 3210 | |
| 3211 | 3211 | /* If T refers to a register then return the register number and type. |
| 3212 | 3212 | Otherwise return -1. */ |
| 3213 | −ST_FUNC int asm_parse_regvar (int t) | |
| 3213 | +ST_FUNC int asm_parse_regvar (TCCState *S, int t) | |
| 3214 | 3214 | { |
| 3215 | 3215 | if (t >= TOK_ASM_r0 && t <= TOK_ASM_pc) { /* register name */ |
| 3216 | 3216 | switch (t) { |
| @@ -179,24 +179,17 @@ ST_DATA const int reg_classes[NB_REGS] = { · 178 unmodified lines | ||
| 179 | 179 | static int func_sub_sp_offset, last_itod_magic; |
| 180 | 180 | static int leaffunc; |
| 181 | 181 | |
| 182 | −#if defined(CONFIG_TCC_BCHECK) | |
| 183 | −static addr_t func_bound_offset; | |
| 184 | −static unsigned long func_bound_ind; | |
| 185 | −ST_DATA int func_bound_add_epilog; | |
| 186 | −#endif | |
| 187 | − | |
| 188 | 182 | #if defined(TCC_ARM_EABI) && defined(TCC_ARM_VFP) |
| 189 | −static CType float_type, double_type, func_float_type, func_double_type; | |
| 190 | −ST_FUNC void arm_init(struct TCCState *s) | |
| 183 | +ST_FUNC void arm_init(TCCState *S) | |
| 191 | 184 | { |
| 192 | − float_type.t = VT_FLOAT; | |
| 193 | − double_type.t = VT_DOUBLE; | |
| 194 | − func_float_type.t = VT_FUNC; | |
| 195 | − func_float_type.ref = sym_push(SYM_FIELD, &float_type, FUNC_CDECL, FUNC_OLD); | |
| 196 | − func_double_type.t = VT_FUNC; | |
| 197 | − func_double_type.ref = sym_push(SYM_FIELD, &double_type, FUNC_CDECL, FUNC_OLD); | |
| 198 | − | |
| 199 | − float_abi = s->float_abi; | |
| 185 | + S->armgen_float_type.t = VT_FLOAT; | |
| 186 | + S->armgen_double_type.t = VT_DOUBLE; | |
| 187 | + S->armgen_func_float_type.t = VT_FUNC; | |
| 188 | + S->armgen_func_float_type.ref = sym_push(S, SYM_FIELD, &S->armgen_float_type, FUNC_CDECL, FUNC_OLD); | |
| 189 | + S->armgen_func_double_type.t = VT_FUNC; | |
| 190 | + S->armgen_func_double_type.ref = sym_push(S, SYM_FIELD, &S->armgen_double_type, FUNC_CDECL, FUNC_OLD); | |
| 191 | + | |
| 192 | + float_abi = S->float_abi; | |
| 200 | 193 | #ifndef TCC_ARM_HARDFLOAT |
| 201 | 194 | // XXX: Works on OpenBSD |
| 202 | 195 | // # warning "soft float ABI currently not supported: default to softfp" |
| @@ -223,15 +216,15 @@ ST_FUNC void arm_init(struct TCCState *s) · 20 unmodified lines | ||
| 223 | 216 | |
| 224 | 217 | #define CHECK_R(r) ((r) >= TREG_R0 && (r) <= TREG_LR) |
| 225 | 218 | |
| 226 | −static int two2mask(int a,int b) { | |
| 219 | +static int two2mask(TCCState* S, int a,int b) { | |
| 227 | 220 | if (!CHECK_R(a) || !CHECK_R(b)) |
| 228 | − tcc_error("compiler error! registers %i,%i is not valid",a,b); | |
| 221 | + tcc_error(S, "compiler error! registers %i,%i is not valid",a,b); | |
| 229 | 222 | return (reg_classes[a]|reg_classes[b])&~(RC_INT|RC_FLOAT); |
| 230 | 223 | } |
| 231 | 224 | |
| 232 | −static int regmask(int r) { | |
| 225 | +static int regmask(TCCState* S, int r) { | |
| 233 | 226 | if (!CHECK_R(r)) |
| 234 | − tcc_error("compiler error! register %i is not valid",r); | |
| 227 | + tcc_error(S, "compiler error! register %i is not valid",r); | |
| 235 | 228 | return reg_classes[r]&~(RC_INT|RC_FLOAT); |
| 236 | 229 | } |
| 237 | 230 | |
| @@ -247,25 +240,25 @@ const char *default_elfinterp(struct TCCState *s) · 9 unmodified lines | ||
| 247 | 240 | } |
| 248 | 241 | #endif |
| 249 | 242 | |
| 250 | −void o(uint32_t i) | |
| 243 | +void o(TCCState* S, uint32_t i) | |
| 251 | 244 | { |
| 252 | 245 | /* this is a good place to start adding big-endian support*/ |
| 253 | 246 | int ind1; |
| 254 | − if (nocode_wanted) | |
| 247 | + if (S->tccgen_nocode_wanted) | |
| 255 | 248 | return; |
| 256 | − ind1 = ind + 4; | |
| 249 | + ind1 = S->tccgen_ind + 4; | |
| 257 | 250 | if (!cur_text_section) |
| 258 | − tcc_error("compiler error! This happens f.ex. if the compiler\n" | |
| 251 | + tcc_error(S, "compiler error! This happens f.ex. if the compiler\n" | |
| 259 | 252 | "can't evaluate constant expressions outside of a function."); |
| 260 | 253 | if (ind1 > cur_text_section->data_allocated) |
| 261 | − section_realloc(cur_text_section, ind1); | |
| 262 | − cur_text_section->data[ind++] = i&255; | |
| 254 | + section_realloc(S, cur_text_section, ind1); | |
| 255 | + cur_text_section->data[S->tccgen_ind++] = i&255; | |
| 263 | 256 | i>>=8; |
| 264 | − cur_text_section->data[ind++] = i&255; | |
| 257 | + cur_text_section->data[S->tccgen_ind++] = i&255; | |
| 265 | 258 | i>>=8; |
| 266 | − cur_text_section->data[ind++] = i&255; | |
| 259 | + cur_text_section->data[S->tccgen_ind++] = i&255; | |
| 267 | 260 | i>>=8; |
| 268 | − cur_text_section->data[ind++] = i; | |
| 261 | + cur_text_section->data[S->tccgen_ind++] = i; | |
| 269 | 262 | } |
| 270 | 263 | |
| 271 | 264 | static uint32_t stuff_const(uint32_t op, uint32_t c) |
| @@ -322,11 +315,11 @@ static uint32_t stuff_const(uint32_t op, uint32_t c) · 50 unmodified lines | ||
| 322 | 315 | |
| 323 | 316 | |
| 324 | 317 | //only add,sub |
| 325 | −void stuff_const_harder(uint32_t op, uint32_t v) { | |
| 318 | +void stuff_const_harder(TCCState* S, uint32_t op, uint32_t v) { | |
| 326 | 319 | uint32_t x; |
| 327 | 320 | x=stuff_const(op,v); |
| 328 | 321 | if(x) |
| 329 | − o(x); | |
| 322 | + o(S, x); | |
| 330 | 323 | else { |
| 331 | 324 | uint32_t a[16], nv, no, o2, n2; |
| 332 | 325 | int i,j,k; |
| @@ -337,8 +330,8 @@ void stuff_const_harder(uint32_t op, uint32_t v) { · 4 unmodified lines | ||
| 337 | 330 | for(i=0;i<12;i++) |
| 338 | 331 | for(j=i<4?i+12:15;j>=i+4;j--) |
| 339 | 332 | if((v&(a[i]|a[j]))==v) { |
| 340 | − o(stuff_const(op,v&a[i])); | |
| 341 | − o(stuff_const(o2,v&a[j])); | |
| 333 | + o(S, stuff_const(op,v&a[i])); | |
| 334 | + o(S, stuff_const(o2,v&a[j])); | |
| 342 | 335 | return; |
| 343 | 336 | } |
| 344 | 337 | no=op^0xC00000; |
| @@ -347,17 +340,17 @@ void stuff_const_harder(uint32_t op, uint32_t v) { · 2 unmodified lines | ||
| 347 | 340 | for(i=0;i<12;i++) |
| 348 | 341 | for(j=i<4?i+12:15;j>=i+4;j--) |
| 349 | 342 | if((nv&(a[i]|a[j]))==nv) { |
| 350 | − o(stuff_const(no,nv&a[i])); | |
| 351 | − o(stuff_const(n2,nv&a[j])); | |
| 343 | + o(S, stuff_const(no,nv&a[i])); | |
| 344 | + o(S, stuff_const(n2,nv&a[j])); | |
| 352 | 345 | return; |
| 353 | 346 | } |
| 354 | 347 | for(i=0;i<8;i++) |
| 355 | 348 | for(j=i+4;j<12;j++) |
| 356 | 349 | for(k=i<4?i+12:15;k>=j+4;k--) |
| 357 | 350 | if((v&(a[i]|a[j]|a[k]))==v) { |
| 358 | − o(stuff_const(op,v&a[i])); | |
| 359 | − o(stuff_const(o2,v&a[j])); | |
| 360 | − o(stuff_const(o2,v&a[k])); | |
| 351 | + o(S, stuff_const(op,v&a[i])); | |
| 352 | + o(S, stuff_const(o2,v&a[j])); | |
| 353 | + o(S, stuff_const(o2,v&a[k])); | |
| 361 | 354 | return; |
| 362 | 355 | } |
| 363 | 356 | no=op^0xC00000; |
| @@ -366,31 +359,31 @@ void stuff_const_harder(uint32_t op, uint32_t v) { · 2 unmodified lines | ||
| 366 | 359 | for(j=i+4;j<12;j++) |
| 367 | 360 | for(k=i<4?i+12:15;k>=j+4;k--) |
| 368 | 361 | if((nv&(a[i]|a[j]|a[k]))==nv) { |
| 369 | − o(stuff_const(no,nv&a[i])); | |
| 370 | − o(stuff_const(n2,nv&a[j])); | |
| 371 | − o(stuff_const(n2,nv&a[k])); | |
| 362 | + o(S, stuff_const(no,nv&a[i])); | |
| 363 | + o(S, stuff_const(n2,nv&a[j])); | |
| 364 | + o(S, stuff_const(n2,nv&a[k])); | |
| 372 | 365 | return; |
| 373 | 366 | } |
| 374 | − o(stuff_const(op,v&a[0])); | |
| 375 | − o(stuff_const(o2,v&a[4])); | |
| 376 | − o(stuff_const(o2,v&a[8])); | |
| 377 | − o(stuff_const(o2,v&a[12])); | |
| 367 | + o(S, stuff_const(op,v&a[0])); | |
| 368 | + o(S, stuff_const(o2,v&a[4])); | |
| 369 | + o(S, stuff_const(o2,v&a[8])); | |
| 370 | + o(S, stuff_const(o2,v&a[12])); | |
| 378 | 371 | } |
| 379 | 372 | } |
| 380 | 373 | |
| 381 | −uint32_t encbranch(int pos, int addr, int fail) | |
| 374 | +uint32_t encbranch(TCCState* S, int pos, int addr, int fail) | |
| 382 | 375 | { |
| 383 | 376 | addr-=pos+8; |
| 384 | 377 | addr/=4; |
| 385 | 378 | if(addr>=0x1000000 || addr<-0x1000000) { |
| 386 | 379 | if(fail) |
| 387 | − tcc_error("FIXME: function bigger than 32MB"); | |
| 380 | + tcc_error(S, "FIXME: function bigger than 32MB"); | |
| 388 | 381 | return 0; |
| 389 | 382 | } |
| 390 | 383 | return 0x0A000000|(addr&0xffffff); |
| 391 | 384 | } |
| 392 | 385 | |
| 393 | −int decbranch(int pos) | |
| 386 | +int decbranch(TCCState* S, int pos) | |
| 394 | 387 | { |
| 395 | 388 | int x; |
| 396 | 389 | x=*(uint32_t *)(cur_text_section->data + pos); |
| @@ -401,50 +394,50 @@ int decbranch(int pos) · 4 unmodified lines | ||
| 401 | 394 | } |
| 402 | 395 | |
| 403 | 396 | /* output a symbol and patch all calls to it */ |
| 404 | −void gsym_addr(int t, int a) | |
| 397 | +void gsym_addr(TCCState* S, int t, int a) | |
| 405 | 398 | { |
| 406 | 399 | uint32_t *x; |
| 407 | 400 | int lt; |
| 408 | 401 | while(t) { |
| 409 | 402 | x=(uint32_t *)(cur_text_section->data + t); |
| 410 | − t=decbranch(lt=t); | |
| 403 | + t=decbranch(S, lt=t); | |
| 411 | 404 | if(a==lt+4) |
| 412 | 405 | *x=0xE1A00000; // nop |
| 413 | 406 | else { |
| 414 | 407 | *x &= 0xff000000; |
| 415 | − *x |= encbranch(lt,a,1); | |
| 408 | + *x |= encbranch(S, lt,a,1); | |
| 416 | 409 | } |
| 417 | 410 | } |
| 418 | 411 | } |
| 419 | 412 | |
| 420 | 413 | #ifdef TCC_ARM_VFP |
| 421 | −static uint32_t vfpr(int r) | |
| 414 | +static uint32_t vfpr(TCCState* S, int r) | |
| 422 | 415 | { |
| 423 | 416 | if(r<TREG_F0 || r>TREG_F7) |
| 424 | − tcc_error("compiler error! register %i is no vfp register",r); | |
| 417 | + tcc_error(S, "compiler error! register %i is no vfp register",r); | |
| 425 | 418 | return r - TREG_F0; |
| 426 | 419 | } |
| 427 | 420 | #else |
| 428 | −static uint32_t fpr(int r) | |
| 421 | +static uint32_t fpr(TCCState* S, int r) | |
| 429 | 422 | { |
| 430 | 423 | if(r<TREG_F0 || r>TREG_F3) |
| 431 | − tcc_error("compiler error! register %i is no fpa register",r); | |
| 424 | + tcc_error(S, "compiler error! register %i is no fpa register",r); | |
| 432 | 425 | return r - TREG_F0; |
| 433 | 426 | } |
| 434 | 427 | #endif |
| 435 | 428 | |
| 436 | −static uint32_t intr(int r) | |
| 429 | +static uint32_t intr(TCCState* S, int r) | |
| 437 | 430 | { |
| 438 | 431 | if(r == TREG_R12) |
| 439 | 432 | return 12; |
| 440 | 433 | if(r >= TREG_R0 && r <= TREG_R3) |
| 441 | 434 | return r - TREG_R0; |
| 442 | 435 | if (!(r >= TREG_SP && r <= TREG_LR)) |
| 443 | − tcc_error("compiler error! register %i is no int register",r); | |
| 436 | + tcc_error(S, "compiler error! register %i is no int register",r); | |
| 444 | 437 | return r + (13 - TREG_SP); |
| 445 | 438 | } |
| 446 | 439 | |
| 447 | −static void calcaddr(uint32_t *base, int *off, int *sgn, int maxoff, unsigned shift) | |
| 440 | +static void calcaddr(TCCState* S, uint32_t *base, int *off, int *sgn, int maxoff, unsigned shift) | |
| 448 | 441 | { |
| 449 | 442 | if(*off>maxoff || *off&((1<<shift)-1)) { |
| 450 | 443 | uint32_t x, y; |
| @@ -455,23 +448,23 @@ static void calcaddr(uint32_t *base, int *off, int *sgn, int maxoff, unsigned sh · 4 unmodified lines | ||
| 455 | 448 | *base=14; // lr |
| 456 | 449 | y=stuff_const(x,*off&~maxoff); |
| 457 | 450 | if(y) { |
| 458 | − o(y); | |
| 451 | + o(S, y); | |
| 459 | 452 | *off&=maxoff; |
| 460 | 453 | return; |
| 461 | 454 | } |
| 462 | 455 | y=stuff_const(x,(*off+maxoff)&~maxoff); |
| 463 | 456 | if(y) { |
| 464 | − o(y); | |
| 457 | + o(S, y); | |
| 465 | 458 | *sgn=!*sgn; |
| 466 | 459 | *off=((*off+maxoff)&~maxoff)-*off; |
| 467 | 460 | return; |
| 468 | 461 | } |
| 469 | − stuff_const_harder(x,*off&~maxoff); | |
| 462 | + stuff_const_harder(S, x,*off&~maxoff); | |
| 470 | 463 | *off&=maxoff; |
| 471 | 464 | } |
| 472 | 465 | } |
| 473 | 466 | |
| 474 | −static uint32_t mapcc(int cc) | |
| 467 | +static uint32_t mapcc(TCCState* S, int cc) | |
| 475 | 468 | { |
| 476 | 469 | switch(cc) |
| 477 | 470 | { |
| @@ -500,11 +493,11 @@ static uint32_t mapcc(int cc) · 22 unmodified lines | ||
| 500 | 493 | case TOK_GT: |
| 501 | 494 | return 0xC0000000; /* GT */ |
| 502 | 495 | } |
| 503 | − tcc_error("unexpected condition code"); | |
| 496 | + tcc_error(S, "unexpected condition code"); | |
| 504 | 497 | return 0xE0000000; /* AL */ |
| 505 | 498 | } |
| 506 | 499 | |
| 507 | −static int negcc(int cc) | |
| 500 | +static int negcc(TCCState* S, int cc) | |
| 508 | 501 | { |
| 509 | 502 | switch(cc) |
| 510 | 503 | { |
| @@ -533,44 +526,44 @@ static int negcc(int cc) · 22 unmodified lines | ||
| 533 | 526 | case TOK_GT: |
| 534 | 527 | return TOK_LE; |
| 535 | 528 | } |
| 536 | − tcc_error("unexpected condition code"); | |
| 529 | + tcc_error(S, "unexpected condition code"); | |
| 537 | 530 | return TOK_NE; |
| 538 | 531 | } |
| 539 | 532 | |
| 540 | 533 | /* Load value into register r. |
| 541 | 534 | Use relative/got addressing to avoid setting DT_TEXTREL */ |
| 542 | −static void load_value(SValue *sv, int r) | |
| 535 | +static void load_value(TCCState* S, SValue *sv, int r) | |
| 543 | 536 | { |
| 544 | − o(0xE59F0000|(intr(r)<<12)); /* ldr r, [pc] */ | |
| 545 | − o(0xEA000000); /* b $+4 */ | |
| 537 | + o(S, 0xE59F0000|(intr(S, r)<<12)); /* ldr r, [pc] */ | |
| 538 | + o(S, 0xEA000000); /* b $+4 */ | |
| 546 | 539 | #ifndef CONFIG_TCC_PIE |
| 547 | 540 | if(sv->r & VT_SYM) |
| 548 | − greloc(cur_text_section, sv->sym, ind, R_ARM_ABS32); | |
| 549 | − o(sv->c.i); | |
| 541 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind, R_ARM_ABS32); | |
| 542 | + o(S, sv->c.i); | |
| 550 | 543 | #else |
| 551 | 544 | if(sv->r & VT_SYM) { |
| 552 | 545 | if (sv->sym->type.t & VT_STATIC) { |
| 553 | 546 | greloc(cur_text_section, sv->sym, ind, R_ARM_REL32); |
| 554 | − o(sv->c.i - 12); | |
| 555 | − o(0xe080000f | (intr(r)<<12) | (intr(r)<<16)); // add rx,rx,pc | |
| 547 | + o(S, sv->c.i - 12); | |
| 548 | + o(S, 0xe080000f | (intr(S, r)<<12) | (intr(S, r)<<16)); // add rx,rx,pc | |
| 556 | 549 | } |
| 557 | 550 | else { |
| 558 | 551 | greloc(cur_text_section, sv->sym, ind, R_ARM_GOT_PREL); |
| 559 | − o(-12); | |
| 560 | − o(0xe080000f | (intr(r)<<12) | (intr(r)<<16)); // add rx,rx,pc | |
| 561 | − o(0xe5900000 | (intr(r)<<12) | (intr(r)<<16)); // ldr rx,[rx] | |
| 552 | + o(S, -12); | |
| 553 | + o(S, 0xe080000f | (intr(S, r)<<12) | (intr(S, r)<<16)); // add rx,rx,pc | |
| 554 | + o(S, 0xe5900000 | (intr(S, r)<<12) | (intr(S, r)<<16)); // ldr rx,[rx] | |
| 562 | 555 | if (sv->c.i) |
| 563 | − stuff_const_harder(0xe2800000 | (intr(r)<<12) | (intr(r)<<16), | |
| 556 | + stuff_const_harder(S, 0xe2800000 | (intr(S, r)<<12) | (intr(S, r)<<16), | |
| 564 | 557 | sv->c.i); |
| 565 | 558 | } |
| 566 | 559 | } |
| 567 | 560 | else |
| 568 | − o(sv->c.i); | |
| 561 | + o(S, sv->c.i); | |
| 569 | 562 | #endif |
| 570 | 563 | } |
| 571 | 564 | |
| 572 | 565 | /* load 'r' from value 'sv' */ |
| 573 | −void load(int r, SValue *sv) | |
| 566 | +void load(TCCState* S, int r, SValue *sv) | |
| 574 | 567 | { |
| 575 | 568 | int v, ft, fc, fr, sign; |
| 576 | 569 | uint32_t op; |
| @@ -594,7 +587,7 @@ void load(int r, SValue *sv) · 17 unmodified lines | ||
| 594 | 587 | v1.type.t = VT_PTR; |
| 595 | 588 | v1.r = VT_LOCAL | VT_LVAL; |
| 596 | 589 | v1.c.i = sv->c.i; |
| 597 | − load(TREG_LR, &v1); | |
| 590 | + load(S, TREG_LR, &v1); | |
| 598 | 591 | base = 14; /* lr */ |
| 599 | 592 | fc=sign=0; |
| 600 | 593 | v=VT_LOCAL; |
| @@ -603,25 +596,25 @@ void load(int r, SValue *sv) · 2 unmodified lines | ||
| 603 | 596 | v1.r = fr&~VT_LVAL; |
| 604 | 597 | v1.c.i = sv->c.i; |
| 605 | 598 | v1.sym=sv->sym; |
| 606 | − load(TREG_LR, &v1); | |
| 599 | + load(S, TREG_LR, &v1); | |
| 607 | 600 | base = 14; /* lr */ |
| 608 | 601 | fc=sign=0; |
| 609 | 602 | v=VT_LOCAL; |
| 610 | 603 | } else if(v < VT_CONST) { |
| 611 | − base=intr(v); | |
| 604 | + base=intr(S, v); | |
| 612 | 605 | fc=sign=0; |
| 613 | 606 | v=VT_LOCAL; |
| 614 | 607 | } |
| 615 | 608 | if(v == VT_LOCAL) { |
| 616 | 609 | if(is_float(ft)) { |
| 617 | − calcaddr(&base,&fc,&sign,1020,2); | |
| 610 | + calcaddr(S, &base,&fc,&sign,1020,2); | |
| 618 | 611 | #ifdef TCC_ARM_VFP |
| 619 | 612 | op=0xED100A00; /* flds */ |
| 620 | 613 | if(!sign) |
| 621 | 614 | op|=0x800000; |
| 622 | 615 | if ((ft & VT_BTYPE) != VT_FLOAT) |
| 623 | 616 | op|=0x100; /* flds -> fldd */ |
| 624 | − o(op|(vfpr(r)<<12)|(fc>>2)|(base<<16)); | |
| 617 | + o(S, op|(vfpr(S, r)<<12)|(fc>>2)|(base<<16)); | |
| 625 | 618 | #else |
| 626 | 619 | op=0xED100100; |
| 627 | 620 | if(!sign) |
| @@ -635,11 +628,11 @@ void load(int r, SValue *sv) · 7 unmodified lines | ||
| 635 | 628 | else if ((ft & VT_BTYPE) == VT_LDOUBLE) |
| 636 | 629 | op|=0x400000; |
| 637 | 630 | #endif |
| 638 | − o(op|(fpr(r)<<12)|(fc>>2)|(base<<16)); | |
| 631 | + o(S, op|(fpr(S, r)<<12)|(fc>>2)|(base<<16)); | |
| 639 | 632 | #endif |
| 640 | 633 | } else if((ft & (VT_BTYPE|VT_UNSIGNED)) == VT_BYTE |
| 641 | 634 | || (ft & VT_BTYPE) == VT_SHORT) { |
| 642 | − calcaddr(&base,&fc,&sign,255,0); | |
| 635 | + calcaddr(S, &base,&fc,&sign,255,0); | |
| 643 | 636 | op=0xE1500090; |
| 644 | 637 | if ((ft & VT_BTYPE) == VT_SHORT) |
| 645 | 638 | op|=0x20; |
| @@ -647,63 +640,63 @@ void load(int r, SValue *sv) · 1 unmodified line | ||
| 647 | 640 | op|=0x40; |
| 648 | 641 | if(!sign) |
| 649 | 642 | op|=0x800000; |
| 650 | − o(op|(intr(r)<<12)|(base<<16)|((fc&0xf0)<<4)|(fc&0xf)); | |
| 643 | + o(S, op|(intr(S, r)<<12)|(base<<16)|((fc&0xf0)<<4)|(fc&0xf)); | |
| 651 | 644 | } else { |
| 652 | − calcaddr(&base,&fc,&sign,4095,0); | |
| 645 | + calcaddr(S, &base,&fc,&sign,4095,0); | |
| 653 | 646 | op=0xE5100000; |
| 654 | 647 | if(!sign) |
| 655 | 648 | op|=0x800000; |
| 656 | 649 | if ((ft & VT_BTYPE) == VT_BYTE || (ft & VT_BTYPE) == VT_BOOL) |
| 657 | 650 | op|=0x400000; |
| 658 | − o(op|(intr(r)<<12)|fc|(base<<16)); | |
| 651 | + o(S, op|(intr(S, r)<<12)|fc|(base<<16)); | |
| 659 | 652 | } |
| 660 | 653 | return; |
| 661 | 654 | } |
| 662 | 655 | } else { |
| 663 | 656 | if (v == VT_CONST) { |
| 664 | − op=stuff_const(0xE3A00000|(intr(r)<<12),sv->c.i); | |
| 657 | + op=stuff_const(0xE3A00000|(intr(S, r)<<12),sv->c.i); | |
| 665 | 658 | if (fr & VT_SYM || !op) |
| 666 | − load_value(sv, r); | |
| 659 | + load_value(S, sv, r); | |
| 667 | 660 | else |
| 668 | − o(op); | |
| 661 | + o(S, op); | |
| 669 | 662 | return; |
| 670 | 663 | } else if (v == VT_LOCAL) { |
| 671 | − op=stuff_const(0xE28B0000|(intr(r)<<12),sv->c.i); | |
| 664 | + op=stuff_const(0xE28B0000|(intr(S, r)<<12),sv->c.i); | |
| 672 | 665 | if (fr & VT_SYM || !op) { |
| 673 | − load_value(sv, r); | |
| 674 | − o(0xE08B0000|(intr(r)<<12)|intr(r)); | |
| 666 | + load_value(S, sv, r); | |
| 667 | + o(S, 0xE08B0000|(intr(S, r)<<12)|intr(S, r)); | |
| 675 | 668 | } else |
| 676 | − o(op); | |
| 669 | + o(S, op); | |
| 677 | 670 | return; |
| 678 | 671 | } else if(v == VT_CMP) { |
| 679 | − o(mapcc(sv->c.i)|0x3A00001|(intr(r)<<12)); | |
| 680 | − o(mapcc(negcc(sv->c.i))|0x3A00000|(intr(r)<<12)); | |
| 672 | + o(S, mapcc(S, sv->c.i)|0x3A00001|(intr(S, r)<<12)); | |
| 673 | + o(S, mapcc(S, negcc(S, sv->c.i))|0x3A00000|(intr(S, r)<<12)); | |
| 681 | 674 | return; |
| 682 | 675 | } else if (v == VT_JMP || v == VT_JMPI) { |
| 683 | 676 | int t; |
| 684 | 677 | t = v & 1; |
| 685 | − o(0xE3A00000|(intr(r)<<12)|t); | |
| 686 | − o(0xEA000000); | |
| 687 | − gsym(sv->c.i); | |
| 688 | − o(0xE3A00000|(intr(r)<<12)|(t^1)); | |
| 678 | + o(S, 0xE3A00000|(intr(S, r)<<12)|t); | |
| 679 | + o(S, 0xEA000000); | |
| 680 | + gsym(S, sv->c.i); | |
| 681 | + o(S, 0xE3A00000|(intr(S, r)<<12)|(t^1)); | |
| 689 | 682 | return; |
| 690 | 683 | } else if (v < VT_CONST) { |
| 691 | 684 | if(is_float(ft)) |
| 692 | 685 | #ifdef TCC_ARM_VFP |
| 693 | − o(0xEEB00A40|(vfpr(r)<<12)|vfpr(v)|T2CPR(ft)); /* fcpyX */ | |
| 686 | + o(S, 0xEEB00A40|(vfpr(S, r)<<12)|vfpr(S, v)|T2CPR(ft)); /* fcpyX */ | |
| 694 | 687 | #else |
| 695 | − o(0xEE008180|(fpr(r)<<12)|fpr(v)); | |
| 688 | + o(S, 0xEE008180|(fpr(S, r)<<12)|fpr(S, v)); | |
| 696 | 689 | #endif |
| 697 | 690 | else |
| 698 | − o(0xE1A00000|(intr(r)<<12)|intr(v)); | |
| 691 | + o(S, 0xE1A00000|(intr(S, r)<<12)|intr(S, v)); | |
| 699 | 692 | return; |
| 700 | 693 | } |
| 701 | 694 | } |
| 702 | − tcc_error("load unimplemented!"); | |
| 695 | + tcc_error(S, "load unimplemented!"); | |
| 703 | 696 | } |
| 704 | 697 | |
| 705 | 698 | /* store register 'r' in lvalue 'v' */ |
| 706 | −void store(int r, SValue *sv) | |
| 699 | +void store(TCCState* S, int r, SValue *sv) | |
| 707 | 700 | { |
| 708 | 701 | SValue v1; |
| 709 | 702 | int v, ft, fc, fr, sign; |
| @@ -724,7 +717,7 @@ void store(int r, SValue *sv) · 14 unmodified lines | ||
| 724 | 717 | if (fr & VT_LVAL || fr == VT_LOCAL) { |
| 725 | 718 | uint32_t base = 0xb; /* fp */ |
| 726 | 719 | if(v < VT_CONST) { |
| 727 | − base=intr(v); | |
| 720 | + base=intr(S, v); | |
| 728 | 721 | v=VT_LOCAL; |
| 729 | 722 | fc=sign=0; |
| 730 | 723 | } else if(v == VT_CONST) { |
| @@ -732,21 +725,21 @@ void store(int r, SValue *sv) · 1 unmodified line | ||
| 732 | 725 | v1.r = fr&~VT_LVAL; |
| 733 | 726 | v1.c.i = sv->c.i; |
| 734 | 727 | v1.sym=sv->sym; |
| 735 | − load(TREG_LR, &v1); | |
| 728 | + load(S, TREG_LR, &v1); | |
| 736 | 729 | base = 14; /* lr */ |
| 737 | 730 | fc=sign=0; |
| 738 | 731 | v=VT_LOCAL; |
| 739 | 732 | } |
| 740 | 733 | if(v == VT_LOCAL) { |
| 741 | 734 | if(is_float(ft)) { |
| 742 | − calcaddr(&base,&fc,&sign,1020,2); | |
| 735 | + calcaddr(S, &base,&fc,&sign,1020,2); | |
| 743 | 736 | #ifdef TCC_ARM_VFP |
| 744 | 737 | op=0xED000A00; /* fsts */ |
| 745 | 738 | if(!sign) |
| 746 | 739 | op|=0x800000; |
| 747 | 740 | if ((ft & VT_BTYPE) != VT_FLOAT) |
| 748 | 741 | op|=0x100; /* fsts -> fstd */ |
| 749 | − o(op|(vfpr(r)<<12)|(fc>>2)|(base<<16)); | |
| 742 | + o(S, op|(vfpr(S, r)<<12)|(fc>>2)|(base<<16)); | |
| 750 | 743 | #else |
| 751 | 744 | op=0xED000100; |
| 752 | 745 | if(!sign) |
| @@ -760,138 +753,138 @@ void store(int r, SValue *sv) · 7 unmodified lines | ||
| 760 | 753 | if ((ft & VT_BTYPE) == VT_LDOUBLE) |
| 761 | 754 | op|=0x400000; |
| 762 | 755 | #endif |
| 763 | − o(op|(fpr(r)<<12)|(fc>>2)|(base<<16)); | |
| 756 | + o(S, op|(fpr(S, r)<<12)|(fc>>2)|(base<<16)); | |
| 764 | 757 | #endif |
| 765 | 758 | return; |
| 766 | 759 | } else if((ft & VT_BTYPE) == VT_SHORT) { |
| 767 | − calcaddr(&base,&fc,&sign,255,0); | |
| 760 | + calcaddr(S, &base,&fc,&sign,255,0); | |
| 768 | 761 | op=0xE14000B0; |
| 769 | 762 | if(!sign) |
| 770 | 763 | op|=0x800000; |
| 771 | − o(op|(intr(r)<<12)|(base<<16)|((fc&0xf0)<<4)|(fc&0xf)); | |
| 764 | + o(S, op|(intr(S, r)<<12)|(base<<16)|((fc&0xf0)<<4)|(fc&0xf)); | |
| 772 | 765 | } else { |
| 773 | − calcaddr(&base,&fc,&sign,4095,0); | |
| 766 | + calcaddr(S, &base,&fc,&sign,4095,0); | |
| 774 | 767 | op=0xE5000000; |
| 775 | 768 | if(!sign) |
| 776 | 769 | op|=0x800000; |
| 777 | 770 | if ((ft & VT_BTYPE) == VT_BYTE || (ft & VT_BTYPE) == VT_BOOL) |
| 778 | 771 | op|=0x400000; |
| 779 | − o(op|(intr(r)<<12)|fc|(base<<16)); | |
| 772 | + o(S, op|(intr(S, r)<<12)|fc|(base<<16)); | |
| 780 | 773 | } |
| 781 | 774 | return; |
| 782 | 775 | } |
| 783 | 776 | } |
| 784 | − tcc_error("store unimplemented"); | |
| 777 | + tcc_error(S, "store unimplemented"); | |
| 785 | 778 | } |
| 786 | 779 | |
| 787 | −static void gadd_sp(int val) | |
| 780 | +static void gadd_sp(TCCState* S, int val) | |
| 788 | 781 | { |
| 789 | − stuff_const_harder(0xE28DD000,val); | |
| 782 | + stuff_const_harder(S, 0xE28DD000,val); | |
| 790 | 783 | } |
| 791 | 784 | |
| 792 | 785 | /* 'is_jmp' is '1' if it is a jump */ |
| 793 | −static void gcall_or_jmp(int is_jmp) | |
| 786 | +static void gcall_or_jmp(TCCState* S, int is_jmp) | |
| 794 | 787 | { |
| 795 | 788 | int r; |
| 796 | 789 | uint32_t x; |
| 797 | − if ((vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST) { | |
| 790 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST) { | |
| 798 | 791 | /* constant case */ |
| 799 | − if(vtop->r & VT_SYM){ | |
| 800 | − x=encbranch(ind,ind+vtop->c.i,0); | |
| 792 | + if(S->tccgen_vtop->r & VT_SYM){ | |
| 793 | + x=encbranch(S, S->tccgen_ind, S->tccgen_ind+S->tccgen_vtop->c.i,0); | |
| 801 | 794 | if(x) { |
| 802 | 795 | /* relocation case */ |
| 803 | − greloc(cur_text_section, vtop->sym, ind, R_ARM_PC24); | |
| 804 | − o(x|(is_jmp?0xE0000000:0xE1000000)); | |
| 796 | + greloc(S, cur_text_section, S->tccgen_vtop->sym, S->tccgen_ind, R_ARM_PC24); | |
| 797 | + o(S, x|(is_jmp?0xE0000000:0xE1000000)); | |
| 805 | 798 | } else { |
| 806 | 799 | r = TREG_LR; |
| 807 | − load_value(vtop, r); | |
| 800 | + load_value(S, S->tccgen_vtop, r); | |
| 808 | 801 | if(is_jmp) |
| 809 | − o(0xE1A0F000 | intr(r)); // mov pc, r | |
| 802 | + o(S, 0xE1A0F000 | intr(S, r)); // mov pc, r | |
| 810 | 803 | else |
| 811 | − o(0xe12fff30 | intr(r)); // blx r | |
| 804 | + o(S, 0xe12fff30 | intr(S, r)); // blx r | |
| 812 | 805 | } |
| 813 | 806 | }else{ |
| 814 | 807 | if(!is_jmp) |
| 815 | − o(0xE28FE004); // add lr,pc,#4 | |
| 816 | − o(0xE51FF004); // ldr pc,[pc,#-4] | |
| 817 | − o(vtop->c.i); | |
| 808 | + o(S, 0xE28FE004); // add lr,pc,#4 | |
| 809 | + o(S, 0xE51FF004); // ldr pc,[pc,#-4] | |
| 810 | + o(S, S->tccgen_vtop->c.i); | |
| 818 | 811 | } |
| 819 | 812 | } else { |
| 820 | 813 | /* otherwise, indirect call */ |
| 821 | 814 | #ifdef CONFIG_TCC_BCHECK |
| 822 | − vtop->r &= ~VT_MUSTBOUND; | |
| 815 | + S->tccgen_vtop->r &= ~VT_MUSTBOUND; | |
| 823 | 816 | #endif |
| 824 | − r = gv(RC_INT); | |
| 817 | + r = gv(S, RC_INT); | |
| 825 | 818 | if(!is_jmp) |
| 826 | − o(0xE1A0E00F); // mov lr,pc | |
| 827 | − o(0xE1A0F000|intr(r)); // mov pc,r | |
| 819 | + o(S, 0xE1A0E00F); // mov lr,pc | |
| 820 | + o(S, 0xE1A0F000|intr(S, r)); // mov pc,r | |
| 828 | 821 | } |
| 829 | 822 | } |
| 830 | 823 | |
| 831 | 824 | #if defined(CONFIG_TCC_BCHECK) |
| 832 | 825 | |
| 833 | −static void gen_bounds_call(int v) | |
| 826 | +static void gen_bounds_call(TCCState* S, int v) | |
| 834 | 827 | { |
| 835 | − Sym *sym = external_helper_sym(v); | |
| 828 | + Sym *sym = external_helper_sym(S, v); | |
| 836 | 829 | |
| 837 | − greloc(cur_text_section, sym, ind, R_ARM_PC24); | |
| 838 | − o(0xebfffffe); | |
| 830 | + greloc(S, cur_text_section, sym, S->tccgen_ind, R_ARM_PC24); | |
| 831 | + o(S, 0xebfffffe); | |
| 839 | 832 | } |
| 840 | 833 | |
| 841 | −static void gen_bounds_prolog(void) | |
| 834 | +static void gen_bounds_prolog(TCCState* S) | |
| 842 | 835 | { |
| 843 | 836 | /* leave some room for bound checking code */ |
| 844 | − func_bound_offset = lbounds_section->data_offset; | |
| 845 | − func_bound_ind = ind; | |
| 846 | − func_bound_add_epilog = 0; | |
| 847 | − o(0xe1a00000); /* ld r0,lbounds_section->data_offset */ | |
| 848 | − o(0xe1a00000); | |
| 849 | − o(0xe1a00000); | |
| 850 | − o(0xe1a00000); | |
| 851 | − o(0xe1a00000); /* call __bound_local_new */ | |
| 837 | + S->func_bound_offset = lbounds_section->data_offset; | |
| 838 | + S->func_bound_ind = S->tccgen_ind; | |
| 839 | + S->func_bound_add_epilog = 0; | |
| 840 | + o(S, 0xe1a00000); /* ld r0,lbounds_section->data_offset */ | |
| 841 | + o(S, 0xe1a00000); | |
| 842 | + o(S, 0xe1a00000); | |
| 843 | + o(S, 0xe1a00000); | |
| 844 | + o(S, 0xe1a00000); /* call __bound_local_new */ | |
| 852 | 845 | } |
| 853 | 846 | |
| 854 | −static void gen_bounds_epilog(void) | |
| 847 | +static void gen_bounds_epilog(TCCState* S) | |
| 855 | 848 | { |
| 856 | 849 | addr_t saved_ind; |
| 857 | 850 | addr_t *bounds_ptr; |
| 858 | 851 | Sym *sym_data; |
| 859 | − int offset_modified = func_bound_offset != lbounds_section->data_offset; | |
| 852 | + int offset_modified = S->func_bound_offset != lbounds_section->data_offset; | |
| 860 | 853 | |
| 861 | − if (!offset_modified && !func_bound_add_epilog) | |
| 854 | + if (!offset_modified && !S->func_bound_add_epilog) | |
| 862 | 855 | return; |
| 863 | 856 | |
| 864 | 857 | /* add end of table info */ |
| 865 | − bounds_ptr = section_ptr_add(lbounds_section, sizeof(addr_t)); | |
| 858 | + bounds_ptr = section_ptr_add(S, lbounds_section, sizeof(addr_t)); | |
| 866 | 859 | *bounds_ptr = 0; |
| 867 | 860 | |
| 868 | − sym_data = get_sym_ref(&char_pointer_type, lbounds_section, | |
| 869 | − func_bound_offset, lbounds_section->data_offset); | |
| 861 | + sym_data = get_sym_ref(S, &S->tccgen_char_pointer_type, lbounds_section, | |
| 862 | + S->func_bound_offset, lbounds_section->data_offset); | |
| 870 | 863 | |
| 871 | 864 | /* generate bound local allocation */ |
| 872 | 865 | if (offset_modified) { |
| 873 | − saved_ind = ind; | |
| 874 | − ind = func_bound_ind; | |
| 875 | − o(0xe59f0000); /* ldr r0, [pc] */ | |
| 876 | − o(0xea000000); /* b $+4 */ | |
| 877 | − greloc(cur_text_section, sym_data, ind, R_ARM_REL32); | |
| 878 | − o(-12); /* lbounds_section->data_offset */ | |
| 879 | − o(0xe080000f); /* add r0,r0,pc */ | |
| 880 | − gen_bounds_call(TOK___bound_local_new); | |
| 881 | − ind = saved_ind; | |
| 866 | + saved_ind = S->tccgen_ind; | |
| 867 | + S->tccgen_ind = S->func_bound_ind; | |
| 868 | + o(S, 0xe59f0000); /* ldr r0, [pc] */ | |
| 869 | + o(S, 0xea000000); /* b $+4 */ | |
| 870 | + greloc(S, cur_text_section, sym_data, S->tccgen_ind, R_ARM_REL32); | |
| 871 | + o(S, -12); /* lbounds_section->data_offset */ | |
| 872 | + o(S, 0xe080000f); /* add r0,r0,pc */ | |
| 873 | + gen_bounds_call(S, TOK___bound_local_new); | |
| 874 | + S->tccgen_ind = saved_ind; | |
| 882 | 875 | } |
| 883 | 876 | |
| 884 | 877 | /* generate bound check local freeing */ |
| 885 | − o(0xe92d0003); /* push {r0,r1} */ | |
| 886 | − o(0xed2d0b02); /* vpush {d0} */ | |
| 887 | − o(0xe59f0000); /* ldr r0, [pc] */ | |
| 888 | − o(0xea000000); /* b $+4 */ | |
| 889 | − greloc(cur_text_section, sym_data, ind, R_ARM_REL32); | |
| 890 | − o(-12); /* lbounds_section->data_offset */ | |
| 891 | − o(0xe080000f); /* add r0,r0,pc */ | |
| 892 | − gen_bounds_call(TOK___bound_local_delete); | |
| 893 | − o(0xecbd0b02); /* vpop {d0} */ | |
| 894 | − o(0xe8bd0003); /* pop {r0,r1} */ | |
| 878 | + o(S, 0xe92d0003); /* push {r0,r1} */ | |
| 879 | + o(S, 0xed2d0b02); /* vpush {d0} */ | |
| 880 | + o(S, 0xe59f0000); /* ldr r0, [pc] */ | |
| 881 | + o(S, 0xea000000); /* b $+4 */ | |
| 882 | + greloc(S, cur_text_section, sym_data, S->tccgen_ind, R_ARM_REL32); | |
| 883 | + o(S, -12); /* lbounds_section->data_offset */ | |
| 884 | + o(S, 0xe080000f); /* add r0,r0,pc */ | |
| 885 | + gen_bounds_call(S, TOK___bound_local_delete); | |
| 886 | + o(S, 0xecbd0b02); /* vpop {d0} */ | |
| 887 | + o(S, 0xe8bd0003); /* pop {r0,r1} */ | |
| 895 | 888 | } |
| 896 | 889 | #endif |
| 897 | 890 | |
| @@ -1077,7 +1070,7 @@ static void add_param_plan(struct plan* plan, int cls, int start, int end, SValu · 179 unmodified lines | ||
| 1077 | 1070 | Note: this function allocated an array in plan->pplans with tcc_malloc. It |
| 1078 | 1071 | is the responsibility of the caller to free this array once used (ie not |
| 1079 | 1072 | before copy_params). */ |
| 1080 | −static int assign_regs(int nb_args, int float_abi, struct plan *plan, int *todo) | |
| 1073 | +static int assign_regs(TCCState *S, int nb_args, int float_abi, struct plan *plan, int *todo) | |
| 1081 | 1074 | { |
| 1082 | 1075 | int i, size, align; |
| 1083 | 1076 | int ncrn /* next core register number */, nsaa /* next stacked argument address*/; |
| @@ -1088,12 +1081,12 @@ static int assign_regs(int nb_args, int float_abi, struct plan *plan, int *todo) · 4 unmodified lines | ||
| 1088 | 1081 | |
| 1089 | 1082 | for(i = nb_args; i-- ;) { |
| 1090 | 1083 | int j, start_vfpreg = 0; |
| 1091 | − CType type = vtop[-i].type; | |
| 1084 | + CType type = S->tccgen_vtop[-i].type; | |
| 1092 | 1085 | type.t &= ~VT_ARRAY; |
| 1093 | 1086 | size = type_size(&type, &align); |
| 1094 | 1087 | size = (size + 3) & ~3; |
| 1095 | 1088 | align = (align + 3) & ~3; |
| 1096 | − switch(vtop[-i].type.t & VT_BTYPE) { | |
| 1089 | + switch(S->tccgen_vtop[-i].type.t & VT_BTYPE) { | |
| 1097 | 1090 | case VT_STRUCT: |
| 1098 | 1091 | case VT_FLOAT: |
| 1099 | 1092 | case VT_DOUBLE: |
| @@ -1101,15 +1094,15 @@ static int assign_regs(int nb_args, int float_abi, struct plan *plan, int *todo) · 1 unmodified line | ||
| 1101 | 1094 | if (float_abi == ARM_HARD_FLOAT) { |
| 1102 | 1095 | int is_hfa = 0; /* Homogeneous float aggregate */ |
| 1103 | 1096 | |
| 1104 | − if (is_float(vtop[-i].type.t) | |
| 1105 | − || (is_hfa = is_hgen_float_aggr(&vtop[-i].type))) { | |
| 1097 | + if (is_float(S->tccgen_vtop[-i].type.t) | |
| 1098 | + || (is_hfa = is_hgen_float_aggr(&S->tccgen_vtop[-i].type))) { | |
| 1106 | 1099 | int end_vfpreg; |
| 1107 | 1100 | |
| 1108 | 1101 | start_vfpreg = assign_vfpreg(&avregs, align, size); |
| 1109 | 1102 | end_vfpreg = start_vfpreg + ((size - 1) >> 2); |
| 1110 | 1103 | if (start_vfpreg >= 0) { |
| 1111 | 1104 | add_param_plan(plan, is_hfa ? VFP_STRUCT_CLASS : VFP_CLASS, |
| 1112 | − start_vfpreg, end_vfpreg, &vtop[-i]); | |
| 1105 | + start_vfpreg, end_vfpreg, &S->tccgen_vtop[-i]); | |
| 1113 | 1106 | continue; |
| 1114 | 1107 | } else |
| 1115 | 1108 | break; |
| @@ -1122,7 +1115,7 @@ static int assign_regs(int nb_args, int float_abi, struct plan *plan, int *todo) · 6 unmodified lines | ||
| 1122 | 1115 | * CORE_STRUCT_CLASS or the first of STACK_CLASS. */ |
| 1123 | 1116 | for (j = ncrn; j < 4 && j < ncrn + size / 4; j++) |
| 1124 | 1117 | *todo|=(1<<j); |
| 1125 | − add_param_plan(plan, CORE_STRUCT_CLASS, ncrn, j, &vtop[-i]); | |
| 1118 | + add_param_plan(plan, CORE_STRUCT_CLASS, ncrn, j, &S->tccgen_vtop[-i]); | |
| 1126 | 1119 | ncrn += size/4; |
| 1127 | 1120 | if (ncrn > 4) |
| 1128 | 1121 | nsaa = (ncrn - 4) * 4; |
| @@ -1133,20 +1126,20 @@ static int assign_regs(int nb_args, int float_abi, struct plan *plan, int *todo) · 4 unmodified lines | ||
| 1133 | 1126 | continue; |
| 1134 | 1127 | default: |
| 1135 | 1128 | if (ncrn < 4) { |
| 1136 | − int is_long = (vtop[-i].type.t & VT_BTYPE) == VT_LLONG; | |
| 1129 | + int is_long = (S->tccgen_vtop[-i].type.t & VT_BTYPE) == VT_LLONG; | |
| 1137 | 1130 | |
| 1138 | 1131 | if (is_long) { |
| 1139 | 1132 | ncrn = (ncrn + 1) & -2; |
| 1140 | 1133 | if (ncrn == 4) |
| 1141 | 1134 | break; |
| 1142 | 1135 | } |
| 1143 | − add_param_plan(plan, CORE_CLASS, ncrn, ncrn + is_long, &vtop[-i]); | |
| 1136 | + add_param_plan(plan, CORE_CLASS, ncrn, ncrn + is_long, &S->tccgen_vtop[-i]); | |
| 1144 | 1137 | ncrn += 1 + is_long; |
| 1145 | 1138 | continue; |
| 1146 | 1139 | } |
| 1147 | 1140 | } |
| 1148 | 1141 | nsaa = (nsaa + (align - 1)) & ~(align - 1); |
| 1149 | − add_param_plan(plan, STACK_CLASS, nsaa, nsaa + size, &vtop[-i]); | |
| 1142 | + add_param_plan(plan, STACK_CLASS, nsaa, nsaa + size, &S->tccgen_vtop[-i]); | |
| 1150 | 1143 | nsaa += size; /* size already rounded up before */ |
| 1151 | 1144 | } |
| 1152 | 1145 | return nsaa; |
| @@ -1160,7 +1153,7 @@ static int assign_regs(int nb_args, int float_abi, struct plan *plan, int *todo) · 7 unmodified lines | ||
| 1160 | 1153 | todo: a bitmap indicating what core reg will hold a parameter |
| 1161 | 1154 | |
| 1162 | 1155 | Returns the number of SValue added by this function on the value stack */ |
| 1163 | −static int copy_params(int nb_args, struct plan *plan, int todo) | |
| 1156 | +static int copy_params(TCCState* S, int nb_args, struct plan *plan, int todo) | |
| 1164 | 1157 | { |
| 1165 | 1158 | int size, align, r, i, nb_extra_sval = 0; |
| 1166 | 1159 | struct param_plan *pplan; |
| @@ -1189,7 +1182,7 @@ again: · 22 unmodified lines | ||
| 1189 | 1182 | && (i != CORE_CLASS || pplan->sval->r < VT_CONST)) |
| 1190 | 1183 | continue; |
| 1191 | 1184 | |
| 1192 | − vpushv(pplan->sval); | |
| 1185 | + vpushv(S, pplan->sval); | |
| 1193 | 1186 | pplan->sval->r = pplan->sval->r2 = VT_CONST; /* disable entry */ |
| 1194 | 1187 | switch(i) { |
| 1195 | 1188 | case STACK_CLASS: |
| @@ -1204,16 +1197,16 @@ again: · 8 unmodified lines | ||
| 1204 | 1197 | padding = pplan->start - pplan->prev->end; |
| 1205 | 1198 | size += padding; /* Add padding if any */ |
| 1206 | 1199 | /* allocate the necessary size on stack */ |
| 1207 | − gadd_sp(-size); | |
| 1200 | + gadd_sp(S, -size); | |
| 1208 | 1201 | /* generate structure store */ |
| 1209 | − r = get_reg(RC_INT); | |
| 1210 | − o(0xE28D0000|(intr(r)<<12)|padding); /* add r, sp, padding */ | |
| 1211 | − vset(&vtop->type, r | VT_LVAL, 0); | |
| 1212 | − vswap(); | |
| 1202 | + r = get_reg(S, RC_INT); | |
| 1203 | + o(S, 0xE28D0000|(intr(S, r)<<12)|padding); /* add r, sp, padding */ | |
| 1204 | + vset(S, &S->tccgen_vtop->type, r | VT_LVAL, 0); | |
| 1205 | + vswap(S); | |
| 1213 | 1206 | /* XXX: optimize. Save all register because memcpy can use them */ |
| 1214 | − o(0xED2D0A00|(0&1)<<22|(0>>1)<<12|16); /* vpush {s0-s15} */ | |
| 1215 | − vstore(); /* memcpy to current sp + potential padding */ | |
| 1216 | − o(0xECBD0A00|(0&1)<<22|(0>>1)<<12|16); /* vpop {s0-s15} */ | |
| 1207 | + o(S, 0xED2D0A00|(0&1)<<22|(0>>1)<<12|16); /* vpush {s0-s15} */ | |
| 1208 | + vstore(S); /* memcpy to current sp + potential padding */ | |
| 1209 | + o(S, 0xECBD0A00|(0&1)<<22|(0>>1)<<12|16); /* vpop {s0-s15} */ | |
| 1217 | 1210 | |
| 1218 | 1211 | /* Homogeneous float aggregate are loaded to VFP registers |
| 1219 | 1212 | immediately since there is no way of loading data in multiple |
| @@ -1222,23 +1215,23 @@ again: · 2 unmodified lines | ||
| 1222 | 1215 | if (i == VFP_STRUCT_CLASS) { |
| 1223 | 1216 | int first = pplan->start, nb = pplan->end - first + 1; |
| 1224 | 1217 | /* vpop.32 {pplan->start, ..., pplan->end} */ |
| 1225 | − o(0xECBD0A00|(first&1)<<22|(first>>1)<<12|nb); | |
| 1218 | + o(S, 0xECBD0A00|(first&1)<<22|(first>>1)<<12|nb); | |
| 1226 | 1219 | /* No need to write the register used to a SValue since VFP regs |
| 1227 | 1220 | cannot be used for gcall_or_jmp */ |
| 1228 | 1221 | } |
| 1229 | 1222 | } else { |
| 1230 | 1223 | if (is_float(pplan->sval->type.t)) { |
| 1231 | 1224 | #ifdef TCC_ARM_VFP |
| 1232 | − r = vfpr(gv(RC_FLOAT)) << 12; | |
| 1225 | + r = vfpr(S, gv(S, RC_FLOAT)) << 12; | |
| 1233 | 1226 | if ((pplan->sval->type.t & VT_BTYPE) == VT_FLOAT) |
| 1234 | 1227 | size = 4; |
| 1235 | 1228 | else { |
| 1236 | 1229 | size = 8; |
| 1237 | 1230 | r |= 0x101; /* vpush.32 -> vpush.64 */ |
| 1238 | 1231 | } |
| 1239 | − o(0xED2D0A01 + r); /* vpush */ | |
| 1232 | + o(S, 0xED2D0A01 + r); /* vpush */ | |
| 1240 | 1233 | #else |
| 1241 | − r = fpr(gv(RC_FLOAT)) << 12; | |
| 1234 | + r = fpr(S, gv(S, RC_FLOAT)) << 12; | |
| 1242 | 1235 | if ((pplan->sval->type.t & VT_BTYPE) == VT_FLOAT) |
| 1243 | 1236 | size = 4; |
| 1244 | 1237 | else if ((pplan->sval->type.t & VT_BTYPE) == VT_DOUBLE) |
| @@ -1251,49 +1244,49 @@ again: · 6 unmodified lines | ||
| 1251 | 1244 | else if(size == 8) |
| 1252 | 1245 | r|=0x8000; |
| 1253 | 1246 | |
| 1254 | − o(0xED2D0100|r|(size>>2)); /* some kind of vpush for FPA */ | |
| 1247 | + o(S, 0xED2D0100|r|(size>>2)); /* some kind of vpush for FPA */ | |
| 1255 | 1248 | #endif |
| 1256 | 1249 | } else { |
| 1257 | 1250 | /* simple type (currently always same size) */ |
| 1258 | 1251 | /* XXX: implicit cast ? */ |
| 1259 | 1252 | size=4; |
| 1260 | 1253 | if ((pplan->sval->type.t & VT_BTYPE) == VT_LLONG) { |
| 1261 | − lexpand(); | |
| 1254 | + lexpand(S); | |
| 1262 | 1255 | size = 8; |
| 1263 | − r = gv(RC_INT); | |
| 1264 | − o(0xE52D0004|(intr(r)<<12)); /* push r */ | |
| 1265 | − vtop--; | |
| 1256 | + r = gv(S, RC_INT); | |
| 1257 | + o(S, 0xE52D0004|(intr(S, r)<<12)); /* push r */ | |
| 1258 | + S->tccgen_vtop--; | |
| 1266 | 1259 | } |
| 1267 | − r = gv(RC_INT); | |
| 1268 | − o(0xE52D0004|(intr(r)<<12)); /* push r */ | |
| 1260 | + r = gv(S, RC_INT); | |
| 1261 | + o(S, 0xE52D0004|(intr(S, r)<<12)); /* push r */ | |
| 1269 | 1262 | } |
| 1270 | 1263 | if (i == STACK_CLASS && pplan->prev) |
| 1271 | − gadd_sp(pplan->prev->end - pplan->start); /* Add padding if any */ | |
| 1264 | + gadd_sp(S, pplan->prev->end - pplan->start); /* Add padding if any */ | |
| 1272 | 1265 | } |
| 1273 | 1266 | break; |
| 1274 | 1267 | |
| 1275 | 1268 | case VFP_CLASS: |
| 1276 | − gv(regmask(TREG_F0 + (pplan->start >> 1))); | |
| 1269 | + gv(S, regmask(S, TREG_F0 + (pplan->start >> 1))); | |
| 1277 | 1270 | if (pplan->start & 1) { /* Must be in upper part of double register */ |
| 1278 | − o(0xEEF00A40|((pplan->start>>1)<<12)|(pplan->start>>1)); /* vmov.f32 s(n+1), sn */ | |
| 1279 | − vtop->r = VT_CONST; /* avoid being saved on stack by gv for next float */ | |
| 1271 | + o(S, 0xEEF00A40|((pplan->start>>1)<<12)|(pplan->start>>1)); /* vmov.f32 s(n+1), sn */ | |
| 1272 | + S->tccgen_vtop->r = VT_CONST; /* avoid being saved on stack by gv for next float */ | |
| 1280 | 1273 | } |
| 1281 | 1274 | break; |
| 1282 | 1275 | |
| 1283 | 1276 | case CORE_CLASS: |
| 1284 | 1277 | if ((pplan->sval->type.t & VT_BTYPE) == VT_LLONG) { |
| 1285 | − lexpand(); | |
| 1286 | − gv(regmask(pplan->end)); | |
| 1287 | − pplan->sval->r2 = vtop->r; | |
| 1288 | − vtop--; | |
| 1278 | + lexpand(S); | |
| 1279 | + gv(S, regmask(S, pplan->end)); | |
| 1280 | + pplan->sval->r2 = S->tccgen_vtop->r; | |
| 1281 | + S->tccgen_vtop--; | |
| 1289 | 1282 | } |
| 1290 | − gv(regmask(pplan->start)); | |
| 1283 | + gv(S, regmask(S, pplan->start)); | |
| 1291 | 1284 | /* Mark register as used so that gcall_or_jmp use another one |
| 1292 | 1285 | (regs >=4 are free as never used to pass parameters) */ |
| 1293 | − pplan->sval->r = vtop->r; | |
| 1286 | + pplan->sval->r = S->tccgen_vtop->r; | |
| 1294 | 1287 | break; |
| 1295 | 1288 | } |
| 1296 | − vtop--; | |
| 1289 | + S->tccgen_vtop--; | |
| 1297 | 1290 | } |
| 1298 | 1291 | } |
| 1299 | 1292 | |
| @@ -1304,10 +1297,10 @@ again: · 4 unmodified lines | ||
| 1304 | 1297 | |
| 1305 | 1298 | /* Manually free remaining registers since next parameters are loaded |
| 1306 | 1299 | * manually, without the help of gv(int). */ |
| 1307 | − save_regs(nb_args); | |
| 1300 | + save_regs(S, nb_args); | |
| 1308 | 1301 | |
| 1309 | 1302 | if(todo) { |
| 1310 | − o(0xE8BD0000|todo); /* pop {todo} */ | |
| 1303 | + o(S, 0xE8BD0000|todo); /* pop {todo} */ | |
| 1311 | 1304 | for(pplan = plan->clsplans[CORE_STRUCT_CLASS]; pplan; pplan = pplan->prev) { |
| 1312 | 1305 | int r; |
| 1313 | 1306 | pplan->sval->r = pplan->start; |
| @@ -1318,8 +1311,8 @@ again: · 4 unmodified lines | ||
| 1318 | 1311 | for (r = pplan->start + 1; r <= pplan->end; r++) { |
| 1319 | 1312 | if (todo & (1 << r)) { |
| 1320 | 1313 | nb_extra_sval++; |
| 1321 | − vpushi(0); | |
| 1322 | − vtop->r = r; | |
| 1314 | + vpushi(S, 0); | |
| 1315 | + S->tccgen_vtop->r = r; | |
| 1323 | 1316 | } |
| 1324 | 1317 | } |
| 1325 | 1318 | } |
| @@ -1330,7 +1323,7 @@ again: · 4 unmodified lines | ||
| 1330 | 1323 | /* Generate function call. The function address is pushed first, then |
| 1331 | 1324 | all the parameters in call order. This functions pops all the |
| 1332 | 1325 | parameters and the function address. */ |
| 1333 | −void gfunc_call(int nb_args) | |
| 1326 | +void gfunc_call(TCCState* S, int nb_args) | |
| 1334 | 1327 | { |
| 1335 | 1328 | int r, args_size; |
| 1336 | 1329 | int def_float_abi = float_abi; |
| @@ -1341,62 +1334,62 @@ void gfunc_call(int nb_args) · 4 unmodified lines | ||
| 1341 | 1334 | #endif |
| 1342 | 1335 | |
| 1343 | 1336 | #ifdef CONFIG_TCC_BCHECK |
| 1344 | − if (tcc_state->do_bounds_check) | |
| 1345 | − gbound_args(nb_args); | |
| 1337 | + if (S->do_bounds_check) | |
| 1338 | + gbound_args(S, nb_args); | |
| 1346 | 1339 | #endif |
| 1347 | 1340 | |
| 1348 | 1341 | #ifdef TCC_ARM_EABI |
| 1349 | 1342 | if (float_abi == ARM_HARD_FLOAT) { |
| 1350 | − variadic = (vtop[-nb_args].type.ref->f.func_type == FUNC_ELLIPSIS); | |
| 1351 | − if (variadic || floats_in_core_regs(&vtop[-nb_args])) | |
| 1343 | + variadic = (S->tccgen_vtop[-nb_args].type.ref->f.func_type == FUNC_ELLIPSIS); | |
| 1344 | + if (variadic || floats_in_core_regs(&S->tccgen_vtop[-nb_args])) | |
| 1352 | 1345 | float_abi = ARM_SOFTFP_FLOAT; |
| 1353 | 1346 | } |
| 1354 | 1347 | #endif |
| 1355 | 1348 | /* cannot let cpu flags if other instruction are generated. Also avoid leaving |
| 1356 | 1349 | VT_JMP anywhere except on the top of the stack because it would complicate |
| 1357 | 1350 | the code generator. */ |
| 1358 | − r = vtop->r & VT_VALMASK; | |
| 1351 | + r = S->tccgen_vtop->r & VT_VALMASK; | |
| 1359 | 1352 | if (r == VT_CMP || (r & ~1) == VT_JMP) |
| 1360 | − gv(RC_INT); | |
| 1353 | + gv(S, RC_INT); | |
| 1361 | 1354 | |
| 1362 | 1355 | memset(&plan, 0, sizeof plan); |
| 1363 | 1356 | if (nb_args) |
| 1364 | − plan.pplans = tcc_malloc(nb_args * sizeof(*plan.pplans)); | |
| 1357 | + plan.pplans = tcc_malloc(S, nb_args * sizeof(*plan.pplans)); | |
| 1365 | 1358 | |
| 1366 | − args_size = assign_regs(nb_args, float_abi, &plan, &todo); | |
| 1359 | + args_size = assign_regs(S, nb_args, float_abi, &plan, &todo); | |
| 1367 | 1360 | |
| 1368 | 1361 | #ifdef TCC_ARM_EABI |
| 1369 | 1362 | if (args_size & 7) { /* Stack must be 8 byte aligned at fct call for EABI */ |
| 1370 | 1363 | args_size = (args_size + 7) & ~7; |
| 1371 | − o(0xE24DD004); /* sub sp, sp, #4 */ | |
| 1364 | + o(S, 0xE24DD004); /* sub sp, sp, #4 */ | |
| 1372 | 1365 | } |
| 1373 | 1366 | #endif |
| 1374 | 1367 | |
| 1375 | − nb_args += copy_params(nb_args, &plan, todo); | |
| 1376 | − tcc_free(plan.pplans); | |
| 1368 | + nb_args += copy_params(S, nb_args, &plan, todo); | |
| 1369 | + tcc_free(S, plan.pplans); | |
| 1377 | 1370 | |
| 1378 | 1371 | /* Move fct SValue on top as required by gcall_or_jmp */ |
| 1379 | − vrotb(nb_args + 1); | |
| 1380 | − gcall_or_jmp(0); | |
| 1372 | + vrotb(S, nb_args + 1); | |
| 1373 | + gcall_or_jmp(S, 0); | |
| 1381 | 1374 | if (args_size) |
| 1382 | − gadd_sp(args_size); /* pop all parameters passed on the stack */ | |
| 1375 | + gadd_sp(S, args_size); /* pop all parameters passed on the stack */ | |
| 1383 | 1376 | #if defined(TCC_ARM_EABI) && defined(TCC_ARM_VFP) |
| 1384 | − if(float_abi == ARM_SOFTFP_FLOAT && is_float(vtop->type.ref->type.t)) { | |
| 1385 | − if((vtop->type.ref->type.t & VT_BTYPE) == VT_FLOAT) { | |
| 1386 | − o(0xEE000A10); /*vmov s0, r0 */ | |
| 1377 | + if(float_abi == ARM_SOFTFP_FLOAT && is_float(S->tccgen_vtop->type.ref->type.t)) { | |
| 1378 | + if((S->tccgen_vtop->type.ref->type.t & VT_BTYPE) == VT_FLOAT) { | |
| 1379 | + o(S, 0xEE000A10); /*vmov s0, r0 */ | |
| 1387 | 1380 | } else { |
| 1388 | − o(0xEE000B10); /* vmov.32 d0[0], r0 */ | |
| 1389 | − o(0xEE201B10); /* vmov.32 d0[1], r1 */ | |
| 1381 | + o(S, 0xEE000B10); /* vmov.32 d0[0], r0 */ | |
| 1382 | + o(S, 0xEE201B10); /* vmov.32 d0[1], r1 */ | |
| 1390 | 1383 | } |
| 1391 | 1384 | } |
| 1392 | 1385 | #endif |
| 1393 | − vtop -= nb_args + 1; /* Pop all params and fct address from value stack */ | |
| 1386 | + S->tccgen_vtop -= nb_args + 1; /* Pop all params and fct address from value stack */ | |
| 1394 | 1387 | leaffunc = 0; /* we are calling a function, so we aren't in a leaf function */ |
| 1395 | 1388 | float_abi = def_float_abi; |
| 1396 | 1389 | } |
| 1397 | 1390 | |
| 1398 | 1391 | /* generate function prolog of type 't' */ |
| 1399 | −void gfunc_prolog(Sym *func_sym) | |
| 1392 | +void gfunc_prolog(TCCState* S, Sym *func_sym) | |
| 1400 | 1393 | { |
| 1401 | 1394 | CType *func_type = &func_sym->type; |
| 1402 | 1395 | Sym *sym,*sym2; |
| @@ -1411,17 +1404,17 @@ void gfunc_prolog(Sym *func_sym) · 8 unmodified lines | ||
| 1411 | 1404 | sym = func_type->ref; |
| 1412 | 1405 | |
| 1413 | 1406 | n = nf = 0; |
| 1414 | − if ((func_vt.t & VT_BTYPE) == VT_STRUCT && | |
| 1415 | − !gfunc_sret(&func_vt, func_var, &ret_type, &align, &rs)) | |
| 1407 | + if ((S->tccgen_func_vt.t & VT_BTYPE) == VT_STRUCT && | |
| 1408 | + !gfunc_sret(&S->tccgen_func_vt, S->tccgen_func_var, &ret_type, &align, &rs)) | |
| 1416 | 1409 | { |
| 1417 | 1410 | n++; |
| 1418 | 1411 | struct_ret = 1; |
| 1419 | − func_vc = 12; /* Offset from fp of the place to store the result */ | |
| 1412 | + S->tccgen_func_vc = 12; /* Offset from fp of the place to store the result */ | |
| 1420 | 1413 | } |
| 1421 | 1414 | for(sym2 = sym->next; sym2 && (n < 4 || nf < 16); sym2 = sym2->next) { |
| 1422 | 1415 | size = type_size(&sym2->type, &align); |
| 1423 | 1416 | #ifdef TCC_ARM_EABI |
| 1424 | − if (float_abi == ARM_HARD_FLOAT && !func_var && | |
| 1417 | + if (float_abi == ARM_HARD_FLOAT && !S->tccgen_func_var && | |
| 1425 | 1418 | (is_float(sym2->type.t) || is_hgen_float_aggr(&sym2->type))) { |
| 1426 | 1419 | int tmpnf = assign_vfpreg(&avregs, align, size); |
| 1427 | 1420 | tmpnf += (size + 3) / 4; |
| @@ -1431,8 +1424,8 @@ void gfunc_prolog(Sym *func_sym) · 3 unmodified lines | ||
| 1431 | 1424 | if (n < 4) |
| 1432 | 1425 | n += (size + 3) / 4; |
| 1433 | 1426 | } |
| 1434 | − o(0xE1A0C00D); /* mov ip,sp */ | |
| 1435 | − if (func_var) | |
| 1427 | + o(S, 0xE1A0C00D); /* mov ip,sp */ | |
| 1428 | + if (S->tccgen_func_var) | |
| 1436 | 1429 | n=4; |
| 1437 | 1430 | if (n) { |
| 1438 | 1431 | if(n>4) |
| @@ -1440,22 +1433,22 @@ void gfunc_prolog(Sym *func_sym) · 1 unmodified line | ||
| 1440 | 1433 | #ifdef TCC_ARM_EABI |
| 1441 | 1434 | n=(n+1)&-2; |
| 1442 | 1435 | #endif |
| 1443 | − o(0xE92D0000|((1<<n)-1)); /* save r0-r4 on stack if needed */ | |
| 1436 | + o(S, 0xE92D0000|((1<<n)-1)); /* save r0-r4 on stack if needed */ | |
| 1444 | 1437 | } |
| 1445 | 1438 | if (nf) { |
| 1446 | 1439 | if (nf>16) |
| 1447 | 1440 | nf=16; |
| 1448 | 1441 | nf=(nf+1)&-2; /* nf => HARDFLOAT => EABI */ |
| 1449 | − o(0xED2D0A00|nf); /* save s0-s15 on stack if needed */ | |
| 1442 | + o(S, 0xED2D0A00|nf); /* save s0-s15 on stack if needed */ | |
| 1450 | 1443 | } |
| 1451 | − o(0xE92D5800); /* save fp, ip, lr */ | |
| 1452 | − o(0xE1A0B00D); /* mov fp, sp */ | |
| 1453 | − func_sub_sp_offset = ind; | |
| 1454 | − o(0xE1A00000); /* nop, leave space for stack adjustment in epilog */ | |
| 1444 | + o(S, 0xE92D5800); /* save fp, ip, lr */ | |
| 1445 | + o(S, 0xE1A0B00D); /* mov fp, sp */ | |
| 1446 | + func_sub_sp_offset = S->tccgen_ind; | |
| 1447 | + o(S, 0xE1A00000); /* nop, leave space for stack adjustment in epilog */ | |
| 1455 | 1448 | |
| 1456 | 1449 | #ifdef TCC_ARM_EABI |
| 1457 | 1450 | if (float_abi == ARM_HARD_FLOAT) { |
| 1458 | − func_vc += nf * 4; | |
| 1451 | + S->tccgen_func_vc += nf * 4; | |
| 1459 | 1452 | memset(&avregs, 0, sizeof avregs); |
| 1460 | 1453 | } |
| 1461 | 1454 | #endif |
| @@ -1467,7 +1460,7 @@ void gfunc_prolog(Sym *func_sym) · 5 unmodified lines | ||
| 1467 | 1460 | size = (size + 3) >> 2; |
| 1468 | 1461 | align = (align + 3) & ~3; |
| 1469 | 1462 | #ifdef TCC_ARM_EABI |
| 1470 | − if (float_abi == ARM_HARD_FLOAT && !func_var && (is_float(sym->type.t) | |
| 1463 | + if (float_abi == ARM_HARD_FLOAT && !S->tccgen_func_var && (is_float(sym->type.t) | |
| 1471 | 1464 | || is_hgen_float_aggr(&sym->type))) { |
| 1472 | 1465 | int fpn = assign_vfpreg(&avregs, align, size << 2); |
| 1473 | 1466 | if (fpn >= 0) |
| @@ -1492,42 +1485,42 @@ from_stack: · 18 unmodified lines | ||
| 1492 | 1485 | addr = (n + nf + sn) * 4; |
| 1493 | 1486 | sn += size; |
| 1494 | 1487 | } |
| 1495 | − sym_push(sym->v & ~SYM_FIELD, type, VT_LOCAL | VT_LVAL, | |
| 1488 | + sym_push(S, sym->v & ~SYM_FIELD, type, VT_LOCAL | VT_LVAL, | |
| 1496 | 1489 | addr + 12); |
| 1497 | 1490 | } |
| 1498 | 1491 | last_itod_magic=0; |
| 1499 | 1492 | leaffunc = 1; |
| 1500 | − loc = 0; | |
| 1493 | + S->tccgen_loc = 0; | |
| 1501 | 1494 | #ifdef CONFIG_TCC_BCHECK |
| 1502 | − if (tcc_state->do_bounds_check) | |
| 1503 | − gen_bounds_prolog(); | |
| 1495 | + if (S->do_bounds_check) | |
| 1496 | + gen_bounds_prolog(S); | |
| 1504 | 1497 | #endif |
| 1505 | 1498 | } |
| 1506 | 1499 | |
| 1507 | 1500 | /* generate function epilog */ |
| 1508 | −void gfunc_epilog(void) | |
| 1501 | +void gfunc_epilog(TCCState* S) | |
| 1509 | 1502 | { |
| 1510 | 1503 | uint32_t x; |
| 1511 | 1504 | int diff; |
| 1512 | 1505 | |
| 1513 | 1506 | #ifdef CONFIG_TCC_BCHECK |
| 1514 | − if (tcc_state->do_bounds_check) | |
| 1515 | − gen_bounds_epilog(); | |
| 1507 | + if (S->do_bounds_check) | |
| 1508 | + gen_bounds_epilog(S); | |
| 1516 | 1509 | #endif |
| 1517 | 1510 | /* Copy float return value to core register if base standard is used and |
| 1518 | 1511 | float computation is made with VFP */ |
| 1519 | 1512 | #if defined(TCC_ARM_EABI) && defined(TCC_ARM_VFP) |
| 1520 | − if ((float_abi == ARM_SOFTFP_FLOAT || func_var) && is_float(func_vt.t)) { | |
| 1521 | − if((func_vt.t & VT_BTYPE) == VT_FLOAT) | |
| 1522 | − o(0xEE100A10); /* fmrs r0, s0 */ | |
| 1513 | + if ((float_abi == ARM_SOFTFP_FLOAT || S->tccgen_func_var) && is_float(S->tccgen_func_vt.t)) { | |
| 1514 | + if((S->tccgen_func_vt.t & VT_BTYPE) == VT_FLOAT) | |
| 1515 | + o(S, 0xEE100A10); /* fmrs r0, s0 */ | |
| 1523 | 1516 | else { |
| 1524 | − o(0xEE100B10); /* fmrdl r0, d0 */ | |
| 1525 | − o(0xEE301B10); /* fmrdh r1, d0 */ | |
| 1517 | + o(S, 0xEE100B10); /* fmrdl r0, d0 */ | |
| 1518 | + o(S, 0xEE301B10); /* fmrdh r1, d0 */ | |
| 1526 | 1519 | } |
| 1527 | 1520 | } |
| 1528 | 1521 | #endif |
| 1529 | − o(0xE89BA800); /* restore fp, sp, pc */ | |
| 1530 | − diff = (-loc + 3) & -4; | |
| 1522 | + o(S, 0xE89BA800); /* restore fp, sp, pc */ | |
| 1523 | + diff = (-S->tccgen_loc + 3) & -4; | |
| 1531 | 1524 | #ifdef TCC_ARM_EABI |
| 1532 | 1525 | if(!leaffunc) |
| 1533 | 1526 | diff = ((diff + 11) & -8) - 4; |
| @@ -1538,74 +1531,74 @@ void gfunc_epilog(void) · 4 unmodified lines | ||
| 1538 | 1531 | *(uint32_t *)(cur_text_section->data + func_sub_sp_offset) = x; |
| 1539 | 1532 | else { |
| 1540 | 1533 | int addr; |
| 1541 | − addr=ind; | |
| 1542 | − o(0xE59FC004); /* ldr ip,[pc+4] */ | |
| 1543 | − o(0xE04BD00C); /* sub sp,fp,ip */ | |
| 1544 | − o(0xE1A0F00E); /* mov pc,lr */ | |
| 1545 | − o(diff); | |
| 1546 | − *(uint32_t *)(cur_text_section->data + func_sub_sp_offset) = 0xE1000000|encbranch(func_sub_sp_offset,addr,1); | |
| 1534 | + addr=S->tccgen_ind; | |
| 1535 | + o(S, 0xE59FC004); /* ldr ip,[pc+4] */ | |
| 1536 | + o(S, 0xE04BD00C); /* sub sp,fp,ip */ | |
| 1537 | + o(S, 0xE1A0F00E); /* mov pc,lr */ | |
| 1538 | + o(S, diff); | |
| 1539 | + *(uint32_t *)(cur_text_section->data + func_sub_sp_offset) = 0xE1000000|encbranch(S, func_sub_sp_offset,addr,1); | |
| 1547 | 1540 | } |
| 1548 | 1541 | } |
| 1549 | 1542 | } |
| 1550 | 1543 | |
| 1551 | −ST_FUNC void gen_fill_nops(int bytes) | |
| 1544 | +ST_FUNC void gen_fill_nops(TCCState* S, int bytes) | |
| 1552 | 1545 | { |
| 1553 | 1546 | if ((bytes & 3)) |
| 1554 | − tcc_error("alignment of code section not multiple of 4"); | |
| 1547 | + tcc_error(S, "alignment of code section not multiple of 4"); | |
| 1555 | 1548 | while (bytes > 0) { |
| 1556 | − o(0xE1A00000); | |
| 1549 | + o(S, 0xE1A00000); | |
| 1557 | 1550 | bytes -= 4; |
| 1558 | 1551 | } |
| 1559 | 1552 | } |
| 1560 | 1553 | |
| 1561 | 1554 | /* generate a jump to a label */ |
| 1562 | −ST_FUNC int gjmp(int t) | |
| 1555 | +ST_FUNC int gjmp(TCCState* S, int t) | |
| 1563 | 1556 | { |
| 1564 | 1557 | int r; |
| 1565 | − if (nocode_wanted) | |
| 1558 | + if (S->tccgen_nocode_wanted) | |
| 1566 | 1559 | return t; |
| 1567 | − r=ind; | |
| 1568 | − o(0xE0000000|encbranch(r,t,1)); | |
| 1560 | + r=S->tccgen_ind; | |
| 1561 | + o(S, 0xE0000000|encbranch(S, r,t,1)); | |
| 1569 | 1562 | return r; |
| 1570 | 1563 | } |
| 1571 | 1564 | |
| 1572 | 1565 | /* generate a jump to a fixed address */ |
| 1573 | −ST_FUNC void gjmp_addr(int a) | |
| 1566 | +ST_FUNC void gjmp_addr(TCCState* S, int a) | |
| 1574 | 1567 | { |
| 1575 | − gjmp(a); | |
| 1568 | + gjmp(S, a); | |
| 1576 | 1569 | } |
| 1577 | 1570 | |
| 1578 | −ST_FUNC int gjmp_cond(int op, int t) | |
| 1571 | +ST_FUNC int gjmp_cond(TCCState* S, int op, int t) | |
| 1579 | 1572 | { |
| 1580 | 1573 | int r; |
| 1581 | − if (nocode_wanted) | |
| 1574 | + if (S->tccgen_nocode_wanted) | |
| 1582 | 1575 | return t; |
| 1583 | − r=ind; | |
| 1584 | − op=mapcc(op); | |
| 1585 | − op|=encbranch(r,t,1); | |
| 1586 | − o(op); | |
| 1576 | + r=S->tccgen_ind; | |
| 1577 | + op=mapcc(S, op); | |
| 1578 | + op|=encbranch(S, r,t,1); | |
| 1579 | + o(S, op); | |
| 1587 | 1580 | return r; |
| 1588 | 1581 | } |
| 1589 | 1582 | |
| 1590 | −ST_FUNC int gjmp_append(int n, int t) | |
| 1583 | +ST_FUNC int gjmp_append(TCCState* S, int n, int t) | |
| 1591 | 1584 | { |
| 1592 | 1585 | uint32_t *x; |
| 1593 | 1586 | int p,lp; |
| 1594 | 1587 | if(n) { |
| 1595 | 1588 | p = n; |
| 1596 | 1589 | do { |
| 1597 | − p = decbranch(lp=p); | |
| 1590 | + p = decbranch(S, lp=p); | |
| 1598 | 1591 | } while(p); |
| 1599 | 1592 | x = (uint32_t *)(cur_text_section->data + lp); |
| 1600 | 1593 | *x &= 0xff000000; |
| 1601 | − *x |= encbranch(lp,t,1); | |
| 1594 | + *x |= encbranch(S, lp,t,1); | |
| 1602 | 1595 | t = n; |
| 1603 | 1596 | } |
| 1604 | 1597 | return t; |
| 1605 | 1598 | } |
| 1606 | 1599 | |
| 1607 | 1600 | /* generate an integer binary operation */ |
| 1608 | −void gen_opi(int op) | |
| 1601 | +void gen_opi(TCCState* S, int op) | |
| 1609 | 1602 | { |
| 1610 | 1603 | int c, func = 0; |
| 1611 | 1604 | uint32_t opc = 0, r, fr; |
| @@ -1650,11 +1643,11 @@ void gen_opi(int op) · 38 unmodified lines | ||
| 1650 | 1643 | c=1; |
| 1651 | 1644 | break; |
| 1652 | 1645 | case '*': |
| 1653 | − gv2(RC_INT, RC_INT); | |
| 1654 | − r = vtop[-1].r; | |
| 1655 | − fr = vtop[0].r; | |
| 1656 | − vtop--; | |
| 1657 | − o(0xE0000090|(intr(r)<<16)|(intr(r)<<8)|intr(fr)); | |
| 1646 | + gv2(S, RC_INT, RC_INT); | |
| 1647 | + r = S->tccgen_vtop[-1].r; | |
| 1648 | + fr = S->tccgen_vtop[0].r; | |
| 1649 | + S->tccgen_vtop--; | |
| 1650 | + o(S, 0xE0000090|(intr(S, r)<<16)|(intr(S, r)<<8)|intr(S, fr)); | |
| 1658 | 1651 | return; |
| 1659 | 1652 | case TOK_SHL: |
| 1660 | 1653 | opc = 0; |
| @@ -1696,12 +1689,12 @@ void gen_opi(int op) · 35 unmodified lines | ||
| 1696 | 1689 | c=3; |
| 1697 | 1690 | break; |
| 1698 | 1691 | case TOK_UMULL: |
| 1699 | − gv2(RC_INT, RC_INT); | |
| 1700 | − r=intr(vtop[-1].r2=get_reg(RC_INT)); | |
| 1701 | − c=vtop[-1].r; | |
| 1702 | − vtop[-1].r=get_reg_ex(RC_INT,regmask(c)); | |
| 1703 | − vtop--; | |
| 1704 | − o(0xE0800090|(r<<16)|(intr(vtop->r)<<12)|(intr(c)<<8)|intr(vtop[1].r)); | |
| 1692 | + gv2(S, RC_INT, RC_INT); | |
| 1693 | + r=intr(S, S->tccgen_vtop[-1].r2=get_reg(S, RC_INT)); | |
| 1694 | + c=S->tccgen_vtop[-1].r; | |
| 1695 | + S->tccgen_vtop[-1].r=get_reg_ex(S, RC_INT,regmask(S, c)); | |
| 1696 | + S->tccgen_vtop--; | |
| 1697 | + o(S, 0xE0800090|(r<<16)|(intr(S, S->tccgen_vtop->r)<<12)|(intr(S, c)<<8)|intr(S, S->tccgen_vtop[1].r)); | |
| 1705 | 1698 | return; |
| 1706 | 1699 | default: |
| 1707 | 1700 | opc = 0x15; |
| @@ -1710,128 +1703,128 @@ void gen_opi(int op) · 2 unmodified lines | ||
| 1710 | 1703 | } |
| 1711 | 1704 | switch(c) { |
| 1712 | 1705 | case 1: |
| 1713 | − if((vtop[-1].r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1706 | + if((S->tccgen_vtop[-1].r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1714 | 1707 | if(opc == 4 || opc == 5 || opc == 0xc) { |
| 1715 | − vswap(); | |
| 1708 | + vswap(S); | |
| 1716 | 1709 | opc|=2; // sub -> rsb |
| 1717 | 1710 | } |
| 1718 | 1711 | } |
| 1719 | − if ((vtop->r & VT_VALMASK) == VT_CMP || | |
| 1720 | − (vtop->r & (VT_VALMASK & ~1)) == VT_JMP) | |
| 1721 | − gv(RC_INT); | |
| 1722 | − vswap(); | |
| 1723 | − c=intr(gv(RC_INT)); | |
| 1724 | − vswap(); | |
| 1712 | + if ((S->tccgen_vtop->r & VT_VALMASK) == VT_CMP || | |
| 1713 | + (S->tccgen_vtop->r & (VT_VALMASK & ~1)) == VT_JMP) | |
| 1714 | + gv(S, RC_INT); | |
| 1715 | + vswap(S); | |
| 1716 | + c=intr(S, gv(S, RC_INT)); | |
| 1717 | + vswap(S); | |
| 1725 | 1718 | opc=0xE0000000|(opc<<20); |
| 1726 | − if((vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1719 | + if((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1727 | 1720 | uint32_t x; |
| 1728 | − x=stuff_const(opc|0x2000000|(c<<16),vtop->c.i); | |
| 1721 | + x=stuff_const(opc|0x2000000|(c<<16),S->tccgen_vtop->c.i); | |
| 1729 | 1722 | if(x) { |
| 1730 | 1723 | if ((x & 0xfff00000) == 0xe3500000) // cmp rx,#c |
| 1731 | − o(x); | |
| 1724 | + o(S, x); | |
| 1732 | 1725 | else { |
| 1733 | − r=intr(vtop[-1].r=get_reg_ex(RC_INT,regmask(vtop[-1].r))); | |
| 1734 | − o(x|(r<<12)); | |
| 1726 | + r=intr(S, S->tccgen_vtop[-1].r=get_reg_ex(S, RC_INT,regmask(S, S->tccgen_vtop[-1].r))); | |
| 1727 | + o(S, x|(r<<12)); | |
| 1735 | 1728 | } |
| 1736 | 1729 | goto done; |
| 1737 | 1730 | } |
| 1738 | 1731 | } |
| 1739 | − fr=intr(gv(RC_INT)); | |
| 1732 | + fr=intr(S, gv(S, RC_INT)); | |
| 1740 | 1733 | #ifdef CONFIG_TCC_BCHECK |
| 1741 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1742 | − vswap(); | |
| 1743 | − c=intr(gv(RC_INT)); | |
| 1744 | − vswap(); | |
| 1734 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1735 | + vswap(S); | |
| 1736 | + c=intr(S, gv(S, RC_INT)); | |
| 1737 | + vswap(S); | |
| 1745 | 1738 | } |
| 1746 | 1739 | #endif |
| 1747 | 1740 | if ((opc & 0xfff00000) == 0xe1500000) // cmp rx,ry |
| 1748 | − o(opc|(c<<16)|fr); | |
| 1741 | + o(S, opc|(c<<16)|fr); | |
| 1749 | 1742 | else { |
| 1750 | − r=intr(vtop[-1].r=get_reg_ex(RC_INT,two2mask(vtop->r,vtop[-1].r))); | |
| 1751 | − o(opc|(c<<16)|(r<<12)|fr); | |
| 1743 | + r=intr(S, S->tccgen_vtop[-1].r=get_reg_ex(S, RC_INT,two2mask(S, S->tccgen_vtop->r,S->tccgen_vtop[-1].r))); | |
| 1744 | + o(S, opc|(c<<16)|(r<<12)|fr); | |
| 1752 | 1745 | } |
| 1753 | 1746 | done: |
| 1754 | − vtop--; | |
| 1747 | + S->tccgen_vtop--; | |
| 1755 | 1748 | if (op >= TOK_ULT && op <= TOK_GT) |
| 1756 | − vset_VT_CMP(op); | |
| 1749 | + vset_VT_CMP(S, op); | |
| 1757 | 1750 | break; |
| 1758 | 1751 | case 2: |
| 1759 | 1752 | opc=0xE1A00000|(opc<<5); |
| 1760 | − if ((vtop->r & VT_VALMASK) == VT_CMP || | |
| 1761 | − (vtop->r & (VT_VALMASK & ~1)) == VT_JMP) | |
| 1762 | − gv(RC_INT); | |
| 1763 | − vswap(); | |
| 1764 | − r=intr(gv(RC_INT)); | |
| 1765 | − vswap(); | |
| 1766 | − if ((vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1767 | − fr=intr(vtop[-1].r=get_reg_ex(RC_INT,regmask(vtop[-1].r))); | |
| 1768 | − c = vtop->c.i & 0x1f; | |
| 1769 | − o(opc|r|(c<<7)|(fr<<12)); | |
| 1753 | + if ((S->tccgen_vtop->r & VT_VALMASK) == VT_CMP || | |
| 1754 | + (S->tccgen_vtop->r & (VT_VALMASK & ~1)) == VT_JMP) | |
| 1755 | + gv(S, RC_INT); | |
| 1756 | + vswap(S); | |
| 1757 | + r=intr(S, gv(S, RC_INT)); | |
| 1758 | + vswap(S); | |
| 1759 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1760 | + fr=intr(S, S->tccgen_vtop[-1].r=get_reg_ex(S, RC_INT,regmask(S, S->tccgen_vtop[-1].r))); | |
| 1761 | + c = S->tccgen_vtop->c.i & 0x1f; | |
| 1762 | + o(S, opc|r|(c<<7)|(fr<<12)); | |
| 1770 | 1763 | } else { |
| 1771 | − fr=intr(gv(RC_INT)); | |
| 1764 | + fr=intr(S, gv(S, RC_INT)); | |
| 1772 | 1765 | #ifdef CONFIG_TCC_BCHECK |
| 1773 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1774 | − vswap(); | |
| 1775 | − r=intr(gv(RC_INT)); | |
| 1776 | − vswap(); | |
| 1766 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1767 | + vswap(S); | |
| 1768 | + r=intr(S, gv(S, RC_INT)); | |
| 1769 | + vswap(S); | |
| 1777 | 1770 | } |
| 1778 | 1771 | #endif |
| 1779 | − c=intr(vtop[-1].r=get_reg_ex(RC_INT,two2mask(vtop->r,vtop[-1].r))); | |
| 1780 | − o(opc|r|(c<<12)|(fr<<8)|0x10); | |
| 1772 | + c=intr(S, S->tccgen_vtop[-1].r=get_reg_ex(S, RC_INT,two2mask(S, S->tccgen_vtop->r,S->tccgen_vtop[-1].r))); | |
| 1773 | + o(S, opc|r|(c<<12)|(fr<<8)|0x10); | |
| 1781 | 1774 | } |
| 1782 | − vtop--; | |
| 1775 | + S->tccgen_vtop--; | |
| 1783 | 1776 | break; |
| 1784 | 1777 | case 3: |
| 1785 | − vpush_helper_func(func); | |
| 1786 | − vrott(3); | |
| 1787 | − gfunc_call(2); | |
| 1788 | − vpushi(0); | |
| 1789 | − vtop->r = retreg; | |
| 1778 | + vpush_helper_func(S, func); | |
| 1779 | + vrott(S, 3); | |
| 1780 | + gfunc_call(S, 2); | |
| 1781 | + vpushi(S, 0); | |
| 1782 | + S->tccgen_vtop->r = retreg; | |
| 1790 | 1783 | break; |
| 1791 | 1784 | default: |
| 1792 | − tcc_error("gen_opi %i unimplemented!",op); | |
| 1785 | + tcc_error(S, "gen_opi %i unimplemented!",op); | |
| 1793 | 1786 | } |
| 1794 | 1787 | } |
| 1795 | 1788 | |
| 1796 | 1789 | #ifdef TCC_ARM_VFP |
| 1797 | −static int is_zero(int i) | |
| 1790 | +static int is_zero(TCCState* S, int i) | |
| 1798 | 1791 | { |
| 1799 | − if((vtop[i].r & (VT_VALMASK | VT_LVAL | VT_SYM)) != VT_CONST) | |
| 1792 | + if((S->tccgen_vtop[i].r & (VT_VALMASK | VT_LVAL | VT_SYM)) != VT_CONST) | |
| 1800 | 1793 | return 0; |
| 1801 | − if (vtop[i].type.t == VT_FLOAT) | |
| 1802 | − return (vtop[i].c.f == 0.f); | |
| 1803 | − else if (vtop[i].type.t == VT_DOUBLE) | |
| 1804 | − return (vtop[i].c.d == 0.0); | |
| 1805 | − return (vtop[i].c.ld == 0.l); | |
| 1794 | + if (S->tccgen_vtop[i].type.t == VT_FLOAT) | |
| 1795 | + return (S->tccgen_vtop[i].c.f == 0.f); | |
| 1796 | + else if (S->tccgen_vtop[i].type.t == VT_DOUBLE) | |
| 1797 | + return (S->tccgen_vtop[i].c.d == 0.0); | |
| 1798 | + return (S->tccgen_vtop[i].c.ld == 0.l); | |
| 1806 | 1799 | } |
| 1807 | 1800 | |
| 1808 | 1801 | /* generate a floating point operation 'v = t1 op t2' instruction. The |
| 1809 | 1802 | * two operands are guaranteed to have the same floating point type */ |
| 1810 | −void gen_opf(int op) | |
| 1803 | +void gen_opf(TCCState* S, int op) | |
| 1811 | 1804 | { |
| 1812 | 1805 | uint32_t x; |
| 1813 | 1806 | int fneg=0,r; |
| 1814 | − x=0xEE000A00|T2CPR(vtop->type.t); | |
| 1807 | + x=0xEE000A00|T2CPR(S->tccgen_vtop->type.t); | |
| 1815 | 1808 | switch(op) { |
| 1816 | 1809 | case '+': |
| 1817 | − if(is_zero(-1)) | |
| 1818 | − vswap(); | |
| 1819 | − if(is_zero(0)) { | |
| 1820 | − vtop--; | |
| 1810 | + if(is_zero(S, -1)) | |
| 1811 | + vswap(S); | |
| 1812 | + if(is_zero(S, 0)) { | |
| 1813 | + S->tccgen_vtop--; | |
| 1821 | 1814 | return; |
| 1822 | 1815 | } |
| 1823 | 1816 | x|=0x300000; |
| 1824 | 1817 | break; |
| 1825 | 1818 | case '-': |
| 1826 | 1819 | x|=0x300040; |
| 1827 | − if(is_zero(0)) { | |
| 1828 | − vtop--; | |
| 1820 | + if(is_zero(S, 0)) { | |
| 1821 | + S->tccgen_vtop--; | |
| 1829 | 1822 | return; |
| 1830 | 1823 | } |
| 1831 | − if(is_zero(-1)) { | |
| 1824 | + if(is_zero(S, -1)) { | |
| 1832 | 1825 | x|=0x810000; /* fsubX -> fnegX */ |
| 1833 | − vswap(); | |
| 1834 | − vtop--; | |
| 1826 | + vswap(S); | |
| 1827 | + S->tccgen_vtop--; | |
| 1835 | 1828 | fneg=1; |
| 1836 | 1829 | } |
| 1837 | 1830 | break; |
| @@ -1843,11 +1836,11 @@ void gen_opf(int op) · 5 unmodified lines | ||
| 1843 | 1836 | break; |
| 1844 | 1837 | default: |
| 1845 | 1838 | if(op < TOK_ULT || op > TOK_GT) { |
| 1846 | − tcc_error("unknown fp op %x!",op); | |
| 1839 | + tcc_error(S, "unknown fp op %x!",op); | |
| 1847 | 1840 | return; |
| 1848 | 1841 | } |
| 1849 | − if(is_zero(-1)) { | |
| 1850 | − vswap(); | |
| 1842 | + if(is_zero(S, -1)) { | |
| 1843 | + vswap(S); | |
| 1851 | 1844 | switch(op) { |
| 1852 | 1845 | case TOK_LT: op=TOK_GT; break; |
| 1853 | 1846 | case TOK_GE: op=TOK_ULE; break; |
| @@ -1858,16 +1851,16 @@ void gen_opf(int op) · 4 unmodified lines | ||
| 1858 | 1851 | x|=0xB40040; /* fcmpX */ |
| 1859 | 1852 | if(op!=TOK_EQ && op!=TOK_NE) |
| 1860 | 1853 | x|=0x80; /* fcmpX -> fcmpeX */ |
| 1861 | − if(is_zero(0)) { | |
| 1862 | − vtop--; | |
| 1863 | − o(x|0x10000|(vfpr(gv(RC_FLOAT))<<12)); /* fcmp(e)X -> fcmp(e)zX */ | |
| 1854 | + if(is_zero(S, 0)) { | |
| 1855 | + S->tccgen_vtop--; | |
| 1856 | + o(S, x|0x10000|(vfpr(S, gv(S, RC_FLOAT))<<12)); /* fcmp(e)X -> fcmp(e)zX */ | |
| 1864 | 1857 | } else { |
| 1865 | − gv2(RC_FLOAT,RC_FLOAT); | |
| 1866 | − x|=vfpr(vtop[0].r); | |
| 1867 | − o(x|(vfpr(vtop[-1].r) << 12)); | |
| 1868 | − vtop--; | |
| 1858 | + gv2(S, RC_FLOAT,RC_FLOAT); | |
| 1859 | + x|=vfpr(S, S->tccgen_vtop[0].r); | |
| 1860 | + o(S, x|(vfpr(S, S->tccgen_vtop[-1].r) << 12)); | |
| 1861 | + S->tccgen_vtop--; | |
| 1869 | 1862 | } |
| 1870 | − o(0xEEF1FA10); /* fmstat */ | |
| 1863 | + o(S, 0xEEF1FA10); /* fmstat */ | |
| 1871 | 1864 | |
| 1872 | 1865 | switch(op) { |
| 1873 | 1866 | case TOK_LE: op=TOK_ULE; break; |
| @@ -1875,46 +1868,46 @@ void gen_opf(int op) · 1 unmodified line | ||
| 1875 | 1868 | case TOK_UGE: op=TOK_GE; break; |
| 1876 | 1869 | case TOK_UGT: op=TOK_GT; break; |
| 1877 | 1870 | } |
| 1878 | − vset_VT_CMP(op); | |
| 1871 | + vset_VT_CMP(S, op); | |
| 1879 | 1872 | return; |
| 1880 | 1873 | } |
| 1881 | − r=gv(RC_FLOAT); | |
| 1882 | − x|=vfpr(r); | |
| 1883 | − r=regmask(r); | |
| 1874 | + r=gv(S, RC_FLOAT); | |
| 1875 | + x|=vfpr(S, r); | |
| 1876 | + r=regmask(S, r); | |
| 1884 | 1877 | if(!fneg) { |
| 1885 | 1878 | int r2; |
| 1886 | − vswap(); | |
| 1887 | − r2=gv(RC_FLOAT); | |
| 1888 | − x|=vfpr(r2)<<16; | |
| 1889 | − r|=regmask(r2); | |
| 1879 | + vswap(S); | |
| 1880 | + r2=gv(S, RC_FLOAT); | |
| 1881 | + x|=vfpr(S, r2)<<16; | |
| 1882 | + r|=regmask(S, r2); | |
| 1890 | 1883 | #ifdef CONFIG_TCC_BCHECK |
| 1891 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1892 | − vswap(); | |
| 1893 | − r=gv(RC_FLOAT); | |
| 1894 | − vswap(); | |
| 1895 | − x=(x&~0xf)|vfpr(r); | |
| 1884 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1885 | + vswap(S); | |
| 1886 | + r=gv(S, RC_FLOAT); | |
| 1887 | + vswap(S); | |
| 1888 | + x=(x&~0xf)|vfpr(S, r); | |
| 1896 | 1889 | } |
| 1897 | 1890 | #endif |
| 1898 | 1891 | } |
| 1899 | − vtop->r=get_reg_ex(RC_FLOAT,r); | |
| 1892 | + S->tccgen_vtop->r=get_reg_ex(S, RC_FLOAT,r); | |
| 1900 | 1893 | if(!fneg) |
| 1901 | − vtop--; | |
| 1902 | − o(x|(vfpr(vtop->r)<<12)); | |
| 1894 | + S->tccgen_vtop--; | |
| 1895 | + o(S, x|(vfpr(S, S->tccgen_vtop->r)<<12)); | |
| 1903 | 1896 | } |
| 1904 | 1897 | |
| 1905 | 1898 | #else |
| 1906 | −static uint32_t is_fconst() | |
| 1899 | +static uint32_t is_fconst(TCCState* S) | |
| 1907 | 1900 | { |
| 1908 | 1901 | long double f; |
| 1909 | 1902 | uint32_t r; |
| 1910 | − if((vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) != VT_CONST) | |
| 1903 | + if((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) != VT_CONST) | |
| 1911 | 1904 | return 0; |
| 1912 | − if (vtop->type.t == VT_FLOAT) | |
| 1913 | − f = vtop->c.f; | |
| 1914 | − else if (vtop->type.t == VT_DOUBLE) | |
| 1915 | − f = vtop->c.d; | |
| 1905 | + if (S->tccgen_vtop->type.t == VT_FLOAT) | |
| 1906 | + f = S->tccgen_vtop->c.f; | |
| 1907 | + else if (S->tccgen_vtop->type.t == VT_DOUBLE) | |
| 1908 | + f = S->tccgen_vtop->c.d; | |
| 1916 | 1909 | else |
| 1917 | − f = vtop->c.ld; | |
| 1910 | + f = S->tccgen_vtop->c.ld; | |
| 1918 | 1911 | if(!ieee_finite(f)) |
| 1919 | 1912 | return 0; |
| 1920 | 1913 | r=0x8; |
| @@ -1943,45 +1936,45 @@ static uint32_t is_fconst() · 22 unmodified lines | ||
| 1943 | 1936 | |
| 1944 | 1937 | /* generate a floating point operation 'v = t1 op t2' instruction. The |
| 1945 | 1938 | two operands are guaranteed to have the same floating point type */ |
| 1946 | −void gen_opf(int op) | |
| 1939 | +void gen_opf(TCCState* S, int op) | |
| 1947 | 1940 | { |
| 1948 | 1941 | uint32_t x, r, r2, c1, c2; |
| 1949 | 1942 | //fputs("gen_opf\n",stderr); |
| 1950 | − vswap(); | |
| 1951 | − c1 = is_fconst(); | |
| 1952 | − vswap(); | |
| 1953 | − c2 = is_fconst(); | |
| 1943 | + vswap(S); | |
| 1944 | + c1 = is_fconst(S); | |
| 1945 | + vswap(S); | |
| 1946 | + c2 = is_fconst(S); | |
| 1954 | 1947 | x=0xEE000100; |
| 1955 | 1948 | #if LDOUBLE_SIZE == 8 |
| 1956 | − if ((vtop->type.t & VT_BTYPE) != VT_FLOAT) | |
| 1949 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) != VT_FLOAT) | |
| 1957 | 1950 | x|=0x80; |
| 1958 | 1951 | #else |
| 1959 | − if ((vtop->type.t & VT_BTYPE) == VT_DOUBLE) | |
| 1952 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_DOUBLE) | |
| 1960 | 1953 | x|=0x80; |
| 1961 | − else if ((vtop->type.t & VT_BTYPE) == VT_LDOUBLE) | |
| 1954 | + else if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LDOUBLE) | |
| 1962 | 1955 | x|=0x80000; |
| 1963 | 1956 | #endif |
| 1964 | 1957 | switch(op) |
| 1965 | 1958 | { |
| 1966 | 1959 | case '+': |
| 1967 | 1960 | if(!c2) { |
| 1968 | − vswap(); | |
| 1961 | + vswap(S); | |
| 1969 | 1962 | c2=c1; |
| 1970 | 1963 | } |
| 1971 | − vswap(); | |
| 1972 | − r=fpr(gv(RC_FLOAT)); | |
| 1973 | − vswap(); | |
| 1964 | + vswap(S); | |
| 1965 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 1966 | + vswap(S); | |
| 1974 | 1967 | if(c2) { |
| 1975 | 1968 | if(c2>0xf) |
| 1976 | 1969 | x|=0x200000; // suf |
| 1977 | 1970 | r2=c2&0xf; |
| 1978 | 1971 | } else { |
| 1979 | − r2=fpr(gv(RC_FLOAT)); | |
| 1972 | + r2=fpr(S, gv(S, RC_FLOAT)); | |
| 1980 | 1973 | #ifdef CONFIG_TCC_BCHECK |
| 1981 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1982 | − vswap(); | |
| 1983 | − r=fpr(gv(RC_FLOAT)); | |
| 1984 | − vswap(); | |
| 1974 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 1975 | + vswap(S); | |
| 1976 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 1977 | + vswap(S); | |
| 1985 | 1978 | } |
| 1986 | 1979 | #endif |
| 1987 | 1980 | } |
| @@ -1991,46 +1984,46 @@ void gen_opf(int op) · 3 unmodified lines | ||
| 1991 | 1984 | if(c2<=0xf) |
| 1992 | 1985 | x|=0x200000; // suf |
| 1993 | 1986 | r2=c2&0xf; |
| 1994 | − vswap(); | |
| 1995 | − r=fpr(gv(RC_FLOAT)); | |
| 1996 | − vswap(); | |
| 1987 | + vswap(S); | |
| 1988 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 1989 | + vswap(S); | |
| 1997 | 1990 | } else if(c1 && c1<=0xf) { |
| 1998 | 1991 | x|=0x300000; // rsf |
| 1999 | 1992 | r2=c1; |
| 2000 | − r=fpr(gv(RC_FLOAT)); | |
| 2001 | − vswap(); | |
| 1993 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 1994 | + vswap(S); | |
| 2002 | 1995 | } else { |
| 2003 | 1996 | x|=0x200000; // suf |
| 2004 | − vswap(); | |
| 2005 | − r=fpr(gv(RC_FLOAT)); | |
| 2006 | − vswap(); | |
| 2007 | − r2=fpr(gv(RC_FLOAT)); | |
| 1997 | + vswap(S); | |
| 1998 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 1999 | + vswap(S); | |
| 2000 | + r2=fpr(S, gv(S, RC_FLOAT)); | |
| 2008 | 2001 | #ifdef CONFIG_TCC_BCHECK |
| 2009 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2010 | − vswap(); | |
| 2011 | − r=fpr(gv(RC_FLOAT)); | |
| 2012 | − vswap(); | |
| 2002 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2003 | + vswap(S); | |
| 2004 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2005 | + vswap(S); | |
| 2013 | 2006 | } |
| 2014 | 2007 | #endif |
| 2015 | 2008 | } |
| 2016 | 2009 | break; |
| 2017 | 2010 | case '*': |
| 2018 | 2011 | if(!c2 || c2>0xf) { |
| 2019 | − vswap(); | |
| 2012 | + vswap(S); | |
| 2020 | 2013 | c2=c1; |
| 2021 | 2014 | } |
| 2022 | − vswap(); | |
| 2023 | − r=fpr(gv(RC_FLOAT)); | |
| 2024 | − vswap(); | |
| 2015 | + vswap(S); | |
| 2016 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2017 | + vswap(S); | |
| 2025 | 2018 | if(c2 && c2<=0xf) |
| 2026 | 2019 | r2=c2; |
| 2027 | 2020 | else { |
| 2028 | − r2=fpr(gv(RC_FLOAT)); | |
| 2021 | + r2=fpr(S, gv(S, RC_FLOAT)); | |
| 2029 | 2022 | #ifdef CONFIG_TCC_BCHECK |
| 2030 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2031 | − vswap(); | |
| 2032 | − r=fpr(gv(RC_FLOAT)); | |
| 2033 | − vswap(); | |
| 2023 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2024 | + vswap(S); | |
| 2025 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2026 | + vswap(S); | |
| 2034 | 2027 | } |
| 2035 | 2028 | #endif |
| 2036 | 2029 | } |
| @@ -2040,25 +2033,25 @@ void gen_opf(int op) · 3 unmodified lines | ||
| 2040 | 2033 | if(c2 && c2<=0xf) { |
| 2041 | 2034 | x|=0x400000; // dvf |
| 2042 | 2035 | r2=c2; |
| 2043 | − vswap(); | |
| 2044 | − r=fpr(gv(RC_FLOAT)); | |
| 2045 | − vswap(); | |
| 2036 | + vswap(S); | |
| 2037 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2038 | + vswap(S); | |
| 2046 | 2039 | } else if(c1 && c1<=0xf) { |
| 2047 | 2040 | x|=0x500000; // rdf |
| 2048 | 2041 | r2=c1; |
| 2049 | − r=fpr(gv(RC_FLOAT)); | |
| 2050 | − vswap(); | |
| 2042 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2043 | + vswap(S); | |
| 2051 | 2044 | } else { |
| 2052 | 2045 | x|=0x400000; // dvf |
| 2053 | − vswap(); | |
| 2054 | − r=fpr(gv(RC_FLOAT)); | |
| 2055 | − vswap(); | |
| 2056 | − r2=fpr(gv(RC_FLOAT)); | |
| 2046 | + vswap(S); | |
| 2047 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2048 | + vswap(S); | |
| 2049 | + r2=fpr(S, gv(S, RC_FLOAT)); | |
| 2057 | 2050 | #ifdef CONFIG_TCC_BCHECK |
| 2058 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2059 | − vswap(); | |
| 2060 | − r=fpr(gv(RC_FLOAT)); | |
| 2061 | − vswap(); | |
| 2051 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2052 | + vswap(S); | |
| 2053 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2054 | + vswap(S); | |
| 2062 | 2055 | } |
| 2063 | 2056 | #endif |
| 2064 | 2057 | } |
| @@ -2073,7 +2066,7 @@ void gen_opf(int op) · 8 unmodified lines | ||
| 2073 | 2066 | case TOK_UGE: |
| 2074 | 2067 | case TOK_ULE: |
| 2075 | 2068 | case TOK_UGT: |
| 2076 | − tcc_error("unsigned comparison on floats?"); | |
| 2069 | + tcc_error(S, "unsigned comparison on floats?"); | |
| 2077 | 2070 | break; |
| 2078 | 2071 | case TOK_LT: |
| 2079 | 2072 | op=TOK_Nset; |
| @@ -2088,7 +2081,7 @@ void gen_opf(int op) · 8 unmodified lines | ||
| 2088 | 2081 | } |
| 2089 | 2082 | if(c1 && !c2) { |
| 2090 | 2083 | c2=c1; |
| 2091 | − vswap(); | |
| 2084 | + vswap(S); | |
| 2092 | 2085 | switch(op) { |
| 2093 | 2086 | case TOK_Nset: |
| 2094 | 2087 | op=TOK_GT; |
| @@ -2104,86 +2097,86 @@ void gen_opf(int op) · 9 unmodified lines | ||
| 2104 | 2097 | break; |
| 2105 | 2098 | } |
| 2106 | 2099 | } |
| 2107 | − vswap(); | |
| 2108 | − r=fpr(gv(RC_FLOAT)); | |
| 2109 | − vswap(); | |
| 2100 | + vswap(S); | |
| 2101 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2102 | + vswap(S); | |
| 2110 | 2103 | if(c2) { |
| 2111 | 2104 | if(c2>0xf) |
| 2112 | 2105 | x|=0x200000; |
| 2113 | 2106 | r2=c2&0xf; |
| 2114 | 2107 | } else { |
| 2115 | − r2=fpr(gv(RC_FLOAT)); | |
| 2108 | + r2=fpr(S, gv(S, RC_FLOAT)); | |
| 2116 | 2109 | #ifdef CONFIG_TCC_BCHECK |
| 2117 | − if ((vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2118 | − vswap(); | |
| 2119 | − r=fpr(gv(RC_FLOAT)); | |
| 2120 | − vswap(); | |
| 2110 | + if ((S->tccgen_vtop[-1].r & VT_VALMASK) >= VT_CONST) { | |
| 2111 | + vswap(S); | |
| 2112 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2113 | + vswap(S); | |
| 2121 | 2114 | } |
| 2122 | 2115 | #endif |
| 2123 | 2116 | } |
| 2124 | − --vtop; | |
| 2125 | − vset_VT_CMP(op); | |
| 2126 | − ++vtop; | |
| 2117 | + --S->tccgen_vtop; | |
| 2118 | + vset_VT_CMP(S, op); | |
| 2119 | + ++S->tccgen_vtop; | |
| 2127 | 2120 | } else { |
| 2128 | − tcc_error("unknown fp op %x!",op); | |
| 2121 | + tcc_error(S, "unknown fp op %x!",op); | |
| 2129 | 2122 | return; |
| 2130 | 2123 | } |
| 2131 | 2124 | } |
| 2132 | − if(vtop[-1].r == VT_CMP) | |
| 2125 | + if(S->tccgen_vtop[-1].r == VT_CMP) | |
| 2133 | 2126 | c1=15; |
| 2134 | 2127 | else { |
| 2135 | − c1=vtop->r; | |
| 2128 | + c1=S->tccgen_vtop->r; | |
| 2136 | 2129 | if(r2&0x8) |
| 2137 | − c1=vtop[-1].r; | |
| 2138 | − vtop[-1].r=get_reg_ex(RC_FLOAT,two2mask(vtop[-1].r,c1)); | |
| 2139 | − c1=fpr(vtop[-1].r); | |
| 2130 | + c1=S->tccgen_vtop[-1].r; | |
| 2131 | + S->tccgen_vtop[-1].r=get_reg_ex(S, RC_FLOAT,two2mask(S, S->tccgen_vtop[-1].r,c1)); | |
| 2132 | + c1=fpr(S, S->tccgen_vtop[-1].r); | |
| 2140 | 2133 | } |
| 2141 | − vtop--; | |
| 2142 | − o(x|(r<<16)|(c1<<12)|r2); | |
| 2134 | + S->tccgen_vtop--; | |
| 2135 | + o(S, x|(r<<16)|(c1<<12)|r2); | |
| 2143 | 2136 | } |
| 2144 | 2137 | #endif |
| 2145 | 2138 | |
| 2146 | 2139 | /* convert integers to fp 't' type. Must handle 'int', 'unsigned int' |
| 2147 | 2140 | and 'long long' cases. */ |
| 2148 | −ST_FUNC void gen_cvt_itof(int t) | |
| 2141 | +ST_FUNC void gen_cvt_itof(TCCState* S, int t) | |
| 2149 | 2142 | { |
| 2150 | 2143 | uint32_t r, r2; |
| 2151 | 2144 | int bt; |
| 2152 | − bt=vtop->type.t & VT_BTYPE; | |
| 2145 | + bt=S->tccgen_vtop->type.t & VT_BTYPE; | |
| 2153 | 2146 | if(bt == VT_INT || bt == VT_SHORT || bt == VT_BYTE) { |
| 2154 | 2147 | #ifndef TCC_ARM_VFP |
| 2155 | 2148 | uint32_t dsize = 0; |
| 2156 | 2149 | #endif |
| 2157 | − r=intr(gv(RC_INT)); | |
| 2150 | + r=intr(S, gv(S, RC_INT)); | |
| 2158 | 2151 | #ifdef TCC_ARM_VFP |
| 2159 | − r2=vfpr(vtop->r=get_reg(RC_FLOAT)); | |
| 2160 | − o(0xEE000A10|(r<<12)|(r2<<16)); /* fmsr */ | |
| 2152 | + r2=vfpr(S, S->tccgen_vtop->r=get_reg(S, RC_FLOAT)); | |
| 2153 | + o(S, 0xEE000A10|(r<<12)|(r2<<16)); /* fmsr */ | |
| 2161 | 2154 | r2|=r2<<12; |
| 2162 | − if(!(vtop->type.t & VT_UNSIGNED)) | |
| 2155 | + if(!(S->tccgen_vtop->type.t & VT_UNSIGNED)) | |
| 2163 | 2156 | r2|=0x80; /* fuitoX -> fsituX */ |
| 2164 | − o(0xEEB80A40|r2|T2CPR(t)); /* fYitoX*/ | |
| 2157 | + o(S, 0xEEB80A40|r2|T2CPR(t)); /* fYitoX*/ | |
| 2165 | 2158 | #else |
| 2166 | − r2=fpr(vtop->r=get_reg(RC_FLOAT)); | |
| 2159 | + r2=fpr(S, S->tccgen_vtop->r=get_reg(S, RC_FLOAT)); | |
| 2167 | 2160 | if((t & VT_BTYPE) != VT_FLOAT) |
| 2168 | 2161 | dsize=0x80; /* flts -> fltd */ |
| 2169 | − o(0xEE000110|dsize|(r2<<16)|(r<<12)); /* flts */ | |
| 2170 | − if((vtop->type.t & (VT_UNSIGNED|VT_BTYPE)) == (VT_UNSIGNED|VT_INT)) { | |
| 2162 | + o(S, 0xEE000110|dsize|(r2<<16)|(r<<12)); /* flts */ | |
| 2163 | + if((S->tccgen_vtop->type.t & (VT_UNSIGNED|VT_BTYPE)) == (VT_UNSIGNED|VT_INT)) { | |
| 2171 | 2164 | uint32_t off = 0; |
| 2172 | − o(0xE3500000|(r<<12)); /* cmp */ | |
| 2173 | − r=fpr(get_reg(RC_FLOAT)); | |
| 2165 | + o(S, 0xE3500000|(r<<12)); /* cmp */ | |
| 2166 | + r=fpr(S, get_reg(S, RC_FLOAT)); | |
| 2174 | 2167 | if(last_itod_magic) { |
| 2175 | − off=ind+8-last_itod_magic; | |
| 2168 | + off=S->tccgen_ind+8-last_itod_magic; | |
| 2176 | 2169 | off/=4; |
| 2177 | 2170 | if(off>255) |
| 2178 | 2171 | off=0; |
| 2179 | 2172 | } |
| 2180 | − o(0xBD1F0100|(r<<12)|off); /* ldflts */ | |
| 2173 | + o(S, 0xBD1F0100|(r<<12)|off); /* ldflts */ | |
| 2181 | 2174 | if(!off) { |
| 2182 | − o(0xEA000000); /* b */ | |
| 2183 | − last_itod_magic=ind; | |
| 2184 | − o(0x4F800000); /* 4294967296.0f */ | |
| 2175 | + o(S, 0xEA000000); /* b */ | |
| 2176 | + last_itod_magic=S->tccgen_ind; | |
| 2177 | + o(S, 0x4F800000); /* 4294967296.0f */ | |
| 2185 | 2178 | } |
| 2186 | − o(0xBE000100|dsize|(r2<<16)|(r2<<12)|r); /* adflt */ | |
| 2179 | + o(S, 0xBE000100|dsize|(r2<<16)|(r2<<12)|r); /* adflt */ | |
| 2187 | 2180 | } |
| 2188 | 2181 | #endif |
| 2189 | 2182 | return; |
| @@ -2191,15 +2184,15 @@ ST_FUNC void gen_cvt_itof(int t) · 1 unmodified line | ||
| 2191 | 2184 | int func; |
| 2192 | 2185 | CType *func_type = 0; |
| 2193 | 2186 | if((t & VT_BTYPE) == VT_FLOAT) { |
| 2194 | − func_type = &func_float_type; | |
| 2195 | − if(vtop->type.t & VT_UNSIGNED) | |
| 2187 | + func_type = &S->armgen_func_float_type; | |
| 2188 | + if(S->tccgen_vtop->type.t & VT_UNSIGNED) | |
| 2196 | 2189 | func=TOK___floatundisf; |
| 2197 | 2190 | else |
| 2198 | 2191 | func=TOK___floatdisf; |
| 2199 | 2192 | #if LDOUBLE_SIZE != 8 |
| 2200 | 2193 | } else if((t & VT_BTYPE) == VT_LDOUBLE) { |
| 2201 | − func_type = &func_ldouble_type; | |
| 2202 | − if(vtop->type.t & VT_UNSIGNED) | |
| 2194 | + func_type = &S->armgen_func_ldouble_type; | |
| 2195 | + if(S->tccgen_vtop->type.t & VT_UNSIGNED) | |
| 2203 | 2196 | func=TOK___floatundixf; |
| 2204 | 2197 | else |
| 2205 | 2198 | func=TOK___floatdixf; |
| @@ -2207,39 +2200,39 @@ ST_FUNC void gen_cvt_itof(int t) · 1 unmodified line | ||
| 2207 | 2200 | #else |
| 2208 | 2201 | } else if((t & VT_BTYPE) == VT_DOUBLE || (t & VT_BTYPE) == VT_LDOUBLE) { |
| 2209 | 2202 | #endif |
| 2210 | − func_type = &func_double_type; | |
| 2211 | − if(vtop->type.t & VT_UNSIGNED) | |
| 2203 | + func_type = &S->armgen_func_double_type; | |
| 2204 | + if(S->tccgen_vtop->type.t & VT_UNSIGNED) | |
| 2212 | 2205 | func=TOK___floatundidf; |
| 2213 | 2206 | else |
| 2214 | 2207 | func=TOK___floatdidf; |
| 2215 | 2208 | } |
| 2216 | 2209 | if(func_type) { |
| 2217 | − vpushsym(func_type, external_helper_sym(func)); | |
| 2218 | − vswap(); | |
| 2219 | − gfunc_call(1); | |
| 2220 | − vpushi(0); | |
| 2221 | − vtop->r=TREG_F0; | |
| 2210 | + vpushsym(S, func_type, external_helper_sym(S, func)); | |
| 2211 | + vswap(S); | |
| 2212 | + gfunc_call(S, 1); | |
| 2213 | + vpushi(S, 0); | |
| 2214 | + S->tccgen_vtop->r=TREG_F0; | |
| 2222 | 2215 | return; |
| 2223 | 2216 | } |
| 2224 | 2217 | } |
| 2225 | − tcc_error("unimplemented gen_cvt_itof %x!",vtop->type.t); | |
| 2218 | + tcc_error(S, "unimplemented gen_cvt_itof %x!",S->tccgen_vtop->type.t); | |
| 2226 | 2219 | } |
| 2227 | 2220 | |
| 2228 | 2221 | /* convert fp to int 't' type */ |
| 2229 | −void gen_cvt_ftoi(int t) | |
| 2222 | +void gen_cvt_ftoi(TCCState* S, int t) | |
| 2230 | 2223 | { |
| 2231 | 2224 | uint32_t r, r2; |
| 2232 | 2225 | int u, func = 0; |
| 2233 | 2226 | u=t&VT_UNSIGNED; |
| 2234 | 2227 | t&=VT_BTYPE; |
| 2235 | − r2=vtop->type.t & VT_BTYPE; | |
| 2228 | + r2=S->tccgen_vtop->type.t & VT_BTYPE; | |
| 2236 | 2229 | if(t==VT_INT) { |
| 2237 | 2230 | #ifdef TCC_ARM_VFP |
| 2238 | − r=vfpr(gv(RC_FLOAT)); | |
| 2231 | + r=vfpr(S, gv(S, RC_FLOAT)); | |
| 2239 | 2232 | u=u?0:0x10000; |
| 2240 | − o(0xEEBC0AC0|(r<<12)|r|T2CPR(r2)|u); /* ftoXizY */ | |
| 2241 | − r2=intr(vtop->r=get_reg(RC_INT)); | |
| 2242 | − o(0xEE100A10|(r<<16)|(r2<<12)); | |
| 2233 | + o(S, 0xEEBC0AC0|(r<<12)|r|T2CPR(r2)|u); /* ftoXizY */ | |
| 2234 | + r2=intr(S, S->tccgen_vtop->r=get_reg(S, RC_INT)); | |
| 2235 | + o(S, 0xEE100A10|(r<<16)|(r2<<12)); | |
| 2243 | 2236 | return; |
| 2244 | 2237 | #else |
| 2245 | 2238 | if(u) { |
| @@ -2254,9 +2247,9 @@ void gen_cvt_ftoi(int t) · 8 unmodified lines | ||
| 2254 | 2247 | #endif |
| 2255 | 2248 | func=TOK___fixunsdfsi; |
| 2256 | 2249 | } else { |
| 2257 | − r=fpr(gv(RC_FLOAT)); | |
| 2258 | − r2=intr(vtop->r=get_reg(RC_INT)); | |
| 2259 | − o(0xEE100170|(r2<<12)|r); | |
| 2250 | + r=fpr(S, gv(S, RC_FLOAT)); | |
| 2251 | + r2=intr(S, S->tccgen_vtop->r=get_reg(S, RC_INT)); | |
| 2252 | + o(S, 0xEE100170|(r2<<12)|r); | |
| 2260 | 2253 | return; |
| 2261 | 2254 | } |
| 2262 | 2255 | #endif |
| @@ -2273,93 +2266,93 @@ void gen_cvt_ftoi(int t) · 10 unmodified lines | ||
| 2273 | 2266 | func=TOK___fixdfdi; |
| 2274 | 2267 | } |
| 2275 | 2268 | if(func) { |
| 2276 | − vpush_helper_func(func); | |
| 2277 | − vswap(); | |
| 2278 | − gfunc_call(1); | |
| 2279 | − vpushi(0); | |
| 2269 | + vpush_helper_func(S, func); | |
| 2270 | + vswap(S); | |
| 2271 | + gfunc_call(S, 1); | |
| 2272 | + vpushi(S, 0); | |
| 2280 | 2273 | if(t == VT_LLONG) |
| 2281 | − vtop->r2 = REG_IRE2; | |
| 2282 | − vtop->r = REG_IRET; | |
| 2274 | + S->tccgen_vtop->r2 = REG_IRE2; | |
| 2275 | + S->tccgen_vtop->r = REG_IRET; | |
| 2283 | 2276 | return; |
| 2284 | 2277 | } |
| 2285 | − tcc_error("unimplemented gen_cvt_ftoi!"); | |
| 2278 | + tcc_error(S, "unimplemented gen_cvt_ftoi!"); | |
| 2286 | 2279 | } |
| 2287 | 2280 | |
| 2288 | 2281 | /* convert from one floating point type to another */ |
| 2289 | −void gen_cvt_ftof(int t) | |
| 2282 | +void gen_cvt_ftof(TCCState* S, int t) | |
| 2290 | 2283 | { |
| 2291 | 2284 | #ifdef TCC_ARM_VFP |
| 2292 | − if(((vtop->type.t & VT_BTYPE) == VT_FLOAT) != ((t & VT_BTYPE) == VT_FLOAT)) { | |
| 2293 | − uint32_t r = vfpr(gv(RC_FLOAT)); | |
| 2294 | − o(0xEEB70AC0|(r<<12)|r|T2CPR(vtop->type.t)); | |
| 2285 | + if(((S->tccgen_vtop->type.t & VT_BTYPE) == VT_FLOAT) != ((t & VT_BTYPE) == VT_FLOAT)) { | |
| 2286 | + uint32_t r = vfpr(S, gv(S, RC_FLOAT)); | |
| 2287 | + o(S, 0xEEB70AC0|(r<<12)|r|T2CPR(S->tccgen_vtop->type.t)); | |
| 2295 | 2288 | } |
| 2296 | 2289 | #else |
| 2297 | 2290 | /* all we have to do on i386 and FPA ARM is to put the float in a register */ |
| 2298 | − gv(RC_FLOAT); | |
| 2291 | + gv(S, RC_FLOAT); | |
| 2299 | 2292 | #endif |
| 2300 | 2293 | } |
| 2301 | 2294 | |
| 2302 | 2295 | /* increment tcov counter */ |
| 2303 | −ST_FUNC void gen_increment_tcov (SValue *sv) | |
| 2296 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv) | |
| 2304 | 2297 | { |
| 2305 | 2298 | int r1, r2; |
| 2306 | 2299 | |
| 2307 | − vpushv(sv); | |
| 2308 | − vtop->r = r1 = get_reg(RC_INT); | |
| 2309 | − r2 = get_reg(RC_INT); | |
| 2310 | − o(0xE59F0000 | (intr(r1)<<12)); // ldr r1,[pc] | |
| 2311 | − o(0xEA000000); // b $+4 | |
| 2312 | − greloc(cur_text_section, sv->sym, ind, R_ARM_REL32); | |
| 2313 | − o(-12); | |
| 2314 | − o(0xe080000f | (intr(r1)<<16) | (intr(r1)<<12)); // add r1,r1,pc | |
| 2315 | − o(0xe5900000 | (intr(r1)<<16) | (intr(r2)<<12)); // ldr r2, [r1] | |
| 2316 | − o(0xe2900001 | (intr(r2)<<16) | (intr(r2)<<12)); // adds r2, r2, #1 | |
| 2317 | − o(0xe5800000 | (intr(r1)<<16) | (intr(r2)<<12)); // str r2, [r1] | |
| 2318 | − o(0xe2800004 | (intr(r1)<<16) | (intr(r1)<<12)); // add r1, r1, #4 | |
| 2319 | − o(0xe5900000 | (intr(r1)<<16) | (intr(r2)<<12)); // ldr r2, [r1] | |
| 2320 | − o(0xe2a00000 | (intr(r2)<<16) | (intr(r2)<<12)); // adc r2, r2, #0 | |
| 2321 | − o(0xe5800000 | (intr(r1)<<16) | (intr(r2)<<12)); // str r2, [r1] | |
| 2322 | − vpop(); | |
| 2300 | + vpushv(S, sv); | |
| 2301 | + S->tccgen_vtop->r = r1 = get_reg(S, RC_INT); | |
| 2302 | + r2 = get_reg(S, RC_INT); | |
| 2303 | + o(S, 0xE59F0000 | (intr(S, r1)<<12)); // ldr r1,[pc] | |
| 2304 | + o(S, 0xEA000000); // b $+4 | |
| 2305 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind, R_ARM_REL32); | |
| 2306 | + o(S, -12); | |
| 2307 | + o(S, 0xe080000f | (intr(S, r1)<<16) | (intr(S, r1)<<12)); // add r1,r1,pc | |
| 2308 | + o(S, 0xe5900000 | (intr(S, r1)<<16) | (intr(S, r2)<<12)); // ldr r2, [r1] | |
| 2309 | + o(S, 0xe2900001 | (intr(S, r2)<<16) | (intr(S, r2)<<12)); // adds r2, r2, #1 | |
| 2310 | + o(S, 0xe5800000 | (intr(S, r1)<<16) | (intr(S, r2)<<12)); // str r2, [r1] | |
| 2311 | + o(S, 0xe2800004 | (intr(S, r1)<<16) | (intr(S, r1)<<12)); // add r1, r1, #4 | |
| 2312 | + o(S, 0xe5900000 | (intr(S, r1)<<16) | (intr(S, r2)<<12)); // ldr r2, [r1] | |
| 2313 | + o(S, 0xe2a00000 | (intr(S, r2)<<16) | (intr(S, r2)<<12)); // adc r2, r2, #0 | |
| 2314 | + o(S, 0xe5800000 | (intr(S, r1)<<16) | (intr(S, r2)<<12)); // str r2, [r1] | |
| 2315 | + vpop(S); | |
| 2323 | 2316 | } |
| 2324 | 2317 | |
| 2325 | 2318 | /* computed goto support */ |
| 2326 | −void ggoto(void) | |
| 2319 | +void ggoto(TCCState* S) | |
| 2327 | 2320 | { |
| 2328 | − gcall_or_jmp(1); | |
| 2329 | − vtop--; | |
| 2321 | + gcall_or_jmp(S, 1); | |
| 2322 | + S->tccgen_vtop--; | |
| 2330 | 2323 | } |
| 2331 | 2324 | |
| 2332 | 2325 | /* Save the stack pointer onto the stack and return the location of its address */ |
| 2333 | −ST_FUNC void gen_vla_sp_save(int addr) { | |
| 2326 | +ST_FUNC void gen_vla_sp_save(TCCState* S, int addr) { | |
| 2334 | 2327 | SValue v; |
| 2335 | 2328 | v.type.t = VT_PTR; |
| 2336 | 2329 | v.r = VT_LOCAL | VT_LVAL; |
| 2337 | 2330 | v.c.i = addr; |
| 2338 | − store(TREG_SP, &v); | |
| 2331 | + store(S, TREG_SP, &v); | |
| 2339 | 2332 | } |
| 2340 | 2333 | |
| 2341 | 2334 | /* Restore the SP from a location on the stack */ |
| 2342 | −ST_FUNC void gen_vla_sp_restore(int addr) { | |
| 2335 | +ST_FUNC void gen_vla_sp_restore(TCCState* S, int addr) { | |
| 2343 | 2336 | SValue v; |
| 2344 | 2337 | v.type.t = VT_PTR; |
| 2345 | 2338 | v.r = VT_LOCAL | VT_LVAL; |
| 2346 | 2339 | v.c.i = addr; |
| 2347 | − load(TREG_SP, &v); | |
| 2340 | + load(S, TREG_SP, &v); | |
| 2348 | 2341 | } |
| 2349 | 2342 | |
| 2350 | 2343 | /* Subtract from the stack pointer, and push the resulting value onto the stack */ |
| 2351 | −ST_FUNC void gen_vla_alloc(CType *type, int align) { | |
| 2344 | +ST_FUNC void gen_vla_alloc(TCCState* S, CType *type, int align) { | |
| 2352 | 2345 | int r; |
| 2353 | 2346 | #if defined(CONFIG_TCC_BCHECK) |
| 2354 | − if (tcc_state->do_bounds_check) | |
| 2355 | − vpushv(vtop); | |
| 2347 | + if (S->do_bounds_check) | |
| 2348 | + vpushv(S, S->tccgen_vtop); | |
| 2356 | 2349 | #endif |
| 2357 | − r = intr(gv(RC_INT)); | |
| 2350 | + r = intr(S, gv(S, RC_INT)); | |
| 2358 | 2351 | #if defined(CONFIG_TCC_BCHECK) |
| 2359 | − if (tcc_state->do_bounds_check) | |
| 2360 | − o(0xe2800001 | (r<<16)|(r<<12)); /* add r,r,#1 */ | |
| 2352 | + if (S->do_bounds_check) | |
| 2353 | + o(S, 0xe2800001 | (r<<16)|(r<<12)); /* add r,r,#1 */ | |
| 2361 | 2354 | #endif |
| 2362 | − o(0xE04D0000|(r<<12)|r); /* sub r, sp, r */ | |
| 2355 | + o(S, 0xE04D0000|(r<<12)|r); /* sub r, sp, r */ | |
| 2363 | 2356 | #ifdef TCC_ARM_EABI |
| 2364 | 2357 | if (align < 8) |
| 2365 | 2358 | align = 8; |
| @@ -2368,19 +2361,19 @@ ST_FUNC void gen_vla_alloc(CType *type, int align) { · 2 unmodified lines | ||
| 2368 | 2361 | align = 4; |
| 2369 | 2362 | #endif |
| 2370 | 2363 | if (align & (align - 1)) |
| 2371 | − tcc_error("alignment is not a power of 2: %i", align); | |
| 2372 | − o(stuff_const(0xE3C0D000|(r<<16), align - 1)); /* bic sp, r, #align-1 */ | |
| 2373 | − vpop(); | |
| 2364 | + tcc_error(S, "alignment is not a power of 2: %i", align); | |
| 2365 | + o(S, stuff_const(0xE3C0D000|(r<<16), align - 1)); /* bic sp, r, #align-1 */ | |
| 2366 | + vpop(S); | |
| 2374 | 2367 | #if defined(CONFIG_TCC_BCHECK) |
| 2375 | − if (tcc_state->do_bounds_check) { | |
| 2376 | − vpushi(0); | |
| 2377 | − vtop->r = TREG_R0; | |
| 2378 | − o(0xe1a0000d | (vtop->r << 12)); // mov r0,sp | |
| 2379 | − vswap(); | |
| 2380 | − vpush_helper_func(TOK___bound_new_region); | |
| 2381 | − vrott(3); | |
| 2382 | − gfunc_call(2); | |
| 2383 | − func_bound_add_epilog = 1; | |
| 2368 | + if (S->do_bounds_check) { | |
| 2369 | + vpushi(S, 0); | |
| 2370 | + S->tccgen_vtop->r = TREG_R0; | |
| 2371 | + o(S, 0xe1a0000d | (S->tccgen_vtop->r << 12)); // mov r0,sp | |
| 2372 | + vswap(S); | |
| 2373 | + vpush_helper_func(S, TOK___bound_new_region); | |
| 2374 | + vrott(S, 3); | |
| 2375 | + gfunc_call(S, 2); | |
| 2376 | + S->func_bound_add_epilog = 1; | |
| 2384 | 2377 | } |
| 2385 | 2378 | #endif |
| 2386 | 2379 | } |
| @@ -107,9 +107,9 @@ int gotplt_entry_type (int reloc_type) · 106 unmodified lines | ||
| 107 | 107 | } |
| 108 | 108 | |
| 109 | 109 | #ifndef TCC_TARGET_PE |
| 110 | −ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_attr *attr) | |
| 110 | +ST_FUNC unsigned create_plt_entry(TCCState *S, unsigned got_offset, struct sym_attr *attr) | |
| 111 | 111 | { |
| 112 | − Section *plt = s1->plt; | |
| 112 | + Section *plt = S->plt; | |
| 113 | 113 | uint8_t *p; |
| 114 | 114 | unsigned plt_offset; |
| 115 | 115 | |
| @@ -119,7 +119,7 @@ ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_ · 3 unmodified lines | ||
| 119 | 119 | /* empty PLT: create PLT0 entry that push address of call site and |
| 120 | 120 | jump to ld.so resolution routine (GOT + 8) */ |
| 121 | 121 | if (plt->data_offset == 0) { |
| 122 | − p = section_ptr_add(plt, 20); | |
| 122 | + p = section_ptr_add(S, plt, 20); | |
| 123 | 123 | write32le(p, 0xe52de004); /* push {lr} */ |
| 124 | 124 | write32le(p+4, 0xe59fe004); /* ldr lr, [pc, #4] */ |
| 125 | 125 | write32le(p+8, 0xe08fe00e); /* add lr, pc, lr */ |
| @@ -129,11 +129,11 @@ ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_ · 3 unmodified lines | ||
| 129 | 129 | plt_offset = plt->data_offset; |
| 130 | 130 | |
| 131 | 131 | if (attr->plt_thumb_stub) { |
| 132 | − p = section_ptr_add(plt, 4); | |
| 132 | + p = section_ptr_add(S, plt, 4); | |
| 133 | 133 | write32le(p, 0x4778); /* bx pc */ |
| 134 | 134 | write32le(p+2, 0x46c0); /* nop */ |
| 135 | 135 | } |
| 136 | − p = section_ptr_add(plt, 16); | |
| 136 | + p = section_ptr_add(S, plt, 16); | |
| 137 | 137 | /* save GOT offset for relocate_plt */ |
| 138 | 138 | write32le(p + 4, got_offset); |
| 139 | 139 | return plt_offset; |
| @@ -141,22 +141,22 @@ ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_ · 1 unmodified line | ||
| 141 | 141 | |
| 142 | 142 | /* relocate the PLT: compute addresses and offsets in the PLT now that final |
| 143 | 143 | address for PLT and GOT are known (see fill_program_header) */ |
| 144 | −ST_FUNC void relocate_plt(TCCState *s1) | |
| 144 | +ST_FUNC void relocate_plt(TCCState *S) | |
| 145 | 145 | { |
| 146 | 146 | uint8_t *p, *p_end; |
| 147 | 147 | |
| 148 | − if (!s1->plt) | |
| 148 | + if (!S->plt) | |
| 149 | 149 | return; |
| 150 | 150 | |
| 151 | − p = s1->plt->data; | |
| 152 | − p_end = p + s1->plt->data_offset; | |
| 151 | + p = S->plt->data; | |
| 152 | + p_end = p + S->plt->data_offset; | |
| 153 | 153 | |
| 154 | 154 | if (p < p_end) { |
| 155 | − int x = s1->got->sh_addr - s1->plt->sh_addr - 12; | |
| 156 | − write32le(s1->plt->data + 16, x - 4); | |
| 155 | + int x = S->got->sh_addr - S->plt->sh_addr - 12; | |
| 156 | + write32le(S->plt->data + 16, x - 4); | |
| 157 | 157 | p += 20; |
| 158 | 158 | while (p < p_end) { |
| 159 | − unsigned off = x + read32le(p + 4) + (s1->plt->data - p) + 4; | |
| 159 | + unsigned off = x + read32le(p + 4) + (S->plt->data - p) + 4; | |
| 160 | 160 | if (read32le(p) == 0x46c04778) /* PLT Thumb stub present */ |
| 161 | 161 | p += 4; |
| 162 | 162 | write32le(p, 0xe28fc200 | ((off >> 28) & 0xf)); // add ip, pc, #0xN0000000 |
| @@ -167,17 +167,17 @@ ST_FUNC void relocate_plt(TCCState *s1) · 4 unmodified lines | ||
| 167 | 167 | } |
| 168 | 168 | } |
| 169 | 169 | |
| 170 | − if (s1->plt->reloc) { | |
| 170 | + if (S->plt->reloc) { | |
| 171 | 171 | ElfW_Rel *rel; |
| 172 | − p = s1->got->data; | |
| 173 | − for_each_elem(s1->plt->reloc, 0, rel, ElfW_Rel) { | |
| 174 | − write32le(p + rel->r_offset, s1->plt->sh_addr); | |
| 172 | + p = S->got->data; | |
| 173 | + for_each_elem(S->plt->reloc, 0, rel, ElfW_Rel) { | |
| 174 | + write32le(p + rel->r_offset, S->plt->sh_addr); | |
| 175 | 175 | } |
| 176 | 176 | } |
| 177 | 177 | } |
| 178 | 178 | #endif |
| 179 | 179 | |
| 180 | −void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 180 | +void relocate(TCCState *S, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 181 | 181 | { |
| 182 | 182 | ElfW(Sym) *sym; |
| 183 | 183 | int sym_index, esym_index; |
| @@ -212,7 +212,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 28 unmodified lines | ||
| 212 | 212 | h = x & 2; |
| 213 | 213 | th_ko = (x & 3) && (!blx_avail || !is_call); |
| 214 | 214 | if (th_ko || x >= 0x2000000 || x < -0x2000000) |
| 215 | − tcc_error("can't relocate value at %x,%d",addr, type); | |
| 215 | + tcc_error(S, "can't relocate value at %x,%d",addr, type); | |
| 216 | 216 | x >>= 2; |
| 217 | 217 | x &= 0xffffff; |
| 218 | 218 | /* Only reached if blx is avail and it is a call */ |
| @@ -255,7 +255,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 36 unmodified lines | ||
| 255 | 255 | |
| 256 | 256 | /* Relocation infos */ |
| 257 | 257 | to_thumb = val & 1; |
| 258 | − plt = s1->plt; | |
| 258 | + plt = S->plt; | |
| 259 | 259 | to_plt = (val >= plt->sh_addr) && |
| 260 | 260 | (val < plt->sh_addr + plt->data_offset); |
| 261 | 261 | is_call = (type == R_ARM_THM_PC22); |
| @@ -267,10 +267,10 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 5 unmodified lines | ||
| 267 | 267 | Section *text; |
| 268 | 268 | |
| 269 | 269 | name = (char *) symtab_section->link->data + sym->st_name; |
| 270 | − text = s1->sections[sym->st_shndx]; | |
| 270 | + text = S->sections[sym->st_shndx]; | |
| 271 | 271 | /* Modify reloc to target a thumb stub to switch to ARM */ |
| 272 | 272 | snprintf(buf, sizeof(buf), "%s_from_thumb", name); |
| 273 | − index = put_elf_sym(symtab_section, | |
| 273 | + index = put_elf_sym(S, symtab_section, | |
| 274 | 274 | text->data_offset + 1, |
| 275 | 275 | sym->st_size, sym->st_info, 0, |
| 276 | 276 | sym->st_shndx, buf); |
| @@ -281,7 +281,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 4 unmodified lines | ||
| 281 | 281 | put_elf_reloc(symtab_section, text, |
| 282 | 282 | text->data_offset + 4, R_ARM_JUMP24, |
| 283 | 283 | sym_index); |
| 284 | − p = section_ptr_add(text, 8); | |
| 284 | + p = section_ptr_add(S, text, 8); | |
| 285 | 285 | write32le(p, 0x4778); /* bx pc */ |
| 286 | 286 | write32le(p+2, 0x46c0); /* nop */ |
| 287 | 287 | write32le(p+4, 0xeafffffe); /* b $sym */ |
| @@ -301,7 +301,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 13 unmodified lines | ||
| 301 | 301 | - instruction must be a call (bl) or a jump to PLT */ |
| 302 | 302 | if (!to_thumb || x >= 0x1000000 || x < -0x1000000) |
| 303 | 303 | if (to_thumb || (val & 2) || (!is_call && !to_plt)) |
| 304 | − tcc_error("can't relocate value at %x,%d",addr, type); | |
| 304 | + tcc_error(S, "can't relocate value at %x,%d",addr, type); | |
| 305 | 305 | |
| 306 | 306 | /* Compute and store final offset */ |
| 307 | 307 | s = (x >> 24) & 1; |
| @@ -372,14 +372,14 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 64 unmodified lines | ||
| 372 | 372 | x = (x * 2) / 2; |
| 373 | 373 | x += val - addr; |
| 374 | 374 | if((x^(x>>1))&0x40000000) |
| 375 | − tcc_error("can't relocate value at %x,%d",addr, type); | |
| 375 | + tcc_error(S, "can't relocate value at %x,%d",addr, type); | |
| 376 | 376 | (*(int *)ptr) |= x & 0x7fffffff; |
| 377 | 377 | } |
| 378 | 378 | return; |
| 379 | 379 | case R_ARM_ABS32: |
| 380 | 380 | case R_ARM_TARGET1: |
| 381 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 382 | − esym_index = get_sym_attr(s1, sym_index, 0)->dyn_index; | |
| 381 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 382 | + esym_index = get_sym_attr(S, sym_index, 0)->dyn_index; | |
| 383 | 383 | qrel->r_offset = rel->r_offset; |
| 384 | 384 | if (esym_index) { |
| 385 | 385 | qrel->r_info = ELFW(R_INFO)(esym_index, R_ARM_ABS32); |
| @@ -396,19 +396,19 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 10 unmodified lines | ||
| 396 | 396 | *(int *)ptr += val - addr; |
| 397 | 397 | return; |
| 398 | 398 | case R_ARM_GOTPC: |
| 399 | − *(int *)ptr += s1->got->sh_addr - addr; | |
| 399 | + *(int *)ptr += S->got->sh_addr - addr; | |
| 400 | 400 | return; |
| 401 | 401 | case R_ARM_GOTOFF: |
| 402 | − *(int *)ptr += val - s1->got->sh_addr; | |
| 402 | + *(int *)ptr += val - S->got->sh_addr; | |
| 403 | 403 | return; |
| 404 | 404 | case R_ARM_GOT32: |
| 405 | 405 | /* we load the got offset */ |
| 406 | − *(int *)ptr += get_sym_attr(s1, sym_index, 0)->got_offset; | |
| 406 | + *(int *)ptr += get_sym_attr(S, sym_index, 0)->got_offset; | |
| 407 | 407 | return; |
| 408 | 408 | case R_ARM_GOT_PREL: |
| 409 | 409 | /* we load the pc relative got offset */ |
| 410 | − *(int *)ptr += s1->got->sh_addr + | |
| 411 | − get_sym_attr(s1, sym_index, 0)->got_offset - | |
| 410 | + *(int *)ptr += S->got->sh_addr + | |
| 411 | + get_sym_attr(S, sym_index, 0)->got_offset - | |
| 412 | 412 | addr; |
| 413 | 413 | return; |
| 414 | 414 | case R_ARM_COPY: |
| @@ -428,7 +428,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 13 unmodified lines | ||
| 428 | 428 | return; |
| 429 | 429 | case R_ARM_RELATIVE: |
| 430 | 430 | #ifdef TCC_TARGET_PE |
| 431 | − add32le(ptr, val - s1->pe_imagebase); | |
| 431 | + add32le(ptr, val - S->pe_imagebase); | |
| 432 | 432 | #endif |
| 433 | 433 | /* do nothing */ |
| 434 | 434 | return; |
| @@ -9,9 +9,9 @@ · 8 unmodified lines | ||
| 9 | 9 | #define CONFIG_TCC_ASM |
| 10 | 10 | #define NB_ASM_REGS 16 |
| 11 | 11 | |
| 12 | −ST_FUNC void g(int c); | |
| 13 | −ST_FUNC void gen_le16(int c); | |
| 14 | −ST_FUNC void gen_le32(int c); | |
| 12 | +ST_FUNC void g(TCCState* S, int c); | |
| 13 | +ST_FUNC void gen_le16(TCCState* S, int c); | |
| 14 | +ST_FUNC void gen_le32(TCCState* S, int c); | |
| 15 | 15 | |
| 16 | 16 | /*************************************************************/ |
| 17 | 17 | #else |
| @@ -25,7 +25,7 @@ static void asm_error(void) · 7 unmodified lines | ||
| 25 | 25 | } |
| 26 | 26 | |
| 27 | 27 | /* XXX: make it faster ? */ |
| 28 | −ST_FUNC void g(int c) | |
| 28 | +ST_FUNC void g(TCCState* S, int c) | |
| 29 | 29 | { |
| 30 | 30 | int ind1; |
| 31 | 31 | if (nocode_wanted) |
| @@ -37,24 +37,24 @@ ST_FUNC void g(int c) · 5 unmodified lines | ||
| 37 | 37 | ind = ind1; |
| 38 | 38 | } |
| 39 | 39 | |
| 40 | −ST_FUNC void gen_le16 (int i) | |
| 40 | +ST_FUNC void gen_le16 (TCCState* S, int i) | |
| 41 | 41 | { |
| 42 | − g(i); | |
| 43 | − g(i>>8); | |
| 42 | + g(S, i); | |
| 43 | + g(S, i>>8); | |
| 44 | 44 | } |
| 45 | 45 | |
| 46 | −ST_FUNC void gen_le32 (int i) | |
| 46 | +ST_FUNC void gen_le32 (TCCState* S, int i) | |
| 47 | 47 | { |
| 48 | − gen_le16(i); | |
| 49 | − gen_le16(i>>16); | |
| 48 | + gen_le16(S, i); | |
| 49 | + gen_le16(S, i>>16); | |
| 50 | 50 | } |
| 51 | 51 | |
| 52 | −ST_FUNC void gen_expr32(ExprValue *pe) | |
| 52 | +ST_FUNC void gen_expr32(TCCState* S, ExprValue *pe) | |
| 53 | 53 | { |
| 54 | − gen_le32(pe->v); | |
| 54 | + gen_le32(S, pe->v); | |
| 55 | 55 | } |
| 56 | 56 | |
| 57 | −ST_FUNC void asm_opcode(TCCState *s1, int opcode) | |
| 57 | +ST_FUNC void asm_opcode(TCCState *S, int opcode) | |
| 58 | 58 | { |
| 59 | 59 | asm_error(); |
| 60 | 60 | } |
| @@ -90,15 +90,9 @@ ST_DATA const int reg_classes[NB_REGS] = { · 89 unmodified lines | ||
| 90 | 90 | RC_FLOAT | RC_F(7) |
| 91 | 91 | }; |
| 92 | 92 | |
| 93 | −#if defined(CONFIG_TCC_BCHECK) | |
| 94 | −static addr_t func_bound_offset; | |
| 95 | −static unsigned long func_bound_ind; | |
| 96 | −ST_DATA int func_bound_add_epilog; | |
| 97 | −#endif | |
| 98 | − | |
| 99 | 93 | #define IS_FREG(x) ((x) >= TREG_F(0)) |
| 100 | 94 | |
| 101 | −static uint32_t intr(int r) | |
| 95 | +static uint32_t intr(TCCState *S, int r) | |
| 102 | 96 | { |
| 103 | 97 | assert(TREG_R(0) <= r && r <= TREG_R30); |
| 104 | 98 | return r < TREG_R30 ? r : 30; |
| @@ -111,15 +105,15 @@ static uint32_t fltr(int r) · 6 unmodified lines | ||
| 111 | 105 | } |
| 112 | 106 | |
| 113 | 107 | // Add an instruction to text section: |
| 114 | −ST_FUNC void o(unsigned int c) | |
| 108 | +ST_FUNC void o(TCCState *S, unsigned int c) | |
| 115 | 109 | { |
| 116 | − int ind1 = ind + 4; | |
| 117 | − if (nocode_wanted) | |
| 110 | + int ind1 = S->tccgen_ind + 4; | |
| 111 | + if (S->tccgen_nocode_wanted) | |
| 118 | 112 | return; |
| 119 | 113 | if (ind1 > cur_text_section->data_allocated) |
| 120 | − section_realloc(cur_text_section, ind1); | |
| 121 | − write32le(cur_text_section->data + ind, c); | |
| 122 | − ind = ind1; | |
| 114 | + section_realloc(S, cur_text_section, ind1); | |
| 115 | + write32le(cur_text_section->data + S->tccgen_ind, c); | |
| 116 | + S->tccgen_ind = ind1; | |
| 123 | 117 | } |
| 124 | 118 | |
| 125 | 119 | static int arm64_encode_bimm64(uint64_t x) |
| @@ -208,11 +202,11 @@ static uint32_t arm64_movi(int r, uint64_t x) · 82 unmodified lines | ||
| 208 | 202 | return 0; |
| 209 | 203 | } |
| 210 | 204 | |
| 211 | −static void arm64_movimm(int r, uint64_t x) | |
| 205 | +static void arm64_movimm(TCCState *S, int r, uint64_t x) | |
| 212 | 206 | { |
| 213 | 207 | uint32_t i; |
| 214 | 208 | if ((i = arm64_movi(r, x))) |
| 215 | − o(i); // a single MOV | |
| 209 | + o(S, i); // a single MOV | |
| 216 | 210 | else { |
| 217 | 211 | // MOVZ/MOVN and 1-3 MOVKs |
| 218 | 212 | int z = 0, m = 0; |
| @@ -228,19 +222,19 @@ static void arm64_movimm(int r, uint64_t x) · 9 unmodified lines | ||
| 228 | 222 | } |
| 229 | 223 | for (i = 0; i < 64; i += 16) |
| 230 | 224 | if (x1 >> i & 0xffff) { |
| 231 | − o(mov1 | r | (x1 >> i & 0xffff) << 5 | i << 17); | |
| 225 | + o(S, mov1 | r | (x1 >> i & 0xffff) << 5 | i << 17); | |
| 232 | 226 | // movz/movn x(r),#(*),lsl #(i) |
| 233 | 227 | break; |
| 234 | 228 | } |
| 235 | 229 | for (i += 16; i < 64; i += 16) |
| 236 | 230 | if (x1 >> i & 0xffff) |
| 237 | − o(0xf2800000 | r | (x >> i & 0xffff) << 5 | i << 17); | |
| 231 | + o(S, 0xf2800000 | r | (x >> i & 0xffff) << 5 | i << 17); | |
| 238 | 232 | // movk x(r),#(*),lsl #(i) |
| 239 | 233 | } |
| 240 | 234 | } |
| 241 | 235 | |
| 242 | 236 | // Patch all branches in list pointed to by t to branch to a: |
| 243 | −ST_FUNC void gsym_addr(int t_, int a_) | |
| 237 | +ST_FUNC void gsym_addr(TCCState *S, int t_, int a_) | |
| 244 | 238 | { |
| 245 | 239 | uint32_t t = t_; |
| 246 | 240 | uint32_t a = a_; |
| @@ -248,7 +242,7 @@ ST_FUNC void gsym_addr(int t_, int a_) · 1 unmodified line | ||
| 248 | 242 | unsigned char *ptr = cur_text_section->data + t; |
| 249 | 243 | uint32_t next = read32le(ptr); |
| 250 | 244 | if (a - t + 0x8000000 >= 0x10000000) |
| 251 | − tcc_error("branch out of range"); | |
| 245 | + tcc_error(S, "branch out of range"); | |
| 252 | 246 | write32le(ptr, (a - t == 4 ? 0xd503201f : // nop |
| 253 | 247 | 0x14000000 | ((a - t) >> 2 & 0x3ffffff))); // b |
| 254 | 248 | t = next; |
| @@ -278,17 +272,17 @@ static int arm64_type_size(int t) · 23 unmodified lines | ||
| 278 | 272 | return 0; |
| 279 | 273 | } |
| 280 | 274 | |
| 281 | −static void arm64_spoff(int reg, uint64_t off) | |
| 275 | +static void arm64_spoff(TCCState *S, int reg, uint64_t off) | |
| 282 | 276 | { |
| 283 | 277 | uint32_t sub = off >> 63; |
| 284 | 278 | if (sub) |
| 285 | 279 | off = -off; |
| 286 | 280 | if (off < 4096) |
| 287 | − o(0x910003e0 | sub << 30 | reg | off << 10); | |
| 281 | + o(S, 0x910003e0 | sub << 30 | reg | off << 10); | |
| 288 | 282 | // (add|sub) x(reg),sp,#(off) |
| 289 | 283 | else { |
| 290 | − arm64_movimm(30, off); // use x30 for offset | |
| 291 | − o(0x8b3e63e0 | sub << 30 | reg); // (add|sub) x(reg),sp,x30 | |
| 284 | + arm64_movimm(S, 30, off); // use x30 for offset | |
| 285 | + o(S, 0x8b3e63e0 | sub << 30 | reg); // (add|sub) x(reg),sp,x30 | |
| 292 | 286 | } |
| 293 | 287 | } |
| 294 | 288 | |
| @@ -309,41 +303,41 @@ static uint64_t arm64_check_offset(int invert, int sz_, uint64_t off) · 14 unmodified lines | ||
| 309 | 303 | return invert ? 0ul : off; |
| 310 | 304 | } |
| 311 | 305 | |
| 312 | −static void arm64_ldrx(int sg, int sz_, int dst, int bas, uint64_t off) | |
| 306 | +static void arm64_ldrx(TCCState *S, int sg, int sz_, int dst, int bas, uint64_t off) | |
| 313 | 307 | { |
| 314 | 308 | uint32_t sz = sz_; |
| 315 | 309 | if (sz >= 2) |
| 316 | 310 | sg = 0; |
| 317 | 311 | if (!(off & ~((uint32_t)0xfff << sz))) |
| 318 | − o(0x39400000 | dst | bas << 5 | off << (10 - sz) | | |
| 312 | + o(S, 0x39400000 | dst | bas << 5 | off << (10 - sz) | | |
| 319 | 313 | (uint32_t)!!sg << 23 | sz << 30); // ldr(*) x(dst),[x(bas),#(off)] |
| 320 | 314 | else if (off < 256 || -off <= 256) |
| 321 | − o(0x38400000 | dst | bas << 5 | (off & 511) << 12 | | |
| 315 | + o(S, 0x38400000 | dst | bas << 5 | (off & 511) << 12 | | |
| 322 | 316 | (uint32_t)!!sg << 23 | sz << 30); // ldur(*) x(dst),[x(bas),#(off)] |
| 323 | 317 | else { |
| 324 | − arm64_movimm(30, off); // use x30 for offset | |
| 325 | − o(0x38206800 | dst | bas << 5 | (uint32_t)30 << 16 | | |
| 318 | + arm64_movimm(S, 30, off); // use x30 for offset | |
| 319 | + o(S, 0x38206800 | dst | bas << 5 | (uint32_t)30 << 16 | | |
| 326 | 320 | (uint32_t)(!!sg + 1) << 22 | sz << 30); // ldr(*) x(dst),[x(bas),x30] |
| 327 | 321 | } |
| 328 | 322 | } |
| 329 | 323 | |
| 330 | −static void arm64_ldrv(int sz_, int dst, int bas, uint64_t off) | |
| 324 | +static void arm64_ldrv(TCCState *S, int sz_, int dst, int bas, uint64_t off) | |
| 331 | 325 | { |
| 332 | 326 | uint32_t sz = sz_; |
| 333 | 327 | if (!(off & ~((uint32_t)0xfff << sz))) |
| 334 | − o(0x3d400000 | dst | bas << 5 | off << (10 - sz) | | |
| 328 | + o(S, 0x3d400000 | dst | bas << 5 | off << (10 - sz) | | |
| 335 | 329 | (sz & 4) << 21 | (sz & 3) << 30); // ldr (s|d|q)(dst),[x(bas),#(off)] |
| 336 | 330 | else if (off < 256 || -off <= 256) |
| 337 | − o(0x3c400000 | dst | bas << 5 | (off & 511) << 12 | | |
| 331 | + o(S, 0x3c400000 | dst | bas << 5 | (off & 511) << 12 | | |
| 338 | 332 | (sz & 4) << 21 | (sz & 3) << 30); // ldur (s|d|q)(dst),[x(bas),#(off)] |
| 339 | 333 | else { |
| 340 | − arm64_movimm(30, off); // use x30 for offset | |
| 341 | − o(0x3c606800 | dst | bas << 5 | (uint32_t)30 << 16 | | |
| 334 | + arm64_movimm(S, 30, off); // use x30 for offset | |
| 335 | + o(S, 0x3c606800 | dst | bas << 5 | (uint32_t)30 << 16 | | |
| 342 | 336 | sz << 30 | (sz & 4) << 21); // ldr (s|d|q)(dst),[x(bas),x30] |
| 343 | 337 | } |
| 344 | 338 | } |
| 345 | 339 | |
| 346 | −static void arm64_ldrs(int reg_, int size) | |
| 340 | +static void arm64_ldrs(TCCState *S, int reg_, int size) | |
| 347 | 341 | { |
| 348 | 342 | uint32_t reg = reg_; |
| 349 | 343 | // Use x30 for intermediate value in some cases. |
| @@ -353,138 +347,138 @@ static void arm64_ldrs(int reg_, int size) · 3 unmodified lines | ||
| 353 | 347 | /* Can happen with zero size structs */ |
| 354 | 348 | break; |
| 355 | 349 | case 1: |
| 356 | − arm64_ldrx(0, 0, reg, reg, 0); | |
| 350 | + arm64_ldrx(S, 0, 0, reg, reg, 0); | |
| 357 | 351 | break; |
| 358 | 352 | case 2: |
| 359 | − arm64_ldrx(0, 1, reg, reg, 0); | |
| 353 | + arm64_ldrx(S, 0, 1, reg, reg, 0); | |
| 360 | 354 | break; |
| 361 | 355 | case 3: |
| 362 | − arm64_ldrx(0, 1, 30, reg, 0); | |
| 363 | − arm64_ldrx(0, 0, reg, reg, 2); | |
| 364 | − o(0x2a0043c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #16 | |
| 356 | + arm64_ldrx(S, 0, 1, 30, reg, 0); | |
| 357 | + arm64_ldrx(S, 0, 0, reg, reg, 2); | |
| 358 | + o(S, 0x2a0043c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #16 | |
| 365 | 359 | break; |
| 366 | 360 | case 4: |
| 367 | − arm64_ldrx(0, 2, reg, reg, 0); | |
| 361 | + arm64_ldrx(S, 0, 2, reg, reg, 0); | |
| 368 | 362 | break; |
| 369 | 363 | case 5: |
| 370 | − arm64_ldrx(0, 2, 30, reg, 0); | |
| 371 | − arm64_ldrx(0, 0, reg, reg, 4); | |
| 372 | − o(0xaa0083c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #32 | |
| 364 | + arm64_ldrx(S, 0, 2, 30, reg, 0); | |
| 365 | + arm64_ldrx(S, 0, 0, reg, reg, 4); | |
| 366 | + o(S, 0xaa0083c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #32 | |
| 373 | 367 | break; |
| 374 | 368 | case 6: |
| 375 | − arm64_ldrx(0, 2, 30, reg, 0); | |
| 376 | − arm64_ldrx(0, 1, reg, reg, 4); | |
| 377 | − o(0xaa0083c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #32 | |
| 369 | + arm64_ldrx(S, 0, 2, 30, reg, 0); | |
| 370 | + arm64_ldrx(S, 0, 1, reg, reg, 4); | |
| 371 | + o(S, 0xaa0083c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #32 | |
| 378 | 372 | break; |
| 379 | 373 | case 7: |
| 380 | − arm64_ldrx(0, 2, 30, reg, 0); | |
| 381 | − arm64_ldrx(0, 2, reg, reg, 3); | |
| 382 | − o(0x53087c00 | reg | reg << 5); // lsr w(reg), w(reg), #8 | |
| 383 | − o(0xaa0083c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #32 | |
| 374 | + arm64_ldrx(S, 0, 2, 30, reg, 0); | |
| 375 | + arm64_ldrx(S, 0, 2, reg, reg, 3); | |
| 376 | + o(S, 0x53087c00 | reg | reg << 5); // lsr w(reg), w(reg), #8 | |
| 377 | + o(S, 0xaa0083c0 | reg | reg << 16); // orr x(reg),x30,x(reg),lsl #32 | |
| 384 | 378 | break; |
| 385 | 379 | case 8: |
| 386 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 380 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 387 | 381 | break; |
| 388 | 382 | case 9: |
| 389 | − arm64_ldrx(0, 0, reg + 1, reg, 8); | |
| 390 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 383 | + arm64_ldrx(S, 0, 0, reg + 1, reg, 8); | |
| 384 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 391 | 385 | break; |
| 392 | 386 | case 10: |
| 393 | − arm64_ldrx(0, 1, reg + 1, reg, 8); | |
| 394 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 387 | + arm64_ldrx(S, 0, 1, reg + 1, reg, 8); | |
| 388 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 395 | 389 | break; |
| 396 | 390 | case 11: |
| 397 | − arm64_ldrx(0, 2, reg + 1, reg, 7); | |
| 398 | − o(0x53087c00 | (reg+1) | (reg+1) << 5); // lsr w(reg+1), w(reg+1), #8 | |
| 399 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 391 | + arm64_ldrx(S, 0, 2, reg + 1, reg, 7); | |
| 392 | + o(S, 0x53087c00 | (reg+1) | (reg+1) << 5); // lsr w(reg+1), w(reg+1), #8 | |
| 393 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 400 | 394 | break; |
| 401 | 395 | case 12: |
| 402 | − arm64_ldrx(0, 2, reg + 1, reg, 8); | |
| 403 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 396 | + arm64_ldrx(S, 0, 2, reg + 1, reg, 8); | |
| 397 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 404 | 398 | break; |
| 405 | 399 | case 13: |
| 406 | − arm64_ldrx(0, 3, reg + 1, reg, 5); | |
| 407 | − o(0xd358fc00 | (reg+1) | (reg+1) << 5); // lsr x(reg+1), x(reg+1), #24 | |
| 408 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 400 | + arm64_ldrx(S, 0, 3, reg + 1, reg, 5); | |
| 401 | + o(S, 0xd358fc00 | (reg+1) | (reg+1) << 5); // lsr x(reg+1), x(reg+1), #24 | |
| 402 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 409 | 403 | break; |
| 410 | 404 | case 14: |
| 411 | − arm64_ldrx(0, 3, reg + 1, reg, 6); | |
| 412 | − o(0xd350fc00 | (reg+1) | (reg+1) << 5); // lsr x(reg+1), x(reg+1), #16 | |
| 413 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 405 | + arm64_ldrx(S, 0, 3, reg + 1, reg, 6); | |
| 406 | + o(S, 0xd350fc00 | (reg+1) | (reg+1) << 5); // lsr x(reg+1), x(reg+1), #16 | |
| 407 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 414 | 408 | break; |
| 415 | 409 | case 15: |
| 416 | − arm64_ldrx(0, 3, reg + 1, reg, 7); | |
| 417 | − o(0xd348fc00 | (reg+1) | (reg+1) << 5); // lsr x(reg+1), x(reg+1), #8 | |
| 418 | − arm64_ldrx(0, 3, reg, reg, 0); | |
| 410 | + arm64_ldrx(S, 0, 3, reg + 1, reg, 7); | |
| 411 | + o(S, 0xd348fc00 | (reg+1) | (reg+1) << 5); // lsr x(reg+1), x(reg+1), #8 | |
| 412 | + arm64_ldrx(S, 0, 3, reg, reg, 0); | |
| 419 | 413 | break; |
| 420 | 414 | case 16: |
| 421 | − o(0xa9400000 | reg | (reg+1) << 10 | reg << 5); | |
| 415 | + o(S, 0xa9400000 | reg | (reg+1) << 10 | reg << 5); | |
| 422 | 416 | // ldp x(reg),x(reg+1),[x(reg)] |
| 423 | 417 | break; |
| 424 | 418 | } |
| 425 | 419 | } |
| 426 | 420 | |
| 427 | −static void arm64_strx(int sz_, int dst, int bas, uint64_t off) | |
| 421 | +static void arm64_strx(TCCState *S, int sz_, int dst, int bas, uint64_t off) | |
| 428 | 422 | { |
| 429 | 423 | uint32_t sz = sz_; |
| 430 | 424 | if (!(off & ~((uint32_t)0xfff << sz))) |
| 431 | − o(0x39000000 | dst | bas << 5 | off << (10 - sz) | sz << 30); | |
| 425 | + o(S, 0x39000000 | dst | bas << 5 | off << (10 - sz) | sz << 30); | |
| 432 | 426 | // str(*) x(dst),[x(bas],#(off)] |
| 433 | 427 | else if (off < 256 || -off <= 256) |
| 434 | − o(0x38000000 | dst | bas << 5 | (off & 511) << 12 | sz << 30); | |
| 428 | + o(S, 0x38000000 | dst | bas << 5 | (off & 511) << 12 | sz << 30); | |
| 435 | 429 | // stur(*) x(dst),[x(bas],#(off)] |
| 436 | 430 | else { |
| 437 | − arm64_movimm(30, off); // use x30 for offset | |
| 438 | − o(0x38206800 | dst | bas << 5 | (uint32_t)30 << 16 | sz << 30); | |
| 431 | + arm64_movimm(S, 30, off); // use x30 for offset | |
| 432 | + o(S, 0x38206800 | dst | bas << 5 | (uint32_t)30 << 16 | sz << 30); | |
| 439 | 433 | // str(*) x(dst),[x(bas),x30] |
| 440 | 434 | } |
| 441 | 435 | } |
| 442 | 436 | |
| 443 | −static void arm64_strv(int sz_, int dst, int bas, uint64_t off) | |
| 437 | +static void arm64_strv(TCCState *S, int sz_, int dst, int bas, uint64_t off) | |
| 444 | 438 | { |
| 445 | 439 | uint32_t sz = sz_; |
| 446 | 440 | if (!(off & ~((uint32_t)0xfff << sz))) |
| 447 | − o(0x3d000000 | dst | bas << 5 | off << (10 - sz) | | |
| 441 | + o(S, 0x3d000000 | dst | bas << 5 | off << (10 - sz) | | |
| 448 | 442 | (sz & 4) << 21 | (sz & 3) << 30); // str (s|d|q)(dst),[x(bas),#(off)] |
| 449 | 443 | else if (off < 256 || -off <= 256) |
| 450 | − o(0x3c000000 | dst | bas << 5 | (off & 511) << 12 | | |
| 444 | + o(S, 0x3c000000 | dst | bas << 5 | (off & 511) << 12 | | |
| 451 | 445 | (sz & 4) << 21 | (sz & 3) << 30); // stur (s|d|q)(dst),[x(bas),#(off)] |
| 452 | 446 | else { |
| 453 | − arm64_movimm(30, off); // use x30 for offset | |
| 454 | − o(0x3c206800 | dst | bas << 5 | (uint32_t)30 << 16 | | |
| 447 | + arm64_movimm(S, 30, off); // use x30 for offset | |
| 448 | + o(S, 0x3c206800 | dst | bas << 5 | (uint32_t)30 << 16 | | |
| 455 | 449 | sz << 30 | (sz & 4) << 21); // str (s|d|q)(dst),[x(bas),x30] |
| 456 | 450 | } |
| 457 | 451 | } |
| 458 | 452 | |
| 459 | −static void arm64_sym(int r, Sym *sym, unsigned long addend) | |
| 453 | +static void arm64_sym(TCCState *S, int r, Sym *sym, unsigned long addend) | |
| 460 | 454 | { |
| 461 | − greloca(cur_text_section, sym, ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 462 | − o(0x90000000 | r); // adrp xr, #sym | |
| 463 | − greloca(cur_text_section, sym, ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 464 | − o(0xf9400000 | r | (r << 5)); // ld xr,[xr, #sym] | |
| 455 | + greloca(S, cur_text_section, sym, S->tccgen_ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 456 | + o(S, 0x90000000 | r); // adrp xr, #sym | |
| 457 | + greloca(S, cur_text_section, sym, S->tccgen_ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 458 | + o(S, 0xf9400000 | r | (r << 5)); // ld xr,[xr, #sym] | |
| 465 | 459 | if (addend) { |
| 466 | 460 | // add xr, xr, #addend |
| 467 | 461 | if (addend & 0xffful) |
| 468 | − o(0x91000000 | r | r << 5 | (addend & 0xfff) << 10); | |
| 462 | + o(S, 0x91000000 | r | r << 5 | (addend & 0xfff) << 10); | |
| 469 | 463 | if (addend > 0xffful) { |
| 470 | 464 | // add xr, xr, #addend, lsl #12 |
| 471 | 465 | if (addend & 0xfff000ul) |
| 472 | − o(0x91400000 | r | r << 5 | ((addend >> 12) & 0xfff) << 10); | |
| 466 | + o(S, 0x91400000 | r | r << 5 | ((addend >> 12) & 0xfff) << 10); | |
| 473 | 467 | if (addend > 0xfffffful) { |
| 474 | 468 | /* very unlikely */ |
| 475 | 469 | int t = r ? 0 : 1; |
| 476 | − o(0xf81f0fe0 | t); /* str xt, [sp, #-16]! */ | |
| 477 | − arm64_movimm(t, addend & ~0xfffffful); // use xt for addent | |
| 478 | − o(0x91000000 | r | (t << 5)); /* add xr, xt, #0 */ | |
| 479 | − o(0xf84107e0 | t); /* ldr xt, [sp], #16 */ | |
| 470 | + o(S, 0xf81f0fe0 | t); /* str xt, [sp, #-16]! */ | |
| 471 | + arm64_movimm(S, t, addend & ~0xfffffful); // use xt for addent | |
| 472 | + o(S, 0x91000000 | r | (t << 5)); /* add xr, xt, #0 */ | |
| 473 | + o(S, 0xf84107e0 | t); /* ldr xt, [sp], #16 */ | |
| 480 | 474 | } |
| 481 | 475 | } |
| 482 | 476 | } |
| 483 | 477 | } |
| 484 | 478 | |
| 485 | −static void arm64_load_cmp(int r, SValue *sv); | |
| 479 | +static void arm64_load_cmp(TCCState *S, int r, SValue *sv); | |
| 486 | 480 | |
| 487 | −ST_FUNC void load(int r, SValue *sv) | |
| 481 | +ST_FUNC void load(TCCState *S, int r, SValue *sv) | |
| 488 | 482 | { |
| 489 | 483 | int svtt = sv->type.t; |
| 490 | 484 | int svr = sv->r & ~VT_BOUNDED; |
| @@ -494,24 +488,24 @@ ST_FUNC void load(int r, SValue *sv) · 3 unmodified lines | ||
| 494 | 488 | |
| 495 | 489 | if (svr == (VT_LOCAL | VT_LVAL)) { |
| 496 | 490 | if (IS_FREG(r)) |
| 497 | − arm64_ldrv(arm64_type_size(svtt), fltr(r), 29, svcul); | |
| 491 | + arm64_ldrv(S, arm64_type_size(svtt), fltr(r), 29, svcul); | |
| 498 | 492 | else |
| 499 | − arm64_ldrx(!(svtt & VT_UNSIGNED), arm64_type_size(svtt), | |
| 500 | − intr(r), 29, svcul); | |
| 493 | + arm64_ldrx(S, !(svtt & VT_UNSIGNED), arm64_type_size(svtt), | |
| 494 | + intr(S, r), 29, svcul); | |
| 501 | 495 | return; |
| 502 | 496 | } |
| 503 | 497 | |
| 504 | 498 | if (svr == (VT_CONST | VT_LVAL)) { |
| 505 | 499 | if (sv->sym) |
| 506 | − arm64_sym(30, sv->sym, // use x30 for address | |
| 500 | + arm64_sym(S, 30, sv->sym, // use x30 for address | |
| 507 | 501 | arm64_check_offset(0, arm64_type_size(svtt), sv->c.i)); |
| 508 | 502 | else |
| 509 | − arm64_movimm (30, sv->c.i); | |
| 503 | + arm64_movimm (S, 30, sv->c.i); | |
| 510 | 504 | if (IS_FREG(r)) |
| 511 | − arm64_ldrv(arm64_type_size(svtt), fltr(r), 30, | |
| 505 | + arm64_ldrv(S, arm64_type_size(svtt), fltr(r), 30, | |
| 512 | 506 | arm64_check_offset(1, arm64_type_size(svtt), sv->c.i)); |
| 513 | 507 | else |
| 514 | − arm64_ldrx(!(svtt&VT_UNSIGNED), arm64_type_size(svtt), intr(r), 30, | |
| 508 | + arm64_ldrx(S, !(svtt&VT_UNSIGNED), arm64_type_size(svtt), intr(S, r), 30, | |
| 515 | 509 | arm64_check_offset(1, arm64_type_size(svtt), sv->c.i)); |
| 516 | 510 | return; |
| 517 | 511 | } |
| @@ -519,34 +513,34 @@ ST_FUNC void load(int r, SValue *sv) · 1 unmodified line | ||
| 519 | 513 | if ((svr & ~VT_VALMASK) == VT_LVAL && svrv < VT_CONST) { |
| 520 | 514 | if ((svtt & VT_BTYPE) != VT_VOID) { |
| 521 | 515 | if (IS_FREG(r)) |
| 522 | − arm64_ldrv(arm64_type_size(svtt), fltr(r), intr(svrv), 0); | |
| 516 | + arm64_ldrv(S, arm64_type_size(svtt), fltr(r), intr(S, svrv), 0); | |
| 523 | 517 | else |
| 524 | − arm64_ldrx(!(svtt & VT_UNSIGNED), arm64_type_size(svtt), | |
| 525 | − intr(r), intr(svrv), 0); | |
| 518 | + arm64_ldrx(S, !(svtt & VT_UNSIGNED), arm64_type_size(svtt), | |
| 519 | + intr(S, r), intr(S, svrv), 0); | |
| 526 | 520 | } |
| 527 | 521 | return; |
| 528 | 522 | } |
| 529 | 523 | |
| 530 | 524 | if (svr == (VT_CONST | VT_LVAL | VT_SYM)) { |
| 531 | − arm64_sym(30, sv->sym, // use x30 for address | |
| 525 | + arm64_sym(S, 30, sv->sym, // use x30 for address | |
| 532 | 526 | arm64_check_offset(0, arm64_type_size(svtt), svcul)); |
| 533 | 527 | if (IS_FREG(r)) |
| 534 | − arm64_ldrv(arm64_type_size(svtt), fltr(r), 30, | |
| 528 | + arm64_ldrv(S, arm64_type_size(svtt), fltr(r), 30, | |
| 535 | 529 | arm64_check_offset(1, arm64_type_size(svtt), svcul)); |
| 536 | 530 | else |
| 537 | − arm64_ldrx(!(svtt&VT_UNSIGNED), arm64_type_size(svtt), intr(r), 30, | |
| 531 | + arm64_ldrx(S, !(svtt&VT_UNSIGNED), arm64_type_size(svtt), intr(S, r), 30, | |
| 538 | 532 | arm64_check_offset(1, arm64_type_size(svtt), svcul)); |
| 539 | 533 | return; |
| 540 | 534 | } |
| 541 | 535 | |
| 542 | 536 | if (svr == (VT_CONST | VT_SYM)) { |
| 543 | − arm64_sym(intr(r), sv->sym, svcul); | |
| 537 | + arm64_sym(S, intr(S, r), sv->sym, svcul); | |
| 544 | 538 | return; |
| 545 | 539 | } |
| 546 | 540 | |
| 547 | 541 | if (svr == VT_CONST) { |
| 548 | 542 | if ((svtt & VT_BTYPE) != VT_VOID) |
| 549 | − arm64_movimm(intr(r), arm64_type_size(svtt) == 3 ? | |
| 543 | + arm64_movimm(S, intr(S, r), arm64_type_size(svtt) == 3 ? | |
| 550 | 544 | sv->c.i : (uint32_t)svcul); |
| 551 | 545 | return; |
| 552 | 546 | } |
| @@ -554,12 +548,12 @@ ST_FUNC void load(int r, SValue *sv) · 1 unmodified line | ||
| 554 | 548 | if (svr < VT_CONST) { |
| 555 | 549 | if (IS_FREG(r) && IS_FREG(svr)) |
| 556 | 550 | if (svtt == VT_LDOUBLE) |
| 557 | − o(0x4ea01c00 | fltr(r) | fltr(svr) << 5); | |
| 551 | + o(S, 0x4ea01c00 | fltr(r) | fltr(svr) << 5); | |
| 558 | 552 | // mov v(r).16b,v(svr).16b |
| 559 | 553 | else |
| 560 | − o(0x1e604000 | fltr(r) | fltr(svr) << 5); // fmov d(r),d(svr) | |
| 554 | + o(S, 0x1e604000 | fltr(r) | fltr(svr) << 5); // fmov d(r),d(svr) | |
| 561 | 555 | else if (!IS_FREG(r) && !IS_FREG(svr)) |
| 562 | − o(0xaa0003e0 | intr(r) | intr(svr) << 16); // mov x(r),x(svr) | |
| 556 | + o(S, 0xaa0003e0 | intr(S, r) | intr(S, svr) << 16); // mov x(r),x(svr) | |
| 563 | 557 | else |
| 564 | 558 | assert(0); |
| 565 | 559 | return; |
| @@ -567,35 +561,35 @@ ST_FUNC void load(int r, SValue *sv) · 1 unmodified line | ||
| 567 | 561 | |
| 568 | 562 | if (svr == VT_LOCAL) { |
| 569 | 563 | if (-svcul < 0x1000) |
| 570 | − o(0xd10003a0 | intr(r) | -svcul << 10); // sub x(r),x29,#... | |
| 564 | + o(S, 0xd10003a0 | intr(S, r) | -svcul << 10); // sub x(r),x29,#... | |
| 571 | 565 | else { |
| 572 | − arm64_movimm(30, -svcul); // use x30 for offset | |
| 573 | − o(0xcb0003a0 | intr(r) | (uint32_t)30 << 16); // sub x(r),x29,x30 | |
| 566 | + arm64_movimm(S, 30, -svcul); // use x30 for offset | |
| 567 | + o(S, 0xcb0003a0 | intr(S, r) | (uint32_t)30 << 16); // sub x(r),x29,x30 | |
| 574 | 568 | } |
| 575 | 569 | return; |
| 576 | 570 | } |
| 577 | 571 | |
| 578 | 572 | if (svr == VT_JMP || svr == VT_JMPI) { |
| 579 | 573 | int t = (svr == VT_JMPI); |
| 580 | − arm64_movimm(intr(r), t); | |
| 581 | − o(0x14000002); // b .+8 | |
| 582 | − gsym(svcul); | |
| 583 | − arm64_movimm(intr(r), t ^ 1); | |
| 574 | + arm64_movimm(S, intr(S, r), t); | |
| 575 | + o(S, 0x14000002); // b .+8 | |
| 576 | + gsym(S, svcul); | |
| 577 | + arm64_movimm(S, intr(S, r), t ^ 1); | |
| 584 | 578 | return; |
| 585 | 579 | } |
| 586 | 580 | |
| 587 | 581 | if (svr == (VT_LLOCAL | VT_LVAL)) { |
| 588 | − arm64_ldrx(0, 3, 30, 29, svcul); // use x30 for offset | |
| 582 | + arm64_ldrx(S, 0, 3, 30, 29, svcul); // use x30 for offset | |
| 589 | 583 | if (IS_FREG(r)) |
| 590 | − arm64_ldrv(arm64_type_size(svtt), fltr(r), 30, 0); | |
| 584 | + arm64_ldrv(S, arm64_type_size(svtt), fltr(r), 30, 0); | |
| 591 | 585 | else |
| 592 | − arm64_ldrx(!(svtt & VT_UNSIGNED), arm64_type_size(svtt), | |
| 593 | − intr(r), 30, 0); | |
| 586 | + arm64_ldrx(S, !(svtt & VT_UNSIGNED), arm64_type_size(svtt), | |
| 587 | + intr(S, r), 30, 0); | |
| 594 | 588 | return; |
| 595 | 589 | } |
| 596 | 590 | |
| 597 | 591 | if (svr == VT_CMP) { |
| 598 | − arm64_load_cmp(r, sv); | |
| 592 | + arm64_load_cmp(S, r, sv); | |
| 599 | 593 | return; |
| 600 | 594 | } |
| 601 | 595 | |
| @@ -603,7 +597,7 @@ ST_FUNC void load(int r, SValue *sv) · 1 unmodified line | ||
| 603 | 597 | assert(0); |
| 604 | 598 | } |
| 605 | 599 | |
| 606 | −ST_FUNC void store(int r, SValue *sv) | |
| 600 | +ST_FUNC void store(TCCState *S, int r, SValue *sv) | |
| 607 | 601 | { |
| 608 | 602 | int svtt = sv->type.t; |
| 609 | 603 | int svr = sv->r & ~VT_BOUNDED; |
| @@ -613,43 +607,43 @@ ST_FUNC void store(int r, SValue *sv) · 3 unmodified lines | ||
| 613 | 607 | |
| 614 | 608 | if (svr == (VT_LOCAL | VT_LVAL)) { |
| 615 | 609 | if (IS_FREG(r)) |
| 616 | − arm64_strv(arm64_type_size(svtt), fltr(r), 29, svcul); | |
| 610 | + arm64_strv(S, arm64_type_size(svtt), fltr(r), 29, svcul); | |
| 617 | 611 | else |
| 618 | − arm64_strx(arm64_type_size(svtt), intr(r), 29, svcul); | |
| 612 | + arm64_strx(S, arm64_type_size(svtt), intr(S, r), 29, svcul); | |
| 619 | 613 | return; |
| 620 | 614 | } |
| 621 | 615 | |
| 622 | 616 | if (svr == (VT_CONST | VT_LVAL)) { |
| 623 | 617 | if (sv->sym) |
| 624 | − arm64_sym(30, sv->sym, // use x30 for address | |
| 618 | + arm64_sym(S, 30, sv->sym, // use x30 for address | |
| 625 | 619 | arm64_check_offset(0, arm64_type_size(svtt), sv->c.i)); |
| 626 | 620 | else |
| 627 | − arm64_movimm (30, sv->c.i); | |
| 621 | + arm64_movimm(S, 30, sv->c.i); | |
| 628 | 622 | if (IS_FREG(r)) |
| 629 | − arm64_strv(arm64_type_size(svtt), fltr(r), 30, | |
| 623 | + arm64_strv(S, arm64_type_size(svtt), fltr(r), 30, | |
| 630 | 624 | arm64_check_offset(1, arm64_type_size(svtt), sv->c.i)); |
| 631 | 625 | else |
| 632 | − arm64_strx(arm64_type_size(svtt), intr(r), 30, | |
| 626 | + arm64_strx(S, arm64_type_size(svtt), intr(S, r), 30, | |
| 633 | 627 | arm64_check_offset(1, arm64_type_size(svtt), sv->c.i)); |
| 634 | 628 | return; |
| 635 | 629 | } |
| 636 | 630 | |
| 637 | 631 | if ((svr & ~VT_VALMASK) == VT_LVAL && svrv < VT_CONST) { |
| 638 | 632 | if (IS_FREG(r)) |
| 639 | − arm64_strv(arm64_type_size(svtt), fltr(r), intr(svrv), 0); | |
| 633 | + arm64_strv(S, arm64_type_size(svtt), fltr(r), intr(S, svrv), 0); | |
| 640 | 634 | else |
| 641 | − arm64_strx(arm64_type_size(svtt), intr(r), intr(svrv), 0); | |
| 635 | + arm64_strx(S, arm64_type_size(svtt), intr(S, r), intr(S, svrv), 0); | |
| 642 | 636 | return; |
| 643 | 637 | } |
| 644 | 638 | |
| 645 | 639 | if (svr == (VT_CONST | VT_LVAL | VT_SYM)) { |
| 646 | − arm64_sym(30, sv->sym, // use x30 for address | |
| 640 | + arm64_sym(S, 30, sv->sym, // use x30 for address | |
| 647 | 641 | arm64_check_offset(0, arm64_type_size(svtt), svcul)); |
| 648 | 642 | if (IS_FREG(r)) |
| 649 | − arm64_strv(arm64_type_size(svtt), fltr(r), 30, | |
| 643 | + arm64_strv(S, arm64_type_size(svtt), fltr(r), 30, | |
| 650 | 644 | arm64_check_offset(1, arm64_type_size(svtt), svcul)); |
| 651 | 645 | else |
| 652 | − arm64_strx(arm64_type_size(svtt), intr(r), 30, | |
| 646 | + arm64_strx(S, arm64_type_size(svtt), intr(S, r), 30, | |
| 653 | 647 | arm64_check_offset(1, arm64_type_size(svtt), svcul)); |
| 654 | 648 | return; |
| 655 | 649 | } |
| @@ -658,82 +652,82 @@ ST_FUNC void store(int r, SValue *sv) · 2 unmodified lines | ||
| 658 | 652 | assert(0); |
| 659 | 653 | } |
| 660 | 654 | |
| 661 | −static void arm64_gen_bl_or_b(int b) | |
| 655 | +static void arm64_gen_bl_or_b(TCCState *S, int b) | |
| 662 | 656 | { |
| 663 | − if ((vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST && (vtop->r & VT_SYM)) { | |
| 664 | − greloca(cur_text_section, vtop->sym, ind, | |
| 657 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST && (S->tccgen_vtop->r & VT_SYM)) { | |
| 658 | + greloca(S, cur_text_section, S->tccgen_vtop->sym, S->tccgen_ind, | |
| 665 | 659 | b ? R_AARCH64_JUMP26 : R_AARCH64_CALL26, 0); |
| 666 | − o(0x14000000 | (uint32_t)!b << 31); // b/bl . | |
| 660 | + o(S, 0x14000000 | (uint32_t)!b << 31); // b/bl . | |
| 667 | 661 | } |
| 668 | 662 | else { |
| 669 | 663 | #ifdef CONFIG_TCC_BCHECK |
| 670 | − vtop->r &= ~VT_MUSTBOUND; | |
| 664 | + S->tccgen_vtop->r &= ~VT_MUSTBOUND; | |
| 671 | 665 | #endif |
| 672 | − o(0xd61f0000 | (uint32_t)!b << 21 | intr(gv(RC_R30)) << 5); // br/blr | |
| 666 | + o(S, 0xd61f0000 | (uint32_t)!b << 21 | intr(S, gv(S, RC_R30)) << 5); // br/blr | |
| 673 | 667 | } |
| 674 | 668 | } |
| 675 | 669 | |
| 676 | 670 | #if defined(CONFIG_TCC_BCHECK) |
| 677 | 671 | |
| 678 | −static void gen_bounds_call(int v) | |
| 672 | +static void gen_bounds_call(TCCState *S, int v) | |
| 679 | 673 | { |
| 680 | − Sym *sym = external_helper_sym(v); | |
| 674 | + Sym *sym = external_helper_sym(S, v); | |
| 681 | 675 | |
| 682 | − greloca(cur_text_section, sym, ind, R_AARCH64_CALL26, 0); | |
| 683 | − o(0x94000000); // bl | |
| 676 | + greloca(S, cur_text_section, sym, S->tccgen_ind, R_AARCH64_CALL26, 0); | |
| 677 | + o(S, 0x94000000); // bl | |
| 684 | 678 | } |
| 685 | 679 | |
| 686 | −static void gen_bounds_prolog(void) | |
| 680 | +static void gen_bounds_prolog(TCCState *S) | |
| 687 | 681 | { |
| 688 | 682 | /* leave some room for bound checking code */ |
| 689 | − func_bound_offset = lbounds_section->data_offset; | |
| 690 | − func_bound_ind = ind; | |
| 691 | − func_bound_add_epilog = 0; | |
| 692 | − o(0xd503201f); /* nop -> mov x0, lbound section pointer */ | |
| 693 | − o(0xd503201f); | |
| 694 | − o(0xd503201f); | |
| 695 | − o(0xd503201f); /* nop -> call __bound_local_new */ | |
| 683 | + S->func_bound_offset = lbounds_section->data_offset; | |
| 684 | + S->func_bound_ind = S->tccgen_ind; | |
| 685 | + S->func_bound_add_epilog = 0; | |
| 686 | + o(S, 0xd503201f); /* nop -> mov x0, lbound section pointer */ | |
| 687 | + o(S, 0xd503201f); | |
| 688 | + o(S, 0xd503201f); | |
| 689 | + o(S, 0xd503201f); /* nop -> call __bound_local_new */ | |
| 696 | 690 | } |
| 697 | 691 | |
| 698 | −static void gen_bounds_epilog(void) | |
| 692 | +static void gen_bounds_epilog(TCCState *S) | |
| 699 | 693 | { |
| 700 | 694 | addr_t saved_ind; |
| 701 | 695 | addr_t *bounds_ptr; |
| 702 | 696 | Sym *sym_data; |
| 703 | − int offset_modified = func_bound_offset != lbounds_section->data_offset; | |
| 697 | + int offset_modified = S->func_bound_offset != lbounds_section->data_offset; | |
| 704 | 698 | |
| 705 | − if (!offset_modified && !func_bound_add_epilog) | |
| 699 | + if (!offset_modified && !S->func_bound_add_epilog) | |
| 706 | 700 | return; |
| 707 | 701 | |
| 708 | 702 | /* add end of table info */ |
| 709 | − bounds_ptr = section_ptr_add(lbounds_section, sizeof(addr_t)); | |
| 703 | + bounds_ptr = section_ptr_add(S, lbounds_section, sizeof(addr_t)); | |
| 710 | 704 | *bounds_ptr = 0; |
| 711 | 705 | |
| 712 | − sym_data = get_sym_ref(&char_pointer_type, lbounds_section, | |
| 713 | − func_bound_offset, lbounds_section->data_offset); | |
| 706 | + sym_data = get_sym_ref(S, &S->tccgen_char_pointer_type, lbounds_section, | |
| 707 | + S->func_bound_offset, lbounds_section->data_offset); | |
| 714 | 708 | |
| 715 | 709 | /* generate bound local allocation */ |
| 716 | 710 | if (offset_modified) { |
| 717 | − saved_ind = ind; | |
| 718 | − ind = func_bound_ind; | |
| 719 | − greloca(cur_text_section, sym_data, ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 720 | − o(0x90000000 | 0); // adrp x0, #sym_data | |
| 721 | − greloca(cur_text_section, sym_data, ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 722 | − o(0xf9400000 | 0 | (0 << 5)); // ld x0,[x0, #sym_data] | |
| 723 | − gen_bounds_call(TOK___bound_local_new); | |
| 724 | − ind = saved_ind; | |
| 711 | + saved_ind = S->tccgen_ind; | |
| 712 | + S->tccgen_ind = S->func_bound_ind; | |
| 713 | + greloca(S, cur_text_section, sym_data, S->tccgen_ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 714 | + o(S, 0x90000000 | 0); // adrp x0, #sym_data | |
| 715 | + greloca(S, cur_text_section, sym_data, S->tccgen_ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 716 | + o(S, 0xf9400000 | 0 | (0 << 5)); // ld x0,[x0, #sym_data] | |
| 717 | + gen_bounds_call(S, TOK___bound_local_new); | |
| 718 | + S->tccgen_ind = saved_ind; | |
| 725 | 719 | } |
| 726 | 720 | |
| 727 | 721 | /* generate bound check local freeing */ |
| 728 | − o(0xf81f0fe0); /* str x0, [sp, #-16]! */ | |
| 729 | − o(0x3c9f0fe0); /* str q0, [sp, #-16]! */ | |
| 730 | − greloca(cur_text_section, sym_data, ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 731 | − o(0x90000000 | 0); // adrp x0, #sym_data | |
| 732 | − greloca(cur_text_section, sym_data, ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 733 | − o(0xf9400000 | 0 | (0 << 5)); // ld x0,[x0, #sym_data] | |
| 734 | − gen_bounds_call(TOK___bound_local_delete); | |
| 735 | − o(0x3cc107e0); /* ldr q0, [sp], #16 */ | |
| 736 | − o(0xf84107e0); /* ldr x0, [sp], #16 */ | |
| 722 | + o(S, 0xf81f0fe0); /* str x0, [sp, #-16]! */ | |
| 723 | + o(S, 0x3c9f0fe0); /* str q0, [sp, #-16]! */ | |
| 724 | + greloca(S, cur_text_section, sym_data, S->tccgen_ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 725 | + o(S, 0x90000000 | 0); // adrp x0, #sym_data | |
| 726 | + greloca(S, cur_text_section, sym_data, S->tccgen_ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 727 | + o(S, 0xf9400000 | 0 | (0 << 5)); // ld x0,[x0, #sym_data] | |
| 728 | + gen_bounds_call(S, TOK___bound_local_delete); | |
| 729 | + o(S, 0x3cc107e0); /* ldr q0, [sp], #16 */ | |
| 730 | + o(S, 0xf84107e0); /* ldr x0, [sp], #16 */ | |
| 737 | 731 | } |
| 738 | 732 | #endif |
| 739 | 733 | |
| @@ -970,7 +964,7 @@ static unsigned long arm64_pcs(int n, CType **type, unsigned long *a) · 230 unmodified lines | ||
| 970 | 964 | return stack; |
| 971 | 965 | } |
| 972 | 966 | |
| 973 | −ST_FUNC void gfunc_call(int nb_args) | |
| 967 | +ST_FUNC void gfunc_call(TCCState *S, int nb_args) | |
| 974 | 968 | { |
| 975 | 969 | CType *return_type; |
| 976 | 970 | CType **t; |
| @@ -979,28 +973,28 @@ ST_FUNC void gfunc_call(int nb_args) · 2 unmodified lines | ||
| 979 | 973 | int i; |
| 980 | 974 | |
| 981 | 975 | #ifdef CONFIG_TCC_BCHECK |
| 982 | − if (tcc_state->do_bounds_check) | |
| 983 | − gbound_args(nb_args); | |
| 976 | + if (S->do_bounds_check) | |
| 977 | + gbound_args(S, nb_args); | |
| 984 | 978 | #endif |
| 985 | 979 | |
| 986 | − return_type = &vtop[-nb_args].type.ref->type; | |
| 980 | + return_type = &S->tccgen_vtop[-nb_args].type.ref->type; | |
| 987 | 981 | if ((return_type->t & VT_BTYPE) == VT_STRUCT) |
| 988 | 982 | --nb_args; |
| 989 | 983 | |
| 990 | − t = tcc_malloc((nb_args + 1) * sizeof(*t)); | |
| 991 | − a = tcc_malloc((nb_args + 1) * sizeof(*a)); | |
| 992 | − a1 = tcc_malloc((nb_args + 1) * sizeof(*a1)); | |
| 984 | + t = tcc_malloc(S, (nb_args + 1) * sizeof(*t)); | |
| 985 | + a = tcc_malloc(S, (nb_args + 1) * sizeof(*a)); | |
| 986 | + a1 = tcc_malloc(S, (nb_args + 1) * sizeof(*a1)); | |
| 993 | 987 | |
| 994 | 988 | t[0] = return_type; |
| 995 | 989 | for (i = 0; i < nb_args; i++) |
| 996 | − t[nb_args - i] = &vtop[-i].type; | |
| 990 | + t[nb_args - i] = &S->tccgen_vtop[-i].type; | |
| 997 | 991 | |
| 998 | 992 | stack = arm64_pcs(nb_args, t, a); |
| 999 | 993 | |
| 1000 | 994 | // Allocate space for structs replaced by pointer: |
| 1001 | 995 | for (i = nb_args; i; i--) |
| 1002 | 996 | if (a[i] & 1) { |
| 1003 | − SValue *arg = &vtop[i - nb_args]; | |
| 997 | + SValue *arg = &S->tccgen_vtop[i - nb_args]; | |
| 1004 | 998 | int align, size = type_size(&arg->type, &align); |
| 1005 | 999 | assert((arg->type.t & VT_BTYPE) == VT_STRUCT); |
| 1006 | 1000 | stack = (stack + align - 1) & -align; |
| @@ -1011,134 +1005,134 @@ ST_FUNC void gfunc_call(int nb_args) · 4 unmodified lines | ||
| 1011 | 1005 | stack = (stack + 15) >> 4 << 4; |
| 1012 | 1006 | |
| 1013 | 1007 | /* fetch cpu flag before generating any code */ |
| 1014 | − if ((vtop->r & VT_VALMASK) == VT_CMP) | |
| 1015 | − gv(RC_INT); | |
| 1008 | + if ((S->tccgen_vtop->r & VT_VALMASK) == VT_CMP) | |
| 1009 | + gv(S, RC_INT); | |
| 1016 | 1010 | |
| 1017 | 1011 | if (stack >= 0x1000000) // 16Mb |
| 1018 | − tcc_error("stack size too big %lu", stack); | |
| 1012 | + tcc_error(S, "stack size too big %lu", stack); | |
| 1019 | 1013 | if (stack & 0xfff) |
| 1020 | − o(0xd10003ff | (stack & 0xfff) << 10); // sub sp,sp,#(n) | |
| 1014 | + o(S, 0xd10003ff | (stack & 0xfff) << 10); // sub sp,sp,#(n) | |
| 1021 | 1015 | if (stack >> 12) |
| 1022 | − o(0xd14003ff | (stack >> 12) << 10); | |
| 1016 | + o(S, 0xd14003ff | (stack >> 12) << 10); | |
| 1023 | 1017 | |
| 1024 | 1018 | // First pass: set all values on stack |
| 1025 | 1019 | for (i = nb_args; i; i--) { |
| 1026 | − vpushv(vtop - nb_args + i); | |
| 1020 | + vpushv(S, S->tccgen_vtop - nb_args + i); | |
| 1027 | 1021 | |
| 1028 | 1022 | if (a[i] & 1) { |
| 1029 | 1023 | // struct replaced by pointer |
| 1030 | − int r = get_reg(RC_INT); | |
| 1031 | − arm64_spoff(intr(r), a1[i]); | |
| 1032 | − vset(&vtop->type, r | VT_LVAL, 0); | |
| 1033 | − vswap(); | |
| 1034 | − vstore(); | |
| 1024 | + int r = get_reg(S, RC_INT); | |
| 1025 | + arm64_spoff(S, intr(S, r), a1[i]); | |
| 1026 | + vset(S, &S->tccgen_vtop->type, r | VT_LVAL, 0); | |
| 1027 | + vswap(S); | |
| 1028 | + vstore(S); | |
| 1035 | 1029 | if (a[i] >= 32) { |
| 1036 | 1030 | // pointer on stack |
| 1037 | − r = get_reg(RC_INT); | |
| 1038 | − arm64_spoff(intr(r), a1[i]); | |
| 1039 | − arm64_strx(3, intr(r), 31, (a[i] - 32) >> 1 << 1); | |
| 1031 | + r = get_reg(S, RC_INT); | |
| 1032 | + arm64_spoff(S, intr(S, r), a1[i]); | |
| 1033 | + arm64_strx(S, 3, intr(S, r), 31, (a[i] - 32) >> 1 << 1); | |
| 1040 | 1034 | } |
| 1041 | 1035 | } |
| 1042 | 1036 | else if (a[i] >= 32) { |
| 1043 | 1037 | // value on stack |
| 1044 | − if ((vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1045 | − int r = get_reg(RC_INT); | |
| 1046 | − arm64_spoff(intr(r), a[i] - 32); | |
| 1047 | − vset(&vtop->type, r | VT_LVAL, 0); | |
| 1048 | − vswap(); | |
| 1049 | − vstore(); | |
| 1038 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1039 | + int r = get_reg(S, RC_INT); | |
| 1040 | + arm64_spoff(S, intr(S, r), a[i] - 32); | |
| 1041 | + vset(S, &S->tccgen_vtop->type, r | VT_LVAL, 0); | |
| 1042 | + vswap(S); | |
| 1043 | + vstore(S); | |
| 1050 | 1044 | } |
| 1051 | − else if (is_float(vtop->type.t)) { | |
| 1052 | − gv(RC_FLOAT); | |
| 1053 | − arm64_strv(arm64_type_size(vtop[0].type.t), | |
| 1054 | − fltr(vtop[0].r), 31, a[i] - 32); | |
| 1045 | + else if (is_float(S->tccgen_vtop->type.t)) { | |
| 1046 | + gv(S, RC_FLOAT); | |
| 1047 | + arm64_strv(S, arm64_type_size(S->tccgen_vtop[0].type.t), | |
| 1048 | + fltr(S->tccgen_vtop[0].r), 31, a[i] - 32); | |
| 1055 | 1049 | } |
| 1056 | 1050 | else { |
| 1057 | − gv(RC_INT); | |
| 1058 | − arm64_strx(arm64_type_size(vtop[0].type.t), | |
| 1059 | − intr(vtop[0].r), 31, a[i] - 32); | |
| 1051 | + gv(S, RC_INT); | |
| 1052 | + arm64_strx(S, arm64_type_size(S->tccgen_vtop[0].type.t), | |
| 1053 | + intr(S, S->tccgen_vtop[0].r), 31, a[i] - 32); | |
| 1060 | 1054 | } |
| 1061 | 1055 | } |
| 1062 | 1056 | |
| 1063 | − --vtop; | |
| 1057 | + --S->tccgen_vtop; | |
| 1064 | 1058 | } |
| 1065 | 1059 | |
| 1066 | 1060 | // Second pass: assign values to registers |
| 1067 | − for (i = nb_args; i; i--, vtop--) { | |
| 1061 | + for (i = nb_args; i; i--, S->tccgen_vtop--) { | |
| 1068 | 1062 | if (a[i] < 16 && !(a[i] & 1)) { |
| 1069 | 1063 | // value in general-purpose registers |
| 1070 | − if ((vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1071 | − int align, size = type_size(&vtop->type, &align); | |
| 1064 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1065 | + int align, size = type_size(&S->tccgen_vtop->type, &align); | |
| 1072 | 1066 | if (size) { |
| 1073 | − vtop->type.t = VT_PTR; | |
| 1074 | − gaddrof(); | |
| 1075 | − gv(RC_R(a[i] / 2)); | |
| 1076 | − arm64_ldrs(a[i] / 2, size); | |
| 1067 | + S->tccgen_vtop->type.t = VT_PTR; | |
| 1068 | + gaddrof(S); | |
| 1069 | + gv(S, RC_R(a[i] / 2)); | |
| 1070 | + arm64_ldrs(S, a[i] / 2, size); | |
| 1077 | 1071 | } |
| 1078 | 1072 | } |
| 1079 | 1073 | else |
| 1080 | − gv(RC_R(a[i] / 2)); | |
| 1074 | + gv(S, RC_R(a[i] / 2)); | |
| 1081 | 1075 | } |
| 1082 | 1076 | else if (a[i] < 16) |
| 1083 | 1077 | // struct replaced by pointer in register |
| 1084 | − arm64_spoff(a[i] / 2, a1[i]); | |
| 1078 | + arm64_spoff(S, a[i] / 2, a1[i]); | |
| 1085 | 1079 | else if (a[i] < 32) { |
| 1086 | 1080 | // value in floating-point registers |
| 1087 | − if ((vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1088 | − uint32_t j, sz, n = arm64_hfa(&vtop->type, &sz); | |
| 1089 | − vtop->type.t = VT_PTR; | |
| 1090 | − gaddrof(); | |
| 1091 | − gv(RC_R30); | |
| 1081 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1082 | + uint32_t j, sz, n = arm64_hfa(&S->tccgen_vtop->type, &sz); | |
| 1083 | + S->tccgen_vtop->type.t = VT_PTR; | |
| 1084 | + gaddrof(S); | |
| 1085 | + gv(S, RC_R30); | |
| 1092 | 1086 | for (j = 0; j < n; j++) |
| 1093 | − o(0x3d4003c0 | | |
| 1087 | + o(S, 0x3d4003c0 | | |
| 1094 | 1088 | (sz & 16) << 19 | -(sz & 8) << 27 | (sz & 4) << 29 | |
| 1095 | 1089 | (a[i] / 2 - 8 + j) | |
| 1096 | 1090 | j << 10); // ldr ([sdq])(*),[x30,#(j * sz)] |
| 1097 | 1091 | } |
| 1098 | 1092 | else |
| 1099 | − gv(RC_F(a[i] / 2 - 8)); | |
| 1093 | + gv(S, RC_F(a[i] / 2 - 8)); | |
| 1100 | 1094 | } |
| 1101 | 1095 | } |
| 1102 | 1096 | |
| 1103 | 1097 | if ((return_type->t & VT_BTYPE) == VT_STRUCT) { |
| 1104 | 1098 | if (a[0] == 1) { |
| 1105 | 1099 | // indirect return: set x8 and discard the stack value |
| 1106 | − gv(RC_R(8)); | |
| 1107 | − --vtop; | |
| 1100 | + gv(S, RC_R(8)); | |
| 1101 | + --S->tccgen_vtop; | |
| 1108 | 1102 | } |
| 1109 | 1103 | else |
| 1110 | 1104 | // return in registers: keep the address for after the call |
| 1111 | − vswap(); | |
| 1105 | + vswap(S); | |
| 1112 | 1106 | } |
| 1113 | 1107 | |
| 1114 | − save_regs(0); | |
| 1115 | − arm64_gen_bl_or_b(0); | |
| 1116 | − --vtop; | |
| 1108 | + save_regs(S, 0); | |
| 1109 | + arm64_gen_bl_or_b(S, 0); | |
| 1110 | + --S->tccgen_vtop; | |
| 1117 | 1111 | if (stack & 0xfff) |
| 1118 | − o(0x910003ff | (stack & 0xfff) << 10); // add sp,sp,#(n) | |
| 1112 | + o(S, 0x910003ff | (stack & 0xfff) << 10); // add sp,sp,#(n) | |
| 1119 | 1113 | if (stack >> 12) |
| 1120 | − o(0x914003ff | (stack >> 12) << 10); | |
| 1114 | + o(S, 0x914003ff | (stack >> 12) << 10); | |
| 1121 | 1115 | |
| 1122 | 1116 | { |
| 1123 | 1117 | int rt = return_type->t; |
| 1124 | 1118 | int bt = rt & VT_BTYPE; |
| 1125 | 1119 | if (bt == VT_STRUCT && !(a[0] & 1)) { |
| 1126 | 1120 | // A struct was returned in registers, so write it out: |
| 1127 | − gv(RC_R(8)); | |
| 1128 | − --vtop; | |
| 1121 | + gv(S, RC_R(8)); | |
| 1122 | + --S->tccgen_vtop; | |
| 1129 | 1123 | if (a[0] == 0) { |
| 1130 | 1124 | int align, size = type_size(return_type, &align); |
| 1131 | 1125 | assert(size <= 16); |
| 1132 | 1126 | if (size > 8) |
| 1133 | − o(0xa9000500); // stp x0,x1,[x8] | |
| 1127 | + o(S, 0xa9000500); // stp x0,x1,[x8] | |
| 1134 | 1128 | else if (size) |
| 1135 | − arm64_strx(size > 4 ? 3 : size > 2 ? 2 : size > 1, 0, 8, 0); | |
| 1129 | + arm64_strx(S, size > 4 ? 3 : size > 2 ? 2 : size > 1, 0, 8, 0); | |
| 1136 | 1130 | |
| 1137 | 1131 | } |
| 1138 | 1132 | else if (a[0] == 16) { |
| 1139 | 1133 | uint32_t j, sz, n = arm64_hfa(return_type, &sz); |
| 1140 | 1134 | for (j = 0; j < n; j++) |
| 1141 | − o(0x3d000100 | | |
| 1135 | + o(S, 0x3d000100 | | |
| 1142 | 1136 | (sz & 16) << 19 | -(sz & 8) << 27 | (sz & 4) << 29 | |
| 1143 | 1137 | (a[i] / 2 - 8 + j) | |
| 1144 | 1138 | j << 10); // str ([sdq])(*),[x8,#(j * sz)] |
| @@ -1146,9 +1140,9 @@ ST_FUNC void gfunc_call(int nb_args) · 1 unmodified line | ||
| 1146 | 1140 | } |
| 1147 | 1141 | } |
| 1148 | 1142 | |
| 1149 | − tcc_free(a1); | |
| 1150 | − tcc_free(a); | |
| 1151 | − tcc_free(t); | |
| 1143 | + tcc_free(S, a1); | |
| 1144 | + tcc_free(S, a); | |
| 1145 | + tcc_free(S, t); | |
| 1152 | 1146 | } |
| 1153 | 1147 | |
| 1154 | 1148 | static unsigned long arm64_func_va_list_stack; |
| @@ -1156,7 +1150,7 @@ static int arm64_func_va_list_gr_offs; · 1 unmodified line | ||
| 1156 | 1150 | static int arm64_func_va_list_vr_offs; |
| 1157 | 1151 | static int arm64_func_sub_sp_offset; |
| 1158 | 1152 | |
| 1159 | −ST_FUNC void gfunc_prolog(Sym *func_sym) | |
| 1153 | +ST_FUNC void gfunc_prolog(TCCState *S, Sym *func_sym) | |
| 1160 | 1154 | { |
| 1161 | 1155 | CType *func_type = &func_sym->type; |
| 1162 | 1156 | int n = 0; |
| @@ -1165,28 +1159,28 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 2 unmodified lines | ||
| 1165 | 1159 | CType **t; |
| 1166 | 1160 | unsigned long *a; |
| 1167 | 1161 | |
| 1168 | − func_vc = 144; // offset of where x8 is stored | |
| 1162 | + S->tccgen_func_vc = 144; // offset of where x8 is stored | |
| 1169 | 1163 | |
| 1170 | 1164 | for (sym = func_type->ref; sym; sym = sym->next) |
| 1171 | 1165 | ++n; |
| 1172 | − t = n ? tcc_malloc(n * sizeof(*t)) : NULL; | |
| 1173 | − a = n ? tcc_malloc(n * sizeof(*a)) : NULL; | |
| 1166 | + t = n ? tcc_malloc(S, n * sizeof(*t)) : NULL; | |
| 1167 | + a = n ? tcc_malloc(S, n * sizeof(*a)) : NULL; | |
| 1174 | 1168 | |
| 1175 | 1169 | for (sym = func_type->ref; sym; sym = sym->next) |
| 1176 | 1170 | t[i++] = &sym->type; |
| 1177 | 1171 | |
| 1178 | 1172 | arm64_func_va_list_stack = arm64_pcs(n - 1, t, a); |
| 1179 | 1173 | |
| 1180 | − o(0xa9b27bfd); // stp x29,x30,[sp,#-224]! | |
| 1181 | − o(0xad0087e0); // stp q0,q1,[sp,#16] | |
| 1182 | − o(0xad018fe2); // stp q2,q3,[sp,#48] | |
| 1183 | − o(0xad0297e4); // stp q4,q5,[sp,#80] | |
| 1184 | − o(0xad039fe6); // stp q6,q7,[sp,#112] | |
| 1185 | − o(0xa90923e8); // stp x8,x8,[sp,#144] | |
| 1186 | − o(0xa90a07e0); // stp x0,x1,[sp,#160] | |
| 1187 | − o(0xa90b0fe2); // stp x2,x3,[sp,#176] | |
| 1188 | − o(0xa90c17e4); // stp x4,x5,[sp,#192] | |
| 1189 | − o(0xa90d1fe6); // stp x6,x7,[sp,#208] | |
| 1174 | + o(S, 0xa9b27bfd); // stp x29,x30,[sp,#-224]! | |
| 1175 | + o(S, 0xad0087e0); // stp q0,q1,[sp,#16] | |
| 1176 | + o(S, 0xad018fe2); // stp q2,q3,[sp,#48] | |
| 1177 | + o(S, 0xad0297e4); // stp q4,q5,[sp,#80] | |
| 1178 | + o(S, 0xad039fe6); // stp q6,q7,[sp,#112] | |
| 1179 | + o(S, 0xa90923e8); // stp x8,x8,[sp,#144] | |
| 1180 | + o(S, 0xa90a07e0); // stp x0,x1,[sp,#160] | |
| 1181 | + o(S, 0xa90b0fe2); // stp x2,x3,[sp,#176] | |
| 1182 | + o(S, 0xa90c17e4); // stp x4,x5,[sp,#192] | |
| 1183 | + o(S, 0xa90d1fe6); // stp x6,x7,[sp,#208] | |
| 1190 | 1184 | |
| 1191 | 1185 | arm64_func_va_list_gr_offs = -64; |
| 1192 | 1186 | arm64_func_va_list_vr_offs = -128; |
| @@ -1195,7 +1189,7 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 2 unmodified lines | ||
| 1195 | 1189 | int off = (a[i] < 16 ? 160 + a[i] / 2 * 8 : |
| 1196 | 1190 | a[i] < 32 ? 16 + (a[i] - 16) / 2 * 16 : |
| 1197 | 1191 | 224 + ((a[i] - 32) >> 1 << 1)); |
| 1198 | − sym_push(sym->v & ~SYM_FIELD, &sym->type, | |
| 1192 | + sym_push(S, sym->v & ~SYM_FIELD, &sym->type, | |
| 1199 | 1193 | (a[i] & 1 ? VT_LLOCAL : VT_LOCAL) | VT_LVAL, |
| 1200 | 1194 | off); |
| 1201 | 1195 | |
| @@ -1215,65 +1209,65 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 13 unmodified lines | ||
| 1215 | 1209 | uint32_t j, sz, k = arm64_hfa(&sym->type, &sz); |
| 1216 | 1210 | if (sz < 16) |
| 1217 | 1211 | for (j = 0; j < k; j++) { |
| 1218 | − o(0x3d0003e0 | -(sz & 8) << 27 | (sz & 4) << 29 | | |
| 1212 | + o(S, 0x3d0003e0 | -(sz & 8) << 27 | (sz & 4) << 29 | | |
| 1219 | 1213 | ((a[i] - 16) / 2 + j) | (off / sz + j) << 10); |
| 1220 | 1214 | // str ([sdq])(*),[sp,#(j * sz)] |
| 1221 | 1215 | } |
| 1222 | 1216 | } |
| 1223 | 1217 | } |
| 1224 | 1218 | |
| 1225 | − tcc_free(a); | |
| 1226 | − tcc_free(t); | |
| 1219 | + tcc_free(S, a); | |
| 1220 | + tcc_free(S, t); | |
| 1227 | 1221 | |
| 1228 | − o(0x910003fd); // mov x29,sp | |
| 1229 | − arm64_func_sub_sp_offset = ind; | |
| 1222 | + o(S, 0x910003fd); // mov x29,sp | |
| 1223 | + arm64_func_sub_sp_offset = S->tccgen_ind; | |
| 1230 | 1224 | // In gfunc_epilog these will be replaced with code to decrement SP: |
| 1231 | − o(0xd503201f); // nop | |
| 1232 | − o(0xd503201f); // nop | |
| 1233 | − loc = 0; | |
| 1225 | + o(S, 0xd503201f); // nop | |
| 1226 | + o(S, 0xd503201f); // nop | |
| 1227 | + S->tccgen_loc = 0; | |
| 1234 | 1228 | #ifdef CONFIG_TCC_BCHECK |
| 1235 | − if (tcc_state->do_bounds_check) | |
| 1236 | − gen_bounds_prolog(); | |
| 1229 | + if (S->do_bounds_check) | |
| 1230 | + gen_bounds_prolog(S); | |
| 1237 | 1231 | #endif |
| 1238 | 1232 | } |
| 1239 | 1233 | |
| 1240 | −ST_FUNC void gen_va_start(void) | |
| 1234 | +ST_FUNC void gen_va_start(TCCState *S) | |
| 1241 | 1235 | { |
| 1242 | 1236 | int r; |
| 1243 | − --vtop; // we don't need the "arg" | |
| 1244 | − gaddrof(); | |
| 1245 | − r = intr(gv(RC_INT)); | |
| 1237 | + --S->tccgen_vtop; // we don't need the "arg" | |
| 1238 | + gaddrof(S); | |
| 1239 | + r = intr(S, gv(S, RC_INT)); | |
| 1246 | 1240 | |
| 1247 | 1241 | if (arm64_func_va_list_stack) { |
| 1248 | 1242 | //xx could use add (immediate) here |
| 1249 | − arm64_movimm(30, arm64_func_va_list_stack + 224); | |
| 1250 | − o(0x8b1e03be); // add x30,x29,x30 | |
| 1243 | + arm64_movimm(S, 30, arm64_func_va_list_stack + 224); | |
| 1244 | + o(S, 0x8b1e03be); // add x30,x29,x30 | |
| 1251 | 1245 | } |
| 1252 | 1246 | else |
| 1253 | − o(0x910383be); // add x30,x29,#224 | |
| 1254 | − o(0xf900001e | r << 5); // str x30,[x(r)] | |
| 1247 | + o(S, 0x910383be); // add x30,x29,#224 | |
| 1248 | + o(S, 0xf900001e | r << 5); // str x30,[x(r)] | |
| 1255 | 1249 | |
| 1256 | 1250 | if (arm64_func_va_list_gr_offs) { |
| 1257 | 1251 | if (arm64_func_va_list_stack) |
| 1258 | − o(0x910383be); // add x30,x29,#224 | |
| 1259 | − o(0xf900041e | r << 5); // str x30,[x(r),#8] | |
| 1252 | + o(S, 0x910383be); // add x30,x29,#224 | |
| 1253 | + o(S, 0xf900041e | r << 5); // str x30,[x(r),#8] | |
| 1260 | 1254 | } |
| 1261 | 1255 | |
| 1262 | 1256 | if (arm64_func_va_list_vr_offs) { |
| 1263 | − o(0x910243be); // add x30,x29,#144 | |
| 1264 | − o(0xf900081e | r << 5); // str x30,[x(r),#16] | |
| 1257 | + o(S, 0x910243be); // add x30,x29,#144 | |
| 1258 | + o(S, 0xf900081e | r << 5); // str x30,[x(r),#16] | |
| 1265 | 1259 | } |
| 1266 | 1260 | |
| 1267 | − arm64_movimm(30, arm64_func_va_list_gr_offs); | |
| 1268 | − o(0xb900181e | r << 5); // str w30,[x(r),#24] | |
| 1261 | + arm64_movimm(S, 30, arm64_func_va_list_gr_offs); | |
| 1262 | + o(S, 0xb900181e | r << 5); // str w30,[x(r),#24] | |
| 1269 | 1263 | |
| 1270 | − arm64_movimm(30, arm64_func_va_list_vr_offs); | |
| 1271 | − o(0xb9001c1e | r << 5); // str w30,[x(r),#28] | |
| 1264 | + arm64_movimm(S, 30, arm64_func_va_list_vr_offs); | |
| 1265 | + o(S, 0xb9001c1e | r << 5); // str w30,[x(r),#28] | |
| 1272 | 1266 | |
| 1273 | − --vtop; | |
| 1267 | + --S->tccgen_vtop; | |
| 1274 | 1268 | } |
| 1275 | 1269 | |
| 1276 | −ST_FUNC void gen_va_arg(CType *t) | |
| 1270 | +ST_FUNC void gen_va_arg(TCCState *S, CType *t) | |
| 1277 | 1271 | { |
| 1278 | 1272 | int align, size = type_size(t, &align); |
| 1279 | 1273 | unsigned fsize, hfa = arm64_hfa(t, &fsize); |
| @@ -1284,69 +1278,69 @@ ST_FUNC void gen_va_arg(CType *t) · 4 unmodified lines | ||
| 1284 | 1278 | fsize = size; |
| 1285 | 1279 | } |
| 1286 | 1280 | |
| 1287 | − gaddrof(); | |
| 1288 | − r0 = intr(gv(RC_INT)); | |
| 1289 | − r1 = get_reg(RC_INT); | |
| 1290 | − vtop[0].r = r1 | VT_LVAL; | |
| 1291 | − r1 = intr(r1); | |
| 1281 | + gaddrof(S); | |
| 1282 | + r0 = intr(S, gv(S, RC_INT)); | |
| 1283 | + r1 = get_reg(S, RC_INT); | |
| 1284 | + S->tccgen_vtop[0].r = r1 | VT_LVAL; | |
| 1285 | + r1 = intr(S, r1); | |
| 1292 | 1286 | |
| 1293 | 1287 | if (!hfa) { |
| 1294 | 1288 | uint32_t n = size > 16 ? 8 : (size + 7) & -8; |
| 1295 | − o(0xb940181e | r0 << 5); // ldr w30,[x(r0),#24] // __gr_offs | |
| 1289 | + o(S, 0xb940181e | r0 << 5); // ldr w30,[x(r0),#24] // __gr_offs | |
| 1296 | 1290 | if (align == 16) { |
| 1297 | 1291 | assert(0); // this path untested but needed for __uint128_t |
| 1298 | − o(0x11003fde); // add w30,w30,#15 | |
| 1299 | − o(0x121c6fde); // and w30,w30,#-16 | |
| 1292 | + o(S, 0x11003fde); // add w30,w30,#15 | |
| 1293 | + o(S, 0x121c6fde); // and w30,w30,#-16 | |
| 1300 | 1294 | } |
| 1301 | − o(0x310003c0 | r1 | n << 10); // adds w(r1),w30,#(n) | |
| 1302 | − o(0x540000ad); // b.le .+20 | |
| 1303 | − o(0xf9400000 | r1 | r0 << 5); // ldr x(r1),[x(r0)] // __stack | |
| 1304 | − o(0x9100001e | r1 << 5 | n << 10); // add x30,x(r1),#(n) | |
| 1305 | − o(0xf900001e | r0 << 5); // str x30,[x(r0)] // __stack | |
| 1306 | − o(0x14000004); // b .+16 | |
| 1307 | − o(0xb9001800 | r1 | r0 << 5); // str w(r1),[x(r0),#24] // __gr_offs | |
| 1308 | − o(0xf9400400 | r1 | r0 << 5); // ldr x(r1),[x(r0),#8] // __gr_top | |
| 1309 | − o(0x8b3ec000 | r1 | r1 << 5); // add x(r1),x(r1),w30,sxtw | |
| 1295 | + o(S, 0x310003c0 | r1 | n << 10); // adds w(r1),w30,#(n) | |
| 1296 | + o(S, 0x540000ad); // b.le .+20 | |
| 1297 | + o(S, 0xf9400000 | r1 | r0 << 5); // ldr x(r1),[x(r0)] // __stack | |
| 1298 | + o(S, 0x9100001e | r1 << 5 | n << 10); // add x30,x(r1),#(n) | |
| 1299 | + o(S, 0xf900001e | r0 << 5); // str x30,[x(r0)] // __stack | |
| 1300 | + o(S, 0x14000004); // b .+16 | |
| 1301 | + o(S, 0xb9001800 | r1 | r0 << 5); // str w(r1),[x(r0),#24] // __gr_offs | |
| 1302 | + o(S, 0xf9400400 | r1 | r0 << 5); // ldr x(r1),[x(r0),#8] // __gr_top | |
| 1303 | + o(S, 0x8b3ec000 | r1 | r1 << 5); // add x(r1),x(r1),w30,sxtw | |
| 1310 | 1304 | if (size > 16) |
| 1311 | − o(0xf9400000 | r1 | r1 << 5); // ldr x(r1),[x(r1)] | |
| 1305 | + o(S, 0xf9400000 | r1 | r1 << 5); // ldr x(r1),[x(r1)] | |
| 1312 | 1306 | } |
| 1313 | 1307 | else { |
| 1314 | 1308 | uint32_t rsz = hfa << 4; |
| 1315 | 1309 | uint32_t ssz = (size + 7) & -(uint32_t)8; |
| 1316 | 1310 | uint32_t b1, b2; |
| 1317 | − o(0xb9401c1e | r0 << 5); // ldr w30,[x(r0),#28] // __vr_offs | |
| 1318 | − o(0x310003c0 | r1 | rsz << 10); // adds w(r1),w30,#(rsz) | |
| 1319 | − b1 = ind; o(0x5400000d); // b.le lab1 | |
| 1320 | − o(0xf9400000 | r1 | r0 << 5); // ldr x(r1),[x(r0)] // __stack | |
| 1311 | + o(S, 0xb9401c1e | r0 << 5); // ldr w30,[x(r0),#28] // __vr_offs | |
| 1312 | + o(S, 0x310003c0 | r1 | rsz << 10); // adds w(r1),w30,#(rsz) | |
| 1313 | + b1 = S->tccgen_ind; o(S, 0x5400000d); // b.le lab1 | |
| 1314 | + o(S, 0xf9400000 | r1 | r0 << 5); // ldr x(r1),[x(r0)] // __stack | |
| 1321 | 1315 | if (fsize == 16) { |
| 1322 | − o(0x91003c00 | r1 | r1 << 5); // add x(r1),x(r1),#15 | |
| 1323 | − o(0x927cec00 | r1 | r1 << 5); // and x(r1),x(r1),#-16 | |
| 1316 | + o(S, 0x91003c00 | r1 | r1 << 5); // add x(r1),x(r1),#15 | |
| 1317 | + o(S, 0x927cec00 | r1 | r1 << 5); // and x(r1),x(r1),#-16 | |
| 1324 | 1318 | } |
| 1325 | − o(0x9100001e | r1 << 5 | ssz << 10); // add x30,x(r1),#(ssz) | |
| 1326 | − o(0xf900001e | r0 << 5); // str x30,[x(r0)] // __stack | |
| 1327 | − b2 = ind; o(0x14000000); // b lab2 | |
| 1319 | + o(S, 0x9100001e | r1 << 5 | ssz << 10); // add x30,x(r1),#(ssz) | |
| 1320 | + o(S, 0xf900001e | r0 << 5); // str x30,[x(r0)] // __stack | |
| 1321 | + b2 = S->tccgen_ind; o(S, 0x14000000); // b lab2 | |
| 1328 | 1322 | // lab1: |
| 1329 | − write32le(cur_text_section->data + b1, 0x5400000d | (ind - b1) << 3); | |
| 1330 | − o(0xb9001c00 | r1 | r0 << 5); // str w(r1),[x(r0),#28] // __vr_offs | |
| 1331 | − o(0xf9400800 | r1 | r0 << 5); // ldr x(r1),[x(r0),#16] // __vr_top | |
| 1323 | + write32le(cur_text_section->data + b1, 0x5400000d | (S->tccgen_ind - b1) << 3); | |
| 1324 | + o(S, 0xb9001c00 | r1 | r0 << 5); // str w(r1),[x(r0),#28] // __vr_offs | |
| 1325 | + o(S, 0xf9400800 | r1 | r0 << 5); // ldr x(r1),[x(r0),#16] // __vr_top | |
| 1332 | 1326 | if (hfa == 1 || fsize == 16) |
| 1333 | − o(0x8b3ec000 | r1 | r1 << 5); // add x(r1),x(r1),w30,sxtw | |
| 1327 | + o(S, 0x8b3ec000 | r1 | r1 << 5); // add x(r1),x(r1),w30,sxtw | |
| 1334 | 1328 | else { |
| 1335 | 1329 | // We need to change the layout of this HFA. |
| 1336 | 1330 | // Get some space on the stack using global variable "loc": |
| 1337 | − loc = (loc - size) & -(uint32_t)align; | |
| 1338 | − o(0x8b3ec000 | 30 | r1 << 5); // add x30,x(r1),w30,sxtw | |
| 1339 | − arm64_movimm(r1, loc); | |
| 1340 | − o(0x8b0003a0 | r1 | r1 << 16); // add x(r1),x29,x(r1) | |
| 1341 | − o(0x4c402bdc | (uint32_t)fsize << 7 | | |
| 1331 | + S->tccgen_loc = (S->tccgen_loc - size) & -(uint32_t)align; | |
| 1332 | + o(S, 0x8b3ec000 | 30 | r1 << 5); // add x30,x(r1),w30,sxtw | |
| 1333 | + arm64_movimm(S, r1, S->tccgen_loc); | |
| 1334 | + o(S, 0x8b0003a0 | r1 | r1 << 16); // add x(r1),x29,x(r1) | |
| 1335 | + o(S, 0x4c402bdc | (uint32_t)fsize << 7 | | |
| 1342 | 1336 | (uint32_t)(hfa == 2) << 15 | |
| 1343 | 1337 | (uint32_t)(hfa == 3) << 14); // ld1 {v28.(4s|2d),...},[x30] |
| 1344 | − o(0x0d00801c | r1 << 5 | (fsize == 8) << 10 | | |
| 1338 | + o(S, 0x0d00801c | r1 << 5 | (fsize == 8) << 10 | | |
| 1345 | 1339 | (uint32_t)(hfa != 2) << 13 | |
| 1346 | 1340 | (uint32_t)(hfa != 3) << 21); // st(hfa) {v28.(s|d),...}[0],[x(r1)] |
| 1347 | 1341 | } |
| 1348 | 1342 | // lab2: |
| 1349 | − write32le(cur_text_section->data + b2, 0x14000000 | (ind - b2) >> 2); | |
| 1343 | + write32le(cur_text_section->data + b2, 0x14000000 | (S->tccgen_ind - b2) >> 2); | |
| 1350 | 1344 | } |
| 1351 | 1345 | } |
| 1352 | 1346 | |
| @@ -1356,7 +1350,7 @@ ST_FUNC int gfunc_sret(CType *vt, int variadic, CType *ret, · 3 unmodified lines | ||
| 1356 | 1350 | return 0; |
| 1357 | 1351 | } |
| 1358 | 1352 | |
| 1359 | −ST_FUNC void gfunc_return(CType *func_type) | |
| 1353 | +ST_FUNC void gfunc_return(TCCState *S, CType *func_type) | |
| 1360 | 1354 | { |
| 1361 | 1355 | CType *t = func_type; |
| 1362 | 1356 | unsigned long a; |
| @@ -1368,52 +1362,52 @@ ST_FUNC void gfunc_return(CType *func_type) · 5 unmodified lines | ||
| 1368 | 1362 | case 0: |
| 1369 | 1363 | if ((func_type->t & VT_BTYPE) == VT_STRUCT) { |
| 1370 | 1364 | int align, size = type_size(func_type, &align); |
| 1371 | − gaddrof(); | |
| 1372 | − gv(RC_R(0)); | |
| 1373 | − arm64_ldrs(0, size); | |
| 1365 | + gaddrof(S); | |
| 1366 | + gv(S, RC_R(0)); | |
| 1367 | + arm64_ldrs(S, 0, size); | |
| 1374 | 1368 | } |
| 1375 | 1369 | else |
| 1376 | − gv(RC_IRET); | |
| 1370 | + gv(S, RC_IRET); | |
| 1377 | 1371 | break; |
| 1378 | 1372 | case 1: { |
| 1379 | 1373 | CType type = *func_type; |
| 1380 | − mk_pointer(&type); | |
| 1381 | − vset(&type, VT_LOCAL | VT_LVAL, func_vc); | |
| 1382 | − indir(); | |
| 1383 | − vswap(); | |
| 1384 | − vstore(); | |
| 1374 | + mk_pointer(S, &type); | |
| 1375 | + vset(S, &type, VT_LOCAL | VT_LVAL, S->tccgen_func_vc); | |
| 1376 | + indir(S); | |
| 1377 | + vswap(S); | |
| 1378 | + vstore(S); | |
| 1385 | 1379 | break; |
| 1386 | 1380 | } |
| 1387 | 1381 | case 16: |
| 1388 | 1382 | if ((func_type->t & VT_BTYPE) == VT_STRUCT) { |
| 1389 | − uint32_t j, sz, n = arm64_hfa(&vtop->type, &sz); | |
| 1390 | − gaddrof(); | |
| 1391 | − gv(RC_R(0)); | |
| 1383 | + uint32_t j, sz, n = arm64_hfa(&S->tccgen_vtop->type, &sz); | |
| 1384 | + gaddrof(S); | |
| 1385 | + gv(S, RC_R(0)); | |
| 1392 | 1386 | for (j = 0; j < n; j++) |
| 1393 | − o(0x3d400000 | | |
| 1387 | + o(S, 0x3d400000 | | |
| 1394 | 1388 | (sz & 16) << 19 | -(sz & 8) << 27 | (sz & 4) << 29 | |
| 1395 | 1389 | j | j << 10); // ldr ([sdq])(*),[x0,#(j * sz)] |
| 1396 | 1390 | } |
| 1397 | 1391 | else |
| 1398 | − gv(RC_FRET); | |
| 1392 | + gv(S, RC_FRET); | |
| 1399 | 1393 | break; |
| 1400 | 1394 | default: |
| 1401 | 1395 | assert(0); |
| 1402 | 1396 | } |
| 1403 | − vtop--; | |
| 1397 | + S->tccgen_vtop--; | |
| 1404 | 1398 | } |
| 1405 | 1399 | |
| 1406 | −ST_FUNC void gfunc_epilog(void) | |
| 1400 | +ST_FUNC void gfunc_epilog(TCCState *S) | |
| 1407 | 1401 | { |
| 1408 | 1402 | #ifdef CONFIG_TCC_BCHECK |
| 1409 | − if (tcc_state->do_bounds_check) | |
| 1410 | − gen_bounds_epilog(); | |
| 1403 | + if (S->do_bounds_check) | |
| 1404 | + gen_bounds_epilog(S); | |
| 1411 | 1405 | #endif |
| 1412 | 1406 | |
| 1413 | − if (loc) { | |
| 1407 | + if (S->tccgen_loc) { | |
| 1414 | 1408 | // Insert instructions to subtract size of stack frame from SP. |
| 1415 | 1409 | unsigned char *ptr = cur_text_section->data + arm64_func_sub_sp_offset; |
| 1416 | − uint64_t diff = (-loc + 15) & ~15; | |
| 1410 | + uint64_t diff = (-S->tccgen_loc + 15) & ~15; | |
| 1417 | 1411 | if (!(diff >> 24)) { |
| 1418 | 1412 | if (diff & 0xfff) // sub sp,sp,#(diff & 0xfff) |
| 1419 | 1413 | write32le(ptr, 0xd10003ff | (diff & 0xfff) << 10); |
| @@ -1439,40 +1433,40 @@ ST_FUNC void gfunc_epilog(void) · 19 unmodified lines | ||
| 1439 | 1433 | // sub sp,sp,x16,lsl #(j) |
| 1440 | 1434 | } |
| 1441 | 1435 | } |
| 1442 | − o(0x910003bf); // mov sp,x29 | |
| 1443 | − o(0xa8ce7bfd); // ldp x29,x30,[sp],#224 | |
| 1436 | + o(S, 0x910003bf); // mov sp,x29 | |
| 1437 | + o(S, 0xa8ce7bfd); // ldp x29,x30,[sp],#224 | |
| 1444 | 1438 | |
| 1445 | − o(0xd65f03c0); // ret | |
| 1439 | + o(S, 0xd65f03c0); // ret | |
| 1446 | 1440 | } |
| 1447 | 1441 | |
| 1448 | −ST_FUNC void gen_fill_nops(int bytes) | |
| 1442 | +ST_FUNC void gen_fill_nops(TCCState *S, int bytes) | |
| 1449 | 1443 | { |
| 1450 | 1444 | if ((bytes & 3)) |
| 1451 | − tcc_error("alignment of code section not multiple of 4"); | |
| 1445 | + tcc_error(S, "alignment of code section not multiple of 4"); | |
| 1452 | 1446 | while (bytes > 0) { |
| 1453 | − o(0xd503201f); // nop | |
| 1447 | + o(S, 0xd503201f); // nop | |
| 1454 | 1448 | bytes -= 4; |
| 1455 | 1449 | } |
| 1456 | 1450 | } |
| 1457 | 1451 | |
| 1458 | 1452 | // Generate forward branch to label: |
| 1459 | −ST_FUNC int gjmp(int t) | |
| 1453 | +ST_FUNC int gjmp(TCCState *S, int t) | |
| 1460 | 1454 | { |
| 1461 | − int r = ind; | |
| 1462 | − if (nocode_wanted) | |
| 1455 | + int r = S->tccgen_ind; | |
| 1456 | + if (S->tccgen_nocode_wanted) | |
| 1463 | 1457 | return t; |
| 1464 | − o(t); | |
| 1458 | + o(S, t); | |
| 1465 | 1459 | return r; |
| 1466 | 1460 | } |
| 1467 | 1461 | |
| 1468 | 1462 | // Generate branch to known address: |
| 1469 | −ST_FUNC void gjmp_addr(int a) | |
| 1463 | +ST_FUNC void gjmp_addr(TCCState *S, int a) | |
| 1470 | 1464 | { |
| 1471 | − assert(a - ind + 0x8000000 < 0x10000000); | |
| 1472 | − o(0x14000000 | ((a - ind) >> 2 & 0x3ffffff)); | |
| 1465 | + assert(a - S->tccgen_ind + 0x8000000 < 0x10000000); | |
| 1466 | + o(S, 0x14000000 | ((a - S->tccgen_ind) >> 2 & 0x3ffffff)); | |
| 1473 | 1467 | } |
| 1474 | 1468 | |
| 1475 | −ST_FUNC int gjmp_append(int n, int t) | |
| 1469 | +ST_FUNC int gjmp_append(TCCState *S, int n, int t) | |
| 1476 | 1470 | { |
| 1477 | 1471 | void *p; |
| 1478 | 1472 | /* insert vtop->c jump list in t */ |
| @@ -1486,61 +1480,61 @@ ST_FUNC int gjmp_append(int n, int t) · 7 unmodified lines | ||
| 1486 | 1480 | return t; |
| 1487 | 1481 | } |
| 1488 | 1482 | |
| 1489 | −void arm64_vset_VT_CMP(int op) | |
| 1483 | +void arm64_vset_VT_CMP(TCCState *S, int op) | |
| 1490 | 1484 | { |
| 1491 | 1485 | if (op >= TOK_ULT && op <= TOK_GT) { |
| 1492 | − vtop->cmp_r = vtop->r; | |
| 1493 | − vset_VT_CMP(0x80); | |
| 1486 | + S->tccgen_vtop->cmp_r = S->tccgen_vtop->r; | |
| 1487 | + vset_VT_CMP(S, 0x80); | |
| 1494 | 1488 | } |
| 1495 | 1489 | } |
| 1496 | 1490 | |
| 1497 | −static void arm64_gen_opil(int op, uint32_t l); | |
| 1491 | +static void arm64_gen_opil(TCCState *S, int op, uint32_t l); | |
| 1498 | 1492 | |
| 1499 | −static void arm64_load_cmp(int r, SValue *sv) | |
| 1493 | +static void arm64_load_cmp(TCCState *S, int r, SValue *sv) | |
| 1500 | 1494 | { |
| 1501 | 1495 | sv->r = sv->cmp_r; |
| 1502 | 1496 | if (sv->c.i & 1) { |
| 1503 | − vpushi(1); | |
| 1504 | − arm64_gen_opil('^', 0); | |
| 1497 | + vpushi(S, 1); | |
| 1498 | + arm64_gen_opil(S, '^', 0); | |
| 1505 | 1499 | } |
| 1506 | 1500 | if (r != sv->r) { |
| 1507 | − load(r, sv); | |
| 1501 | + load(S, r, sv); | |
| 1508 | 1502 | sv->r = r; |
| 1509 | 1503 | } |
| 1510 | 1504 | } |
| 1511 | 1505 | |
| 1512 | −ST_FUNC int gjmp_cond(int op, int t) | |
| 1506 | +ST_FUNC int gjmp_cond(TCCState *S, int op, int t) | |
| 1513 | 1507 | { |
| 1514 | − int bt = vtop->type.t & VT_BTYPE; | |
| 1508 | + int bt = S->tccgen_vtop->type.t & VT_BTYPE; | |
| 1515 | 1509 | |
| 1516 | 1510 | int inv = op & 1; |
| 1517 | − vtop->r = vtop->cmp_r; | |
| 1511 | + S->tccgen_vtop->r = S->tccgen_vtop->cmp_r; | |
| 1518 | 1512 | |
| 1519 | 1513 | if (bt == VT_LDOUBLE) { |
| 1520 | − uint32_t a, b, f = fltr(gv(RC_FLOAT)); | |
| 1521 | − a = get_reg(RC_INT); | |
| 1522 | − vpushi(0); | |
| 1523 | − vtop[0].r = a; | |
| 1524 | − b = get_reg(RC_INT); | |
| 1525 | − a = intr(a); | |
| 1526 | − b = intr(b); | |
| 1527 | − o(0x4e083c00 | a | f << 5); // mov x(a),v(f).d[0] | |
| 1528 | − o(0x4e183c00 | b | f << 5); // mov x(b),v(f).d[1] | |
| 1529 | − o(0xaa000400 | a | a << 5 | b << 16); // orr x(a),x(a),x(b),lsl #1 | |
| 1530 | − o(0xb4000040 | a | !!inv << 24); // cbz/cbnz x(a),.+8 | |
| 1531 | − --vtop; | |
| 1514 | + uint32_t a, b, f = fltr(gv(S, RC_FLOAT)); | |
| 1515 | + a = get_reg(S, RC_INT); | |
| 1516 | + vpushi(S, 0); | |
| 1517 | + S->tccgen_vtop[0].r = a; | |
| 1518 | + b = get_reg(S, RC_INT); | |
| 1519 | + a = intr(S, a); | |
| 1520 | + b = intr(S, b); | |
| 1521 | + o(S, 0x4e083c00 | a | f << 5); // mov x(a),v(f).d[0] | |
| 1522 | + o(S, 0x4e183c00 | b | f << 5); // mov x(b),v(f).d[1] | |
| 1523 | + o(S, 0xaa000400 | a | a << 5 | b << 16); // orr x(a),x(a),x(b),lsl #1 | |
| 1524 | + o(S, 0xb4000040 | a | !!inv << 24); // cbz/cbnz x(a),.+8 | |
| 1525 | + --S->tccgen_vtop; | |
| 1532 | 1526 | } |
| 1533 | 1527 | else if (bt == VT_FLOAT || bt == VT_DOUBLE) { |
| 1534 | − uint32_t a = fltr(gv(RC_FLOAT)); | |
| 1535 | − o(0x1e202008 | a << 5 | (bt != VT_FLOAT) << 22); // fcmp | |
| 1536 | − o(0x54000040 | !!inv); // b.eq/b.ne .+8 | |
| 1528 | + uint32_t a = fltr(gv(S, RC_FLOAT)); | |
| 1529 | + o(S, 0x1e202008 | a << 5 | (bt != VT_FLOAT) << 22); // fcmp | |
| 1530 | + o(S, 0x54000040 | !!inv); // b.eq/b.ne .+8 | |
| 1537 | 1531 | } |
| 1538 | 1532 | else { |
| 1539 | 1533 | uint32_t ll = (bt == VT_PTR || bt == VT_LLONG); |
| 1540 | − uint32_t a = intr(gv(RC_INT)); | |
| 1541 | − o(0x34000040 | a | !!inv << 24 | ll << 31); // cbz/cbnz wA,.+8 | |
| 1534 | + uint32_t a = intr(S, gv(S, RC_INT)); | |
| 1535 | + o(S, 0x34000040 | a | !!inv << 24 | ll << 31); // cbz/cbnz wA,.+8 | |
| 1542 | 1536 | } |
| 1543 | − return gjmp(t); | |
| 1537 | + return gjmp(S, t); | |
| 1544 | 1538 | } |
| 1545 | 1539 | |
| 1546 | 1540 | static int arm64_iconst(uint64_t *val, SValue *sv) |
| @@ -1557,7 +1551,7 @@ static int arm64_iconst(uint64_t *val, SValue *sv) · 10 unmodified lines | ||
| 1557 | 1551 | return 1; |
| 1558 | 1552 | } |
| 1559 | 1553 | |
| 1560 | −static int arm64_gen_opic(int op, uint32_t l, int rev, uint64_t val, | |
| 1554 | +static int arm64_gen_opic(TCCState *S, int op, uint32_t l, int rev, uint64_t val, | |
| 1561 | 1555 | uint32_t x, uint32_t a) |
| 1562 | 1556 | { |
| 1563 | 1557 | if (op == '-' && !rev) { |
| @@ -1573,30 +1567,30 @@ static int arm64_gen_opic(int op, uint32_t l, int rev, uint64_t val, · 9 unmodified lines | ||
| 1573 | 1567 | val = s ? -val : val; |
| 1574 | 1568 | val = l ? val : (uint32_t)val; |
| 1575 | 1569 | if (!(val & ~(uint64_t)0xfff)) |
| 1576 | − o(0x11000000 | l << 31 | s << 30 | x | a << 5 | val << 10); | |
| 1570 | + o(S, 0x11000000 | l << 31 | s << 30 | x | a << 5 | val << 10); | |
| 1577 | 1571 | else if (!(val & ~(uint64_t)0xfff000)) |
| 1578 | − o(0x11400000 | l << 31 | s << 30 | x | a << 5 | val >> 12 << 10); | |
| 1572 | + o(S, 0x11400000 | l << 31 | s << 30 | x | a << 5 | val >> 12 << 10); | |
| 1579 | 1573 | else { |
| 1580 | − arm64_movimm(30, val); // use x30 | |
| 1581 | − o(0x0b1e0000 | l << 31 | s << 30 | x | a << 5); | |
| 1574 | + arm64_movimm(S, 30, val); // use x30 | |
| 1575 | + o(S, 0x0b1e0000 | l << 31 | s << 30 | x | a << 5); | |
| 1582 | 1576 | } |
| 1583 | 1577 | return 1; |
| 1584 | 1578 | } |
| 1585 | 1579 | |
| 1586 | 1580 | case '-': |
| 1587 | 1581 | if (!val) |
| 1588 | − o(0x4b0003e0 | l << 31 | x | a << 16); // neg | |
| 1582 | + o(S, 0x4b0003e0 | l << 31 | x | a << 16); // neg | |
| 1589 | 1583 | else if (val == (l ? (uint64_t)-1 : (uint32_t)-1)) |
| 1590 | − o(0x2a2003e0 | l << 31 | x | a << 16); // mvn | |
| 1584 | + o(S, 0x2a2003e0 | l << 31 | x | a << 16); // mvn | |
| 1591 | 1585 | else { |
| 1592 | − arm64_movimm(30, val); // use x30 | |
| 1593 | − o(0x4b0003c0 | l << 31 | x | a << 16); // sub | |
| 1586 | + arm64_movimm(S, 30, val); // use x30 | |
| 1587 | + o(S, 0x4b0003c0 | l << 31 | x | a << 16); // sub | |
| 1594 | 1588 | } |
| 1595 | 1589 | return 1; |
| 1596 | 1590 | |
| 1597 | 1591 | case '^': |
| 1598 | 1592 | if (val == -1 || (val == 0xffffffff && !l)) { |
| 1599 | − o(0x2a2003e0 | l << 31 | x | a << 16); // mvn | |
| 1593 | + o(S, 0x2a2003e0 | l << 31 | x | a << 16); // mvn | |
| 1600 | 1594 | return 1; |
| 1601 | 1595 | } |
| 1602 | 1596 | // fall through |
| @@ -1605,7 +1599,7 @@ static int arm64_gen_opic(int op, uint32_t l, int rev, uint64_t val, · 2 unmodified lines | ||
| 1605 | 1599 | int e = arm64_encode_bimm64(l ? val : val | val << 32); |
| 1606 | 1600 | if (e < 0) |
| 1607 | 1601 | return 0; |
| 1608 | − o((op == '&' ? 0x12000000 : | |
| 1602 | + o(S, (op == '&' ? 0x12000000 : | |
| 1609 | 1603 | op == '|' ? 0x32000000 : 0x52000000) | |
| 1610 | 1604 | l << 31 | x | a << 5 | (uint32_t)e << 10); |
| 1611 | 1605 | return 1; |
| @@ -1620,14 +1614,14 @@ static int arm64_gen_opic(int op, uint32_t l, int rev, uint64_t val, · 8 unmodified lines | ||
| 1620 | 1614 | return 0; |
| 1621 | 1615 | if (!val) { |
| 1622 | 1616 | // tcc_warning("shift count >= width of type"); |
| 1623 | − o(0x2a0003e0 | l << 31 | a << 16); | |
| 1617 | + o(S, 0x2a0003e0 | l << 31 | a << 16); | |
| 1624 | 1618 | return 1; |
| 1625 | 1619 | } |
| 1626 | 1620 | else if (op == TOK_SHL) |
| 1627 | − o(0x53000000 | l << 31 | l << 22 | x | a << 5 | | |
| 1621 | + o(S, 0x53000000 | l << 31 | l << 22 | x | a << 5 | | |
| 1628 | 1622 | (n - val) << 16 | (n - 1 - val) << 10); // lsl |
| 1629 | 1623 | else |
| 1630 | − o(0x13000000 | (op == TOK_SHR) << 30 | l << 31 | l << 22 | | |
| 1624 | + o(S, 0x13000000 | (op == TOK_SHR) << 30 | l << 31 | l << 22 | | |
| 1631 | 1625 | x | a << 5 | val << 16 | (n - 1) << 10); // lsr/asr |
| 1632 | 1626 | return 1; |
| 1633 | 1627 | } |
| @@ -1636,7 +1630,7 @@ static int arm64_gen_opic(int op, uint32_t l, int rev, uint64_t val, · 2 unmodified lines | ||
| 1636 | 1630 | return 0; |
| 1637 | 1631 | } |
| 1638 | 1632 | |
| 1639 | −static void arm64_gen_opil(int op, uint32_t l) | |
| 1633 | +static void arm64_gen_opil(TCCState *S, int op, uint32_t l) | |
| 1640 | 1634 | { |
| 1641 | 1635 | uint32_t x, a, b; |
| 1642 | 1636 | |
| @@ -1645,122 +1639,122 @@ static void arm64_gen_opil(int op, uint32_t l) · 2 unmodified lines | ||
| 1645 | 1639 | uint64_t val; |
| 1646 | 1640 | int rev = 1; |
| 1647 | 1641 | |
| 1648 | − if (arm64_iconst(0, &vtop[0])) { | |
| 1649 | − vswap(); | |
| 1642 | + if (arm64_iconst(0, &S->tccgen_vtop[0])) { | |
| 1643 | + vswap(S); | |
| 1650 | 1644 | rev = 0; |
| 1651 | 1645 | } |
| 1652 | − if (arm64_iconst(&val, &vtop[-1])) { | |
| 1653 | − gv(RC_INT); | |
| 1654 | − a = intr(vtop[0].r); | |
| 1655 | − --vtop; | |
| 1656 | − x = get_reg(RC_INT); | |
| 1657 | − ++vtop; | |
| 1658 | − if (arm64_gen_opic(op, l, rev, val, intr(x), a)) { | |
| 1659 | − vtop[0].r = x; | |
| 1660 | − vswap(); | |
| 1661 | − --vtop; | |
| 1646 | + if (arm64_iconst(&val, &S->tccgen_vtop[-1])) { | |
| 1647 | + gv(S, RC_INT); | |
| 1648 | + a = intr(S, S->tccgen_vtop[0].r); | |
| 1649 | + --S->tccgen_vtop; | |
| 1650 | + x = get_reg(S, RC_INT); | |
| 1651 | + ++S->tccgen_vtop; | |
| 1652 | + if (arm64_gen_opic(S, op, l, rev, val, intr(S, x), a)) { | |
| 1653 | + S->tccgen_vtop[0].r = x; | |
| 1654 | + vswap(S); | |
| 1655 | + --S->tccgen_vtop; | |
| 1662 | 1656 | return; |
| 1663 | 1657 | } |
| 1664 | 1658 | } |
| 1665 | 1659 | if (!rev) |
| 1666 | − vswap(); | |
| 1660 | + vswap(S); | |
| 1667 | 1661 | } |
| 1668 | 1662 | |
| 1669 | − gv2(RC_INT, RC_INT); | |
| 1670 | − assert(vtop[-1].r < VT_CONST && vtop[0].r < VT_CONST); | |
| 1671 | − a = intr(vtop[-1].r); | |
| 1672 | − b = intr(vtop[0].r); | |
| 1673 | − vtop -= 2; | |
| 1674 | − x = get_reg(RC_INT); | |
| 1675 | − ++vtop; | |
| 1676 | − vtop[0].r = x; | |
| 1677 | − x = intr(x); | |
| 1663 | + gv2(S, RC_INT, RC_INT); | |
| 1664 | + assert(S->tccgen_vtop[-1].r < VT_CONST && S->tccgen_vtop[0].r < VT_CONST); | |
| 1665 | + a = intr(S, S->tccgen_vtop[-1].r); | |
| 1666 | + b = intr(S, S->tccgen_vtop[0].r); | |
| 1667 | + S->tccgen_vtop -= 2; | |
| 1668 | + x = get_reg(S, RC_INT); | |
| 1669 | + ++S->tccgen_vtop; | |
| 1670 | + S->tccgen_vtop[0].r = x; | |
| 1671 | + x = intr(S, x); | |
| 1678 | 1672 | |
| 1679 | 1673 | switch (op) { |
| 1680 | 1674 | case '%': |
| 1681 | 1675 | // Use x30 for quotient: |
| 1682 | − o(0x1ac00c00 | l << 31 | 30 | a << 5 | b << 16); // sdiv | |
| 1683 | − o(0x1b008000 | l << 31 | x | (uint32_t)30 << 5 | | |
| 1676 | + o(S, 0x1ac00c00 | l << 31 | 30 | a << 5 | b << 16); // sdiv | |
| 1677 | + o(S, 0x1b008000 | l << 31 | x | (uint32_t)30 << 5 | | |
| 1684 | 1678 | b << 16 | a << 10); // msub |
| 1685 | 1679 | break; |
| 1686 | 1680 | case '&': |
| 1687 | − o(0x0a000000 | l << 31 | x | a << 5 | b << 16); // and | |
| 1681 | + o(S, 0x0a000000 | l << 31 | x | a << 5 | b << 16); // and | |
| 1688 | 1682 | break; |
| 1689 | 1683 | case '*': |
| 1690 | − o(0x1b007c00 | l << 31 | x | a << 5 | b << 16); // mul | |
| 1684 | + o(S, 0x1b007c00 | l << 31 | x | a << 5 | b << 16); // mul | |
| 1691 | 1685 | break; |
| 1692 | 1686 | case '+': |
| 1693 | − o(0x0b000000 | l << 31 | x | a << 5 | b << 16); // add | |
| 1687 | + o(S, 0x0b000000 | l << 31 | x | a << 5 | b << 16); // add | |
| 1694 | 1688 | break; |
| 1695 | 1689 | case '-': |
| 1696 | − o(0x4b000000 | l << 31 | x | a << 5 | b << 16); // sub | |
| 1690 | + o(S, 0x4b000000 | l << 31 | x | a << 5 | b << 16); // sub | |
| 1697 | 1691 | break; |
| 1698 | 1692 | case '/': |
| 1699 | − o(0x1ac00c00 | l << 31 | x | a << 5 | b << 16); // sdiv | |
| 1693 | + o(S, 0x1ac00c00 | l << 31 | x | a << 5 | b << 16); // sdiv | |
| 1700 | 1694 | break; |
| 1701 | 1695 | case '^': |
| 1702 | − o(0x4a000000 | l << 31 | x | a << 5 | b << 16); // eor | |
| 1696 | + o(S, 0x4a000000 | l << 31 | x | a << 5 | b << 16); // eor | |
| 1703 | 1697 | break; |
| 1704 | 1698 | case '|': |
| 1705 | − o(0x2a000000 | l << 31 | x | a << 5 | b << 16); // orr | |
| 1699 | + o(S, 0x2a000000 | l << 31 | x | a << 5 | b << 16); // orr | |
| 1706 | 1700 | break; |
| 1707 | 1701 | case TOK_EQ: |
| 1708 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1709 | − o(0x1a9f17e0 | x); // cset wA,eq | |
| 1702 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1703 | + o(S, 0x1a9f17e0 | x); // cset wA,eq | |
| 1710 | 1704 | break; |
| 1711 | 1705 | case TOK_GE: |
| 1712 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1713 | − o(0x1a9fb7e0 | x); // cset wA,ge | |
| 1706 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1707 | + o(S, 0x1a9fb7e0 | x); // cset wA,ge | |
| 1714 | 1708 | break; |
| 1715 | 1709 | case TOK_GT: |
| 1716 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1717 | − o(0x1a9fd7e0 | x); // cset wA,gt | |
| 1710 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1711 | + o(S, 0x1a9fd7e0 | x); // cset wA,gt | |
| 1718 | 1712 | break; |
| 1719 | 1713 | case TOK_LE: |
| 1720 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1721 | − o(0x1a9fc7e0 | x); // cset wA,le | |
| 1714 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1715 | + o(S, 0x1a9fc7e0 | x); // cset wA,le | |
| 1722 | 1716 | break; |
| 1723 | 1717 | case TOK_LT: |
| 1724 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1725 | − o(0x1a9fa7e0 | x); // cset wA,lt | |
| 1718 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1719 | + o(S, 0x1a9fa7e0 | x); // cset wA,lt | |
| 1726 | 1720 | break; |
| 1727 | 1721 | case TOK_NE: |
| 1728 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1729 | − o(0x1a9f07e0 | x); // cset wA,ne | |
| 1722 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1723 | + o(S, 0x1a9f07e0 | x); // cset wA,ne | |
| 1730 | 1724 | break; |
| 1731 | 1725 | case TOK_SAR: |
| 1732 | − o(0x1ac02800 | l << 31 | x | a << 5 | b << 16); // asr | |
| 1726 | + o(S, 0x1ac02800 | l << 31 | x | a << 5 | b << 16); // asr | |
| 1733 | 1727 | break; |
| 1734 | 1728 | case TOK_SHL: |
| 1735 | − o(0x1ac02000 | l << 31 | x | a << 5 | b << 16); // lsl | |
| 1729 | + o(S, 0x1ac02000 | l << 31 | x | a << 5 | b << 16); // lsl | |
| 1736 | 1730 | break; |
| 1737 | 1731 | case TOK_SHR: |
| 1738 | − o(0x1ac02400 | l << 31 | x | a << 5 | b << 16); // lsr | |
| 1732 | + o(S, 0x1ac02400 | l << 31 | x | a << 5 | b << 16); // lsr | |
| 1739 | 1733 | break; |
| 1740 | 1734 | case TOK_UDIV: |
| 1741 | 1735 | case TOK_PDIV: |
| 1742 | − o(0x1ac00800 | l << 31 | x | a << 5 | b << 16); // udiv | |
| 1736 | + o(S, 0x1ac00800 | l << 31 | x | a << 5 | b << 16); // udiv | |
| 1743 | 1737 | break; |
| 1744 | 1738 | case TOK_UGE: |
| 1745 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1746 | − o(0x1a9f37e0 | x); // cset wA,cs | |
| 1739 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1740 | + o(S, 0x1a9f37e0 | x); // cset wA,cs | |
| 1747 | 1741 | break; |
| 1748 | 1742 | case TOK_UGT: |
| 1749 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1750 | − o(0x1a9f97e0 | x); // cset wA,hi | |
| 1743 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1744 | + o(S, 0x1a9f97e0 | x); // cset wA,hi | |
| 1751 | 1745 | break; |
| 1752 | 1746 | case TOK_ULT: |
| 1753 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1754 | − o(0x1a9f27e0 | x); // cset wA,cc | |
| 1747 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1748 | + o(S, 0x1a9f27e0 | x); // cset wA,cc | |
| 1755 | 1749 | break; |
| 1756 | 1750 | case TOK_ULE: |
| 1757 | − o(0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1758 | − o(0x1a9f87e0 | x); // cset wA,ls | |
| 1751 | + o(S, 0x6b00001f | l << 31 | a << 5 | b << 16); // cmp | |
| 1752 | + o(S, 0x1a9f87e0 | x); // cset wA,ls | |
| 1759 | 1753 | break; |
| 1760 | 1754 | case TOK_UMOD: |
| 1761 | 1755 | // Use x30 for quotient: |
| 1762 | − o(0x1ac00800 | l << 31 | 30 | a << 5 | b << 16); // udiv | |
| 1763 | − o(0x1b008000 | l << 31 | x | (uint32_t)30 << 5 | | |
| 1756 | + o(S, 0x1ac00800 | l << 31 | 30 | a << 5 | b << 16); // udiv | |
| 1757 | + o(S, 0x1b008000 | l << 31 | x | (uint32_t)30 << 5 | | |
| 1764 | 1758 | b << 16 | a << 10); // msub |
| 1765 | 1759 | break; |
| 1766 | 1760 | default: |
| @@ -1768,24 +1762,24 @@ static void arm64_gen_opil(int op, uint32_t l) · 1 unmodified line | ||
| 1768 | 1762 | } |
| 1769 | 1763 | } |
| 1770 | 1764 | |
| 1771 | −ST_FUNC void gen_opi(int op) | |
| 1765 | +ST_FUNC void gen_opi(TCCState *S, int op) | |
| 1772 | 1766 | { |
| 1773 | − arm64_gen_opil(op, 0); | |
| 1774 | − arm64_vset_VT_CMP(op); | |
| 1767 | + arm64_gen_opil(S, op, 0); | |
| 1768 | + arm64_vset_VT_CMP(S, op); | |
| 1775 | 1769 | } |
| 1776 | 1770 | |
| 1777 | −ST_FUNC void gen_opl(int op) | |
| 1771 | +ST_FUNC void gen_opl(TCCState* S, int op) | |
| 1778 | 1772 | { |
| 1779 | − arm64_gen_opil(op, 1); | |
| 1780 | − arm64_vset_VT_CMP(op); | |
| 1773 | + arm64_gen_opil(S, op, 1); | |
| 1774 | + arm64_vset_VT_CMP(S, op); | |
| 1781 | 1775 | } |
| 1782 | 1776 | |
| 1783 | −ST_FUNC void gen_opf(int op) | |
| 1777 | +ST_FUNC void gen_opf(TCCState *S, int op) | |
| 1784 | 1778 | { |
| 1785 | 1779 | uint32_t x, a, b, dbl; |
| 1786 | 1780 | |
| 1787 | − if (vtop[0].type.t == VT_LDOUBLE) { | |
| 1788 | − CType type = vtop[0].type; | |
| 1781 | + if (S->tccgen_vtop[0].type.t == VT_LDOUBLE) { | |
| 1782 | + CType type = S->tccgen_vtop[0].type; | |
| 1789 | 1783 | int func = 0; |
| 1790 | 1784 | int cond = -1; |
| 1791 | 1785 | switch (op) { |
| @@ -1801,162 +1795,162 @@ ST_FUNC void gen_opf(int op) · 9 unmodified lines | ||
| 1801 | 1795 | case TOK_GT: func = TOK___gttf2; cond = 13; break; |
| 1802 | 1796 | default: assert(0); break; |
| 1803 | 1797 | } |
| 1804 | − vpush_helper_func(func); | |
| 1805 | − vrott(3); | |
| 1806 | − gfunc_call(2); | |
| 1807 | − vpushi(0); | |
| 1808 | − vtop->r = cond < 0 ? REG_FRET : REG_IRET; | |
| 1798 | + vpush_helper_func(S, func); | |
| 1799 | + vrott(S, 3); | |
| 1800 | + gfunc_call(S, 2); | |
| 1801 | + vpushi(S, 0); | |
| 1802 | + S->tccgen_vtop->r = cond < 0 ? REG_FRET : REG_IRET; | |
| 1809 | 1803 | if (cond < 0) |
| 1810 | − vtop->type = type; | |
| 1804 | + S->tccgen_vtop->type = type; | |
| 1811 | 1805 | else { |
| 1812 | − o(0x7100001f); // cmp w0,#0 | |
| 1813 | − o(0x1a9f07e0 | (uint32_t)cond << 12); // cset w0,(cond) | |
| 1806 | + o(S, 0x7100001f); // cmp w0,#0 | |
| 1807 | + o(S, 0x1a9f07e0 | (uint32_t)cond << 12); // cset w0,(cond) | |
| 1814 | 1808 | } |
| 1815 | 1809 | return; |
| 1816 | 1810 | } |
| 1817 | 1811 | |
| 1818 | − dbl = vtop[0].type.t != VT_FLOAT; | |
| 1819 | − gv2(RC_FLOAT, RC_FLOAT); | |
| 1820 | − assert(vtop[-1].r < VT_CONST && vtop[0].r < VT_CONST); | |
| 1821 | − a = fltr(vtop[-1].r); | |
| 1822 | − b = fltr(vtop[0].r); | |
| 1823 | − vtop -= 2; | |
| 1812 | + dbl = S->tccgen_vtop[0].type.t != VT_FLOAT; | |
| 1813 | + gv2(S, RC_FLOAT, RC_FLOAT); | |
| 1814 | + assert(S->tccgen_vtop[-1].r < VT_CONST && S->tccgen_vtop[0].r < VT_CONST); | |
| 1815 | + a = fltr(S->tccgen_vtop[-1].r); | |
| 1816 | + b = fltr(S->tccgen_vtop[0].r); | |
| 1817 | + S->tccgen_vtop -= 2; | |
| 1824 | 1818 | switch (op) { |
| 1825 | 1819 | case TOK_EQ: case TOK_NE: |
| 1826 | 1820 | case TOK_LT: case TOK_GE: case TOK_LE: case TOK_GT: |
| 1827 | − x = get_reg(RC_INT); | |
| 1828 | − ++vtop; | |
| 1829 | − vtop[0].r = x; | |
| 1830 | − x = intr(x); | |
| 1821 | + x = get_reg(S, RC_INT); | |
| 1822 | + ++S->tccgen_vtop; | |
| 1823 | + S->tccgen_vtop[0].r = x; | |
| 1824 | + x = intr(S, x); | |
| 1831 | 1825 | break; |
| 1832 | 1826 | default: |
| 1833 | − x = get_reg(RC_FLOAT); | |
| 1834 | − ++vtop; | |
| 1835 | − vtop[0].r = x; | |
| 1827 | + x = get_reg(S, RC_FLOAT); | |
| 1828 | + ++S->tccgen_vtop; | |
| 1829 | + S->tccgen_vtop[0].r = x; | |
| 1836 | 1830 | x = fltr(x); |
| 1837 | 1831 | break; |
| 1838 | 1832 | } |
| 1839 | 1833 | |
| 1840 | 1834 | switch (op) { |
| 1841 | 1835 | case '*': |
| 1842 | − o(0x1e200800 | dbl << 22 | x | a << 5 | b << 16); // fmul | |
| 1836 | + o(S, 0x1e200800 | dbl << 22 | x | a << 5 | b << 16); // fmul | |
| 1843 | 1837 | break; |
| 1844 | 1838 | case '+': |
| 1845 | − o(0x1e202800 | dbl << 22 | x | a << 5 | b << 16); // fadd | |
| 1839 | + o(S, 0x1e202800 | dbl << 22 | x | a << 5 | b << 16); // fadd | |
| 1846 | 1840 | break; |
| 1847 | 1841 | case '-': |
| 1848 | − o(0x1e203800 | dbl << 22 | x | a << 5 | b << 16); // fsub | |
| 1842 | + o(S, 0x1e203800 | dbl << 22 | x | a << 5 | b << 16); // fsub | |
| 1849 | 1843 | break; |
| 1850 | 1844 | case '/': |
| 1851 | − o(0x1e201800 | dbl << 22 | x | a << 5 | b << 16); // fdiv | |
| 1845 | + o(S, 0x1e201800 | dbl << 22 | x | a << 5 | b << 16); // fdiv | |
| 1852 | 1846 | break; |
| 1853 | 1847 | case TOK_EQ: |
| 1854 | − o(0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1855 | − o(0x1a9f17e0 | x); // cset w(x),eq | |
| 1848 | + o(S, 0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1849 | + o(S, 0x1a9f17e0 | x); // cset w(x),eq | |
| 1856 | 1850 | break; |
| 1857 | 1851 | case TOK_GE: |
| 1858 | − o(0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1859 | − o(0x1a9fb7e0 | x); // cset w(x),ge | |
| 1852 | + o(S, 0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1853 | + o(S, 0x1a9fb7e0 | x); // cset w(x),ge | |
| 1860 | 1854 | break; |
| 1861 | 1855 | case TOK_GT: |
| 1862 | − o(0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1863 | − o(0x1a9fd7e0 | x); // cset w(x),gt | |
| 1856 | + o(S, 0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1857 | + o(S, 0x1a9fd7e0 | x); // cset w(x),gt | |
| 1864 | 1858 | break; |
| 1865 | 1859 | case TOK_LE: |
| 1866 | − o(0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1867 | − o(0x1a9f87e0 | x); // cset w(x),ls | |
| 1860 | + o(S, 0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1861 | + o(S, 0x1a9f87e0 | x); // cset w(x),ls | |
| 1868 | 1862 | break; |
| 1869 | 1863 | case TOK_LT: |
| 1870 | − o(0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1871 | − o(0x1a9f57e0 | x); // cset w(x),mi | |
| 1864 | + o(S, 0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1865 | + o(S, 0x1a9f57e0 | x); // cset w(x),mi | |
| 1872 | 1866 | break; |
| 1873 | 1867 | case TOK_NE: |
| 1874 | − o(0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1875 | − o(0x1a9f07e0 | x); // cset w(x),ne | |
| 1868 | + o(S, 0x1e202000 | dbl << 22 | a << 5 | b << 16); // fcmp | |
| 1869 | + o(S, 0x1a9f07e0 | x); // cset w(x),ne | |
| 1876 | 1870 | break; |
| 1877 | 1871 | default: |
| 1878 | 1872 | assert(0); |
| 1879 | 1873 | } |
| 1880 | − arm64_vset_VT_CMP(op); | |
| 1874 | + arm64_vset_VT_CMP(S, op); | |
| 1881 | 1875 | } |
| 1882 | 1876 | |
| 1883 | 1877 | // Generate sign extension from 32 to 64 bits: |
| 1884 | −ST_FUNC void gen_cvt_sxtw(void) | |
| 1878 | +ST_FUNC void gen_cvt_sxtw(TCCState *S) | |
| 1885 | 1879 | { |
| 1886 | − uint32_t r = intr(gv(RC_INT)); | |
| 1887 | − o(0x93407c00 | r | r << 5); // sxtw x(r),w(r) | |
| 1880 | + uint32_t r = intr(S, gv(S, RC_INT)); | |
| 1881 | + o(S, 0x93407c00 | r | r << 5); // sxtw x(r),w(r) | |
| 1888 | 1882 | } |
| 1889 | 1883 | |
| 1890 | 1884 | /* char/short to int conversion */ |
| 1891 | −ST_FUNC void gen_cvt_csti(int t) | |
| 1885 | +ST_FUNC void gen_cvt_csti(TCCState *S, int t) | |
| 1892 | 1886 | { |
| 1893 | − int r = intr(gv(RC_INT)); | |
| 1894 | − o(0x13001c00 | |
| 1887 | + int r = intr(S, gv(S, RC_INT)); | |
| 1888 | + o(S, 0x13001c00 | |
| 1895 | 1889 | | ((t & VT_BTYPE) == VT_SHORT) << 13 |
| 1896 | 1890 | | (uint32_t)!!(t & VT_UNSIGNED) << 30 |
| 1897 | 1891 | | r | r << 5); // [su]xt[bh] w(r),w(r) |
| 1898 | 1892 | } |
| 1899 | 1893 | |
| 1900 | −ST_FUNC void gen_cvt_itof(int t) | |
| 1894 | +ST_FUNC void gen_cvt_itof(TCCState *S, int t) | |
| 1901 | 1895 | { |
| 1902 | 1896 | if (t == VT_LDOUBLE) { |
| 1903 | − int f = vtop->type.t; | |
| 1897 | + int f = S->tccgen_vtop->type.t; | |
| 1904 | 1898 | int func = (f & VT_BTYPE) == VT_LLONG ? |
| 1905 | 1899 | (f & VT_UNSIGNED ? TOK___floatunditf : TOK___floatditf) : |
| 1906 | 1900 | (f & VT_UNSIGNED ? TOK___floatunsitf : TOK___floatsitf); |
| 1907 | − vpush_helper_func(func); | |
| 1908 | − vrott(2); | |
| 1909 | − gfunc_call(1); | |
| 1910 | − vpushi(0); | |
| 1911 | − vtop->type.t = t; | |
| 1912 | − vtop->r = REG_FRET; | |
| 1901 | + vpush_helper_func(S, func); | |
| 1902 | + vrott(S, 2); | |
| 1903 | + gfunc_call(S, 1); | |
| 1904 | + vpushi(S, 0); | |
| 1905 | + S->tccgen_vtop->type.t = t; | |
| 1906 | + S->tccgen_vtop->r = REG_FRET; | |
| 1913 | 1907 | return; |
| 1914 | 1908 | } |
| 1915 | 1909 | else { |
| 1916 | − int d, n = intr(gv(RC_INT)); | |
| 1917 | − int s = !(vtop->type.t & VT_UNSIGNED); | |
| 1918 | − uint32_t l = ((vtop->type.t & VT_BTYPE) == VT_LLONG); | |
| 1919 | − --vtop; | |
| 1920 | − d = get_reg(RC_FLOAT); | |
| 1921 | − ++vtop; | |
| 1922 | − vtop[0].r = d; | |
| 1923 | − o(0x1e220000 | (uint32_t)!s << 16 | | |
| 1910 | + int d, n = intr(S, gv(S, RC_INT)); | |
| 1911 | + int s = !(S->tccgen_vtop->type.t & VT_UNSIGNED); | |
| 1912 | + uint32_t l = ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LLONG); | |
| 1913 | + --S->tccgen_vtop; | |
| 1914 | + d = get_reg(S, RC_FLOAT); | |
| 1915 | + ++S->tccgen_vtop; | |
| 1916 | + S->tccgen_vtop[0].r = d; | |
| 1917 | + o(S, 0x1e220000 | (uint32_t)!s << 16 | | |
| 1924 | 1918 | (uint32_t)(t != VT_FLOAT) << 22 | fltr(d) | |
| 1925 | 1919 | l << 31 | n << 5); // [us]cvtf [sd](d),[wx](n) |
| 1926 | 1920 | } |
| 1927 | 1921 | } |
| 1928 | 1922 | |
| 1929 | −ST_FUNC void gen_cvt_ftoi(int t) | |
| 1923 | +ST_FUNC void gen_cvt_ftoi(TCCState *S, int t) | |
| 1930 | 1924 | { |
| 1931 | − if ((vtop->type.t & VT_BTYPE) == VT_LDOUBLE) { | |
| 1925 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LDOUBLE) { | |
| 1932 | 1926 | int func = (t & VT_BTYPE) == VT_LLONG ? |
| 1933 | 1927 | (t & VT_UNSIGNED ? TOK___fixunstfdi : TOK___fixtfdi) : |
| 1934 | 1928 | (t & VT_UNSIGNED ? TOK___fixunstfsi : TOK___fixtfsi); |
| 1935 | − vpush_helper_func(func); | |
| 1936 | − vrott(2); | |
| 1937 | − gfunc_call(1); | |
| 1938 | − vpushi(0); | |
| 1939 | − vtop->type.t = t; | |
| 1940 | − vtop->r = REG_IRET; | |
| 1929 | + vpush_helper_func(S, func); | |
| 1930 | + vrott(S, 2); | |
| 1931 | + gfunc_call(S, 1); | |
| 1932 | + vpushi(S, 0); | |
| 1933 | + S->tccgen_vtop->type.t = t; | |
| 1934 | + S->tccgen_vtop->r = REG_IRET; | |
| 1941 | 1935 | return; |
| 1942 | 1936 | } |
| 1943 | 1937 | else { |
| 1944 | − int d, n = fltr(gv(RC_FLOAT)); | |
| 1945 | − uint32_t l = ((vtop->type.t & VT_BTYPE) != VT_FLOAT); | |
| 1946 | − --vtop; | |
| 1947 | − d = get_reg(RC_INT); | |
| 1948 | − ++vtop; | |
| 1949 | − vtop[0].r = d; | |
| 1950 | − o(0x1e380000 | | |
| 1938 | + int d, n = fltr(gv(S, RC_FLOAT)); | |
| 1939 | + uint32_t l = ((S->tccgen_vtop->type.t & VT_BTYPE) != VT_FLOAT); | |
| 1940 | + --S->tccgen_vtop; | |
| 1941 | + d = get_reg(S, RC_INT); | |
| 1942 | + ++S->tccgen_vtop; | |
| 1943 | + S->tccgen_vtop[0].r = d; | |
| 1944 | + o(S, 0x1e380000 | | |
| 1951 | 1945 | (uint32_t)!!(t & VT_UNSIGNED) << 16 | |
| 1952 | − (uint32_t)((t & VT_BTYPE) == VT_LLONG) << 31 | intr(d) | | |
| 1946 | + (uint32_t)((t & VT_BTYPE) == VT_LLONG) << 31 | intr(S, d) | | |
| 1953 | 1947 | l << 22 | n << 5); // fcvtz[su] [wx](d),[sd](n) |
| 1954 | 1948 | } |
| 1955 | 1949 | } |
| 1956 | 1950 | |
| 1957 | −ST_FUNC void gen_cvt_ftof(int t) | |
| 1951 | +ST_FUNC void gen_cvt_ftof(TCCState *S, int t) | |
| 1958 | 1952 | { |
| 1959 | − int f = vtop[0].type.t & VT_BTYPE; | |
| 1953 | + int f = S->tccgen_vtop[0].type.t & VT_BTYPE; | |
| 1960 | 1954 | assert(t == VT_FLOAT || t == VT_DOUBLE || t == VT_LDOUBLE); |
| 1961 | 1955 | assert(f == VT_FLOAT || f == VT_DOUBLE || f == VT_LDOUBLE); |
| 1962 | 1956 | if (t == f) |
| @@ -1966,142 +1960,142 @@ ST_FUNC void gen_cvt_ftof(int t) · 3 unmodified lines | ||
| 1966 | 1960 | int func = (t == VT_LDOUBLE) ? |
| 1967 | 1961 | (f == VT_FLOAT ? TOK___extendsftf2 : TOK___extenddftf2) : |
| 1968 | 1962 | (t == VT_FLOAT ? TOK___trunctfsf2 : TOK___trunctfdf2); |
| 1969 | − vpush_helper_func(func); | |
| 1970 | − vrott(2); | |
| 1971 | − gfunc_call(1); | |
| 1972 | − vpushi(0); | |
| 1973 | − vtop->type.t = t; | |
| 1974 | − vtop->r = REG_FRET; | |
| 1963 | + vpush_helper_func(S, func); | |
| 1964 | + vrott(S, 2); | |
| 1965 | + gfunc_call(S, 1); | |
| 1966 | + vpushi(S, 0); | |
| 1967 | + S->tccgen_vtop->type.t = t; | |
| 1968 | + S->tccgen_vtop->r = REG_FRET; | |
| 1975 | 1969 | } |
| 1976 | 1970 | else { |
| 1977 | 1971 | int x, a; |
| 1978 | − gv(RC_FLOAT); | |
| 1979 | − assert(vtop[0].r < VT_CONST); | |
| 1980 | − a = fltr(vtop[0].r); | |
| 1981 | − --vtop; | |
| 1982 | − x = get_reg(RC_FLOAT); | |
| 1983 | − ++vtop; | |
| 1984 | − vtop[0].r = x; | |
| 1972 | + gv(S, RC_FLOAT); | |
| 1973 | + assert(S->tccgen_vtop[0].r < VT_CONST); | |
| 1974 | + a = fltr(S->tccgen_vtop[0].r); | |
| 1975 | + --S->tccgen_vtop; | |
| 1976 | + x = get_reg(S, RC_FLOAT); | |
| 1977 | + ++S->tccgen_vtop; | |
| 1978 | + S->tccgen_vtop[0].r = x; | |
| 1985 | 1979 | x = fltr(x); |
| 1986 | 1980 | |
| 1987 | 1981 | if (f == VT_FLOAT) |
| 1988 | − o(0x1e22c000 | x | a << 5); // fcvt d(x),s(a) | |
| 1982 | + o(S, 0x1e22c000 | x | a << 5); // fcvt d(x),s(a) | |
| 1989 | 1983 | else |
| 1990 | − o(0x1e624000 | x | a << 5); // fcvt s(x),d(a) | |
| 1984 | + o(S, 0x1e624000 | x | a << 5); // fcvt s(x),d(a) | |
| 1991 | 1985 | } |
| 1992 | 1986 | } |
| 1993 | 1987 | |
| 1994 | 1988 | /* increment tcov counter */ |
| 1995 | −ST_FUNC void gen_increment_tcov (SValue *sv) | |
| 1989 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv) | |
| 1996 | 1990 | { |
| 1997 | 1991 | int r1, r2; |
| 1998 | 1992 | |
| 1999 | − vpushv(sv); | |
| 2000 | − vtop->r = r1 = get_reg(RC_INT); | |
| 2001 | − r2 = get_reg(RC_INT); | |
| 2002 | − greloca(cur_text_section, sv->sym, ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 2003 | − o(0x90000000 | r1); // adrp r1, #sym | |
| 2004 | − greloca(cur_text_section, sv->sym, ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 2005 | − o(0xf9400000 | r1 | (r1 << 5)); // ld xr,[xr, #sym] | |
| 2006 | − o(0xf9400000 | (intr(r1)<<5) | intr(r2)); // ldr r2, [r1] | |
| 2007 | − o(0x91000400 | (intr(r2)<<5) | intr(r2)); // add r2, r2, #1 | |
| 2008 | − o(0xf9000000 | (intr(r1)<<5) | intr(r2)); // str r2, [r1] | |
| 2009 | − vpop(); | |
| 1993 | + vpushv(S, sv); | |
| 1994 | + S->tccgen_vtop->r = r1 = get_reg(S, RC_INT); | |
| 1995 | + r2 = get_reg(S, RC_INT); | |
| 1996 | + greloca(S, cur_text_section, sv->sym, S->tccgen_ind, R_AARCH64_ADR_GOT_PAGE, 0); | |
| 1997 | + o(S, 0x90000000 | r1); // adrp r1, #sym | |
| 1998 | + greloca(S, cur_text_section, sv->sym, S->tccgen_ind, R_AARCH64_LD64_GOT_LO12_NC, 0); | |
| 1999 | + o(S, 0xf9400000 | r1 | (r1 << 5)); // ld xr,[xr, #sym] | |
| 2000 | + o(S, 0xf9400000 | (intr(S, r1)<<5) | intr(S, r2)); // ldr r2, [r1] | |
| 2001 | + o(S, 0x91000400 | (intr(S, r2)<<5) | intr(S, r2)); // add r2, r2, #1 | |
| 2002 | + o(S, 0xf9000000 | (intr(S, r1)<<5) | intr(S, r2)); // str r2, [r1] | |
| 2003 | + vpop(S); | |
| 2010 | 2004 | } |
| 2011 | 2005 | |
| 2012 | −ST_FUNC void ggoto(void) | |
| 2006 | +ST_FUNC void ggoto(TCCState *S) | |
| 2013 | 2007 | { |
| 2014 | − arm64_gen_bl_or_b(1); | |
| 2015 | − --vtop; | |
| 2008 | + arm64_gen_bl_or_b(S, 1); | |
| 2009 | + --S->tccgen_vtop; | |
| 2016 | 2010 | } |
| 2017 | 2011 | |
| 2018 | −ST_FUNC void gen_clear_cache(void) | |
| 2012 | +ST_FUNC void gen_clear_cache(TCCState *S) | |
| 2019 | 2013 | { |
| 2020 | 2014 | uint32_t beg, end, dsz, isz, p, lab1, b1; |
| 2021 | − gv2(RC_INT, RC_INT); | |
| 2022 | − vpushi(0); | |
| 2023 | − vtop->r = get_reg(RC_INT); | |
| 2024 | − vpushi(0); | |
| 2025 | − vtop->r = get_reg(RC_INT); | |
| 2026 | − vpushi(0); | |
| 2027 | − vtop->r = get_reg(RC_INT); | |
| 2028 | − beg = intr(vtop[-4].r); // x0 | |
| 2029 | − end = intr(vtop[-3].r); // x1 | |
| 2030 | − dsz = intr(vtop[-2].r); // x2 | |
| 2031 | − isz = intr(vtop[-1].r); // x3 | |
| 2032 | − p = intr(vtop[0].r); // x4 | |
| 2033 | − vtop -= 5; | |
| 2034 | − | |
| 2035 | − o(0xd53b0020 | isz); // mrs x(isz),ctr_el0 | |
| 2036 | − o(0x52800080 | p); // mov w(p),#4 | |
| 2037 | − o(0x53104c00 | dsz | isz << 5); // ubfx w(dsz),w(isz),#16,#4 | |
| 2038 | − o(0x1ac02000 | dsz | p << 5 | dsz << 16); // lsl w(dsz),w(p),w(dsz) | |
| 2039 | − o(0x12000c00 | isz | isz << 5); // and w(isz),w(isz),#15 | |
| 2040 | − o(0x1ac02000 | isz | p << 5 | isz << 16); // lsl w(isz),w(p),w(isz) | |
| 2041 | − o(0x51000400 | p | dsz << 5); // sub w(p),w(dsz),#1 | |
| 2042 | − o(0x8a240004 | p | beg << 5 | p << 16); // bic x(p),x(beg),x(p) | |
| 2043 | − b1 = ind; o(0x14000000); // b | |
| 2044 | − lab1 = ind; | |
| 2045 | − o(0xd50b7b20 | p); // dc cvau,x(p) | |
| 2046 | − o(0x8b000000 | p | p << 5 | dsz << 16); // add x(p),x(p),x(dsz) | |
| 2047 | − write32le(cur_text_section->data + b1, 0x14000000 | (ind - b1) >> 2); | |
| 2048 | − o(0xeb00001f | p << 5 | end << 16); // cmp x(p),x(end) | |
| 2049 | − o(0x54ffffa3 | ((lab1 - ind) << 3 & 0xffffe0)); // b.cc lab1 | |
| 2050 | − o(0xd5033b9f); // dsb ish | |
| 2051 | − o(0x51000400 | p | isz << 5); // sub w(p),w(isz),#1 | |
| 2052 | − o(0x8a240004 | p | beg << 5 | p << 16); // bic x(p),x(beg),x(p) | |
| 2053 | − b1 = ind; o(0x14000000); // b | |
| 2054 | − lab1 = ind; | |
| 2055 | − o(0xd50b7520 | p); // ic ivau,x(p) | |
| 2056 | − o(0x8b000000 | p | p << 5 | isz << 16); // add x(p),x(p),x(isz) | |
| 2057 | − write32le(cur_text_section->data + b1, 0x14000000 | (ind - b1) >> 2); | |
| 2058 | − o(0xeb00001f | p << 5 | end << 16); // cmp x(p),x(end) | |
| 2059 | − o(0x54ffffa3 | ((lab1 - ind) << 3 & 0xffffe0)); // b.cc lab1 | |
| 2060 | − o(0xd5033b9f); // dsb ish | |
| 2061 | − o(0xd5033fdf); // isb | |
| 2015 | + gv2(S, RC_INT, RC_INT); | |
| 2016 | + vpushi(S, 0); | |
| 2017 | + S->tccgen_vtop->r = get_reg(S, RC_INT); | |
| 2018 | + vpushi(S, 0); | |
| 2019 | + S->tccgen_vtop->r = get_reg(S, RC_INT); | |
| 2020 | + vpushi(S, 0); | |
| 2021 | + S->tccgen_vtop->r = get_reg(S, RC_INT); | |
| 2022 | + beg = intr(S, S->tccgen_vtop[-4].r); // x0 | |
| 2023 | + end = intr(S, S->tccgen_vtop[-3].r); // x1 | |
| 2024 | + dsz = intr(S, S->tccgen_vtop[-2].r); // x2 | |
| 2025 | + isz = intr(S, S->tccgen_vtop[-1].r); // x3 | |
| 2026 | + p = intr(S, S->tccgen_vtop[0].r); // x4 | |
| 2027 | + S->tccgen_vtop -= 5; | |
| 2028 | + | |
| 2029 | + o(S, 0xd53b0020 | isz); // mrs x(isz),ctr_el0 | |
| 2030 | + o(S, 0x52800080 | p); // mov w(p),#4 | |
| 2031 | + o(S, 0x53104c00 | dsz | isz << 5); // ubfx w(dsz),w(isz),#16,#4 | |
| 2032 | + o(S, 0x1ac02000 | dsz | p << 5 | dsz << 16); // lsl w(dsz),w(p),w(dsz) | |
| 2033 | + o(S, 0x12000c00 | isz | isz << 5); // and w(isz),w(isz),#15 | |
| 2034 | + o(S, 0x1ac02000 | isz | p << 5 | isz << 16); // lsl w(isz),w(p),w(isz) | |
| 2035 | + o(S, 0x51000400 | p | dsz << 5); // sub w(p),w(dsz),#1 | |
| 2036 | + o(S, 0x8a240004 | p | beg << 5 | p << 16); // bic x(p),x(beg),x(p) | |
| 2037 | + b1 = S->tccgen_ind; o(S, 0x14000000); // b | |
| 2038 | + lab1 = S->tccgen_ind; | |
| 2039 | + o(S, 0xd50b7b20 | p); // dc cvau,x(p) | |
| 2040 | + o(S, 0x8b000000 | p | p << 5 | dsz << 16); // add x(p),x(p),x(dsz) | |
| 2041 | + write32le(cur_text_section->data + b1, 0x14000000 | (S->tccgen_ind - b1) >> 2); | |
| 2042 | + o(S, 0xeb00001f | p << 5 | end << 16); // cmp x(p),x(end) | |
| 2043 | + o(S, 0x54ffffa3 | ((lab1 - S->tccgen_ind) << 3 & 0xffffe0)); // b.cc lab1 | |
| 2044 | + o(S, 0xd5033b9f); // dsb ish | |
| 2045 | + o(S, 0x51000400 | p | isz << 5); // sub w(p),w(isz),#1 | |
| 2046 | + o(S, 0x8a240004 | p | beg << 5 | p << 16); // bic x(p),x(beg),x(p) | |
| 2047 | + b1 = S->tccgen_ind; o(S, 0x14000000); // b | |
| 2048 | + lab1 = S->tccgen_ind; | |
| 2049 | + o(S, 0xd50b7520 | p); // ic ivau,x(p) | |
| 2050 | + o(S, 0x8b000000 | p | p << 5 | isz << 16); // add x(p),x(p),x(isz) | |
| 2051 | + write32le(cur_text_section->data + b1, 0x14000000 | (S->tccgen_ind - b1) >> 2); | |
| 2052 | + o(S, 0xeb00001f | p << 5 | end << 16); // cmp x(p),x(end) | |
| 2053 | + o(S, 0x54ffffa3 | ((lab1 - S->tccgen_ind) << 3 & 0xffffe0)); // b.cc lab1 | |
| 2054 | + o(S, 0xd5033b9f); // dsb ish | |
| 2055 | + o(S, 0xd5033fdf); // isb | |
| 2062 | 2056 | } |
| 2063 | 2057 | |
| 2064 | −ST_FUNC void gen_vla_sp_save(int addr) { | |
| 2065 | − uint32_t r = intr(get_reg(RC_INT)); | |
| 2066 | − o(0x910003e0 | r); // mov x(r),sp | |
| 2067 | − arm64_strx(3, r, 29, addr); | |
| 2058 | +ST_FUNC void gen_vla_sp_save(TCCState *S, int addr) { | |
| 2059 | + uint32_t r = intr(S, get_reg(S, RC_INT)); | |
| 2060 | + o(S, 0x910003e0 | r); // mov x(r),sp | |
| 2061 | + arm64_strx(S, 3, r, 29, addr); | |
| 2068 | 2062 | } |
| 2069 | 2063 | |
| 2070 | −ST_FUNC void gen_vla_sp_restore(int addr) { | |
| 2064 | +ST_FUNC void gen_vla_sp_restore(TCCState *S, int addr) { | |
| 2071 | 2065 | // Use x30 because this function can be called when there |
| 2072 | 2066 | // is a live return value in x0 but there is nothing on |
| 2073 | 2067 | // the value stack to prevent get_reg from returning x0. |
| 2074 | 2068 | uint32_t r = 30; |
| 2075 | − arm64_ldrx(0, 3, r, 29, addr); | |
| 2076 | − o(0x9100001f | r << 5); // mov sp,x(r) | |
| 2069 | + arm64_ldrx(S, 0, 3, r, 29, addr); | |
| 2070 | + o(S, 0x9100001f | r << 5); // mov sp,x(r) | |
| 2077 | 2071 | } |
| 2078 | 2072 | |
| 2079 | −ST_FUNC void gen_vla_alloc(CType *type, int align) { | |
| 2073 | +ST_FUNC void gen_vla_alloc(TCCState *S, CType *type, int align) { | |
| 2080 | 2074 | uint32_t r; |
| 2081 | 2075 | #if defined(CONFIG_TCC_BCHECK) |
| 2082 | − if (tcc_state->do_bounds_check) | |
| 2083 | − vpushv(vtop); | |
| 2076 | + if (S->do_bounds_check) | |
| 2077 | + vpushv(S, S->tccgen_vtop); | |
| 2084 | 2078 | #endif |
| 2085 | − r = intr(gv(RC_INT)); | |
| 2079 | + r = intr(S, gv(S, RC_INT)); | |
| 2086 | 2080 | #if defined(CONFIG_TCC_BCHECK) |
| 2087 | − if (tcc_state->do_bounds_check) | |
| 2088 | − o(0x91004000 | r | r << 5); // add x(r),x(r),#15+1 | |
| 2081 | + if (S->do_bounds_check) | |
| 2082 | + o(S, 0x91004000 | r | r << 5); // add x(r),x(r),#15+1 | |
| 2089 | 2083 | else |
| 2090 | 2084 | #endif |
| 2091 | − o(0x91003c00 | r | r << 5); // add x(r),x(r),#15 | |
| 2092 | − o(0x927cec00 | r | r << 5); // bic x(r),x(r),#15 | |
| 2093 | − o(0xcb2063ff | r << 16); // sub sp,sp,x(r) | |
| 2094 | − vpop(); | |
| 2085 | + o(S, 0x91003c00 | r | r << 5); // add x(r),x(r),#15 | |
| 2086 | + o(S, 0x927cec00 | r | r << 5); // bic x(r),x(r),#15 | |
| 2087 | + o(S, 0xcb2063ff | r << 16); // sub sp,sp,x(r) | |
| 2088 | + vpop(S); | |
| 2095 | 2089 | #if defined(CONFIG_TCC_BCHECK) |
| 2096 | − if (tcc_state->do_bounds_check) { | |
| 2097 | − vpushi(0); | |
| 2098 | − vtop->r = TREG_R(0); | |
| 2099 | − o(0x910003e0 | vtop->r); // mov r0,sp | |
| 2100 | − vswap(); | |
| 2101 | − vpush_helper_func(TOK___bound_new_region); | |
| 2102 | − vrott(3); | |
| 2103 | − gfunc_call(2); | |
| 2104 | − func_bound_add_epilog = 1; | |
| 2090 | + if (S->do_bounds_check) { | |
| 2091 | + vpushi(S, 0); | |
| 2092 | + S->tccgen_vtop->r = TREG_R(0); | |
| 2093 | + o(S, 0x910003e0 | S->tccgen_vtop->r); // mov r0,sp | |
| 2094 | + vswap(S); | |
| 2095 | + vpush_helper_func(S, TOK___bound_new_region); | |
| 2096 | + vrott(S, 3); | |
| 2097 | + gfunc_call(S, 2); | |
| 2098 | + S->func_bound_add_epilog = 1; | |
| 2105 | 2099 | } |
| 2106 | 2100 | #endif |
| 2107 | 2101 | } |
| @@ -90,18 +90,18 @@ int gotplt_entry_type (int reloc_type) · 89 unmodified lines | ||
| 90 | 90 | return -1; |
| 91 | 91 | } |
| 92 | 92 | |
| 93 | −ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_attr *attr) | |
| 93 | +ST_FUNC unsigned create_plt_entry(TCCState *S, unsigned got_offset, struct sym_attr *attr) | |
| 94 | 94 | { |
| 95 | − Section *plt = s1->plt; | |
| 95 | + Section *plt = S->plt; | |
| 96 | 96 | uint8_t *p; |
| 97 | 97 | unsigned plt_offset; |
| 98 | 98 | |
| 99 | 99 | if (plt->data_offset == 0) { |
| 100 | − section_ptr_add(plt, 32); | |
| 100 | + section_ptr_add(S, plt, 32); | |
| 101 | 101 | } |
| 102 | 102 | plt_offset = plt->data_offset; |
| 103 | 103 | |
| 104 | − p = section_ptr_add(plt, 16); | |
| 104 | + p = section_ptr_add(S, plt, 16); | |
| 105 | 105 | write32le(p, got_offset); |
| 106 | 106 | write32le(p + 4, (uint64_t) got_offset >> 32); |
| 107 | 107 | return plt_offset; |
| @@ -109,22 +109,22 @@ ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_ · 1 unmodified line | ||
| 109 | 109 | |
| 110 | 110 | /* relocate the PLT: compute addresses and offsets in the PLT now that final |
| 111 | 111 | address for PLT and GOT are known (see fill_program_header) */ |
| 112 | −ST_FUNC void relocate_plt(TCCState *s1) | |
| 112 | +ST_FUNC void relocate_plt(TCCState *S) | |
| 113 | 113 | { |
| 114 | 114 | uint8_t *p, *p_end; |
| 115 | 115 | |
| 116 | − if (!s1->plt) | |
| 116 | + if (!S->plt) | |
| 117 | 117 | return; |
| 118 | 118 | |
| 119 | − p = s1->plt->data; | |
| 120 | − p_end = p + s1->plt->data_offset; | |
| 119 | + p = S->plt->data; | |
| 120 | + p_end = p + S->plt->data_offset; | |
| 121 | 121 | |
| 122 | 122 | if (p < p_end) { |
| 123 | − uint64_t plt = s1->plt->sh_addr; | |
| 124 | − uint64_t got = s1->got->sh_addr + 16; | |
| 123 | + uint64_t plt = S->plt->sh_addr; | |
| 124 | + uint64_t got = S->got->sh_addr + 16; | |
| 125 | 125 | uint64_t off = (got >> 12) - (plt >> 12); |
| 126 | 126 | if ((off + ((uint32_t)1 << 20)) >> 21) |
| 127 | − tcc_error("Failed relocating PLT (off=0x%lx, got=0x%lx, plt=0x%lx)", (long)off, (long)got, (long)plt); | |
| 127 | + tcc_error(S, "Failed relocating PLT (off=0x%lx, got=0x%lx, plt=0x%lx)", (long)off, (long)got, (long)plt); | |
| 128 | 128 | write32le(p, 0xa9bf7bf0); // stp x16,x30,[sp,#-16]! |
| 129 | 129 | write32le(p + 4, (0x90000010 | // adrp x16,... |
| 130 | 130 | (off & 0x1ffffc) << 3 | (off & 3) << 29)); |
| @@ -137,13 +137,13 @@ ST_FUNC void relocate_plt(TCCState *s1) · 6 unmodified lines | ||
| 137 | 137 | write32le(p + 24, 0xd503201f); // nop |
| 138 | 138 | write32le(p + 28, 0xd503201f); // nop |
| 139 | 139 | p += 32; |
| 140 | − got = s1->got->sh_addr; | |
| 140 | + got = S->got->sh_addr; | |
| 141 | 141 | while (p < p_end) { |
| 142 | − uint64_t pc = plt + (p - s1->plt->data); | |
| 142 | + uint64_t pc = plt + (p - S->plt->data); | |
| 143 | 143 | uint64_t addr = got + read64le(p); |
| 144 | 144 | uint64_t off = (addr >> 12) - (pc >> 12); |
| 145 | 145 | if ((off + ((uint32_t)1 << 20)) >> 21) |
| 146 | − tcc_error("Failed relocating PLT (off=0x%lx, addr=0x%lx, pc=0x%lx)", (long)off, (long)addr, (long)pc); | |
| 146 | + tcc_error(S, "Failed relocating PLT (off=0x%lx, addr=0x%lx, pc=0x%lx)", (long)off, (long)addr, (long)pc); | |
| 147 | 147 | write32le(p, (0x90000010 | // adrp x16,... |
| 148 | 148 | (off & 0x1ffffc) << 3 | (off & 3) << 29)); |
| 149 | 149 | write32le(p + 4, (0xf9400211 | // ldr x17,[x16,#...] |
| @@ -155,16 +155,16 @@ ST_FUNC void relocate_plt(TCCState *s1) · 5 unmodified lines | ||
| 155 | 155 | } |
| 156 | 156 | } |
| 157 | 157 | |
| 158 | − if (s1->plt->reloc) { | |
| 158 | + if (S->plt->reloc) { | |
| 159 | 159 | ElfW_Rel *rel; |
| 160 | − p = s1->got->data; | |
| 161 | − for_each_elem(s1->plt->reloc, 0, rel, ElfW_Rel) { | |
| 162 | − write64le(p + rel->r_offset, s1->plt->sh_addr); | |
| 160 | + p = S->got->data; | |
| 161 | + for_each_elem(S->plt->reloc, 0, rel, ElfW_Rel) { | |
| 162 | + write64le(p + rel->r_offset, S->plt->sh_addr); | |
| 163 | 163 | } |
| 164 | 164 | } |
| 165 | 165 | } |
| 166 | 166 | |
| 167 | −void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 167 | +void relocate(TCCState *S, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 168 | 168 | { |
| 169 | 169 | int sym_index = ELFW(R_SYM)(rel->r_info), esym_index; |
| 170 | 170 | #ifdef DEBUG_RELOC |
| @@ -173,8 +173,8 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 2 unmodified lines | ||
| 173 | 173 | |
| 174 | 174 | switch(type) { |
| 175 | 175 | case R_AARCH64_ABS64: |
| 176 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 177 | − esym_index = get_sym_attr(s1, sym_index, 0)->dyn_index; | |
| 176 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 177 | + esym_index = get_sym_attr(S, sym_index, 0)->dyn_index; | |
| 178 | 178 | qrel->r_offset = rel->r_offset; |
| 179 | 179 | if (esym_index) { |
| 180 | 180 | qrel->r_info = ELFW(R_INFO)(esym_index, R_AARCH64_ABS64); |
| @@ -190,7 +190,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 9 unmodified lines | ||
| 190 | 190 | add64le(ptr, val); |
| 191 | 191 | return; |
| 192 | 192 | case R_AARCH64_ABS32: |
| 193 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 193 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 194 | 194 | /* XXX: this logic may depend on TCC's codegen |
| 195 | 195 | now TCC uses R_AARCH64_RELATIVE even for a 64bit pointer */ |
| 196 | 196 | qrel->r_offset = rel->r_offset; |
| @@ -202,9 +202,9 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 5 unmodified lines | ||
| 202 | 202 | add32le(ptr, val); |
| 203 | 203 | return; |
| 204 | 204 | case R_AARCH64_PREL32: |
| 205 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 205 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 206 | 206 | /* DLL relocation */ |
| 207 | − esym_index = get_sym_attr(s1, sym_index, 0)->dyn_index; | |
| 207 | + esym_index = get_sym_attr(S, sym_index, 0)->dyn_index; | |
| 208 | 208 | if (esym_index) { |
| 209 | 209 | qrel->r_offset = rel->r_offset; |
| 210 | 210 | qrel->r_info = ELFW(R_INFO)(esym_index, R_AARCH64_PREL32); |
| @@ -235,7 +235,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 24 unmodified lines | ||
| 235 | 235 | case R_AARCH64_ADR_PREL_PG_HI21: { |
| 236 | 236 | uint64_t off = (val >> 12) - (addr >> 12); |
| 237 | 237 | if ((off + ((uint64_t)1 << 20)) >> 21) |
| 238 | − tcc_error("R_AARCH64_ADR_PREL_PG_HI21 relocation failed"); | |
| 238 | + tcc_error(S, "R_AARCH64_ADR_PREL_PG_HI21 relocation failed"); | |
| 239 | 239 | write32le(ptr, ((read32le(ptr) & 0x9f00001f) | |
| 240 | 240 | (off & 0x1ffffc) << 3 | (off & 3) << 29)); |
| 241 | 241 | return; |
| @@ -268,7 +268,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 26 unmodified lines | ||
| 268 | 268 | (char *) symtab_section->link->data + sym->st_name); |
| 269 | 269 | #endif |
| 270 | 270 | if (((val - addr) + ((uint64_t)1 << 27)) & ~(uint64_t)0xffffffc) |
| 271 | − tcc_error("R_AARCH64_(JUMP|CALL)26 relocation failed" | |
| 271 | + tcc_error(S, "R_AARCH64_(JUMP|CALL)26 relocation failed" | |
| 272 | 272 | " (val=%lx, addr=%lx)", (long)val, (long)addr); |
| 273 | 273 | write32le(ptr, (0x14000000 | |
| 274 | 274 | (uint32_t)(type == R_AARCH64_CALL26) << 31 | |
| @@ -276,10 +276,10 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 1 unmodified line | ||
| 276 | 276 | return; |
| 277 | 277 | case R_AARCH64_ADR_GOT_PAGE: { |
| 278 | 278 | uint64_t off = |
| 279 | − (((s1->got->sh_addr + | |
| 280 | − get_sym_attr(s1, sym_index, 0)->got_offset) >> 12) - (addr >> 12)); | |
| 279 | + (((S->got->sh_addr + | |
| 280 | + get_sym_attr(S, sym_index, 0)->got_offset) >> 12) - (addr >> 12)); | |
| 281 | 281 | if ((off + ((uint64_t)1 << 20)) >> 21) |
| 282 | − tcc_error("R_AARCH64_ADR_GOT_PAGE relocation failed"); | |
| 282 | + tcc_error(S, "R_AARCH64_ADR_GOT_PAGE relocation failed"); | |
| 283 | 283 | write32le(ptr, ((read32le(ptr) & 0x9f00001f) | |
| 284 | 284 | (off & 0x1ffffc) << 3 | (off & 3) << 29)); |
| 285 | 285 | return; |
| @@ -287,8 +287,8 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 1 unmodified line | ||
| 287 | 287 | case R_AARCH64_LD64_GOT_LO12_NC: |
| 288 | 288 | write32le(ptr, |
| 289 | 289 | ((read32le(ptr) & 0xfff803ff) | |
| 290 | − ((s1->got->sh_addr + | |
| 291 | − get_sym_attr(s1, sym_index, 0)->got_offset) & 0xff8) << 7)); | |
| 290 | + ((S->got->sh_addr + | |
| 291 | + get_sym_attr(S, sym_index, 0)->got_offset) & 0xff8) << 7)); | |
| 292 | 292 | return; |
| 293 | 293 | case R_AARCH64_COPY: |
| 294 | 294 | return; |
| @@ -304,7 +304,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 9 unmodified lines | ||
| 304 | 304 | return; |
| 305 | 305 | case R_AARCH64_RELATIVE: |
| 306 | 306 | #ifdef TCC_TARGET_PE |
| 307 | − add32le(ptr, val - s1->pe_imagebase); | |
| 307 | + add32le(ptr, val - S->pe_imagebase); | |
| 308 | 308 | #endif |
| 309 | 309 | /* do nothing */ |
| 310 | 310 | return; |
| @@ -172,7 +172,7 @@ int TotalBytesPushedOnStack; · 171 unmodified lines | ||
| 172 | 172 | #define ALWAYS_ASSERT(x) \ |
| 173 | 173 | do {\ |
| 174 | 174 | if (!(x))\ |
| 175 | − tcc_error("internal compiler error file at %s:%d", __FILE__, __LINE__);\ | |
| 175 | + tcc_error(S, "internal compiler error file at %s:%d", __FILE__, __LINE__);\ | |
| 176 | 176 | } while (0) |
| 177 | 177 | |
| 178 | 178 | /******************************************************/ |
| @@ -186,27 +186,27 @@ static int C67_compare_reg; · 7 unmodified lines | ||
| 186 | 186 | FILE *f = NULL; |
| 187 | 187 | #endif |
| 188 | 188 | |
| 189 | −void C67_g(int c) | |
| 189 | +void C67_g(TCCState* S, int c) | |
| 190 | 190 | { |
| 191 | 191 | int ind1; |
| 192 | − if (nocode_wanted) | |
| 192 | + if (S->tccgen_nocode_wanted) | |
| 193 | 193 | return; |
| 194 | 194 | #ifdef ASSEMBLY_LISTING_C67 |
| 195 | 195 | fprintf(f, " %08X", c); |
| 196 | 196 | #endif |
| 197 | − ind1 = ind + 4; | |
| 197 | + ind1 = S->tccgen_ind + 4; | |
| 198 | 198 | if (ind1 > (int) cur_text_section->data_allocated) |
| 199 | − section_realloc(cur_text_section, ind1); | |
| 200 | − cur_text_section->data[ind] = c & 0xff; | |
| 201 | − cur_text_section->data[ind + 1] = (c >> 8) & 0xff; | |
| 202 | − cur_text_section->data[ind + 2] = (c >> 16) & 0xff; | |
| 203 | − cur_text_section->data[ind + 3] = (c >> 24) & 0xff; | |
| 204 | − ind = ind1; | |
| 199 | + section_realloc(S, cur_text_section, ind1); | |
| 200 | + cur_text_section->data[S->tccgen_ind] = c & 0xff; | |
| 201 | + cur_text_section->data[S->tccgen_ind + 1] = (c >> 8) & 0xff; | |
| 202 | + cur_text_section->data[S->tccgen_ind + 2] = (c >> 16) & 0xff; | |
| 203 | + cur_text_section->data[S->tccgen_ind + 3] = (c >> 24) & 0xff; | |
| 204 | + S->tccgen_ind = ind1; | |
| 205 | 205 | } |
| 206 | 206 | |
| 207 | 207 | |
| 208 | 208 | /* output a symbol and patch all calls to it */ |
| 209 | −void gsym_addr(int t, int a) | |
| 209 | +void gsym_addr(TCCState* S, int t, int a) | |
| 210 | 210 | { |
| 211 | 211 | int n, *ptr; |
| 212 | 212 | while (t) { |
| @@ -220,9 +220,9 @@ void gsym_addr(int t, int a) · 7 unmodified lines | ||
| 220 | 220 | |
| 221 | 221 | // define a label that will be relocated |
| 222 | 222 | |
| 223 | − sym = get_sym_ref(&char_pointer_type, cur_text_section, a, 0); | |
| 224 | − greloc(cur_text_section, sym, t, R_C60LO16); | |
| 225 | − greloc(cur_text_section, sym, t + 4, R_C60HI16); | |
| 223 | + sym = get_sym_ref(S, &S->tccgen_char_pointer_type, cur_text_section, a, 0); | |
| 224 | + greloc(S, cur_text_section, sym, t, R_C60LO16); | |
| 225 | + greloc(S, cur_text_section, sym, t + 4, R_C60HI16); | |
| 226 | 226 | |
| 227 | 227 | // clear out where the pointer was |
| 228 | 228 | |
| @@ -255,7 +255,7 @@ int ConvertRegToRegClass(int r) · 26 unmodified lines | ||
| 255 | 255 | |
| 256 | 256 | // map TCC reg to C67 reg number |
| 257 | 257 | |
| 258 | −int C67_map_regn(int r) | |
| 258 | +int C67_map_regn(TCCState* S, int r) | |
| 259 | 259 | { |
| 260 | 260 | if (r == 0) // normal tcc regs |
| 261 | 261 | return 0x2; // A2 |
| @@ -296,7 +296,7 @@ int C67_map_regn(int r) · 34 unmodified lines | ||
| 296 | 296 | // tcc reg 1 -> A3 -> X |
| 297 | 297 | // tcc reg B2 -> 3 |
| 298 | 298 | |
| 299 | −int C67_map_regc(int r) | |
| 299 | +int C67_map_regc(TCCState* S, int r) | |
| 300 | 300 | { |
| 301 | 301 | if (r == 0) // normal tcc regs |
| 302 | 302 | return 0x5; |
| @@ -317,7 +317,7 @@ int C67_map_regc(int r) · 14 unmodified lines | ||
| 317 | 317 | |
| 318 | 318 | // map TCC reg to C67 reg side A or B |
| 319 | 319 | |
| 320 | −int C67_map_regs(int r) | |
| 320 | +int C67_map_regs(TCCState* S, int r) | |
| 321 | 321 | { |
| 322 | 322 | if (r == 0) // normal tcc regs |
| 323 | 323 | return 0x0; |
| @@ -345,7 +345,7 @@ int C67_map_regs(int r) · 21 unmodified lines | ||
| 345 | 345 | return 0; |
| 346 | 346 | } |
| 347 | 347 | |
| 348 | −int C67_map_S12(char *s) | |
| 348 | +int C67_map_S12(TCCState* S, char *s) | |
| 349 | 349 | { |
| 350 | 350 | if (strstr(s, ".S1") != NULL) |
| 351 | 351 | return 0; |
| @@ -357,7 +357,7 @@ int C67_map_S12(char *s) · 5 unmodified lines | ||
| 357 | 357 | return 0; |
| 358 | 358 | } |
| 359 | 359 | |
| 360 | −int C67_map_D12(char *s) | |
| 360 | +int C67_map_D12(TCCState* S, char *s) | |
| 361 | 361 | { |
| 362 | 362 | if (strstr(s, ".D1") != NULL) |
| 363 | 363 | return 0; |
| @@ -371,7 +371,7 @@ int C67_map_D12(char *s) · 7 unmodified lines | ||
| 371 | 371 | |
| 372 | 372 | |
| 373 | 373 | |
| 374 | −void C67_asm(const char *s, int a, int b, int c) | |
| 374 | +void C67_asm(TCCState* S, const char *s, int a, int b, int c) | |
| 375 | 375 | { |
| 376 | 376 | BOOL xpath; |
| 377 | 377 | |
| @@ -383,14 +383,14 @@ void C67_asm(const char *s, int a, int b, int c) · 5 unmodified lines | ||
| 383 | 383 | #endif |
| 384 | 384 | |
| 385 | 385 | if (strstr(s, "MVKL") == s) { |
| 386 | − C67_g((C67_map_regn(b) << 23) | | |
| 387 | − ((a & 0xffff) << 7) | (0x0a << 2) | (C67_map_regs(b) << 1)); | |
| 386 | + C67_g(S, (C67_map_regn(S, b) << 23) | | |
| 387 | + ((a & 0xffff) << 7) | (0x0a << 2) | (C67_map_regs(S, b) << 1)); | |
| 388 | 388 | } else if (strstr(s, "MVKH") == s) { |
| 389 | − C67_g((C67_map_regn(b) << 23) | | |
| 389 | + C67_g(S, (C67_map_regn(S, b) << 23) | | |
| 390 | 390 | (((a >> 16) & 0xffff) << 7) | |
| 391 | − (0x1a << 2) | (C67_map_regs(b) << 1)); | |
| 391 | + (0x1a << 2) | (C67_map_regs(S, b) << 1)); | |
| 392 | 392 | } else if (strstr(s, "STW.D SP POST DEC") == s) { |
| 393 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 393 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 394 | 394 | (15 << 18) | //SP B15 |
| 395 | 395 | (2 << 13) | //ucst5 (must keep 8 byte boundary !!) |
| 396 | 396 | (0xa << 9) | //mode a = post dec ucst |
| @@ -398,10 +398,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 398 | 398 | (1 << 7) | //y D1/D2 use B side |
| 399 | 399 | (7 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 400 | 400 | (1 << 2) | //opcode |
| 401 | − (C67_map_regs(a) << 1) | //side of src | |
| 401 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 402 | 402 | (0 << 0)); //parallel |
| 403 | 403 | } else if (strstr(s, "STB.D *+SP[A0]") == s) { |
| 404 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 404 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 405 | 405 | (15 << 18) | //base reg A15 |
| 406 | 406 | (0 << 13) | //offset reg A0 |
| 407 | 407 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -409,10 +409,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 409 | 409 | (0 << 7) | //y D1/D2 A side |
| 410 | 410 | (3 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 411 | 411 | (1 << 2) | //opcode |
| 412 | − (C67_map_regs(a) << 1) | //side of src | |
| 412 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 413 | 413 | (0 << 0)); //parallel |
| 414 | 414 | } else if (strstr(s, "STH.D *+SP[A0]") == s) { |
| 415 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 415 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 416 | 416 | (15 << 18) | //base reg A15 |
| 417 | 417 | (0 << 13) | //offset reg A0 |
| 418 | 418 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -420,10 +420,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 420 | 420 | (0 << 7) | //y D1/D2 A side |
| 421 | 421 | (5 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 422 | 422 | (1 << 2) | //opcode |
| 423 | − (C67_map_regs(a) << 1) | //side of src | |
| 423 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 424 | 424 | (0 << 0)); //parallel |
| 425 | 425 | } else if (strstr(s, "STB.D *+SP[A0]") == s) { |
| 426 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 426 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 427 | 427 | (15 << 18) | //base reg A15 |
| 428 | 428 | (0 << 13) | //offset reg A0 |
| 429 | 429 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -431,10 +431,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 431 | 431 | (0 << 7) | //y D1/D2 A side |
| 432 | 432 | (3 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 433 | 433 | (1 << 2) | //opcode |
| 434 | − (C67_map_regs(a) << 1) | //side of src | |
| 434 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 435 | 435 | (0 << 0)); //parallel |
| 436 | 436 | } else if (strstr(s, "STH.D *+SP[A0]") == s) { |
| 437 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 437 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 438 | 438 | (15 << 18) | //base reg A15 |
| 439 | 439 | (0 << 13) | //offset reg A0 |
| 440 | 440 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -442,10 +442,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 442 | 442 | (0 << 7) | //y D1/D2 A side |
| 443 | 443 | (5 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 444 | 444 | (1 << 2) | //opcode |
| 445 | − (C67_map_regs(a) << 1) | //side of src | |
| 445 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 446 | 446 | (0 << 0)); //parallel |
| 447 | 447 | } else if (strstr(s, "STW.D *+SP[A0]") == s) { |
| 448 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 448 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 449 | 449 | (15 << 18) | //base reg A15 |
| 450 | 450 | (0 << 13) | //offset reg A0 |
| 451 | 451 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -453,55 +453,55 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 453 | 453 | (0 << 7) | //y D1/D2 A side |
| 454 | 454 | (7 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 455 | 455 | (1 << 2) | //opcode |
| 456 | − (C67_map_regs(a) << 1) | //side of src | |
| 456 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 457 | 457 | (0 << 0)); //parallel |
| 458 | 458 | } else if (strstr(s, "STW.D *") == s) { |
| 459 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 460 | − (C67_map_regn(b) << 18) | //base reg A0 | |
| 459 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 460 | + (C67_map_regn(S, b) << 18) | //base reg A0 | |
| 461 | 461 | (0 << 13) | //cst5 |
| 462 | 462 | (1 << 9) | //mode 1 = pos cst offset |
| 463 | 463 | (0 << 8) | //r (LDDW bit 0) |
| 464 | − (C67_map_regs(b) << 7) | //y D1/D2 base reg side | |
| 464 | + (C67_map_regs(S, b) << 7) | //y D1/D2 base reg side | |
| 465 | 465 | (7 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 466 | 466 | (1 << 2) | //opcode |
| 467 | − (C67_map_regs(a) << 1) | //side of src | |
| 467 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 468 | 468 | (0 << 0)); //parallel |
| 469 | 469 | } else if (strstr(s, "STH.D *") == s) { |
| 470 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 471 | − (C67_map_regn(b) << 18) | //base reg A0 | |
| 470 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 471 | + (C67_map_regn(S, b) << 18) | //base reg A0 | |
| 472 | 472 | (0 << 13) | //cst5 |
| 473 | 473 | (1 << 9) | //mode 1 = pos cst offset |
| 474 | 474 | (0 << 8) | //r (LDDW bit 0) |
| 475 | − (C67_map_regs(b) << 7) | //y D1/D2 base reg side | |
| 475 | + (C67_map_regs(S, b) << 7) | //y D1/D2 base reg side | |
| 476 | 476 | (5 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 477 | 477 | (1 << 2) | //opcode |
| 478 | − (C67_map_regs(a) << 1) | //side of src | |
| 478 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 479 | 479 | (0 << 0)); //parallel |
| 480 | 480 | } else if (strstr(s, "STB.D *") == s) { |
| 481 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 482 | − (C67_map_regn(b) << 18) | //base reg A0 | |
| 481 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 482 | + (C67_map_regn(S, b) << 18) | //base reg A0 | |
| 483 | 483 | (0 << 13) | //cst5 |
| 484 | 484 | (1 << 9) | //mode 1 = pos cst offset |
| 485 | 485 | (0 << 8) | //r (LDDW bit 0) |
| 486 | − (C67_map_regs(b) << 7) | //y D1/D2 base reg side | |
| 486 | + (C67_map_regs(S, b) << 7) | //y D1/D2 base reg side | |
| 487 | 487 | (3 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 488 | 488 | (1 << 2) | //opcode |
| 489 | − (C67_map_regs(a) << 1) | //side of src | |
| 489 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 490 | 490 | (0 << 0)); //parallel |
| 491 | 491 | } else if (strstr(s, "STW.D +*") == s) { |
| 492 | 492 | ALWAYS_ASSERT(c < 32); |
| 493 | − C67_g((C67_map_regn(a) << 23) | //src | |
| 494 | − (C67_map_regn(b) << 18) | //base reg A0 | |
| 493 | + C67_g(S, (C67_map_regn(S, a) << 23) | //src | |
| 494 | + (C67_map_regn(S, b) << 18) | //base reg A0 | |
| 495 | 495 | (c << 13) | //cst5 |
| 496 | 496 | (1 << 9) | //mode 1 = pos cst offset |
| 497 | 497 | (0 << 8) | //r (LDDW bit 0) |
| 498 | − (C67_map_regs(b) << 7) | //y D1/D2 base reg side | |
| 498 | + (C67_map_regs(S, b) << 7) | //y D1/D2 base reg side | |
| 499 | 499 | (7 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 500 | 500 | (1 << 2) | //opcode |
| 501 | − (C67_map_regs(a) << 1) | //side of src | |
| 501 | + (C67_map_regs(S, a) << 1) | //side of src | |
| 502 | 502 | (0 << 0)); //parallel |
| 503 | 503 | } else if (strstr(s, "LDW.D SP PRE INC") == s) { |
| 504 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 504 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 505 | 505 | (15 << 18) | //base reg B15 |
| 506 | 506 | (2 << 13) | //ucst5 (must keep 8 byte boundary) |
| 507 | 507 | (9 << 9) | //mode 9 = pre inc ucst5 |
| @@ -509,10 +509,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 509 | 509 | (1 << 7) | //y D1/D2 B side |
| 510 | 510 | (6 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 511 | 511 | (1 << 2) | //opcode |
| 512 | − (C67_map_regs(a) << 1) | //side of dst | |
| 512 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 513 | 513 | (0 << 0)); //parallel |
| 514 | 514 | } else if (strstr(s, "LDDW.D SP PRE INC") == s) { |
| 515 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 515 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 516 | 516 | (15 << 18) | //base reg B15 |
| 517 | 517 | (1 << 13) | //ucst5 (must keep 8 byte boundary) |
| 518 | 518 | (9 << 9) | //mode 9 = pre inc ucst5 |
| @@ -520,10 +520,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 520 | 520 | (1 << 7) | //y D1/D2 B side |
| 521 | 521 | (6 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 522 | 522 | (1 << 2) | //opcode |
| 523 | − (C67_map_regs(a) << 1) | //side of dst | |
| 523 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 524 | 524 | (0 << 0)); //parallel |
| 525 | 525 | } else if (strstr(s, "LDW.D *+SP[A0]") == s) { |
| 526 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 526 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 527 | 527 | (15 << 18) | //base reg A15 |
| 528 | 528 | (0 << 13) | //offset reg A0 |
| 529 | 529 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -531,10 +531,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 531 | 531 | (0 << 7) | //y D1/D2 A side |
| 532 | 532 | (6 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 533 | 533 | (1 << 2) | //opcode |
| 534 | − (C67_map_regs(a) << 1) | //side of dst | |
| 534 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 535 | 535 | (0 << 0)); //parallel |
| 536 | 536 | } else if (strstr(s, "LDDW.D *+SP[A0]") == s) { |
| 537 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 537 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 538 | 538 | (15 << 18) | //base reg A15 |
| 539 | 539 | (0 << 13) | //offset reg A0 |
| 540 | 540 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -542,10 +542,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 542 | 542 | (0 << 7) | //y D1/D2 A side |
| 543 | 543 | (6 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 544 | 544 | (1 << 2) | //opcode |
| 545 | − (C67_map_regs(a) << 1) | //side of dst | |
| 545 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 546 | 546 | (0 << 0)); //parallel |
| 547 | 547 | } else if (strstr(s, "LDH.D *+SP[A0]") == s) { |
| 548 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 548 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 549 | 549 | (15 << 18) | //base reg A15 |
| 550 | 550 | (0 << 13) | //offset reg A0 |
| 551 | 551 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -553,10 +553,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 553 | 553 | (0 << 7) | //y D1/D2 A side |
| 554 | 554 | (4 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 555 | 555 | (1 << 2) | //opcode |
| 556 | − (C67_map_regs(a) << 1) | //side of dst | |
| 556 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 557 | 557 | (0 << 0)); //parallel |
| 558 | 558 | } else if (strstr(s, "LDB.D *+SP[A0]") == s) { |
| 559 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 559 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 560 | 560 | (15 << 18) | //base reg A15 |
| 561 | 561 | (0 << 13) | //offset reg A0 |
| 562 | 562 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -564,10 +564,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 564 | 564 | (0 << 7) | //y D1/D2 A side |
| 565 | 565 | (2 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 566 | 566 | (1 << 2) | //opcode |
| 567 | − (C67_map_regs(a) << 1) | //side of dst | |
| 567 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 568 | 568 | (0 << 0)); //parallel |
| 569 | 569 | } else if (strstr(s, "LDHU.D *+SP[A0]") == s) { |
| 570 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 570 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 571 | 571 | (15 << 18) | //base reg A15 |
| 572 | 572 | (0 << 13) | //offset reg A0 |
| 573 | 573 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -575,10 +575,10 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 575 | 575 | (0 << 7) | //y D1/D2 A side |
| 576 | 576 | (0 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 577 | 577 | (1 << 2) | //opcode |
| 578 | − (C67_map_regs(a) << 1) | //side of dst | |
| 578 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 579 | 579 | (0 << 0)); //parallel |
| 580 | 580 | } else if (strstr(s, "LDBU.D *+SP[A0]") == s) { |
| 581 | − C67_g((C67_map_regn(a) << 23) | //dst | |
| 581 | + C67_g(S, (C67_map_regn(S, a) << 23) | //dst | |
| 582 | 582 | (15 << 18) | //base reg A15 |
| 583 | 583 | (0 << 13) | //offset reg A0 |
| 584 | 584 | (5 << 9) | //mode 5 = pos offset, base reg + off reg |
| @@ -586,233 +586,233 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 586 | 586 | (0 << 7) | //y D1/D2 A side |
| 587 | 587 | (1 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 588 | 588 | (1 << 2) | //opcode |
| 589 | − (C67_map_regs(a) << 1) | //side of dst | |
| 589 | + (C67_map_regs(S, a) << 1) | //side of dst | |
| 590 | 590 | (0 << 0)); //parallel |
| 591 | 591 | } else if (strstr(s, "LDW.D *") == s) { |
| 592 | − C67_g((C67_map_regn(b) << 23) | //dst | |
| 593 | − (C67_map_regn(a) << 18) | //base reg A15 | |
| 592 | + C67_g(S, (C67_map_regn(S, b) << 23) | //dst | |
| 593 | + (C67_map_regn(S, a) << 18) | //base reg A15 | |
| 594 | 594 | (0 << 13) | //cst5 |
| 595 | 595 | (1 << 9) | //mode 1 = pos cst offset |
| 596 | 596 | (0 << 8) | //r (LDDW bit 0) |
| 597 | − (C67_map_regs(a) << 7) | //y D1/D2 src side | |
| 597 | + (C67_map_regs(S, a) << 7) | //y D1/D2 src side | |
| 598 | 598 | (6 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 599 | 599 | (1 << 2) | //opcode |
| 600 | − (C67_map_regs(b) << 1) | //side of dst | |
| 600 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 601 | 601 | (0 << 0)); //parallel |
| 602 | 602 | } else if (strstr(s, "LDDW.D *") == s) { |
| 603 | − C67_g((C67_map_regn(b) << 23) | //dst | |
| 604 | − (C67_map_regn(a) << 18) | //base reg A15 | |
| 603 | + C67_g(S, (C67_map_regn(S, b) << 23) | //dst | |
| 604 | + (C67_map_regn(S, a) << 18) | //base reg A15 | |
| 605 | 605 | (0 << 13) | //cst5 |
| 606 | 606 | (1 << 9) | //mode 1 = pos cst offset |
| 607 | 607 | (1 << 8) | //r (LDDW bit 1) |
| 608 | − (C67_map_regs(a) << 7) | //y D1/D2 src side | |
| 608 | + (C67_map_regs(S, a) << 7) | //y D1/D2 src side | |
| 609 | 609 | (6 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 610 | 610 | (1 << 2) | //opcode |
| 611 | − (C67_map_regs(b) << 1) | //side of dst | |
| 611 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 612 | 612 | (0 << 0)); //parallel |
| 613 | 613 | } else if (strstr(s, "LDH.D *") == s) { |
| 614 | − C67_g((C67_map_regn(b) << 23) | //dst | |
| 615 | − (C67_map_regn(a) << 18) | //base reg A15 | |
| 614 | + C67_g(S, (C67_map_regn(S, b) << 23) | //dst | |
| 615 | + (C67_map_regn(S, a) << 18) | //base reg A15 | |
| 616 | 616 | (0 << 13) | //cst5 |
| 617 | 617 | (1 << 9) | //mode 1 = pos cst offset |
| 618 | 618 | (0 << 8) | //r (LDDW bit 0) |
| 619 | − (C67_map_regs(a) << 7) | //y D1/D2 src side | |
| 619 | + (C67_map_regs(S, a) << 7) | //y D1/D2 src side | |
| 620 | 620 | (4 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 621 | 621 | (1 << 2) | //opcode |
| 622 | − (C67_map_regs(b) << 1) | //side of dst | |
| 622 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 623 | 623 | (0 << 0)); //parallel |
| 624 | 624 | } else if (strstr(s, "LDB.D *") == s) { |
| 625 | − C67_g((C67_map_regn(b) << 23) | //dst | |
| 626 | − (C67_map_regn(a) << 18) | //base reg A15 | |
| 625 | + C67_g(S, (C67_map_regn(S, b) << 23) | //dst | |
| 626 | + (C67_map_regn(S, a) << 18) | //base reg A15 | |
| 627 | 627 | (0 << 13) | //cst5 |
| 628 | 628 | (1 << 9) | //mode 1 = pos cst offset |
| 629 | 629 | (0 << 8) | //r (LDDW bit 0) |
| 630 | − (C67_map_regs(a) << 7) | //y D1/D2 src side | |
| 630 | + (C67_map_regs(S, a) << 7) | //y D1/D2 src side | |
| 631 | 631 | (2 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 632 | 632 | (1 << 2) | //opcode |
| 633 | − (C67_map_regs(b) << 1) | //side of dst | |
| 633 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 634 | 634 | (0 << 0)); //parallel |
| 635 | 635 | } else if (strstr(s, "LDHU.D *") == s) { |
| 636 | − C67_g((C67_map_regn(b) << 23) | //dst | |
| 637 | − (C67_map_regn(a) << 18) | //base reg A15 | |
| 636 | + C67_g(S, (C67_map_regn(S, b) << 23) | //dst | |
| 637 | + (C67_map_regn(S, a) << 18) | //base reg A15 | |
| 638 | 638 | (0 << 13) | //cst5 |
| 639 | 639 | (1 << 9) | //mode 1 = pos cst offset |
| 640 | 640 | (0 << 8) | //r (LDDW bit 0) |
| 641 | − (C67_map_regs(a) << 7) | //y D1/D2 src side | |
| 641 | + (C67_map_regs(S, a) << 7) | //y D1/D2 src side | |
| 642 | 642 | (0 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 643 | 643 | (1 << 2) | //opcode |
| 644 | − (C67_map_regs(b) << 1) | //side of dst | |
| 644 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 645 | 645 | (0 << 0)); //parallel |
| 646 | 646 | } else if (strstr(s, "LDBU.D *") == s) { |
| 647 | − C67_g((C67_map_regn(b) << 23) | //dst | |
| 648 | − (C67_map_regn(a) << 18) | //base reg A15 | |
| 647 | + C67_g(S, (C67_map_regn(S, b) << 23) | //dst | |
| 648 | + (C67_map_regn(S, a) << 18) | //base reg A15 | |
| 649 | 649 | (0 << 13) | //cst5 |
| 650 | 650 | (1 << 9) | //mode 1 = pos cst offset |
| 651 | 651 | (0 << 8) | //r (LDDW bit 0) |
| 652 | − (C67_map_regs(a) << 7) | //y D1/D2 src side | |
| 652 | + (C67_map_regs(S, a) << 7) | //y D1/D2 src side | |
| 653 | 653 | (1 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 654 | 654 | (1 << 2) | //opcode |
| 655 | − (C67_map_regs(b) << 1) | //side of dst | |
| 655 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 656 | 656 | (0 << 0)); //parallel |
| 657 | 657 | } else if (strstr(s, "LDW.D +*") == s) { |
| 658 | − C67_g((C67_map_regn(b) << 23) | //dst | |
| 659 | − (C67_map_regn(a) << 18) | //base reg A15 | |
| 658 | + C67_g(S, (C67_map_regn(S, b) << 23) | //dst | |
| 659 | + (C67_map_regn(S, a) << 18) | //base reg A15 | |
| 660 | 660 | (1 << 13) | //cst5 |
| 661 | 661 | (1 << 9) | //mode 1 = pos cst offset |
| 662 | 662 | (0 << 8) | //r (LDDW bit 0) |
| 663 | − (C67_map_regs(a) << 7) | //y D1/D2 src side | |
| 663 | + (C67_map_regs(S, a) << 7) | //y D1/D2 src side | |
| 664 | 664 | (6 << 4) | //ldst 3=STB, 5=STH 5, 7=STW, 6=LDW 4=LDH 2=LDB 0=LDHU 1=LDBU |
| 665 | 665 | (1 << 2) | //opcode |
| 666 | − (C67_map_regs(b) << 1) | //side of dst | |
| 666 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 667 | 667 | (0 << 0)); //parallel |
| 668 | 668 | } else if (strstr(s, "CMPLTSP") == s) { |
| 669 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 670 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 669 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 670 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 671 | 671 | |
| 672 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 673 | − (C67_map_regn(b) << 18) | //src2 | |
| 674 | − (C67_map_regn(a) << 13) | //src1 | |
| 672 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 673 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 674 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 675 | 675 | (xpath << 12) | //x use cross path for src2 |
| 676 | 676 | (0x3a << 6) | //opcode |
| 677 | 677 | (0x8 << 2) | //opcode fixed |
| 678 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 678 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 679 | 679 | (0 << 0)); //parallel |
| 680 | 680 | } else if (strstr(s, "CMPGTSP") == s) { |
| 681 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 682 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 681 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 682 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 683 | 683 | |
| 684 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 685 | − (C67_map_regn(b) << 18) | //src2 | |
| 686 | − (C67_map_regn(a) << 13) | //src1 | |
| 684 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 685 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 686 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 687 | 687 | (xpath << 12) | //x use cross path for src2 |
| 688 | 688 | (0x39 << 6) | //opcode |
| 689 | 689 | (0x8 << 2) | //opcode fixed |
| 690 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 690 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 691 | 691 | (0 << 0)); //parallel |
| 692 | 692 | } else if (strstr(s, "CMPEQSP") == s) { |
| 693 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 694 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 693 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 694 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 695 | 695 | |
| 696 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 697 | − (C67_map_regn(b) << 18) | //src2 | |
| 698 | − (C67_map_regn(a) << 13) | //src1 | |
| 696 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 697 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 698 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 699 | 699 | (xpath << 12) | //x use cross path for src2 |
| 700 | 700 | (0x38 << 6) | //opcode |
| 701 | 701 | (0x8 << 2) | //opcode fixed |
| 702 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 702 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 703 | 703 | (0 << 0)); //parallel |
| 704 | 704 | } |
| 705 | 705 | |
| 706 | 706 | else if (strstr(s, "CMPLTDP") == s) { |
| 707 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 708 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 707 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 708 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 709 | 709 | |
| 710 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 711 | − (C67_map_regn(b) << 18) | //src2 | |
| 712 | − (C67_map_regn(a) << 13) | //src1 | |
| 710 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 711 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 712 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 713 | 713 | (xpath << 12) | //x use cross path for src2 |
| 714 | 714 | (0x2a << 6) | //opcode |
| 715 | 715 | (0x8 << 2) | //opcode fixed |
| 716 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 716 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 717 | 717 | (0 << 0)); //parallel |
| 718 | 718 | } else if (strstr(s, "CMPGTDP") == s) { |
| 719 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 720 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 719 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 720 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 721 | 721 | |
| 722 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 723 | − (C67_map_regn(b) << 18) | //src2 | |
| 724 | − (C67_map_regn(a) << 13) | //src1 | |
| 722 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 723 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 724 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 725 | 725 | (xpath << 12) | //x use cross path for src2 |
| 726 | 726 | (0x29 << 6) | //opcode |
| 727 | 727 | (0x8 << 2) | //opcode fixed |
| 728 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 728 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 729 | 729 | (0 << 0)); //parallel |
| 730 | 730 | } else if (strstr(s, "CMPEQDP") == s) { |
| 731 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 732 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 731 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 732 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 733 | 733 | |
| 734 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 735 | − (C67_map_regn(b) << 18) | //src2 | |
| 736 | − (C67_map_regn(a) << 13) | //src1 | |
| 734 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 735 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 736 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 737 | 737 | (xpath << 12) | //x use cross path for src2 |
| 738 | 738 | (0x28 << 6) | //opcode |
| 739 | 739 | (0x8 << 2) | //opcode fixed |
| 740 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 740 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 741 | 741 | (0 << 0)); //parallel |
| 742 | 742 | } else if (strstr(s, "CMPLT") == s) { |
| 743 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 744 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 743 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 744 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 745 | 745 | |
| 746 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 747 | − (C67_map_regn(b) << 18) | //src2 | |
| 748 | − (C67_map_regn(a) << 13) | //src1 | |
| 746 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 747 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 748 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 749 | 749 | (xpath << 12) | //x use cross path for src2 |
| 750 | 750 | (0x57 << 5) | //opcode |
| 751 | 751 | (0x6 << 2) | //opcode fixed |
| 752 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 752 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 753 | 753 | (0 << 0)); //parallel |
| 754 | 754 | } else if (strstr(s, "CMPGT") == s) { |
| 755 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 756 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 755 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 756 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 757 | 757 | |
| 758 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 759 | − (C67_map_regn(b) << 18) | //src2 | |
| 760 | − (C67_map_regn(a) << 13) | //src1 | |
| 758 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 759 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 760 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 761 | 761 | (xpath << 12) | //x use cross path for src2 |
| 762 | 762 | (0x47 << 5) | //opcode |
| 763 | 763 | (0x6 << 2) | //opcode fixed |
| 764 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 764 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 765 | 765 | (0 << 0)); //parallel |
| 766 | 766 | } else if (strstr(s, "CMPEQ") == s) { |
| 767 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 768 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 767 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 768 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 769 | 769 | |
| 770 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 771 | − (C67_map_regn(b) << 18) | //src2 | |
| 772 | − (C67_map_regn(a) << 13) | //src1 | |
| 770 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 771 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 772 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 773 | 773 | (xpath << 12) | //x use cross path for src2 |
| 774 | 774 | (0x53 << 5) | //opcode |
| 775 | 775 | (0x6 << 2) | //opcode fixed |
| 776 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 776 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 777 | 777 | (0 << 0)); //parallel |
| 778 | 778 | } else if (strstr(s, "CMPLTU") == s) { |
| 779 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 780 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 779 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 780 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 781 | 781 | |
| 782 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 783 | − (C67_map_regn(b) << 18) | //src2 | |
| 784 | − (C67_map_regn(a) << 13) | //src1 | |
| 782 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 783 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 784 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 785 | 785 | (xpath << 12) | //x use cross path for src2 |
| 786 | 786 | (0x5f << 5) | //opcode |
| 787 | 787 | (0x6 << 2) | //opcode fixed |
| 788 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 788 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 789 | 789 | (0 << 0)); //parallel |
| 790 | 790 | } else if (strstr(s, "CMPGTU") == s) { |
| 791 | − xpath = C67_map_regs(a) ^ C67_map_regs(b); | |
| 792 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 791 | + xpath = C67_map_regs(S, a) ^ C67_map_regs(S, b); | |
| 792 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 793 | 793 | |
| 794 | − C67_g((C67_map_regn(c) << 23) | //dst | |
| 795 | − (C67_map_regn(b) << 18) | //src2 | |
| 796 | − (C67_map_regn(a) << 13) | //src1 | |
| 794 | + C67_g(S, (C67_map_regn(S, c) << 23) | //dst | |
| 795 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 796 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 797 | 797 | (xpath << 12) | //x use cross path for src2 |
| 798 | 798 | (0x4f << 5) | //opcode |
| 799 | 799 | (0x6 << 2) | //opcode fixed |
| 800 | − (C67_map_regs(c) << 1) | //side for reg c | |
| 800 | + (C67_map_regs(S, c) << 1) | //side for reg c | |
| 801 | 801 | (0 << 0)); //parallel |
| 802 | 802 | } else if (strstr(s, "B DISP") == s) { |
| 803 | − C67_g((0 << 29) | //creg | |
| 803 | + C67_g(S, (0 << 29) | //creg | |
| 804 | 804 | (0 << 28) | //z |
| 805 | 805 | (a << 7) | //cnst |
| 806 | 806 | (0x4 << 2) | //opcode fixed |
| 807 | 807 | (0 << 1) | //S0/S1 |
| 808 | 808 | (0 << 0)); //parallel |
| 809 | 809 | } else if (strstr(s, "B.") == s) { |
| 810 | − xpath = C67_map_regs(c) ^ 1; | |
| 810 | + xpath = C67_map_regs(S, c) ^ 1; | |
| 811 | 811 | |
| 812 | − C67_g((C67_map_regc(b) << 29) | //creg | |
| 812 | + C67_g(S, (C67_map_regc(S, b) << 29) | //creg | |
| 813 | 813 | (a << 28) | //inv |
| 814 | 814 | (0 << 23) | //dst |
| 815 | − (C67_map_regn(c) << 18) | //src2 | |
| 815 | + (C67_map_regn(S, c) << 18) | //src2 | |
| 816 | 816 | (0 << 13) | // |
| 817 | 817 | (xpath << 12) | //x cross path if !B side |
| 818 | 818 | (0xd << 6) | //opcode |
| @@ -820,369 +820,369 @@ void C67_asm(const char *s, int a, int b, int c) · 1 unmodified line | ||
| 820 | 820 | (1 << 1) | //must be S2 |
| 821 | 821 | (0 << 0)); //parallel |
| 822 | 822 | } else if (strstr(s, "MV.L") == s) { |
| 823 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 823 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 824 | 824 | |
| 825 | − C67_g((0 << 29) | //creg | |
| 825 | + C67_g(S, (0 << 29) | //creg | |
| 826 | 826 | (0 << 28) | //inv |
| 827 | − (C67_map_regn(c) << 23) | //dst | |
| 828 | − (C67_map_regn(b) << 18) | //src2 | |
| 827 | + (C67_map_regn(S, c) << 23) | //dst | |
| 828 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 829 | 829 | (0 << 13) | //src1 (cst5) |
| 830 | 830 | (xpath << 12) | //x cross path if opposite sides |
| 831 | 831 | (0x2 << 5) | //opcode |
| 832 | 832 | (0x6 << 2) | //opcode fixed |
| 833 | − (C67_map_regs(c) << 1) | //side of dest | |
| 833 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 834 | 834 | (0 << 0)); //parallel |
| 835 | 835 | } else if (strstr(s, "SPTRUNC.L") == s) { |
| 836 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 836 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 837 | 837 | |
| 838 | − C67_g((0 << 29) | //creg | |
| 838 | + C67_g(S, (0 << 29) | //creg | |
| 839 | 839 | (0 << 28) | //inv |
| 840 | − (C67_map_regn(c) << 23) | //dst | |
| 841 | − (C67_map_regn(b) << 18) | //src2 | |
| 840 | + (C67_map_regn(S, c) << 23) | //dst | |
| 841 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 842 | 842 | (0 << 13) | //src1 NA |
| 843 | 843 | (xpath << 12) | //x cross path if opposite sides |
| 844 | 844 | (0xb << 5) | //opcode |
| 845 | 845 | (0x6 << 2) | //opcode fixed |
| 846 | − (C67_map_regs(c) << 1) | //side of dest | |
| 846 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 847 | 847 | (0 << 0)); //parallel |
| 848 | 848 | } else if (strstr(s, "DPTRUNC.L") == s) { |
| 849 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 849 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 850 | 850 | |
| 851 | − C67_g((0 << 29) | //creg | |
| 851 | + C67_g(S, (0 << 29) | //creg | |
| 852 | 852 | (0 << 28) | //inv |
| 853 | − (C67_map_regn(c) << 23) | //dst | |
| 854 | − ((C67_map_regn(b) + 1) << 18) | //src2 WEIRD CPU must specify odd reg for some reason | |
| 853 | + (C67_map_regn(S, c) << 23) | //dst | |
| 854 | + ((C67_map_regn(S, b) + 1) << 18) | //src2 WEIRD CPU must specify odd reg for some reason | |
| 855 | 855 | (0 << 13) | //src1 NA |
| 856 | 856 | (xpath << 12) | //x cross path if opposite sides |
| 857 | 857 | (0x1 << 5) | //opcode |
| 858 | 858 | (0x6 << 2) | //opcode fixed |
| 859 | − (C67_map_regs(c) << 1) | //side of dest | |
| 859 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 860 | 860 | (0 << 0)); //parallel |
| 861 | 861 | } else if (strstr(s, "INTSP.L") == s) { |
| 862 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 862 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 863 | 863 | |
| 864 | − C67_g((0 << 29) | //creg | |
| 864 | + C67_g(S, (0 << 29) | //creg | |
| 865 | 865 | (0 << 28) | //inv |
| 866 | − (C67_map_regn(c) << 23) | //dst | |
| 867 | − (C67_map_regn(b) << 18) | //src2 | |
| 866 | + (C67_map_regn(S, c) << 23) | //dst | |
| 867 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 868 | 868 | (0 << 13) | //src1 NA |
| 869 | 869 | (xpath << 12) | //x cross path if opposite sides |
| 870 | 870 | (0x4a << 5) | //opcode |
| 871 | 871 | (0x6 << 2) | //opcode fixed |
| 872 | − (C67_map_regs(c) << 1) | //side of dest | |
| 872 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 873 | 873 | (0 << 0)); //parallel |
| 874 | 874 | } else if (strstr(s, "INTSPU.L") == s) { |
| 875 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 875 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 876 | 876 | |
| 877 | − C67_g((0 << 29) | //creg | |
| 877 | + C67_g(S, (0 << 29) | //creg | |
| 878 | 878 | (0 << 28) | //inv |
| 879 | − (C67_map_regn(c) << 23) | //dst | |
| 880 | − (C67_map_regn(b) << 18) | //src2 | |
| 879 | + (C67_map_regn(S, c) << 23) | //dst | |
| 880 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 881 | 881 | (0 << 13) | //src1 NA |
| 882 | 882 | (xpath << 12) | //x cross path if opposite sides |
| 883 | 883 | (0x49 << 5) | //opcode |
| 884 | 884 | (0x6 << 2) | //opcode fixed |
| 885 | − (C67_map_regs(c) << 1) | //side of dest | |
| 885 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 886 | 886 | (0 << 0)); //parallel |
| 887 | 887 | } else if (strstr(s, "INTDP.L") == s) { |
| 888 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 888 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 889 | 889 | |
| 890 | − C67_g((0 << 29) | //creg | |
| 890 | + C67_g(S, (0 << 29) | //creg | |
| 891 | 891 | (0 << 28) | //inv |
| 892 | − (C67_map_regn(c) << 23) | //dst | |
| 893 | − (C67_map_regn(b) << 18) | //src2 | |
| 892 | + (C67_map_regn(S, c) << 23) | //dst | |
| 893 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 894 | 894 | (0 << 13) | //src1 NA |
| 895 | 895 | (xpath << 12) | //x cross path if opposite sides |
| 896 | 896 | (0x39 << 5) | //opcode |
| 897 | 897 | (0x6 << 2) | //opcode fixed |
| 898 | − (C67_map_regs(c) << 1) | //side of dest | |
| 898 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 899 | 899 | (0 << 0)); //parallel |
| 900 | 900 | } else if (strstr(s, "INTDPU.L") == s) { |
| 901 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 901 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 902 | 902 | |
| 903 | − C67_g((0 << 29) | //creg | |
| 903 | + C67_g(S, (0 << 29) | //creg | |
| 904 | 904 | (0 << 28) | //inv |
| 905 | − (C67_map_regn(c) << 23) | //dst | |
| 906 | − ((C67_map_regn(b) + 1) << 18) | //src2 WEIRD CPU must specify odd reg for some reason | |
| 905 | + (C67_map_regn(S, c) << 23) | //dst | |
| 906 | + ((C67_map_regn(S, b) + 1) << 18) | //src2 WEIRD CPU must specify odd reg for some reason | |
| 907 | 907 | (0 << 13) | //src1 NA |
| 908 | 908 | (xpath << 12) | //x cross path if opposite sides |
| 909 | 909 | (0x3b << 5) | //opcode |
| 910 | 910 | (0x6 << 2) | //opcode fixed |
| 911 | − (C67_map_regs(c) << 1) | //side of dest | |
| 911 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 912 | 912 | (0 << 0)); //parallel |
| 913 | 913 | } else if (strstr(s, "SPDP.L") == s) { |
| 914 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 914 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 915 | 915 | |
| 916 | − C67_g((0 << 29) | //creg | |
| 916 | + C67_g(S, (0 << 29) | //creg | |
| 917 | 917 | (0 << 28) | //inv |
| 918 | − (C67_map_regn(c) << 23) | //dst | |
| 919 | − (C67_map_regn(b) << 18) | //src2 | |
| 918 | + (C67_map_regn(S, c) << 23) | //dst | |
| 919 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 920 | 920 | (0 << 13) | //src1 NA |
| 921 | 921 | (xpath << 12) | //x cross path if opposite sides |
| 922 | 922 | (0x2 << 6) | //opcode |
| 923 | 923 | (0x8 << 2) | //opcode fixed |
| 924 | − (C67_map_regs(c) << 1) | //side of dest | |
| 924 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 925 | 925 | (0 << 0)); //parallel |
| 926 | 926 | } else if (strstr(s, "DPSP.L") == s) { |
| 927 | − ALWAYS_ASSERT(C67_map_regs(b) == C67_map_regs(c)); | |
| 927 | + ALWAYS_ASSERT(C67_map_regs(S, b) == C67_map_regs(S, c)); | |
| 928 | 928 | |
| 929 | − C67_g((0 << 29) | //creg | |
| 929 | + C67_g(S, (0 << 29) | //creg | |
| 930 | 930 | (0 << 28) | //inv |
| 931 | − (C67_map_regn(c) << 23) | //dst | |
| 932 | − ((C67_map_regn(b) + 1) << 18) | //src2 WEIRD CPU must specify odd reg for some reason | |
| 931 | + (C67_map_regn(S, c) << 23) | //dst | |
| 932 | + ((C67_map_regn(S, b) + 1) << 18) | //src2 WEIRD CPU must specify odd reg for some reason | |
| 933 | 933 | (0 << 13) | //src1 NA |
| 934 | 934 | (0 << 12) | //x cross path if opposite sides |
| 935 | 935 | (0x9 << 5) | //opcode |
| 936 | 936 | (0x6 << 2) | //opcode fixed |
| 937 | − (C67_map_regs(c) << 1) | //side of dest | |
| 937 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 938 | 938 | (0 << 0)); //parallel |
| 939 | 939 | } else if (strstr(s, "ADD.L") == s) { |
| 940 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 940 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 941 | 941 | |
| 942 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 942 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 943 | 943 | |
| 944 | − C67_g((0 << 29) | //creg | |
| 944 | + C67_g(S, (0 << 29) | //creg | |
| 945 | 945 | (0 << 28) | //inv |
| 946 | − (C67_map_regn(c) << 23) | //dst | |
| 947 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 948 | − (C67_map_regn(a) << 13) | //src1 | |
| 946 | + (C67_map_regn(S, c) << 23) | //dst | |
| 947 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 948 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 949 | 949 | (xpath << 12) | //x cross path if opposite sides |
| 950 | 950 | (0x3 << 5) | //opcode |
| 951 | 951 | (0x6 << 2) | //opcode fixed |
| 952 | − (C67_map_regs(c) << 1) | //side of dest | |
| 952 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 953 | 953 | (0 << 0)); //parallel |
| 954 | 954 | } else if (strstr(s, "SUB.L") == s) { |
| 955 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 955 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 956 | 956 | |
| 957 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 957 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 958 | 958 | |
| 959 | − C67_g((0 << 29) | //creg | |
| 959 | + C67_g(S, (0 << 29) | //creg | |
| 960 | 960 | (0 << 28) | //inv |
| 961 | − (C67_map_regn(c) << 23) | //dst | |
| 962 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 963 | − (C67_map_regn(a) << 13) | //src1 | |
| 961 | + (C67_map_regn(S, c) << 23) | //dst | |
| 962 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 963 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 964 | 964 | (xpath << 12) | //x cross path if opposite sides |
| 965 | 965 | (0x7 << 5) | //opcode |
| 966 | 966 | (0x6 << 2) | //opcode fixed |
| 967 | − (C67_map_regs(c) << 1) | //side of dest | |
| 967 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 968 | 968 | (0 << 0)); //parallel |
| 969 | 969 | } else if (strstr(s, "OR.L") == s) { |
| 970 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 970 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 971 | 971 | |
| 972 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 972 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 973 | 973 | |
| 974 | − C67_g((0 << 29) | //creg | |
| 974 | + C67_g(S, (0 << 29) | //creg | |
| 975 | 975 | (0 << 28) | //inv |
| 976 | − (C67_map_regn(c) << 23) | //dst | |
| 977 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 978 | − (C67_map_regn(a) << 13) | //src1 | |
| 976 | + (C67_map_regn(S, c) << 23) | //dst | |
| 977 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 978 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 979 | 979 | (xpath << 12) | //x cross path if opposite sides |
| 980 | 980 | (0x7f << 5) | //opcode |
| 981 | 981 | (0x6 << 2) | //opcode fixed |
| 982 | − (C67_map_regs(c) << 1) | //side of dest | |
| 982 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 983 | 983 | (0 << 0)); //parallel |
| 984 | 984 | } else if (strstr(s, "AND.L") == s) { |
| 985 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 985 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 986 | 986 | |
| 987 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 987 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 988 | 988 | |
| 989 | − C67_g((0 << 29) | //creg | |
| 989 | + C67_g(S, (0 << 29) | //creg | |
| 990 | 990 | (0 << 28) | //inv |
| 991 | − (C67_map_regn(c) << 23) | //dst | |
| 992 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 993 | − (C67_map_regn(a) << 13) | //src1 | |
| 991 | + (C67_map_regn(S, c) << 23) | //dst | |
| 992 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 993 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 994 | 994 | (xpath << 12) | //x cross path if opposite sides |
| 995 | 995 | (0x7b << 5) | //opcode |
| 996 | 996 | (0x6 << 2) | //opcode fixed |
| 997 | − (C67_map_regs(c) << 1) | //side of dest | |
| 997 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 998 | 998 | (0 << 0)); //parallel |
| 999 | 999 | } else if (strstr(s, "XOR.L") == s) { |
| 1000 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1000 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1001 | 1001 | |
| 1002 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1002 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1003 | 1003 | |
| 1004 | − C67_g((0 << 29) | //creg | |
| 1004 | + C67_g(S, (0 << 29) | //creg | |
| 1005 | 1005 | (0 << 28) | //inv |
| 1006 | − (C67_map_regn(c) << 23) | //dst | |
| 1007 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 1008 | − (C67_map_regn(a) << 13) | //src1 | |
| 1006 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1007 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 1008 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1009 | 1009 | (xpath << 12) | //x cross path if opposite sides |
| 1010 | 1010 | (0x6f << 5) | //opcode |
| 1011 | 1011 | (0x6 << 2) | //opcode fixed |
| 1012 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1012 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1013 | 1013 | (0 << 0)); //parallel |
| 1014 | 1014 | } else if (strstr(s, "ADDSP.L") == s) { |
| 1015 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1015 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1016 | 1016 | |
| 1017 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1017 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1018 | 1018 | |
| 1019 | − C67_g((0 << 29) | //creg | |
| 1019 | + C67_g(S, (0 << 29) | //creg | |
| 1020 | 1020 | (0 << 28) | //inv |
| 1021 | − (C67_map_regn(c) << 23) | //dst | |
| 1022 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 1023 | − (C67_map_regn(a) << 13) | //src1 | |
| 1021 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1022 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 1023 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1024 | 1024 | (xpath << 12) | //x cross path if opposite sides |
| 1025 | 1025 | (0x10 << 5) | //opcode |
| 1026 | 1026 | (0x6 << 2) | //opcode fixed |
| 1027 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1027 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1028 | 1028 | (0 << 0)); //parallel |
| 1029 | 1029 | } else if (strstr(s, "ADDDP.L") == s) { |
| 1030 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1030 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1031 | 1031 | |
| 1032 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1032 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1033 | 1033 | |
| 1034 | − C67_g((0 << 29) | //creg | |
| 1034 | + C67_g(S, (0 << 29) | //creg | |
| 1035 | 1035 | (0 << 28) | //inv |
| 1036 | − (C67_map_regn(c) << 23) | //dst | |
| 1037 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 1038 | − (C67_map_regn(a) << 13) | //src1 | |
| 1036 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1037 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 1038 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1039 | 1039 | (xpath << 12) | //x cross path if opposite sides |
| 1040 | 1040 | (0x18 << 5) | //opcode |
| 1041 | 1041 | (0x6 << 2) | //opcode fixed |
| 1042 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1042 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1043 | 1043 | (0 << 0)); //parallel |
| 1044 | 1044 | } else if (strstr(s, "SUBSP.L") == s) { |
| 1045 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1045 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1046 | 1046 | |
| 1047 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1047 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1048 | 1048 | |
| 1049 | − C67_g((0 << 29) | //creg | |
| 1049 | + C67_g(S, (0 << 29) | //creg | |
| 1050 | 1050 | (0 << 28) | //inv |
| 1051 | − (C67_map_regn(c) << 23) | //dst | |
| 1052 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 1053 | − (C67_map_regn(a) << 13) | //src1 | |
| 1051 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1052 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 1053 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1054 | 1054 | (xpath << 12) | //x cross path if opposite sides |
| 1055 | 1055 | (0x11 << 5) | //opcode |
| 1056 | 1056 | (0x6 << 2) | //opcode fixed |
| 1057 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1057 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1058 | 1058 | (0 << 0)); //parallel |
| 1059 | 1059 | } else if (strstr(s, "SUBDP.L") == s) { |
| 1060 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1060 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1061 | 1061 | |
| 1062 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1062 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1063 | 1063 | |
| 1064 | − C67_g((0 << 29) | //creg | |
| 1064 | + C67_g(S, (0 << 29) | //creg | |
| 1065 | 1065 | (0 << 28) | //inv |
| 1066 | − (C67_map_regn(c) << 23) | //dst | |
| 1067 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 1068 | − (C67_map_regn(a) << 13) | //src1 | |
| 1066 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1067 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 1068 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1069 | 1069 | (xpath << 12) | //x cross path if opposite sides |
| 1070 | 1070 | (0x19 << 5) | //opcode |
| 1071 | 1071 | (0x6 << 2) | //opcode fixed |
| 1072 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1072 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1073 | 1073 | (0 << 0)); //parallel |
| 1074 | 1074 | } else if (strstr(s, "MPYSP.M") == s) { |
| 1075 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1075 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1076 | 1076 | |
| 1077 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1077 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1078 | 1078 | |
| 1079 | − C67_g((0 << 29) | //creg | |
| 1079 | + C67_g(S, (0 << 29) | //creg | |
| 1080 | 1080 | (0 << 28) | //inv |
| 1081 | − (C67_map_regn(c) << 23) | //dst | |
| 1082 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 1083 | − (C67_map_regn(a) << 13) | //src1 | |
| 1081 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1082 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 1083 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1084 | 1084 | (xpath << 12) | //x cross path if opposite sides |
| 1085 | 1085 | (0x1c << 7) | //opcode |
| 1086 | 1086 | (0x0 << 2) | //opcode fixed |
| 1087 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1087 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1088 | 1088 | (0 << 0)); //parallel |
| 1089 | 1089 | } else if (strstr(s, "MPYDP.M") == s) { |
| 1090 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1090 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1091 | 1091 | |
| 1092 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1092 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1093 | 1093 | |
| 1094 | − C67_g((0 << 29) | //creg | |
| 1094 | + C67_g(S, (0 << 29) | //creg | |
| 1095 | 1095 | (0 << 28) | //inv |
| 1096 | − (C67_map_regn(c) << 23) | //dst | |
| 1097 | − (C67_map_regn(b) << 18) | //src2 (possible x path) | |
| 1098 | − (C67_map_regn(a) << 13) | //src1 | |
| 1096 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1097 | + (C67_map_regn(S, b) << 18) | //src2 (possible x path) | |
| 1098 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1099 | 1099 | (xpath << 12) | //x cross path if opposite sides |
| 1100 | 1100 | (0x0e << 7) | //opcode |
| 1101 | 1101 | (0x0 << 2) | //opcode fixed |
| 1102 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1102 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1103 | 1103 | (0 << 0)); //parallel |
| 1104 | 1104 | } else if (strstr(s, "MPYI.M") == s) { |
| 1105 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1105 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1106 | 1106 | |
| 1107 | − ALWAYS_ASSERT(C67_map_regs(a) == C67_map_regs(c)); | |
| 1107 | + ALWAYS_ASSERT(C67_map_regs(S, a) == C67_map_regs(S, c)); | |
| 1108 | 1108 | |
| 1109 | − C67_g((0 << 29) | //creg | |
| 1109 | + C67_g(S, (0 << 29) | //creg | |
| 1110 | 1110 | (0 << 28) | //inv |
| 1111 | − (C67_map_regn(c) << 23) | //dst | |
| 1112 | − (C67_map_regn(b) << 18) | //src2 | |
| 1113 | − (C67_map_regn(a) << 13) | //src1 (cst5) | |
| 1111 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1112 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 1113 | + (C67_map_regn(S, a) << 13) | //src1 (cst5) | |
| 1114 | 1114 | (xpath << 12) | //x cross path if opposite sides |
| 1115 | 1115 | (0x4 << 7) | //opcode |
| 1116 | 1116 | (0x0 << 2) | //opcode fixed |
| 1117 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1117 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1118 | 1118 | (0 << 0)); //parallel |
| 1119 | 1119 | } else if (strstr(s, "SHR.S") == s) { |
| 1120 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1120 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1121 | 1121 | |
| 1122 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 1122 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 1123 | 1123 | |
| 1124 | − C67_g((0 << 29) | //creg | |
| 1124 | + C67_g(S, (0 << 29) | //creg | |
| 1125 | 1125 | (0 << 28) | //inv |
| 1126 | − (C67_map_regn(c) << 23) | //dst | |
| 1127 | − (C67_map_regn(b) << 18) | //src2 | |
| 1128 | − (C67_map_regn(a) << 13) | //src1 | |
| 1126 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1127 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 1128 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1129 | 1129 | (xpath << 12) | //x cross path if opposite sides |
| 1130 | 1130 | (0x37 << 6) | //opcode |
| 1131 | 1131 | (0x8 << 2) | //opcode fixed |
| 1132 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1132 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1133 | 1133 | (0 << 0)); //parallel |
| 1134 | 1134 | } else if (strstr(s, "SHRU.S") == s) { |
| 1135 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1135 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1136 | 1136 | |
| 1137 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 1137 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 1138 | 1138 | |
| 1139 | − C67_g((0 << 29) | //creg | |
| 1139 | + C67_g(S, (0 << 29) | //creg | |
| 1140 | 1140 | (0 << 28) | //inv |
| 1141 | − (C67_map_regn(c) << 23) | //dst | |
| 1142 | − (C67_map_regn(b) << 18) | //src2 | |
| 1143 | − (C67_map_regn(a) << 13) | //src1 | |
| 1141 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1142 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 1143 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1144 | 1144 | (xpath << 12) | //x cross path if opposite sides |
| 1145 | 1145 | (0x27 << 6) | //opcode |
| 1146 | 1146 | (0x8 << 2) | //opcode fixed |
| 1147 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1147 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1148 | 1148 | (0 << 0)); //parallel |
| 1149 | 1149 | } else if (strstr(s, "SHL.S") == s) { |
| 1150 | − xpath = C67_map_regs(b) ^ C67_map_regs(c); | |
| 1150 | + xpath = C67_map_regs(S, b) ^ C67_map_regs(S, c); | |
| 1151 | 1151 | |
| 1152 | − ALWAYS_ASSERT(C67_map_regs(c) == C67_map_regs(a)); | |
| 1152 | + ALWAYS_ASSERT(C67_map_regs(S, c) == C67_map_regs(S, a)); | |
| 1153 | 1153 | |
| 1154 | − C67_g((0 << 29) | //creg | |
| 1154 | + C67_g(S, (0 << 29) | //creg | |
| 1155 | 1155 | (0 << 28) | //inv |
| 1156 | − (C67_map_regn(c) << 23) | //dst | |
| 1157 | − (C67_map_regn(b) << 18) | //src2 | |
| 1158 | − (C67_map_regn(a) << 13) | //src1 | |
| 1156 | + (C67_map_regn(S, c) << 23) | //dst | |
| 1157 | + (C67_map_regn(S, b) << 18) | //src2 | |
| 1158 | + (C67_map_regn(S, a) << 13) | //src1 | |
| 1159 | 1159 | (xpath << 12) | //x cross path if opposite sides |
| 1160 | 1160 | (0x33 << 6) | //opcode |
| 1161 | 1161 | (0x8 << 2) | //opcode fixed |
| 1162 | − (C67_map_regs(c) << 1) | //side of dest | |
| 1162 | + (C67_map_regs(S, c) << 1) | //side of dest | |
| 1163 | 1163 | (0 << 0)); //parallel |
| 1164 | 1164 | } else if (strstr(s, "||ADDK") == s) { |
| 1165 | 1165 | xpath = 0; // no xpath required just use the side of the src/dst |
| 1166 | 1166 | |
| 1167 | − C67_g((0 << 29) | //creg | |
| 1167 | + C67_g(S, (0 << 29) | //creg | |
| 1168 | 1168 | (0 << 28) | //inv |
| 1169 | − (C67_map_regn(b) << 23) | //dst | |
| 1169 | + (C67_map_regn(S, b) << 23) | //dst | |
| 1170 | 1170 | (a << 07) | //scst16 |
| 1171 | 1171 | (0x14 << 2) | //opcode fixed |
| 1172 | − (C67_map_regs(b) << 1) | //side of dst | |
| 1172 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 1173 | 1173 | (1 << 0)); //parallel |
| 1174 | 1174 | } else if (strstr(s, "ADDK") == s) { |
| 1175 | 1175 | xpath = 0; // no xpath required just use the side of the src/dst |
| 1176 | 1176 | |
| 1177 | − C67_g((0 << 29) | //creg | |
| 1177 | + C67_g(S, (0 << 29) | //creg | |
| 1178 | 1178 | (0 << 28) | //inv |
| 1179 | − (C67_map_regn(b) << 23) | //dst | |
| 1179 | + (C67_map_regn(S, b) << 23) | //dst | |
| 1180 | 1180 | (a << 07) | //scst16 |
| 1181 | 1181 | (0x14 << 2) | //opcode fixed |
| 1182 | − (C67_map_regs(b) << 1) | //side of dst | |
| 1182 | + (C67_map_regs(S, b) << 1) | //side of dst | |
| 1183 | 1183 | (0 << 0)); //parallel |
| 1184 | 1184 | } else if (strstr(s, "NOP") == s) { |
| 1185 | − C67_g(((a - 1) << 13) | //no of cycles | |
| 1185 | + C67_g(S, ((a - 1) << 13) | //no of cycles | |
| 1186 | 1186 | (0 << 0)); //parallel |
| 1187 | 1187 | } else |
| 1188 | 1188 | ALWAYS_ASSERT(FALSE); |
| @@ -1195,198 +1195,198 @@ void C67_asm(const char *s, int a, int b, int c) · 6 unmodified lines | ||
| 1195 | 1195 | |
| 1196 | 1196 | //r=reg to load, fr=from reg, symbol for relocation, constant |
| 1197 | 1197 | |
| 1198 | −void C67_MVKL(int r, int fc) | |
| 1198 | +void C67_MVKL(TCCState* S, int r, int fc) | |
| 1199 | 1199 | { |
| 1200 | − C67_asm("MVKL.", fc, r, 0); | |
| 1200 | + C67_asm(S, "MVKL.", fc, r, 0); | |
| 1201 | 1201 | } |
| 1202 | 1202 | |
| 1203 | −void C67_MVKH(int r, int fc) | |
| 1203 | +void C67_MVKH(TCCState* S, int r, int fc) | |
| 1204 | 1204 | { |
| 1205 | − C67_asm("MVKH.", fc, r, 0); | |
| 1205 | + C67_asm(S, "MVKH.", fc, r, 0); | |
| 1206 | 1206 | } |
| 1207 | 1207 | |
| 1208 | −void C67_STB_SP_A0(int r) | |
| 1208 | +void C67_STB_SP_A0(TCCState* S, int r) | |
| 1209 | 1209 | { |
| 1210 | − C67_asm("STB.D *+SP[A0]", r, 0, 0); // STB r,*+SP[A0] | |
| 1210 | + C67_asm(S, "STB.D *+SP[A0]", r, 0, 0); // STB r,*+SP[A0] | |
| 1211 | 1211 | } |
| 1212 | 1212 | |
| 1213 | −void C67_STH_SP_A0(int r) | |
| 1213 | +void C67_STH_SP_A0(TCCState* S, int r) | |
| 1214 | 1214 | { |
| 1215 | − C67_asm("STH.D *+SP[A0]", r, 0, 0); // STH r,*+SP[A0] | |
| 1215 | + C67_asm(S, "STH.D *+SP[A0]", r, 0, 0); // STH r,*+SP[A0] | |
| 1216 | 1216 | } |
| 1217 | 1217 | |
| 1218 | −void C67_STW_SP_A0(int r) | |
| 1218 | +void C67_STW_SP_A0(TCCState* S, int r) | |
| 1219 | 1219 | { |
| 1220 | − C67_asm("STW.D *+SP[A0]", r, 0, 0); // STW r,*+SP[A0] | |
| 1220 | + C67_asm(S, "STW.D *+SP[A0]", r, 0, 0); // STW r,*+SP[A0] | |
| 1221 | 1221 | } |
| 1222 | 1222 | |
| 1223 | −void C67_STB_PTR(int r, int r2) | |
| 1223 | +void C67_STB_PTR(TCCState* S, int r, int r2) | |
| 1224 | 1224 | { |
| 1225 | − C67_asm("STB.D *", r, r2, 0); // STB r, *r2 | |
| 1225 | + C67_asm(S, "STB.D *", r, r2, 0); // STB r, *r2 | |
| 1226 | 1226 | } |
| 1227 | 1227 | |
| 1228 | −void C67_STH_PTR(int r, int r2) | |
| 1228 | +void C67_STH_PTR(TCCState* S, int r, int r2) | |
| 1229 | 1229 | { |
| 1230 | − C67_asm("STH.D *", r, r2, 0); // STH r, *r2 | |
| 1230 | + C67_asm(S, "STH.D *", r, r2, 0); // STH r, *r2 | |
| 1231 | 1231 | } |
| 1232 | 1232 | |
| 1233 | −void C67_STW_PTR(int r, int r2) | |
| 1233 | +void C67_STW_PTR(TCCState* S, int r, int r2) | |
| 1234 | 1234 | { |
| 1235 | − C67_asm("STW.D *", r, r2, 0); // STW r, *r2 | |
| 1235 | + C67_asm(S, "STW.D *", r, r2, 0); // STW r, *r2 | |
| 1236 | 1236 | } |
| 1237 | 1237 | |
| 1238 | −void C67_STW_PTR_PRE_INC(int r, int r2, int n) | |
| 1238 | +void C67_STW_PTR_PRE_INC(TCCState* S, int r, int r2, int n) | |
| 1239 | 1239 | { |
| 1240 | − C67_asm("STW.D +*", r, r2, n); // STW r, *+r2 | |
| 1240 | + C67_asm(S, "STW.D +*", r, r2, n); // STW r, *+r2 | |
| 1241 | 1241 | } |
| 1242 | 1242 | |
| 1243 | −void C67_PUSH(int r) | |
| 1243 | +void C67_PUSH(TCCState* S, int r) | |
| 1244 | 1244 | { |
| 1245 | − C67_asm("STW.D SP POST DEC", r, 0, 0); // STW r,*SP-- | |
| 1245 | + C67_asm(S, "STW.D SP POST DEC", r, 0, 0); // STW r,*SP-- | |
| 1246 | 1246 | } |
| 1247 | 1247 | |
| 1248 | −void C67_LDW_SP_A0(int r) | |
| 1248 | +void C67_LDW_SP_A0(TCCState* S, int r) | |
| 1249 | 1249 | { |
| 1250 | − C67_asm("LDW.D *+SP[A0]", r, 0, 0); // LDW *+SP[A0],r | |
| 1250 | + C67_asm(S, "LDW.D *+SP[A0]", r, 0, 0); // LDW *+SP[A0],r | |
| 1251 | 1251 | } |
| 1252 | 1252 | |
| 1253 | −void C67_LDDW_SP_A0(int r) | |
| 1253 | +void C67_LDDW_SP_A0(TCCState* S, int r) | |
| 1254 | 1254 | { |
| 1255 | − C67_asm("LDDW.D *+SP[A0]", r, 0, 0); // LDDW *+SP[A0],r | |
| 1255 | + C67_asm(S, "LDDW.D *+SP[A0]", r, 0, 0); // LDDW *+SP[A0],r | |
| 1256 | 1256 | } |
| 1257 | 1257 | |
| 1258 | −void C67_LDH_SP_A0(int r) | |
| 1258 | +void C67_LDH_SP_A0(TCCState* S, int r) | |
| 1259 | 1259 | { |
| 1260 | − C67_asm("LDH.D *+SP[A0]", r, 0, 0); // LDH *+SP[A0],r | |
| 1260 | + C67_asm(S, "LDH.D *+SP[A0]", r, 0, 0); // LDH *+SP[A0],r | |
| 1261 | 1261 | } |
| 1262 | 1262 | |
| 1263 | −void C67_LDB_SP_A0(int r) | |
| 1263 | +void C67_LDB_SP_A0(TCCState* S, int r) | |
| 1264 | 1264 | { |
| 1265 | − C67_asm("LDB.D *+SP[A0]", r, 0, 0); // LDB *+SP[A0],r | |
| 1265 | + C67_asm(S, "LDB.D *+SP[A0]", r, 0, 0); // LDB *+SP[A0],r | |
| 1266 | 1266 | } |
| 1267 | 1267 | |
| 1268 | −void C67_LDHU_SP_A0(int r) | |
| 1268 | +void C67_LDHU_SP_A0(TCCState* S, int r) | |
| 1269 | 1269 | { |
| 1270 | − C67_asm("LDHU.D *+SP[A0]", r, 0, 0); // LDHU *+SP[A0],r | |
| 1270 | + C67_asm(S, "LDHU.D *+SP[A0]", r, 0, 0); // LDHU *+SP[A0],r | |
| 1271 | 1271 | } |
| 1272 | 1272 | |
| 1273 | −void C67_LDBU_SP_A0(int r) | |
| 1273 | +void C67_LDBU_SP_A0(TCCState* S, int r) | |
| 1274 | 1274 | { |
| 1275 | − C67_asm("LDBU.D *+SP[A0]", r, 0, 0); // LDBU *+SP[A0],r | |
| 1275 | + C67_asm(S, "LDBU.D *+SP[A0]", r, 0, 0); // LDBU *+SP[A0],r | |
| 1276 | 1276 | } |
| 1277 | 1277 | |
| 1278 | −void C67_LDW_PTR(int r, int r2) | |
| 1278 | +void C67_LDW_PTR(TCCState* S, int r, int r2) | |
| 1279 | 1279 | { |
| 1280 | − C67_asm("LDW.D *", r, r2, 0); // LDW *r,r2 | |
| 1280 | + C67_asm(S, "LDW.D *", r, r2, 0); // LDW *r,r2 | |
| 1281 | 1281 | } |
| 1282 | 1282 | |
| 1283 | −void C67_LDDW_PTR(int r, int r2) | |
| 1283 | +void C67_LDDW_PTR(TCCState* S, int r, int r2) | |
| 1284 | 1284 | { |
| 1285 | − C67_asm("LDDW.D *", r, r2, 0); // LDDW *r,r2 | |
| 1285 | + C67_asm(S, "LDDW.D *", r, r2, 0); // LDDW *r,r2 | |
| 1286 | 1286 | } |
| 1287 | 1287 | |
| 1288 | −void C67_LDH_PTR(int r, int r2) | |
| 1288 | +void C67_LDH_PTR(TCCState* S, int r, int r2) | |
| 1289 | 1289 | { |
| 1290 | − C67_asm("LDH.D *", r, r2, 0); // LDH *r,r2 | |
| 1290 | + C67_asm(S, "LDH.D *", r, r2, 0); // LDH *r,r2 | |
| 1291 | 1291 | } |
| 1292 | 1292 | |
| 1293 | −void C67_LDB_PTR(int r, int r2) | |
| 1293 | +void C67_LDB_PTR(TCCState* S, int r, int r2) | |
| 1294 | 1294 | { |
| 1295 | − C67_asm("LDB.D *", r, r2, 0); // LDB *r,r2 | |
| 1295 | + C67_asm(S, "LDB.D *", r, r2, 0); // LDB *r,r2 | |
| 1296 | 1296 | } |
| 1297 | 1297 | |
| 1298 | −void C67_LDHU_PTR(int r, int r2) | |
| 1298 | +void C67_LDHU_PTR(TCCState* S, int r, int r2) | |
| 1299 | 1299 | { |
| 1300 | − C67_asm("LDHU.D *", r, r2, 0); // LDHU *r,r2 | |
| 1300 | + C67_asm(S, "LDHU.D *", r, r2, 0); // LDHU *r,r2 | |
| 1301 | 1301 | } |
| 1302 | 1302 | |
| 1303 | −void C67_LDBU_PTR(int r, int r2) | |
| 1303 | +void C67_LDBU_PTR(TCCState* S, int r, int r2) | |
| 1304 | 1304 | { |
| 1305 | − C67_asm("LDBU.D *", r, r2, 0); // LDBU *r,r2 | |
| 1305 | + C67_asm(S, "LDBU.D *", r, r2, 0); // LDBU *r,r2 | |
| 1306 | 1306 | } |
| 1307 | 1307 | |
| 1308 | −void C67_LDW_PTR_PRE_INC(int r, int r2) | |
| 1308 | +void C67_LDW_PTR_PRE_INC(TCCState* S, int r, int r2) | |
| 1309 | 1309 | { |
| 1310 | − C67_asm("LDW.D +*", r, r2, 0); // LDW *+r,r2 | |
| 1310 | + C67_asm(S, "LDW.D +*", r, r2, 0); // LDW *+r,r2 | |
| 1311 | 1311 | } |
| 1312 | 1312 | |
| 1313 | −void C67_POP(int r) | |
| 1313 | +void C67_POP(TCCState* S, int r) | |
| 1314 | 1314 | { |
| 1315 | − C67_asm("LDW.D SP PRE INC", r, 0, 0); // LDW *++SP,r | |
| 1315 | + C67_asm(S, "LDW.D SP PRE INC", r, 0, 0); // LDW *++SP,r | |
| 1316 | 1316 | } |
| 1317 | 1317 | |
| 1318 | −void C67_POP_DW(int r) | |
| 1318 | +void C67_POP_DW(TCCState* S, int r) | |
| 1319 | 1319 | { |
| 1320 | − C67_asm("LDDW.D SP PRE INC", r, 0, 0); // LDDW *++SP,r | |
| 1320 | + C67_asm(S, "LDDW.D SP PRE INC", r, 0, 0); // LDDW *++SP,r | |
| 1321 | 1321 | } |
| 1322 | 1322 | |
| 1323 | −void C67_CMPLT(int s1, int s2, int dst) | |
| 1323 | +void C67_CMPLT(TCCState* S, int s1, int s2, int dst) | |
| 1324 | 1324 | { |
| 1325 | − C67_asm("CMPLT.L1", s1, s2, dst); | |
| 1325 | + C67_asm(S, "CMPLT.L1", s1, s2, dst); | |
| 1326 | 1326 | } |
| 1327 | 1327 | |
| 1328 | −void C67_CMPGT(int s1, int s2, int dst) | |
| 1328 | +void C67_CMPGT(TCCState* S, int s1, int s2, int dst) | |
| 1329 | 1329 | { |
| 1330 | − C67_asm("CMPGT.L1", s1, s2, dst); | |
| 1330 | + C67_asm(S, "CMPGT.L1", s1, s2, dst); | |
| 1331 | 1331 | } |
| 1332 | 1332 | |
| 1333 | −void C67_CMPEQ(int s1, int s2, int dst) | |
| 1333 | +void C67_CMPEQ(TCCState* S, int s1, int s2, int dst) | |
| 1334 | 1334 | { |
| 1335 | − C67_asm("CMPEQ.L1", s1, s2, dst); | |
| 1335 | + C67_asm(S, "CMPEQ.L1", s1, s2, dst); | |
| 1336 | 1336 | } |
| 1337 | 1337 | |
| 1338 | −void C67_CMPLTU(int s1, int s2, int dst) | |
| 1338 | +void C67_CMPLTU(TCCState* S, int s1, int s2, int dst) | |
| 1339 | 1339 | { |
| 1340 | − C67_asm("CMPLTU.L1", s1, s2, dst); | |
| 1340 | + C67_asm(S, "CMPLTU.L1", s1, s2, dst); | |
| 1341 | 1341 | } |
| 1342 | 1342 | |
| 1343 | −void C67_CMPGTU(int s1, int s2, int dst) | |
| 1343 | +void C67_CMPGTU(TCCState* S, int s1, int s2, int dst) | |
| 1344 | 1344 | { |
| 1345 | − C67_asm("CMPGTU.L1", s1, s2, dst); | |
| 1345 | + C67_asm(S, "CMPGTU.L1", s1, s2, dst); | |
| 1346 | 1346 | } |
| 1347 | 1347 | |
| 1348 | 1348 | |
| 1349 | −void C67_CMPLTSP(int s1, int s2, int dst) | |
| 1349 | +void C67_CMPLTSP(TCCState* S, int s1, int s2, int dst) | |
| 1350 | 1350 | { |
| 1351 | − C67_asm("CMPLTSP.S1", s1, s2, dst); | |
| 1351 | + C67_asm(S, "CMPLTSP.S1", s1, s2, dst); | |
| 1352 | 1352 | } |
| 1353 | 1353 | |
| 1354 | −void C67_CMPGTSP(int s1, int s2, int dst) | |
| 1354 | +void C67_CMPGTSP(TCCState* S, int s1, int s2, int dst) | |
| 1355 | 1355 | { |
| 1356 | − C67_asm("CMPGTSP.S1", s1, s2, dst); | |
| 1356 | + C67_asm(S, "CMPGTSP.S1", s1, s2, dst); | |
| 1357 | 1357 | } |
| 1358 | 1358 | |
| 1359 | −void C67_CMPEQSP(int s1, int s2, int dst) | |
| 1359 | +void C67_CMPEQSP(TCCState* S, int s1, int s2, int dst) | |
| 1360 | 1360 | { |
| 1361 | − C67_asm("CMPEQSP.S1", s1, s2, dst); | |
| 1361 | + C67_asm(S, "CMPEQSP.S1", s1, s2, dst); | |
| 1362 | 1362 | } |
| 1363 | 1363 | |
| 1364 | −void C67_CMPLTDP(int s1, int s2, int dst) | |
| 1364 | +void C67_CMPLTDP(TCCState* S, int s1, int s2, int dst) | |
| 1365 | 1365 | { |
| 1366 | − C67_asm("CMPLTDP.S1", s1, s2, dst); | |
| 1366 | + C67_asm(S, "CMPLTDP.S1", s1, s2, dst); | |
| 1367 | 1367 | } |
| 1368 | 1368 | |
| 1369 | −void C67_CMPGTDP(int s1, int s2, int dst) | |
| 1369 | +void C67_CMPGTDP(TCCState* S, int s1, int s2, int dst) | |
| 1370 | 1370 | { |
| 1371 | − C67_asm("CMPGTDP.S1", s1, s2, dst); | |
| 1371 | + C67_asm(S, "CMPGTDP.S1", s1, s2, dst); | |
| 1372 | 1372 | } |
| 1373 | 1373 | |
| 1374 | −void C67_CMPEQDP(int s1, int s2, int dst) | |
| 1374 | +void C67_CMPEQDP(TCCState* S, int s1, int s2, int dst) | |
| 1375 | 1375 | { |
| 1376 | − C67_asm("CMPEQDP.S1", s1, s2, dst); | |
| 1376 | + C67_asm(S, "CMPEQDP.S1", s1, s2, dst); | |
| 1377 | 1377 | } |
| 1378 | 1378 | |
| 1379 | 1379 | |
| 1380 | −void C67_IREG_B_REG(int inv, int r1, int r2) // [!R] B r2 | |
| 1380 | +void C67_IREG_B_REG(TCCState* S, int inv, int r1, int r2) // [!R] B r2 | |
| 1381 | 1381 | { |
| 1382 | − C67_asm("B.S2", inv, r1, r2); | |
| 1382 | + C67_asm(S, "B.S2", inv, r1, r2); | |
| 1383 | 1383 | } |
| 1384 | 1384 | |
| 1385 | 1385 | |
| 1386 | 1386 | // call with how many 32 bit words to skip |
| 1387 | 1387 | // (0 would branch to the branch instruction) |
| 1388 | 1388 | |
| 1389 | −void C67_B_DISP(int disp) // B +2 Branch with constant displacement | |
| 1389 | +void C67_B_DISP(TCCState* S, int disp) // B +2 Branch with constant displacement | |
| 1390 | 1390 | { |
| 1391 | 1391 | // Branch point is relative to the 8 word fetch packet |
| 1392 | 1392 | // |
| @@ -1395,160 +1395,160 @@ void C67_B_DISP(int disp) // B +2 Branch with constant displacement · 2 unmodified lines | ||
| 1395 | 1395 | // so add in how many words into the fetch packet the branch is |
| 1396 | 1396 | |
| 1397 | 1397 | |
| 1398 | − C67_asm("B DISP", disp + ((ind & 31) >> 2), 0, 0); | |
| 1398 | + C67_asm(S, "B DISP", disp + ((S->tccgen_ind & 31) >> 2), 0, 0); | |
| 1399 | 1399 | } |
| 1400 | 1400 | |
| 1401 | −void C67_NOP(int n) | |
| 1401 | +void C67_NOP(TCCState* S, int n) | |
| 1402 | 1402 | { |
| 1403 | − C67_asm("NOP", n, 0, 0); | |
| 1403 | + C67_asm(S, "NOP", n, 0, 0); | |
| 1404 | 1404 | } |
| 1405 | 1405 | |
| 1406 | −void C67_ADDK(int n, int r) | |
| 1406 | +void C67_ADDK(TCCState* S, int n, int r) | |
| 1407 | 1407 | { |
| 1408 | 1408 | ALWAYS_ASSERT(abs(n) < 32767); |
| 1409 | 1409 | |
| 1410 | − C67_asm("ADDK", n, r, 0); | |
| 1410 | + C67_asm(S, "ADDK", n, r, 0); | |
| 1411 | 1411 | } |
| 1412 | 1412 | |
| 1413 | −void C67_ADDK_PARALLEL(int n, int r) | |
| 1413 | +void C67_ADDK_PARALLEL(TCCState* S, int n, int r) | |
| 1414 | 1414 | { |
| 1415 | 1415 | ALWAYS_ASSERT(abs(n) < 32767); |
| 1416 | 1416 | |
| 1417 | − C67_asm("||ADDK", n, r, 0); | |
| 1417 | + C67_asm(S, "||ADDK", n, r, 0); | |
| 1418 | 1418 | } |
| 1419 | 1419 | |
| 1420 | −void C67_Adjust_ADDK(int *inst, int n) | |
| 1420 | +void C67_Adjust_ADDK(TCCState* S, int *inst, int n) | |
| 1421 | 1421 | { |
| 1422 | 1422 | ALWAYS_ASSERT(abs(n) < 32767); |
| 1423 | 1423 | |
| 1424 | 1424 | *inst = (*inst & (~(0xffff << 7))) | ((n & 0xffff) << 7); |
| 1425 | 1425 | } |
| 1426 | 1426 | |
| 1427 | −void C67_MV(int r, int v) | |
| 1427 | +void C67_MV(TCCState* S, int r, int v) | |
| 1428 | 1428 | { |
| 1429 | − C67_asm("MV.L", 0, r, v); | |
| 1429 | + C67_asm(S, "MV.L", 0, r, v); | |
| 1430 | 1430 | } |
| 1431 | 1431 | |
| 1432 | 1432 | |
| 1433 | −void C67_DPTRUNC(int r, int v) | |
| 1433 | +void C67_DPTRUNC(TCCState* S, int r, int v) | |
| 1434 | 1434 | { |
| 1435 | − C67_asm("DPTRUNC.L", 0, r, v); | |
| 1435 | + C67_asm(S, "DPTRUNC.L", 0, r, v); | |
| 1436 | 1436 | } |
| 1437 | 1437 | |
| 1438 | −void C67_SPTRUNC(int r, int v) | |
| 1438 | +void C67_SPTRUNC(TCCState* S, int r, int v) | |
| 1439 | 1439 | { |
| 1440 | − C67_asm("SPTRUNC.L", 0, r, v); | |
| 1440 | + C67_asm(S, "SPTRUNC.L", 0, r, v); | |
| 1441 | 1441 | } |
| 1442 | 1442 | |
| 1443 | −void C67_INTSP(int r, int v) | |
| 1443 | +void C67_INTSP(TCCState* S, int r, int v) | |
| 1444 | 1444 | { |
| 1445 | − C67_asm("INTSP.L", 0, r, v); | |
| 1445 | + C67_asm(S, "INTSP.L", 0, r, v); | |
| 1446 | 1446 | } |
| 1447 | 1447 | |
| 1448 | −void C67_INTDP(int r, int v) | |
| 1448 | +void C67_INTDP(TCCState* S, int r, int v) | |
| 1449 | 1449 | { |
| 1450 | − C67_asm("INTDP.L", 0, r, v); | |
| 1450 | + C67_asm(S, "INTDP.L", 0, r, v); | |
| 1451 | 1451 | } |
| 1452 | 1452 | |
| 1453 | −void C67_INTSPU(int r, int v) | |
| 1453 | +void C67_INTSPU(TCCState* S, int r, int v) | |
| 1454 | 1454 | { |
| 1455 | − C67_asm("INTSPU.L", 0, r, v); | |
| 1455 | + C67_asm(S, "INTSPU.L", 0, r, v); | |
| 1456 | 1456 | } |
| 1457 | 1457 | |
| 1458 | −void C67_INTDPU(int r, int v) | |
| 1458 | +void C67_INTDPU(TCCState* S, int r, int v) | |
| 1459 | 1459 | { |
| 1460 | − C67_asm("INTDPU.L", 0, r, v); | |
| 1460 | + C67_asm(S, "INTDPU.L", 0, r, v); | |
| 1461 | 1461 | } |
| 1462 | 1462 | |
| 1463 | −void C67_SPDP(int r, int v) | |
| 1463 | +void C67_SPDP(TCCState* S, int r, int v) | |
| 1464 | 1464 | { |
| 1465 | − C67_asm("SPDP.L", 0, r, v); | |
| 1465 | + C67_asm(S, "SPDP.L", 0, r, v); | |
| 1466 | 1466 | } |
| 1467 | 1467 | |
| 1468 | −void C67_DPSP(int r, int v) // note regs must be on the same side | |
| 1468 | +void C67_DPSP(TCCState* S, int r, int v) // note regs must be on the same side | |
| 1469 | 1469 | { |
| 1470 | − C67_asm("DPSP.L", 0, r, v); | |
| 1470 | + C67_asm(S, "DPSP.L", 0, r, v); | |
| 1471 | 1471 | } |
| 1472 | 1472 | |
| 1473 | −void C67_ADD(int r, int v) | |
| 1473 | +void C67_ADD(TCCState* S, int r, int v) | |
| 1474 | 1474 | { |
| 1475 | − C67_asm("ADD.L", v, r, v); | |
| 1475 | + C67_asm(S, "ADD.L", v, r, v); | |
| 1476 | 1476 | } |
| 1477 | 1477 | |
| 1478 | −void C67_SUB(int r, int v) | |
| 1478 | +void C67_SUB(TCCState* S, int r, int v) | |
| 1479 | 1479 | { |
| 1480 | − C67_asm("SUB.L", v, r, v); | |
| 1480 | + C67_asm(S, "SUB.L", v, r, v); | |
| 1481 | 1481 | } |
| 1482 | 1482 | |
| 1483 | −void C67_AND(int r, int v) | |
| 1483 | +void C67_AND(TCCState* S, int r, int v) | |
| 1484 | 1484 | { |
| 1485 | − C67_asm("AND.L", v, r, v); | |
| 1485 | + C67_asm(S, "AND.L", v, r, v); | |
| 1486 | 1486 | } |
| 1487 | 1487 | |
| 1488 | −void C67_OR(int r, int v) | |
| 1488 | +void C67_OR(TCCState* S, int r, int v) | |
| 1489 | 1489 | { |
| 1490 | − C67_asm("OR.L", v, r, v); | |
| 1490 | + C67_asm(S, "OR.L", v, r, v); | |
| 1491 | 1491 | } |
| 1492 | 1492 | |
| 1493 | −void C67_XOR(int r, int v) | |
| 1493 | +void C67_XOR(TCCState* S, int r, int v) | |
| 1494 | 1494 | { |
| 1495 | − C67_asm("XOR.L", v, r, v); | |
| 1495 | + C67_asm(S, "XOR.L", v, r, v); | |
| 1496 | 1496 | } |
| 1497 | 1497 | |
| 1498 | −void C67_ADDSP(int r, int v) | |
| 1498 | +void C67_ADDSP(TCCState* S, int r, int v) | |
| 1499 | 1499 | { |
| 1500 | − C67_asm("ADDSP.L", v, r, v); | |
| 1500 | + C67_asm(S, "ADDSP.L", v, r, v); | |
| 1501 | 1501 | } |
| 1502 | 1502 | |
| 1503 | −void C67_SUBSP(int r, int v) | |
| 1503 | +void C67_SUBSP(TCCState* S, int r, int v) | |
| 1504 | 1504 | { |
| 1505 | − C67_asm("SUBSP.L", v, r, v); | |
| 1505 | + C67_asm(S, "SUBSP.L", v, r, v); | |
| 1506 | 1506 | } |
| 1507 | 1507 | |
| 1508 | −void C67_MPYSP(int r, int v) | |
| 1508 | +void C67_MPYSP(TCCState* S, int r, int v) | |
| 1509 | 1509 | { |
| 1510 | − C67_asm("MPYSP.M", v, r, v); | |
| 1510 | + C67_asm(S, "MPYSP.M", v, r, v); | |
| 1511 | 1511 | } |
| 1512 | 1512 | |
| 1513 | −void C67_ADDDP(int r, int v) | |
| 1513 | +void C67_ADDDP(TCCState* S, int r, int v) | |
| 1514 | 1514 | { |
| 1515 | − C67_asm("ADDDP.L", v, r, v); | |
| 1515 | + C67_asm(S, "ADDDP.L", v, r, v); | |
| 1516 | 1516 | } |
| 1517 | 1517 | |
| 1518 | −void C67_SUBDP(int r, int v) | |
| 1518 | +void C67_SUBDP(TCCState* S, int r, int v) | |
| 1519 | 1519 | { |
| 1520 | − C67_asm("SUBDP.L", v, r, v); | |
| 1520 | + C67_asm(S, "SUBDP.L", v, r, v); | |
| 1521 | 1521 | } |
| 1522 | 1522 | |
| 1523 | −void C67_MPYDP(int r, int v) | |
| 1523 | +void C67_MPYDP(TCCState* S, int r, int v) | |
| 1524 | 1524 | { |
| 1525 | − C67_asm("MPYDP.M", v, r, v); | |
| 1525 | + C67_asm(S, "MPYDP.M", v, r, v); | |
| 1526 | 1526 | } |
| 1527 | 1527 | |
| 1528 | −void C67_MPYI(int r, int v) | |
| 1528 | +void C67_MPYI(TCCState* S, int r, int v) | |
| 1529 | 1529 | { |
| 1530 | − C67_asm("MPYI.M", v, r, v); | |
| 1530 | + C67_asm(S, "MPYI.M", v, r, v); | |
| 1531 | 1531 | } |
| 1532 | 1532 | |
| 1533 | −void C67_SHL(int r, int v) | |
| 1533 | +void C67_SHL(TCCState* S, int r, int v) | |
| 1534 | 1534 | { |
| 1535 | − C67_asm("SHL.S", r, v, v); | |
| 1535 | + C67_asm(S, "SHL.S", r, v, v); | |
| 1536 | 1536 | } |
| 1537 | 1537 | |
| 1538 | −void C67_SHRU(int r, int v) | |
| 1538 | +void C67_SHRU(TCCState* S, int r, int v) | |
| 1539 | 1539 | { |
| 1540 | − C67_asm("SHRU.S", r, v, v); | |
| 1540 | + C67_asm(S, "SHRU.S", r, v, v); | |
| 1541 | 1541 | } |
| 1542 | 1542 | |
| 1543 | −void C67_SHR(int r, int v) | |
| 1543 | +void C67_SHR(TCCState* S, int r, int v) | |
| 1544 | 1544 | { |
| 1545 | − C67_asm("SHR.S", r, v, v); | |
| 1545 | + C67_asm(S, "SHR.S", r, v, v); | |
| 1546 | 1546 | } |
| 1547 | 1547 | |
| 1548 | 1548 | |
| 1549 | 1549 | |
| 1550 | 1550 | /* load 'r' from value 'sv' */ |
| 1551 | −void load(int r, SValue * sv) | |
| 1551 | +void load(TCCState* S, int r, SValue * sv) | |
| 1552 | 1552 | { |
| 1553 | 1553 | int v, t, ft, fc, fr, size = 0, element; |
| 1554 | 1554 | BOOL Unsigned = FALSE; |
| @@ -1564,10 +1564,10 @@ void load(int r, SValue * sv) · 9 unmodified lines | ||
| 1564 | 1564 | v1.type.t = VT_INT; |
| 1565 | 1565 | v1.r = VT_LOCAL | VT_LVAL; |
| 1566 | 1566 | v1.c.i = fc; |
| 1567 | − load(r, &v1); | |
| 1567 | + load(S, r, &v1); | |
| 1568 | 1568 | fr = r; |
| 1569 | 1569 | } else if ((ft & VT_BTYPE) == VT_LDOUBLE) { |
| 1570 | − tcc_error("long double not supported"); | |
| 1570 | + tcc_error(S, "long double not supported"); | |
| 1571 | 1571 | } else if ((ft & VT_TYPE) == VT_BYTE) { |
| 1572 | 1572 | size = 1; |
| 1573 | 1573 | } else if ((ft & VT_TYPE) == (VT_BYTE | VT_UNSIGNED)) { |
| @@ -1608,109 +1608,109 @@ void load(int r, SValue * sv) · 34 unmodified lines | ||
| 1608 | 1608 | { |
| 1609 | 1609 | if (size == 1) { |
| 1610 | 1610 | if (Unsigned) |
| 1611 | − C67_LDBU_PTR(v, r); // LDBU *v,r | |
| 1611 | + C67_LDBU_PTR(S, v, r); // LDBU *v,r | |
| 1612 | 1612 | else |
| 1613 | − C67_LDB_PTR(v, r); // LDB *v,r | |
| 1613 | + C67_LDB_PTR(S, v, r); // LDB *v,r | |
| 1614 | 1614 | } else if (size == 2) { |
| 1615 | 1615 | if (Unsigned) |
| 1616 | − C67_LDHU_PTR(v, r); // LDHU *v,r | |
| 1616 | + C67_LDHU_PTR(S, v, r); // LDHU *v,r | |
| 1617 | 1617 | else |
| 1618 | − C67_LDH_PTR(v, r); // LDH *v,r | |
| 1618 | + C67_LDH_PTR(S, v, r); // LDH *v,r | |
| 1619 | 1619 | } else if (size == 4) { |
| 1620 | − C67_LDW_PTR(v, r); // LDW *v,r | |
| 1620 | + C67_LDW_PTR(S, v, r); // LDW *v,r | |
| 1621 | 1621 | } else if (size == 8) { |
| 1622 | − C67_LDDW_PTR(v, r); // LDDW *v,r | |
| 1622 | + C67_LDDW_PTR(S, v, r); // LDDW *v,r | |
| 1623 | 1623 | } |
| 1624 | 1624 | |
| 1625 | − C67_NOP(4); // NOP 4 | |
| 1625 | + C67_NOP(S, 4); // NOP 4 | |
| 1626 | 1626 | return; |
| 1627 | 1627 | } else if (fr & VT_SYM) { |
| 1628 | − greloc(cur_text_section, sv->sym, ind, R_C60LO16); // rem the inst need to be patched | |
| 1629 | − greloc(cur_text_section, sv->sym, ind + 4, R_C60HI16); | |
| 1628 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind, R_C60LO16); // rem the inst need to be patched | |
| 1629 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind + 4, R_C60HI16); | |
| 1630 | 1630 | |
| 1631 | 1631 | |
| 1632 | − C67_MVKL(C67_A0, fc); //r=reg to load, constant | |
| 1633 | − C67_MVKH(C67_A0, fc); //r=reg to load, constant | |
| 1632 | + C67_MVKL(S, C67_A0, fc); //r=reg to load, constant | |
| 1633 | + C67_MVKH(S, C67_A0, fc); //r=reg to load, constant | |
| 1634 | 1634 | |
| 1635 | 1635 | |
| 1636 | 1636 | if (size == 1) { |
| 1637 | 1637 | if (Unsigned) |
| 1638 | − C67_LDBU_PTR(C67_A0, r); // LDBU *A0,r | |
| 1638 | + C67_LDBU_PTR(S, C67_A0, r); // LDBU *A0,r | |
| 1639 | 1639 | else |
| 1640 | − C67_LDB_PTR(C67_A0, r); // LDB *A0,r | |
| 1640 | + C67_LDB_PTR(S, C67_A0, r); // LDB *A0,r | |
| 1641 | 1641 | } else if (size == 2) { |
| 1642 | 1642 | if (Unsigned) |
| 1643 | − C67_LDHU_PTR(C67_A0, r); // LDHU *A0,r | |
| 1643 | + C67_LDHU_PTR(S, C67_A0, r); // LDHU *A0,r | |
| 1644 | 1644 | else |
| 1645 | − C67_LDH_PTR(C67_A0, r); // LDH *A0,r | |
| 1645 | + C67_LDH_PTR(S, C67_A0, r); // LDH *A0,r | |
| 1646 | 1646 | } else if (size == 4) { |
| 1647 | − C67_LDW_PTR(C67_A0, r); // LDW *A0,r | |
| 1647 | + C67_LDW_PTR(S, C67_A0, r); // LDW *A0,r | |
| 1648 | 1648 | } else if (size == 8) { |
| 1649 | − C67_LDDW_PTR(C67_A0, r); // LDDW *A0,r | |
| 1649 | + C67_LDDW_PTR(S, C67_A0, r); // LDDW *A0,r | |
| 1650 | 1650 | } |
| 1651 | 1651 | |
| 1652 | − C67_NOP(4); // NOP 4 | |
| 1652 | + C67_NOP(S, 4); // NOP 4 | |
| 1653 | 1653 | return; |
| 1654 | 1654 | } else { |
| 1655 | 1655 | element = size; |
| 1656 | 1656 | |
| 1657 | 1657 | // divide offset in bytes to create element index |
| 1658 | − C67_MVKL(C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1659 | − C67_MVKH(C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1658 | + C67_MVKL(S, C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1659 | + C67_MVKH(S, C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1660 | 1660 | |
| 1661 | 1661 | if (size == 1) { |
| 1662 | 1662 | if (Unsigned) |
| 1663 | − C67_LDBU_SP_A0(r); // LDBU r, SP[A0] | |
| 1663 | + C67_LDBU_SP_A0(S, r); // LDBU r, SP[A0] | |
| 1664 | 1664 | else |
| 1665 | − C67_LDB_SP_A0(r); // LDB r, SP[A0] | |
| 1665 | + C67_LDB_SP_A0(S, r); // LDB r, SP[A0] | |
| 1666 | 1666 | } else if (size == 2) { |
| 1667 | 1667 | if (Unsigned) |
| 1668 | − C67_LDHU_SP_A0(r); // LDHU r, SP[A0] | |
| 1668 | + C67_LDHU_SP_A0(S, r); // LDHU r, SP[A0] | |
| 1669 | 1669 | else |
| 1670 | − C67_LDH_SP_A0(r); // LDH r, SP[A0] | |
| 1670 | + C67_LDH_SP_A0(S, r); // LDH r, SP[A0] | |
| 1671 | 1671 | } else if (size == 4) { |
| 1672 | − C67_LDW_SP_A0(r); // LDW r, SP[A0] | |
| 1672 | + C67_LDW_SP_A0(S, r); // LDW r, SP[A0] | |
| 1673 | 1673 | } else if (size == 8) { |
| 1674 | − C67_LDDW_SP_A0(r); // LDDW r, SP[A0] | |
| 1674 | + C67_LDDW_SP_A0(S, r); // LDDW r, SP[A0] | |
| 1675 | 1675 | } |
| 1676 | 1676 | |
| 1677 | 1677 | |
| 1678 | − C67_NOP(4); // NOP 4 | |
| 1678 | + C67_NOP(S, 4); // NOP 4 | |
| 1679 | 1679 | return; |
| 1680 | 1680 | } |
| 1681 | 1681 | } else { |
| 1682 | 1682 | if (v == VT_CONST) { |
| 1683 | 1683 | if (fr & VT_SYM) { |
| 1684 | − greloc(cur_text_section, sv->sym, ind, R_C60LO16); // rem the inst need to be patched | |
| 1685 | − greloc(cur_text_section, sv->sym, ind + 4, R_C60HI16); | |
| 1684 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind, R_C60LO16); // rem the inst need to be patched | |
| 1685 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind + 4, R_C60HI16); | |
| 1686 | 1686 | } |
| 1687 | − C67_MVKL(r, fc); //r=reg to load, constant | |
| 1688 | − C67_MVKH(r, fc); //r=reg to load, constant | |
| 1687 | + C67_MVKL(S, r, fc); //r=reg to load, constant | |
| 1688 | + C67_MVKH(S, r, fc); //r=reg to load, constant | |
| 1689 | 1689 | } else if (v == VT_LOCAL) { |
| 1690 | − C67_MVKL(r, fc + 8); //r=reg to load, constant C67 stack points to next free | |
| 1691 | − C67_MVKH(r, fc + 8); //r=reg to load, constant | |
| 1692 | − C67_ADD(C67_FP, r); // MV v,r v -> r | |
| 1690 | + C67_MVKL(S, r, fc + 8); //r=reg to load, constant C67 stack points to next free | |
| 1691 | + C67_MVKH(S, r, fc + 8); //r=reg to load, constant | |
| 1692 | + C67_ADD(S, C67_FP, r); // MV v,r v -> r | |
| 1693 | 1693 | } else if (v == VT_CMP) { |
| 1694 | − C67_MV(C67_compare_reg, r); // MV v,r v -> r | |
| 1694 | + C67_MV(S, C67_compare_reg, r); // MV v,r v -> r | |
| 1695 | 1695 | } else if (v == VT_JMP || v == VT_JMPI) { |
| 1696 | 1696 | t = v & 1; |
| 1697 | − C67_B_DISP(4); // Branch with constant displacement, skip over this branch, load, nop, load | |
| 1698 | − C67_MVKL(r, t); // r=reg to load, 0 or 1 (do this while branching) | |
| 1699 | − C67_NOP(4); // NOP 4 | |
| 1700 | − gsym(fc); // modifies other branches to branch here | |
| 1701 | − C67_MVKL(r, t ^ 1); // r=reg to load, 0 or 1 | |
| 1697 | + C67_B_DISP(S, 4); // Branch with constant displacement, skip over this branch, load, nop, load | |
| 1698 | + C67_MVKL(S, r, t); // r=reg to load, 0 or 1 (do this while branching) | |
| 1699 | + C67_NOP(S, 4); // NOP 4 | |
| 1700 | + gsym(S, fc); // modifies other branches to branch here | |
| 1701 | + C67_MVKL(S, r, t ^ 1); // r=reg to load, 0 or 1 | |
| 1702 | 1702 | } else if (v != r) { |
| 1703 | − C67_MV(v, r); // MV v,r v -> r | |
| 1703 | + C67_MV(S, v, r); // MV v,r v -> r | |
| 1704 | 1704 | |
| 1705 | 1705 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 1706 | − C67_MV(v + 1, r + 1); // MV v,r v -> r | |
| 1706 | + C67_MV(S, v + 1, r + 1); // MV v,r v -> r | |
| 1707 | 1707 | } |
| 1708 | 1708 | } |
| 1709 | 1709 | } |
| 1710 | 1710 | |
| 1711 | 1711 | |
| 1712 | 1712 | /* store register 'r' in lvalue 'v' */ |
| 1713 | −void store(int r, SValue * v) | |
| 1713 | +void store(TCCState* S, int r, SValue * v) | |
| 1714 | 1714 | { |
| 1715 | 1715 | int fr, bt, ft, fc, size, t, element; |
| 1716 | 1716 | |
| @@ -1721,7 +1721,7 @@ void store(int r, SValue * v) · 4 unmodified lines | ||
| 1721 | 1721 | /* XXX: incorrect if float reg to reg */ |
| 1722 | 1722 | |
| 1723 | 1723 | if (bt == VT_LDOUBLE) { |
| 1724 | − tcc_error("long double not supported"); | |
| 1724 | + tcc_error(S, "long double not supported"); | |
| 1725 | 1725 | } else { |
| 1726 | 1726 | if (bt == VT_SHORT) |
| 1727 | 1727 | size = 2; |
| @@ -1736,21 +1736,21 @@ void store(int r, SValue * v) · 8 unmodified lines | ||
| 1736 | 1736 | /* constant memory reference */ |
| 1737 | 1737 | |
| 1738 | 1738 | if (v->r & VT_SYM) { |
| 1739 | − greloc(cur_text_section, v->sym, ind, R_C60LO16); // rem the inst need to be patched | |
| 1740 | − greloc(cur_text_section, v->sym, ind + 4, R_C60HI16); | |
| 1739 | + greloc(S, cur_text_section, v->sym, S->tccgen_ind, R_C60LO16); // rem the inst need to be patched | |
| 1740 | + greloc(S, cur_text_section, v->sym, S->tccgen_ind + 4, R_C60HI16); | |
| 1741 | 1741 | } |
| 1742 | − C67_MVKL(C67_A0, fc); //r=reg to load, constant | |
| 1743 | − C67_MVKH(C67_A0, fc); //r=reg to load, constant | |
| 1742 | + C67_MVKL(S, C67_A0, fc); //r=reg to load, constant | |
| 1743 | + C67_MVKH(S, C67_A0, fc); //r=reg to load, constant | |
| 1744 | 1744 | |
| 1745 | 1745 | if (size == 1) |
| 1746 | − C67_STB_PTR(r, C67_A0); // STB r, *A0 | |
| 1746 | + C67_STB_PTR(S, r, C67_A0); // STB r, *A0 | |
| 1747 | 1747 | else if (size == 2) |
| 1748 | − C67_STH_PTR(r, C67_A0); // STH r, *A0 | |
| 1748 | + C67_STH_PTR(S, r, C67_A0); // STH r, *A0 | |
| 1749 | 1749 | else if (size == 4 || size == 8) |
| 1750 | − C67_STW_PTR(r, C67_A0); // STW r, *A0 | |
| 1750 | + C67_STW_PTR(S, r, C67_A0); // STW r, *A0 | |
| 1751 | 1751 | |
| 1752 | 1752 | if (size == 8) |
| 1753 | − C67_STW_PTR_PRE_INC(r + 1, C67_A0, 1); // STW r, *+A0[1] | |
| 1753 | + C67_STW_PTR_PRE_INC(S, r + 1, C67_A0, 1); // STW r, *+A0[1] | |
| 1754 | 1754 | } else if ((v->r & VT_VALMASK) == VT_LOCAL) { |
| 1755 | 1755 | // check case of storing to passed argument that |
| 1756 | 1756 | // tcc thinks is on the stack but for C67 is |
| @@ -1781,68 +1781,68 @@ void store(int r, SValue * v) · 24 unmodified lines | ||
| 1781 | 1781 | element = size; |
| 1782 | 1782 | |
| 1783 | 1783 | // divide offset in bytes to create word index |
| 1784 | − C67_MVKL(C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1785 | − C67_MVKH(C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1784 | + C67_MVKL(S, C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1785 | + C67_MVKH(S, C67_A0, (fc / element) + 8 / element); //r=reg to load, constant | |
| 1786 | 1786 | |
| 1787 | 1787 | |
| 1788 | 1788 | |
| 1789 | 1789 | if (size == 1) |
| 1790 | − C67_STB_SP_A0(r); // STB r, SP[A0] | |
| 1790 | + C67_STB_SP_A0(S, r); // STB r, SP[A0] | |
| 1791 | 1791 | else if (size == 2) |
| 1792 | − C67_STH_SP_A0(r); // STH r, SP[A0] | |
| 1792 | + C67_STH_SP_A0(S, r); // STH r, SP[A0] | |
| 1793 | 1793 | else if (size == 4 || size == 8) |
| 1794 | − C67_STW_SP_A0(r); // STW r, SP[A0] | |
| 1794 | + C67_STW_SP_A0(S, r); // STW r, SP[A0] | |
| 1795 | 1795 | |
| 1796 | 1796 | if (size == 8) { |
| 1797 | − C67_ADDK(1, C67_A0); // ADDK 1,A0 | |
| 1798 | − C67_STW_SP_A0(r + 1); // STW r, SP[A0] | |
| 1797 | + C67_ADDK(S, 1, C67_A0); // ADDK 1,A0 | |
| 1798 | + C67_STW_SP_A0(S, r + 1); // STW r, SP[A0] | |
| 1799 | 1799 | } |
| 1800 | 1800 | } else { |
| 1801 | 1801 | if (size == 1) |
| 1802 | − C67_STB_PTR(r, fr); // STB r, *fr | |
| 1802 | + C67_STB_PTR(S, r, fr); // STB r, *fr | |
| 1803 | 1803 | else if (size == 2) |
| 1804 | − C67_STH_PTR(r, fr); // STH r, *fr | |
| 1804 | + C67_STH_PTR(S, r, fr); // STH r, *fr | |
| 1805 | 1805 | else if (size == 4 || size == 8) |
| 1806 | − C67_STW_PTR(r, fr); // STW r, *fr | |
| 1806 | + C67_STW_PTR(S, r, fr); // STW r, *fr | |
| 1807 | 1807 | |
| 1808 | 1808 | if (size == 8) { |
| 1809 | − C67_STW_PTR_PRE_INC(r + 1, fr, 1); // STW r, *+fr[1] | |
| 1809 | + C67_STW_PTR_PRE_INC(S, r + 1, fr, 1); // STW r, *+fr[1] | |
| 1810 | 1810 | } |
| 1811 | 1811 | } |
| 1812 | 1812 | } |
| 1813 | 1813 | } |
| 1814 | 1814 | |
| 1815 | 1815 | /* 'is_jmp' is '1' if it is a jump */ |
| 1816 | −static void gcall_or_jmp(int is_jmp) | |
| 1816 | +static void gcall_or_jmp(TCCState* S, int is_jmp) | |
| 1817 | 1817 | { |
| 1818 | 1818 | int r; |
| 1819 | 1819 | Sym *sym; |
| 1820 | 1820 | |
| 1821 | − if ((vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST) { | |
| 1821 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST) { | |
| 1822 | 1822 | /* constant case */ |
| 1823 | − if (vtop->r & VT_SYM) { | |
| 1823 | + if (S->tccgen_vtop->r & VT_SYM) { | |
| 1824 | 1824 | /* relocation case */ |
| 1825 | 1825 | |
| 1826 | 1826 | // get add into A0, then start the jump B3 |
| 1827 | 1827 | |
| 1828 | − greloc(cur_text_section, vtop->sym, ind, R_C60LO16); // rem the inst need to be patched | |
| 1829 | − greloc(cur_text_section, vtop->sym, ind + 4, R_C60HI16); | |
| 1828 | + greloc(S, cur_text_section, S->tccgen_vtop->sym, S->tccgen_ind, R_C60LO16); // rem the inst need to be patched | |
| 1829 | + greloc(S, cur_text_section, S->tccgen_vtop->sym, S->tccgen_ind + 4, R_C60HI16); | |
| 1830 | 1830 | |
| 1831 | − C67_MVKL(C67_A0, 0); //r=reg to load, constant | |
| 1832 | − C67_MVKH(C67_A0, 0); //r=reg to load, constant | |
| 1833 | − C67_IREG_B_REG(0, C67_CREG_ZERO, C67_A0); // B.S2x A0 | |
| 1831 | + C67_MVKL(S, C67_A0, 0); //r=reg to load, constant | |
| 1832 | + C67_MVKH(S, C67_A0, 0); //r=reg to load, constant | |
| 1833 | + C67_IREG_B_REG(S, 0, C67_CREG_ZERO, C67_A0); // B.S2x A0 | |
| 1834 | 1834 | |
| 1835 | 1835 | if (is_jmp) { |
| 1836 | − C67_NOP(5); // simple jump, just put NOP | |
| 1836 | + C67_NOP(S, 5); // simple jump, just put NOP | |
| 1837 | 1837 | } else { |
| 1838 | 1838 | // Call, must load return address into B3 during delay slots |
| 1839 | 1839 | |
| 1840 | − sym = get_sym_ref(&char_pointer_type, cur_text_section, ind + 12, 0); // symbol for return address | |
| 1841 | − greloc(cur_text_section, sym, ind, R_C60LO16); // rem the inst need to be patched | |
| 1842 | − greloc(cur_text_section, sym, ind + 4, R_C60HI16); | |
| 1843 | − C67_MVKL(C67_B3, 0); //r=reg to load, constant | |
| 1844 | − C67_MVKH(C67_B3, 0); //r=reg to load, constant | |
| 1845 | − C67_NOP(3); // put remaining NOPs | |
| 1840 | + sym = get_sym_ref(S, &S->tccgen_char_pointer_type, cur_text_section, S->tccgen_ind + 12, 0); // symbol for return address | |
| 1841 | + greloc(S, cur_text_section, sym, S->tccgen_ind, R_C60LO16); // rem the inst need to be patched | |
| 1842 | + greloc(S, cur_text_section, sym, S->tccgen_ind + 4, R_C60HI16); | |
| 1843 | + C67_MVKL(S, C67_B3, 0); //r=reg to load, constant | |
| 1844 | + C67_MVKH(S, C67_B3, 0); //r=reg to load, constant | |
| 1845 | + C67_NOP(S, 3); // put remaining NOPs | |
| 1846 | 1846 | } |
| 1847 | 1847 | } else { |
| 1848 | 1848 | /* put an empty PC32 relocation */ |
| @@ -1850,20 +1850,20 @@ static void gcall_or_jmp(int is_jmp) · 1 unmodified line | ||
| 1850 | 1850 | } |
| 1851 | 1851 | } else { |
| 1852 | 1852 | /* otherwise, indirect call */ |
| 1853 | − r = gv(RC_INT); | |
| 1854 | − C67_IREG_B_REG(0, C67_CREG_ZERO, r); // B.S2x r | |
| 1853 | + r = gv(S, RC_INT); | |
| 1854 | + C67_IREG_B_REG(S, 0, C67_CREG_ZERO, r); // B.S2x r | |
| 1855 | 1855 | |
| 1856 | 1856 | if (is_jmp) { |
| 1857 | − C67_NOP(5); // simple jump, just put NOP | |
| 1857 | + C67_NOP(S, 5); // simple jump, just put NOP | |
| 1858 | 1858 | } else { |
| 1859 | 1859 | // Call, must load return address into B3 during delay slots |
| 1860 | 1860 | |
| 1861 | − sym = get_sym_ref(&char_pointer_type, cur_text_section, ind + 12, 0); // symbol for return address | |
| 1862 | − greloc(cur_text_section, sym, ind, R_C60LO16); // rem the inst need to be patched | |
| 1863 | − greloc(cur_text_section, sym, ind + 4, R_C60HI16); | |
| 1864 | − C67_MVKL(C67_B3, 0); //r=reg to load, constant | |
| 1865 | − C67_MVKH(C67_B3, 0); //r=reg to load, constant | |
| 1866 | − C67_NOP(3); // put remaining NOPs | |
| 1861 | + sym = get_sym_ref(S, &S->tccgen_char_pointer_type, cur_text_section, S->tccgen_ind + 12, 0); // symbol for return address | |
| 1862 | + greloc(S, cur_text_section, sym, S->tccgen_ind, R_C60LO16); // rem the inst need to be patched | |
| 1863 | + greloc(S, cur_text_section, sym, S->tccgen_ind + 4, R_C60HI16); | |
| 1864 | + C67_MVKL(S, C67_B3, 0); //r=reg to load, constant | |
| 1865 | + C67_MVKH(S, C67_B3, 0); //r=reg to load, constant | |
| 1866 | + C67_NOP(S, 3); // put remaining NOPs | |
| 1867 | 1867 | } |
| 1868 | 1868 | } |
| 1869 | 1869 | } |
| @@ -1877,29 +1877,29 @@ ST_FUNC int gfunc_sret(CType *vt, int variadic, CType *ret, int *ret_align, int · 7 unmodified lines | ||
| 1877 | 1877 | |
| 1878 | 1878 | /* generate function call with address in (vtop->t, vtop->c) and free function |
| 1879 | 1879 | context. Stack entry is popped */ |
| 1880 | −void gfunc_call(int nb_args) | |
| 1880 | +void gfunc_call(TCCState* S, int nb_args) | |
| 1881 | 1881 | { |
| 1882 | 1882 | int i, r, size = 0; |
| 1883 | 1883 | int args_sizes[NoCallArgsPassedOnStack]; |
| 1884 | 1884 | |
| 1885 | 1885 | if (nb_args > NoCallArgsPassedOnStack) { |
| 1886 | − tcc_error("more than 10 function params not currently supported"); | |
| 1886 | + tcc_error(S, "more than 10 function params not currently supported"); | |
| 1887 | 1887 | // handle more than 10, put some on the stack |
| 1888 | 1888 | } |
| 1889 | 1889 | |
| 1890 | 1890 | for (i = 0; i < nb_args; i++) { |
| 1891 | − if ((vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1891 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 1892 | 1892 | ALWAYS_ASSERT(FALSE); |
| 1893 | 1893 | } else { |
| 1894 | 1894 | /* simple type (currently always same size) */ |
| 1895 | 1895 | /* XXX: implicit cast ? */ |
| 1896 | 1896 | |
| 1897 | 1897 | |
| 1898 | − if ((vtop->type.t & VT_BTYPE) == VT_LLONG) { | |
| 1899 | − tcc_error("long long not supported"); | |
| 1900 | − } else if ((vtop->type.t & VT_BTYPE) == VT_LDOUBLE) { | |
| 1901 | − tcc_error("long double not supported"); | |
| 1902 | − } else if ((vtop->type.t & VT_BTYPE) == VT_DOUBLE) { | |
| 1898 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LLONG) { | |
| 1899 | + tcc_error(S, "long long not supported"); | |
| 1900 | + } else if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LDOUBLE) { | |
| 1901 | + tcc_error(S, "long double not supported"); | |
| 1902 | + } else if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_DOUBLE) { | |
| 1903 | 1903 | size = 8; |
| 1904 | 1904 | } else { |
| 1905 | 1905 | size = 4; |
| @@ -1907,19 +1907,19 @@ void gfunc_call(int nb_args) · 1 unmodified line | ||
| 1907 | 1907 | |
| 1908 | 1908 | // put the parameter into the corresponding reg (pair) |
| 1909 | 1909 | |
| 1910 | − r = gv(RC_C67_A4 << (2 * i)); | |
| 1910 | + r = gv(S, RC_C67_A4 << (2 * i)); | |
| 1911 | 1911 | |
| 1912 | 1912 | // must put on stack because with 1 pass compiler , no way to tell |
| 1913 | 1913 | // if an up coming nested call might overwrite these regs |
| 1914 | 1914 | |
| 1915 | − C67_PUSH(r); | |
| 1915 | + C67_PUSH(S, r); | |
| 1916 | 1916 | |
| 1917 | 1917 | if (size == 8) { |
| 1918 | − C67_STW_PTR_PRE_INC(r + 1, C67_SP, 3); // STW r, *+SP[3] (go back and put the other) | |
| 1918 | + C67_STW_PTR_PRE_INC(S, r + 1, C67_SP, 3); // STW r, *+SP[3] (go back and put the other) | |
| 1919 | 1919 | } |
| 1920 | 1920 | args_sizes[i] = size; |
| 1921 | 1921 | } |
| 1922 | − vtop--; | |
| 1922 | + S->tccgen_vtop--; | |
| 1923 | 1923 | } |
| 1924 | 1924 | // POP all the params on the stack into registers for the |
| 1925 | 1925 | // immediate call (in reverse order) |
| @@ -1927,12 +1927,12 @@ void gfunc_call(int nb_args) · 1 unmodified line | ||
| 1927 | 1927 | for (i = nb_args - 1; i >= 0; i--) { |
| 1928 | 1928 | |
| 1929 | 1929 | if (args_sizes[i] == 8) |
| 1930 | − C67_POP_DW(TREG_C67_A4 + i * 2); | |
| 1930 | + C67_POP_DW(S, TREG_C67_A4 + i * 2); | |
| 1931 | 1931 | else |
| 1932 | − C67_POP(TREG_C67_A4 + i * 2); | |
| 1932 | + C67_POP(S, TREG_C67_A4 + i * 2); | |
| 1933 | 1933 | } |
| 1934 | − gcall_or_jmp(0); | |
| 1935 | − vtop--; | |
| 1934 | + gcall_or_jmp(S, 0); | |
| 1935 | + S->tccgen_vtop--; | |
| 1936 | 1936 | } |
| 1937 | 1937 | |
| 1938 | 1938 | |
| @@ -1946,7 +1946,7 @@ void gfunc_call(int nb_args) · 7 unmodified lines | ||
| 1946 | 1946 | // parameters are loaded and restored upon return (or if/when needed). |
| 1947 | 1947 | |
| 1948 | 1948 | /* generate function prolog of type 't' */ |
| 1949 | −void gfunc_prolog(Sym *func_sym) | |
| 1949 | +void gfunc_prolog(TCCState* S, Sym *func_sym) | |
| 1950 | 1950 | { |
| 1951 | 1951 | CType *func_type = &func_sym->type; |
| 1952 | 1952 | int addr, align, size, func_call, i; |
| @@ -1958,8 +1958,8 @@ void gfunc_prolog(Sym *func_sym) · 5 unmodified lines | ||
| 1958 | 1958 | addr = 8; |
| 1959 | 1959 | /* if the function returns a structure, then add an |
| 1960 | 1960 | implicit pointer parameter */ |
| 1961 | − if ((func_vt.t & VT_BTYPE) == VT_STRUCT) { | |
| 1962 | − func_vc = addr; | |
| 1961 | + if ((S->tccgen_func_vt.t & VT_BTYPE) == VT_STRUCT) { | |
| 1962 | + S->tccgen_func_vc = addr; | |
| 1963 | 1963 | addr += 4; |
| 1964 | 1964 | } |
| 1965 | 1965 | |
| @@ -1968,7 +1968,7 @@ void gfunc_prolog(Sym *func_sym) · 2 unmodified lines | ||
| 1968 | 1968 | /* define parameters */ |
| 1969 | 1969 | while ((sym = sym->next) != NULL) { |
| 1970 | 1970 | type = &sym->type; |
| 1971 | − sym_push(sym->v & ~SYM_FIELD, type, VT_LOCAL | VT_LVAL, addr); | |
| 1971 | + sym_push(S, sym->v & ~SYM_FIELD, type, VT_LOCAL | VT_LVAL, addr); | |
| 1972 | 1972 | size = type_size(type, &align); |
| 1973 | 1973 | size = (size + 3) & ~3; |
| 1974 | 1974 | |
| @@ -1992,76 +1992,76 @@ void gfunc_prolog(Sym *func_sym) · 17 unmodified lines | ||
| 1992 | 1992 | if (func_call == FUNC_STDCALL) |
| 1993 | 1993 | func_ret_sub = addr - 8; |
| 1994 | 1994 | |
| 1995 | − C67_MV(C67_FP, C67_A0); // move FP -> A0 | |
| 1996 | − C67_MV(C67_SP, C67_FP); // move SP -> FP | |
| 1995 | + C67_MV(S, C67_FP, C67_A0); // move FP -> A0 | |
| 1996 | + C67_MV(S, C67_SP, C67_FP); // move SP -> FP | |
| 1997 | 1997 | |
| 1998 | 1998 | // place all the args passed in regs onto the stack |
| 1999 | 1999 | |
| 2000 | − loc = 0; | |
| 2000 | + S->tccgen_loc = 0; | |
| 2001 | 2001 | for (i = 0; i < NoOfCurFuncArgs; i++) { |
| 2002 | 2002 | |
| 2003 | − ParamLocOnStack[i] = loc; // remember where the param is | |
| 2004 | − loc += -8; | |
| 2003 | + ParamLocOnStack[i] = S->tccgen_loc; // remember where the param is | |
| 2004 | + S->tccgen_loc += -8; | |
| 2005 | 2005 | |
| 2006 | − C67_PUSH(TREG_C67_A4 + i * 2); | |
| 2006 | + C67_PUSH(S, TREG_C67_A4 + i * 2); | |
| 2007 | 2007 | |
| 2008 | 2008 | if (TranslateStackToReg[i] == 8) { |
| 2009 | − C67_STW_PTR_PRE_INC(TREG_C67_A4 + i * 2 + 1, C67_SP, 3); // STW r, *+SP[1] (go back and put the other) | |
| 2009 | + C67_STW_PTR_PRE_INC(S, TREG_C67_A4 + i * 2 + 1, C67_SP, 3); // STW r, *+SP[1] (go back and put the other) | |
| 2010 | 2010 | } |
| 2011 | 2011 | } |
| 2012 | 2012 | |
| 2013 | − TotalBytesPushedOnStack = -loc; | |
| 2013 | + TotalBytesPushedOnStack = -S->tccgen_loc; | |
| 2014 | 2014 | |
| 2015 | − func_sub_sp_offset = ind; // remember where we put the stack instruction | |
| 2016 | − C67_ADDK(0, C67_SP); // ADDK.L2 loc,SP (just put zero temporarily) | |
| 2015 | + func_sub_sp_offset = S->tccgen_ind; // remember where we put the stack instruction | |
| 2016 | + C67_ADDK(S, 0, C67_SP); // ADDK.L2 loc,SP (just put zero temporarily) | |
| 2017 | 2017 | |
| 2018 | − C67_PUSH(C67_A0); | |
| 2019 | − C67_PUSH(C67_B3); | |
| 2018 | + C67_PUSH(S, C67_A0); | |
| 2019 | + C67_PUSH(S, C67_B3); | |
| 2020 | 2020 | } |
| 2021 | 2021 | |
| 2022 | 2022 | /* generate function epilog */ |
| 2023 | −void gfunc_epilog(void) | |
| 2023 | +void gfunc_epilog(TCCState* S) | |
| 2024 | 2024 | { |
| 2025 | 2025 | { |
| 2026 | − int local = (-loc + 7) & -8; // stack must stay aligned to 8 bytes for LDDW instr | |
| 2027 | − C67_POP(C67_B3); | |
| 2028 | − C67_NOP(4); // NOP wait for load | |
| 2029 | − C67_IREG_B_REG(0, C67_CREG_ZERO, C67_B3); // B.S2 B3 | |
| 2030 | − C67_POP(C67_FP); | |
| 2031 | − C67_ADDK(local, C67_SP); // ADDK.L2 loc,SP | |
| 2032 | − C67_Adjust_ADDK((int *) (cur_text_section->data + | |
| 2026 | + int local = (-S->tccgen_loc + 7) & -8; // stack must stay aligned to 8 bytes for LDDW instr | |
| 2027 | + C67_POP(S, C67_B3); | |
| 2028 | + C67_NOP(S, 4); // NOP wait for load | |
| 2029 | + C67_IREG_B_REG(S, 0, C67_CREG_ZERO, C67_B3); // B.S2 B3 | |
| 2030 | + C67_POP(S, C67_FP); | |
| 2031 | + C67_ADDK(S, local, C67_SP); // ADDK.L2 loc,SP | |
| 2032 | + C67_Adjust_ADDK(S, (int *) (cur_text_section->data + | |
| 2033 | 2033 | func_sub_sp_offset), |
| 2034 | 2034 | -local + TotalBytesPushedOnStack); |
| 2035 | − C67_NOP(3); // NOP | |
| 2035 | + C67_NOP(S, 3); // NOP | |
| 2036 | 2036 | } |
| 2037 | 2037 | } |
| 2038 | 2038 | |
| 2039 | −ST_FUNC void gen_fill_nops(int bytes) | |
| 2039 | +ST_FUNC void gen_fill_nops(TCCState* S, int bytes) | |
| 2040 | 2040 | { |
| 2041 | 2041 | if ((bytes & 3)) |
| 2042 | − tcc_error("alignment of code section not multiple of 4"); | |
| 2042 | + tcc_error(S, "alignment of code section not multiple of 4"); | |
| 2043 | 2043 | while (bytes > 0) { |
| 2044 | − C67_NOP(4); | |
| 2044 | + C67_NOP(S, 4); | |
| 2045 | 2045 | bytes -= 4; |
| 2046 | 2046 | } |
| 2047 | 2047 | } |
| 2048 | 2048 | |
| 2049 | 2049 | /* generate a jump to a label */ |
| 2050 | −int gjmp(int t) | |
| 2050 | +int gjmp(TCCState* S, int t) | |
| 2051 | 2051 | { |
| 2052 | − int ind1 = ind; | |
| 2053 | − if (nocode_wanted) | |
| 2052 | + int ind1 = S->tccgen_ind; | |
| 2053 | + if (S->tccgen_nocode_wanted) | |
| 2054 | 2054 | return t; |
| 2055 | 2055 | |
| 2056 | − C67_MVKL(C67_A0, t); //r=reg to load, constant | |
| 2057 | − C67_MVKH(C67_A0, t); //r=reg to load, constant | |
| 2058 | − C67_IREG_B_REG(0, C67_CREG_ZERO, C67_A0); // [!R] B.S2x A0 | |
| 2059 | − C67_NOP(5); | |
| 2056 | + C67_MVKL(S, C67_A0, t); //r=reg to load, constant | |
| 2057 | + C67_MVKH(S, C67_A0, t); //r=reg to load, constant | |
| 2058 | + C67_IREG_B_REG(S, 0, C67_CREG_ZERO, C67_A0); // [!R] B.S2x A0 | |
| 2059 | + C67_NOP(S, 5); | |
| 2060 | 2060 | return ind1; |
| 2061 | 2061 | } |
| 2062 | 2062 | |
| 2063 | 2063 | /* generate a jump to a fixed address */ |
| 2064 | −void gjmp_addr(int a) | |
| 2064 | +void gjmp_addr(TCCState* S, int a) | |
| 2065 | 2065 | { |
| 2066 | 2066 | Sym *sym; |
| 2067 | 2067 | // I guess this routine is used for relative short |
| @@ -2070,42 +2070,42 @@ void gjmp_addr(int a) · 2 unmodified lines | ||
| 2070 | 2070 | |
| 2071 | 2071 | // define a label that will be relocated |
| 2072 | 2072 | |
| 2073 | − sym = get_sym_ref(&char_pointer_type, cur_text_section, a, 0); | |
| 2074 | − greloc(cur_text_section, sym, ind, R_C60LO16); | |
| 2075 | − greloc(cur_text_section, sym, ind + 4, R_C60HI16); | |
| 2073 | + sym = get_sym_ref(S, &S->tccgen_char_pointer_type, cur_text_section, a, 0); | |
| 2074 | + greloc(S, cur_text_section, sym, S->tccgen_ind, R_C60LO16); | |
| 2075 | + greloc(S, cur_text_section, sym, S->tccgen_ind + 4, R_C60HI16); | |
| 2076 | 2076 | |
| 2077 | − gjmp(0); // place a zero there later the symbol will be added to it | |
| 2077 | + gjmp(S, 0); // place a zero there later the symbol will be added to it | |
| 2078 | 2078 | } |
| 2079 | 2079 | |
| 2080 | 2080 | /* generate a test. set 'inv' to invert test. Stack entry is popped */ |
| 2081 | −ST_FUNC int gjmp_cond(int op, int t) | |
| 2081 | +ST_FUNC int gjmp_cond(TCCState* S, int op, int t) | |
| 2082 | 2082 | { |
| 2083 | 2083 | int ind1; |
| 2084 | 2084 | int inv = op & 1; |
| 2085 | − if (nocode_wanted) | |
| 2085 | + if (S->tccgen_nocode_wanted) | |
| 2086 | 2086 | return t; |
| 2087 | 2087 | |
| 2088 | 2088 | /* fast case : can jump directly since flags are set */ |
| 2089 | 2089 | // C67 uses B2 sort of as flags register |
| 2090 | − ind1 = ind; | |
| 2091 | − C67_MVKL(C67_A0, t); //r=reg to load, constant | |
| 2092 | − C67_MVKH(C67_A0, t); //r=reg to load, constant | |
| 2090 | + ind1 = S->tccgen_ind; | |
| 2091 | + C67_MVKL(S, C67_A0, t); //r=reg to load, constant | |
| 2092 | + C67_MVKH(S, C67_A0, t); //r=reg to load, constant | |
| 2093 | 2093 | |
| 2094 | 2094 | if (C67_compare_reg != TREG_EAX && // check if not already in a conditional test reg |
| 2095 | 2095 | C67_compare_reg != TREG_EDX && |
| 2096 | 2096 | C67_compare_reg != TREG_ST0 && C67_compare_reg != C67_B2) { |
| 2097 | − C67_MV(C67_compare_reg, C67_B2); | |
| 2097 | + C67_MV(S, C67_compare_reg, C67_B2); | |
| 2098 | 2098 | C67_compare_reg = C67_B2; |
| 2099 | 2099 | } |
| 2100 | 2100 | |
| 2101 | − C67_IREG_B_REG(C67_invert_test ^ inv, C67_compare_reg, C67_A0); // [!R] B.S2x A0 | |
| 2102 | − C67_NOP(5); | |
| 2101 | + C67_IREG_B_REG(S, C67_invert_test ^ inv, C67_compare_reg, C67_A0); // [!R] B.S2x A0 | |
| 2102 | + C67_NOP(S, 5); | |
| 2103 | 2103 | t = ind1; //return where we need to patch |
| 2104 | 2104 | |
| 2105 | 2105 | return t; |
| 2106 | 2106 | } |
| 2107 | 2107 | |
| 2108 | −ST_FUNC int gjmp_append(int n0, int t) | |
| 2108 | +ST_FUNC int gjmp_append(TCCState* S, int n0, int t) | |
| 2109 | 2109 | { |
| 2110 | 2110 | if (n0) { |
| 2111 | 2111 | int n = n0, *p; |
| @@ -2129,7 +2129,7 @@ ST_FUNC int gjmp_append(int n0, int t) · 17 unmodified lines | ||
| 2129 | 2129 | } |
| 2130 | 2130 | |
| 2131 | 2131 | /* generate an integer binary operation */ |
| 2132 | −void gen_opi(int op) | |
| 2132 | +void gen_opi(TCCState* S, int op) | |
| 2133 | 2133 | { |
| 2134 | 2134 | int r, fr, opc, t; |
| 2135 | 2135 | |
| @@ -2146,62 +2146,62 @@ void gen_opi(int op) · 10 unmodified lines | ||
| 2146 | 2146 | |
| 2147 | 2147 | |
| 2148 | 2148 | if (op >= TOK_ULT && op <= TOK_GT) |
| 2149 | − gv2(RC_INT_BSIDE, RC_INT); // make sure r (src1) is on the B Side of CPU | |
| 2149 | + gv2(S, RC_INT_BSIDE, RC_INT); // make sure r (src1) is on the B Side of CPU | |
| 2150 | 2150 | else |
| 2151 | − gv2(RC_INT, RC_INT); | |
| 2151 | + gv2(S, RC_INT, RC_INT); | |
| 2152 | 2152 | |
| 2153 | − r = vtop[-1].r; | |
| 2154 | − fr = vtop[0].r; | |
| 2153 | + r = S->tccgen_vtop[-1].r; | |
| 2154 | + fr = S->tccgen_vtop[0].r; | |
| 2155 | 2155 | |
| 2156 | 2156 | C67_compare_reg = C67_B2; |
| 2157 | 2157 | |
| 2158 | 2158 | |
| 2159 | 2159 | if (op == TOK_LT) { |
| 2160 | − C67_CMPLT(r, fr, C67_B2); | |
| 2160 | + C67_CMPLT(S, r, fr, C67_B2); | |
| 2161 | 2161 | C67_invert_test = FALSE; |
| 2162 | 2162 | } else if (op == TOK_GE) { |
| 2163 | − C67_CMPLT(r, fr, C67_B2); | |
| 2163 | + C67_CMPLT(S, r, fr, C67_B2); | |
| 2164 | 2164 | C67_invert_test = TRUE; |
| 2165 | 2165 | } else if (op == TOK_GT) { |
| 2166 | − C67_CMPGT(r, fr, C67_B2); | |
| 2166 | + C67_CMPGT(S, r, fr, C67_B2); | |
| 2167 | 2167 | C67_invert_test = FALSE; |
| 2168 | 2168 | } else if (op == TOK_LE) { |
| 2169 | − C67_CMPGT(r, fr, C67_B2); | |
| 2169 | + C67_CMPGT(S, r, fr, C67_B2); | |
| 2170 | 2170 | C67_invert_test = TRUE; |
| 2171 | 2171 | } else if (op == TOK_EQ) { |
| 2172 | − C67_CMPEQ(r, fr, C67_B2); | |
| 2172 | + C67_CMPEQ(S, r, fr, C67_B2); | |
| 2173 | 2173 | C67_invert_test = FALSE; |
| 2174 | 2174 | } else if (op == TOK_NE) { |
| 2175 | − C67_CMPEQ(r, fr, C67_B2); | |
| 2175 | + C67_CMPEQ(S, r, fr, C67_B2); | |
| 2176 | 2176 | C67_invert_test = TRUE; |
| 2177 | 2177 | } else if (op == TOK_ULT) { |
| 2178 | − C67_CMPLTU(r, fr, C67_B2); | |
| 2178 | + C67_CMPLTU(S, r, fr, C67_B2); | |
| 2179 | 2179 | C67_invert_test = FALSE; |
| 2180 | 2180 | } else if (op == TOK_UGE) { |
| 2181 | − C67_CMPLTU(r, fr, C67_B2); | |
| 2181 | + C67_CMPLTU(S, r, fr, C67_B2); | |
| 2182 | 2182 | C67_invert_test = TRUE; |
| 2183 | 2183 | } else if (op == TOK_UGT) { |
| 2184 | − C67_CMPGTU(r, fr, C67_B2); | |
| 2184 | + C67_CMPGTU(S, r, fr, C67_B2); | |
| 2185 | 2185 | C67_invert_test = FALSE; |
| 2186 | 2186 | } else if (op == TOK_ULE) { |
| 2187 | − C67_CMPGTU(r, fr, C67_B2); | |
| 2187 | + C67_CMPGTU(S, r, fr, C67_B2); | |
| 2188 | 2188 | C67_invert_test = TRUE; |
| 2189 | 2189 | } else if (op == '+') |
| 2190 | − C67_ADD(fr, r); // ADD r,fr,r | |
| 2190 | + C67_ADD(S, fr, r); // ADD r,fr,r | |
| 2191 | 2191 | else if (op == '-') |
| 2192 | − C67_SUB(fr, r); // SUB r,fr,r | |
| 2192 | + C67_SUB(S, fr, r); // SUB r,fr,r | |
| 2193 | 2193 | else if (op == '&') |
| 2194 | − C67_AND(fr, r); // AND r,fr,r | |
| 2194 | + C67_AND(S, fr, r); // AND r,fr,r | |
| 2195 | 2195 | else if (op == '|') |
| 2196 | − C67_OR(fr, r); // OR r,fr,r | |
| 2196 | + C67_OR(S, fr, r); // OR r,fr,r | |
| 2197 | 2197 | else if (op == '^') |
| 2198 | − C67_XOR(fr, r); // XOR r,fr,r | |
| 2198 | + C67_XOR(S, fr, r); // XOR r,fr,r | |
| 2199 | 2199 | else |
| 2200 | 2200 | ALWAYS_ASSERT(FALSE); |
| 2201 | 2201 | |
| 2202 | − vtop--; | |
| 2202 | + S->tccgen_vtop--; | |
| 2203 | 2203 | if (op >= TOK_ULT && op <= TOK_GT) |
| 2204 | − vset_VT_CMP(0x80); | |
| 2204 | + vset_VT_CMP(S, 0x80); | |
| 2205 | 2205 | break; |
| 2206 | 2206 | case '-': |
| 2207 | 2207 | case TOK_SUBC1: /* sub with carry generation */ |
| @@ -2224,48 +2224,48 @@ void gen_opi(int op) · 16 unmodified lines | ||
| 2224 | 2224 | goto gen_op8; |
| 2225 | 2225 | case '*': |
| 2226 | 2226 | case TOK_UMULL: |
| 2227 | − gv2(RC_INT, RC_INT); | |
| 2228 | − r = vtop[-1].r; | |
| 2229 | − fr = vtop[0].r; | |
| 2230 | − vtop--; | |
| 2231 | − C67_MPYI(fr, r); // 32 bit multiply fr,r,fr | |
| 2232 | − C67_NOP(8); // NOP 8 for worst case | |
| 2227 | + gv2(S, RC_INT, RC_INT); | |
| 2228 | + r = S->tccgen_vtop[-1].r; | |
| 2229 | + fr = S->tccgen_vtop[0].r; | |
| 2230 | + S->tccgen_vtop--; | |
| 2231 | + C67_MPYI(S, fr, r); // 32 bit multiply fr,r,fr | |
| 2232 | + C67_NOP(S, 8); // NOP 8 for worst case | |
| 2233 | 2233 | break; |
| 2234 | 2234 | case TOK_SHL: |
| 2235 | − gv2(RC_INT_BSIDE, RC_INT_BSIDE); // shift amount must be on same side as dst | |
| 2236 | − r = vtop[-1].r; | |
| 2237 | − fr = vtop[0].r; | |
| 2238 | − vtop--; | |
| 2239 | − C67_SHL(fr, r); // arithmetic/logical shift | |
| 2235 | + gv2(S, RC_INT_BSIDE, RC_INT_BSIDE); // shift amount must be on same side as dst | |
| 2236 | + r = S->tccgen_vtop[-1].r; | |
| 2237 | + fr = S->tccgen_vtop[0].r; | |
| 2238 | + S->tccgen_vtop--; | |
| 2239 | + C67_SHL(S, fr, r); // arithmetic/logical shift | |
| 2240 | 2240 | break; |
| 2241 | 2241 | |
| 2242 | 2242 | case TOK_SHR: |
| 2243 | − gv2(RC_INT_BSIDE, RC_INT_BSIDE); // shift amount must be on same side as dst | |
| 2244 | − r = vtop[-1].r; | |
| 2245 | − fr = vtop[0].r; | |
| 2246 | − vtop--; | |
| 2247 | − C67_SHRU(fr, r); // logical shift | |
| 2243 | + gv2(S, RC_INT_BSIDE, RC_INT_BSIDE); // shift amount must be on same side as dst | |
| 2244 | + r = S->tccgen_vtop[-1].r; | |
| 2245 | + fr = S->tccgen_vtop[0].r; | |
| 2246 | + S->tccgen_vtop--; | |
| 2247 | + C67_SHRU(S, fr, r); // logical shift | |
| 2248 | 2248 | break; |
| 2249 | 2249 | |
| 2250 | 2250 | case TOK_SAR: |
| 2251 | − gv2(RC_INT_BSIDE, RC_INT_BSIDE); // shift amount must be on same side as dst | |
| 2252 | − r = vtop[-1].r; | |
| 2253 | − fr = vtop[0].r; | |
| 2254 | − vtop--; | |
| 2255 | − C67_SHR(fr, r); // arithmetic shift | |
| 2251 | + gv2(S, RC_INT_BSIDE, RC_INT_BSIDE); // shift amount must be on same side as dst | |
| 2252 | + r = S->tccgen_vtop[-1].r; | |
| 2253 | + fr = S->tccgen_vtop[0].r; | |
| 2254 | + S->tccgen_vtop--; | |
| 2255 | + C67_SHR(S, fr, r); // arithmetic shift | |
| 2256 | 2256 | break; |
| 2257 | 2257 | |
| 2258 | 2258 | case '/': |
| 2259 | 2259 | t = TOK__divi; |
| 2260 | 2260 | call_func: |
| 2261 | − vswap(); | |
| 2261 | + vswap(S); | |
| 2262 | 2262 | /* call generic idiv function */ |
| 2263 | − vpush_helper_func(t); | |
| 2264 | − vrott(3); | |
| 2265 | − gfunc_call(2); | |
| 2266 | − vpushi(0); | |
| 2267 | − vtop->r = REG_IRET; | |
| 2268 | − vtop->r2 = VT_CONST; | |
| 2263 | + vpush_helper_func(S, t); | |
| 2264 | + vrott(S, 3); | |
| 2265 | + gfunc_call(S, 2); | |
| 2266 | + vpushi(S, 0); | |
| 2267 | + S->tccgen_vtop->r = REG_IRET; | |
| 2268 | + S->tccgen_vtop->r2 = VT_CONST; | |
| 2269 | 2269 | break; |
| 2270 | 2270 | case TOK_UDIV: |
| 2271 | 2271 | case TOK_PDIV: |
| @@ -2287,127 +2287,127 @@ void gen_opi(int op) · 15 unmodified lines | ||
| 2287 | 2287 | /* generate a floating point operation 'v = t1 op t2' instruction. The |
| 2288 | 2288 | two operands are guaranteed to have the same floating point type */ |
| 2289 | 2289 | /* XXX: need to use ST1 too */ |
| 2290 | −void gen_opf(int op) | |
| 2290 | +void gen_opf(TCCState* S, int op) | |
| 2291 | 2291 | { |
| 2292 | 2292 | int ft, fc, fr, r; |
| 2293 | 2293 | |
| 2294 | 2294 | if (op >= TOK_ULT && op <= TOK_GT) |
| 2295 | − gv2(RC_EDX, RC_EAX); // make sure src2 is on b side | |
| 2295 | + gv2(S, RC_EDX, RC_EAX); // make sure src2 is on b side | |
| 2296 | 2296 | else |
| 2297 | − gv2(RC_FLOAT, RC_FLOAT); // make sure src2 is on b side | |
| 2297 | + gv2(S, RC_FLOAT, RC_FLOAT); // make sure src2 is on b side | |
| 2298 | 2298 | |
| 2299 | − ft = vtop->type.t; | |
| 2300 | − fc = vtop->c.i; | |
| 2301 | − r = vtop->r; | |
| 2302 | − fr = vtop[-1].r; | |
| 2299 | + ft = S->tccgen_vtop->type.t; | |
| 2300 | + fc = S->tccgen_vtop->c.i; | |
| 2301 | + r = S->tccgen_vtop->r; | |
| 2302 | + fr = S->tccgen_vtop[-1].r; | |
| 2303 | 2303 | |
| 2304 | 2304 | |
| 2305 | 2305 | if ((ft & VT_BTYPE) == VT_LDOUBLE) |
| 2306 | − tcc_error("long doubles not supported"); | |
| 2306 | + tcc_error(S, "long doubles not supported"); | |
| 2307 | 2307 | |
| 2308 | 2308 | if (op >= TOK_ULT && op <= TOK_GT) { |
| 2309 | 2309 | |
| 2310 | − r = vtop[-1].r; | |
| 2311 | − fr = vtop[0].r; | |
| 2310 | + r = S->tccgen_vtop[-1].r; | |
| 2311 | + fr = S->tccgen_vtop[0].r; | |
| 2312 | 2312 | |
| 2313 | 2313 | C67_compare_reg = C67_B2; |
| 2314 | 2314 | |
| 2315 | 2315 | if (op == TOK_LT) { |
| 2316 | 2316 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 2317 | − C67_CMPLTDP(r, fr, C67_B2); | |
| 2317 | + C67_CMPLTDP(S, r, fr, C67_B2); | |
| 2318 | 2318 | else |
| 2319 | − C67_CMPLTSP(r, fr, C67_B2); | |
| 2319 | + C67_CMPLTSP(S, r, fr, C67_B2); | |
| 2320 | 2320 | |
| 2321 | 2321 | C67_invert_test = FALSE; |
| 2322 | 2322 | } else if (op == TOK_GE) { |
| 2323 | 2323 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 2324 | − C67_CMPLTDP(r, fr, C67_B2); | |
| 2324 | + C67_CMPLTDP(S, r, fr, C67_B2); | |
| 2325 | 2325 | else |
| 2326 | − C67_CMPLTSP(r, fr, C67_B2); | |
| 2326 | + C67_CMPLTSP(S, r, fr, C67_B2); | |
| 2327 | 2327 | |
| 2328 | 2328 | C67_invert_test = TRUE; |
| 2329 | 2329 | } else if (op == TOK_GT) { |
| 2330 | 2330 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 2331 | − C67_CMPGTDP(r, fr, C67_B2); | |
| 2331 | + C67_CMPGTDP(S, r, fr, C67_B2); | |
| 2332 | 2332 | else |
| 2333 | − C67_CMPGTSP(r, fr, C67_B2); | |
| 2333 | + C67_CMPGTSP(S, r, fr, C67_B2); | |
| 2334 | 2334 | |
| 2335 | 2335 | C67_invert_test = FALSE; |
| 2336 | 2336 | } else if (op == TOK_LE) { |
| 2337 | 2337 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 2338 | − C67_CMPGTDP(r, fr, C67_B2); | |
| 2338 | + C67_CMPGTDP(S, r, fr, C67_B2); | |
| 2339 | 2339 | else |
| 2340 | − C67_CMPGTSP(r, fr, C67_B2); | |
| 2340 | + C67_CMPGTSP(S, r, fr, C67_B2); | |
| 2341 | 2341 | |
| 2342 | 2342 | C67_invert_test = TRUE; |
| 2343 | 2343 | } else if (op == TOK_EQ) { |
| 2344 | 2344 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 2345 | − C67_CMPEQDP(r, fr, C67_B2); | |
| 2345 | + C67_CMPEQDP(S, r, fr, C67_B2); | |
| 2346 | 2346 | else |
| 2347 | − C67_CMPEQSP(r, fr, C67_B2); | |
| 2347 | + C67_CMPEQSP(S, r, fr, C67_B2); | |
| 2348 | 2348 | |
| 2349 | 2349 | C67_invert_test = FALSE; |
| 2350 | 2350 | } else if (op == TOK_NE) { |
| 2351 | 2351 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 2352 | − C67_CMPEQDP(r, fr, C67_B2); | |
| 2352 | + C67_CMPEQDP(S, r, fr, C67_B2); | |
| 2353 | 2353 | else |
| 2354 | − C67_CMPEQSP(r, fr, C67_B2); | |
| 2354 | + C67_CMPEQSP(S, r, fr, C67_B2); | |
| 2355 | 2355 | |
| 2356 | 2356 | C67_invert_test = TRUE; |
| 2357 | 2357 | } else { |
| 2358 | 2358 | ALWAYS_ASSERT(FALSE); |
| 2359 | 2359 | } |
| 2360 | − vset_VT_CMP(0x80); | |
| 2360 | + vset_VT_CMP(S, 0x80); | |
| 2361 | 2361 | } else { |
| 2362 | 2362 | if (op == '+') { |
| 2363 | 2363 | if ((ft & VT_BTYPE) == VT_DOUBLE) { |
| 2364 | − C67_ADDDP(r, fr); // ADD fr,r,fr | |
| 2365 | − C67_NOP(6); | |
| 2364 | + C67_ADDDP(S, r, fr); // ADD fr,r,fr | |
| 2365 | + C67_NOP(S, 6); | |
| 2366 | 2366 | } else { |
| 2367 | − C67_ADDSP(r, fr); // ADD fr,r,fr | |
| 2368 | − C67_NOP(3); | |
| 2367 | + C67_ADDSP(S, r, fr); // ADD fr,r,fr | |
| 2368 | + C67_NOP(S, 3); | |
| 2369 | 2369 | } |
| 2370 | − vtop--; | |
| 2370 | + S->tccgen_vtop--; | |
| 2371 | 2371 | } else if (op == '-') { |
| 2372 | 2372 | if ((ft & VT_BTYPE) == VT_DOUBLE) { |
| 2373 | − C67_SUBDP(r, fr); // SUB fr,r,fr | |
| 2374 | − C67_NOP(6); | |
| 2373 | + C67_SUBDP(S, r, fr); // SUB fr,r,fr | |
| 2374 | + C67_NOP(S, 6); | |
| 2375 | 2375 | } else { |
| 2376 | − C67_SUBSP(r, fr); // SUB fr,r,fr | |
| 2377 | − C67_NOP(3); | |
| 2376 | + C67_SUBSP(S, r, fr); // SUB fr,r,fr | |
| 2377 | + C67_NOP(S, 3); | |
| 2378 | 2378 | } |
| 2379 | − vtop--; | |
| 2379 | + S->tccgen_vtop--; | |
| 2380 | 2380 | } else if (op == '*') { |
| 2381 | 2381 | if ((ft & VT_BTYPE) == VT_DOUBLE) { |
| 2382 | − C67_MPYDP(r, fr); // MPY fr,r,fr | |
| 2383 | − C67_NOP(9); | |
| 2382 | + C67_MPYDP(S, r, fr); // MPY fr,r,fr | |
| 2383 | + C67_NOP(S, 9); | |
| 2384 | 2384 | } else { |
| 2385 | − C67_MPYSP(r, fr); // MPY fr,r,fr | |
| 2386 | − C67_NOP(3); | |
| 2385 | + C67_MPYSP(S, r, fr); // MPY fr,r,fr | |
| 2386 | + C67_NOP(S, 3); | |
| 2387 | 2387 | } |
| 2388 | − vtop--; | |
| 2388 | + S->tccgen_vtop--; | |
| 2389 | 2389 | } else if (op == '/') { |
| 2390 | 2390 | if ((ft & VT_BTYPE) == VT_DOUBLE) { |
| 2391 | 2391 | // must call intrinsic DP floating point divide |
| 2392 | − vswap(); | |
| 2392 | + vswap(S); | |
| 2393 | 2393 | /* call generic idiv function */ |
| 2394 | − vpush_helper_func(TOK__divd); | |
| 2395 | − vrott(3); | |
| 2396 | − gfunc_call(2); | |
| 2397 | − vpushi(0); | |
| 2398 | − vtop->r = REG_FRET; | |
| 2399 | − vtop->r2 = REG_IRE2; | |
| 2394 | + vpush_helper_func(S, TOK__divd); | |
| 2395 | + vrott(S, 3); | |
| 2396 | + gfunc_call(S, 2); | |
| 2397 | + vpushi(S, 0); | |
| 2398 | + S->tccgen_vtop->r = REG_FRET; | |
| 2399 | + S->tccgen_vtop->r2 = REG_IRE2; | |
| 2400 | 2400 | |
| 2401 | 2401 | } else { |
| 2402 | 2402 | // must call intrinsic SP floating point divide |
| 2403 | − vswap(); | |
| 2403 | + vswap(S); | |
| 2404 | 2404 | /* call generic idiv function */ |
| 2405 | − vpush_helper_func(TOK__divf); | |
| 2406 | − vrott(3); | |
| 2407 | − gfunc_call(2); | |
| 2408 | − vpushi(0); | |
| 2409 | − vtop->r = REG_FRET; | |
| 2410 | − vtop->r2 = VT_CONST; | |
| 2405 | + vpush_helper_func(S, TOK__divf); | |
| 2406 | + vrott(S, 3); | |
| 2407 | + gfunc_call(S, 2); | |
| 2408 | + vpushi(S, 0); | |
| 2409 | + S->tccgen_vtop->r = REG_FRET; | |
| 2410 | + S->tccgen_vtop->r2 = VT_CONST; | |
| 2411 | 2411 | } |
| 2412 | 2412 | } else |
| 2413 | 2413 | ALWAYS_ASSERT(FALSE); |
| @@ -2419,122 +2419,122 @@ void gen_opf(int op) · 5 unmodified lines | ||
| 2419 | 2419 | |
| 2420 | 2420 | /* convert integers to fp 't' type. Must handle 'int', 'unsigned int' |
| 2421 | 2421 | and 'long long' cases. */ |
| 2422 | −void gen_cvt_itof(int t) | |
| 2422 | +void gen_cvt_itof(TCCState* S, int t) | |
| 2423 | 2423 | { |
| 2424 | 2424 | int r; |
| 2425 | 2425 | |
| 2426 | − gv(RC_INT); | |
| 2427 | − r = vtop->r; | |
| 2426 | + gv(S, RC_INT); | |
| 2427 | + r = S->tccgen_vtop->r; | |
| 2428 | 2428 | |
| 2429 | 2429 | if ((t & VT_BTYPE) == VT_DOUBLE) { |
| 2430 | 2430 | if (t & VT_UNSIGNED) |
| 2431 | − C67_INTDPU(r, r); | |
| 2431 | + C67_INTDPU(S, r, r); | |
| 2432 | 2432 | else |
| 2433 | − C67_INTDP(r, r); | |
| 2433 | + C67_INTDP(S, r, r); | |
| 2434 | 2434 | |
| 2435 | − C67_NOP(4); | |
| 2436 | − vtop->type.t = VT_DOUBLE; | |
| 2435 | + C67_NOP(S, 4); | |
| 2436 | + S->tccgen_vtop->type.t = VT_DOUBLE; | |
| 2437 | 2437 | } else { |
| 2438 | 2438 | if (t & VT_UNSIGNED) |
| 2439 | − C67_INTSPU(r, r); | |
| 2439 | + C67_INTSPU(S, r, r); | |
| 2440 | 2440 | else |
| 2441 | − C67_INTSP(r, r); | |
| 2442 | − C67_NOP(3); | |
| 2443 | − vtop->type.t = VT_FLOAT; | |
| 2441 | + C67_INTSP(S, r, r); | |
| 2442 | + C67_NOP(S, 3); | |
| 2443 | + S->tccgen_vtop->type.t = VT_FLOAT; | |
| 2444 | 2444 | } |
| 2445 | 2445 | |
| 2446 | 2446 | } |
| 2447 | 2447 | |
| 2448 | 2448 | /* convert fp to int 't' type */ |
| 2449 | 2449 | /* XXX: handle long long case */ |
| 2450 | −void gen_cvt_ftoi(int t) | |
| 2450 | +void gen_cvt_ftoi(TCCState* S, int t) | |
| 2451 | 2451 | { |
| 2452 | 2452 | int r; |
| 2453 | 2453 | |
| 2454 | − gv(RC_FLOAT); | |
| 2455 | − r = vtop->r; | |
| 2454 | + gv(S, RC_FLOAT); | |
| 2455 | + r = S->tccgen_vtop->r; | |
| 2456 | 2456 | |
| 2457 | 2457 | if (t != VT_INT) |
| 2458 | − tcc_error("long long not supported"); | |
| 2458 | + tcc_error(S, "long long not supported"); | |
| 2459 | 2459 | else { |
| 2460 | − if ((vtop->type.t & VT_BTYPE) == VT_DOUBLE) { | |
| 2461 | − C67_DPTRUNC(r, r); | |
| 2462 | − C67_NOP(3); | |
| 2460 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_DOUBLE) { | |
| 2461 | + C67_DPTRUNC(S, r, r); | |
| 2462 | + C67_NOP(S, 3); | |
| 2463 | 2463 | } else { |
| 2464 | − C67_SPTRUNC(r, r); | |
| 2465 | − C67_NOP(3); | |
| 2464 | + C67_SPTRUNC(S, r, r); | |
| 2465 | + C67_NOP(S, 3); | |
| 2466 | 2466 | } |
| 2467 | 2467 | |
| 2468 | − vtop->type.t = VT_INT; | |
| 2468 | + S->tccgen_vtop->type.t = VT_INT; | |
| 2469 | 2469 | |
| 2470 | 2470 | } |
| 2471 | 2471 | } |
| 2472 | 2472 | |
| 2473 | 2473 | /* convert from one floating point type to another */ |
| 2474 | −void gen_cvt_ftof(int t) | |
| 2474 | +void gen_cvt_ftof(TCCState* S, int t) | |
| 2475 | 2475 | { |
| 2476 | 2476 | int r, r2; |
| 2477 | 2477 | |
| 2478 | − if ((vtop->type.t & VT_BTYPE) == VT_DOUBLE && | |
| 2478 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_DOUBLE && | |
| 2479 | 2479 | (t & VT_BTYPE) == VT_FLOAT) { |
| 2480 | 2480 | // convert double to float |
| 2481 | 2481 | |
| 2482 | − gv(RC_FLOAT); // get it in a register pair | |
| 2482 | + gv(S, RC_FLOAT); // get it in a register pair | |
| 2483 | 2483 | |
| 2484 | − r = vtop->r; | |
| 2484 | + r = S->tccgen_vtop->r; | |
| 2485 | 2485 | |
| 2486 | − C67_DPSP(r, r); // convert it to SP same register | |
| 2487 | − C67_NOP(3); | |
| 2486 | + C67_DPSP(S, r, r); // convert it to SP same register | |
| 2487 | + C67_NOP(S, 3); | |
| 2488 | 2488 | |
| 2489 | − vtop->type.t = VT_FLOAT; | |
| 2490 | − vtop->r2 = VT_CONST; // set this as unused | |
| 2491 | − } else if ((vtop->type.t & VT_BTYPE) == VT_FLOAT && | |
| 2489 | + S->tccgen_vtop->type.t = VT_FLOAT; | |
| 2490 | + S->tccgen_vtop->r2 = VT_CONST; // set this as unused | |
| 2491 | + } else if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_FLOAT && | |
| 2492 | 2492 | (t & VT_BTYPE) == VT_DOUBLE) { |
| 2493 | 2493 | // convert float to double |
| 2494 | 2494 | |
| 2495 | − gv(RC_FLOAT); // get it in a register | |
| 2495 | + gv(S, RC_FLOAT); // get it in a register | |
| 2496 | 2496 | |
| 2497 | − r = vtop->r; | |
| 2497 | + r = S->tccgen_vtop->r; | |
| 2498 | 2498 | |
| 2499 | 2499 | if (r == TREG_EAX) { // make sure the paired reg is avail |
| 2500 | − r2 = get_reg(RC_ECX); | |
| 2500 | + r2 = get_reg(S, RC_ECX); | |
| 2501 | 2501 | } else if (r == TREG_EDX) { |
| 2502 | − r2 = get_reg(RC_ST0); | |
| 2502 | + r2 = get_reg(S, RC_ST0); | |
| 2503 | 2503 | } else { |
| 2504 | 2504 | ALWAYS_ASSERT(FALSE); |
| 2505 | 2505 | r2 = 0; /* avoid warning */ |
| 2506 | 2506 | } |
| 2507 | 2507 | |
| 2508 | − C67_SPDP(r, r); // convert it to DP same register | |
| 2509 | − C67_NOP(1); | |
| 2508 | + C67_SPDP(S, r, r); // convert it to DP same register | |
| 2509 | + C67_NOP(S, 1); | |
| 2510 | 2510 | |
| 2511 | − vtop->type.t = VT_DOUBLE; | |
| 2512 | − vtop->r2 = r2; // set this as unused | |
| 2511 | + S->tccgen_vtop->type.t = VT_DOUBLE; | |
| 2512 | + S->tccgen_vtop->r2 = r2; // set this as unused | |
| 2513 | 2513 | } else { |
| 2514 | 2514 | ALWAYS_ASSERT(FALSE); |
| 2515 | 2515 | } |
| 2516 | 2516 | } |
| 2517 | 2517 | |
| 2518 | 2518 | /* computed goto support */ |
| 2519 | −void ggoto(void) | |
| 2519 | +void ggoto(TCCState* S) | |
| 2520 | 2520 | { |
| 2521 | − gcall_or_jmp(1); | |
| 2522 | − vtop--; | |
| 2521 | + gcall_or_jmp(S, 1); | |
| 2522 | + S->tccgen_vtop--; | |
| 2523 | 2523 | } |
| 2524 | 2524 | |
| 2525 | 2525 | /* Save the stack pointer onto the stack and return the location of its address */ |
| 2526 | −ST_FUNC void gen_vla_sp_save(int addr) { | |
| 2527 | − tcc_error("variable length arrays unsupported for this target"); | |
| 2526 | +ST_FUNC void gen_vla_sp_save(TCCState* S, int addr) { | |
| 2527 | + tcc_error(S, "variable length arrays unsupported for this target"); | |
| 2528 | 2528 | } |
| 2529 | 2529 | |
| 2530 | 2530 | /* Restore the SP from a location on the stack */ |
| 2531 | −ST_FUNC void gen_vla_sp_restore(int addr) { | |
| 2532 | − tcc_error("variable length arrays unsupported for this target"); | |
| 2531 | +ST_FUNC void gen_vla_sp_restore(TCCState* S, int addr) { | |
| 2532 | + tcc_error(S, "variable length arrays unsupported for this target"); | |
| 2533 | 2533 | } |
| 2534 | 2534 | |
| 2535 | 2535 | /* Subtract from the stack pointer, and push the resulting value onto the stack */ |
| 2536 | −ST_FUNC void gen_vla_alloc(CType *type, int align) { | |
| 2537 | − tcc_error("variable length arrays unsupported for this target"); | |
| 2536 | +ST_FUNC void gen_vla_alloc(TCCState* S, CType *type, int align) { | |
| 2537 | + tcc_error(S, "variable length arrays unsupported for this target"); | |
| 2538 | 2538 | } |
| 2539 | 2539 | |
| 2540 | 2540 | /* end of C67 code generator */ |
| @@ -65,23 +65,23 @@ int gotplt_entry_type (int reloc_type) · 64 unmodified lines | ||
| 65 | 65 | return -1; |
| 66 | 66 | } |
| 67 | 67 | |
| 68 | −ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_attr *attr) | |
| 68 | +ST_FUNC unsigned create_plt_entry(TCCState *S, unsigned got_offset, struct sym_attr *attr) | |
| 69 | 69 | { |
| 70 | − tcc_error("C67 got not implemented"); | |
| 70 | + tcc_error(S, "C67 got not implemented"); | |
| 71 | 71 | return 0; |
| 72 | 72 | } |
| 73 | 73 | |
| 74 | 74 | /* relocate the PLT: compute addresses and offsets in the PLT now that final |
| 75 | 75 | address for PLT and GOT are known (see fill_program_header) */ |
| 76 | −ST_FUNC void relocate_plt(TCCState *s1) | |
| 76 | +ST_FUNC void relocate_plt(TCCState *S) | |
| 77 | 77 | { |
| 78 | 78 | uint8_t *p, *p_end; |
| 79 | 79 | |
| 80 | − if (!s1->plt) | |
| 80 | + if (!S->plt) | |
| 81 | 81 | return; |
| 82 | 82 | |
| 83 | − p = s1->plt->data; | |
| 84 | − p_end = p + s1->plt->data_offset; | |
| 83 | + p = S->plt->data; | |
| 84 | + p_end = p + S->plt->data_offset; | |
| 85 | 85 | |
| 86 | 86 | if (p < p_end) { |
| 87 | 87 | /* XXX: TODO */ |
| @@ -91,7 +91,7 @@ ST_FUNC void relocate_plt(TCCState *s1) · 3 unmodified lines | ||
| 91 | 91 | } |
| 92 | 92 | } |
| 93 | 93 | |
| 94 | −void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 94 | +void relocate(TCCState *S, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 95 | 95 | { |
| 96 | 96 | switch(type) { |
| 97 | 97 | case R_C60_32: |
| @@ -253,10 +253,10 @@ static const uint16_t op0_codes[] = { · 252 unmodified lines | ||
| 253 | 253 | #endif |
| 254 | 254 | }; |
| 255 | 255 | |
| 256 | −static inline int get_reg_shift(TCCState *s1) | |
| 256 | +static inline int get_reg_shift(TCCState *S) | |
| 257 | 257 | { |
| 258 | 258 | int shift, v; |
| 259 | − v = asm_int_expr(s1); | |
| 259 | + v = asm_int_expr(S); | |
| 260 | 260 | switch(v) { |
| 261 | 261 | case 1: |
| 262 | 262 | shift = 0; |
| @@ -271,7 +271,7 @@ static inline int get_reg_shift(TCCState *s1) · 8 unmodified lines | ||
| 271 | 271 | shift = 3; |
| 272 | 272 | break; |
| 273 | 273 | default: |
| 274 | − expect("1, 2, 4 or 8 constant"); | |
| 274 | + expect(S, "1, 2, 4 or 8 constant"); | |
| 275 | 275 | shift = 0; |
| 276 | 276 | break; |
| 277 | 277 | } |
| @@ -279,11 +279,11 @@ static inline int get_reg_shift(TCCState *s1) · 1 unmodified line | ||
| 279 | 279 | } |
| 280 | 280 | |
| 281 | 281 | #ifdef TCC_TARGET_X86_64 |
| 282 | −static int asm_parse_numeric_reg(int t, unsigned int *type) | |
| 282 | +static int asm_parse_numeric_reg(TCCState *S, int t, unsigned int *type) | |
| 283 | 283 | { |
| 284 | 284 | int reg = -1; |
| 285 | − if (t >= TOK_IDENT && t < tok_ident) { | |
| 286 | − const char *s = table_ident[t - TOK_IDENT]->str; | |
| 285 | + if (t >= TOK_IDENT && t < S->tccpp_tok_ident) { | |
| 286 | + const char *s = S->tccpp_table_ident[t - TOK_IDENT]->str; | |
| 287 | 287 | char c; |
| 288 | 288 | *type = OP_REG64; |
| 289 | 289 | if (*s == 'c') { |
| @@ -318,51 +318,51 @@ static int asm_parse_numeric_reg(int t, unsigned int *type) · 28 unmodified lines | ||
| 318 | 318 | } |
| 319 | 319 | #endif |
| 320 | 320 | |
| 321 | −static int asm_parse_reg(unsigned int *type) | |
| 321 | +static int asm_parse_reg(TCCState* S, unsigned int *type) | |
| 322 | 322 | { |
| 323 | 323 | int reg = 0; |
| 324 | 324 | *type = 0; |
| 325 | − if (tok != '%') | |
| 325 | + if (S->tccpp_tok != '%') | |
| 326 | 326 | goto error_32; |
| 327 | − next(); | |
| 328 | − if (tok >= TOK_ASM_eax && tok <= TOK_ASM_edi) { | |
| 329 | − reg = tok - TOK_ASM_eax; | |
| 327 | + next(S); | |
| 328 | + if (S->tccpp_tok >= TOK_ASM_eax && S->tccpp_tok <= TOK_ASM_edi) { | |
| 329 | + reg = S->tccpp_tok - TOK_ASM_eax; | |
| 330 | 330 | *type = OP_REG32; |
| 331 | 331 | #ifdef TCC_TARGET_X86_64 |
| 332 | − } else if (tok >= TOK_ASM_rax && tok <= TOK_ASM_rdi) { | |
| 333 | − reg = tok - TOK_ASM_rax; | |
| 332 | + } else if (S->tccpp_tok >= TOK_ASM_rax && S->tccpp_tok <= TOK_ASM_rdi) { | |
| 333 | + reg = S->tccpp_tok - TOK_ASM_rax; | |
| 334 | 334 | *type = OP_REG64; |
| 335 | − } else if (tok == TOK_ASM_rip) { | |
| 335 | + } else if (S->tccpp_tok == TOK_ASM_rip) { | |
| 336 | 336 | reg = -2; /* Probably should use different escape code. */ |
| 337 | 337 | *type = OP_REG64; |
| 338 | − } else if ((reg = asm_parse_numeric_reg(tok, type)) >= 0 | |
| 338 | + } else if ((reg = asm_parse_numeric_reg(S, S->tccpp_tok, type)) >= 0 | |
| 339 | 339 | && (*type == OP_REG32 || *type == OP_REG64)) { |
| 340 | 340 | ; |
| 341 | 341 | #endif |
| 342 | 342 | } else { |
| 343 | 343 | error_32: |
| 344 | − expect("register"); | |
| 344 | + expect(S, "register"); | |
| 345 | 345 | } |
| 346 | − next(); | |
| 346 | + next(S); | |
| 347 | 347 | return reg; |
| 348 | 348 | } |
| 349 | 349 | |
| 350 | −static void parse_operand(TCCState *s1, Operand *op) | |
| 350 | +static void parse_operand(TCCState *S, Operand *op) | |
| 351 | 351 | { |
| 352 | 352 | ExprValue e; |
| 353 | 353 | int reg, indir; |
| 354 | 354 | const char *p; |
| 355 | 355 | |
| 356 | 356 | indir = 0; |
| 357 | − if (tok == '*') { | |
| 358 | − next(); | |
| 357 | + if (S->tccpp_tok == '*') { | |
| 358 | + next(S); | |
| 359 | 359 | indir = OP_INDIR; |
| 360 | 360 | } |
| 361 | 361 | |
| 362 | − if (tok == '%') { | |
| 363 | − next(); | |
| 364 | − if (tok >= TOK_ASM_al && tok <= TOK_ASM_db7) { | |
| 365 | − reg = tok - TOK_ASM_al; | |
| 362 | + if (S->tccpp_tok == '%') { | |
| 363 | + next(S); | |
| 364 | + if (S->tccpp_tok >= TOK_ASM_al && S->tccpp_tok <= TOK_ASM_db7) { | |
| 365 | + reg = S->tccpp_tok - TOK_ASM_al; | |
| 366 | 366 | op->type = 1 << (reg >> 3); /* WARNING: do not change constant order */ |
| 367 | 367 | op->reg = reg & 7; |
| 368 | 368 | if ((op->type & OP_REG) && op->reg == TREG_XAX) |
| @@ -371,48 +371,48 @@ static void parse_operand(TCCState *s1, Operand *op) · 2 unmodified lines | ||
| 371 | 371 | op->type |= OP_CL; |
| 372 | 372 | else if (op->type == OP_REG16 && op->reg == TREG_XDX) |
| 373 | 373 | op->type |= OP_DX; |
| 374 | − } else if (tok >= TOK_ASM_dr0 && tok <= TOK_ASM_dr7) { | |
| 374 | + } else if (S->tccpp_tok >= TOK_ASM_dr0 && S->tccpp_tok <= TOK_ASM_dr7) { | |
| 375 | 375 | op->type = OP_DB; |
| 376 | − op->reg = tok - TOK_ASM_dr0; | |
| 377 | − } else if (tok >= TOK_ASM_es && tok <= TOK_ASM_gs) { | |
| 376 | + op->reg = S->tccpp_tok - TOK_ASM_dr0; | |
| 377 | + } else if (S->tccpp_tok >= TOK_ASM_es && S->tccpp_tok <= TOK_ASM_gs) { | |
| 378 | 378 | op->type = OP_SEG; |
| 379 | − op->reg = tok - TOK_ASM_es; | |
| 380 | − } else if (tok == TOK_ASM_st) { | |
| 379 | + op->reg = S->tccpp_tok - TOK_ASM_es; | |
| 380 | + } else if (S->tccpp_tok == TOK_ASM_st) { | |
| 381 | 381 | op->type = OP_ST; |
| 382 | 382 | op->reg = 0; |
| 383 | − next(); | |
| 384 | − if (tok == '(') { | |
| 385 | − next(); | |
| 386 | − if (tok != TOK_PPNUM) | |
| 383 | + next(S); | |
| 384 | + if (S->tccpp_tok == '(') { | |
| 385 | + next(S); | |
| 386 | + if (S->tccpp_tok != TOK_PPNUM) | |
| 387 | 387 | goto reg_error; |
| 388 | − p = tokc.str.data; | |
| 388 | + p = S->tccpp_tokc.str.data; | |
| 389 | 389 | reg = p[0] - '0'; |
| 390 | 390 | if ((unsigned)reg >= 8 || p[1] != '\0') |
| 391 | 391 | goto reg_error; |
| 392 | 392 | op->reg = reg; |
| 393 | − next(); | |
| 394 | − skip(')'); | |
| 393 | + next(S); | |
| 394 | + skip(S, ')'); | |
| 395 | 395 | } |
| 396 | 396 | if (op->reg == 0) |
| 397 | 397 | op->type |= OP_ST0; |
| 398 | 398 | goto no_skip; |
| 399 | 399 | #ifdef TCC_TARGET_X86_64 |
| 400 | − } else if (tok >= TOK_ASM_spl && tok <= TOK_ASM_dil) { | |
| 400 | + } else if (S->tccpp_tok >= TOK_ASM_spl && S->tccpp_tok <= TOK_ASM_dil) { | |
| 401 | 401 | op->type = OP_REG8 | OP_REG8_LOW; |
| 402 | − op->reg = 4 + tok - TOK_ASM_spl; | |
| 403 | − } else if ((op->reg = asm_parse_numeric_reg(tok, &op->type)) >= 0) { | |
| 402 | + op->reg = 4 + S->tccpp_tok - TOK_ASM_spl; | |
| 403 | + } else if ((op->reg = asm_parse_numeric_reg(S, S->tccpp_tok, &op->type)) >= 0) { | |
| 404 | 404 | ; |
| 405 | 405 | #endif |
| 406 | 406 | } else { |
| 407 | 407 | reg_error: |
| 408 | − tcc_error("unknown register %%%s", get_tok_str(tok, &tokc)); | |
| 408 | + tcc_error(S, "unknown register %%%s", get_tok_str(S, S->tccpp_tok, &S->tccpp_tokc)); | |
| 409 | 409 | } |
| 410 | − next(); | |
| 410 | + next(S); | |
| 411 | 411 | no_skip: ; |
| 412 | − } else if (tok == '$') { | |
| 412 | + } else if (S->tccpp_tok == '$') { | |
| 413 | 413 | /* constant value */ |
| 414 | − next(); | |
| 415 | − asm_expr(s1, &e); | |
| 414 | + next(S); | |
| 415 | + asm_expr(S, &e); | |
| 416 | 416 | op->type = OP_IM32; |
| 417 | 417 | op->e = e; |
| 418 | 418 | if (!op->e.sym) { |
| @@ -433,45 +433,45 @@ static void parse_operand(TCCState *s1, Operand *op) · 14 unmodified lines | ||
| 433 | 433 | op->reg = -1; |
| 434 | 434 | op->reg2 = -1; |
| 435 | 435 | op->shift = 0; |
| 436 | − if (tok != '(') { | |
| 437 | − asm_expr(s1, &e); | |
| 436 | + if (S->tccpp_tok != '(') { | |
| 437 | + asm_expr(S, &e); | |
| 438 | 438 | op->e = e; |
| 439 | 439 | } else { |
| 440 | − next(); | |
| 441 | − if (tok == '%') { | |
| 442 | − unget_tok('('); | |
| 440 | + next(S); | |
| 441 | + if (S->tccpp_tok == '%') { | |
| 442 | + unget_tok(S, '('); | |
| 443 | 443 | op->e.v = 0; |
| 444 | 444 | op->e.sym = NULL; |
| 445 | 445 | } else { |
| 446 | 446 | /* bracketed offset expression */ |
| 447 | − asm_expr(s1, &e); | |
| 448 | − if (tok != ')') | |
| 449 | − expect(")"); | |
| 450 | − next(); | |
| 447 | + asm_expr(S, &e); | |
| 448 | + if (S->tccpp_tok != ')') | |
| 449 | + expect(S, ")"); | |
| 450 | + next(S); | |
| 451 | 451 | op->e.v = e.v; |
| 452 | 452 | op->e.sym = e.sym; |
| 453 | 453 | } |
| 454 | 454 | op->e.pcrel = 0; |
| 455 | 455 | } |
| 456 | − if (tok == '(') { | |
| 456 | + if (S->tccpp_tok == '(') { | |
| 457 | 457 | unsigned int type = 0; |
| 458 | − next(); | |
| 459 | − if (tok != ',') { | |
| 460 | − op->reg = asm_parse_reg(&type); | |
| 458 | + next(S); | |
| 459 | + if (S->tccpp_tok != ',') { | |
| 460 | + op->reg = asm_parse_reg(S, &type); | |
| 461 | 461 | } |
| 462 | − if (tok == ',') { | |
| 463 | − next(); | |
| 464 | − if (tok != ',') { | |
| 465 | − op->reg2 = asm_parse_reg(&type); | |
| 462 | + if (S->tccpp_tok == ',') { | |
| 463 | + next(S); | |
| 464 | + if (S->tccpp_tok != ',') { | |
| 465 | + op->reg2 = asm_parse_reg(S, &type); | |
| 466 | 466 | } |
| 467 | − if (tok == ',') { | |
| 468 | − next(); | |
| 469 | − op->shift = get_reg_shift(s1); | |
| 467 | + if (S->tccpp_tok == ',') { | |
| 468 | + next(S); | |
| 469 | + op->shift = get_reg_shift(S); | |
| 470 | 470 | } |
| 471 | 471 | } |
| 472 | 472 | if (type & OP_REG32) |
| 473 | 473 | op->type |= OP_EA32; |
| 474 | − skip(')'); | |
| 474 | + skip(S, ')'); | |
| 475 | 475 | } |
| 476 | 476 | if (op->reg == -1 && op->reg2 == -1) |
| 477 | 477 | op->type |= OP_ADDR; |
| @@ -480,65 +480,65 @@ static void parse_operand(TCCState *s1, Operand *op) · 2 unmodified lines | ||
| 480 | 480 | } |
| 481 | 481 | |
| 482 | 482 | /* XXX: unify with C code output ? */ |
| 483 | −ST_FUNC void gen_expr32(ExprValue *pe) | |
| 483 | +ST_FUNC void gen_expr32(TCCState* S, ExprValue *pe) | |
| 484 | 484 | { |
| 485 | 485 | if (pe->pcrel) |
| 486 | 486 | /* If PC-relative, always set VT_SYM, even without symbol, |
| 487 | 487 | so as to force a relocation to be emitted. */ |
| 488 | − gen_addrpc32(VT_SYM, pe->sym, pe->v); | |
| 488 | + gen_addrpc32(S, VT_SYM, pe->sym, pe->v); | |
| 489 | 489 | else |
| 490 | − gen_addr32(pe->sym ? VT_SYM : 0, pe->sym, pe->v); | |
| 490 | + gen_addr32(S, pe->sym ? VT_SYM : 0, pe->sym, pe->v); | |
| 491 | 491 | } |
| 492 | 492 | |
| 493 | 493 | #ifdef TCC_TARGET_X86_64 |
| 494 | −ST_FUNC void gen_expr64(ExprValue *pe) | |
| 494 | +ST_FUNC void gen_expr64(TCCState* S, ExprValue *pe) | |
| 495 | 495 | { |
| 496 | − gen_addr64(pe->sym ? VT_SYM : 0, pe->sym, pe->v); | |
| 496 | + gen_addr64(S, pe->sym ? VT_SYM : 0, pe->sym, pe->v); | |
| 497 | 497 | } |
| 498 | 498 | #endif |
| 499 | 499 | |
| 500 | 500 | /* XXX: unify with C code output ? */ |
| 501 | −static void gen_disp32(ExprValue *pe) | |
| 501 | +static void gen_disp32(TCCState* S, ExprValue *pe) | |
| 502 | 502 | { |
| 503 | 503 | Sym *sym = pe->sym; |
| 504 | − ElfSym *esym = elfsym(sym); | |
| 504 | + ElfSym *esym = elfsym(S, sym); | |
| 505 | 505 | if (esym && esym->st_shndx == cur_text_section->sh_num) { |
| 506 | 506 | /* same section: we can output an absolute value. Note |
| 507 | 507 | that the TCC compiler behaves differently here because |
| 508 | 508 | it always outputs a relocation to ease (future) code |
| 509 | 509 | elimination in the linker */ |
| 510 | − gen_le32(pe->v + esym->st_value - ind - 4); | |
| 510 | + gen_le32(S, pe->v + esym->st_value - S->tccgen_ind - 4); | |
| 511 | 511 | } else { |
| 512 | 512 | if (sym && sym->type.t == VT_VOID) { |
| 513 | 513 | sym->type.t = VT_FUNC; |
| 514 | 514 | sym->type.ref = NULL; |
| 515 | 515 | } |
| 516 | − gen_addrpc32(VT_SYM, sym, pe->v); | |
| 516 | + gen_addrpc32(S, VT_SYM, sym, pe->v); | |
| 517 | 517 | } |
| 518 | 518 | } |
| 519 | 519 | |
| 520 | 520 | /* generate the modrm operand */ |
| 521 | −static inline int asm_modrm(int reg, Operand *op) | |
| 521 | +static inline int asm_modrm(TCCState* S, int reg, Operand *op) | |
| 522 | 522 | { |
| 523 | 523 | int mod, reg1, reg2, sib_reg1; |
| 524 | 524 | |
| 525 | 525 | if (op->type & (OP_REG | OP_MMX | OP_SSE)) { |
| 526 | − g(0xc0 + (reg << 3) + op->reg); | |
| 526 | + g(S, 0xc0 + (reg << 3) + op->reg); | |
| 527 | 527 | } else if (op->reg == -1 && op->reg2 == -1) { |
| 528 | 528 | /* displacement only */ |
| 529 | 529 | #ifdef TCC_TARGET_X86_64 |
| 530 | − g(0x04 + (reg << 3)); | |
| 531 | − g(0x25); | |
| 530 | + g(S, 0x04 + (reg << 3)); | |
| 531 | + g(S, 0x25); | |
| 532 | 532 | #else |
| 533 | − g(0x05 + (reg << 3)); | |
| 533 | + g(S, 0x05 + (reg << 3)); | |
| 534 | 534 | #endif |
| 535 | − gen_expr32(&op->e); | |
| 535 | + gen_expr32(S, &op->e); | |
| 536 | 536 | #ifdef TCC_TARGET_X86_64 |
| 537 | 537 | } else if (op->reg == -2) { |
| 538 | 538 | ExprValue *pe = &op->e; |
| 539 | − g(0x05 + (reg << 3)); | |
| 540 | − gen_addrpc32(pe->sym ? VT_SYM : 0, pe->sym, pe->v); | |
| 541 | − return ind; | |
| 539 | + g(S, 0x05 + (reg << 3)); | |
| 540 | + gen_addrpc32(S, pe->sym ? VT_SYM : 0, pe->sym, pe->v); | |
| 541 | + return S->tccgen_ind; | |
| 542 | 542 | #endif |
| 543 | 543 | } else { |
| 544 | 544 | sib_reg1 = op->reg; |
| @@ -557,19 +557,19 @@ static inline int asm_modrm(int reg, Operand *op) · 12 unmodified lines | ||
| 557 | 557 | reg1 = op->reg; |
| 558 | 558 | if (op->reg2 != -1) |
| 559 | 559 | reg1 = 4; |
| 560 | − g(mod + (reg << 3) + reg1); | |
| 560 | + g(S, mod + (reg << 3) + reg1); | |
| 561 | 561 | if (reg1 == 4) { |
| 562 | 562 | /* add sib byte */ |
| 563 | 563 | reg2 = op->reg2; |
| 564 | 564 | if (reg2 == -1) |
| 565 | 565 | reg2 = 4; /* indicate no index */ |
| 566 | − g((op->shift << 6) + (reg2 << 3) + sib_reg1); | |
| 566 | + g(S, (op->shift << 6) + (reg2 << 3) + sib_reg1); | |
| 567 | 567 | } |
| 568 | 568 | /* add offset */ |
| 569 | 569 | if (mod == 0x40) { |
| 570 | − g(op->e.v); | |
| 570 | + g(S, op->e.v); | |
| 571 | 571 | } else if (mod == 0x80 || op->reg == -1) { |
| 572 | − gen_expr32(&op->e); | |
| 572 | + gen_expr32(S, &op->e); | |
| 573 | 573 | } |
| 574 | 574 | } |
| 575 | 575 | return 0; |
| @@ -581,7 +581,7 @@ static inline int asm_modrm(int reg, Operand *op) · 5 unmodified lines | ||
| 581 | 581 | #define REX_X 0x42 |
| 582 | 582 | #define REX_B 0x41 |
| 583 | 583 | |
| 584 | −static void asm_rex(int width64, Operand *ops, int nb_ops, int *op_type, | |
| 584 | +static void asm_rex(TCCState* S, int width64, Operand *ops, int nb_ops, int *op_type, | |
| 585 | 585 | int regi, int rmi) |
| 586 | 586 | { |
| 587 | 587 | unsigned char rex = width64 ? 0x48 : 0; |
| @@ -631,9 +631,9 @@ static void asm_rex(int width64, Operand *ops, int nb_ops, int *op_type, · 43 unmodified lines | ||
| 631 | 631 | } |
| 632 | 632 | if (rex) { |
| 633 | 633 | if (saw_high_8bit) |
| 634 | − tcc_error("can't encode register %%%ch when REX prefix is required", | |
| 634 | + tcc_error(S, "can't encode register %%%ch when REX prefix is required", | |
| 635 | 635 | "acdb"[saw_high_8bit-4]); |
| 636 | − g(rex); | |
| 636 | + g(S, rex); | |
| 637 | 637 | } |
| 638 | 638 | } |
| 639 | 639 | #endif |
| @@ -679,7 +679,7 @@ static void maybe_print_stats (void) · 39 unmodified lines | ||
| 679 | 679 | } |
| 680 | 680 | } |
| 681 | 681 | |
| 682 | −ST_FUNC void asm_opcode(TCCState *s1, int opcode) | |
| 682 | +ST_FUNC void asm_opcode(TCCState *S, int opcode) | |
| 683 | 683 | { |
| 684 | 684 | const ASMInstr *pa; |
| 685 | 685 | int i, modrm_index, modreg_index, reg, v, op1, seg_prefix, pc; |
| @@ -697,7 +697,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int opcode) · 11 unmodified lines | ||
| 697 | 697 | /* force synthetic ';' after prefix instruction, so we can handle */ |
| 698 | 698 | /* one-line things like "rep stosb" instead of only "rep\nstosb" */ |
| 699 | 699 | if (opcode >= TOK_ASM_wait && opcode <= TOK_ASM_repnz) |
| 700 | − unget_tok(';'); | |
| 700 | + unget_tok(S, ';'); | |
| 701 | 701 | |
| 702 | 702 | /* get operands */ |
| 703 | 703 | pop = ops; |
| @@ -705,27 +705,27 @@ ST_FUNC void asm_opcode(TCCState *s1, int opcode) · 1 unmodified line | ||
| 705 | 705 | seg_prefix = 0; |
| 706 | 706 | alltypes = 0; |
| 707 | 707 | for(;;) { |
| 708 | − if (tok == ';' || tok == TOK_LINEFEED) | |
| 708 | + if (S->tccpp_tok == ';' || S->tccpp_tok == TOK_LINEFEED) | |
| 709 | 709 | break; |
| 710 | 710 | if (nb_ops >= MAX_OPERANDS) { |
| 711 | − tcc_error("incorrect number of operands"); | |
| 711 | + tcc_error(S, "incorrect number of operands"); | |
| 712 | 712 | } |
| 713 | − parse_operand(s1, pop); | |
| 714 | − if (tok == ':') { | |
| 713 | + parse_operand(S, pop); | |
| 714 | + if (S->tccpp_tok == ':') { | |
| 715 | 715 | if (pop->type != OP_SEG || seg_prefix) |
| 716 | − tcc_error("incorrect prefix"); | |
| 716 | + tcc_error(S, "incorrect prefix"); | |
| 717 | 717 | seg_prefix = segment_prefixes[pop->reg]; |
| 718 | − next(); | |
| 719 | − parse_operand(s1, pop); | |
| 718 | + next(S); | |
| 719 | + parse_operand(S, pop); | |
| 720 | 720 | if (!(pop->type & OP_EA)) { |
| 721 | − tcc_error("segment prefix must be followed by memory reference"); | |
| 721 | + tcc_error(S, "segment prefix must be followed by memory reference"); | |
| 722 | 722 | } |
| 723 | 723 | } |
| 724 | 724 | pop++; |
| 725 | 725 | nb_ops++; |
| 726 | − if (tok != ',') | |
| 726 | + if (S->tccpp_tok != ',') | |
| 727 | 727 | break; |
| 728 | − next(); | |
| 728 | + next(S); | |
| 729 | 729 | } |
| 730 | 730 | |
| 731 | 731 | s = 0; /* avoid warning */ |
| @@ -842,23 +842,23 @@ again: · 110 unmodified lines | ||
| 842 | 842 | int b; |
| 843 | 843 | b = op0_codes[opcode - TOK_ASM_first]; |
| 844 | 844 | if (b & 0xff00) |
| 845 | − g(b >> 8); | |
| 846 | − g(b); | |
| 845 | + g(S, b >> 8); | |
| 846 | + g(S, b); | |
| 847 | 847 | return; |
| 848 | 848 | } else if (opcode <= TOK_ASM_alllast) { |
| 849 | − tcc_error("bad operand with opcode '%s'", | |
| 850 | − get_tok_str(opcode, NULL)); | |
| 849 | + tcc_error(S, "bad operand with opcode '%s'", | |
| 850 | + get_tok_str(S, opcode, NULL)); | |
| 851 | 851 | } else { |
| 852 | 852 | /* Special case for cmovcc, we accept size suffixes but ignore |
| 853 | 853 | them, but we don't want them to blow up our tables. */ |
| 854 | − TokenSym *ts = table_ident[opcode - TOK_IDENT]; | |
| 854 | + TokenSym *ts = S->tccpp_table_ident[opcode - TOK_IDENT]; | |
| 855 | 855 | if (ts->len >= 6 |
| 856 | 856 | && strchr("wlq", ts->str[ts->len-1]) |
| 857 | 857 | && !memcmp(ts->str, "cmov", 4)) { |
| 858 | − opcode = tok_alloc(ts->str, ts->len-1)->tok; | |
| 858 | + opcode = tok_alloc(S, ts->str, ts->len-1)->tok; | |
| 859 | 859 | goto again; |
| 860 | 860 | } |
| 861 | − tcc_error("unknown opcode '%s'", ts->str); | |
| 861 | + tcc_error(S, "unknown opcode '%s'", ts->str); | |
| 862 | 862 | } |
| 863 | 863 | } |
| 864 | 864 | /* if the size is unknown, then evaluate it (OPC_B or OPC_WL case) */ |
| @@ -886,7 +886,7 @@ again: · 21 unmodified lines | ||
| 886 | 886 | (ops[0].type & OP_EA)) |
| 887 | 887 | s = NBWLX - 2; |
| 888 | 888 | else |
| 889 | − tcc_error("cannot infer opcode suffix"); | |
| 889 | + tcc_error(S, "cannot infer opcode suffix"); | |
| 890 | 890 | } |
| 891 | 891 | } |
| 892 | 892 | |
| @@ -894,7 +894,7 @@ again: · 1 unmodified line | ||
| 894 | 894 | /* Generate addr32 prefix if needed */ |
| 895 | 895 | for(i = 0; i < nb_ops; i++) { |
| 896 | 896 | if (ops[i].type & OP_EA32) { |
| 897 | − g(0x67); | |
| 897 | + g(S, 0x67); | |
| 898 | 898 | break; |
| 899 | 899 | } |
| 900 | 900 | } |
| @@ -913,7 +913,7 @@ again: · 12 unmodified lines | ||
| 913 | 913 | p66 = 1; |
| 914 | 914 | } |
| 915 | 915 | if (p66) |
| 916 | − g(0x66); | |
| 916 | + g(S, 0x66); | |
| 917 | 917 | #ifdef TCC_TARGET_X86_64 |
| 918 | 918 | rex64 = 0; |
| 919 | 919 | if (pa->instr_type & OPC_48) |
| @@ -943,9 +943,9 @@ again: · 23 unmodified lines | ||
| 943 | 943 | |
| 944 | 944 | /* now generates the operation */ |
| 945 | 945 | if (OPCT_IS(pa->instr_type, OPC_FWAIT)) |
| 946 | − g(0x9b); | |
| 946 | + g(S, 0x9b); | |
| 947 | 947 | if (seg_prefix) |
| 948 | − g(seg_prefix); | |
| 948 | + g(S, seg_prefix); | |
| 949 | 949 | |
| 950 | 950 | v = pa->opcode; |
| 951 | 951 | if (pa->instr_type & OPC_0F) |
| @@ -998,7 +998,7 @@ again: · 46 unmodified lines | ||
| 998 | 998 | goto modrm_found; |
| 999 | 999 | } |
| 1000 | 1000 | #ifdef ASM_DEBUG |
| 1001 | − tcc_error("bad op table"); | |
| 1001 | + tcc_error(S, "bad op table"); | |
| 1002 | 1002 | #endif |
| 1003 | 1003 | modrm_found: |
| 1004 | 1004 | modrm_index = i; |
| @@ -1014,7 +1014,7 @@ again: · 9 unmodified lines | ||
| 1014 | 1014 | } |
| 1015 | 1015 | } |
| 1016 | 1016 | #ifdef TCC_TARGET_X86_64 |
| 1017 | − asm_rex (rex64, ops, nb_ops, op_type, modreg_index, modrm_index); | |
| 1017 | + asm_rex (S, rex64, ops, nb_ops, op_type, modreg_index, modrm_index); | |
| 1018 | 1018 | #endif |
| 1019 | 1019 | |
| 1020 | 1020 | if (pa->instr_type & OPC_REG) { |
| @@ -1035,10 +1035,10 @@ again: · 14 unmodified lines | ||
| 1035 | 1035 | int jmp_disp; |
| 1036 | 1036 | |
| 1037 | 1037 | /* see if we can really generate the jump with a byte offset */ |
| 1038 | − esym = elfsym(ops[0].e.sym); | |
| 1038 | + esym = elfsym(S, ops[0].e.sym); | |
| 1039 | 1039 | if (!esym || esym->st_shndx != cur_text_section->sh_num) |
| 1040 | 1040 | goto no_short_jump; |
| 1041 | − jmp_disp = ops[0].e.v + esym->st_value - ind - 2 - (v >= 0xff); | |
| 1041 | + jmp_disp = ops[0].e.v + esym->st_value - S->tccgen_ind - 2 - (v >= 0xff); | |
| 1042 | 1042 | if (jmp_disp == (int8_t)jmp_disp) { |
| 1043 | 1043 | /* OK to generate jump */ |
| 1044 | 1044 | ops[0].e.sym = 0; |
| @@ -1053,18 +1053,18 @@ again: · 8 unmodified lines | ||
| 1053 | 1053 | else if (v == 0x70) /* jcc */ |
| 1054 | 1054 | v += 0x0f10; |
| 1055 | 1055 | else |
| 1056 | − tcc_error("invalid displacement"); | |
| 1056 | + tcc_error(S, "invalid displacement"); | |
| 1057 | 1057 | } |
| 1058 | 1058 | } |
| 1059 | 1059 | if (OPCT_IS(pa->instr_type, OPC_TEST)) |
| 1060 | 1060 | v += test_bits[opcode - pa->sym]; |
| 1061 | 1061 | op1 = v >> 16; |
| 1062 | 1062 | if (op1) |
| 1063 | − g(op1); | |
| 1063 | + g(S, op1); | |
| 1064 | 1064 | op1 = (v >> 8) & 0xff; |
| 1065 | 1065 | if (op1) |
| 1066 | − g(op1); | |
| 1067 | − g(v); | |
| 1066 | + g(S, op1); | |
| 1067 | + g(S, v); | |
| 1068 | 1068 | |
| 1069 | 1069 | if (OPCT_IS(pa->instr_type, OPC_SHIFT)) { |
| 1070 | 1070 | reg = (opcode - pa->sym) / NBWLX; |
| @@ -1084,7 +1084,7 @@ again: · 13 unmodified lines | ||
| 1084 | 1084 | used instead of group */ |
| 1085 | 1085 | if (modreg_index >= 0) |
| 1086 | 1086 | reg = ops[modreg_index].reg; |
| 1087 | − pc = asm_modrm(reg, &ops[modrm_index]); | |
| 1087 | + pc = asm_modrm(S, reg, &ops[modrm_index]); | |
| 1088 | 1088 | } |
| 1089 | 1089 | |
| 1090 | 1090 | /* emit constants */ |
| @@ -1092,10 +1092,10 @@ again: · 1 unmodified line | ||
| 1092 | 1092 | if (!(pa->instr_type & OPC_0F) |
| 1093 | 1093 | && (pa->opcode == 0x9a || pa->opcode == 0xea)) { |
| 1094 | 1094 | /* ljmp or lcall kludge */ |
| 1095 | − gen_expr32(&ops[1].e); | |
| 1095 | + gen_expr32(S, &ops[1].e); | |
| 1096 | 1096 | if (ops[0].e.sym) |
| 1097 | − tcc_error("cannot relocate"); | |
| 1098 | − gen_le16(ops[0].e.v); | |
| 1097 | + tcc_error(S, "cannot relocate"); | |
| 1098 | + gen_le16(S, ops[0].e.v); | |
| 1099 | 1099 | return; |
| 1100 | 1100 | } |
| 1101 | 1101 | #endif |
| @@ -1116,32 +1116,32 @@ again: · 14 unmodified lines | ||
| 1116 | 1116 | } |
| 1117 | 1117 | |
| 1118 | 1118 | if ((v & (OP_IM8 | OP_IM8S | OP_IM16)) && ops[i].e.sym) |
| 1119 | − tcc_error("cannot relocate"); | |
| 1119 | + tcc_error(S, "cannot relocate"); | |
| 1120 | 1120 | |
| 1121 | 1121 | if (v & (OP_IM8 | OP_IM8S)) { |
| 1122 | − g(ops[i].e.v); | |
| 1122 | + g(S, ops[i].e.v); | |
| 1123 | 1123 | } else if (v & OP_IM16) { |
| 1124 | − gen_le16(ops[i].e.v); | |
| 1124 | + gen_le16(S, ops[i].e.v); | |
| 1125 | 1125 | #ifdef TCC_TARGET_X86_64 |
| 1126 | 1126 | } else if (v & OP_IM64) { |
| 1127 | − gen_expr64(&ops[i].e); | |
| 1127 | + gen_expr64(S, &ops[i].e); | |
| 1128 | 1128 | #endif |
| 1129 | 1129 | } else if (pa->op_type[i] == OPT_DISP || pa->op_type[i] == OPT_DISP8) { |
| 1130 | − gen_disp32(&ops[i].e); | |
| 1130 | + gen_disp32(S, &ops[i].e); | |
| 1131 | 1131 | } else { |
| 1132 | − gen_expr32(&ops[i].e); | |
| 1132 | + gen_expr32(S, &ops[i].e); | |
| 1133 | 1133 | } |
| 1134 | 1134 | } |
| 1135 | 1135 | } |
| 1136 | 1136 | |
| 1137 | 1137 | /* after immediate operands, adjust pc-relative address */ |
| 1138 | 1138 | if (pc) |
| 1139 | − add32le(cur_text_section->data + pc - 4, pc - ind); | |
| 1139 | + add32le(cur_text_section->data + pc - 4, pc - S->tccgen_ind); | |
| 1140 | 1140 | } |
| 1141 | 1141 | |
| 1142 | 1142 | /* return the constraint priority (we allocate first the lowest |
| 1143 | 1143 | numbered constraints) */ |
| 1144 | −static inline int constraint_priority(const char *str) | |
| 1144 | +static inline int constraint_priority(TCCState* S, const char *str) | |
| 1145 | 1145 | { |
| 1146 | 1146 | int priority, c, pr; |
| 1147 | 1147 | |
| @@ -1182,7 +1182,7 @@ static inline int constraint_priority(const char *str) · 34 unmodified lines | ||
| 1182 | 1182 | pr = 4; |
| 1183 | 1183 | break; |
| 1184 | 1184 | default: |
| 1185 | − tcc_error("unknown constraint '%c'", c); | |
| 1185 | + tcc_error(S, "unknown constraint '%c'", c); | |
| 1186 | 1186 | pr = 0; |
| 1187 | 1187 | } |
| 1188 | 1188 | if (pr > priority) |
| @@ -1200,19 +1200,19 @@ static const char *skip_constraint_modifiers(const char *p) · 11 unmodified lines | ||
| 1200 | 1200 | |
| 1201 | 1201 | /* If T (a token) is of the form "%reg" returns the register |
| 1202 | 1202 | number and type, otherwise return -1. */ |
| 1203 | −ST_FUNC int asm_parse_regvar (int t) | |
| 1203 | +ST_FUNC int asm_parse_regvar (TCCState* S, int t) | |
| 1204 | 1204 | { |
| 1205 | 1205 | const char *s; |
| 1206 | 1206 | Operand op; |
| 1207 | 1207 | if (t < TOK_IDENT || (t & SYM_FIELD)) |
| 1208 | 1208 | return -1; |
| 1209 | − s = table_ident[t - TOK_IDENT]->str; | |
| 1209 | + s = S->tccpp_table_ident[t - TOK_IDENT]->str; | |
| 1210 | 1210 | if (s[0] != '%') |
| 1211 | 1211 | return -1; |
| 1212 | − t = tok_alloc_const(s + 1); | |
| 1213 | − unget_tok(t); | |
| 1214 | − unget_tok('%'); | |
| 1215 | − parse_operand(tcc_state, &op); | |
| 1212 | + t = tok_alloc_const(S, s + 1); | |
| 1213 | + unget_tok(S, t); | |
| 1214 | + unget_tok(S, '%'); | |
| 1215 | + parse_operand(S, &op); | |
| 1216 | 1216 | /* Accept only integer regs for now. */ |
| 1217 | 1217 | if (op.type & OP_REG) |
| 1218 | 1218 | return op.reg; |
| @@ -1225,7 +1225,7 @@ ST_FUNC int asm_parse_regvar (int t) · 6 unmodified lines | ||
| 1225 | 1225 | |
| 1226 | 1226 | #define is_reg_allocated(reg) (regs_allocated[reg] & reg_mask) |
| 1227 | 1227 | |
| 1228 | −ST_FUNC void asm_compute_constraints(ASMOperand *operands, | |
| 1228 | +ST_FUNC void asm_compute_constraints(TCCState* S, ASMOperand *operands, | |
| 1229 | 1229 | int nb_operands, int nb_outputs, |
| 1230 | 1230 | const uint8_t *clobber_regs, |
| 1231 | 1231 | int *pout_reg) |
| @@ -1253,13 +1253,13 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 21 unmodified lines | ||
| 1253 | 1253 | str = skip_constraint_modifiers(str); |
| 1254 | 1254 | if (isnum(*str) || *str == '[') { |
| 1255 | 1255 | /* this is a reference to another constraint */ |
| 1256 | − k = find_constraint(operands, nb_operands, str, NULL); | |
| 1256 | + k = find_constraint(S, operands, nb_operands, str, NULL); | |
| 1257 | 1257 | if ((unsigned)k >= i || i < nb_outputs) |
| 1258 | − tcc_error("invalid reference in constraint %d ('%s')", | |
| 1258 | + tcc_error(S, "invalid reference in constraint %d ('%s')", | |
| 1259 | 1259 | i, str); |
| 1260 | 1260 | op->ref_index = k; |
| 1261 | 1261 | if (operands[k].input_index >= 0) |
| 1262 | − tcc_error("cannot reference twice the same operand"); | |
| 1262 | + tcc_error(S, "cannot reference twice the same operand"); | |
| 1263 | 1263 | operands[k].input_index = i; |
| 1264 | 1264 | op->priority = 5; |
| 1265 | 1265 | } else if ((op->vt->r & VT_VALMASK) == VT_LOCAL |
| @@ -1268,7 +1268,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 2 unmodified lines | ||
| 1268 | 1268 | op->priority = 1; |
| 1269 | 1269 | op->reg = reg; |
| 1270 | 1270 | } else { |
| 1271 | − op->priority = constraint_priority(str); | |
| 1271 | + op->priority = constraint_priority(S, str); | |
| 1272 | 1272 | } |
| 1273 | 1273 | } |
| 1274 | 1274 | |
| @@ -1316,7 +1316,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 41 unmodified lines | ||
| 1316 | 1316 | } |
| 1317 | 1317 | if (op->reg >= 0) { |
| 1318 | 1318 | if (is_reg_allocated(op->reg)) |
| 1319 | − tcc_error("asm regvar requests register that's taken already"); | |
| 1319 | + tcc_error(S, "asm regvar requests register that's taken already"); | |
| 1320 | 1320 | reg = op->reg; |
| 1321 | 1321 | goto reg_found; |
| 1322 | 1322 | } |
| @@ -1330,7 +1330,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 7 unmodified lines | ||
| 1330 | 1330 | /* FALL THRU */ |
| 1331 | 1331 | case '&': |
| 1332 | 1332 | if (j >= nb_outputs) |
| 1333 | − tcc_error("'%c' modifier can only be applied to outputs", c); | |
| 1333 | + tcc_error(S, "'%c' modifier can only be applied to outputs", c); | |
| 1334 | 1334 | reg_mask = REG_IN_MASK | REG_OUT_MASK; |
| 1335 | 1335 | goto try_next; |
| 1336 | 1336 | case 'A': |
| @@ -1424,7 +1424,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 87 unmodified lines | ||
| 1424 | 1424 | } |
| 1425 | 1425 | break; |
| 1426 | 1426 | default: |
| 1427 | − tcc_error("asm constraint %d ('%s') could not be satisfied", | |
| 1427 | + tcc_error(S, "asm constraint %d ('%s') could not be satisfied", | |
| 1428 | 1428 | j, op->constraint); |
| 1429 | 1429 | break; |
| 1430 | 1430 | } |
| @@ -1447,7 +1447,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 16 unmodified lines | ||
| 1447 | 1447 | if (!(regs_allocated[reg] & REG_OUT_MASK)) |
| 1448 | 1448 | goto reg_found2; |
| 1449 | 1449 | } |
| 1450 | − tcc_error("could not find free output register for reloading"); | |
| 1450 | + tcc_error(S, "could not find free output register for reloading"); | |
| 1451 | 1451 | reg_found2: |
| 1452 | 1452 | *pout_reg = reg; |
| 1453 | 1453 | break; |
| @@ -1461,7 +1461,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 7 unmodified lines | ||
| 1461 | 1461 | op = &operands[j]; |
| 1462 | 1462 | printf("%%%d [%s]: \"%s\" r=0x%04x reg=%d\n", |
| 1463 | 1463 | j, |
| 1464 | − op->id ? get_tok_str(op->id, NULL) : "", | |
| 1464 | + op->id ? get_tok_str(S, op->id, NULL) : "", | |
| 1465 | 1465 | op->constraint, |
| 1466 | 1466 | op->vt->r, |
| 1467 | 1467 | op->reg); |
| @@ -1471,7 +1471,7 @@ ST_FUNC void asm_compute_constraints(ASMOperand *operands, · 3 unmodified lines | ||
| 1471 | 1471 | #endif |
| 1472 | 1472 | } |
| 1473 | 1473 | |
| 1474 | −ST_FUNC void subst_asm_operand(CString *add_str, | |
| 1474 | +ST_FUNC void subst_asm_operand(TCCState* S, CString *add_str, | |
| 1475 | 1475 | SValue *sv, int modifier) |
| 1476 | 1476 | { |
| 1477 | 1477 | int r, reg, size, val; |
| @@ -1481,33 +1481,33 @@ ST_FUNC void subst_asm_operand(CString *add_str, · 3 unmodified lines | ||
| 1481 | 1481 | if ((r & VT_VALMASK) == VT_CONST) { |
| 1482 | 1482 | if (!(r & VT_LVAL) && modifier != 'c' && modifier != 'n' && |
| 1483 | 1483 | modifier != 'P') |
| 1484 | − cstr_ccat(add_str, '$'); | |
| 1484 | + cstr_ccat(S, add_str, '$'); | |
| 1485 | 1485 | if (r & VT_SYM) { |
| 1486 | − const char *name = get_tok_str(sv->sym->v, NULL); | |
| 1486 | + const char *name = get_tok_str(S, sv->sym->v, NULL); | |
| 1487 | 1487 | if (sv->sym->v >= SYM_FIRST_ANOM) { |
| 1488 | 1488 | /* In case of anonymous symbols ("L.42", used |
| 1489 | 1489 | for static data labels) we can't find them |
| 1490 | 1490 | in the C symbol table when later looking up |
| 1491 | 1491 | this name. So enter them now into the asm label |
| 1492 | 1492 | list when we still know the symbol. */ |
| 1493 | − get_asm_sym(tok_alloc_const(name), sv->sym); | |
| 1493 | + get_asm_sym(S, tok_alloc_const(S, name), sv->sym); | |
| 1494 | 1494 | } |
| 1495 | − if (tcc_state->leading_underscore) | |
| 1496 | − cstr_ccat(add_str, '_'); | |
| 1497 | − cstr_cat(add_str, name, -1); | |
| 1495 | + if (S->leading_underscore) | |
| 1496 | + cstr_ccat(S, add_str, '_'); | |
| 1497 | + cstr_cat(S, add_str, name, -1); | |
| 1498 | 1498 | if ((uint32_t)sv->c.i == 0) |
| 1499 | 1499 | goto no_offset; |
| 1500 | − cstr_ccat(add_str, '+'); | |
| 1500 | + cstr_ccat(S, add_str, '+'); | |
| 1501 | 1501 | } |
| 1502 | 1502 | val = sv->c.i; |
| 1503 | 1503 | if (modifier == 'n') |
| 1504 | 1504 | val = -val; |
| 1505 | 1505 | snprintf(buf, sizeof(buf), "%d", (int)sv->c.i); |
| 1506 | − cstr_cat(add_str, buf, -1); | |
| 1506 | + cstr_cat(S, add_str, buf, -1); | |
| 1507 | 1507 | no_offset:; |
| 1508 | 1508 | #ifdef TCC_TARGET_X86_64 |
| 1509 | 1509 | if (r & VT_LVAL) |
| 1510 | − cstr_cat(add_str, "(%rip)", -1); | |
| 1510 | + cstr_cat(S, add_str, "(%rip)", -1); | |
| 1511 | 1511 | #endif |
| 1512 | 1512 | } else if ((r & VT_VALMASK) == VT_LOCAL) { |
| 1513 | 1513 | #ifdef TCC_TARGET_X86_64 |
| @@ -1515,24 +1515,24 @@ ST_FUNC void subst_asm_operand(CString *add_str, · 1 unmodified line | ||
| 1515 | 1515 | #else |
| 1516 | 1516 | snprintf(buf, sizeof(buf), "%d(%%ebp)", (int)sv->c.i); |
| 1517 | 1517 | #endif |
| 1518 | − cstr_cat(add_str, buf, -1); | |
| 1518 | + cstr_cat(S, add_str, buf, -1); | |
| 1519 | 1519 | } else if (r & VT_LVAL) { |
| 1520 | 1520 | reg = r & VT_VALMASK; |
| 1521 | 1521 | if (reg >= VT_CONST) |
| 1522 | − tcc_internal_error(""); | |
| 1522 | + tcc_internal_error(S, ""); | |
| 1523 | 1523 | snprintf(buf, sizeof(buf), "(%%%s)", |
| 1524 | 1524 | #ifdef TCC_TARGET_X86_64 |
| 1525 | − get_tok_str(TOK_ASM_rax + reg, NULL) | |
| 1525 | + get_tok_str(S, TOK_ASM_rax + reg, NULL) | |
| 1526 | 1526 | #else |
| 1527 | − get_tok_str(TOK_ASM_eax + reg, NULL) | |
| 1527 | + get_tok_str(S, TOK_ASM_eax + reg, NULL) | |
| 1528 | 1528 | #endif |
| 1529 | 1529 | ); |
| 1530 | − cstr_cat(add_str, buf, -1); | |
| 1530 | + cstr_cat(S, add_str, buf, -1); | |
| 1531 | 1531 | } else { |
| 1532 | 1532 | /* register case */ |
| 1533 | 1533 | reg = r & VT_VALMASK; |
| 1534 | 1534 | if (reg >= VT_CONST) |
| 1535 | − tcc_internal_error(""); | |
| 1535 | + tcc_internal_error(S, ""); | |
| 1536 | 1536 | |
| 1537 | 1537 | /* choose register operand size */ |
| 1538 | 1538 | if ((sv->type.t & VT_BTYPE) == VT_BYTE || |
| @@ -1552,11 +1552,11 @@ ST_FUNC void subst_asm_operand(CString *add_str, · 13 unmodified lines | ||
| 1552 | 1552 | |
| 1553 | 1553 | if (modifier == 'b') { |
| 1554 | 1554 | if (reg >= 4) |
| 1555 | − tcc_error("cannot use byte register"); | |
| 1555 | + tcc_error(S, "cannot use byte register"); | |
| 1556 | 1556 | size = 1; |
| 1557 | 1557 | } else if (modifier == 'h') { |
| 1558 | 1558 | if (reg >= 4) |
| 1559 | − tcc_error("cannot use byte register"); | |
| 1559 | + tcc_error(S, "cannot use byte register"); | |
| 1560 | 1560 | size = -1; |
| 1561 | 1561 | } else if (modifier == 'w') { |
| 1562 | 1562 | size = 2; |
| @@ -1587,13 +1587,13 @@ ST_FUNC void subst_asm_operand(CString *add_str, · 24 unmodified lines | ||
| 1587 | 1587 | break; |
| 1588 | 1588 | #endif |
| 1589 | 1589 | } |
| 1590 | − snprintf(buf, sizeof(buf), "%%%s", get_tok_str(reg, NULL)); | |
| 1591 | − cstr_cat(add_str, buf, -1); | |
| 1590 | + snprintf(buf, sizeof(buf), "%%%s", get_tok_str(S, reg, NULL)); | |
| 1591 | + cstr_cat(S, add_str, buf, -1); | |
| 1592 | 1592 | } |
| 1593 | 1593 | } |
| 1594 | 1594 | |
| 1595 | 1595 | /* generate prolog and epilog code for asm statement */ |
| 1596 | −ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, | |
| 1596 | +ST_FUNC void asm_gen_code(TCCState* S, ASMOperand *operands, int nb_operands, | |
| 1597 | 1597 | int nb_outputs, int is_output, |
| 1598 | 1598 | uint8_t *clobber_regs, |
| 1599 | 1599 | int out_reg) |
| @@ -1627,8 +1627,8 @@ ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, · 27 unmodified lines | ||
| 1627 | 1627 | reg = reg_saved[i]; |
| 1628 | 1628 | if (regs_allocated[reg]) { |
| 1629 | 1629 | if (reg >= 8) |
| 1630 | − g(0x41), reg-=8; | |
| 1631 | − g(0x50 + reg); | |
| 1630 | + g(S, 0x41), reg-=8; | |
| 1631 | + g(S, 0x50 + reg); | |
| 1632 | 1632 | } |
| 1633 | 1633 | } |
| 1634 | 1634 | |
| @@ -1644,15 +1644,15 @@ ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, · 9 unmodified lines | ||
| 1644 | 1644 | sv = *op->vt; |
| 1645 | 1645 | sv.r = (sv.r & ~VT_VALMASK) | VT_LOCAL | VT_LVAL; |
| 1646 | 1646 | sv.type.t = VT_PTR; |
| 1647 | − load(op->reg, &sv); | |
| 1647 | + load(S, op->reg, &sv); | |
| 1648 | 1648 | } else if (i >= nb_outputs || op->is_rw) { |
| 1649 | 1649 | /* load value in register */ |
| 1650 | − load(op->reg, op->vt); | |
| 1650 | + load(S, op->reg, op->vt); | |
| 1651 | 1651 | if (op->is_llong) { |
| 1652 | 1652 | SValue sv; |
| 1653 | 1653 | sv = *op->vt; |
| 1654 | 1654 | sv.c.i += 4; |
| 1655 | − load(TREG_XDX, &sv); | |
| 1655 | + load(S, TREG_XDX, &sv); | |
| 1656 | 1656 | } |
| 1657 | 1657 | } |
| 1658 | 1658 | } |
| @@ -1668,19 +1668,19 @@ ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, · 9 unmodified lines | ||
| 1668 | 1668 | sv = *op->vt; |
| 1669 | 1669 | sv.r = (sv.r & ~VT_VALMASK) | VT_LOCAL; |
| 1670 | 1670 | sv.type.t = VT_PTR; |
| 1671 | − load(out_reg, &sv); | |
| 1671 | + load(S, out_reg, &sv); | |
| 1672 | 1672 | |
| 1673 | 1673 | sv = *op->vt; |
| 1674 | 1674 | sv.r = (sv.r & ~VT_VALMASK) | out_reg; |
| 1675 | − store(op->reg, &sv); | |
| 1675 | + store(S, op->reg, &sv); | |
| 1676 | 1676 | } |
| 1677 | 1677 | } else { |
| 1678 | − store(op->reg, op->vt); | |
| 1678 | + store(S, op->reg, op->vt); | |
| 1679 | 1679 | if (op->is_llong) { |
| 1680 | 1680 | SValue sv; |
| 1681 | 1681 | sv = *op->vt; |
| 1682 | 1682 | sv.c.i += 4; |
| 1683 | − store(TREG_XDX, &sv); | |
| 1683 | + store(S, TREG_XDX, &sv); | |
| 1684 | 1684 | } |
| 1685 | 1685 | } |
| 1686 | 1686 | } |
| @@ -1690,14 +1690,14 @@ ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, · 3 unmodified lines | ||
| 1690 | 1690 | reg = reg_saved[i]; |
| 1691 | 1691 | if (regs_allocated[reg]) { |
| 1692 | 1692 | if (reg >= 8) |
| 1693 | − g(0x41), reg-=8; | |
| 1694 | − g(0x58 + reg); | |
| 1693 | + g(S, 0x41), reg-=8; | |
| 1694 | + g(S, 0x58 + reg); | |
| 1695 | 1695 | } |
| 1696 | 1696 | } |
| 1697 | 1697 | } |
| 1698 | 1698 | } |
| 1699 | 1699 | |
| 1700 | −ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str) | |
| 1700 | +ST_FUNC void asm_clobber(TCCState* S, uint8_t *clobber_regs, const char *str) | |
| 1701 | 1701 | { |
| 1702 | 1702 | int reg; |
| 1703 | 1703 | #ifdef TCC_TARGET_X86_64 |
| @@ -1708,7 +1708,7 @@ ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str) · 4 unmodified lines | ||
| 1708 | 1708 | !strcmp(str, "cc") || |
| 1709 | 1709 | !strcmp(str, "flags")) |
| 1710 | 1710 | return; |
| 1711 | − reg = tok_alloc_const(str); | |
| 1711 | + reg = tok_alloc_const(S, str); | |
| 1712 | 1712 | if (reg >= TOK_ASM_eax && reg <= TOK_ASM_edi) { |
| 1713 | 1713 | reg -= TOK_ASM_eax; |
| 1714 | 1714 | } else if (reg >= TOK_ASM_ax && reg <= TOK_ASM_di) { |
| @@ -1716,11 +1716,11 @@ ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str) · 1 unmodified line | ||
| 1716 | 1716 | #ifdef TCC_TARGET_X86_64 |
| 1717 | 1717 | } else if (reg >= TOK_ASM_rax && reg <= TOK_ASM_rdi) { |
| 1718 | 1718 | reg -= TOK_ASM_rax; |
| 1719 | − } else if ((reg = asm_parse_numeric_reg(reg, &type)) >= 0) { | |
| 1719 | + } else if ((reg = asm_parse_numeric_reg(S, reg, &type)) >= 0) { | |
| 1720 | 1720 | ; |
| 1721 | 1721 | #endif |
| 1722 | 1722 | } else { |
| 1723 | − tcc_error("invalid clobber register '%s'", str); | |
| 1723 | + tcc_error(S, "invalid clobber register '%s'", str); | |
| 1724 | 1724 | } |
| 1725 | 1725 | clobber_regs[reg] = 1; |
| 1726 | 1726 | } |
| @@ -100,50 +100,47 @@ ST_DATA const int reg_classes[NB_REGS] = { · 99 unmodified lines | ||
| 100 | 100 | static unsigned long func_sub_sp_offset; |
| 101 | 101 | static int func_ret_sub; |
| 102 | 102 | #ifdef CONFIG_TCC_BCHECK |
| 103 | −static addr_t func_bound_offset; | |
| 104 | −static unsigned long func_bound_ind; | |
| 105 | −ST_DATA int func_bound_add_epilog; | |
| 106 | −static void gen_bounds_prolog(void); | |
| 107 | −static void gen_bounds_epilog(void); | |
| 103 | +static void gen_bounds_prolog(TCCState* S); | |
| 104 | +static void gen_bounds_epilog(TCCState* S); | |
| 108 | 105 | #endif |
| 109 | 106 | |
| 110 | 107 | /* XXX: make it faster ? */ |
| 111 | −ST_FUNC void g(int c) | |
| 108 | +ST_FUNC void g(TCCState* S, int c) | |
| 112 | 109 | { |
| 113 | 110 | int ind1; |
| 114 | − if (nocode_wanted) | |
| 111 | + if (S->tccgen_nocode_wanted) | |
| 115 | 112 | return; |
| 116 | − ind1 = ind + 1; | |
| 113 | + ind1 = S->tccgen_ind + 1; | |
| 117 | 114 | if (ind1 > cur_text_section->data_allocated) |
| 118 | − section_realloc(cur_text_section, ind1); | |
| 119 | − cur_text_section->data[ind] = c; | |
| 120 | − ind = ind1; | |
| 115 | + section_realloc(S, cur_text_section, ind1); | |
| 116 | + cur_text_section->data[S->tccgen_ind] = c; | |
| 117 | + S->tccgen_ind = ind1; | |
| 121 | 118 | } |
| 122 | 119 | |
| 123 | −ST_FUNC void o(unsigned int c) | |
| 120 | +ST_FUNC void o(TCCState* S, unsigned int c) | |
| 124 | 121 | { |
| 125 | 122 | while (c) { |
| 126 | − g(c); | |
| 123 | + g(S, c); | |
| 127 | 124 | c = c >> 8; |
| 128 | 125 | } |
| 129 | 126 | } |
| 130 | 127 | |
| 131 | −ST_FUNC void gen_le16(int v) | |
| 128 | +ST_FUNC void gen_le16(TCCState* S, int v) | |
| 132 | 129 | { |
| 133 | − g(v); | |
| 134 | − g(v >> 8); | |
| 130 | + g(S, v); | |
| 131 | + g(S, v >> 8); | |
| 135 | 132 | } |
| 136 | 133 | |
| 137 | −ST_FUNC void gen_le32(int c) | |
| 134 | +ST_FUNC void gen_le32(TCCState* S, int c) | |
| 138 | 135 | { |
| 139 | − g(c); | |
| 140 | − g(c >> 8); | |
| 141 | − g(c >> 16); | |
| 142 | − g(c >> 24); | |
| 136 | + g(S, c); | |
| 137 | + g(S, c >> 8); | |
| 138 | + g(S, c >> 16); | |
| 139 | + g(S, c >> 24); | |
| 143 | 140 | } |
| 144 | 141 | |
| 145 | 142 | /* output a symbol and patch all calls to it */ |
| 146 | −ST_FUNC void gsym_addr(int t, int a) | |
| 143 | +ST_FUNC void gsym_addr(TCCState* S, int t, int a) | |
| 147 | 144 | { |
| 148 | 145 | while (t) { |
| 149 | 146 | unsigned char *ptr = cur_text_section->data + t; |
| @@ -154,73 +151,73 @@ ST_FUNC void gsym_addr(int t, int a) · 4 unmodified lines | ||
| 154 | 151 | } |
| 155 | 152 | |
| 156 | 153 | /* instruction + 4 bytes data. Return the address of the data */ |
| 157 | −static int oad(int c, int s) | |
| 154 | +static int oad(TCCState* S, int c, int s) | |
| 158 | 155 | { |
| 159 | 156 | int t; |
| 160 | − if (nocode_wanted) | |
| 157 | + if (S->tccgen_nocode_wanted) | |
| 161 | 158 | return s; |
| 162 | − o(c); | |
| 163 | − t = ind; | |
| 164 | − gen_le32(s); | |
| 159 | + o(S, c); | |
| 160 | + t = S->tccgen_ind; | |
| 161 | + gen_le32(S, s); | |
| 165 | 162 | return t; |
| 166 | 163 | } |
| 167 | 164 | |
| 168 | −ST_FUNC void gen_fill_nops(int bytes) | |
| 165 | +ST_FUNC void gen_fill_nops(TCCState* S, int bytes) | |
| 169 | 166 | { |
| 170 | 167 | while (bytes--) |
| 171 | − g(0x90); | |
| 168 | + g(S, 0x90); | |
| 172 | 169 | } |
| 173 | 170 | |
| 174 | 171 | /* generate jmp to a label */ |
| 175 | −#define gjmp2(instr,lbl) oad(instr,lbl) | |
| 172 | +#define gjmp2(s, instr,lbl) oad(s, instr,lbl) | |
| 176 | 173 | |
| 177 | 174 | /* output constant with relocation if 'r & VT_SYM' is true */ |
| 178 | −ST_FUNC void gen_addr32(int r, Sym *sym, int c) | |
| 175 | +ST_FUNC void gen_addr32(TCCState* S, int r, Sym *sym, int c) | |
| 179 | 176 | { |
| 180 | 177 | if (r & VT_SYM) |
| 181 | − greloc(cur_text_section, sym, ind, R_386_32); | |
| 182 | − gen_le32(c); | |
| 178 | + greloc(S, cur_text_section, sym, S->tccgen_ind, R_386_32); | |
| 179 | + gen_le32(S, c); | |
| 183 | 180 | } |
| 184 | 181 | |
| 185 | −ST_FUNC void gen_addrpc32(int r, Sym *sym, int c) | |
| 182 | +ST_FUNC void gen_addrpc32(TCCState* S, int r, Sym *sym, int c) | |
| 186 | 183 | { |
| 187 | 184 | if (r & VT_SYM) |
| 188 | − greloc(cur_text_section, sym, ind, R_386_PC32); | |
| 189 | − gen_le32(c - 4); | |
| 185 | + greloc(S, cur_text_section, sym, S->tccgen_ind, R_386_PC32); | |
| 186 | + gen_le32(S, c - 4); | |
| 190 | 187 | } |
| 191 | 188 | |
| 192 | 189 | /* generate a modrm reference. 'op_reg' contains the additional 3 |
| 193 | 190 | opcode bits */ |
| 194 | −static void gen_modrm(int op_reg, int r, Sym *sym, int c) | |
| 191 | +static void gen_modrm(TCCState* S, int op_reg, int r, Sym *sym, int c) | |
| 195 | 192 | { |
| 196 | 193 | op_reg = op_reg << 3; |
| 197 | 194 | if ((r & VT_VALMASK) == VT_CONST) { |
| 198 | 195 | /* constant memory reference */ |
| 199 | − o(0x05 | op_reg); | |
| 200 | − gen_addr32(r, sym, c); | |
| 196 | + o(S, 0x05 | op_reg); | |
| 197 | + gen_addr32(S, r, sym, c); | |
| 201 | 198 | } else if ((r & VT_VALMASK) == VT_LOCAL) { |
| 202 | 199 | /* currently, we use only ebp as base */ |
| 203 | 200 | if (c == (char)c) { |
| 204 | 201 | /* short reference */ |
| 205 | − o(0x45 | op_reg); | |
| 206 | − g(c); | |
| 202 | + o(S, 0x45 | op_reg); | |
| 203 | + g(S, c); | |
| 207 | 204 | } else { |
| 208 | − oad(0x85 | op_reg, c); | |
| 205 | + oad(S, 0x85 | op_reg, c); | |
| 209 | 206 | } |
| 210 | 207 | } else { |
| 211 | − g(0x00 | op_reg | (r & VT_VALMASK)); | |
| 208 | + g(S, 0x00 | op_reg | (r & VT_VALMASK)); | |
| 212 | 209 | } |
| 213 | 210 | } |
| 214 | 211 | |
| 215 | 212 | /* load 'r' from value 'sv' */ |
| 216 | −ST_FUNC void load(int r, SValue *sv) | |
| 213 | +ST_FUNC void load(TCCState* S, int r, SValue *sv) | |
| 217 | 214 | { |
| 218 | 215 | int v, t, ft, fc, fr; |
| 219 | 216 | SValue v1; |
| 220 | 217 | |
| 221 | 218 | #ifdef TCC_TARGET_PE |
| 222 | 219 | SValue v2; |
| 223 | − sv = pe_getimport(sv, &v2); | |
| 220 | + sv = pe_getimport(S, sv, &v2); | |
| 224 | 221 | #endif |
| 225 | 222 | |
| 226 | 223 | fr = sv->r; |
| @@ -238,68 +235,68 @@ ST_FUNC void load(int r, SValue *sv) · 11 unmodified lines | ||
| 238 | 235 | v1.sym = NULL; |
| 239 | 236 | fr = r; |
| 240 | 237 | if (!(reg_classes[fr] & RC_INT)) |
| 241 | − fr = get_reg(RC_INT); | |
| 242 | − load(fr, &v1); | |
| 238 | + fr = get_reg(S, RC_INT); | |
| 239 | + load(S, fr, &v1); | |
| 243 | 240 | } |
| 244 | 241 | if ((ft & VT_BTYPE) == VT_FLOAT) { |
| 245 | − o(0xd9); /* flds */ | |
| 242 | + o(S, 0xd9); /* flds */ | |
| 246 | 243 | r = 0; |
| 247 | 244 | } else if ((ft & VT_BTYPE) == VT_DOUBLE) { |
| 248 | − o(0xdd); /* fldl */ | |
| 245 | + o(S, 0xdd); /* fldl */ | |
| 249 | 246 | r = 0; |
| 250 | 247 | } else if ((ft & VT_BTYPE) == VT_LDOUBLE) { |
| 251 | − o(0xdb); /* fldt */ | |
| 248 | + o(S, 0xdb); /* fldt */ | |
| 252 | 249 | r = 5; |
| 253 | 250 | } else if ((ft & VT_TYPE) == VT_BYTE || (ft & VT_TYPE) == VT_BOOL) { |
| 254 | − o(0xbe0f); /* movsbl */ | |
| 251 | + o(S, 0xbe0f); /* movsbl */ | |
| 255 | 252 | } else if ((ft & VT_TYPE) == (VT_BYTE | VT_UNSIGNED)) { |
| 256 | − o(0xb60f); /* movzbl */ | |
| 253 | + o(S, 0xb60f); /* movzbl */ | |
| 257 | 254 | } else if ((ft & VT_TYPE) == VT_SHORT) { |
| 258 | − o(0xbf0f); /* movswl */ | |
| 255 | + o(S, 0xbf0f); /* movswl */ | |
| 259 | 256 | } else if ((ft & VT_TYPE) == (VT_SHORT | VT_UNSIGNED)) { |
| 260 | − o(0xb70f); /* movzwl */ | |
| 257 | + o(S, 0xb70f); /* movzwl */ | |
| 261 | 258 | } else { |
| 262 | − o(0x8b); /* movl */ | |
| 259 | + o(S, 0x8b); /* movl */ | |
| 263 | 260 | } |
| 264 | − gen_modrm(r, fr, sv->sym, fc); | |
| 261 | + gen_modrm(S, r, fr, sv->sym, fc); | |
| 265 | 262 | } else { |
| 266 | 263 | if (v == VT_CONST) { |
| 267 | − o(0xb8 + r); /* mov $xx, r */ | |
| 268 | − gen_addr32(fr, sv->sym, fc); | |
| 264 | + o(S, 0xb8 + r); /* mov $xx, r */ | |
| 265 | + gen_addr32(S, fr, sv->sym, fc); | |
| 269 | 266 | } else if (v == VT_LOCAL) { |
| 270 | 267 | if (fc) { |
| 271 | − o(0x8d); /* lea xxx(%ebp), r */ | |
| 272 | − gen_modrm(r, VT_LOCAL, sv->sym, fc); | |
| 268 | + o(S, 0x8d); /* lea xxx(%ebp), r */ | |
| 269 | + gen_modrm(S, r, VT_LOCAL, sv->sym, fc); | |
| 273 | 270 | } else { |
| 274 | − o(0x89); | |
| 275 | − o(0xe8 + r); /* mov %ebp, r */ | |
| 271 | + o(S, 0x89); | |
| 272 | + o(S, 0xe8 + r); /* mov %ebp, r */ | |
| 276 | 273 | } |
| 277 | 274 | } else if (v == VT_CMP) { |
| 278 | − o(0x0f); /* setxx %br */ | |
| 279 | − o(fc); | |
| 280 | − o(0xc0 + r); | |
| 281 | − o(0xc0b60f + r * 0x90000); /* movzbl %al, %eax */ | |
| 275 | + o(S, 0x0f); /* setxx %br */ | |
| 276 | + o(S, fc); | |
| 277 | + o(S, 0xc0 + r); | |
| 278 | + o(S, 0xc0b60f + r * 0x90000); /* movzbl %al, %eax */ | |
| 282 | 279 | } else if (v == VT_JMP || v == VT_JMPI) { |
| 283 | 280 | t = v & 1; |
| 284 | − oad(0xb8 + r, t); /* mov $1, r */ | |
| 285 | − o(0x05eb); /* jmp after */ | |
| 286 | − gsym(fc); | |
| 287 | − oad(0xb8 + r, t ^ 1); /* mov $0, r */ | |
| 281 | + oad(S, 0xb8 + r, t); /* mov $1, r */ | |
| 282 | + o(S, 0x05eb); /* jmp after */ | |
| 283 | + gsym(S, fc); | |
| 284 | + oad(S, 0xb8 + r, t ^ 1); /* mov $0, r */ | |
| 288 | 285 | } else if (v != r) { |
| 289 | − o(0x89); | |
| 290 | − o(0xc0 + r + v * 8); /* mov v, r */ | |
| 286 | + o(S, 0x89); | |
| 287 | + o(S, 0xc0 + r + v * 8); /* mov v, r */ | |
| 291 | 288 | } |
| 292 | 289 | } |
| 293 | 290 | } |
| 294 | 291 | |
| 295 | 292 | /* store register 'r' in lvalue 'v' */ |
| 296 | −ST_FUNC void store(int r, SValue *v) | |
| 293 | +ST_FUNC void store(TCCState* S, int r, SValue *v) | |
| 297 | 294 | { |
| 298 | 295 | int fr, bt, ft, fc; |
| 299 | 296 | |
| 300 | 297 | #ifdef TCC_TARGET_PE |
| 301 | 298 | SValue v2; |
| 302 | − v = pe_getimport(v, &v2); | |
| 299 | + v = pe_getimport(S, v, &v2); | |
| 303 | 300 | #endif |
| 304 | 301 | |
| 305 | 302 | ft = v->type.t; |
| @@ -309,66 +306,66 @@ ST_FUNC void store(int r, SValue *v) · 3 unmodified lines | ||
| 309 | 306 | bt = ft & VT_BTYPE; |
| 310 | 307 | /* XXX: incorrect if float reg to reg */ |
| 311 | 308 | if (bt == VT_FLOAT) { |
| 312 | − o(0xd9); /* fsts */ | |
| 309 | + o(S, 0xd9); /* fsts */ | |
| 313 | 310 | r = 2; |
| 314 | 311 | } else if (bt == VT_DOUBLE) { |
| 315 | − o(0xdd); /* fstpl */ | |
| 312 | + o(S, 0xdd); /* fstpl */ | |
| 316 | 313 | r = 2; |
| 317 | 314 | } else if (bt == VT_LDOUBLE) { |
| 318 | − o(0xc0d9); /* fld %st(0) */ | |
| 319 | − o(0xdb); /* fstpt */ | |
| 315 | + o(S, 0xc0d9); /* fld %st(0) */ | |
| 316 | + o(S, 0xdb); /* fstpt */ | |
| 320 | 317 | r = 7; |
| 321 | 318 | } else { |
| 322 | 319 | if (bt == VT_SHORT) |
| 323 | − o(0x66); | |
| 320 | + o(S, 0x66); | |
| 324 | 321 | if (bt == VT_BYTE || bt == VT_BOOL) |
| 325 | − o(0x88); | |
| 322 | + o(S, 0x88); | |
| 326 | 323 | else |
| 327 | − o(0x89); | |
| 324 | + o(S, 0x89); | |
| 328 | 325 | } |
| 329 | 326 | if (fr == VT_CONST || |
| 330 | 327 | fr == VT_LOCAL || |
| 331 | 328 | (v->r & VT_LVAL)) { |
| 332 | − gen_modrm(r, v->r, v->sym, fc); | |
| 329 | + gen_modrm(S, r, v->r, v->sym, fc); | |
| 333 | 330 | } else if (fr != r) { |
| 334 | − o(0xc0 + fr + r * 8); /* mov r, fr */ | |
| 331 | + o(S, 0xc0 + fr + r * 8); /* mov r, fr */ | |
| 335 | 332 | } |
| 336 | 333 | } |
| 337 | 334 | |
| 338 | −static void gadd_sp(int val) | |
| 335 | +static void gadd_sp(TCCState* S, int val) | |
| 339 | 336 | { |
| 340 | 337 | if (val == (char)val) { |
| 341 | − o(0xc483); | |
| 342 | − g(val); | |
| 338 | + o(S, 0xc483); | |
| 339 | + g(S, val); | |
| 343 | 340 | } else { |
| 344 | − oad(0xc481, val); /* add $xxx, %esp */ | |
| 341 | + oad(S, 0xc481, val); /* add $xxx, %esp */ | |
| 345 | 342 | } |
| 346 | 343 | } |
| 347 | 344 | |
| 348 | 345 | #if defined CONFIG_TCC_BCHECK || defined TCC_TARGET_PE |
| 349 | −static void gen_static_call(int v) | |
| 346 | +static void gen_static_call(TCCState* S, int v) | |
| 350 | 347 | { |
| 351 | 348 | Sym *sym; |
| 352 | 349 | |
| 353 | − sym = external_helper_sym(v); | |
| 354 | − oad(0xe8, -4); | |
| 355 | − greloc(cur_text_section, sym, ind-4, R_386_PC32); | |
| 350 | + sym = external_helper_sym(S, v); | |
| 351 | + oad(S, 0xe8, -4); | |
| 352 | + greloc(S, cur_text_section, sym, S->tccgen_ind-4, R_386_PC32); | |
| 356 | 353 | } |
| 357 | 354 | #endif |
| 358 | 355 | |
| 359 | 356 | /* 'is_jmp' is '1' if it is a jump */ |
| 360 | −static void gcall_or_jmp(int is_jmp) | |
| 357 | +static void gcall_or_jmp(TCCState* S, int is_jmp) | |
| 361 | 358 | { |
| 362 | 359 | int r; |
| 363 | − if ((vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST && (vtop->r & VT_SYM)) { | |
| 360 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST && (S->tccgen_vtop->r & VT_SYM)) { | |
| 364 | 361 | /* constant and relocation case */ |
| 365 | − greloc(cur_text_section, vtop->sym, ind + 1, R_386_PC32); | |
| 366 | − oad(0xe8 + is_jmp, vtop->c.i - 4); /* call/jmp im */ | |
| 362 | + greloc(S, cur_text_section, S->tccgen_vtop->sym, S->tccgen_ind + 1, R_386_PC32); | |
| 363 | + oad(S, 0xe8 + is_jmp, S->tccgen_vtop->c.i - 4); /* call/jmp im */ | |
| 367 | 364 | } else { |
| 368 | 365 | /* otherwise, indirect call */ |
| 369 | − r = gv(RC_INT); | |
| 370 | − o(0xff); /* call/jmp *r */ | |
| 371 | − o(0xd0 + r + (is_jmp << 4)); | |
| 366 | + r = gv(S, RC_INT); | |
| 367 | + o(S, 0xff); /* call/jmp *r */ | |
| 368 | + o(S, 0xd0 + r + (is_jmp << 4)); | |
| 372 | 369 | } |
| 373 | 370 | } |
| 374 | 371 | |
| @@ -405,75 +402,75 @@ ST_FUNC int gfunc_sret(CType *vt, int variadic, CType *ret, int *ret_align, int · 30 unmodified lines | ||
| 405 | 402 | /* Generate function call. The function address is pushed first, then |
| 406 | 403 | all the parameters in call order. This functions pops all the |
| 407 | 404 | parameters and the function address. */ |
| 408 | −ST_FUNC void gfunc_call(int nb_args) | |
| 405 | +ST_FUNC void gfunc_call(TCCState* S, int nb_args) | |
| 409 | 406 | { |
| 410 | 407 | int size, align, r, args_size, i, func_call; |
| 411 | 408 | Sym *func_sym; |
| 412 | 409 | |
| 413 | 410 | #ifdef CONFIG_TCC_BCHECK |
| 414 | − if (tcc_state->do_bounds_check) | |
| 415 | − gbound_args(nb_args); | |
| 411 | + if (S->do_bounds_check) | |
| 412 | + gbound_args(S, nb_args); | |
| 416 | 413 | #endif |
| 417 | 414 | |
| 418 | 415 | args_size = 0; |
| 419 | 416 | for(i = 0;i < nb_args; i++) { |
| 420 | − if ((vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 421 | − size = type_size(&vtop->type, &align); | |
| 417 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_STRUCT) { | |
| 418 | + size = type_size(&S->tccgen_vtop->type, &align); | |
| 422 | 419 | /* align to stack align size */ |
| 423 | 420 | size = (size + 3) & ~3; |
| 424 | 421 | /* allocate the necessary size on stack */ |
| 425 | 422 | #ifdef TCC_TARGET_PE |
| 426 | 423 | if (size >= 4096) { |
| 427 | − r = get_reg(RC_EAX); | |
| 428 | − oad(0x68, size); // push size | |
| 424 | + r = get_reg(S, RC_EAX); | |
| 425 | + oad(S, 0x68, size); // push size | |
| 429 | 426 | /* cannot call normal 'alloca' with bound checking */ |
| 430 | − gen_static_call(tok_alloc_const("__alloca")); | |
| 431 | − gadd_sp(4); | |
| 427 | + gen_static_call(S, tok_alloc_const(S, "__alloca")); | |
| 428 | + gadd_sp(S, 4); | |
| 432 | 429 | } else |
| 433 | 430 | #endif |
| 434 | 431 | { |
| 435 | − oad(0xec81, size); /* sub $xxx, %esp */ | |
| 432 | + oad(S, 0xec81, size); /* sub $xxx, %esp */ | |
| 436 | 433 | /* generate structure store */ |
| 437 | − r = get_reg(RC_INT); | |
| 438 | − o(0xe089 + (r << 8)); /* mov %esp, r */ | |
| 434 | + r = get_reg(S, RC_INT); | |
| 435 | + o(S, 0xe089 + (r << 8)); /* mov %esp, r */ | |
| 439 | 436 | } |
| 440 | − vset(&vtop->type, r | VT_LVAL, 0); | |
| 441 | − vswap(); | |
| 442 | − vstore(); | |
| 437 | + vset(S, &S->tccgen_vtop->type, r | VT_LVAL, 0); | |
| 438 | + vswap(S); | |
| 439 | + vstore(S); | |
| 443 | 440 | args_size += size; |
| 444 | − } else if (is_float(vtop->type.t)) { | |
| 445 | − gv(RC_FLOAT); /* only one float register */ | |
| 446 | − if ((vtop->type.t & VT_BTYPE) == VT_FLOAT) | |
| 441 | + } else if (is_float(S->tccgen_vtop->type.t)) { | |
| 442 | + gv(S, RC_FLOAT); /* only one float register */ | |
| 443 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_FLOAT) | |
| 447 | 444 | size = 4; |
| 448 | − else if ((vtop->type.t & VT_BTYPE) == VT_DOUBLE) | |
| 445 | + else if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_DOUBLE) | |
| 449 | 446 | size = 8; |
| 450 | 447 | else |
| 451 | 448 | size = 12; |
| 452 | − oad(0xec81, size); /* sub $xxx, %esp */ | |
| 449 | + oad(S, 0xec81, size); /* sub $xxx, %esp */ | |
| 453 | 450 | if (size == 12) |
| 454 | − o(0x7cdb); | |
| 451 | + o(S, 0x7cdb); | |
| 455 | 452 | else |
| 456 | − o(0x5cd9 + size - 4); /* fstp[s|l] 0(%esp) */ | |
| 457 | − g(0x24); | |
| 458 | − g(0x00); | |
| 453 | + o(S, 0x5cd9 + size - 4); /* fstp[s|l] 0(%esp) */ | |
| 454 | + g(S, 0x24); | |
| 455 | + g(S, 0x00); | |
| 459 | 456 | args_size += size; |
| 460 | 457 | } else { |
| 461 | 458 | /* simple type (currently always same size) */ |
| 462 | 459 | /* XXX: implicit cast ? */ |
| 463 | − r = gv(RC_INT); | |
| 464 | − if ((vtop->type.t & VT_BTYPE) == VT_LLONG) { | |
| 460 | + r = gv(S, RC_INT); | |
| 461 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LLONG) { | |
| 465 | 462 | size = 8; |
| 466 | − o(0x50 + vtop->r2); /* push r */ | |
| 463 | + o(S, 0x50 + S->tccgen_vtop->r2); /* push r */ | |
| 467 | 464 | } else { |
| 468 | 465 | size = 4; |
| 469 | 466 | } |
| 470 | − o(0x50 + r); /* push r */ | |
| 467 | + o(S, 0x50 + r); /* push r */ | |
| 471 | 468 | args_size += size; |
| 472 | 469 | } |
| 473 | − vtop--; | |
| 470 | + S->tccgen_vtop--; | |
| 474 | 471 | } |
| 475 | − save_regs(0); /* save used temporary registers */ | |
| 476 | − func_sym = vtop->type.ref; | |
| 472 | + save_regs(S, 0); /* save used temporary registers */ | |
| 473 | + func_sym = S->tccgen_vtop->type.ref; | |
| 477 | 474 | func_call = func_sym->f.func_call; |
| 478 | 475 | /* fast call case */ |
| 479 | 476 | if ((func_call >= FUNC_FASTCALL1 && func_call <= FUNC_FASTCALL3) || |
| @@ -490,21 +487,21 @@ ST_FUNC void gfunc_call(int nb_args) · 10 unmodified lines | ||
| 490 | 487 | for(i = 0;i < fastcall_nb_regs; i++) { |
| 491 | 488 | if (args_size <= 0) |
| 492 | 489 | break; |
| 493 | − o(0x58 + fastcall_regs_ptr[i]); /* pop r */ | |
| 490 | + o(S, 0x58 + fastcall_regs_ptr[i]); /* pop r */ | |
| 494 | 491 | /* XXX: incorrect for struct/floats */ |
| 495 | 492 | args_size -= 4; |
| 496 | 493 | } |
| 497 | 494 | } |
| 498 | 495 | #if !defined(TCC_TARGET_PE) && !TARGETOS_FreeBSD || TARGETOS_OpenBSD |
| 499 | − else if ((vtop->type.ref->type.t & VT_BTYPE) == VT_STRUCT) | |
| 496 | + else if ((S->tccgen_vtop->type.ref->type.t & VT_BTYPE) == VT_STRUCT) | |
| 500 | 497 | args_size -= 4; |
| 501 | 498 | #endif |
| 502 | 499 | |
| 503 | − gcall_or_jmp(0); | |
| 500 | + gcall_or_jmp(S, 0); | |
| 504 | 501 | |
| 505 | 502 | if (args_size && func_call != FUNC_STDCALL && func_call != FUNC_FASTCALLW) |
| 506 | − gadd_sp(args_size); | |
| 507 | − vtop--; | |
| 503 | + gadd_sp(S, args_size); | |
| 504 | + S->tccgen_vtop--; | |
| 508 | 505 | } |
| 509 | 506 | |
| 510 | 507 | #ifdef TCC_TARGET_PE |
| @@ -514,7 +511,7 @@ ST_FUNC void gfunc_call(int nb_args) · 3 unmodified lines | ||
| 514 | 511 | #endif |
| 515 | 512 | |
| 516 | 513 | /* generate function prolog of type 't' */ |
| 517 | −ST_FUNC void gfunc_prolog(Sym *func_sym) | |
| 514 | +ST_FUNC void gfunc_prolog(TCCState* S, Sym *func_sym) | |
| 518 | 515 | { |
| 519 | 516 | CType *func_type = &func_sym->type; |
| 520 | 517 | int addr, align, size, func_call, fastcall_nb_regs; |
| @@ -526,8 +523,8 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 5 unmodified lines | ||
| 526 | 523 | sym = func_type->ref; |
| 527 | 524 | func_call = sym->f.func_call; |
| 528 | 525 | addr = 8; |
| 529 | − loc = 0; | |
| 530 | − func_vc = 0; | |
| 526 | + S->tccgen_loc = 0; | |
| 527 | + S->tccgen_func_vc = 0; | |
| 531 | 528 | |
| 532 | 529 | if (func_call >= FUNC_FASTCALL1 && func_call <= FUNC_FASTCALL3) { |
| 533 | 530 | fastcall_nb_regs = func_call - FUNC_FASTCALL1 + 1; |
| @@ -541,19 +538,19 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 7 unmodified lines | ||
| 541 | 538 | } |
| 542 | 539 | param_index = 0; |
| 543 | 540 | |
| 544 | − ind += FUNC_PROLOG_SIZE; | |
| 545 | − func_sub_sp_offset = ind; | |
| 541 | + S->tccgen_ind += FUNC_PROLOG_SIZE; | |
| 542 | + func_sub_sp_offset = S->tccgen_ind; | |
| 546 | 543 | /* if the function returns a structure, then add an |
| 547 | 544 | implicit pointer parameter */ |
| 548 | 545 | #if defined(TCC_TARGET_PE) || TARGETOS_FreeBSD || TARGETOS_OpenBSD |
| 549 | − size = type_size(&func_vt,&align); | |
| 550 | − if (((func_vt.t & VT_BTYPE) == VT_STRUCT) | |
| 546 | + size = type_size(&S->tccgen_func_vt,&align); | |
| 547 | + if (((S->tccgen_func_vt.t & VT_BTYPE) == VT_STRUCT) | |
| 551 | 548 | && (size > 8 || (size & (size - 1)))) { |
| 552 | 549 | #else |
| 553 | − if ((func_vt.t & VT_BTYPE) == VT_STRUCT) { | |
| 550 | + if ((S->tccgen_func_vt.t & VT_BTYPE) == VT_STRUCT) { | |
| 554 | 551 | #endif |
| 555 | 552 | /* XXX: fastcall case ? */ |
| 556 | − func_vc = addr; | |
| 553 | + S->tccgen_func_vc = addr; | |
| 557 | 554 | addr += 4; |
| 558 | 555 | param_index++; |
| 559 | 556 | } |
| @@ -570,15 +567,15 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 10 unmodified lines | ||
| 570 | 567 | #endif |
| 571 | 568 | if (param_index < fastcall_nb_regs) { |
| 572 | 569 | /* save FASTCALL register */ |
| 573 | − loc -= 4; | |
| 574 | − o(0x89); /* movl */ | |
| 575 | − gen_modrm(fastcall_regs_ptr[param_index], VT_LOCAL, NULL, loc); | |
| 576 | − param_addr = loc; | |
| 570 | + S->tccgen_loc -= 4; | |
| 571 | + o(S, 0x89); /* movl */ | |
| 572 | + gen_modrm(S, fastcall_regs_ptr[param_index], VT_LOCAL, NULL, S->tccgen_loc); | |
| 573 | + param_addr = S->tccgen_loc; | |
| 577 | 574 | } else { |
| 578 | 575 | param_addr = addr; |
| 579 | 576 | addr += size; |
| 580 | 577 | } |
| 581 | − sym_push(sym->v & ~SYM_FIELD, type, | |
| 578 | + sym_push(S, sym->v & ~SYM_FIELD, type, | |
| 582 | 579 | VT_LOCAL | VT_LVAL, param_addr); |
| 583 | 580 | param_index++; |
| 584 | 581 | } |
| @@ -587,94 +584,94 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 2 unmodified lines | ||
| 587 | 584 | if (func_call == FUNC_STDCALL || func_call == FUNC_FASTCALLW) |
| 588 | 585 | func_ret_sub = addr - 8; |
| 589 | 586 | #if !defined(TCC_TARGET_PE) && !TARGETOS_FreeBSD || TARGETOS_OpenBSD |
| 590 | − else if (func_vc) | |
| 587 | + else if (S->tccgen_func_vc) | |
| 591 | 588 | func_ret_sub = 4; |
| 592 | 589 | #endif |
| 593 | 590 | |
| 594 | 591 | #ifdef CONFIG_TCC_BCHECK |
| 595 | − if (tcc_state->do_bounds_check) | |
| 596 | − gen_bounds_prolog(); | |
| 592 | + if (S->do_bounds_check) | |
| 593 | + gen_bounds_prolog(S); | |
| 597 | 594 | #endif |
| 598 | 595 | } |
| 599 | 596 | |
| 600 | 597 | /* generate function epilog */ |
| 601 | −ST_FUNC void gfunc_epilog(void) | |
| 598 | +ST_FUNC void gfunc_epilog(TCCState* S) | |
| 602 | 599 | { |
| 603 | 600 | addr_t v, saved_ind; |
| 604 | 601 | |
| 605 | 602 | #ifdef CONFIG_TCC_BCHECK |
| 606 | − if (tcc_state->do_bounds_check) | |
| 607 | − gen_bounds_epilog(); | |
| 603 | + if (S->do_bounds_check) | |
| 604 | + gen_bounds_epilog(S); | |
| 608 | 605 | #endif |
| 609 | 606 | |
| 610 | 607 | /* align local size to word & save local variables */ |
| 611 | − v = (-loc + 3) & -4; | |
| 608 | + v = (-S->tccgen_loc + 3) & -4; | |
| 612 | 609 | |
| 613 | 610 | #if USE_EBX |
| 614 | − o(0x8b); | |
| 615 | − gen_modrm(TREG_EBX, VT_LOCAL, NULL, -(v+4)); | |
| 611 | + o(S, 0x8b); | |
| 612 | + gen_modrm(S, TREG_EBX, VT_LOCAL, NULL, -(v+4)); | |
| 616 | 613 | #endif |
| 617 | 614 | |
| 618 | − o(0xc9); /* leave */ | |
| 615 | + o(S, 0xc9); /* leave */ | |
| 619 | 616 | if (func_ret_sub == 0) { |
| 620 | − o(0xc3); /* ret */ | |
| 617 | + o(S, 0xc3); /* ret */ | |
| 621 | 618 | } else { |
| 622 | − o(0xc2); /* ret n */ | |
| 623 | − g(func_ret_sub); | |
| 624 | − g(func_ret_sub >> 8); | |
| 619 | + o(S, 0xc2); /* ret n */ | |
| 620 | + g(S, func_ret_sub); | |
| 621 | + g(S, func_ret_sub >> 8); | |
| 625 | 622 | } |
| 626 | − saved_ind = ind; | |
| 627 | − ind = func_sub_sp_offset - FUNC_PROLOG_SIZE; | |
| 623 | + saved_ind = S->tccgen_ind; | |
| 624 | + S->tccgen_ind = func_sub_sp_offset - FUNC_PROLOG_SIZE; | |
| 628 | 625 | #ifdef TCC_TARGET_PE |
| 629 | 626 | if (v >= 4096) { |
| 630 | − oad(0xb8, v); /* mov stacksize, %eax */ | |
| 631 | − gen_static_call(TOK___chkstk); /* call __chkstk, (does the stackframe too) */ | |
| 627 | + oad(S, 0xb8, v); /* mov stacksize, %eax */ | |
| 628 | + gen_static_call(S, TOK___chkstk); /* call __chkstk, (does the stackframe too) */ | |
| 632 | 629 | } else |
| 633 | 630 | #endif |
| 634 | 631 | { |
| 635 | − o(0xe58955); /* push %ebp, mov %esp, %ebp */ | |
| 636 | − o(0xec81); /* sub esp, stacksize */ | |
| 637 | − gen_le32(v); | |
| 632 | + o(S, 0xe58955); /* push %ebp, mov %esp, %ebp */ | |
| 633 | + o(S, 0xec81); /* sub esp, stacksize */ | |
| 634 | + gen_le32(S, v); | |
| 638 | 635 | #ifdef TCC_TARGET_PE |
| 639 | − o(0x90); /* adjust to FUNC_PROLOG_SIZE */ | |
| 636 | + o(S, 0x90); /* adjust to FUNC_PROLOG_SIZE */ | |
| 640 | 637 | #endif |
| 641 | 638 | } |
| 642 | − o(0x53 * USE_EBX); /* push ebx */ | |
| 643 | − ind = saved_ind; | |
| 639 | + o(S, 0x53 * USE_EBX); /* push ebx */ | |
| 640 | + S->tccgen_ind = saved_ind; | |
| 644 | 641 | } |
| 645 | 642 | |
| 646 | 643 | /* generate a jump to a label */ |
| 647 | −ST_FUNC int gjmp(int t) | |
| 644 | +ST_FUNC int gjmp(TCCState* S, int t) | |
| 648 | 645 | { |
| 649 | − return gjmp2(0xe9, t); | |
| 646 | + return gjmp2(S, 0xe9, t); | |
| 650 | 647 | } |
| 651 | 648 | |
| 652 | 649 | /* generate a jump to a fixed address */ |
| 653 | −ST_FUNC void gjmp_addr(int a) | |
| 650 | +ST_FUNC void gjmp_addr(TCCState* S, int a) | |
| 654 | 651 | { |
| 655 | 652 | int r; |
| 656 | − r = a - ind - 2; | |
| 653 | + r = a - S->tccgen_ind - 2; | |
| 657 | 654 | if (r == (char)r) { |
| 658 | − g(0xeb); | |
| 659 | − g(r); | |
| 655 | + g(S, 0xeb); | |
| 656 | + g(S, r); | |
| 660 | 657 | } else { |
| 661 | − oad(0xe9, a - ind - 5); | |
| 658 | + oad(S, 0xe9, a - S->tccgen_ind - 5); | |
| 662 | 659 | } |
| 663 | 660 | } |
| 664 | 661 | |
| 665 | 662 | #if 0 |
| 666 | 663 | /* generate a jump to a fixed address */ |
| 667 | −ST_FUNC void gjmp_cond_addr(int a, int op) | |
| 664 | +ST_FUNC void gjmp_cond_addr(TCCState* S, int a, int op) | |
| 668 | 665 | { |
| 669 | − int r = a - ind - 2; | |
| 666 | + int r = a - S->tccgen_ind - 2; | |
| 670 | 667 | if (r == (char)r) |
| 671 | − g(op - 32), g(r); | |
| 668 | + g(S, op - 32), g(r); | |
| 672 | 669 | else |
| 673 | − g(0x0f), gjmp2(op - 16, r - 4); | |
| 670 | + g(S, 0x0f), gjmp2(S, op - 16, r - 4); | |
| 674 | 671 | } |
| 675 | 672 | #endif |
| 676 | 673 | |
| 677 | −ST_FUNC int gjmp_append(int n, int t) | |
| 674 | +ST_FUNC int gjmp_append(TCCState* S, int n, int t) | |
| 678 | 675 | { |
| 679 | 676 | void *p; |
| 680 | 677 | /* insert vtop->c jump list in t */ |
| @@ -688,14 +685,14 @@ ST_FUNC int gjmp_append(int n, int t) · 7 unmodified lines | ||
| 688 | 685 | return t; |
| 689 | 686 | } |
| 690 | 687 | |
| 691 | −ST_FUNC int gjmp_cond(int op, int t) | |
| 688 | +ST_FUNC int gjmp_cond(TCCState* S, int op, int t) | |
| 692 | 689 | { |
| 693 | − g(0x0f); | |
| 694 | − t = gjmp2(op - 16, t); | |
| 690 | + g(S, 0x0f); | |
| 691 | + t = gjmp2(S, op - 16, t); | |
| 695 | 692 | return t; |
| 696 | 693 | } |
| 697 | 694 | |
| 698 | −ST_FUNC void gen_opi(int op) | |
| 695 | +ST_FUNC void gen_opi(TCCState* S, int op) | |
| 699 | 696 | { |
| 700 | 697 | int r, fr, opc, c; |
| 701 | 698 | |
| @@ -704,36 +701,36 @@ ST_FUNC void gen_opi(int op) · 2 unmodified lines | ||
| 704 | 701 | case TOK_ADDC1: /* add with carry generation */ |
| 705 | 702 | opc = 0; |
| 706 | 703 | gen_op8: |
| 707 | − if ((vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 704 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 708 | 705 | /* constant case */ |
| 709 | − vswap(); | |
| 710 | − r = gv(RC_INT); | |
| 711 | − vswap(); | |
| 712 | − c = vtop->c.i; | |
| 706 | + vswap(S); | |
| 707 | + r = gv(S, RC_INT); | |
| 708 | + vswap(S); | |
| 709 | + c = S->tccgen_vtop->c.i; | |
| 713 | 710 | if (c == (char)c) { |
| 714 | 711 | /* generate inc and dec for smaller code */ |
| 715 | 712 | if ((c == 1 || c == -1) && (op == '+' || op == '-')) { |
| 716 | 713 | opc = (c == 1) ^ (op == '+'); |
| 717 | − o (0x40 | (opc << 3) | r); // inc,dec | |
| 714 | + o(S, 0x40 | (opc << 3) | r); // inc,dec | |
| 718 | 715 | } else { |
| 719 | − o(0x83); | |
| 720 | − o(0xc0 | (opc << 3) | r); | |
| 721 | − g(c); | |
| 716 | + o(S, 0x83); | |
| 717 | + o(S, 0xc0 | (opc << 3) | r); | |
| 718 | + g(S, c); | |
| 722 | 719 | } |
| 723 | 720 | } else { |
| 724 | − o(0x81); | |
| 725 | − oad(0xc0 | (opc << 3) | r, c); | |
| 721 | + o(S, 0x81); | |
| 722 | + oad(S, 0xc0 | (opc << 3) | r, c); | |
| 726 | 723 | } |
| 727 | 724 | } else { |
| 728 | − gv2(RC_INT, RC_INT); | |
| 729 | − r = vtop[-1].r; | |
| 730 | − fr = vtop[0].r; | |
| 731 | − o((opc << 3) | 0x01); | |
| 732 | − o(0xc0 + r + fr * 8); | |
| 725 | + gv2(S, RC_INT, RC_INT); | |
| 726 | + r = S->tccgen_vtop[-1].r; | |
| 727 | + fr = S->tccgen_vtop[0].r; | |
| 728 | + o(S, (opc << 3) | 0x01); | |
| 729 | + o(S, 0xc0 + r + fr * 8); | |
| 733 | 730 | } |
| 734 | − vtop--; | |
| 731 | + S->tccgen_vtop--; | |
| 735 | 732 | if (op >= TOK_ULT && op <= TOK_GT) |
| 736 | − vset_VT_CMP(op); | |
| 733 | + vset_VT_CMP(S, op); | |
| 737 | 734 | break; |
| 738 | 735 | case '-': |
| 739 | 736 | case TOK_SUBC1: /* sub with carry generation */ |
| @@ -755,12 +752,12 @@ ST_FUNC void gen_opi(int op) · 15 unmodified lines | ||
| 755 | 752 | opc = 1; |
| 756 | 753 | goto gen_op8; |
| 757 | 754 | case '*': |
| 758 | − gv2(RC_INT, RC_INT); | |
| 759 | − r = vtop[-1].r; | |
| 760 | − fr = vtop[0].r; | |
| 761 | − vtop--; | |
| 762 | − o(0xaf0f); /* imul fr, r */ | |
| 763 | − o(0xc0 + fr + r * 8); | |
| 755 | + gv2(S, RC_INT, RC_INT); | |
| 756 | + r = S->tccgen_vtop[-1].r; | |
| 757 | + fr = S->tccgen_vtop[0].r; | |
| 758 | + S->tccgen_vtop--; | |
| 759 | + o(S, 0xaf0f); /* imul fr, r */ | |
| 760 | + o(S, 0xc0 + fr + r * 8); | |
| 764 | 761 | break; |
| 765 | 762 | case TOK_SHL: |
| 766 | 763 | opc = 4; |
| @@ -772,23 +769,23 @@ ST_FUNC void gen_opi(int op) · 5 unmodified lines | ||
| 772 | 769 | opc = 7; |
| 773 | 770 | gen_shift: |
| 774 | 771 | opc = 0xc0 | (opc << 3); |
| 775 | − if ((vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 772 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 776 | 773 | /* constant case */ |
| 777 | − vswap(); | |
| 778 | − r = gv(RC_INT); | |
| 779 | − vswap(); | |
| 780 | − c = vtop->c.i & 0x1f; | |
| 781 | − o(0xc1); /* shl/shr/sar $xxx, r */ | |
| 782 | − o(opc | r); | |
| 783 | − g(c); | |
| 774 | + vswap(S); | |
| 775 | + r = gv(S, RC_INT); | |
| 776 | + vswap(S); | |
| 777 | + c = S->tccgen_vtop->c.i & 0x1f; | |
| 778 | + o(S, 0xc1); /* shl/shr/sar $xxx, r */ | |
| 779 | + o(S, opc | r); | |
| 780 | + g(S, c); | |
| 784 | 781 | } else { |
| 785 | 782 | /* we generate the shift in ecx */ |
| 786 | − gv2(RC_INT, RC_ECX); | |
| 787 | − r = vtop[-1].r; | |
| 788 | − o(0xd3); /* shl/shr/sar %cl, r */ | |
| 789 | − o(opc | r); | |
| 783 | + gv2(S, RC_INT, RC_ECX); | |
| 784 | + r = S->tccgen_vtop[-1].r; | |
| 785 | + o(S, 0xd3); /* shl/shr/sar %cl, r */ | |
| 786 | + o(S, opc | r); | |
| 790 | 787 | } |
| 791 | − vtop--; | |
| 788 | + S->tccgen_vtop--; | |
| 792 | 789 | break; |
| 793 | 790 | case '/': |
| 794 | 791 | case TOK_UDIV: |
| @@ -798,32 +795,32 @@ ST_FUNC void gen_opi(int op) · 3 unmodified lines | ||
| 798 | 795 | case TOK_UMULL: |
| 799 | 796 | /* first operand must be in eax */ |
| 800 | 797 | /* XXX: need better constraint for second operand */ |
| 801 | − gv2(RC_EAX, RC_ECX); | |
| 802 | − r = vtop[-1].r; | |
| 803 | − fr = vtop[0].r; | |
| 804 | − vtop--; | |
| 805 | − save_reg(TREG_EDX); | |
| 798 | + gv2(S, RC_EAX, RC_ECX); | |
| 799 | + r = S->tccgen_vtop[-1].r; | |
| 800 | + fr = S->tccgen_vtop[0].r; | |
| 801 | + S->tccgen_vtop--; | |
| 802 | + save_reg(S, TREG_EDX); | |
| 806 | 803 | /* save EAX too if used otherwise */ |
| 807 | − save_reg_upstack(TREG_EAX, 1); | |
| 804 | + save_reg_upstack(S, TREG_EAX, 1); | |
| 808 | 805 | if (op == TOK_UMULL) { |
| 809 | − o(0xf7); /* mul fr */ | |
| 810 | − o(0xe0 + fr); | |
| 811 | − vtop->r2 = TREG_EDX; | |
| 806 | + o(S, 0xf7); /* mul fr */ | |
| 807 | + o(S, 0xe0 + fr); | |
| 808 | + S->tccgen_vtop->r2 = TREG_EDX; | |
| 812 | 809 | r = TREG_EAX; |
| 813 | 810 | } else { |
| 814 | 811 | if (op == TOK_UDIV || op == TOK_UMOD) { |
| 815 | − o(0xf7d231); /* xor %edx, %edx, div fr, %eax */ | |
| 816 | − o(0xf0 + fr); | |
| 812 | + o(S, 0xf7d231); /* xor %edx, %edx, div fr, %eax */ | |
| 813 | + o(S, 0xf0 + fr); | |
| 817 | 814 | } else { |
| 818 | − o(0xf799); /* cltd, idiv fr, %eax */ | |
| 819 | − o(0xf8 + fr); | |
| 815 | + o(S, 0xf799); /* cltd, idiv fr, %eax */ | |
| 816 | + o(S, 0xf8 + fr); | |
| 820 | 817 | } |
| 821 | 818 | if (op == '%' || op == TOK_UMOD) |
| 822 | 819 | r = TREG_EDX; |
| 823 | 820 | else |
| 824 | 821 | r = TREG_EAX; |
| 825 | 822 | } |
| 826 | − vtop->r = r; | |
| 823 | + S->tccgen_vtop->r = r; | |
| 827 | 824 | break; |
| 828 | 825 | default: |
| 829 | 826 | opc = 7; |
| @@ -834,74 +831,74 @@ ST_FUNC void gen_opi(int op) · 4 unmodified lines | ||
| 834 | 831 | /* generate a floating point operation 'v = t1 op t2' instruction. The |
| 835 | 832 | two operands are guaranteed to have the same floating point type */ |
| 836 | 833 | /* XXX: need to use ST1 too */ |
| 837 | −ST_FUNC void gen_opf(int op) | |
| 834 | +ST_FUNC void gen_opf(TCCState* S, int op) | |
| 838 | 835 | { |
| 839 | 836 | int a, ft, fc, swapped, r; |
| 840 | 837 | |
| 841 | 838 | if (op == TOK_NEG) { /* unary minus */ |
| 842 | − gv(RC_FLOAT); | |
| 843 | − o(0xe0d9); /* fchs */ | |
| 839 | + gv(S, RC_FLOAT); | |
| 840 | + o(S, 0xe0d9); /* fchs */ | |
| 844 | 841 | return; |
| 845 | 842 | } |
| 846 | 843 | |
| 847 | 844 | /* convert constants to memory references */ |
| 848 | − if ((vtop[-1].r & (VT_VALMASK | VT_LVAL)) == VT_CONST) { | |
| 849 | − vswap(); | |
| 850 | − gv(RC_FLOAT); | |
| 851 | − vswap(); | |
| 845 | + if ((S->tccgen_vtop[-1].r & (VT_VALMASK | VT_LVAL)) == VT_CONST) { | |
| 846 | + vswap(S); | |
| 847 | + gv(S, RC_FLOAT); | |
| 848 | + vswap(S); | |
| 852 | 849 | } |
| 853 | − if ((vtop[0].r & (VT_VALMASK | VT_LVAL)) == VT_CONST) | |
| 854 | − gv(RC_FLOAT); | |
| 850 | + if ((S->tccgen_vtop[0].r & (VT_VALMASK | VT_LVAL)) == VT_CONST) | |
| 851 | + gv(S, RC_FLOAT); | |
| 855 | 852 | |
| 856 | 853 | /* must put at least one value in the floating point register */ |
| 857 | − if ((vtop[-1].r & VT_LVAL) && | |
| 858 | − (vtop[0].r & VT_LVAL)) { | |
| 859 | − vswap(); | |
| 860 | − gv(RC_FLOAT); | |
| 861 | − vswap(); | |
| 854 | + if ((S->tccgen_vtop[-1].r & VT_LVAL) && | |
| 855 | + (S->tccgen_vtop[0].r & VT_LVAL)) { | |
| 856 | + vswap(S); | |
| 857 | + gv(S, RC_FLOAT); | |
| 858 | + vswap(S); | |
| 862 | 859 | } |
| 863 | 860 | swapped = 0; |
| 864 | 861 | /* swap the stack if needed so that t1 is the register and t2 is |
| 865 | 862 | the memory reference */ |
| 866 | − if (vtop[-1].r & VT_LVAL) { | |
| 867 | − vswap(); | |
| 863 | + if (S->tccgen_vtop[-1].r & VT_LVAL) { | |
| 864 | + vswap(S); | |
| 868 | 865 | swapped = 1; |
| 869 | 866 | } |
| 870 | 867 | if (op >= TOK_ULT && op <= TOK_GT) { |
| 871 | 868 | /* load on stack second operand */ |
| 872 | − load(TREG_ST0, vtop); | |
| 873 | − save_reg(TREG_EAX); /* eax is used by FP comparison code */ | |
| 869 | + load(S, TREG_ST0, S->tccgen_vtop); | |
| 870 | + save_reg(S, TREG_EAX); /* eax is used by FP comparison code */ | |
| 874 | 871 | if (op == TOK_GE || op == TOK_GT) |
| 875 | 872 | swapped = !swapped; |
| 876 | 873 | else if (op == TOK_EQ || op == TOK_NE) |
| 877 | 874 | swapped = 0; |
| 878 | 875 | if (swapped) |
| 879 | − o(0xc9d9); /* fxch %st(1) */ | |
| 876 | + o(S, 0xc9d9); /* fxch %st(1) */ | |
| 880 | 877 | if (op == TOK_EQ || op == TOK_NE) |
| 881 | − o(0xe9da); /* fucompp */ | |
| 878 | + o(S, 0xe9da); /* fucompp */ | |
| 882 | 879 | else |
| 883 | − o(0xd9de); /* fcompp */ | |
| 884 | − o(0xe0df); /* fnstsw %ax */ | |
| 880 | + o(S, 0xd9de); /* fcompp */ | |
| 881 | + o(S, 0xe0df); /* fnstsw %ax */ | |
| 885 | 882 | if (op == TOK_EQ) { |
| 886 | − o(0x45e480); /* and $0x45, %ah */ | |
| 887 | − o(0x40fC80); /* cmp $0x40, %ah */ | |
| 883 | + o(S, 0x45e480); /* and $0x45, %ah */ | |
| 884 | + o(S, 0x40fC80); /* cmp $0x40, %ah */ | |
| 888 | 885 | } else if (op == TOK_NE) { |
| 889 | − o(0x45e480); /* and $0x45, %ah */ | |
| 890 | − o(0x40f480); /* xor $0x40, %ah */ | |
| 886 | + o(S, 0x45e480); /* and $0x45, %ah */ | |
| 887 | + o(S, 0x40f480); /* xor $0x40, %ah */ | |
| 891 | 888 | op = TOK_NE; |
| 892 | 889 | } else if (op == TOK_GE || op == TOK_LE) { |
| 893 | − o(0x05c4f6); /* test $0x05, %ah */ | |
| 890 | + o(S, 0x05c4f6); /* test $0x05, %ah */ | |
| 894 | 891 | op = TOK_EQ; |
| 895 | 892 | } else { |
| 896 | − o(0x45c4f6); /* test $0x45, %ah */ | |
| 893 | + o(S, 0x45c4f6); /* test $0x45, %ah */ | |
| 897 | 894 | op = TOK_EQ; |
| 898 | 895 | } |
| 899 | − vtop--; | |
| 900 | − vset_VT_CMP(op); | |
| 896 | + S->tccgen_vtop--; | |
| 897 | + vset_VT_CMP(S, op); | |
| 901 | 898 | } else { |
| 902 | 899 | /* no memory reference possible for long double operations */ |
| 903 | − if ((vtop->type.t & VT_BTYPE) == VT_LDOUBLE) { | |
| 904 | − load(TREG_ST0, vtop); | |
| 900 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LDOUBLE) { | |
| 901 | + load(S, TREG_ST0, S->tccgen_vtop); | |
| 905 | 902 | swapped = !swapped; |
| 906 | 903 | } |
| 907 | 904 | |
| @@ -924,213 +921,213 @@ ST_FUNC void gen_opf(int op) · 16 unmodified lines | ||
| 924 | 921 | a++; |
| 925 | 922 | break; |
| 926 | 923 | } |
| 927 | − ft = vtop->type.t; | |
| 928 | − fc = vtop->c.i; | |
| 924 | + ft = S->tccgen_vtop->type.t; | |
| 925 | + fc = S->tccgen_vtop->c.i; | |
| 929 | 926 | if ((ft & VT_BTYPE) == VT_LDOUBLE) { |
| 930 | − o(0xde); /* fxxxp %st, %st(1) */ | |
| 931 | − o(0xc1 + (a << 3)); | |
| 927 | + o(S, 0xde); /* fxxxp %st, %st(1) */ | |
| 928 | + o(S, 0xc1 + (a << 3)); | |
| 932 | 929 | } else { |
| 933 | 930 | /* if saved lvalue, then we must reload it */ |
| 934 | − r = vtop->r; | |
| 931 | + r = S->tccgen_vtop->r; | |
| 935 | 932 | if ((r & VT_VALMASK) == VT_LLOCAL) { |
| 936 | 933 | SValue v1; |
| 937 | − r = get_reg(RC_INT); | |
| 934 | + r = get_reg(S, RC_INT); | |
| 938 | 935 | v1.type.t = VT_INT; |
| 939 | 936 | v1.r = VT_LOCAL | VT_LVAL; |
| 940 | 937 | v1.c.i = fc; |
| 941 | 938 | v1.sym = NULL; |
| 942 | − load(r, &v1); | |
| 939 | + load(S, r, &v1); | |
| 943 | 940 | fc = 0; |
| 944 | 941 | } |
| 945 | 942 | |
| 946 | 943 | if ((ft & VT_BTYPE) == VT_DOUBLE) |
| 947 | − o(0xdc); | |
| 944 | + o(S, 0xdc); | |
| 948 | 945 | else |
| 949 | − o(0xd8); | |
| 950 | − gen_modrm(a, r, vtop->sym, fc); | |
| 946 | + o(S, 0xd8); | |
| 947 | + gen_modrm(S, a, r, S->tccgen_vtop->sym, fc); | |
| 951 | 948 | } |
| 952 | − vtop--; | |
| 949 | + S->tccgen_vtop--; | |
| 953 | 950 | } |
| 954 | 951 | } |
| 955 | 952 | |
| 956 | 953 | /* convert integers to fp 't' type. Must handle 'int', 'unsigned int' |
| 957 | 954 | and 'long long' cases. */ |
| 958 | −ST_FUNC void gen_cvt_itof(int t) | |
| 955 | +ST_FUNC void gen_cvt_itof(TCCState* S, int t) | |
| 959 | 956 | { |
| 960 | − save_reg(TREG_ST0); | |
| 961 | − gv(RC_INT); | |
| 962 | − if ((vtop->type.t & VT_BTYPE) == VT_LLONG) { | |
| 957 | + save_reg(S, TREG_ST0); | |
| 958 | + gv(S, RC_INT); | |
| 959 | + if ((S->tccgen_vtop->type.t & VT_BTYPE) == VT_LLONG) { | |
| 963 | 960 | /* signed long long to float/double/long double (unsigned case |
| 964 | 961 | is handled generically) */ |
| 965 | − o(0x50 + vtop->r2); /* push r2 */ | |
| 966 | − o(0x50 + (vtop->r & VT_VALMASK)); /* push r */ | |
| 967 | − o(0x242cdf); /* fildll (%esp) */ | |
| 968 | − o(0x08c483); /* add $8, %esp */ | |
| 969 | − vtop->r2 = VT_CONST; | |
| 970 | − } else if ((vtop->type.t & (VT_BTYPE | VT_UNSIGNED)) == | |
| 962 | + o(S, 0x50 + S->tccgen_vtop->r2); /* push r2 */ | |
| 963 | + o(S, 0x50 + (S->tccgen_vtop->r & VT_VALMASK)); /* push r */ | |
| 964 | + o(S, 0x242cdf); /* fildll (%esp) */ | |
| 965 | + o(S, 0x08c483); /* add $8, %esp */ | |
| 966 | + S->tccgen_vtop->r2 = VT_CONST; | |
| 967 | + } else if ((S->tccgen_vtop->type.t & (VT_BTYPE | VT_UNSIGNED)) == | |
| 971 | 968 | (VT_INT | VT_UNSIGNED)) { |
| 972 | 969 | /* unsigned int to float/double/long double */ |
| 973 | − o(0x6a); /* push $0 */ | |
| 974 | − g(0x00); | |
| 975 | − o(0x50 + (vtop->r & VT_VALMASK)); /* push r */ | |
| 976 | − o(0x242cdf); /* fildll (%esp) */ | |
| 977 | − o(0x08c483); /* add $8, %esp */ | |
| 970 | + o(S, 0x6a); /* push $0 */ | |
| 971 | + g(S, 0x00); | |
| 972 | + o(S, 0x50 + (S->tccgen_vtop->r & VT_VALMASK)); /* push r */ | |
| 973 | + o(S, 0x242cdf); /* fildll (%esp) */ | |
| 974 | + o(S, 0x08c483); /* add $8, %esp */ | |
| 978 | 975 | } else { |
| 979 | 976 | /* int to float/double/long double */ |
| 980 | − o(0x50 + (vtop->r & VT_VALMASK)); /* push r */ | |
| 981 | − o(0x2404db); /* fildl (%esp) */ | |
| 982 | − o(0x04c483); /* add $4, %esp */ | |
| 977 | + o(S, 0x50 + (S->tccgen_vtop->r & VT_VALMASK)); /* push r */ | |
| 978 | + o(S, 0x2404db); /* fildl (%esp) */ | |
| 979 | + o(S, 0x04c483); /* add $4, %esp */ | |
| 983 | 980 | } |
| 984 | − vtop->r2 = VT_CONST; | |
| 985 | − vtop->r = TREG_ST0; | |
| 981 | + S->tccgen_vtop->r2 = VT_CONST; | |
| 982 | + S->tccgen_vtop->r = TREG_ST0; | |
| 986 | 983 | } |
| 987 | 984 | |
| 988 | 985 | /* convert fp to int 't' type */ |
| 989 | −ST_FUNC void gen_cvt_ftoi(int t) | |
| 986 | +ST_FUNC void gen_cvt_ftoi(TCCState* S, int t) | |
| 990 | 987 | { |
| 991 | − int bt = vtop->type.t & VT_BTYPE; | |
| 988 | + int bt = S->tccgen_vtop->type.t & VT_BTYPE; | |
| 992 | 989 | if (bt == VT_FLOAT) |
| 993 | − vpush_helper_func(TOK___fixsfdi); | |
| 990 | + vpush_helper_func(S, TOK___fixsfdi); | |
| 994 | 991 | else if (bt == VT_LDOUBLE) |
| 995 | − vpush_helper_func(TOK___fixxfdi); | |
| 992 | + vpush_helper_func(S, TOK___fixxfdi); | |
| 996 | 993 | else |
| 997 | − vpush_helper_func(TOK___fixdfdi); | |
| 998 | − vswap(); | |
| 999 | − gfunc_call(1); | |
| 1000 | − vpushi(0); | |
| 1001 | − vtop->r = REG_IRET; | |
| 994 | + vpush_helper_func(S, TOK___fixdfdi); | |
| 995 | + vswap(S); | |
| 996 | + gfunc_call(S, 1); | |
| 997 | + vpushi(S, 0); | |
| 998 | + S->tccgen_vtop->r = REG_IRET; | |
| 1002 | 999 | if ((t & VT_BTYPE) == VT_LLONG) |
| 1003 | − vtop->r2 = REG_IRE2; | |
| 1000 | + S->tccgen_vtop->r2 = REG_IRE2; | |
| 1004 | 1001 | } |
| 1005 | 1002 | |
| 1006 | 1003 | /* convert from one floating point type to another */ |
| 1007 | −ST_FUNC void gen_cvt_ftof(int t) | |
| 1004 | +ST_FUNC void gen_cvt_ftof(TCCState* S, int t) | |
| 1008 | 1005 | { |
| 1009 | 1006 | /* all we have to do on i386 is to put the float in a register */ |
| 1010 | − gv(RC_FLOAT); | |
| 1007 | + gv(S, RC_FLOAT); | |
| 1011 | 1008 | } |
| 1012 | 1009 | |
| 1013 | 1010 | /* char/short to int conversion */ |
| 1014 | −ST_FUNC void gen_cvt_csti(int t) | |
| 1011 | +ST_FUNC void gen_cvt_csti(TCCState* S, int t) | |
| 1015 | 1012 | { |
| 1016 | 1013 | int r, sz, xl; |
| 1017 | − r = gv(RC_INT); | |
| 1014 | + r = gv(S, RC_INT); | |
| 1018 | 1015 | sz = !(t & VT_UNSIGNED); |
| 1019 | 1016 | xl = (t & VT_BTYPE) == VT_SHORT; |
| 1020 | − o(0xc0b60f /* mov[sz] %a[xl], %eax */ | |
| 1017 | + o(S, 0xc0b60f /* mov[sz] %a[xl], %eax */ | |
| 1021 | 1018 | | (sz << 3 | xl) << 8 |
| 1022 | 1019 | | (r << 3 | r) << 16 |
| 1023 | 1020 | ); |
| 1024 | 1021 | } |
| 1025 | 1022 | |
| 1026 | 1023 | /* increment tcov counter */ |
| 1027 | −ST_FUNC void gen_increment_tcov (SValue *sv) | |
| 1024 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv) | |
| 1028 | 1025 | { |
| 1029 | − o(0x0583); /* addl $1, xxx */ | |
| 1030 | − greloc(cur_text_section, sv->sym, ind, R_386_32); | |
| 1031 | − gen_le32(0); | |
| 1032 | − o(1); | |
| 1033 | − o(0x1583); /* addcl $0, xxx */ | |
| 1034 | − greloc(cur_text_section, sv->sym, ind, R_386_32); | |
| 1035 | − gen_le32(4); | |
| 1036 | − g(0); | |
| 1026 | + o(S, 0x0583); /* addl $1, xxx */ | |
| 1027 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind, R_386_32); | |
| 1028 | + gen_le32(S, 0); | |
| 1029 | + o(S, 1); | |
| 1030 | + o(S, 0x1583); /* addcl $0, xxx */ | |
| 1031 | + greloc(S, cur_text_section, sv->sym, S->tccgen_ind, R_386_32); | |
| 1032 | + gen_le32(S, 4); | |
| 1033 | + g(S, 0); | |
| 1037 | 1034 | } |
| 1038 | 1035 | |
| 1039 | 1036 | /* computed goto support */ |
| 1040 | −ST_FUNC void ggoto(void) | |
| 1037 | +ST_FUNC void ggoto(TCCState* S) | |
| 1041 | 1038 | { |
| 1042 | − gcall_or_jmp(1); | |
| 1043 | − vtop--; | |
| 1039 | + gcall_or_jmp(S, 1); | |
| 1040 | + S->tccgen_vtop--; | |
| 1044 | 1041 | } |
| 1045 | 1042 | |
| 1046 | 1043 | /* bound check support functions */ |
| 1047 | 1044 | #ifdef CONFIG_TCC_BCHECK |
| 1048 | 1045 | |
| 1049 | −static void gen_bounds_prolog(void) | |
| 1046 | +static void gen_bounds_prolog(TCCState* S) | |
| 1050 | 1047 | { |
| 1051 | 1048 | /* leave some room for bound checking code */ |
| 1052 | − func_bound_offset = lbounds_section->data_offset; | |
| 1053 | − func_bound_ind = ind; | |
| 1054 | − func_bound_add_epilog = 0; | |
| 1055 | − oad(0xb8, 0); /* lbound section pointer */ | |
| 1056 | − oad(0xb8, 0); /* call to function */ | |
| 1049 | + S->func_bound_offset = lbounds_section->data_offset; | |
| 1050 | + S->func_bound_ind = S->tccgen_ind; | |
| 1051 | + S->func_bound_add_epilog = 0; | |
| 1052 | + oad(S, 0xb8, 0); /* lbound section pointer */ | |
| 1053 | + oad(S, 0xb8, 0); /* call to function */ | |
| 1057 | 1054 | } |
| 1058 | 1055 | |
| 1059 | −static void gen_bounds_epilog(void) | |
| 1056 | +static void gen_bounds_epilog(TCCState* S) | |
| 1060 | 1057 | { |
| 1061 | 1058 | addr_t saved_ind; |
| 1062 | 1059 | addr_t *bounds_ptr; |
| 1063 | 1060 | Sym *sym_data; |
| 1064 | − int offset_modified = func_bound_offset != lbounds_section->data_offset; | |
| 1061 | + int offset_modified = S->func_bound_offset != lbounds_section->data_offset; | |
| 1065 | 1062 | |
| 1066 | − if (!offset_modified && !func_bound_add_epilog) | |
| 1063 | + if (!offset_modified && !S->func_bound_add_epilog) | |
| 1067 | 1064 | return; |
| 1068 | 1065 | |
| 1069 | 1066 | /* add end of table info */ |
| 1070 | − bounds_ptr = section_ptr_add(lbounds_section, sizeof(addr_t)); | |
| 1067 | + bounds_ptr = section_ptr_add(S, lbounds_section, sizeof(addr_t)); | |
| 1071 | 1068 | *bounds_ptr = 0; |
| 1072 | 1069 | |
| 1073 | − sym_data = get_sym_ref(&char_pointer_type, lbounds_section, | |
| 1074 | − func_bound_offset, lbounds_section->data_offset); | |
| 1070 | + sym_data = get_sym_ref(S, &S->tccgen_char_pointer_type, lbounds_section, | |
| 1071 | + S->func_bound_offset, lbounds_section->data_offset); | |
| 1075 | 1072 | |
| 1076 | 1073 | /* generate bound local allocation */ |
| 1077 | 1074 | if (offset_modified) { |
| 1078 | − saved_ind = ind; | |
| 1079 | − ind = func_bound_ind; | |
| 1080 | − greloc(cur_text_section, sym_data, ind + 1, R_386_32); | |
| 1081 | − ind = ind + 5; | |
| 1082 | − gen_static_call(TOK___bound_local_new); | |
| 1083 | − ind = saved_ind; | |
| 1075 | + saved_ind = S->tccgen_ind; | |
| 1076 | + S->tccgen_ind = S->func_bound_ind; | |
| 1077 | + greloc(S, cur_text_section, sym_data, S->tccgen_ind + 1, R_386_32); | |
| 1078 | + S->tccgen_ind = S->tccgen_ind + 5; | |
| 1079 | + gen_static_call(S, TOK___bound_local_new); | |
| 1080 | + S->tccgen_ind = saved_ind; | |
| 1084 | 1081 | } |
| 1085 | 1082 | |
| 1086 | 1083 | /* generate bound check local freeing */ |
| 1087 | − o(0x5250); /* save returned value, if any */ | |
| 1088 | − greloc(cur_text_section, sym_data, ind + 1, R_386_32); | |
| 1089 | − oad(0xb8, 0); /* mov %eax, xxx */ | |
| 1090 | − gen_static_call(TOK___bound_local_delete); | |
| 1091 | − o(0x585a); /* restore returned value, if any */ | |
| 1084 | + o(S, 0x5250); /* save returned value, if any */ | |
| 1085 | + greloc(S, cur_text_section, sym_data, S->tccgen_ind + 1, R_386_32); | |
| 1086 | + oad(S, 0xb8, 0); /* mov %eax, xxx */ | |
| 1087 | + gen_static_call(S, TOK___bound_local_delete); | |
| 1088 | + o(S, 0x585a); /* restore returned value, if any */ | |
| 1092 | 1089 | } |
| 1093 | 1090 | #endif |
| 1094 | 1091 | |
| 1095 | 1092 | /* Save the stack pointer onto the stack */ |
| 1096 | −ST_FUNC void gen_vla_sp_save(int addr) { | |
| 1093 | +ST_FUNC void gen_vla_sp_save(TCCState* S, int addr) { | |
| 1097 | 1094 | /* mov %esp,addr(%ebp)*/ |
| 1098 | − o(0x89); | |
| 1099 | − gen_modrm(TREG_ESP, VT_LOCAL, NULL, addr); | |
| 1095 | + o(S, 0x89); | |
| 1096 | + gen_modrm(S, TREG_ESP, VT_LOCAL, NULL, addr); | |
| 1100 | 1097 | } |
| 1101 | 1098 | |
| 1102 | 1099 | /* Restore the SP from a location on the stack */ |
| 1103 | −ST_FUNC void gen_vla_sp_restore(int addr) { | |
| 1104 | − o(0x8b); | |
| 1105 | − gen_modrm(TREG_ESP, VT_LOCAL, NULL, addr); | |
| 1100 | +ST_FUNC void gen_vla_sp_restore(TCCState* S, int addr) { | |
| 1101 | + o(S, 0x8b); | |
| 1102 | + gen_modrm(S, TREG_ESP, VT_LOCAL, NULL, addr); | |
| 1106 | 1103 | } |
| 1107 | 1104 | |
| 1108 | 1105 | /* Subtract from the stack pointer, and push the resulting value onto the stack */ |
| 1109 | −ST_FUNC void gen_vla_alloc(CType *type, int align) { | |
| 1106 | +ST_FUNC void gen_vla_alloc(TCCState* S, CType *type, int align) { | |
| 1110 | 1107 | int use_call = 0; |
| 1111 | 1108 | |
| 1112 | 1109 | #if defined(CONFIG_TCC_BCHECK) |
| 1113 | − use_call = tcc_state->do_bounds_check; | |
| 1110 | + use_call = S->do_bounds_check; | |
| 1114 | 1111 | #endif |
| 1115 | 1112 | #ifdef TCC_TARGET_PE /* alloca does more than just adjust %rsp on Windows */ |
| 1116 | 1113 | use_call = 1; |
| 1117 | 1114 | #endif |
| 1118 | 1115 | if (use_call) |
| 1119 | 1116 | { |
| 1120 | − vpush_helper_func(TOK_alloca); | |
| 1121 | − vswap(); /* Move alloca ref past allocation size */ | |
| 1122 | − gfunc_call(1); | |
| 1117 | + vpush_helper_func(S, TOK_alloca); | |
| 1118 | + vswap(S); /* Move alloca ref past allocation size */ | |
| 1119 | + gfunc_call(S, 1); | |
| 1123 | 1120 | } |
| 1124 | 1121 | else { |
| 1125 | 1122 | int r; |
| 1126 | − r = gv(RC_INT); /* allocation size */ | |
| 1123 | + r = gv(S, RC_INT); /* allocation size */ | |
| 1127 | 1124 | /* sub r,%rsp */ |
| 1128 | − o(0x2b); | |
| 1129 | − o(0xe0 | r); | |
| 1125 | + o(S, 0x2b); | |
| 1126 | + o(S, 0xe0 | r); | |
| 1130 | 1127 | /* We align to 16 bytes rather than align */ |
| 1131 | 1128 | /* and ~15, %esp */ |
| 1132 | − o(0xf0e483); | |
| 1133 | − vpop(); | |
| 1129 | + o(S, 0xf0e483); | |
| 1130 | + vpop(S); | |
| 1134 | 1131 | } |
| 1135 | 1132 | } |
| 1136 | 1133 | |
| @@ -91,15 +91,15 @@ int gotplt_entry_type (int reloc_type) · 90 unmodified lines | ||
| 91 | 91 | return -1; |
| 92 | 92 | } |
| 93 | 93 | |
| 94 | −ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_attr *attr) | |
| 94 | +ST_FUNC unsigned create_plt_entry(TCCState *S, unsigned got_offset, struct sym_attr *attr) | |
| 95 | 95 | { |
| 96 | − Section *plt = s1->plt; | |
| 96 | + Section *plt = S->plt; | |
| 97 | 97 | uint8_t *p; |
| 98 | 98 | int modrm; |
| 99 | 99 | unsigned plt_offset, relofs; |
| 100 | 100 | |
| 101 | 101 | /* on i386 if we build a DLL, we add a %ebx offset */ |
| 102 | − if (s1->output_type == TCC_OUTPUT_DLL) | |
| 102 | + if (S->output_type == TCC_OUTPUT_DLL) | |
| 103 | 103 | modrm = 0xa3; |
| 104 | 104 | else |
| 105 | 105 | modrm = 0x25; |
| @@ -108,7 +108,7 @@ ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_ · 2 unmodified lines | ||
| 108 | 108 | (GOT + PTR_SIZE) and jumps to ld.so resolution routine |
| 109 | 109 | (GOT + 2 * PTR_SIZE) */ |
| 110 | 110 | if (plt->data_offset == 0) { |
| 111 | − p = section_ptr_add(plt, 16); | |
| 111 | + p = section_ptr_add(S, plt, 16); | |
| 112 | 112 | p[0] = 0xff; /* pushl got + PTR_SIZE */ |
| 113 | 113 | p[1] = modrm + 0x10; |
| 114 | 114 | write32le(p + 2, PTR_SIZE); |
| @@ -121,10 +121,10 @@ ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_ · 6 unmodified lines | ||
| 121 | 121 | /* The PLT slot refers to the relocation entry it needs via offset. |
| 122 | 122 | The reloc entry is created below, so its offset is the current |
| 123 | 123 | data_offset */ |
| 124 | − relofs = s1->plt->reloc ? s1->plt->reloc->data_offset : 0; | |
| 124 | + relofs = S->plt->reloc ? S->plt->reloc->data_offset : 0; | |
| 125 | 125 | |
| 126 | 126 | /* Jump to GOT entry where ld.so initially put the address of ip + 4 */ |
| 127 | − p = section_ptr_add(plt, 16); | |
| 127 | + p = section_ptr_add(S, plt, 16); | |
| 128 | 128 | p[0] = 0xff; /* jmp *(got + x) */ |
| 129 | 129 | p[1] = modrm; |
| 130 | 130 | write32le(p + 2, got_offset); |
| @@ -137,31 +137,31 @@ ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_ · 6 unmodified lines | ||
| 137 | 137 | |
| 138 | 138 | /* relocate the PLT: compute addresses and offsets in the PLT now that final |
| 139 | 139 | address for PLT and GOT are known (see fill_program_header) */ |
| 140 | −ST_FUNC void relocate_plt(TCCState *s1) | |
| 140 | +ST_FUNC void relocate_plt(TCCState *S) | |
| 141 | 141 | { |
| 142 | 142 | uint8_t *p, *p_end; |
| 143 | 143 | |
| 144 | − if (!s1->plt) | |
| 144 | + if (!S->plt) | |
| 145 | 145 | return; |
| 146 | 146 | |
| 147 | − p = s1->plt->data; | |
| 148 | − p_end = p + s1->plt->data_offset; | |
| 147 | + p = S->plt->data; | |
| 148 | + p_end = p + S->plt->data_offset; | |
| 149 | 149 | |
| 150 | − if (s1->output_type != TCC_OUTPUT_DLL && p < p_end) { | |
| 151 | − add32le(p + 2, s1->got->sh_addr); | |
| 152 | − add32le(p + 8, s1->got->sh_addr); | |
| 150 | + if (S->output_type != TCC_OUTPUT_DLL && p < p_end) { | |
| 151 | + add32le(p + 2, S->got->sh_addr); | |
| 152 | + add32le(p + 8, S->got->sh_addr); | |
| 153 | 153 | p += 16; |
| 154 | 154 | while (p < p_end) { |
| 155 | − add32le(p + 2, s1->got->sh_addr); | |
| 155 | + add32le(p + 2, S->got->sh_addr); | |
| 156 | 156 | p += 16; |
| 157 | 157 | } |
| 158 | 158 | } |
| 159 | 159 | |
| 160 | − if (s1->plt->reloc) { | |
| 160 | + if (S->plt->reloc) { | |
| 161 | 161 | ElfW_Rel *rel; |
| 162 | − int x = s1->plt->sh_addr + 16 + 6; | |
| 163 | − p = s1->got->data; | |
| 164 | − for_each_elem(s1->plt->reloc, 0, rel, ElfW_Rel) { | |
| 162 | + int x = S->plt->sh_addr + 16 + 6; | |
| 163 | + p = S->got->data; | |
| 164 | + for_each_elem(S->plt->reloc, 0, rel, ElfW_Rel) { | |
| 165 | 165 | write32le(p + rel->r_offset, x); |
| 166 | 166 | x += 16; |
| 167 | 167 | } |
| @@ -169,7 +169,7 @@ ST_FUNC void relocate_plt(TCCState *s1) · 1 unmodified line | ||
| 169 | 169 | } |
| 170 | 170 | #endif |
| 171 | 171 | |
| 172 | −void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 172 | +void relocate(TCCState *S, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val) | |
| 173 | 173 | { |
| 174 | 174 | int sym_index, esym_index; |
| 175 | 175 | |
| @@ -177,8 +177,8 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 1 unmodified line | ||
| 177 | 177 | |
| 178 | 178 | switch (type) { |
| 179 | 179 | case R_386_32: |
| 180 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 181 | − esym_index = get_sym_attr(s1, sym_index, 0)->dyn_index; | |
| 180 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 181 | + esym_index = get_sym_attr(S, sym_index, 0)->dyn_index; | |
| 182 | 182 | qrel->r_offset = rel->r_offset; |
| 183 | 183 | if (esym_index) { |
| 184 | 184 | qrel->r_info = ELFW(R_INFO)(esym_index, R_386_32); |
| @@ -192,9 +192,9 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 7 unmodified lines | ||
| 192 | 192 | add32le(ptr, val); |
| 193 | 193 | return; |
| 194 | 194 | case R_386_PC32: |
| 195 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 195 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 196 | 196 | /* DLL relocation */ |
| 197 | − esym_index = get_sym_attr(s1, sym_index, 0)->dyn_index; | |
| 197 | + esym_index = get_sym_attr(S, sym_index, 0)->dyn_index; | |
| 198 | 198 | if (esym_index) { |
| 199 | 199 | qrel->r_offset = rel->r_offset; |
| 200 | 200 | qrel->r_info = ELFW(R_INFO)(esym_index, R_386_PC32); |
| @@ -212,31 +212,31 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 11 unmodified lines | ||
| 212 | 212 | write32le(ptr, val); |
| 213 | 213 | return; |
| 214 | 214 | case R_386_GOTPC: |
| 215 | − add32le(ptr, s1->got->sh_addr - addr); | |
| 215 | + add32le(ptr, S->got->sh_addr - addr); | |
| 216 | 216 | return; |
| 217 | 217 | case R_386_GOTOFF: |
| 218 | − add32le(ptr, val - s1->got->sh_addr); | |
| 218 | + add32le(ptr, val - S->got->sh_addr); | |
| 219 | 219 | return; |
| 220 | 220 | case R_386_GOT32: |
| 221 | 221 | case R_386_GOT32X: |
| 222 | 222 | /* we load the got offset */ |
| 223 | − add32le(ptr, get_sym_attr(s1, sym_index, 0)->got_offset); | |
| 223 | + add32le(ptr, get_sym_attr(S, sym_index, 0)->got_offset); | |
| 224 | 224 | return; |
| 225 | 225 | case R_386_16: |
| 226 | − if (s1->output_format != TCC_OUTPUT_FORMAT_BINARY) { | |
| 226 | + if (S->output_format != TCC_OUTPUT_FORMAT_BINARY) { | |
| 227 | 227 | output_file: |
| 228 | − tcc_error("can only produce 16-bit binary files"); | |
| 228 | + tcc_error(S, "can only produce 16-bit binary files"); | |
| 229 | 229 | } |
| 230 | 230 | write16le(ptr, read16le(ptr) + val); |
| 231 | 231 | return; |
| 232 | 232 | case R_386_PC16: |
| 233 | − if (s1->output_format != TCC_OUTPUT_FORMAT_BINARY) | |
| 233 | + if (S->output_format != TCC_OUTPUT_FORMAT_BINARY) | |
| 234 | 234 | goto output_file; |
| 235 | 235 | write16le(ptr, read16le(ptr) + val - addr); |
| 236 | 236 | return; |
| 237 | 237 | case R_386_RELATIVE: |
| 238 | 238 | #ifdef TCC_TARGET_PE |
| 239 | − add32le(ptr, val - s1->pe_imagebase); | |
| 239 | + add32le(ptr, val - S->pe_imagebase); | |
| 240 | 240 | #endif |
| 241 | 241 | /* do nothing */ |
| 242 | 242 | return; |
| @@ -267,12 +267,12 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 24 unmodified lines | ||
| 267 | 267 | memcpy(ptr-3, replace, sizeof(replace)); |
| 268 | 268 | rel[1].r_info = ELFW(R_INFO)(0, R_386_NONE); |
| 269 | 269 | sym = &((ElfW(Sym) *)symtab_section->data)[sym_index]; |
| 270 | − sec = s1->sections[sym->st_shndx]; | |
| 270 | + sec = S->sections[sym->st_shndx]; | |
| 271 | 271 | x = sym->st_value - sec->sh_addr - sec->data_offset; |
| 272 | 272 | add32le(ptr + 5, -x); |
| 273 | 273 | } |
| 274 | 274 | else |
| 275 | − tcc_error("unexpected R_386_TLS_GD pattern"); | |
| 275 | + tcc_error(S, "unexpected R_386_TLS_GD pattern"); | |
| 276 | 276 | } |
| 277 | 277 | return; |
| 278 | 278 | case R_386_TLS_LDM: |
| @@ -295,7 +295,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 16 unmodified lines | ||
| 295 | 295 | rel[1].r_info = ELFW(R_INFO)(0, R_386_NONE); |
| 296 | 296 | } |
| 297 | 297 | else |
| 298 | − tcc_error("unexpected R_386_TLS_LDM pattern"); | |
| 298 | + tcc_error(S, "unexpected R_386_TLS_LDM pattern"); | |
| 299 | 299 | } |
| 300 | 300 | return; |
| 301 | 301 | case R_386_TLS_LDO_32: |
| @@ -306,7 +306,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t · 4 unmodified lines | ||
| 306 | 306 | int32_t x; |
| 307 | 307 | |
| 308 | 308 | sym = &((ElfW(Sym) *)symtab_section->data)[sym_index]; |
| 309 | − sec = s1->sections[sym->st_shndx]; | |
| 309 | + sec = S->sections[sym->st_shndx]; | |
| 310 | 310 | x = val - sec->sh_addr - sec->data_offset; |
| 311 | 311 | add32le(ptr, x); |
| 312 | 312 | } |
| @@ -65,7 +65,6 @@ · 64 unmodified lines | ||
| 65 | 65 | /* global variables */ |
| 66 | 66 | |
| 67 | 67 | /* XXX: get rid of this ASAP (or maybe not) */ |
| 68 | −ST_DATA struct TCCState *tcc_state; | |
| 69 | 68 | TCC_SEM(static tcc_compile_sem); |
| 70 | 69 | |
| 71 | 70 | #ifdef MEM_DEBUG |
| @@ -111,11 +110,11 @@ static inline char *config_tccdir_w32(char *path) · 39 unmodified lines | ||
| 111 | 110 | #endif |
| 112 | 111 | |
| 113 | 112 | #ifdef TCC_TARGET_PE |
| 114 | −static void tcc_add_systemdir(TCCState *s) | |
| 113 | +static void tcc_add_systemdir(TCCState *S) | |
| 115 | 114 | { |
| 116 | 115 | char buf[1000]; |
| 117 | 116 | GetSystemDirectory(buf, sizeof buf); |
| 118 | − tcc_add_library_path(s, normalize_slashes(buf)); | |
| 117 | + tcc_add_library_path(S, normalize_slashes(buf)); | |
| 119 | 118 | } |
| 120 | 119 | #endif |
| 121 | 120 | #endif |
| @@ -160,19 +159,19 @@ ST_FUNC void post_sem(TCCSem *p) · 38 unmodified lines | ||
| 160 | 159 | #endif |
| 161 | 160 | #endif |
| 162 | 161 | |
| 163 | −PUB_FUNC void tcc_enter_state(TCCState *s1) | |
| 162 | +PUB_FUNC void tcc_enter_state(TCCState *S) | |
| 164 | 163 | { |
| 165 | − if (s1->error_set_jmp_enabled) | |
| 164 | + if (S->error_set_jmp_enabled) | |
| 166 | 165 | return; |
| 167 | 166 | WAIT_SEM(&tcc_compile_sem); |
| 168 | − tcc_state = s1; | |
| 167 | + /*S = S;*/ | |
| 169 | 168 | } |
| 170 | 169 | |
| 171 | −PUB_FUNC void tcc_exit_state(TCCState *s1) | |
| 170 | +PUB_FUNC void tcc_exit_state(TCCState *S) | |
| 172 | 171 | { |
| 173 | − if (s1->error_set_jmp_enabled) | |
| 172 | + if (S->error_set_jmp_enabled) | |
| 174 | 173 | return; |
| 175 | − tcc_state = NULL; | |
| 174 | + S = NULL; | |
| 176 | 175 | POST_SEM(&tcc_compile_sem); |
| 177 | 176 | } |
| 178 | 177 | |
| @@ -234,10 +233,10 @@ PUB_FUNC char *tcc_fileextension (const char *name) · 55 unmodified lines | ||
| 234 | 233 | return e ? e : strchr(b, 0); |
| 235 | 234 | } |
| 236 | 235 | |
| 237 | −ST_FUNC char *tcc_load_text(int fd) | |
| 236 | +ST_FUNC char *tcc_load_text(TCCState* S, int fd) | |
| 238 | 237 | { |
| 239 | 238 | int len = lseek(fd, 0, SEEK_END); |
| 240 | − char *buf = load_data(fd, 0, len + 1); | |
| 239 | + char *buf = load_data(S, fd, 0, len + 1); | |
| 241 | 240 | buf[len] = 0; |
| 242 | 241 | return buf; |
| 243 | 242 | } |
| @@ -249,44 +248,69 @@ ST_FUNC char *tcc_load_text(int fd) · 5 unmodified lines | ||
| 249 | 248 | #undef malloc |
| 250 | 249 | #undef realloc |
| 251 | 250 | |
| 251 | +PUB_FUNC void tcc_free_base(void *ptr) | |
| 252 | +{ | |
| 253 | + free(ptr); | |
| 254 | +} | |
| 255 | + | |
| 256 | +PUB_FUNC void *tcc_malloc_base(unsigned long size) | |
| 257 | +{ | |
| 258 | + void *ptr; | |
| 259 | + ptr = malloc(size); | |
| 260 | + if (!ptr && size) { | |
| 261 | + printf("memory full (malloc)\n"); | |
| 262 | + exit(1); | |
| 263 | + } | |
| 264 | + return ptr; | |
| 265 | +} | |
| 266 | + | |
| 267 | +PUB_FUNC void *tcc_mallocz_base(unsigned long size) | |
| 268 | +{ | |
| 269 | + void *ptr; | |
| 270 | + ptr = tcc_malloc_base(size); | |
| 271 | + if (size) | |
| 272 | + memset(ptr, 0, size); | |
| 273 | + return ptr; | |
| 274 | +} | |
| 275 | + | |
| 252 | 276 | #ifndef MEM_DEBUG |
| 253 | 277 | |
| 254 | −PUB_FUNC void tcc_free(void *ptr) | |
| 278 | +PUB_FUNC void tcc_free(TCCState* S, void *ptr) | |
| 255 | 279 | { |
| 256 | 280 | free(ptr); |
| 257 | 281 | } |
| 258 | 282 | |
| 259 | −PUB_FUNC void *tcc_malloc(unsigned long size) | |
| 283 | +PUB_FUNC void *tcc_malloc(TCCState* S, unsigned long size) | |
| 260 | 284 | { |
| 261 | 285 | void *ptr; |
| 262 | 286 | ptr = malloc(size); |
| 263 | 287 | if (!ptr && size) |
| 264 | − _tcc_error("memory full (malloc)"); | |
| 288 | + _tcc_error(S, "memory full (malloc)"); | |
| 265 | 289 | return ptr; |
| 266 | 290 | } |
| 267 | 291 | |
| 268 | −PUB_FUNC void *tcc_mallocz(unsigned long size) | |
| 292 | +PUB_FUNC void *tcc_mallocz(TCCState* S, unsigned long size) | |
| 269 | 293 | { |
| 270 | 294 | void *ptr; |
| 271 | − ptr = tcc_malloc(size); | |
| 295 | + ptr = tcc_malloc(S, size); | |
| 272 | 296 | if (size) |
| 273 | 297 | memset(ptr, 0, size); |
| 274 | 298 | return ptr; |
| 275 | 299 | } |
| 276 | 300 | |
| 277 | −PUB_FUNC void *tcc_realloc(void *ptr, unsigned long size) | |
| 301 | +PUB_FUNC void *tcc_realloc(TCCState* S, void *ptr, unsigned long size) | |
| 278 | 302 | { |
| 279 | 303 | void *ptr1; |
| 280 | 304 | ptr1 = realloc(ptr, size); |
| 281 | 305 | if (!ptr1 && size) |
| 282 | − _tcc_error("memory full (realloc)"); | |
| 306 | + _tcc_error(S, "memory full (realloc)"); | |
| 283 | 307 | return ptr1; |
| 284 | 308 | } |
| 285 | 309 | |
| 286 | −PUB_FUNC char *tcc_strdup(const char *str) | |
| 310 | +PUB_FUNC char *tcc_strdup(TCCState* S, const char *str) | |
| 287 | 311 | { |
| 288 | 312 | char *ptr; |
| 289 | − ptr = tcc_malloc(strlen(str) + 1); | |
| 313 | + ptr = tcc_malloc(S, strlen(str) + 1); | |
| 290 | 314 | strcpy(ptr, str); |
| 291 | 315 | return ptr; |
| 292 | 316 | } |
| @@ -337,14 +361,14 @@ static mem_debug_header_t *malloc_check(void *ptr, const char *msg) · 44 unmodified lines | ||
| 337 | 361 | return header; |
| 338 | 362 | } |
| 339 | 363 | |
| 340 | −PUB_FUNC void *tcc_malloc_debug(unsigned long size, const char *file, int line) | |
| 364 | +PUB_FUNC void *tcc_malloc_debug(TCCState* S, unsigned long size, const char *file, int line) | |
| 341 | 365 | { |
| 342 | 366 | int ofs; |
| 343 | 367 | mem_debug_header_t *header; |
| 344 | 368 | |
| 345 | 369 | header = malloc(sizeof(mem_debug_header_t) + size); |
| 346 | 370 | if (!header) |
| 347 | − _tcc_error("memory full (malloc)"); | |
| 371 | + _tcc_error(S, "memory full (malloc)"); | |
| 348 | 372 | |
| 349 | 373 | header->magic1 = MEM_DEBUG_MAGIC1; |
| 350 | 374 | header->magic2 = MEM_DEBUG_MAGIC2; |
| @@ -368,7 +392,7 @@ PUB_FUNC void *tcc_malloc_debug(unsigned long size, const char *file, int line) · 17 unmodified lines | ||
| 368 | 392 | return MEM_USER_PTR(header); |
| 369 | 393 | } |
| 370 | 394 | |
| 371 | −PUB_FUNC void tcc_free_debug(void *ptr) | |
| 395 | +PUB_FUNC void tcc_free_debug(TCCState* S, void *ptr) | |
| 372 | 396 | { |
| 373 | 397 | mem_debug_header_t *header; |
| 374 | 398 | if (!ptr) |
| @@ -385,26 +409,26 @@ PUB_FUNC void tcc_free_debug(void *ptr) · 10 unmodified lines | ||
| 385 | 409 | free(header); |
| 386 | 410 | } |
| 387 | 411 | |
| 388 | −PUB_FUNC void *tcc_mallocz_debug(unsigned long size, const char *file, int line) | |
| 412 | +PUB_FUNC void *tcc_mallocz_debug(TCCState* S, unsigned long size, const char *file, int line) | |
| 389 | 413 | { |
| 390 | 414 | void *ptr; |
| 391 | − ptr = tcc_malloc_debug(size,file,line); | |
| 415 | + ptr = tcc_malloc_debug(S, size,file,line); | |
| 392 | 416 | memset(ptr, 0, size); |
| 393 | 417 | return ptr; |
| 394 | 418 | } |
| 395 | 419 | |
| 396 | −PUB_FUNC void *tcc_realloc_debug(void *ptr, unsigned long size, const char *file, int line) | |
| 420 | +PUB_FUNC void *tcc_realloc_debug(TCCState* S, void *ptr, unsigned long size, const char *file, int line) | |
| 397 | 421 | { |
| 398 | 422 | mem_debug_header_t *header; |
| 399 | 423 | int mem_debug_chain_update = 0; |
| 400 | 424 | if (!ptr) |
| 401 | − return tcc_malloc_debug(size, file, line); | |
| 425 | + return tcc_malloc_debug(S, size, file, line); | |
| 402 | 426 | header = malloc_check(ptr, "tcc_realloc"); |
| 403 | 427 | mem_cur_size -= header->size; |
| 404 | 428 | mem_debug_chain_update = (header == mem_debug_chain); |
| 405 | 429 | header = realloc(header, sizeof(mem_debug_header_t) + size); |
| 406 | 430 | if (!header) |
| 407 | − _tcc_error("memory full (realloc)"); | |
| 431 | + _tcc_error(S, "memory full (realloc)"); | |
| 408 | 432 | header->size = size; |
| 409 | 433 | write32le(MEM_DEBUG_CHECK3(header), MEM_DEBUG_MAGIC3); |
| 410 | 434 | if (header->next) |
| @@ -419,10 +443,10 @@ PUB_FUNC void *tcc_realloc_debug(void *ptr, unsigned long size, const char *file · 8 unmodified lines | ||
| 419 | 443 | return MEM_USER_PTR(header); |
| 420 | 444 | } |
| 421 | 445 | |
| 422 | −PUB_FUNC char *tcc_strdup_debug(const char *str, const char *file, int line) | |
| 446 | +PUB_FUNC char *tcc_strdup_debug(TCCState* S, const char *str, const char *file, int line) | |
| 423 | 447 | { |
| 424 | 448 | char *ptr; |
| 425 | − ptr = tcc_malloc_debug(strlen(str) + 1, file, line); | |
| 449 | + ptr = tcc_malloc_debug(S, strlen(str) + 1, file, line); | |
| 426 | 450 | strcpy(ptr, str); |
| 427 | 451 | return ptr; |
| 428 | 452 | } |
| @@ -449,10 +473,66 @@ PUB_FUNC void tcc_memcheck(void) · 20 unmodified lines | ||
| 449 | 473 | #define malloc(s) use_tcc_malloc(s) |
| 450 | 474 | #define realloc(p, s) use_tcc_realloc(p, s) |
| 451 | 475 | |
| 476 | +/********************************************************/ | |
| 477 | +/* virtual io */ | |
| 478 | + | |
| 479 | +LIBTCCAPI void tcc_set_vio_module(TCCState *S, vio_module_t *vio_module){ | |
| 480 | + S->vio_module = vio_module; | |
| 481 | + vio_module->S = S; | |
| 482 | +} | |
| 483 | + | |
| 484 | +void vio_initialize(vio_fd *fd) { | |
| 485 | + fd->fd = -1; | |
| 486 | + fd->vio_udata = NULL; | |
| 487 | + fd->vio_module = NULL; | |
| 488 | +} | |
| 489 | + | |
| 490 | +int vio_open(struct TCCState *S, vio_fd *fd, const char *fn, int oflag) { | |
| 491 | + int rc; | |
| 492 | + vio_initialize(fd); | |
| 493 | + fd->vio_module = S->vio_module; | |
| 494 | + if(S->vio_module && (S->vio_module->call_vio_open_flags & CALL_VIO_OPEN_FIRST)) { | |
| 495 | + rc = S->vio_module->vio_open(fd, fn, oflag); | |
| 496 | + if(rc >= 0) return rc; | |
| 497 | + } | |
| 498 | + | |
| 499 | + fd->fd = open(fn, oflag); | |
| 500 | + | |
| 501 | + if(fd->fd < 0 && S->vio_module && (S->vio_module->call_vio_open_flags & CALL_VIO_OPEN_LAST)) { | |
| 502 | + rc = S->vio_module->vio_open(fd, fn, oflag); | |
| 503 | + if(rc >= 0) return rc; | |
| 504 | + } | |
| 505 | + //printf("vio_open = %d %s\n", fd->fd, fn); | |
| 506 | + return fd->fd; | |
| 507 | +} | |
| 508 | + | |
| 509 | +off_t vio_lseek(vio_fd fd, off_t offset, int whence) { | |
| 510 | + if(fd.vio_udata) { | |
| 511 | + return fd.vio_module->vio_lseek(fd, offset, whence); | |
| 512 | + } | |
| 513 | + return lseek(fd.fd, offset, whence); | |
| 514 | +} | |
| 515 | + | |
| 516 | +size_t vio_read(vio_fd fd, void *buf, size_t bytes) { | |
| 517 | + if(fd.vio_udata) { | |
| 518 | + return fd.vio_module->vio_read(fd, buf, bytes); | |
| 519 | + } | |
| 520 | + return read(fd.fd, buf, bytes); | |
| 521 | +} | |
| 522 | + | |
| 523 | +int vio_close(vio_fd *fd) { | |
| 524 | + int rc = 0; | |
| 525 | + if(fd->vio_udata){ | |
| 526 | + fd->vio_module->vio_close(fd); | |
| 527 | + } else rc = close(fd->fd); | |
| 528 | + vio_initialize(fd); | |
| 529 | + return rc; | |
| 530 | +} | |
| 531 | + | |
| 452 | 532 | /********************************************************/ |
| 453 | 533 | /* dynarrays */ |
| 454 | 534 | |
| 455 | −ST_FUNC void dynarray_add(void *ptab, int *nb_ptr, void *data) | |
| 535 | +ST_FUNC void dynarray_add(TCCState* S, void *ptab, int *nb_ptr, void *data) | |
| 456 | 536 | { |
| 457 | 537 | int nb, nb_alloc; |
| 458 | 538 | void **pp; |
| @@ -465,54 +545,54 @@ ST_FUNC void dynarray_add(void *ptab, int *nb_ptr, void *data) · 6 unmodified lines | ||
| 465 | 545 | nb_alloc = 1; |
| 466 | 546 | else |
| 467 | 547 | nb_alloc = nb * 2; |
| 468 | − pp = tcc_realloc(pp, nb_alloc * sizeof(void *)); | |
| 548 | + pp = tcc_realloc(S, pp, nb_alloc * sizeof(void *)); | |
| 469 | 549 | *(void***)ptab = pp; |
| 470 | 550 | } |
| 471 | 551 | pp[nb++] = data; |
| 472 | 552 | *nb_ptr = nb; |
| 473 | 553 | } |
| 474 | 554 | |
| 475 | −ST_FUNC void dynarray_reset(void *pp, int *n) | |
| 555 | +ST_FUNC void dynarray_reset(TCCState* S, void *pp, int *n) | |
| 476 | 556 | { |
| 477 | 557 | void **p; |
| 478 | 558 | for (p = *(void***)pp; *n; ++p, --*n) |
| 479 | 559 | if (*p) |
| 480 | − tcc_free(*p); | |
| 481 | − tcc_free(*(void**)pp); | |
| 560 | + tcc_free(S, *p); | |
| 561 | + tcc_free(S, *(void**)pp); | |
| 482 | 562 | *(void**)pp = NULL; |
| 483 | 563 | } |
| 484 | 564 | |
| 485 | −static void tcc_split_path(TCCState *s, void *p_ary, int *p_nb_ary, const char *in) | |
| 565 | +static void tcc_split_path(TCCState *S, void *p_ary, int *p_nb_ary, const char *in) | |
| 486 | 566 | { |
| 487 | 567 | const char *p; |
| 488 | 568 | do { |
| 489 | 569 | int c; |
| 490 | 570 | CString str; |
| 491 | 571 | |
| 492 | − cstr_new(&str); | |
| 572 | + cstr_new(S, &str); | |
| 493 | 573 | for (p = in; c = *p, c != '\0' && c != PATHSEP[0]; ++p) { |
| 494 | 574 | if (c == '{' && p[1] && p[2] == '}') { |
| 495 | 575 | c = p[1], p += 2; |
| 496 | 576 | if (c == 'B') |
| 497 | − cstr_cat(&str, s->tcc_lib_path, -1); | |
| 498 | − if (c == 'f' && file) { | |
| 577 | + cstr_cat(S, &str, S->tcc_lib_path, -1); | |
| 578 | + if (c == 'f' && S->tccpp_file) { | |
| 499 | 579 | /* substitute current file's dir */ |
| 500 | − const char *f = file->true_filename; | |
| 580 | + const char *f = S->tccpp_file->true_filename; | |
| 501 | 581 | const char *b = tcc_basename(f); |
| 502 | 582 | if (b > f) |
| 503 | − cstr_cat(&str, f, b - f - 1); | |
| 583 | + cstr_cat(S, &str, f, b - f - 1); | |
| 504 | 584 | else |
| 505 | − cstr_cat(&str, ".", 1); | |
| 585 | + cstr_cat(S, &str, ".", 1); | |
| 506 | 586 | } |
| 507 | 587 | } else { |
| 508 | − cstr_ccat(&str, c); | |
| 588 | + cstr_ccat(S, &str, c); | |
| 509 | 589 | } |
| 510 | 590 | } |
| 511 | 591 | if (str.size) { |
| 512 | − cstr_ccat(&str, '\0'); | |
| 513 | − dynarray_add(p_ary, p_nb_ary, tcc_strdup(str.data)); | |
| 592 | + cstr_ccat(S, &str, '\0'); | |
| 593 | + dynarray_add(S, p_ary, p_nb_ary, tcc_strdup(S, str.data)); | |
| 514 | 594 | } |
| 515 | − cstr_free(&str); | |
| 595 | + cstr_free(S, &str); | |
| 516 | 596 | in = p+1; |
| 517 | 597 | } while (*p); |
| 518 | 598 | } |
| @@ -528,27 +608,26 @@ static void tcc_split_path(TCCState *s, void *p_ary, int *p_nb_ary, const char * · 9 unmodified lines | ||
| 528 | 608 | /* error1() modes */ |
| 529 | 609 | enum { ERROR_WARN, ERROR_NOABORT, ERROR_ERROR }; |
| 530 | 610 | |
| 531 | −static void error1(int mode, const char *fmt, va_list ap) | |
| 611 | +static void error1(TCCState* S, int mode, const char *fmt, va_list ap) | |
| 532 | 612 | { |
| 533 | 613 | BufferedFile **pf, *f; |
| 534 | − TCCState *s1 = tcc_state; | |
| 535 | 614 | CString cs; |
| 536 | 615 | |
| 537 | − cstr_new(&cs); | |
| 616 | + cstr_new(S, &cs); | |
| 538 | 617 | |
| 539 | − if (s1 == NULL) | |
| 618 | + if (S == NULL) | |
| 540 | 619 | /* can happen only if called from tcc_malloc(): 'out of memory' */ |
| 541 | 620 | goto no_file; |
| 542 | 621 | |
| 543 | − tcc_exit_state(s1); | |
| 622 | + tcc_exit_state(S); | |
| 544 | 623 | |
| 545 | 624 | if (mode == ERROR_WARN) { |
| 546 | − if (s1->warn_error) | |
| 625 | + if (S->warn_error) | |
| 547 | 626 | mode = ERROR_ERROR; |
| 548 | − if (s1->warn_num) { | |
| 627 | + if (S->warn_num) { | |
| 549 | 628 | /* handle tcc_warning_c(warn_option)(fmt, ...) */ |
| 550 | − int wopt = *(&s1->warn_none + s1->warn_num); | |
| 551 | − s1->warn_num = 0; | |
| 629 | + int wopt = *(&S->warn_none + S->warn_num); | |
| 630 | + S->warn_num = 0; | |
| 552 | 631 | if (0 == (wopt & WARN_ON)) |
| 553 | 632 | return; |
| 554 | 633 | if (wopt & WARN_ERR) |
| @@ -556,102 +635,102 @@ static void error1(int mode, const char *fmt, va_list ap) · 1 unmodified line | ||
| 556 | 635 | if (wopt & WARN_NOE) |
| 557 | 636 | mode = ERROR_WARN; |
| 558 | 637 | } |
| 559 | − if (s1->warn_none) | |
| 638 | + if (S->warn_none) | |
| 560 | 639 | return; |
| 561 | 640 | } |
| 562 | 641 | |
| 563 | 642 | f = NULL; |
| 564 | − if (s1->error_set_jmp_enabled) { /* we're called while parsing a file */ | |
| 643 | + if (S->error_set_jmp_enabled) { /* we're called while parsing a file */ | |
| 565 | 644 | /* use upper file if inline ":asm:" or token ":paste:" */ |
| 566 | − for (f = file; f && f->filename[0] == ':'; f = f->prev) | |
| 645 | + for (f = S->tccpp_file; f && f->filename[0] == ':'; f = f->prev) | |
| 567 | 646 | ; |
| 568 | 647 | } |
| 569 | 648 | if (f) { |
| 570 | − for(pf = s1->include_stack; pf < s1->include_stack_ptr; pf++) | |
| 571 | − cstr_printf(&cs, "In file included from %s:%d:\n", | |
| 649 | + for(pf = S->include_stack; pf < S->include_stack_ptr; pf++) | |
| 650 | + cstr_printf(S, &cs, "In file included from %s:%d:\n", | |
| 572 | 651 | (*pf)->filename, (*pf)->line_num); |
| 573 | − cstr_printf(&cs, "%s:%d: ", | |
| 574 | − f->filename, f->line_num - !!(tok_flags & TOK_FLAG_BOL)); | |
| 575 | − } else if (s1->current_filename) { | |
| 576 | − cstr_printf(&cs, "%s: ", s1->current_filename); | |
| 652 | + cstr_printf(S, &cs, "%s:%d: ", | |
| 653 | + f->filename, (*pf)->line_num - !!(S->tccpp_tok_flags & TOK_FLAG_BOL)); | |
| 654 | + } else if (S->current_filename) { | |
| 655 | + cstr_printf(S, &cs, "%s: ", S->current_filename); | |
| 577 | 656 | } |
| 578 | 657 | |
| 579 | 658 | no_file: |
| 580 | 659 | if (0 == cs.size) |
| 581 | − cstr_printf(&cs, "tcc: "); | |
| 582 | − cstr_printf(&cs, mode == ERROR_WARN ? "warning: " : "error: "); | |
| 583 | − cstr_vprintf(&cs, fmt, ap); | |
| 584 | − if (!s1 || !s1->error_func) { | |
| 660 | + cstr_printf(S, &cs, "tcc: "); | |
| 661 | + cstr_printf(S, &cs, mode == ERROR_WARN ? "warning: " : "error: "); | |
| 662 | + cstr_vprintf(S, &cs, fmt, ap); | |
| 663 | + if (!S || !S->error_func) { | |
| 585 | 664 | /* default case: stderr */ |
| 586 | − if (s1 && s1->output_type == TCC_OUTPUT_PREPROCESS && s1->ppfp == stdout) | |
| 665 | + if (S && S->output_type == TCC_OUTPUT_PREPROCESS && S->ppfp == stdout) | |
| 587 | 666 | printf("\n"); /* print a newline during tcc -E */ |
| 588 | 667 | fflush(stdout); /* flush -v output */ |
| 589 | 668 | fprintf(stderr, "%s\n", (char*)cs.data); |
| 590 | 669 | fflush(stderr); /* print error/warning now (win32) */ |
| 591 | 670 | } else { |
| 592 | − s1->error_func(s1->error_opaque, (char*)cs.data); | |
| 671 | + S->error_func(S->error_opaque, (char*)cs.data); | |
| 593 | 672 | } |
| 594 | − cstr_free(&cs); | |
| 595 | − if (s1) { | |
| 673 | + cstr_free(S, &cs); | |
| 674 | + if (S) { | |
| 596 | 675 | if (mode != ERROR_WARN) |
| 597 | − s1->nb_errors++; | |
| 676 | + S->nb_errors++; | |
| 598 | 677 | if (mode != ERROR_ERROR) |
| 599 | 678 | return; |
| 600 | − if (s1->error_set_jmp_enabled) | |
| 601 | − longjmp(s1->error_jmp_buf, 1); | |
| 679 | + if (S->error_set_jmp_enabled) | |
| 680 | + longjmp(S->error_jmp_buf, 1); | |
| 602 | 681 | } |
| 603 | 682 | exit(1); |
| 604 | 683 | } |
| 605 | 684 | |
| 606 | −LIBTCCAPI void tcc_set_error_func(TCCState *s, void *error_opaque, TCCErrorFunc error_func) | |
| 685 | +LIBTCCAPI void tcc_set_error_func(TCCState *S, void *error_opaque, TCCErrorFunc error_func) | |
| 607 | 686 | { |
| 608 | − s->error_opaque = error_opaque; | |
| 609 | − s->error_func = error_func; | |
| 687 | + S->error_opaque = error_opaque; | |
| 688 | + S->error_func = error_func; | |
| 610 | 689 | } |
| 611 | 690 | |
| 612 | −LIBTCCAPI TCCErrorFunc tcc_get_error_func(TCCState *s) | |
| 691 | +LIBTCCAPI TCCErrorFunc tcc_get_error_func(TCCState *S) | |
| 613 | 692 | { |
| 614 | − return s->error_func; | |
| 693 | + return S->error_func; | |
| 615 | 694 | } |
| 616 | 695 | |
| 617 | −LIBTCCAPI void *tcc_get_error_opaque(TCCState *s) | |
| 696 | +LIBTCCAPI void *tcc_get_error_opaque(TCCState *S) | |
| 618 | 697 | { |
| 619 | − return s->error_opaque; | |
| 698 | + return S->error_opaque; | |
| 620 | 699 | } |
| 621 | 700 | |
| 622 | 701 | /* error without aborting current compilation */ |
| 623 | −PUB_FUNC void _tcc_error_noabort(const char *fmt, ...) | |
| 702 | +PUB_FUNC void _tcc_error_noabort(TCCState* S, const char *fmt, ...) | |
| 624 | 703 | { |
| 625 | 704 | va_list ap; |
| 626 | 705 | va_start(ap, fmt); |
| 627 | − error1(ERROR_NOABORT, fmt, ap); | |
| 706 | + error1(S, ERROR_NOABORT, fmt, ap); | |
| 628 | 707 | va_end(ap); |
| 629 | 708 | } |
| 630 | 709 | |
| 631 | −PUB_FUNC void _tcc_error(const char *fmt, ...) | |
| 710 | +PUB_FUNC void _tcc_error(TCCState* S, const char *fmt, ...) | |
| 632 | 711 | { |
| 633 | 712 | va_list ap; |
| 634 | 713 | va_start(ap, fmt); |
| 635 | − for (;;) error1(ERROR_ERROR, fmt, ap); | |
| 714 | + for (;;) error1(S, ERROR_ERROR, fmt, ap); | |
| 636 | 715 | } |
| 637 | 716 | |
| 638 | −PUB_FUNC void _tcc_warning(const char *fmt, ...) | |
| 717 | +PUB_FUNC void _tcc_warning(TCCState* S, const char *fmt, ...) | |
| 639 | 718 | { |
| 640 | 719 | va_list ap; |
| 641 | 720 | va_start(ap, fmt); |
| 642 | − error1(ERROR_WARN, fmt, ap); | |
| 721 | + error1(S, ERROR_WARN, fmt, ap); | |
| 643 | 722 | va_end(ap); |
| 644 | 723 | } |
| 645 | 724 | |
| 646 | 725 | /********************************************************/ |
| 647 | 726 | /* I/O layer */ |
| 648 | 727 | |
| 649 | −ST_FUNC void tcc_open_bf(TCCState *s1, const char *filename, int initlen) | |
| 728 | +ST_FUNC void tcc_open_bf(TCCState *S, const char *filename, int initlen) | |
| 650 | 729 | { |
| 651 | 730 | BufferedFile *bf; |
| 652 | 731 | int buflen = initlen ? initlen : IO_BUF_SIZE; |
| 653 | 732 | |
| 654 | − bf = tcc_mallocz(sizeof(BufferedFile) + buflen); | |
| 733 | + bf = tcc_mallocz(S, sizeof(BufferedFile) + buflen); | |
| 655 | 734 | bf->buf_ptr = bf->buffer; |
| 656 | 735 | bf->buf_end = bf->buffer + initlen; |
| 657 | 736 | bf->buf_end[0] = CH_EOB; /* put eob symbol */ |
| @@ -661,52 +740,51 @@ ST_FUNC void tcc_open_bf(TCCState *s1, const char *filename, int initlen) · 3 unmodified lines | ||
| 661 | 740 | #endif |
| 662 | 741 | bf->true_filename = bf->filename; |
| 663 | 742 | bf->line_num = 1; |
| 664 | − bf->ifdef_stack_ptr = s1->ifdef_stack_ptr; | |
| 743 | + bf->ifdef_stack_ptr = S->ifdef_stack_ptr; | |
| 665 | 744 | bf->fd = -1; |
| 666 | − bf->prev = file; | |
| 667 | − file = bf; | |
| 668 | − tok_flags = TOK_FLAG_BOL | TOK_FLAG_BOF; | |
| 745 | + bf->prev = S->tccpp_file; | |
| 746 | + S->tccpp_file = bf; | |
| 747 | + S->tccpp_tok_flags = TOK_FLAG_BOL | TOK_FLAG_BOF; | |
| 669 | 748 | } |
| 670 | 749 | |
| 671 | −ST_FUNC void tcc_close(void) | |
| 750 | +ST_FUNC void tcc_close(TCCState* S) | |
| 672 | 751 | { |
| 673 | − TCCState *s1 = tcc_state; | |
| 674 | − BufferedFile *bf = file; | |
| 752 | + BufferedFile *bf = S->tccpp_file; | |
| 675 | 753 | if (bf->fd > 0) { |
| 676 | 754 | close(bf->fd); |
| 677 | 755 | total_lines += bf->line_num; |
| 678 | 756 | } |
| 679 | 757 | if (bf->true_filename != bf->filename) |
| 680 | − tcc_free(bf->true_filename); | |
| 681 | − file = bf->prev; | |
| 682 | − tcc_free(bf); | |
| 758 | + tcc_free(S, bf->true_filename); | |
| 759 | + S->tccpp_file = bf->prev; | |
| 760 | + tcc_free(S, bf); | |
| 683 | 761 | } |
| 684 | 762 | |
| 685 | −static int _tcc_open(TCCState *s1, const char *filename) | |
| 763 | +static int _tcc_open(TCCState *S, const char *filename) | |
| 686 | 764 | { |
| 687 | 765 | int fd; |
| 688 | 766 | if (strcmp(filename, "-") == 0) |
| 689 | 767 | fd = 0, filename = "<stdin>"; |
| 690 | 768 | else |
| 691 | 769 | fd = open(filename, O_RDONLY | O_BINARY); |
| 692 | − if ((s1->verbose == 2 && fd >= 0) || s1->verbose == 3) | |
| 770 | + if ((S->verbose == 2 && fd >= 0) || S->verbose == 3) | |
| 693 | 771 | printf("%s %*s%s\n", fd < 0 ? "nf":"->", |
| 694 | − (int)(s1->include_stack_ptr - s1->include_stack), "", filename); | |
| 772 | + (int)(S->include_stack_ptr - S->include_stack), "", filename); | |
| 695 | 773 | return fd; |
| 696 | 774 | } |
| 697 | 775 | |
| 698 | −ST_FUNC int tcc_open(TCCState *s1, const char *filename) | |
| 776 | +ST_FUNC int tcc_open(TCCState *S, const char *filename) | |
| 699 | 777 | { |
| 700 | − int fd = _tcc_open(s1, filename); | |
| 778 | + int fd = _tcc_open(S, filename); | |
| 701 | 779 | if (fd < 0) |
| 702 | 780 | return -1; |
| 703 | − tcc_open_bf(s1, filename, 0); | |
| 704 | − file->fd = fd; | |
| 781 | + tcc_open_bf(S, filename, 0); | |
| 782 | + S->tccpp_file->fd = fd; | |
| 705 | 783 | return 0; |
| 706 | 784 | } |
| 707 | 785 | |
| 708 | 786 | /* compile the file opened in 'file'. Return non zero if errors. */ |
| 709 | −static int tcc_compile(TCCState *s1, int filetype, const char *str, int fd) | |
| 787 | +static int tcc_compile(TCCState *S, int filetype, const char *str, int fd) | |
| 710 | 788 | { |
| 711 | 789 | /* Here we enter the code section where we use the global variables for |
| 712 | 790 | parsing and code generation (tccpp.c, tccgen.c, <target>-gen.c). |
| @@ -715,62 +793,62 @@ static int tcc_compile(TCCState *s1, int filetype, const char *str, int fd) · 2 unmodified lines | ||
| 715 | 793 | Alternatively we could use thread local storage for those global |
| 716 | 794 | variables, which may or may not have advantages */ |
| 717 | 795 | |
| 718 | − tcc_enter_state(s1); | |
| 719 | − s1->error_set_jmp_enabled = 1; | |
| 796 | + tcc_enter_state(S); | |
| 797 | + S->error_set_jmp_enabled = 1; | |
| 720 | 798 | |
| 721 | − if (setjmp(s1->error_jmp_buf) == 0) { | |
| 722 | − s1->nb_errors = 0; | |
| 799 | + if (setjmp(S->error_jmp_buf) == 0) { | |
| 800 | + S->nb_errors = 0; | |
| 723 | 801 | |
| 724 | 802 | if (fd == -1) { |
| 725 | 803 | int len = strlen(str); |
| 726 | − tcc_open_bf(s1, "<string>", len); | |
| 727 | − memcpy(file->buffer, str, len); | |
| 804 | + tcc_open_bf(S, "<string>", len); | |
| 805 | + memcpy(S->tccpp_file->buffer, str, len); | |
| 728 | 806 | } else { |
| 729 | − tcc_open_bf(s1, str, 0); | |
| 730 | − file->fd = fd; | |
| 807 | + tcc_open_bf(S, str, 0); | |
| 808 | + S->tccpp_file->fd = fd; | |
| 731 | 809 | } |
| 732 | 810 | |
| 733 | − tccelf_begin_file(s1); | |
| 734 | − preprocess_start(s1, filetype); | |
| 735 | − tccgen_init(s1); | |
| 736 | − if (s1->output_type == TCC_OUTPUT_PREPROCESS) { | |
| 737 | − tcc_preprocess(s1); | |
| 811 | + tccelf_begin_file(S); | |
| 812 | + preprocess_start(S, filetype); | |
| 813 | + tccgen_init(S); | |
| 814 | + if (S->output_type == TCC_OUTPUT_PREPROCESS) { | |
| 815 | + tcc_preprocess(S); | |
| 738 | 816 | } else if (filetype & (AFF_TYPE_ASM | AFF_TYPE_ASMPP)) { |
| 739 | − tcc_assemble(s1, !!(filetype & AFF_TYPE_ASMPP)); | |
| 817 | + tcc_assemble(S, !!(filetype & AFF_TYPE_ASMPP)); | |
| 740 | 818 | } else { |
| 741 | − tccgen_compile(s1); | |
| 819 | + tccgen_compile(S); | |
| 742 | 820 | } |
| 743 | 821 | } |
| 744 | − tccgen_finish(s1); | |
| 745 | − preprocess_end(s1); | |
| 822 | + tccgen_finish(S); | |
| 823 | + preprocess_end(S); | |
| 746 | 824 | |
| 747 | − s1->error_set_jmp_enabled = 0; | |
| 748 | − tcc_exit_state(s1); | |
| 825 | + S->error_set_jmp_enabled = 0; | |
| 826 | + tcc_exit_state(S); | |
| 749 | 827 | |
| 750 | − tccelf_end_file(s1); | |
| 751 | − return s1->nb_errors != 0 ? -1 : 0; | |
| 828 | + tccelf_end_file(S); | |
| 829 | + return S->nb_errors != 0 ? -1 : 0; | |
| 752 | 830 | } |
| 753 | 831 | |
| 754 | −LIBTCCAPI int tcc_compile_string(TCCState *s, const char *str) | |
| 832 | +LIBTCCAPI int tcc_compile_string(TCCState *S, const char *str) | |
| 755 | 833 | { |
| 756 | − return tcc_compile(s, s->filetype, str, -1); | |
| 834 | + return tcc_compile(S, S->filetype, str, -1); | |
| 757 | 835 | } |
| 758 | 836 | |
| 759 | 837 | /* define a preprocessor symbol. value can be NULL, sym can be "sym=val" */ |
| 760 | −LIBTCCAPI void tcc_define_symbol(TCCState *s1, const char *sym, const char *value) | |
| 838 | +LIBTCCAPI void tcc_define_symbol(TCCState *S, const char *sym, const char *value) | |
| 761 | 839 | { |
| 762 | 840 | const char *eq; |
| 763 | 841 | if (NULL == (eq = strchr(sym, '='))) |
| 764 | 842 | eq = strchr(sym, 0); |
| 765 | 843 | if (NULL == value) |
| 766 | 844 | value = *eq ? eq + 1 : "1"; |
| 767 | − cstr_printf(&s1->cmdline_defs, "#define %.*s %s\n", (int)(eq-sym), sym, value); | |
| 845 | + cstr_printf(S, &S->cmdline_defs, "#define %.*s %s\n", (int)(eq-sym), sym, value); | |
| 768 | 846 | } |
| 769 | 847 | |
| 770 | 848 | /* undefine a preprocessor symbol */ |
| 771 | −LIBTCCAPI void tcc_undefine_symbol(TCCState *s1, const char *sym) | |
| 849 | +LIBTCCAPI void tcc_undefine_symbol(TCCState *S, const char *sym) | |
| 772 | 850 | { |
| 773 | − cstr_printf(&s1->cmdline_defs, "#undef %s\n", sym); | |
| 851 | + cstr_printf(S, &S->cmdline_defs, "#undef %s\n", sym); | |
| 774 | 852 | } |
| 775 | 853 | |
| 776 | 854 | |
| @@ -778,7 +856,7 @@ LIBTCCAPI TCCState *tcc_new(void) · 1 unmodified line | ||
| 778 | 856 | { |
| 779 | 857 | TCCState *s; |
| 780 | 858 | |
| 781 | − s = tcc_mallocz(sizeof(TCCState)); | |
| 859 | + s = tcc_mallocz_base(sizeof(TCCState)); | |
| 782 | 860 | if (!s) |
| 783 | 861 | return NULL; |
| 784 | 862 | #ifdef MEM_DEBUG |
| @@ -820,153 +898,153 @@ LIBTCCAPI TCCState *tcc_new(void) · 35 unmodified lines | ||
| 820 | 898 | return s; |
| 821 | 899 | } |
| 822 | 900 | |
| 823 | −LIBTCCAPI void tcc_delete(TCCState *s1) | |
| 901 | +LIBTCCAPI void tcc_delete(TCCState *S) | |
| 824 | 902 | { |
| 825 | 903 | /* free sections */ |
| 826 | − tccelf_delete(s1); | |
| 904 | + tccelf_delete(S); | |
| 827 | 905 | |
| 828 | 906 | /* free library paths */ |
| 829 | − dynarray_reset(&s1->library_paths, &s1->nb_library_paths); | |
| 830 | − dynarray_reset(&s1->crt_paths, &s1->nb_crt_paths); | |
| 907 | + dynarray_reset(S, &S->library_paths, &S->nb_library_paths); | |
| 908 | + dynarray_reset(S, &S->crt_paths, &S->nb_crt_paths); | |
| 831 | 909 | |
| 832 | 910 | /* free include paths */ |
| 833 | − dynarray_reset(&s1->include_paths, &s1->nb_include_paths); | |
| 834 | − dynarray_reset(&s1->sysinclude_paths, &s1->nb_sysinclude_paths); | |
| 835 | − | |
| 836 | − tcc_free(s1->tcc_lib_path); | |
| 837 | − tcc_free(s1->soname); | |
| 838 | − tcc_free(s1->rpath); | |
| 839 | − tcc_free(s1->init_symbol); | |
| 840 | − tcc_free(s1->fini_symbol); | |
| 841 | − tcc_free(s1->outfile); | |
| 842 | − tcc_free(s1->deps_outfile); | |
| 843 | − dynarray_reset(&s1->files, &s1->nb_files); | |
| 844 | − dynarray_reset(&s1->target_deps, &s1->nb_target_deps); | |
| 845 | − dynarray_reset(&s1->pragma_libs, &s1->nb_pragma_libs); | |
| 846 | − dynarray_reset(&s1->argv, &s1->argc); | |
| 847 | − cstr_free(&s1->cmdline_defs); | |
| 848 | − cstr_free(&s1->cmdline_incl); | |
| 911 | + dynarray_reset(S, &S->include_paths, &S->nb_include_paths); | |
| 912 | + dynarray_reset(S, &S->sysinclude_paths, &S->nb_sysinclude_paths); | |
| 913 | + | |
| 914 | + tcc_free(S, S->tcc_lib_path); | |
| 915 | + tcc_free(S, S->soname); | |
| 916 | + tcc_free(S, S->rpath); | |
| 917 | + tcc_free(S, S->init_symbol); | |
| 918 | + tcc_free(S, S->fini_symbol); | |
| 919 | + tcc_free(S, S->outfile); | |
| 920 | + tcc_free(S, S->deps_outfile); | |
| 921 | + dynarray_reset(S, &S->files, &S->nb_files); | |
| 922 | + dynarray_reset(S, &S->target_deps, &S->nb_target_deps); | |
| 923 | + dynarray_reset(S, &S->pragma_libs, &S->nb_pragma_libs); | |
| 924 | + dynarray_reset(S, &S->argv, &S->argc); | |
| 925 | + cstr_free(S, &S->cmdline_defs); | |
| 926 | + cstr_free(S, &S->cmdline_incl); | |
| 849 | 927 | #ifdef TCC_IS_NATIVE |
| 850 | 928 | /* free runtime memory */ |
| 851 | − tcc_run_free(s1); | |
| 929 | + tcc_run_free(S); | |
| 852 | 930 | #endif |
| 853 | 931 | |
| 854 | − tcc_free(s1); | |
| 932 | + tcc_free_base(S); | |
| 855 | 933 | #ifdef MEM_DEBUG |
| 856 | 934 | if (0 == --nb_states) |
| 857 | 935 | tcc_memcheck(); |
| 858 | 936 | #endif |
| 859 | 937 | } |
| 860 | 938 | |
| 861 | −LIBTCCAPI int tcc_set_output_type(TCCState *s, int output_type) | |
| 939 | +LIBTCCAPI int tcc_set_output_type(TCCState *S, int output_type) | |
| 862 | 940 | { |
| 863 | − s->output_type = output_type; | |
| 941 | + S->output_type = output_type; | |
| 864 | 942 | |
| 865 | − if (!s->nostdinc) { | |
| 943 | + if (!S->nostdinc) { | |
| 866 | 944 | /* default include paths */ |
| 867 | 945 | /* -isystem paths have already been handled */ |
| 868 | − tcc_add_sysinclude_path(s, CONFIG_TCC_SYSINCLUDEPATHS); | |
| 946 | + tcc_add_sysinclude_path(S, CONFIG_TCC_SYSINCLUDEPATHS); | |
| 869 | 947 | } |
| 870 | 948 | #ifdef CONFIG_TCC_BCHECK |
| 871 | − if (s->do_bounds_check) { | |
| 949 | + if (S->do_bounds_check) { | |
| 872 | 950 | /* if bound checking, then add corresponding sections */ |
| 873 | − tccelf_bounds_new(s); | |
| 951 | + tccelf_bounds_new(S); | |
| 874 | 952 | } |
| 875 | 953 | #endif |
| 876 | − if (s->do_debug) { | |
| 954 | + if (S->do_debug) { | |
| 877 | 955 | /* add debug sections */ |
| 878 | − tccelf_stab_new(s); | |
| 956 | + tccelf_stab_new(S); | |
| 879 | 957 | } |
| 880 | 958 | if (output_type == TCC_OUTPUT_OBJ) { |
| 881 | 959 | /* always elf for objects */ |
| 882 | − s->output_format = TCC_OUTPUT_FORMAT_ELF; | |
| 960 | + S->output_format = TCC_OUTPUT_FORMAT_ELF; | |
| 883 | 961 | return 0; |
| 884 | 962 | } |
| 885 | 963 | |
| 886 | − tcc_add_library_path(s, CONFIG_TCC_LIBPATHS); | |
| 964 | + tcc_add_library_path(S, CONFIG_TCC_LIBPATHS); | |
| 887 | 965 | |
| 888 | 966 | #ifdef TCC_TARGET_PE |
| 889 | 967 | # ifdef _WIN32 |
| 890 | 968 | /* allow linking with system dll's directly */ |
| 891 | − tcc_add_systemdir(s); | |
| 969 | + tcc_add_systemdir(S); | |
| 892 | 970 | # endif |
| 893 | 971 | /* target PE has its own startup code in libtcc1.a */ |
| 894 | 972 | return 0; |
| 895 | 973 | |
| 896 | 974 | #elif defined TCC_TARGET_MACHO |
| 897 | 975 | # ifdef TCC_IS_NATIVE |
| 898 | − tcc_add_macos_sdkpath(s); | |
| 976 | + tcc_add_macos_sdkpath(S); | |
| 899 | 977 | # endif |
| 900 | 978 | /* Mach-O with LC_MAIN doesn't need any crt startup code. */ |
| 901 | 979 | return 0; |
| 902 | 980 | |
| 903 | 981 | #else |
| 904 | 982 | /* paths for crt objects */ |
| 905 | − tcc_split_path(s, &s->crt_paths, &s->nb_crt_paths, CONFIG_TCC_CRTPREFIX); | |
| 983 | + tcc_split_path(S, &S->crt_paths, &S->nb_crt_paths, CONFIG_TCC_CRTPREFIX); | |
| 906 | 984 | /* add libc crt1/crti objects */ |
| 907 | 985 | if ((output_type == TCC_OUTPUT_EXE || output_type == TCC_OUTPUT_DLL) && |
| 908 | − !s->nostdlib) { | |
| 986 | + !S->nostdlib) { | |
| 909 | 987 | #if TARGETOS_OpenBSD |
| 910 | 988 | if (output_type != TCC_OUTPUT_DLL) |
| 911 | − tcc_add_crt(s, "crt0.o"); | |
| 989 | + tcc_add_crt(S, "crt0.o"); | |
| 912 | 990 | if (output_type == TCC_OUTPUT_DLL) |
| 913 | − tcc_add_crt(s, "crtbeginS.o"); | |
| 991 | + tcc_add_crt(S, "crtbeginS.o"); | |
| 914 | 992 | else |
| 915 | − tcc_add_crt(s, "crtbegin.o"); | |
| 993 | + tcc_add_crt(S, "crtbegin.o"); | |
| 916 | 994 | #elif TARGETOS_FreeBSD |
| 917 | 995 | if (output_type != TCC_OUTPUT_DLL) |
| 918 | − tcc_add_crt(s, "crt1.o"); | |
| 919 | − tcc_add_crt(s, "crti.o"); | |
| 920 | − if (s->static_link) | |
| 921 | − tcc_add_crt(s, "crtbeginT.o"); | |
| 996 | + tcc_add_crt(S, "crt1.o"); | |
| 997 | + tcc_add_crt(S, "crti.o"); | |
| 998 | + if (S->static_link) | |
| 999 | + tcc_add_crt(S, "crtbeginT.o"); | |
| 922 | 1000 | else if (output_type == TCC_OUTPUT_DLL) |
| 923 | − tcc_add_crt(s, "crtbeginS.o"); | |
| 1001 | + tcc_add_crt(S, "crtbeginS.o"); | |
| 924 | 1002 | else |
| 925 | − tcc_add_crt(s, "crtbegin.o"); | |
| 1003 | + tcc_add_crt(S, "crtbegin.o"); | |
| 926 | 1004 | #elif TARGETOS_NetBSD |
| 927 | 1005 | if (output_type != TCC_OUTPUT_DLL) |
| 928 | − tcc_add_crt(s, "crt0.o"); | |
| 929 | − tcc_add_crt(s, "crti.o"); | |
| 930 | − if (s->static_link) | |
| 931 | − tcc_add_crt(s, "crtbeginT.o"); | |
| 1006 | + tcc_add_crt(S, "crt0.o"); | |
| 1007 | + tcc_add_crt(S, "crti.o"); | |
| 1008 | + if (S->static_link) | |
| 1009 | + tcc_add_crt(S, "crtbeginT.o"); | |
| 932 | 1010 | else if (output_type == TCC_OUTPUT_DLL) |
| 933 | − tcc_add_crt(s, "crtbeginS.o"); | |
| 1011 | + tcc_add_crt(S, "crtbeginS.o"); | |
| 934 | 1012 | else |
| 935 | − tcc_add_crt(s, "crtbegin.o"); | |
| 1013 | + tcc_add_crt(S, "crtbegin.o"); | |
| 936 | 1014 | #else |
| 937 | 1015 | if (output_type != TCC_OUTPUT_DLL) |
| 938 | − tcc_add_crt(s, "crt1.o"); | |
| 939 | − tcc_add_crt(s, "crti.o"); | |
| 1016 | + tcc_add_crt(S, "crt1.o"); | |
| 1017 | + tcc_add_crt(S, "crti.o"); | |
| 940 | 1018 | #endif |
| 941 | 1019 | } |
| 942 | 1020 | return 0; |
| 943 | 1021 | #endif |
| 944 | 1022 | } |
| 945 | 1023 | |
| 946 | −LIBTCCAPI int tcc_add_include_path(TCCState *s, const char *pathname) | |
| 1024 | +LIBTCCAPI int tcc_add_include_path(TCCState *S, const char *pathname) | |
| 947 | 1025 | { |
| 948 | − tcc_split_path(s, &s->include_paths, &s->nb_include_paths, pathname); | |
| 1026 | + tcc_split_path(S, &S->include_paths, &S->nb_include_paths, pathname); | |
| 949 | 1027 | return 0; |
| 950 | 1028 | } |
| 951 | 1029 | |
| 952 | −LIBTCCAPI int tcc_add_sysinclude_path(TCCState *s, const char *pathname) | |
| 1030 | +LIBTCCAPI int tcc_add_sysinclude_path(TCCState *S, const char *pathname) | |
| 953 | 1031 | { |
| 954 | − tcc_split_path(s, &s->sysinclude_paths, &s->nb_sysinclude_paths, pathname); | |
| 1032 | + tcc_split_path(S, &S->sysinclude_paths, &S->nb_sysinclude_paths, pathname); | |
| 955 | 1033 | return 0; |
| 956 | 1034 | } |
| 957 | 1035 | |
| 958 | −ST_FUNC DLLReference *tcc_add_dllref(TCCState *s1, const char *dllname) | |
| 1036 | +ST_FUNC DLLReference *tcc_add_dllref(TCCState *S, const char *dllname) | |
| 959 | 1037 | { |
| 960 | − DLLReference *ref = tcc_mallocz(sizeof(DLLReference) + strlen(dllname)); | |
| 1038 | + DLLReference *ref = tcc_mallocz(S, sizeof(DLLReference) + strlen(dllname)); | |
| 961 | 1039 | strcpy(ref->name, dllname); |
| 962 | − dynarray_add(&s1->loaded_dlls, &s1->nb_loaded_dlls, ref); | |
| 1040 | + dynarray_add(S, &S->loaded_dlls, &S->nb_loaded_dlls, ref); | |
| 963 | 1041 | return ref; |
| 964 | 1042 | } |
| 965 | 1043 | |
| 966 | 1044 | /* OpenBSD: choose latest from libxxx.so.x.y versions */ |
| 967 | 1045 | #if defined TARGETOS_OpenBSD && !defined _WIN32 |
| 968 | 1046 | #include <glob.h> |
| 969 | −static int tcc_glob_so(TCCState *s1, const char *pattern, char *buf, int size) | |
| 1047 | +static int tcc_glob_so(TCCState *S, const char *pattern, char *buf, int size) | |
| 970 | 1048 | { |
| 971 | 1049 | const char *star; |
| 972 | 1050 | glob_t g; |
| @@ -988,25 +1066,25 @@ static int tcc_glob_so(TCCState *s1, const char *pattern, char *buf, int size) · 15 unmodified lines | ||
| 988 | 1066 | } |
| 989 | 1067 | #endif |
| 990 | 1068 | |
| 991 | −ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags) | |
| 1069 | +ST_FUNC int tcc_add_file_internal(TCCState *S, const char *filename, int flags) | |
| 992 | 1070 | { |
| 993 | 1071 | int fd, ret = -1; |
| 994 | 1072 | |
| 995 | 1073 | #if defined TARGETOS_OpenBSD && !defined _WIN32 |
| 996 | 1074 | char buf[1024]; |
| 997 | − if (tcc_glob_so(s1, filename, buf, sizeof buf) >= 0) | |
| 1075 | + if (tcc_glob_so(S, filename, buf, sizeof buf) >= 0) | |
| 998 | 1076 | filename = buf; |
| 999 | 1077 | #endif |
| 1000 | 1078 | |
| 1001 | 1079 | /* open the file */ |
| 1002 | − fd = _tcc_open(s1, filename); | |
| 1080 | + fd = _tcc_open(S, filename); | |
| 1003 | 1081 | if (fd < 0) { |
| 1004 | 1082 | if (flags & AFF_PRINT_ERROR) |
| 1005 | − tcc_error_noabort("file '%s' not found", filename); | |
| 1083 | + tcc_error_noabort(S, "file '%s' not found", filename); | |
| 1006 | 1084 | return ret; |
| 1007 | 1085 | } |
| 1008 | 1086 | |
| 1009 | − s1->current_filename = filename; | |
| 1087 | + S->current_filename = filename; | |
| 1010 | 1088 | if (flags & AFF_TYPE_BIN) { |
| 1011 | 1089 | ElfW(Ehdr) ehdr; |
| 1012 | 1090 | int obj_type; |
| @@ -1017,22 +1095,22 @@ ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags) · 4 unmodified lines | ||
| 1017 | 1095 | switch (obj_type) { |
| 1018 | 1096 | |
| 1019 | 1097 | case AFF_BINTYPE_REL: |
| 1020 | − ret = tcc_load_object_file(s1, fd, 0); | |
| 1098 | + ret = tcc_load_object_file(S, fd, 0); | |
| 1021 | 1099 | break; |
| 1022 | 1100 | |
| 1023 | 1101 | case AFF_BINTYPE_AR: |
| 1024 | − ret = tcc_load_archive(s1, fd, !(flags & AFF_WHOLE_ARCHIVE)); | |
| 1102 | + ret = tcc_load_archive(S, fd, !(flags & AFF_WHOLE_ARCHIVE)); | |
| 1025 | 1103 | break; |
| 1026 | 1104 | |
| 1027 | 1105 | #ifdef TCC_TARGET_PE |
| 1028 | 1106 | default: |
| 1029 | − ret = pe_load_file(s1, fd, filename); | |
| 1107 | + ret = pe_load_file(S, fd, filename); | |
| 1030 | 1108 | goto check_success; |
| 1031 | 1109 | |
| 1032 | 1110 | #elif defined TCC_TARGET_MACHO |
| 1033 | 1111 | case AFF_BINTYPE_DYN: |
| 1034 | 1112 | case_dyn_or_tbd: |
| 1035 | − if (s1->output_type == TCC_OUTPUT_MEMORY) { | |
| 1113 | + if (S->output_type == TCC_OUTPUT_MEMORY) { | |
| 1036 | 1114 | #ifdef TCC_IS_NATIVE |
| 1037 | 1115 | void* dl; |
| 1038 | 1116 | const char* soname = filename; |
| @@ -1040,14 +1118,14 @@ ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags) · 1 unmodified line | ||
| 1040 | 1118 | soname = macho_tbd_soname(filename); |
| 1041 | 1119 | dl = dlopen(soname, RTLD_GLOBAL | RTLD_LAZY); |
| 1042 | 1120 | if (dl) |
| 1043 | − tcc_add_dllref(s1, soname)->handle = dl, ret = 0; | |
| 1121 | + tcc_add_dllref(S, soname)->handle = dl, ret = 0; | |
| 1044 | 1122 | if (filename != soname) |
| 1045 | − tcc_free((void *)soname); | |
| 1123 | + tcc_free(S, (void *)soname); | |
| 1046 | 1124 | #endif |
| 1047 | 1125 | } else if (obj_type == AFF_BINTYPE_DYN) { |
| 1048 | − ret = macho_load_dll(s1, fd, filename, (flags & AFF_REFERENCED_DLL) != 0); | |
| 1126 | + ret = macho_load_dll(S, fd, filename, (flags & AFF_REFERENCED_DLL) != 0); | |
| 1049 | 1127 | } else { |
| 1050 | − ret = macho_load_tbd(s1, fd, filename, (flags & AFF_REFERENCED_DLL) != 0); | |
| 1128 | + ret = macho_load_tbd(S, fd, filename, (flags & AFF_REFERENCED_DLL) != 0); | |
| 1051 | 1129 | } |
| 1052 | 1130 | break; |
| 1053 | 1131 | default: |
| @@ -1064,47 +1142,47 @@ ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags) · 10 unmodified lines | ||
| 1064 | 1142 | |
| 1065 | 1143 | #else /* unix */ |
| 1066 | 1144 | case AFF_BINTYPE_DYN: |
| 1067 | − if (s1->output_type == TCC_OUTPUT_MEMORY) { | |
| 1145 | + if (S->output_type == TCC_OUTPUT_MEMORY) { | |
| 1068 | 1146 | #ifdef TCC_IS_NATIVE |
| 1069 | 1147 | void* dl = dlopen(filename, RTLD_GLOBAL | RTLD_LAZY); |
| 1070 | 1148 | if (dl) |
| 1071 | − tcc_add_dllref(s1, filename)->handle = dl, ret = 0; | |
| 1149 | + tcc_add_dllref(S, filename)->handle = dl, ret = 0; | |
| 1072 | 1150 | #endif |
| 1073 | 1151 | } else |
| 1074 | − ret = tcc_load_dll(s1, fd, filename, (flags & AFF_REFERENCED_DLL) != 0); | |
| 1152 | + ret = tcc_load_dll(S, fd, filename, (flags & AFF_REFERENCED_DLL) != 0); | |
| 1075 | 1153 | break; |
| 1076 | 1154 | |
| 1077 | 1155 | default: |
| 1078 | 1156 | /* as GNU ld, consider it is an ld script if not recognized */ |
| 1079 | − ret = tcc_load_ldscript(s1, fd); | |
| 1157 | + ret = tcc_load_ldscript(S, fd); | |
| 1080 | 1158 | goto check_success; |
| 1081 | 1159 | |
| 1082 | 1160 | #endif /* pe / macos / unix */ |
| 1083 | 1161 | |
| 1084 | 1162 | check_success: |
| 1085 | 1163 | if (ret < 0) |
| 1086 | − tcc_error_noabort("%s: unrecognized file type", filename); | |
| 1164 | + tcc_error_noabort(S, "%s: unrecognized file type", filename); | |
| 1087 | 1165 | break; |
| 1088 | 1166 | |
| 1089 | 1167 | #ifdef TCC_TARGET_COFF |
| 1090 | 1168 | case AFF_BINTYPE_C67: |
| 1091 | − ret = tcc_load_coff(s1, fd); | |
| 1169 | + ret = tcc_load_coff(S, fd); | |
| 1092 | 1170 | break; |
| 1093 | 1171 | #endif |
| 1094 | 1172 | } |
| 1095 | 1173 | close(fd); |
| 1096 | 1174 | } else { |
| 1097 | 1175 | /* update target deps */ |
| 1098 | − dynarray_add(&s1->target_deps, &s1->nb_target_deps, tcc_strdup(filename)); | |
| 1099 | − ret = tcc_compile(s1, flags, filename, fd); | |
| 1176 | + dynarray_add(S, &S->target_deps, &S->nb_target_deps, tcc_strdup(S, filename)); | |
| 1177 | + ret = tcc_compile(S, flags, filename, fd); | |
| 1100 | 1178 | } |
| 1101 | − s1->current_filename = NULL; | |
| 1179 | + S->current_filename = NULL; | |
| 1102 | 1180 | return ret; |
| 1103 | 1181 | } |
| 1104 | 1182 | |
| 1105 | −LIBTCCAPI int tcc_add_file(TCCState *s, const char *filename) | |
| 1183 | +LIBTCCAPI int tcc_add_file(TCCState *S, const char *filename) | |
| 1106 | 1184 | { |
| 1107 | − int filetype = s->filetype; | |
| 1185 | + int filetype = S->filetype; | |
| 1108 | 1186 | if (0 == (filetype & AFF_TYPE_MASK)) { |
| 1109 | 1187 | /* use a file extension to detect a filetype */ |
| 1110 | 1188 | const char *ext = tcc_fileextension(filename); |
| @@ -1124,16 +1202,16 @@ LIBTCCAPI int tcc_add_file(TCCState *s, const char *filename) · 13 unmodified lines | ||
| 1124 | 1202 | filetype = AFF_TYPE_C; |
| 1125 | 1203 | } |
| 1126 | 1204 | } |
| 1127 | − return tcc_add_file_internal(s, filename, filetype | AFF_PRINT_ERROR); | |
| 1205 | + return tcc_add_file_internal(S, filename, filetype | AFF_PRINT_ERROR); | |
| 1128 | 1206 | } |
| 1129 | 1207 | |
| 1130 | −LIBTCCAPI int tcc_add_library_path(TCCState *s, const char *pathname) | |
| 1208 | +LIBTCCAPI int tcc_add_library_path(TCCState *S, const char *pathname) | |
| 1131 | 1209 | { |
| 1132 | − tcc_split_path(s, &s->library_paths, &s->nb_library_paths, pathname); | |
| 1210 | + tcc_split_path(S, &S->library_paths, &S->nb_library_paths, pathname); | |
| 1133 | 1211 | return 0; |
| 1134 | 1212 | } |
| 1135 | 1213 | |
| 1136 | −static int tcc_add_library_internal(TCCState *s, const char *fmt, | |
| 1214 | +static int tcc_add_library_internal(TCCState *S, const char *fmt, | |
| 1137 | 1215 | const char *filename, int flags, char **paths, int nb_paths) |
| 1138 | 1216 | { |
| 1139 | 1217 | char buf[1024]; |
| @@ -1141,7 +1219,7 @@ static int tcc_add_library_internal(TCCState *s, const char *fmt, · 1 unmodified line | ||
| 1141 | 1219 | |
| 1142 | 1220 | for(i = 0; i < nb_paths; i++) { |
| 1143 | 1221 | snprintf(buf, sizeof(buf), fmt, paths[i], filename); |
| 1144 | − if (tcc_add_file_internal(s, buf, flags | AFF_TYPE_BIN) == 0) | |
| 1222 | + if (tcc_add_file_internal(S, buf, flags | AFF_TYPE_BIN) == 0) | |
| 1145 | 1223 | return 0; |
| 1146 | 1224 | } |
| 1147 | 1225 | return -1; |
| @@ -1150,87 +1228,87 @@ static int tcc_add_library_internal(TCCState *s, const char *fmt, · 2 unmodified lines | ||
| 1150 | 1228 | #ifndef TCC_TARGET_MACHO |
| 1151 | 1229 | /* find and load a dll. Return non zero if not found */ |
| 1152 | 1230 | /* XXX: add '-rpath' option support ? */ |
| 1153 | −ST_FUNC int tcc_add_dll(TCCState *s, const char *filename, int flags) | |
| 1231 | +ST_FUNC int tcc_add_dll(TCCState *S, const char *filename, int flags) | |
| 1154 | 1232 | { |
| 1155 | − return tcc_add_library_internal(s, "%s/%s", filename, flags, | |
| 1156 | − s->library_paths, s->nb_library_paths); | |
| 1233 | + return tcc_add_library_internal(S, "%s/%s", filename, flags, | |
| 1234 | + S->library_paths, S->nb_library_paths); | |
| 1157 | 1235 | } |
| 1158 | 1236 | #endif |
| 1159 | 1237 | |
| 1160 | 1238 | #if !defined TCC_TARGET_PE && !defined TCC_TARGET_MACHO |
| 1161 | −ST_FUNC int tcc_add_crt(TCCState *s1, const char *filename) | |
| 1239 | +ST_FUNC int tcc_add_crt(TCCState *S, const char *filename) | |
| 1162 | 1240 | { |
| 1163 | − if (-1 == tcc_add_library_internal(s1, "%s/%s", | |
| 1164 | − filename, 0, s1->crt_paths, s1->nb_crt_paths)) | |
| 1165 | − tcc_error_noabort("file '%s' not found", filename); | |
| 1241 | + if (-1 == tcc_add_library_internal(S, "%s/%s", | |
| 1242 | + filename, 0, S->crt_paths, S->nb_crt_paths)) | |
| 1243 | + tcc_error_noabort(S, "file '%s' not found", filename); | |
| 1166 | 1244 | return 0; |
| 1167 | 1245 | } |
| 1168 | 1246 | #endif |
| 1169 | 1247 | |
| 1170 | 1248 | /* the library name is the same as the argument of the '-l' option */ |
| 1171 | −LIBTCCAPI int tcc_add_library(TCCState *s, const char *libraryname) | |
| 1249 | +LIBTCCAPI int tcc_add_library(TCCState *S, const char *libraryname) | |
| 1172 | 1250 | { |
| 1173 | 1251 | #if defined TCC_TARGET_PE |
| 1174 | 1252 | static const char * const libs[] = { "%s/%s.def", "%s/lib%s.def", "%s/%s.dll", "%s/lib%s.dll", "%s/lib%s.a", NULL }; |
| 1175 | − const char * const *pp = s->static_link ? libs + 4 : libs; | |
| 1253 | + const char * const *pp = S->static_link ? libs + 4 : libs; | |
| 1176 | 1254 | #elif defined TCC_TARGET_MACHO |
| 1177 | 1255 | static const char * const libs[] = { "%s/lib%s.dylib", "%s/lib%s.tbd", "%s/lib%s.a", NULL }; |
| 1178 | − const char * const *pp = s->static_link ? libs + 2 : libs; | |
| 1256 | + const char * const *pp = S->static_link ? libs + 2 : libs; | |
| 1179 | 1257 | #elif defined TARGETOS_OpenBSD |
| 1180 | 1258 | static const char * const libs[] = { "%s/lib%s.so.*", "%s/lib%s.a", NULL }; |
| 1181 | − const char * const *pp = s->static_link ? libs + 1 : libs; | |
| 1259 | + const char * const *pp = S->static_link ? libs + 1 : libs; | |
| 1182 | 1260 | #else |
| 1183 | 1261 | static const char * const libs[] = { "%s/lib%s.so", "%s/lib%s.a", NULL }; |
| 1184 | − const char * const *pp = s->static_link ? libs + 1 : libs; | |
| 1262 | + const char * const *pp = S->static_link ? libs + 1 : libs; | |
| 1185 | 1263 | #endif |
| 1186 | − int flags = s->filetype & AFF_WHOLE_ARCHIVE; | |
| 1264 | + int flags = S->filetype & AFF_WHOLE_ARCHIVE; | |
| 1187 | 1265 | while (*pp) { |
| 1188 | − if (0 == tcc_add_library_internal(s, *pp, | |
| 1189 | − libraryname, flags, s->library_paths, s->nb_library_paths)) | |
| 1266 | + if (0 == tcc_add_library_internal(S, *pp, | |
| 1267 | + libraryname, flags, S->library_paths, S->nb_library_paths)) | |
| 1190 | 1268 | return 0; |
| 1191 | 1269 | ++pp; |
| 1192 | 1270 | } |
| 1193 | 1271 | return -1; |
| 1194 | 1272 | } |
| 1195 | 1273 | |
| 1196 | −PUB_FUNC int tcc_add_library_err(TCCState *s1, const char *libname) | |
| 1274 | +PUB_FUNC int tcc_add_library_err(TCCState *S, const char *libname) | |
| 1197 | 1275 | { |
| 1198 | − int ret = tcc_add_library(s1, libname); | |
| 1276 | + int ret = tcc_add_library(S, libname); | |
| 1199 | 1277 | if (ret < 0) |
| 1200 | − tcc_error_noabort("library '%s' not found", libname); | |
| 1278 | + tcc_error_noabort(S, "library '%s' not found", libname); | |
| 1201 | 1279 | return ret; |
| 1202 | 1280 | } |
| 1203 | 1281 | |
| 1204 | 1282 | /* handle #pragma comment(lib,) */ |
| 1205 | −ST_FUNC void tcc_add_pragma_libs(TCCState *s1) | |
| 1283 | +ST_FUNC void tcc_add_pragma_libs(TCCState *S) | |
| 1206 | 1284 | { |
| 1207 | 1285 | int i; |
| 1208 | − for (i = 0; i < s1->nb_pragma_libs; i++) | |
| 1209 | − tcc_add_library_err(s1, s1->pragma_libs[i]); | |
| 1286 | + for (i = 0; i < S->nb_pragma_libs; i++) | |
| 1287 | + tcc_add_library_err(S, S->pragma_libs[i]); | |
| 1210 | 1288 | } |
| 1211 | 1289 | |
| 1212 | −LIBTCCAPI int tcc_add_symbol(TCCState *s1, const char *name, const void *val) | |
| 1290 | +LIBTCCAPI int tcc_add_symbol(TCCState *S, const char *name, const void *val) | |
| 1213 | 1291 | { |
| 1214 | 1292 | #ifdef TCC_TARGET_PE |
| 1215 | 1293 | /* On x86_64 'val' might not be reachable with a 32bit offset. |
| 1216 | 1294 | So it is handled here as if it were in a DLL. */ |
| 1217 | − pe_putimport(s1, 0, name, (uintptr_t)val); | |
| 1295 | + pe_putimport(S, 0, name, (uintptr_t)val); | |
| 1218 | 1296 | #else |
| 1219 | 1297 | char buf[256]; |
| 1220 | − if (s1->leading_underscore) { | |
| 1298 | + if (S->leading_underscore) { | |
| 1221 | 1299 | buf[0] = '_'; |
| 1222 | 1300 | pstrcpy(buf + 1, sizeof(buf) - 1, name); |
| 1223 | 1301 | name = buf; |
| 1224 | 1302 | } |
| 1225 | − set_global_sym(s1, name, NULL, (addr_t)(uintptr_t)val); /* NULL: SHN_ABS */ | |
| 1303 | + set_global_sym(S, name, NULL, (addr_t)(uintptr_t)val); /* NULL: SHN_ABS */ | |
| 1226 | 1304 | #endif |
| 1227 | 1305 | return 0; |
| 1228 | 1306 | } |
| 1229 | 1307 | |
| 1230 | −LIBTCCAPI void tcc_set_lib_path(TCCState *s, const char *path) | |
| 1308 | +LIBTCCAPI void tcc_set_lib_path(TCCState *S, const char *path) | |
| 1231 | 1309 | { |
| 1232 | − tcc_free(s->tcc_lib_path); | |
| 1233 | − s->tcc_lib_path = tcc_strdup(path); | |
| 1310 | + tcc_free(S, S->tcc_lib_path); | |
| 1311 | + S->tcc_lib_path = tcc_strdup(S, path); | |
| 1234 | 1312 | } |
| 1235 | 1313 | |
| 1236 | 1314 | /********************************************************/ |
| @@ -1310,7 +1388,7 @@ static const char *skip_linker_arg(const char **str) · 73 unmodified lines | ||
| 1310 | 1388 | return s2; |
| 1311 | 1389 | } |
| 1312 | 1390 | |
| 1313 | −static void copy_linker_arg(char **pp, const char *s, int sep) | |
| 1391 | +static void copy_linker_arg(TCCState* S, char **pp, const char *s, int sep) | |
| 1314 | 1392 | { |
| 1315 | 1393 | const char *q = s; |
| 1316 | 1394 | char *p = *pp; |
| @@ -1318,13 +1396,12 @@ static void copy_linker_arg(char **pp, const char *s, int sep) · 1 unmodified line | ||
| 1318 | 1396 | if (p && sep) |
| 1319 | 1397 | p[l = strlen(p)] = sep, ++l; |
| 1320 | 1398 | skip_linker_arg(&q); |
| 1321 | − pstrncpy(l + (*pp = tcc_realloc(p, q - s + l + 1)), s, q - s); | |
| 1399 | + pstrncpy(l + (*pp = tcc_realloc(S, p, q - s + l + 1)), s, q - s); | |
| 1322 | 1400 | } |
| 1323 | 1401 | |
| 1324 | 1402 | /* set linker options */ |
| 1325 | −static int tcc_set_linker(TCCState *s, const char *option) | |
| 1403 | +static int tcc_set_linker(TCCState *S, const char *option) | |
| 1326 | 1404 | { |
| 1327 | − TCCState *s1 = s; | |
| 1328 | 1405 | while (*option) { |
| 1329 | 1406 | |
| 1330 | 1407 | const char *p = NULL; |
| @@ -1333,18 +1410,18 @@ static int tcc_set_linker(TCCState *s, const char *option) · 2 unmodified lines | ||
| 1333 | 1410 | int ret; |
| 1334 | 1411 | |
| 1335 | 1412 | if (link_option(option, "Bsymbolic", &p)) { |
| 1336 | − s->symbolic = 1; | |
| 1413 | + S->symbolic = 1; | |
| 1337 | 1414 | } else if (link_option(option, "nostdlib", &p)) { |
| 1338 | − s->nostdlib = 1; | |
| 1415 | + S->nostdlib = 1; | |
| 1339 | 1416 | } else if (link_option(option, "fini=", &p)) { |
| 1340 | − copy_linker_arg(&s->fini_symbol, p, 0); | |
| 1417 | + copy_linker_arg(S, &S->fini_symbol, p, 0); | |
| 1341 | 1418 | ignoring = 1; |
| 1342 | 1419 | } else if (link_option(option, "image-base=", &p) |
| 1343 | 1420 | || link_option(option, "Ttext=", &p)) { |
| 1344 | − s->text_addr = strtoull(p, &end, 16); | |
| 1345 | − s->has_text_addr = 1; | |
| 1421 | + S->text_addr = strtoull(p, &end, 16); | |
| 1422 | + S->has_text_addr = 1; | |
| 1346 | 1423 | } else if (link_option(option, "init=", &p)) { |
| 1347 | − copy_linker_arg(&s->init_symbol, p, 0); | |
| 1424 | + copy_linker_arg(S, &S->init_symbol, p, 0); | |
| 1348 | 1425 | ignoring = 1; |
| 1349 | 1426 | } else if (link_option(option, "oformat=", &p)) { |
| 1350 | 1427 | #if defined(TCC_TARGET_PE) |
| @@ -1354,12 +1431,12 @@ static int tcc_set_linker(TCCState *s, const char *option) · 3 unmodified lines | ||
| 1354 | 1431 | #else |
| 1355 | 1432 | if (strstart("elf32-", &p)) { |
| 1356 | 1433 | #endif |
| 1357 | − s->output_format = TCC_OUTPUT_FORMAT_ELF; | |
| 1434 | + S->output_format = TCC_OUTPUT_FORMAT_ELF; | |
| 1358 | 1435 | } else if (!strcmp(p, "binary")) { |
| 1359 | − s->output_format = TCC_OUTPUT_FORMAT_BINARY; | |
| 1436 | + S->output_format = TCC_OUTPUT_FORMAT_BINARY; | |
| 1360 | 1437 | #ifdef TCC_TARGET_COFF |
| 1361 | 1438 | } else if (!strcmp(p, "coff")) { |
| 1362 | − s->output_format = TCC_OUTPUT_FORMAT_COFF; | |
| 1439 | + S->output_format = TCC_OUTPUT_FORMAT_COFF; | |
| 1363 | 1440 | #endif |
| 1364 | 1441 | } else |
| 1365 | 1442 | goto err; |
| @@ -1369,64 +1446,64 @@ static int tcc_set_linker(TCCState *s, const char *option) · 3 unmodified lines | ||
| 1369 | 1446 | } else if (link_option(option, "O", &p)) { |
| 1370 | 1447 | ignoring = 1; |
| 1371 | 1448 | } else if (link_option(option, "export-all-symbols", &p)) { |
| 1372 | − s->rdynamic = 1; | |
| 1449 | + S->rdynamic = 1; | |
| 1373 | 1450 | } else if (link_option(option, "export-dynamic", &p)) { |
| 1374 | − s->rdynamic = 1; | |
| 1451 | + S->rdynamic = 1; | |
| 1375 | 1452 | } else if (link_option(option, "rpath=", &p)) { |
| 1376 | − copy_linker_arg(&s->rpath, p, ':'); | |
| 1453 | + copy_linker_arg(S, &S->rpath, p, ':'); | |
| 1377 | 1454 | } else if (link_option(option, "enable-new-dtags", &p)) { |
| 1378 | − s->enable_new_dtags = 1; | |
| 1455 | + S->enable_new_dtags = 1; | |
| 1379 | 1456 | } else if (link_option(option, "section-alignment=", &p)) { |
| 1380 | − s->section_align = strtoul(p, &end, 16); | |
| 1457 | + S->section_align = strtoul(p, &end, 16); | |
| 1381 | 1458 | } else if (link_option(option, "soname=", &p)) { |
| 1382 | − copy_linker_arg(&s->soname, p, 0); | |
| 1459 | + copy_linker_arg(S, &S->soname, p, 0); | |
| 1383 | 1460 | #ifdef TCC_TARGET_PE |
| 1384 | 1461 | } else if (link_option(option, "large-address-aware", &p)) { |
| 1385 | − s->pe_characteristics |= 0x20; | |
| 1462 | + S->pe_characteristics |= 0x20; | |
| 1386 | 1463 | } else if (link_option(option, "file-alignment=", &p)) { |
| 1387 | − s->pe_file_align = strtoul(p, &end, 16); | |
| 1464 | + S->pe_file_align = strtoul(p, &end, 16); | |
| 1388 | 1465 | } else if (link_option(option, "stack=", &p)) { |
| 1389 | − s->pe_stack_size = strtoul(p, &end, 10); | |
| 1466 | + S->pe_stack_size = strtoul(p, &end, 10); | |
| 1390 | 1467 | } else if (link_option(option, "subsystem=", &p)) { |
| 1391 | 1468 | #if defined(TCC_TARGET_I386) || defined(TCC_TARGET_X86_64) |
| 1392 | 1469 | if (!strcmp(p, "native")) { |
| 1393 | − s->pe_subsystem = 1; | |
| 1470 | + S->pe_subsystem = 1; | |
| 1394 | 1471 | } else if (!strcmp(p, "console")) { |
| 1395 | − s->pe_subsystem = 3; | |
| 1472 | + S->pe_subsystem = 3; | |
| 1396 | 1473 | } else if (!strcmp(p, "gui") || !strcmp(p, "windows")) { |
| 1397 | − s->pe_subsystem = 2; | |
| 1474 | + S->pe_subsystem = 2; | |
| 1398 | 1475 | } else if (!strcmp(p, "posix")) { |
| 1399 | − s->pe_subsystem = 7; | |
| 1476 | + S->pe_subsystem = 7; | |
| 1400 | 1477 | } else if (!strcmp(p, "efiapp")) { |
| 1401 | − s->pe_subsystem = 10; | |
| 1478 | + S->pe_subsystem = 10; | |
| 1402 | 1479 | } else if (!strcmp(p, "efiboot")) { |
| 1403 | − s->pe_subsystem = 11; | |
| 1480 | + S->pe_subsystem = 11; | |
| 1404 | 1481 | } else if (!strcmp(p, "efiruntime")) { |
| 1405 | − s->pe_subsystem = 12; | |
| 1482 | + S->pe_subsystem = 12; | |
| 1406 | 1483 | } else if (!strcmp(p, "efirom")) { |
| 1407 | − s->pe_subsystem = 13; | |
| 1484 | + S->pe_subsystem = 13; | |
| 1408 | 1485 | #elif defined(TCC_TARGET_ARM) |
| 1409 | 1486 | if (!strcmp(p, "wince")) { |
| 1410 | − s->pe_subsystem = 9; | |
| 1487 | + S->pe_subsystem = 9; | |
| 1411 | 1488 | #endif |
| 1412 | 1489 | } else |
| 1413 | 1490 | goto err; |
| 1414 | 1491 | #endif |
| 1415 | 1492 | } else if (ret = link_option(option, "?whole-archive", &p), ret) { |
| 1416 | 1493 | if (ret > 0) |
| 1417 | − s->filetype |= AFF_WHOLE_ARCHIVE; | |
| 1494 | + S->filetype |= AFF_WHOLE_ARCHIVE; | |
| 1418 | 1495 | else |
| 1419 | − s->filetype &= ~AFF_WHOLE_ARCHIVE; | |
| 1496 | + S->filetype &= ~AFF_WHOLE_ARCHIVE; | |
| 1420 | 1497 | } else if (link_option(option, "z=", &p)) { |
| 1421 | 1498 | ignoring = 1; |
| 1422 | 1499 | } else if (p) { |
| 1423 | 1500 | return 0; |
| 1424 | 1501 | } else { |
| 1425 | 1502 | err: |
| 1426 | − tcc_error("unsupported linker option '%s'", option); | |
| 1503 | + tcc_error(S, "unsupported linker option '%s'", option); | |
| 1427 | 1504 | } |
| 1428 | 1505 | if (ignoring) |
| 1429 | − tcc_warning_c(warn_unsupported)("unsupported linker option '%s'", option); | |
| 1506 | + tcc_warning_c(warn_unsupported)(S, "unsupported linker option '%s'", option); | |
| 1430 | 1507 | option = skip_linker_arg(&p); |
| 1431 | 1508 | } |
| 1432 | 1509 | return 1; |
| @@ -1604,7 +1681,7 @@ static const FlagDef options_m[] = { · 171 unmodified lines | ||
| 1604 | 1681 | { 0, 0, NULL } |
| 1605 | 1682 | }; |
| 1606 | 1683 | |
| 1607 | −static int set_flag(TCCState *s, const FlagDef *flags, const char *name) | |
| 1684 | +static int set_flag(TCCState *S, const FlagDef *flags, const char *name) | |
| 1608 | 1685 | { |
| 1609 | 1686 | int value, mask, ret; |
| 1610 | 1687 | const FlagDef *p; |
| @@ -1626,7 +1703,7 @@ static int set_flag(TCCState *s, const FlagDef *flags, const char *name) · 15 unmodified lines | ||
| 1626 | 1703 | continue; |
| 1627 | 1704 | } |
| 1628 | 1705 | |
| 1629 | − f = (unsigned char *)s + p->offset; | |
| 1706 | + f = (unsigned char *)S + p->offset; | |
| 1630 | 1707 | *f = (*f & mask) | (value ^ !!(p->flags & FD_INVERT)); |
| 1631 | 1708 | |
| 1632 | 1709 | if (ret) { |
| @@ -1638,15 +1715,15 @@ static int set_flag(TCCState *s, const FlagDef *flags, const char *name) · 5 unmodified lines | ||
| 1638 | 1715 | return ret; |
| 1639 | 1716 | } |
| 1640 | 1717 | |
| 1641 | −static void args_parser_add_file(TCCState *s, const char* filename, int filetype) | |
| 1718 | +static void args_parser_add_file(TCCState *S, const char* filename, int filetype) | |
| 1642 | 1719 | { |
| 1643 | − struct filespec *f = tcc_malloc(sizeof *f + strlen(filename)); | |
| 1720 | + struct filespec *f = tcc_malloc(S, sizeof *f + strlen(filename)); | |
| 1644 | 1721 | f->type = filetype; |
| 1645 | 1722 | strcpy(f->name, filename); |
| 1646 | − dynarray_add(&s->files, &s->nb_files, f); | |
| 1723 | + dynarray_add(S, &S->files, &S->nb_files, f); | |
| 1647 | 1724 | } |
| 1648 | 1725 | |
| 1649 | −static int args_parser_make_argv(const char *r, int *argc, char ***argv) | |
| 1726 | +static int args_parser_make_argv(TCCState* S, const char *r, int *argc, char ***argv) | |
| 1650 | 1727 | { |
| 1651 | 1728 | int ret = 0, q, c; |
| 1652 | 1729 | CString str; |
| @@ -1656,7 +1733,7 @@ static int args_parser_make_argv(const char *r, int *argc, char ***argv) · 3 unmodified lines | ||
| 1656 | 1733 | if (c == 0) |
| 1657 | 1734 | break; |
| 1658 | 1735 | q = 0; |
| 1659 | − cstr_new(&str); | |
| 1736 | + cstr_new(S, &str); | |
| 1660 | 1737 | while (c = (unsigned char)*r, c) { |
| 1661 | 1738 | ++r; |
| 1662 | 1739 | if (c == '\\' && (*r == '"' || *r == '\\')) { |
| @@ -1667,22 +1744,21 @@ static int args_parser_make_argv(const char *r, int *argc, char ***argv) · 4 unmodified lines | ||
| 1667 | 1744 | } else if (q == 0 && c <= ' ') { |
| 1668 | 1745 | break; |
| 1669 | 1746 | } |
| 1670 | − cstr_ccat(&str, c); | |
| 1747 | + cstr_ccat(S, &str, c); | |
| 1671 | 1748 | } |
| 1672 | − cstr_ccat(&str, 0); | |
| 1749 | + cstr_ccat(S, &str, 0); | |
| 1673 | 1750 | //printf("<%s>\n", str.data), fflush(stdout); |
| 1674 | − dynarray_add(argv, argc, tcc_strdup(str.data)); | |
| 1675 | − cstr_free(&str); | |
| 1751 | + dynarray_add(S, argv, argc, tcc_strdup(S, str.data)); | |
| 1752 | + cstr_free(S, &str); | |
| 1676 | 1753 | ++ret; |
| 1677 | 1754 | } |
| 1678 | 1755 | return ret; |
| 1679 | 1756 | } |
| 1680 | 1757 | |
| 1681 | 1758 | /* read list file */ |
| 1682 | −static void args_parser_listfile(TCCState *s, | |
| 1759 | +static void args_parser_listfile(TCCState *S, | |
| 1683 | 1760 | const char *filename, int optind, int *pargc, char ***pargv) |
| 1684 | 1761 | { |
| 1685 | − TCCState *s1 = s; | |
| 1686 | 1762 | int fd, i; |
| 1687 | 1763 | char *p; |
| 1688 | 1764 | int argc = 0; |
| @@ -1690,23 +1766,22 @@ static void args_parser_listfile(TCCState *s, · 1 unmodified line | ||
| 1690 | 1766 | |
| 1691 | 1767 | fd = open(filename, O_RDONLY | O_BINARY); |
| 1692 | 1768 | if (fd < 0) |
| 1693 | − tcc_error("listfile '%s' not found", filename); | |
| 1769 | + tcc_error(S, "listfile '%s' not found", filename); | |
| 1694 | 1770 | |
| 1695 | − p = tcc_load_text(fd); | |
| 1771 | + p = tcc_load_text(S, fd); | |
| 1696 | 1772 | for (i = 0; i < *pargc; ++i) |
| 1697 | 1773 | if (i == optind) |
| 1698 | − args_parser_make_argv(p, &argc, &argv); | |
| 1774 | + args_parser_make_argv(S, p, &argc, &argv); | |
| 1699 | 1775 | else |
| 1700 | − dynarray_add(&argv, &argc, tcc_strdup((*pargv)[i])); | |
| 1776 | + dynarray_add(S, &argv, &argc, tcc_strdup(S, (*pargv)[i])); | |
| 1701 | 1777 | |
| 1702 | − tcc_free(p); | |
| 1703 | − dynarray_reset(&s->argv, &s->argc); | |
| 1704 | − *pargc = s->argc = argc, *pargv = s->argv = argv; | |
| 1778 | + tcc_free(S, p); | |
| 1779 | + dynarray_reset(S, &S->argv, &S->argc); | |
| 1780 | + *pargc = S->argc = argc, *pargv = S->argv = argv; | |
| 1705 | 1781 | } |
| 1706 | 1782 | |
| 1707 | −PUB_FUNC int tcc_parse_args(TCCState *s, int *pargc, char ***pargv, int optind) | |
| 1783 | +PUB_FUNC int tcc_parse_args(TCCState *S, int *pargc, char ***pargv, int optind) | |
| 1708 | 1784 | { |
| 1709 | − TCCState *s1 = s; | |
| 1710 | 1785 | const TCCOption *popt; |
| 1711 | 1786 | const char *optarg, *r; |
| 1712 | 1787 | const char *run = NULL; |
| @@ -1716,26 +1791,26 @@ PUB_FUNC int tcc_parse_args(TCCState *s, int *pargc, char ***pargv, int optind) · 3 unmodified lines | ||
| 1716 | 1791 | char **argv = *pargv; |
| 1717 | 1792 | int argc = *pargc; |
| 1718 | 1793 | |
| 1719 | − cstr_new(&linker_arg); | |
| 1794 | + cstr_new(S, &linker_arg); | |
| 1720 | 1795 | |
| 1721 | 1796 | while (optind < argc) { |
| 1722 | 1797 | r = argv[optind]; |
| 1723 | 1798 | if (r[0] == '@' && r[1] != '\0') { |
| 1724 | − args_parser_listfile(s, r + 1, optind, &argc, &argv); | |
| 1799 | + args_parser_listfile(S, r + 1, optind, &argc, &argv); | |
| 1725 | 1800 | continue; |
| 1726 | 1801 | } |
| 1727 | 1802 | optind++; |
| 1728 | 1803 | if (tool) { |
| 1729 | 1804 | if (r[0] == '-' && r[1] == 'v' && r[2] == 0) |
| 1730 | − ++s->verbose; | |
| 1805 | + ++S->verbose; | |
| 1731 | 1806 | continue; |
| 1732 | 1807 | } |
| 1733 | 1808 | reparse: |
| 1734 | 1809 | if (r[0] != '-' || r[1] == '\0') { |
| 1735 | 1810 | if (r[0] != '@') /* allow "tcc file(s) -run @ args ..." */ |
| 1736 | − args_parser_add_file(s, r, s->filetype); | |
| 1811 | + args_parser_add_file(S, r, S->filetype); | |
| 1737 | 1812 | if (run) { |
| 1738 | − tcc_set_options(s, run); | |
| 1813 | + tcc_set_options(S, run); | |
| 1739 | 1814 | arg_start = optind - 1; |
| 1740 | 1815 | break; |
| 1741 | 1816 | } |
| @@ -1747,7 +1822,7 @@ reparse: · 5 unmodified lines | ||
| 1747 | 1822 | const char *p1 = popt->name; |
| 1748 | 1823 | const char *r1 = r + 1; |
| 1749 | 1824 | if (p1 == NULL) |
| 1750 | − tcc_error("invalid option -- '%s'", r); | |
| 1825 | + tcc_error(S, "invalid option -- '%s'", r); | |
| 1751 | 1826 | if (!strstart(p1, &r1)) |
| 1752 | 1827 | continue; |
| 1753 | 1828 | optarg = r1; |
| @@ -1755,7 +1830,7 @@ reparse: · 1 unmodified line | ||
| 1755 | 1830 | if (*r1 == '\0' && !(popt->flags & TCC_OPTION_NOSEP)) { |
| 1756 | 1831 | if (optind >= argc) |
| 1757 | 1832 | arg_err: |
| 1758 | − tcc_error("argument to '%s' is missing", r); | |
| 1833 | + tcc_error(S, "argument to '%s' is missing", r); | |
| 1759 | 1834 | optarg = argv[optind++]; |
| 1760 | 1835 | } |
| 1761 | 1836 | } else if (*r1 != '\0') |
| @@ -1771,132 +1846,132 @@ reparse: · 9 unmodified lines | ||
| 1771 | 1846 | x = OPT_HELP2; |
| 1772 | 1847 | goto extra_action; |
| 1773 | 1848 | case TCC_OPTION_I: |
| 1774 | − tcc_add_include_path(s, optarg); | |
| 1849 | + tcc_add_include_path(S, optarg); | |
| 1775 | 1850 | break; |
| 1776 | 1851 | case TCC_OPTION_D: |
| 1777 | − tcc_define_symbol(s, optarg, NULL); | |
| 1852 | + tcc_define_symbol(S, optarg, NULL); | |
| 1778 | 1853 | break; |
| 1779 | 1854 | case TCC_OPTION_U: |
| 1780 | − tcc_undefine_symbol(s, optarg); | |
| 1855 | + tcc_undefine_symbol(S, optarg); | |
| 1781 | 1856 | break; |
| 1782 | 1857 | case TCC_OPTION_L: |
| 1783 | − tcc_add_library_path(s, optarg); | |
| 1858 | + tcc_add_library_path(S, optarg); | |
| 1784 | 1859 | break; |
| 1785 | 1860 | case TCC_OPTION_B: |
| 1786 | 1861 | /* set tcc utilities path (mainly for tcc development) */ |
| 1787 | − tcc_set_lib_path(s, optarg); | |
| 1862 | + tcc_set_lib_path(S, optarg); | |
| 1788 | 1863 | break; |
| 1789 | 1864 | case TCC_OPTION_l: |
| 1790 | − args_parser_add_file(s, optarg, AFF_TYPE_LIB | (s->filetype & ~AFF_TYPE_MASK)); | |
| 1791 | − s->nb_libraries++; | |
| 1865 | + args_parser_add_file(S, optarg, AFF_TYPE_LIB | (S->filetype & ~AFF_TYPE_MASK)); | |
| 1866 | + S->nb_libraries++; | |
| 1792 | 1867 | break; |
| 1793 | 1868 | case TCC_OPTION_pthread: |
| 1794 | − s->option_pthread = 1; | |
| 1869 | + S->option_pthread = 1; | |
| 1795 | 1870 | break; |
| 1796 | 1871 | case TCC_OPTION_bench: |
| 1797 | − s->do_bench = 1; | |
| 1872 | + S->do_bench = 1; | |
| 1798 | 1873 | break; |
| 1799 | 1874 | #ifdef CONFIG_TCC_BACKTRACE |
| 1800 | 1875 | case TCC_OPTION_bt: |
| 1801 | − s->rt_num_callers = atoi(optarg); | |
| 1802 | − s->do_backtrace = 1; | |
| 1803 | − s->do_debug = 1; | |
| 1876 | + S->rt_num_callers = atoi(optarg); | |
| 1877 | + S->do_backtrace = 1; | |
| 1878 | + S->do_debug = 1; | |
| 1804 | 1879 | break; |
| 1805 | 1880 | #endif |
| 1806 | 1881 | #ifdef CONFIG_TCC_BCHECK |
| 1807 | 1882 | case TCC_OPTION_b: |
| 1808 | − s->do_bounds_check = 1; | |
| 1809 | − s->do_backtrace = 1; | |
| 1810 | − s->do_debug = 1; | |
| 1883 | + S->do_bounds_check = 1; | |
| 1884 | + S->do_backtrace = 1; | |
| 1885 | + S->do_debug = 1; | |
| 1811 | 1886 | break; |
| 1812 | 1887 | #endif |
| 1813 | 1888 | case TCC_OPTION_g: |
| 1814 | − s->do_debug = 1; | |
| 1889 | + S->do_debug = 1; | |
| 1815 | 1890 | break; |
| 1816 | 1891 | case TCC_OPTION_c: |
| 1817 | 1892 | x = TCC_OUTPUT_OBJ; |
| 1818 | 1893 | set_output_type: |
| 1819 | − if (s->output_type) | |
| 1820 | − tcc_warning("-%s: overriding compiler action already specified", popt->name); | |
| 1821 | − s->output_type = x; | |
| 1894 | + if (S->output_type) | |
| 1895 | + tcc_warning(S, "-%s: overriding compiler action already specified", popt->name); | |
| 1896 | + S->output_type = x; | |
| 1822 | 1897 | break; |
| 1823 | 1898 | case TCC_OPTION_d: |
| 1824 | 1899 | if (*optarg == 'D') |
| 1825 | − s->dflag = 3; | |
| 1900 | + S->dflag = TCC_OPTION_d_D; | |
| 1826 | 1901 | else if (*optarg == 'M') |
| 1827 | − s->dflag = 7; | |
| 1902 | + S->dflag = TCC_OPTION_d_M; | |
| 1828 | 1903 | else if (*optarg == 't') |
| 1829 | − s->dflag = 16; | |
| 1904 | + S->dflag = TCC_OPTION_d_t; | |
| 1830 | 1905 | else if (isnum(*optarg)) |
| 1831 | − s->g_debug |= atoi(optarg); | |
| 1906 | + S->g_debug |= atoi(optarg); | |
| 1832 | 1907 | else |
| 1833 | 1908 | goto unsupported_option; |
| 1834 | 1909 | break; |
| 1835 | 1910 | case TCC_OPTION_static: |
| 1836 | − s->static_link = 1; | |
| 1911 | + S->static_link = 1; | |
| 1837 | 1912 | break; |
| 1838 | 1913 | case TCC_OPTION_std: |
| 1839 | 1914 | if (strcmp(optarg, "=c11") == 0) |
| 1840 | − s->cversion = 201112; | |
| 1915 | + S->cversion = 201112; | |
| 1841 | 1916 | break; |
| 1842 | 1917 | case TCC_OPTION_shared: |
| 1843 | 1918 | x = TCC_OUTPUT_DLL; |
| 1844 | 1919 | goto set_output_type; |
| 1845 | 1920 | case TCC_OPTION_soname: |
| 1846 | − s->soname = tcc_strdup(optarg); | |
| 1921 | + S->soname = tcc_strdup(S, optarg); | |
| 1847 | 1922 | break; |
| 1848 | 1923 | case TCC_OPTION_o: |
| 1849 | − if (s->outfile) { | |
| 1850 | − tcc_warning("multiple -o option"); | |
| 1851 | − tcc_free(s->outfile); | |
| 1924 | + if (S->outfile) { | |
| 1925 | + tcc_warning(S, "multiple -o option"); | |
| 1926 | + tcc_free(S, S->outfile); | |
| 1852 | 1927 | } |
| 1853 | − s->outfile = tcc_strdup(optarg); | |
| 1928 | + S->outfile = tcc_strdup(S, optarg); | |
| 1854 | 1929 | break; |
| 1855 | 1930 | case TCC_OPTION_r: |
| 1856 | 1931 | /* generate a .o merging several output files */ |
| 1857 | − s->option_r = 1; | |
| 1932 | + S->option_r = 1; | |
| 1858 | 1933 | x = TCC_OUTPUT_OBJ; |
| 1859 | 1934 | goto set_output_type; |
| 1860 | 1935 | case TCC_OPTION_isystem: |
| 1861 | − tcc_add_sysinclude_path(s, optarg); | |
| 1936 | + tcc_add_sysinclude_path(S, optarg); | |
| 1862 | 1937 | break; |
| 1863 | 1938 | case TCC_OPTION_include: |
| 1864 | − cstr_printf(&s->cmdline_incl, "#include \"%s\"\n", optarg); | |
| 1939 | + cstr_printf(S, &S->cmdline_incl, "#include \"%s\"\n", optarg); | |
| 1865 | 1940 | break; |
| 1866 | 1941 | case TCC_OPTION_nostdinc: |
| 1867 | − s->nostdinc = 1; | |
| 1942 | + S->nostdinc = 1; | |
| 1868 | 1943 | break; |
| 1869 | 1944 | case TCC_OPTION_nostdlib: |
| 1870 | − s->nostdlib = 1; | |
| 1945 | + S->nostdlib = 1; | |
| 1871 | 1946 | break; |
| 1872 | 1947 | case TCC_OPTION_run: |
| 1873 | 1948 | #ifndef TCC_IS_NATIVE |
| 1874 | − tcc_error("-run is not available in a cross compiler"); | |
| 1949 | + tcc_error(S, "-run is not available in a cross compiler"); | |
| 1875 | 1950 | #endif |
| 1876 | 1951 | run = optarg; |
| 1877 | 1952 | x = TCC_OUTPUT_MEMORY; |
| 1878 | 1953 | goto set_output_type; |
| 1879 | 1954 | case TCC_OPTION_v: |
| 1880 | − do ++s->verbose; while (*optarg++ == 'v'); | |
| 1955 | + do ++S->verbose; while (*optarg++ == 'v'); | |
| 1881 | 1956 | ++noaction; |
| 1882 | 1957 | break; |
| 1883 | 1958 | case TCC_OPTION_f: |
| 1884 | − if (set_flag(s, options_f, optarg) < 0) | |
| 1959 | + if (set_flag(S, options_f, optarg) < 0) | |
| 1885 | 1960 | goto unsupported_option; |
| 1886 | 1961 | break; |
| 1887 | 1962 | #ifdef TCC_TARGET_ARM |
| 1888 | 1963 | case TCC_OPTION_mfloat_abi: |
| 1889 | 1964 | /* tcc doesn't support soft float yet */ |
| 1890 | 1965 | if (!strcmp(optarg, "softfp")) { |
| 1891 | − s->float_abi = ARM_SOFTFP_FLOAT; | |
| 1966 | + S->float_abi = ARM_SOFTFP_FLOAT; | |
| 1892 | 1967 | } else if (!strcmp(optarg, "hard")) |
| 1893 | − s->float_abi = ARM_HARD_FLOAT; | |
| 1968 | + S->float_abi = ARM_HARD_FLOAT; | |
| 1894 | 1969 | else |
| 1895 | − tcc_error("unsupported float abi '%s'", optarg); | |
| 1970 | + tcc_error(S, "unsupported float abi '%s'", optarg); | |
| 1896 | 1971 | break; |
| 1897 | 1972 | #endif |
| 1898 | 1973 | case TCC_OPTION_m: |
| 1899 | − if (set_flag(s, options_m, optarg) < 0) { | |
| 1974 | + if (set_flag(S, options_m, optarg) < 0) { | |
| 1900 | 1975 | if (x = atoi(optarg), x != 32 && x != 64) |
| 1901 | 1976 | goto unsupported_option; |
| 1902 | 1977 | if (PTR_SIZE != x/8) |
| @@ -1905,22 +1980,22 @@ reparse: · 2 unmodified lines | ||
| 1905 | 1980 | } |
| 1906 | 1981 | break; |
| 1907 | 1982 | case TCC_OPTION_W: |
| 1908 | − s->warn_none = 0; | |
| 1909 | − if (optarg[0] && set_flag(s, options_W, optarg) < 0) | |
| 1983 | + S->warn_none = 0; | |
| 1984 | + if (optarg[0] && set_flag(S, options_W, optarg) < 0) | |
| 1910 | 1985 | goto unsupported_option; |
| 1911 | 1986 | break; |
| 1912 | 1987 | case TCC_OPTION_w: |
| 1913 | − s->warn_none = 1; | |
| 1988 | + S->warn_none = 1; | |
| 1914 | 1989 | break; |
| 1915 | 1990 | case TCC_OPTION_rdynamic: |
| 1916 | − s->rdynamic = 1; | |
| 1991 | + S->rdynamic = 1; | |
| 1917 | 1992 | break; |
| 1918 | 1993 | case TCC_OPTION_Wl: |
| 1919 | 1994 | if (linker_arg.size) |
| 1920 | − --linker_arg.size, cstr_ccat(&linker_arg, ','); | |
| 1921 | − cstr_cat(&linker_arg, optarg, 0); | |
| 1922 | − if (tcc_set_linker(s, linker_arg.data)) | |
| 1923 | − cstr_free(&linker_arg); | |
| 1995 | + --linker_arg.size, cstr_ccat(S, &linker_arg, ','); | |
| 1996 | + cstr_cat(S, &linker_arg, optarg, 0); | |
| 1997 | + if (tcc_set_linker(S, linker_arg.data)) | |
| 1998 | + cstr_free(S, &linker_arg); | |
| 1924 | 1999 | break; |
| 1925 | 2000 | case TCC_OPTION_Wp: |
| 1926 | 2001 | r = optarg; |
| @@ -1929,25 +2004,25 @@ reparse: · 2 unmodified lines | ||
| 1929 | 2004 | x = TCC_OUTPUT_PREPROCESS; |
| 1930 | 2005 | goto set_output_type; |
| 1931 | 2006 | case TCC_OPTION_P: |
| 1932 | − s->Pflag = atoi(optarg) + 1; | |
| 2007 | + S->Pflag = atoi(optarg) + 1; | |
| 1933 | 2008 | break; |
| 1934 | 2009 | case TCC_OPTION_M: |
| 1935 | − s->include_sys_deps = 1; | |
| 2010 | + S->include_sys_deps = 1; | |
| 1936 | 2011 | // fall through |
| 1937 | 2012 | case TCC_OPTION_MM: |
| 1938 | − s->just_deps = 1; | |
| 1939 | − if(!s->deps_outfile) | |
| 1940 | − s->deps_outfile = tcc_strdup("-"); | |
| 2013 | + S->just_deps = 1; | |
| 2014 | + if(!S->deps_outfile) | |
| 2015 | + S->deps_outfile = tcc_strdup(S, "-"); | |
| 1941 | 2016 | // fall through |
| 1942 | 2017 | case TCC_OPTION_MMD: |
| 1943 | − s->gen_deps = 1; | |
| 2018 | + S->gen_deps = 1; | |
| 1944 | 2019 | break; |
| 1945 | 2020 | case TCC_OPTION_MD: |
| 1946 | − s->gen_deps = 1; | |
| 1947 | − s->include_sys_deps = 1; | |
| 2021 | + S->gen_deps = 1; | |
| 2022 | + S->include_sys_deps = 1; | |
| 1948 | 2023 | break; |
| 1949 | 2024 | case TCC_OPTION_MF: |
| 1950 | − s->deps_outfile = tcc_strdup(optarg); | |
| 2025 | + S->deps_outfile = tcc_strdup(S, optarg); | |
| 1951 | 2026 | break; |
| 1952 | 2027 | case TCC_OPTION_dumpversion: |
| 1953 | 2028 | printf ("%s\n", TCC_VERSION); |
| @@ -1964,11 +2039,11 @@ reparse: · 10 unmodified lines | ||
| 1964 | 2039 | else if (*optarg == 'n') |
| 1965 | 2040 | x = AFF_TYPE_NONE; |
| 1966 | 2041 | else |
| 1967 | − tcc_warning("unsupported language '%s'", optarg); | |
| 1968 | − s->filetype = x | (s->filetype & ~AFF_TYPE_MASK); | |
| 2042 | + tcc_warning(S, "unsupported language '%s'", optarg); | |
| 2043 | + S->filetype = x | (S->filetype & ~AFF_TYPE_MASK); | |
| 1969 | 2044 | break; |
| 1970 | 2045 | case TCC_OPTION_O: |
| 1971 | − s->optimize = atoi(optarg); | |
| 2046 | + S->optimize = atoi(optarg); | |
| 1972 | 2047 | break; |
| 1973 | 2048 | case TCC_OPTION_print_search_dirs: |
| 1974 | 2049 | x = OPT_PRINT_DIRS; |
| @@ -1981,12 +2056,12 @@ reparse: · 6 unmodified lines | ||
| 1981 | 2056 | extra_action: |
| 1982 | 2057 | arg_start = optind - 1; |
| 1983 | 2058 | if (arg_start != noaction) |
| 1984 | − tcc_error("cannot parse %s here", r); | |
| 2059 | + tcc_error(S, "cannot parse %s here", r); | |
| 1985 | 2060 | tool = x; |
| 1986 | 2061 | break; |
| 1987 | 2062 | default: |
| 1988 | 2063 | unsupported_option: |
| 1989 | − tcc_warning_c(warn_unsupported)("unsupported option '%s'", r); | |
| 2064 | + tcc_warning_c(warn_unsupported)(S, "unsupported option '%s'", r); | |
| 1990 | 2065 | break; |
| 1991 | 2066 | } |
| 1992 | 2067 | } |
| @@ -2000,23 +2075,23 @@ unsupported_option: · 7 unmodified lines | ||
| 2000 | 2075 | return tool; |
| 2001 | 2076 | if (optind != noaction) |
| 2002 | 2077 | return 0; |
| 2003 | − if (s->verbose == 2) | |
| 2078 | + if (S->verbose == 2) | |
| 2004 | 2079 | return OPT_PRINT_DIRS; |
| 2005 | − if (s->verbose) | |
| 2080 | + if (S->verbose) | |
| 2006 | 2081 | return OPT_V; |
| 2007 | 2082 | return OPT_HELP; |
| 2008 | 2083 | } |
| 2009 | 2084 | |
| 2010 | −LIBTCCAPI void tcc_set_options(TCCState *s, const char *r) | |
| 2085 | +LIBTCCAPI void tcc_set_options(TCCState *S, const char *r) | |
| 2011 | 2086 | { |
| 2012 | 2087 | char **argv = NULL; |
| 2013 | 2088 | int argc = 0; |
| 2014 | − args_parser_make_argv(r, &argc, &argv); | |
| 2015 | − tcc_parse_args(s, &argc, &argv, 0); | |
| 2016 | − dynarray_reset(&argv, &argc); | |
| 2089 | + args_parser_make_argv(S, r, &argc, &argv); | |
| 2090 | + tcc_parse_args(S, &argc, &argv, 0); | |
| 2091 | + dynarray_reset(S, &argv, &argc); | |
| 2017 | 2092 | } |
| 2018 | 2093 | |
| 2019 | −PUB_FUNC void tcc_print_stats(TCCState *s1, unsigned total_time) | |
| 2094 | +PUB_FUNC void tcc_print_stats(TCCState *S, unsigned total_time) | |
| 2020 | 2095 | { |
| 2021 | 2096 | if (total_time < 1) |
| 2022 | 2097 | total_time = 1; |
| @@ -2029,12 +2104,14 @@ PUB_FUNC void tcc_print_stats(TCCState *s1, unsigned total_time) · 6 unmodified lines | ||
| 2029 | 2104 | (unsigned)total_lines*1000/total_time, |
| 2030 | 2105 | (double)total_bytes/1000/total_time); |
| 2031 | 2106 | fprintf(stderr, "* text %d, data.rw %d, data.ro %d, bss %d bytes\n", |
| 2032 | − s1->total_output[0], | |
| 2033 | − s1->total_output[1], | |
| 2034 | − s1->total_output[2], | |
| 2035 | − s1->total_output[3] | |
| 2107 | + S->total_output[0], | |
| 2108 | + S->total_output[1], | |
| 2109 | + S->total_output[2], | |
| 2110 | + S->total_output[3] | |
| 2036 | 2111 | ); |
| 2037 | 2112 | #ifdef MEM_DEBUG |
| 2038 | 2113 | fprintf(stderr, "* %d bytes memory used\n", mem_max_size); |
| 2039 | 2114 | #endif |
| 2040 | 2115 | } |
| 2116 | + | |
| 2117 | +#include "tccqsort.c" | |
| @@ -15,56 +15,95 @@ typedef struct TCCState TCCState; · 14 unmodified lines | ||
| 15 | 15 | |
| 16 | 16 | typedef void (*TCCErrorFunc)(void *opaque, const char *msg); |
| 17 | 17 | |
| 18 | +#ifndef _OFF_T_DEFINED | |
| 19 | +#define _OFF_T_DEFINED | |
| 20 | +#ifndef _OFF_T_ | |
| 21 | +#define _OFF_T_ | |
| 22 | + typedef long _off_t; | |
| 23 | +#ifndef _SIZE_T_ | |
| 24 | +#define _SIZE_T_ | |
| 25 | + typedef unsigned long size_t; | |
| 26 | +#endif | |
| 27 | +#if !defined(NO_OLDNAMES) || defined(_POSIX) | |
| 28 | + typedef long off_t; | |
| 29 | +#endif | |
| 30 | +#endif | |
| 31 | +#endif | |
| 32 | + | |
| 33 | +struct vio_module_t; | |
| 34 | + | |
| 35 | +typedef struct vio_fd { | |
| 36 | + int fd; | |
| 37 | + void *vio_udata; | |
| 38 | + struct vio_module_t *vio_module; | |
| 39 | +} vio_fd; | |
| 40 | + | |
| 41 | +#define CALL_VIO_OPEN_FIRST 0x01 | |
| 42 | +#define CALL_VIO_OPEN_LAST 0x02 | |
| 43 | + | |
| 44 | +typedef struct vio_module_t { | |
| 45 | + void *user_data; | |
| 46 | + struct TCCState *S; | |
| 47 | + int call_vio_open_flags; /*CALL_VIO_OPEN_FIRST, CALL_VIO_OPEN_LAST, one or both */ | |
| 48 | + int (*vio_open)(vio_fd *fd, const char *fn, int oflag) ; | |
| 49 | + off_t (*vio_lseek)(vio_fd fd, off_t offset, int whence); | |
| 50 | + size_t (*vio_read)(vio_fd fd, void *buf, size_t bytes); | |
| 51 | + int (*vio_close)(vio_fd *fd); | |
| 52 | +} vio_module_t; | |
| 53 | + | |
| 18 | 54 | /* create a new TCC compilation context */ |
| 19 | 55 | LIBTCCAPI TCCState *tcc_new(void); |
| 20 | 56 | |
| 21 | 57 | /* free a TCC compilation context */ |
| 22 | −LIBTCCAPI void tcc_delete(TCCState *s); | |
| 58 | +LIBTCCAPI void tcc_delete(TCCState *S); | |
| 23 | 59 | |
| 24 | 60 | /* set CONFIG_TCCDIR at runtime */ |
| 25 | −LIBTCCAPI void tcc_set_lib_path(TCCState *s, const char *path); | |
| 61 | +LIBTCCAPI void tcc_set_lib_path(TCCState *S, const char *path); | |
| 26 | 62 | |
| 27 | 63 | /* set error/warning display callback */ |
| 28 | −LIBTCCAPI void tcc_set_error_func(TCCState *s, void *error_opaque, TCCErrorFunc error_func); | |
| 64 | +LIBTCCAPI void tcc_set_error_func(TCCState *S, void *error_opaque, TCCErrorFunc error_func); | |
| 29 | 65 | |
| 30 | 66 | /* return error/warning callback */ |
| 31 | −LIBTCCAPI TCCErrorFunc tcc_get_error_func(TCCState *s); | |
| 67 | +LIBTCCAPI TCCErrorFunc tcc_get_error_func(TCCState *S); | |
| 32 | 68 | |
| 33 | 69 | /* return error/warning callback opaque pointer */ |
| 34 | −LIBTCCAPI void *tcc_get_error_opaque(TCCState *s); | |
| 70 | +LIBTCCAPI void *tcc_get_error_opaque(TCCState *S); | |
| 35 | 71 | |
| 36 | 72 | /* set options as from command line (multiple supported) */ |
| 37 | −LIBTCCAPI void tcc_set_options(TCCState *s, const char *str); | |
| 73 | +LIBTCCAPI void tcc_set_options(TCCState *S, const char *str); | |
| 74 | + | |
| 75 | +/* set virtual io module */ | |
| 76 | +LIBTCCAPI void tcc_set_vio_module(TCCState *S, vio_module_t *vio_module); | |
| 38 | 77 | |
| 39 | 78 | /*****************************/ |
| 40 | 79 | /* preprocessor */ |
| 41 | 80 | |
| 42 | 81 | /* add include path */ |
| 43 | −LIBTCCAPI int tcc_add_include_path(TCCState *s, const char *pathname); | |
| 82 | +LIBTCCAPI int tcc_add_include_path(TCCState *S, const char *pathname); | |
| 44 | 83 | |
| 45 | 84 | /* add in system include path */ |
| 46 | −LIBTCCAPI int tcc_add_sysinclude_path(TCCState *s, const char *pathname); | |
| 85 | +LIBTCCAPI int tcc_add_sysinclude_path(TCCState *S, const char *pathname); | |
| 47 | 86 | |
| 48 | 87 | /* define preprocessor symbol 'sym'. value can be NULL, sym can be "sym=val" */ |
| 49 | −LIBTCCAPI void tcc_define_symbol(TCCState *s, const char *sym, const char *value); | |
| 88 | +LIBTCCAPI void tcc_define_symbol(TCCState *S, const char *sym, const char *value); | |
| 50 | 89 | |
| 51 | 90 | /* undefine preprocess symbol 'sym' */ |
| 52 | −LIBTCCAPI void tcc_undefine_symbol(TCCState *s, const char *sym); | |
| 91 | +LIBTCCAPI void tcc_undefine_symbol(TCCState *S, const char *sym); | |
| 53 | 92 | |
| 54 | 93 | /*****************************/ |
| 55 | 94 | /* compiling */ |
| 56 | 95 | |
| 57 | 96 | /* add a file (C file, dll, object, library, ld script). Return -1 if error. */ |
| 58 | −LIBTCCAPI int tcc_add_file(TCCState *s, const char *filename); | |
| 97 | +LIBTCCAPI int tcc_add_file(TCCState *S, const char *filename); | |
| 59 | 98 | |
| 60 | 99 | /* compile a string containing a C source. Return -1 if error. */ |
| 61 | −LIBTCCAPI int tcc_compile_string(TCCState *s, const char *buf); | |
| 100 | +LIBTCCAPI int tcc_compile_string(TCCState *S, const char *buf); | |
| 62 | 101 | |
| 63 | 102 | /*****************************/ |
| 64 | 103 | /* linking commands */ |
| 65 | 104 | |
| 66 | 105 | /* set output type. MUST BE CALLED before any compilation */ |
| 67 | −LIBTCCAPI int tcc_set_output_type(TCCState *s, int output_type); | |
| 106 | +LIBTCCAPI int tcc_set_output_type(TCCState *S, int output_type); | |
| 68 | 107 | #define TCC_OUTPUT_MEMORY 1 /* output will be run in memory (default) */ |
| 69 | 108 | #define TCC_OUTPUT_EXE 2 /* executable file */ |
| 70 | 109 | #define TCC_OUTPUT_DLL 3 /* dynamic library */ |
| @@ -72,24 +111,24 @@ LIBTCCAPI int tcc_set_output_type(TCCState *s, int output_type); · 1 unmodified line | ||
| 72 | 111 | #define TCC_OUTPUT_PREPROCESS 5 /* only preprocess (used internally) */ |
| 73 | 112 | |
| 74 | 113 | /* equivalent to -Lpath option */ |
| 75 | −LIBTCCAPI int tcc_add_library_path(TCCState *s, const char *pathname); | |
| 114 | +LIBTCCAPI int tcc_add_library_path(TCCState *S, const char *pathname); | |
| 76 | 115 | |
| 77 | 116 | /* the library name is the same as the argument of the '-l' option */ |
| 78 | −LIBTCCAPI int tcc_add_library(TCCState *s, const char *libraryname); | |
| 117 | +LIBTCCAPI int tcc_add_library(TCCState *S, const char *libraryname); | |
| 79 | 118 | |
| 80 | 119 | /* add a symbol to the compiled program */ |
| 81 | −LIBTCCAPI int tcc_add_symbol(TCCState *s, const char *name, const void *val); | |
| 120 | +LIBTCCAPI int tcc_add_symbol(TCCState *S, const char *name, const void *val); | |
| 82 | 121 | |
| 83 | 122 | /* output an executable, library or object file. DO NOT call |
| 84 | 123 | tcc_relocate() before. */ |
| 85 | −LIBTCCAPI int tcc_output_file(TCCState *s, const char *filename); | |
| 124 | +LIBTCCAPI int tcc_output_file(TCCState *S, const char *filename); | |
| 86 | 125 | |
| 87 | 126 | /* link and run main() function and return its value. DO NOT call |
| 88 | 127 | tcc_relocate() before. */ |
| 89 | −LIBTCCAPI int tcc_run(TCCState *s, int argc, char **argv); | |
| 128 | +LIBTCCAPI int tcc_run(TCCState *S, int argc, char **argv); | |
| 90 | 129 | |
| 91 | 130 | /* do all relocations (needed before using tcc_get_symbol()) */ |
| 92 | −LIBTCCAPI int tcc_relocate(TCCState *s1, void *ptr); | |
| 131 | +LIBTCCAPI int tcc_relocate(TCCState *S, void *ptr); | |
| 93 | 132 | /* possible values for 'ptr': |
| 94 | 133 | - TCC_RELOCATE_AUTO : Allocate and manage memory internally |
| 95 | 134 | - NULL : return required memory size for the step below |
| @@ -98,12 +137,24 @@ LIBTCCAPI int tcc_relocate(TCCState *s1, void *ptr); · 2 unmodified lines | ||
| 98 | 137 | #define TCC_RELOCATE_AUTO (void*)1 |
| 99 | 138 | |
| 100 | 139 | /* return symbol value or NULL if not found */ |
| 101 | −LIBTCCAPI void *tcc_get_symbol(TCCState *s, const char *name); | |
| 140 | +LIBTCCAPI void *tcc_get_symbol(TCCState *S, const char *name); | |
| 102 | 141 | |
| 103 | 142 | /* return symbol value or NULL if not found */ |
| 104 | −LIBTCCAPI void tcc_list_symbols(TCCState *s, void *ctx, | |
| 143 | +LIBTCCAPI void tcc_list_symbols(TCCState *S, void *ctx, | |
| 105 | 144 | void (*symbol_cb)(void *ctx, const char *name, const void *val)); |
| 106 | 145 | |
| 146 | +typedef int (*tcc_cmpfun)(const void *, const void *, void *); | |
| 147 | +LIBTCCAPI void tcc_qsort_s(void *base, size_t nel, size_t width, tcc_cmpfun cmp, void *ctx); | |
| 148 | + | |
| 149 | +enum { /*need better names for some of then*/ | |
| 150 | + TCC_OPTION_d_BI = 1, | |
| 151 | + TCC_OPTION_d_D = 3, | |
| 152 | + TCC_OPTION_d_4 = 4, | |
| 153 | + TCC_OPTION_d_M = 7, | |
| 154 | + TCC_OPTION_d_t = 16, | |
| 155 | + TCC_OPTION_d_32 = 32, | |
| 156 | +}; | |
| 157 | + | |
| 107 | 158 | #ifdef __cplusplus |
| 108 | 159 | } |
| 109 | 160 | #endif |
| @@ -9,9 +9,9 @@ · 8 unmodified lines | ||
| 9 | 9 | #define CONFIG_TCC_ASM |
| 10 | 10 | #define NB_ASM_REGS 32 |
| 11 | 11 | |
| 12 | −ST_FUNC void g(int c); | |
| 13 | −ST_FUNC void gen_le16(int c); | |
| 14 | −ST_FUNC void gen_le32(int c); | |
| 12 | +ST_FUNC void g(TCCState* S, int c); | |
| 13 | +ST_FUNC void gen_le16(TCCState* S, int c); | |
| 14 | +ST_FUNC void gen_le32(TCCState* S, int c); | |
| 15 | 15 | |
| 16 | 16 | /*************************************************************/ |
| 17 | 17 | #else |
| @@ -20,85 +20,85 @@ ST_FUNC void gen_le32(int c); · 2 unmodified lines | ||
| 20 | 20 | #include "tcc.h" |
| 21 | 21 | |
| 22 | 22 | /* XXX: make it faster ? */ |
| 23 | −ST_FUNC void g(int c) | |
| 23 | +ST_FUNC void g(TCCState* S, int c) | |
| 24 | 24 | { |
| 25 | 25 | int ind1; |
| 26 | − if (nocode_wanted) | |
| 26 | + if (S->tccgen_nocode_wanted) | |
| 27 | 27 | return; |
| 28 | − ind1 = ind + 1; | |
| 28 | + ind1 = S->tccgen_ind + 1; | |
| 29 | 29 | if (ind1 > cur_text_section->data_allocated) |
| 30 | − section_realloc(cur_text_section, ind1); | |
| 31 | − cur_text_section->data[ind] = c; | |
| 32 | − ind = ind1; | |
| 30 | + section_realloc(S, cur_text_section, ind1); | |
| 31 | + cur_text_section->data[S->tccgen_ind] = c; | |
| 32 | + S->tccgen_ind = ind1; | |
| 33 | 33 | } |
| 34 | 34 | |
| 35 | −ST_FUNC void gen_le16 (int i) | |
| 35 | +ST_FUNC void gen_le16 (TCCState* S, int i) | |
| 36 | 36 | { |
| 37 | − g(i); | |
| 38 | − g(i>>8); | |
| 37 | + g(S, i); | |
| 38 | + g(S, i>>8); | |
| 39 | 39 | } |
| 40 | 40 | |
| 41 | −ST_FUNC void gen_le32 (int i) | |
| 41 | +ST_FUNC void gen_le32 (TCCState* S, int i) | |
| 42 | 42 | { |
| 43 | 43 | int ind1; |
| 44 | − if (nocode_wanted) | |
| 44 | + if (S->tccgen_nocode_wanted) | |
| 45 | 45 | return; |
| 46 | − ind1 = ind + 4; | |
| 46 | + ind1 = S->tccgen_ind + 4; | |
| 47 | 47 | if (ind1 > cur_text_section->data_allocated) |
| 48 | − section_realloc(cur_text_section, ind1); | |
| 49 | − cur_text_section->data[ind++] = i & 0xFF; | |
| 50 | − cur_text_section->data[ind++] = (i >> 8) & 0xFF; | |
| 51 | − cur_text_section->data[ind++] = (i >> 16) & 0xFF; | |
| 52 | − cur_text_section->data[ind++] = (i >> 24) & 0xFF; | |
| 48 | + section_realloc(S, cur_text_section, ind1); | |
| 49 | + cur_text_section->data[S->tccgen_ind++] = i & 0xFF; | |
| 50 | + cur_text_section->data[S->tccgen_ind++] = (i >> 8) & 0xFF; | |
| 51 | + cur_text_section->data[S->tccgen_ind++] = (i >> 16) & 0xFF; | |
| 52 | + cur_text_section->data[S->tccgen_ind++] = (i >> 24) & 0xFF; | |
| 53 | 53 | } |
| 54 | 54 | |
| 55 | −ST_FUNC void gen_expr32(ExprValue *pe) | |
| 55 | +ST_FUNC void gen_expr32(TCCState* S, ExprValue *pe) | |
| 56 | 56 | { |
| 57 | − gen_le32(pe->v); | |
| 57 | + gen_le32(S, pe->v); | |
| 58 | 58 | } |
| 59 | 59 | |
| 60 | −static void asm_emit_opcode(uint32_t opcode) { | |
| 61 | − gen_le32(opcode); | |
| 60 | +static void asm_emit_opcode(TCCState* S, uint32_t opcode) { | |
| 61 | + gen_le32(S, opcode); | |
| 62 | 62 | } |
| 63 | 63 | |
| 64 | −static void asm_nullary_opcode(TCCState *s1, int token) | |
| 64 | +static void asm_nullary_opcode(TCCState *S, int token) | |
| 65 | 65 | { |
| 66 | 66 | switch (token) { |
| 67 | 67 | // Sync instructions |
| 68 | 68 | |
| 69 | 69 | case TOK_ASM_fence: // I |
| 70 | − asm_emit_opcode((0x3 << 2) | 3 | (0 << 12)); | |
| 70 | + asm_emit_opcode(S, (0x3 << 2) | 3 | (0 << 12)); | |
| 71 | 71 | return; |
| 72 | 72 | case TOK_ASM_fence_i: // I |
| 73 | − asm_emit_opcode((0x3 << 2) | 3| (1 << 12)); | |
| 73 | + asm_emit_opcode(S, (0x3 << 2) | 3| (1 << 12)); | |
| 74 | 74 | return; |
| 75 | 75 | |
| 76 | 76 | // System calls |
| 77 | 77 | |
| 78 | 78 | case TOK_ASM_scall: // I (pseudo) |
| 79 | − asm_emit_opcode((0x1C << 2) | 3 | (0 << 12)); | |
| 79 | + asm_emit_opcode(S, (0x1C << 2) | 3 | (0 << 12)); | |
| 80 | 80 | return; |
| 81 | 81 | case TOK_ASM_sbreak: // I (pseudo) |
| 82 | − asm_emit_opcode((0x1C << 2) | 3 | (0 << 12) | (1 << 20)); | |
| 82 | + asm_emit_opcode(S, (0x1C << 2) | 3 | (0 << 12) | (1 << 20)); | |
| 83 | 83 | return; |
| 84 | 84 | |
| 85 | 85 | // Privileged Instructions |
| 86 | 86 | |
| 87 | 87 | case TOK_ASM_ecall: |
| 88 | − asm_emit_opcode((0x1C << 2) | 3 | (0 << 20)); | |
| 88 | + asm_emit_opcode(S, (0x1C << 2) | 3 | (0 << 20)); | |
| 89 | 89 | return; |
| 90 | 90 | case TOK_ASM_ebreak: |
| 91 | − asm_emit_opcode((0x1C << 2) | 3 | (1 << 20)); | |
| 91 | + asm_emit_opcode(S, (0x1C << 2) | 3 | (1 << 20)); | |
| 92 | 92 | return; |
| 93 | 93 | |
| 94 | 94 | // Other |
| 95 | 95 | |
| 96 | 96 | case TOK_ASM_wfi: |
| 97 | − asm_emit_opcode((0x1C << 2) | 3 | (0x105 << 20)); | |
| 97 | + asm_emit_opcode(S, (0x1C << 2) | 3 | (0x105 << 20)); | |
| 98 | 98 | return; |
| 99 | 99 | |
| 100 | 100 | default: |
| 101 | − expect("nullary instruction"); | |
| 101 | + expect(S, "nullary instruction"); | |
| 102 | 102 | } |
| 103 | 103 | } |
| 104 | 104 | |
| @@ -121,30 +121,30 @@ typedef struct Operand { · 16 unmodified lines | ||
| 121 | 121 | } Operand; |
| 122 | 122 | |
| 123 | 123 | /* Parse a text containing operand and store the result in OP */ |
| 124 | −static void parse_operand(TCCState *s1, Operand *op) | |
| 124 | +static void parse_operand(TCCState *S, Operand *op) | |
| 125 | 125 | { |
| 126 | 126 | ExprValue e; |
| 127 | 127 | int8_t reg; |
| 128 | 128 | |
| 129 | 129 | op->type = 0; |
| 130 | 130 | |
| 131 | − if ((reg = asm_parse_regvar(tok)) != -1) { | |
| 132 | − next(); // skip register name | |
| 131 | + if ((reg = asm_parse_regvar(S, S->tccpp_tok)) != -1) { | |
| 132 | + next(S); // skip register name | |
| 133 | 133 | op->type = OP_REG; |
| 134 | 134 | op->reg = (uint8_t) reg; |
| 135 | 135 | return; |
| 136 | − } else if (tok == '$') { | |
| 136 | + } else if (S->tccpp_tok == '$') { | |
| 137 | 137 | /* constant value */ |
| 138 | − next(); // skip '#' or '$' | |
| 138 | + next(S); // skip '#' or '$' | |
| 139 | 139 | } |
| 140 | − asm_expr(s1, &e); | |
| 140 | + asm_expr(S, &e); | |
| 141 | 141 | op->type = OP_IM32; |
| 142 | 142 | op->e = e; |
| 143 | 143 | if (!op->e.sym) { |
| 144 | 144 | if ((int) op->e.v >= -2048 && (int) op->e.v < 2048) |
| 145 | 145 | op->type = OP_IM12S; |
| 146 | 146 | } else |
| 147 | − expect("operand"); | |
| 147 | + expect(S, "operand"); | |
| 148 | 148 | } |
| 149 | 149 | |
| 150 | 150 | #define ENCODE_RS1(register_index) ((register_index) << 15) |
| @@ -152,96 +152,96 @@ static void parse_operand(TCCState *s1, Operand *op) · 1 unmodified line | ||
| 152 | 152 | #define ENCODE_RD(register_index) ((register_index) << 7) |
| 153 | 153 | |
| 154 | 154 | // Note: Those all map to CSR--so they are pseudo-instructions. |
| 155 | −static void asm_unary_opcode(TCCState *s1, int token) | |
| 155 | +static void asm_unary_opcode(TCCState *S, int token) | |
| 156 | 156 | { |
| 157 | 157 | uint32_t opcode = (0x1C << 2) | 3 | (2 << 12); |
| 158 | 158 | Operand op; |
| 159 | − parse_operand(s1, &op); | |
| 159 | + parse_operand(S, &op); | |
| 160 | 160 | if (op.type != OP_REG) { |
| 161 | − expect("register"); | |
| 161 | + expect(S, "register"); | |
| 162 | 162 | return; |
| 163 | 163 | } |
| 164 | 164 | opcode |= ENCODE_RD(op.reg); |
| 165 | 165 | |
| 166 | 166 | switch (token) { |
| 167 | 167 | case TOK_ASM_rdcycle: |
| 168 | − asm_emit_opcode(opcode | (0xC00 << 20)); | |
| 168 | + asm_emit_opcode(S, opcode | (0xC00 << 20)); | |
| 169 | 169 | return; |
| 170 | 170 | case TOK_ASM_rdcycleh: |
| 171 | − asm_emit_opcode(opcode | (0xC80 << 20)); | |
| 171 | + asm_emit_opcode(S, opcode | (0xC80 << 20)); | |
| 172 | 172 | return; |
| 173 | 173 | case TOK_ASM_rdtime: |
| 174 | − asm_emit_opcode(opcode | (0xC01 << 20) | ENCODE_RD(op.reg)); | |
| 174 | + asm_emit_opcode(S, opcode | (0xC01 << 20) | ENCODE_RD(op.reg)); | |
| 175 | 175 | return; |
| 176 | 176 | case TOK_ASM_rdtimeh: |
| 177 | − asm_emit_opcode(opcode | (0xC81 << 20) | ENCODE_RD(op.reg)); | |
| 177 | + asm_emit_opcode(S, opcode | (0xC81 << 20) | ENCODE_RD(op.reg)); | |
| 178 | 178 | return; |
| 179 | 179 | case TOK_ASM_rdinstret: |
| 180 | − asm_emit_opcode(opcode | (0xC02 << 20) | ENCODE_RD(op.reg)); | |
| 180 | + asm_emit_opcode(S, opcode | (0xC02 << 20) | ENCODE_RD(op.reg)); | |
| 181 | 181 | return; |
| 182 | 182 | case TOK_ASM_rdinstreth: |
| 183 | − asm_emit_opcode(opcode | (0xC82 << 20) | ENCODE_RD(op.reg)); | |
| 183 | + asm_emit_opcode(S, opcode | (0xC82 << 20) | ENCODE_RD(op.reg)); | |
| 184 | 184 | return; |
| 185 | 185 | default: |
| 186 | − expect("unary instruction"); | |
| 186 | + expect(S, "unary instruction"); | |
| 187 | 187 | } |
| 188 | 188 | } |
| 189 | 189 | |
| 190 | −static void asm_emit_u(int token, uint32_t opcode, const Operand* rd, const Operand* rs2) | |
| 190 | +static void asm_emit_u(TCCState *S, int token, uint32_t opcode, const Operand* rd, const Operand* rs2) | |
| 191 | 191 | { |
| 192 | 192 | if (rd->type != OP_REG) { |
| 193 | − tcc_error("'%s': Expected destination operand that is a register", get_tok_str(token, NULL)); | |
| 193 | + tcc_error(S, "'%s': Expected destination operand that is a register", get_tok_str(S, token, NULL)); | |
| 194 | 194 | return; |
| 195 | 195 | } |
| 196 | 196 | if (rs2->type != OP_IM12S && rs2->type != OP_IM32) { |
| 197 | − tcc_error("'%s': Expected second source operand that is an immediate value", get_tok_str(token, NULL)); | |
| 197 | + tcc_error(S, "'%s': Expected second source operand that is an immediate value", get_tok_str(S, token, NULL)); | |
| 198 | 198 | return; |
| 199 | 199 | } else if (rs2->e.v >= 0x100000) { |
| 200 | − tcc_error("'%s': Expected second source operand that is an immediate value between 0 and 0xfffff", get_tok_str(token, NULL)); | |
| 200 | + tcc_error(S, "'%s': Expected second source operand that is an immediate value between 0 and 0xfffff", get_tok_str(S, token, NULL)); | |
| 201 | 201 | return; |
| 202 | 202 | } |
| 203 | 203 | /* U-type instruction: |
| 204 | 204 | 31...12 imm[31:12] |
| 205 | 205 | 11...7 rd |
| 206 | 206 | 6...0 opcode */ |
| 207 | − gen_le32(opcode | ENCODE_RD(rd->reg) | (rs2->e.v << 12)); | |
| 207 | + gen_le32(S, opcode | ENCODE_RD(rd->reg) | (rs2->e.v << 12)); | |
| 208 | 208 | } |
| 209 | 209 | |
| 210 | −static void asm_binary_opcode(TCCState* s1, int token) | |
| 210 | +static void asm_binary_opcode(TCCState* S, int token) | |
| 211 | 211 | { |
| 212 | 212 | Operand ops[2]; |
| 213 | − parse_operand(s1, &ops[0]); | |
| 214 | − if (tok == ',') | |
| 215 | − next(); | |
| 213 | + parse_operand(S, &ops[0]); | |
| 214 | + if (S->tccpp_tok == ',') | |
| 215 | + next(S); | |
| 216 | 216 | else |
| 217 | − expect("','"); | |
| 218 | − parse_operand(s1, &ops[1]); | |
| 217 | + expect(S, "','"); | |
| 218 | + parse_operand(S, &ops[1]); | |
| 219 | 219 | |
| 220 | 220 | switch (token) { |
| 221 | 221 | case TOK_ASM_lui: |
| 222 | − asm_emit_u(token, (0xD << 2) | 3, &ops[0], &ops[1]); | |
| 222 | + asm_emit_u(S, token, (0xD << 2) | 3, &ops[0], &ops[1]); | |
| 223 | 223 | return; |
| 224 | 224 | case TOK_ASM_auipc: |
| 225 | − asm_emit_u(token, (0x05 << 2) | 3, &ops[0], &ops[1]); | |
| 225 | + asm_emit_u(S, token, (0x05 << 2) | 3, &ops[0], &ops[1]); | |
| 226 | 226 | return; |
| 227 | 227 | default: |
| 228 | − expect("binary instruction"); | |
| 228 | + expect(S, "binary instruction"); | |
| 229 | 229 | } |
| 230 | 230 | } |
| 231 | 231 | |
| 232 | 232 | /* caller: Add funct3, funct7 into opcode */ |
| 233 | −static void asm_emit_r(int token, uint32_t opcode, const Operand* rd, const Operand* rs1, const Operand* rs2) | |
| 233 | +static void asm_emit_r(TCCState* S, int token, uint32_t opcode, const Operand* rd, const Operand* rs1, const Operand* rs2) | |
| 234 | 234 | { |
| 235 | 235 | if (rd->type != OP_REG) { |
| 236 | − tcc_error("'%s': Expected destination operand that is a register", get_tok_str(token, NULL)); | |
| 236 | + tcc_error(S, "'%s': Expected destination operand that is a register", get_tok_str(S, token, NULL)); | |
| 237 | 237 | return; |
| 238 | 238 | } |
| 239 | 239 | if (rs1->type != OP_REG) { |
| 240 | − tcc_error("'%s': Expected first source operand that is a register", get_tok_str(token, NULL)); | |
| 240 | + tcc_error(S, "'%s': Expected first source operand that is a register", get_tok_str(S, token, NULL)); | |
| 241 | 241 | return; |
| 242 | 242 | } |
| 243 | 243 | if (rs2->type != OP_REG) { |
| 244 | − tcc_error("'%s': Expected second source operand that is a register or immediate", get_tok_str(token, NULL)); | |
| 244 | + tcc_error(S, "'%s': Expected second source operand that is a register or immediate", get_tok_str(S, token, NULL)); | |
| 245 | 245 | return; |
| 246 | 246 | } |
| 247 | 247 | /* R-type instruction: |
| @@ -251,22 +251,22 @@ static void asm_emit_r(int token, uint32_t opcode, const Operand* rd, const Oper · 3 unmodified lines | ||
| 251 | 251 | 14...12 funct3 |
| 252 | 252 | 11...7 rd |
| 253 | 253 | 6...0 opcode */ |
| 254 | − gen_le32(opcode | ENCODE_RD(rd->reg) | ENCODE_RS1(rs1->reg) | ENCODE_RS2(rs2->reg)); | |
| 254 | + gen_le32(S, opcode | ENCODE_RD(rd->reg) | ENCODE_RS1(rs1->reg) | ENCODE_RS2(rs2->reg)); | |
| 255 | 255 | } |
| 256 | 256 | |
| 257 | 257 | /* caller: Add funct3 into opcode */ |
| 258 | −static void asm_emit_i(int token, uint32_t opcode, const Operand* rd, const Operand* rs1, const Operand* rs2) | |
| 258 | +static void asm_emit_i(TCCState* S, int token, uint32_t opcode, const Operand* rd, const Operand* rs1, const Operand* rs2) | |
| 259 | 259 | { |
| 260 | 260 | if (rd->type != OP_REG) { |
| 261 | − tcc_error("'%s': Expected destination operand that is a register", get_tok_str(token, NULL)); | |
| 261 | + tcc_error(S, "'%s': Expected destination operand that is a register", get_tok_str(S, token, NULL)); | |
| 262 | 262 | return; |
| 263 | 263 | } |
| 264 | 264 | if (rs1->type != OP_REG) { |
| 265 | − tcc_error("'%s': Expected first source operand that is a register", get_tok_str(token, NULL)); | |
| 265 | + tcc_error(S, "'%s': Expected first source operand that is a register", get_tok_str(S, token, NULL)); | |
| 266 | 266 | return; |
| 267 | 267 | } |
| 268 | 268 | if (rs2->type != OP_IM12S) { |
| 269 | − tcc_error("'%s': Expected second source operand that is an immediate value between 0 and 4095", get_tok_str(token, NULL)); | |
| 269 | + tcc_error(S, "'%s': Expected second source operand that is an immediate value between 0 and 4095", get_tok_str(S, token, NULL)); | |
| 270 | 270 | return; |
| 271 | 271 | } |
| 272 | 272 | /* I-type instruction: |
| @@ -276,156 +276,156 @@ static void asm_emit_i(int token, uint32_t opcode, const Operand* rd, const Oper · 3 unmodified lines | ||
| 276 | 276 | 11...7 rd |
| 277 | 277 | 6...0 opcode */ |
| 278 | 278 | |
| 279 | − gen_le32(opcode | ENCODE_RD(rd->reg) | ENCODE_RS1(rs1->reg) | (rs2->e.v << 20)); | |
| 279 | + gen_le32(S, opcode | ENCODE_RD(rd->reg) | ENCODE_RS1(rs1->reg) | (rs2->e.v << 20)); | |
| 280 | 280 | } |
| 281 | 281 | |
| 282 | −static void asm_shift_opcode(TCCState *s1, int token) | |
| 282 | +static void asm_shift_opcode(TCCState *S, int token) | |
| 283 | 283 | { |
| 284 | 284 | Operand ops[3]; |
| 285 | − parse_operand(s1, &ops[0]); | |
| 286 | − if (tok == ',') | |
| 287 | − next(); | |
| 285 | + parse_operand(S, &ops[0]); | |
| 286 | + if (S->tccpp_tok == ',') | |
| 287 | + next(S); | |
| 288 | 288 | else |
| 289 | − expect("','"); | |
| 290 | − parse_operand(s1, &ops[1]); | |
| 291 | − if (tok == ',') | |
| 292 | − next(); | |
| 289 | + expect(S, "','"); | |
| 290 | + parse_operand(S, &ops[1]); | |
| 291 | + if (S->tccpp_tok == ',') | |
| 292 | + next(S); | |
| 293 | 293 | else |
| 294 | − expect("','"); | |
| 295 | − parse_operand(s1, &ops[2]); | |
| 294 | + expect(S, "','"); | |
| 295 | + parse_operand(S, &ops[2]); | |
| 296 | 296 | |
| 297 | 297 | switch (token) { |
| 298 | 298 | case TOK_ASM_sll: |
| 299 | − asm_emit_r(token, (0xC << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 299 | + asm_emit_r(S, token, (0xC << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 300 | 300 | return; |
| 301 | 301 | case TOK_ASM_slli: |
| 302 | − asm_emit_i(token, (4 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 302 | + asm_emit_i(S, token, (4 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 303 | 303 | return; |
| 304 | 304 | case TOK_ASM_srl: |
| 305 | − asm_emit_r(token, (0xC << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 305 | + asm_emit_r(S, token, (0xC << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 306 | 306 | return; |
| 307 | 307 | case TOK_ASM_srli: |
| 308 | − asm_emit_i(token, (0x4 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 308 | + asm_emit_i(S, token, (0x4 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 309 | 309 | return; |
| 310 | 310 | case TOK_ASM_sra: |
| 311 | − asm_emit_r(token, (0xC << 2) | 3 | (5 << 12) | (32 << 25), &ops[0], &ops[1], &ops[2]); | |
| 311 | + asm_emit_r(S, token, (0xC << 2) | 3 | (5 << 12) | (32 << 25), &ops[0], &ops[1], &ops[2]); | |
| 312 | 312 | return; |
| 313 | 313 | case TOK_ASM_srai: |
| 314 | − asm_emit_i(token, (0x4 << 2) | 3 | (5 << 12) | (16 << 26), &ops[0], &ops[1], &ops[2]); | |
| 314 | + asm_emit_i(S, token, (0x4 << 2) | 3 | (5 << 12) | (16 << 26), &ops[0], &ops[1], &ops[2]); | |
| 315 | 315 | return; |
| 316 | 316 | case TOK_ASM_sllw: |
| 317 | − asm_emit_r(token, (0xE << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 317 | + asm_emit_r(S, token, (0xE << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 318 | 318 | return; |
| 319 | 319 | case TOK_ASM_slliw: |
| 320 | − asm_emit_i(token, (6 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 320 | + asm_emit_i(S, token, (6 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 321 | 321 | return; |
| 322 | 322 | case TOK_ASM_srlw: |
| 323 | − asm_emit_r(token, (0xE << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 323 | + asm_emit_r(S, token, (0xE << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 324 | 324 | return; |
| 325 | 325 | case TOK_ASM_srliw: |
| 326 | − asm_emit_i(token, (0x6 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 326 | + asm_emit_i(S, token, (0x6 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 327 | 327 | return; |
| 328 | 328 | case TOK_ASM_sraw: |
| 329 | − asm_emit_r(token, (0xE << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 329 | + asm_emit_r(S, token, (0xE << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 330 | 330 | return; |
| 331 | 331 | case TOK_ASM_sraiw: |
| 332 | − asm_emit_i(token, (0x6 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 332 | + asm_emit_i(S, token, (0x6 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 333 | 333 | return; |
| 334 | 334 | default: |
| 335 | − expect("shift instruction"); | |
| 335 | + expect(S, "shift instruction"); | |
| 336 | 336 | } |
| 337 | 337 | } |
| 338 | 338 | |
| 339 | −static void asm_data_processing_opcode(TCCState* s1, int token) | |
| 339 | +static void asm_data_processing_opcode(TCCState* S, int token) | |
| 340 | 340 | { |
| 341 | 341 | Operand ops[3]; |
| 342 | − parse_operand(s1, &ops[0]); | |
| 343 | − if (tok == ',') | |
| 344 | − next(); | |
| 342 | + parse_operand(S, &ops[0]); | |
| 343 | + if (S->tccpp_tok == ',') | |
| 344 | + next(S); | |
| 345 | 345 | else |
| 346 | − expect("','"); | |
| 347 | − parse_operand(s1, &ops[1]); | |
| 348 | − if (tok == ',') | |
| 349 | − next(); | |
| 346 | + expect(S, "','"); | |
| 347 | + parse_operand(S, &ops[1]); | |
| 348 | + if (S->tccpp_tok == ',') | |
| 349 | + next(S); | |
| 350 | 350 | else |
| 351 | − expect("','"); | |
| 352 | − parse_operand(s1, &ops[2]); | |
| 351 | + expect(S, "','"); | |
| 352 | + parse_operand(S, &ops[2]); | |
| 353 | 353 | |
| 354 | 354 | switch (token) { |
| 355 | 355 | // Arithmetic (RD,RS1,(RS2|IMM)); R-format, I-format or U-format |
| 356 | 356 | |
| 357 | 357 | case TOK_ASM_add: |
| 358 | − asm_emit_r(token, (0xC << 2) | 3, &ops[0], &ops[1], &ops[2]); | |
| 358 | + asm_emit_r(S, token, (0xC << 2) | 3, &ops[0], &ops[1], &ops[2]); | |
| 359 | 359 | return; |
| 360 | 360 | case TOK_ASM_addi: |
| 361 | − asm_emit_i(token, (4 << 2) | 3, &ops[0], &ops[1], &ops[2]); | |
| 361 | + asm_emit_i(S, token, (4 << 2) | 3, &ops[0], &ops[1], &ops[2]); | |
| 362 | 362 | return; |
| 363 | 363 | case TOK_ASM_sub: |
| 364 | − asm_emit_r(token, (0xC << 2) | 3 | (32 << 25), &ops[0], &ops[1], &ops[2]); | |
| 364 | + asm_emit_r(S, token, (0xC << 2) | 3 | (32 << 25), &ops[0], &ops[1], &ops[2]); | |
| 365 | 365 | return; |
| 366 | 366 | case TOK_ASM_addw: |
| 367 | − asm_emit_r(token, (0xE << 2) | 3 | (0 << 12), &ops[0], &ops[1], &ops[2]); | |
| 367 | + asm_emit_r(S, token, (0xE << 2) | 3 | (0 << 12), &ops[0], &ops[1], &ops[2]); | |
| 368 | 368 | return; |
| 369 | 369 | case TOK_ASM_addiw: // 64 bit |
| 370 | − asm_emit_i(token, (0x6 << 2) | 3 | (0 << 12), &ops[0], &ops[1], &ops[2]); | |
| 370 | + asm_emit_i(S, token, (0x6 << 2) | 3 | (0 << 12), &ops[0], &ops[1], &ops[2]); | |
| 371 | 371 | return; |
| 372 | 372 | case TOK_ASM_subw: |
| 373 | − asm_emit_r(token, (0xE << 2) | 3 | (0 << 12) | (32 << 25), &ops[0], &ops[1], &ops[2]); | |
| 373 | + asm_emit_r(S, token, (0xE << 2) | 3 | (0 << 12) | (32 << 25), &ops[0], &ops[1], &ops[2]); | |
| 374 | 374 | return; |
| 375 | 375 | |
| 376 | 376 | // Logical (RD,RS1,(RS2|IMM)); R-format or I-format |
| 377 | 377 | |
| 378 | 378 | case TOK_ASM_xor: |
| 379 | − asm_emit_r(token, (0xC << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 379 | + asm_emit_r(S, token, (0xC << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 380 | 380 | return; |
| 381 | 381 | case TOK_ASM_xori: |
| 382 | − asm_emit_i(token, (0x4 << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 382 | + asm_emit_i(S, token, (0x4 << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 383 | 383 | return; |
| 384 | 384 | case TOK_ASM_or: |
| 385 | − asm_emit_r(token, (0xC << 2) | 3 | (6 << 12), &ops[0], &ops[1], &ops[2]); | |
| 385 | + asm_emit_r(S, token, (0xC << 2) | 3 | (6 << 12), &ops[0], &ops[1], &ops[2]); | |
| 386 | 386 | return; |
| 387 | 387 | case TOK_ASM_ori: |
| 388 | − asm_emit_i(token, (0x4 << 2) | 3 | (6 << 12), &ops[0], &ops[1], &ops[2]); | |
| 388 | + asm_emit_i(S, token, (0x4 << 2) | 3 | (6 << 12), &ops[0], &ops[1], &ops[2]); | |
| 389 | 389 | return; |
| 390 | 390 | case TOK_ASM_and: |
| 391 | − asm_emit_r(token, (0xC << 2) | 3 | (7 << 12), &ops[0], &ops[1], &ops[2]); | |
| 391 | + asm_emit_r(S, token, (0xC << 2) | 3 | (7 << 12), &ops[0], &ops[1], &ops[2]); | |
| 392 | 392 | return; |
| 393 | 393 | case TOK_ASM_andi: |
| 394 | − asm_emit_i(token, (0x4 << 2) | 3 | (7 << 12), &ops[0], &ops[1], &ops[2]); | |
| 394 | + asm_emit_i(S, token, (0x4 << 2) | 3 | (7 << 12), &ops[0], &ops[1], &ops[2]); | |
| 395 | 395 | return; |
| 396 | 396 | |
| 397 | 397 | // Compare (RD,RS1,(RS2|IMM)); R-format or I-format |
| 398 | 398 | |
| 399 | 399 | case TOK_ASM_slt: |
| 400 | − asm_emit_r(token, (0xC << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 400 | + asm_emit_r(S, token, (0xC << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 401 | 401 | return; |
| 402 | 402 | case TOK_ASM_slti: |
| 403 | − asm_emit_i(token, (0x4 << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 403 | + asm_emit_i(S, token, (0x4 << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 404 | 404 | return; |
| 405 | 405 | case TOK_ASM_sltu: |
| 406 | − asm_emit_r(token, (0xC << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 406 | + asm_emit_r(S, token, (0xC << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 407 | 407 | return; |
| 408 | 408 | case TOK_ASM_sltiu: |
| 409 | − asm_emit_i(token, (0x4 << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 409 | + asm_emit_i(S, token, (0x4 << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 410 | 410 | return; |
| 411 | 411 | default: |
| 412 | − expect("known data processing instruction"); | |
| 412 | + expect(S, "known data processing instruction"); | |
| 413 | 413 | } |
| 414 | 414 | } |
| 415 | 415 | |
| 416 | 416 | /* caller: Add funct3 to opcode */ |
| 417 | −static void asm_emit_s(int token, uint32_t opcode, const Operand* rs1, const Operand* rs2, const Operand* imm) | |
| 417 | +static void asm_emit_s(TCCState* S, int token, uint32_t opcode, const Operand* rs1, const Operand* rs2, const Operand* imm) | |
| 418 | 418 | { |
| 419 | 419 | if (rs1->type != OP_REG) { |
| 420 | − tcc_error("'%s': Expected first source operand that is a register", get_tok_str(token, NULL)); | |
| 420 | + tcc_error(S, "'%s': Expected first source operand that is a register", get_tok_str(S, token, NULL)); | |
| 421 | 421 | return; |
| 422 | 422 | } |
| 423 | 423 | if (rs2->type != OP_REG) { |
| 424 | − tcc_error("'%s': Expected second source operand that is a register", get_tok_str(token, NULL)); | |
| 424 | + tcc_error(S, "'%s': Expected second source operand that is a register", get_tok_str(S, token, NULL)); | |
| 425 | 425 | return; |
| 426 | 426 | } |
| 427 | 427 | if (imm->type != OP_IM12S) { |
| 428 | − tcc_error("'%s': Expected third operand that is an immediate value between 0 and 0xfff", get_tok_str(token, NULL)); | |
| 428 | + tcc_error(S, "'%s': Expected third operand that is an immediate value between 0 and 0xfff", get_tok_str(S, token, NULL)); | |
| 429 | 429 | return; |
| 430 | 430 | } |
| 431 | 431 | { |
| @@ -438,112 +438,112 @@ static void asm_emit_s(int token, uint32_t opcode, const Operand* rs1, const Ope · 6 unmodified lines | ||
| 438 | 438 | 11...7 imm[4:0] |
| 439 | 439 | 6...0 opcode |
| 440 | 440 | opcode always fixed pos. */ |
| 441 | − gen_le32(opcode | ENCODE_RS1(rs1->reg) | ENCODE_RS2(rs2->reg) | ((v & 0x1F) << 7) | ((v >> 5) << 25)); | |
| 441 | + gen_le32(S, opcode | ENCODE_RS1(rs1->reg) | ENCODE_RS2(rs2->reg) | ((v & 0x1F) << 7) | ((v >> 5) << 25)); | |
| 442 | 442 | } |
| 443 | 443 | } |
| 444 | 444 | |
| 445 | −static void asm_data_transfer_opcode(TCCState* s1, int token) | |
| 445 | +static void asm_data_transfer_opcode(TCCState* S, int token) | |
| 446 | 446 | { |
| 447 | 447 | Operand ops[3]; |
| 448 | − parse_operand(s1, &ops[0]); | |
| 448 | + parse_operand(S, &ops[0]); | |
| 449 | 449 | if (ops[0].type != OP_REG) { |
| 450 | − expect("register"); | |
| 450 | + expect(S, "register"); | |
| 451 | 451 | return; |
| 452 | 452 | } |
| 453 | − if (tok == ',') | |
| 454 | − next(); | |
| 453 | + if (S->tccpp_tok == ',') | |
| 454 | + next(S); | |
| 455 | 455 | else |
| 456 | − expect("','"); | |
| 457 | − parse_operand(s1, &ops[1]); | |
| 456 | + expect(S, "','"); | |
| 457 | + parse_operand(S, &ops[1]); | |
| 458 | 458 | if (ops[1].type != OP_REG) { |
| 459 | − expect("register"); | |
| 459 | + expect(S, "register"); | |
| 460 | 460 | return; |
| 461 | 461 | } |
| 462 | − if (tok == ',') | |
| 463 | − next(); | |
| 462 | + if (S->tccpp_tok == ',') | |
| 463 | + next(S); | |
| 464 | 464 | else |
| 465 | − expect("','"); | |
| 466 | − parse_operand(s1, &ops[2]); | |
| 465 | + expect(S, "','"); | |
| 466 | + parse_operand(S, &ops[2]); | |
| 467 | 467 | |
| 468 | 468 | switch (token) { |
| 469 | 469 | // Loads (RD,RS1,I); I-format |
| 470 | 470 | |
| 471 | 471 | case TOK_ASM_lb: |
| 472 | − asm_emit_i(token, (0x0 << 2) | 3, &ops[0], &ops[1], &ops[2]); | |
| 472 | + asm_emit_i(S, token, (0x0 << 2) | 3, &ops[0], &ops[1], &ops[2]); | |
| 473 | 473 | return; |
| 474 | 474 | case TOK_ASM_lh: |
| 475 | − asm_emit_i(token, (0x0 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 475 | + asm_emit_i(S, token, (0x0 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 476 | 476 | return; |
| 477 | 477 | case TOK_ASM_lw: |
| 478 | − asm_emit_i(token, (0x0 << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 478 | + asm_emit_i(S, token, (0x0 << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 479 | 479 | return; |
| 480 | 480 | case TOK_ASM_lbu: |
| 481 | − asm_emit_i(token, (0x0 << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 481 | + asm_emit_i(S, token, (0x0 << 2) | 3 | (4 << 12), &ops[0], &ops[1], &ops[2]); | |
| 482 | 482 | return; |
| 483 | 483 | case TOK_ASM_lhu: |
| 484 | − asm_emit_i(token, (0x0 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 484 | + asm_emit_i(S, token, (0x0 << 2) | 3 | (5 << 12), &ops[0], &ops[1], &ops[2]); | |
| 485 | 485 | return; |
| 486 | 486 | // 64 bit |
| 487 | 487 | case TOK_ASM_ld: |
| 488 | − asm_emit_i(token, (0x0 << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 488 | + asm_emit_i(S, token, (0x0 << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 489 | 489 | return; |
| 490 | 490 | case TOK_ASM_lwu: |
| 491 | − asm_emit_i(token, (0x0 << 2) | 3 | (6 << 12), &ops[0], &ops[1], &ops[2]); | |
| 491 | + asm_emit_i(S, token, (0x0 << 2) | 3 | (6 << 12), &ops[0], &ops[1], &ops[2]); | |
| 492 | 492 | return; |
| 493 | 493 | |
| 494 | 494 | // Stores (RS1,RS2,I); S-format |
| 495 | 495 | |
| 496 | 496 | case TOK_ASM_sb: |
| 497 | − asm_emit_s(token, (0x8 << 2) | 3 | (0 << 12), &ops[0], &ops[1], &ops[2]); | |
| 497 | + asm_emit_s(S, token, (0x8 << 2) | 3 | (0 << 12), &ops[0], &ops[1], &ops[2]); | |
| 498 | 498 | return; |
| 499 | 499 | case TOK_ASM_sh: |
| 500 | − asm_emit_s(token, (0x8 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 500 | + asm_emit_s(S, token, (0x8 << 2) | 3 | (1 << 12), &ops[0], &ops[1], &ops[2]); | |
| 501 | 501 | return; |
| 502 | 502 | case TOK_ASM_sw: |
| 503 | − asm_emit_s(token, (0x8 << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 503 | + asm_emit_s(S, token, (0x8 << 2) | 3 | (2 << 12), &ops[0], &ops[1], &ops[2]); | |
| 504 | 504 | return; |
| 505 | 505 | case TOK_ASM_sd: |
| 506 | − asm_emit_s(token, (0x8 << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 506 | + asm_emit_s(S, token, (0x8 << 2) | 3 | (3 << 12), &ops[0], &ops[1], &ops[2]); | |
| 507 | 507 | return; |
| 508 | 508 | |
| 509 | 509 | default: |
| 510 | − expect("known data transfer instruction"); | |
| 510 | + expect(S, "known data transfer instruction"); | |
| 511 | 511 | } |
| 512 | 512 | } |
| 513 | 513 | |
| 514 | −static void asm_branch_opcode(TCCState* s1, int token) | |
| 514 | +static void asm_branch_opcode(TCCState* S, int token) | |
| 515 | 515 | { |
| 516 | 516 | // Branch (RS1,RS2,IMM); SB-format |
| 517 | 517 | uint32_t opcode = (0x18 << 2) | 3; |
| 518 | 518 | uint32_t offset = 0; |
| 519 | 519 | Operand ops[3]; |
| 520 | − parse_operand(s1, &ops[0]); | |
| 520 | + parse_operand(S, &ops[0]); | |
| 521 | 521 | if (ops[0].type != OP_REG) { |
| 522 | − expect("register"); | |
| 522 | + expect(S, "register"); | |
| 523 | 523 | return; |
| 524 | 524 | } |
| 525 | − if (tok == ',') | |
| 526 | − next(); | |
| 525 | + if (S->tccpp_tok == ',') | |
| 526 | + next(S); | |
| 527 | 527 | else |
| 528 | − expect("','"); | |
| 529 | − parse_operand(s1, &ops[1]); | |
| 528 | + expect(S, "','"); | |
| 529 | + parse_operand(S, &ops[1]); | |
| 530 | 530 | if (ops[1].type != OP_REG) { |
| 531 | − expect("register"); | |
| 531 | + expect(S, "register"); | |
| 532 | 532 | return; |
| 533 | 533 | } |
| 534 | − if (tok == ',') | |
| 535 | − next(); | |
| 534 | + if (S->tccpp_tok == ',') | |
| 535 | + next(S); | |
| 536 | 536 | else |
| 537 | − expect("','"); | |
| 538 | − parse_operand(s1, &ops[2]); | |
| 537 | + expect(S, "','"); | |
| 538 | + parse_operand(S, &ops[2]); | |
| 539 | 539 | |
| 540 | 540 | if (ops[2].type != OP_IM12S) { |
| 541 | − tcc_error("'%s': Expected third operand that is an immediate value between 0 and 0xfff", get_tok_str(token, NULL)); | |
| 541 | + tcc_error(S, "'%s': Expected third operand that is an immediate value between 0 and 0xfff", get_tok_str(S, token, NULL)); | |
| 542 | 542 | return; |
| 543 | 543 | } |
| 544 | 544 | offset = ops[2].e.v; |
| 545 | 545 | if (offset & 1) { |
| 546 | − tcc_error("'%s': Expected third operand that is an even immediate value", get_tok_str(token, NULL)); | |
| 546 | + tcc_error(S, "'%s': Expected third operand that is an even immediate value", get_tok_str(S, token, NULL)); | |
| 547 | 547 | return; |
| 548 | 548 | } |
| 549 | 549 | |
| @@ -567,12 +567,12 @@ static void asm_branch_opcode(TCCState* s1, int token) · 17 unmodified lines | ||
| 567 | 567 | opcode |= 7 << 12; |
| 568 | 568 | break; |
| 569 | 569 | default: |
| 570 | − expect("known branch instruction"); | |
| 570 | + expect(S, "known branch instruction"); | |
| 571 | 571 | } |
| 572 | − asm_emit_opcode(opcode | ENCODE_RS1(ops[0].reg) | ENCODE_RS2(ops[1].reg) | (((offset >> 1) & 0xF) << 8) | (((offset >> 5) & 0x1f) << 25) | (((offset >> 11) & 1) << 7) | (((offset >> 12) & 1) << 31)); | |
| 572 | + asm_emit_opcode(S, opcode | ENCODE_RS1(ops[0].reg) | ENCODE_RS2(ops[1].reg) | (((offset >> 1) & 0xF) << 8) | (((offset >> 5) & 0x1f) << 25) | (((offset >> 11) & 1) << 7) | (((offset >> 12) & 1) << 31)); | |
| 573 | 573 | } |
| 574 | 574 | |
| 575 | −ST_FUNC void asm_opcode(TCCState *s1, int token) | |
| 575 | +ST_FUNC void asm_opcode(TCCState *S, int token) | |
| 576 | 576 | { |
| 577 | 577 | switch (token) { |
| 578 | 578 | case TOK_ASM_fence: |
| @@ -585,7 +585,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 6 unmodified lines | ||
| 585 | 585 | case TOK_ASM_mrth: |
| 586 | 586 | case TOK_ASM_hrts: |
| 587 | 587 | case TOK_ASM_wfi: |
| 588 | − asm_nullary_opcode(s1, token); | |
| 588 | + asm_nullary_opcode(S, token); | |
| 589 | 589 | return; |
| 590 | 590 | |
| 591 | 591 | case TOK_ASM_rdcycle: |
| @@ -594,12 +594,12 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 594 | 594 | case TOK_ASM_rdtimeh: |
| 595 | 595 | case TOK_ASM_rdinstret: |
| 596 | 596 | case TOK_ASM_rdinstreth: |
| 597 | − asm_unary_opcode(s1, token); | |
| 597 | + asm_unary_opcode(S, token); | |
| 598 | 598 | return; |
| 599 | 599 | |
| 600 | 600 | case TOK_ASM_lui: |
| 601 | 601 | case TOK_ASM_auipc: |
| 602 | − asm_binary_opcode(s1, token); | |
| 602 | + asm_binary_opcode(S, token); | |
| 603 | 603 | return; |
| 604 | 604 | |
| 605 | 605 | case TOK_ASM_sll: |
| @@ -620,7 +620,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 14 unmodified lines | ||
| 620 | 620 | case TOK_ASM_srad: |
| 621 | 621 | case TOK_ASM_sraiw: |
| 622 | 622 | case TOK_ASM_sraid: |
| 623 | − asm_shift_opcode(s1, token); | |
| 623 | + asm_shift_opcode(S, token); | |
| 624 | 624 | return; |
| 625 | 625 | |
| 626 | 626 | case TOK_ASM_add: |
| @@ -642,7 +642,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 15 unmodified lines | ||
| 642 | 642 | case TOK_ASM_slti: |
| 643 | 643 | case TOK_ASM_sltu: |
| 644 | 644 | case TOK_ASM_sltiu: |
| 645 | − asm_data_processing_opcode(s1, token); | |
| 645 | + asm_data_processing_opcode(S, token); | |
| 646 | 646 | |
| 647 | 647 | case TOK_ASM_lb: |
| 648 | 648 | case TOK_ASM_lh: |
| @@ -655,7 +655,7 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 6 unmodified lines | ||
| 655 | 655 | case TOK_ASM_sh: |
| 656 | 656 | case TOK_ASM_sw: |
| 657 | 657 | case TOK_ASM_sd: |
| 658 | − asm_data_transfer_opcode(s1, token); | |
| 658 | + asm_data_transfer_opcode(S, token); | |
| 659 | 659 | return; |
| 660 | 660 | |
| 661 | 661 | case TOK_ASM_beq: |
| @@ -664,35 +664,35 @@ ST_FUNC void asm_opcode(TCCState *s1, int token) · 2 unmodified lines | ||
| 664 | 664 | case TOK_ASM_bge: |
| 665 | 665 | case TOK_ASM_bltu: |
| 666 | 666 | case TOK_ASM_bgeu: |
| 667 | − asm_branch_opcode(s1, token); | |
| 667 | + asm_branch_opcode(S, token); | |
| 668 | 668 | return; |
| 669 | 669 | |
| 670 | 670 | default: |
| 671 | − expect("known instruction"); | |
| 671 | + expect(S, "known instruction"); | |
| 672 | 672 | } |
| 673 | 673 | } |
| 674 | 674 | |
| 675 | −ST_FUNC void subst_asm_operand(CString *add_str, SValue *sv, int modifier) | |
| 675 | +ST_FUNC void subst_asm_operand(TCCState *S, CString *add_str, SValue *sv, int modifier) | |
| 676 | 676 | { |
| 677 | − tcc_error("RISCV64 asm not implemented."); | |
| 677 | + tcc_error(S, "RISCV64 asm not implemented."); | |
| 678 | 678 | } |
| 679 | 679 | |
| 680 | 680 | /* generate prolog and epilog code for asm statement */ |
| 681 | −ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, | |
| 681 | +ST_FUNC void asm_gen_code(TCCState *S, ASMOperand *operands, int nb_operands, | |
| 682 | 682 | int nb_outputs, int is_output, |
| 683 | 683 | uint8_t *clobber_regs, |
| 684 | 684 | int out_reg) |
| 685 | 685 | { |
| 686 | 686 | } |
| 687 | 687 | |
| 688 | −ST_FUNC void asm_compute_constraints(ASMOperand *operands, | |
| 688 | +ST_FUNC void asm_compute_constraints(TCCState *S, ASMOperand *operands, | |
| 689 | 689 | int nb_operands, int nb_outputs, |
| 690 | 690 | const uint8_t *clobber_regs, |
| 691 | 691 | int *pout_reg) |
| 692 | 692 | { |
| 693 | 693 | } |
| 694 | 694 | |
| 695 | −ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str) | |
| 695 | +ST_FUNC void asm_clobber(TCCState *S, uint8_t *clobber_regs, const char *str) | |
| 696 | 696 | { |
| 697 | 697 | int reg; |
| 698 | 698 | TokenSym *ts; |
| @@ -701,15 +701,15 @@ ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str) · 2 unmodified lines | ||
| 701 | 701 | !strcmp(str, "cc") || |
| 702 | 702 | !strcmp(str, "flags")) |
| 703 | 703 | return; |
| 704 | − ts = tok_alloc(str, strlen(str)); | |
| 705 | − reg = asm_parse_regvar(ts->tok); | |
| 704 | + ts = tok_alloc(S, str, strlen(str)); | |
| 705 | + reg = asm_parse_regvar(S, ts->tok); | |
| 706 | 706 | if (reg == -1) { |
| 707 | − tcc_error("invalid clobber register '%s'", str); | |
| 707 | + tcc_error(S, "invalid clobber register '%s'", str); | |
| 708 | 708 | } |
| 709 | 709 | clobber_regs[reg] = 1; |
| 710 | 710 | } |
| 711 | 711 | |
| 712 | −ST_FUNC int asm_parse_regvar (int t) | |
| 712 | +ST_FUNC int asm_parse_regvar (TCCState* S, int t) | |
| 713 | 713 | { |
| 714 | 714 | if (t >= TOK_ASM_x0 && t <= TOK_ASM_pc) { /* register name */ |
| 715 | 715 | switch (t) { |
| @@ -74,12 +74,6 @@ ST_DATA const int reg_classes[NB_REGS] = { · 73 unmodified lines | ||
| 74 | 74 | 1 << TREG_SP |
| 75 | 75 | }; |
| 76 | 76 | |
| 77 | −#if defined(CONFIG_TCC_BCHECK) | |
| 78 | −static addr_t func_bound_offset; | |
| 79 | −static unsigned long func_bound_ind; | |
| 80 | −ST_DATA int func_bound_add_epilog; | |
| 81 | −#endif | |
| 82 | − | |
| 83 | 77 | static int ireg(int r) |
| 84 | 78 | { |
| 85 | 79 | if (r == TREG_RA) |
| @@ -106,46 +100,46 @@ static int is_freg(int r) · 20 unmodified lines | ||
| 106 | 100 | return r >= 8 && r < 16; |
| 107 | 101 | } |
| 108 | 102 | |
| 109 | −ST_FUNC void o(unsigned int c) | |
| 103 | +ST_FUNC void o(TCCState* S, unsigned int c) | |
| 110 | 104 | { |
| 111 | − int ind1 = ind + 4; | |
| 112 | − if (nocode_wanted) | |
| 105 | + int ind1 = S->tccgen_ind + 4; | |
| 106 | + if (S->tccgen_nocode_wanted) | |
| 113 | 107 | return; |
| 114 | 108 | if (ind1 > cur_text_section->data_allocated) |
| 115 | − section_realloc(cur_text_section, ind1); | |
| 116 | − write32le(cur_text_section->data + ind, c); | |
| 117 | − ind = ind1; | |
| 109 | + section_realloc(S, cur_text_section, ind1); | |
| 110 | + write32le(cur_text_section->data + S->tccgen_ind, c); | |
| 111 | + S->tccgen_ind = ind1; | |
| 118 | 112 | } |
| 119 | 113 | |
| 120 | −static void EIu(uint32_t opcode, uint32_t func3, | |
| 114 | +static void EIu(TCCState* S, uint32_t opcode, uint32_t func3, | |
| 121 | 115 | uint32_t rd, uint32_t rs1, uint32_t imm) |
| 122 | 116 | { |
| 123 | − o(opcode | (func3 << 12) | (rd << 7) | (rs1 << 15) | (imm << 20)); | |
| 117 | + o(S, opcode | (func3 << 12) | (rd << 7) | (rs1 << 15) | (imm << 20)); | |
| 124 | 118 | } |
| 125 | 119 | |
| 126 | −static void ER(uint32_t opcode, uint32_t func3, | |
| 120 | +static void ER(TCCState* S, uint32_t opcode, uint32_t func3, | |
| 127 | 121 | uint32_t rd, uint32_t rs1, uint32_t rs2, uint32_t func7) |
| 128 | 122 | { |
| 129 | − o(opcode | func3 << 12 | rd << 7 | rs1 << 15 | rs2 << 20 | func7 << 25); | |
| 123 | + o(S, opcode | func3 << 12 | rd << 7 | rs1 << 15 | rs2 << 20 | func7 << 25); | |
| 130 | 124 | } |
| 131 | 125 | |
| 132 | −static void EI(uint32_t opcode, uint32_t func3, | |
| 126 | +static void EI(TCCState* S, uint32_t opcode, uint32_t func3, | |
| 133 | 127 | uint32_t rd, uint32_t rs1, uint32_t imm) |
| 134 | 128 | { |
| 135 | 129 | assert(! ((imm + (1 << 11)) >> 12)); |
| 136 | − EIu(opcode, func3, rd, rs1, imm); | |
| 130 | + EIu(S, opcode, func3, rd, rs1, imm); | |
| 137 | 131 | } |
| 138 | 132 | |
| 139 | −static void ES(uint32_t opcode, uint32_t func3, | |
| 133 | +static void ES(TCCState* S, uint32_t opcode, uint32_t func3, | |
| 140 | 134 | uint32_t rs1, uint32_t rs2, uint32_t imm) |
| 141 | 135 | { |
| 142 | 136 | assert(! ((imm + (1 << 11)) >> 12)); |
| 143 | − o(opcode | (func3 << 12) | ((imm & 0x1f) << 7) | (rs1 << 15) | |
| 137 | + o(S, opcode | (func3 << 12) | ((imm & 0x1f) << 7) | (rs1 << 15) | |
| 144 | 138 | | (rs2 << 20) | ((imm >> 5) << 25)); |
| 145 | 139 | } |
| 146 | 140 | |
| 147 | 141 | // Patch all branches in list pointed to by t to branch to a: |
| 148 | −ST_FUNC void gsym_addr(int t_, int a_) | |
| 142 | +ST_FUNC void gsym_addr(TCCState* S, int t_, int a_) | |
| 149 | 143 | { |
| 150 | 144 | uint32_t t = t_; |
| 151 | 145 | uint32_t a = a_; |
| @@ -154,7 +148,7 @@ ST_FUNC void gsym_addr(int t_, int a_) · 2 unmodified lines | ||
| 154 | 148 | uint32_t next = read32le(ptr); |
| 155 | 149 | uint32_t r = a - t, imm; |
| 156 | 150 | if ((r + (1 << 21)) & ~((1U << 22) - 2)) |
| 157 | − tcc_error("out-of-range branch chain"); | |
| 151 | + tcc_error(S, "out-of-range branch chain"); | |
| 158 | 152 | imm = (((r >> 12) & 0xff) << 12) |
| 159 | 153 | | (((r >> 11) & 1) << 20) |
| 160 | 154 | | (((r >> 1) & 0x3ff) << 21) |
| @@ -164,7 +158,7 @@ ST_FUNC void gsym_addr(int t_, int a_) · 3 unmodified lines | ||
| 164 | 158 | } |
| 165 | 159 | } |
| 166 | 160 | |
| 167 | −static int load_symofs(int r, SValue *sv, int forstore) | |
| 161 | +static int load_symofs(TCCState* S, int r, SValue *sv, int forstore) | |
| 168 | 162 | { |
| 169 | 163 | int rr, doload = 0; |
| 170 | 164 | int fc = sv->c.i, v = sv->r & VT_VALMASK; |
| @@ -172,56 +166,56 @@ static int load_symofs(int r, SValue *sv, int forstore) · 1 unmodified line | ||
| 172 | 166 | Sym label = {0}; |
| 173 | 167 | assert(v == VT_CONST); |
| 174 | 168 | if (sv->sym->type.t & VT_STATIC) { // XXX do this per linker relax |
| 175 | − greloca(cur_text_section, sv->sym, ind, | |
| 169 | + greloca(S, cur_text_section, sv->sym, S->tccgen_ind, | |
| 176 | 170 | R_RISCV_PCREL_HI20, sv->c.i); |
| 177 | 171 | sv->c.i = 0; |
| 178 | 172 | } else { |
| 179 | 173 | if (((unsigned)fc + (1 << 11)) >> 12) |
| 180 | − tcc_error("unimp: large addend for global address (0x%lx)", (long)sv->c.i); | |
| 181 | − greloca(cur_text_section, sv->sym, ind, | |
| 174 | + tcc_error(S, "unimp: large addend for global address (0x%lx)", (long)sv->c.i); | |
| 175 | + greloca(S, cur_text_section, sv->sym, S->tccgen_ind, | |
| 182 | 176 | R_RISCV_GOT_HI20, 0); |
| 183 | 177 | doload = 1; |
| 184 | 178 | } |
| 185 | 179 | label.type.t = VT_VOID | VT_STATIC; |
| 186 | − put_extern_sym(&label, cur_text_section, ind, 0); | |
| 180 | + put_extern_sym(S, &label, cur_text_section, S->tccgen_ind, 0); | |
| 187 | 181 | rr = is_ireg(r) ? ireg(r) : 5; |
| 188 | − o(0x17 | (rr << 7)); // auipc RR, 0 %pcrel_hi(sym)+addend | |
| 189 | − greloca(cur_text_section, &label, ind, | |
| 182 | + o(S, 0x17 | (rr << 7)); // auipc RR, 0 %pcrel_hi(sym)+addend | |
| 183 | + greloca(S, cur_text_section, &label, S->tccgen_ind, | |
| 190 | 184 | doload || !forstore |
| 191 | 185 | ? R_RISCV_PCREL_LO12_I : R_RISCV_PCREL_LO12_S, 0); |
| 192 | 186 | if (doload) { |
| 193 | − EI(0x03, 3, rr, rr, 0); // ld RR, 0(RR) | |
| 187 | + EI(S, 0x03, 3, rr, rr, 0); // ld RR, 0(RR) | |
| 194 | 188 | } |
| 195 | 189 | } else if (v == VT_LOCAL || v == VT_LLOCAL) { |
| 196 | 190 | rr = 8; // s0 |
| 197 | 191 | if (fc != sv->c.i) |
| 198 | − tcc_error("unimp: store(giant local off) (0x%lx)", (long)sv->c.i); | |
| 192 | + tcc_error(S, "unimp: store(giant local off) (0x%lx)", (long)sv->c.i); | |
| 199 | 193 | if (((unsigned)fc + (1 << 11)) >> 12) { |
| 200 | 194 | rr = is_ireg(r) ? ireg(r) : 5; // t0 |
| 201 | − o(0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) | |
| 202 | − ER(0x33, 0, rr, rr, 8, 0); // add RR, RR, s0 | |
| 195 | + o(S, 0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) | |
| 196 | + ER(S, 0x33, 0, rr, rr, 8, 0); // add RR, RR, s0 | |
| 203 | 197 | sv->c.i = fc << 20 >> 20; |
| 204 | 198 | } |
| 205 | 199 | } else |
| 206 | − tcc_error("uhh"); | |
| 200 | + tcc_error(S, "uhh"); | |
| 207 | 201 | return rr; |
| 208 | 202 | } |
| 209 | 203 | |
| 210 | −static void load_large_constant(int rr, int fc, uint32_t pi) | |
| 204 | +static void load_large_constant(TCCState* S, int rr, int fc, uint32_t pi) | |
| 211 | 205 | { |
| 212 | 206 | if (fc < 0) |
| 213 | 207 | pi++; |
| 214 | − o(0x37 | (rr << 7) | (((pi + 0x800) & 0xfffff000))); // lui RR, up(up(fc)) | |
| 215 | − EI(0x13, 0, rr, rr, (int)pi << 20 >> 20); // addi RR, RR, lo(up(fc)) | |
| 216 | − EI(0x13, 1, rr, rr, 12); // slli RR, RR, 12 | |
| 217 | − EI(0x13, 0, rr, rr, (fc + (1 << 19)) >> 20); // addi RR, RR, up(lo(fc)) | |
| 218 | − EI(0x13, 1, rr, rr, 12); // slli RR, RR, 12 | |
| 208 | + o(S, 0x37 | (rr << 7) | (((pi + 0x800) & 0xfffff000))); // lui RR, up(up(fc)) | |
| 209 | + EI(S, 0x13, 0, rr, rr, (int)pi << 20 >> 20); // addi RR, RR, lo(up(fc)) | |
| 210 | + EI(S, 0x13, 1, rr, rr, 12); // slli RR, RR, 12 | |
| 211 | + EI(S, 0x13, 0, rr, rr, (fc + (1 << 19)) >> 20); // addi RR, RR, up(lo(fc)) | |
| 212 | + EI(S, 0x13, 1, rr, rr, 12); // slli RR, RR, 12 | |
| 219 | 213 | fc = fc << 12 >> 12; |
| 220 | − EI(0x13, 0, rr, rr, fc >> 8); // addi RR, RR, lo1(lo(fc)) | |
| 221 | − EI(0x13, 1, rr, rr, 8); // slli RR, RR, 8 | |
| 214 | + EI(S, 0x13, 0, rr, rr, fc >> 8); // addi RR, RR, lo1(lo(fc)) | |
| 215 | + EI(S, 0x13, 1, rr, rr, 8); // slli RR, RR, 8 | |
| 222 | 216 | } |
| 223 | 217 | |
| 224 | −ST_FUNC void load(int r, SValue *sv) | |
| 218 | +ST_FUNC void load(TCCState* S, int r, SValue *sv) | |
| 225 | 219 | { |
| 226 | 220 | int fr = sv->r; |
| 227 | 221 | int v = fr & VT_VALMASK; |
| @@ -239,49 +233,49 @@ ST_FUNC void load(int r, SValue *sv) · 11 unmodified lines | ||
| 239 | 233 | if (size < 4 && !is_float(sv->type.t) && (sv->type.t & VT_UNSIGNED)) |
| 240 | 234 | func3 |= 4; |
| 241 | 235 | if (v == VT_LOCAL || (fr & VT_SYM)) { |
| 242 | − br = load_symofs(r, sv, 0); | |
| 236 | + br = load_symofs(S, r, sv, 0); | |
| 243 | 237 | fc = sv->c.i; |
| 244 | 238 | } else if (v < VT_CONST) { |
| 245 | 239 | br = ireg(v); |
| 246 | 240 | /*if (((unsigned)fc + (1 << 11)) >> 12) |
| 247 | − tcc_error("unimp: load(large addend) (0x%x)", fc);*/ | |
| 241 | + tcc_error(S, "unimp: load(large addend) (0x%x)", fc);*/ | |
| 248 | 242 | fc = 0; // XXX store ofs in LVAL(reg) |
| 249 | 243 | } else if (v == VT_LLOCAL) { |
| 250 | − br = load_symofs(r, sv, 0); | |
| 244 | + br = load_symofs(S, r, sv, 0); | |
| 251 | 245 | fc = sv->c.i; |
| 252 | − EI(0x03, 3, rr, br, fc); // ld RR, fc(BR) | |
| 246 | + EI(S, 0x03, 3, rr, br, fc); // ld RR, fc(BR) | |
| 253 | 247 | br = rr; |
| 254 | 248 | fc = 0; |
| 255 | 249 | } else if (v == VT_CONST) { |
| 256 | 250 | int64_t si = sv->c.i; |
| 257 | 251 | si >>= 32; |
| 258 | 252 | if (si != 0) { |
| 259 | − load_large_constant(rr, fc, si); | |
| 253 | + load_large_constant(S, rr, fc, si); | |
| 260 | 254 | fc &= 0xff; |
| 261 | 255 | } else { |
| 262 | − o(0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) | |
| 256 | + o(S, 0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) | |
| 263 | 257 | fc = fc << 20 >> 20; |
| 264 | 258 | } |
| 265 | 259 | br = rr; |
| 266 | 260 | } else { |
| 267 | − tcc_error("unimp: load(non-local lval)"); | |
| 261 | + tcc_error(S, "unimp: load(non-local lval)"); | |
| 268 | 262 | } |
| 269 | − EI(opcode, func3, rr, br, fc); // l[bhwd][u] / fl[wd] RR, fc(BR) | |
| 263 | + EI(S, opcode, func3, rr, br, fc); // l[bhwd][u] / fl[wd] RR, fc(BR) | |
| 270 | 264 | } else if (v == VT_CONST) { |
| 271 | 265 | int rb = 0, do32bit = 8, zext = 0; |
| 272 | 266 | assert((!is_float(sv->type.t) && is_ireg(r)) || bt == VT_LDOUBLE); |
| 273 | 267 | if (fr & VT_SYM) { |
| 274 | − rb = load_symofs(r, sv, 0); | |
| 268 | + rb = load_symofs(S, r, sv, 0); | |
| 275 | 269 | fc = sv->c.i; |
| 276 | 270 | do32bit = 0; |
| 277 | 271 | } |
| 278 | 272 | if (is_float(sv->type.t) && bt != VT_LDOUBLE) |
| 279 | − tcc_error("unimp: load(float)"); | |
| 273 | + tcc_error(S, "unimp: load(float)"); | |
| 280 | 274 | if (fc != sv->c.i) { |
| 281 | 275 | int64_t si = sv->c.i; |
| 282 | 276 | si >>= 32; |
| 283 | 277 | if (si != 0) { |
| 284 | − load_large_constant(rr, fc, si); | |
| 278 | + load_large_constant(S, rr, fc, si); | |
| 285 | 279 | fc &= 0xff; |
| 286 | 280 | rb = rr; |
| 287 | 281 | do32bit = 0; |
| @@ -292,37 +286,37 @@ ST_FUNC void load(int r, SValue *sv) · 4 unmodified lines | ||
| 292 | 286 | } |
| 293 | 287 | } |
| 294 | 288 | if (((unsigned)fc + (1 << 11)) >> 12) |
| 295 | − o(0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)), rb = rr; //lui RR, upper(fc) | |
| 289 | + o(S, 0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)), rb = rr; //lui RR, upper(fc) | |
| 296 | 290 | if (fc || (rr != rb) || do32bit || (fr & VT_SYM)) |
| 297 | − EI(0x13 | do32bit, 0, rr, rb, fc << 20 >> 20); // addi[w] R, x0|R, FC | |
| 291 | + EI(S, 0x13 | do32bit, 0, rr, rb, fc << 20 >> 20); // addi[w] R, x0|R, FC | |
| 298 | 292 | if (zext) { |
| 299 | − EI(0x13, 1, rr, rr, 32); // slli RR, RR, 32 | |
| 300 | − EI(0x13, 5, rr, rr, 32); // srli RR, RR, 32 | |
| 293 | + EI(S, 0x13, 1, rr, rr, 32); // slli RR, RR, 32 | |
| 294 | + EI(S, 0x13, 5, rr, rr, 32); // srli RR, RR, 32 | |
| 301 | 295 | } |
| 302 | 296 | } else if (v == VT_LOCAL) { |
| 303 | − int br = load_symofs(r, sv, 0); | |
| 297 | + int br = load_symofs(S, r, sv, 0); | |
| 304 | 298 | assert(is_ireg(r)); |
| 305 | 299 | fc = sv->c.i; |
| 306 | − EI(0x13, 0, rr, br, fc); // addi R, s0, FC | |
| 300 | + EI(S, 0x13, 0, rr, br, fc); // addi R, s0, FC | |
| 307 | 301 | } else if (v < VT_CONST) { /* reg-reg */ |
| 308 | 302 | //assert(!fc); XXX support offseted regs |
| 309 | 303 | if (is_freg(r) && is_freg(v)) |
| 310 | − ER(0x53, 0, rr, freg(v), freg(v), bt == VT_DOUBLE ? 0x11 : 0x10); //fsgnj.[sd] RR, V, V == fmv.[sd] RR, V | |
| 304 | + ER(S, 0x53, 0, rr, freg(v), freg(v), bt == VT_DOUBLE ? 0x11 : 0x10); //fsgnj.[sd] RR, V, V == fmv.[sd] RR, V | |
| 311 | 305 | else if (is_ireg(r) && is_ireg(v)) |
| 312 | − EI(0x13, 0, rr, ireg(v), 0); // addi RR, V, 0 == mv RR, V | |
| 306 | + EI(S, 0x13, 0, rr, ireg(v), 0); // addi RR, V, 0 == mv RR, V | |
| 313 | 307 | else { |
| 314 | 308 | int func7 = is_ireg(r) ? 0x70 : 0x78; |
| 315 | 309 | size = type_size(&sv->type, &align); |
| 316 | 310 | if (size == 8) |
| 317 | 311 | func7 |= 1; |
| 318 | 312 | assert(size == 4 || size == 8); |
| 319 | − o(0x53 | (rr << 7) | ((is_freg(v) ? freg(v) : ireg(v)) << 15) | |
| 313 | + o(S, 0x53 | (rr << 7) | ((is_freg(v) ? freg(v) : ireg(v)) << 15) | |
| 320 | 314 | | (func7 << 25)); // fmv.{w.x, x.w, d.x, x.d} RR, VR |
| 321 | 315 | } |
| 322 | 316 | } else if (v == VT_CMP) { |
| 323 | − int op = vtop->cmp_op; | |
| 324 | − int a = vtop->cmp_r & 0xff; | |
| 325 | − int b = (vtop->cmp_r >> 8) & 0xff; | |
| 317 | + int op = S->tccgen_vtop->cmp_op; | |
| 318 | + int a = S->tccgen_vtop->cmp_r & 0xff; | |
| 319 | + int b = (S->tccgen_vtop->cmp_r >> 8) & 0xff; | |
| 326 | 320 | int inv = 0; |
| 327 | 321 | switch (op) { |
| 328 | 322 | case TOK_ULT: |
| @@ -341,32 +335,32 @@ ST_FUNC void load(int r, SValue *sv) · 12 unmodified lines | ||
| 341 | 335 | int t = a; a = b; b = t; |
| 342 | 336 | inv ^= 1; |
| 343 | 337 | } |
| 344 | − ER(0x33, (op > TOK_UGT) ? 2 : 3, rr, a, b, 0); // slt[u] d, a, b | |
| 338 | + ER(S, 0x33, (op > TOK_UGT) ? 2 : 3, rr, a, b, 0); // slt[u] d, a, b | |
| 345 | 339 | if (inv) |
| 346 | − EI(0x13, 4, rr, rr, 1); // xori d, d, 1 | |
| 340 | + EI(S, 0x13, 4, rr, rr, 1); // xori d, d, 1 | |
| 347 | 341 | break; |
| 348 | 342 | case TOK_NE: |
| 349 | 343 | case TOK_EQ: |
| 350 | 344 | if (rr != a || b) |
| 351 | − ER(0x33, 0, rr, a, b, 0x20); // sub d, a, b | |
| 345 | + ER(S, 0x33, 0, rr, a, b, 0x20); // sub d, a, b | |
| 352 | 346 | if (op == TOK_NE) |
| 353 | − ER(0x33, 3, rr, 0, rr, 0); // sltu d, x0, d == snez d,d | |
| 347 | + ER(S, 0x33, 3, rr, 0, rr, 0); // sltu d, x0, d == snez d,d | |
| 354 | 348 | else |
| 355 | − EI(0x13, 3, rr, rr, 1); // sltiu d, d, 1 == seqz d,d | |
| 349 | + EI(S, 0x13, 3, rr, rr, 1); // sltiu d, d, 1 == seqz d,d | |
| 356 | 350 | break; |
| 357 | 351 | } |
| 358 | 352 | } else if ((v & ~1) == VT_JMP) { |
| 359 | 353 | int t = v & 1; |
| 360 | 354 | assert(is_ireg(r)); |
| 361 | − EI(0x13, 0, rr, 0, t); // addi RR, x0, t | |
| 362 | − gjmp_addr(ind + 8); | |
| 363 | − gsym(fc); | |
| 364 | − EI(0x13, 0, rr, 0, t ^ 1); // addi RR, x0, !t | |
| 355 | + EI(S, 0x13, 0, rr, 0, t); // addi RR, x0, t | |
| 356 | + gjmp_addr(S, S->tccgen_ind + 8); | |
| 357 | + gsym(S, fc); | |
| 358 | + EI(S, 0x13, 0, rr, 0, t ^ 1); // addi RR, x0, !t | |
| 365 | 359 | } else |
| 366 | − tcc_error("unimp: load(non-const)"); | |
| 360 | + tcc_error(S, "unimp: load(non-const)"); | |
| 367 | 361 | } |
| 368 | 362 | |
| 369 | −ST_FUNC void store(int r, SValue *sv) | |
| 363 | +ST_FUNC void store(TCCState* S, int r, SValue *sv) | |
| 370 | 364 | { |
| 371 | 365 | int fr = sv->r & VT_VALMASK; |
| 372 | 366 | int rr = is_ireg(r) ? ireg(r) : freg(r), ptrreg; |
| @@ -379,125 +373,125 @@ ST_FUNC void store(int r, SValue *sv) · 6 unmodified lines | ||
| 379 | 373 | if (bt == VT_LDOUBLE) |
| 380 | 374 | size = align = 8; |
| 381 | 375 | if (bt == VT_STRUCT) |
| 382 | − tcc_error("unimp: store(struct)"); | |
| 376 | + tcc_error(S, "unimp: store(struct)"); | |
| 383 | 377 | if (size > 8) |
| 384 | − tcc_error("unimp: large sized store"); | |
| 378 | + tcc_error(S, "unimp: large sized store"); | |
| 385 | 379 | assert(sv->r & VT_LVAL); |
| 386 | 380 | if (fr == VT_LOCAL || (sv->r & VT_SYM)) { |
| 387 | − ptrreg = load_symofs(-1, sv, 1); | |
| 381 | + ptrreg = load_symofs(S, -1, sv, 1); | |
| 388 | 382 | fc = sv->c.i; |
| 389 | 383 | } else if (fr < VT_CONST) { |
| 390 | 384 | ptrreg = ireg(fr); |
| 391 | 385 | /*if (((unsigned)fc + (1 << 11)) >> 12) |
| 392 | − tcc_error("unimp: store(large addend) (0x%x)", fc);*/ | |
| 386 | + tcc_error(S, "unimp: store(large addend) (0x%x)", fc);*/ | |
| 393 | 387 | fc = 0; // XXX support offsets regs |
| 394 | 388 | } else if (fr == VT_CONST) { |
| 395 | 389 | int64_t si = sv->c.i; |
| 396 | 390 | ptrreg = 8; // s0 |
| 397 | 391 | si >>= 32; |
| 398 | 392 | if (si != 0) { |
| 399 | − load_large_constant(ptrreg, fc, si); | |
| 393 | + load_large_constant(S, ptrreg, fc, si); | |
| 400 | 394 | fc &= 0xff; |
| 401 | 395 | } else { |
| 402 | − o(0x37 | (ptrreg << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) | |
| 396 | + o(S, 0x37 | (ptrreg << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) | |
| 403 | 397 | fc = fc << 20 >> 20; |
| 404 | 398 | } |
| 405 | 399 | } else |
| 406 | − tcc_error("implement me: %s(!local)", __FUNCTION__); | |
| 407 | − ES(is_freg(r) ? 0x27 : 0x23, // fs... | s... | |
| 400 | + tcc_error(S, "implement me: %s(!local)", __FUNCTION__); | |
| 401 | + ES(S, is_freg(r) ? 0x27 : 0x23, // fs... | s... | |
| 408 | 402 | size == 1 ? 0 : size == 2 ? 1 : size == 4 ? 2 : 3, // ... [wd] | [bhwd] |
| 409 | 403 | ptrreg, rr, fc); // RR, fc(base) |
| 410 | 404 | } |
| 411 | 405 | |
| 412 | −static void gcall_or_jmp(int docall) | |
| 406 | +static void gcall_or_jmp(TCCState* S, int docall) | |
| 413 | 407 | { |
| 414 | 408 | int tr = docall ? 1 : 5; // ra or t0 |
| 415 | − if ((vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST && | |
| 416 | − ((vtop->r & VT_SYM) && vtop->c.i == (int)vtop->c.i)) { | |
| 409 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL)) == VT_CONST && | |
| 410 | + ((S->tccgen_vtop->r & VT_SYM) && S->tccgen_vtop->c.i == (int)S->tccgen_vtop->c.i)) { | |
| 417 | 411 | /* constant symbolic case -> simple relocation */ |
| 418 | − greloca(cur_text_section, vtop->sym, ind, | |
| 419 | − R_RISCV_CALL_PLT, (int)vtop->c.i); | |
| 420 | − o(0x17 | (tr << 7)); // auipc TR, 0 %call(func) | |
| 421 | − EI(0x67, 0, tr, tr, 0);// jalr TR, r(TR) | |
| 422 | − } else if (vtop->r < VT_CONST) { | |
| 423 | − int r = ireg(vtop->r); | |
| 424 | − EI(0x67, 0, tr, r, 0); // jalr TR, 0(R) | |
| 412 | + greloca(S, cur_text_section, S->tccgen_vtop->sym, S->tccgen_ind, | |
| 413 | + R_RISCV_CALL_PLT, (int)S->tccgen_vtop->c.i); | |
| 414 | + o(S, 0x17 | (tr << 7)); // auipc TR, 0 %call(func) | |
| 415 | + EI(S, 0x67, 0, tr, tr, 0);// jalr TR, r(TR) | |
| 416 | + } else if (S->tccgen_vtop->r < VT_CONST) { | |
| 417 | + int r = ireg(S->tccgen_vtop->r); | |
| 418 | + EI(S, 0x67, 0, tr, r, 0); // jalr TR, 0(R) | |
| 425 | 419 | } else { |
| 426 | 420 | int r = TREG_RA; |
| 427 | − load(r, vtop); | |
| 421 | + load(S, r, S->tccgen_vtop); | |
| 428 | 422 | r = ireg(r); |
| 429 | − EI(0x67, 0, tr, r, 0); // jalr TR, 0(R) | |
| 423 | + EI(S, 0x67, 0, tr, r, 0); // jalr TR, 0(R) | |
| 430 | 424 | } |
| 431 | 425 | } |
| 432 | 426 | |
| 433 | 427 | #if defined(CONFIG_TCC_BCHECK) |
| 434 | 428 | |
| 435 | −static void gen_bounds_call(int v) | |
| 429 | +static void gen_bounds_call(TCCState* S, int v) | |
| 436 | 430 | { |
| 437 | − Sym *sym = external_helper_sym(v); | |
| 431 | + Sym *sym = external_helper_sym(S, v); | |
| 438 | 432 | |
| 439 | − greloca(cur_text_section, sym, ind, R_RISCV_CALL_PLT, 0); | |
| 440 | − o(0x17 | (1 << 7)); // auipc TR, 0 %call(func) | |
| 441 | − EI(0x67, 0, 1, 1, 0); // jalr TR, r(TR) | |
| 433 | + greloca(S, cur_text_section, sym, S->tccgen_ind, R_RISCV_CALL_PLT, 0); | |
| 434 | + o(S, 0x17 | (1 << 7)); // auipc TR, 0 %call(func) | |
| 435 | + EI(S, 0x67, 0, 1, 1, 0); // jalr TR, r(TR) | |
| 442 | 436 | } |
| 443 | 437 | |
| 444 | −static void gen_bounds_prolog(void) | |
| 438 | +static void gen_bounds_prolog(TCCState* S) | |
| 445 | 439 | { |
| 446 | 440 | /* leave some room for bound checking code */ |
| 447 | − func_bound_offset = lbounds_section->data_offset; | |
| 448 | − func_bound_ind = ind; | |
| 449 | − func_bound_add_epilog = 0; | |
| 450 | − o(0x00000013); /* ld a0,#lbound section pointer */ | |
| 451 | − o(0x00000013); | |
| 452 | − o(0x00000013); /* nop -> call __bound_local_new */ | |
| 453 | − o(0x00000013); | |
| 441 | + S->func_bound_offset = lbounds_section->data_offset; | |
| 442 | + S->func_bound_ind = S->tccgen_ind; | |
| 443 | + S->func_bound_add_epilog = 0; | |
| 444 | + o(S, 0x00000013); /* ld a0,#lbound section pointer */ | |
| 445 | + o(S, 0x00000013); | |
| 446 | + o(S, 0x00000013); /* nop -> call __bound_local_new */ | |
| 447 | + o(S, 0x00000013); | |
| 454 | 448 | } |
| 455 | 449 | |
| 456 | −static void gen_bounds_epilog(void) | |
| 450 | +static void gen_bounds_epilog(TCCState* S) | |
| 457 | 451 | { |
| 458 | 452 | addr_t saved_ind; |
| 459 | 453 | addr_t *bounds_ptr; |
| 460 | 454 | Sym *sym_data; |
| 461 | 455 | Sym label = {0}; |
| 462 | 456 | |
| 463 | − int offset_modified = func_bound_offset != lbounds_section->data_offset; | |
| 457 | + int offset_modified = S->func_bound_offset != lbounds_section->data_offset; | |
| 464 | 458 | |
| 465 | − if (!offset_modified && !func_bound_add_epilog) | |
| 459 | + if (!offset_modified && !S->func_bound_add_epilog) | |
| 466 | 460 | return; |
| 467 | 461 | |
| 468 | 462 | /* add end of table info */ |
| 469 | − bounds_ptr = section_ptr_add(lbounds_section, sizeof(addr_t)); | |
| 463 | + bounds_ptr = section_ptr_add(S, lbounds_section, sizeof(addr_t)); | |
| 470 | 464 | *bounds_ptr = 0; |
| 471 | 465 | |
| 472 | − sym_data = get_sym_ref(&char_pointer_type, lbounds_section, | |
| 473 | − func_bound_offset, lbounds_section->data_offset); | |
| 466 | + sym_data = get_sym_ref(S, &S->tccgen_char_pointer_type, lbounds_section, | |
| 467 | + S->func_bound_offset, lbounds_section->data_offset); | |
| 474 | 468 | |
| 475 | 469 | label.type.t = VT_VOID | VT_STATIC; |
| 476 | 470 | /* generate bound local allocation */ |
| 477 | 471 | if (offset_modified) { |
| 478 | − saved_ind = ind; | |
| 479 | − ind = func_bound_ind; | |
| 480 | − put_extern_sym(&label, cur_text_section, ind, 0); | |
| 481 | − greloca(cur_text_section, sym_data, ind, R_RISCV_GOT_HI20, 0); | |
| 482 | − o(0x17 | (10 << 7)); // auipc a0, 0 %pcrel_hi(sym)+addend | |
| 483 | − greloca(cur_text_section, &label, ind, R_RISCV_PCREL_LO12_I, 0); | |
| 484 | − EI(0x03, 3, 10, 10, 0); // ld a0, 0(a0) | |
| 485 | − gen_bounds_call(TOK___bound_local_new); | |
| 486 | − ind = saved_ind; | |
| 472 | + saved_ind = S->tccgen_ind; | |
| 473 | + S->tccgen_ind = S->func_bound_ind; | |
| 474 | + put_extern_sym(S, &label, cur_text_section, S->tccgen_ind, 0); | |
| 475 | + greloca(S, cur_text_section, sym_data, S->tccgen_ind, R_RISCV_GOT_HI20, 0); | |
| 476 | + o(S, 0x17 | (10 << 7)); // auipc a0, 0 %pcrel_hi(sym)+addend | |
| 477 | + greloca(S, cur_text_section, &label, S->tccgen_ind, R_RISCV_PCREL_LO12_I, 0); | |
| 478 | + EI(S, 0x03, 3, 10, 10, 0); // ld a0, 0(a0) | |
| 479 | + gen_bounds_call(S, TOK___bound_local_new); | |
| 480 | + S->tccgen_ind = saved_ind; | |
| 487 | 481 | label.c = 0; /* force new local ELF symbol */ |
| 488 | 482 | } |
| 489 | 483 | |
| 490 | 484 | /* generate bound check local freeing */ |
| 491 | − o(0xe02a1101); /* addi sp,sp,-32 sd a0,0(sp) */ | |
| 492 | − o(0xa82ae42e); /* sd a1,8(sp) fsd fa0,16(sp) */ | |
| 493 | − put_extern_sym(&label, cur_text_section, ind, 0); | |
| 494 | − greloca(cur_text_section, sym_data, ind, R_RISCV_GOT_HI20, 0); | |
| 495 | − o(0x17 | (10 << 7)); // auipc a0, 0 %pcrel_hi(sym)+addend | |
| 496 | − greloca(cur_text_section, &label, ind, R_RISCV_PCREL_LO12_I, 0); | |
| 497 | − EI(0x03, 3, 10, 10, 0); // ld a0, 0(a0) | |
| 498 | − gen_bounds_call(TOK___bound_local_delete); | |
| 499 | − o(0x65a26502); /* ld a0,0(sp) ld a1,8(sp) */ | |
| 500 | − o(0x61052542); /* fld fa0,16(sp) addi sp,sp,32 */ | |
| 485 | + o(S, 0xe02a1101); /* addi sp,sp,-32 sd a0,0(sp) */ | |
| 486 | + o(S, 0xa82ae42e); /* sd a1,8(sp) fsd fa0,16(sp) */ | |
| 487 | + put_extern_sym(S, &label, cur_text_section, S->tccgen_ind, 0); | |
| 488 | + greloca(S, cur_text_section, sym_data, S->tccgen_ind, R_RISCV_GOT_HI20, 0); | |
| 489 | + o(S, 0x17 | (10 << 7)); // auipc a0, 0 %pcrel_hi(sym)+addend | |
| 490 | + greloca(S, cur_text_section, &label, S->tccgen_ind, R_RISCV_PCREL_LO12_I, 0); | |
| 491 | + EI(S, 0x03, 3, 10, 10, 0); // ld a0, 0(a0) | |
| 492 | + gen_bounds_call(S, TOK___bound_local_delete); | |
| 493 | + o(S, 0x65a26502); /* ld a0,0(sp) ld a1,8(sp) */ | |
| 494 | + o(S, 0x61052542); /* fld fa0,16(sp) addi sp,sp,32 */ | |
| 501 | 495 | } |
| 502 | 496 | #endif |
| 503 | 497 | |
| @@ -546,27 +540,27 @@ static void reg_pass(CType *type, int *prc, int *fieldofs, int named) · 42 unmodified lines | ||
| 546 | 540 | } |
| 547 | 541 | } |
| 548 | 542 | |
| 549 | −ST_FUNC void gfunc_call(int nb_args) | |
| 543 | +ST_FUNC void gfunc_call(TCCState* S, int nb_args) | |
| 550 | 544 | { |
| 551 | 545 | int i, align, size, areg[2]; |
| 552 | − int *info = tcc_malloc((nb_args + 1) * sizeof (int)); | |
| 546 | + int *info = tcc_malloc(S, (nb_args + 1) * sizeof (int)); | |
| 553 | 547 | int stack_adj = 0, tempspace = 0, stack_add, ofs, splitofs = 0; |
| 554 | 548 | SValue *sv; |
| 555 | 549 | Sym *sa; |
| 556 | 550 | |
| 557 | 551 | #ifdef CONFIG_TCC_BCHECK |
| 558 | − int bc_save = tcc_state->do_bounds_check; | |
| 559 | − if (tcc_state->do_bounds_check) | |
| 560 | − gbound_args(nb_args); | |
| 552 | + int bc_save = S->do_bounds_check; | |
| 553 | + if (S->do_bounds_check) | |
| 554 | + gbound_args(S, nb_args); | |
| 561 | 555 | #endif |
| 562 | 556 | |
| 563 | 557 | areg[0] = 0; /* int arg regs */ |
| 564 | 558 | areg[1] = 8; /* float arg regs */ |
| 565 | − sa = vtop[-nb_args].type.ref->next; | |
| 559 | + sa = S->tccgen_vtop[-nb_args].type.ref->next; | |
| 566 | 560 | for (i = 0; i < nb_args; i++) { |
| 567 | 561 | int nregs, byref = 0, tempofs; |
| 568 | 562 | int prc[3], fieldofs[3]; |
| 569 | − sv = &vtop[1 + i - nb_args]; | |
| 563 | + sv = &S->tccgen_vtop[1 + i - nb_args]; | |
| 570 | 564 | sv->type.t &= ~VT_ARRAY; // XXX this should be done in tccgen.c |
| 571 | 565 | size = type_size(&sv->type, &align); |
| 572 | 566 | if (size > 16) { |
| @@ -623,53 +617,53 @@ ST_FUNC void gfunc_call(int nb_args) · 50 unmodified lines | ||
| 623 | 617 | stack_add = stack_adj + tempspace; |
| 624 | 618 | |
| 625 | 619 | /* fetch cpu flag before generating any code */ |
| 626 | − if ((vtop->r & VT_VALMASK) == VT_CMP) | |
| 627 | − gv(RC_INT); | |
| 620 | + if ((S->tccgen_vtop->r & VT_VALMASK) == VT_CMP) | |
| 621 | + gv(S, RC_INT); | |
| 628 | 622 | |
| 629 | 623 | if (stack_add) { |
| 630 | 624 | if (stack_add >= 0x1000) { |
| 631 | − o(0x37 | (5 << 7) | (-stack_add & 0xfffff000)); //lui t0, upper(v) | |
| 632 | − EI(0x13, 0, 5, 5, -stack_add << 20 >> 20); // addi t0, t0, lo(v) | |
| 633 | − ER(0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 | |
| 625 | + o(S, 0x37 | (5 << 7) | (-stack_add & 0xfffff000)); //lui t0, upper(v) | |
| 626 | + EI(S, 0x13, 0, 5, 5, -stack_add << 20 >> 20); // addi t0, t0, lo(v) | |
| 627 | + ER(S, 0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 | |
| 634 | 628 | } |
| 635 | 629 | else |
| 636 | − EI(0x13, 0, 2, 2, -stack_add); // addi sp, sp, -adj | |
| 630 | + EI(S, 0x13, 0, 2, 2, -stack_add); // addi sp, sp, -adj | |
| 637 | 631 | for (i = ofs = 0; i < nb_args; i++) { |
| 638 | 632 | if (info[i] & (64 | 32)) { |
| 639 | − vrotb(nb_args - i); | |
| 640 | − size = type_size(&vtop->type, &align); | |
| 633 | + vrotb(S, nb_args - i); | |
| 634 | + size = type_size(&S->tccgen_vtop->type, &align); | |
| 641 | 635 | if (info[i] & 64) { |
| 642 | − vset(&char_pointer_type, TREG_SP, 0); | |
| 643 | − vpushi(stack_adj + (info[i] >> 7)); | |
| 644 | − gen_op('+'); | |
| 645 | − vpushv(vtop); // this replaces the old argument | |
| 646 | − vrott(3); | |
| 647 | − indir(); | |
| 648 | − vtop->type = vtop[-1].type; | |
| 649 | − vswap(); | |
| 650 | − vstore(); | |
| 651 | − vpop(); | |
| 636 | + vset(S, &S->tccgen_char_pointer_type, TREG_SP, 0); | |
| 637 | + vpushi(S, stack_adj + (info[i] >> 7)); | |
| 638 | + gen_op(S, '+'); | |
| 639 | + vpushv(S, S->tccgen_vtop); // this replaces the old argument | |
| 640 | + vrott(S, 3); | |
| 641 | + indir(S); | |
| 642 | + S->tccgen_vtop->type = S->tccgen_vtop[-1].type; | |
| 643 | + vswap(S); | |
| 644 | + vstore(S); | |
| 645 | + vpop(S); | |
| 652 | 646 | size = align = 8; |
| 653 | 647 | } |
| 654 | 648 | if (info[i] & 32) { |
| 655 | 649 | if (align < XLEN) |
| 656 | 650 | align = XLEN; |
| 657 | 651 | /* Once we support offseted regs we can do this: |
| 658 | − vset(&vtop->type, TREG_SP | VT_LVAL, ofs); | |
| 652 | + vset(S, &S->tccgen_vtop->type, TREG_SP | VT_LVAL, ofs); | |
| 659 | 653 | to construct the lvalue for the outgoing stack slot, |
| 660 | 654 | until then we have to jump through hoops. */ |
| 661 | − vset(&char_pointer_type, TREG_SP, 0); | |
| 655 | + vset(S, &S->tccgen_char_pointer_type, TREG_SP, 0); | |
| 662 | 656 | ofs = (ofs + align - 1) & -align; |
| 663 | − vpushi(ofs); | |
| 664 | − gen_op('+'); | |
| 665 | − indir(); | |
| 666 | − vtop->type = vtop[-1].type; | |
| 667 | − vswap(); | |
| 668 | − vstore(); | |
| 669 | − vtop->r = vtop->r2 = VT_CONST; // this arg is done | |
| 657 | + vpushi(S, ofs); | |
| 658 | + gen_op(S, '+'); | |
| 659 | + indir(S); | |
| 660 | + S->tccgen_vtop->type = S->tccgen_vtop[-1].type; | |
| 661 | + vswap(S); | |
| 662 | + vstore(S); | |
| 663 | + S->tccgen_vtop->r = S->tccgen_vtop->r2 = VT_CONST; // this arg is done | |
| 670 | 664 | ofs += size; |
| 671 | 665 | } |
| 672 | − vrott(nb_args - i); | |
| 666 | + vrott(S, nb_args - i); | |
| 673 | 667 | } else if (info[i] & 16) { |
| 674 | 668 | assert(!splitofs); |
| 675 | 669 | splitofs = ofs; |
| @@ -685,12 +679,12 @@ ST_FUNC void gfunc_call(int nb_args) · 9 unmodified lines | ||
| 685 | 679 | r &= 15; |
| 686 | 680 | r2 = r2 & 64 ? 0 : (r2 >> 7) & 31; |
| 687 | 681 | assert(r2 <= 16); |
| 688 | − vrotb(i+1); | |
| 689 | − origtype = vtop->type; | |
| 690 | − size = type_size(&vtop->type, &align); | |
| 682 | + vrotb(S, i+1); | |
| 683 | + origtype = S->tccgen_vtop->type; | |
| 684 | + size = type_size(&S->tccgen_vtop->type, &align); | |
| 691 | 685 | if (size == 0) |
| 692 | 686 | goto done; |
| 693 | − loadt = vtop->type.t & VT_BTYPE; | |
| 687 | + loadt = S->tccgen_vtop->type.t & VT_BTYPE; | |
| 694 | 688 | if (loadt == VT_STRUCT) { |
| 695 | 689 | loadt = (ii >> 12) & VT_BTYPE; |
| 696 | 690 | } |
| @@ -702,74 +696,74 @@ ST_FUNC void gfunc_call(int nb_args) · 5 unmodified lines | ||
| 702 | 696 | assert(r2); |
| 703 | 697 | r2--; |
| 704 | 698 | } else if (r2) { |
| 705 | − test_lvalue(); | |
| 706 | − vpushv(vtop); | |
| 699 | + test_lvalue(S); | |
| 700 | + vpushv(S, S->tccgen_vtop); | |
| 707 | 701 | } |
| 708 | − vtop->type.t = loadt | (vtop->type.t & VT_UNSIGNED); | |
| 709 | − gv(r < 8 ? RC_R(r) : RC_F(r - 8)); | |
| 710 | − vtop->type = origtype; | |
| 702 | + S->tccgen_vtop->type.t = loadt | (S->tccgen_vtop->type.t & VT_UNSIGNED); | |
| 703 | + gv(S, r < 8 ? RC_R(r) : RC_F(r - 8)); | |
| 704 | + S->tccgen_vtop->type = origtype; | |
| 711 | 705 | |
| 712 | 706 | if (r2 && loadt != VT_LDOUBLE) { |
| 713 | 707 | r2--; |
| 714 | 708 | assert(r2 < 16 || r2 == TREG_RA); |
| 715 | − vswap(); | |
| 716 | − gaddrof(); | |
| 717 | − vtop->type = char_pointer_type; | |
| 718 | − vpushi(ii >> 20); | |
| 709 | + vswap(S); | |
| 710 | + gaddrof(S); | |
| 711 | + S->tccgen_vtop->type = S->tccgen_char_pointer_type; | |
| 712 | + vpushi(S, ii >> 20); | |
| 719 | 713 | #ifdef CONFIG_TCC_BCHECK |
| 720 | 714 | if ((origtype.t & VT_BTYPE) == VT_STRUCT) |
| 721 | − tcc_state->do_bounds_check = 0; | |
| 715 | + S->do_bounds_check = 0; | |
| 722 | 716 | #endif |
| 723 | − gen_op('+'); | |
| 717 | + gen_op(S, '+'); | |
| 724 | 718 | #ifdef CONFIG_TCC_BCHECK |
| 725 | − tcc_state->do_bounds_check = bc_save; | |
| 719 | + S->do_bounds_check = bc_save; | |
| 726 | 720 | #endif |
| 727 | − indir(); | |
| 728 | − vtop->type = origtype; | |
| 729 | − loadt = vtop->type.t & VT_BTYPE; | |
| 721 | + indir(S); | |
| 722 | + S->tccgen_vtop->type = origtype; | |
| 723 | + loadt = S->tccgen_vtop->type.t & VT_BTYPE; | |
| 730 | 724 | if (loadt == VT_STRUCT) { |
| 731 | 725 | loadt = (ii >> 16) & VT_BTYPE; |
| 732 | 726 | } |
| 733 | − save_reg_upstack(r2, 1); | |
| 734 | − vtop->type.t = loadt | (vtop->type.t & VT_UNSIGNED); | |
| 735 | − load(r2, vtop); | |
| 727 | + save_reg_upstack(S, r2, 1); | |
| 728 | + S->tccgen_vtop->type.t = loadt | (S->tccgen_vtop->type.t & VT_UNSIGNED); | |
| 729 | + load(S, r2, S->tccgen_vtop); | |
| 736 | 730 | assert(r2 < VT_CONST); |
| 737 | − vtop--; | |
| 738 | − vtop->r2 = r2; | |
| 731 | + S->tccgen_vtop--; | |
| 732 | + S->tccgen_vtop->r2 = r2; | |
| 739 | 733 | } |
| 740 | 734 | if (info[nb_args - 1 - i] & 16) { |
| 741 | − ES(0x23, 3, 2, ireg(vtop->r2), splitofs); // sd t0, ofs(sp) | |
| 742 | − vtop->r2 = VT_CONST; | |
| 743 | − } else if (loadt == VT_LDOUBLE && vtop->r2 != r2) { | |
| 744 | − assert(vtop->r2 <= 7 && r2 <= 7); | |
| 735 | + ES(S, 0x23, 3, 2, ireg(S->tccgen_vtop->r2), splitofs); // sd t0, ofs(sp) | |
| 736 | + S->tccgen_vtop->r2 = VT_CONST; | |
| 737 | + } else if (loadt == VT_LDOUBLE && S->tccgen_vtop->r2 != r2) { | |
| 738 | + assert(S->tccgen_vtop->r2 <= 7 && r2 <= 7); | |
| 745 | 739 | /* XXX we'd like to have 'gv' move directly into |
| 746 | 740 | the right class instead of us fixing it up. */ |
| 747 | − EI(0x13, 0, ireg(r2), ireg(vtop->r2), 0); // mv Ra+1, RR2 | |
| 748 | − vtop->r2 = r2; | |
| 741 | + EI(S, 0x13, 0, ireg(r2), ireg(S->tccgen_vtop->r2), 0); // mv Ra+1, RR2 | |
| 742 | + S->tccgen_vtop->r2 = r2; | |
| 749 | 743 | } |
| 750 | 744 | done: |
| 751 | − vrott(i+1); | |
| 745 | + vrott(S, i+1); | |
| 752 | 746 | } |
| 753 | 747 | } |
| 754 | − vrotb(nb_args + 1); | |
| 755 | − save_regs(nb_args + 1); | |
| 756 | − gcall_or_jmp(1); | |
| 757 | − vtop -= nb_args + 1; | |
| 748 | + vrotb(S, nb_args + 1); | |
| 749 | + save_regs(S, nb_args + 1); | |
| 750 | + gcall_or_jmp(S, 1); | |
| 751 | + S->tccgen_vtop -= nb_args + 1; | |
| 758 | 752 | if (stack_add) { |
| 759 | 753 | if (stack_add >= 0x1000) { |
| 760 | − o(0x37 | (5 << 7) | (stack_add & 0xfffff000)); //lui t0, upper(v) | |
| 761 | − EI(0x13, 0, 5, 5, stack_add << 20 >> 20); // addi t0, t0, lo(v) | |
| 762 | − ER(0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 | |
| 754 | + o(S, 0x37 | (5 << 7) | (stack_add & 0xfffff000)); //lui t0, upper(v) | |
| 755 | + EI(S, 0x13, 0, 5, 5, stack_add << 20 >> 20); // addi t0, t0, lo(v) | |
| 756 | + ER(S, 0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 | |
| 763 | 757 | } |
| 764 | 758 | else |
| 765 | − EI(0x13, 0, 2, 2, stack_add); // addi sp, sp, adj | |
| 759 | + EI(S, 0x13, 0, 2, 2, stack_add); // addi sp, sp, adj | |
| 766 | 760 | } |
| 767 | − tcc_free(info); | |
| 761 | + tcc_free(S, info); | |
| 768 | 762 | } |
| 769 | 763 | |
| 770 | 764 | static int func_sub_sp_offset, num_va_regs, func_va_list_ofs; |
| 771 | 765 | |
| 772 | −ST_FUNC void gfunc_prolog(Sym *func_sym) | |
| 766 | +ST_FUNC void gfunc_prolog(TCCState* S, Sym *func_sym) | |
| 773 | 767 | { |
| 774 | 768 | CType *func_type = &func_sym->type; |
| 775 | 769 | int i, addr, align, size; |
| @@ -779,19 +773,19 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 3 unmodified lines | ||
| 779 | 773 | CType *type; |
| 780 | 774 | |
| 781 | 775 | sym = func_type->ref; |
| 782 | − loc = -16; // for ra and s0 | |
| 783 | − func_sub_sp_offset = ind; | |
| 784 | − ind += 5 * 4; | |
| 776 | + S->tccgen_loc = -16; // for ra and s0 | |
| 777 | + func_sub_sp_offset = S->tccgen_ind; | |
| 778 | + S->tccgen_ind += 5 * 4; | |
| 785 | 779 | |
| 786 | 780 | areg[0] = 0, areg[1] = 0; |
| 787 | 781 | addr = 0; |
| 788 | 782 | /* if the function returns by reference, then add an |
| 789 | 783 | implicit pointer parameter */ |
| 790 | − size = type_size(&func_vt, &align); | |
| 784 | + size = type_size(&S->tccgen_func_vt, &align); | |
| 791 | 785 | if (size > 2 * XLEN) { |
| 792 | − loc -= 8; | |
| 793 | − func_vc = loc; | |
| 794 | − ES(0x23, 3, 8, 10 + areg[0]++, loc); // sd a0, loc(s0) | |
| 786 | + S->tccgen_loc -= 8; | |
| 787 | + S->tccgen_func_vc = S->tccgen_loc; | |
| 788 | + ES(S, 0x23, 3, 8, 10 + areg[0]++, S->tccgen_loc); // sd a0, loc(s0) | |
| 795 | 789 | } |
| 796 | 790 | /* define parameters */ |
| 797 | 791 | while ((sym = sym->next) != NULL) { |
| @@ -801,7 +795,7 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 3 unmodified lines | ||
| 801 | 795 | type = &sym->type; |
| 802 | 796 | size = type_size(type, &align); |
| 803 | 797 | if (size > 2 * XLEN) { |
| 804 | − type = &char_pointer_type; | |
| 798 | + type = &S->tccgen_char_pointer_type; | |
| 805 | 799 | size = align = byref = 8; |
| 806 | 800 | } |
| 807 | 801 | reg_pass(type, prc, fieldofs, 1); |
| @@ -816,36 +810,36 @@ ST_FUNC void gfunc_prolog(Sym *func_sym) · 8 unmodified lines | ||
| 816 | 810 | param_addr = addr; |
| 817 | 811 | addr += size; |
| 818 | 812 | } else { |
| 819 | − loc -= regcount * 8; // XXX could reserve only 'size' bytes | |
| 820 | − param_addr = loc; | |
| 813 | + S->tccgen_loc -= regcount * 8; // XXX could reserve only 'size' bytes | |
| 814 | + param_addr = S->tccgen_loc; | |
| 821 | 815 | for (i = 0; i < regcount; i++) { |
| 822 | 816 | if (areg[prc[1+i] - 1] >= 8) { |
| 823 | 817 | assert(i == 1 && regcount == 2 && !(addr & 7)); |
| 824 | − EI(0x03, 3, 5, 8, addr); // ld t0, addr(s0) | |
| 818 | + EI(S, 0x03, 3, 5, 8, addr); // ld t0, addr(s0) | |
| 825 | 819 | addr += 8; |
| 826 | − ES(0x23, 3, 8, 5, loc + i*8); // sd t0, loc(s0) | |
| 820 | + ES(S, 0x23, 3, 8, 5, S->tccgen_loc + i*8); // sd t0, loc(s0) | |
| 827 | 821 | } else if (prc[1+i] == RC_FLOAT) { |
| 828 | − ES(0x27, (size / regcount) == 4 ? 2 : 3, 8, 10 + areg[1]++, loc + (fieldofs[i+1] >> 4)); // fs[wd] FAi, loc(s0) | |
| 822 | + ES(S, 0x27, (size / regcount) == 4 ? 2 : 3, 8, 10 + areg[1]++, S->tccgen_loc + (fieldofs[i+1] >> 4)); // fs[wd] FAi, loc(s0) | |
| 829 | 823 | } else { |
| 830 | − ES(0x23, 3, 8, 10 + areg[0]++, loc + i*8); // sd aX, loc(s0) // XXX | |
| 824 | + ES(S, 0x23, 3, 8, 10 + areg[0]++, S->tccgen_loc + i*8); // sd aX, loc(s0) // XXX | |
| 831 | 825 | } |
| 832 | 826 | } |
| 833 | 827 | } |
| 834 | − sym_push(sym->v & ~SYM_FIELD, &sym->type, | |
| 828 | + sym_push(S, sym->v & ~SYM_FIELD, &sym->type, | |
| 835 | 829 | (byref ? VT_LLOCAL : VT_LOCAL) | VT_LVAL, |
| 836 | 830 | param_addr); |
| 837 | 831 | } |
| 838 | 832 | func_va_list_ofs = addr; |
| 839 | 833 | num_va_regs = 0; |
| 840 | − if (func_var) { | |
| 834 | + if (S->tccgen_func_var) { | |
| 841 | 835 | for (; areg[0] < 8; areg[0]++) { |
| 842 | 836 | num_va_regs++; |
| 843 | − ES(0x23, 3, 8, 10 + areg[0], -8 + num_va_regs * 8); // sd aX, loc(s0) | |
| 837 | + ES(S, 0x23, 3, 8, 10 + areg[0], -8 + num_va_regs * 8); // sd aX, loc(s0) | |
| 844 | 838 | } |
| 845 | 839 | } |
| 846 | 840 | #ifdef CONFIG_TCC_BCHECK |
| 847 | − if (tcc_state->do_bounds_check) | |
| 848 | − gen_bounds_prolog(); | |
| 841 | + if (S->do_bounds_check) | |
| 842 | + gen_bounds_prolog(S); | |
| 849 | 843 | #endif |
| 850 | 844 | } |
| 851 | 845 | |
| @@ -870,113 +864,113 @@ ST_FUNC int gfunc_sret(CType *vt, int variadic, CType *ret, · 18 unmodified lines | ||
| 870 | 864 | return nregs; |
| 871 | 865 | } |
| 872 | 866 | |
| 873 | −ST_FUNC void arch_transfer_ret_regs(int aftercall) | |
| 867 | +ST_FUNC void arch_transfer_ret_regs(TCCState* S, int aftercall) | |
| 874 | 868 | { |
| 875 | 869 | int prc[3], fieldofs[3]; |
| 876 | − reg_pass(&vtop->type, prc, fieldofs, 1); | |
| 870 | + reg_pass(&S->tccgen_vtop->type, prc, fieldofs, 1); | |
| 877 | 871 | assert(prc[0] == 2 && prc[1] != prc[2] && !(fieldofs[1] >> 4)); |
| 878 | − assert(vtop->r == (VT_LOCAL | VT_LVAL)); | |
| 879 | − vpushv(vtop); | |
| 880 | − vtop->type.t = fieldofs[1] & VT_BTYPE; | |
| 881 | − (aftercall ? store : load)(prc[1] == RC_INT ? REG_IRET : REG_FRET, vtop); | |
| 882 | − vtop->c.i += fieldofs[2] >> 4; | |
| 883 | − vtop->type.t = fieldofs[2] & VT_BTYPE; | |
| 884 | − (aftercall ? store : load)(prc[2] == RC_INT ? REG_IRET : REG_FRET, vtop); | |
| 885 | − vtop--; | |
| 872 | + assert(S->tccgen_vtop->r == (VT_LOCAL | VT_LVAL)); | |
| 873 | + vpushv(S, S->tccgen_vtop); | |
| 874 | + S->tccgen_vtop->type.t = fieldofs[1] & VT_BTYPE; | |
| 875 | + (aftercall ? store : load)(S, prc[1] == RC_INT ? REG_IRET : REG_FRET, S->tccgen_vtop); | |
| 876 | + S->tccgen_vtop->c.i += fieldofs[2] >> 4; | |
| 877 | + S->tccgen_vtop->type.t = fieldofs[2] & VT_BTYPE; | |
| 878 | + (aftercall ? store : load)(S, prc[2] == RC_INT ? REG_IRET : REG_FRET, S->tccgen_vtop); | |
| 879 | + S->tccgen_vtop--; | |
| 886 | 880 | } |
| 887 | 881 | |
| 888 | −ST_FUNC void gfunc_epilog(void) | |
| 882 | +ST_FUNC void gfunc_epilog(TCCState* S) | |
| 889 | 883 | { |
| 890 | 884 | int v, saved_ind, d, large_ofs_ind; |
| 891 | 885 | |
| 892 | 886 | #ifdef CONFIG_TCC_BCHECK |
| 893 | − if (tcc_state->do_bounds_check) | |
| 894 | − gen_bounds_epilog(); | |
| 887 | + if (S->do_bounds_check) | |
| 888 | + gen_bounds_epilog(S); | |
| 895 | 889 | #endif |
| 896 | 890 | |
| 897 | − loc = (loc - num_va_regs * 8); | |
| 898 | − d = v = (-loc + 15) & -16; | |
| 891 | + S->tccgen_loc = (S->tccgen_loc - num_va_regs * 8); | |
| 892 | + d = v = (-S->tccgen_loc + 15) & -16; | |
| 899 | 893 | |
| 900 | 894 | if (v >= (1 << 11)) { |
| 901 | 895 | d = 16; |
| 902 | − o(0x37 | (5 << 7) | ((0x800 + (v-16)) & 0xfffff000)); //lui t0, upper(v) | |
| 903 | − EI(0x13, 0, 5, 5, (v-16) << 20 >> 20); // addi t0, t0, lo(v) | |
| 904 | − ER(0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 | |
| 896 | + o(S, 0x37 | (5 << 7) | ((0x800 + (v-16)) & 0xfffff000)); //lui t0, upper(v) | |
| 897 | + EI(S, 0x13, 0, 5, 5, (v-16) << 20 >> 20); // addi t0, t0, lo(v) | |
| 898 | + ER(S, 0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 | |
| 905 | 899 | } |
| 906 | − EI(0x03, 3, 1, 2, d - 8 - num_va_regs * 8); // ld ra, v-8(sp) | |
| 907 | − EI(0x03, 3, 8, 2, d - 16 - num_va_regs * 8); // ld s0, v-16(sp) | |
| 908 | − EI(0x13, 0, 2, 2, d); // addi sp, sp, v | |
| 909 | − EI(0x67, 0, 0, 1, 0); // jalr x0, 0(x1), aka ret | |
| 910 | − large_ofs_ind = ind; | |
| 900 | + EI(S, 0x03, 3, 1, 2, d - 8 - num_va_regs * 8); // ld ra, v-8(sp) | |
| 901 | + EI(S, 0x03, 3, 8, 2, d - 16 - num_va_regs * 8); // ld s0, v-16(sp) | |
| 902 | + EI(S, 0x13, 0, 2, 2, d); // addi sp, sp, v | |
| 903 | + EI(S, 0x67, 0, 0, 1, 0); // jalr x0, 0(x1), aka ret | |
| 904 | + large_ofs_ind = S->tccgen_ind; | |
| 911 | 905 | if (v >= (1 << 11)) { |
| 912 | − EI(0x13, 0, 8, 2, d - num_va_regs * 8); // addi s0, sp, d | |
| 913 | − o(0x37 | (5 << 7) | ((0x800 + (v-16)) & 0xfffff000)); //lui t0, upper(v) | |
| 914 | − EI(0x13, 0, 5, 5, (v-16) << 20 >> 20); // addi t0, t0, lo(v) | |
| 915 | − ER(0x33, 0, 2, 2, 5, 0x20); // sub sp, sp, t0 | |
| 916 | − gjmp_addr(func_sub_sp_offset + 5*4); | |
| 906 | + EI(S, 0x13, 0, 8, 2, d - num_va_regs * 8); // addi s0, sp, d | |
| 907 | + o(S, 0x37 | (5 << 7) | ((0x800 + (v-16)) & 0xfffff000)); //lui t0, upper(v) | |
| 908 | + EI(S, 0x13, 0, 5, 5, (v-16) << 20 >> 20); // addi t0, t0, lo(v) | |
| 909 | + ER(S, 0x33, 0, 2, 2, 5, 0x20); // sub sp, sp, t0 | |
| 910 | + gjmp_addr(S, func_sub_sp_offset + 5*4); | |
| 917 | 911 | } |
| 918 | − saved_ind = ind; | |
| 912 | + saved_ind = S->tccgen_ind; | |
| 919 | 913 | |
| 920 | − ind = func_sub_sp_offset; | |
| 921 | − EI(0x13, 0, 2, 2, -d); // addi sp, sp, -d | |
| 922 | − ES(0x23, 3, 2, 1, d - 8 - num_va_regs * 8); // sd ra, d-8(sp) | |
| 923 | − ES(0x23, 3, 2, 8, d - 16 - num_va_regs * 8); // sd s0, d-16(sp) | |
| 914 | + S->tccgen_ind = func_sub_sp_offset; | |
| 915 | + EI(S, 0x13, 0, 2, 2, -d); // addi sp, sp, -d | |
| 916 | + ES(S, 0x23, 3, 2, 1, d - 8 - num_va_regs * 8); // sd ra, d-8(sp) | |
| 917 | + ES(S, 0x23, 3, 2, 8, d - 16 - num_va_regs * 8); // sd s0, d-16(sp) | |
| 924 | 918 | if (v < (1 << 11)) |
| 925 | − EI(0x13, 0, 8, 2, d - num_va_regs * 8); // addi s0, sp, d | |
| 919 | + EI(S, 0x13, 0, 8, 2, d - num_va_regs * 8); // addi s0, sp, d | |
| 926 | 920 | else |
| 927 | − gjmp_addr(large_ofs_ind); | |
| 928 | − if ((ind - func_sub_sp_offset) != 5*4) | |
| 929 | − EI(0x13, 0, 0, 0, 0); // addi x0, x0, 0 == nop | |
| 930 | − ind = saved_ind; | |
| 921 | + gjmp_addr(S, large_ofs_ind); | |
| 922 | + if ((S->tccgen_ind - func_sub_sp_offset) != 5*4) | |
| 923 | + EI(S, 0x13, 0, 0, 0, 0); // addi x0, x0, 0 == nop | |
| 924 | + S->tccgen_ind = saved_ind; | |
| 931 | 925 | } |
| 932 | 926 | |
| 933 | −ST_FUNC void gen_va_start(void) | |
| 927 | +ST_FUNC void gen_va_start(TCCState *S) | |
| 934 | 928 | { |
| 935 | − vtop--; | |
| 936 | − vset(&char_pointer_type, VT_LOCAL, func_va_list_ofs); | |
| 929 | + S->tccgen_vtop--; | |
| 930 | + vset(S, &S->tccgen_char_pointer_type, VT_LOCAL, func_va_list_ofs); | |
| 937 | 931 | } |
| 938 | 932 | |
| 939 | −ST_FUNC void gen_fill_nops(int bytes) | |
| 933 | +ST_FUNC void gen_fill_nops(TCCState* S, int bytes) | |
| 940 | 934 | { |
| 941 | 935 | if ((bytes & 3)) |
| 942 | − tcc_error("alignment of code section not multiple of 4"); | |
| 936 | + tcc_error(S, "alignment of code section not multiple of 4"); | |
| 943 | 937 | while (bytes > 0) { |
| 944 | − EI(0x13, 0, 0, 0, 0); // addi x0, x0, 0 == nop | |
| 938 | + EI(S, 0x13, 0, 0, 0, 0); // addi x0, x0, 0 == nop | |
| 945 | 939 | bytes -= 4; |
| 946 | 940 | } |
| 947 | 941 | } |
| 948 | 942 | |
| 949 | 943 | // Generate forward branch to label: |
| 950 | −ST_FUNC int gjmp(int t) | |
| 944 | +ST_FUNC int gjmp(TCCState* S, int t) | |
| 951 | 945 | { |
| 952 | − if (nocode_wanted) | |
| 946 | + if (S->tccgen_nocode_wanted) | |
| 953 | 947 | return t; |
| 954 | − o(t); | |
| 955 | − return ind - 4; | |
| 948 | + o(S, t); | |
| 949 | + return S->tccgen_ind - 4; | |
| 956 | 950 | } |
| 957 | 951 | |
| 958 | 952 | // Generate branch to known address: |
| 959 | −ST_FUNC void gjmp_addr(int a) | |
| 953 | +ST_FUNC void gjmp_addr(TCCState* S, int a) | |
| 960 | 954 | { |
| 961 | − uint32_t r = a - ind, imm; | |
| 955 | + uint32_t r = a - S->tccgen_ind, imm; | |
| 962 | 956 | if ((r + (1 << 21)) & ~((1U << 22) - 2)) { |
| 963 | − o(0x17 | (5 << 7) | (((r + 0x800) & 0xfffff000))); // lui RR, up(r) | |
| 957 | + o(S, 0x17 | (5 << 7) | (((r + 0x800) & 0xfffff000))); // lui RR, up(r) | |
| 964 | 958 | r = (int)r << 20 >> 20; |
| 965 | − EI(0x67, 0, 0, 5, r); // jalr x0, r(t0) | |
| 959 | + EI(S, 0x67, 0, 0, 5, r); // jalr x0, r(t0) | |
| 966 | 960 | } else { |
| 967 | 961 | imm = (((r >> 12) & 0xff) << 12) |
| 968 | 962 | | (((r >> 11) & 1) << 20) |
| 969 | 963 | | (((r >> 1) & 0x3ff) << 21) |
| 970 | 964 | | (((r >> 20) & 1) << 31); |
| 971 | − o(0x6f | imm); // jal x0, imm == j imm | |
| 965 | + o(S, 0x6f | imm); // jal x0, imm == j imm | |
| 972 | 966 | } |
| 973 | 967 | } |
| 974 | 968 | |
| 975 | −ST_FUNC int gjmp_cond(int op, int t) | |
| 969 | +ST_FUNC int gjmp_cond(TCCState* S, int op, int t) | |
| 976 | 970 | { |
| 977 | 971 | int tmp; |
| 978 | − int a = vtop->cmp_r & 0xff; | |
| 979 | − int b = (vtop->cmp_r >> 8) & 0xff; | |
| 972 | + int a = S->tccgen_vtop->cmp_r & 0xff; | |
| 973 | + int b = (S->tccgen_vtop->cmp_r >> 8) & 0xff; | |
| 980 | 974 | switch (op) { |
| 981 | 975 | case TOK_ULT: op = 6; break; |
| 982 | 976 | case TOK_UGE: op = 7; break; |
| @@ -989,11 +983,11 @@ ST_FUNC int gjmp_cond(int op, int t) · 6 unmodified lines | ||
| 989 | 983 | case TOK_NE: op = 1; break; |
| 990 | 984 | case TOK_EQ: op = 0; break; |
| 991 | 985 | } |
| 992 | − o(0x63 | (op ^ 1) << 12 | a << 15 | b << 20 | 8 << 7); // bOP a,b,+4 | |
| 993 | − return gjmp(t); | |
| 986 | + o(S, 0x63 | (op ^ 1) << 12 | a << 15 | b << 20 | 8 << 7); // bOP a,b,+4 | |
| 987 | + return gjmp(S, t); | |
| 994 | 988 | } |
| 995 | 989 | |
| 996 | −ST_FUNC int gjmp_append(int n, int t) | |
| 990 | +ST_FUNC int gjmp_append(TCCState* S, int n, int t) | |
| 997 | 991 | { |
| 998 | 992 | void *p; |
| 999 | 993 | /* insert jump list n into t */ |
| @@ -1007,23 +1001,23 @@ ST_FUNC int gjmp_append(int n, int t) · 7 unmodified lines | ||
| 1007 | 1001 | return t; |
| 1008 | 1002 | } |
| 1009 | 1003 | |
| 1010 | −static void gen_opil(int op, int ll) | |
| 1004 | +static void gen_opil(TCCState* S, int op, int ll) | |
| 1011 | 1005 | { |
| 1012 | 1006 | int a, b, d; |
| 1013 | 1007 | int func3 = 0; |
| 1014 | 1008 | ll = ll ? 0 : 8; |
| 1015 | − if ((vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1016 | − int fc = vtop->c.i; | |
| 1017 | − if (fc == vtop->c.i && !(((unsigned)fc + (1 << 11)) >> 12)) { | |
| 1009 | + if ((S->tccgen_vtop->r & (VT_VALMASK | VT_LVAL | VT_SYM)) == VT_CONST) { | |
| 1010 | + int fc = S->tccgen_vtop->c.i; | |
| 1011 | + if (fc == S->tccgen_vtop->c.i && !(((unsigned)fc + (1 << 11)) >> 12)) { | |
| 1018 | 1012 | int cll = 0; |
| 1019 | 1013 | int m = ll ? 31 : 63; |
| 1020 | − vswap(); | |
| 1021 | − gv(RC_INT); | |
| 1022 | − a = ireg(vtop[0].r); | |
| 1023 | − --vtop; | |
| 1024 | − d = get_reg(RC_INT); | |
| 1025 | − ++vtop; | |
| 1026 | − vswap(); | |
| 1014 | + vswap(S); | |
| 1015 | + gv(S, RC_INT); | |
| 1016 | + a = ireg(S->tccgen_vtop[0].r); | |
| 1017 | + --S->tccgen_vtop; | |
| 1018 | + d = get_reg(S, RC_INT); | |
| 1019 | + ++S->tccgen_vtop; | |
| 1020 | + vswap(S); | |
| 1027 | 1021 | switch (op) { |
| 1028 | 1022 | case '-': |
| 1029 | 1023 | if (fc <= -(1 << 11)) |
| @@ -1033,13 +1027,13 @@ static void gen_opil(int op, int ll) · 3 unmodified lines | ||
| 1033 | 1027 | func3 = 0; // addi d, a, fc |
| 1034 | 1028 | cll = ll; |
| 1035 | 1029 | do_cop: |
| 1036 | − EI(0x13 | cll, func3, ireg(d), a, fc); | |
| 1037 | − --vtop; | |
| 1030 | + EI(S, 0x13 | cll, func3, ireg(d), a, fc); | |
| 1031 | + --S->tccgen_vtop; | |
| 1038 | 1032 | if (op >= TOK_ULT && op <= TOK_GT) { |
| 1039 | − vset_VT_CMP(TOK_NE); | |
| 1040 | − vtop->cmp_r = ireg(d) | 0 << 8; | |
| 1033 | + vset_VT_CMP(S, TOK_NE); | |
| 1034 | + S->tccgen_vtop->cmp_r = ireg(d) | 0 << 8; | |
| 1041 | 1035 | } else |
| 1042 | − vtop[0].r = d; | |
| 1036 | + S->tccgen_vtop[0].r = d; | |
| 1043 | 1037 | return; |
| 1044 | 1038 | case TOK_LE: |
| 1045 | 1039 | if (fc >= (1 << 11) - 1) |
| @@ -1062,97 +1056,97 @@ static void gen_opil(int op, int ll) · 16 unmodified lines | ||
| 1062 | 1056 | case TOK_UGT: /* -> TOK_ULE */ |
| 1063 | 1057 | case TOK_GE: /* -> TOK_LT */ |
| 1064 | 1058 | case TOK_GT: /* -> TOK_LE */ |
| 1065 | − gen_opil(op - 1, !ll); | |
| 1066 | − vtop->cmp_op ^= 1; | |
| 1059 | + gen_opil(S, op - 1, !ll); | |
| 1060 | + S->tccgen_vtop->cmp_op ^= 1; | |
| 1067 | 1061 | return; |
| 1068 | 1062 | |
| 1069 | 1063 | case TOK_NE: |
| 1070 | 1064 | case TOK_EQ: |
| 1071 | 1065 | if (fc) |
| 1072 | − gen_opil('-', !ll), a = ireg(vtop++->r); | |
| 1073 | − --vtop; | |
| 1074 | − vset_VT_CMP(op); | |
| 1075 | − vtop->cmp_r = a | 0 << 8; | |
| 1066 | + gen_opil(S, '-', !ll), a = ireg(S->tccgen_vtop++->r); | |
| 1067 | + --S->tccgen_vtop; | |
| 1068 | + vset_VT_CMP(S, op); | |
| 1069 | + S->tccgen_vtop->cmp_r = a | 0 << 8; | |
| 1076 | 1070 | return; |
| 1077 | 1071 | } |
| 1078 | 1072 | } |
| 1079 | 1073 | } |
| 1080 | − gv2(RC_INT, RC_INT); | |
| 1081 | − a = ireg(vtop[-1].r); | |
| 1082 | − b = ireg(vtop[0].r); | |
| 1083 | − vtop -= 2; | |
| 1084 | − d = get_reg(RC_INT); | |
| 1085 | − vtop++; | |
| 1086 | − vtop[0].r = d; | |
| 1074 | + gv2(S, RC_INT, RC_INT); | |
| 1075 | + a = ireg(S->tccgen_vtop[-1].r); | |
| 1076 | + b = ireg(S->tccgen_vtop[0].r); | |
| 1077 | + S->tccgen_vtop -= 2; | |
| 1078 | + d = get_reg(S, RC_INT); | |
| 1079 | + S->tccgen_vtop++; | |
| 1080 | + S->tccgen_vtop[0].r = d; | |
| 1087 | 1081 | d = ireg(d); |
| 1088 | 1082 | switch (op) { |
| 1089 | 1083 | default: |
| 1090 | 1084 | if (op >= TOK_ULT && op <= TOK_GT) { |
| 1091 | − vset_VT_CMP(op); | |
| 1092 | − vtop->cmp_r = a | b << 8; | |
| 1085 | + vset_VT_CMP(S, op); | |
| 1086 | + S->tccgen_vtop->cmp_r = a | b << 8; | |
| 1093 | 1087 | break; |
| 1094 | 1088 | } |
| 1095 | − tcc_error("implement me: %s(%s)", __FUNCTION__, get_tok_str(op, NULL)); | |
| 1089 | + tcc_error(S, "implement me: %s(%s)", __FUNCTION__, get_tok_str(S, op, NULL)); | |
| 1096 | 1090 | break; |
| 1097 | 1091 | |
| 1098 | 1092 | case '+': |
| 1099 | − ER(0x33 | ll, 0, d, a, b, 0); // add d, a, b | |
| 1093 | + ER(S, 0x33 | ll, 0, d, a, b, 0); // add d, a, b | |
| 1100 | 1094 | break; |
| 1101 | 1095 | case '-': |
| 1102 | − ER(0x33 | ll, 0, d, a, b, 0x20); // sub d, a, b | |
| 1096 | + ER(S, 0x33 | ll, 0, d, a, b, 0x20); // sub d, a, b | |
| 1103 | 1097 | break; |
| 1104 | 1098 | case TOK_SAR: |
| 1105 | − ER(0x33 | ll | ll, 5, d, a, b, 0x20); // sra d, a, b | |
| 1099 | + ER(S, 0x33 | ll | ll, 5, d, a, b, 0x20); // sra d, a, b | |
| 1106 | 1100 | break; |
| 1107 | 1101 | case TOK_SHR: |
| 1108 | − ER(0x33 | ll | ll, 5, d, a, b, 0); // srl d, a, b | |
| 1102 | + ER(S, 0x33 | ll | ll, 5, d, a, b, 0); // srl d, a, b | |
| 1109 | 1103 | break; |
| 1110 | 1104 | case TOK_SHL: |
| 1111 | − ER(0x33 | ll, 1, d, a, b, 0); // sll d, a, b | |
| 1105 | + ER(S, 0x33 | ll, 1, d, a, b, 0); // sll d, a, b | |
| 1112 | 1106 | break; |
| 1113 | 1107 | case '*': |
| 1114 | − ER(0x33 | ll, 0, d, a, b, 1); // mul d, a, b | |
| 1108 | + ER(S, 0x33 | ll, 0, d, a, b, 1); // mul d, a, b | |
| 1115 | 1109 | break; |
| 1116 | 1110 | case '/': |
| 1117 | − ER(0x33 | ll, 4, d, a, b, 1); // div d, a, b | |
| 1111 | + ER(S, 0x33 | ll, 4, d, a, b, 1); // div d, a, b | |
| 1118 | 1112 | break; |
| 1119 | 1113 | case '&': |
| 1120 | − ER(0x33, 7, d, a, b, 0); // and d, a, b | |
| 1114 | + ER(S, 0x33, 7, d, a, b, 0); // and d, a, b | |
| 1121 | 1115 | break; |
| 1122 | 1116 | case '^': |
| 1123 | − ER(0x33, 4, d, a, b, 0); // xor d, a, b | |
| 1117 | + ER(S, 0x33, 4, d, a, b, 0); // xor d, a, b | |
| 1124 | 1118 | break; |
| 1125 | 1119 | case '|': |
| 1126 | − ER(0x33, 6, d, a, b, 0); // or d, a, b | |
| 1120 | + ER(S, 0x33, 6, d, a, b, 0); // or d, a, b | |
| 1127 | 1121 | break; |
| 1128 | 1122 | case '%': |
| 1129 | − ER(ll ? 0x3b: 0x33, 6, d, a, b, 1); // rem d, a, b | |
| 1123 | + ER(S, ll ? 0x3b: 0x33, 6, d, a, b, 1); // rem d, a, b | |
| 1130 | 1124 | break; |
| 1131 | 1125 | case TOK_UMOD: |
| 1132 | − ER(0x33 | ll, 7, d, a, b, 1); // remu d, a, b | |
| 1126 | + ER(S, 0x33 | ll, 7, d, a, b, 1); // remu d, a, b | |
| 1133 | 1127 | break; |
| 1134 | 1128 | case TOK_PDIV: |
| 1135 | 1129 | case TOK_UDIV: |
| 1136 | − ER(0x33 | ll, 5, d, a, b, 1); // divu d, a, b | |
| 1130 | + ER(S, 0x33 | ll, 5, d, a, b, 1); // divu d, a, b | |
| 1137 | 1131 | break; |
| 1138 | 1132 | } |
| 1139 | 1133 | } |
| 1140 | 1134 | |
| 1141 | −ST_FUNC void gen_opi(int op) | |
| 1135 | +ST_FUNC void gen_opi(TCCState* S, int op) | |
| 1142 | 1136 | { |
| 1143 | − gen_opil(op, 0); | |
| 1137 | + gen_opil(S, op, 0); | |
| 1144 | 1138 | } |
| 1145 | 1139 | |
| 1146 | −ST_FUNC void gen_opl(int op) | |
| 1140 | +ST_FUNC void gen_opl(TCCState* S, int op) | |
| 1147 | 1141 | { |
| 1148 | − gen_opil(op, 1); | |
| 1142 | + gen_opil(S, op, 1); | |
| 1149 | 1143 | } |
| 1150 | 1144 | |
| 1151 | −ST_FUNC void gen_opf(int op) | |
| 1145 | +ST_FUNC void gen_opf(TCCState* S, int op) | |
| 1152 | 1146 | { |
| 1153 | 1147 | int rs1, rs2, rd, dbl, invert; |
| 1154 | − if (vtop[0].type.t == VT_LDOUBLE) { | |
| 1155 | − CType type = vtop[0].type; | |
| 1148 | + if (S->tccgen_vtop[0].type.t == VT_LDOUBLE) { | |
| 1149 | + CType type = S->tccgen_vtop[0].type; | |
| 1156 | 1150 | int func = 0; |
| 1157 | 1151 | int cond = -1; |
| 1158 | 1152 | switch (op) { |
| @@ -1168,27 +1162,27 @@ ST_FUNC void gen_opf(int op) · 9 unmodified lines | ||
| 1168 | 1162 | case TOK_GT: func = TOK___gttf2; cond = 13; break; |
| 1169 | 1163 | default: assert(0); break; |
| 1170 | 1164 | } |
| 1171 | − vpush_helper_func(func); | |
| 1172 | − vrott(3); | |
| 1173 | − gfunc_call(2); | |
| 1174 | − vpushi(0); | |
| 1175 | − vtop->r = REG_IRET; | |
| 1176 | − vtop->r2 = cond < 0 ? TREG_R(1) : VT_CONST; | |
| 1165 | + vpush_helper_func(S, func); | |
| 1166 | + vrott(S, 3); | |
| 1167 | + gfunc_call(S, 2); | |
| 1168 | + vpushi(S, 0); | |
| 1169 | + S->tccgen_vtop->r = REG_IRET; | |
| 1170 | + S->tccgen_vtop->r2 = cond < 0 ? TREG_R(1) : VT_CONST; | |
| 1177 | 1171 | if (cond < 0) |
| 1178 | − vtop->type = type; | |
| 1172 | + S->tccgen_vtop->type = type; | |
| 1179 | 1173 | else { |
| 1180 | − vpushi(0); | |
| 1181 | − gen_opil(op, 1); | |
| 1174 | + vpushi(S, 0); | |
| 1175 | + gen_opil(S, op, 1); | |
| 1182 | 1176 | } |
| 1183 | 1177 | return; |
| 1184 | 1178 | } |
| 1185 | 1179 | |
| 1186 | − gv2(RC_FLOAT, RC_FLOAT); | |
| 1187 | − assert(vtop->type.t == VT_DOUBLE || vtop->type.t == VT_FLOAT); | |
| 1188 | − dbl = vtop->type.t == VT_DOUBLE; | |
| 1189 | − rs1 = freg(vtop[-1].r); | |
| 1190 | − rs2 = freg(vtop->r); | |
| 1191 | − vtop--; | |
| 1180 | + gv2(S, RC_FLOAT, RC_FLOAT); | |
| 1181 | + assert(S->tccgen_vtop->type.t == VT_DOUBLE || S->tccgen_vtop->type.t == VT_FLOAT); | |
| 1182 | + dbl = S->tccgen_vtop->type.t == VT_DOUBLE; | |
| 1183 | + rs1 = freg(S->tccgen_vtop[-1].r); | |
| 1184 | + rs2 = freg(S->tccgen_vtop->r); | |
| 1185 | + S->tccgen_vtop--; | |
| 1192 | 1186 | invert = 0; |
| 1193 | 1187 | switch(op) { |
| 1194 | 1188 | default: |
| @@ -1196,10 +1190,10 @@ ST_FUNC void gen_opf(int op) · 1 unmodified line | ||
| 1196 | 1190 | case '+': |
| 1197 | 1191 | op = 0; // fadd |
| 1198 | 1192 | arithop: |
| 1199 | − rd = get_reg(RC_FLOAT); | |
| 1200 | − vtop->r = rd; | |
| 1193 | + rd = get_reg(S, RC_FLOAT); | |
| 1194 | + S->tccgen_vtop->r = rd; | |
| 1201 | 1195 | rd = freg(rd); |
| 1202 | − ER(0x53, 7, rd, rs1, rs2, dbl | (op << 2)); // fop.[sd] RD, RS1, RS2 (dyn rm) | |
| 1196 | + ER(S, 0x53, 7, rd, rs1, rs2, dbl | (op << 2)); // fop.[sd] RD, RS1, RS2 (dyn rm) | |
| 1203 | 1197 | break; |
| 1204 | 1198 | case '-': |
| 1205 | 1199 | op = 1; // fsub |
| @@ -1213,12 +1207,12 @@ ST_FUNC void gen_opf(int op) · 7 unmodified lines | ||
| 1213 | 1207 | case TOK_EQ: |
| 1214 | 1208 | op = 2; // EQ |
| 1215 | 1209 | cmpop: |
| 1216 | − rd = get_reg(RC_INT); | |
| 1217 | − vtop->r = rd; | |
| 1210 | + rd = get_reg(S, RC_INT); | |
| 1211 | + S->tccgen_vtop->r = rd; | |
| 1218 | 1212 | rd = ireg(rd); |
| 1219 | − ER(0x53, op, rd, rs1, rs2, dbl | 0x50); // fcmp.[sd] RD, RS1, RS2 (op == eq/lt/le) | |
| 1213 | + ER(S, 0x53, op, rd, rs1, rs2, dbl | 0x50); // fcmp.[sd] RD, RS1, RS2 (op == eq/lt/le) | |
| 1220 | 1214 | if (invert) |
| 1221 | − EI(0x13, 4, rd, rd, 1); // xori RD, 1 | |
| 1215 | + EI(S, 0x13, 4, rd, rd, 1); // xori RD, 1 | |
| 1222 | 1216 | break; |
| 1223 | 1217 | case TOK_NE: |
| 1224 | 1218 | invert = 1; |
| @@ -1241,67 +1235,67 @@ ST_FUNC void gen_opf(int op) · 16 unmodified lines | ||
| 1241 | 1235 | } |
| 1242 | 1236 | } |
| 1243 | 1237 | |
| 1244 | −ST_FUNC void gen_cvt_sxtw(void) | |
| 1238 | +ST_FUNC void gen_cvt_sxtw(TCCState *S) | |
| 1245 | 1239 | { |
| 1246 | 1240 | /* XXX on risc-v the registers are usually sign-extended already. |
| 1247 | 1241 | Let's try to not do anything here. */ |
| 1248 | 1242 | } |
| 1249 | 1243 | |
| 1250 | −ST_FUNC void gen_cvt_itof(int t) | |
| 1244 | +ST_FUNC void gen_cvt_itof(TCCState* S, int t) | |
| 1251 | 1245 | { |
| 1252 | − int rr = ireg(gv(RC_INT)), dr; | |
| 1253 | − int u = vtop->type.t & VT_UNSIGNED; | |
| 1254 | − int l = (vtop->type.t & VT_BTYPE) == VT_LLONG; | |
| 1246 | + int rr = ireg(gv(S, RC_INT)), dr; | |
| 1247 | + int u = S->tccgen_vtop->type.t & VT_UNSIGNED; | |
| 1248 | + int l = (S->tccgen_vtop->type.t & VT_BTYPE) == VT_LLONG; | |
| 1255 | 1249 | if (t == VT_LDOUBLE) { |
| 1256 | 1250 | int func = l ? |
| 1257 | 1251 | (u ? TOK___floatunditf : TOK___floatditf) : |
| 1258 | 1252 | (u ? TOK___floatunsitf : TOK___floatsitf); |
| 1259 | − vpush_helper_func(func); | |
| 1260 | − vrott(2); | |
| 1261 | − gfunc_call(1); | |
| 1262 | − vpushi(0); | |
| 1263 | − vtop->type.t = t; | |
| 1264 | − vtop->r = REG_IRET; | |
| 1265 | − vtop->r2 = TREG_R(1); | |
| 1253 | + vpush_helper_func(S, func); | |
| 1254 | + vrott(S, 2); | |
| 1255 | + gfunc_call(S, 1); | |
| 1256 | + vpushi(S, 0); | |
| 1257 | + S->tccgen_vtop->type.t = t; | |
| 1258 | + S->tccgen_vtop->r = REG_IRET; | |
| 1259 | + S->tccgen_vtop->r2 = TREG_R(1); | |
| 1266 | 1260 | } else { |
| 1267 | − vtop--; | |
| 1268 | − dr = get_reg(RC_FLOAT); | |
| 1269 | − vtop++; | |
| 1270 | − vtop->r = dr; | |
| 1261 | + S->tccgen_vtop--; | |
| 1262 | + dr = get_reg(S, RC_FLOAT); | |
| 1263 | + S->tccgen_vtop++; | |
| 1264 | + S->tccgen_vtop->r = dr; | |
| 1271 | 1265 | dr = freg(dr); |
| 1272 | − EIu(0x53, 7, dr, rr, ((0x68 | (t == VT_DOUBLE ? 1 : 0)) << 5) | (u ? 1 : 0) | (l ? 2 : 0)); // fcvt.[sd].[wl][u] | |
| 1266 | + EIu(S, 0x53, 7, dr, rr, ((0x68 | (t == VT_DOUBLE ? 1 : 0)) << 5) | (u ? 1 : 0) | (l ? 2 : 0)); // fcvt.[sd].[wl][u] | |
| 1273 | 1267 | } |
| 1274 | 1268 | } |
| 1275 | 1269 | |
| 1276 | −ST_FUNC void gen_cvt_ftoi(int t) | |
| 1270 | +ST_FUNC void gen_cvt_ftoi(TCCState* S, int t) | |
| 1277 | 1271 | { |
| 1278 | − int ft = vtop->type.t & VT_BTYPE; | |
| 1272 | + int ft = S->tccgen_vtop->type.t & VT_BTYPE; | |
| 1279 | 1273 | int l = (t & VT_BTYPE) == VT_LLONG; |
| 1280 | 1274 | int u = t & VT_UNSIGNED; |
| 1281 | 1275 | if (ft == VT_LDOUBLE) { |
| 1282 | 1276 | int func = l ? |
| 1283 | 1277 | (u ? TOK___fixunstfdi : TOK___fixtfdi) : |
| 1284 | 1278 | (u ? TOK___fixunstfsi : TOK___fixtfsi); |
| 1285 | − vpush_helper_func(func); | |
| 1286 | − vrott(2); | |
| 1287 | − gfunc_call(1); | |
| 1288 | − vpushi(0); | |
| 1289 | − vtop->type.t = t; | |
| 1290 | − vtop->r = REG_IRET; | |
| 1279 | + vpush_helper_func(S, func); | |
| 1280 | + vrott(S, 2); | |
| 1281 | + gfunc_call(S, 1); | |
| 1282 | + vpushi(S, 0); | |
| 1283 | + S->tccgen_vtop->type.t = t; | |
| 1284 | + S->tccgen_vtop->r = REG_IRET; | |
| 1291 | 1285 | } else { |
| 1292 | − int rr = freg(gv(RC_FLOAT)), dr; | |
| 1293 | − vtop--; | |
| 1294 | − dr = get_reg(RC_INT); | |
| 1295 | − vtop++; | |
| 1296 | − vtop->r = dr; | |
| 1286 | + int rr = freg(gv(S, RC_FLOAT)), dr; | |
| 1287 | + S->tccgen_vtop--; | |
| 1288 | + dr = get_reg(S, RC_INT); | |
| 1289 | + S->tccgen_vtop++; | |
| 1290 | + S->tccgen_vtop->r = dr; | |
| 1297 | 1291 | dr = ireg(dr); |
| 1298 | − EIu(0x53, 1, dr, rr, ((0x60 | (ft == VT_DOUBLE ? 1 : 0)) << 5) | (u ? 1 : 0) | (l ? 2 : 0)); // fcvt.[wl][u].[sd] rtz | |
| 1292 | + EIu(S, 0x53, 1, dr, rr, ((0x60 | (ft == VT_DOUBLE ? 1 : 0)) << 5) | (u ? 1 : 0) | (l ? 2 : 0)); // fcvt.[wl][u].[sd] rtz | |
| 1299 | 1293 | } |
| 1300 | 1294 | } |
| 1301 | 1295 | |
| 1302 | −ST_FUNC void gen_cvt_ftof(int dt) | |
| 1296 | +ST_FUNC void gen_cvt_ftof(TCCState* S, int dt) | |
| 1303 | 1297 | { |
| 1304 | − int st = vtop->type.t & VT_BTYPE, rs, rd; | |
| 1298 | + int st = S->tccgen_vtop->type.t & VT_BTYPE, rs, rd; | |
| 1305 | 1299 | dt &= VT_BTYPE; |
| 1306 | 1300 | if (st == dt) |
| 1307 | 1301 | return; |
| @@ -1313,109 +1307,109 @@ ST_FUNC void gen_cvt_ftof(int dt) · 5 unmodified lines | ||
| 1313 | 1307 | functions, and on riscv unnamed float args are passed like |
| 1314 | 1308 | integers. But we really need them in the float argument registers |
| 1315 | 1309 | for extendsftf2/extenddftf2. So, do it explicitely. */ |
| 1316 | − save_regs(1); | |
| 1310 | + save_regs(S, 1); | |
| 1317 | 1311 | if (dt == VT_LDOUBLE) |
| 1318 | − gv(RC_F(0)); | |
| 1312 | + gv(S, RC_F(0)); | |
| 1319 | 1313 | else { |
| 1320 | − gv(RC_R(0)); | |
| 1321 | − assert(vtop->r2 < 7); | |
| 1322 | − if (vtop->r2 != 1 + vtop->r) { | |
| 1323 | − EI(0x13, 0, ireg(vtop->r) + 1, ireg(vtop->r2), 0); // mv Ra+1, RR2 | |
| 1324 | − vtop->r2 = 1 + vtop->r; | |
| 1314 | + gv(S, RC_R(0)); | |
| 1315 | + assert(S->tccgen_vtop->r2 < 7); | |
| 1316 | + if (S->tccgen_vtop->r2 != 1 + S->tccgen_vtop->r) { | |
| 1317 | + EI(S, 0x13, 0, ireg(S->tccgen_vtop->r) + 1, ireg(S->tccgen_vtop->r2), 0); // mv Ra+1, RR2 | |
| 1318 | + S->tccgen_vtop->r2 = 1 + S->tccgen_vtop->r; | |
| 1325 | 1319 | } |
| 1326 | 1320 | } |
| 1327 | − vpush_helper_func(func); | |
| 1328 | − gcall_or_jmp(1); | |
| 1329 | − vtop -= 2; | |
| 1330 | − vpushi(0); | |
| 1331 | − vtop->type.t = dt; | |
| 1321 | + vpush_helper_func(S, func); | |
| 1322 | + gcall_or_jmp(S, 1); | |
| 1323 | + S->tccgen_vtop -= 2; | |
| 1324 | + vpushi(S, 0); | |
| 1325 | + S->tccgen_vtop->type.t = dt; | |
| 1332 | 1326 | if (dt == VT_LDOUBLE) |
| 1333 | − vtop->r = REG_IRET, vtop->r2 = REG_IRET+1; | |
| 1327 | + S->tccgen_vtop->r = REG_IRET, S->tccgen_vtop->r2 = REG_IRET+1; | |
| 1334 | 1328 | else |
| 1335 | − vtop->r = REG_FRET; | |
| 1329 | + S->tccgen_vtop->r = REG_FRET; | |
| 1336 | 1330 | } else { |
| 1337 | 1331 | assert (dt == VT_FLOAT || dt == VT_DOUBLE); |
| 1338 | 1332 | assert (st == VT_FLOAT || st == VT_DOUBLE); |
| 1339 | − rs = gv(RC_FLOAT); | |
| 1340 | − rd = get_reg(RC_FLOAT); | |
| 1333 | + rs = gv(S, RC_FLOAT); | |
| 1334 | + rd = get_reg(S, RC_FLOAT); | |
| 1341 | 1335 | if (dt == VT_DOUBLE) |
| 1342 | − EI(0x53, 0, freg(rd), freg(rs), 0x21 << 5); // fcvt.d.s RD, RS (no rm) | |
| 1336 | + EI(S, 0x53, 0, freg(rd), freg(rs), 0x21 << 5); // fcvt.d.s RD, RS (no rm) | |
| 1343 | 1337 | else |
| 1344 | − EI(0x53, 7, freg(rd), freg(rs), (0x20 << 5) | 1); // fcvt.s.d RD, RS (dyn rm) | |
| 1345 | − vtop->r = rd; | |
| 1338 | + EI(S, 0x53, 7, freg(rd), freg(rs), (0x20 << 5) | 1); // fcvt.s.d RD, RS (dyn rm) | |
| 1339 | + S->tccgen_vtop->r = rd; | |
| 1346 | 1340 | } |
| 1347 | 1341 | } |
| 1348 | 1342 | |
| 1349 | 1343 | /* increment tcov counter */ |
| 1350 | −ST_FUNC void gen_increment_tcov (SValue *sv) | |
| 1344 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv) | |
| 1351 | 1345 | { |
| 1352 | 1346 | int r1, r2; |
| 1353 | 1347 | Sym label = {0}; |
| 1354 | 1348 | label.type.t = VT_VOID | VT_STATIC; |
| 1355 | 1349 | |
| 1356 | − vpushv(sv); | |
| 1357 | − vtop->r = r1 = get_reg(RC_INT); | |
| 1358 | − r2 = get_reg(RC_INT); | |
| 1350 | + vpushv(S, sv); | |
| 1351 | + S->tccgen_vtop->r = r1 = get_reg(S, RC_INT); | |
| 1352 | + r2 = get_reg(S, RC_INT); | |
| 1359 | 1353 | r1 = ireg(r1); |
| 1360 | 1354 | r2 = ireg(r2); |
| 1361 | − greloca(cur_text_section, sv->sym, ind, R_RISCV_PCREL_HI20, 0); | |
| 1362 | − put_extern_sym(&label, cur_text_section, ind, 0); | |
| 1363 | − o(0x17 | (r1 << 7)); // auipc RR, 0 %pcrel_hi(sym) | |
| 1364 | − greloca(cur_text_section, &label, ind, R_RISCV_PCREL_LO12_I, 0); | |
| 1365 | − EI(0x03, 3, r2, r1, 0); // ld r2, x[r1] | |
| 1366 | − EI(0x13, 0, r2, r2, 1); // addi r2, r2, #1 | |
| 1367 | − greloca(cur_text_section, sv->sym, ind, R_RISCV_PCREL_HI20, 0); | |
| 1355 | + greloca(S, cur_text_section, sv->sym, S->tccgen_ind, R_RISCV_PCREL_HI20, 0); | |
| 1356 | + put_extern_sym(S, &label, cur_text_section, S->tccgen_ind, 0); | |
| 1357 | + o(S, 0x17 | (r1 << 7)); // auipc RR, 0 %pcrel_hi(sym) | |
| 1358 | + greloca(S, cur_text_section, &label, S->tccgen_ind, R_RISCV_PCREL_LO12_I, 0); | |
| 1359 | + EI(S, 0x03, 3, r2, r1, 0); // ld r2, x[r1] | |
| 1360 | + EI(S, 0x13, 0, r2, r2, 1); // addi r2, r2, #1 | |
| 1361 | + greloca(S, cur_text_section, sv->sym, S->tccgen_ind, R_RISCV_PCREL_HI20, 0); | |
| 1368 | 1362 | label.c = 0; /* force new local ELF symbol */ |
| 1369 | − put_extern_sym(&label, cur_text_section, ind, 0); | |
| 1370 | − o(0x17 | (r1 << 7)); // auipc RR, 0 %pcrel_hi(sym) | |
| 1371 | − greloca(cur_text_section, &label, ind, R_RISCV_PCREL_LO12_S, 0); | |
| 1372 | − ES(0x23, 3, r1, r2, 0); // sd r2, [r1] | |
| 1373 | − vpop(); | |
| 1363 | + put_extern_sym(S, &label, cur_text_section, S->tccgen_ind, 0); | |
| 1364 | + o(S, 0x17 | (r1 << 7)); // auipc RR, 0 %pcrel_hi(sym) | |
| 1365 | + greloca(S, cur_text_section, &label, S->tccgen_ind, R_RISCV_PCREL_LO12_S, 0); | |
| 1366 | + ES(S, 0x23, 3, r1, r2, 0); // sd r2, [r1] | |
| 1367 | + vpop(S); | |
| 1374 | 1368 | } |
| 1375 | 1369 | |
| 1376 | −ST_FUNC void ggoto(void) | |
| 1370 | +ST_FUNC void ggoto(TCCState* S) | |
| 1377 | 1371 | { |
| 1378 | − gcall_or_jmp(0); | |
| 1379 | − vtop--; | |
| 1372 | + gcall_or_jmp(S, 0); | |
| 1373 | + S->tccgen_vtop--; | |
| 1380 | 1374 | } |
| 1381 | 1375 | |
| 1382 | −ST_FUNC void gen_vla_sp_save(int addr) | |
| 1376 | +ST_FUNC void gen_vla_sp_save(TCCState* S, int addr) | |
| 1383 | 1377 | { |
| 1384 | − ES(0x23, 3, 8, 2, addr); // sd sp, fc(s0) | |
| 1378 | + ES(S, 0x23, 3, 8, 2, addr); // sd sp, fc(s0) | |
| 1385 | 1379 | } |
| 1386 | 1380 | |
| 1387 | −ST_FUNC void gen_vla_sp_restore(int addr) | |
| 1381 | +ST_FUNC void gen_vla_sp_restore(TCCState* S, int addr) | |
| 1388 | 1382 | { |
| 1389 | − EI(0x03, 3, 2, 8, addr); // ld sp, fc(s0) | |
| 1383 | + EI(S, 0x03, 3, 2, 8, addr); // ld sp, fc(s0) | |
| 1390 | 1384 | } |
| 1391 | 1385 | |
| 1392 | −ST_FUNC void gen_vla_alloc(CType *type, int align) | |
| 1386 | +ST_FUNC void gen_vla_alloc(TCCState* S, CType *type, int align) | |
| 1393 | 1387 | { |
| 1394 | 1388 | int rr; |
| 1395 | 1389 | #if defined(CONFIG_TCC_BCHECK) |
| 1396 | − if (tcc_state->do_bounds_check) | |
| 1397 | − vpushv(vtop); | |
| 1390 | + if (S->do_bounds_check) | |
| 1391 | + vpushv(S, S->tccgen_vtop); | |
| 1398 | 1392 | #endif |
| 1399 | − rr = ireg(gv(RC_INT)); | |
| 1393 | + rr = ireg(gv(S, RC_INT)); | |
| 1400 | 1394 | #if defined(CONFIG_TCC_BCHECK) |
| 1401 | − if (tcc_state->do_bounds_check) | |
| 1402 | − EI(0x13, 0, rr, rr, 15+1); // addi RR, RR, 15+1 | |
| 1395 | + if (S->do_bounds_check) | |
| 1396 | + EI(S, 0x13, 0, rr, rr, 15+1); // addi RR, RR, 15+1 | |
| 1403 | 1397 | else |
| 1404 | 1398 | #endif |
| 1405 | − EI(0x13, 0, rr, rr, 15); // addi RR, RR, 15 | |
| 1406 | − EI(0x13, 7, rr, rr, -16); // andi, RR, RR, -16 | |
| 1407 | − ER(0x33, 0, 2, 2, rr, 0x20); // sub sp, sp, rr | |
| 1408 | − vpop(); | |
| 1399 | + EI(S, 0x13, 0, rr, rr, 15); // addi RR, RR, 15 | |
| 1400 | + EI(S, 0x13, 7, rr, rr, -16); // andi, RR, RR, -16 | |
| 1401 | + ER(S, 0x33, 0, 2, 2, rr, 0x20); // sub sp, sp, rr | |
| 1402 | + vpop(S); | |
| 1409 | 1403 | #if defined(CONFIG_TCC_BCHECK) |
| 1410 | − if (tcc_state->do_bounds_check) { | |
| 1411 | − vpushi(0); | |
| 1412 | − vtop->r = TREG_R(0); | |
| 1413 | − o(0x00010513); /* mv a0,sp */ | |
| 1414 | − vswap(); | |
| 1415 | − vpush_helper_func(TOK___bound_new_region); | |
| 1416 | − vrott(3); | |
| 1417 | − gfunc_call(2); | |
| 1418 | − func_bound_add_epilog = 1; | |
| 1404 | + if (S->do_bounds_check) { | |
| 1405 | + vpushi(S, 0); | |
| 1406 | + S->tccgen_vtop->r = TREG_R(0); | |
| 1407 | + o(S, 0x00010513); /* mv a0,sp */ | |
| 1408 | + vswap(S); | |
| 1409 | + vpush_helper_func(S, TOK___bound_new_region); | |
| 1410 | + vrott(S, 3); | |
| 1411 | + gfunc_call(S, 2); | |
| 1412 | + S->func_bound_add_epilog = 1; | |
| 1419 | 1413 | } |
| 1420 | 1414 | #endif |
| 1421 | 1415 | } |
| @@ -95,39 +95,39 @@ int gotplt_entry_type (int reloc_type) · 94 unmodified lines | ||
| 95 | 95 | return -1; |
| 96 | 96 | } |
| 97 | 97 | |
| 98 | −ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_attr *attr) | |
| 98 | +ST_FUNC unsigned create_plt_entry(TCCState *S, unsigned got_offset, struct sym_attr *attr) | |
| 99 | 99 | { |
| 100 | − Section *plt = s1->plt; | |
| 100 | + Section *plt = S->plt; | |
| 101 | 101 | uint8_t *p; |
| 102 | 102 | unsigned plt_offset; |
| 103 | 103 | |
| 104 | 104 | if (plt->data_offset == 0) |
| 105 | − section_ptr_add(plt, 32); | |
| 105 | + section_ptr_add(S, plt, 32); | |
| 106 | 106 | plt_offset = plt->data_offset; |
| 107 | 107 | |
| 108 | − p = section_ptr_add(plt, 16); | |
| 108 | + p = section_ptr_add(S, plt, 16); | |
| 109 | 109 | write64le(p, got_offset); |
| 110 | 110 | return plt_offset; |
| 111 | 111 | } |
| 112 | 112 | |
| 113 | 113 | /* relocate the PLT: compute addresses and offsets in the PLT now that final |
| 114 | 114 | address for PLT and GOT are known (see fill_program_header) */ |
| 115 | −ST_FUNC void relocate_plt(TCCState *s1) | |
| 115 | +ST_FUNC void relocate_plt(TCCState *S) | |
| 116 | 116 | { |
| 117 | 117 | uint8_t *p, *p_end; |
| 118 | 118 | |
| 119 | − if (!s1->plt) | |
| 119 | + if (!S->plt) | |
| 120 | 120 | return; |
| 121 | 121 | |
| 122 | − p = s1->plt->data; | |
| 123 | − p_end = p + s1->plt->data_offset; | |
| 122 | + p = S->plt->data; | |
| 123 | + p_end = p + S->plt->data_offset; | |
| 124 | 124 | |
| 125 | 125 | if (p < p_end) { |
| 126 | − uint64_t plt = s1->plt->sh_addr; | |
| 127 | − uint64_t got = s1->got->sh_addr; | |
| 126 | + uint64_t plt = S->plt->sh_addr; | |
| 127 | + uint64_t got = S->got->sh_addr; | |
| 128 | 128 | uint64_t off = (got - plt + 0x800) >> 12; |
| 129 | 129 | if ((off + ((uint32_t)1 << 20)) >> 21) |
| 130 | − tcc_error("Failed relocating PLT (off=0x%lx, got=0x%lx, plt=0x%lx)", (long)off, (long)got, (long)plt); | |
| 130 | + tcc_error(S, "Failed relocating PLT (off=0x%lx, got=0x%lx, plt=0x%lx)", (long)off, (long)got, (long)plt); | |
| 131 | 131 | write32le(p, 0x397 | (off << 12)); // auipc t2, %pcrel_hi(got) |
| 132 | 132 | write32le(p + 4, 0x41c30333); // sub t1, t1, t3 |
| 133 | 133 | write32le(p + 8, 0x0003be03 // ld t3, %pcrel_lo(got)(t2) |
| @@ -140,11 +140,11 @@ ST_FUNC void relocate_plt(TCCState *s1) · 6 unmodified lines | ||
| 140 | 140 | write32le(p + 28, 0x000e0067); // jr t3 |
| 141 | 141 | p += 32; |
| 142 | 142 | while (p < p_end) { |
| 143 | − uint64_t pc = plt + (p - s1->plt->data); | |
| 143 | + uint64_t pc = plt + (p - S->plt->data); | |
| 144 | 144 | uint64_t addr = got + read64le(p); |
| 145 | 145 | uint64_t off = (addr - pc + 0x800) >> 12; |
| 146 | 146 | if ((off + ((uint32_t)1 << 20)) >> 21) |
| 147 | − tcc_error("Failed relocating PLT (off=0x%lx, addr=0x%lx, pc=0x%lx)", (long)off, (long)addr, (long)pc); | |
| 147 | + tcc_error(S, "Failed relocating PLT (off=0x%lx, addr=0x%lx, pc=0x%lx)", (long)off, (long)addr, (long)pc); | |
| 148 | 148 | write32le(p, 0xe17 | (off << 12)); // auipc t3, %pcrel_hi(func@got) |
| 149 | 149 | write32le(p + 4, 0x000e3e03 // ld t3, %pcrel_lo(func@got)(t3) |
| 150 | 150 | | (((addr - pc) & 0xfff) << 20)); |
| @@ -154,16 +154,16 @@ ST_FUNC void relocate_plt(TCCState *s1) · 3 unmodified lines | ||
| 154 | 154 | } |
| 155 | 155 | } |
| 156 | 156 | |
| 157 | − if (s1->plt->reloc) { | |
| 157 | + if (S->plt->reloc) { | |
| 158 | 158 | ElfW_Rel *rel; |
| 159 | − p = s1->got->data; | |
| 160 | − for_each_elem(s1->plt->reloc, 0, rel, ElfW_Rel) { | |
| 161 | − write64le(p + rel->r_offset, s1->plt->sh_addr); | |
| 159 | + p = S->got->data; | |
| 160 | + for_each_elem(S->plt->reloc, 0, rel, ElfW_Rel) { | |
| 161 | + write64le(p + rel->r_offset, S->plt->sh_addr); | |
| 162 | 162 | } |
| 163 | 163 | } |
| 164 | 164 | } |
| 165 | 165 | |
| 166 | −void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, | |
| 166 | +void relocate(TCCState *S, ElfW_Rel *rel, int type, unsigned char *ptr, | |
| 167 | 167 | addr_t addr, addr_t val) |
| 168 | 168 | { |
| 169 | 169 | uint64_t off64; |
| @@ -179,7 +179,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 9 unmodified lines | ||
| 179 | 179 | case R_RISCV_BRANCH: |
| 180 | 180 | off64 = val - addr; |
| 181 | 181 | if ((off64 + (1 << 12)) & ~(uint64_t)0x1ffe) |
| 182 | − tcc_error("R_RISCV_BRANCH relocation failed" | |
| 182 | + tcc_error(S, "R_RISCV_BRANCH relocation failed" | |
| 183 | 183 | " (val=%lx, addr=%lx)", (long)val, (long)addr); |
| 184 | 184 | off32 = off64 >> 1; |
| 185 | 185 | write32le(ptr, (read32le(ptr) & ~0xfe000f80) |
| @@ -191,7 +191,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 5 unmodified lines | ||
| 191 | 191 | case R_RISCV_JAL: |
| 192 | 192 | off64 = val - addr; |
| 193 | 193 | if ((off64 + (1 << 21)) & ~(((uint64_t)1 << 22) - 2)) |
| 194 | − tcc_error("R_RISCV_JAL relocation failed" | |
| 194 | + tcc_error(S, "R_RISCV_JAL relocation failed" | |
| 195 | 195 | " (val=%lx, addr=%lx)", (long)val, (long)addr); |
| 196 | 196 | off32 = off64; |
| 197 | 197 | write32le(ptr, (read32le(ptr) & 0xfff) |
| @@ -213,7 +213,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 15 unmodified lines | ||
| 213 | 213 | #endif |
| 214 | 214 | off64 = (int64_t)(val - addr + 0x800) >> 12; |
| 215 | 215 | if ((off64 + ((uint64_t)1 << 20)) >> 21) |
| 216 | − tcc_error("R_RISCV_PCREL_HI20 relocation failed: off=%lx cond=%lx sym=%s", | |
| 216 | + tcc_error(S, "R_RISCV_PCREL_HI20 relocation failed: off=%lx cond=%lx sym=%s", | |
| 217 | 217 | (long)off64, (long)((int64_t)(off64 + ((uint64_t)1 << 20)) >> 21), |
| 218 | 218 | symtab_section->link->data + sym->st_name); |
| 219 | 219 | write32le(ptr, (read32le(ptr) & 0xfff) |
| @@ -222,10 +222,10 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 2 unmodified lines | ||
| 222 | 222 | last_hi.val = val; |
| 223 | 223 | return; |
| 224 | 224 | case R_RISCV_GOT_HI20: |
| 225 | − val = s1->got->sh_addr + get_sym_attr(s1, sym_index, 0)->got_offset; | |
| 225 | + val = S->got->sh_addr + get_sym_attr(S, sym_index, 0)->got_offset; | |
| 226 | 226 | off64 = (int64_t)(val - addr + 0x800) >> 12; |
| 227 | 227 | if ((off64 + ((uint64_t)1 << 20)) >> 21) |
| 228 | − tcc_error("R_RISCV_GOT_HI20 relocation failed"); | |
| 228 | + tcc_error(S, "R_RISCV_GOT_HI20 relocation failed"); | |
| 229 | 229 | last_hi.addr = addr; |
| 230 | 230 | last_hi.val = val; |
| 231 | 231 | write32le(ptr, (read32le(ptr) & 0xfff) |
| @@ -236,7 +236,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 4 unmodified lines | ||
| 236 | 236 | printf("PCREL_LO12_I: val=%lx addr=%lx\n", (long)val, (long)addr); |
| 237 | 237 | #endif |
| 238 | 238 | if (val != last_hi.addr) |
| 239 | − tcc_error("unsupported hi/lo pcrel reloc scheme"); | |
| 239 | + tcc_error(S, "unsupported hi/lo pcrel reloc scheme"); | |
| 240 | 240 | val = last_hi.val; |
| 241 | 241 | addr = last_hi.addr; |
| 242 | 242 | write32le(ptr, (read32le(ptr) & 0xfffff) |
| @@ -244,7 +244,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 1 unmodified line | ||
| 244 | 244 | return; |
| 245 | 245 | case R_RISCV_PCREL_LO12_S: |
| 246 | 246 | if (val != last_hi.addr) |
| 247 | − tcc_error("unsupported hi/lo pcrel reloc scheme"); | |
| 247 | + tcc_error(S, "unsupported hi/lo pcrel reloc scheme"); | |
| 248 | 248 | val = last_hi.val; |
| 249 | 249 | addr = last_hi.addr; |
| 250 | 250 | off32 = val - addr; |
| @@ -256,7 +256,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 5 unmodified lines | ||
| 256 | 256 | case R_RISCV_RVC_BRANCH: |
| 257 | 257 | off64 = (val - addr); |
| 258 | 258 | if ((off64 + (1 << 8)) & ~(uint64_t)0x1fe) |
| 259 | − tcc_error("R_RISCV_RVC_BRANCH relocation failed" | |
| 259 | + tcc_error(S, "R_RISCV_RVC_BRANCH relocation failed" | |
| 260 | 260 | " (val=%lx, addr=%lx)", (long)val, (long)addr); |
| 261 | 261 | off32 = off64; |
| 262 | 262 | write16le(ptr, (read16le(ptr) & 0xe383) |
| @@ -269,7 +269,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 6 unmodified lines | ||
| 269 | 269 | case R_RISCV_RVC_JUMP: |
| 270 | 270 | off64 = (val - addr); |
| 271 | 271 | if ((off64 + (1 << 11)) & ~(uint64_t)0xffe) |
| 272 | − tcc_error("R_RISCV_RVC_BRANCH relocation failed" | |
| 272 | + tcc_error(S, "R_RISCV_RVC_BRANCH relocation failed" | |
| 273 | 273 | " (val=%lx, addr=%lx)", (long)val, (long)addr); |
| 274 | 274 | off32 = off64; |
| 275 | 275 | write16le(ptr, (read16le(ptr) & 0xe003) |
| @@ -284,7 +284,7 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 8 unmodified lines | ||
| 284 | 284 | return; |
| 285 | 285 | |
| 286 | 286 | case R_RISCV_32: |
| 287 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 287 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 288 | 288 | /* XXX: this logic may depend on TCC's codegen |
| 289 | 289 | now TCC uses R_RISCV_RELATIVE even for a 64bit pointer */ |
| 290 | 290 | qrel->r_offset = rel->r_offset; |
| @@ -296,8 +296,8 @@ void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, · 5 unmodified lines | ||
| 296 | 296 | add32le(ptr, val); |
| 297 | 297 | return; |
| 298 | 298 | case R_RISCV_64: |
| 299 | − if (s1->output_type == TCC_OUTPUT_DLL) { | |
| 300 | − esym_index = get_sym_attr(s1, sym_index, 0)->dyn_index; | |
| 299 | + if (S->output_type == TCC_OUTPUT_DLL) { | |
| 300 | + esym_index = get_sym_attr(S, sym_index, 0)->dyn_index; | |
| 301 | 301 | qrel->r_offset = rel->r_offset; |
| 302 | 302 | if (esym_index) { |
| 303 | 303 | qrel->r_info = ELFW(R_INFO)(esym_index, R_RISCV_64); |
| @@ -199,40 +199,40 @@ static void print_dirs(const char *msg, char **paths, int nb_paths) · 198 unmodified lines | ||
| 199 | 199 | printf(" %s\n", paths[i]); |
| 200 | 200 | } |
| 201 | 201 | |
| 202 | −static void print_search_dirs(TCCState *s) | |
| 202 | +static void print_search_dirs(TCCState *S) | |
| 203 | 203 | { |
| 204 | − printf("install: %s\n", s->tcc_lib_path); | |
| 204 | + printf("install: %s\n", S->tcc_lib_path); | |
| 205 | 205 | /* print_dirs("programs", NULL, 0); */ |
| 206 | − print_dirs("include", s->sysinclude_paths, s->nb_sysinclude_paths); | |
| 207 | − print_dirs("libraries", s->library_paths, s->nb_library_paths); | |
| 206 | + print_dirs("include", S->sysinclude_paths, S->nb_sysinclude_paths); | |
| 207 | + print_dirs("libraries", S->library_paths, S->nb_library_paths); | |
| 208 | 208 | #ifdef TCC_TARGET_PE |
| 209 | − printf("libtcc1:\n %s/lib/"TCC_LIBTCC1"\n", s->tcc_lib_path); | |
| 209 | + printf("libtcc1:\n %s/lib/"TCC_LIBTCC1"\n", S->tcc_lib_path); | |
| 210 | 210 | #else |
| 211 | − printf("libtcc1:\n %s/"TCC_LIBTCC1"\n", s->tcc_lib_path); | |
| 212 | − print_dirs("crt", s->crt_paths, s->nb_crt_paths); | |
| 213 | − printf("elfinterp:\n %s\n", DEFAULT_ELFINTERP(s)); | |
| 211 | + printf("libtcc1:\n %s/"TCC_LIBTCC1"\n", S->tcc_lib_path); | |
| 212 | + print_dirs("crt", S->crt_paths, S->nb_crt_paths); | |
| 213 | + printf("elfinterp:\n %s\n", DEFAULT_ELFINTERP(S)); | |
| 214 | 214 | #endif |
| 215 | 215 | } |
| 216 | 216 | |
| 217 | −static void set_environment(TCCState *s) | |
| 217 | +static void set_environment(TCCState *S) | |
| 218 | 218 | { |
| 219 | 219 | char * path; |
| 220 | 220 | |
| 221 | 221 | path = getenv("C_INCLUDE_PATH"); |
| 222 | 222 | if(path != NULL) { |
| 223 | − tcc_add_sysinclude_path(s, path); | |
| 223 | + tcc_add_sysinclude_path(S, path); | |
| 224 | 224 | } |
| 225 | 225 | path = getenv("CPATH"); |
| 226 | 226 | if(path != NULL) { |
| 227 | − tcc_add_include_path(s, path); | |
| 227 | + tcc_add_include_path(S, path); | |
| 228 | 228 | } |
| 229 | 229 | path = getenv("LIBRARY_PATH"); |
| 230 | 230 | if(path != NULL) { |
| 231 | − tcc_add_library_path(s, path); | |
| 231 | + tcc_add_library_path(S, path); | |
| 232 | 232 | } |
| 233 | 233 | } |
| 234 | 234 | |
| 235 | −static char *default_outputfile(TCCState *s, const char *first_file) | |
| 235 | +static char *default_outputfile(TCCState *S, const char *first_file) | |
| 236 | 236 | { |
| 237 | 237 | char buf[1024]; |
| 238 | 238 | char *ext; |
| @@ -243,18 +243,18 @@ static char *default_outputfile(TCCState *s, const char *first_file) · 4 unmodified lines | ||
| 243 | 243 | snprintf(buf, sizeof(buf), "%s", name); |
| 244 | 244 | ext = tcc_fileextension(buf); |
| 245 | 245 | #ifdef TCC_TARGET_PE |
| 246 | − if (s->output_type == TCC_OUTPUT_DLL) | |
| 246 | + if (S->output_type == TCC_OUTPUT_DLL) | |
| 247 | 247 | strcpy(ext, ".dll"); |
| 248 | 248 | else |
| 249 | − if (s->output_type == TCC_OUTPUT_EXE) | |
| 249 | + if (S->output_type == TCC_OUTPUT_EXE) | |
| 250 | 250 | strcpy(ext, ".exe"); |
| 251 | 251 | else |
| 252 | 252 | #endif |
| 253 | − if ((s->just_deps || s->output_type == TCC_OUTPUT_OBJ) && !s->option_r && *ext) | |
| 253 | + if ((S->just_deps || S->output_type == TCC_OUTPUT_OBJ) && !S->option_r && *ext) | |
| 254 | 254 | strcpy(ext, ".o"); |
| 255 | 255 | else |
| 256 | 256 | strcpy(buf, "a.out"); |
| 257 | − return tcc_strdup(buf); | |
| 257 | + return tcc_strdup(S, buf); | |
| 258 | 258 | } |
| 259 | 259 | |
| 260 | 260 | static unsigned getclock_ms(void) |
| @@ -268,9 +268,101 @@ static unsigned getclock_ms(void) · 7 unmodified lines | ||
| 268 | 268 | #endif |
| 269 | 269 | } |
| 270 | 270 | |
| 271 | +#ifdef WITH_ATTACHMENTS | |
| 272 | +#include "tcc_attachments.h" | |
| 273 | +#define ATTACH_PREFIX "/_attach_" | |
| 274 | + | |
| 275 | +static vio_module_t vio_module; | |
| 276 | + | |
| 277 | +typedef struct vio_memfile_t { | |
| 278 | + off_t size; | |
| 279 | + off_t pos; | |
| 280 | + const unsigned char *mem; | |
| 281 | +} vio_memfile_t; | |
| 282 | + | |
| 283 | +static int vio_mem_open(vio_fd *fd, const char *fn, int oflag) { | |
| 284 | + //printf("%d:%s\n", fd->fd, fn); | |
| 285 | + if(fd->vio_module && strncmp(ATTACH_PREFIX, fn, sizeof(ATTACH_PREFIX)-1) == 0){ | |
| 286 | + int i, count = sizeof(bin2c_filesAttached)/sizeof(bin2c_filesAttached_st); | |
| 287 | + for(i=0; i < count; ++i) { | |
| 288 | + //printf("%s:%s\n", fn, bin2c_filesAttached[i].file_name); | |
| 289 | + if(strcmp(fn, bin2c_filesAttached[i].file_name) == 0) { | |
| 290 | + vio_memfile_t *mf = (vio_memfile_t*)tcc_malloc(S, fd->vio_module->tcc_state); | |
| 291 | + mf->mem = bin2c_filesAttached[i].sym_name; | |
| 292 | + mf->size = bin2c_filesAttached[i].size; | |
| 293 | + mf->pos = 0; | |
| 294 | + fd->fd = 1; | |
| 295 | + fd->vio_udata = mf; | |
| 296 | + //printf("%d:%s\n", fd->fd, fn); | |
| 297 | + return fd->fd; | |
| 298 | + } | |
| 299 | + } | |
| 300 | + } | |
| 301 | + return -1; | |
| 302 | +} | |
| 303 | + | |
| 304 | +static off_t vio_mem_lseek(vio_fd fd, off_t offset, int whence) { | |
| 305 | + if(fd.vio_udata) { | |
| 306 | + off_t loffset = 0; | |
| 307 | + vio_memfile_t *mf = (vio_memfile_t*)fd.vio_udata; | |
| 308 | + if (whence == SEEK_CUR) | |
| 309 | + loffset = mf->pos + offset; | |
| 310 | + else if (whence == SEEK_SET) | |
| 311 | + loffset = offset; | |
| 312 | + else if (whence == SEEK_END) | |
| 313 | + loffset = ((off_t)mf->size) + offset; | |
| 314 | + | |
| 315 | + if (loffset < 0 && loffset > mf->size) | |
| 316 | + return -1; | |
| 317 | + | |
| 318 | + mf->pos = loffset; | |
| 319 | + | |
| 320 | + return mf->pos; | |
| 321 | + } | |
| 322 | + return lseek(fd.fd, offset, whence); | |
| 323 | +} | |
| 324 | + | |
| 325 | +static size_t vio_mem_read(vio_fd fd, void *buf, size_t bytes) { | |
| 326 | + if(fd.vio_udata) { | |
| 327 | + vio_memfile_t *mf = (vio_memfile_t*)fd.vio_udata; | |
| 328 | + if( (mf->pos + bytes) > mf->size) { | |
| 329 | + long bc = mf->size - mf->pos; | |
| 330 | + if(bc > 0) { | |
| 331 | + memcpy(buf, mf->mem + mf->pos, bc); | |
| 332 | + mf->pos = mf->size; | |
| 333 | + return bc; | |
| 334 | + } | |
| 335 | + return 0; | |
| 336 | + } | |
| 337 | + memcpy(buf, mf->mem + mf->pos, bytes); | |
| 338 | + mf->pos += bytes; | |
| 339 | + return bytes; | |
| 340 | + } | |
| 341 | + return 0; | |
| 342 | +} | |
| 343 | + | |
| 344 | +static int vio_mem_close(vio_fd *fd) { | |
| 345 | + if(fd->vio_udata){ | |
| 346 | + tcc_free(S, fd->vio_udata); | |
| 347 | + } | |
| 348 | + return 0; | |
| 349 | +} | |
| 350 | + | |
| 351 | +void set_vio_module(TCCState *S){ | |
| 352 | + vio_module.user_data = NULL; | |
| 353 | + vio_module.call_vio_open_flags = CALL_VIO_OPEN_FIRST; | |
| 354 | + vio_module.vio_open = &vio_mem_open; | |
| 355 | + vio_module.vio_lseek = &vio_mem_lseek; | |
| 356 | + vio_module.vio_read = &vio_mem_read; | |
| 357 | + vio_module.vio_close = &vio_mem_close; | |
| 358 | + tcc_set_vio_module(s, &vio_module); | |
| 359 | +} | |
| 360 | + | |
| 361 | +#endif | |
| 362 | + | |
| 271 | 363 | int main(int argc0, char **argv0) |
| 272 | 364 | { |
| 273 | − TCCState *s, *s1; | |
| 365 | + TCCState *S, *s1; | |
| 274 | 366 | int ret, opt, n = 0, t = 0, done; |
| 275 | 367 | unsigned start_time = 0, end_time = 0; |
| 276 | 368 | const char *first_file; |
| @@ -279,13 +371,19 @@ int main(int argc0, char **argv0) · 2 unmodified lines | ||
| 279 | 371 | |
| 280 | 372 | redo: |
| 281 | 373 | argc = argc0, argv = argv0; |
| 282 | − s = s1 = tcc_new(); | |
| 283 | − opt = tcc_parse_args(s, &argc, &argv, 1); | |
| 374 | + S = s1 = tcc_new(); | |
| 375 | + opt = tcc_parse_args(S, &argc, &argv, 1); | |
| 376 | + | |
| 377 | +#ifdef WITH_ATTACHMENTS | |
| 378 | + tcc_set_lib_path(S, ATTACH_PREFIX); | |
| 379 | + tcc_add_include_path(S, ATTACH_PREFIX); | |
| 380 | + set_vio_module(S); | |
| 381 | +#endif | |
| 284 | 382 | |
| 285 | 383 | if (n == 0) { |
| 286 | 384 | if (opt == OPT_HELP) { |
| 287 | 385 | fputs(help, stdout); |
| 288 | − if (!s->verbose) | |
| 386 | + if (!S->verbose) | |
| 289 | 387 | return 0; |
| 290 | 388 | ++opt; |
| 291 | 389 | } |
| @@ -294,57 +392,57 @@ redo: · 2 unmodified lines | ||
| 294 | 392 | return 0; |
| 295 | 393 | } |
| 296 | 394 | if (opt == OPT_M32 || opt == OPT_M64) |
| 297 | − tcc_tool_cross(s, argv, opt); /* never returns */ | |
| 298 | − if (s->verbose) | |
| 395 | + tcc_tool_cross(S, argv, opt); /* never returns */ | |
| 396 | + if (S->verbose) | |
| 299 | 397 | printf(version); |
| 300 | 398 | if (opt == OPT_AR) |
| 301 | − return tcc_tool_ar(s, argc, argv); | |
| 399 | + return tcc_tool_ar(S, argc, argv); | |
| 302 | 400 | #ifdef TCC_TARGET_PE |
| 303 | 401 | if (opt == OPT_IMPDEF) |
| 304 | − return tcc_tool_impdef(s, argc, argv); | |
| 402 | + return tcc_tool_impdef(S, argc, argv); | |
| 305 | 403 | #endif |
| 306 | 404 | if (opt == OPT_V) |
| 307 | 405 | return 0; |
| 308 | 406 | if (opt == OPT_PRINT_DIRS) { |
| 309 | 407 | /* initialize search dirs */ |
| 310 | − set_environment(s); | |
| 311 | − tcc_set_output_type(s, TCC_OUTPUT_MEMORY); | |
| 312 | − print_search_dirs(s); | |
| 408 | + set_environment(S); | |
| 409 | + tcc_set_output_type(S, TCC_OUTPUT_MEMORY); | |
| 410 | + print_search_dirs(S); | |
| 313 | 411 | return 0; |
| 314 | 412 | } |
| 315 | 413 | |
| 316 | − if (s->nb_files == 0) | |
| 317 | − tcc_error("no input files"); | |
| 414 | + if (S->nb_files == 0) | |
| 415 | + tcc_error(S, "no input files"); | |
| 318 | 416 | |
| 319 | − if (s->output_type == TCC_OUTPUT_PREPROCESS) { | |
| 320 | − if (s->outfile && 0!=strcmp("-",s->outfile)) { | |
| 321 | − ppfp = fopen(s->outfile, "w"); | |
| 417 | + if (S->output_type == TCC_OUTPUT_PREPROCESS) { | |
| 418 | + if (S->outfile && 0!=strcmp("-",S->outfile)) { | |
| 419 | + ppfp = fopen(S->outfile, "w"); | |
| 322 | 420 | if (!ppfp) |
| 323 | − tcc_error("could not write '%s'", s->outfile); | |
| 421 | + tcc_error(S, "could not write '%s'", S->outfile); | |
| 324 | 422 | } |
| 325 | − } else if (s->output_type == TCC_OUTPUT_OBJ && !s->option_r) { | |
| 326 | − if (s->nb_libraries) | |
| 327 | − tcc_error("cannot specify libraries with -c"); | |
| 328 | − if (s->nb_files > 1 && s->outfile) | |
| 329 | − tcc_error("cannot specify output file with -c many files"); | |
| 423 | + } else if (S->output_type == TCC_OUTPUT_OBJ && !S->option_r) { | |
| 424 | + if (S->nb_libraries) | |
| 425 | + tcc_error(S, "cannot specify libraries with -c"); | |
| 426 | + if (S->nb_files > 1 && S->outfile) | |
| 427 | + tcc_error(S, "cannot specify output file with -c many files"); | |
| 330 | 428 | } |
| 331 | 429 | |
| 332 | − if (s->do_bench) | |
| 430 | + if (S->do_bench) | |
| 333 | 431 | start_time = getclock_ms(); |
| 334 | 432 | } |
| 335 | 433 | |
| 336 | − set_environment(s); | |
| 337 | − if (s->output_type == 0) | |
| 338 | − s->output_type = TCC_OUTPUT_EXE; | |
| 339 | − tcc_set_output_type(s, s->output_type); | |
| 340 | − s->ppfp = ppfp; | |
| 434 | + set_environment(S); | |
| 435 | + if (S->output_type == 0) | |
| 436 | + S->output_type = TCC_OUTPUT_EXE; | |
| 437 | + tcc_set_output_type(S, S->output_type); | |
| 438 | + S->ppfp = ppfp; | |
| 341 | 439 | |
| 342 | − if ((s->output_type == TCC_OUTPUT_MEMORY | |
| 343 | − || s->output_type == TCC_OUTPUT_PREPROCESS) | |
| 344 | − && (s->dflag & 16)) { /* -dt option */ | |
| 440 | + if ((S->output_type == TCC_OUTPUT_MEMORY | |
| 441 | + || S->output_type == TCC_OUTPUT_PREPROCESS) | |
| 442 | + && (S->dflag & TCC_OPTION_d_t)) { /* -dt option */ | |
| 345 | 443 | if (t) |
| 346 | − s->dflag |= 32; | |
| 347 | − s->run_test = ++t; | |
| 444 | + S->dflag |= TCC_OPTION_d_32; | |
| 445 | + S->run_test = ++t; | |
| 348 | 446 | if (n) |
| 349 | 447 | --n; |
| 350 | 448 | } |
| @@ -352,48 +450,48 @@ redo: · 1 unmodified line | ||
| 352 | 450 | /* compile or add each files or library */ |
| 353 | 451 | first_file = NULL, ret = 0; |
| 354 | 452 | do { |
| 355 | − struct filespec *f = s->files[n]; | |
| 356 | − s->filetype = f->type; | |
| 453 | + struct filespec *f = S->files[n]; | |
| 454 | + S->filetype = f->type; | |
| 357 | 455 | if (f->type & AFF_TYPE_LIB) { |
| 358 | − if (tcc_add_library_err(s, f->name) < 0) | |
| 456 | + if (tcc_add_library_err(S, f->name) < 0) | |
| 359 | 457 | ret = 1; |
| 360 | 458 | } else { |
| 361 | − if (1 == s->verbose) | |
| 459 | + if (1 == S->verbose) | |
| 362 | 460 | printf("-> %s\n", f->name); |
| 363 | 461 | if (!first_file) |
| 364 | 462 | first_file = f->name; |
| 365 | − if (tcc_add_file(s, f->name) < 0) | |
| 463 | + if (tcc_add_file(S, f->name) < 0) | |
| 366 | 464 | ret = 1; |
| 367 | 465 | } |
| 368 | − done = ret || ++n >= s->nb_files; | |
| 369 | − } while (!done && (s->output_type != TCC_OUTPUT_OBJ || s->option_r)); | |
| 466 | + done = ret || ++n >= S->nb_files; | |
| 467 | + } while (!done && (S->output_type != TCC_OUTPUT_OBJ || S->option_r)); | |
| 370 | 468 | |
| 371 | − if (s->do_bench) | |
| 469 | + if (S->do_bench) | |
| 372 | 470 | end_time = getclock_ms(); |
| 373 | 471 | |
| 374 | − if (s->run_test) { | |
| 472 | + if (S->run_test) { | |
| 375 | 473 | t = 0; |
| 376 | − } else if (s->output_type == TCC_OUTPUT_PREPROCESS) { | |
| 474 | + } else if (S->output_type == TCC_OUTPUT_PREPROCESS) { | |
| 377 | 475 | ; |
| 378 | 476 | } else if (0 == ret) { |
| 379 | − if (s->output_type == TCC_OUTPUT_MEMORY) { | |
| 477 | + if (S->output_type == TCC_OUTPUT_MEMORY) { | |
| 380 | 478 | #ifdef TCC_IS_NATIVE |
| 381 | − ret = tcc_run(s, argc, argv); | |
| 479 | + ret = tcc_run(S, argc, argv); | |
| 382 | 480 | #endif |
| 383 | 481 | } else { |
| 384 | − if (!s->outfile) | |
| 385 | − s->outfile = default_outputfile(s, first_file); | |
| 386 | − if (!s->just_deps && tcc_output_file(s, s->outfile)) | |
| 482 | + if (!S->outfile) | |
| 483 | + S->outfile = default_outputfile(S, first_file); | |
| 484 | + if (!S->just_deps && tcc_output_file(S, S->outfile)) | |
| 387 | 485 | ret = 1; |
| 388 | − else if (s->gen_deps) | |
| 389 | − gen_makedeps(s, s->outfile, s->deps_outfile); | |
| 486 | + else if (S->gen_deps) | |
| 487 | + gen_makedeps(S, S->outfile, S->deps_outfile); | |
| 390 | 488 | } |
| 391 | 489 | } |
| 392 | 490 | |
| 393 | − if (done && 0 == t && 0 == ret && s->do_bench) | |
| 394 | − tcc_print_stats(s, end_time - start_time); | |
| 491 | + if (done && 0 == t && 0 == ret && S->do_bench) | |
| 492 | + tcc_print_stats(S, end_time - start_time); | |
| 395 | 493 | |
| 396 | − tcc_delete(s); | |
| 494 | + tcc_delete(S); | |
| 397 | 495 | if (!done) |
| 398 | 496 | goto redo; /* compile more files with -c */ |
| 399 | 497 | if (t) |
| @@ -585,7 +585,7 @@ typedef struct Section { · 584 unmodified lines | ||
| 585 | 585 | unsigned long data_offset; /* current data offset */ |
| 586 | 586 | unsigned char *data; /* section data */ |
| 587 | 587 | unsigned long data_allocated; /* used for realloc() handling */ |
| 588 | − TCCState *s1; | |
| 588 | + TCCState *S; | |
| 589 | 589 | int sh_name; /* elf section name (only used during output) */ |
| 590 | 590 | int sh_num; /* elf section number */ |
| 591 | 591 | int sh_type; /* elf section type */ |
| @@ -743,6 +743,78 @@ struct sym_attr { · 151 unmodified lines | ||
| 743 | 743 | #endif |
| 744 | 744 | }; |
| 745 | 745 | |
| 746 | +/*From tccpp.c*/ | |
| 747 | +typedef struct TinyAlloc { | |
| 748 | + unsigned limit; | |
| 749 | + unsigned size; | |
| 750 | + uint8_t *buffer; | |
| 751 | + uint8_t *p; | |
| 752 | + unsigned nb_allocs; | |
| 753 | + struct TinyAlloc *next, *top; | |
| 754 | +#ifdef TAL_INFO | |
| 755 | + unsigned nb_peak; | |
| 756 | + unsigned nb_total; | |
| 757 | + unsigned nb_missed; | |
| 758 | + uint8_t *peak_p; | |
| 759 | +#endif | |
| 760 | +} TinyAlloc; | |
| 761 | + | |
| 762 | +/*From tccgen.c*/ | |
| 763 | +typedef struct scope_t { | |
| 764 | + struct scope_t *prev; | |
| 765 | + struct { int loc, locorig, num; } vla; | |
| 766 | + struct { Sym *s; int n; } cl; | |
| 767 | + int *bsym, *csym; | |
| 768 | + Sym *lstk, *llstk; | |
| 769 | +} scope_t; | |
| 770 | + | |
| 771 | +typedef struct switch_t { | |
| 772 | + struct case_t { | |
| 773 | + int64_t v1, v2; | |
| 774 | + int sym; | |
| 775 | + } **p; int n; /* list of case ranges */ | |
| 776 | + int def_sym; /* default symbol */ | |
| 777 | + int *bsym; | |
| 778 | + scope_t *scope; | |
| 779 | + struct switch_t *prev; | |
| 780 | + SValue sv; | |
| 781 | +} switch_t; | |
| 782 | + | |
| 783 | +#define MAX_TEMP_LOCAL_VARIABLE_NUMBER 8 | |
| 784 | +/*list of temporary local variables on the stack in current function. */ | |
| 785 | +typedef struct temp_local_variable_t { | |
| 786 | + int location; //offset on stack. Svalue.c.i | |
| 787 | + short size; | |
| 788 | + short align; | |
| 789 | +} temp_local_variable_t; | |
| 790 | + | |
| 791 | +typedef struct { | |
| 792 | + unsigned long offset; | |
| 793 | + unsigned long last_file_name; | |
| 794 | + unsigned long last_func_name; | |
| 795 | + int ind; | |
| 796 | + int line; | |
| 797 | +} tcov_data_t; | |
| 798 | + | |
| 799 | +typedef struct { | |
| 800 | + int debug_type; | |
| 801 | + Sym *type; | |
| 802 | +} debug_hash_t; | |
| 803 | + | |
| 804 | +typedef struct debug_info_t { | |
| 805 | + int start; | |
| 806 | + int end; | |
| 807 | + int n_sym; | |
| 808 | + struct debug_sym { | |
| 809 | + int type; | |
| 810 | + unsigned long value; | |
| 811 | + char *str; | |
| 812 | + Section *sec; | |
| 813 | + int sym_index; | |
| 814 | + } *sym; | |
| 815 | + struct debug_info_t *child, *next, *last, *parent; | |
| 816 | +} debug_info_t; | |
| 817 | + | |
| 746 | 818 | struct TCCState { |
| 747 | 819 | unsigned char verbose; /* if true, display some information during compilation */ |
| 748 | 820 | unsigned char nostdinc; /* if true, no standard headers are added */ |
| @@ -927,11 +999,11 @@ struct TCCState { · 178 unmodified lines | ||
| 927 | 999 | int nb_sym_attrs; |
| 928 | 1000 | /* ptr to next reloc entry reused */ |
| 929 | 1001 | ElfW_Rel *qrel; |
| 930 | − #define qrel s1->qrel | |
| 1002 | + #define qrel S->qrel | |
| 931 | 1003 | |
| 932 | 1004 | #ifdef TCC_TARGET_RISCV64 |
| 933 | 1005 | struct pcrel_hi { addr_t addr, val; } last_hi; |
| 934 | − #define last_hi s1->last_hi | |
| 1006 | + #define last_hi S->last_hi | |
| 935 | 1007 | #endif |
| 936 | 1008 | |
| 937 | 1009 | #ifdef TCC_TARGET_PE |
| @@ -962,6 +1034,10 @@ struct TCCState { · 24 unmodified lines | ||
| 962 | 1034 | const char *runtime_main; |
| 963 | 1035 | void **runtime_mem; |
| 964 | 1036 | int nb_runtime_mem; |
| 1037 | +# ifdef HAVE_SELINUX | |
| 1038 | + void *write_mem; | |
| 1039 | + unsigned long mem_size; | |
| 1040 | +# endif | |
| 965 | 1041 | #endif |
| 966 | 1042 | |
| 967 | 1043 | #ifdef CONFIG_TCC_BACKTRACE |
| @@ -991,6 +1067,117 @@ struct TCCState { · 23 unmodified lines | ||
| 991 | 1067 | char *deps_outfile; /* option -MF */ |
| 992 | 1068 | int argc; |
| 993 | 1069 | char **argv; |
| 1070 | + | |
| 1071 | + /* Entries needed to make it reentrant */ | |
| 1072 | + vio_module_t *vio_module; | |
| 1073 | + | |
| 1074 | + /* ------------ tccpp.c ------------ */ | |
| 1075 | + | |
| 1076 | + struct BufferedFile *tccpp_file; | |
| 1077 | + int tccpp_ch, tccpp_tok; | |
| 1078 | + CValue tccpp_tokc; | |
| 1079 | + const int *tccpp_macro_ptr; | |
| 1080 | + int tccpp_parse_flags; | |
| 1081 | + int tccpp_tok_flags; | |
| 1082 | + CString tccpp_tokcstr; /* current parsed string, if any */ | |
| 1083 | + CString tccpp_cstr_buf; | |
| 1084 | + CString tccpp_macro_equal_buf; | |
| 1085 | + TokenString tccpp_tokstr_buf; | |
| 1086 | + TokenString *tccpp_macro_stack; | |
| 1087 | + | |
| 1088 | + /* display benchmark infos */ | |
| 1089 | + int tccpp_total_lines; | |
| 1090 | + int tccpp_total_bytes; | |
| 1091 | + int tccpp_tok_ident; | |
| 1092 | + TokenSym **tccpp_table_ident; | |
| 1093 | + | |
| 1094 | + int *tccpp_macro_ptr_allocated; | |
| 1095 | + const int *tccpp_unget_saved_macro_ptr; | |
| 1096 | + int tccpp_unget_saved_buffer[TOK_MAX_SIZE + 1]; | |
| 1097 | + int tccpp_unget_buffer_enabled; | |
| 1098 | + TokenSym *tccpp_hash_ident[TOK_HASH_SIZE]; | |
| 1099 | + char tccpp_token_buf[STRING_MAX_SIZE + 1]; | |
| 1100 | + /* true if isid(c) || isnum(c) */ | |
| 1101 | + unsigned char tccpp_isidnum_table[256-CH_EOF]; | |
| 1102 | + | |
| 1103 | + int tccpp_pp_debug_tok, tccpp_pp_debug_symv; | |
| 1104 | + int tccpp_pp_once; | |
| 1105 | + int tccpp_pp_expr; | |
| 1106 | + int tccpp_pp_counter; | |
| 1107 | + | |
| 1108 | + TinyAlloc *tccpp_toksym_alloc; | |
| 1109 | + TinyAlloc *tccpp_tokstr_alloc; | |
| 1110 | + | |
| 1111 | + /*----------- tccasm.c --------*/ | |
| 1112 | + Section *tccasm_last_text_section; /* to handle .previous asm directive */ | |
| 1113 | + | |
| 1114 | + /* ------------ tccgen.c ------------ */ | |
| 1115 | + | |
| 1116 | + Sym *tccgen_global_stack; | |
| 1117 | + Sym *tccgen_local_stack; | |
| 1118 | + Sym *tccgen_local_label_stack; | |
| 1119 | + Sym *tccgen_global_label_stack; | |
| 1120 | + Sym *tccgen_define_stack; | |
| 1121 | + CType tccgen_int_type, tccgen_func_old_type, tccgen_char_type, tccgen_char_pointer_type; | |
| 1122 | + SValue *tccgen_vtop; | |
| 1123 | + SValue tccgen__vstack[1 + VSTACK_SIZE]; | |
| 1124 | + int tccgen_rsym, tccgen_anon_sym, tccgen_ind, tccgen_loc; | |
| 1125 | + char tccgen_debug_modes; | |
| 1126 | + | |
| 1127 | + int tccgen_const_wanted; /* true if constant wanted */ | |
| 1128 | + int tccgen_nocode_wanted; /* true if no code generation wanted for an expression */ | |
| 1129 | + int tccgen_global_expr; /* true if compound literals must be allocated globally (used during initializers parsing */ | |
| 1130 | + CType tccgen_func_vt; /* current function return type (used by return instruction) */ | |
| 1131 | + int tccgen_func_var; /* true if current function is variadic */ | |
| 1132 | + int tccgen_func_vc; | |
| 1133 | + const char *tccgen_funcname; | |
| 1134 | + | |
| 1135 | + Sym *tccgen_sym_free_first; | |
| 1136 | + void **tccgen_sym_pools; | |
| 1137 | + int tccgen_nb_sym_pools; | |
| 1138 | + Sym *tccgen_all_cleanups, *tccgen_pending_gotos; | |
| 1139 | + int tccgen_local_scope; | |
| 1140 | + int tccgen_in_sizeof; | |
| 1141 | + int tccgen_in_generic; | |
| 1142 | + int tccgen_section_sym; | |
| 1143 | + | |
| 1144 | + int tccgen_last_line_num, tccgen_new_file, tccgen_func_ind; /* debug info control */ | |
| 1145 | + CString tccgen_initstr; | |
| 1146 | + | |
| 1147 | + switch_t *tccgen_cur_switch; /* current switch */ | |
| 1148 | + | |
| 1149 | + temp_local_variable_t tccgen_arr_temp_local_vars[MAX_TEMP_LOCAL_VARIABLE_NUMBER]; | |
| 1150 | + int tccgen_nb_temp_local_vars; | |
| 1151 | + | |
| 1152 | + scope_t *tccgen_cur_scope, *tccgen_loop_scope, *tccgen_root_scope; | |
| 1153 | + | |
| 1154 | + tcov_data_t tccgen_tcov_data; | |
| 1155 | + int tccgen_debug_next_type; | |
| 1156 | + debug_hash_t *tccgen_debug_hash; | |
| 1157 | + int tccgen_n_debug_hash; | |
| 1158 | + debug_info_t *tccgen_debug_info, *tccgen_debug_info_root; | |
| 1159 | + | |
| 1160 | + unsigned char tccgen_prec[256]; | |
| 1161 | + | |
| 1162 | + /*--------armg-gen.c-----------*/ | |
| 1163 | +/*#if defined(TCC_ARM_EABI) && defined(TCC_ARM_VFP)*/ | |
| 1164 | + CType armgen_float_type, armgen_double_type, armgen_func_float_type, armgen_func_double_type; | |
| 1165 | +/*#endif*/ | |
| 1166 | + | |
| 1167 | + /*------- tccrun.c ------------*/ | |
| 1168 | + | |
| 1169 | + /*--------x86_64-gen.c --------*/ | |
| 1170 | + unsigned long x86_64_gen_func_sub_sp_offset; | |
| 1171 | + int x86_64_gen_func_ret_sub; | |
| 1172 | +#if defined(CONFIG_TCC_BCHECK) | |
| 1173 | + addr_t func_bound_offset; | |
| 1174 | + unsigned long func_bound_ind; | |
| 1175 | + int func_bound_add_epilog; | |
| 1176 | +#endif | |
| 1177 | +#ifdef TCC_TARGET_PE | |
| 1178 | + int x86_64_gen_func_scratch, x86_64_gen_func_alloca; | |
| 1179 | +#endif | |
| 1180 | + | |
| 994 | 1181 | }; |
| 995 | 1182 | |
| 996 | 1183 | struct filespec { |
| @@ -1174,7 +1361,7 @@ enum tcc_token { · 177 unmodified lines | ||
| 1174 | 1361 | |
| 1175 | 1362 | /* ------------ libtcc.c ------------ */ |
| 1176 | 1363 | |
| 1177 | −ST_DATA struct TCCState *tcc_state; | |
| 1364 | +//ST_DATA struct TCCState *S; | |
| 1178 | 1365 | |
| 1179 | 1366 | /* public functions currently used by the tcc main function */ |
| 1180 | 1367 | ST_FUNC char *pstrcpy(char *buf, size_t buf_size, const char *s); |
| @@ -1183,53 +1370,56 @@ ST_FUNC char *pstrncpy(char *out, const char *in, size_t num); · 2 unmodified lines | ||
| 1183 | 1370 | PUB_FUNC char *tcc_basename(const char *name); |
| 1184 | 1371 | PUB_FUNC char *tcc_fileextension (const char *name); |
| 1185 | 1372 | |
| 1373 | +PUB_FUNC void tcc_free_base(void *ptr); | |
| 1374 | +PUB_FUNC void *tcc_malloc_base(unsigned long size); | |
| 1375 | +PUB_FUNC void *tcc_mallocz_base(unsigned long size); | |
| 1186 | 1376 | #ifndef MEM_DEBUG |
| 1187 | −PUB_FUNC void tcc_free(void *ptr); | |
| 1188 | −PUB_FUNC void *tcc_malloc(unsigned long size); | |
| 1189 | −PUB_FUNC void *tcc_mallocz(unsigned long size); | |
| 1190 | −PUB_FUNC void *tcc_realloc(void *ptr, unsigned long size); | |
| 1191 | −PUB_FUNC char *tcc_strdup(const char *str); | |
| 1377 | +PUB_FUNC void tcc_free(TCCState* S, void *ptr); | |
| 1378 | +PUB_FUNC void *tcc_malloc(TCCState* S, unsigned long size); | |
| 1379 | +PUB_FUNC void *tcc_mallocz(TCCState* S, unsigned long size); | |
| 1380 | +PUB_FUNC void *tcc_realloc(TCCState* S, void *ptr, unsigned long size); | |
| 1381 | +PUB_FUNC char *tcc_strdup(TCCState* S, const char *str); | |
| 1192 | 1382 | #else |
| 1193 | −#define tcc_free(ptr) tcc_free_debug(ptr) | |
| 1194 | −#define tcc_malloc(size) tcc_malloc_debug(size, __FILE__, __LINE__) | |
| 1195 | −#define tcc_mallocz(size) tcc_mallocz_debug(size, __FILE__, __LINE__) | |
| 1196 | −#define tcc_realloc(ptr,size) tcc_realloc_debug(ptr, size, __FILE__, __LINE__) | |
| 1197 | −#define tcc_strdup(str) tcc_strdup_debug(str, __FILE__, __LINE__) | |
| 1198 | −PUB_FUNC void tcc_free_debug(void *ptr); | |
| 1199 | −PUB_FUNC void *tcc_malloc_debug(unsigned long size, const char *file, int line); | |
| 1200 | −PUB_FUNC void *tcc_mallocz_debug(unsigned long size, const char *file, int line); | |
| 1201 | −PUB_FUNC void *tcc_realloc_debug(void *ptr, unsigned long size, const char *file, int line); | |
| 1202 | −PUB_FUNC char *tcc_strdup_debug(const char *str, const char *file, int line); | |
| 1203 | −#endif | |
| 1204 | − | |
| 1205 | −#define free(p) use_tcc_free(p) | |
| 1206 | −#define malloc(s) use_tcc_malloc(s) | |
| 1207 | −#define realloc(p, s) use_tcc_realloc(p, s) | |
| 1383 | +#define tcc_free(s, ptr) tcc_free_debug(s, ptr) | |
| 1384 | +#define tcc_malloc(s, size) tcc_malloc_debug(s, size, __FILE__, __LINE__) | |
| 1385 | +#define tcc_mallocz(s, size) tcc_mallocz_debug(s, size, __FILE__, __LINE__) | |
| 1386 | +#define tcc_realloc(s, ptr, size) tcc_realloc_debug(s, ptr, size, __FILE__, __LINE__) | |
| 1387 | +#define tcc_strdup(s, str) tcc_strdup_debug(s, str, __FILE__, __LINE__) | |
| 1388 | +PUB_FUNC void tcc_free_debug(TCCState* S, void *ptr); | |
| 1389 | +PUB_FUNC void *tcc_malloc_debug(TCCState* S, unsigned long size, const char *file, int line); | |
| 1390 | +PUB_FUNC void *tcc_mallocz_debug(TCCState* S, unsigned long size, const char *file, int line); | |
| 1391 | +PUB_FUNC void *tcc_realloc_debug(TCCState* S, void *ptr, unsigned long size, const char *file, int line); | |
| 1392 | +PUB_FUNC char *tcc_strdup_debug(TCCState* S, const char *str, const char *file, int line); | |
| 1393 | +#endif | |
| 1394 | + | |
| 1395 | +#define free(p) use_tcc_free(S, p) | |
| 1396 | +#define malloc(s) use_tcc_malloc(S, s) | |
| 1397 | +#define realloc(p, s) use_tcc_realloc(S, p, s) | |
| 1208 | 1398 | #undef strdup |
| 1209 | −#define strdup(s) use_tcc_strdup(s) | |
| 1210 | −PUB_FUNC void _tcc_error_noabort(const char *fmt, ...) PRINTF_LIKE(1,2); | |
| 1211 | −PUB_FUNC NORETURN void _tcc_error(const char *fmt, ...) PRINTF_LIKE(1,2); | |
| 1212 | −PUB_FUNC void _tcc_warning(const char *fmt, ...) PRINTF_LIKE(1,2); | |
| 1213 | −#define tcc_internal_error(msg) tcc_error("internal compiler error\n"\ | |
| 1399 | +#define strdup(s) use_tcc_strdup(S, s) | |
| 1400 | +PUB_FUNC void _tcc_error_noabort(TCCState* S, const char *fmt, ...) PRINTF_LIKE(2,3); | |
| 1401 | +PUB_FUNC NORETURN void _tcc_error(TCCState* S, const char *fmt, ...) PRINTF_LIKE(2,3); | |
| 1402 | +PUB_FUNC void _tcc_warning(TCCState* S, const char *fmt, ...) PRINTF_LIKE(2,3); | |
| 1403 | +#define tcc_internal_error(S, msg) tcc_error(S, "internal compiler error\n"\ | |
| 1214 | 1404 | "%s:%d: in %s(): " msg, __FILE__,__LINE__,__FUNCTION__) |
| 1215 | 1405 | |
| 1216 | 1406 | /* other utilities */ |
| 1217 | −ST_FUNC void dynarray_add(void *ptab, int *nb_ptr, void *data); | |
| 1218 | −ST_FUNC void dynarray_reset(void *pp, int *n); | |
| 1219 | −ST_INLN void cstr_ccat(CString *cstr, int ch); | |
| 1220 | −ST_FUNC void cstr_cat(CString *cstr, const char *str, int len); | |
| 1221 | −ST_FUNC void cstr_wccat(CString *cstr, int ch); | |
| 1222 | −ST_FUNC void cstr_new(CString *cstr); | |
| 1223 | −ST_FUNC void cstr_free(CString *cstr); | |
| 1224 | −ST_FUNC int cstr_printf(CString *cs, const char *fmt, ...) PRINTF_LIKE(2,3); | |
| 1225 | −ST_FUNC int cstr_vprintf(CString *cstr, const char *fmt, va_list ap); | |
| 1407 | +ST_FUNC void dynarray_add(TCCState* S, void *ptab, int *nb_ptr, void *data); | |
| 1408 | +ST_FUNC void dynarray_reset(TCCState* S, void *pp, int *n); | |
| 1409 | +ST_INLN void cstr_ccat(TCCState* S, CString *cstr, int ch); | |
| 1410 | +ST_FUNC void cstr_cat(TCCState* S, CString *cstr, const char *str, int len); | |
| 1411 | +ST_FUNC void cstr_wccat(TCCState* S, CString *cstr, int ch); | |
| 1412 | +ST_FUNC void cstr_new(TCCState* S, CString *cstr); | |
| 1413 | +ST_FUNC void cstr_free(TCCState* S, CString *cstr); | |
| 1414 | +ST_FUNC int cstr_printf(TCCState* S, CString *cs, const char *fmt, ...) PRINTF_LIKE(3,4); | |
| 1415 | +ST_FUNC int cstr_vprintf(TCCState* S, CString *cstr, const char *fmt, va_list ap); | |
| 1226 | 1416 | ST_FUNC void cstr_reset(CString *cstr); |
| 1227 | 1417 | |
| 1228 | −ST_FUNC void tcc_open_bf(TCCState *s1, const char *filename, int initlen); | |
| 1229 | −ST_FUNC int tcc_open(TCCState *s1, const char *filename); | |
| 1230 | −ST_FUNC void tcc_close(void); | |
| 1418 | +ST_FUNC void tcc_open_bf(TCCState *S, const char *filename, int initlen); | |
| 1419 | +ST_FUNC int tcc_open(TCCState *S, const char *filename); | |
| 1420 | +ST_FUNC void tcc_close(TCCState *S); | |
| 1231 | 1421 | |
| 1232 | −ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags); | |
| 1422 | +ST_FUNC int tcc_add_file_internal(TCCState *S, const char *filename, int flags); | |
| 1233 | 1423 | /* flags: */ |
| 1234 | 1424 | #define AFF_PRINT_ERROR 0x10 /* print error if file not found */ |
| 1235 | 1425 | #define AFF_REFERENCED_DLL 0x20 /* load a referenced dll from another dll */ |
| @@ -1249,26 +1439,26 @@ ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags) · 13 unmodified lines | ||
| 1249 | 1439 | #define AFF_BINTYPE_C67 4 |
| 1250 | 1440 | |
| 1251 | 1441 | #ifndef ELF_OBJ_ONLY |
| 1252 | −ST_FUNC int tcc_add_crt(TCCState *s, const char *filename); | |
| 1442 | +ST_FUNC int tcc_add_crt(TCCState *S, const char *filename); | |
| 1253 | 1443 | #endif |
| 1254 | 1444 | #ifndef TCC_TARGET_MACHO |
| 1255 | −ST_FUNC int tcc_add_dll(TCCState *s, const char *filename, int flags); | |
| 1445 | +ST_FUNC int tcc_add_dll(TCCState *S, const char *filename, int flags); | |
| 1256 | 1446 | #endif |
| 1257 | 1447 | #ifdef CONFIG_TCC_BCHECK |
| 1258 | −ST_FUNC void tcc_add_bcheck(TCCState *s1); | |
| 1448 | +ST_FUNC void tcc_add_bcheck(TCCState *S); | |
| 1259 | 1449 | #endif |
| 1260 | 1450 | #ifdef CONFIG_TCC_BACKTRACE |
| 1261 | −ST_FUNC void tcc_add_btstub(TCCState *s1); | |
| 1451 | +ST_FUNC void tcc_add_btstub(TCCState *S); | |
| 1262 | 1452 | #endif |
| 1263 | −ST_FUNC void tcc_add_pragma_libs(TCCState *s1); | |
| 1264 | −PUB_FUNC int tcc_add_library_err(TCCState *s, const char *f); | |
| 1265 | −PUB_FUNC void tcc_print_stats(TCCState *s, unsigned total_time); | |
| 1266 | −PUB_FUNC int tcc_parse_args(TCCState *s, int *argc, char ***argv, int optind); | |
| 1453 | +ST_FUNC void tcc_add_pragma_libs(TCCState *S); | |
| 1454 | +PUB_FUNC int tcc_add_library_err(TCCState *S, const char *f); | |
| 1455 | +PUB_FUNC void tcc_print_stats(TCCState *S, unsigned total_time); | |
| 1456 | +PUB_FUNC int tcc_parse_args(TCCState *S, int *argc, char ***argv, int optind); | |
| 1267 | 1457 | #ifdef _WIN32 |
| 1268 | 1458 | ST_FUNC char *normalize_slashes(char *path); |
| 1269 | 1459 | #endif |
| 1270 | −ST_FUNC DLLReference *tcc_add_dllref(TCCState *s1, const char *dllname); | |
| 1271 | −ST_FUNC char *tcc_load_text(int fd); | |
| 1460 | +ST_FUNC DLLReference *tcc_add_dllref(TCCState *S, const char *dllname); | |
| 1461 | +ST_FUNC char *tcc_load_text(TCCState *S, int fd); | |
| 1272 | 1462 | |
| 1273 | 1463 | /* tcc_parse_args return codes: */ |
| 1274 | 1464 | #define OPT_HELP 1 |
| @@ -1282,18 +1472,6 @@ ST_FUNC char *tcc_load_text(int fd); · 7 unmodified lines | ||
| 1282 | 1472 | |
| 1283 | 1473 | /* ------------ tccpp.c ------------ */ |
| 1284 | 1474 | |
| 1285 | −ST_DATA struct BufferedFile *file; | |
| 1286 | −ST_DATA int ch, tok; | |
| 1287 | −ST_DATA CValue tokc; | |
| 1288 | −ST_DATA const int *macro_ptr; | |
| 1289 | −ST_DATA int parse_flags; | |
| 1290 | −ST_DATA int tok_flags; | |
| 1291 | −ST_DATA CString tokcstr; /* current parsed string, if any */ | |
| 1292 | − | |
| 1293 | −/* display benchmark infos */ | |
| 1294 | −ST_DATA int tok_ident; | |
| 1295 | −ST_DATA TokenSym **table_ident; | |
| 1296 | − | |
| 1297 | 1475 | #define TOK_FLAG_BOL 0x0001 /* beginning of line before */ |
| 1298 | 1476 | #define TOK_FLAG_BOF 0x0002 /* beginning of file before */ |
| 1299 | 1477 | #define TOK_FLAG_ENDIF 0x0004 /* a endif was found matching starting #ifdef */ |
| @@ -1321,36 +1499,36 @@ enum line_macro_output_format { · 21 unmodified lines | ||
| 1321 | 1499 | LINE_MACRO_OUTPUT_FORMAT_P10 = 11 |
| 1322 | 1500 | }; |
| 1323 | 1501 | |
| 1324 | −ST_FUNC TokenSym *tok_alloc(const char *str, int len); | |
| 1325 | −ST_FUNC int tok_alloc_const(const char *str); | |
| 1326 | −ST_FUNC const char *get_tok_str(int v, CValue *cv); | |
| 1327 | −ST_FUNC void begin_macro(TokenString *str, int alloc); | |
| 1328 | −ST_FUNC void end_macro(void); | |
| 1329 | −ST_FUNC int set_idnum(int c, int val); | |
| 1502 | +ST_FUNC TokenSym *tok_alloc(TCCState* S, const char *str, int len); | |
| 1503 | +ST_FUNC int tok_alloc_const(TCCState* S, const char *str); | |
| 1504 | +ST_FUNC const char *get_tok_str(TCCState* S, int v, CValue *cv); | |
| 1505 | +ST_FUNC void begin_macro(TCCState* S, TokenString *str, int alloc); | |
| 1506 | +ST_FUNC void end_macro(TCCState* S); | |
| 1507 | +ST_FUNC int set_idnum(TCCState* S, int c, int val); | |
| 1330 | 1508 | ST_INLN void tok_str_new(TokenString *s); |
| 1331 | −ST_FUNC TokenString *tok_str_alloc(void); | |
| 1332 | −ST_FUNC void tok_str_free(TokenString *s); | |
| 1333 | −ST_FUNC void tok_str_free_str(int *str); | |
| 1334 | −ST_FUNC void tok_str_add(TokenString *s, int t); | |
| 1335 | −ST_FUNC void tok_str_add_tok(TokenString *s); | |
| 1336 | −ST_INLN void define_push(int v, int macro_type, int *str, Sym *first_arg); | |
| 1337 | −ST_FUNC void define_undef(Sym *s); | |
| 1338 | −ST_INLN Sym *define_find(int v); | |
| 1339 | −ST_FUNC void free_defines(Sym *b); | |
| 1340 | −ST_FUNC Sym *label_find(int v); | |
| 1341 | −ST_FUNC Sym *label_push(Sym **ptop, int v, int flags); | |
| 1342 | −ST_FUNC void label_pop(Sym **ptop, Sym *slast, int keep); | |
| 1343 | −ST_FUNC void parse_define(void); | |
| 1344 | −ST_FUNC void preprocess(int is_bof); | |
| 1345 | −ST_FUNC void next(void); | |
| 1346 | −ST_INLN void unget_tok(int last_tok); | |
| 1347 | −ST_FUNC void preprocess_start(TCCState *s1, int filetype); | |
| 1348 | −ST_FUNC void preprocess_end(TCCState *s1); | |
| 1349 | −ST_FUNC void tccpp_new(TCCState *s); | |
| 1350 | −ST_FUNC void tccpp_delete(TCCState *s); | |
| 1351 | −ST_FUNC int tcc_preprocess(TCCState *s1); | |
| 1352 | −ST_FUNC void skip(int c); | |
| 1353 | −ST_FUNC NORETURN void expect(const char *msg); | |
| 1509 | +ST_FUNC TokenString *tok_str_alloc(TCCState* S); | |
| 1510 | +ST_FUNC void tok_str_free(TCCState* S, TokenString *s); | |
| 1511 | +ST_FUNC void tok_str_free_str(TCCState* S, int *str); | |
| 1512 | +ST_FUNC void tok_str_add(TCCState* S, TokenString *s, int t); | |
| 1513 | +ST_FUNC void tok_str_add_tok(TCCState* S, TokenString *s); | |
| 1514 | +ST_INLN void define_push(TCCState* S, int v, int macro_type, int *str, Sym *first_arg); | |
| 1515 | +ST_FUNC void define_undef(TCCState* S, Sym *s); | |
| 1516 | +ST_INLN Sym *define_find(TCCState* S, int v); | |
| 1517 | +ST_FUNC void free_defines(TCCState* S, Sym *b); | |
| 1518 | +ST_FUNC Sym *label_find(TCCState* S, int v); | |
| 1519 | +ST_FUNC Sym *label_push(TCCState* S, Sym **ptop, int v, int flags); | |
| 1520 | +ST_FUNC void label_pop(TCCState* S, Sym **ptop, Sym *slast, int keep); | |
| 1521 | +ST_FUNC void parse_define(TCCState* S); | |
| 1522 | +ST_FUNC void preprocess(TCCState* S, int is_bof); | |
| 1523 | +ST_FUNC void next(TCCState* S); | |
| 1524 | +ST_INLN void unget_tok(TCCState* S, int last_tok); | |
| 1525 | +ST_FUNC void preprocess_start(TCCState *S, int filetype); | |
| 1526 | +ST_FUNC void preprocess_end(TCCState *S); | |
| 1527 | +ST_FUNC void tccpp_new(TCCState *S); | |
| 1528 | +ST_FUNC void tccpp_delete(TCCState *S); | |
| 1529 | +ST_FUNC int tcc_preprocess(TCCState *S); | |
| 1530 | +ST_FUNC void skip(TCCState* S, int c); | |
| 1531 | +ST_FUNC NORETURN void expect(TCCState* S, const char *msg); | |
| 1354 | 1532 | |
| 1355 | 1533 | /* space excluding newline */ |
| 1356 | 1534 | static inline int is_space(int ch) { |
| @@ -1372,104 +1550,85 @@ static inline int toup(int c) { · 15 unmodified lines | ||
| 1372 | 1550 | /* ------------ tccgen.c ------------ */ |
| 1373 | 1551 | |
| 1374 | 1552 | #define SYM_POOL_NB (8192 / sizeof(Sym)) |
| 1553 | +ST_FUNC void tcc_debug_start(TCCState *S); | |
| 1554 | +ST_FUNC void tcc_debug_end(TCCState *S); | |
| 1555 | +ST_FUNC void tcc_debug_bincl(TCCState *S); | |
| 1556 | +ST_FUNC void tcc_debug_eincl(TCCState *S); | |
| 1557 | +ST_FUNC void tcc_debug_putfile(TCCState *S, const char *filename); | |
| 1375 | 1558 | |
| 1376 | −ST_DATA Sym *global_stack; | |
| 1377 | −ST_DATA Sym *local_stack; | |
| 1378 | −ST_DATA Sym *local_label_stack; | |
| 1379 | −ST_DATA Sym *global_label_stack; | |
| 1380 | −ST_DATA Sym *define_stack; | |
| 1381 | −ST_DATA CType int_type, func_old_type, char_pointer_type; | |
| 1382 | −ST_DATA SValue *vtop; | |
| 1383 | −ST_DATA int rsym, anon_sym, ind, loc; | |
| 1384 | −ST_DATA char debug_modes; | |
| 1385 | − | |
| 1386 | −ST_DATA int const_wanted; /* true if constant wanted */ | |
| 1387 | −ST_DATA int nocode_wanted; /* true if no code generation wanted for an expression */ | |
| 1388 | −ST_DATA int global_expr; /* true if compound literals must be allocated globally (used during initializers parsing */ | |
| 1389 | −ST_DATA CType func_vt; /* current function return type (used by return instruction) */ | |
| 1390 | −ST_DATA int func_var; /* true if current function is variadic */ | |
| 1391 | −ST_DATA int func_vc; | |
| 1392 | −ST_DATA const char *funcname; | |
| 1393 | − | |
| 1394 | −ST_FUNC void tcc_debug_start(TCCState *s1); | |
| 1395 | −ST_FUNC void tcc_debug_end(TCCState *s1); | |
| 1396 | −ST_FUNC void tcc_debug_bincl(TCCState *s1); | |
| 1397 | −ST_FUNC void tcc_debug_eincl(TCCState *s1); | |
| 1398 | −ST_FUNC void tcc_debug_putfile(TCCState *s1, const char *filename); | |
| 1399 | − | |
| 1400 | −ST_FUNC void tccgen_init(TCCState *s1); | |
| 1401 | −ST_FUNC int tccgen_compile(TCCState *s1); | |
| 1402 | −ST_FUNC void tccgen_finish(TCCState *s1); | |
| 1403 | −ST_FUNC void check_vstack(void); | |
| 1559 | +ST_FUNC void tccgen_init(TCCState *S); | |
| 1560 | +ST_FUNC int tccgen_compile(TCCState *S); | |
| 1561 | +ST_FUNC void tccgen_finish(TCCState *S); | |
| 1562 | +ST_FUNC void check_vstack(TCCState* S); | |
| 1404 | 1563 | |
| 1405 | 1564 | ST_INLN int is_float(int t); |
| 1406 | 1565 | ST_FUNC int ieee_finite(double d); |
| 1407 | 1566 | ST_FUNC int exact_log2p1(int i); |
| 1408 | −ST_FUNC void test_lvalue(void); | |
| 1567 | +ST_FUNC void test_lvalue(TCCState* S); | |
| 1409 | 1568 | |
| 1410 | −ST_FUNC ElfSym *elfsym(Sym *); | |
| 1411 | −ST_FUNC void update_storage(Sym *sym); | |
| 1412 | −ST_FUNC void put_extern_sym2(Sym *sym, int sh_num, addr_t value, unsigned long size, int can_add_underscore); | |
| 1413 | −ST_FUNC void put_extern_sym(Sym *sym, Section *section, addr_t value, unsigned long size); | |
| 1569 | +ST_FUNC ElfSym *elfsym(TCCState* S, Sym *); | |
| 1570 | +ST_FUNC void update_storage(TCCState* S, Sym *sym); | |
| 1571 | +ST_FUNC void put_extern_sym2(TCCState* S, Sym *sym, int sh_num, addr_t value, unsigned long size, int can_add_underscore); | |
| 1572 | +ST_FUNC void put_extern_sym(TCCState* S, Sym *sym, Section *section, addr_t value, unsigned long size); | |
| 1414 | 1573 | #if PTR_SIZE == 4 |
| 1415 | −ST_FUNC void greloc(Section *s, Sym *sym, unsigned long offset, int type); | |
| 1574 | +ST_FUNC void greloc(TCCState* S, Section *s, Sym *sym, unsigned long offset, int type); | |
| 1416 | 1575 | #endif |
| 1417 | −ST_FUNC void greloca(Section *s, Sym *sym, unsigned long offset, int type, addr_t addend); | |
| 1576 | +ST_FUNC void greloca(TCCState* S, Section *s, Sym *sym, unsigned long offset, int type, addr_t addend); | |
| 1418 | 1577 | |
| 1419 | −ST_INLN void sym_free(Sym *sym); | |
| 1420 | −ST_FUNC Sym *sym_push(int v, CType *type, int r, int c); | |
| 1421 | −ST_FUNC void sym_pop(Sym **ptop, Sym *b, int keep); | |
| 1422 | −ST_FUNC Sym *sym_push2(Sym **ps, int v, int t, int c); | |
| 1578 | +ST_INLN void sym_free(TCCState* S, Sym *sym); | |
| 1579 | +ST_FUNC Sym *sym_push(TCCState* S, int v, CType *type, int r, int c); | |
| 1580 | +ST_FUNC void sym_pop(TCCState* S, Sym **ptop, Sym *b, int keep); | |
| 1581 | +ST_FUNC Sym *sym_push2(TCCState* S, Sym **ps, int v, int t, int c); | |
| 1423 | 1582 | ST_FUNC Sym *sym_find2(Sym *s, int v); |
| 1424 | −ST_INLN Sym *sym_find(int v); | |
| 1425 | −ST_INLN Sym *struct_find(int v); | |
| 1426 | − | |
| 1427 | −ST_FUNC Sym *global_identifier_push(int v, int t, int c); | |
| 1428 | −ST_FUNC Sym *external_global_sym(int v, CType *type); | |
| 1429 | −ST_FUNC Sym *external_helper_sym(int v); | |
| 1430 | −ST_FUNC void vpush_helper_func(int v); | |
| 1431 | −ST_FUNC void vset(CType *type, int r, int v); | |
| 1432 | −ST_FUNC void vset_VT_CMP(int op); | |
| 1433 | −ST_FUNC void vpushi(int v); | |
| 1434 | −ST_FUNC void vpushv(SValue *v); | |
| 1435 | −ST_FUNC void vpushsym(CType *type, Sym *sym); | |
| 1436 | −ST_FUNC void vswap(void); | |
| 1437 | −ST_FUNC void vrote(SValue *e, int n); | |
| 1438 | −ST_FUNC void vrott(int n); | |
| 1439 | −ST_FUNC void vrotb(int n); | |
| 1440 | −ST_FUNC void vpop(void); | |
| 1583 | +ST_INLN Sym *sym_find(TCCState* S, int v); | |
| 1584 | +ST_INLN Sym *struct_find(TCCState* S, int v); | |
| 1585 | + | |
| 1586 | +ST_FUNC Sym *global_identifier_push(TCCState* S, int v, int t, int c); | |
| 1587 | +ST_FUNC Sym *external_global_sym(TCCState* S, int v, CType *type); | |
| 1588 | +ST_FUNC Sym *external_helper_sym(TCCState* S, int v); | |
| 1589 | +ST_FUNC void vpush_helper_func(TCCState* S, int v); | |
| 1590 | +ST_FUNC void vset(TCCState* S, CType *type, int r, int v); | |
| 1591 | +ST_FUNC void vset_VT_CMP(TCCState* S, int op); | |
| 1592 | +ST_FUNC void vpushi(TCCState* S, int v); | |
| 1593 | +ST_FUNC void vpushv(TCCState* S, SValue *v); | |
| 1594 | +ST_FUNC void vpushsym(TCCState* S, CType *type, Sym *sym); | |
| 1595 | +ST_FUNC void vswap(TCCState* S); | |
| 1596 | +ST_FUNC void vrote(TCCState* S, SValue *e, int n); | |
| 1597 | +ST_FUNC void vrott(TCCState* S, int n); | |
| 1598 | +ST_FUNC void vrotb(TCCState* S, int n); | |
| 1599 | +ST_FUNC void vpop(TCCState* S); | |
| 1441 | 1600 | #if PTR_SIZE == 4 |
| 1442 | −ST_FUNC void lexpand(void); | |
| 1601 | +ST_FUNC void lexpand(TCCState* S); | |
| 1443 | 1602 | #endif |
| 1444 | 1603 | #ifdef TCC_TARGET_ARM |
| 1445 | −ST_FUNC int get_reg_ex(int rc, int rc2); | |
| 1446 | −#endif | |
| 1447 | −ST_FUNC void save_reg(int r); | |
| 1448 | −ST_FUNC void save_reg_upstack(int r, int n); | |
| 1449 | −ST_FUNC int get_reg(int rc); | |
| 1450 | −ST_FUNC void save_regs(int n); | |
| 1451 | −ST_FUNC void gaddrof(void); | |
| 1452 | −ST_FUNC int gv(int rc); | |
| 1453 | −ST_FUNC void gv2(int rc1, int rc2); | |
| 1454 | −ST_FUNC void gen_op(int op); | |
| 1604 | +ST_FUNC int get_reg_ex(TCCState* S, int rc, int rc2); | |
| 1605 | +#endif | |
| 1606 | +ST_FUNC void save_reg(TCCState* S, int r); | |
| 1607 | +ST_FUNC void save_reg_upstack(TCCState* S, int r, int n); | |
| 1608 | +ST_FUNC int get_reg(TCCState* S, int rc); | |
| 1609 | +ST_FUNC void save_regs(TCCState* S, int n); | |
| 1610 | +ST_FUNC void gaddrof(TCCState* S); | |
| 1611 | +ST_FUNC int gv(TCCState* S, int rc); | |
| 1612 | +ST_FUNC void gv2(TCCState* S, int rc1, int rc2); | |
| 1613 | +ST_FUNC void gen_op(TCCState* S, int op); | |
| 1455 | 1614 | ST_FUNC int type_size(CType *type, int *a); |
| 1456 | −ST_FUNC void mk_pointer(CType *type); | |
| 1457 | −ST_FUNC void vstore(void); | |
| 1458 | −ST_FUNC void inc(int post, int c); | |
| 1459 | −ST_FUNC void parse_mult_str (CString *astr, const char *msg); | |
| 1460 | −ST_FUNC void parse_asm_str(CString *astr); | |
| 1461 | −ST_FUNC void indir(void); | |
| 1462 | −ST_FUNC void unary(void); | |
| 1463 | −ST_FUNC void gexpr(void); | |
| 1464 | −ST_FUNC int expr_const(void); | |
| 1615 | +ST_FUNC void mk_pointer(TCCState* S, CType *type); | |
| 1616 | +ST_FUNC void vstore(TCCState* S); | |
| 1617 | +ST_FUNC void inc(TCCState* S, int post, int c); | |
| 1618 | +ST_FUNC void parse_mult_str (TCCState* S, CString *astr, const char *msg); | |
| 1619 | +ST_FUNC void parse_asm_str(TCCState* S, CString *astr); | |
| 1620 | +ST_FUNC void indir(TCCState* S); | |
| 1621 | +ST_FUNC void unary(TCCState* S); | |
| 1622 | +ST_FUNC void gexpr(TCCState* S); | |
| 1623 | +ST_FUNC int expr_const(TCCState* S); | |
| 1465 | 1624 | #if defined CONFIG_TCC_BCHECK || defined TCC_TARGET_C67 |
| 1466 | −ST_FUNC Sym *get_sym_ref(CType *type, Section *sec, unsigned long offset, unsigned long size); | |
| 1625 | +ST_FUNC Sym *get_sym_ref(TCCState* S, CType *type, Section *sec, unsigned long offset, unsigned long size); | |
| 1467 | 1626 | #endif |
| 1468 | 1627 | #if defined TCC_TARGET_X86_64 && !defined TCC_TARGET_PE |
| 1469 | 1628 | ST_FUNC int classify_x86_64_va_arg(CType *ty); |
| 1470 | 1629 | #endif |
| 1471 | 1630 | #ifdef CONFIG_TCC_BCHECK |
| 1472 | −ST_FUNC void gbound_args(int nb_args); | |
| 1631 | +ST_FUNC void gbound_args(TCCState* S, int nb_args); | |
| 1473 | 1632 | ST_DATA int func_bound_add_epilog; |
| 1474 | 1633 | #endif |
| 1475 | 1634 | |
| @@ -1489,51 +1648,51 @@ typedef struct { · 13 unmodified lines | ||
| 1489 | 1648 | unsigned int n_value; /* value of symbol */ |
| 1490 | 1649 | } Stab_Sym; |
| 1491 | 1650 | |
| 1492 | −ST_FUNC void tccelf_new(TCCState *s); | |
| 1493 | −ST_FUNC void tccelf_delete(TCCState *s); | |
| 1494 | −ST_FUNC void tccelf_stab_new(TCCState *s); | |
| 1495 | −ST_FUNC void tccelf_begin_file(TCCState *s1); | |
| 1496 | −ST_FUNC void tccelf_end_file(TCCState *s1); | |
| 1651 | +ST_FUNC void tccelf_new(TCCState *S); | |
| 1652 | +ST_FUNC void tccelf_delete(TCCState *S); | |
| 1653 | +ST_FUNC void tccelf_stab_new(TCCState *S); | |
| 1654 | +ST_FUNC void tccelf_begin_file(TCCState *S); | |
| 1655 | +ST_FUNC void tccelf_end_file(TCCState *S); | |
| 1497 | 1656 | #ifdef CONFIG_TCC_BCHECK |
| 1498 | −ST_FUNC void tccelf_bounds_new(TCCState *s); | |
| 1499 | −#endif | |
| 1500 | −ST_FUNC Section *new_section(TCCState *s1, const char *name, int sh_type, int sh_flags); | |
| 1501 | −ST_FUNC void section_realloc(Section *sec, unsigned long new_size); | |
| 1502 | −ST_FUNC size_t section_add(Section *sec, addr_t size, int align); | |
| 1503 | −ST_FUNC void *section_ptr_add(Section *sec, addr_t size); | |
| 1504 | −ST_FUNC Section *find_section(TCCState *s1, const char *name); | |
| 1505 | −ST_FUNC Section *new_symtab(TCCState *s1, const char *symtab_name, int sh_type, int sh_flags, const char *strtab_name, const char *hash_name, int hash_sh_flags); | |
| 1506 | − | |
| 1507 | −ST_FUNC int put_elf_str(Section *s, const char *sym); | |
| 1508 | −ST_FUNC int put_elf_sym(Section *s, addr_t value, unsigned long size, int info, int other, int shndx, const char *name); | |
| 1509 | −ST_FUNC int set_elf_sym(Section *s, addr_t value, unsigned long size, int info, int other, int shndx, const char *name); | |
| 1510 | −ST_FUNC int find_elf_sym(Section *s, const char *name); | |
| 1657 | +ST_FUNC void tccelf_bounds_new(TCCState *S); | |
| 1658 | +#endif | |
| 1659 | +ST_FUNC Section *new_section(TCCState *S, const char *name, int sh_type, int sh_flags); | |
| 1660 | +ST_FUNC void section_realloc(TCCState* S, Section *sec, unsigned long new_size); | |
| 1661 | +ST_FUNC size_t section_add(TCCState* S, Section *sec, addr_t size, int align); | |
| 1662 | +ST_FUNC void *section_ptr_add(TCCState* S, Section *sec, addr_t size); | |
| 1663 | +ST_FUNC Section *find_section(TCCState *S, const char *name); | |
| 1664 | +ST_FUNC Section *new_symtab(TCCState *S, const char *symtab_name, int sh_type, int sh_flags, const char *strtab_name, const char *hash_name, int hash_sh_flags); | |
| 1665 | + | |
| 1666 | +ST_FUNC int put_elf_str(TCCState* S, Section *s, const char *sym); | |
| 1667 | +ST_FUNC int put_elf_sym(TCCState* S, Section *s, addr_t value, unsigned long size, int info, int other, int shndx, const char *name); | |
| 1668 | +ST_FUNC int set_elf_sym(Section *S, addr_t value, unsigned long size, int info, int other, int shndx, const char *name); | |
| 1669 | +ST_FUNC int find_elf_sym(Section *S, const char *name); | |
| 1511 | 1670 | ST_FUNC void put_elf_reloc(Section *symtab, Section *s, unsigned long offset, int type, int symbol); |
| 1512 | 1671 | ST_FUNC void put_elf_reloca(Section *symtab, Section *s, unsigned long offset, int type, int symbol, addr_t addend); |
| 1513 | 1672 | |
| 1514 | −ST_FUNC void put_stabs(TCCState *s1, const char *str, int type, int other, int desc, unsigned long value); | |
| 1515 | −ST_FUNC void put_stabs_r(TCCState *s1, const char *str, int type, int other, int desc, unsigned long value, Section *sec, int sym_index); | |
| 1516 | −ST_FUNC void put_stabn(TCCState *s1, int type, int other, int desc, int value); | |
| 1673 | +ST_FUNC void put_stabs(TCCState *S, const char *str, int type, int other, int desc, unsigned long value); | |
| 1674 | +ST_FUNC void put_stabs_r(TCCState *S, const char *str, int type, int other, int desc, unsigned long value, Section *sec, int sym_index); | |
| 1675 | +ST_FUNC void put_stabn(TCCState *S, int type, int other, int desc, int value); | |
| 1517 | 1676 | |
| 1518 | −ST_FUNC void resolve_common_syms(TCCState *s1); | |
| 1519 | −ST_FUNC void relocate_syms(TCCState *s1, Section *symtab, int do_resolve); | |
| 1520 | −ST_FUNC void relocate_sections(TCCState *s1); | |
| 1677 | +ST_FUNC void resolve_common_syms(TCCState *S); | |
| 1678 | +ST_FUNC void relocate_syms(TCCState *S, Section *symtab, int do_resolve); | |
| 1679 | +ST_FUNC void relocate_sections(TCCState *S); | |
| 1521 | 1680 | |
| 1522 | 1681 | ST_FUNC ssize_t full_read(int fd, void *buf, size_t count); |
| 1523 | −ST_FUNC void *load_data(int fd, unsigned long file_offset, unsigned long size); | |
| 1682 | +ST_FUNC void *load_data(TCCState* S, int fd, unsigned long file_offset, unsigned long size); | |
| 1524 | 1683 | ST_FUNC int tcc_object_type(int fd, ElfW(Ehdr) *h); |
| 1525 | −ST_FUNC int tcc_load_object_file(TCCState *s1, int fd, unsigned long file_offset); | |
| 1526 | −ST_FUNC int tcc_load_archive(TCCState *s1, int fd, int alacarte); | |
| 1527 | −ST_FUNC void add_array(TCCState *s1, const char *sec, int c); | |
| 1684 | +ST_FUNC int tcc_load_object_file(TCCState *S, int fd, unsigned long file_offset); | |
| 1685 | +ST_FUNC int tcc_load_archive(TCCState *S, int fd, int alacarte); | |
| 1686 | +ST_FUNC void add_array(TCCState *S, const char *sec, int c); | |
| 1528 | 1687 | |
| 1529 | 1688 | #if !defined(ELF_OBJ_ONLY) || (defined(TCC_TARGET_MACHO) && defined TCC_IS_NATIVE) |
| 1530 | −ST_FUNC void build_got_entries(TCCState *s1); | |
| 1689 | +ST_FUNC void build_got_entries(TCCState *S); | |
| 1531 | 1690 | #endif |
| 1532 | −ST_FUNC struct sym_attr *get_sym_attr(TCCState *s1, int index, int alloc); | |
| 1533 | −ST_FUNC addr_t get_sym_addr(TCCState *s, const char *name, int err, int forc); | |
| 1534 | −ST_FUNC void list_elf_symbols(TCCState *s, void *ctx, | |
| 1691 | +ST_FUNC struct sym_attr *get_sym_attr(TCCState *S, int index, int alloc); | |
| 1692 | +ST_FUNC addr_t get_sym_addr(TCCState *S, const char *name, int err, int forc); | |
| 1693 | +ST_FUNC void list_elf_symbols(TCCState *S, void *ctx, | |
| 1535 | 1694 | void (*symbol_cb)(void *ctx, const char *name, const void *val)); |
| 1536 | −ST_FUNC int set_global_sym(TCCState *s1, const char *name, Section *sec, addr_t offs); | |
| 1695 | +ST_FUNC int set_global_sym(TCCState *S, const char *name, Section *sec, addr_t offs); | |
| 1537 | 1696 | |
| 1538 | 1697 | /* Browse each elem of type <type> in section <sec> starting at elem <startoff> |
| 1539 | 1698 | using variable <elem> */ |
| @@ -1542,11 +1701,11 @@ ST_FUNC int set_global_sym(TCCState *s1, const char *name, Section *sec, addr_t · 2 unmodified lines | ||
| 1542 | 1701 | elem < (type *) (sec->data + sec->data_offset); elem++) |
| 1543 | 1702 | |
| 1544 | 1703 | #ifndef ELF_OBJ_ONLY |
| 1545 | −ST_FUNC int tcc_load_dll(TCCState *s1, int fd, const char *filename, int level); | |
| 1546 | −ST_FUNC int tcc_load_ldscript(TCCState *s1, int fd); | |
| 1704 | +ST_FUNC int tcc_load_dll(TCCState *S, int fd, const char *filename, int level); | |
| 1705 | +ST_FUNC int tcc_load_ldscript(TCCState *S, int fd); | |
| 1547 | 1706 | #endif |
| 1548 | 1707 | #ifndef TCC_TARGET_PE |
| 1549 | −ST_FUNC void tcc_add_runtime(TCCState *s1); | |
| 1708 | +ST_FUNC void tcc_add_runtime(TCCState *S); | |
| 1550 | 1709 | #endif |
| 1551 | 1710 | |
| 1552 | 1711 | /* ------------ xxx-link.c ------------ */ |
| @@ -1564,41 +1723,41 @@ enum gotplt_entry { · 11 unmodified lines | ||
| 1564 | 1723 | ST_FUNC int code_reloc (int reloc_type); |
| 1565 | 1724 | ST_FUNC int gotplt_entry_type (int reloc_type); |
| 1566 | 1725 | #if !defined(TCC_TARGET_MACHO) || defined TCC_IS_NATIVE |
| 1567 | −ST_FUNC unsigned create_plt_entry(TCCState *s1, unsigned got_offset, struct sym_attr *attr); | |
| 1568 | −ST_FUNC void relocate_plt(TCCState *s1); | |
| 1726 | +ST_FUNC unsigned create_plt_entry(TCCState *S, unsigned got_offset, struct sym_attr *attr); | |
| 1727 | +ST_FUNC void relocate_plt(TCCState *S); | |
| 1569 | 1728 | #endif |
| 1570 | 1729 | #endif |
| 1571 | −ST_FUNC void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val); | |
| 1730 | +ST_FUNC void relocate(TCCState *S, ElfW_Rel *rel, int type, unsigned char *ptr, addr_t addr, addr_t val); | |
| 1572 | 1731 | |
| 1573 | 1732 | /* ------------ xxx-gen.c ------------ */ |
| 1574 | 1733 | ST_DATA const char * const target_machine_defs; |
| 1575 | 1734 | ST_DATA const int reg_classes[NB_REGS]; |
| 1576 | 1735 | |
| 1577 | −ST_FUNC void gsym_addr(int t, int a); | |
| 1578 | −ST_FUNC void gsym(int t); | |
| 1579 | −ST_FUNC void load(int r, SValue *sv); | |
| 1580 | −ST_FUNC void store(int r, SValue *v); | |
| 1736 | +ST_FUNC void gsym_addr(TCCState* S, int t, int a); | |
| 1737 | +ST_FUNC void gsym(TCCState* S, int t); | |
| 1738 | +ST_FUNC void load(TCCState *S, int r, SValue *sv); | |
| 1739 | +ST_FUNC void store(TCCState *S, int r, SValue *v); | |
| 1581 | 1740 | ST_FUNC int gfunc_sret(CType *vt, int variadic, CType *ret, int *align, int *regsize); |
| 1582 | −ST_FUNC void gfunc_call(int nb_args); | |
| 1583 | −ST_FUNC void gfunc_prolog(Sym *func_sym); | |
| 1584 | −ST_FUNC void gfunc_epilog(void); | |
| 1585 | −ST_FUNC void gen_fill_nops(int); | |
| 1586 | −ST_FUNC int gjmp(int t); | |
| 1587 | −ST_FUNC void gjmp_addr(int a); | |
| 1588 | −ST_FUNC int gjmp_cond(int op, int t); | |
| 1589 | −ST_FUNC int gjmp_append(int n, int t); | |
| 1590 | −ST_FUNC void gen_opi(int op); | |
| 1591 | −ST_FUNC void gen_opf(int op); | |
| 1592 | −ST_FUNC void gen_cvt_ftoi(int t); | |
| 1593 | −ST_FUNC void gen_cvt_itof(int t); | |
| 1594 | −ST_FUNC void gen_cvt_ftof(int t); | |
| 1595 | −ST_FUNC void ggoto(void); | |
| 1741 | +ST_FUNC void gfunc_call(TCCState *S, int nb_args); | |
| 1742 | +ST_FUNC void gfunc_prolog(TCCState *S, Sym *func_sym); | |
| 1743 | +ST_FUNC void gfunc_epilog(TCCState *S); | |
| 1744 | +ST_FUNC void gen_fill_nops(TCCState* S, int); | |
| 1745 | +ST_FUNC int gjmp(TCCState* S, int t); | |
| 1746 | +ST_FUNC void gjmp_addr(TCCState* S, int a); | |
| 1747 | +ST_FUNC int gjmp_cond(TCCState* S, int op, int t); | |
| 1748 | +ST_FUNC int gjmp_append(TCCState *S, int n, int t); | |
| 1749 | +ST_FUNC void gen_opi(TCCState* S, int op); | |
| 1750 | +ST_FUNC void gen_opf(TCCState* S, int op); | |
| 1751 | +ST_FUNC void gen_cvt_ftoi(TCCState *S, int t); | |
| 1752 | +ST_FUNC void gen_cvt_itof(TCCState *S, int t); | |
| 1753 | +ST_FUNC void gen_cvt_ftof(TCCState *S, int t); | |
| 1754 | +ST_FUNC void ggoto(TCCState *S); | |
| 1596 | 1755 | #ifndef TCC_TARGET_C67 |
| 1597 | −ST_FUNC void o(unsigned int c); | |
| 1756 | +ST_FUNC void o(TCCState* S, unsigned int c); | |
| 1598 | 1757 | #endif |
| 1599 | −ST_FUNC void gen_vla_sp_save(int addr); | |
| 1600 | −ST_FUNC void gen_vla_sp_restore(int addr); | |
| 1601 | −ST_FUNC void gen_vla_alloc(CType *type, int align); | |
| 1758 | +ST_FUNC void gen_vla_sp_save(TCCState* S, int addr); | |
| 1759 | +ST_FUNC void gen_vla_sp_restore(TCCState* S, int addr); | |
| 1760 | +ST_FUNC void gen_vla_alloc(TCCState* S, CType *type, int align); | |
| 1602 | 1761 | |
| 1603 | 1762 | static inline uint16_t read16le(unsigned char *p) { |
| 1604 | 1763 | return p[0] | (uint16_t)p[1] << 8; |
| @@ -1627,57 +1786,57 @@ static inline void add64le(unsigned char *p, int64_t x) { · 22 unmodified lines | ||
| 1627 | 1786 | |
| 1628 | 1787 | /* ------------ i386-gen.c ------------ */ |
| 1629 | 1788 | #if defined TCC_TARGET_I386 || defined TCC_TARGET_X86_64 || defined TCC_TARGET_ARM |
| 1630 | −ST_FUNC void g(int c); | |
| 1631 | −ST_FUNC void gen_le16(int c); | |
| 1632 | −ST_FUNC void gen_le32(int c); | |
| 1789 | +ST_FUNC void g(TCCState* S, int c); | |
| 1790 | +ST_FUNC void gen_le16(TCCState* S, int c); | |
| 1791 | +ST_FUNC void gen_le32(TCCState* S, int c); | |
| 1633 | 1792 | #endif |
| 1634 | 1793 | #if defined TCC_TARGET_I386 || defined TCC_TARGET_X86_64 |
| 1635 | −ST_FUNC void gen_addr32(int r, Sym *sym, int c); | |
| 1636 | −ST_FUNC void gen_addrpc32(int r, Sym *sym, int c); | |
| 1637 | −ST_FUNC void gen_cvt_csti(int t); | |
| 1638 | −ST_FUNC void gen_increment_tcov (SValue *sv); | |
| 1794 | +ST_FUNC void gen_addr32(TCCState* S, int r, Sym *sym, int c); | |
| 1795 | +ST_FUNC void gen_addrpc32(TCCState* S, int r, Sym *sym, int c); | |
| 1796 | +ST_FUNC void gen_cvt_csti(TCCState* S, int t); | |
| 1797 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv); | |
| 1639 | 1798 | #endif |
| 1640 | 1799 | |
| 1641 | 1800 | /* ------------ x86_64-gen.c ------------ */ |
| 1642 | 1801 | #ifdef TCC_TARGET_X86_64 |
| 1643 | −ST_FUNC void gen_addr64(int r, Sym *sym, int64_t c); | |
| 1644 | −ST_FUNC void gen_opl(int op); | |
| 1802 | +ST_FUNC void gen_addr64(TCCState* S, int r, Sym *sym, int64_t c); | |
| 1803 | +ST_FUNC void gen_opl(TCCState* S, int op); | |
| 1645 | 1804 | #ifdef TCC_TARGET_PE |
| 1646 | −ST_FUNC void gen_vla_result(int addr); | |
| 1805 | +ST_FUNC void gen_vla_result(TCCState* S, int addr); | |
| 1647 | 1806 | #endif |
| 1648 | −ST_FUNC void gen_cvt_sxtw(void); | |
| 1649 | −ST_FUNC void gen_cvt_csti(int t); | |
| 1807 | +ST_FUNC void gen_cvt_sxtw(TCCState *S); | |
| 1808 | +ST_FUNC void gen_cvt_csti(TCCState* S, int t); | |
| 1650 | 1809 | #endif |
| 1651 | 1810 | |
| 1652 | 1811 | /* ------------ arm-gen.c ------------ */ |
| 1653 | 1812 | #ifdef TCC_TARGET_ARM |
| 1654 | 1813 | #if defined(TCC_ARM_EABI) && !defined(CONFIG_TCC_ELFINTERP) |
| 1655 | −PUB_FUNC const char *default_elfinterp(struct TCCState *s); | |
| 1814 | +PUB_FUNC const char *default_elfinterp(TCCState *S); | |
| 1656 | 1815 | #endif |
| 1657 | −ST_FUNC void arm_init(struct TCCState *s); | |
| 1658 | −ST_FUNC void gen_increment_tcov (SValue *sv); | |
| 1816 | +ST_FUNC void arm_init(TCCState *S); | |
| 1817 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv); | |
| 1659 | 1818 | #endif |
| 1660 | 1819 | |
| 1661 | 1820 | /* ------------ arm64-gen.c ------------ */ |
| 1662 | 1821 | #ifdef TCC_TARGET_ARM64 |
| 1663 | −ST_FUNC void gen_opl(int op); | |
| 1664 | −ST_FUNC void gfunc_return(CType *func_type); | |
| 1665 | −ST_FUNC void gen_va_start(void); | |
| 1666 | −ST_FUNC void gen_va_arg(CType *t); | |
| 1667 | −ST_FUNC void gen_clear_cache(void); | |
| 1668 | −ST_FUNC void gen_cvt_sxtw(void); | |
| 1669 | −ST_FUNC void gen_cvt_csti(int t); | |
| 1670 | −ST_FUNC void gen_increment_tcov (SValue *sv); | |
| 1822 | +ST_FUNC void gen_opl(TCCState* S, int op); | |
| 1823 | +ST_FUNC void gfunc_return(TCCState *S, CType *func_type); | |
| 1824 | +ST_FUNC void gen_va_start(TCCState *S); | |
| 1825 | +ST_FUNC void gen_va_arg(TCCState *S, CType *t); | |
| 1826 | +ST_FUNC void gen_clear_cache(TCCState *S); | |
| 1827 | +ST_FUNC void gen_cvt_sxtw(TCCState *S); | |
| 1828 | +ST_FUNC void gen_cvt_csti(TCCState *S, int t); | |
| 1829 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv); | |
| 1671 | 1830 | #endif |
| 1672 | 1831 | |
| 1673 | 1832 | /* ------------ riscv64-gen.c ------------ */ |
| 1674 | 1833 | #ifdef TCC_TARGET_RISCV64 |
| 1675 | −ST_FUNC void gen_opl(int op); | |
| 1676 | −//ST_FUNC void gfunc_return(CType *func_type); | |
| 1677 | −ST_FUNC void gen_va_start(void); | |
| 1678 | −ST_FUNC void arch_transfer_ret_regs(int); | |
| 1679 | −ST_FUNC void gen_cvt_sxtw(void); | |
| 1680 | −ST_FUNC void gen_increment_tcov (SValue *sv); | |
| 1834 | +ST_FUNC void gen_opl(TCCState* S, int op); | |
| 1835 | +//ST_FUNC void gfunc_return(TCCState *S, CType *func_type); | |
| 1836 | +ST_FUNC void gen_va_start(TCCState *S); | |
| 1837 | +ST_FUNC void arch_transfer_ret_regs(TCCState* S, int); | |
| 1838 | +ST_FUNC void gen_cvt_sxtw(TCCState *S); | |
| 1839 | +ST_FUNC void gen_increment_tcov (TCCState* S, SValue *sv); | |
| 1681 | 1840 | #endif |
| 1682 | 1841 | |
| 1683 | 1842 | /* ------------ c67-gen.c ------------ */ |
| @@ -1687,44 +1846,44 @@ ST_FUNC void gen_increment_tcov (SValue *sv); · 3 unmodified lines | ||
| 1687 | 1846 | /* ------------ tcccoff.c ------------ */ |
| 1688 | 1847 | |
| 1689 | 1848 | #ifdef TCC_TARGET_COFF |
| 1690 | −ST_FUNC int tcc_output_coff(TCCState *s1, FILE *f); | |
| 1691 | −ST_FUNC int tcc_load_coff(TCCState * s1, int fd); | |
| 1849 | +ST_FUNC int tcc_output_coff(TCCState *S, FILE *f); | |
| 1850 | +ST_FUNC int tcc_load_coff(TCCState *S, int fd); | |
| 1692 | 1851 | #endif |
| 1693 | 1852 | |
| 1694 | 1853 | /* ------------ tccasm.c ------------ */ |
| 1695 | −ST_FUNC void asm_instr(void); | |
| 1696 | −ST_FUNC void asm_global_instr(void); | |
| 1697 | −ST_FUNC int tcc_assemble(TCCState *s1, int do_preprocess); | |
| 1854 | +ST_FUNC void asm_instr(TCCState* S); | |
| 1855 | +ST_FUNC void asm_global_instr(TCCState* S); | |
| 1856 | +ST_FUNC int tcc_assemble(TCCState *S, int do_preprocess); | |
| 1698 | 1857 | #ifdef CONFIG_TCC_ASM |
| 1699 | −ST_FUNC int find_constraint(ASMOperand *operands, int nb_operands, const char *name, const char **pp); | |
| 1700 | −ST_FUNC Sym* get_asm_sym(int name, Sym *csym); | |
| 1701 | −ST_FUNC void asm_expr(TCCState *s1, ExprValue *pe); | |
| 1702 | −ST_FUNC int asm_int_expr(TCCState *s1); | |
| 1858 | +ST_FUNC int find_constraint(TCCState* S, ASMOperand *operands, int nb_operands, const char *name, const char **pp); | |
| 1859 | +ST_FUNC Sym* get_asm_sym(TCCState* S, int name, Sym *csym); | |
| 1860 | +ST_FUNC void asm_expr(TCCState *S, ExprValue *pe); | |
| 1861 | +ST_FUNC int asm_int_expr(TCCState *S); | |
| 1703 | 1862 | /* ------------ i386-asm.c ------------ */ |
| 1704 | −ST_FUNC void gen_expr32(ExprValue *pe); | |
| 1863 | +ST_FUNC void gen_expr32(TCCState* S, ExprValue *pe); | |
| 1705 | 1864 | #ifdef TCC_TARGET_X86_64 |
| 1706 | −ST_FUNC void gen_expr64(ExprValue *pe); | |
| 1865 | +ST_FUNC void gen_expr64(TCCState* S, ExprValue *pe); | |
| 1707 | 1866 | #endif |
| 1708 | −ST_FUNC void asm_opcode(TCCState *s1, int opcode); | |
| 1709 | −ST_FUNC int asm_parse_regvar(int t); | |
| 1710 | −ST_FUNC void asm_compute_constraints(ASMOperand *operands, int nb_operands, int nb_outputs, const uint8_t *clobber_regs, int *pout_reg); | |
| 1711 | −ST_FUNC void subst_asm_operand(CString *add_str, SValue *sv, int modifier); | |
| 1712 | −ST_FUNC void asm_gen_code(ASMOperand *operands, int nb_operands, int nb_outputs, int is_output, uint8_t *clobber_regs, int out_reg); | |
| 1713 | −ST_FUNC void asm_clobber(uint8_t *clobber_regs, const char *str); | |
| 1867 | +ST_FUNC void asm_opcode(TCCState *S, int opcode); | |
| 1868 | +ST_FUNC int asm_parse_regvar(TCCState* S, int t); | |
| 1869 | +ST_FUNC void asm_compute_constraints(TCCState* S, ASMOperand *operands, int nb_operands, int nb_outputs, const uint8_t *clobber_regs, int *pout_reg); | |
| 1870 | +ST_FUNC void subst_asm_operand(TCCState* S, CString *add_str, SValue *sv, int modifier); | |
| 1871 | +ST_FUNC void asm_gen_code(TCCState* S, ASMOperand *operands, int nb_operands, int nb_outputs, int is_output, uint8_t *clobber_regs, int out_reg); | |
| 1872 | +ST_FUNC void asm_clobber(TCCState* S, uint8_t *clobber_regs, const char *str); | |
| 1714 | 1873 | #endif |
| 1715 | 1874 | |
| 1716 | 1875 | /* ------------ tccpe.c -------------- */ |
| 1717 | 1876 | #ifdef TCC_TARGET_PE |
| 1718 | −ST_FUNC int pe_load_file(struct TCCState *s1, int fd, const char *filename); | |
| 1719 | −ST_FUNC int pe_output_file(TCCState * s1, const char *filename); | |
| 1720 | −ST_FUNC int pe_putimport(TCCState *s1, int dllindex, const char *name, addr_t value); | |
| 1877 | +ST_FUNC int pe_load_file(struct TCCState *S, int fd, const char *filename); | |
| 1878 | +ST_FUNC int pe_output_file(TCCState * S, const char *filename); | |
| 1879 | +ST_FUNC int pe_putimport(TCCState *S, int dllindex, const char *name, addr_t value); | |
| 1721 | 1880 | #if defined TCC_TARGET_I386 || defined TCC_TARGET_X86_64 |
| 1722 | −ST_FUNC SValue *pe_getimport(SValue *sv, SValue *v2); | |
| 1881 | +ST_FUNC SValue *pe_getimport(TCCState * S, SValue *sv, SValue *v2); | |
| 1723 | 1882 | #endif |
| 1724 | 1883 | #ifdef TCC_TARGET_X86_64 |
| 1725 | −ST_FUNC void pe_add_unwind_data(unsigned start, unsigned end, unsigned stack); | |
| 1884 | +ST_FUNC void pe_add_unwind_data(TCCState* S, unsigned start, unsigned end, unsigned stack); | |
| 1726 | 1885 | #endif |
| 1727 | −PUB_FUNC int tcc_get_dllexports(const char *filename, char **pp); | |
| 1886 | +PUB_FUNC int tcc_get_dllexports(TCCState* S, const char *filename, char **pp); | |
| 1728 | 1887 | /* symbol properties stored in Elf32_Sym->st_other */ |
| 1729 | 1888 | # define ST_PE_EXPORT 0x10 |
| 1730 | 1889 | # define ST_PE_IMPORT 0x20 |
| @@ -1734,11 +1893,11 @@ PUB_FUNC int tcc_get_dllexports(const char *filename, char **pp); · 3 unmodified lines | ||
| 1734 | 1893 | |
| 1735 | 1894 | /* ------------ tccmacho.c ----------------- */ |
| 1736 | 1895 | #ifdef TCC_TARGET_MACHO |
| 1737 | −ST_FUNC int macho_output_file(TCCState * s1, const char *filename); | |
| 1738 | −ST_FUNC int macho_load_dll(TCCState *s1, int fd, const char *filename, int lev); | |
| 1739 | −ST_FUNC int macho_load_tbd(TCCState *s1, int fd, const char *filename, int lev); | |
| 1896 | +ST_FUNC int macho_output_file(TCCState * S, const char *filename); | |
| 1897 | +ST_FUNC int macho_load_dll(TCCState *S, int fd, const char *filename, int lev); | |
| 1898 | +ST_FUNC int macho_load_tbd(TCCState *S, int fd, const char *filename, int lev); | |
| 1740 | 1899 | #ifdef TCC_IS_NATIVE |
| 1741 | −ST_FUNC void tcc_add_macos_sdkpath(TCCState* s); | |
| 1900 | +ST_FUNC void tcc_add_macos_sdkpath(TCCState* S); | |
| 1742 | 1901 | ST_FUNC const char* macho_tbd_soname(const char* filename); |
| 1743 | 1902 | #endif |
| 1744 | 1903 | #endif |
| @@ -1755,17 +1914,17 @@ ST_FUNC void dlclose(void *p); · 10 unmodified lines | ||
| 1755 | 1914 | ST_FUNC const char *dlerror(void); |
| 1756 | 1915 | ST_FUNC void *dlsym(void *handle, const char *symbol); |
| 1757 | 1916 | #endif |
| 1758 | −ST_FUNC void tcc_run_free(TCCState *s1); | |
| 1917 | +ST_FUNC void tcc_run_free(TCCState *S); | |
| 1759 | 1918 | #endif |
| 1760 | 1919 | |
| 1761 | 1920 | /* ------------ tcctools.c ----------------- */ |
| 1762 | 1921 | #if 0 /* included in tcc.c */ |
| 1763 | −ST_FUNC int tcc_tool_ar(TCCState *s, int argc, char **argv); | |
| 1922 | +ST_FUNC int tcc_tool_ar(TCCState *S, int argc, char **argv); | |
| 1764 | 1923 | #ifdef TCC_TARGET_PE |
| 1765 | −ST_FUNC int tcc_tool_impdef(TCCState *s, int argc, char **argv); | |
| 1924 | +ST_FUNC int tcc_tool_impdef(TCCState *S, int argc, char **argv); | |
| 1766 | 1925 | #endif |
| 1767 | −ST_FUNC void tcc_tool_cross(TCCState *s, char **argv, int option); | |
| 1768 | −ST_FUNC void gen_makedeps(TCCState *s, const char *target, const char *filename); | |
| 1926 | +ST_FUNC void tcc_tool_cross(TCCState *S, char **argv, int option); | |
| 1927 | +ST_FUNC void gen_makedeps(TCCState *S, const char *target, const char *filename); | |
| 1769 | 1928 | #endif |
| 1770 | 1929 | |
| 1771 | 1930 | /********************************************************/ |
| @@ -1820,12 +1979,12 @@ ST_FUNC void post_sem(TCCSem *p); · 48 unmodified lines | ||
| 1820 | 1979 | #define total_lines TCC_STATE_VAR(total_lines) |
| 1821 | 1980 | #define total_bytes TCC_STATE_VAR(total_bytes) |
| 1822 | 1981 | |
| 1823 | −PUB_FUNC void tcc_enter_state(TCCState *s1); | |
| 1824 | −PUB_FUNC void tcc_exit_state(TCCState *s1); | |
| 1982 | +PUB_FUNC void tcc_enter_state(TCCState *S); | |
| 1983 | +PUB_FUNC void tcc_exit_state(TCCState *S); | |
| 1825 | 1984 | |
| 1826 | 1985 | /* conditional warning depending on switch */ |
| 1827 | 1986 | #define tcc_warning_c(sw) TCC_SET_STATE((\ |
| 1828 | − tcc_state->warn_num = offsetof(TCCState, sw) \ | |
| 1987 | + S->warn_num = offsetof(TCCState, sw) \ | |
| 1829 | 1988 | - offsetof(TCCState, warn_none), _tcc_warning)) |
| 1830 | 1989 | |
| 1831 | 1990 | /********************************************************/ |
| @@ -1835,10 +1994,10 @@ PUB_FUNC void tcc_exit_state(TCCState *s1); · 3 unmodified lines | ||
| 1835 | 1994 | #undef TCC_SET_STATE |
| 1836 | 1995 | |
| 1837 | 1996 | #ifdef USING_GLOBALS |
| 1838 | −# define TCC_STATE_VAR(sym) tcc_state->sym | |
| 1997 | +# define TCC_STATE_VAR(sym) S->sym | |
| 1839 | 1998 | # define TCC_SET_STATE(fn) fn |
| 1840 | 1999 | # undef USING_GLOBALS |
| 1841 | 2000 | #else |
| 1842 | −# define TCC_STATE_VAR(sym) s1->sym | |
| 1843 | −# define TCC_SET_STATE(fn) (tcc_enter_state(s1),fn) | |
| 2001 | +# define TCC_STATE_VAR(sym) S->sym | |
| 2002 | +# define TCC_SET_STATE(fn) (tcc_enter_state(S),fn) | |
| 1844 | 2003 | #endif |
| @@ -22,18 +22,16 @@ · 21 unmodified lines | ||
| 22 | 22 | #include "tcc.h" |
| 23 | 23 | #ifdef CONFIG_TCC_ASM |
| 24 | 24 | |
| 25 | −static Section *last_text_section; /* to handle .previous asm directive */ | |
| 26 | − | |
| 27 | −ST_FUNC int asm_get_local_label_name(TCCState *s1, unsigned int n) | |
| 25 | +ST_FUNC int asm_get_local_label_name(TCCState *S, unsigned int n) | |
| 28 | 26 | { |
| 29 | 27 | char buf[64]; |
| 30 | 28 | snprintf(buf, sizeof(buf), "L..%u", n); |
| 31 | − return tok_alloc_const(buf); | |
| 29 | + return tok_alloc_const(S, buf); | |
| 32 | 30 | } |
| 33 | 31 | |
| 34 | −static int tcc_assemble_internal(TCCState *s1, int do_preprocess, int global); | |
| 35 | −static Sym* asm_new_label(TCCState *s1, int label, int is_local); | |
| 36 | −static Sym* asm_new_label1(TCCState *s1, int label, int is_local, int sh_num, int value); | |
| 32 | +static int tcc_assemble_internal(TCCState *S, int do_preprocess, int global); | |
| 33 | +static Sym* asm_new_label(TCCState *S, int label, int is_local); | |
| 34 | +static Sym* asm_new_label1(TCCState *S, int label, int is_local, int sh_num, int value); | |
| 37 | 35 | |
| 38 | 36 | /* If a C name has an _ prepended then only asm labels that start |
| 39 | 37 | with _ are representable in C, by removing the first _. ASM names |
| @@ -41,44 +39,44 @@ static Sym* asm_new_label1(TCCState *s1, int label, int is_local, int sh_num, in · 1 unmodified line | ||
| 41 | 39 | the global C symbol table to track ASM names as well, so we need to |
| 42 | 40 | transform those into ones that don't conflict with a C name, |
| 43 | 41 | so prepend a '.' for them, but force the ELF asm name to be set. */ |
| 44 | −static int asm2cname(int v, int *addeddot) | |
| 42 | +static int asm2cname(TCCState* S, int v, int *addeddot) | |
| 45 | 43 | { |
| 46 | 44 | const char *name; |
| 47 | 45 | *addeddot = 0; |
| 48 | − if (!tcc_state->leading_underscore) | |
| 46 | + if (!S->leading_underscore) | |
| 49 | 47 | return v; |
| 50 | − name = get_tok_str(v, NULL); | |
| 48 | + name = get_tok_str(S, v, NULL); | |
| 51 | 49 | if (!name) |
| 52 | 50 | return v; |
| 53 | 51 | if (name[0] == '_') { |
| 54 | − v = tok_alloc_const(name + 1); | |
| 52 | + v = tok_alloc_const(S, name + 1); | |
| 55 | 53 | } else if (!strchr(name, '.')) { |
| 56 | 54 | char newname[256]; |
| 57 | 55 | snprintf(newname, sizeof newname, ".%s", name); |
| 58 | − v = tok_alloc_const(newname); | |
| 56 | + v = tok_alloc_const(S, newname); | |
| 59 | 57 | *addeddot = 1; |
| 60 | 58 | } |
| 61 | 59 | return v; |
| 62 | 60 | } |
| 63 | 61 | |
| 64 | −static Sym *asm_label_find(int v) | |
| 62 | +static Sym *asm_label_find(TCCState* S, int v) | |
| 65 | 63 | { |
| 66 | 64 | Sym *sym; |
| 67 | 65 | int addeddot; |
| 68 | − v = asm2cname(v, &addeddot); | |
| 69 | − sym = sym_find(v); | |
| 66 | + v = asm2cname(S, v, &addeddot); | |
| 67 | + sym = sym_find(S, v); | |
| 70 | 68 | while (sym && sym->sym_scope && !(sym->type.t & VT_STATIC)) |
| 71 | 69 | sym = sym->prev_tok; |
| 72 | 70 | return sym; |
| 73 | 71 | } |
| 74 | 72 | |
| 75 | −static Sym *asm_label_push(int v) | |
| 73 | +static Sym *asm_label_push(TCCState* S, int v) | |
| 76 | 74 | { |
| 77 | − int addeddot, v2 = asm2cname(v, &addeddot); | |
| 75 | + int addeddot, v2 = asm2cname(S, v, &addeddot); | |
| 78 | 76 | /* We always add VT_EXTERN, for sym definition that's tentative |
| 79 | 77 | (for .set, removed for real defs), for mere references it's correct |
| 80 | 78 | as is. */ |
| 81 | − Sym *sym = global_identifier_push(v2, VT_ASM | VT_EXTERN | VT_STATIC, 0); | |
| 79 | + Sym *sym = global_identifier_push(S, v2, VT_ASM | VT_EXTERN | VT_STATIC, 0); | |
| 82 | 80 | if (addeddot) |
| 83 | 81 | sym->asm_label = v; |
| 84 | 82 | return sym; |
| @@ -94,55 +92,55 @@ static Sym *asm_label_push(int v) · 9 unmodified lines | ||
| 94 | 92 | are anonymous in C, in this case CSYM can be used to transfer |
| 95 | 93 | all information from that symbol to the (possibly newly created) |
| 96 | 94 | asm symbol. */ |
| 97 | −ST_FUNC Sym* get_asm_sym(int name, Sym *csym) | |
| 95 | +ST_FUNC Sym* get_asm_sym(TCCState* S, int name, Sym *csym) | |
| 98 | 96 | { |
| 99 | − Sym *sym = asm_label_find(name); | |
| 97 | + Sym *sym = asm_label_find(S, name); | |
| 100 | 98 | if (!sym) { |
| 101 | − sym = asm_label_push(name); | |
| 99 | + sym = asm_label_push(S, name); | |
| 102 | 100 | if (csym) |
| 103 | 101 | sym->c = csym->c; |
| 104 | 102 | } |
| 105 | 103 | return sym; |
| 106 | 104 | } |
| 107 | 105 | |
| 108 | −static Sym* asm_section_sym(TCCState *s1, Section *sec) | |
| 106 | +static Sym* asm_section_sym(TCCState *S, Section *sec) | |
| 109 | 107 | { |
| 110 | 108 | char buf[100]; int label; Sym *sym; |
| 111 | 109 | snprintf(buf, sizeof buf, "L.%s", sec->name); |
| 112 | − label = tok_alloc_const(buf); | |
| 113 | − sym = asm_label_find(label); | |
| 114 | − return sym ? sym : asm_new_label1(s1, label, 1, sec->sh_num, 0); | |
| 110 | + label = tok_alloc_const(S, buf); | |
| 111 | + sym = asm_label_find(S, label); | |
| 112 | + return sym ? sym : asm_new_label1(S, label, 1, sec->sh_num, 0); | |
| 115 | 113 | } |
| 116 | 114 | |
| 117 | 115 | /* We do not use the C expression parser to handle symbols. Maybe the |
| 118 | 116 | C expression parser could be tweaked to do so. */ |
| 119 | 117 | |
| 120 | −static void asm_expr_unary(TCCState *s1, ExprValue *pe) | |
| 118 | +static void asm_expr_unary(TCCState *S, ExprValue *pe) | |
| 121 | 119 | { |
| 122 | 120 | Sym *sym; |
| 123 | 121 | int op, label; |
| 124 | 122 | uint64_t n; |
| 125 | 123 | const char *p; |
| 126 | 124 | |
| 127 | − switch(tok) { | |
| 125 | + switch(S->tccpp_tok) { | |
| 128 | 126 | case TOK_PPNUM: |
| 129 | − p = tokc.str.data; | |
| 127 | + p = S->tccpp_tokc.str.data; | |
| 130 | 128 | n = strtoull(p, (char **)&p, 0); |
| 131 | 129 | if (*p == 'b' || *p == 'f') { |
| 132 | 130 | /* backward or forward label */ |
| 133 | − label = asm_get_local_label_name(s1, n); | |
| 134 | − sym = asm_label_find(label); | |
| 131 | + label = asm_get_local_label_name(S, n); | |
| 132 | + sym = asm_label_find(S, label); | |
| 135 | 133 | if (*p == 'b') { |
| 136 | 134 | /* backward : find the last corresponding defined label */ |
| 137 | − if (sym && (!sym->c || elfsym(sym)->st_shndx == SHN_UNDEF)) | |
| 135 | + if (sym && (!sym->c || elfsym(S, sym)->st_shndx == SHN_UNDEF)) | |
| 138 | 136 | sym = sym->prev_tok; |
| 139 | 137 | if (!sym) |
| 140 | − tcc_error("local label '%d' not found backward", (int)n); | |
| 138 | + tcc_error(S, "local label '%d' not found backward", (int)n); | |
| 141 | 139 | } else { |
| 142 | 140 | /* forward */ |
| 143 | − if (!sym || (sym->c && elfsym(sym)->st_shndx != SHN_UNDEF)) { | |
| 141 | + if (!sym || (sym->c && elfsym(S, sym)->st_shndx != SHN_UNDEF)) { | |
| 144 | 142 | /* if the last label is defined, then define a new one */ |
| 145 | − sym = asm_label_push(label); | |
| 143 | + sym = asm_label_push(S, label); | |
| 146 | 144 | } |
| 147 | 145 | } |
| 148 | 146 | pe->v = 0; |
| @@ -153,21 +151,21 @@ static void asm_expr_unary(TCCState *s1, ExprValue *pe) · 4 unmodified lines | ||
| 153 | 151 | pe->sym = NULL; |
| 154 | 152 | pe->pcrel = 0; |
| 155 | 153 | } else { |
| 156 | − tcc_error("invalid number syntax"); | |
| 154 | + tcc_error(S, "invalid number syntax"); | |
| 157 | 155 | } |
| 158 | − next(); | |
| 156 | + next(S); | |
| 159 | 157 | break; |
| 160 | 158 | case '+': |
| 161 | − next(); | |
| 162 | − asm_expr_unary(s1, pe); | |
| 159 | + next(S); | |
| 160 | + asm_expr_unary(S, pe); | |
| 163 | 161 | break; |
| 164 | 162 | case '-': |
| 165 | 163 | case '~': |
| 166 | − op = tok; | |
| 167 | − next(); | |
| 168 | − asm_expr_unary(s1, pe); | |
| 164 | + op = S->tccpp_tok; | |
| 165 | + next(S); | |
| 166 | + asm_expr_unary(S, pe); | |
| 169 | 167 | if (pe->sym) |
| 170 | − tcc_error("invalid operation with label"); | |
| 168 | + tcc_error(S, "invalid operation with label"); | |
| 171 | 169 | if (op == '-') |
| 172 | 170 | pe->v = -pe->v; |
| 173 | 171 | else |
| @@ -175,28 +173,28 @@ static void asm_expr_unary(TCCState *s1, ExprValue *pe) · 1 unmodified line | ||
| 175 | 173 | break; |
| 176 | 174 | case TOK_CCHAR: |
| 177 | 175 | case TOK_LCHAR: |
| 178 | − pe->v = tokc.i; | |
| 176 | + pe->v = S->tccpp_tokc.i; | |
| 179 | 177 | pe->sym = NULL; |
| 180 | 178 | pe->pcrel = 0; |
| 181 | − next(); | |
| 179 | + next(S); | |
| 182 | 180 | break; |
| 183 | 181 | case '(': |
| 184 | − next(); | |
| 185 | − asm_expr(s1, pe); | |
| 186 | − skip(')'); | |
| 182 | + next(S); | |
| 183 | + asm_expr(S, pe); | |
| 184 | + skip(S, ')'); | |
| 187 | 185 | break; |
| 188 | 186 | case '.': |
| 189 | − pe->v = ind; | |
| 190 | − pe->sym = asm_section_sym(s1, cur_text_section); | |
| 187 | + pe->v = S->tccgen_ind; | |
| 188 | + pe->sym = asm_section_sym(S, cur_text_section); | |
| 191 | 189 | pe->pcrel = 0; |
| 192 | − next(); | |
| 190 | + next(S); | |
| 193 | 191 | break; |
| 194 | 192 | default: |
| 195 | − if (tok >= TOK_IDENT) { | |
| 193 | + if (S->tccpp_tok >= TOK_IDENT) { | |
| 196 | 194 | ElfSym *esym; |
| 197 | 195 | /* label case : if the label was not found, add one */ |
| 198 | − sym = get_asm_sym(tok, NULL); | |
| 199 | − esym = elfsym(sym); | |
| 196 | + sym = get_asm_sym(S, S->tccpp_tok, NULL); | |
| 197 | + esym = elfsym(S, sym); | |
| 200 | 198 | if (esym && esym->st_shndx == SHN_ABS) { |
| 201 | 199 | /* if absolute symbol, no need to put a symbol value */ |
| 202 | 200 | pe->v = esym->st_value; |
| @@ -207,29 +205,29 @@ static void asm_expr_unary(TCCState *s1, ExprValue *pe) · 4 unmodified lines | ||
| 207 | 205 | pe->sym = sym; |
| 208 | 206 | pe->pcrel = 0; |
| 209 | 207 | } |
| 210 | − next(); | |
| 208 | + next(S); | |
| 211 | 209 | } else { |
| 212 | − tcc_error("bad expression syntax [%s]", get_tok_str(tok, &tokc)); | |
| 210 | + tcc_error(S, "bad expression syntax [%s]", get_tok_str(S, S->tccpp_tok, &S->tccpp_tokc)); | |
| 213 | 211 | } |
| 214 | 212 | break; |
| 215 | 213 | } |
| 216 | 214 | } |
| 217 | 215 | |
| 218 | −static void asm_expr_prod(TCCState *s1, ExprValue *pe) | |
| 216 | +static void asm_expr_prod(TCCState *S, ExprValue *pe) | |
| 219 | 217 | { |
| 220 | 218 | int op; |
| 221 | 219 | ExprValue e2; |
| 222 | 220 | |
| 223 | − asm_expr_unary(s1, pe); | |
| 221 | + asm_expr_unary(S, pe); | |
| 224 | 222 | for(;;) { |
| 225 | − op = tok; | |
| 223 | + op = S->tccpp_tok; | |
| 226 | 224 | if (op != '*' && op != '/' && op != '%' && |
| 227 | 225 | op != TOK_SHL && op != TOK_SAR) |
| 228 | 226 | break; |
| 229 | − next(); | |
| 230 | − asm_expr_unary(s1, &e2); | |
| 227 | + next(S); | |
| 228 | + asm_expr_unary(S, &e2); | |
| 231 | 229 | if (pe->sym || e2.sym) |
| 232 | − tcc_error("invalid operation with label"); | |
| 230 | + tcc_error(S, "invalid operation with label"); | |
| 233 | 231 | switch(op) { |
| 234 | 232 | case '*': |
| 235 | 233 | pe->v *= e2.v; |
| @@ -237,7 +235,7 @@ static void asm_expr_prod(TCCState *s1, ExprValue *pe) · 1 unmodified line | ||
| 237 | 235 | case '/': |
| 238 | 236 | if (e2.v == 0) { |
| 239 | 237 | div_error: |
| 240 | − tcc_error("division by zero"); | |
| 238 | + tcc_error(S, "division by zero"); | |
| 241 | 239 | } |
| 242 | 240 | pe->v /= e2.v; |
| 243 | 241 | break; |
| @@ -257,20 +255,20 @@ static void asm_expr_prod(TCCState *s1, ExprValue *pe) · 13 unmodified lines | ||
| 257 | 255 | } |
| 258 | 256 | } |
| 259 | 257 | |
| 260 | −static void asm_expr_logic(TCCState *s1, ExprValue *pe) | |
| 258 | +static void asm_expr_logic(TCCState *S, ExprValue *pe) | |
| 261 | 259 | { |
| 262 | 260 | int op; |
| 263 | 261 | ExprValue e2; |
| 264 | 262 | |
| 265 | − asm_expr_prod(s1, pe); | |
| 263 | + asm_expr_prod(S, pe); | |
| 266 | 264 | for(;;) { |
| 267 | − op = tok; | |
| 265 | + op = S->tccpp_tok; | |
| 268 | 266 | if (op != '&' && op != '|' && op != '^') |
| 269 | 267 | break; |
| 270 | − next(); | |
| 271 | − asm_expr_prod(s1, &e2); | |
| 268 | + next(S); | |
| 269 | + asm_expr_prod(S, &e2); | |
| 272 | 270 | if (pe->sym || e2.sym) |
| 273 | − tcc_error("invalid operation with label"); | |
| 271 | + tcc_error(S, "invalid operation with label"); | |
| 274 | 272 | switch(op) { |
| 275 | 273 | case '&': |
| 276 | 274 | pe->v &= e2.v; |
| @@ -286,18 +284,18 @@ static void asm_expr_logic(TCCState *s1, ExprValue *pe) · 9 unmodified lines | ||
| 286 | 284 | } |
| 287 | 285 | } |
| 288 | 286 | |
| 289 | −static inline void asm_expr_sum(TCCState *s1, ExprValue *pe) | |
| 287 | +static inline void asm_expr_sum(TCCState *S, ExprValue *pe) | |
| 290 | 288 | { |
| 291 | 289 | int op; |
| 292 | 290 | ExprValue e2; |
| 293 | 291 | |
| 294 | − asm_expr_logic(s1, pe); | |
| 292 | + asm_expr_logic(S, pe); | |
| 295 | 293 | for(;;) { |
| 296 | − op = tok; | |
| 294 | + op = S->tccpp_tok; | |
| 297 | 295 | if (op != '+' && op != '-') |
| 298 | 296 | break; |
| 299 | − next(); | |
| 300 | − asm_expr_logic(s1, &e2); | |
| 297 | + next(S); | |
| 298 | + asm_expr_logic(S, &e2); | |
| 301 | 299 | if (op == '+') { |
| 302 | 300 | if (pe->sym != NULL && e2.sym != NULL) |
| 303 | 301 | goto cannot_relocate; |
| @@ -315,8 +313,8 @@ static inline void asm_expr_sum(TCCState *s1, ExprValue *pe) · 11 unmodified lines | ||
| 315 | 313 | pe->sym = NULL; /* same symbols can be subtracted to NULL */ |
| 316 | 314 | } else { |
| 317 | 315 | ElfSym *esym1, *esym2; |
| 318 | − esym1 = elfsym(pe->sym); | |
| 319 | − esym2 = elfsym(e2.sym); | |
| 316 | + esym1 = elfsym(S, pe->sym); | |
| 317 | + esym2 = elfsym(S, e2.sym); | |
| 320 | 318 | if (esym1 && esym1->st_shndx == esym2->st_shndx |
| 321 | 319 | && esym1->st_shndx != SHN_UNDEF) { |
| 322 | 320 | /* we also accept defined symbols in the same section */ |
| @@ -325,33 +323,33 @@ static inline void asm_expr_sum(TCCState *s1, ExprValue *pe) · 2 unmodified lines | ||
| 325 | 323 | } else if (esym2->st_shndx == cur_text_section->sh_num) { |
| 326 | 324 | /* When subtracting a defined symbol in current section |
| 327 | 325 | this actually makes the value PC-relative. */ |
| 328 | − pe->v -= esym2->st_value - ind - 4; | |
| 326 | + pe->v -= esym2->st_value - S->tccgen_ind - 4; | |
| 329 | 327 | pe->pcrel = 1; |
| 330 | 328 | e2.sym = NULL; |
| 331 | 329 | } else { |
| 332 | 330 | cannot_relocate: |
| 333 | − tcc_error("invalid operation with label"); | |
| 331 | + tcc_error(S, "invalid operation with label"); | |
| 334 | 332 | } |
| 335 | 333 | } |
| 336 | 334 | } |
| 337 | 335 | } |
| 338 | 336 | } |
| 339 | 337 | |
| 340 | −static inline void asm_expr_cmp(TCCState *s1, ExprValue *pe) | |
| 338 | +static inline void asm_expr_cmp(TCCState *S, ExprValue *pe) | |
| 341 | 339 | { |
| 342 | 340 | int op; |
| 343 | 341 | ExprValue e2; |
| 344 | 342 | |
| 345 | − asm_expr_sum(s1, pe); | |
| 343 | + asm_expr_sum(S, pe); | |
| 346 | 344 | for(;;) { |
| 347 | − op = tok; | |
| 345 | + op = S->tccpp_tok; | |
| 348 | 346 | if (op != TOK_EQ && op != TOK_NE |
| 349 | 347 | && (op > TOK_GT || op < TOK_ULE)) |
| 350 | 348 | break; |
| 351 | − next(); | |
| 352 | − asm_expr_sum(s1, &e2); | |
| 349 | + next(S); | |
| 350 | + asm_expr_sum(S, &e2); | |
| 353 | 351 | if (pe->sym || e2.sym) |
| 354 | − tcc_error("invalid operation with label"); | |
| 352 | + tcc_error(S, "invalid operation with label"); | |
| 355 | 353 | switch(op) { |
| 356 | 354 | case TOK_EQ: |
| 357 | 355 | pe->v = pe->v == e2.v; |
| @@ -379,29 +377,29 @@ static inline void asm_expr_cmp(TCCState *s1, ExprValue *pe) · 21 unmodified lines | ||
| 379 | 377 | } |
| 380 | 378 | } |
| 381 | 379 | |
| 382 | −ST_FUNC void asm_expr(TCCState *s1, ExprValue *pe) | |
| 380 | +ST_FUNC void asm_expr(TCCState *S, ExprValue *pe) | |
| 383 | 381 | { |
| 384 | − asm_expr_cmp(s1, pe); | |
| 382 | + asm_expr_cmp(S, pe); | |
| 385 | 383 | } |
| 386 | 384 | |
| 387 | −ST_FUNC int asm_int_expr(TCCState *s1) | |
| 385 | +ST_FUNC int asm_int_expr(TCCState *S) | |
| 388 | 386 | { |
| 389 | 387 | ExprValue e; |
| 390 | − asm_expr(s1, &e); | |
| 388 | + asm_expr(S, &e); | |
| 391 | 389 | if (e.sym) |
| 392 | − expect("constant"); | |
| 390 | + expect(S, "constant"); | |
| 393 | 391 | return e.v; |
| 394 | 392 | } |
| 395 | 393 | |
| 396 | −static Sym* asm_new_label1(TCCState *s1, int label, int is_local, | |
| 394 | +static Sym* asm_new_label1(TCCState *S, int label, int is_local, | |
| 397 | 395 | int sh_num, int value) |
| 398 | 396 | { |
| 399 | 397 | Sym *sym; |
| 400 | 398 | ElfSym *esym; |
| 401 | 399 | |
| 402 | − sym = asm_label_find(label); | |
| 400 | + sym = asm_label_find(S, label); | |
| 403 | 401 | if (sym) { |
| 404 | − esym = elfsym(sym); | |
| 402 | + esym = elfsym(S, sym); | |
| 405 | 403 | /* A VT_EXTERN symbol, even if it has a section is considered |
| 406 | 404 | overridable. This is how we "define" .set targets. Real |
| 407 | 405 | definitions won't have VT_EXTERN set. */ |
| @@ -411,16 +409,16 @@ static Sym* asm_new_label1(TCCState *s1, int label, int is_local, · 3 unmodified lines | ||
| 411 | 409 | && (is_local == 1 || (sym->type.t & VT_EXTERN))) |
| 412 | 410 | goto new_label; |
| 413 | 411 | if (!(sym->type.t & VT_EXTERN)) |
| 414 | − tcc_error("assembler label '%s' already defined", | |
| 415 | − get_tok_str(label, NULL)); | |
| 412 | + tcc_error(S, "assembler label '%s' already defined", | |
| 413 | + get_tok_str(S, label, NULL)); | |
| 416 | 414 | } |
| 417 | 415 | } else { |
| 418 | 416 | new_label: |
| 419 | − sym = asm_label_push(label); | |
| 417 | + sym = asm_label_push(S, label); | |
| 420 | 418 | } |
| 421 | 419 | if (!sym->c) |
| 422 | − put_extern_sym2(sym, SHN_UNDEF, 0, 0, 1); | |
| 423 | − esym = elfsym(sym); | |
| 420 | + put_extern_sym2(S, sym, SHN_UNDEF, 0, 0, 1); | |
| 421 | + esym = elfsym(S, sym); | |
| 424 | 422 | esym->st_shndx = sh_num; |
| 425 | 423 | esym->st_value = value; |
| 426 | 424 | if (is_local != 2) |
| @@ -428,61 +426,61 @@ static Sym* asm_new_label1(TCCState *s1, int label, int is_local, · 1 unmodified line | ||
| 428 | 426 | return sym; |
| 429 | 427 | } |
| 430 | 428 | |
| 431 | −static Sym* asm_new_label(TCCState *s1, int label, int is_local) | |
| 429 | +static Sym* asm_new_label(TCCState *S, int label, int is_local) | |
| 432 | 430 | { |
| 433 | − return asm_new_label1(s1, label, is_local, cur_text_section->sh_num, ind); | |
| 431 | + return asm_new_label1(S, label, is_local, cur_text_section->sh_num, S->tccgen_ind); | |
| 434 | 432 | } |
| 435 | 433 | |
| 436 | 434 | /* Set the value of LABEL to that of some expression (possibly |
| 437 | 435 | involving other symbols). LABEL can be overwritten later still. */ |
| 438 | −static Sym* set_symbol(TCCState *s1, int label) | |
| 436 | +static Sym* set_symbol(TCCState *S, int label) | |
| 439 | 437 | { |
| 440 | 438 | long n; |
| 441 | 439 | ExprValue e; |
| 442 | 440 | Sym *sym; |
| 443 | 441 | ElfSym *esym; |
| 444 | − next(); | |
| 445 | − asm_expr(s1, &e); | |
| 442 | + next(S); | |
| 443 | + asm_expr(S, &e); | |
| 446 | 444 | n = e.v; |
| 447 | − esym = elfsym(e.sym); | |
| 445 | + esym = elfsym(S, e.sym); | |
| 448 | 446 | if (esym) |
| 449 | 447 | n += esym->st_value; |
| 450 | − sym = asm_new_label1(s1, label, 2, esym ? esym->st_shndx : SHN_ABS, n); | |
| 451 | − elfsym(sym)->st_other |= ST_ASM_SET; | |
| 448 | + sym = asm_new_label1(S, label, 2, esym ? esym->st_shndx : SHN_ABS, n); | |
| 449 | + elfsym(S, sym)->st_other |= ST_ASM_SET; | |
| 452 | 450 | return sym; |
| 453 | 451 | } |
| 454 | 452 | |
| 455 | −static void use_section1(TCCState *s1, Section *sec) | |
| 453 | +static void use_section1(TCCState *S, Section *sec) | |
| 456 | 454 | { |
| 457 | − cur_text_section->data_offset = ind; | |
| 455 | + cur_text_section->data_offset = S->tccgen_ind; | |
| 458 | 456 | cur_text_section = sec; |
| 459 | − ind = cur_text_section->data_offset; | |
| 457 | + S->tccgen_ind = cur_text_section->data_offset; | |
| 460 | 458 | } |
| 461 | 459 | |
| 462 | −static void use_section(TCCState *s1, const char *name) | |
| 460 | +static void use_section(TCCState *S, const char *name) | |
| 463 | 461 | { |
| 464 | 462 | Section *sec; |
| 465 | − sec = find_section(s1, name); | |
| 466 | − use_section1(s1, sec); | |
| 463 | + sec = find_section(S, name); | |
| 464 | + use_section1(S, sec); | |
| 467 | 465 | } |
| 468 | 466 | |
| 469 | −static void push_section(TCCState *s1, const char *name) | |
| 467 | +static void push_section(TCCState *S, const char *name) | |
| 470 | 468 | { |
| 471 | − Section *sec = find_section(s1, name); | |
| 469 | + Section *sec = find_section(S, name); | |
| 472 | 470 | sec->prev = cur_text_section; |
| 473 | − use_section1(s1, sec); | |
| 471 | + use_section1(S, sec); | |
| 474 | 472 | } |
| 475 | 473 | |
| 476 | −static void pop_section(TCCState *s1) | |
| 474 | +static void pop_section(TCCState *S) | |
| 477 | 475 | { |
| 478 | 476 | Section *prev = cur_text_section->prev; |
| 479 | 477 | if (!prev) |
| 480 | − tcc_error(".popsection without .pushsection"); | |
| 478 | + tcc_error(S, ".popsection without .pushsection"); | |
| 481 | 479 | cur_text_section->prev = NULL; |
| 482 | − use_section1(s1, prev); | |
| 480 | + use_section1(S, prev); | |
| 483 | 481 | } |
| 484 | 482 | |
| 485 | −static void asm_parse_directive(TCCState *s1, int global) | |
| 483 | +static void asm_parse_directive(TCCState *S, int global) | |
| 486 | 484 | { |
| 487 | 485 | int n, offset, v, size, tok1; |
| 488 | 486 | Section *sec; |
| @@ -490,27 +488,27 @@ static void asm_parse_directive(TCCState *s1, int global) · 1 unmodified line | ||
| 490 | 488 | |
| 491 | 489 | /* assembler directive */ |
| 492 | 490 | sec = cur_text_section; |
| 493 | − switch(tok) { | |
| 491 | + switch(S->tccpp_tok) { | |
| 494 | 492 | case TOK_ASMDIR_align: |
| 495 | 493 | case TOK_ASMDIR_balign: |
| 496 | 494 | case TOK_ASMDIR_p2align: |
| 497 | 495 | case TOK_ASMDIR_skip: |
| 498 | 496 | case TOK_ASMDIR_space: |
| 499 | − tok1 = tok; | |
| 500 | − next(); | |
| 501 | − n = asm_int_expr(s1); | |
| 497 | + tok1 = S->tccpp_tok; | |
| 498 | + next(S); | |
| 499 | + n = asm_int_expr(S); | |
| 502 | 500 | if (tok1 == TOK_ASMDIR_p2align) |
| 503 | 501 | { |
| 504 | 502 | if (n < 0 || n > 30) |
| 505 | − tcc_error("invalid p2align, must be between 0 and 30"); | |
| 503 | + tcc_error(S, "invalid p2align, must be between 0 and 30"); | |
| 506 | 504 | n = 1 << n; |
| 507 | 505 | tok1 = TOK_ASMDIR_align; |
| 508 | 506 | } |
| 509 | 507 | if (tok1 == TOK_ASMDIR_align || tok1 == TOK_ASMDIR_balign) { |
| 510 | 508 | if (n < 0 || (n & (n-1)) != 0) |
| 511 | − tcc_error("alignment must be a positive power of two"); | |
| 512 | − offset = (ind + n - 1) & -n; | |
| 513 | − size = offset - ind; | |
| 509 | + tcc_error(S, "alignment must be a positive power of two"); | |
| 510 | + offset = (S->tccgen_ind + n - 1) & -n; | |
| 511 | + size = offset - S->tccgen_ind; | |
| 514 | 512 | /* the section must have a compatible alignment */ |
| 515 | 513 | if (sec->sh_addralign < n) |
| 516 | 514 | sec->sh_addralign = n; |
| @@ -520,47 +518,47 @@ static void asm_parse_directive(TCCState *s1, int global) · 3 unmodified lines | ||
| 520 | 518 | size = n; |
| 521 | 519 | } |
| 522 | 520 | v = 0; |
| 523 | − if (tok == ',') { | |
| 524 | − next(); | |
| 525 | − v = asm_int_expr(s1); | |
| 521 | + if (S->tccpp_tok == ',') { | |
| 522 | + next(S); | |
| 523 | + v = asm_int_expr(S); | |
| 526 | 524 | } |
| 527 | 525 | zero_pad: |
| 528 | 526 | if (sec->sh_type != SHT_NOBITS) { |
| 529 | − sec->data_offset = ind; | |
| 530 | − ptr = section_ptr_add(sec, size); | |
| 527 | + sec->data_offset = S->tccgen_ind; | |
| 528 | + ptr = section_ptr_add(S, sec, size); | |
| 531 | 529 | memset(ptr, v, size); |
| 532 | 530 | } |
| 533 | − ind += size; | |
| 531 | + S->tccgen_ind += size; | |
| 534 | 532 | break; |
| 535 | 533 | case TOK_ASMDIR_quad: |
| 536 | 534 | #ifdef TCC_TARGET_X86_64 |
| 537 | 535 | size = 8; |
| 538 | 536 | goto asm_data; |
| 539 | 537 | #else |
| 540 | − next(); | |
| 538 | + next(S); | |
| 541 | 539 | for(;;) { |
| 542 | 540 | uint64_t vl; |
| 543 | 541 | const char *p; |
| 544 | 542 | |
| 545 | − p = tokc.str.data; | |
| 546 | − if (tok != TOK_PPNUM) { | |
| 543 | + p = S->tccpp_tokc.str.data; | |
| 544 | + if (S->tccpp_tok != TOK_PPNUM) { | |
| 547 | 545 | error_constant: |
| 548 | − tcc_error("64 bit constant"); | |
| 546 | + tcc_error(S, "64 bit constant"); | |
| 549 | 547 | } |
| 550 | 548 | vl = strtoll(p, (char **)&p, 0); |
| 551 | 549 | if (*p != '\0') |
| 552 | 550 | goto error_constant; |
| 553 | − next(); | |
| 551 | + next(S); | |
| 554 | 552 | if (sec->sh_type != SHT_NOBITS) { |
| 555 | 553 | /* XXX: endianness */ |
| 556 | − gen_le32(vl); | |
| 557 | − gen_le32(vl >> 32); | |
| 554 | + gen_le32(S, vl); | |
| 555 | + gen_le32(S, vl >> 32); | |
| 558 | 556 | } else { |
| 559 | − ind += 8; | |
| 557 | + S->tccgen_ind += 8; | |
| 560 | 558 | } |
| 561 | − if (tok != ',') | |
| 559 | + if (S->tccpp_tok != ',') | |
| 562 | 560 | break; |
| 563 | − next(); | |
| 561 | + next(S); | |
| 564 | 562 | } |
| 565 | 563 | break; |
| 566 | 564 | #endif |
| @@ -575,57 +573,57 @@ static void asm_parse_directive(TCCState *s1, int global) · 8 unmodified lines | ||
| 575 | 573 | case TOK_ASMDIR_int: |
| 576 | 574 | size = 4; |
| 577 | 575 | asm_data: |
| 578 | − next(); | |
| 576 | + next(S); | |
| 579 | 577 | for(;;) { |
| 580 | 578 | ExprValue e; |
| 581 | − asm_expr(s1, &e); | |
| 579 | + asm_expr(S, &e); | |
| 582 | 580 | if (sec->sh_type != SHT_NOBITS) { |
| 583 | 581 | if (size == 4) { |
| 584 | − gen_expr32(&e); | |
| 582 | + gen_expr32(S, &e); | |
| 585 | 583 | #ifdef TCC_TARGET_X86_64 |
| 586 | 584 | } else if (size == 8) { |
| 587 | − gen_expr64(&e); | |
| 585 | + gen_expr64(S, &e); | |
| 588 | 586 | #endif |
| 589 | 587 | } else { |
| 590 | 588 | if (e.sym) |
| 591 | − expect("constant"); | |
| 589 | + expect(S, "constant"); | |
| 592 | 590 | if (size == 1) |
| 593 | − g(e.v); | |
| 591 | + g(S, e.v); | |
| 594 | 592 | else |
| 595 | − gen_le16(e.v); | |
| 593 | + gen_le16(S, e.v); | |
| 596 | 594 | } |
| 597 | 595 | } else { |
| 598 | − ind += size; | |
| 596 | + S->tccgen_ind += size; | |
| 599 | 597 | } |
| 600 | − if (tok != ',') | |
| 598 | + if (S->tccpp_tok != ',') | |
| 601 | 599 | break; |
| 602 | − next(); | |
| 600 | + next(S); | |
| 603 | 601 | } |
| 604 | 602 | break; |
| 605 | 603 | case TOK_ASMDIR_fill: |
| 606 | 604 | { |
| 607 | 605 | int repeat, size, val, i, j; |
| 608 | 606 | uint8_t repeat_buf[8]; |
| 609 | − next(); | |
| 610 | − repeat = asm_int_expr(s1); | |
| 607 | + next(S); | |
| 608 | + repeat = asm_int_expr(S); | |
| 611 | 609 | if (repeat < 0) { |
| 612 | − tcc_error("repeat < 0; .fill ignored"); | |
| 610 | + tcc_error(S, "repeat < 0; .fill ignored"); | |
| 613 | 611 | break; |
| 614 | 612 | } |
| 615 | 613 | size = 1; |
| 616 | 614 | val = 0; |
| 617 | − if (tok == ',') { | |
| 618 | − next(); | |
| 619 | − size = asm_int_expr(s1); | |
| 615 | + if (S->tccpp_tok == ',') { | |
| 616 | + next(S); | |
| 617 | + size = asm_int_expr(S); | |
| 620 | 618 | if (size < 0) { |
| 621 | − tcc_error("size < 0; .fill ignored"); | |
| 619 | + tcc_error(S, "size < 0; .fill ignored"); | |
| 622 | 620 | break; |
| 623 | 621 | } |
| 624 | 622 | if (size > 8) |
| 625 | 623 | size = 8; |
| 626 | − if (tok == ',') { | |
| 627 | − next(); | |
| 628 | − val = asm_int_expr(s1); | |
| 624 | + if (S->tccpp_tok == ',') { | |
| 625 | + next(S); | |
| 626 | + val = asm_int_expr(S); | |
| 629 | 627 | } |
| 630 | 628 | } |
| 631 | 629 | /* XXX: endianness */ |
| @@ -639,7 +637,7 @@ static void asm_parse_directive(TCCState *s1, int global) · 7 unmodified lines | ||
| 639 | 637 | repeat_buf[7] = 0; |
| 640 | 638 | for(i = 0; i < repeat; i++) { |
| 641 | 639 | for(j = 0; j < size; j++) { |
| 642 | − g(repeat_buf[j]); | |
| 640 | + g(S, repeat_buf[j]); | |
| 643 | 641 | } |
| 644 | 642 | } |
| 645 | 643 | } |
| @@ -648,24 +646,24 @@ static void asm_parse_directive(TCCState *s1, int global) · 2 unmodified lines | ||
| 648 | 646 | { |
| 649 | 647 | int repeat; |
| 650 | 648 | TokenString *init_str; |
| 651 | − next(); | |
| 652 | − repeat = asm_int_expr(s1); | |
| 653 | − init_str = tok_str_alloc(); | |
| 654 | − while (next(), tok != TOK_ASMDIR_endr) { | |
| 655 | − if (tok == CH_EOF) | |
| 656 | − tcc_error("we at end of file, .endr not found"); | |
| 657 | − tok_str_add_tok(init_str); | |
| 649 | + next(S); | |
| 650 | + repeat = asm_int_expr(S); | |
| 651 | + init_str = tok_str_alloc(S); | |
| 652 | + while (next(S), S->tccpp_tok != TOK_ASMDIR_endr) { | |
| 653 | + if (S->tccpp_tok == CH_EOF) | |
| 654 | + tcc_error(S, "we at end of file, .endr not found"); | |
| 655 | + tok_str_add_tok(S, init_str); | |
| 658 | 656 | } |
| 659 | − tok_str_add(init_str, -1); | |
| 660 | − tok_str_add(init_str, 0); | |
| 661 | − begin_macro(init_str, 1); | |
| 657 | + tok_str_add(S, init_str, -1); | |
| 658 | + tok_str_add(S, init_str, 0); | |
| 659 | + begin_macro(S, init_str, 1); | |
| 662 | 660 | while (repeat-- > 0) { |
| 663 | − tcc_assemble_internal(s1, (parse_flags & PARSE_FLAG_PREPROCESS), | |
| 661 | + tcc_assemble_internal(S, (S->tccpp_parse_flags & PARSE_FLAG_PREPROCESS), | |
| 664 | 662 | global); |
| 665 | − macro_ptr = init_str->str; | |
| 663 | + S->tccpp_macro_ptr = init_str->str; | |
| 666 | 664 | } |
| 667 | − end_macro(); | |
| 668 | − next(); | |
| 665 | + end_macro(S); | |
| 666 | + next(S); | |
| 669 | 667 | break; |
| 670 | 668 | } |
| 671 | 669 | case TOK_ASMDIR_org: |
| @@ -673,49 +671,49 @@ static void asm_parse_directive(TCCState *s1, int global) · 1 unmodified line | ||
| 673 | 671 | unsigned long n; |
| 674 | 672 | ExprValue e; |
| 675 | 673 | ElfSym *esym; |
| 676 | − next(); | |
| 677 | − asm_expr(s1, &e); | |
| 674 | + next(S); | |
| 675 | + asm_expr(S, &e); | |
| 678 | 676 | n = e.v; |
| 679 | − esym = elfsym(e.sym); | |
| 677 | + esym = elfsym(S, e.sym); | |
| 680 | 678 | if (esym) { |
| 681 | 679 | if (esym->st_shndx != cur_text_section->sh_num) |
| 682 | − expect("constant or same-section symbol"); | |
| 680 | + expect(S, "constant or same-section symbol"); | |
| 683 | 681 | n += esym->st_value; |
| 684 | 682 | } |
| 685 | − if (n < ind) | |
| 686 | − tcc_error("attempt to .org backwards"); | |
| 683 | + if (n < S->tccgen_ind) | |
| 684 | + tcc_error(S, "attempt to .org backwards"); | |
| 687 | 685 | v = 0; |
| 688 | − size = n - ind; | |
| 686 | + size = n - S->tccgen_ind; | |
| 689 | 687 | goto zero_pad; |
| 690 | 688 | } |
| 691 | 689 | break; |
| 692 | 690 | case TOK_ASMDIR_set: |
| 693 | − next(); | |
| 694 | − tok1 = tok; | |
| 695 | − next(); | |
| 691 | + next(S); | |
| 692 | + tok1 = S->tccpp_tok; | |
| 693 | + next(S); | |
| 696 | 694 | /* Also accept '.set stuff', but don't do anything with this. |
| 697 | 695 | It's used in GAS to set various features like '.set mips16'. */ |
| 698 | − if (tok == ',') | |
| 699 | − set_symbol(s1, tok1); | |
| 696 | + if (S->tccpp_tok == ',') | |
| 697 | + set_symbol(S, tok1); | |
| 700 | 698 | break; |
| 701 | 699 | case TOK_ASMDIR_globl: |
| 702 | 700 | case TOK_ASMDIR_global: |
| 703 | 701 | case TOK_ASMDIR_weak: |
| 704 | 702 | case TOK_ASMDIR_hidden: |
| 705 | − tok1 = tok; | |
| 703 | + tok1 = S->tccpp_tok; | |
| 706 | 704 | do { |
| 707 | 705 | Sym *sym; |
| 708 | − next(); | |
| 709 | − sym = get_asm_sym(tok, NULL); | |
| 706 | + next(S); | |
| 707 | + sym = get_asm_sym(S, S->tccpp_tok, NULL); | |
| 710 | 708 | if (tok1 != TOK_ASMDIR_hidden) |
| 711 | 709 | sym->type.t &= ~VT_STATIC; |
| 712 | 710 | if (tok1 == TOK_ASMDIR_weak) |
| 713 | 711 | sym->a.weak = 1; |
| 714 | 712 | else if (tok1 == TOK_ASMDIR_hidden) |
| 715 | 713 | sym->a.visibility = STV_HIDDEN; |
| 716 | − update_storage(sym); | |
| 717 | − next(); | |
| 718 | − } while (tok == ','); | |
| 714 | + update_storage(S, sym); | |
| 715 | + next(S); | |
| 716 | + } while (S->tccpp_tok == ','); | |
| 719 | 717 | break; |
| 720 | 718 | case TOK_ASMDIR_string: |
| 721 | 719 | case TOK_ASMDIR_ascii: |
| @@ -724,21 +722,21 @@ static void asm_parse_directive(TCCState *s1, int global) · 2 unmodified lines | ||
| 724 | 722 | const uint8_t *p; |
| 725 | 723 | int i, size, t; |
| 726 | 724 | |
| 727 | − t = tok; | |
| 728 | − next(); | |
| 725 | + t = S->tccpp_tok; | |
| 726 | + next(S); | |
| 729 | 727 | for(;;) { |
| 730 | − if (tok != TOK_STR) | |
| 731 | − expect("string constant"); | |
| 732 | − p = tokc.str.data; | |
| 733 | − size = tokc.str.size; | |
| 728 | + if (S->tccpp_tok != TOK_STR) | |
| 729 | + expect(S, "string constant"); | |
| 730 | + p = S->tccpp_tokc.str.data; | |
| 731 | + size = S->tccpp_tokc.str.size; | |
| 734 | 732 | if (t == TOK_ASMDIR_ascii && size > 0) |
| 735 | 733 | size--; |
| 736 | 734 | for(i = 0; i < size; i++) |
| 737 | − g(p[i]); | |
| 738 | − next(); | |
| 739 | − if (tok == ',') { | |
| 740 | − next(); | |
| 741 | − } else if (tok != TOK_STR) { | |
| 735 | + g(S, p[i]); | |
| 736 | + next(S); | |
| 737 | + if (S->tccpp_tok == ',') { | |
| 738 | + next(S); | |
| 739 | + } else if (S->tccpp_tok != TOK_STR) { | |
| 742 | 740 | break; |
| 743 | 741 | } |
| 744 | 742 | } |
| @@ -749,18 +747,18 @@ static void asm_parse_directive(TCCState *s1, int global) · 4 unmodified lines | ||
| 749 | 747 | case TOK_ASMDIR_bss: |
| 750 | 748 | { |
| 751 | 749 | char sname[64]; |
| 752 | − tok1 = tok; | |
| 750 | + tok1 = S->tccpp_tok; | |
| 753 | 751 | n = 0; |
| 754 | − next(); | |
| 755 | − if (tok != ';' && tok != TOK_LINEFEED) { | |
| 756 | − n = asm_int_expr(s1); | |
| 757 | − next(); | |
| 752 | + next(S); | |
| 753 | + if (S->tccpp_tok != ';' && S->tccpp_tok != TOK_LINEFEED) { | |
| 754 | + n = asm_int_expr(S); | |
| 755 | + next(S); | |
| 758 | 756 | } |
| 759 | 757 | if (n) |
| 760 | − sprintf(sname, "%s%d", get_tok_str(tok1, NULL), n); | |
| 758 | + sprintf(sname, "%s%d", get_tok_str(S, tok1, NULL), n); | |
| 761 | 759 | else |
| 762 | − sprintf(sname, "%s", get_tok_str(tok1, NULL)); | |
| 763 | − use_section(s1, sname); | |
| 760 | + sprintf(sname, "%s", get_tok_str(S, tok1, NULL)); | |
| 761 | + use_section(S, sname); | |
| 764 | 762 | } |
| 765 | 763 | break; |
| 766 | 764 | case TOK_ASMDIR_file: |
| @@ -768,13 +766,13 @@ static void asm_parse_directive(TCCState *s1, int global) · 1 unmodified line | ||
| 768 | 766 | char filename[512]; |
| 769 | 767 | |
| 770 | 768 | filename[0] = '\0'; |
| 771 | − next(); | |
| 772 | − if (tok == TOK_STR) | |
| 773 | − pstrcat(filename, sizeof(filename), tokc.str.data); | |
| 769 | + next(S); | |
| 770 | + if (S->tccpp_tok == TOK_STR) | |
| 771 | + pstrcat(filename, sizeof(filename), S->tccpp_tokc.str.data); | |
| 774 | 772 | else |
| 775 | − pstrcat(filename, sizeof(filename), get_tok_str(tok, NULL)); | |
| 776 | − tcc_warning_c(warn_unsupported)("ignoring .file %s", filename); | |
| 777 | − next(); | |
| 773 | + pstrcat(filename, sizeof(filename), get_tok_str(S, S->tccpp_tok, NULL)); | |
| 774 | + tcc_warning_c(warn_unsupported)(S, "ignoring .file %s", filename); | |
| 775 | + next(S); | |
| 778 | 776 | } |
| 779 | 777 | break; |
| 780 | 778 | case TOK_ASMDIR_ident: |
| @@ -782,30 +780,30 @@ static void asm_parse_directive(TCCState *s1, int global) · 1 unmodified line | ||
| 782 | 780 | char ident[256]; |
| 783 | 781 | |
| 784 | 782 | ident[0] = '\0'; |
| 785 | − next(); | |
| 786 | − if (tok == TOK_STR) | |
| 787 | − pstrcat(ident, sizeof(ident), tokc.str.data); | |
| 783 | + next(S); | |
| 784 | + if (S->tccpp_tok == TOK_STR) | |
| 785 | + pstrcat(ident, sizeof(ident), S->tccpp_tokc.str.data); | |
| 788 | 786 | else |
| 789 | − pstrcat(ident, sizeof(ident), get_tok_str(tok, NULL)); | |
| 790 | − tcc_warning_c(warn_unsupported)("ignoring .ident %s", ident); | |
| 791 | − next(); | |
| 787 | + pstrcat(ident, sizeof(ident), get_tok_str(S, S->tccpp_tok, NULL)); | |
| 788 | + tcc_warning_c(warn_unsupported)(S, "ignoring .ident %s", ident); | |
| 789 | + next(S); | |
| 792 | 790 | } |
| 793 | 791 | break; |
| 794 | 792 | case TOK_ASMDIR_size: |
| 795 | 793 | { |
| 796 | 794 | Sym *sym; |
| 797 | 795 | |
| 798 | − next(); | |
| 799 | − sym = asm_label_find(tok); | |
| 796 | + next(S); | |
| 797 | + sym = asm_label_find(S, S->tccpp_tok); | |
| 800 | 798 | if (!sym) { |
| 801 | − tcc_error("label not found: %s", get_tok_str(tok, NULL)); | |
| 799 | + tcc_error(S, "label not found: %s", get_tok_str(S, S->tccpp_tok, NULL)); | |
| 802 | 800 | } |
| 803 | 801 | /* XXX .size name,label2-label1 */ |
| 804 | − tcc_warning_c(warn_unsupported)("ignoring .size %s,*", get_tok_str(tok, NULL)); | |
| 805 | − next(); | |
| 806 | − skip(','); | |
| 807 | − while (tok != TOK_LINEFEED && tok != ';' && tok != CH_EOF) { | |
| 808 | − next(); | |
| 802 | + tcc_warning_c(warn_unsupported)(S, "ignoring .size %s,*", get_tok_str(S, S->tccpp_tok, NULL)); | |
| 803 | + next(S); | |
| 804 | + skip(S, ','); | |
| 805 | + while (S->tccpp_tok != TOK_LINEFEED && S->tccpp_tok != ';' && S->tccpp_tok != CH_EOF) { | |
| 806 | + next(S); | |
| 809 | 807 | } |
| 810 | 808 | } |
| 811 | 809 | break; |
| @@ -814,182 +812,182 @@ static void asm_parse_directive(TCCState *s1, int global) · 2 unmodified lines | ||
| 814 | 812 | Sym *sym; |
| 815 | 813 | const char *newtype; |
| 816 | 814 | |
| 817 | − next(); | |
| 818 | − sym = get_asm_sym(tok, NULL); | |
| 819 | − next(); | |
| 820 | − skip(','); | |
| 821 | − if (tok == TOK_STR) { | |
| 822 | − newtype = tokc.str.data; | |
| 815 | + next(S); | |
| 816 | + sym = get_asm_sym(S, S->tccpp_tok, NULL); | |
| 817 | + next(S); | |
| 818 | + skip(S, ','); | |
| 819 | + if (S->tccpp_tok == TOK_STR) { | |
| 820 | + newtype = S->tccpp_tokc.str.data; | |
| 823 | 821 | } else { |
| 824 | − if (tok == '@' || tok == '%') | |
| 825 | − next(); | |
| 826 | − newtype = get_tok_str(tok, NULL); | |
| 822 | + if (S->tccpp_tok == '@' || S->tccpp_tok == '%') | |
| 823 | + next(S); | |
| 824 | + newtype = get_tok_str(S, S->tccpp_tok, NULL); | |
| 827 | 825 | } |
| 828 | 826 | |
| 829 | 827 | if (!strcmp(newtype, "function") || !strcmp(newtype, "STT_FUNC")) { |
| 830 | 828 | sym->type.t = (sym->type.t & ~VT_BTYPE) | VT_FUNC; |
| 831 | 829 | } else |
| 832 | − tcc_warning_c(warn_unsupported)("change type of '%s' from 0x%x to '%s' ignored", | |
| 833 | − get_tok_str(sym->v, NULL), sym->type.t, newtype); | |
| 830 | + tcc_warning_c(warn_unsupported)(S, "change type of '%s' from 0x%x to '%s' ignored", | |
| 831 | + get_tok_str(S, sym->v, NULL), sym->type.t, newtype); | |
| 834 | 832 | |
| 835 | − next(); | |
| 833 | + next(S); | |
| 836 | 834 | } |
| 837 | 835 | break; |
| 838 | 836 | case TOK_ASMDIR_pushsection: |
| 839 | 837 | case TOK_ASMDIR_section: |
| 840 | 838 | { |
| 841 | 839 | char sname[256]; |
| 842 | − int old_nb_section = s1->nb_sections; | |
| 840 | + int old_nb_section = S->nb_sections; | |
| 843 | 841 | |
| 844 | − tok1 = tok; | |
| 842 | + tok1 = S->tccpp_tok; | |
| 845 | 843 | /* XXX: support more options */ |
| 846 | − next(); | |
| 844 | + next(S); | |
| 847 | 845 | sname[0] = '\0'; |
| 848 | − while (tok != ';' && tok != TOK_LINEFEED && tok != ',') { | |
| 849 | − if (tok == TOK_STR) | |
| 850 | − pstrcat(sname, sizeof(sname), tokc.str.data); | |
| 846 | + while (S->tccpp_tok != ';' && S->tccpp_tok != TOK_LINEFEED && S->tccpp_tok != ',') { | |
| 847 | + if (S->tccpp_tok == TOK_STR) | |
| 848 | + pstrcat(sname, sizeof(sname), S->tccpp_tokc.str.data); | |
| 851 | 849 | else |
| 852 | − pstrcat(sname, sizeof(sname), get_tok_str(tok, NULL)); | |
| 853 | − next(); | |
| 850 | + pstrcat(sname, sizeof(sname), get_tok_str(S, S->tccpp_tok, NULL)); | |
| 851 | + next(S); | |
| 854 | 852 | } |
| 855 | − if (tok == ',') { | |
| 853 | + if (S->tccpp_tok == ',') { | |
| 856 | 854 | /* skip section options */ |
| 857 | − next(); | |
| 858 | − if (tok != TOK_STR) | |
| 859 | − expect("string constant"); | |
| 860 | − next(); | |
| 861 | − if (tok == ',') { | |
| 862 | − next(); | |
| 863 | − if (tok == '@' || tok == '%') | |
| 864 | − next(); | |
| 865 | − next(); | |
| 855 | + next(S); | |
| 856 | + if (S->tccpp_tok != TOK_STR) | |
| 857 | + expect(S, "string constant"); | |
| 858 | + next(S); | |
| 859 | + if (S->tccpp_tok == ',') { | |
| 860 | + next(S); | |
| 861 | + if (S->tccpp_tok == '@' || S->tccpp_tok == '%') | |
| 862 | + next(S); | |
| 863 | + next(S); | |
| 866 | 864 | } |
| 867 | 865 | } |
| 868 | − last_text_section = cur_text_section; | |
| 866 | + S->tccasm_last_text_section = cur_text_section; | |
| 869 | 867 | if (tok1 == TOK_ASMDIR_section) |
| 870 | − use_section(s1, sname); | |
| 868 | + use_section(S, sname); | |
| 871 | 869 | else |
| 872 | − push_section(s1, sname); | |
| 870 | + push_section(S, sname); | |
| 873 | 871 | /* If we just allocated a new section reset its alignment to |
| 874 | 872 | 1. new_section normally acts for GCC compatibility and |
| 875 | 873 | sets alignment to PTR_SIZE. The assembler behaves different. */ |
| 876 | − if (old_nb_section != s1->nb_sections) | |
| 874 | + if (old_nb_section != S->nb_sections) | |
| 877 | 875 | cur_text_section->sh_addralign = 1; |
| 878 | 876 | } |
| 879 | 877 | break; |
| 880 | 878 | case TOK_ASMDIR_previous: |
| 881 | 879 | { |
| 882 | 880 | Section *sec; |
| 883 | − next(); | |
| 884 | − if (!last_text_section) | |
| 885 | − tcc_error("no previous section referenced"); | |
| 881 | + next(S); | |
| 882 | + if (!S->tccasm_last_text_section) | |
| 883 | + tcc_error(S, "no previous section referenced"); | |
| 886 | 884 | sec = cur_text_section; |
| 887 | − use_section1(s1, last_text_section); | |
| 888 | − last_text_section = sec; | |
| 885 | + use_section1(S, S->tccasm_last_text_section); | |
| 886 | + S->tccasm_last_text_section = sec; | |
| 889 | 887 | } |
| 890 | 888 | break; |
| 891 | 889 | case TOK_ASMDIR_popsection: |
| 892 | − next(); | |
| 893 | − pop_section(s1); | |
| 890 | + next(S); | |
| 891 | + pop_section(S); | |
| 894 | 892 | break; |
| 895 | 893 | #ifdef TCC_TARGET_I386 |
| 896 | 894 | case TOK_ASMDIR_code16: |
| 897 | 895 | { |
| 898 | − next(); | |
| 899 | − s1->seg_size = 16; | |
| 896 | + next(S); | |
| 897 | + S->seg_size = 16; | |
| 900 | 898 | } |
| 901 | 899 | break; |
| 902 | 900 | case TOK_ASMDIR_code32: |
| 903 | 901 | { |
| 904 | − next(); | |
| 905 | − s1->seg_size = 32; | |
| 902 | + next(S); | |
| 903 | + S->seg_size = 32; | |
| 906 | 904 | } |
| 907 | 905 | break; |
| 908 | 906 | #endif |
| 909 | 907 | #ifdef TCC_TARGET_X86_64 |
| 910 | 908 | /* added for compatibility with GAS */ |
| 911 | 909 | case TOK_ASMDIR_code64: |
| 912 | − next(); | |
| 910 | + next(S); | |
| 913 | 911 | break; |
| 914 | 912 | #endif |
| 915 | 913 | default: |
| 916 | − tcc_error("unknown assembler directive '.%s'", get_tok_str(tok, NULL)); | |
| 914 | + tcc_error(S, "unknown assembler directive '.%s'", get_tok_str(S, S->tccpp_tok, NULL)); | |
| 917 | 915 | break; |
| 918 | 916 | } |
| 919 | 917 | } |
| 920 | 918 | |
| 921 | 919 | |
| 922 | 920 | /* assemble a file */ |
| 923 | −static int tcc_assemble_internal(TCCState *s1, int do_preprocess, int global) | |
| 921 | +static int tcc_assemble_internal(TCCState *S, int do_preprocess, int global) | |
| 924 | 922 | { |
| 925 | 923 | int opcode; |
| 926 | − int saved_parse_flags = parse_flags; | |
| 924 | + int saved_parse_flags = S->tccpp_parse_flags; | |
| 927 | 925 | |
| 928 | − parse_flags = PARSE_FLAG_ASM_FILE | PARSE_FLAG_TOK_STR; | |
| 926 | + S->tccpp_parse_flags = PARSE_FLAG_ASM_FILE | PARSE_FLAG_TOK_STR; | |
| 929 | 927 | if (do_preprocess) |
| 930 | − parse_flags |= PARSE_FLAG_PREPROCESS; | |
| 928 | + S->tccpp_parse_flags |= PARSE_FLAG_PREPROCESS; | |
| 931 | 929 | for(;;) { |
| 932 | − next(); | |
| 933 | − if (tok == TOK_EOF) | |
| 930 | + next(S); | |
| 931 | + if (S->tccpp_tok == TOK_EOF) | |
| 934 | 932 | break; |
| 935 | − parse_flags |= PARSE_FLAG_LINEFEED; /* XXX: suppress that hack */ | |
| 933 | + S->tccpp_parse_flags |= PARSE_FLAG_LINEFEED; /* XXX: suppress that hack */ | |
| 936 | 934 | redo: |
| 937 | − if (tok == '#') { | |
| 935 | + if (S->tccpp_tok == '#') { | |
| 938 | 936 | /* horrible gas comment */ |
| 939 | − while (tok != TOK_LINEFEED) | |
| 940 | − next(); | |
| 941 | − } else if (tok >= TOK_ASMDIR_FIRST && tok <= TOK_ASMDIR_LAST) { | |
| 942 | − asm_parse_directive(s1, global); | |
| 943 | − } else if (tok == TOK_PPNUM) { | |
| 937 | + while (S->tccpp_tok != TOK_LINEFEED) | |
| 938 | + next(S); | |
| 939 | + } else if (S->tccpp_tok >= TOK_ASMDIR_FIRST && S->tccpp_tok <= TOK_ASMDIR_LAST) { | |
| 940 | + asm_parse_directive(S, global); | |
| 941 | + } else if (S->tccpp_tok == TOK_PPNUM) { | |
| 944 | 942 | const char *p; |
| 945 | 943 | int n; |
| 946 | − p = tokc.str.data; | |
| 944 | + p = S->tccpp_tokc.str.data; | |
| 947 | 945 | n = strtoul(p, (char **)&p, 10); |
| 948 | 946 | if (*p != '\0') |
| 949 | − expect("':'"); | |
| 947 | + expect(S, "':'"); | |
| 950 | 948 | /* new local label */ |
| 951 | − asm_new_label(s1, asm_get_local_label_name(s1, n), 1); | |
| 952 | − next(); | |
| 953 | − skip(':'); | |
| 949 | + asm_new_label(S, asm_get_local_label_name(S, n), 1); | |
| 950 | + next(S); | |
| 951 | + skip(S, ':'); | |
| 954 | 952 | goto redo; |
| 955 | − } else if (tok >= TOK_IDENT) { | |
| 953 | + } else if (S->tccpp_tok >= TOK_IDENT) { | |
| 956 | 954 | /* instruction or label */ |
| 957 | − opcode = tok; | |
| 958 | − next(); | |
| 959 | − if (tok == ':') { | |
| 955 | + opcode = S->tccpp_tok; | |
| 956 | + next(S); | |
| 957 | + if (S->tccpp_tok == ':') { | |
| 960 | 958 | /* new label */ |
| 961 | − asm_new_label(s1, opcode, 0); | |
| 962 | − next(); | |
| 959 | + asm_new_label(S, opcode, 0); | |
| 960 | + next(S); | |
| 963 | 961 | goto redo; |
| 964 | − } else if (tok == '=') { | |
| 965 | − set_symbol(s1, opcode); | |
| 962 | + } else if (S->tccpp_tok == '=') { | |
| 963 | + set_symbol(S, opcode); | |
| 966 | 964 | goto redo; |
| 967 | 965 | } else { |
| 968 | − asm_opcode(s1, opcode); | |
| 966 | + asm_opcode(S, opcode); | |
| 969 | 967 | } |
| 970 | 968 | } |
| 971 | 969 | /* end of line */ |
| 972 | − if (tok != ';' && tok != TOK_LINEFEED) | |
| 973 | − expect("end of line"); | |
| 974 | − parse_flags &= ~PARSE_FLAG_LINEFEED; /* XXX: suppress that hack */ | |
| 970 | + if (S->tccpp_tok != ';' && S->tccpp_tok != TOK_LINEFEED) | |
| 971 | + expect(S, "end of line"); | |
| 972 | + S->tccpp_parse_flags &= ~PARSE_FLAG_LINEFEED; /* XXX: suppress that hack */ | |
| 975 | 973 | } |
| 976 | 974 | |
| 977 | − parse_flags = saved_parse_flags; | |
| 975 | + S->tccpp_parse_flags = saved_parse_flags; | |
| 978 | 976 | return 0; |
| 979 | 977 | } |
| 980 | 978 | |
| 981 | 979 | /* Assemble the current file */ |
| 982 | −ST_FUNC int tcc_assemble(TCCState *s1, int do_preprocess) | |
| 980 | +ST_FUNC int tcc_assemble(TCCState *S, int do_preprocess) | |
| 983 | 981 | { |
| 984 | 982 | int ret; |
| 985 | − tcc_debug_start(s1); | |
| 983 | + tcc_debug_start(S); | |
| 986 | 984 | /* default section is text */ |
| 987 | 985 | cur_text_section = text_section; |
| 988 | − ind = cur_text_section->data_offset; | |
| 989 | − nocode_wanted = 0; | |
| 990 | − ret = tcc_assemble_internal(s1, do_preprocess, 1); | |
| 991 | − cur_text_section->data_offset = ind; | |
| 992 | − tcc_debug_end(s1); | |
| 986 | + S->tccgen_ind = cur_text_section->data_offset; | |
| 987 | + S->tccgen_nocode_wanted = 0; | |
| 988 | + ret = tcc_assemble_internal(S, do_preprocess, 1); | |
| 989 | + cur_text_section->data_offset = S->tccgen_ind; | |
| 990 | + tcc_debug_end(S); | |
| 993 | 991 | return ret; |
| 994 | 992 | } |
| 995 | 993 | |
| @@ -999,27 +997,27 @@ ST_FUNC int tcc_assemble(TCCState *s1, int do_preprocess) · 3 unmodified lines | ||
| 999 | 997 | /* assemble the string 'str' in the current C compilation unit without |
| 1000 | 998 | C preprocessing. NOTE: str is modified by modifying the '\0' at the |
| 1001 | 999 | end */ |
| 1002 | −static void tcc_assemble_inline(TCCState *s1, char *str, int len, int global) | |
| 1000 | +static void tcc_assemble_inline(TCCState *S, char *str, int len, int global) | |
| 1003 | 1001 | { |
| 1004 | − const int *saved_macro_ptr = macro_ptr; | |
| 1005 | − int dotid = set_idnum('.', IS_ID); | |
| 1006 | − int dolid = set_idnum('$', 0); | |
| 1007 | − | |
| 1008 | − tcc_open_bf(s1, ":asm:", len); | |
| 1009 | − memcpy(file->buffer, str, len); | |
| 1010 | − macro_ptr = NULL; | |
| 1011 | − tcc_assemble_internal(s1, 0, global); | |
| 1012 | − tcc_close(); | |
| 1013 | − | |
| 1014 | − set_idnum('$', dolid); | |
| 1015 | − set_idnum('.', dotid); | |
| 1016 | − macro_ptr = saved_macro_ptr; | |
| 1002 | + const int *saved_macro_ptr = S->tccpp_macro_ptr; | |
| 1003 | + int dotid = set_idnum(S, '.', IS_ID); | |
| 1004 | + int dolid = set_idnum(S, '$', 0); | |
| 1005 | + | |
| 1006 | + tcc_open_bf(S, ":asm:", len); | |
| 1007 | + memcpy(S->tccpp_file->buffer, str, len); | |
| 1008 | + S->tccpp_macro_ptr = NULL; | |
| 1009 | + tcc_assemble_internal(S, 0, global); | |
| 1010 | + tcc_close(S); | |
| 1011 | + | |
| 1012 | + set_idnum(S, '$', dolid); | |
| 1013 | + set_idnum(S, '.', dotid); | |
| 1014 | + S->tccpp_macro_ptr = saved_macro_ptr; | |
| 1017 | 1015 | } |
| 1018 | 1016 | |
| 1019 | 1017 | /* find a constraint by its number or id (gcc 3 extended |
| 1020 | 1018 | syntax). return -1 if not found. Return in *pp in char after the |
| 1021 | 1019 | constraint */ |
| 1022 | −ST_FUNC int find_constraint(ASMOperand *operands, int nb_operands, | |
| 1020 | +ST_FUNC int find_constraint(TCCState* S, ASMOperand *operands, int nb_operands, | |
| 1023 | 1021 | const char *name, const char **pp) |
| 1024 | 1022 | { |
| 1025 | 1023 | int index; |
| @@ -1038,7 +1036,7 @@ ST_FUNC int find_constraint(ASMOperand *operands, int nb_operands, · 12 unmodified lines | ||
| 1038 | 1036 | name++; |
| 1039 | 1037 | p = strchr(name, ']'); |
339 more lines aren’t shown here.
This diff is large: its 368 lines aren’t shown here.
This diff is large: its 3251 lines aren’t shown here.
This diff is large: its 9788 lines aren’t shown here.
This diff is large: its 616 lines aren’t shown here.
This diff is large: its 960 lines aren’t shown here.
This diff is large: its 4250 lines aren’t shown here.
This diff is large: its 262 lines aren’t shown here.
This diff is large: its 311 lines aren’t shown here.
This diff is large: its 188 lines aren’t shown here.
This diff is large: its 2366 lines aren’t shown here.
This diff is large: its 222 lines aren’t shown here.