Home | History | Annotate | Download | only in linux
      1 // Copyright (c) 2012, Google Inc.
      2 // All rights reserved.
      3 //
      4 // Redistribution and use in source and binary forms, with or without
      5 // modification, are permitted provided that the following conditions are
      6 // met:
      7 //
      8 //     * Redistributions of source code must retain the above copyright
      9 // notice, this list of conditions and the following disclaimer.
     10 //     * Redistributions in binary form must reproduce the above
     11 // copyright notice, this list of conditions and the following disclaimer
     12 // in the documentation and/or other materials provided with the
     13 // distribution.
     14 //     * Neither the name of Google Inc. nor the names of its
     15 // contributors may be used to endorse or promote products derived from
     16 // this software without specific prior written permission.
     17 //
     18 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     19 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     20 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     21 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     22 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     23 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     24 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     25 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     26 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     27 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     28 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     29 //
     30 // elfutils.h: Utilities for dealing with ELF files.
     31 //
     32 
     33 #ifndef COMMON_LINUX_ELFUTILS_H_
     34 #define COMMON_LINUX_ELFUTILS_H_
     35 
     36 #include <elf.h>
     37 #include <link.h>
     38 #include <stdint.h>
     39 
     40 namespace google_breakpad {
     41 
     42 // Traits classes so consumers can write templatized code to deal
     43 // with specific ELF bits.
     44 struct ElfClass32 {
     45   typedef Elf32_Addr Addr;
     46   typedef Elf32_Ehdr Ehdr;
     47   typedef Elf32_Nhdr Nhdr;
     48   typedef Elf32_Phdr Phdr;
     49   typedef Elf32_Shdr Shdr;
     50   typedef Elf32_Half Half;
     51   typedef Elf32_Off Off;
     52   typedef Elf32_Word Word;
     53   static const int kClass = ELFCLASS32;
     54   static const size_t kAddrSize = sizeof(Elf32_Addr);
     55 };
     56 
     57 struct ElfClass64 {
     58   typedef Elf64_Addr Addr;
     59   typedef Elf64_Ehdr Ehdr;
     60   typedef Elf64_Nhdr Nhdr;
     61   typedef Elf64_Phdr Phdr;
     62   typedef Elf64_Shdr Shdr;
     63   typedef Elf64_Half Half;
     64   typedef Elf64_Off Off;
     65   typedef Elf64_Word Word;
     66   static const int kClass = ELFCLASS64;
     67   static const size_t kAddrSize = sizeof(Elf64_Addr);
     68 };
     69 
     70 bool IsValidElf(const void* elf_header);
     71 int ElfClass(const void* elf_base);
     72 
     73 // Attempt to find a section named |section_name| of type |section_type|
     74 // in the ELF binary data at |elf_mapped_base|. On success, returns true
     75 // and sets |*section_start| to point to the start of the section data,
     76 // and |*section_size| to the size of the section's data. If |elfclass|
     77 // is not NULL, set |*elfclass| to the ELF file class.
     78 bool FindElfSection(const void *elf_mapped_base,
     79                     const char *section_name,
     80                     uint32_t section_type,
     81                     const void **section_start,
     82                     size_t *section_size,
     83                     int *elfclass);
     84 
     85 // Internal helper method, exposed for convenience for callers
     86 // that already have more info.
     87 template<typename ElfClass>
     88 const typename ElfClass::Shdr*
     89 FindElfSectionByName(const char* name,
     90                      typename ElfClass::Word section_type,
     91                      const typename ElfClass::Shdr* sections,
     92                      const char* section_names,
     93                      const char* names_end,
     94                      int nsection);
     95 
     96 // Attempt to find the first segment of type |segment_type| in the ELF
     97 // binary data at |elf_mapped_base|. On success, returns true and sets
     98 // |*segment_start| to point to the start of the segment data, and
     99 // and |*segment_size| to the size of the segment's data. If |elfclass|
    100 // is not NULL, set |*elfclass| to the ELF file class.
    101 bool FindElfSegment(const void *elf_mapped_base,
    102                     uint32_t segment_type,
    103                     const void **segment_start,
    104                     size_t *segment_size,
    105                     int *elfclass);
    106 
    107 // Convert an offset from an Elf header into a pointer to the mapped
    108 // address in the current process. Takes an extra template parameter
    109 // to specify the return type to avoid having to dynamic_cast the
    110 // result.
    111 template<typename ElfClass, typename T>
    112 const T*
    113 GetOffset(const typename ElfClass::Ehdr* elf_header,
    114           typename ElfClass::Off offset);
    115 
    116 }  // namespace google_breakpad
    117 
    118 #endif  // COMMON_LINUX_ELFUTILS_H_
    119