diff options
author | Kito Cheng <kito.cheng@sifive.com> | 2021-01-22 16:29:09 +0800 |
---|---|---|
committer | Kito Cheng <kito.cheng@sifive.com> | 2021-02-02 16:56:06 +0800 |
commit | bc7c2b34c34f21ea58198ba58a48eb065bdda25d (patch) | |
tree | 1e790669a1a090b73234f5eae23f5b1494af6baa /gcc | |
parent | 250fd9fb118a6897e6c824a0faac634861ea7716 (diff) | |
download | gcc-bc7c2b34c34f21ea58198ba58a48eb065bdda25d.zip gcc-bc7c2b34c34f21ea58198ba58a48eb065bdda25d.tar.gz gcc-bc7c2b34c34f21ea58198ba58a48eb065bdda25d.tar.bz2 |
PR target/98743: Fix ICE in convert_move for RISC-V
- Check `from` mode is not BLMmode before call store_expr, calling store_expr
with BLKmode will cause ICE.
- Verified with riscv64, x86_64 and aarch64, no introduce new regression.
Note: Those logic was introduced by 3e60ddeb8220ed388819bb3f14e8caa9309fd3c2,
so I cc Jakub for reivew.
Changes for V2:
- Checking mode of `from` rather than mode of `to`.
- Verified on riscv64, x86_64 and aarch64 again.
gcc/ChangeLog:
PR target/98743
* expr.c: Check mode before calling store_expr.
gcc/testsuite/ChangeLog:
PR target/98743
* g++.dg/opt/pr98743.C: New.
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/expr.c | 1 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/opt/pr98743.C | 27 |
2 files changed, 28 insertions, 0 deletions
@@ -5459,6 +5459,7 @@ expand_assignment (tree to, tree from, bool nontemporal) /* If to_rtx is a promoted subreg, we need to zero or sign extend the value afterwards. */ if (TREE_CODE (to) == MEM_REF + && TYPE_MODE (TREE_TYPE (from)) != BLKmode && !REF_REVERSE_STORAGE_ORDER (to) && known_eq (bitpos, 0) && known_eq (bitsize, GET_MODE_BITSIZE (GET_MODE (to_rtx)))) diff --git a/gcc/testsuite/g++.dg/opt/pr98743.C b/gcc/testsuite/g++.dg/opt/pr98743.C new file mode 100644 index 0000000..41f476f --- /dev/null +++ b/gcc/testsuite/g++.dg/opt/pr98743.C @@ -0,0 +1,27 @@ +// Test for value-initialization via {} +// { dg-do run { target c++11 } } +/* { dg-options "-Og -fno-early-inlining -finline-small-functions -fpack-struct" */ +void * operator new (__SIZE_TYPE__, void *p) { return p; } +void * operator new[] (__SIZE_TYPE__, void *p) { return p; } + +// Empty base so A isn't an aggregate +struct B {}; +struct A: B { + int i; +}; + +struct C: A { + C(): A{} {} +}; + +int main() +{ + int space = 42; + A* ap = new (&space) A{}; + int space1[1] = { 42 }; + A* a1p = new (space1) A[1]{}; + if (ap->i != 0 || + a1p[0].i != 0) + return 1; + return 0; +} |