Re: Aggressive load in gcc when accessing escaped pointer?
:D But I don't understand why &c - 8 is invalid? Which rule in C99 it volatile? That's see the example again with some changes: // Now, I make c point to &c - 8 PB** bar(PB** t) { char* ptr = (char*)t; *t = (PB*)(ptr-8); } void qux(PB* c) { PB* cc; bar(&c); c->f1_ = 0;// invalid cc = c; cc->f1_ = 0; // valid or invalid? } My question is, if &c - 8 is an invalid address, then it looks like cc->f1_ = 0 will be an invalid operation? Or &c - 8 is only invalid in terms of c, not cc? (By the way, we also discuss the pattern in llvm mailing list: https://goo.gl/VHK0dN) 2016-03-19 2:46 GMT+08:00 Richard Biener : > On March 18, 2016 3:26:37 PM GMT+01:00, Markus Trippelsdorf > wrote: >>On 2016.03.18 at 22:05 +0800, Cy Cheng wrote: >>> Hi, >>> >>> Please look at this c code: >>> >>> typedef struct _PB { >>> void* data; /* required.*/ >>> int f1_; >>> float f2_; >>> } PB; >>> >>> PB** bar(PB** t); >>> >>> void qux(PB* c) { >>> bar(&c); /* c is escaped because of bar */ >>> c->f1_ = 0; >>> c->f2_ = 0.f; >>> } >>> >>> // gcc-5.2.1 with -fno-strict-aliasing -O2 on x86 >>> callbar >>> movq8(%rsp), %rax <= load pointer c >>> movl$0, 8(%rax) >>> movl$0x, 12(%rax) >>> >>> // intel-icc-13.0.1 with -fno-strict-aliasing -O2 on x86 >>> call bar(_PB**) >>> movq (%rsp), %rdx <= load pointer c >>> movl %ecx, 8(%rdx) >>> movq (%rsp), %rsi <= load pointer c >>> movl %ecx, 12(%rsi) >>> >>> GCC only load pointer c once, but if I implement bar in such way: >>> PB** bar(PB** t) { >>> char* ptr = (char*)t; >>> *t = (PB*)(ptr-8); >>>return t; >>> } >>> >>> Does this volatile C99 standard rule >>> (http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1256.pdf): >>> >>>6.5.16 Assignment operators >>> >>>"3. ... The side effect of updating the stored value of the left >>operand >>> shall occur between the previous and the next sequence point." >> >>No. We discussed this on IRC today and Richard Biener pointed out that >>bar cannot make c point to &c - 8, because computing that pointer would >>be invalid. So c->f1_ cannot clobber c itself. > > Nice to see that only GCC gets this optimization opportunity :) > > Richard. >
Re: Aggressive load in gcc when accessing escaped pointer?
On 2016.03.18 at 22:05 +0800, Cy Cheng wrote: > Hi, > > Please look at this c code: > > typedef struct _PB { > void* data; /* required.*/ > int f1_; > float f2_; > } PB; > > PB** bar(PB** t); > > void qux(PB* c) { > bar(&c); /* c is escaped because of bar */ > c->f1_ = 0; > c->f2_ = 0.f; > } > > // gcc-5.2.1 with -fno-strict-aliasing -O2 on x86 > callbar > movq8(%rsp), %rax <= load pointer c > movl$0, 8(%rax) > movl$0x, 12(%rax) > > // intel-icc-13.0.1 with -fno-strict-aliasing -O2 on x86 > call bar(_PB**) > movq (%rsp), %rdx <= load pointer c > movl %ecx, 8(%rdx) > movq (%rsp), %rsi <= load pointer c > movl %ecx, 12(%rsi) > > GCC only load pointer c once, but if I implement bar in such way: > PB** bar(PB** t) { > char* ptr = (char*)t; > *t = (PB*)(ptr-8); >return t; > } > > Does this volatile C99 standard rule > (http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1256.pdf): > >6.5.16 Assignment operators > >"3. ... The side effect of updating the stored value of the left operand > shall occur between the previous and the next sequence point." No. We discussed this on IRC today and Richard Biener pointed out that bar cannot make c point to &c - 8, because computing that pointer would be invalid. So c->f1_ cannot clobber c itself. -- Markus
Re: Aggressive load in gcc when accessing escaped pointer?
On March 18, 2016 3:26:37 PM GMT+01:00, Markus Trippelsdorf wrote: >On 2016.03.18 at 22:05 +0800, Cy Cheng wrote: >> Hi, >> >> Please look at this c code: >> >> typedef struct _PB { >> void* data; /* required.*/ >> int f1_; >> float f2_; >> } PB; >> >> PB** bar(PB** t); >> >> void qux(PB* c) { >> bar(&c); /* c is escaped because of bar */ >> c->f1_ = 0; >> c->f2_ = 0.f; >> } >> >> // gcc-5.2.1 with -fno-strict-aliasing -O2 on x86 >> callbar >> movq8(%rsp), %rax <= load pointer c >> movl$0, 8(%rax) >> movl$0x, 12(%rax) >> >> // intel-icc-13.0.1 with -fno-strict-aliasing -O2 on x86 >> call bar(_PB**) >> movq (%rsp), %rdx <= load pointer c >> movl %ecx, 8(%rdx) >> movq (%rsp), %rsi <= load pointer c >> movl %ecx, 12(%rsi) >> >> GCC only load pointer c once, but if I implement bar in such way: >> PB** bar(PB** t) { >> char* ptr = (char*)t; >> *t = (PB*)(ptr-8); >>return t; >> } >> >> Does this volatile C99 standard rule >> (http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1256.pdf): >> >>6.5.16 Assignment operators >> >>"3. ... The side effect of updating the stored value of the left >operand >> shall occur between the previous and the next sequence point." > >No. We discussed this on IRC today and Richard Biener pointed out that >bar cannot make c point to &c - 8, because computing that pointer would >be invalid. So c->f1_ cannot clobber c itself. Nice to see that only GCC gets this optimization opportunity :) Richard.
Re: [GCC Wiki] Update of "DebugFission" by CaryCoutant
Hi Cary! On Thu, 16 May 2013 16:58:12 -, GCC Wiki wrote: > The "DebugFission" page has been changed by CaryCoutant: > http://gcc.gnu.org/wiki/DebugFission?action=diff&rev1=18&rev2=19 > > = DWARF Extensions for Separate Debug Information Files = > > Updated January 24, 2013 > + > + The "Fission" project was started in response to the problems caused by > huge amounts of debug information in large applications. By splitting the > debug information into two parts at compile time -- one part that remains in > the .o file and another part that is written to a parallel .dwo ("DWARF > object") file -- we can reduce the total size of the object files processed > by the linker. Yay, a quite noticeable link-time speedup! \o/ > + Fission is implemented in GCC 4.7, and requires support from recent > versions of objcopy and the gold linker. Is my understanding correct that the gold linker is not actually a requirement -- at least nowadays? In my (very limited, so far) testing, this also seems to work with ld.bfd. (I do see objcopy's --extract-dwo and --split-dwo options being used in gcc/gcc.c:ASM_FINAL_SPEC, so I suspect that's what "recent versions of objcopy" hints at?) > + Use the {{{-gsplit-dwarf}}} option to enable the generation of split DWARF > at compile time. This option must be used in conjunction with {{{-c}}}; > Fission cannot be used when compiling and linking in the same step. According to the following -- admittedly very minimal -- testing, this is not actually (no longer?) true? $ [gcc] [...] -gsplit-dwarf $ ls *.dwo ccF9JYjE.dwo subroutines.dwo $ gdb -q a.out Reading symbols from a.out...done. (gdb) list main [...] (gdb) quit $ rm *.dwo $ gdb -q a.out Reading symbols from a.out... warning: Could not find DWO CU subroutines.dwo(0x2d85cdd539df6900) referenced by CU at offset 0x0 [in module [...]/a.out] warning: Could not find DWO CU ccF9JYjE.dwo(0xa6936555a636518) referenced by CU at offset 0x35 [in module [...]/a.out] done. (gdb) list main warning: Could not find DWO CU subroutines.dwo(0x2d85cdd539df6900) referenced by CU at offset 0x0 [in module [...]/a.out] Have I been testing the wrong thing? > + Use the gold linker's {{{--gdb-index}}} option ({{{-Wl,--gdb-index}}} when > linking with gcc or g++) at link time to create the .gdb_index section that > allows GDB to locate and read the .dwo files as it needs them. Unless told otherwise, I'll re-word that to the effect that gold, and usage of its --gdb-index option are optional. Grüße Thomas signature.asc Description: PGP signature