https://gcc.gnu.org/bugzilla/show_bug.cgi?id=97143
Bug ID: 97143 Summary: aarch64-none-elf Code generated for array after another array within a global structure marked volatile is broken. Product: gcc Version: 8.2.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: target Assignee: unassigned at gcc dot gnu.org Reporter: simon.willcocks at gmx dot de Target Milestone: --- Using built-in specs. COLLECT_GCC=aarch64-none-elf-gcc COLLECT_LTO_WRAPPER=/media/simon/b4ea8e46-fe87-4ddd-9e94-506c37005ac5/IsambardOS/IsambardOS/cross-compiler64-8.2/bin/../libexec/gcc/aarch64-none-elf/8.2.0/lto-wrapper Target: aarch64-none-elf Configured with: gcc-8.2.0/configure --prefix=/home/simon/cross-compiler64 --target=aarch64-none-elf --disable-libstdcxx --disable-threads --disable-multilib --disable-nls --disable-libssp --disable-bootstrap --enable-languages=c : (reconfigured) gcc-8.2.0/configure --prefix=/home/simon/cross-compiler64 --target=aarch64-none-elf --disable-libstdcxx --disable-threads --disable-multilib --disable-nls --disable-libssp --disable-bootstrap --enable-languages=c CFLAGS='-g -O2' Thread model: single gcc version 8.2.0 (GCC) Remove array_not_at_start, or make the number of elements not a multiple of 4, or remove the volatile keyword, and the problem disappears. The generated code adds the number of elements in the first array to the index, before multiplying the sum by 4 (x0, lsl #2), instead of just the index. Taking the address of the array, then accessing the element works as expected. aarch64-none-elf-gcc gcc-bug.c -c -Os (problem is idependent of optimisation level) Code: extern struct { struct { unsigned int array_not_at_start[0x88]; unsigned int Core_IRQ_Source[4]; } QA7; } volatile device_pages; unsigned int this_function_is_broken( unsigned int i ) { return device_pages.QA7.Core_IRQ_Source[i]; } unsigned int this_function_works( unsigned int i ) { unsigned int volatile *p = device_pages.QA7.Core_IRQ_Source; return p[i]; } Annotated objdump: 0000000000000000 <this_function_is_broken>: 0: 2a0003e0 mov w0, w0 4: 90000001 adrp x1, 0 <device_pages> 4: R_AARCH64_ADR_PREL_PG_HI21 device_pages 8: 91022000 add x0, x0, #0x88 <<<< Elements in 1st array c: 91000021 add x1, x1, #0x0 c: R_AARCH64_ADD_ABS_LO12_NC device_pages 10: b8607820 ldr w0, [x1, x0, lsl #2] <<<< x1 + (index + elements) * 4 14: d65f03c0 ret 0000000000000018 <this_function_works>: 18: d37e7c00 ubfiz x0, x0, #2, #32 1c: 90000001 adrp x1, 0 <device_pages> 1c: R_AARCH64_ADR_PREL_PG_HI21 device_pages+0x220 20: 91000021 add x1, x1, #0x0 20: R_AARCH64_ADD_ABS_LO12_NC device_pages+0x220 24: b8616800 ldr w0, [x0, x1] 28: d65f03c0 ret