summaryrefslogtreecommitdiff
path: root/src/format/elf/symbols.c
diff options
context:
space:
mode:
authorCyrille Bagard <nocbos@gmail.com>2017-10-01 17:32:12 (GMT)
committerCyrille Bagard <nocbos@gmail.com>2017-10-01 17:32:12 (GMT)
commit208abfe4182c0dafc230e0377b3efcc6c24be0f9 (patch)
tree4e084364b0a211ee36a5e8e55b70367f01d720d5 /src/format/elf/symbols.c
parent593aee561015251dfd042dc5e00388f63232c45f (diff)
Defined the ELF support as plugin.
Diffstat (limited to 'src/format/elf/symbols.c')
-rw-r--r--src/format/elf/symbols.c952
1 files changed, 0 insertions, 952 deletions
diff --git a/src/format/elf/symbols.c b/src/format/elf/symbols.c
deleted file mode 100644
index c6056ca..0000000
--- a/src/format/elf/symbols.c
+++ /dev/null
@@ -1,952 +0,0 @@
-
-/* Chrysalide - Outil d'analyse de fichiers binaires
- * symbols.c - gestion des symboles d'un ELF
- *
- * Copyright (C) 2009-2017 Cyrille Bagard
- *
- * This file is part of Chrysalide.
- *
- * Chrysalide is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 3 of the License, or
- * (at your option) any later version.
- *
- * Chrysalide is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
- */
-
-
-#include "symbols.h"
-
-
-#include <assert.h>
-#include <malloc.h>
-#include <string.h>
-
-
-#include <i18n.h>
-
-
-#include "dynamic.h"
-#include "elf-int.h"
-#include "helper_arm.h"
-#include "helper_x86.h"
-#include "loading.h"
-#include "program.h"
-#include "section.h"
-#include "../mangling/demangler.h"
-#include "../../arch/raw.h"
-#include "../../common/extstr.h"
-#include "../../core/global.h"
-#include "../../core/params.h"
-#include "../../gui/panels/log.h"
-
-
-
-
-
-
-
-
-
-
-/* Enregistre un point d'entrée au sein d'un binaire ELF. */
-static void register_elf_entry_point(GElfFormat *, virt_t, phys_t, GBinRoutine *);
-
-/* Enumère tous les points d'entrée principaux d'un binaire ELF. */
-static bool load_all_elf_basic_entry_points(GElfFormat *);
-
-
-
-
-
-
-
-
-
-/* -------------------------- DETAIL DES SYMBOLES INTERNES -------------------------- */
-
-
-/* Assure le chargement des symboles internes ELF en différé. */
-static bool do_elf_internal_symbol_loading(GElfLoading *, GElfFormat *, phys_t *);
-
-/* Charge tous les symboles internes possibles. */
-static bool load_elf_internal_symbols(GElfFormat *, wgroup_id_t, GtkStatusStack *);
-
-
-
-/* -------------------------- DETAIL DES SYMBOLES EXTERNES -------------------------- */
-
-
-/* Retrouve un élément donné dans la section dynamique. */
-static bool find_elf_dynamic_item(const GElfFormat *, const elf_shdr *, int32_t, elf_dyn *);
-
-/* Charge tous les éléments dynamiques externes possibles. */
-static bool load_elf_external_symbols(GElfFormat *, const elf_shdr *);
-
-
-
-
-
-
-
-
-
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : format = description de l'exécutable à compléter. *
- status = barre de statut à tenir informée. *
-* *
-* Description : Charge en mémoire la liste humaine des symboles. *
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-bool load_elf_symbols(GElfFormat *format, GtkStatusStack *status)
-{
- bool result; /* Bilan à retourner */
- wgroup_id_t gid; /* Identifiant pour les tâches */
-
- elf_shdr *sections; /* Groupe de sections trouvées */
- size_t count; /* Quantité de données */
-
- result = true;
-
- gid = g_work_queue_define_work_group(get_work_queue());
-
- /* Symboles internes */
-
- result &= load_elf_internal_symbols(format, gid, status);
-
-
-
-
- /* Symboles externes */
-#if 1
- if (find_elf_sections_by_type(format, SHT_DYNAMIC, &sections, &count))
- {
- log_variadic_message(LMT_INFO, _("Binary is dynamically linked"));
-
- result &= load_elf_external_symbols(format, &sections[0]);
-
- free(sections);
-
- }
- else log_variadic_message(LMT_INFO, _("Binary is statically linked"));
-#endif
- /* Symboles internes */
- //result &= load_elf_internal_symbols(format);
-
-
-
- /* Symboles d'entrée, si encore besoin */
-
- /**
- * Le tri en préalable
- */
-
-
-
-
-
- result &= load_all_elf_basic_entry_points(format);
-
- return result;
-
-}
-
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : format = description de l'exécutable à compléter. *
-* vaddr = adresse virtuelle du symbole à insérer. *
-* len = taille de la routine à ajouter. *
-* routine = représentation de la fonction repérée. *
-* *
-* Description : Enregistre un point d'entrée au sein d'un binaire ELF. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static void register_elf_entry_point(GElfFormat *format, virt_t vaddr, phys_t len, GBinRoutine *routine)
-{
- GBinFormat *base; /* Version basique du format */
- virt_t final_vaddr; /* Adresse virtuelle retenue */
- bool status; /* Bilan d'une opération */
- vmpa2t addr; /* Localisation d'une routine */
- mrange_t range; /* Couverture mémoire associée */
- GBinSymbol *symbol; /* Nouveau symbole construit */
-
- /* Localisation complète du symbole */
-
- if (ELF_HDR(format, format->header, e_machine) == EM_ARM)
- final_vaddr = vaddr & ~0x1;
- else
- final_vaddr = vaddr;
-
- status = g_exe_format_translate_address_into_vmpa(G_EXE_FORMAT(format), final_vaddr, &addr);
- if (!status) return;
-
- /* Comptabilisation en tant que symbole */
-
- if (g_binary_format_find_symbol_at(G_BIN_FORMAT(format), &addr, &symbol))
- g_object_unref(G_OBJECT(routine));
-
- else
- {
- base = G_BIN_FORMAT(format);
-
- init_mrange(&range, &addr, len);
-
- symbol = G_BIN_SYMBOL(routine);
-
- g_binary_symbol_set_range(symbol, &range);
- g_binary_symbol_set_target_type(symbol, STP_ENTRY_POINT);
-
- g_binary_format_add_symbol(base, symbol);
-
- /* Comptabilisation pour le désassemblage brut */
- g_binary_format_register_code_point(base, vaddr, true);
-
- }
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = description de l'exécutable à consulter. *
-* *
-* Description : Enumère tous les points d'entrée principaux d'un binaire ELF.*
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static bool load_all_elf_basic_entry_points(GElfFormat *format)
-{
- virt_t ep; /* Point d'entrée détecté */
- GBinRoutine *routine; /* Routine à associer à un pt. */
- elf_phdr dynamic; /* En-tête de programme DYNAMIC*/
- elf_dyn item_a; /* Premier élément DYNAMIC */
- elf_dyn item_b; /* Second élément DYNAMIC */
- const GBinContent *content; /* Contenu binaire à lire */
- phys_t length; /* Taille totale du contenu */
- bool status; /* Bilan d'une opération */
- vmpa2t pos; /* Tête de lecture courante */
- uint32_t virt_32; /* Adresse virtuelle sur 32b */
- uint64_t virt_64; /* Adresse virtuelle sur 64b */
-
- /* Point d'entrée principal éventuel */
-
- ep = ELF_HDR(format, format->header, e_entry);
-
- if (ep != 0x0)
- {
- routine = try_to_demangle_routine("entry_point");
- register_elf_entry_point(format, ep, 0, routine);
- }
-
- /* Chargemet de l'en-tête de programme DYNAMIC */
-
- if (!find_elf_dynamic_program_header(format, &dynamic))
- goto laebep_exit;
-
- /* Détection des constructeurs & destructeurs */
-
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_INIT, &item_a))
- {
- ep = ELF_DYN(format, item_a, d_un.d_ptr);
-
- if (ep != 0x0)
- {
- routine = try_to_demangle_routine("init_function");
- register_elf_entry_point(format, ep, 0, routine);
- }
-
- }
-
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_FINI, &item_a))
- {
- ep = ELF_DYN(format, item_a, d_un.d_ptr);
-
- if (ep != 0x0)
- {
- routine = try_to_demangle_routine("termination_function");
- register_elf_entry_point(format, ep, 0, routine);
- }
-
- }
-
- void load_entry_points_from_array(GElfFormat *fmt, const elf_dyn *ar, const elf_dyn *sz, const char *prefix)
- {
- unsigned int i; /* Boucle de parcours */
- char fullname[64]; /* Désignation humaine */
-
- assert(sizeof(fullname) >= (strlen(prefix) + sizeof(XSTR(UINT64_MAX) + 1)));
-
- content = G_BIN_FORMAT(fmt)->content;
-
- status = g_exe_format_translate_address_into_vmpa(G_EXE_FORMAT(format),
- ELF_DYN(fmt, *ar, d_un.d_val),
- &pos);
- if (!status) return;
-
- length = get_phy_addr(&pos) + ELF_DYN(fmt, *sz, d_un.d_val);
-
- for (i = 0; get_phy_addr(&pos) < length; i++)
- {
- /**
- * Selon la libc d'Android (https://www.codeaurora.org/.../android/bionic/linker/README.TXT) :
- *
- * DT_INIT_ARRAY
- * Points to an array of function addresses that must be
- * called, in-order, to perform initialization. Some of
- * the entries in the array can be 0 or -1, and should
- * be ignored.
- *
- * On étend le principe aux sections DT_FINI_ARRAY et DT_PREINIT_ARRAY.
- */
-
- if (fmt->is_32b)
- {
- status = g_binary_content_read_u32(content, &pos, fmt->endian, &virt_32);
- status &= (virt_32 != 0x0 && virt_32 != 0xffffffff);
- ep = virt_32;
- }
- else
- {
- status = g_binary_content_read_u64(content, &pos, fmt->endian, &virt_64);
- status &= (virt_64 != 0x0 && virt_64 != 0xffffffffffffffff);
- ep = virt_64;
- }
-
- if (!status) break;
-
- snprintf(fullname, sizeof(fullname), "%s%u", prefix, i);
-
- routine = try_to_demangle_routine(fullname);
- register_elf_entry_point(fmt, ep, 0, routine);
-
- }
-
- }
-
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_INIT_ARRAY, &item_a))
- {
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_INIT_ARRAYSZ, &item_b))
- {
- load_entry_points_from_array(format, &item_a, &item_b, "init_array_function_");
- }
-
- }
-
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_FINI_ARRAY, &item_a))
- {
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_FINI_ARRAYSZ, &item_b))
- {
- load_entry_points_from_array(format, &item_a, &item_b, "fini_array_function_");
- }
-
- }
-
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_PREINIT_ARRAY, &item_a))
- {
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_PREINIT_ARRAYSZ, &item_b))
- {
- load_entry_points_from_array(format, &item_a, &item_b, "preinit_array_function_");
- }
-
- }
-
- /* Identification de l'entrée de la PLT */
-
- if (find_elf_dynamic_item_from_pheader(format, &dynamic, DT_PLTGOT, &item_a))
- {
- status = g_exe_format_translate_address_into_vmpa(G_EXE_FORMAT(format),
- ELF_DYN(format, item_a, d_un.d_val),
- &pos);
-
- if (status)
- {
- content = G_BIN_FORMAT(format)->content;
-
- /* On saute le premier élément... */
- if (format->is_32b)
- status = g_binary_content_read_u32(content, &pos, format->endian, &virt_32);
- else
- status = g_binary_content_read_u64(content, &pos, format->endian, &virt_64);
-
- while (1)
- {
- if (format->is_32b)
- {
- status = g_binary_content_read_u32(content, &pos, format->endian, &virt_32);
- ep = virt_32;
- }
- else
- {
- status = g_binary_content_read_u64(content, &pos, format->endian, &virt_64);
- ep = virt_64;
- }
-
- if (!status) break;
-
- if (ep != 0x0)
- {
- routine = try_to_demangle_routine("plt_entry");
- register_elf_entry_point(format, ep, 0, routine);
- break;
- }
-
- }
-
- }
-
- }
-
- laebep_exit:
-
- return true;
-
-}
-
-
-
-
-
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : format = description de l'exécutable à consulter. *
-* sym = section comprenant les symboles à venir lire. *
-* index = indice de l'entrée à venir lire. *
-* symbol = ensemble d'informations lues. [OUT] *
-* *
-* Description : Récupère la définition complète d'un symbole donné. *
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-bool get_elf_symbol_by_index(GElfFormat *format, const elf_shdr *sym, off_t index, elf_sym *symbol)
-{
- phys_t sym_start; /* Début de section */
- phys_t sym_size; /* Taille de section */
- phys_t offset; /* Emplacement à venir lire */
-
- get_elf_section_content(format, sym, &sym_start, &sym_size, NULL);
-
- offset = sym_start + index * ELF_SIZEOF_SYM(format);
- if ((offset + ELF_SIZEOF_SYM(format)) > (sym_start + sym_size)) return NULL;
-
- return read_elf_symbol(format, &offset, symbol);
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = description de l'exécutable à consulter. *
-* sym = section comprenant les symboles à venir lire. *
-* str = section de chaînes de caractères pour les noms. *
-* index = indice de l'entrée à venir lire. *
-* *
-* Description : Récupère la désignation d'un symbole donné. *
-* *
-* Retour : Nom du symbole trouvé, ou NULL si erreur ou non adapté. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-const char *get_elf_symbol_name(GElfFormat *format, const elf_shdr *sym, const elf_shdr *str, off_t index)
-{
- const char *result; /* Résultat à retourner */
- elf_sym symbol; /* Symbole aux infos visées */
-
- result = NULL;
-
- if (get_elf_symbol_by_index(format, sym, index, &symbol))
- result = extract_name_from_elf_string_section(format, str, ELF_SYM(format, symbol, st_name));
-
- return result;
-
-}
-
-
-
-/* ---------------------------------------------------------------------------------- */
-/* DETAIL DES SYMBOLES INTERNES */
-/* ---------------------------------------------------------------------------------- */
-
-
-/******************************************************************************
-* *
-* Paramètres : loading = chargement de symboles internes en cours. *
-* format = format ELF à compléter. *
-* iter = tête de lecture évoluant avec le temps. [OUT] *
-* *
-* Description : Assure le chargement des symboles internes ELF en différé. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static bool do_elf_internal_symbol_loading(GElfLoading *loading, GElfFormat *format, phys_t *iter)
-{
- bool result; /* Bilan à retourner */
- elf_sym sym; /* Symbole aux infos visées */
- virt_t virt; /* Adresse virtuelle */
- const elf_shdr *section; /* Groupe de sections trouvées */
- bool use_virt; /* Choix de construction de nom*/
- const elf_shdr *strtab; /* Section .strtab trouvée */
- bool has_strtab; /* Présence de cette section */
- phys_t first; /* Position du premier élément */
- const char *name; /* Nom du symbole trouvé */
- GBinFormat *base; /* Version basique du format */
- vmpa2t addr; /* Localisation d'une routine */
- GBinSymbol *symbol; /* Nouveau symbole construit */
- char alt_name[6 + VMPA_MAX_LEN]; /* Nom abstrait de substitution*/
- virt_t final_virt; /* Adresse virtuelle retenue */
- mrange_t range; /* Couverture mémoire associée */
- GBinRoutine *routine; /* Nouvelle routine trouvée */
-
- result = read_elf_symbol(format, iter, &sym);
- if (!result) goto geslp_done;
-
- /* On rejette les symboles qui ne sont pas définis au sein du binaire */
-
- if (ELF_SYM(format, sym, st_shndx) == 0) goto geslp_done;
-
- /* Résolution précise d'adresse */
-
- virt = ELF_SYM(format, sym, st_value);
- if (virt == 0) goto geslp_done;
-
-
- /* TODO */
-
- //init_vmpa(&addr, VMPA_NO_PHYSICAL, ELF_SYM(format, sym, st_value));
-
-
- //init_mrange(&range, &addr, 0);
-
-
- /* Première ébauche de nom */
-
- g_elf_loading_get_internal_info(loading, &section, &use_virt, &strtab, &has_strtab, &first);
-
- if (!has_strtab)
- name = NULL;
-
- else
- name = get_elf_symbol_name(format, section, strtab,
- ((*iter - first) / ELF_SIZEOF_SYM(format)) - 1);
-
- /* Traitements particuliers */
-
- base = G_BIN_FORMAT(format);
-
- switch (ELF_ST_TYPE(format, sym))
- {
- case STT_OBJECT:
-
- /* Ajustement de la position */
-
- if (!g_exe_format_translate_address_into_vmpa(G_EXE_FORMAT(format), virt, &addr))
- {
- symbol = NULL;
- break;
- }
-
- /* Création d'un nom unique ? */
-
- if (name == NULL)
- {
- strcpy(alt_name, "obj_");
-
- if (use_virt)
- vmpa2_virt_to_string(&addr, MDS_UNDEFINED, alt_name + 4, NULL);
- else
- vmpa2_phys_to_string(&addr, MDS_UNDEFINED, alt_name + 4, NULL);
-
- name = alt_name;
-
- }
-
-
- /* TODO */
-
- symbol = NULL;
-
-
- break;
-
- case STT_FUNC:
-
- /* Ajustement de la position */
-
- if (ELF_HDR(format, format->header, e_machine) == EM_ARM)
- final_virt = virt & ~0x1;
- else
- final_virt = virt;
-
- if (!g_exe_format_translate_address_into_vmpa(G_EXE_FORMAT(format), final_virt, &addr))
- {
- symbol = NULL;
- break;
- }
-
- init_mrange(&range, &addr, ELF_SYM(format, sym, st_size));
-
- /* Création d'un nom unique ? */
-
- if (name == NULL)
- {
- strcpy(alt_name, "func_");
-
- if (use_virt)
- vmpa2_virt_to_string(&addr, MDS_UNDEFINED, alt_name + 5, NULL);
- else
- vmpa2_phys_to_string(&addr, MDS_UNDEFINED, alt_name + 5, NULL);
-
- name = alt_name;
-
- }
-
- /* Routine */
-
- routine = try_to_demangle_routine(name);
- symbol = G_BIN_SYMBOL(routine);
-
- g_binary_symbol_set_range(symbol, &range);
-
- /* Comptabilisation pour le désassemblage brut */
-
- g_binary_format_register_code_point(G_BIN_FORMAT(format), virt, false);
-
- break;
-
- default:
- symbol = NULL;
- break;
-
- }
-
- if (symbol != NULL)
- g_binary_format_add_symbol(base, symbol);
-
- geslp_done:
-
- return result;
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = description de l'exécutable à compléter. *
-* gid = groupe de travail impliqué. *
- status = barre de statut à tenir informée. *
-* *
-* Description : Charge tous les symboles internes possibles. *
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static bool load_elf_internal_symbols(GElfFormat *format, wgroup_id_t gid, GtkStatusStack *status)
-{
- bool result; /* Bilan à retourner */
- bool no_name; /* Choix de construction de nom*/
- activity_id_t msg; /* Message de progression */
- GWorkQueue *queue; /* Gestionnaire de différés */
- elf_shdr *dynsym_sections; /* Groupe de sections trouvées */
- size_t count; /* Quantité de données */
- elf_shdr *symtab_sections; /* Groupe de sections trouvées */
- size_t i; /* Boucle de parcours */
-
- result = true;
-
- /* Charge tous les symboles définis dans une section */
- void add_all_symbols_from_section(const elf_shdr *section, bool use_virt, GWorkQueue *wq, activity_id_t id)
- {
- phys_t start; /* Début de la zone à traiter */
- phys_t size; /* Taille de cette même zone */
- phys_t sym_size; /* Taille de chaque symbole lu */
- guint runs_count; /* Qté d'exécutions parallèles */
- phys_t run_size; /* Volume réparti par exécution*/
- guint i; /* Boucle de parcours */
- phys_t begin; /* Début de zone de traitement */
- phys_t end; /* Fin d'un zone de traitement */
- GElfLoading *loading; /* Tâche de chargement à lancer*/
-
- get_elf_section_content(format, section, &start, &size, NULL);
-
- sym_size = ELF_SIZEOF_SYM(format);
-
- runs_count = g_get_num_processors();
-
- run_size = size / (sym_size * runs_count);
-
- gtk_status_stack_extend_activity(status, id, size / sym_size);
-
- for (i = 0; i < runs_count; i++)
- {
- begin = start + i * run_size * sym_size;
-
- if ((i + 1) == runs_count)
- end = start + size;
- else
- end = begin + run_size * sym_size;
-
- loading = g_elf_loading_new(format, section, use_virt, start, begin, end,
- id, do_elf_internal_symbol_loading);
-
- g_work_queue_schedule_work(wq, G_DELAYED_WORK(loading), gid);
-
- }
-
- }
-
- if (!g_generic_config_get_value(get_main_configuration(), MPK_FORMAT_NO_NAME, &no_name))
- return false;
-
- msg = gtk_status_stack_add_activity(status, _("Loading internal symbols..."), 0);
-
- queue = get_work_queue();
-
- if (find_elf_sections_by_type(format, SHT_DYNSYM, &dynsym_sections, &count))
- for (i = 0; i < count; i++)
- add_all_symbols_from_section(&dynsym_sections[i], no_name, queue, msg);
-
- if (find_elf_sections_by_type(format, SHT_SYMTAB, &symtab_sections, &count))
- for (i = 0; i < count; i++)
- add_all_symbols_from_section(&symtab_sections[i], no_name, queue, msg);
-
- g_work_queue_wait_for_completion(queue, gid);
-
- gtk_status_stack_remove_activity(status, msg);
-
- if (dynsym_sections != NULL) free(dynsym_sections);
- if (symtab_sections != NULL) free(symtab_sections);
-
- return result;
-
-}
-
-
-
-/* ---------------------------------------------------------------------------------- */
-/* DETAIL DES SYMBOLES EXTERNES */
-/* ---------------------------------------------------------------------------------- */
-
-
-/******************************************************************************
-* *
-* Paramètres : format = informations chargées à consulter. *
-* dynamic = section de type SHT_DYNAMIC. *
-* type = sorte d'élément recherché. *
-* item = élément retrouvé dans la section. [OUT] *
-* *
-* Description : Retrouve un élément donné dans la section dynamique. *
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static bool find_elf_dynamic_item(const GElfFormat *format, const elf_shdr *section, int32_t type, elf_dyn *item)
-{
- bool result; /* Bilan à retourner */
- const GBinContent *content; /* Contenu binaire à lire */
- phys_t pos; /* Position de lecture */
- vmpa2t tmp; /* Position écrasable */
- int32_t tag32; /* Type de l'entrée (32 bits) */
- int64_t tag64; /* Type de l'entrée (64 bits) */
-
- result = true;
-
- content = G_BIN_FORMAT(format)->content;
-
- for (pos = ELF_SHDR(format, *section, sh_offset);
- result;
- pos += ELF_SIZEOF_DYN(format))
- {
- init_vmpa(&tmp, pos, VMPA_NO_VIRTUAL);
-
- if (format->is_32b)
- {
- result = g_binary_content_read_s32(content, &tmp, format->endian, &tag32);
- if (tag32 == type) break;
- }
- else
- {
- result = g_binary_content_read_s64(content, &tmp, format->endian, &tag64);
- if (tag64 == type) break;
- }
-
- }
-
- if (result)
- {
- init_vmpa(&tmp, pos, VMPA_NO_VIRTUAL);
-
- if (format->is_32b)
- {
- result = g_binary_content_read_s32(content, &tmp, format->endian, &item->dyn32.d_tag);
- result &= g_binary_content_read_s32(content, &tmp, format->endian, &item->dyn32.d_un.d_val);
- }
- else
- {
- result = g_binary_content_read_s64(content, &tmp, format->endian, &item->dyn64.d_tag);
- result &= g_binary_content_read_s64(content, &tmp, format->endian, &item->dyn64.d_un.d_val);
- }
-
- }
-
- return result;
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = informations chargées à consulter. *
-* dynamic = section de type SHT_DYNAMIC. *
-* *
-* Description : Charge tous les éléments dynamiques externes possibles. *
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static bool load_elf_external_symbols(GElfFormat *format, const elf_shdr *section)
-{
- bool result; /* Bilan à retourner */
-
- elf_dyn item; /* Elément dynamique */
- elf_shdr relxxx; /* Section .rel.xxx trouvée */
- elf_shdr dynsym; /* Section .dynsym trouvée */
- elf_shdr dynstr; /* Section .dynstr trouvée */
- elf_shdr plt; /* Section .plt trouvée */
-
- result = true;
-
-
-
-
-
-
- /* Section .rel.plt */
- if (find_elf_dynamic_item(format, section, DT_JMPREL, &item))
- {
- result &= find_elf_section_by_virtual_address(format, ELF_DYN(format, item, d_un.d_ptr), &relxxx);
-
- if (result)
- result = find_elf_section_by_index(format, ELF_SHDR(format, relxxx, sh_link), &dynsym);
-
- if (result)
- result = find_elf_section_by_index(format, ELF_SHDR(format, dynsym, sh_link), &dynstr);
-
- if (result)
- switch (ELF_HDR(format, format->header, e_machine))
- {
- case EM_ARM:
- result = load_elf_arm_relocated_symbols(format, &relxxx, &dynsym, &dynstr);
- break;
-
- case EM_386:
- result = load_elf_x86_relocated_symbols(format, &relxxx, &dynsym, &dynstr);
- break;
-
- default:
- break;
-
- }
-
- }
-
-#if 0
-
- /* Entrées équivalentes dans le binaire */
- if (find_elf_dynamic_item(format, section, DT_SYMTAB, &item))
- {
- result &= find_elf_section_by_virtual_address(format, ELF_DYN(format, item, d_un.d_ptr), &dynsym);
-
- if (result)
- result = find_elf_section_by_index(format, ELF_SHDR(format, dynsym, sh_link), &dynstr);
-
- if (result)
- switch (g_exe_format_get_target_machine(G_EXE_FORMAT(format)))
- {
- case FTM_MIPS:
- //result = find_elf_mips_dynamic_symbols(format, &dynsym, &dynstr);
- break;
-
- case FTM_386:
-
- if (find_elf_dynamic_item(format, section, DT_JMPREL, &item))
- {
- result &= find_elf_section_by_virtual_address(format, ELF_DYN(format, item, d_un.d_ptr), &relxxx);
-
-
- printf("VMA :: 0x%08llx\n", ELF_DYN(format, item, d_un.d_ptr));
-
-
-
- if (result)
- result = find_elf_section_by_index(format, ELF_SHDR(format, relxxx, sh_info), &plt);
-
- if (result)
- result = find_elf_x86_dynamic_symbols(format, &plt, &relxxx, &dynsym, &dynstr);
-
- }
-
- break;
-
- default:
- break;
-
- }
-
- }
-
-#endif
-
- return result;
-
-}