bintools/checklib/object/elf/elf_file_header.cpp
author raptorbot <raptorbot@systemstesthead.symbian.intra>
Fri, 18 Dec 2009 19:57:42 +0000
branchwip
changeset 117 ecf683438dc6
parent 0 044383f39525
permissions -rw-r--r--
Don't mess around with EPOCROOT until actually entering raptor so we know what the original was Put the original epocroot back on the front of the whatcomp output. This allows what output to be either relative or absolute depending on what your epocroot is.

// Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies).
// All rights reserved.
// This component and the accompanying materials are made available
// under the terms of "Eclipse Public License v1.0"
// which accompanies this distribution, and is available
// at the URL "http://www.eclipse.org/legal/epl-v10.html".
//
// Initial Contributors:
// Nokia Corporation - initial contribution.
//
// Contributors:
//
// Description:
//

#include "elf_file_header.h"
#include <stdexcept>
#include <string>


namespace elf
{
    File_header::File_header(const char* p1, const char* p2, bool a_pedantic)
        : m_data( reinterpret_cast<const Elf32_Ehdr*>(p1) )
    {
        if ( p1 + sizeof(Elf32_Ehdr) > p2 )
        {
            throw std::runtime_error("not an ELF object; file too small");
        }

        uint8_t m0 = m_data->e_ident[0];
        uint8_t m1 = m_data->e_ident[1];
        uint8_t m2 = m_data->e_ident[2];
        uint8_t m3 = m_data->e_ident[3];

        if (m0 != 0x7f || m1 != 'E' || m2 != 'L' || m3 != 'F')
        {
            throw std::runtime_error("not an ELF object; bad magic");
        }

        if (a_pedantic) // Do some extra checks for correctness.
        {
            //if (m_data->e_ident[4] != 1)
            //{
            //    throw std::runtime_error("invalid class; this program can only handle 32-bit objects");
            //}

            //if (m_data->e_ident[5] != 1)
            //{
            //    throw std::runtime_error("invalid encoding; this program can only handle little-endian objects");
            //}

            //for (unsigned i = EI_PAD; i < sizeof(m_data->e_ident); ++i)
            //{
            //    if (m_data->e_ident[i] != 0)
            //    {
            //        throw std::runtime_error("non-zero pading");
            //    }
            //}

            //if (m_data->e_type == ET_NONE)
            //{
            //    throw std::runtime_error("invalid type");
            //}

            //if (m_data->e_phoff == 0 && m_data->e_shoff == 0)
            //{
            //    throw std::runtime_error("no program headers and no section headers");
            //}

            //if ( m_data->e_phoff + m_data->e_phentsize * m_data->e_phnum > p2 - p1 + 1 )
            //{
            //    throw std::runtime_error("file too small for header table");
            //}

            //if (m_data->e_shoff + m_data->e_shentsize * m_data->e_shnum > a_mem.get_size() )
            //{
            //    throw std::runtime_error("file too small for header table");
            //}

            //if ( m_data->e_shentsize != sizeof(Elf32_Shdr) )
            //{
            //    throw std::runtime_error("e_shentsize doesn't match the actual size of the type");
            //}

            //if (m_data->e_shoff > 0 && m_data->e_shnum == 0)
            //{
            //    throw std::runtime_error("this program can't handle the combination e_shoff > 0 and e_shnum == 0");
            //}

            //if (m_data->e_shstrndx >= 0xff00)
            //{
            //    throw std::runtime_error("this program can only handle e_shstrndx < 0xff00");
            //}

        } // if (a_pedantic)
    }

    // The following functions are obvious candidates for inlining ...

    // e_type

    bool File_header::is_type_rel() const
    {
        return (m_data->e_type == ET_REL);
    }
    bool File_header::is_type_exec() const
    {
        return (m_data->e_type == ET_EXEC);
    }
    bool File_header::is_type_dyn() const
    {
        return (m_data->e_type == ET_DYN);
    }

    // e_machine

    bool File_header::is_machine_none() const
    {
        return (m_data->e_machine == EM_NONE);
    }
    bool File_header::is_machine_arm() const
    {
        return (m_data->e_machine == EM_ARM);
    }
    bool File_header::is_machine_386() const
    {
        return (m_data->e_machine == EM_386);
    }

    uint32_t File_header::get_entry() const
    {
        return m_data->e_entry;
    }

    uint32_t File_header::get_phoff() const
    {
        return m_data->e_phoff;
    }

    uint32_t File_header::get_shoff() const
    {
        return m_data->e_shoff;
    }

    uint32_t File_header::get_flags() const
    {
        return m_data->e_flags;
    }

    uint16_t File_header::get_ehsize() const
    {
        return m_data->e_ehsize;
    }

    uint16_t File_header::get_phentsize() const
    {
        return m_data->e_phentsize;
    }

    uint16_t File_header::get_phnum() const
    {
        return m_data->e_phnum;
    }

    uint16_t File_header::get_shentsize() const
    {
        return m_data->e_shentsize;
    }

    uint16_t File_header::get_shnum() const
    {
        return m_data->e_shnum;
    }

    uint16_t File_header::get_shstrndx() const
    {
        return m_data->e_shstrndx;
    }

} // namespace elf