Skip to main content

Basic Python project scaffold for dwarffi.

Project description

dwarffi

An authentic, DWARF-powered FFI for Python.

dwarffi allows you to interact with C memory layouts using Intermediate Symbol Files (ISF) generated from DWARF debug information. It provides a CFFI-like experience without requiring header files—instead, it uses the actual compiled structures from your binaries.

Whether you're doing embedded systems reverse engineering, interacting with a QEMU instance, or analyzing kernel memory, dwarffi ensures that bitness, endianness, and padding are handled exactly as they appear in the target architecture.

🚀 Features

DWARF-Native: No need to rewrite C headers. Just point to a .json or .json.xz ISF file (generated by dwarf2json).

Architecture Agnostic: Seamlessly handles Big Endian (PowerPC/MIPS) and Little Endian (ARM/x86) in the same script.

Dynamic cdef: Compile C code on the fly to generate types, with automatic "type-keep" logic to prevent the compiler from stripping unused definitions.

Recursive Typedefs: Automatic type decay for typedef chains.

C-Style Magic: Supports pointer arithmetic (ptr + 5), array slicing (arr[1:5]), and deep struct initialization via nested Python dictionaries.

Safety: Automatic bit-masking and sign-extension to mimic C integer overflow/underflow behavior in Python.

📦 Installation

pip install dwarffi

Note: For the cdef functionality, you will need a C compiler (like gcc or clang) and dwarf2json installed in your PATH.

🛠️ Quick Start

1. The CFFI-style cdef

If you have a snippet of C and want to work with it immediately:

Python from dwarffi.dffi import DFFI

ffi = DFFI() ffi.cdef(""" struct sensor_data { uint32_t timestamp; int16_t readings[3]; uint8_t status; }; """)

Create an instance in a fresh bytearray

sensor = ffi.new("struct sensor_data", {
    "timestamp": 1234567,
    "readings": [10, -5, 20],
    "status": 0x01
})

print(f"Bytes: {sensor.to_bytes().hex()}")
print(f"Reading[1]: {sensor.readings[1]}") # -5
  1. Embedded Architecture Analysis Analyze a Big Endian MIPS structure from a raw binary dump:

Python

# Load a pre-generated ISF for a MIPS target
ffi = DFFI("mips_be_target.json")

Map existing memory (e.g., from an emulator or hex dump)

raw_data = bytearray(b'\x00\x00\x12\x34\xff\xff\xff\xfb')
cpu_ctx = ffi.from_buffer("struct cpu_context", raw_data)

Values are automatically unpacked according to MIPS Big Endian rules

print(hex(cpu_ctx.pc))      # 0x1234
print(cpu_ctx.status)       # -5 (Sign-extended from 32-bit BE)

🧩 Advanced Usage

Anonymous Unions and Bitfields

dwarffi lets you access anonymous members directly, common in hardware register maps.

ffi.cdef("""
struct reg_map {
    union {
        uint32_t ALL;
        struct {
            uint16_t LOW;
            uint16_t HIGH;
        };
    };
};
""")

reg = ffi.new("struct reg_map")
reg.ALL = 0x12345678
print(hex(reg.HIGH)) # 0x1234

Pointer Arithmetic

ptr = ffi.cast("int *", 0x4000)
next_ptr = ptr + 1  # Increments by sizeof(int)
print(hex(next_ptr.address)) # 0x4004

⚙️ How it Works

dwarffi acts as a middleman between raw memory and Python objects.

  • Parsing: It reads ISF files (which represent the DWARF tree).
  • Synthesis: It creates Pythonic wrappers for C types.
  • Memory Mapping: Using struct.pack and struct.unpack, it translates Python integers/strings into the exact byte representation required by the target architecture.

🤝 Contributing

We welcome contributions! Please ensure that you add tests for any new features. dwarffi uses pytest for its extensive test suite, covering integer packing, architecture variances, and magic method semantics.

pytest tests/

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

dwarffi-0.0.2.tar.gz (31.2 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

dwarffi-0.0.2-py3-none-any.whl (22.0 kB view details)

Uploaded Python 3

File details

Details for the file dwarffi-0.0.2.tar.gz.

File metadata

  • Download URL: dwarffi-0.0.2.tar.gz
  • Upload date:
  • Size: 31.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for dwarffi-0.0.2.tar.gz
Algorithm Hash digest
SHA256 a0891ae3a0814514c77c3baffd64c98aba2176413eb18aad207aa71fb92dc65a
MD5 ec7e04b9ad6b4d29b59dc811c7f75237
BLAKE2b-256 b30cfc4d176eae6acfb9d0d375f38ad23a294a0f35e63edc8d8cbeea4f4ae74d

See more details on using hashes here.

Provenance

The following attestation bundles were made for dwarffi-0.0.2.tar.gz:

Publisher: publish.yml on rehosting/dwarffi

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dwarffi-0.0.2-py3-none-any.whl.

File metadata

  • Download URL: dwarffi-0.0.2-py3-none-any.whl
  • Upload date:
  • Size: 22.0 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for dwarffi-0.0.2-py3-none-any.whl
Algorithm Hash digest
SHA256 ae27af4d7561daebba035f084a1b48f2d14044fadf8a9b77df6df94ea83ffd8a
MD5 55a43a5752cf75e4c530e0fadb924e26
BLAKE2b-256 e4196dcdfc2a239257d6b84df8382bb2dbb1e22b0c74800d3bad6175b520fb81

See more details on using hashes here.

Provenance

The following attestation bundles were made for dwarffi-0.0.2-py3-none-any.whl:

Publisher: publish.yml on rehosting/dwarffi

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page