@@ -85,6 +85,25 @@ static uint64_t (*r8)(const uint64_t *);
85
85
static void (* w )(uint32_t , uint32_t * );
86
86
typedef void (* table_sort_t )(char * , int );
87
87
88
+ static struct elf_funcs {
89
+ int (* compare_extable )(const void * a , const void * b );
90
+ uint64_t (* ehdr_shoff )(Elf_Ehdr * ehdr );
91
+ uint16_t (* ehdr_shstrndx )(Elf_Ehdr * ehdr );
92
+ uint16_t (* ehdr_shentsize )(Elf_Ehdr * ehdr );
93
+ uint16_t (* ehdr_shnum )(Elf_Ehdr * ehdr );
94
+ uint64_t (* shdr_addr )(Elf_Shdr * shdr );
95
+ uint64_t (* shdr_offset )(Elf_Shdr * shdr );
96
+ uint64_t (* shdr_size )(Elf_Shdr * shdr );
97
+ uint64_t (* shdr_entsize )(Elf_Shdr * shdr );
98
+ uint32_t (* shdr_link )(Elf_Shdr * shdr );
99
+ uint32_t (* shdr_name )(Elf_Shdr * shdr );
100
+ uint32_t (* shdr_type )(Elf_Shdr * shdr );
101
+ uint8_t (* sym_type )(Elf_Sym * sym );
102
+ uint32_t (* sym_name )(Elf_Sym * sym );
103
+ uint64_t (* sym_value )(Elf_Sym * sym );
104
+ uint16_t (* sym_shndx )(Elf_Sym * sym );
105
+ } e ;
106
+
88
107
static uint64_t ehdr64_shoff (Elf_Ehdr * ehdr )
89
108
{
90
109
return r8 (& ehdr -> e64 .e_shoff );
@@ -95,6 +114,11 @@ static uint64_t ehdr32_shoff(Elf_Ehdr *ehdr)
95
114
return r (& ehdr -> e32 .e_shoff );
96
115
}
97
116
117
+ static uint64_t ehdr_shoff (Elf_Ehdr * ehdr )
118
+ {
119
+ return e .ehdr_shoff (ehdr );
120
+ }
121
+
98
122
#define EHDR_HALF (fn_name ) \
99
123
static uint16_t ehdr64_##fn_name(Elf_Ehdr *ehdr) \
100
124
{ \
@@ -104,6 +128,11 @@ static uint16_t ehdr64_##fn_name(Elf_Ehdr *ehdr) \
104
128
static uint16_t ehdr32_##fn_name(Elf_Ehdr *ehdr) \
105
129
{ \
106
130
return r2(&ehdr->e32.e_##fn_name); \
131
+ } \
132
+ \
133
+ static uint16_t ehdr_##fn_name(Elf_Ehdr *ehdr) \
134
+ { \
135
+ return e.ehdr_##fn_name(ehdr); \
107
136
}
108
137
109
138
EHDR_HALF (shentsize )
@@ -119,6 +148,11 @@ static uint32_t shdr64_##fn_name(Elf_Shdr *shdr) \
119
148
static uint32_t shdr32_##fn_name(Elf_Shdr *shdr) \
120
149
{ \
121
150
return r(&shdr->e32.sh_##fn_name); \
151
+ } \
152
+ \
153
+ static uint32_t shdr_##fn_name(Elf_Shdr *shdr) \
154
+ { \
155
+ return e.shdr_##fn_name(shdr); \
122
156
}
123
157
124
158
#define SHDR_ADDR (fn_name ) \
@@ -130,6 +164,11 @@ static uint64_t shdr64_##fn_name(Elf_Shdr *shdr) \
130
164
static uint64_t shdr32_##fn_name(Elf_Shdr *shdr) \
131
165
{ \
132
166
return r(&shdr->e32.sh_##fn_name); \
167
+ } \
168
+ \
169
+ static uint64_t shdr_##fn_name(Elf_Shdr *shdr) \
170
+ { \
171
+ return e.shdr_##fn_name(shdr); \
133
172
}
134
173
135
174
#define SHDR_WORD (fn_name ) \
@@ -141,6 +180,10 @@ static uint32_t shdr64_##fn_name(Elf_Shdr *shdr) \
141
180
static uint32_t shdr32_##fn_name(Elf_Shdr *shdr) \
142
181
{ \
143
182
return r(&shdr->e32.sh_##fn_name); \
183
+ } \
184
+ static uint32_t shdr_##fn_name(Elf_Shdr *shdr) \
185
+ { \
186
+ return e.shdr_##fn_name(shdr); \
144
187
}
145
188
146
189
SHDR_ADDR (addr )
@@ -161,6 +204,11 @@ static uint64_t sym64_##fn_name(Elf_Sym *sym) \
161
204
static uint64_t sym32_##fn_name(Elf_Sym *sym) \
162
205
{ \
163
206
return r(&sym->e32.st_##fn_name); \
207
+ } \
208
+ \
209
+ static uint64_t sym_##fn_name(Elf_Sym *sym) \
210
+ { \
211
+ return e.sym_##fn_name(sym); \
164
212
}
165
213
166
214
#define SYM_WORD (fn_name ) \
@@ -172,6 +220,11 @@ static uint32_t sym64_##fn_name(Elf_Sym *sym) \
172
220
static uint32_t sym32_##fn_name(Elf_Sym *sym) \
173
221
{ \
174
222
return r(&sym->e32.st_##fn_name); \
223
+ } \
224
+ \
225
+ static uint32_t sym_##fn_name(Elf_Sym *sym) \
226
+ { \
227
+ return e.sym_##fn_name(sym); \
175
228
}
176
229
177
230
#define SYM_HALF (fn_name ) \
@@ -183,6 +236,11 @@ static uint16_t sym64_##fn_name(Elf_Sym *sym) \
183
236
static uint16_t sym32_##fn_name(Elf_Sym *sym) \
184
237
{ \
185
238
return r2(&sym->e32.st_##fn_name); \
239
+ } \
240
+ \
241
+ static uint16_t sym_##fn_name(Elf_Sym *sym) \
242
+ { \
243
+ return e.sym_##fn_name(sym); \
186
244
}
187
245
188
246
static uint8_t sym64_type (Elf_Sym * sym )
@@ -195,6 +253,11 @@ static uint8_t sym32_type(Elf_Sym *sym)
195
253
return ELF32_ST_TYPE (sym -> e32 .st_info );
196
254
}
197
255
256
+ static uint8_t sym_type (Elf_Sym * sym )
257
+ {
258
+ return e .sym_type (sym );
259
+ }
260
+
198
261
SYM_ADDR (value )
199
262
SYM_WORD (name )
200
263
SYM_HALF (shndx )
@@ -322,29 +385,16 @@ static int compare_extable_64(const void *a, const void *b)
322
385
return av > bv ;
323
386
}
324
387
388
+ static int compare_extable (const void * a , const void * b )
389
+ {
390
+ return e .compare_extable (a , b );
391
+ }
392
+
325
393
static inline void * get_index (void * start , int entsize , int index )
326
394
{
327
395
return start + (entsize * index );
328
396
}
329
397
330
-
331
- static int (* compare_extable )(const void * a , const void * b );
332
- static uint64_t (* ehdr_shoff )(Elf_Ehdr * ehdr );
333
- static uint16_t (* ehdr_shstrndx )(Elf_Ehdr * ehdr );
334
- static uint16_t (* ehdr_shentsize )(Elf_Ehdr * ehdr );
335
- static uint16_t (* ehdr_shnum )(Elf_Ehdr * ehdr );
336
- static uint64_t (* shdr_addr )(Elf_Shdr * shdr );
337
- static uint64_t (* shdr_offset )(Elf_Shdr * shdr );
338
- static uint64_t (* shdr_size )(Elf_Shdr * shdr );
339
- static uint64_t (* shdr_entsize )(Elf_Shdr * shdr );
340
- static uint32_t (* shdr_link )(Elf_Shdr * shdr );
341
- static uint32_t (* shdr_name )(Elf_Shdr * shdr );
342
- static uint32_t (* shdr_type )(Elf_Shdr * shdr );
343
- static uint8_t (* sym_type )(Elf_Sym * sym );
344
- static uint32_t (* sym_name )(Elf_Sym * sym );
345
- static uint64_t (* sym_value )(Elf_Sym * sym );
346
- static uint16_t (* sym_shndx )(Elf_Sym * sym );
347
-
348
398
static int extable_ent_size ;
349
399
static int long_size ;
350
400
@@ -864,34 +914,63 @@ static int do_file(char const *const fname, void *addr)
864
914
}
865
915
866
916
switch (ehdr -> e32 .e_ident [EI_CLASS ]) {
867
- case ELFCLASS32 :
917
+ case ELFCLASS32 : {
918
+ struct elf_funcs efuncs = {
919
+ .compare_extable = compare_extable_32 ,
920
+ .ehdr_shoff = ehdr32_shoff ,
921
+ .ehdr_shentsize = ehdr32_shentsize ,
922
+ .ehdr_shstrndx = ehdr32_shstrndx ,
923
+ .ehdr_shnum = ehdr32_shnum ,
924
+ .shdr_addr = shdr32_addr ,
925
+ .shdr_offset = shdr32_offset ,
926
+ .shdr_link = shdr32_link ,
927
+ .shdr_size = shdr32_size ,
928
+ .shdr_name = shdr32_name ,
929
+ .shdr_type = shdr32_type ,
930
+ .shdr_entsize = shdr32_entsize ,
931
+ .sym_type = sym32_type ,
932
+ .sym_name = sym32_name ,
933
+ .sym_value = sym32_value ,
934
+ .sym_shndx = sym32_shndx ,
935
+ };
936
+
937
+ e = efuncs ;
938
+ long_size = 4 ;
939
+ extable_ent_size = 8 ;
940
+
868
941
if (r2 (& ehdr -> e32 .e_ehsize ) != sizeof (Elf32_Ehdr ) ||
869
942
r2 (& ehdr -> e32 .e_shentsize ) != sizeof (Elf32_Shdr )) {
870
943
fprintf (stderr ,
871
944
"unrecognized ET_EXEC/ET_DYN file: %s\n" , fname );
872
945
return -1 ;
873
946
}
874
947
875
- compare_extable = compare_extable_32 ;
876
- ehdr_shoff = ehdr32_shoff ;
877
- ehdr_shentsize = ehdr32_shentsize ;
878
- ehdr_shstrndx = ehdr32_shstrndx ;
879
- ehdr_shnum = ehdr32_shnum ;
880
- shdr_addr = shdr32_addr ;
881
- shdr_offset = shdr32_offset ;
882
- shdr_link = shdr32_link ;
883
- shdr_size = shdr32_size ;
884
- shdr_name = shdr32_name ;
885
- shdr_type = shdr32_type ;
886
- shdr_entsize = shdr32_entsize ;
887
- sym_type = sym32_type ;
888
- sym_name = sym32_name ;
889
- sym_value = sym32_value ;
890
- sym_shndx = sym32_shndx ;
891
- long_size = 4 ;
892
- extable_ent_size = 8 ;
948
+ }
893
949
break ;
894
- case ELFCLASS64 :
950
+ case ELFCLASS64 : {
951
+ struct elf_funcs efuncs = {
952
+ .compare_extable = compare_extable_64 ,
953
+ .ehdr_shoff = ehdr64_shoff ,
954
+ .ehdr_shentsize = ehdr64_shentsize ,
955
+ .ehdr_shstrndx = ehdr64_shstrndx ,
956
+ .ehdr_shnum = ehdr64_shnum ,
957
+ .shdr_addr = shdr64_addr ,
958
+ .shdr_offset = shdr64_offset ,
959
+ .shdr_link = shdr64_link ,
960
+ .shdr_size = shdr64_size ,
961
+ .shdr_name = shdr64_name ,
962
+ .shdr_type = shdr64_type ,
963
+ .shdr_entsize = shdr64_entsize ,
964
+ .sym_type = sym64_type ,
965
+ .sym_name = sym64_name ,
966
+ .sym_value = sym64_value ,
967
+ .sym_shndx = sym64_shndx ,
968
+ };
969
+
970
+ e = efuncs ;
971
+ long_size = 8 ;
972
+ extable_ent_size = 16 ;
973
+
895
974
if (r2 (& ehdr -> e64 .e_ehsize ) != sizeof (Elf64_Ehdr ) ||
896
975
r2 (& ehdr -> e64 .e_shentsize ) != sizeof (Elf64_Shdr )) {
897
976
fprintf (stderr ,
@@ -900,25 +979,7 @@ static int do_file(char const *const fname, void *addr)
900
979
return -1 ;
901
980
}
902
981
903
- compare_extable = compare_extable_64 ;
904
- ehdr_shoff = ehdr64_shoff ;
905
- ehdr_shentsize = ehdr64_shentsize ;
906
- ehdr_shstrndx = ehdr64_shstrndx ;
907
- ehdr_shnum = ehdr64_shnum ;
908
- shdr_addr = shdr64_addr ;
909
- shdr_offset = shdr64_offset ;
910
- shdr_link = shdr64_link ;
911
- shdr_size = shdr64_size ;
912
- shdr_name = shdr64_name ;
913
- shdr_type = shdr64_type ;
914
- shdr_entsize = shdr64_entsize ;
915
- sym_type = sym64_type ;
916
- sym_name = sym64_name ;
917
- sym_value = sym64_value ;
918
- sym_shndx = sym64_shndx ;
919
- long_size = 8 ;
920
- extable_ent_size = 16 ;
921
-
982
+ }
922
983
break ;
923
984
default :
924
985
fprintf (stderr , "unrecognized ELF class %d %s\n" ,
0 commit comments