aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2021-05-01 22:59:59 +0200
committerChristian Grothoff <christian@grothoff.org>2021-05-01 22:59:59 +0200
commit1cb89d0393bac19f3b9e409ba46d1fd4136ff332 (patch)
tree2cebe25379cb82268a7b1426747fbcb4faa0ee59
parentad9dc67eb7331616c4bbe6229576495a25741928 (diff)
downloadlibextractor-1cb89d0393bac19f3b9e409ba46d1fd4136ff332.tar.gz
libextractor-1cb89d0393bac19f3b9e409ba46d1fd4136ff332.zip
revive ELF plugin
-rw-r--r--.gitignore258
-rw-r--r--ChangeLog3
-rw-r--r--src/plugins/Makefile.am15
-rw-r--r--src/plugins/elf_extractor.c (renamed from src/plugins/old/elf_extractor.c)460
-rw-r--r--src/plugins/pack.c (renamed from src/plugins/old/pack.c)0
-rw-r--r--src/plugins/pack.h (renamed from src/plugins/old/pack.h)0
-rw-r--r--src/plugins/test_elf.c83
-rwxr-xr-xsrc/plugins/testdata/chello-elfbin0 -> 2984 bytes
8 files changed, 411 insertions, 408 deletions
diff --git a/.gitignore b/.gitignore
index e508732..073b4ef 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,8 +1,4 @@
1On branch master 1**/*~
2Your branch is up-to-date with 'origin/master'.
3Untracked files:
4 (use "git add <file>..." to include in what will be committed)
5
6INSTALL 2INSTALL
7Makefile 3Makefile
8Makefile.in 4Makefile.in
@@ -72,290 +68,60 @@ src/main/extract.o
72src/main/getopt.o 68src/main/getopt.o
73src/main/getopt1.o 69src/main/getopt1.o
74src/main/libextractor.la 70src/main/libextractor.la
75src/main/libextractor_la-extractor.lo 71src/main/*.o
76src/main/libextractor_la-extractor.o 72src/main/*.lo
77src/main/libextractor_la-extractor_common.lo 73src/main/*.la
78src/main/libextractor_la-extractor_common.o 74src/main/*.trs
79src/main/libextractor_la-extractor_datasource.lo 75src/main/*.log
80src/main/libextractor_la-extractor_datasource.o
81src/main/libextractor_la-extractor_ipc.lo
82src/main/libextractor_la-extractor_ipc.o
83src/main/libextractor_la-extractor_ipc_gnu.lo
84src/main/libextractor_la-extractor_ipc_gnu.o
85src/main/libextractor_la-extractor_logging.lo
86src/main/libextractor_la-extractor_logging.o
87src/main/libextractor_la-extractor_metatypes.lo
88src/main/libextractor_la-extractor_metatypes.o
89src/main/libextractor_la-extractor_plugin_main.lo
90src/main/libextractor_la-extractor_plugin_main.o
91src/main/libextractor_la-extractor_plugins.lo
92src/main/libextractor_la-extractor_plugins.o
93src/main/libextractor_la-extractor_plugpath.lo
94src/main/libextractor_la-extractor_plugpath.o
95src/main/libextractor_la-extractor_print.lo
96src/main/libextractor_la-extractor_print.o
97src/main/libextractor_test.la
98src/main/libextractor_test2.la
99src/main/test-suite.log
100src/main/test2_extractor.lo
101src/main/test2_extractor.o
102src/main/test_bzip2 76src/main/test_bzip2
103src/main/test_bzip2.log
104src/main/test_bzip2.o
105src/main/test_bzip2.trs
106src/main/test_extractor.lo
107src/main/test_extractor.o
108src/main/test_file 77src/main/test_file
109src/main/test_file.log
110src/main/test_file.o
111src/main/test_file.trs
112src/main/test_gzip 78src/main/test_gzip
113src/main/test_gzip.log
114src/main/test_gzip.o
115src/main/test_gzip.trs
116src/main/test_ipc 79src/main/test_ipc
117src/main/test_ipc.log
118src/main/test_ipc.o
119src/main/test_ipc.trs
120src/main/test_plugin_load_multi 80src/main/test_plugin_load_multi
121src/main/test_plugin_load_multi.log
122src/main/test_plugin_load_multi.o
123src/main/test_plugin_load_multi.trs
124src/main/test_plugin_loading 81src/main/test_plugin_loading
125src/main/test_plugin_loading.log
126src/main/test_plugin_loading.o
127src/main/test_plugin_loading.trs
128src/main/test_trivial 82src/main/test_trivial
129src/main/test_trivial.log
130src/main/test_trivial.o
131src/main/test_trivial.trs
132src/plugins/.deps/ 83src/plugins/.deps/
133src/plugins/.libs/ 84src/plugins/.libs/
134src/plugins/Makefile 85src/plugins/Makefile
135src/plugins/Makefile.in 86src/plugins/Makefile.in
136src/plugins/archive_extractor.lo 87src/plugins/*.o
137src/plugins/archive_extractor.o 88src/plugins/*.lo
138src/plugins/deb_extractor.lo 89src/plugins/*.la
139src/plugins/deb_extractor.o 90src/plugins/*.log
140src/plugins/dvi_extractor.lo 91src/plugins/*.trs
141src/plugins/dvi_extractor.o
142src/plugins/exiv2_extractor.lo
143src/plugins/exiv2_extractor.o
144src/plugins/flac_extractor.lo
145src/plugins/flac_extractor.o
146src/plugins/gif_extractor.lo
147src/plugins/gif_extractor.o
148src/plugins/html_extractor.lo
149src/plugins/html_extractor.o
150src/plugins/it_extractor.lo
151src/plugins/it_extractor.o
152src/plugins/jpeg_extractor.lo
153src/plugins/jpeg_extractor.o
154src/plugins/thumbnailffmpeg_extractor.lo
155src/plugins/thumbnailffmpeg_extractor.o
156src/plugins/libextractor_archive.la
157src/plugins/libextractor_deb.la
158src/plugins/libextractor_dvi.la
159src/plugins/libextractor_exiv2.la
160src/plugins/libextractor_flac.la
161src/plugins/libextractor_gif.la
162src/plugins/libextractor_gstreamer.la
163src/plugins/libextractor_thumbnailffmpeg.la
164src/plugins/libextractor_gstreamer_la-gstreamer_extractor.lo
165src/plugins/libextractor_gstreamer_la-gstreamer_extractor.o
166src/plugins/libextractor_html.la
167src/plugins/libextractor_it.la
168src/plugins/libextractor_jpeg.la
169src/plugins/libextractor_man.la
170src/plugins/libextractor_midi.la
171src/plugins/libextractor_midi_la-midi_extractor.lo
172src/plugins/libextractor_midi_la-midi_extractor.o
173src/plugins/libextractor_mime.la
174src/plugins/libextractor_mpeg.la
175src/plugins/libextractor_nsf.la
176src/plugins/libextractor_nsfe.la
177src/plugins/libextractor_odf.la
178src/plugins/libextractor_ogg.la
179src/plugins/libextractor_ole2.la
180src/plugins/libextractor_ole2_la-ole2_extractor.lo
181src/plugins/libextractor_ole2_la-ole2_extractor.o
182src/plugins/libextractor_pdf.la
183src/plugins/libextractor_png.la
184src/plugins/libextractor_ps.la
185src/plugins/libextractor_riff.la
186src/plugins/libextractor_rpm.la
187src/plugins/libextractor_s3m.la
188src/plugins/libextractor_sid.la
189src/plugins/libextractor_thumbnailgtk.la
190src/plugins/libextractor_thumbnailgtk_la-thumbnailgtk_extractor.lo
191src/plugins/libextractor_thumbnailgtk_la-thumbnailgtk_extractor.o
192src/plugins/libextractor_tiff.la
193src/plugins/libextractor_wav.la
194src/plugins/libextractor_xm.la
195src/plugins/libextractor_zip.la
196src/plugins/libtest.la
197src/plugins/man_extractor.lo
198src/plugins/man_extractor.o
199src/plugins/mime_extractor.lo
200src/plugins/mime_extractor.o
201src/plugins/mpeg_extractor.lo
202src/plugins/mpeg_extractor.o
203src/plugins/nsf_extractor.lo
204src/plugins/nsf_extractor.o
205src/plugins/nsfe_extractor.lo
206src/plugins/nsfe_extractor.o
207src/plugins/odf_extractor.lo
208src/plugins/odf_extractor.o
209src/plugins/ogg_extractor.lo
210src/plugins/ogg_extractor.o
211src/plugins/pdf_extractor.lo
212src/plugins/pdf_extractor.o
213src/plugins/png_extractor.lo
214src/plugins/png_extractor.o
215src/plugins/ps_extractor.lo
216src/plugins/ps_extractor.o
217src/plugins/riff_extractor.lo
218src/plugins/riff_extractor.o
219src/plugins/rpm_extractor.lo
220src/plugins/rpm_extractor.o
221src/plugins/s3m_extractor.lo
222src/plugins/s3m_extractor.o
223src/plugins/sid_extractor.lo
224src/plugins/sid_extractor.o
225src/plugins/test-suite.log 92src/plugins/test-suite.log
226src/plugins/test_archive 93src/plugins/test_archive
227src/plugins/test_archive.log
228src/plugins/test_archive.o
229src/plugins/test_archive.trs
230src/plugins/test_deb 94src/plugins/test_deb
231src/plugins/test_deb.log
232src/plugins/test_deb.o
233src/plugins/test_deb.trs
234src/plugins/test_dvi 95src/plugins/test_dvi
235src/plugins/test_dvi.log 96src/plugins/test_elf
236src/plugins/test_dvi.o
237src/plugins/test_dvi.trs
238src/plugins/test_exiv2 97src/plugins/test_exiv2
239src/plugins/test_exiv2.log
240src/plugins/test_exiv2.o
241src/plugins/test_exiv2.trs
242src/plugins/test_flac 98src/plugins/test_flac
243src/plugins/test_flac.log
244src/plugins/test_flac.o
245src/plugins/test_flac.trs
246src/plugins/test_gif 99src/plugins/test_gif
247src/plugins/test_gif.log
248src/plugins/test_gif.o
249src/plugins/test_gif.trs
250src/plugins/test_gstreamer 100src/plugins/test_gstreamer
251src/plugins/test_gstreamer-test_gstreamer.o
252src/plugins/test_gstreamer.log
253src/plugins/test_gstreamer.trs
254src/plugins/test_html 101src/plugins/test_html
255src/plugins/test_html.log
256src/plugins/test_html.o
257src/plugins/test_html.trs
258src/plugins/test_it 102src/plugins/test_it
259src/plugins/test_it.log
260src/plugins/test_it.o
261src/plugins/test_it.trs
262src/plugins/test_jpeg 103src/plugins/test_jpeg
263src/plugins/test_jpeg.log
264src/plugins/test_jpeg.o
265src/plugins/test_jpeg.trs
266src/plugins/test_lib.lo
267src/plugins/test_lib.o
268src/plugins/test_man 104src/plugins/test_man
269src/plugins/test_man.log
270src/plugins/test_man.o
271src/plugins/test_man.trs
272src/plugins/test_midi 105src/plugins/test_midi
273src/plugins/test_midi.log
274src/plugins/test_midi.o
275src/plugins/test_midi.trs
276src/plugins/test_mime 106src/plugins/test_mime
277src/plugins/test_mime.log
278src/plugins/test_mime.o
279src/plugins/test_mime.trs
280src/plugins/test_mpeg 107src/plugins/test_mpeg
281src/plugins/test_mpeg.log
282src/plugins/test_mpeg.o
283src/plugins/test_mpeg.trs
284src/plugins/test_nsf 108src/plugins/test_nsf
285src/plugins/test_nsf.log
286src/plugins/test_nsf.o
287src/plugins/test_nsf.trs
288src/plugins/test_nsfe 109src/plugins/test_nsfe
289src/plugins/test_nsfe.log
290src/plugins/test_nsfe.o
291src/plugins/test_nsfe.trs
292src/plugins/test_odf 110src/plugins/test_odf
293src/plugins/test_odf.log
294src/plugins/test_odf.o
295src/plugins/test_odf.trs
296src/plugins/test_ogg 111src/plugins/test_ogg
297src/plugins/test_ogg.log
298src/plugins/test_ogg.o
299src/plugins/test_ogg.trs
300src/plugins/test_ole2 112src/plugins/test_ole2
301src/plugins/test_ole2.log
302src/plugins/test_ole2.o
303src/plugins/test_ole2.trs
304src/plugins/test_png 113src/plugins/test_png
305src/plugins/test_png.log
306src/plugins/test_png.o
307src/plugins/test_png.trs
308src/plugins/test_ps 114src/plugins/test_ps
309src/plugins/test_ps.log
310src/plugins/test_ps.o
311src/plugins/test_ps.trs
312src/plugins/test_riff 115src/plugins/test_riff
313src/plugins/test_riff.log
314src/plugins/test_riff.o
315src/plugins/test_riff.trs
316src/plugins/test_rpm 116src/plugins/test_rpm
317src/plugins/test_rpm.log
318src/plugins/test_rpm.o
319src/plugins/test_rpm.trs
320src/plugins/test_s3m 117src/plugins/test_s3m
321src/plugins/test_s3m.log
322src/plugins/test_s3m.o
323src/plugins/test_s3m.trs
324src/plugins/test_sid 118src/plugins/test_sid
325src/plugins/test_sid.log
326src/plugins/test_sid.o
327src/plugins/test_sid.trs
328src/plugins/test_thumbnailgtk 119src/plugins/test_thumbnailgtk
329src/plugins/test_thumbnailgtk.log
330src/plugins/test_thumbnailgtk.o
331src/plugins/test_thumbnailgtk.trs
332src/plugins/test_tiff 120src/plugins/test_tiff
333src/plugins/test_tiff.log
334src/plugins/test_tiff.o
335src/plugins/test_tiff.trs
336src/plugins/test_wav 121src/plugins/test_wav
337src/plugins/test_wav.log
338src/plugins/test_wav.o
339src/plugins/test_wav.trs
340src/plugins/test_xm 122src/plugins/test_xm
341src/plugins/test_xm.log
342src/plugins/test_xm.o
343src/plugins/test_xm.trs
344src/plugins/test_zip 123src/plugins/test_zip
345src/plugins/test_zip.log
346src/plugins/test_zip.o
347src/plugins/test_zip.trs
348src/plugins/tiff_extractor.lo
349src/plugins/tiff_extractor.o
350src/plugins/wav_extractor.lo
351src/plugins/wav_extractor.o
352src/plugins/xm_extractor.lo
353src/plugins/xm_extractor.o
354src/plugins/zip_extractor.lo
355src/plugins/zip_extractor.o
356stamp-h1 124stamp-h1
357test-driver 125test-driver
358
359nothing added to commit but untracked files present (use "git add" to track)
360src/plugins/test_thumbnailffmpeg 126src/plugins/test_thumbnailffmpeg
361build-aux/ 127build-aux/
diff --git a/ChangeLog b/ChangeLog
index c16dbf3..1e68017 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,6 @@
1Sat 01 May 2021 10:57:55 PM CEST
2 Revive ELF plugin (fixes #2516). -CG
3
1Tue 20 Apr 2021 06:33:46 PM CEST 4Tue 20 Apr 2021 06:33:46 PM CEST
2 Removing plugins depending on buggy, unstable libffmpeg library. -CG 5 Removing plugins depending on buggy, unstable libffmpeg library. -CG
3 6
diff --git a/src/plugins/Makefile.am b/src/plugins/Makefile.am
index a0e0ae3..8cbe21a 100644
--- a/src/plugins/Makefile.am
+++ b/src/plugins/Makefile.am
@@ -165,6 +165,7 @@ endif
165 165
166plugin_LTLIBRARIES = \ 166plugin_LTLIBRARIES = \
167 libextractor_dvi.la \ 167 libextractor_dvi.la \
168 libextractor_elf.la \
168 libextractor_it.la \ 169 libextractor_it.la \
169 libextractor_man.la \ 170 libextractor_man.la \
170 libextractor_nsf.la \ 171 libextractor_nsf.la \
@@ -200,6 +201,7 @@ endif
200 201
201check_PROGRAMS = \ 202check_PROGRAMS = \
202 test_dvi \ 203 test_dvi \
204 test_elf \
203 test_it \ 205 test_it \
204 test_man \ 206 test_man \
205 test_nsf \ 207 test_nsf \
@@ -283,6 +285,19 @@ test_dvi_SOURCES = \
283test_dvi_LDADD = \ 285test_dvi_LDADD = \
284 $(top_builddir)/src/plugins/libtest.la 286 $(top_builddir)/src/plugins/libtest.la
285 287
288libextractor_elf_la_SOURCES = \
289 elf_extractor.c \
290 pack.c pack.h
291libextractor_elf_la_LDFLAGS = \
292 $(PLUGINFLAGS)
293libextractor_elf_la_LIBADD = \
294 $(XLIB) $(SOCKET_LIBS)
295
296test_elf_SOURCES = \
297 test_elf.c
298test_elf_LDADD = \
299 $(top_builddir)/src/plugins/libtest.la
300
286 301
287libextractor_exiv2_la_SOURCES = \ 302libextractor_exiv2_la_SOURCES = \
288 exiv2_extractor.cc 303 exiv2_extractor.cc
diff --git a/src/plugins/old/elf_extractor.c b/src/plugins/elf_extractor.c
index 9c35e7c..379f615 100644
--- a/src/plugins/old/elf_extractor.c
+++ b/src/plugins/elf_extractor.c
@@ -1,10 +1,10 @@
1/* 1/*
2 This file is part of libextractor. 2 This file is part of libextractor.
3 Copyright (C) 2004, 2009 Vidyut Samanta and Christian Grothoff 3 Copyright (C) 2012 Vidyut Samanta and Christian Grothoff
4 4
5 libextractor is free software; you can redistribute it and/or modify 5 libextractor is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published 6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 2, or (at your 7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version. 8 option) any later version.
9 9
10 libextractor is distributed in the hope that it will be useful, but 10 libextractor is distributed in the hope that it will be useful, but
@@ -17,12 +17,17 @@
17 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 17 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18 Boston, MA 02110-1301, USA. 18 Boston, MA 02110-1301, USA.
19 */ 19 */
20 20/**
21 * @file plugins/gif_extractor.c
22 * @brief plugin to support GIF files
23 * @author Christian Grothoff
24 */
21#include "platform.h" 25#include "platform.h"
22#include "extractor.h" 26#include "extractor.h"
23#include "pack.h" 27#include "pack.h"
24#include <stdint.h> 28#include <stdint.h>
25 29
30
26typedef uint32_t Elf32_Addr; 31typedef uint32_t Elf32_Addr;
27typedef uint16_t Elf32_Half; 32typedef uint16_t Elf32_Half;
28typedef uint32_t Elf32_Off; 33typedef uint32_t Elf32_Off;
@@ -334,15 +339,34 @@ getByteorder (char ei_data)
334 * @return 0 on success, -1 on error 339 * @return 0 on success, -1 on error
335 */ 340 */
336static int 341static int
337getSectionHdr (const char *data, 342getSectionHdr (struct EXTRACTOR_ExtractContext *ec,
338 size_t size, 343 unsigned int bo,
339 Elf32_Ehdr *ehdr, Elf32_Half idx, Elf32_Shdr *ret) 344 const Elf32_Ehdr *ehdr,
345 Elf32_Half idx,
346 Elf32_Shdr *ret)
340{ 347{
348 ssize_t size;
349 uint64_t max;
350 int64_t off;
351 void *data;
352
341 if (ehdr->e_shnum <= idx) 353 if (ehdr->e_shnum <= idx)
342 return -1; 354 return -1;
343 355 max = ec->get_size (ec->cls);
344 EXTRACTOR_common_cat_unpack (&data[ehdr->e_shoff + ehdr->e_shentsize * idx], 356 if (ehdr->e_shoff + ehdr->e_shentsize * idx + sizeof (*ret) > max)
345 ELF_SECTION_SPECS[getByteorder (data[EI_CLASS])], 357 return -1;
358 off = ec->seek (ec->cls,
359 ehdr->e_shoff + ehdr->e_shentsize * idx,
360 SEEK_SET);
361 if (-1 == off)
362 return -1;
363 size = ec->read (ec->cls,
364 &data,
365 sizeof (*ret));
366 if (size < sizeof (*ret))
367 return -1;
368 EXTRACTOR_common_cat_unpack (data,
369 ELF_SECTION_SPECS[bo],
346 ELF_SECTION_FIELDS (ret)); 370 ELF_SECTION_FIELDS (ret));
347 return 0; 371 return 0;
348} 372}
@@ -353,15 +377,37 @@ getSectionHdr (const char *data,
353 * @return 0 on success, -1 on error 377 * @return 0 on success, -1 on error
354 */ 378 */
355static int 379static int
356getDynTag (const char *data, 380getDynTag (struct EXTRACTOR_ExtractContext *ec,
357 size_t size, 381 unsigned int bo,
358 Elf32_Ehdr *ehdr, 382 const Elf32_Ehdr *ehdr,
359 Elf32_Off off, Elf32_Word osize, unsigned int idx, Elf32_Dyn *ret) 383 Elf32_Off off,
384 Elf32_Word osize,
385 unsigned int idx,
386 Elf32_Dyn *ret)
360{ 387{
361 if ((off + osize > size) || ((idx + 1) * ELF_DYN_SIZE > osize)) 388 ssize_t size;
389 uint64_t max;
390 int64_t soff;
391 void *data;
392
393 max = ec->get_size (ec->cls);
394 if ( (off + osize > max) ||
395 ((idx + 1) * ELF_DYN_SIZE > osize) )
362 return -1; 396 return -1;
363 EXTRACTOR_common_cat_unpack (&data[off + idx * ELF_DYN_SIZE], 397 if (off + idx * ELF_DYN_SIZE + sizeof (*ret) > max)
364 ELF_DYN_SPECS[getByteorder (data[EI_CLASS])], 398 return -1;
399 soff = ec->seek (ec->cls,
400 off + idx * ELF_DYN_SIZE,
401 SEEK_SET);
402 if (-1 == soff)
403 return -1;
404 size = ec->read (ec->cls,
405 &data,
406 sizeof (*ret));
407 if (size < sizeof (*ret))
408 return -1;
409 EXTRACTOR_common_cat_unpack (data,
410 ELF_DYN_SPECS[bo],
365 ELF_DYN_FIELDS (ret)); 411 ELF_DYN_FIELDS (ret));
366 return 0; 412 return 0;
367} 413}
@@ -372,295 +418,385 @@ getDynTag (const char *data,
372 * @return 0 on success, -1 on error 418 * @return 0 on success, -1 on error
373 */ 419 */
374static int 420static int
375getProgramHdr (const char *data, 421getProgramHdr (struct EXTRACTOR_ExtractContext *ec,
376 size_t size, 422 unsigned int bo,
377 Elf32_Ehdr *ehdr, Elf32_Half idx, Elf32_Phdr *ret) 423 const Elf32_Ehdr *ehdr,
424 Elf32_Half idx,
425 Elf32_Phdr *ret)
378{ 426{
427 void *data;
428 ssize_t size;
429 int64_t off;
430
379 if (ehdr->e_phnum <= idx) 431 if (ehdr->e_phnum <= idx)
380 return -1; 432 return -1;
381 433 off = ec->seek (ec->cls,
382 EXTRACTOR_common_cat_unpack (&data[ehdr->e_phoff + ehdr->e_phensize * idx], 434 ehdr->e_phoff + ehdr->e_phensize * idx,
383 ELF_PHDR_SPECS[getByteorder (data[EI_CLASS])], 435 SEEK_SET);
384 ELF_PHDR_FIELDS (ret)); 436 if (-1 == off)
385 return 0;
386}
387
388
389/**
390 * Parse ELF header.
391 * @return 0 on success for 32 bit, 1 on success for 64 bit, -1 on error
392 */
393static int
394getELFHdr (const char *data,
395 size_t size,
396 Elf32_Ehdr *ehdr,
397 Elf64_Ehdr *ehdr64)
398{
399 /* catlib */
400 if (size < EI_NIDENT)
401 return -1; 437 return -1;
402 if (0 != strncmp (data, elfMagic, sizeof (elfMagic))) 438 size = ec->read (ec->cls,
403 return -1; /* not an elf */ 439 &data,
404 440 sizeof (*ret));
405 switch (data[EI_CLASS]) 441 if (size < sizeof (*ret))
406 {
407 case ELFCLASS32:
408 if (size < sizeof (Elf32_Ehdr) + EI_NIDENT)
409 return -1;
410 EXTRACTOR_common_cat_unpack (&data[EI_NIDENT],
411 ELF_HEADER_SPECS[getByteorder (data[EI_DATA])],
412 ELF_HEADER_FIELDS (ehdr));
413 if (ehdr->e_shoff + ehdr->e_shentsize * ehdr->e_shnum > size)
414 return -1; /* invalid offsets... */
415 if (ehdr->e_shentsize < ELF_SECTION_SIZE)
416 return -1; /* huh? */
417 if (ehdr->e_phoff + ehdr->e_phensize * ehdr->e_phnum > size)
418 return -1;
419 return 0;
420 case ELFCLASS64:
421 if (size < sizeof (Elf64_Ehdr) + EI_NIDENT)
422 return -1;
423 EXTRACTOR_common_cat_unpack (&data[EI_NIDENT],
424 ELF64_HEADER_SPECS[getByteorder (
425 data[EI_DATA])],
426 ELF64_HEADER_FIELDS (ehdr64));
427 if (ehdr64->e_shoff + ((uint32_t) ehdr64->e_shentsize * ehdr64->e_shnum) >
428 size)
429 return -1; /* invalid offsets... */
430 if (ehdr64->e_phoff + ((uint32_t) ehdr64->e_phensize * ehdr64->e_phnum) >
431 size)
432 return -1;
433 return 1;
434 default:
435 return -1; 442 return -1;
436 } 443 EXTRACTOR_common_cat_unpack (data,
444 ELF_PHDR_SPECS[bo],
445 ELF_PHDR_FIELDS (ret));
446 return 0;
437} 447}
438 448
439 449
440/** 450/**
441 * @return the string (offset into data, do NOT free), NULL on error 451 * @return the string (offset into data, do NOT free), NULL on error
442 */ 452 */
443static const char * 453static char *
444readStringTable (const char *data, 454readStringTable (struct EXTRACTOR_ExtractContext *ec,
445 size_t size, 455 unsigned int bo,
446 Elf32_Ehdr *ehdr, 456 const Elf32_Ehdr *ehdr,
447 Elf32_Half strTableOffset, Elf32_Word sh_name) 457 Elf32_Half strTableOffset,
458 Elf32_Word sh_name)
448{ 459{
449 Elf32_Shdr shrd; 460 Elf32_Shdr shrd;
450 if (-1 == getSectionHdr (data, size, ehdr, strTableOffset, &shrd)) 461 char *data;
462 ssize_t size;
463 int64_t off;
464
465 if (-1 == getSectionHdr (ec,
466 bo,
467 ehdr,
468 strTableOffset,
469 &shrd))
451 return NULL; 470 return NULL;
452 if ((shrd.sh_type != SHT_STRTAB) || 471 if ((shrd.sh_type != SHT_STRTAB) ||
453 (shrd.sh_offset + shrd.sh_size > size) || 472 (shrd.sh_size <= sh_name) )
454 (shrd.sh_size <= sh_name) || 473 return NULL;
455 (data[shrd.sh_offset + shrd.sh_size - 1] != '\0')) 474 off = ec->seek (ec->cls,
475 shrd.sh_offset,
476 SEEK_SET);
477 if (-1 == off)
456 return NULL; 478 return NULL;
457 return &data[shrd.sh_offset + sh_name]; 479 size = ec->read (ec->cls,
480 (void **) &data,
481 shrd.sh_size);
482 if (size < shrd.sh_size)
483 return NULL;
484 if (data[shrd.sh_size - 1] != '\0')
485 return NULL;
486 return strdup (&data[sh_name]);
458} 487}
459 488
460 489
461#define ADD(s, type) do { if (0!=proc (proc_cls, "elf", type, \ 490#define ADD(s, type) do { \
462 EXTRACTOR_METAFORMAT_UTF8, "text/plain", \ 491 if (0!=ec->proc (ec->cls, "elf", type, \
463 s, strlen (s) + 1)) return 1; \ 492 EXTRACTOR_METAFORMAT_UTF8, "text/plain", \
493 s, strlen (s) + 1)) \
494 { \
495 return; \
496 } \
464} while (0) 497} while (0)
465 498
466/* application/x-executable, ELF */ 499
467int 500/**
468EXTRACTOR_elf_extract (const char *data, 501 * Main entry method for the 'application/x-executable' extraction plugin.
469 size_t size, 502 *
470 EXTRACTOR_MetaDataProcessor proc, 503 * @param ec extraction context provided to the plugin
471 void *proc_cls, 504 */
472 const char *options) 505void
506EXTRACTOR_elf_extract_method (struct EXTRACTOR_ExtractContext *ec)
473{ 507{
474 Elf32_Ehdr ehdr; 508 Elf32_Ehdr ehdr;
475 Elf32_Half idx;
476 Elf64_Ehdr ehdr64; 509 Elf64_Ehdr ehdr64;
477 int ret; 510 int ret;
511 unsigned int bo;
512 char *data;
513 ssize_t size;
514 uint64_t max;
515 size_t want;
516
517 max = ec->get_size (ec->cls);
518 want = sizeof (ehdr);
519 if (sizeof (ehdr64) > want)
520 want = sizeof (ehdr64);
521 want += EI_NIDENT;
522 if (max < want)
523 return;
524 size = ec->read (ec->cls,
525 (void**) &data,
526 max);
527 if (size < EI_NIDENT)
528 return;
529 if (0 != memcmp (data,
530 elfMagic,
531 sizeof (elfMagic)))
532 return; /* not an elf */
533 switch (data[EI_CLASS])
534 {
535 case ELFCLASS32:
536 if (size < sizeof (Elf32_Ehdr) + EI_NIDENT)
537 return;
538 bo = getByteorder (data[EI_DATA]);
539 EXTRACTOR_common_cat_unpack (&data[EI_NIDENT],
540 ELF_HEADER_SPECS[bo],
541 ELF_HEADER_FIELDS (&ehdr));
542 if (ehdr.e_shoff + ehdr.e_shentsize * ehdr.e_shnum > max)
543 return; /* invalid offsets... */
544 if (ehdr.e_shentsize < ELF_SECTION_SIZE)
545 return; /* huh? */
546 if (ehdr.e_phoff + ehdr.e_phensize * ehdr.e_phnum > max)
547 return;
548 ret = 0;
549 bo = getByteorder (data[EI_CLASS]);
550 break;
551 case ELFCLASS64:
552 if (size < sizeof (Elf64_Ehdr) + EI_NIDENT)
553 return;
554 bo = getByteorder (data[EI_DATA]);
555 EXTRACTOR_common_cat_unpack (&data[EI_NIDENT],
556 ELF64_HEADER_SPECS[bo],
557 ELF64_HEADER_FIELDS (&ehdr64));
558 if (ehdr64.e_shoff + ((uint32_t) ehdr64.e_shentsize * ehdr64.e_shnum) >
559 max)
560 return; /* invalid offsets... */
561 if (ehdr64.e_phoff + ((uint32_t) ehdr64.e_phensize * ehdr64.e_phnum) >
562 max)
563 return;
564 bo = getByteorder (data[EI_CLASS]);
565 ret = 1;
566 break;
567 default:
568 return;
569 }
478 570
479 ret = getELFHdr (data, size, &ehdr, &ehdr64); 571 ADD ("application/x-executable",
480 if (ret == -1) 572 EXTRACTOR_METATYPE_MIMETYPE);
481 return 0;
482 ADD ("application/x-executable", EXTRACTOR_METATYPE_MIMETYPE);
483 switch ( ((unsigned char*) data)[EI_OSABI]) 573 switch ( ((unsigned char*) data)[EI_OSABI])
484 { 574 {
485 case ELFOSABI_LINUX: 575 case ELFOSABI_LINUX:
486 ADD ("Linux", EXTRACTOR_METATYPE_TARGET_OS); 576 ADD ("Linux",
577 EXTRACTOR_METATYPE_TARGET_OS);
487 break; 578 break;
488 case ELFOSABI_FREEBSD: 579 case ELFOSABI_FREEBSD:
489 ADD ("FreeBSD", EXTRACTOR_METATYPE_TARGET_OS); 580 ADD ("FreeBSD",
581 EXTRACTOR_METATYPE_TARGET_OS);
490 break; 582 break;
491 case ELFOSABI_NETBSD: 583 case ELFOSABI_NETBSD:
492 ADD ("NetBSD", EXTRACTOR_METATYPE_TARGET_OS); 584 ADD ("NetBSD",
585 EXTRACTOR_METATYPE_TARGET_OS);
493 break; 586 break;
494 case ELFOSABI_OPENBSD: 587 case ELFOSABI_OPENBSD:
495 ADD ("OpenBSD", EXTRACTOR_METATYPE_TARGET_OS); 588 ADD ("OpenBSD",
589 EXTRACTOR_METATYPE_TARGET_OS);
496 break; 590 break;
497 case ELFOSABI_IRIX: 591 case ELFOSABI_IRIX:
498 ADD ("IRIX", EXTRACTOR_METATYPE_TARGET_OS); 592 ADD ("IRIX",
593 EXTRACTOR_METATYPE_TARGET_OS);
499 break; 594 break;
500 default: 595 default:
501 break; 596 break;
502 } 597 }
503 switch ( (ret == 0) ? ehdr.e_type : ehdr64.e_type) 598 switch ( (0 == ret) ? ehdr.e_type : ehdr64.e_type)
504 { 599 {
505 case ET_REL: 600 case ET_REL:
506 ADD ("Relocatable file", EXTRACTOR_METATYPE_RESOURCE_TYPE); 601 ADD ("Relocatable file",
602 EXTRACTOR_METATYPE_RESOURCE_TYPE);
507 break; 603 break;
508 case ET_EXEC: 604 case ET_EXEC:
509 ADD ("Executable file", EXTRACTOR_METATYPE_RESOURCE_TYPE); 605 ADD ("Executable file",
606 EXTRACTOR_METATYPE_RESOURCE_TYPE);
510 break; 607 break;
511 case ET_DYN: 608 case ET_DYN:
512 ADD ("Shared object file", EXTRACTOR_METATYPE_RESOURCE_TYPE); 609 ADD ("Shared object file",
610 EXTRACTOR_METATYPE_RESOURCE_TYPE);
513 break; 611 break;
514 case ET_CORE: 612 case ET_CORE:
515 ADD ("Core file", EXTRACTOR_METATYPE_RESOURCE_TYPE); 613 ADD ("Core file",
614 EXTRACTOR_METATYPE_RESOURCE_TYPE);
516 break; 615 break;
517 default: 616 default:
518 break; /* unknown */ 617 break; /* unknown */
519 } 618 }
520 switch ( (ret == 0) ? ehdr.e_machine : ehdr64.e_machine) 619 switch ( (0 == ret) ? ehdr.e_machine : ehdr64.e_machine)
521 { 620 {
522 case EM_M32: 621 case EM_M32:
523 ADD ("M32", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 622 ADD ("M32",
623 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
524 break; 624 break;
525 case EM_386: 625 case EM_386:
526 ADD ("i386", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 626 ADD ("i386",
627 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
527 break; 628 break;
528 case EM_68K: 629 case EM_68K:
529 ADD ("68K", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 630 ADD ("68K",
631 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
530 break; 632 break;
531 case EM_88K: 633 case EM_88K:
532 ADD ("88K", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 634 ADD ("88K",
635 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
533 break; 636 break;
534 case EM_SPARC: 637 case EM_SPARC:
535 ADD ("Sparc", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 638 ADD ("Sparc",
639 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
536 break; 640 break;
537 case EM_860: 641 case EM_860:
538 ADD ("960", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 642 ADD ("960",
643 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
539 break; 644 break;
540 case EM_MIPS: 645 case EM_MIPS:
541 ADD ("MIPS", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 646 ADD ("MIPS",
647 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
542 break; 648 break;
543 case EM_PPC: 649 case EM_PPC:
544 ADD ("PPC", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 650 ADD ("PPC",
651 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
545 break; 652 break;
546 case EM_PPC64: 653 case EM_PPC64:
547 ADD ("PPC64", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 654 ADD ("PPC64",
655 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
548 break; 656 break;
549 case EM_S390: 657 case EM_S390:
550 ADD ("S390", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 658 ADD ("S390",
659 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
551 break; 660 break;
552 case EM_ARM: 661 case EM_ARM:
553 ADD ("ARM", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 662 ADD ("ARM",
663 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
554 break; 664 break;
555 case EM_ALPHA: 665 case EM_ALPHA:
556 ADD ("ALPHA", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 666 ADD ("ALPHA",
667 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
557 break; 668 break;
558 case EM_IA_64: 669 case EM_IA_64:
559 ADD ("IA-64", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 670 ADD ("IA-64",
671 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
560 break; 672 break;
561 case EM_X86_64: 673 case EM_X86_64:
562 ADD ("x86_64", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 674 ADD ("x86_64",
675 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
563 break; 676 break;
564 case EM_CUDA: 677 case EM_CUDA:
565 ADD ("NVIDIA CUDA", EXTRACTOR_METATYPE_TARGET_ARCHITECTURE); 678 ADD ("NVIDIA CUDA",
679 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE);
566 break; 680 break;
567 default: 681 default:
568 break; /* oops */ 682 break; /* oops */
569 } 683 }
570 684
571 if (ret != 0) 685 if (0 != ret)
572 return 0; /* FIXME: full support for 64-bit ELF... */ 686 return; /* FIXME: full support for 64-bit ELF... */
573 for (idx = 0; idx < ehdr.e_phnum; idx++) 687 for (Elf32_Half idx = 0; idx < ehdr.e_phnum; idx++)
574 { 688 {
575 Elf32_Phdr phdr; 689 Elf32_Phdr phdr;
576 690
577 if (0 != getProgramHdr (data, size, &ehdr, idx, &phdr)) 691 if (0 != getProgramHdr (ec,
578 return 0; 692 bo,
693 &ehdr,
694 idx,
695 &phdr))
696 return;
579 if (phdr.p_type == PT_DYNAMIC) 697 if (phdr.p_type == PT_DYNAMIC)
580 { 698 {
581 unsigned int dc = phdr.p_filesz / ELF_DYN_SIZE; 699 unsigned int dc = phdr.p_filesz / ELF_DYN_SIZE;
582 unsigned int id;
583 Elf32_Addr stringPtr; 700 Elf32_Addr stringPtr;
584 Elf32_Half stringIdx; 701 Elf32_Half stringIdx;
585 Elf32_Half six; 702 Elf32_Half six;
586 703
587 stringPtr = 0; 704 stringPtr = 0;
588 705 for (unsigned int id = 0; id < dc; id++)
589 for (id = 0; id < dc; id++)
590 { 706 {
591 Elf32_Dyn dyn; 707 Elf32_Dyn dyn;
592 if (0 != getDynTag (data, 708
593 size, 709 if (0 != getDynTag (ec,
710 bo,
594 &ehdr, 711 &ehdr,
595 phdr.p_offset, phdr.p_filesz, id, &dyn)) 712 phdr.p_offset,
596 return 0; 713 phdr.p_filesz,
714 id,
715 &dyn))
716 return;
597 if (DT_STRTAB == dyn.d_tag) 717 if (DT_STRTAB == dyn.d_tag)
598 { 718 {
599 stringPtr = dyn.d_un.d_ptr; 719 stringPtr = dyn.d_un.d_ptr;
600 break; 720 break;
601 } 721 }
602 } 722 }
603 if (stringPtr == 0) 723 if (0 == stringPtr)
604 return 0; 724 return;
605 for (six = 0; six < ehdr.e_shnum; six++) 725 for (six = 0; six < ehdr.e_shnum; six++)
606 { 726 {
607 Elf32_Shdr sec; 727 Elf32_Shdr sec;
608 if (-1 == getSectionHdr (data, size, &ehdr, six, &sec)) 728
609 return 0; 729 if (-1 == getSectionHdr (ec,
610 if ((sec.sh_addr == stringPtr) && (sec.sh_type == SHT_STRTAB)) 730 bo,
731 &ehdr,
732 six,
733 &sec))
734 return;
735 if ( (sec.sh_addr == stringPtr) &&
736 (sec.sh_type == SHT_STRTAB) )
611 { 737 {
612 stringIdx = six; 738 stringIdx = six;
613 break; 739 break;
614 } 740 }
615 } 741 }
616 if (six == ehdr.e_shnum) 742 if (six == ehdr.e_shnum)
617 return 0; /* stringIdx not found */ 743 return; /* stringIdx not found */
618 744
619 for (id = 0; id < dc; id++) 745 for (unsigned int id = 0; id < dc; id++)
620 { 746 {
621 Elf32_Dyn dyn; 747 Elf32_Dyn dyn;
622 if (0 != getDynTag (data, 748
623 size, 749 if (0 != getDynTag (ec,
750 bo,
624 &ehdr, 751 &ehdr,
625 phdr.p_offset, phdr.p_filesz, id, &dyn)) 752 phdr.p_offset,
626 return 0; 753 phdr.p_filesz,
754 id,
755 &dyn))
756 return;
627 switch (dyn.d_tag) 757 switch (dyn.d_tag)
628 { 758 {
629 case DT_RPATH: 759 case DT_RPATH:
630 { 760 {
631 const char *rpath; 761 char *rpath;
632 762
633 rpath = readStringTable (data, 763 rpath = readStringTable (ec,
634 size, 764 bo,
635 &ehdr, 765 &ehdr,
636 stringIdx, dyn.d_un.d_val); 766 stringIdx,
767 dyn.d_un.d_val);
637 /* "source" of the dependencies: path 768 /* "source" of the dependencies: path
638 to dynamic libraries */ 769 to dynamic libraries */
639 if (rpath != NULL) 770 if (NULL != rpath)
640 { 771 {
641 ADD (rpath, EXTRACTOR_METATYPE_LIBRARY_SEARCH_PATH); 772 ADD (rpath,
773 EXTRACTOR_METATYPE_LIBRARY_SEARCH_PATH);
774 free (rpath);
642 } 775 }
643 break; 776 break;
644 } 777 }
645 case DT_NEEDED: 778 case DT_NEEDED:
646 { 779 {
647 const char *needed; 780 char *needed;
648 781
649 needed = readStringTable (data, 782 needed = readStringTable (ec,
650 size, 783 bo,
651 &ehdr, 784 &ehdr,
652 stringIdx, dyn.d_un.d_val); 785 stringIdx,
653 if (needed != NULL) 786 dyn.d_un.d_val);
787 if (NULL != needed)
654 { 788 {
655 ADD (needed, EXTRACTOR_METATYPE_LIBRARY_DEPENDENCY); 789 ADD (needed,
790 EXTRACTOR_METATYPE_LIBRARY_DEPENDENCY);
791 free (needed);
656 } 792 }
657 break; 793 break;
658 } 794 }
659 } 795 }
660 } 796 }
661
662 } 797 }
663 } 798 }
664
665 return 0;
666} 799}
800
801
802/* end of gif_extractor.c */
diff --git a/src/plugins/old/pack.c b/src/plugins/pack.c
index 4f9e19d..4f9e19d 100644
--- a/src/plugins/old/pack.c
+++ b/src/plugins/pack.c
diff --git a/src/plugins/old/pack.h b/src/plugins/pack.h
index 74bc172..74bc172 100644
--- a/src/plugins/old/pack.h
+++ b/src/plugins/pack.h
diff --git a/src/plugins/test_elf.c b/src/plugins/test_elf.c
new file mode 100644
index 0000000..0400304
--- /dev/null
+++ b/src/plugins/test_elf.c
@@ -0,0 +1,83 @@
1/*
2 This file is part of libextractor.
3 Copyright (C) 2021 Christian Grothoff
4
5 libextractor is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 libextractor is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with libextractor; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18 Boston, MA 02110-1301, USA.
19*/
20/**
21 * @file plugins/test_elf.c
22 * @brief testcase for elf plugin
23 * @author Christian Grothoff
24 */
25#include "platform.h"
26#include "test_lib.h"
27
28
29/**
30 * Main function for the ELF testcase.
31 *
32 * @param argc number of arguments (ignored)
33 * @param argv arguments (ignored)
34 * @return 0 on success
35 */
36int
37main (int argc, char *argv[])
38{
39 struct SolutionData elf_sol[] = {
40 {
41 EXTRACTOR_METATYPE_MIMETYPE,
42 EXTRACTOR_METAFORMAT_UTF8,
43 "text/plain",
44 "application/x-executable",
45 strlen ("application/x-executable") + 1,
46 0
47 },
48 {
49 EXTRACTOR_METATYPE_TARGET_ARCHITECTURE,
50 EXTRACTOR_METAFORMAT_UTF8,
51 "text/plain",
52 "i386",
53 strlen ("i386") + 1,
54 0
55 },
56 {
57 EXTRACTOR_METATYPE_RESOURCE_TYPE,
58 EXTRACTOR_METAFORMAT_UTF8,
59 "text/plain",
60 "Executable file",
61 strlen ("Executable file") + 1,
62 0
63 },
64 {
65 EXTRACTOR_METATYPE_LIBRARY_DEPENDENCY,
66 EXTRACTOR_METAFORMAT_UTF8,
67 "text/plain",
68 "libc.so.6",
69 strlen ("libc.so.6") + 1,
70 0
71 },
72 { 0, 0, NULL, NULL, 0, -1 }
73 };
74 struct ProblemSet ps[] = {
75 { "testdata/chello-elf",
76 elf_sol },
77 { NULL, NULL }
78 };
79 return ET_main ("elf", ps);
80}
81
82
83/* end of test_elf.c */
diff --git a/src/plugins/testdata/chello-elf b/src/plugins/testdata/chello-elf
new file mode 100755
index 0000000..3422476
--- /dev/null
+++ b/src/plugins/testdata/chello-elf
Binary files differ