-
Notifications
You must be signed in to change notification settings - Fork 160
/
Copy pathgoto.c
92 lines (73 loc) · 1.87 KB
/
goto.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
/*
# goto
One of the most basic loops: tranlates to an unconditional `jmp` in x86.
*/
#include "common.h"
int goto_func(int i) {
/*goto goto_func_after;*/
in_func_label:
return 1;
}
int main(void) {
/*
However, avoid using this as it may generate unreadable code.
Opinions vary, but possible acceptable uses are:
- break out of nested loops, widely supported
- any forward jump, e.g. for error handling.
Those are equivalent to return, which is well accepted.
Very few people support gotos that go backwards.
`return` is essentially a forward jump inside a function.
*/
/* Basic example. */
{
goto basic_example;
assert(0);
basic_example:
assert(1);
}
/*
goto cannot cross functions: that would lead to crazy
things like uninitialized parameters, and no return.
Use `setjmp` for that.
*/
{
int i;
goto_func_after:
i = 1;
/*goto in_func_label;*/
}
/* Labels cannot be at the end of compound statments */
{
{ /*label_end_compound:*/ }
{ label_end_compound: 1; }
}
/* Labels and loops */
{
int i;
for ( /*label_in_for:*/ i = 0; i < 2; i++)
label_after_if:
{
label_after_if2: 1;
}
}
/* Labels and switch. */
{
int a = 1;
switch (a) {
case 0:
label_case_0:
assert(a == 1);
break;
case 1:
goto label_case_0;
break;
}
}
/*
Store label in variable and jump to it:
- http://stackoverflow.com/questions/1777990/c-programming-address-of-a-label
- http://stackoverflow.com/questions/938518/how-to-store-goto-labels-in-an-array-and-then-jump-to-them
Impossible.
*/
return EXIT_SUCCESS;
}