summaryrefslogtreecommitdiff
path: root/plugins/dwarf/info.c
diff options
context:
space:
mode:
Diffstat (limited to 'plugins/dwarf/info.c')
-rw-r--r--plugins/dwarf/info.c872
1 files changed, 138 insertions, 734 deletions
diff --git a/plugins/dwarf/info.c b/plugins/dwarf/info.c
index 432280e..7a2be44 100644
--- a/plugins/dwarf/info.c
+++ b/plugins/dwarf/info.c
@@ -2,7 +2,7 @@
/* Chrysalide - Outil d'analyse de fichiers binaires
* info.c - lecture des informations principales du format DWARF
*
- * Copyright (C) 2008-2017 Cyrille Bagard
+ * Copyright (C) 2008-2018 Cyrille Bagard
*
* This file is part of Chrysalide.
*
@@ -24,215 +24,43 @@
#include "info.h"
-#include "die.h"
-#include "dwarf-int.h"
-#include "../debuggable-int.h"
-
-
+#include <i18n.h>
+#include <analysis/contents/restricted.h>
+#include <core/nproc.h>
+#include <glibext/seq.h>
+#include <core/global.h>
-
-static bool extract_dies_from_debug_information(GDwarfFormat *format, vmpa2t *pos, SourceEndian endian, const dw_compil_unit_header *header, dw_die *parent, dw_die **die);
+#include "die.h"
+#include "format-int.h"
+#include "utils.h"
+#define RANGE_ALLOC_BLOCK 100
-/******************************************************************************
-* *
-* Paramètres : format = informations de débogage DWARF à compléter. *
-* *
-* Description : Charge les informations depuis une section ".debug_info". *
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-bool load_dwarf_debug_information(GDwarfFormat *format)
+/* Rassemblement des informations utiles */
+typedef struct _work_data
{
- bool result; /* Bilan à renvoyer */
-
-
-
- mrange_t range; /* Couverture d'une section */
- vmpa2t end;
- vmpa2t iter; /* Tête de lecture mouvante */
-
- dw_compil_unit_header header;
- dw_die *die;
-
-
-
- result = g_exe_format_get_section_range_by_name(G_DBG_FORMAT(format)->executable, ".debug_info", &range);
- if (!result) goto lddi_exit;
-
- copy_vmpa(&iter, get_mrange_addr(&range));
-
-
- printf("[%d] Passage :: 0x%08llx 0x%08llx\n",
- result,
- (unsigned long long)range.addr.physical,
- (unsigned long long)range.addr.virtual);
-
- compute_mrange_end_addr(&range, &end);
-
- while (result)
- {
- /* Si il n'y a plus rien à lire dans la section... */
- if (cmp_vmpa(&iter, &end) >= 0) break;
-
-
- printf("========================================================================\n");
- printf("========================================================================\n");
- printf("========================================================================\n");
- printf("========================================================================\n");
- printf("\n");
- printf("HEADER START :: 0x%x\n", (unsigned int)iter.physical);
-
-
- result = read_dwarf_compil_unit_header(G_BIN_FORMAT(format)->content, &iter,
- SRE_LITTLE /* FIXME */, &header);
- if (!result) break;
-
- printf("[%d] header :: addr size=%hhu\n", result, header.address_size);
-
-
- result = extract_dies_from_debug_information(format, &iter,
- SRE_LITTLE /* FIXME */, &header,
- NULL, &die);
-
-
-
- }
+ GDwarfFormat *format; /* Format à manipuler */
+ mrange_t *ranges; /* Espace des DIE à charger */
+} work_data;
- format->info_die = die;
-
-
- lddi_exit:
-
- return result;
-
-}
+/* Procède au chargement d'un DIE de la section debug_info. */
+static bool extract_dies_from_debug_info(const work_data *, size_t, GtkStatusStack *, activity_id_t);
/******************************************************************************
* *
* Paramètres : format = informations de débogage DWARF à compléter. *
-* pos = position de début de lecture. [OUT] *
-* endian = boutisme reconnu dans le format. *
-* header = en-tête de description de l'unité à traiter. *
-* parent = entrée parent de rattachement ou NULL si racine. *
-* die = emplacement de stockage de l'entrée. [OUT] *
-* *
-* Description : Procède à la lecture de l'en-tête d'un contenu binaire DWARF.*
-* *
-* Retour : Bilan de l'opération. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static bool extract_dies_from_debug_information(GDwarfFormat *format, vmpa2t *pos, SourceEndian endian, const dw_compil_unit_header *header, dw_die *parent, dw_die **die)
-{
- bool result; /* Bilan à faire remonter */
- dw_die *child; /* Entrée subordonnée à charger*/
-
- printf("==================================\n");
- printf("=== version : 0x%hx\n", header->version);
- printf("=== offset abbrev : 0x%llx\n", (unsigned long long)header->debug_abbrev_offset);
- printf("==================================\n");
-
-
- phys_t start = 0x1039;
-
- printf("start :: 0x%x\n", (unsigned int)(pos->physical - start));
- printf("start :: 0x%x\n", (unsigned int)(0x0 + pos->physical));
-
- result = build_dwarf_die(format, pos, SRE_LITTLE /* FIXME */, header, die);
- if (*die == NULL) return result;
-
- if (parent != NULL)
- dw_die_append_child(parent, *die);
-
- if (dw_die_has_children(*die))
- {
- printf("<<<< children >>>>\n");
-
- printf("next :: 0x%x\n", (unsigned int)(pos->physical - start));
-
- while (result)
- {
- result = extract_dies_from_debug_information(format, pos, endian, header, *die, &child);
-
- if (!result)
- delete_dwarf_die(*die);
-
- /* Entrée avec un code nul -> fin */
- if (child == NULL) break;
-
- }
-
- }
-
- return result;
-
-}
-
-
-
-
-
-
-
-#if 0
-#include <malloc.h>
-#include <string.h>
+* gid = groupe de travail impliqué. *
+ status = barre de statut à tenir informée. *
-
-#include "abbrev.h"
-#include "dwarf-int.h"
-#include "utils.h"
-
-
-/* Informations utiles d'une unité de compilation */
-typedef struct _compil_unit
-{
- off_t startpos; /* Position de début d'unité */
- off_t endpos; /* Position d'unité suivante */
-
- off_t offset; /* Position dans les abréviat° */
- uint8_t ptrsize; /* Taille des adresses mémoire */
-
-} compil_unit;
-
-
-
-#define _(str) str
-
-
-/* Procède à la lecture d'une unité de compilation. */
-bool read_dwarf_compilation_unit(dwarf_format *, off_t *, compil_unit *);
-
-/* Récupère toutes les déclarations DWARF utiles trouvées. */
-bool parse_dwarf_compilation_unit(dwarf_format *, off_t *, const compil_unit *);
-
-/* Enregistre toutes les déclarations de fonction trouvées. */
-dw_dbg_function *look_for_dwarf_subprograms(dwarf_format *, const dw_abbrev *, off_t *, const compil_unit *);
-
-/* Obtient la description humaine d'un type. */
-char *resolve_dwarf_function_type(dwarf_format *, const dw_abbrev *, const off_t *, const compil_unit *);
-
-
-
-
-/******************************************************************************
* *
-* Paramètres : format = informations de débogage à compléter. *
-* *
-* Description : Charge les informations trouvées dans un DWARF. *
+* Description : Charge les informations depuis une section ".debug_info". *
* *
* Retour : Bilan de l'opération. *
* *
@@ -240,614 +68,190 @@ char *resolve_dwarf_function_type(dwarf_format *, const dw_abbrev *, const off_t
* *
******************************************************************************/
-bool load_dwarf_information(dwarf_format *format)
+bool load_dwarf_debug_information(GDwarfFormat *format, wgroup_id_t gid, GtkStatusStack *status)
{
bool result; /* Bilan à renvoyer */
-
-
-
-
- off_t offset;
- off_t start;
- off_t size;
-
- bool test;
-
- int i;
-
-
- compil_unit cu;
-
-
-
- result = true;
-
- test = find_exe_section(DBG_FORMAT(format)->e_format, ".debug_info", &start, &size, NULL);
-
- offset = start;
-
-
- printf(" -> offset=%d size=%d\n", offset, size);
-
-
-
- for (i = 0; i < size; i++)
- {
- if (i % 25 == 0) printf("\n");
- printf("0x%02hhx ", DBG_FORMAT(format)->content[offset + i]);
- }
-
- printf("\n");
-
-
-
- while (offset < (start + size) && result)
- {
- printf("-------------\n");
-
- result = read_dwarf_compilation_unit(format, &offset, &cu);
-
- if (result)
- parse_dwarf_compilation_unit(format, &offset, &cu);
-
- }
-
-
- printf("##############\nRegistered functions:\n");
-
- for (i = 0; i < format->dbg_fc_count; i++)
- printf(" > [0x%08llx] %s\n", format->dbg_functions[i]->low_pc, format->dbg_functions[i]->prototype);
-
- return result;
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = informations de débogage à effacer. *
-* *
-* Description : Décharge les informations trouvées dans un DWARF. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-void unload_dwarf_information(dwarf_format *format)
-{
-
-
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = informations de débogage à compléter. *
-* pos = tête de lecture à mettre à jour. [OUT] *
-* cu = unité de compilation lue. [OUT] *
-* *
-* Description : Procède à la lecture d'une unité de compilation. *
-* *
-* Retour : true en cas de succès de la lecture, false sinon. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-bool read_dwarf_compilation_unit(dwarf_format *format, off_t *pos, compil_unit *cu)
-{
- off_t ulength; /* Taille de l'unité */
- uint16_t version; /* Version du format DWARF */
-
- cu->startpos = *pos;
-
- if (!read_unit_length(format, pos, &ulength))
- return false;
-
- cu->endpos = *pos + ulength;
-
- if (!read_uhalf(format, pos, &version))
- return false;
-
- if (version > 3) return false;
-
- if (!read_abbrev_offset(format, pos, &cu->offset))
- return false;
-
- if (!read_address_size(format, pos, &cu->ptrsize))
- return false;
-
- return true;
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = informations de débogage à compléter. *
-* pos = tête de lecture à mettre à jour. [OUT] *
-* cu = unité de compilation courante. *
-* *
-* Description : Récupère toutes les déclarations DWARF utiles trouvées. *
-* *
-* Retour : true en cas de succès de la lecture, false sinon. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-bool parse_dwarf_compilation_unit(dwarf_format *format, off_t *pos, const compil_unit *cu)
-{
- bool result; /* Bilan à retourner */
- const dw_abbrev *abbrev; /* Abréviation rencontrée */
- dw_dbg_function *function; /* Nouvelle fonction lue */
-
-
-
- result = true;
-
- while (*pos < cu->endpos && result)
+ GExeFormat *exe; /* Exécutable associé */
+ mrange_t range; /* Couverture d'une section */
+ GBinContent *content; /* Contenu binaire à lire */
+ GBinContent *restricted; /* Limitation des traitements */
+ vmpa2t stop; /* Point d'arrivée à atteindre */
+ mrange_t *ranges; /* Séquences de zones à traiter*/
+ size_t count; /* Nombre de ces séquences */
+ size_t allocated; /* Quantité d'allocations */
+ SourceEndian endian; /* Boutisme du format parent */
+ vmpa2t iter; /* Tête de lecture mouvante */
+ vmpa2t start; /* Sauvegarde de position */
+ dw_compil_unit_header header; /* Unité à cerner puis traiter */
+ vmpa2t next; /* Départ de l'unité suivante */
+ phys_t size; /* Taille complète d'une unité */
+ work_data data; /* Données à communiquer */
+ guint runs_count; /* Qté d'exécutions parallèles */
+ size_t run_size; /* Volume réparti par exécution*/
+ GWorkQueue *queue; /* Gestionnaire de différés */
+ activity_id_t msg; /* Message de progression */
+ guint i; /* Boucle de parcours */
+ size_t begin; /* Début de bloc de traitement */
+ size_t end; /* Fin d'un bloc de traitement */
+ GSeqWork *work; /* Tâche de chargement à lancer*/
+
+ exe = G_DBG_FORMAT(format)->executable;
+
+ result = g_exe_format_get_section_range_by_name(exe, ".debug_info", &range);
+
+ if (result)
{
+ content = G_BIN_FORMAT(format)->content;
+ restricted = g_restricted_content_new(content, &range);
- printf(" =+> Cur :: 0x%02hhx 0x%02hhx 0x%02hhx 0x%02hhx 0x%02hhx\n",
- DBG_FORMAT(format)->content[*pos],
- DBG_FORMAT(format)->content[*pos + 1],
- DBG_FORMAT(format)->content[*pos + 2],
- DBG_FORMAT(format)->content[*pos + 3],
- DBG_FORMAT(format)->content[*pos + 4]);
-
-
-
- abbrev = find_dwarf_abbreviations(format, &cu->offset, pos);
-
- if (abbrev == NULL)
- break;
+ compute_mrange_end_addr(&range, &stop);
+ /* Constitution des zones de travail */
+ ranges = NULL;
+ count = 0;
+ allocated = 0;
- printf(" --> %p\n", abbrev);
+ endian = g_binary_format_get_endianness(G_BIN_FORMAT(exe));
- printf(" == 0x%02x (matched ? %d)\n", abbrev->tag, abbrev->tag == DWT_SUBPROGRAM);
-
-
-
- switch (abbrev->tag)
+ for (copy_vmpa(&iter, get_mrange_addr(&range));
+ result && cmp_vmpa(&iter, &stop) < 0;
+ copy_vmpa(&iter, &next))
{
- case DWT_SUBPROGRAM:
- function = look_for_dwarf_subprograms(format, abbrev, pos, cu);
-
- if (function != NULL)
- {
- format->dbg_functions = (dw_dbg_function **)realloc(format->dbg_functions, ++format->dbg_fc_count * sizeof(dw_dbg_function *));
- format->dbg_functions[format->dbg_fc_count - 1] = function;
- }
- else result = false;
-
- break;
-
- default:
- break;
-
- }
-
-
-
+ copy_vmpa(&start, &iter);
+ result = read_dwarf_compil_unit_header(restricted, &iter, endian, &header, &next);
+ if (!result) break;
+ if (count == allocated)
+ {
+ allocated += RANGE_ALLOC_BLOCK;
+ ranges = realloc(ranges, allocated * sizeof(mrange_t));
+ }
+ size = compute_vmpa_diff(&start, &next);
+ init_mrange(&ranges[count++], &start, size);
+ }
+ if (!result)
+ goto exit;
+ /* Préparation des réceptacles */
+ format->info = calloc(count, sizeof(dw_die *));
+ format->info_count = count;
- if (!skip_dwarf_abbrev(format, pos, abbrev))
- printf("error skipping :(\n");
-
-
- }
-
-
- printf(" =+> Next :: 0x%02hhx 0x%02hhx 0x%02hhx 0x%02hhx 0x%02hhx\n",
- DBG_FORMAT(format)->content[*pos],
- DBG_FORMAT(format)->content[*pos + 1],
- DBG_FORMAT(format)->content[*pos + 2],
- DBG_FORMAT(format)->content[*pos + 3],
- DBG_FORMAT(format)->content[*pos + 4]);
-
-
-
- return result;
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : format = informations de débogage à compléter. *
-* abbrev = abréviation trouvée à traiter. *
-* pos = tête de lecture à mettre à jour. [OUT] *
-* cu = unité de compilation courante. *
-* *
-* Description : Enregistre toutes les déclarations de fonction trouvées. *
-* *
-* Retour : Fonction chargée en mémoire ou NULL en cas d'échec. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-dw_dbg_function *look_for_dwarf_subprograms(dwarf_format *format, const dw_abbrev *abbrev, off_t *pos, const compil_unit *cu)
-{
- dw_dbg_function *result; /* Structure à retourner */
- uint32_t type_pos; /* Décalage p/r au pt courant */
- off_t subpos; /* Sous-position de lecture #1 */
- const dw_abbrev *subabbrev; /* Abréviation fille à lire */
- char *retstr; /* Elément du prototype */
- char *prototype; /* Stockage temporaire */
- size_t proto_len; /* Taille du prototype */
- bool is_pointer; /* Mémorise le type 'pointeur' */
- uint64_t index; /* Index de la fonction */
- bool first_arg; /* Marque le 1er argument */
- off_t subpos2; /* Sous-position de lecture #2 */
- const dw_abbrev *subabbrev2; /* Abréviation fille à lire #2 */
-
- result = (dw_dbg_function *)calloc(1, sizeof(dw_dbg_function));
-
- /* Récupération des informations de base */
-
- if (!read_dwarf_abbrev_attribute(format, pos, false, abbrev, DWA_NAME, &result->name))
- goto lfds_error;
-
- if (!read_dwarf_abbrev_attribute(format, pos, false, abbrev, DWA_LOW_PC, &result->low_pc))
- goto lfds_error;
-
- if (!read_dwarf_abbrev_attribute(format, pos, false, abbrev, DWA_HIGH_PC, &result->high_pc))
- goto lfds_error;
-
- /* Type de la fonction */
-
- if (test_dwarf_abbrev_attribute(abbrev, DWA_TYPE))
- {
- if (!read_dwarf_abbrev_attribute(format, pos, false, abbrev, DWA_TYPE, &type_pos))
- goto lfds_error;
-
- subpos = cu->startpos + type_pos;
-
- subabbrev = find_dwarf_abbreviations(format, &cu->offset, &subpos);
-
- retstr = resolve_dwarf_function_type(format, subabbrev, &subpos, cu);
-
- }
- else retstr = strdup("void");
-
- if (retstr == NULL)
- {
- proto_len = 3;
- prototype = (char *)calloc(proto_len + 1, sizeof(char));
- strcat(prototype, "???");
-
- is_pointer = false;
-
- }
- else
- {
- proto_len = strlen(retstr);
- prototype = (char *)calloc(proto_len + 1, sizeof(char));
- strcat(prototype, retstr);
-
- is_pointer = (retstr[strlen(retstr) - 1] == '*');
-
- free(retstr);
-
- }
-
- /* On saute l'abréviation de la déclaration de fonction... */
-
- subpos = *pos;
+ data.format = format;
+ data.ranges = ranges;
- if (!read_uleb128(format, &subpos, &index, true))
- goto lfds_error;
+ /* Lancement des travaux */
- if (!skip_dwarf_abbrev(format, &subpos, abbrev))
- goto lfds_error;
+ runs_count = get_max_online_threads();
- /* Lecture des différents arguments */
+ run_size = count / runs_count;
- proto_len += (!is_pointer ? 1 : 0) + strlen(result->name) + 1;
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- if (!is_pointer) strcat(prototype, " ");
- strcat(prototype, result->name);
- strcat(prototype, "(");
+ queue = get_work_queue();
- first_arg = true;
+ msg = gtk_status_stack_add_activity(status, _("Loading all information from the .debug_info section..."),
+ get_mrange_length(&range));
- while (1)
- {
- subabbrev = find_dwarf_abbreviations(format, &cu->offset, &subpos);
- if (subabbrev == NULL) goto exit_loop;
-
- switch (subabbrev->tag)
+ for (i = 0; i < runs_count; i++)
{
- case DWT_UNSPECIFIED_PARAMETERS:
-
- /* Virgule de séparation */
-
- if (first_arg) first_arg = false;
- else
- {
- proto_len += 2;
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- strcat(prototype, ", ");
- }
-
- /* Marque de l'absence de type */
-
- proto_len += 3;
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- strcat(prototype, "...");
-
- break;
-
- case DWT_FORMAL_PARAMETER:
-
- if (!read_dwarf_abbrev_attribute(format, &subpos, false, subabbrev, DWA_TYPE, &type_pos))
- goto lfds_error;
-
- subpos2 = cu->startpos + type_pos;
-
- subabbrev2 = find_dwarf_abbreviations(format, &cu->offset, &subpos2);
-
- retstr = resolve_dwarf_function_type(format, subabbrev2, &subpos2, cu);
-
- /* Virgule de séparation */
-
- if (first_arg) first_arg = false;
- else
- {
- proto_len += 2;
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- strcat(prototype, ", ");
- }
+ begin = i * run_size;
- /* Type de l'argument */
+ if ((i + 1) == runs_count)
+ end = count;
+ else
+ end = begin + run_size;
- if (retstr == NULL)
- {
- proto_len += 3;
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- strcat(prototype, "???");
+ work = g_seq_work_new_boolean(&data, begin, end, msg,
+ (seq_work_bool_cb)extract_dies_from_debug_info, &result);
- is_pointer = false;
+ g_work_queue_schedule_work(queue, G_DELAYED_WORK(work), gid);
- }
- else
- {
- proto_len += strlen(retstr);
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- strcat(prototype, retstr);
-
- is_pointer = (retstr[strlen(retstr) - 1] == '*');
-
- free(retstr);
-
- }
-
- /* Nom de l'argument */
-
- if (test_dwarf_abbrev_attribute(abbrev, DWA_NAME))
- {
- if (!read_dwarf_abbrev_attribute(format, &subpos, false, subabbrev, DWA_NAME, &retstr))
- goto lfds_error;
- }
- else retstr = strdup(_("[no name]"));
-
- if (retstr != NULL)
- {
- proto_len += strlen(retstr) + (!is_pointer ? 1 : 0) + 1;
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- if (!is_pointer) strcat(prototype, " ");
- strcat(prototype, retstr);
-
- free(retstr);
+ }
- }
+ g_work_queue_wait_for_completion(queue, gid);
- break;
+ gtk_status_stack_remove_activity(status, msg);
- default:
- goto exit_loop;
- break;
+ exit:
- }
+ if (ranges != NULL)
+ free(ranges);
- if (!skip_dwarf_abbrev(format, &subpos, subabbrev))
- goto lfds_error;
+ g_object_unref(G_OBJECT(restricted));
}
- exit_loop:
-
- proto_len += 1;
- prototype = (char *)realloc(prototype, (proto_len + 1) * sizeof(char));
- strcat(prototype, ")");
-
- result->prototype = prototype;
-
return result;
- lfds_error:
-
- if (result->name != NULL) free(result->name);
- if (result->prototype != NULL) free(result->prototype);
-
- free(result);
-
- return NULL;
-
}
/******************************************************************************
* *
-* Paramètres : format = informations de débogage à compléter. *
-* abbrev = abréviation associée au type. *
-* pos = tête de lecture à avoir sous le coude. *
-* cu = unité de compilation courante. *
+* Paramètres : data = ensemble d'informations utiles à l'opération. *
+* i = indice des éléments à traiter. *
+* status = barre de statut à tenir informée. *
+* id = identifiant du message affiché à l'utilisateur. *
* *
-* Description : Obtient la description humaine d'un type. *
+* Description : Procède au chargement d'un DIE de la section debug_info. *
* *
-* Retour : Chaîne de caractères en cas de succès, NULL sinon. *
+* Retour : Bilan de l'opération. *
* *
* Remarques : - *
* *
******************************************************************************/
-char *resolve_dwarf_function_type(dwarf_format *format, const dw_abbrev *abbrev, const off_t *pos, const compil_unit *cu)
+static bool extract_dies_from_debug_info(const work_data *data, size_t i, GtkStatusStack *status, activity_id_t id)
{
- char *result; /* Description à retourner */
- off_t oldpos; /* Conservation de l'indice */
- uint32_t type_pos; /* Sous-type détecté */
- uint64_t index; /* Indice de l'abréviation... */
- const dw_abbrev *subabbrev; /* ... et abréviation associée */
- size_t len; /* Longeur d'un résultat */
-
- result = NULL;
- oldpos = *pos;
-
- switch (abbrev->tag)
- {
- /* 0x04 */
- case DWT_ENUMERATION_TYPE:
-
- oldpos = *pos;
- read_dwarf_abbrev_attribute(format, &oldpos, true /* ??? */, abbrev, DWA_NAME, &result);
-
- if (result != NULL)
- {
- len = strlen(result);
-
- result = (char *)realloc(result, (strlen("enum ") + len + 1) * sizeof(char));
- memmove(&result[strlen("enum ")], result, len);
- memcpy(result, "enum ", strlen("enum "));
-
- }
-
- break;
-
- /* 0x0f */
- case DWT_POINTER_TYPE:
-
- if (test_dwarf_abbrev_attribute(abbrev, DWA_TYPE))
- {
- if (!read_dwarf_abbrev_attribute(format, &oldpos, true, abbrev, DWA_TYPE, &type_pos))
- return NULL;
-
- oldpos = cu->startpos + type_pos;
-
- subabbrev = find_dwarf_abbreviations(format, &cu->offset, &oldpos);
-
- result = resolve_dwarf_function_type(format, subabbrev, &oldpos, cu);
-
- }
- else result = strdup("void");
-
- if (result != NULL)
- {
- len = strlen(result);
-
- if (result[len - 1] == '*')
- {
- result = (char *)realloc(result, (len + 2) * sizeof(char));
- result[len] = '*';
- }
- else
- {
- result = (char *)realloc(result, (len + 3) * sizeof(char));
- strcat(result, " *");
- }
-
- }
-
- break;
-
- /* 0x13 */
- case DWT_STRUCTURE_TYPE:
-
- oldpos = *pos;
- read_dwarf_abbrev_attribute(format, &oldpos, true /* ??? */, abbrev, DWA_NAME, &result);
-
- if (result != NULL)
- {
- len = strlen(result);
-
- result = (char *)realloc(result, (strlen("struct ") + len + 1) * sizeof(char));
- memmove(&result[strlen("struct ")], result, len);
- memcpy(result, "struct ", strlen("struct "));
-
- }
-
- break;
-
- /* 0x16 */
- case DWT_TYPEDEF:
- oldpos = *pos;
- read_dwarf_abbrev_attribute(format, &oldpos, true /* ??? */, abbrev, DWA_NAME, &result);
- break;
-
- /* 0x24 */
- case DWT_BASE_TYPE:
- oldpos = *pos;
- read_dwarf_abbrev_attribute(format, &oldpos, true /* ??? */, abbrev, DWA_NAME, &result);
- break;
-
- /* 0x26 */
- case DWT_CONST_TYPE:
-
-
-
- if (read_dwarf_abbrev_attribute(format, &oldpos, true, abbrev, DWA_TYPE, &type_pos))
- printf(" ## sub type :: 0x%08x\n", type_pos);
- else printf(" error: no type\n");
-
- oldpos = cu->startpos + type_pos;
-
-
-
-
+ bool result; /* Bilan à retourner */
+ GDwarfFormat *format; /* Format en cours d'analyse */
+ GBinContent *content; /* Contenu binaire à lire */
+ GExeFormat *exe; /* Exécutable associé */
+ SourceEndian endian; /* Boutisme du format parent */
+ vmpa2t iter; /* Tête de lecture mouvante */
+ dw_compil_unit_header header; /* Unité à cerner puis traiter */
+ vmpa2t next; /* Départ de l'unité suivante */
+ dw_abbrev_brotherhood *abbrevs; /* Série d'abréviations */
+ format = data->format;
- subabbrev = find_dwarf_abbreviations(format, &cu->offset, &oldpos);
- printf("subabbrev == %p\n", subabbrev);
+ /**
+ * Comme les informations peuvent aller taper ailleurs dans le binaire
+ * (par exemple dans la section debug_str pour certaine valeur, on ne peut
+ * pas restreinte le contenu au seul espace traité.
+ *
+ * L'en-tête lui même a déjà été valide, donc on ne s'embête pas à distinguer
+ * différents cas ici.
+ */
+ content = G_BIN_FORMAT(format)->content;
+ exe = G_DBG_FORMAT(format)->executable;
+ endian = g_binary_format_get_endianness(G_BIN_FORMAT(exe));
- result = resolve_dwarf_function_type(format, subabbrev, &oldpos, cu);
+ copy_vmpa(&iter, get_mrange_addr(&data->ranges[i]));
- if (result != NULL)
- {
- len = strlen(result);
+ result = read_dwarf_compil_unit_header(content, &iter, endian, &header, &next);
+ if (!result) goto exit;
- result = (char *)realloc(result, (strlen("const ") + len + 1) * sizeof(char));
- memmove(&result[strlen("const ")], result, len);
- memcpy(result, "const ", strlen("const "));
+ abbrevs = load_all_dwarf_abbreviations(format, &header);
+ if (abbrevs == NULL) goto exit;
- }
+ result = build_dwarf_die(format, content, &iter, &header, abbrevs, &format->info[i]);
- break;
+ free_all_dwarf_abbreviations(abbrevs);
- default:
- printf("### NOT HANDLED ### Tag :: 0x%02x\n", abbrev->tag);
- break;
+ gtk_status_stack_update_activity_value(status, id, get_mrange_length(&data->ranges[i]));
- }
+ exit:
return result;
}
-#endif