Skip to content

Commit 8279166

Browse files
committed
Fix undefined behavior caused by mismatched parameter types
When using 'make ENABLE_UBSAN=1 check CC=clang', the following error is observed: src/emulate.c:1110:13: runtime error: call to function do_fuse1 through pointer to incorrect function type 'bool (*)(struct riscv_internal *, const struct rv_insn *, unsigned long, unsigned int)' /home/eleanor/code/rv32emu/src/emulate.c:415: note: do_fuse1 defined here SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior src/emulate.c:1110:13 After fixing the first error with 'do_fuse1', similar errors were observed for other functions like 'do_fuse2', 'do_fuse3', 'do_fuse4', and 'do_jal'. The root cause was type mismatches in parameter declarations, where 'rv_insn_t *' was used instead of the expected 'const rv_insn_t *'. Since 'do_jal' was generated by the 'RVOP' macro in 'rv32emu_template.c', the macro was also corrected. These changes resolve the UBSAN errors and align all function pointers and implementations.
1 parent cffc5ff commit 8279166

File tree

1 file changed

+45
-33
lines changed

1 file changed

+45
-33
lines changed

src/emulate.c

Lines changed: 45 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -376,42 +376,45 @@ static uint32_t peripheral_update_ctr = 64;
376376
#endif
377377

378378
/* Interpreter-based execution path */
379-
#define RVOP(inst, code, asm) \
380-
static bool do_##inst(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, \
381-
uint32_t PC) \
382-
{ \
383-
IIF(RV32_HAS(SYSTEM))(ctr++;, ) cycle++; \
384-
code; \
385-
IIF(RV32_HAS(SYSTEM)) \
386-
( \
387-
if (need_handle_signal) { \
388-
need_handle_signal = false; \
389-
return true; \
390-
}, ) nextop : PC += __rv_insn_##inst##_len; \
391-
IIF(RV32_HAS(SYSTEM)) \
392-
(IIF(RV32_HAS(JIT))( \
393-
, if (unlikely(need_clear_block_map)) { \
394-
block_map_clear(rv); \
395-
need_clear_block_map = false; \
396-
rv->csr_cycle = cycle; \
397-
rv->PC = PC; \
398-
return false; \
399-
}), ); \
400-
if (unlikely(RVOP_NO_NEXT(ir))) \
401-
goto end_op; \
402-
const rv_insn_t *next = ir->next; \
403-
MUST_TAIL return next->impl(rv, next, cycle, PC); \
404-
end_op: \
405-
rv->csr_cycle = cycle; \
406-
rv->PC = PC; \
407-
return true; \
379+
#define RVOP(inst, code, asm) \
380+
static bool do_##inst(riscv_t *rv, const rv_insn_t *ir, uint64_t cycle, \
381+
uint32_t PC) \
382+
{ \
383+
IIF(RV32_HAS(SYSTEM))(ctr++;, ) cycle++; \
384+
code; \
385+
IIF(RV32_HAS(SYSTEM)) \
386+
( \
387+
if (need_handle_signal) { \
388+
need_handle_signal = false; \
389+
return true; \
390+
}, ) nextop : PC += __rv_insn_##inst##_len; \
391+
IIF(RV32_HAS(SYSTEM)) \
392+
(IIF(RV32_HAS(JIT))( \
393+
, if (unlikely(need_clear_block_map)) { \
394+
block_map_clear(rv); \
395+
need_clear_block_map = false; \
396+
rv->csr_cycle = cycle; \
397+
rv->PC = PC; \
398+
return false; \
399+
}), ); \
400+
if (unlikely(RVOP_NO_NEXT(ir))) \
401+
goto end_op; \
402+
const rv_insn_t *next = ir->next; \
403+
MUST_TAIL return next->impl(rv, next, cycle, PC); \
404+
end_op: \
405+
rv->csr_cycle = cycle; \
406+
rv->PC = PC; \
407+
return true; \
408408
}
409409

410410
#include "rv32_template.c"
411411
#undef RVOP
412412

413413
/* multiple LUI */
414-
static bool do_fuse1(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, uint32_t PC)
414+
static bool do_fuse1(riscv_t *rv,
415+
const rv_insn_t *ir,
416+
uint64_t cycle,
417+
uint32_t PC)
415418
{
416419
cycle += ir->imm2;
417420
opcode_fuse_t *fuse = ir->fuse;
@@ -428,7 +431,10 @@ static bool do_fuse1(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, uint32_t PC)
428431
}
429432

430433
/* LUI + ADD */
431-
static bool do_fuse2(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, uint32_t PC)
434+
static bool do_fuse2(riscv_t *rv,
435+
const rv_insn_t *ir,
436+
uint64_t cycle,
437+
uint32_t PC)
432438
{
433439
cycle += 2;
434440
rv->X[ir->rd] = ir->imm;
@@ -444,7 +450,10 @@ static bool do_fuse2(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, uint32_t PC)
444450
}
445451

446452
/* multiple SW */
447-
static bool do_fuse3(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, uint32_t PC)
453+
static bool do_fuse3(riscv_t *rv,
454+
const rv_insn_t *ir,
455+
uint64_t cycle,
456+
uint32_t PC)
448457
{
449458
cycle += ir->imm2;
450459
opcode_fuse_t *fuse = ir->fuse;
@@ -468,7 +477,10 @@ static bool do_fuse3(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, uint32_t PC)
468477
}
469478

470479
/* multiple LW */
471-
static bool do_fuse4(riscv_t *rv, rv_insn_t *ir, uint64_t cycle, uint32_t PC)
480+
static bool do_fuse4(riscv_t *rv,
481+
const rv_insn_t *ir,
482+
uint64_t cycle,
483+
uint32_t PC)
472484
{
473485
cycle += ir->imm2;
474486
opcode_fuse_t *fuse = ir->fuse;

0 commit comments

Comments
 (0)