On Fri, 2016-01-08 at 12:56 +0100, Richard Biener wrote: > On Fri, Jan 8, 2016 at 12:40 PM, Eric Botcazou <ebotca...@libertysurf.fr> > wrote: > >> I think we only assume it if the pointer is actually dereferenced, > >> otherwise > >> it just breaks too much code in the wild. And while memcpy dereferences, > >> it dereferences it through a char * cast, and thus only the minimum > >> alignment is assumed. > > > > Yet the compiler was generating the expected code for Steve's testcase on > > strict-alignment architectures until very recently (GCC 4.5 IIUC) and this > > worked perfectly.
Yes, I just checked and I did get the better code in GCC 4.5 and I get the current slower code in GCC 4.6. > Consider > > int a[256]; > int > main() > { > void *p = (char *)a + 1; > void *q = (char *)a + 5; > __builtin_memcpy (p, q, 4); > return 0; > } > > where the ME would be entitled to "drop" the char */void * conversions > and use &a typed temps. I am not sure how this works but I tweaked get_pointer_alignment_1 so that if there was no align info or if get_ptr_info_alignment returned false then the routine would return type based alignment information instead of default 'void *' alignment. In that case and using your example, GCC still accessed p & q as pointers to unaligned data. In fact if I used int pointers: int a[256]; int main() { int *p = (int *)((char *)a + 1); int *q = (int *)((char *)a + 5); __builtin_memcpy (p, q, 4); return 0; } GCC did unaligned accesses when optimizing, but when unoptimized (and with my change) GCC did aligned accesses, which would not work on a strict alignment machine like MIPS This seems to match what happens with: int a[256]; int main() { int *p = (int *)((char *)a + 1); int *q = (int *)((char *)a + 5); *p = *q; return 0; } When I optimize it, GCC does unaligned accesses and when unoptimized GCC does aligned accesses which will not work on MIPS. Steve Ellcey sell...@imgtec.com