| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
|
|
||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,21 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,21 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,17 @@ | ||
| /* { dg-do compile { target *-*-linux* } } */ | ||
| /* { dg-options "-O2 -fpic -fno-plt -mindirect-branch=thunk" } */ | ||
|
|
||
| extern void bar (void); | ||
|
|
||
| void | ||
| foo (void) | ||
| { | ||
| bar (); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,18 @@ | ||
| /* { dg-do compile { target *-*-linux* } } */ | ||
| /* { dg-options "-O2 -fpic -fno-plt -mindirect-branch=thunk" } */ | ||
|
|
||
| extern void bar (void); | ||
|
|
||
| int | ||
| foo (void) | ||
| { | ||
| bar (); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,44 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fno-pic" } */ | ||
|
|
||
| void func0 (void); | ||
| void func1 (void); | ||
| void func2 (void); | ||
| void func3 (void); | ||
| void func4 (void); | ||
| void func4 (void); | ||
| void func5 (void); | ||
|
|
||
| void | ||
| bar (int i) | ||
| { | ||
| switch (i) | ||
| { | ||
| default: | ||
| func0 (); | ||
| break; | ||
| case 1: | ||
| func1 (); | ||
| break; | ||
| case 2: | ||
| func2 (); | ||
| break; | ||
| case 3: | ||
| func3 (); | ||
| break; | ||
| case 4: | ||
| func4 (); | ||
| break; | ||
| case 5: | ||
| func5 (); | ||
| break; | ||
| } | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*\.L\[0-9\]+\\(,%" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,23 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
|
|
||
| extern void male_indirect_jump (long) | ||
| __attribute__ ((indirect_branch("thunk"))); | ||
|
|
||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,21 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| __attribute__ ((indirect_branch("thunk"))) | ||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,23 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
| extern int male_indirect_jump (long) | ||
| __attribute__ ((indirect_branch("thunk-inline"))); | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not "pushq\[ \t\]%rax" { target x32 } } } */ |
| @@ -0,0 +1,22 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| __attribute__ ((indirect_branch("thunk-inline"))) | ||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not "pushq\[ \t\]%rax" { target x32 } } } */ |
| @@ -0,0 +1,22 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
| extern int male_indirect_jump (long) | ||
| __attribute__ ((indirect_branch("thunk-extern"))); | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ |
| @@ -0,0 +1,21 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| __attribute__ ((indirect_branch("thunk-extern"))) | ||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ |
| @@ -0,0 +1,44 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -fno-pic" } */ | ||
|
|
||
| void func0 (void); | ||
| void func1 (void); | ||
| void func2 (void); | ||
| void func3 (void); | ||
| void func4 (void); | ||
| void func4 (void); | ||
| void func5 (void); | ||
|
|
||
| __attribute__ ((indirect_branch("thunk-extern"))) | ||
| void | ||
| bar (int i) | ||
| { | ||
| switch (i) | ||
| { | ||
| default: | ||
| func0 (); | ||
| break; | ||
| case 1: | ||
| func1 (); | ||
| break; | ||
| case 2: | ||
| func2 (); | ||
| break; | ||
| case 3: | ||
| func3 (); | ||
| break; | ||
| case 4: | ||
| func4 (); | ||
| break; | ||
| case 5: | ||
| func5 (); | ||
| break; | ||
| } | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*\.L\[0-9\]+\\(,%" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ | ||
| /* { dg-final { scan-assembler-not "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler-not "call\[ \t\]*\.LIND" } } */ |
| @@ -0,0 +1,42 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fno-pic" } */ | ||
|
|
||
| void func0 (void); | ||
| void func1 (void); | ||
| void func2 (void); | ||
| void func3 (void); | ||
| void func4 (void); | ||
| void func4 (void); | ||
| void func5 (void); | ||
|
|
||
| __attribute__ ((indirect_branch("keep"))) | ||
| void | ||
| bar (int i) | ||
| { | ||
| switch (i) | ||
| { | ||
| default: | ||
| func0 (); | ||
| break; | ||
| case 1: | ||
| func1 (); | ||
| break; | ||
| case 2: | ||
| func2 (); | ||
| break; | ||
| case 3: | ||
| func3 (); | ||
| break; | ||
| case 4: | ||
| func4 (); | ||
| break; | ||
| case 5: | ||
| func5 (); | ||
| break; | ||
| } | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ | ||
| /* { dg-final { scan-assembler-not "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler-not "call\[ \t\]*\.LIND" } } */ |
| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile { target { ! x32 } } } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fcheck-pointer-bounds -mmpx -fno-pic" } */ | ||
|
|
||
| void (*dispatch) (char *); | ||
| char buf[10]; | ||
|
|
||
| void | ||
| foo (void) | ||
| { | ||
| dispatch (buf); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "pushq\[ \t\]%rax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "bnd jmp\[ \t\]*__x86_indirect_thunk_bnd" } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "bnd call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "bnd ret" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,21 @@ | ||
| /* { dg-do compile { target { ! x32 } } } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fcheck-pointer-bounds -mmpx -fno-pic" } */ | ||
|
|
||
| void (*dispatch) (char *); | ||
| char buf[10]; | ||
|
|
||
| int | ||
| foo (void) | ||
| { | ||
| dispatch (buf); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "pushq\[ \t\]%rax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "bnd jmp\[ \t\]*__x86_indirect_thunk_bnd" } } */ | ||
| /* { dg-final { scan-assembler "bnd jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "bnd call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "bnd ret" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,19 @@ | ||
| /* { dg-do compile { target { *-*-linux* && { ! x32 } } } } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fcheck-pointer-bounds -mmpx -fpic -fno-plt" } */ | ||
|
|
||
| void bar (char *); | ||
| char buf[10]; | ||
|
|
||
| void | ||
| foo (void) | ||
| { | ||
| bar (buf); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler "bnd jmp\[ \t\]*__x86_indirect_thunk_bnd" } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "bnd call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "bnd ret" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile { target { *-*-linux* && { ! x32 } } } } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk -fcheck-pointer-bounds -mmpx -fpic -fno-plt" } */ | ||
|
|
||
| void bar (char *); | ||
| char buf[10]; | ||
|
|
||
| int | ||
| foo (void) | ||
| { | ||
| bar (buf); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler "bnd jmp\[ \t\]*__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler "bnd jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler-times "bnd call\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler "bnd ret" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ |
| @@ -0,0 +1,19 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-extern -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
|
|
||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ | ||
| /* { dg-final { scan-assembler-not "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler-not "call\[ \t\]*\.LIND" } } */ |
| @@ -0,0 +1,19 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-extern -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ | ||
| /* { dg-final { scan-assembler-not "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler-not "call\[ \t\]*\.LIND" } } */ |
| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-extern -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ |
| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-extern -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 1 { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ |
| @@ -0,0 +1,16 @@ | ||
| /* { dg-do compile { target *-*-linux* } } */ | ||
| /* { dg-options "-O2 -fpic -fno-plt -mindirect-branch=thunk-extern" } */ | ||
|
|
||
| extern void bar (void); | ||
|
|
||
| void | ||
| foo (void) | ||
| { | ||
| bar (); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ | ||
| /* { dg-final { scan-assembler-not "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler-not "call\[ \t\]*\.LIND" } } */ |
| @@ -0,0 +1,17 @@ | ||
| /* { dg-do compile { target *-*-linux* } } */ | ||
| /* { dg-options "-O2 -fpic -fno-plt -mindirect-branch=thunk-extern" } */ | ||
|
|
||
| extern void bar (void); | ||
|
|
||
| int | ||
| foo (void) | ||
| { | ||
| bar (); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 1 } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 1 } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ |
| @@ -0,0 +1,43 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-extern -fno-pic" } */ | ||
|
|
||
| void func0 (void); | ||
| void func1 (void); | ||
| void func2 (void); | ||
| void func3 (void); | ||
| void func4 (void); | ||
| void func4 (void); | ||
| void func5 (void); | ||
|
|
||
| void | ||
| bar (int i) | ||
| { | ||
| switch (i) | ||
| { | ||
| default: | ||
| func0 (); | ||
| break; | ||
| case 1: | ||
| func1 (); | ||
| break; | ||
| case 2: | ||
| func2 (); | ||
| break; | ||
| case 3: | ||
| func3 (); | ||
| break; | ||
| case 4: | ||
| func4 (); | ||
| break; | ||
| case 5: | ||
| func5 (); | ||
| break; | ||
| } | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*\.L\[0-9\]+\\(,%" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*__x86_indirect_thunk_(r|e)ax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler-not {\t(lfence|pause)} } } */ | ||
| /* { dg-final { scan-assembler-not "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler-not "call\[ \t\]*\.LIND" } } */ |
| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-inline -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
|
|
||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not "pushq\[ \t\]%rax" { target x32 } } } */ |
| @@ -0,0 +1,20 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-inline -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| void | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not "pushq\[ \t\]%rax" { target x32 } } } */ |
| @@ -0,0 +1,21 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-inline -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch; | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch(offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times {\tpause} 1 } } */ | ||
| /* { dg-final { scan-assembler-times {\tlfence} 1 } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not "pushq\[ \t\]%rax" { target x32 } } } */ |
| @@ -0,0 +1,21 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-inline -fno-pic" } */ | ||
|
|
||
| typedef void (*dispatch_t)(long offset); | ||
|
|
||
| dispatch_t dispatch[256]; | ||
|
|
||
| int | ||
| male_indirect_jump (long offset) | ||
| { | ||
| dispatch[offset](offset); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*_?dispatch" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times {\tpause} 1 } } */ | ||
| /* { dg-final { scan-assembler-times {\tlfence} 1 } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ | ||
| /* { dg-final { scan-assembler-not "pushq\[ \t\]%rax" { target x32 } } } */ |
| @@ -0,0 +1,17 @@ | ||
| /* { dg-do compile { target *-*-linux* } } */ | ||
| /* { dg-options "-O2 -fpic -fno-plt -mindirect-branch=thunk-inline" } */ | ||
|
|
||
| extern void bar (void); | ||
|
|
||
| void | ||
| foo (void) | ||
| { | ||
| bar (); | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ |
| @@ -0,0 +1,18 @@ | ||
| /* { dg-do compile { target *-*-linux* } } */ | ||
| /* { dg-options "-O2 -fpic -fno-plt -mindirect-branch=thunk-inline" } */ | ||
|
|
||
| extern void bar (void); | ||
|
|
||
| int | ||
| foo (void) | ||
| { | ||
| bar (); | ||
| return 0; | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*bar@GOT" } } */ | ||
| /* { dg-final { scan-assembler-times "jmp\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times "call\[ \t\]*\.LIND" 2 } } */ | ||
| /* { dg-final { scan-assembler-times {\tpause} 1 } } */ | ||
| /* { dg-final { scan-assembler-times {\tlfence} 1 } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ |
| @@ -0,0 +1,44 @@ | ||
| /* { dg-do compile } */ | ||
| /* { dg-options "-O2 -mindirect-branch=thunk-inline -fno-pic" } */ | ||
|
|
||
| void func0 (void); | ||
| void func1 (void); | ||
| void func2 (void); | ||
| void func3 (void); | ||
| void func4 (void); | ||
| void func4 (void); | ||
| void func5 (void); | ||
|
|
||
| void | ||
| bar (int i) | ||
| { | ||
| switch (i) | ||
| { | ||
| default: | ||
| func0 (); | ||
| break; | ||
| case 1: | ||
| func1 (); | ||
| break; | ||
| case 2: | ||
| func2 (); | ||
| break; | ||
| case 3: | ||
| func3 (); | ||
| break; | ||
| case 4: | ||
| func4 (); | ||
| break; | ||
| case 5: | ||
| func5 (); | ||
| break; | ||
| } | ||
| } | ||
|
|
||
| /* { dg-final { scan-assembler "push(?:l|q)\[ \t\]*\.L\[0-9\]+\\(,%" { target { ! x32 } } } } */ | ||
| /* { dg-final { scan-assembler-not "pushq\[ \t\]%rax" { target x32 } } } */ | ||
| /* { dg-final { scan-assembler "jmp\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler "call\[ \t\]*\.LIND" } } */ | ||
| /* { dg-final { scan-assembler {\tpause} } } */ | ||
| /* { dg-final { scan-assembler {\tlfence} } } */ | ||
| /* { dg-final { scan-assembler-not "__x86_indirect_thunk" } } */ |