Rebuilding ELF from Coredump

Recovering ELF from memory dumps are not new and are well discussed many times in many places. I have used Silvio Cesare's work [ELF EXECUTABLE RECONSTRUCTION FROM A CORE IMAGE] and code here to rebuild many of ELF metadata along with dynamic linking details. Many of these section headers may or may not exists. This is a POC code. Here is the link to source core2elf

[email protected]:~/corerec$ ./hello
Hello World!

[email protected]:~/corerec$ file core
core: ELF 32-bit LSB core file Intel 80386, version 1 (SYSV), SVR4-style, from '/home/renorobert/corerec/hello'

[email protected]:~/corerec$ ./core_recover
[*] Program headers of CORE
0x00000000 - 0x00000000
0x08048000 - 0x08049000
0x08049000 - 0x0804a000
0x0804a000 - 0x0804b000
0xf7e09000 - 0xf7e0a000
0xf7e0a000 - 0xf7fb2000
0xf7fb2000 - 0xf7fb4000
0xf7fb4000 - 0xf7fb5000
0xf7fb5000 - 0xf7fb8000
0xf7fd7000 - 0xf7fd9000
0xf7fd9000 - 0xf7fda000
0xf7fda000 - 0xf7fdc000
0xf7fdc000 - 0xf7ffc000
0xf7ffc000 - 0xf7ffd000
0xf7ffd000 - 0xf7ffe000
0xfffdc000 - 0xffffe000

[*] Program headers of ELF
0x08048034 - 0x08048154
0x08048154 - 0x08048167
0x08048000 - 0x080485bc
0x08049f08 - 0x0804a024
0x08049f14 - 0x08049ffc
0x08048168 - 0x080481ac
0x080484e0 - 0x0804850c
0x00000000 - 0x00000000
0x08049f08 - 0x0804a000

[*] Building section headers from program headers
[*] Building section headers from DYNAMIC section
[*] 6 GOT entries found
[*] Patching GOT entries to PLT address
[*] Done

[email protected]:~/corerec$ file ./rebuild.elf
./rebuild.elf: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked (uses shared libs), for GNU/Linux 2.6.24, stripped


[email protected]:~/corerec$ readelf -a ./rebuild.elf
ELF Header:
Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00
Class: ELF32
Data: 2s complement, little endian
Version: 1 (current)
OS/ABI: UNIX - System V
ABI Version: 0
Type: EXEC (Executable file)
Machine: Intel 80386
Version: 0x1
Entry point address: 0x8048320
Start of program headers: 52 (bytes into file)
Start of section headers: 4412 (bytes into file)
Flags: 0x0
Size of this header: 52 (bytes)
Size of program headers: 32 (bytes)
Number of program headers: 9
Size of section headers: 40 (bytes)
Number of section headers: 25
Section header string table index: 1

Section Headers:
[Nr] Name Type Addr Off Size ES Flg Lk Inf Al
[ 0] NULL 00000000 000000 000000 00 0 0 0
[ 1] .shstrtab STRTAB 00000000 001020 00011c 00 0 0 1
[ 2] .interp PROGBITS 08048154 000154 000013 00 A 0 0 1
[ 3] .dynamic DYNAMIC 08049f14 000f14 0000e8 08 A 0 0 4
[ 4] .note NOTE 08048168 000168 000044 00 A 0 0 1
[ 5] .eh_frame_hdr PROGBITS 080484e0 0004e0 00002c 00 A 0 0 4
[ 6] .eh_frame PROGBITS 0804850c 00050c 0000b0 00 A 0 0 4
[ 7] .bss NOBITS 0804a020 001020 000004 00 WA 0 0 4
[ 8] .init_array INIT_ARRAY 08049f08 000f08 000004 00 WA 0 0 4
[ 9] .fini_array FINI_ARRAY 08049f0c 000f0c 000004 00 WA 0 0 4
[10] .jcr PROGBITS 08049f10 000f10 000004 00 WA 0 0 4
[11] .got.plt PROGBITS 0804a000 001000 000018 00 WA 0 0 4
[12] .data PROGBITS 0804a018 001018 000008 00 WA 0 0 4
[13] .dynstr STRTAB 0804821c 00021c 000049 00 A 0 0 1
[14] .dynsym DYNSYM 080481cc 0001cc 000050 10 A 13 2 4
[15] .init PROGBITS 080482b0 0002b0 000030 00 AX 0 0 4
[16] .plt PROGBITS 080482e0 0002e0 000040 04 AX 0 0 16
[17] .text PROGBITS 08048320 000320 000194 00 AX 0 0 16
[18] .fini PROGBITS 080484b4 0004b4 000000 00 AX 0 0 4
[19] .rel.dyn REL 08048290 000290 000008 08 A 14 0 4
[20] .rel.plt REL 08048298 000298 000018 08 A 14 16 4
[21] .gnu.version VERSYM 08048266 000266 00000a 02 A 14 0 2
[22] .gnu.version_r VERNEED 08048270 000270 000020 00 A 13 1 4
[23] .gnu.hash GNU_HASH 080481ac 0001ac 000020 00 A 14 0 4
[24] .got PROGBITS 08049ffc 000ffc 000004 04 WA 0 0 4
Key to Flags:
W (write), A (alloc), X (execute), M (merge), S (strings)
I (info), L (link order), G (group), T (TLS), E (exclude), x (unknown)
O (extra OS processing required) o (OS specific), p (processor specific)

There are no section groups in this file.

