ARTICLE

Understanding ELF using readelf and objdump
Contributed by Mulyadi Santosa in Misc on 2006-06-16 00:00:00

What is ELF? ELF (Executable and Linking Format) is file format that defines how an object file is composed and organized. With this information, your kernel and the binary loader know how to load the file, where to look for the code, where to look the initialized data, which shared library that needs to be loaded and so on.

First of all, you should know about different kind of ELF object:

  • Relocatable file: an object file that holds code and data suitable for linking with other object files to create an executable or a shared object file. In other word, you can say that relocatable file is a foundation for creating executables and libraries.

    This is kind of file you get if you compile a source code like this:

    $ gcc -c test.c

    That will produce test.o, which is a relocatable file.

    Kernel module (either suffixed with .o or .ko) is also a form of relocatable file.

  • Executable file: object file that holds a program suitable for execution. Yes, that means, your XMMS mp3 player, your vcd software player, even your text editor are all ELF executable files.

    This is also a familiar file if you compile a program:

    $ gcc -o test test.c

    After you make sure the executable bit of "test" is enabled, you can execute it. The question is, what about shell script? Shell script is NOT ELF executable, but the interpreter IS.

  • Shared object file: This file holds code and data suitable for linking in two contexts:

    1. The link editor may process it with other relocatable and shared shared object file to create another object file.
    2. The dynamic linker combines it with an executable file and other shared objects to create a process image.

    In simple words, these are the files that you usually see with suffix .so (normally located inside /usr/lib on most Linux installation).

Is there any other way to detect the ELF type? Yes there is. In every ELF object, there is a file header that explains what kind file it is. Assuming you have installed binutils package, you can use readelf to read this header. For example (command results are shortened to show related fields only):

$ readelf -h /bin/ls
Type:  EXEC (Executable file)

$ readelf -h  /usr/lib/crt1.o
Type:  REL (Relocatable file)

$ readelf -h /lib/libc-2.3.2.so
Type:  DYN (Shared object file)

"File" command works too for object file identification, but I won't discuss it further. Let's focus on readelf and objdump, since we will use both of them.

To make us easier to study ELF, you can use the following simple C program:

/* test.c */
#include

int global_data = 4;
int global_data_2;

int main(int argc, char **argv)
{
        int local_data = 3;

        printf("Hello World\n");
        printf("global_data = %d\n", global_data);
        printf("global_data_2 = %d\n", global_data_2);
        printf("local_data = %d\n", local_data);

        return (0);
}

And compile it:

$ gcc -o test test.c

A. Examining ELF header.

The produced binary will be our examination target. Let's start with the content of the ELF header:

$ readelf -h test
ELF Header:
  Magic:   7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00
  Class:                             ELF32
  Data:                              2's 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:               0x80482c0
  Start of program headers:          52 (bytes into file)
  Start of section headers:          2060 (bytes into file)
  Flags:                             0x0
  Size of this header:               52 (bytes)
  Size of program headers:           32 (bytes)
  Number of program headers:         7
  Size of section headers:           40 (bytes)
  Number of section headers:         28
  Section header string table index: 25

What does this header tell us?

  • This executable is created for Intel x86 32 bit architecture ("machine" and "class" fields).

  • When executed, program will start running from virtual address 0x80482c0 (see entry point address). The "0x" prefix here means it is a hexadecimal number. This address doesn't point to our main() procedure, but to a procedure named _start. Never felt you had created such thing? Of course you don't. _start procedure is created by the linker whose purpose is to initialize your program.

  • This program has a total of 28 sections and 7 segments.

What is section? Section is an area in the object file that contains information which is useful for linking: program's code, program's data (variables, array, string), relocation information and other. So, in each area, several information is grouped and it has a distinct meaning: code section only hold code, data section only holds initialized or non-initialized data, etc. Section Header Table (SHT) tells us exactly what sections the ELF object has, but at least by looking on "Number of section headers" field above, you can tell that "test" contains 28 sections.

If section has meaning for the binary, our Linux kernel doesn't see it the same way. The Linux kernel prepares several VMA (virtual memory area) that contains virtually contigous page frames. Inside these VMA, one or more sections are mapped. Each VMA in this case represents an ELF segment. How the kernel knows which section goes to which segment? This is the function of Program Header Table(PHT).

Figure 1. ELF structure in two different point of view.



Article Index
Understanding ELF using readelf and objdump
Examining Section Header Table(SHT)
How a function is referenced?
 
Discussion(s)
adfaf
Written by adfa on 2007-05-09 11:14:29
afdaf
Discuss! Reply!

sw
Written by hi on 2007-06-27 10:08:36
sws
Discuss! Reply!

nice
Written by trakos on 2007-12-28 11:31:24
Nice work!
Discuss! Reply!

Khali The Great
Written by Khali The Great on 2008-05-09 06:02:24
Real Nice
Discuss! Reply!

Thanks!
Written by iron on 2008-06-12 20:39:23
This was a very informative article.
Discuss! Reply!

WOW!
Written by someone on 2008-06-18 11:37:24
Wow!
Discuss! Reply!