Skip to content

Commit ea227e2

Browse files
jcmvbkbcmdroth
authored andcommitted
target-xtensa: add missing window check for entry
Entry opcode needs to check if moving to new register frame would cause register window overflow. Entry used in function prologue never overflows because preceding windowed call* opcode writes return address to the target register window frame, causing overflow exceptions at the point of call. But when a sequence of entry opcodes is used for register window spilling there may not be a call or other opcode that would cause window check between entries and they would not raise overflow exception themselves resulting in data corruption. Cc: [email protected] Signed-off-by: Max Filippov <[email protected]> (cherry picked from commit 1b3e71f) Signed-off-by: Michael Roth <[email protected]>
1 parent aae114b commit ea227e2

File tree

2 files changed

+12
-0
lines changed

2 files changed

+12
-0
lines changed

target-xtensa/cpu.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -471,6 +471,12 @@ static inline xtensa_tlb_entry *xtensa_tlb_get_entry(CPUXtensaState *env,
471471
env->itlb[wi] + ei;
472472
}
473473

474+
static inline uint32_t xtensa_replicate_windowstart(CPUXtensaState *env)
475+
{
476+
return env->sregs[WINDOW_START] |
477+
(env->sregs[WINDOW_START] << env->config->nareg / 4);
478+
}
479+
474480
/* MMU modes definitions */
475481
#define MMU_MODE0_SUFFIX _ring0
476482
#define MMU_MODE1_SUFFIX _ring1

target-xtensa/op_helper.c

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -235,6 +235,12 @@ void HELPER(entry)(CPUXtensaState *env, uint32_t pc, uint32_t s, uint32_t imm)
235235
pc, env->sregs[PS]);
236236
HELPER(exception_cause)(env, pc, ILLEGAL_INSTRUCTION_CAUSE);
237237
} else {
238+
uint32_t windowstart = xtensa_replicate_windowstart(env) >>
239+
(env->sregs[WINDOW_BASE] + 1);
240+
241+
if (windowstart & ((1 << callinc) - 1)) {
242+
HELPER(window_check)(env, pc, callinc);
243+
}
238244
env->regs[(callinc << 2) | (s & 3)] = env->regs[s] - (imm << 3);
239245
rotate_window(env, callinc);
240246
env->sregs[WINDOW_START] |=

0 commit comments

Comments
 (0)