Ramamohan Paturi

93 papers A* 24A 9B 3C 1Misc 1Journal 47Unranked 5
YearRankTypeTitle / Venue / Authors
2026 J jnl
CoRR
Mohit Gurumukhani, Daniel Kleber, Ramamohan Paturi, Christopher D. Rosin, Navid Talebanfard
2026 J jnl
CoRR
Mohit Gurumukhani, Daniel Kleber, Ramamohan Paturi, Christopher D. Rosin, Michael E. Saks, Navid Talebanfard
2026 A* conf
AAAI
Prudhviraj Naidu, Zixian Wang, Leon Bergen, Ramamohan Paturi
2025 J jnl
CoRR
Jianyou Wang, Weili Cao, Kaicheng Wang, Xiaoyue Wang, Ashish Dalvi, Gino Prasad, Qishan Liang, Hsuan-lin Her, Ming Wang, Qin Yang, Gene W. Yeo, David E. Neal, Maxim Khan, Christopher D. Rosin, Ramamohan Paturi, Leon Bergen
2025 A conf
STACS
Mohit Gurumukhani, Ramamohan Paturi, Michael Saks, Navid Talebanfard
2025 J jnl
CoRR
Mohit Gurumukhani, Ramamohan Paturi, Michael E. Saks, Navid Talebanfard
2025 A* conf
EMNLP
Jianyou Wang, Weili Cao, Longtian Bao, Youze Zheng, Gil Pasternak, Kaicheng Wang, Xiaoyue Wang, Ramamohan Paturi, Leon Bergen
2025 J jnl
CoRR
Prudhviraj Naidu, Zixian Wang, Leon Bergen, Ramamohan Paturi
2025 J jnl
CoRR
Weili Cao, Jianyou Wang, Youze Zheng, Longtian Bao, Qirui Zheng, Taylor Berg-Kirkpatrick, Ramamohan Paturi, Leon Bergen
2024 J jnl
CoRR
Xiaoyue Wang, Jianyou Wang, Weili Cao, Kaicheng Wang, Ramamohan Paturi, Leon Bergen
2024 J jnl
CoRR
Evelyn Yee, Alice Li, Chenyu Tang, Yeon Ho Jung, Ramamohan Paturi, Leon Bergen
2024 conf
LREC/COLING
Jianyou Wang, Kaicheng Wang, Xiaoyue Wang, Weili Cao, Ramamohan Paturi, Leon Bergen
2024 J jnl
CoRR
Jianyou Wang, Kaicheng Wang, Xiaoyue Wang, Weili Cao, Ramamohan Paturi, Leon Bergen
2024 A conf
CCC
Mohit Gurumukhani, Ramamohan Paturi, Pavel Pudlák, Michael E. Saks, Navid Talebanfard
2024 J jnl
CoRR
Mohit Gurumukhani, Ramamohan Paturi, Pavel Pudlák, Michael E. Saks, Navid Talebanfard
2024 J jnl
CoRR
Jianyou Wang, Weili Cao, Longtian Bao, Youze Zheng, Gil Pasternak, Kaicheng Wang, Xiaoyue Wang, Ramamohan Paturi, Leon Bergen
2024 J jnl
CoRR
Mohit Gurumukhani, Marvin Künnemann, Ramamohan Paturi
2023 J jnl
CoRR
Jianyou Wang, Kaicheng Wang, Xiaoyue Wang, Prudhviraj Naidu, Leon Bergen, Ramamohan Paturi
2023 A* conf
NeurIPS
Jianyou Wang, Kaicheng Wang, Xiaoyue Wang, Prudhviraj Naidu, Leon Bergen, Ramamohan Paturi
2019 J jnl
Algorithmica
Marvin Künnemann, Daniel Moeller, Ramamohan Paturi, Stefan Schneider
2018 A* conf
SODA
Daniel Lokshtanov, Ivan Mikhailin, Ramamohan Paturi, Pavel Pudlák
2017 A* conf
SODA
Daniel Lokshtanov, Ramamohan Paturi, Suguru Tamaki, R. Ryan Williams, Huacheng Yu
2017 A* conf
ICALP
Marvin Künnemann, Ramamohan Paturi, Stefan Schneider
2017 J jnl
CoRR
Marvin Künnemann, Ramamohan Paturi, Stefan Schneider
2016 ch.
Encyclopedia of Algorithms
Ramamohan Paturi, Pavel Pudlák, Michael E. Saks, Francis Zane
2016 A conf
ITCS
Marco L. Carmosino, Jiawei Gao, Russell Impagliazzo, Ivan Mihajlin, Ramamohan Paturi, Stefan Schneider
2016 J jnl
ACM Trans. Algorithms
Marek Cygan, Holger Dell, Daniel Lokshtanov, Dániel Marx, Jesper Nederlof, Yoshio Okamoto, Ramamohan Paturi, Saket Saurabh, Magnus Wahlström
2016 Misc conf
CSR
Daniel Moeller, Ramamohan Paturi, Stefan Schneider
2015 J jnl
Electron. Colloquium Comput. Complex.
Marco Carmosino, Jiawei Gao, Russell Impagliazzo, Ivan Mihajlin, Ramamohan Paturi, Stefan Schneider
2015 J jnl
CoRR
Daniel Moeller, Ramamohan Paturi, Stefan Schneider
2014 J jnl
CoRR
Russell Impagliazzo, Shachar Lovett, Ramamohan Paturi, Stefan Schneider
2014 J jnl
Electron. Colloquium Comput. Complex.
Russell Impagliazzo, Shachar Lovett, Ramamohan Paturi, Stefan Schneider
2013 A* conf
FOCS
Russell Impagliazzo, Ramamohan Paturi, Stefan Schneider
2013 B conf
IPEC
Russell Impagliazzo, Ramamohan Paturi
2013 J jnl
Dagstuhl Reports
Thore Husfeldt, Ramamohan Paturi, Gregory B. Sorkin, Ryan Williams
2013 conf
APPROX-RANDOM
Lucia Batman, Russell Impagliazzo, Cody Murray, Ramamohan Paturi
2013 conf
WINE
Moshe Hoffman, Daniel Moeller, Ramamohan Paturi
2013 J jnl
Algorithmica
Chris Calabro, Russell Impagliazzo, Ramamohan Paturi
2012 J jnl
CoRR
Russell Impagliazzo, Ramamohan Paturi, Stefan Schneider
2012 A* conf
SODA
Russell Impagliazzo, William Matthews, Ramamohan Paturi
2012 B conf
SAGT
Nuh Aygün Dalkiran, Moshe Hoffman, Ramamohan Paturi, Daniel Ricketts, Andrea Vattani
2012 J jnl
CoRR
Manuel Cebrián, Ramamohan Paturi, Daniel Ricketts
2012 A conf
CCC
Marek Cygan, Holger Dell, Daniel Lokshtanov, Dániel Marx, Jesper Nederlof, Yoshio Okamoto, Ramamohan Paturi, Saket Saurabh, Magnus Wahlström
2011 J jnl
CoRR
Russell Impagliazzo, William Matthews, Ramamohan Paturi
2011 A* conf
EC
Daniel P. Enemark, Mathew D. McCubbins, Ramamohan Paturi, Nicholas Weller
2011 J jnl
CoRR
Marek Cygan, Holger Dell, Daniel Lokshtanov, Dániel Marx, Jesper Nederlof, Yoshio Okamoto, Ramamohan Paturi, Saket Saurabh, Magnus Wahlström
2010 conf
Exact Complexity of NP-hard Problems
Thore Husfeldt, Dieter Kratsch, Ramamohan Paturi, Gregory B. Sorkin
2010 A conf
SAT
Ramamohan Paturi
2010 ed.
Exact Complexity of NP-hard Problems
Thore Husfeldt, Dieter Kratsch, Ramamohan Paturi, Gregory B. Sorkin
2010 C conf
SSS
Amos Israeli, Mathew D. McCubbins, Ramamohan Paturi, Andrea Vattani
2010 B conf
IPEC
Chris Calabro, Russell Impagliazzo, Ramamohan Paturi
2010 A* conf
STOC
Ramamohan Paturi, Pavel Pudlák
2010 A conf
SAT
William Matthews, Ramamohan Paturi
2009 conf
IWPEC
Chris Calabro, Russell Impagliazzo, Ramamohan Paturi
2008 ch.
Encyclopedia of Algorithms
Ramamohan Paturi, Pavel Pudlák, Michael E. Saks, Francis Zane
2008 J jnl
J. Comput. Syst. Sci.
Chris Calabro, Russell Impagliazzo, Valentine Kabanets, Ramamohan Paturi
2008 A* conf
SIGCOMM
Kirill Levchenko, Geoffrey M. Voelker, Ramamohan Paturi, Stefan Savage
2006 A conf
CCC
Chris Calabro, Russell Impagliazzo, Ramamohan Paturi
2005 J jnl
J. ACM
Ramamohan Paturi, Pavel Pudlák, Michael E. Saks, Francis Zane
2004 J jnl
Electron. Colloquium Comput. Complex.
Ramamohan Paturi, Pavel Pudlák
2004 A* conf
CCS
Kirill Levchenko, Ramamohan Paturi, George Varghese
2003 A conf
CCC
Chris Calabro, Russell Impagliazzo, Valentine Kabanets, Ramamohan Paturi
2001 J jnl
J. Comput. Syst. Sci.
Russell Impagliazzo, Ramamohan Paturi
2001 J jnl
J. Comput. Syst. Sci.
Russell Impagliazzo, Ramamohan Paturi, Francis Zane
2000 J jnl
Comput. Complex.
Ramamohan Paturi, Michael E. Saks, Francis Zane
2000 J jnl
J. Parallel Distributed Comput.
Francis Zane, Philippe J. Marchand, Ramamohan Paturi, Sadik C. Esener
1999 A conf
CCC
Russell Impagliazzo, Ramamohan Paturi
1999 J jnl
Chic. J. Theor. Comput. Sci.
Ramamohan Paturi, Pavel Pudlák, Francis Zane
1998 A* conf
FOCS
Ramamohan Paturi, Pavel Pudlák, Michael E. Saks, Francis Zane
1998 J jnl
SIAM J. Discret. Math.
Ramamohan Paturi, Francis Zane
1998 A* conf
FOCS
Russell Impagliazzo, Ramamohan Paturi, Francis Zane
1997 A* conf
STOC
Ramamohan Paturi, Michael E. Saks, Francis Zane
1997 A* conf
FOCS
Ramamohan Paturi, Pavel Pudlák, Francis Zane
1997 J jnl
SIAM J. Comput.
Russell Impagliazzo, Ramamohan Paturi, Michael E. Saks
1996 J jnl
IEEE Trans. Neural Networks
Ramamohan Paturi
1996 J jnl
IEEE Trans. Comput. Aided Des. Integr. Circuits Syst.
Robert J. Carragher, Chung-Kuan Cheng, Xiao-Ming Xiong, Masahiro Fujita, Ramamohan Paturi
1995 J jnl
Inf. Comput.
Ramamohan Paturi, Sanguthevar Rajasekaran, John H. Reif
1994 J jnl
Inf. Comput.
Ramamohan Paturi, Michael E. Saks
1994 J jnl
J. Parallel Distributed Comput.
Val Donaldson, Francine Berman, Ramamohan Paturi
1993 J jnl
J. Comput. Syst. Sci.
János Komlós, Ramamohan Paturi
1993 A* conf
STOC
Russell Impagliazzo, Ramamohan Paturi, Michael E. Saks
1992 A* conf
STOC
Ramamohan Paturi
1990 J jnl
Inf. Comput.
Ramamohan Paturi, Joel I. Seiferas, Janos Simon, Richard E. Newman-Wolfe
1990 A* conf
FOCS
Ramamohan Paturi, Michael E. Saks
1990 A* conf
COLT
Ramamohan Paturi, Michael E. Saks
1989 A* conf
COLT
Ramamohan Paturi, Sanguthevar Rajasekaran, John H. Reif
1989 J jnl
Inf. Process. Lett.
Mihály Geréb-Graus, Ramamohan Paturi, Endre Szemerédi
1988 J jnl
Neural Networks
János Komlós, Ramamohan Paturi
1988 A* conf
FOCS
János Komlós, Ramamohan Paturi
1988 J jnl
Inf. Process. Lett.
Howard J. Karloff, Ramamohan Paturi, Janos Simon
1986 J jnl
J. Comput. Syst. Sci.
Ramamohan Paturi, Janos Simon
1984 A* conf
FOCS
Ramamohan Paturi, Janos Simon
1983 A* conf
FOCS
Ramamohan Paturi, Janos Simon
redb/extractors/elf_extractors/elf_features.py
← Index redb/extractors/elf_extractors/elf_features.py python
import inspect
import json
from datetime import datetime, timezone
from typing import Any

