aboutsummaryrefslogtreecommitdiff
blob: f87d891713653411e564d8133ea391e8c876c30f (plain)
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
93
94
95
BEGIN {
	COUNT = split(ENVIRON["SYMBOLS"], SYMBOLS);
}

{
	# Unstripped libc's have '.symtab' section as well, and
	# we should stop processing when we hit that
	if ($0 ~ "Symbol table '.symtab'")
		nextfile;

	for (x in SYMBOLS) {
		sym_regex = "^" SYMBOLS[x] "(@|$)"
		if ($8 ~ sym_regex) {
			split($8, symbol_array, /@|@@/);

			# Don't add local symbols of versioned libc's
			if (VERSIONED_LIBC && !symbol_array[2])
				continue;

			# We have a versioned libc
			if (symbol_array[2] && !VERSIONED_LIBC)
			    	VERSIONED_LIBC = 1;

			ADD = 1;
			# Check that we do not add duplicates
			for (x in PROCESSED_SYMBOLS) {
				if (x == $8) {
					ADD = 0;
					break;
				}
			}
			
			if (ADD) {
				SYMBOL_LIST[symbol_array[1]] = SYMBOL_LIST[symbol_array[1]] " " $8;
				PROCESSED_SYMBOLS[$8] = $8;
			}
		}
	}
}

END {
	printf("#ifndef __symbols_h\n");
	printf("#define __symbols_h\n\n");

	# We use the order in SYMBOLS, as some wrappers depends on others ...
	for (i = 1; i <= COUNT; i++) {
		sym_index = SYMBOLS[i];
		split(SYMBOL_LIST[sym_index], sym_full_names);
		
		for (x in sym_full_names) {
			split(sym_full_names[x], symbol_array, /@|@@/);
	
			# Defualt symbol have '@@' and not '@', so name it by
			# prepending '__' rather than the symbol version so
			# that we know what the name is in libsandbox.c ...
			# Also do this for non-versioned libc's ...
			if (sym_full_names[x] ~ /@@/ || !symbol_array[2]) {
				sym_real_name = sym_index "_DEFAULT";
			} else {
				sym_real_name = sym_full_names[x];
				gsub(/@|\./, "_", sym_real_name);
			}
			
			printf("#define symname_%s \"%s\"\n", sym_real_name, sym_index);

			# We handle non-versioned libc's by setting symver_*
			# to NULL ...
			if (!symbol_array[2])
				printf("#define symver_%s NULL\n", sym_real_name);
			else
				printf("#define symver_%s \"%s\"\n", sym_real_name,
				       symbol_array[2]);
			
			printf("%s_decl(%s);\n", sym_index, sym_real_name);
		
			if (symbol_array[2]) {
				# Only add symbol versions for versioned libc's
				if (sym_full_names[x] ~ /@@/)
					printf("default_symbol_version(%s, %s, %s);\n",
					       sym_real_name, sym_index, symbol_array[2]);
				else
					printf("symbol_version(%s, %s, %s);\n",
					       sym_real_name, sym_index, symbol_array[2]);
			} else {
				# For non-versioned libc's we use strong aliases
				printf("strong_alias(%s, %s);\n", sym_real_name,
				       sym_index);
			}
			
			printf("\n");
		}
	}

	printf("#endif /* __symbols_h */\n");
}