diff options
author | Quentin Carbonneaux <quentin@c9x.me> | 2019-04-29 11:29:22 +0200 |
---|---|---|
committer | Quentin Carbonneaux <quentin@c9x.me> | 2019-04-29 12:01:54 +0200 |
commit | 660a8d9dfa44050897b2f5ead823554893d79f24 (patch) | |
tree | d24f77c684f7439c193bb6a7898fafad50eb48f3 /fold.c | |
parent | 0384d73e8daa5c948fb08c7301144c0d7e740ef9 (diff) | |
download | roux-660a8d9dfa44050897b2f5ead823554893d79f24.tar.gz |
fix folding of unsigned operations
This fixes similar bugs than the ones fixed in the previous commit. In the folding code the invariant is that when a result is 32 bits wide, the low 32 bits of 'x' are correct. The high bits can be anything.
Diffstat (limited to 'fold.c')
-rw-r--r-- | fold.c | 6 |
1 files changed, 3 insertions, 3 deletions
diff --git a/fold.c b/fold.c index 521c911..0a3945f 100644 --- a/fold.c +++ b/fold.c @@ -373,14 +373,14 @@ foldint(Con *res, int op, int w, Con *cl, Con *cr) case Osub: x = l.u - r.u; break; case Odiv: x = w ? l.s / r.s : (int32_t)l.s / (int32_t)r.s; break; case Orem: x = w ? l.s % r.s : (int32_t)l.s % (int32_t)r.s; break; - case Oudiv: x = l.u / r.u; break; - case Ourem: x = l.u % r.u; break; + case Oudiv: x = w ? l.u / r.u : (uint32_t)l.u / (uint32_t)r.u; break; + case Ourem: x = w ? l.u % r.u : (uint32_t)l.u % (uint32_t)r.u; break; case Omul: x = l.u * r.u; break; case Oand: x = l.u & r.u; break; case Oor: x = l.u | r.u; break; case Oxor: x = l.u ^ r.u; break; case Osar: x = (w ? l.s : (int32_t)l.s) >> (r.u & 63); break; - case Oshr: x = l.u >> (r.u & 63); break; + case Oshr: x = (w ? l.u : (uint32_t)l.u) >> (r.u & 63); break; case Oshl: x = l.u << (r.u & 63); break; case Oextsb: x = (int8_t)l.u; break; case Oextub: x = (uint8_t)l.u; break; |