{"id":4082,"library":"lief","title":"LIEF - Library to Instrument Executable Formats","description":"LIEF (Library to Instrument Executable Formats) is a robust, cross-platform library designed to parse, modify, and abstract various executable formats, including ELF, PE, Mach-O, OAT, DEX, VDEX, and ART. It provides a comprehensive, user-friendly API for C++, Python, Rust, and C, enabling detailed analysis, manipulation, and reconstruction of binaries without relying on disassemblers. Currently at version 0.17.6, LIEF maintains an active development and release cadence, with frequent updates addressing new features and bug fixes.","status":"active","version":"0.17.6","language":"en","source_language":"en","source_url":"https://github.com/lief-project/LIEF","tags":["binary analysis","reverse engineering","executable formats","ELF","PE","Mach-O","parser","modifier"],"install":[{"cmd":"pip install lief","lang":"bash","label":"Install stable version from PyPI"}],"dependencies":[],"imports":[{"note":"The primary import for accessing all LIEF functionalities.","symbol":"lief","correct":"import lief"},{"note":"Access specific format parsers directly for clarity or C++-like behavior.","symbol":"lief.ELF","correct":"import lief\nelf_binary = lief.ELF.parse('/bin/ls')"},{"note":"Access specific format parsers directly for clarity or C++-like behavior.","symbol":"lief.PE","correct":"import lief\npe_binary = lief.PE.parse('C:\\\\Windows\\\\System32\\\\notepad.exe')"}],"quickstart":{"code":"import lief\nimport sys\nimport os\n\ndef analyze_binary(filepath):\n    if not os.path.exists(filepath):\n        print(f\"Error: File not found at {filepath}\")\n        return\n\n    binary = lief.parse(filepath)\n\n    if binary is None:\n        print(f\"Could not parse {filepath} as an executable.\")\n        return\n\n    print(f\"\\nAnalyzing: {filepath}\")\n    print(f\"  Format: {binary.format}\")\n    print(f\"  Entrypoint: {hex(binary.entrypoint)}\")\n    print(f\"  Number of sections: {len(binary.sections)}\")\n\n    # Example: Accessing ELF-specific features\n    if binary.format == lief.Binary.FORMATS.ELF:\n        elf_binary = binary.as_elf()\n        if elf_binary and elf_binary.header:\n            print(f\"  ELF Machine Type: {elf_binary.header.machine_type}\")\n            if elf_binary.dynamic_entries:\n                print(f\"  Number of dynamic entries: {len(elf_binary.dynamic_entries)}\")\n\n    # Example: Accessing PE-specific features\n    elif binary.format == lief.Binary.FORMATS.PE:\n        pe_binary = binary.as_pe()\n        if pe_binary and pe_binary.header:\n            print(f\"  PE Machine Type: {pe_binary.header.machine_type}\")\n            if pe_binary.imports:\n                print(f\"  Number of imported libraries: {len(pe_binary.imports)}\")\n\n# Try to analyze common executables based on OS\nif sys.platform.startswith('linux'):\n    analyze_binary('/bin/ls')\nelif sys.platform == 'win32':\n    analyze_binary('C:\\\\Windows\\\\System32\\\\notepad.exe')\nelif sys.platform == 'darwin':\n    analyze_binary('/bin/ls') # macOS also uses ELF/MachO, /bin/ls is a good example\nelse:\n    print(\"Unsupported OS for quickstart example.\")","lang":"python","description":"This quickstart demonstrates how to use `lief.parse()` to automatically detect and parse an executable file (ELF on Linux/macOS, PE on Windows). It then prints basic information about the binary, showcasing format-specific attributes like ELF machine type or number of PE imported libraries. Replace the default paths with your target binaries."},"warnings":[{"fix":"Review the 'PE Changelog for LIEF 0.17.0' documentation for specific API changes and migration guidance. Functions returning references that previously threw exceptions now return pointers (or Python `None`) on failure.","message":"LIEF v0.17.0 introduced a significant refactoring of the PE parser and builder API to align with ELF and Mach-O functionalities. Codebases processing PE binaries may require updates.","severity":"breaking","affected_versions":">=0.17.0"},{"fix":"Use `lief.PE.ParserConfig` to enable desired parsing options. For example, `config = lief.PE.ParserConfig(); config.parse_exports = True; binary = lief.PE.parse('path/to/pe.exe', config)`. Review `lief.PE.ParserConfig` for available flags.","message":"When parsing PE files (especially from v0.17.0 onwards), certain in-depth metadata (e.g., ARM64X binaries, exceptions, exports, imports, relocations, resources, signatures) might not be parsed by default. These options must be explicitly enabled.","severity":"gotcha","affected_versions":">=0.17.0"},{"fix":"Avoid using the `create_pe_from_scratch` functionality. Focus on modifying existing binaries, which has seen improvements in the builder engine.","message":"The `create_pe_from_scratch` feature (for building PE files from zero) was deprecated and removed in LIEF 0.17.0 due to significant bugs that often led to corrupted binaries.","severity":"breaking","affected_versions":">=0.17.0"},{"fix":"Upgrade to LIEF 0.17.0 or newer, as the builder engine for PE files has been refactored to address these limitations and provide a more conservative approach to modifications.","message":"Prior to version 0.17.0, modifying PE files using the Python API was highly bugged and often resulted in unexpected file size increases or corrupted binaries, especially when modifying sections like `.rsrc`.","severity":"gotcha","affected_versions":"<0.17.0"},{"fix":"Projects that compile LIEF from source or have custom build setups should review their build configurations, especially regarding `setuptools` and `scikit-build-core` as mentioned in the v0.14.0 changelog.","message":"LIEF v0.14.0 moved from Pybind11 to nanobind for its Python bindings. While this improved performance and compilation, internal changes for `setuptools` (replaced by `scikit-build-core`) could affect custom build processes.","severity":"deprecated","affected_versions":">=0.14.0"}],"env_vars":null,"last_verified":"2026-04-11T00:00:00.000Z","next_check":"2026-07-10T00:00:00.000Z"}