From 56549ed6632859db219d5434079ad94381293a0a Mon Sep 17 00:00:00 2001
From: Cyrille Bagard <nocbos@gmail.com>
Date: Fri, 9 Oct 2015 02:11:35 +0000
Subject: Deleted duplicated symbols to avoid zero-length areas.

git-svn-id: svn://svn.gna.org/svn/chrysalide/trunk@589 abbe820e-26c8-41b2-8c08-b7b2b41f8b0a
---
 ChangeLog                |  8 +++++++
 src/format/elf/elf.c     |  5 ++++
 src/format/elf/symbols.c | 13 ++++++++---
 src/format/format-int.h  |  3 +++
 src/format/format.c      | 59 ++++++++++++++++++++++++++++++++++++++++++++++++
 5 files changed, 85 insertions(+), 3 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 9f66771..43f4374 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+15-10-09  Cyrille Bagard <nocbos@gmail.com>
+
+	* src/format/elf/elf.c:
+	* src/format/elf/symbols.c:
+	* src/format/format.c:
+	* src/format/format-int.h:
+	Delete duplicated symbols to avoid zero-length areas.
+
 15-10-07  Cyrille Bagard <nocbos@gmail.com>
 
 	* src/analysis/disass/loop.c:
diff --git a/src/format/elf/elf.c b/src/format/elf/elf.c
index ea1f1ff..f485dbc 100644
--- a/src/format/elf/elf.c
+++ b/src/format/elf/elf.c
@@ -291,8 +291,13 @@ GBinFormat *g_elf_format_new(GBinContent *content, GExeFormat *parent)
     }
 
 
+    /* TODO : à bouger dans un épilogue commun */
+
     handle_binary_format(PGA_FORMAT_LOADER_LAST, G_BIN_FORMAT(result));
 
+    g_binary_format_delete_duplicated_symbols(G_BIN_FORMAT(result));
+
+    /* .... */
 
     return G_BIN_FORMAT(result);
 
diff --git a/src/format/elf/symbols.c b/src/format/elf/symbols.c
index 57d14cd..c3c2ecd 100644
--- a/src/format/elf/symbols.c
+++ b/src/format/elf/symbols.c
@@ -135,10 +135,17 @@ bool load_elf_symbols(GElfFormat *format)
 
     /* Symboles d'entrée, si encore besoin */
 
-    result &= load_all_elf_basic_entry_points(format);
+    /**
+     * Le tri en préalable
+     */
+
+
 
     g_binary_format_sort_symbols(G_BIN_FORMAT(format));
 
+
+    result &= load_all_elf_basic_entry_points(format);
+
     return result;
 
 }
@@ -563,8 +570,8 @@ static bool load_elf_internal_symbols(GElfFormat *format)
 
 
 
-            //init_mrange(&range, &addr, ELF_SYM(format, sym, st_size));
-            init_mrange(&range, &addr, 0);
+            init_mrange(&range, &addr, ELF_SYM(format, sym, st_size));
+            //init_mrange(&range, &addr, 0);
 
 
             /* Première ébauche de nom */
diff --git a/src/format/format-int.h b/src/format/format-int.h
index 70f1021..3e6ed9c 100644
--- a/src/format/format-int.h
+++ b/src/format/format-int.h
@@ -73,6 +73,9 @@ struct _GBinFormatClass
 /* Définit le contenu binaire à analyser. */
 void g_binary_format_set_content(GBinFormat *, GBinContent *);
 
+/* Supprime les éventuels doublons au sein des symboles. */
+void g_binary_format_delete_duplicated_symbols(GBinFormat *);
+
 
 
 #endif  /* _FORMAT_FORMAT_INT_H */
diff --git a/src/format/format.c b/src/format/format.c
index 74549bc..6128c9a 100644
--- a/src/format/format.c
+++ b/src/format/format.c
@@ -350,6 +350,65 @@ void g_binary_format_sort_symbols(GBinFormat *format)
 
 /******************************************************************************
 *                                                                             *
+*  Paramètres  : format = informations chargées à corriger si besoin est.     *
+*                                                                             *
+*  Description : Supprime les éventuels doublons au sein des symboles.        *
+*                                                                             *
+*  Retour      : -                                                            *
+*                                                                             *
+*  Remarques   : -                                                            *
+*                                                                             *
+******************************************************************************/
+
+void g_binary_format_delete_duplicated_symbols(GBinFormat *format)
+{
+    size_t i;                               /* Boucle de parcours          */
+    const mrange_t *range;                  /* Emplacement à consulter     */
+    mrange_t last;                          /* Dernière localisation vue   */
+    size_t index;                           /* Indice de suppression       */
+
+    g_binary_format_sort_symbols(G_BIN_FORMAT(format));
+
+    g_rw_lock_writer_lock(&format->syms_lock);
+
+    if (format->symbols_count > 1)
+    {
+        range = g_binary_symbol_get_range(format->symbols[0]);
+        copy_mrange(&last, range);
+    }
+
+    for (i = 1; i < format->symbols_count; i++)
+    {
+        range = g_binary_symbol_get_range(format->symbols[i]);
+
+        if (cmp_vmpa(get_mrange_addr(&last), get_mrange_addr(range)) == 0)
+        {
+            /* TODO : établir une meilleur comparaison pour trouver le bon candidat */
+            /* TODO : (éviter de) traiter selon le type aussi */
+            index = (get_mrange_length(&last) == 0 ? i - 1 : i);
+            /*
+            printf("DELETE @ %zu / 0x%08x '%s'\n", index,
+                   (unsigned int)last.addr.virtual,
+                   g_binary_symbol_get_label(format->symbols[index]));
+            */
+
+            _g_binary_format_remove_symbol(format, index);
+
+            i--;
+
+        }
+
+        copy_mrange(&last, range);
+
+    }
+
+    g_rw_lock_writer_unlock(&format->syms_lock);
+
+}
+
+
+/******************************************************************************
+*                                                                             *
 *  Paramètres  : format = informations chargées à consulter.                  *
 *                count  = taille du tableau créé. [OUT]                       *
 *                                                                             *
-- 
cgit v0.11.2-87-g4458