-
Notifications
You must be signed in to change notification settings - Fork 15
/
Copy pathparse_sht.c
132 lines (114 loc) · 4.06 KB
/
parse_sht.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
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
/**************************************************************************************
* Author: Abhinav Thakur *
* email : [email protected] *
* *
* Description: Parser for Section Header Table as a part of Binary Dissection Course *
* *
**************************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <elf.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/mman.h>
#include <stdint.h>
#include <unistd.h>
/*
typedef struct {
uint32_t sh_name;
uint32_t sh_type;
uint64_t sh_flags;
Elf64_Addr sh_addr;
Elf64_Off sh_offset;
uint64_t sh_size;
uint32_t sh_link;
uint32_t sh_info;
uint64_t sh_addralign;
uint64_t sh_entsize;
} Elf64_Shdr;
*/
void parseSht (uint8_t *map) {
Elf64_Ehdr *ehdr = (Elf64_Ehdr *) map;
Elf64_Shdr *sht = (Elf64_Shdr *) &map[ehdr->e_shoff];
char *shstrtab = &map[ sht[ehdr->e_shstrndx].sh_offset ];
fprintf (stderr, "shstrtab: first string: %s\n", shstrtab);
for (int i = 0; i < ehdr->e_shnum; ++i) {
/* sh_name */
fprintf (stderr, "[%d] %s\n\t", i, &shstrtab[sht[i].sh_name]);
/* sh_type */
switch (sht[i].sh_type) {
case SHT_NULL: fprintf (stderr, "NULL");
break;
case SHT_PROGBITS: fprintf (stderr, "PROGBITS");
break;
case SHT_SYMTAB: fprintf (stderr, "SYMTAB");
break;
case SHT_STRTAB: fprintf (stderr, "STRTAB");
break;
case SHT_RELA: fprintf (stderr, "RELA");
break;
case SHT_GNU_HASH: fprintf (stderr, "GNU HASH");
break;
case SHT_DYNAMIC: fprintf (stderr, "DYNAMIC");
break;
case SHT_NOTE: fprintf (stderr, "NOTE");
break;
case SHT_NOBITS: fprintf (stderr, "NOBITS");
break;
case SHT_REL: fprintf (stderr, "REL");
break;
case SHT_SHLIB: fprintf (stderr, "SHLIB");
break;
case SHT_DYNSYM: fprintf (stderr, "DYNSYM");
break;
case SHT_LOPROC: fprintf (stderr, "LOPROC");
break;
case SHT_HIPROC: fprintf (stderr, "HIPROC");
break;
case SHT_LOUSER: fprintf (stderr, "LOUSER");
break;
case SHT_HIUSER: fprintf (stderr, "HIUSER");
break;
default: fprintf (stderr, "Unknown Section");
break;
}
fprintf (stderr, "\t");
/* sh_flags */
if (sht[i].sh_flags & SHF_WRITE) fprintf (stderr, "W");
else fprintf (stderr, " ");
if (sht[i].sh_flags & SHF_ALLOC) fprintf (stderr, "A");
fprintf (stderr, " ");
if (sht[i].sh_flags & SHF_EXECINSTR)fprintf (stderr, "X");
fprintf (stderr, " ");
if (sht[i].sh_flags & SHF_MASKPROC) fprintf (stderr, "M");
fprintf (stderr, " ");
fprintf (stderr, "\t");
/* Similarly, one can access any field of a section header */
fprintf (stderr, "\n");
}
}
int main (int argc, char **argv) {
int fd;
struct stat sb;
uint8_t *map;
if (argc != 2) {
fprintf (stderr, "Usage: %s <target_binary_path>\n", argv[0]);
exit (-1);
}
fd = open (argv[1], O_RDONLY);
if (fd == -1) {
perror ("while opening target binary");
exit (-1);
}
if (fstat (fd, &sb) == -1) {
perror ("while fstat'ing target binary");
exit (-1);
}
map = (uint8_t *) mmap ( NULL, sb.st_size, PROT_READ, MAP_PRIVATE, fd, 0);
if (map == MAP_FAILED) {
perror ("while mmap'ing target binary");
exit(-1);
}
parseSht (map);
}