[Bug c/96956] New: When gcc does not see a label used in a goto it gives the wrong label address &&label
thomas.lynch at reasoningtechnology dot com
gcc-bugzilla@gcc.gnu.org
Mon Sep 7 14:01:54 GMT 2020
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=96956
Bug ID: 96956
Summary: When gcc does not see a label used in a goto it gives
the wrong label address &&label
Product: gcc
Version: 10.2.1
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: c
Assignee: unassigned at gcc dot gnu.org
Reporter: thomas.lynch at reasoningtechnology dot com
Target Milestone: ---
Created attachment 49193
--> https://gcc.gnu.org/bugzilla/attachment.cgi?id=49193&action=edit
.c .i .s gcc version system info
The attached is an example distilled from much larger code. It makes use of
the gcc extension of taking the address of a label. All optimizations are
turned off `-O0`.
The && operator returns the address for a different label than the one
requested. Specificaly in this exmaple `&&nominal` returns the address for a
different label, `&&test0`.
The code example shown makes use of an inlined nested function to hide the goto
from gcc. However, the error occurs before the nested function is called. Note
the printf %p printf statements.
With small variations of this code, gcc will return the correct address for
`&&nominal`. If gcc sees an explicit goto to the label for
`&&nominal`, then the printf %p will give the correct value.
See attached for .c .i .s gcc version and sys info.
/* broken.c ----------------------------------------------------------------
gcc -std=gnu2x -Wall -O0 -ggdb -o broken broken.c
*/
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <stdbool.h>
typedef void **CV·Ptr;
CV·Ptr target_pt;
uint i = 0;
int main(){
goto test0;
inline void do_jmp(CV·Ptr target_pt){
goto *target_pt;
}
test0:;
i++; // gets optimized away
printf("%x\n", i);
goto report;
nominal:
i++;
goto tests_finished;
report:;
target_pt = &&nominal;
printf("test0: %p\n", &&test0);
// this will be identical to &&test0 and we haven't even called do_jmp:
printf("nominal: %p\n", target_pt);
if( i == 2 ){
printf("foo!\n");
goto tests_finished;
}
do_jmp(target_pt);
tests_finished:;
}
More information about the Gcc-bugs
mailing list