summaryrefslogtreecommitdiff
path: root/src/format/elf/elf.c
diff options
context:
space:
mode:
authorCyrille Bagard <nocbos@gmail.com>2013-08-31 15:56:10 (GMT)
committerCyrille Bagard <nocbos@gmail.com>2013-08-31 15:56:10 (GMT)
commited4bb73e5d68c1f81b8e0c3210aa221ec6f2675b (patch)
tree006a4641fc7a5c820d6a4253ff75e79ef01e368b /src/format/elf/elf.c
parent4658d4fa406bad4abe36a76746412cf02c984af0 (diff)
Loaded a binary strip into the editor.
git-svn-id: svn://svn.gna.org/svn/chrysalide/trunk@358 abbe820e-26c8-41b2-8c08-b7b2b41f8b0a
Diffstat (limited to 'src/format/elf/elf.c')
-rw-r--r--src/format/elf/elf.c135
1 files changed, 132 insertions, 3 deletions
diff --git a/src/format/elf/elf.c b/src/format/elf/elf.c
index 158a6b6..6807e36 100644
--- a/src/format/elf/elf.c
+++ b/src/format/elf/elf.c
@@ -26,9 +26,13 @@
#include <malloc.h>
#include <stddef.h>
+#include <stdio.h>
#include <string.h>
+#include <i18n.h>
+
+
#include "elf-int.h"
#include "program.h"
#include "section.h"
@@ -39,11 +43,11 @@
-#ifndef _
-# define _(str) (str)
-#endif
+/* Taille maximale d'une description */
+#define MAX_PORTION_DESC 256
+
/* Initialise la classe des formats d'exécutables ELF. */
@@ -58,6 +62,9 @@ static FormatTargetMachine g_elf_format_get_target_machine(const GElfFormat *);
/* Fournit l'adresse mémoire du point d'entrée du programme. */
static vmpa_t g_elf_format_get_entry_point(const GElfFormat *);
+/* Etend la définition des portions au sein d'un binaire. */
+static void g_elf_format_refine_portions(const GElfFormat *, GBinPortion *);
+
/* Fournit les références aux zones binaires à analyser. */
static GBinPart **g_elf_format_get_parts(const GElfFormat *, size_t *);
@@ -139,6 +146,7 @@ static void g_elf_format_init(GElfFormat *format)
exe_format->get_machine = (get_target_machine_fc)g_elf_format_get_target_machine;
exe_format->get_entry_point = (get_entry_point_fc)g_elf_format_get_entry_point;
+ exe_format->refine_portions = (refine_portions_fc)g_elf_format_refine_portions;
exe_format->get_parts = (get_parts_fc)g_elf_format_get_parts;
exe_format->translate_addr = (translate_addr_fc)g_elf_format_translate_address_into_offset;
@@ -291,6 +299,127 @@ static vmpa_t g_elf_format_get_entry_point(const GElfFormat *format)
/******************************************************************************
* *
* Paramètres : format = informations chargées à consulter. *
+* raw = portion de binaire brut à raffiner. *
+* *
+* Description : Etend la définition des portions au sein d'un binaire. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_elf_format_refine_portions(const GElfFormat *format, GBinPortion *raw)
+{
+ uint16_t i; /* Boucle de parcours */
+ off_t offset; /* Début de part de programme */
+ elf_phdr phdr; /* En-tête de programme ELF */
+ uint32_t p_flags; /* Droits associés à une partie*/
+ const char *background; /* Fond signigicatif */
+ GBinPortion *new; /* Nouvelle portion définie */
+ char desc[MAX_PORTION_DESC]; /* Description d'une portion */
+ PortionAccessRights rights; /* Droits d'une portion */
+ elf_shdr strings; /* Section des descriptions */
+ bool has_strings; /* Section trouvée ? */
+ elf_shdr section; /* En-tête de section ELF */
+ uint64_t sh_flags; /* Droits associés à une partie*/
+ const char *name; /* Nom trouvé ou NULL */
+
+ /* Côté segments basiques */
+
+#if 0
+ for (i = 0; i < ELF_HDR(format, format->header, e_phnum); i++)
+ {
+ offset = ELF_HDR(format, format->header, e_phoff)
+ + ELF_HDR(format, format->header, e_phentsize) * i;
+
+ if (!read_elf_program_header(format, &offset, &phdr))
+ continue;
+
+ p_flags = ELF_PHDR(format, phdr, p_flags);
+
+ if (p_flags & PF_X) background = BPC_CODE;
+ else if (p_flags & PF_W) background = BPC_DATA;
+ else background = BPC_DATA_RO;
+
+ new = g_binary_portion_new(background);
+
+ sprintf(desc, "%s %s",
+ _("Segment"),
+ get_elf_program_type_desc(ELF_PHDR(format, phdr, p_type)));
+
+ g_binary_portion_set_desc(new, desc);
+
+ g_binary_portion_set_values(new,
+ ELF_PHDR(format, phdr, p_offset),
+ ELF_PHDR(format, phdr, p_filesz),
+ ELF_PHDR(format, phdr, p_vaddr));
+
+ rights = PAC_NONE;
+ if (p_flags & PF_R) rights |= PAC_READ;
+ if (p_flags & PF_W) rights |= PAC_WRITE;
+ if (p_flags & PF_X) rights |= PAC_EXEC;
+
+ g_binary_portion_set_rights(new, rights);
+
+ g_binary_portion_include(raw, new);
+
+ }
+#endif
+
+ /* Inclusion des sections, si possible... */
+
+ has_strings = find_elf_section_by_index(format,
+ ELF_HDR(format, format->header, e_shstrndx),
+ &strings);
+
+ for (i = 0; i < ELF_HDR(format, format->header, e_shnum); i++)
+ {
+ if (!find_elf_section_by_index(format, i, &section))
+ continue;
+
+ sh_flags = ELF_SHDR(format, section, sh_flags);
+
+ if (sh_flags & SHF_EXECINSTR) background = BPC_CODE;
+ else if (sh_flags & SHF_WRITE) background = BPC_DATA;
+ else background = BPC_DATA_RO;
+
+ new = g_binary_portion_new(background);
+
+ if (has_strings)
+ name = extract_name_from_elf_string_section(format, &strings,
+ ELF_SHDR(format, section, sh_name));
+ else name = NULL;
+
+ if (name != NULL)
+ sprintf(desc, "%s %s", _("Section"), name);
+ else
+ sprintf(desc, "%s ???", _("Section"));
+
+ g_binary_portion_set_desc(new, desc);
+
+ rights = PAC_NONE;
+ if (sh_flags & SHF_ALLOC) rights |= PAC_READ;
+ if (sh_flags & SHF_WRITE) rights |= PAC_WRITE;
+ if (sh_flags & SHF_EXECINSTR) rights |= PAC_EXEC;
+
+ g_binary_portion_set_rights(new, rights);
+
+ g_binary_portion_set_values(new,
+ ELF_SHDR(format, section, sh_offset),
+ ELF_SHDR(format, section, sh_size),
+ ELF_SHDR(format, section, sh_addr));
+
+ g_binary_portion_include(raw, new);
+
+ }
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : format = informations chargées à consulter. *
* count = quantité de zones listées. [OUT] *
* *
* Description : Fournit les références aux zones binaires à analyser. *