from elftools.elf.elffile import ELFFile
from elftools.common.exceptions import ELFError

from redb.extractors.enum import Tag
from redb.extractors.elf_extractor import ELFExtractor
from redb.models.dataclasses import ELFFeatures


class ELFFeaturesExtractor(ELFExtractor):

    def __init__(
        self,
        filepath,
        log,
        exporters=None,
        index_prefix=None,
        elastic_index=None,
        known_benign=False,
        known_malicious=False,
        elf=None,
    ):
        super().__init__(
            filepath,
            log,
            exporters,
            index_prefix,
            elastic_index,
            known_benign,
            known_malicious,
            elf,
        )
        self.elf_features = None
        self.elastic_index = self.index_prefix + "-elf_features"
        self.log.debug(inspect.currentframe().f_code.co_name)

    def _extract_header_data(self):
        """Extract ELF header data using pyelftools."""
        self.log.debug(inspect.currentframe().f_code.co_name)

        def extract_header(elf):
            # Initialize result with safe defaults
            result = {
                'ei_class': 0, 'ei_data': 0, 'ei_version': 0, 'ei_osabi': 0, 'ei_abiversion': 0,
                'e_type': 0, 'e_machine': 0, 'e_version': 0, 'e_entry': 0, 'e_flags': 0,
                'ei_class_str': 'unknown', 'ei_data_str': 'unknown', 'ei_osabi_str': 'unknown',
                'e_type_str': 'unknown', 'e_machine_str': 'unknown'
            }

            # Try to get the main header - if this fails, we can't extract anything
            try:
                header = elf.header
            except Exception as e:
                self.log.warning(f"Could not access ELF header: {e}")
                return result

            # Try to get e_ident section
            ident = None
            try:
                ident = header.get('e_ident', {})
            except Exception as e:
                self.log.warning(f"Could not access e_ident: {e}")

            # Extract EI_CLASS (32/64 bit)
            try:
                if ident:
                    ei_class_raw = ident.get('EI_CLASS', 'ELFCLASSNONE')
                    result['ei_class'] = 2 if ei_class_raw == 'ELFCLASS64' else 1 if ei_class_raw == 'ELFCLASS32' else 0
                    result['ei_class_str'] = '64-bit' if ei_class_raw == 'ELFCLASS64' else '32-bit' if ei_class_raw == 'ELFCLASS32' else 'unknown'
            except Exception as e:
                self.log.warning(f"Could not extract EI_CLASS: {e}")

            # Extract EI_DATA (endianness)
            try:
                if ident:
                    ei_data_raw = ident.get('EI_DATA', 'ELFDATANONE')
                    result['ei_data'] = 1 if ei_data_raw == 'ELFDATA2LSB' else 2 if ei_data_raw == 'ELFDATA2MSB' else 0
                    result['ei_data_str'] = 'Little-endian' if ei_data_raw == 'ELFDATA2LSB' else 'Big-endian' if ei_data_raw == 'ELFDATA2MSB' else 'unknown'
            except Exception as e:
                self.log.warning(f"Could not extract EI_DATA: {e}")

            # Extract EI_VERSION
            try:
                if ident:
                    ei_version_raw = ident.get('EI_VERSION', 0)
                    # Convert string like 'EV_CURRENT' to integer
                    if isinstance(ei_version_raw, str):
                        version_map = {'EV_NONE': 0, 'EV_CURRENT': 1}
                        result['ei_version'] = version_map.get(ei_version_raw, 1)
                    else:
                        result['ei_version'] = ei_version_raw
            except Exception as e:
                self.log.warning(f"Could not extract EI_VERSION: {e}")

            # Extract EI_OSABI
            try:
                if ident:
                    ei_osabi_raw = ident.get('EI_OSABI', 'ELFOSABI_SYSV')
                    osabi_map = {
                        'ELFOSABI_SYSV': 0, 'ELFOSABI_HPUX': 1, 'ELFOSABI_NETBSD': 2,
                        'ELFOSABI_LINUX': 3, 'ELFOSABI_SOLARIS': 6, 'ELFOSABI_FREEBSD': 9
                    }
                    result['ei_osabi'] = osabi_map.get(ei_osabi_raw, 0)
                    result['ei_osabi_str'] = ei_osabi_raw.replace('ELFOSABI_', '') if ei_osabi_raw and ei_osabi_raw.startswith('ELFOSABI_') else str(ei_osabi_raw) if ei_osabi_raw else 'unknown'
            except Exception as e:
                self.log.warning(f"Could not extract EI_OSABI: {e}")

            # Extract EI_ABIVERSION
            try:
                if ident:
                    result['ei_abiversion'] = ident.get('EI_ABIVERSION', 0)
            except Exception as e:
                self.log.warning(f"Could not extract EI_ABIVERSION: {e}")

            # Extract e_type (file type)
            try:
                e_type_raw = header.get('e_type', 'ET_NONE')
                type_map = {
                    'ET_NONE': 0, 'ET_REL': 1, 'ET_EXEC': 2, 'ET_DYN': 3, 'ET_CORE': 4
                }
                result['e_type'] = type_map.get(e_type_raw, 0)
                result['e_type_str'] = e_type_raw.replace('ET_', '') if e_type_raw and e_type_raw.startswith('ET_') else str(e_type_raw) if e_type_raw else 'unknown'
            except Exception as e:
                self.log.warning(f"Could not extract e_type: {e}")

            # Extract e_machine (architecture)
            try:
                e_machine_raw = header.get('e_machine', 0)
                # Map machine strings to integers and human-readable names
                # https://github.com/eliben/pyelftools/blob/main/elftools/elf/enums.py
                # https://github.com/torvalds/linux/blob/master/include/uapi/linux/elf-em.h
                # https://refspecs.linuxfoundation.org/elf/elf.pdf
                machine_int_map = {
                    'EM_NONE': 0, 'EM_M32': 1, 'EM_SPARC': 2, 'EM_386': 3,
                    'EM_68K': 4, 'EM_88K': 5, 'EM_860': 7, 'EM_MIPS': 8,
                    'EM_S370': 9, 'EM_MIPS_RS3_LE': 10, 'EM_PARISC': 15,
                    'EM_VPP500': 17, 'EM_SPARC32PLUS': 18, 'EM_960': 19,
                    'EM_PPC': 20, 'EM_PPC64': 21, 'EM_S390': 22, 'EM_V800': 36,
                    'EM_FR20': 37, 'EM_RH32': 38, 'EM_RCE': 39, 'EM_ARM': 40,
                    'EM_ALPHA': 41, 'EM_SH': 42, 'EM_SPARCV9': 43, 'EM_TRICORE': 44,
                    'EM_ARC': 45, 'EM_H8_300': 46, 'EM_H8_300H': 47, 'EM_H8S': 48,
                    'EM_H8_500': 49, 'EM_IA_64': 50, 'EM_MIPS_X': 51, 'EM_COLDFIRE': 52,
                    'EM_68HC12': 53, 'EM_X86_64': 62, 'EM_AARCH64': 183, 'EM_RISCV': 243,
                }
                machine_str_map = {
                    'EM_386': 'x86', 'EM_X86_64': 'x86_64', 'EM_ARM': 'ARM', 'EM_AARCH64': 'ARM64',
                    'EM_MIPS': 'MIPS', 'EM_PPC': 'PowerPC', 'EM_PPC64': 'PowerPC64',
                    'EM_SPARC': 'SPARC', 'EM_SPARCV9': 'SPARC64', 'EM_RISCV': 'RISC-V',
                    'EM_IA_64': 'IA-64', 'EM_S390': 'S390', 'EM_SH': 'SuperH',
                }
                if isinstance(e_machine_raw, str):
                    result['e_machine'] = machine_int_map.get(e_machine_raw, 0)
                    result['e_machine_str'] = machine_str_map.get(e_machine_raw, e_machine_raw.replace('EM_', '') if e_machine_raw.startswith('EM_') else e_machine_raw)
                else:
                    result['e_machine'] = e_machine_raw
                    result['e_machine_str'] = str(e_machine_raw)
            except Exception as e:
                self.log.warning(f"Could not extract e_machine: {e}")

            # Extract e_version
            try:
                e_version_raw = header.get('e_version', 0)
                # Convert string like 'EV_CURRENT' to integer
                if isinstance(e_version_raw, str):
                    version_map = {'EV_NONE': 0, 'EV_CURRENT': 1}
                    result['e_version'] = version_map.get(e_version_raw, 1)
                else:
                    result['e_version'] = e_version_raw
            except Exception as e:
                self.log.warning(f"Could not extract e_version: {e}")

            # Extract e_entry (entry point)
            try:
                result['e_entry'] = header.get('e_entry', 0)
            except Exception as e:
                self.log.warning(f"Could not extract e_entry: {e}")

            # Extract e_flags
            try:
                result['e_flags'] = header.get('e_flags', 0)
            except Exception as e:
                self.log.warning(f"Could not extract e_flags: {e}")

            return result

        try:
            return self._with_elf_file(extract_header)
        except Exception as e:
            self.log.error(f"Error extracting header data {self.hash.sha256}: {e}")
            return None

    def _count_dynamic_symbols(self):
        """Count symbols in dynamic symbol table."""
        def count_dynsym(elf):
            dynsym_section = elf.get_section_by_name('.dynsym')
            if dynsym_section and hasattr(dynsym_section, 'num_symbols'):
                return dynsym_section.num_symbols()
            return 0

        try:
            result = self._with_elf_file(count_dynsym)
            return result if result is not None else 0
        except Exception as e:
            self.log.error(f"Error counting dynamic symbols: {e}")
            return 0

    def _count_relocations(self):
        """Count total relocations across all sections."""
        def count_relocs(elf):
            reloc_count = 0
            for section in elf.iter_sections():
                if hasattr(section, 'iter_relocations'):
                    try:
                        reloc_count += section.num_relocations()
                    except:
                        # Some sections might not support num_relocations()
                        for _ in section.iter_relocations():
                            reloc_count += 1
            return reloc_count

        try:
            result = self._with_elf_file(count_relocs)
            return result if result is not None else 0
        except Exception as e:
            self.log.error(f"Error counting relocations: {e}")
            return 0

    def _has_gnu_hash(self):
        """Check if GNU hash table is present."""
        def check_gnu_hash(elf):
            gnu_hash_section = elf.get_section_by_name('.gnu.hash')
            return gnu_hash_section is not None

        try:
            result = self._with_elf_file(check_gnu_hash)
            return bool(result)
        except Exception as e:
            self.log.error(f"Error checking GNU hash: {e}")
            return False

    def _has_fortify(self):
        """Check if binary has fortify source protection."""
        def check_fortify(elf):
            # Look for fortified function symbols
            fortify_symbols = ['__printf_chk', '__sprintf_chk', '__snprintf_chk',
                             '__strcpy_chk', '__strcat_chk', '__memcpy_chk']

            for section in elf.iter_sections():
                if hasattr(section, 'iter_symbols'):
                    for symbol in section.iter_symbols():
                        if symbol.name in fortify_symbols:
                            return True
            return False

        try:
            result = self._with_elf_file(check_fortify)
            return bool(result)
        except Exception as e:
            self.log.error(f"Error checking fortify: {e}")
            return False

    def tag(self):
        return Tag.ELF_FEATURES.value if hasattr(Tag, 'ELF_FEATURES') else "elf_features"

    def extract(self):
        try:
            self.log.debug(inspect.currentframe().f_code.co_name)

            # Check if file is valid ELF
            if not self._is_elf_file():
                self.log.error(f"No valid ELF file for {self.hash.sha256}")
                return None

            # Extract header data (now always returns a result, even with defaults)
            header_data = self._extract_header_data()
            if not header_data:
                self.log.error(f"Complete failure to extract any header data for {self.hash.sha256}")
                return None

            # Extract binary properties
            is_64bit = 1 if self._is_64bit() else 0
            is_stripped = 1 if self._is_stripped() else 0
            is_pie = 1 if self._is_pie() else 0
            has_canary = 1 if self._has_stack_protection() else 0
            has_nx = 1 if self._has_nx_bit() else 0
            has_relro = 1 if self._has_relro() else 0
            has_fortify = 1 if self._has_fortify() else 0

            # Extract counts
            number_of_segments = self._count_segments()
            number_of_sections = self._count_sections()
            number_of_symbols = self._count_symbols()
            number_of_dynamic_symbols = self._count_dynamic_symbols()
            number_of_relocations = self._count_relocations()
            number_of_dependencies = len(self._get_dependencies())

            # Extract build information
            build_id = self._get_build_id()
            gnu_hash_present = 1 if self._has_gnu_hash() else 0
            has_debug_info = 1 if self._has_debug_info() else 0

            self.elf_features = ELFFeatures(
                # ELF Header data
                ei_class=header_data['ei_class'],
                ei_data=header_data['ei_data'],
                ei_version=header_data['ei_version'],
                ei_osabi=header_data['ei_osabi'],
                ei_abiversion=header_data['ei_abiversion'],
                e_type=header_data['e_type'],
                e_machine=header_data['e_machine'],
                e_version=header_data['e_version'],
                e_entry=header_data['e_entry'],
                e_flags=header_data['e_flags'],
                # Human readable values
                ei_class_str=header_data['ei_class_str'],
                ei_data_str=header_data['ei_data_str'],
                ei_osabi_str=header_data['ei_osabi_str'],
                e_type_str=header_data['e_type_str'],
                e_machine_str=header_data['e_machine_str'],
                # Binary properties
                is_64bit=is_64bit,
                is_stripped=is_stripped,
                is_pie=is_pie,
                has_canary=has_canary,
                has_nx=has_nx,
                has_relro=has_relro,
                has_fortify=has_fortify,
                # Counts
                number_of_segments=number_of_segments,
                number_of_sections=number_of_sections,
                number_of_symbols=number_of_symbols,
                number_of_dynamic_symbols=number_of_dynamic_symbols,
                number_of_relocations=number_of_relocations,
                number_of_dependencies=number_of_dependencies,
                # Build information
                build_id=build_id,
                gnu_hash_present=gnu_hash_present,
                has_debug_info=has_debug_info,
            )

            return self.elf_features

        except Exception as e:
            self.log.error(f"Error extracting ELF features {self.hash.sha256}: {e}")
            return None

    def prepare_export_data(self, exporter_type: str) -> Any:
        self.log.debug(inspect.currentframe().f_code.co_name)

        if exporter_type == "ElasticsearchExporter":
            return self.elf_features
        elif exporter_type == "ClickHouseExporter":
            try:
                if not self.elf_features:
                    return None

                # Prepare data array matching the schema
                data = [[
                    self.sha256,
                    self.md5,
                    self.sha1,

                    # ELF Header data
                    self.elf_features.ei_class,
                    self.elf_features.ei_data,
                    self.elf_features.ei_version,
                    self.elf_features.ei_osabi,
                    self.elf_features.ei_abiversion,
                    self.elf_features.e_type,
                    self.elf_features.e_machine,
                    self.elf_features.e_version,
                    self.elf_features.e_entry,
                    self.elf_features.e_flags,

                    # Human readable values
                    self.elf_features.ei_class_str,
                    self.elf_features.ei_data_str,
                    self.elf_features.ei_osabi_str,
                    self.elf_features.e_type_str,
                    self.elf_features.e_machine_str,

                    # Binary properties
                    self.elf_features.is_64bit,
                    self.elf_features.is_stripped,
                    self.elf_features.is_pie,
                    self.elf_features.has_canary,
                    self.elf_features.has_nx,
                    self.elf_features.has_relro,
                    self.elf_features.has_fortify,

                    # Counts
                    self.elf_features.number_of_segments,
                    self.elf_features.number_of_sections,
                    self.elf_features.number_of_symbols,
                    self.elf_features.number_of_dynamic_symbols,
                    self.elf_features.number_of_relocations,
                    self.elf_features.number_of_dependencies,

                    # Build information
                    self.elf_features.build_id,
                    self.elf_features.gnu_hash_present,
                    self.elf_features.has_debug_info,

                    # Analysis metadata
                    datetime.now(timezone.utc)
                ]]

                column_names = [
                    'sha256', 'md5', 'sha1',
                    'ei_class', 'ei_data', 'ei_version', 'ei_osabi', 'ei_abiversion',
                    'e_type', 'e_machine', 'e_version', 'e_entry', 'e_flags',
                    'ei_class_str', 'ei_data_str', 'ei_osabi_str', 'e_type_str', 'e_machine_str',
                    'is_64bit', 'is_stripped', 'is_pie', 'has_canary', 'has_nx', 'has_relro', 'has_fortify',
                    'number_of_segments', 'number_of_sections', 'number_of_symbols',
                    'number_of_dynamic_symbols', 'number_of_relocations', 'number_of_dependencies',
                    'build_id', 'gnu_hash_present', 'has_debug_info',
                    'analysis_date'
                ]

                column_type_names = [
                    'FixedString(64)', 'FixedString(32)', 'FixedString(40)',
                    "Enum8('32-bit'=1, '64-bit'=2)",
                    "Enum8('Little-endian'=1, 'Big-endian'=2)",
                    'UInt8',
                    "Enum8('SYSV'=0, 'HPUX'=1, 'NETBSD'=2, 'LINUX'=3, 'SOLARIS'=6, 'FREEBSD'=9)",
                    'UInt8',
                    "Enum8('NONE'=0, 'REL'=1, 'EXEC'=2, 'DYN'=3, 'CORE'=4)",
                    'UInt16', 'UInt32', 'UInt64', 'UInt32',
                    'LowCardinality(String)', 'LowCardinality(String)', 'LowCardinality(String)',
                    'LowCardinality(String)', 'LowCardinality(String)',
                    'UInt8', 'UInt8', 'UInt8', 'UInt8', 'UInt8', 'UInt8', 'UInt8',
                    'UInt16', 'UInt16', 'UInt32', 'UInt32', 'UInt32', 'UInt16',
                    'Nullable(String)', 'UInt8', 'UInt8',
                    'DateTime64(3, \'UTC\')'
                ]

                if not data:
                    return None

                return (data, column_names, column_type_names)

            except Exception as e:
                self.log.error(f"Error preparing export data: {e}")
                raise

    def get_clickhouse_table(self) -> str:
        return "redb_elf_features"