[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 030/126] target-s390: Send signals for divide
From: |
Richard Henderson |
Subject: |
[Qemu-devel] [PATCH 030/126] target-s390: Send signals for divide |
Date: |
Sun, 9 Sep 2012 14:04:48 -0700 |
Signed-off-by: Richard Henderson <address@hidden>
---
target-s390x/cpu.h | 2 ++
target-s390x/int_helper.c | 51 ++++++++++++++++++++++++++++++++++++++++------
target-s390x/misc_helper.c | 22 ++++++++++++++++++++
3 files changed, 69 insertions(+), 6 deletions(-)
diff --git a/target-s390x/cpu.h b/target-s390x/cpu.h
index 52ab5ea..7d89a6f 100644
--- a/target-s390x/cpu.h
+++ b/target-s390x/cpu.h
@@ -934,5 +934,7 @@ uint32_t set_cc_nz_f64(float64 v);
/* misc_helper.c */
void program_interrupt(CPUS390XState *env, uint32_t code, int ilc);
+void QEMU_NORETURN runtime_exception(CPUS390XState *env, int excp,
+ uintptr_t retaddr);
#endif
diff --git a/target-s390x/int_helper.c b/target-s390x/int_helper.c
index fe1cb87..f2f420c 100644
--- a/target-s390x/int_helper.c
+++ b/target-s390x/int_helper.c
@@ -38,22 +38,54 @@ uint64_t HELPER(mul128)(CPUS390XState *env, uint64_t v1,
uint64_t v2)
}
/* 64/32 -> 32 signed division */
-int64_t HELPER(divs32)(CPUS390XState *env, int64_t a, int64_t b)
+int64_t HELPER(divs32)(CPUS390XState *env, int64_t a, int64_t b64)
{
- env->retxl = a % (int32_t)b;
- return a / (int32_t)b;
+ int32_t ret, b = b64;
+ int64_t q;
+
+ if (b == 0) {
+ runtime_exception(env, PGM_FIXPT_DIVIDE, GETPC());
+ }
+
+ ret = q = a / b;
+ env->retxl = a % b;
+
+ /* Catch non-representable quotient. */
+ if (ret != q) {
+ runtime_exception(env, PGM_FIXPT_DIVIDE, GETPC());
+ }
+
+ return ret;
}
/* 64/32 -> 32 unsigned division */
-uint64_t HELPER(divu32)(CPUS390XState *env, uint64_t a, uint64_t b)
+uint64_t HELPER(divu32)(CPUS390XState *env, uint64_t a, uint64_t b64)
{
- env->retxl = a % (uint32_t)b;
- return a / (uint32_t)b;
+ uint32_t ret, b = b64;
+ uint64_t q;
+
+ if (b == 0) {
+ runtime_exception(env, PGM_FIXPT_DIVIDE, GETPC());
+ }
+
+ ret = q = a / b;
+ env->retxl = a % b;
+
+ /* Catch non-representable quotient. */
+ if (ret != q) {
+ runtime_exception(env, PGM_FIXPT_DIVIDE, GETPC());
+ }
+
+ return ret;
}
/* 64/64 -> 64 signed division */
int64_t HELPER(divs64)(CPUS390XState *env, int64_t a, int64_t b)
{
+ /* Catch divide by zero, and non-representable quotient (MIN / -1). */
+ if (b == 0 || (b == -1 && a == (1ll << 63))) {
+ runtime_exception(env, PGM_FIXPT_DIVIDE, GETPC());
+ }
env->retxl = a % b;
return a / b;
}
@@ -63,6 +95,10 @@ uint64_t HELPER(divu64)(CPUS390XState *env, uint64_t ah,
uint64_t al,
uint64_t b)
{
uint64_t ret;
+ /* Signal divide by zero. */
+ if (b == 0) {
+ runtime_exception(env, PGM_FIXPT_DIVIDE, GETPC());
+ }
if (ah == 0) {
/* 64 -> 64/64 case */
env->retxl = al % b;
@@ -75,6 +111,9 @@ uint64_t HELPER(divu64)(CPUS390XState *env, uint64_t ah,
uint64_t al,
__uint128_t q = a / b;
env->retxl = a % b;
ret = q;
+ if (ret != q) {
+ runtime_exception(env, PGM_FIXPT_DIVIDE, GETPC());
+ }
#else
/* 32-bit hosts would need special wrapper functionality - just abort
if
we encounter such a case; it's very unlikely anyways. */
diff --git a/target-s390x/misc_helper.c b/target-s390x/misc_helper.c
index 1502f15..32b75f2 100644
--- a/target-s390x/misc_helper.c
+++ b/target-s390x/misc_helper.c
@@ -69,6 +69,28 @@
do { } while (0)
#endif
+void QEMU_NORETURN runtime_exception(CPUS390XState *env, int excp,
+ uintptr_t retaddr)
+{
+ TranslationBlock *tb;
+ int t;
+
+ env->exception_index = EXCP_PGM;
+ env->int_pgm_code = excp;
+
+ /* Use the (ultimate) callers address to find the insn that trapped. */
+ tb = tb_find_pc(retaddr);
+ assert(tb != NULL);
+ cpu_restore_state(tb, env, retaddr);
+
+ /* Advance past the insn. */
+ t = cpu_ldub_code(env, env->psw.addr);
+ env->int_pgm_ilc = t = get_ilc(t);
+ env->psw.addr += 2 * t;
+
+ cpu_loop_exit(env);
+}
+
void HELPER(exception)(CPUS390XState *env, uint32_t excp)
{
HELPER_LOG("%s: exception %d\n", __func__, excp);
--
1.7.11.4
- [Qemu-devel] [PATCH 008/126] target-s390: Add format based disassassmbly infrastructure, (continued)
- [Qemu-devel] [PATCH 008/126] target-s390: Add format based disassassmbly infrastructure, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 022/126] target-s390: Convert LOAD COMPLIMENT, POSITIVE, NEGATIVE, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 023/126] target-s390: Convert AND, OR, XOR, INSERT IMMEDIATE, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 019/126] target-s390: Convert LOAD (LOGICAL) BYTE, CHARACTER, HALFWORD, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 024/126] target-s390: Convert STORE, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 026/126] target-s390: Convert BRANCH AND SAVE, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 021/126] target-s390: Convert LOAD LOGICAL IMMEDIATE, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 025/126] target-s390: Convert ADD LOGICAL CARRY and SUBTRACT LOGICAL BORROW, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 027/126] target-s390: Convert BRANCH ON CONDITION, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 032/126] target-s390: Convert SET ADDRESSING MODE, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 030/126] target-s390: Send signals for divide,
Richard Henderson <=
- [Qemu-devel] [PATCH 029/126] target-s390: Convert DIVIDE, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 028/126] target-s390: Convert BRANCH ON COUNT, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 031/126] target-s390: Convert TEST UNDER MASK, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 034/126] target-s390: Convert MOVE LONG, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 036/126] target-s390: Convert INSERT CHARACTER, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 035/126] target-s390: Convert FP LOAD, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 033/126] target-s390: Convert SUPERVISOR CALL, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 038/126] target-s390: Convert INSERT CHARACTERS UNDER MASK, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 042/126] target-s390: Convert SET SYSTEM MASK, Richard Henderson, 2012/09/09
- [Qemu-devel] [PATCH 049/126] target-s390: Convert NI, XI, OI, Richard Henderson, 2012/09/09