https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84101
--- Comment #22 from Richard Biener <rguenth at gcc dot gnu.org> --- But we can side-step this issue with changing the way expand_constructor works: Index: gcc/expr.c =================================================================== --- gcc/expr.c (revision 269963) +++ gcc/expr.c (working copy) @@ -7018,7 +7018,16 @@ store_field (rtx target, poly_int64 bits } } - temp = expand_normal (exp); + if (REG_P (target) + && known_eq (bitpos, 0) + && known_eq (bitsize, GET_MODE_BITSIZE (GET_MODE (target)))) + { + temp = expand_expr (exp, target, VOIDmode, EXPAND_NORMAL); + if (temp == target) + return const0_rtx; + } + else + temp = expand_normal (exp); /* We don't support variable-sized BLKmode bitfields, since our handling of BLKmode is bound up with the ability to break @@ -8191,7 +8202,15 @@ expand_constructor (tree exp, rtx target if (avoid_temp_mem) return NULL_RTX; - target = assign_temp (type, TREE_ADDRESSABLE (exp), 1); + if (target && REG_P (target)) + { + rtx tem = gen_reg_rtx (GET_MODE (target)); + store_constructor (exp, tem, 0, int_expr_size (exp), false); + emit_move_insn (target, tem); + return target; + } + else + target = assign_temp (type, TREE_ADDRESSABLE (exp), 1); } store_constructor (exp, target, 0, int_expr_size (exp), false);