Program Headers:
Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align
PHDR 0x000034 0x08048034 0x08048034 0x00120 0x00120 R E 0x4
INTERP 0x000154 0x08048154 0x08048154 0x00013 0x00013 R 0x1
[Requesting program interpreter: /lib/ld-linux.so.2]
LOAD 0x000000 0x08048000 0x08048000 0x005bc 0x005bc R E 0x1000
LOAD 0x000f08 0x08049f08 0x08049f08 0x00118 0x0011c RW 0x1000
DYNAMIC 0x000f14 0x08049f14 0x08049f14 0x000e8 0x000e8 RW 0x4
NOTE 0x000168 0x08048168 0x08048168 0x00044 0x00044 R 0x4
GNU_EH_FRAME 0x0004e0 0x080484e0 0x080484e0 0x0002c 0x0002c R 0x4
GNU_STACK 0x000000 0x00000000 0x00000000 0x00000 0x00000 RW 0x10
GNU_RELRO 0x000f08 0x08049f08 0x08049f08 0x000f8 0x000f8 R 0x1

Section to Segment mapping:
Segment Sections...
00
01 .interp
02 .interp .note .eh_frame_hdr .eh_frame .dynstr .dynsym .init .plt .text .fini .rel.dyn .rel.plt .gnu.version .gnu.version_r .gnu.hash
03 .dynamic .bss .init_array .fini_array .jcr .got.plt .data .got
04 .dynamic
05 .note
06 .eh_frame_hdr
07
08 .dynamic .init_array .fini_array .jcr .got

Dynamic section at offset 0xf14 contains 24 entries:
Tag Type Name/Value
0x00000001 (NEEDED) Shared library: [libc.so.6]
0x0000000c (INIT) 0x80482b0
0x0000000d (FINI) 0x80484b4
0x00000019 (INIT_ARRAY) 0x8049f08
0x0000001b (INIT_ARRAYSZ) 4 (bytes)
0x0000001a (FINI_ARRAY) 0x8049f0c
0x0000001c (FINI_ARRAYSZ) 4 (bytes)
0x6ffffef5 (GNU_HASH) 0x80481ac
0x00000005 (STRTAB) 0x804821c
0x00000006 (SYMTAB) 0x80481cc
0x0000000a (STRSZ) 74 (bytes)
0x0000000b (SYMENT) 16 (bytes)
0x00000015 (DEBUG) 0xf7ffd924
0x00000003 (PLTGOT) 0x804a000
0x00000002 (PLTRELSZ) 24 (bytes)
0x00000014 (PLTREL) REL
0x00000017 (JMPREL) 0x8048298
0x00000011 (REL) 0x8048290
0x00000012 (RELSZ) 8 (bytes)
0x00000013 (RELENT) 8 (bytes)
0x6ffffffe (VERNEED) 0x8048270
0x6fffffff (VERNEEDNUM) 1
0x6ffffff0 (VERSYM) 0x8048266
0x00000000 (NULL) 0x0

Relocation section '.rel.dyn' at offset 0x290 contains 1 entries:
Offset Info Type Sym.Value Sym. Name
08049ffc 00000206 R_386_GLOB_DAT 00000000 __gmon_start__

Relocation section '.rel.plt' at offset 0x298 contains 3 entries:
Offset Info Type Sym.Value Sym. Name
0804a00c 00000107 R_386_JUMP_SLOT 00000000 puts
0804a010 00000207 R_386_JUMP_SLOT 00000000 __gmon_start__
0804a014 00000307 R_386_JUMP_SLOT 00000000 __libc_start_main

The decoding of unwind sections for machine type Intel 80386 is not currently supported.

Symbol table '.dynsym' contains 5 entries:
Num: Value Size Type Bind Vis Ndx Name
0: 00000000 0 NOTYPE LOCAL DEFAULT UND
1: 00000000 0 FUNC GLOBAL DEFAULT UND [email protected]_2.0 (2)
2: 00000000 0 NOTYPE WEAK DEFAULT UND __gmon_start__
3: 00000000 0 FUNC GLOBAL DEFAULT UND [email protected]_2.0 (2)
4: 080484cc 4 OBJECT GLOBAL DEFAULT 15 _IO_stdin_used

Histogram for '.gnu.hash' bucket list length (total of 2 buckets):
Length Number % of total Coverage
0 1 ( 50.0%)
1 1 ( 50.0%) 100.0%

Version symbols section '.gnu.version' contains 5 entries:
Addr: 0000000008048266 Offset: 0x000266 Link: 14 (.dynsym)
000: 0 (*local*) 2 (GLIBC_2.0) 0 (*local*) 2 (GLIBC_2.0)
004: 1 (*global*)

Version needs section '.gnu.version_r' contains 1 entries:
Addr: 0x0000000008048270 Offset: 0x000270 Link: 13 (.dynstr)
000000: Version: 1 File: libc.so.6 Cnt: 1
0x0010: Name: GLIBC_2.0 Flags: none Version: 2

Displaying notes found at file offset 0x00000168 with length 0x00000044:
Owner Data size Description
GNU 0x00000010 NT_GNU_ABI_TAG (ABI version tag)
OS: Linux, ABI: 2.6.24
GNU 0x00000014 NT_GNU_BUILD_ID (unique build ID bitstring)
Build ID: e8ee1fa34adec405fcd55e166c0508d2f941b6f2

[email protected]:~/corerec$ ./rebuild.elf
Hello World!

[email protected]:~/corerec$ lsb_release -a
No LSB modules are available.
Distributor ID: Ubuntu
Description: Ubuntu 14.04.2 LTS
Release: 14.04
Codename: trusty


[email protected]:~/corerec$ uname -a
Linux ubuntu 3.16.0-30-generic #40~14.04.1-Ubuntu SMP Thu Jan 15 17:43:14 UTC 2015 x86_64 x86_64 x86_64 GNU/Linux
Uncategorized