LCOV - code coverage report
Current view: top level - src/macho - symbol.rs (source / functions) Coverage Total Hit
Test: lief.lcov Lines: 93.5 % 77 72
Test Date: 2024-10-27:00:00:00 Functions: 73.9 % 23 17

            Line data    Source code
       1              : use std::marker::PhantomData;
       2              : 
       3              : use crate::common::{into_optional, FromFFI};
       4              : use crate::declare_iterator;
       5              : use crate::generic;
       6              : use lief_ffi as ffi;
       7              : 
       8              : use super::commands::Dylib;
       9              : use super::{BindingInfo, ExportInfo};
      10              : 
      11              : /// Structure that represents a Symbol in a Mach-O file.
      12              : ///
      13              : /// A Mach-O symbol can come from:
      14              : /// 1. The symbols command (LC_SYMTAB / SymbolCommand)
      15              : /// 2. The Dyld Export trie
      16              : /// 3. The Dyld Symbol bindings
      17              : pub struct Symbol<'a> {
      18              :     ptr: cxx::UniquePtr<ffi::MachO_Symbol>,
      19              :     _owner: PhantomData<&'a ()>,
      20              : }
      21              : 
      22              : #[allow(non_camel_case_types)]
      23       269376 : #[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
      24              : pub enum Category {
      25              :     NONE,
      26              :     LOCAL,
      27              :     EXTERNAL,
      28              :     UNDEFINED,
      29              :     INDIRECT_ABS,
      30              :     INDIRECT_LOCAL,
      31              :     INDIRECT_ABS_LOCAL,
      32              :     UNKNOWN(u32),
      33              : }
      34              : 
      35              : impl From<u32> for Category {
      36       269376 :     fn from(value: u32) -> Self {
      37       269376 :         match value {
      38        69816 :             0x00000000 => Category::NONE,
      39       111008 :             0x00000001 => Category::LOCAL,
      40        55952 :             0x00000002 => Category::EXTERNAL,
      41        32600 :             0x00000003 => Category::UNDEFINED,
      42            0 :             0x00000004 => Category::INDIRECT_ABS,
      43            0 :             0x00000005 => Category::INDIRECT_LOCAL,
      44            0 :             0x00000006 => Category::INDIRECT_ABS_LOCAL,
      45            0 :             _ => Category::UNKNOWN(value),
      46              :         }
      47       269376 :     }
      48              : }
      49              : 
      50              : #[allow(non_camel_case_types)]
      51       269376 : #[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
      52              : pub enum Origin {
      53              :     DYLD_EXPORT,
      54              :     DYLD_BIND,
      55              :     LC_SYMTAB,
      56              :     UNKNOWN(u32),
      57              : }
      58              : 
      59              : impl From<u32> for Origin {
      60       269376 :     fn from(value: u32) -> Self {
      61       269376 :         match value {
      62        33120 :             0x00000001 => Origin::DYLD_EXPORT,
      63        36696 :             0x00000002 => Origin::DYLD_BIND,
      64       199560 :             0x00000003 => Origin::LC_SYMTAB,
      65            0 :             _ => Origin::UNKNOWN(value),
      66              :         }
      67       269376 :     }
      68              : }
      69              : 
      70              : impl Symbol<'_> {
      71       269376 :     pub fn get_type(&self) -> u8 {
      72       269376 :         self.ptr.get_type()
      73       269376 :     }
      74              : 
      75              :     /// It returns the number of sections in which this symbol can be found.
      76              :     /// If the symbol can't be found in any section, it returns 0 (`NO_SECT`)
      77       269376 :     pub fn numberof_sections(&self) -> u8 {
      78       269376 :         self.ptr.numberof_sections()
      79       269376 :     }
      80              : 
      81              :     /// Return information about the symbol
      82       269376 :     pub fn description(&self) -> u16 {
      83       269376 :         self.ptr.description()
      84       269376 :     }
      85              : 
      86              :     /// Return the origin of the symbol: from `LC_SYMTAB` from the Dyld information, ...
      87       269376 :     pub fn origin(&self) -> Origin {
      88       269376 :         Origin::from(self.ptr.origin())
      89       269376 :     }
      90              : 
      91              :     /// Category of the symbol according to the `LC_DYSYMTAB` command
      92       269376 :     pub fn category(&self) -> Category {
      93       269376 :         Category::from(self.ptr.category())
      94       269376 :     }
      95              : 
      96              :     /// Export info associated with this symbol (if any)
      97       269376 :     pub fn export_info(&self) -> Option<ExportInfo> {
      98       269376 :         into_optional(self.ptr.export_info())
      99       269376 :     }
     100              : 
     101              :     /// Binding info associated with this symbol (if any)
     102       269376 :     pub fn binding_info(&self) -> Option<BindingInfo> {
     103       269376 :         into_optional(self.ptr.binding_info())
     104       269376 :     }
     105              : 
     106              :     /// Return the library in which this symbol is defined (if any)
     107       269376 :     pub fn library(&self) -> Option<Dylib> {
     108       269376 :         into_optional(self.ptr.library())
     109       269376 :     }
     110              : 
     111              :     /// Try to demangle the symbol or return an empty string if it is not possible
     112       193760 :     pub fn demangled_name(&self) -> String {
     113       193760 :         self.ptr.demangled_name().to_string()
     114       193760 :     }
     115              : }
     116              : 
     117              : impl std::fmt::Debug for Symbol<'_> {
     118       269376 :     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
     119       269376 :         let base = self as &dyn generic::Symbol;
     120       269376 :         f.debug_struct("Symbol")
     121       269376 :             .field("base", &base)
     122       269376 :             .field("type", &self.get_type())
     123       269376 :             .field("numberof_sections", &self.numberof_sections())
     124       269376 :             .field("description", &self.description())
     125       269376 :             .field("origin", &self.origin())
     126       269376 :             .field("category", &self.category())
     127       269376 :             .field("export_info", &self.export_info())
     128       269376 :             .field("binding_info", &self.binding_info())
     129       269376 :             .field("library", &self.library())
     130       269376 :             .finish()
     131       269376 :     }
     132              : }
     133              : 
     134              : impl<'a> FromFFI<ffi::MachO_Symbol> for Symbol<'a> {
     135       303040 :     fn from_ffi(ptr: cxx::UniquePtr<ffi::MachO_Symbol>) -> Self {
     136       303040 :         Self {
     137       303040 :             ptr,
     138       303040 :             _owner: PhantomData,
     139       303040 :         }
     140       303040 :     }
     141              : }
     142              : 
     143              : impl generic::Symbol for Symbol<'_> {
     144       841792 :     fn as_generic(&self) -> &ffi::AbstractSymbol {
     145       841792 :         self.ptr.as_ref().unwrap().as_ref()
     146       841792 :     }
     147              : }
     148              : 
     149       193760 : declare_iterator!(
     150       193760 :     Symbols,
     151       193760 :     Symbol<'a>,
     152       193760 :     ffi::MachO_Symbol,
     153       193760 :     ffi::MachO_Binary,
     154       193760 :     ffi::MachO_Binary_it_symbols
     155       193760 : );
        

Generated by: LCOV version 2.1-1