target-alpha: Clean up arithmetic traps.
Replace the EXCP_ARITH_OVERFLOW placeholder with the complete set of bits from the EXC_SUM IPR. Use them in the existing places where we raise arithmetic exceptions. Signed-off-by: Richard Henderson <rth@twiddle.net> Signed-off-by: Aurelien Jarno <aurelien@aurel32.net>
This commit is contained in:
parent
dad081ee69
commit
866be65dfd
|
@ -450,9 +450,13 @@ enum {
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Arithmetic exception */
|
/* Arithmetic exception */
|
||||||
enum {
|
#define EXC_M_IOV (1<<16) /* Integer Overflow */
|
||||||
EXCP_ARITH_OVERFLOW,
|
#define EXC_M_INE (1<<15) /* Inexact result */
|
||||||
};
|
#define EXC_M_UNF (1<<14) /* Underflow */
|
||||||
|
#define EXC_M_FOV (1<<13) /* Overflow */
|
||||||
|
#define EXC_M_DZE (1<<12) /* Division by zero */
|
||||||
|
#define EXC_M_INV (1<<11) /* Invalid operation */
|
||||||
|
#define EXC_M_SWC (1<<10) /* Software completion */
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
IR_V0 = 0,
|
IR_V0 = 0,
|
||||||
|
|
|
@ -78,7 +78,7 @@ uint64_t helper_addqv (uint64_t op1, uint64_t op2)
|
||||||
uint64_t tmp = op1;
|
uint64_t tmp = op1;
|
||||||
op1 += op2;
|
op1 += op2;
|
||||||
if (unlikely((tmp ^ op2 ^ (-1ULL)) & (tmp ^ op1) & (1ULL << 63))) {
|
if (unlikely((tmp ^ op2 ^ (-1ULL)) & (tmp ^ op1) & (1ULL << 63))) {
|
||||||
helper_excp(EXCP_ARITH, EXCP_ARITH_OVERFLOW);
|
helper_excp(EXCP_ARITH, EXC_M_IOV);
|
||||||
}
|
}
|
||||||
return op1;
|
return op1;
|
||||||
}
|
}
|
||||||
|
@ -88,7 +88,7 @@ uint64_t helper_addlv (uint64_t op1, uint64_t op2)
|
||||||
uint64_t tmp = op1;
|
uint64_t tmp = op1;
|
||||||
op1 = (uint32_t)(op1 + op2);
|
op1 = (uint32_t)(op1 + op2);
|
||||||
if (unlikely((tmp ^ op2 ^ (-1UL)) & (tmp ^ op1) & (1UL << 31))) {
|
if (unlikely((tmp ^ op2 ^ (-1UL)) & (tmp ^ op1) & (1UL << 31))) {
|
||||||
helper_excp(EXCP_ARITH, EXCP_ARITH_OVERFLOW);
|
helper_excp(EXCP_ARITH, EXC_M_IOV);
|
||||||
}
|
}
|
||||||
return op1;
|
return op1;
|
||||||
}
|
}
|
||||||
|
@ -98,7 +98,7 @@ uint64_t helper_subqv (uint64_t op1, uint64_t op2)
|
||||||
uint64_t res;
|
uint64_t res;
|
||||||
res = op1 - op2;
|
res = op1 - op2;
|
||||||
if (unlikely((op1 ^ op2) & (res ^ op1) & (1ULL << 63))) {
|
if (unlikely((op1 ^ op2) & (res ^ op1) & (1ULL << 63))) {
|
||||||
helper_excp(EXCP_ARITH, EXCP_ARITH_OVERFLOW);
|
helper_excp(EXCP_ARITH, EXC_M_IOV);
|
||||||
}
|
}
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
@ -108,7 +108,7 @@ uint64_t helper_sublv (uint64_t op1, uint64_t op2)
|
||||||
uint32_t res;
|
uint32_t res;
|
||||||
res = op1 - op2;
|
res = op1 - op2;
|
||||||
if (unlikely((op1 ^ op2) & (res ^ op1) & (1UL << 31))) {
|
if (unlikely((op1 ^ op2) & (res ^ op1) & (1UL << 31))) {
|
||||||
helper_excp(EXCP_ARITH, EXCP_ARITH_OVERFLOW);
|
helper_excp(EXCP_ARITH, EXC_M_IOV);
|
||||||
}
|
}
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
@ -118,7 +118,7 @@ uint64_t helper_mullv (uint64_t op1, uint64_t op2)
|
||||||
int64_t res = (int64_t)op1 * (int64_t)op2;
|
int64_t res = (int64_t)op1 * (int64_t)op2;
|
||||||
|
|
||||||
if (unlikely((int32_t)res != res)) {
|
if (unlikely((int32_t)res != res)) {
|
||||||
helper_excp(EXCP_ARITH, EXCP_ARITH_OVERFLOW);
|
helper_excp(EXCP_ARITH, EXC_M_IOV);
|
||||||
}
|
}
|
||||||
return (int64_t)((int32_t)res);
|
return (int64_t)((int32_t)res);
|
||||||
}
|
}
|
||||||
|
@ -130,7 +130,7 @@ uint64_t helper_mulqv (uint64_t op1, uint64_t op2)
|
||||||
muls64(&tl, &th, op1, op2);
|
muls64(&tl, &th, op1, op2);
|
||||||
/* If th != 0 && th != -1, then we had an overflow */
|
/* If th != 0 && th != -1, then we had an overflow */
|
||||||
if (unlikely((th + 1) > 1)) {
|
if (unlikely((th + 1) > 1)) {
|
||||||
helper_excp(EXCP_ARITH, EXCP_ARITH_OVERFLOW);
|
helper_excp(EXCP_ARITH, EXC_M_IOV);
|
||||||
}
|
}
|
||||||
return tl;
|
return tl;
|
||||||
}
|
}
|
||||||
|
@ -987,7 +987,7 @@ static inline uint64_t __helper_cvtql(uint64_t a, int s, int v)
|
||||||
r |= ((uint64_t)(a & 0x7FFFFFFF)) << 29;
|
r |= ((uint64_t)(a & 0x7FFFFFFF)) << 29;
|
||||||
|
|
||||||
if (v && (int64_t)((int32_t)r) != (int64_t)r) {
|
if (v && (int64_t)((int32_t)r) != (int64_t)r) {
|
||||||
helper_excp(EXCP_ARITH, EXCP_ARITH_OVERFLOW);
|
helper_excp(EXCP_ARITH, EXC_M_IOV);
|
||||||
}
|
}
|
||||||
if (s) {
|
if (s) {
|
||||||
/* TODO */
|
/* TODO */
|
||||||
|
|
Loading…
Reference in a new issue