(root)/
binutils-2.41/
elfcpp/
elfcpp_file.h
       1  // elfcpp_file.h -- file access for elfcpp   -*- C++ -*-
       2  
       3  // Copyright (C) 2006-2023 Free Software Foundation, Inc.
       4  // Written by Ian Lance Taylor <iant@google.com>.
       5  
       6  // This file is part of elfcpp.
       7     
       8  // This program is free software; you can redistribute it and/or
       9  // modify it under the terms of the GNU Library General Public License
      10  // as published by the Free Software Foundation; either version 2, or
      11  // (at your option) any later version.
      12  
      13  // In addition to the permissions in the GNU Library General Public
      14  // License, the Free Software Foundation gives you unlimited
      15  // permission to link the compiled version of this file into
      16  // combinations with other programs, and to distribute those
      17  // combinations without any restriction coming from the use of this
      18  // file.  (The Library Public License restrictions do apply in other
      19  // respects; for example, they cover modification of the file, and
      20  /// distribution when not linked into a combined executable.)
      21  
      22  // This program is distributed in the hope that it will be useful, but
      23  // WITHOUT ANY WARRANTY; without even the implied warranty of
      24  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      25  // Library General Public License for more details.
      26  
      27  // You should have received a copy of the GNU Library General Public
      28  // License along with this program; if not, write to the Free Software
      29  // Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
      30  // 02110-1301, USA.
      31  
      32  // This header file defines the class Elf_file which can be used to
      33  // read useful data from an ELF file.  The functions here are all
      34  // templates which take a file interface object as a parameter.  This
      35  // type must have a subtype View.  This type must support two methods:
      36  //     View view(off_t file_offset, off_t data_size)
      37  // returns a View for the specified part of the file.
      38  //     void error(const char* printf_format, ...)
      39  // prints an error message and does not return.  The subtype View must
      40  // support a method
      41  //     const unsigned char* data()
      42  // which returns a pointer to a buffer containing the requested data.
      43  // This general interface is used to read data from the file.  Objects
      44  // of type View will never survive longer than the elfcpp function.
      45  
      46  // Some of these functions must return a reference to part of the
      47  // file.  To use these, the file interface must support a subtype
      48  // Location:
      49  //    Location(off_t file_offset, off_t data_size)
      50  // To use this in conjunction with the accessors types Shdr, etc., the
      51  // file interface should support an overload of view:
      52  //    View view(Location)
      53  // This permits writing
      54  //    elfcpp::Shdr shdr(file, ef.section_header(n));
      55  
      56  #ifndef ELFCPP_FILE_H
      57  #define ELFCPP_FILE_H
      58  
      59  #include <string>
      60  #include <cstdio>
      61  #include <cstring>
      62  
      63  #include "elfcpp.h"
      64  
      65  namespace elfcpp
      66  {
      67  
      68  // A simple helper class to recognize if a file has an ELF header.
      69  
      70  class Elf_recognizer
      71  {
      72   public:
      73    // Maximum header size.  The user should try to read this much of
      74    // the file when using this class.
      75  
      76    static const int max_header_size = Elf_sizes<64>::ehdr_size;
      77  
      78    // Checks if the file contains the ELF magic.  Other header fields
      79    // are not checked.
      80  
      81    static bool
      82    is_elf_file(const unsigned char* ehdr_buf, int size);
      83  
      84    // Check if EHDR_BUF/BUFSIZE is a valid header of a 32-bit or
      85    // 64-bit, little-endian or big-endian ELF file.  Assumes
      86    // is_elf_file() has been checked to be true.  If the header is not
      87    // valid, *ERROR contains a human-readable error message.  If is is,
      88    // *SIZE is set to either 32 or 64, *BIG_ENDIAN is set to indicate
      89    // whether the file is big-endian.
      90  
      91    static bool
      92    is_valid_header(const unsigned char* ehdr_buf, off_t bufsize,
      93                    int* size, bool* big_endian,
      94                    std::string* error);
      95  };
      96  
      97  // This object is used to read an ELF file.
      98  //   SIZE: The size of file, 32 or 64.
      99  //   BIG_ENDIAN: Whether the file is in big-endian format.
     100  //   FILE: A file reading type as described above.
     101  
     102  template<int size, bool big_endian, typename File>
     103  class Elf_file
     104  {
     105   private:
     106    typedef Elf_file<size, big_endian, File> This;
     107  
     108   public:
     109    static const int ehdr_size = Elf_sizes<size>::ehdr_size;
     110    static const int phdr_size = Elf_sizes<size>::phdr_size;
     111    static const int shdr_size = Elf_sizes<size>::shdr_size;
     112    static const int sym_size = Elf_sizes<size>::sym_size;
     113    static const int rel_size = Elf_sizes<size>::rel_size;
     114    static const int rela_size = Elf_sizes<size>::rela_size;
     115  
     116    typedef Ehdr<size, big_endian> Ef_ehdr;
     117    typedef Phdr<size, big_endian> Ef_phdr;
     118    typedef Shdr<size, big_endian> Ef_shdr;
     119    typedef Sym<size, big_endian> Ef_sym;
     120  
     121    // Construct an Elf_file given an ELF file header.
     122    Elf_file(File* file, const Ef_ehdr& ehdr)
     123    { this->construct(file, ehdr); }
     124  
     125    // Construct an ELF file.
     126    inline
     127    Elf_file(File* file);
     128  
     129    // Return the file offset to the section headers.
     130    off_t
     131    shoff() const
     132    { return this->shoff_; }
     133  
     134    // Find the first section with an sh_type field equal to TYPE and
     135    // return its index.  Returns SHN_UNDEF if there is no such section.
     136    unsigned int
     137    find_section_by_type(unsigned int type);
     138  
     139    // Return the number of sections.
     140    unsigned int
     141    shnum()
     142    {
     143      this->initialize_shnum();
     144      return this->shnum_;
     145    }
     146  
     147    unsigned int
     148    shnum() const
     149    {
     150      if (this->shnum_ == 0 && this->shoff_ != 0)
     151        this->file_->error(_("ELF file has not been initialized yet"
     152  			   " (internal error)"));
     153      return this->shnum_;
     154    }
     155  
     156    // Return the section index of the section name string table.
     157    unsigned int
     158    shstrndx()
     159    {
     160      this->initialize_shnum();
     161      return this->shstrndx_;
     162    }
     163  
     164    unsigned int
     165    shstrndx() const
     166    {
     167      if (this->shstrndx_ == SHN_XINDEX && this->shoff_ != 0)
     168        {
     169  	this->file_->error(_("ELF file has not been initialized yet"
     170  			     " (internal error)"));
     171  	return 0;
     172        }
     173      return this->shstrndx_;
     174    }
     175  
     176    // Return the value to subtract from section indexes >=
     177    // SHN_LORESERVE.  See the comment in initialize_shnum.
     178    int
     179    large_shndx_offset()
     180    {
     181      this->initialize_shnum();
     182      return this->large_shndx_offset_;
     183    }
     184  
     185    int
     186    large_shndx_offset() const
     187    {
     188      if (this->shstrndx_ == SHN_XINDEX && this->shoff_ != 0)
     189        this->file_->error(_("ELF file has not been initialized yet"
     190  			   " (internal error)"));
     191      return this->large_shndx_offset_;
     192    }
     193  
     194    // Return the location of the header of section SHNDX.
     195    typename File::Location
     196    section_header(unsigned int shndx)
     197    {
     198      return typename File::Location(this->section_header_offset(shndx),
     199  				   shdr_size);
     200    }
     201  
     202    // Return the name of section SHNDX.
     203    std::string
     204    section_name(unsigned int shndx) const;
     205  
     206    // Return the location of the contents of section SHNDX.
     207    typename File::Location
     208    section_contents(unsigned int shndx);
     209  
     210    // Return the size of section SHNDX.
     211    typename Elf_types<size>::Elf_WXword
     212    section_size(unsigned int shndx);
     213  
     214    // Return the flags of section SHNDX.
     215    typename Elf_types<size>::Elf_WXword
     216    section_flags(unsigned int shndx);
     217  
     218    // Return the address of section SHNDX.
     219    typename Elf_types<size>::Elf_Addr
     220    section_addr(unsigned int shndx);
     221  
     222    // Return the type of section SHNDX.
     223    Elf_Word
     224    section_type(unsigned int shndx);
     225  
     226    // Return the link field of section SHNDX.
     227    Elf_Word
     228    section_link(unsigned int shndx);
     229  
     230    // Return the info field of section SHNDX.
     231    Elf_Word
     232    section_info(unsigned int shndx);
     233  
     234    // Return the addralign field of section SHNDX.
     235    typename Elf_types<size>::Elf_WXword
     236    section_addralign(unsigned int shndx);
     237  
     238   private:
     239    // Shared constructor code.
     240    void
     241    construct(File* file, const Ef_ehdr& ehdr);
     242  
     243    // Initialize shnum_ and shstrndx_.
     244    void
     245    initialize_shnum();
     246  
     247    // Return the file offset of the header of section SHNDX.
     248    off_t
     249    section_header_offset(unsigned int shndx) const;
     250  
     251    // The file we are reading.
     252    File* file_;
     253    // The file offset to the section headers.
     254    off_t shoff_;
     255    // The number of sections.
     256    unsigned int shnum_;
     257    // The section index of the section name string table.
     258    unsigned int shstrndx_;
     259    // Offset to add to sections larger than SHN_LORESERVE.
     260    int large_shndx_offset_;
     261  };
     262  
     263  // A small wrapper around SHT_STRTAB data mapped to memory. It checks that the
     264  // index is not out of bounds and the string is NULL-terminated.
     265  
     266  class Elf_strtab
     267  {
     268   public:
     269    // Construct an Elf_strtab for a section with contents *P and size SIZE.
     270    Elf_strtab(const unsigned char* p, size_t size);
     271  
     272    // Return the file offset to the section headers.
     273    bool
     274    get_c_string(size_t offset, const char** cstring) const
     275    {
     276      if (offset >= this->usable_size_)
     277        return false;
     278      *cstring = this->base_ + offset;
     279      return true;
     280    }
     281  
     282   private:
     283    // Contents of the section mapped to memory.
     284    const char* base_;
     285    // One larger that the position of the last NULL character in the section.
     286    // For valid SHT_STRTAB sections, this is the size of the section.
     287    size_t usable_size_;
     288  };
     289  
     290  // Inline function definitions.
     291  
     292  // Check for presence of the ELF magic number.
     293  
     294  inline bool
     295  Elf_recognizer::is_elf_file(const unsigned char* ehdr_buf, int size)
     296  {
     297    if (size < 4)
     298      return false;
     299  
     300    static unsigned char elfmagic[4] =
     301      {
     302        elfcpp::ELFMAG0, elfcpp::ELFMAG1,
     303        elfcpp::ELFMAG2, elfcpp::ELFMAG3
     304      };
     305    return memcmp(ehdr_buf, elfmagic, 4) == 0;
     306  }
     307  
     308  namespace
     309  {
     310  
     311  // Print a number to a string.
     312  
     313  inline std::string
     314  internal_printf_int(const char* format, int arg)
     315  {
     316    char buf[256];
     317    snprintf(buf, sizeof(buf), format, arg);
     318    return std::string(buf);
     319  }
     320  
     321  }  // End anonymous namespace.
     322  
     323  // Check the validity of the ELF header.
     324  
     325  inline bool
     326  Elf_recognizer::is_valid_header(
     327      const unsigned char* ehdr_buf,
     328      off_t bufsize,
     329      int* size,
     330      bool* big_endian,
     331      std::string* error)
     332  {
     333    if (bufsize < elfcpp::EI_NIDENT)
     334      {
     335        *error = _("ELF file too short");
     336        return false;
     337      }
     338  
     339    int v = ehdr_buf[elfcpp::EI_VERSION];
     340    if (v != elfcpp::EV_CURRENT)
     341      {
     342        if (v == elfcpp::EV_NONE)
     343          *error = _("invalid ELF version 0");
     344        else
     345          *error = internal_printf_int(_("unsupported ELF version %d"), v);
     346        return false;
     347      }
     348  
     349    int c = ehdr_buf[elfcpp::EI_CLASS];
     350    if (c == elfcpp::ELFCLASSNONE)
     351      {
     352        *error = _("invalid ELF class 0");
     353        return false;
     354      }
     355    else if (c != elfcpp::ELFCLASS32
     356             && c != elfcpp::ELFCLASS64)
     357      {
     358        *error = internal_printf_int(_("unsupported ELF class %d"), c);
     359        return false;
     360      }
     361  
     362    int d = ehdr_buf[elfcpp::EI_DATA];
     363    if (d == elfcpp::ELFDATANONE)
     364      {
     365        *error = _("invalid ELF data encoding");
     366        return false;
     367      }
     368    else if (d != elfcpp::ELFDATA2LSB
     369             && d != elfcpp::ELFDATA2MSB)
     370      {
     371        *error = internal_printf_int(_("unsupported ELF data encoding %d"), d);
     372        return false;
     373      }
     374  
     375    *big_endian = (d == elfcpp::ELFDATA2MSB);
     376  
     377    if (c == elfcpp::ELFCLASS32)
     378      {
     379        if (bufsize < elfcpp::Elf_sizes<32>::ehdr_size)
     380          {
     381            *error = _("ELF file too short");
     382            return false;
     383          }
     384        *size = 32;
     385      }
     386    else
     387      {
     388        if (bufsize < elfcpp::Elf_sizes<64>::ehdr_size)
     389          {
     390            *error = _("ELF file too short");
     391            return false;
     392          }
     393        *size = 64;
     394      }
     395  
     396    return true;
     397  }
     398  
     399  // Template function definitions.
     400  
     401  // Construct an Elf_file given an ELF file header.
     402  
     403  template<int size, bool big_endian, typename File>
     404  void
     405  Elf_file<size, big_endian, File>::construct(File* file, const Ef_ehdr& ehdr)
     406  {
     407    this->file_ = file;
     408    this->shoff_ = ehdr.get_e_shoff();
     409    this->shnum_ = ehdr.get_e_shnum();
     410    this->shstrndx_ = ehdr.get_e_shstrndx();
     411    this->large_shndx_offset_ = 0;
     412    if (ehdr.get_e_ehsize() != This::ehdr_size)
     413      file->error(_("bad e_ehsize (%d != %d)"),
     414  		ehdr.get_e_ehsize(), This::ehdr_size);
     415    if (ehdr.get_e_shentsize() != This::shdr_size)
     416      file->error(_("bad e_shentsize (%d != %d)"),
     417  		ehdr.get_e_shentsize(), This::shdr_size);
     418  }
     419  
     420  // Construct an ELF file.
     421  
     422  template<int size, bool big_endian, typename File>
     423  inline
     424  Elf_file<size, big_endian, File>::Elf_file(File* file)
     425  {
     426    typename File::View v(file->view(file_header_offset, This::ehdr_size));
     427    this->construct(file, Ef_ehdr(v.data()));
     428  }
     429  
     430  // Initialize the shnum_ and shstrndx_ fields, handling overflow.
     431  
     432  template<int size, bool big_endian, typename File>
     433  void
     434  Elf_file<size, big_endian, File>::initialize_shnum()
     435  {
     436    if ((this->shnum_ == 0 || this->shstrndx_ == SHN_XINDEX)
     437        && this->shoff_ != 0)
     438      {
     439        typename File::View v(this->file_->view(this->shoff_, This::shdr_size));
     440        Ef_shdr shdr(v.data());
     441  
     442        if (this->shnum_ == 0)
     443  	this->shnum_ = shdr.get_sh_size();
     444  
     445        if (this->shstrndx_ == SHN_XINDEX)
     446  	{
     447  	  this->shstrndx_ = shdr.get_sh_link();
     448  
     449  	  // Versions of the GNU binutils between 2.12 and 2.18 did
     450  	  // not handle objects with more than SHN_LORESERVE sections
     451  	  // correctly.  All large section indexes were offset by
     452  	  // 0x100.  Some information can be found here:
     453  	  // http://sourceware.org/bugzilla/show_bug.cgi?id=5900 .
     454  	  // Fortunately these object files are easy to detect, as the
     455  	  // GNU binutils always put the section header string table
     456  	  // near the end of the list of sections.  Thus if the
     457  	  // section header string table index is larger than the
     458  	  // number of sections, then we know we have to subtract
     459  	  // 0x100 to get the real section index.
     460  	  if (this->shstrndx_ >= this->shnum_)
     461  	    {
     462  	      if (this->shstrndx_ >= elfcpp::SHN_LORESERVE + 0x100)
     463  		{
     464  		  this->large_shndx_offset_ = - 0x100;
     465  		  this->shstrndx_ -= 0x100;
     466  		}
     467  	      if (this->shstrndx_ >= this->shnum_)
     468  		this->file_->error(_("bad shstrndx: %u >= %u"),
     469  				   this->shstrndx_, this->shnum_);
     470  	    }
     471  	}
     472      }
     473  }
     474  
     475  // Find section with sh_type equal to TYPE and return its index.
     476  // Returns SHN_UNDEF if not found.
     477  
     478  template<int size, bool big_endian, typename File>
     479  unsigned int
     480  Elf_file<size, big_endian, File>::find_section_by_type(unsigned int type)
     481  {
     482    unsigned int shnum = this->shnum();
     483    typename File::View v(this->file_->view(this->shoff_,
     484  					  This::shdr_size * shnum));
     485    for (unsigned int i = 0; i < shnum; i++)
     486      {
     487        Ef_shdr shdr(v.data() + This::shdr_size * i);
     488        if (shdr.get_sh_type() == type)
     489          return i;
     490      }
     491    return SHN_UNDEF;
     492  }
     493  
     494  // Return the file offset of the section header of section SHNDX.
     495  
     496  template<int size, bool big_endian, typename File>
     497  off_t
     498  Elf_file<size, big_endian, File>::section_header_offset(unsigned int shndx) const
     499  {
     500    if (shndx >= this->shnum())
     501      this->file_->error(_("section_header_offset: bad shndx %u >= %u"),
     502  		       shndx, this->shnum());
     503    return this->shoff_ + This::shdr_size * shndx;
     504  }
     505  
     506  // Return the name of section SHNDX.
     507  
     508  template<int size, bool big_endian, typename File>
     509  std::string
     510  Elf_file<size, big_endian, File>::section_name(unsigned int shndx) const
     511  {
     512    File* const file = this->file_;
     513  
     514    // Get the section name offset.
     515    unsigned int sh_name;
     516    {
     517      typename File::View v(file->view(this->section_header_offset(shndx),
     518  				     This::shdr_size));
     519      Ef_shdr shdr(v.data());
     520      sh_name = shdr.get_sh_name();
     521    }
     522  
     523    // Get the file offset for the section name string table data.
     524    off_t shstr_off;
     525    typename Elf_types<size>::Elf_WXword shstr_size;
     526    {
     527      const unsigned int shstrndx = this->shstrndx_;
     528      typename File::View v(file->view(this->section_header_offset(shstrndx),
     529  				     This::shdr_size));
     530      Ef_shdr shstr_shdr(v.data());
     531      shstr_off = shstr_shdr.get_sh_offset();
     532      shstr_size = shstr_shdr.get_sh_size();
     533    }
     534  
     535    if (sh_name >= shstr_size)
     536      file->error(_("bad section name offset for section %u: %u"),
     537  		shndx, sh_name);
     538  
     539    typename File::View v(file->view(shstr_off, shstr_size));
     540  
     541    const unsigned char* datau = v.data();
     542    const char* data = reinterpret_cast<const char*>(datau);
     543    const void* p = ::memchr(data + sh_name, '\0', shstr_size - sh_name);
     544    if (p == NULL)
     545      file->error(_("missing null terminator for name of section %u"),
     546  		shndx);
     547  
     548    size_t len = static_cast<const char*>(p) - (data + sh_name);
     549  
     550    return std::string(data + sh_name, len);
     551  }
     552  
     553  // Return the contents of section SHNDX.
     554  
     555  template<int size, bool big_endian, typename File>
     556  typename File::Location
     557  Elf_file<size, big_endian, File>::section_contents(unsigned int shndx)
     558  {
     559    File* const file = this->file_;
     560  
     561    if (shndx >= this->shnum())
     562      file->error(_("section_contents: bad shndx %u >= %u"),
     563  		shndx, this->shnum());
     564  
     565    typename File::View v(file->view(this->section_header_offset(shndx),
     566  				   This::shdr_size));
     567    Ef_shdr shdr(v.data());
     568    return typename File::Location(shdr.get_sh_offset(), shdr.get_sh_size());
     569  }
     570  
     571  // Get the size of section SHNDX.
     572  
     573  template<int size, bool big_endian, typename File>
     574  typename Elf_types<size>::Elf_WXword
     575  Elf_file<size, big_endian, File>::section_size(unsigned int shndx)
     576  {
     577    File* const file = this->file_;
     578  
     579    if (shndx >= this->shnum())
     580      file->error(_("section_size: bad shndx %u >= %u"),
     581  		shndx, this->shnum());
     582  
     583    typename File::View v(file->view(this->section_header_offset(shndx),
     584  				   This::shdr_size));
     585  
     586    Ef_shdr shdr(v.data());
     587    return shdr.get_sh_size();
     588  }
     589  
     590  // Return the section flags of section SHNDX.
     591  
     592  template<int size, bool big_endian, typename File>
     593  typename Elf_types<size>::Elf_WXword
     594  Elf_file<size, big_endian, File>::section_flags(unsigned int shndx)
     595  {
     596    File* const file = this->file_;
     597  
     598    if (shndx >= this->shnum())
     599      file->error(_("section_flags: bad shndx %u >= %u"),
     600  		shndx, this->shnum());
     601  
     602    typename File::View v(file->view(this->section_header_offset(shndx),
     603  				   This::shdr_size));
     604  
     605    Ef_shdr shdr(v.data());
     606    return shdr.get_sh_flags();
     607  }
     608  
     609  // Return the address of section SHNDX.
     610  
     611  template<int size, bool big_endian, typename File>
     612  typename Elf_types<size>::Elf_Addr
     613  Elf_file<size, big_endian, File>::section_addr(unsigned int shndx)
     614  {
     615    File* const file = this->file_;
     616  
     617    if (shndx >= this->shnum())
     618      file->error(_("section_flags: bad shndx %u >= %u"),
     619  		shndx, this->shnum());
     620  
     621    typename File::View v(file->view(this->section_header_offset(shndx),
     622  				   This::shdr_size));
     623  
     624    Ef_shdr shdr(v.data());
     625    return shdr.get_sh_addr();
     626  }
     627  
     628  // Return the type of section SHNDX.
     629  
     630  template<int size, bool big_endian, typename File>
     631  Elf_Word
     632  Elf_file<size, big_endian, File>::section_type(unsigned int shndx)
     633  {
     634    File* const file = this->file_;
     635  
     636    if (shndx >= this->shnum())
     637      file->error(_("section_type: bad shndx %u >= %u"),
     638  		shndx, this->shnum());
     639  
     640    typename File::View v(file->view(this->section_header_offset(shndx),
     641  				   This::shdr_size));
     642  
     643    Ef_shdr shdr(v.data());
     644    return shdr.get_sh_type();
     645  }
     646  
     647  // Return the sh_link field of section SHNDX.
     648  
     649  template<int size, bool big_endian, typename File>
     650  Elf_Word
     651  Elf_file<size, big_endian, File>::section_link(unsigned int shndx)
     652  {
     653    File* const file = this->file_;
     654  
     655    if (shndx >= this->shnum())
     656      file->error(_("section_link: bad shndx %u >= %u"),
     657  		shndx, this->shnum());
     658  
     659    typename File::View v(file->view(this->section_header_offset(shndx),
     660  				   This::shdr_size));
     661  
     662    Ef_shdr shdr(v.data());
     663    return shdr.get_sh_link();
     664  }
     665  
     666  // Return the sh_info field of section SHNDX.
     667  
     668  template<int size, bool big_endian, typename File>
     669  Elf_Word
     670  Elf_file<size, big_endian, File>::section_info(unsigned int shndx)
     671  {
     672    File* const file = this->file_;
     673  
     674    if (shndx >= this->shnum())
     675      file->error(_("section_info: bad shndx %u >= %u"),
     676  		shndx, this->shnum());
     677  
     678    typename File::View v(file->view(this->section_header_offset(shndx),
     679  				   This::shdr_size));
     680  
     681    Ef_shdr shdr(v.data());
     682    return shdr.get_sh_info();
     683  }
     684  
     685  // Return the sh_addralign field of section SHNDX.
     686  
     687  template<int size, bool big_endian, typename File>
     688  typename Elf_types<size>::Elf_WXword
     689  Elf_file<size, big_endian, File>::section_addralign(unsigned int shndx)
     690  {
     691    File* const file = this->file_;
     692  
     693    if (shndx >= this->shnum())
     694      file->error(_("section_addralign: bad shndx %u >= %u"),
     695  		shndx, this->shnum());
     696  
     697    typename File::View v(file->view(this->section_header_offset(shndx),
     698  				   This::shdr_size));
     699  
     700    Ef_shdr shdr(v.data());
     701    return shdr.get_sh_addralign();
     702  }
     703  
     704  inline
     705  Elf_strtab::Elf_strtab(const unsigned char* p, size_t size)
     706  {
     707    // Check if the section is NUL-terminated. If it isn't, we ignore
     708    // the last part to make sure we don't return non-NUL-terminated
     709    // strings.
     710    while (size > 0 && p[size - 1] != 0)
     711      size--;
     712    this->base_ = reinterpret_cast<const char*>(p);
     713    this->usable_size_ = size;
     714  }
     715  
     716  } // End namespace elfcpp.
     717  
     718  #endif // !defined(ELFCPP_FILE_H)