1 #define _POSIX_C_SOURCE 200112L
12 #define RELOCATABLE 0x1
13 #define EXECUTABLE 0x2
18 int readline(FILE *f, char *fn);
19 int checkfile(char *fn, unsigned int want, int perr, int quiet);
24 int main(int ac, char **av) {
26 unsigned int want = 0;
35 while ((option = getopt(ac, av, "vtnredclaqp0f:")) != -1) {
37 case 'r': want |= RELOCATABLE; break;
38 case 'e': want |= EXECUTABLE; break;
39 case 'd': want |= DYNAMIC; break;
40 case 'c': want |= CORE; break;
41 case 'l': want |= SYMLINKS; break;
42 case 'a': want = (RELOCATABLE|EXECUTABLE|DYNAMIC|CORE); break;
43 case 'q': quiet++; break;
44 case 't': printtype++; break;
45 case 'n': printname++; break;
46 case 'v': verbose++; break;
47 case 'p': perr++; break;
48 case '0': zeroterm = 1; break;
50 if (optarg[0] == '-' && optarg[1] == 0) {
53 list = fopen(optarg, "r");
62 if (!want) want = (RELOCATABLE|EXECUTABLE|DYNAMIC|CORE);
68 while (readline(list, fn)) {
69 if ((type = checkfile(fn, want,perr,quiet)) & want) {
73 printf("relocatable "); break;
75 printf("executable "); break;
77 printf("dynamic "); break;
79 printf("core "); break;
81 printf("notelf "); break;
92 if (verbose) fprintf(stderr, "checking %s\n", av[optind]);
93 type = checkfile(fn,want,perr,quiet);
98 printf("relocatable"); break;
100 printf("executable"); break;
102 printf("dynamic"); break;
104 printf("core"); break;
106 printf("notelf"); break;
111 printf("%s%s", printtype ? " " : "", fn);
113 if (printtype || printname) printf("\n");
115 return type & want ? 0 : 1;
117 return errors ? 1 : 0;
120 int readline(FILE *f, char *fn) {
129 if (i == 0) continue;
133 if (i == 0) continue;
141 /* TODO print an error */
150 int checkfile(char *fn, unsigned int want, int perr, int quiet) {
156 if (want & SYMLINKS) {
161 if (!S_ISREG(st.st_mode)) {
165 fd = open(fn, O_RDONLY);
171 bytes = read(fd, &hdr, sizeof hdr);
173 if (bytes < sizeof hdr) {
174 if (perr) fprintf(stderr, "could not read full elf header (wanted %zu got %d bytes)\n", sizeof hdr, bytes);
177 if (hdr.e_ident[EI_MAG0] != ELFMAG0
178 || hdr.e_ident[EI_MAG1] != ELFMAG1
179 || hdr.e_ident[EI_MAG2] != ELFMAG2
180 || hdr.e_ident[EI_MAG3] != ELFMAG3
182 if (perr) fprintf(stderr, "elf header magic wrong\n");
185 switch (hdr.e_ident[EI_CLASS]) {
191 if (perr) fprintf(stderr, "elf header unknown class\n");
195 endian = hdr.e_ident[EI_DATA];
197 case ELFDATA2LSB: break;
198 case ELFDATA2MSB: break;
199 /* TODO swap endian if needed */
201 if (perr) fprintf(stderr, "elf header unknown endian\n");
205 switch (hdr.e_type) {
206 case ET_REL: return RELOCATABLE;
207 case ET_EXEC: return EXECUTABLE;
208 case ET_DYN: return DYNAMIC;
209 case ET_CORE: return CORE;
212 if (perr) fprintf(stderr, "unknown %s\n", fn);