tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

BaseElf.h (3413B)


      1 /* This Source Code Form is subject to the terms of the Mozilla Public
      2 * License, v. 2.0. If a copy of the MPL was not distributed with this file,
      3 * You can obtain one at http://mozilla.org/MPL/2.0/. */
      4 
      5 #ifndef BaseElf_h
      6 #define BaseElf_h
      7 
      8 #include "ElfLoader.h"
      9 #include "Elfxx.h"
     10 
     11 /**
     12 * Base class for ELF libraries. This class includes things that will be
     13 * common between SystemElfs and CustomElfs.
     14 */
     15 class BaseElf : public LibHandle {
     16 public:
     17  /**
     18   * Hash function for symbol lookup, as defined in ELF standard for System V.
     19   */
     20  static unsigned long Hash(const char* symbol);
     21 
     22  /**
     23   * Returns the address corresponding to the given symbol name (with a
     24   * pre-computed hash).
     25   */
     26  void* GetSymbolPtr(const char* symbol, unsigned long hash) const;
     27 
     28  /**
     29   * Returns a pointer to the Elf Symbol in the Dynamic Symbol table
     30   * corresponding to the given symbol name (with a pre-computed hash).
     31   */
     32  const Elf::Sym* GetSymbol(const char* symbol, unsigned long hash) const;
     33 
     34  explicit BaseElf(const char* path, Mappable* mappable = nullptr)
     35      : LibHandle(path), mappable(mappable) {}
     36 
     37 protected:
     38  /**
     39   * Inherited from LibHandle. Those are temporary and are not supposed to
     40   * be used.
     41   */
     42  virtual void* GetSymbolPtr(const char* symbol) const;
     43  virtual bool Contains(void* addr) const;
     44  virtual void* GetBase() const { return GetPtr(0); }
     45 
     46 #ifdef __ARM_EABI__
     47  virtual const void* FindExidx(int* pcount) const;
     48 #endif
     49 
     50 public:
     51  /* private: */
     52  /**
     53   * Returns a pointer relative to the base address where the library is
     54   * loaded.
     55   */
     56  void* GetPtr(const Elf::Addr offset) const {
     57    if (reinterpret_cast<void*>(offset) > base)
     58      return reinterpret_cast<void*>(offset);
     59    return base + offset;
     60  }
     61 
     62  /**
     63   * Like the above, but returns a typed (const) pointer
     64   */
     65  template <typename T>
     66  const T* GetPtr(const Elf::Addr offset) const {
     67    if (reinterpret_cast<void*>(offset) > base)
     68      return reinterpret_cast<const T*>(offset);
     69    return reinterpret_cast<const T*>(base + offset);
     70  }
     71 
     72  /* Appropriated Mappable */
     73  /* /!\ we rely on this being nullptr for BaseElf instances, but not
     74   * CustomElf instances. */
     75  RefPtr<Mappable> mappable;
     76 
     77  /* Base address where the library is loaded */
     78  MappedPtr base;
     79 
     80  /* Buckets and chains for the System V symbol hash table */
     81  Array<Elf::Word> buckets;
     82  UnsizedArray<Elf::Word> chains;
     83 
     84  /* protected: */
     85  /* String table */
     86  Elf::Strtab strtab;
     87 
     88  /* Symbol table */
     89  UnsizedArray<Elf::Sym> symtab;
     90 
     91 #ifdef __ARM_EABI__
     92  /* ARM.exidx information used by FindExidx */
     93  Array<uint32_t[2]> arm_exidx;
     94 #endif
     95 };
     96 
     97 /**
     98 * Class for ELF libraries that already loaded in memory.
     99 */
    100 class LoadedElf : public BaseElf {
    101 public:
    102  /**
    103   * Returns a LoadedElf corresponding to the already loaded ELF
    104   * at the given base address.
    105   */
    106  static already_AddRefed<LibHandle> Create(const char* path, void* base_addr);
    107 
    108 private:
    109  explicit LoadedElf(const char* path) : BaseElf(path) {}
    110 
    111  ~LoadedElf() {
    112    /* Avoid base's destructor unmapping something that doesn't actually
    113     * belong to it. */
    114    base.release();
    115    ElfLoader::Singleton.Forget(this);
    116  }
    117 
    118  /**
    119   * Initializes the library according to information found in the given
    120   * PT_DYNAMIC header.
    121   * Returns whether this succeeded or failed.
    122   */
    123  bool InitDyn(const Elf::Phdr* pt_dyn);
    124 };
    125 
    126 #endif /* BaseElf_h */