> Jan Hubicka <hubi...@ucw.cz> writes: > >> MIPS16 code can't do atomic operations directly, so it calls into > >> out-of-line > >> versions that are compiled as -mno-mips16. These out-of-line versions use > >> the same open-coded implementation as you'd get in normal -mno-mips16 code. > > > > Hmm, and I assume you don't want to use target attribute for this... > > You mean so that any code that calls a __sync function would become > -mno-mips16? Yeah, we want to avoid that. There are specific mips16 > and nomips16 attributes for setting the ISA mode, but the idea is to > allow functions to be compiled as -mips16 wherever possible. > > >> This is done by libgcc/sync.c, which contains code like like: > >> > >> static void > >> sync_synchronize (void) > >> { > >> __sync_synchronize (); > >> } > >> typeof (sync_synchronize) __sync_synchronize > >> __attribute__((alias ("sync_synchronize"))); > >> > >> With the recent cgraph changes, we follow the alias and the function > >> becomes > >> an infinite loop. > > > > Yep, here you define two symbols of same assembler name, so they will be > > identified. > > How exactly the code worked before? > > You'd know better than me how it worked before. :-) All I know is > that until the recent changes, the gimple optimisers didn't redirect > __sync_synchronize() to sync_synchronize(), so the original call > survived until expand and so got replaced with a sync instruction. > This is in contrast to: > > void > __sync_synchronize (void) > { > __sync_synchronize (); > } > > which the compiler always treated as an infinite loop. That's why > the alias indirect was used.
I see, the previous implementation tricked the one-declaration rule by introducing two names. What made the difference is that the second name is expanded as builtin... So you don't have __bulitin_sync_synchronize() at hand that would be translated to __sync_synchronize libcall? > > Thanks, > Richard