summaryrefslogtreecommitdiff
path: root/plugins/elf
diff options
context:
space:
mode:
authorCyrille Bagard <nocbos@gmail.com>2018-01-29 22:49:43 (GMT)
committerCyrille Bagard <nocbos@gmail.com>2018-01-29 22:49:43 (GMT)
commit896b31fbbef2fba442566a422fa4d409771b61dd (patch)
treeb75725f043d54e5a454216a11d89018956ee9c26 /plugins/elf
parent6c51b9eed427fd55ce1457834853386cc8d543cd (diff)
Introduced specific operations for ELF architectures.
Diffstat (limited to 'plugins/elf')
-rw-r--r--plugins/elf/elf-int.h23
-rw-r--r--plugins/elf/format.c20
-rw-r--r--plugins/elf/helper_arm.c23
-rw-r--r--plugins/elf/helper_arm.h3
-rw-r--r--plugins/elf/program.c16
-rw-r--r--plugins/elf/symbols.c15
6 files changed, 73 insertions, 27 deletions
diff --git a/plugins/elf/elf-int.h b/plugins/elf/elf-int.h
index 3b4b67c..291000d 100644
--- a/plugins/elf/elf-int.h
+++ b/plugins/elf/elf-int.h
@@ -34,6 +34,27 @@
+/* Fournit la description humaine d'un type de segment ELF. */
+typedef const char * (* get_elf_prgm_type_desc_cb) (uint32_t);
+
+/* Fournit une adresse virtuelle prête à emploi. */
+typedef virt_t (* fix_elf_virt_addr_cb) (virt_t);
+
+/* Retrouve le décalage appliqué lors d'une résolution. */
+typedef bool (* get_elf_linkage_offset_cb) (GElfFormat *, const mrange_t *, uint64_t *);
+
+
+
+/* Particularités propre aux architectures */
+typedef struct _elf_arch_ops
+{
+ get_elf_prgm_type_desc_cb get_type_desc;/* Description de type */
+ fix_elf_virt_addr_cb fix_virt; /* Retire toute forme d'infos */
+ get_elf_linkage_offset_cb get_linkage_offset; /* Décalage de relocation*/
+
+} elf_arch_ops;
+
+
/* Format d'exécutable générique (instance) */
struct _GElfFormat
{
@@ -43,6 +64,8 @@ struct _GElfFormat
bool is_32b; /* Format du binaire */
SourceEndian endian; /* Boutisme du format */
+ elf_arch_ops ops; /* Opérations spécifiques */
+
};
/* Format d'exécutable générique (classe) */
diff --git a/plugins/elf/format.c b/plugins/elf/format.c
index d48eef9..755bc12 100644
--- a/plugins/elf/format.c
+++ b/plugins/elf/format.c
@@ -36,6 +36,7 @@
#include "elf-int.h"
+#include "helper_arm.h"
#include "program.h"
#include "section.h"
#include "strings.h"
@@ -292,6 +293,25 @@ GBinFormat *g_elf_format_new(GBinContent *content, GExeFormat *parent, GtkStatus
}
+ /* Opérations spécifiques à l'architecture */
+
+ switch (ELF_HDR(result, result->header, e_machine))
+ {
+ case EM_ARM:
+ result->ops.get_type_desc = (get_elf_prgm_type_desc_cb)get_elf_program_arm_type_desc;
+ result->ops.fix_virt = (fix_elf_virt_addr_cb)fix_elf_arm_virtual_address;
+ result->ops.get_linkage_offset = (get_elf_linkage_offset_cb)retrieve_arm_linkage_offset;
+ break;
+
+ default:
+ log_variadic_message(LMT_ERROR, "Architecture not supported for ELF binaries");
+ goto gefn_error;
+ break;
+
+ }
+
+ /* Chargements des informations utiles */
+
/**
* On inscrit les éléments préchargés avant tout !
*
diff --git a/plugins/elf/helper_arm.c b/plugins/elf/helper_arm.c
index 4c34d78..51bdb99 100644
--- a/plugins/elf/helper_arm.c
+++ b/plugins/elf/helper_arm.c
@@ -63,6 +63,29 @@ const char *get_elf_program_arm_type_desc(uint32_t p_type)
/******************************************************************************
* *
+* Paramètres : virt = adresse virtuelle éventuellement porteuse d'infos. *
+* *
+* Description : Fournit une adresse virtuelle prête à emploi. *
+* *
+* Retour : Adresse virtuelle réellement utilisable. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+virt_t fix_elf_arm_virtual_address(virt_t virt)
+{
+ virt_t result; /* Résultat à retourner */
+
+ result = virt & ~0x1;
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : format = description de l'exécutable à manipuler. *
* range = emplacement de la procédure de liaison. *
* offset = décalage retrouvé par désassemblage... [OUT] *
diff --git a/plugins/elf/helper_arm.h b/plugins/elf/helper_arm.h
index 07549ad..3db9324 100644
--- a/plugins/elf/helper_arm.h
+++ b/plugins/elf/helper_arm.h
@@ -32,6 +32,9 @@
/* Fournit la description humaine d'un type de segment ELF. */
const char *get_elf_program_arm_type_desc(uint32_t);
+/* Fournit une adresse virtuelle prête à emploi. */
+virt_t fix_elf_arm_virtual_address(virt_t);
+
/* Retrouve le décalage appliqué lors d'une résolution. */
bool retrieve_arm_linkage_offset(GElfFormat *, const mrange_t *, uint64_t *);
diff --git a/plugins/elf/program.c b/plugins/elf/program.c
index 7e6f2e4..83fdc6f 100644
--- a/plugins/elf/program.c
+++ b/plugins/elf/program.c
@@ -25,7 +25,6 @@
#include "elf-int.h"
-#include "helper_arm.h"
@@ -59,15 +58,11 @@ const char *get_elf_program_type_desc(const GElfFormat *format, uint32_t p_type)
MAKE_STRING_FROM_PT(PT_PHDR);
MAKE_STRING_FROM_PT(PT_TLS);
MAKE_STRING_FROM_PT(PT_NUM);
- MAKE_STRING_FROM_PT(PT_LOOS);
MAKE_STRING_FROM_PT(PT_GNU_EH_FRAME);
MAKE_STRING_FROM_PT(PT_GNU_STACK);
MAKE_STRING_FROM_PT(PT_GNU_RELRO);
MAKE_STRING_FROM_PT(PT_LOSUNW);
MAKE_STRING_FROM_PT(PT_SUNWSTACK);
- MAKE_STRING_FROM_PT(PT_HIOS);
- MAKE_STRING_FROM_PT(PT_LOPROC);
- MAKE_STRING_FROM_PT(PT_HIPROC);
default:
result = NULL;
@@ -76,16 +71,7 @@ const char *get_elf_program_type_desc(const GElfFormat *format, uint32_t p_type)
}
if (result == NULL)
- switch (ELF_HDR(format, format->header, e_machine))
- {
- case EM_ARM:
- result = get_elf_program_arm_type_desc(p_type);
- break;
-
- default:
- break;
-
- }
+ result = format->ops.get_type_desc(p_type);
if (result == NULL)
switch(p_type)
diff --git a/plugins/elf/symbols.c b/plugins/elf/symbols.c
index 4854d7b..dbf3305 100644
--- a/plugins/elf/symbols.c
+++ b/plugins/elf/symbols.c
@@ -42,7 +42,6 @@
#include "dynamic.h"
#include "elf-int.h"
-#include "helper_arm.h"
#include "loading.h"
#include "program.h"
#include "section.h"
@@ -189,10 +188,7 @@ static void register_elf_entry_point(GElfFormat *format, virt_t vaddr, phys_t le
/* Localisation complète du symbole */
- if (ELF_HDR(format, format->header, e_machine) == EM_ARM)
- final_vaddr = vaddr & ~0x1;
- else
- final_vaddr = vaddr;
+ final_vaddr = format->ops.fix_virt(vaddr);
status = g_exe_format_translate_address_into_vmpa(G_EXE_FORMAT(format), final_vaddr, &addr);
if (!status) return;
@@ -514,8 +510,7 @@ static bool do_elf_symbol_loading(GElfLoading *loading, GElfFormat *format, bool
/* Ajustement de la position */
- if (ELF_HDR(format, format->header, e_machine) == EM_ARM)
- virt &= ~0x1;
+ virt = format->ops.fix_virt(virt);
/* Constitution d'une routine */
@@ -1205,11 +1200,7 @@ static bool do_elf_relocation_renaming(GElfLoading *loading, GElfFormat *format,
/* Détermination de la relocalisation associée */
- if (ELF_HDR(format, format->header, e_machine) == EM_ARM)
- result = retrieve_arm_linkage_offset(format, range, &offset);
- else
- result = false;
-
+ result = format->ops.get_linkage_offset(format, range, &offset);
if (!result) goto derr_exit;
result = g_elf_loading_search_for_relocation(loading, &offset, &reloc);