The objective of this tutorial is to provide an overview of LIEF’s API for parsing and manipulating formats.
ELF format. To create an ELF.Binary from a file, simply pass its path to the or functions.Note
import lief
binary = lief.parse("/bin/ls")
Once the ELF file has been parsed, we can access its Header:
header = binary.header
To change the entry point and the target architecture (ARCH):
header.entrypoint = 0x123
header.machine_type = lief.ELF.ARCH.AARCH64
Then, write these changes to a new ELF binary:
binary.write("ls.modified")
We can also iterate over the Section entries as follows:
for section in binary.sections:
print(section.name) # section name
print(section.size) # section size
print(len(section.content)) # Should match the previous print
To modify the content of the .text section:
text = binary.get_section(".text")
text.content = bytes([0x33] * text.size)
ELF section, you can use the or functions to create a PE.Binaryimport lief
binary = lief.parse("C:\\Windows\\explorer.exe")
To access the various PE headers (DosHeader, Header, and OptionalHeader):
print(binary.dos_header)
print(binary.header)
print(binary.optional_header)
You can also access imported functions in two ways:
Using the abstract layer
Using the PE definition
# Using the abstract layer
for func in binary.imported_functions:
print(func)
# Using the PE definition
for func in binary.imports:
print(func)
For finer granularity regarding the location of imported functions in libraries, or to access other fields of the PE imports, we can process the imports as follows:
for imported_library in binary.imports:
print("Library name: " + imported_library.name)
for func in imported_library.entries:
if not func.is_ordinal:
print(func.name)
print(func.iat_address)