From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([2001:4830:134:3::10]:60577) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Y9H06-0004Lf-9x for qemu-devel@nongnu.org; Thu, 08 Jan 2015 12:36:29 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1Y9Gzq-0006o4-Fe for qemu-devel@nongnu.org; Thu, 08 Jan 2015 12:36:02 -0500 Received: from e9.ny.us.ibm.com ([32.97.182.139]:46558) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Y9Gzp-0006nX-TC for qemu-devel@nongnu.org; Thu, 08 Jan 2015 12:35:46 -0500 Received: from /spool/local by e9.ny.us.ibm.com with IBM ESMTP SMTP Gateway: Authorized Use Only! Violators will be prosecuted for from ; Thu, 8 Jan 2015 12:35:45 -0500 From: Michael Roth Date: Thu, 8 Jan 2015 11:34:02 -0600 Message-Id: <1420738472-23267-59-git-send-email-mdroth@linux.vnet.ibm.com> In-Reply-To: <1420738472-23267-1-git-send-email-mdroth@linux.vnet.ibm.com> References: <1420738472-23267-1-git-send-email-mdroth@linux.vnet.ibm.com> Subject: [Qemu-devel] [PATCH 58/88] target-xtensa: add missing window check for entry List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Cc: qemu-stable@nongnu.org From: Max Filippov 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: qemu-stable@nongnu.org Signed-off-by: Max Filippov (cherry picked from commit 1b3e71f8ee17ced609213d9b41758110f3c026e9) Signed-off-by: Michael Roth --- target-xtensa/cpu.h | 6 ++++++ target-xtensa/op_helper.c | 6 ++++++ 2 files changed, 12 insertions(+) diff --git a/target-xtensa/cpu.h b/target-xtensa/cpu.h index d797d26..6e4e2b2 100644 --- a/target-xtensa/cpu.h +++ b/target-xtensa/cpu.h @@ -471,6 +471,12 @@ static inline xtensa_tlb_entry *xtensa_tlb_get_entry(CPUXtensaState *env, env->itlb[wi] + ei; } +static inline uint32_t xtensa_replicate_windowstart(CPUXtensaState *env) +{ + return env->sregs[WINDOW_START] | + (env->sregs[WINDOW_START] << env->config->nareg / 4); +} + /* MMU modes definitions */ #define MMU_MODE0_SUFFIX _ring0 #define MMU_MODE1_SUFFIX _ring1 diff --git a/target-xtensa/op_helper.c b/target-xtensa/op_helper.c index dae1386..872e5a8 100644 --- a/target-xtensa/op_helper.c +++ b/target-xtensa/op_helper.c @@ -235,6 +235,12 @@ void HELPER(entry)(CPUXtensaState *env, uint32_t pc, uint32_t s, uint32_t imm) pc, env->sregs[PS]); HELPER(exception_cause)(env, pc, ILLEGAL_INSTRUCTION_CAUSE); } else { + uint32_t windowstart = xtensa_replicate_windowstart(env) >> + (env->sregs[WINDOW_BASE] + 1); + + if (windowstart & ((1 << callinc) - 1)) { + HELPER(window_check)(env, pc, callinc); + } env->regs[(callinc << 2) | (s & 3)] = env->regs[s] - (imm << 3); rotate_window(env, callinc); env->sregs[WINDOW_START] |= -- 1.9.1