summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog38
-rw-r--r--src/analysis/binary.h2
-rw-r--r--src/analysis/disass/fetch.c6
-rw-r--r--src/analysis/disass/output.c78
-rw-r--r--src/arch/immediate.h2
-rw-r--r--src/arch/instruction-int.h2
-rw-r--r--src/arch/instruction.c26
-rw-r--r--src/arch/instruction.h2
-rw-r--r--src/arch/raw.c96
-rw-r--r--src/arch/raw.h6
-rw-r--r--src/arch/vmpa.c2
-rw-r--r--src/format/elf/elf-int.c46
-rw-r--r--src/format/elf/elf_def.h156
-rw-r--r--src/format/elf/symbols.c932
-rw-r--r--src/format/format.c3
-rw-r--r--src/format/symbol.c54
-rw-r--r--src/format/symbol.h31
17 files changed, 1399 insertions, 83 deletions
diff --git a/ChangeLog b/ChangeLog
index 0362a19..12ac1f3 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,41 @@
+14-08-25 Cyrille Bagard <nocbos@gmail.com>
+
+ * src/analysis/binary.h:
+ Typo.
+
+ * src/analysis/disass/fetch.c:
+ Update code.
+
+ * src/analysis/disass/output.c:
+ Add comments from some kinds of loaded symbols.
+
+ * src/arch/immediate.h:
+ Fix a typo bug.
+
+ * src/arch/instruction.c:
+ * src/arch/instruction.h:
+ * src/arch/instruction-int.h:
+ Return a buffer line when printing one instruction.
+
+ * src/arch/raw.c:
+ * src/arch/raw.h:
+ Show data as padding when required.
+
+ * src/arch/vmpa.c:
+ Fix a typo bug.
+
+ * src/format/elf/elf_def.h:
+ * src/format/elf/elf-int.c:
+ * src/format/elf/symbols.c:
+ Load lots of ELF header information as symbols.
+
+ * src/format/format.c:
+ Remove debug code.
+
+ * src/format/symbol.c:
+ * src/format/symbol.h:
+ Attach comments to symbols.
+
14-08-20 Cyrille Bagard <nocbos@gmail.com>
* src/glibext/gbuffersegment.c:
diff --git a/src/analysis/binary.h b/src/analysis/binary.h
index 2a7e7d9..17da200 100644
--- a/src/analysis/binary.h
+++ b/src/analysis/binary.h
@@ -116,7 +116,7 @@ void g_loaded_binary_set_storage(GLoadedBinary *, DBFeatures, DBStorage);
/* Trouve une collection assurant une fonctionnalité donnée. */
-GDbCollection *g_loaded_binary_find_collection(GLoadedBinary *, DBFeatures );
+GDbCollection *g_loaded_binary_find_collection(GLoadedBinary *, DBFeatures);
/* Demande l'intégration d'une modification dans une collection. */
bool g_loaded_binary_add_to_collection(GLoadedBinary *, DBFeatures, GDbItem *);
diff --git a/src/analysis/disass/fetch.c b/src/analysis/disass/fetch.c
index 9ef6f29..73474b3 100644
--- a/src/analysis/disass/fetch.c
+++ b/src/analysis/disass/fetch.c
@@ -189,8 +189,8 @@ GArchInstruction *disassemble_binary_content(const GLoadedBinary *binary, GtkExt
g_object_ref(G_OBJECT(instr));
border = g_arch_instruction_get_location2(instr, &length);
- length = 4;
-
+ // Utiliser : ???
+ // const vmpa2t *g_binary_symbol_get_address2(const GBinSymbol *symbol)
break;
@@ -218,8 +218,6 @@ GArchInstruction *disassemble_binary_content(const GLoadedBinary *binary, GtkExt
advance_vmpa(last, length);
- printf("length :: %d\n", length);
-
}
/* Raccord final ? */
diff --git a/src/analysis/disass/output.c b/src/analysis/disass/output.c
index 97f9989..927088f 100644
--- a/src/analysis/disass/output.c
+++ b/src/analysis/disass/output.c
@@ -25,6 +25,7 @@
#include "../../arch/processor.h"
+#include "../../common/extstr.h"
#include "../../decomp/lang/asm.h"
#include "../../format/format.h"
@@ -58,11 +59,42 @@ void print_disassembled_instructions(GCodeBuffer *buffer, const GExeFormat *form
vmpa_t end; /* Adresse de fin */
const GArchInstruction *iter; /* Boucle de parcours #1 */
size_t i; /* Boucle de parcours #2 */
- vmpa_t iaddr; /* Adresse d'instruction */
- vmpa_t raddr; /* Adresse de routine */
+ const vmpa2t *iaddr; /* Adresse d'instruction */
+ const vmpa2t *saddr; /* Adresse de symbole */
+
+ GBufferLine *line;
+
+
+ GBinSymbol **symbols; /* Symboles à représenter */
+ size_t sym_count; /* Qté de symboles présents */
+
+
+ size_t sym_index; /* Prochain symbole non traité */
+
+
+ GDbComment *comment; /* Commentaire à ajouter */
+
+
+
+ const char *text;
+
+ char *prefixed;
+
+
output = g_asm_output_new();
+
+ symbols = g_binary_format_get_symbols(format, &sym_count);
+
+ sym_index = 0;
+
+
+ //GDbCollection *g_loaded_binary_find_collection(GLoadedBinary *, DBFeatures);
+
+
+
+
proc = get_arch_processor_from_format(format);
msize = g_arch_processor_get_memory_size(proc);
@@ -90,7 +122,47 @@ void print_disassembled_instructions(GCodeBuffer *buffer, const GExeFormat *form
}
#endif
- g_arch_instruction_print(iter, buffer, msize, content, ASX_INTEL);
+
+
+
+ line = g_arch_instruction_print(iter, buffer, msize, content, ASX_INTEL);
+
+ if (sym_index < sym_count)
+ {
+ iaddr = g_arch_instruction_get_location2(iter, NULL);
+ saddr = g_binary_symbol_get_address2(symbols[sym_index]);
+
+ if (cmp_vmpa_by_phy(iaddr, saddr) == 0)
+ {
+
+
+ comment = g_binary_symbol_get_comment(symbols[sym_index]);
+
+ if (comment != NULL)
+ {
+
+ text = g_db_comment_get_text(comment);
+
+
+ prefixed = strdup("; ");
+ prefixed = stradd(prefixed, text);
+
+
+
+ g_buffer_line_insert_text(line, BLC_COMMENTS, prefixed, strlen(prefixed), RTT_COMMENT);
+
+
+ free(prefixed);
+
+ }
+
+ sym_index++;
+
+
+ }
+
+ }
+
//gtk_extended_status_bar_update_activity(statusbar, id, (iaddr - start) * 1.0 / (end - start));
diff --git a/src/arch/immediate.h b/src/arch/immediate.h
index 71d482a..99d1b7f 100644
--- a/src/arch/immediate.h
+++ b/src/arch/immediate.h
@@ -70,7 +70,7 @@ GArchOperand *_g_imm_operand_new_from_data(MemoryDataSize, const bin_t *, off_t
/* Crée un opérande réprésentant une valeur numérique. */
GArchOperand *_g_imm_operand_new_from_data2(MemoryDataSize, const bin_t *, vmpa2t *, off_t, bool *, SourceEndian);
-#define g_imm_operand_new_from_data2(size, data, pos, len, endian) _g_imm_operand_new_from_data(size, data, pos, len, NULL, endian)
+#define g_imm_operand_new_from_data2(size, data, pos, len, endian) _g_imm_operand_new_from_data2(size, data, pos, len, NULL, endian)
/* Crée un opérande réprésentant une valeur numérique. */
GArchOperand *g_imm_operand_new_from_value(MemoryDataSize, ...);
diff --git a/src/arch/instruction-int.h b/src/arch/instruction-int.h
index 8730792..28caf78 100644
--- a/src/arch/instruction-int.h
+++ b/src/arch/instruction-int.h
@@ -36,7 +36,7 @@
typedef void (* get_instruction_rw_regs_fc) (const GArchInstruction *, GArchRegister ***, size_t *, GArchRegister ***, size_t *);
/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
-typedef void (* print_instruction_fc) (const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+typedef GBufferLine * (* print_instruction_fc) (const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
/* Traduit une instruction en version humainement lisible. */
typedef const char * (* get_instruction_keyword_fc) (const GArchInstruction *, AsmSyntax);
diff --git a/src/arch/instruction.c b/src/arch/instruction.c
index e1ee023..ea713cd 100644
--- a/src/arch/instruction.c
+++ b/src/arch/instruction.c
@@ -51,7 +51,7 @@ static void g_arch_instruction_finalize(GArchInstruction *);
/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
-static void _g_arch_instruction_print(const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+static GBufferLine *_g_arch_instruction_print(const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
@@ -692,39 +692,41 @@ const char *g_arch_instruction_get_keyword(const GArchInstruction *instr, AsmSyn
* *
******************************************************************************/
-static void _g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
+static GBufferLine *_g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
{
- GBufferLine *line; /* Ligne de destination */
+ GBufferLine *result; /* Ligne de destination */
const char *key; /* Mot clef principal */
size_t klen; /* Taille de ce mot clef */
size_t i; /* Boucle de parcours */
- line = g_code_buffer_append_new_line(buffer, &instr->address2);
+ result = g_code_buffer_append_new_line(buffer, &instr->address2);
- g_buffer_line_fill_for_instr(line, msize/* TODO ! */, msize, content, instr->length, true);
+ g_buffer_line_fill_for_instr(result, msize/* TODO ! */, msize, content, instr->length, true);
/* Instruction proprement dite */
key = g_arch_instruction_get_keyword(instr, syntax);
klen = strlen(key);
- g_buffer_line_insert_text(line, BLC_ASSEMBLY_HEAD, key, klen, RTT_INSTRUCTION);
+ g_buffer_line_insert_text(result, BLC_ASSEMBLY_HEAD, key, klen, RTT_INSTRUCTION);
if (instr->operands_count > 0)
{
- g_arch_operand_print(instr->operands[0], line, syntax);
+ g_arch_operand_print(instr->operands[0], result, syntax);
for (i = 1; i < instr->operands_count; i++)
{
- g_buffer_line_insert_text(line, BLC_ASSEMBLY, ",", 1, RTT_PUNCT);
- g_buffer_line_insert_text(line, BLC_ASSEMBLY, " ", 1, RTT_RAW);
+ g_buffer_line_insert_text(result, BLC_ASSEMBLY, ",", 1, RTT_PUNCT);
+ g_buffer_line_insert_text(result, BLC_ASSEMBLY, " ", 1, RTT_RAW);
- g_arch_operand_print(instr->operands[i], line, syntax);
+ g_arch_operand_print(instr->operands[i], result, syntax);
}
}
+ return result;
+
}
@@ -742,9 +744,9 @@ static void _g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer
* *
******************************************************************************/
-void g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
+GBufferLine *g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
{
- G_ARCH_INSTRUCTION_GET_CLASS(instr)->print(instr, buffer, msize, content, syntax);
+ return G_ARCH_INSTRUCTION_GET_CLASS(instr)->print(instr, buffer, msize, content, syntax);
}
diff --git a/src/arch/instruction.h b/src/arch/instruction.h
index 08135a9..f04a458 100644
--- a/src/arch/instruction.h
+++ b/src/arch/instruction.h
@@ -152,7 +152,7 @@ size_t g_arch_instruction_compute_group_index(GArchInstruction **, GArchInstruct
const char *g_arch_instruction_get_keyword(const GArchInstruction *, AsmSyntax);
/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
-void g_arch_instruction_print(const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+GBufferLine *g_arch_instruction_print(const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
/* Décompile une instruction de façon générique. */
GDecInstruction *g_arch_instruction_decompile(const GArchInstruction *, GDecContext *);
diff --git a/src/arch/raw.c b/src/arch/raw.c
index 0d6ae4a..842c2b4 100644
--- a/src/arch/raw.c
+++ b/src/arch/raw.c
@@ -37,6 +37,8 @@ struct _GRawInstruction
{
GArchInstruction parent; /* A laisser en premier */
+ bool is_padding; /* Bourrage à représenter ? */
+
};
/* Définition générique d'une instruction d'architecture inconnue (classe) */
@@ -59,6 +61,9 @@ static void g_raw_instruction_dispose(GRawInstruction *);
/* Procède à la libération totale de la mémoire. */
static void g_raw_instruction_finalize(GRawInstruction *);
+/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
+static GBufferLine *g_raw_instruction_print(const GRawInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+
/* Fournit le nom humain de l'instruction manipulée. */
static const char *g_raw_instruction_get_keyword(const GRawInstruction *, AsmSyntax);
@@ -97,6 +102,7 @@ static void g_raw_instruction_class_init(GRawInstructionClass *klass)
instr = G_ARCH_INSTRUCTION_CLASS(klass);
+ instr->print = (print_instruction_fc)g_raw_instruction_print;
instr->get_key = (get_instruction_keyword_fc)g_raw_instruction_get_keyword;
}
@@ -219,6 +225,54 @@ GArchInstruction *g_raw_instruction_new_array(const bin_t *data, MemoryDataSize
/******************************************************************************
* *
+* Paramètres : instr = instruction d'assemblage à représenter. *
+* buffer = espace où placer ledit contenu. *
+* syntax = type de représentation demandée. *
+* *
+* Description : Ajoute à un tampon GLib le contenu de l'instance spécifiée. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static GBufferLine *g_raw_instruction_print(const GRawInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
+{
+ GBufferLine *result; /* Ligne de destination */
+ GArchInstruction *base; /* Autre version de l'instance */
+ const char *key; /* Mot clef principal */
+ size_t klen; /* Taille de ce mot clef */
+
+ base = G_ARCH_INSTRUCTION(instr);
+
+ if (!instr->is_padding)
+ result = G_ARCH_INSTRUCTION_CLASS(g_raw_instruction_parent_class)->print(base, buffer, msize, content, syntax);
+
+ else
+ {
+ result = g_code_buffer_append_new_line(buffer, &base->address2);
+
+ g_buffer_line_fill_for_instr(result, msize/* TODO ! */, msize, content, base->length, true);
+
+ /* Instruction proprement dite */
+
+ key = g_arch_instruction_get_keyword(base, syntax);
+ klen = strlen(key);
+
+ g_buffer_line_insert_text(result, BLC_ASSEMBLY_HEAD, key, klen, RTT_INSTRUCTION);
+
+ g_buffer_line_insert_text(result, BLC_ASSEMBLY, "...", 3, RTT_RAW);
+
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : instr = instruction à traiter. *
* format = format du binaire manipulé. *
* syntax = type de représentation demandée. *
@@ -238,9 +292,49 @@ static const char *g_raw_instruction_get_keyword(const GRawInstruction *instr, A
static char *defines[] = { "dn", "db", "dw", "dd", "dq" };
- operand = g_arch_instruction_get_operand(instr, 0);
+ operand = g_arch_instruction_get_operand(G_ARCH_INSTRUCTION(instr), 0);
size = g_imm_operand_get_size(G_IMM_OPERAND(operand));
return defines[MDS_RANGE(size)];
}
+
+
+/******************************************************************************
+* *
+* Paramètres : instr = instruction à traiter. *
+* is_padding = nouveau statut à associer au contenu. *
+* *
+* Description : Marque l'instruction comme ne contenant que du bourrage. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+void g_raw_instruction_mark_as_padding(GRawInstruction *instr, bool is_padding)
+{
+ instr->is_padding = is_padding;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : instr = instruction à traiter. *
+* is_padding = nouveau statut à associer au contenu. *
+* *
+* Description : Indique si le contenu de l'instruction est du bourrage. *
+* *
+* Retour : Statut du contenu de l'instruction. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool g_raw_instruction_is_padding(const GRawInstruction *instr)
+{
+ return instr->is_padding;
+
+}
diff --git a/src/arch/raw.h b/src/arch/raw.h
index 08dc620..ce324f5 100644
--- a/src/arch/raw.h
+++ b/src/arch/raw.h
@@ -55,6 +55,12 @@ GType g_raw_instruction_get_type(void);
/* Crée une instruction de type 'db/dw/etc' étendue. */
GArchInstruction *g_raw_instruction_new_array(const bin_t *, MemoryDataSize, size_t, vmpa2t *, off_t, SourceEndian);
+/* Marque l'instruction comme ne contenant que du bourrage. */
+void g_raw_instruction_mark_as_padding(GRawInstruction *, bool);
+
+/* Indique si le contenu de l'instruction est du bourrage. */
+bool g_raw_instruction_is_padding(const GRawInstruction *);
+
#endif /* _ARCH_RAW_H */
diff --git a/src/arch/vmpa.c b/src/arch/vmpa.c
index 93bbfc8..edff789 100644
--- a/src/arch/vmpa.c
+++ b/src/arch/vmpa.c
@@ -191,7 +191,7 @@ void advance_vmpa(vmpa2t *addr, off_t qty)
addr->physical += qty;
if (addr->virtual != VMPA_NO_VIRTUAL)
- addr->virtual =+ qty;
+ addr->virtual += qty;
}
diff --git a/src/format/elf/elf-int.c b/src/format/elf/elf-int.c
index 17aeaf2..677a9ef 100644
--- a/src/format/elf/elf-int.c
+++ b/src/format/elf/elf-int.c
@@ -27,9 +27,6 @@
#include <string.h>
-#include "../../arch/raw.h"
-
-
/******************************************************************************
* *
@@ -52,18 +49,6 @@ bool read_elf_header(GElfFormat *format, elf_header *header, bool *is_32b, Sourc
const bin_t *content; /* Contenu binaire à lire */
off_t length; /* Taille totale du contenu */
off_t pos; /* Position de lecture */
- GArchInstruction *instr; /* Instruction décodée */
-
-
- vmpa2t *pos2;
-
-
- GBinSymbol *symbol;
-
- size_t i; /* Boucle de parcours */
- GArchOperand *operand; /* Opérande à venir modifier */
-
-
content = G_BIN_FORMAT(format)->content;
length = G_BIN_FORMAT(format)->length;
@@ -108,37 +93,6 @@ bool read_elf_header(GElfFormat *format, elf_header *header, bool *is_32b, Sourc
break;
}
-
- pos2 = make_vmpa(0, 0x123);
-
-
-
- instr = g_raw_instruction_new_array(content, MDS_8_BITS, 4, pos2, 4, *endian);
-
-
- for (i = 1; i < 4; i++)
- {
- operand = g_arch_instruction_get_operand(instr, i);
- g_imm_operand_set_display(G_IMM_OPERAND(operand), IOD_CHAR);
- }
-
-
-
-
- symbol = g_binary_symbol_new(STP_OBJECT, "toto", 0);
-
- printf("TOTO\n");
-
- g_binary_symbol_attach_instruction(symbol, instr);
- g_binary_format_add_symbol(format, symbol);
-
-
-
-
-
-
-
-
if (*is_32b)
{
result &= read_u16(&header->hdr32.e_type, content, &pos, length, *endian);
diff --git a/src/format/elf/elf_def.h b/src/format/elf/elf_def.h
index 9d872f4..91e1c18 100644
--- a/src/format/elf/elf_def.h
+++ b/src/format/elf/elf_def.h
@@ -103,6 +103,8 @@ typedef union _elf_header
#define EI_CLASS 4 /* Indice de classe du fichier */
#define EI_DATA 5 /* Indice de l'encodage */
+#define EI_VERSION 6 /* Version de fichier ELF */
+#define EI_OSABI 7 /* Identification de l'ABI OS */
/* ... EI_CLASS */
@@ -117,20 +119,122 @@ typedef union _elf_header
#define ELFDATA2LSB 1 /* Complément à 2, petit bout. */
#define ELFDATA2MSB 2 /* Complément à 2, grand bout. */
+/* ... EI_VERSION */
+
+#define EV_NONE 0 /* Version ELF invalide */
+#define EV_CURRENT 1 /* Version d'ELF courante */
+
+/* ... EI_OSABI */
+
+#define ELFOSABI_NONE 0 /* UNIX System V ABI */
+#define ELFOSABI_SYSV 0 /* Alias. */
+#define ELFOSABI_HPUX 1 /* HP-UX */
+#define ELFOSABI_NETBSD 2 /* NetBSD. */
+#define ELFOSABI_GNU 3 /* Object uses GNU ELF extensions. */
+#define ELFOSABI_LINUX ELFOSABI_GNU /* Compatibility alias. */
+#define ELFOSABI_SOLARIS 6 /* Sun Solaris. */
+#define ELFOSABI_AIX 7 /* IBM AIX. */
+#define ELFOSABI_IRIX 8 /* SGI Irix. */
+#define ELFOSABI_FREEBSD 9 /* FreeBSD. */
+#define ELFOSABI_TRU64 10 /* Compaq TRU64 UNIX. */
+#define ELFOSABI_MODESTO 11 /* Novell Modesto. */
+#define ELFOSABI_OPENBSD 12 /* OpenBSD. */
+#define ELFOSABI_ARM_AEABI 64 /* ARM EABI */
+#define ELFOSABI_ARM 97 /* ARM */
+#define ELFOSABI_STANDALONE 255 /* Standalone (embedded) application */
/* Valeurs possibles pour e_type */
#define ET_NONE 0 /* Aucun type défini */
+#define ET_REL 1 /* Fichier relogeable */
#define ET_EXEC 2 /* Fichier exécutable */
#define ET_DYN 3 /* Bibliothèque dynamique */
+#define ET_CORE 4 /* Fichier Core */
+#define ET_LOOS 0xfe00 /* Spécifique OS : début */
+#define ET_HIOS 0xfeff /* Spécifique OS : fin */
+#define ET_LOPROC 0xff00 /* Spécifique processeur : deb.*/
+#define ET_HIPROC 0xffff /* Spécifique processeur : fin */
/* Valeurs possibles pour e_machine */
-#define EM_NONE 0 /* Aucune machine */
-#define EM_386 3 /* Intel 80386 */
-#define EM_MIPS 8 /* MIPS R3000 big-endian */
-#define EM_MIPS_RS3_LE 10 /* MIPS R3000 little-endian */
-#define EM_ARM 40 /* ARM */
+#define EM_NONE 0 /* No machine */
+#define EM_M32 1 /* AT&T WE 32100 */
+#define EM_SPARC 2 /* SUN SPARC */
+#define EM_386 3 /* Intel 80386 */
+#define EM_68K 4 /* Motorola m68k family */
+#define EM_88K 5 /* Motorola m88k family */
+#define EM_860 7 /* Intel 80860 */
+#define EM_MIPS 8 /* MIPS R3000 big-endian */
+#define EM_S370 9 /* IBM System/370 */
+#define EM_MIPS_RS3_LE 10 /* MIPS R3000 little-endian */
+#define EM_PARISC 15 /* HPPA */
+#define EM_VPP500 17 /* Fujitsu VPP500 */
+#define EM_SPARC32PLUS 18 /* Sun's "v8plus" */
+#define EM_960 19 /* Intel 80960 */
+#define EM_PPC 20 /* PowerPC */
+#define EM_PPC64 21 /* PowerPC 64-bit */
+#define EM_S390 22 /* IBM S390 */
+#define EM_V800 36 /* NEC V800 series */
+#define EM_FR20 37 /* Fujitsu FR20 */
+#define EM_RH32 38 /* TRW RH-32 */
+#define EM_RCE 39 /* Motorola RCE */
+#define EM_ARM 40 /* ARM */
+#define EM_FAKE_ALPHA 41 /* Digital Alpha */
+#define EM_SH 42 /* Hitachi SH */
+#define EM_SPARCV9 43 /* SPARC v9 64-bit */
+#define EM_TRICORE 44 /* Siemens Tricore */
+#define EM_ARC 45 /* Argonaut RISC Core */
+#define EM_H8_300 46 /* Hitachi H8/300 */
+#define EM_H8_300H 47 /* Hitachi H8/300H */
+#define EM_H8S 48 /* Hitachi H8S */
+#define EM_H8_500 49 /* Hitachi H8/500 */
+#define EM_IA_64 50 /* Intel Merced */
+#define EM_MIPS_X 51 /* Stanford MIPS-X */
+#define EM_COLDFIRE 52 /* Motorola Coldfire */
+#define EM_68HC12 53 /* Motorola M68HC12 */
+#define EM_MMA 54 /* Fujitsu MMA Multimedia Accelerator*/
+#define EM_PCP 55 /* Siemens PCP */
+#define EM_NCPU 56 /* Sony nCPU embeeded RISC */
+#define EM_NDR1 57 /* Denso NDR1 microprocessor */
+#define EM_STARCORE 58 /* Motorola Start*Core processor */
+#define EM_ME16 59 /* Toyota ME16 processor */
+#define EM_ST100 60 /* STMicroelectronic ST100 processor */
+#define EM_TINYJ 61 /* Advanced Logic Corp. Tinyj emb.fam*/
+#define EM_X86_64 62 /* AMD x86-64 architecture */
+#define EM_PDSP 63 /* Sony DSP Processor */
+#define EM_FX66 66 /* Siemens FX66 microcontroller */
+#define EM_ST9PLUS 67 /* STMicroelectronics ST9+ 8/16 mc */
+#define EM_ST7 68 /* STmicroelectronics ST7 8 bit mc */
+#define EM_68HC16 69 /* Motorola MC68HC16 microcontroller */
+#define EM_68HC11 70 /* Motorola MC68HC11 microcontroller */
+#define EM_68HC08 71 /* Motorola MC68HC08 microcontroller */
+#define EM_68HC05 72 /* Motorola MC68HC05 microcontroller */
+#define EM_SVX 73 /* Silicon Graphics SVx */
+#define EM_ST19 74 /* STMicroelectronics ST19 8 bit mc */
+#define EM_VAX 75 /* Digital VAX */
+#define EM_CRIS 76 /* Axis Communications 32-bit embedded processor */
+#define EM_JAVELIN 77 /* Infineon Technologies 32-bit embedded processor */
+#define EM_FIREPATH 78 /* Element 14 64-bit DSP Processor */
+#define EM_ZSP 79 /* LSI Logic 16-bit DSP Processor */
+#define EM_MMIX 80 /* Donald Knuth's educational 64-bit processor */
+#define EM_HUANY 81 /* Harvard University machine-independent object files */
+#define EM_PRISM 82 /* SiTera Prism */
+#define EM_AVR 83 /* Atmel AVR 8-bit microcontroller */
+#define EM_FR30 84 /* Fujitsu FR30 */
+#define EM_D10V 85 /* Mitsubishi D10V */
+#define EM_D30V 86 /* Mitsubishi D30V */
+#define EM_V850 87 /* NEC v850 */
+#define EM_M32R 88 /* Mitsubishi M32R */
+#define EM_MN10300 89 /* Matsushita MN10300 */
+#define EM_MN10200 90 /* Matsushita MN10200 */
+#define EM_PJ 91 /* picoJava */
+#define EM_OPENRISC 92 /* OpenRISC 32-bit embedded processor */
+#define EM_ARC_A5 93 /* ARC Cores Tangent-A5 */
+#define EM_XTENSA 94 /* Tensilica Xtensa Architecture */
+#define EM_AARCH64 183 /* ARM AARCH64 */
+#define EM_TILEPRO 188 /* Tilera TILEPro */
+#define EM_MICROBLAZE 189 /* Xilinx MicroBlaze */
+#define EM_TILEGX 191 /* Tilera TILE-Gx */
@@ -203,9 +307,11 @@ typedef union _elf_phdr
/* Valeurs possibles pour p_flags */
-#define PF_X (1 << 0) /* Le segment est exécutable */
-#define PF_W (1 << 1) /* Le segment est écrasable */
-#define PF_R (1 << 2) /* Le segment est lisible */
+#define PF_X (1 << 0) /* Le segment est exécutable */
+#define PF_W (1 << 1) /* Le segment est écrasable */
+#define PF_R (1 << 2) /* Le segment est lisible */
+#define PF_MASKOS 0x0ff00000 /* Spécifique à l'OS */
+#define PF_MASKPROC 0xf0000000 /* Spécifique au processeur */
@@ -263,8 +369,42 @@ typedef union _elf_shdr
#define SHT_PROGBITS 1 /* Données de programme */
#define SHT_SYMTAB 2 /* Table des symboles */
#define SHT_STRTAB 3 /* Table de chaînes de carac. */
+
+#define SHT_RELA 4 /* Relocation entries with addends */
+#define SHT_HASH 5 /* Symbol hash table */
+
#define SHT_DYNAMIC 6 /* Info. de liaison dynamique */
+#define SHT_NOTE 7 /* Notes */
+#define SHT_NOBITS 8 /* Program space with no data (bss) */
+#define SHT_REL 9 /* Relocation entries, no addends */
+#define SHT_SHLIB 10 /* Reserved */
+#define SHT_DYNSYM 11 /* Dynamic linker symbol table */
+#define SHT_INIT_ARRAY 14 /* Array of constructors */
+#define SHT_FINI_ARRAY 15 /* Array of destructors */
+#define SHT_PREINIT_ARRAY 16 /* Array of pre-constructors */
+#define SHT_GROUP 17 /* Section group */
+#define SHT_SYMTAB_SHNDX 18 /* Extended section indeces */
+#define SHT_NUM 19 /* Number of defined types. */
+#define SHT_LOOS 0x60000000 /* Start OS-specific. */
+#define SHT_GNU_ATTRIBUTES 0x6ffffff5 /* Object attributes. */
+#define SHT_GNU_HASH 0x6ffffff6 /* GNU-style hash table. */
+#define SHT_GNU_LIBLIST 0x6ffffff7 /* Prelink library list */
+#define SHT_CHECKSUM 0x6ffffff8 /* Checksum for DSO content. */
+#define SHT_LOSUNW 0x6ffffffa /* Sun-specific low bound. */
+#define SHT_SUNW_move 0x6ffffffa
+#define SHT_SUNW_COMDAT 0x6ffffffb
+#define SHT_SUNW_syminfo 0x6ffffffc
+#define SHT_GNU_verdef 0x6ffffffd /* Version definition section. */
+#define SHT_GNU_verneed 0x6ffffffe /* Version needs section. */
+#define SHT_GNU_versym 0x6fffffff /* Version symbol table. */
+#define SHT_HISUNW 0x6fffffff /* Sun-specific high bound. */
+#define SHT_HIOS 0x6fffffff /* End OS-specific type */
+#define SHT_LOPROC 0x70000000 /* Start of processor-specific */
+#define SHT_HIPROC 0x7fffffff /* End of processor-specific */
+#define SHT_LOUSER 0x80000000 /* Start of application-specific */
+#define SHT_HIUSER 0x8fffffff /* End of application-specific */
+
/* Valeurs possibles pour sh_flags */
diff --git a/src/format/elf/symbols.c b/src/format/elf/symbols.c
index c480c51..33a8c3f 100644
--- a/src/format/elf/symbols.c
+++ b/src/format/elf/symbols.c
@@ -35,6 +35,8 @@
#include "helper_x86.h"
#include "section.h"
#include "../mangling/demangler.h"
+#include "../../arch/raw.h"
+#include "../../common/extstr.h"
#include "../../gui/panels/log.h"
@@ -48,6 +50,23 @@ const char *get_elf_symbol_name(GElfFormat *, const elf_shdr *, const elf_shdr *
+
+
+
+/* ------------------------ CHARGEMENT DE SYMBOLES DU FORMAT ------------------------ */
+
+
+/* Charge tous les symboles de l'en-tête ELF. */
+static bool annotate_elf_header(GElfFormat *);
+
+/* Charge tous les symboles liés aux en-têtes de programme ELF. */
+static bool annotate_elf_program_header_table(GElfFormat *);
+
+/* Charge tous les symboles liés aux en-têtes de section ELF. */
+static bool annotate_elf_section_header_table(GElfFormat *);
+
+
+
/* -------------------------- DETAIL DES SYMBOLES INTERNES -------------------------- */
@@ -72,6 +91,8 @@ static bool load_elf_external_symbols(GElfFormat *, const elf_shdr *);
+
+
/******************************************************************************
* *
* Paramètres : format = description de l'exécutable à compléter. *
@@ -92,6 +113,16 @@ bool load_elf_symbols(GElfFormat *format)
result = true;
+
+
+ annotate_elf_header(format);
+
+ annotate_elf_program_header_table(format);
+
+ annotate_elf_section_header_table(format);
+
+
+
/* Symboles externes */
if (find_elf_sections_by_type(format, SHT_DYNAMIC, &sections, &count))
@@ -155,6 +186,907 @@ const char *get_elf_symbol_name(GElfFormat *format, const elf_shdr *sym, const e
+
+/* ---------------------------------------------------------------------------------- */
+/* CHARGEMENT DE SYMBOLES DU FORMAT */
+/* ---------------------------------------------------------------------------------- */
+
+
+/******************************************************************************
+* *
+* Paramètres : format = description de l'exécutable à compléter. *
+* *
+* Description : Charge tous les symboles de l'en-tête ELF. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static bool annotate_elf_header(GElfFormat *format)
+{
+ const bin_t *content; /* Contenu binaire à lire */
+ off_t length; /* Taille totale du contenu */
+ vmpa2t *pos; /* Localisation des symboles */
+ const char *text; /* Texte constant à insérer */
+ GArchInstruction *instr; /* Instruction décodée */
+ GArchOperand *operand; /* Opérande à venir modifier */
+ GDbComment *comment; /* Définition de commentaire */
+ GBinSymbol *symbol; /* Symbole à intégrer */
+
+ content = G_BIN_FORMAT(format)->content;
+ length = G_BIN_FORMAT(format)->length;
+
+ pos = make_vmpa(0, 0x123);
+
+ /* ELFMAG (0) */
+
+ instr = g_raw_instruction_new_array(content, MDS_8_BITS, 4, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 1, IOD_CHAR);
+ SET_IMM_DISPLAY(instr, operand, 2, IOD_CHAR);
+ SET_IMM_DISPLAY(instr, operand, 3, IOD_CHAR);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("ELF magic number"));
+
+ /* EI_CLASS (4) */
+
+ switch (format->header.hdr32.e_ident[EI_CLASS])
+ {
+ case EV_NONE:
+ text = _("File class: invalid");
+ break;
+ case ELFCLASS32:
+ text = _("File class: 32-bit objects");
+ break;
+ case ELFCLASS64:
+ text = _("File class: 64-bit objects");
+ break;
+ default:
+ text = _("File class: unknown");
+ break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_8_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ /* EI_DATA (5) */
+
+ switch (format->header.hdr32.e_ident[EI_DATA])
+ {
+ case ELFDATANONE:
+ text = _("Data encoding: invalid");
+ break;
+ case ELFDATA2LSB:
+ text = _("Data encoding: 2's complement, little endian");
+ break;
+ case ELFDATA2MSB:
+ text = _("Data encoding: 2's complement, big endian");
+ break;
+ default:
+ text = _("Data encoding: unknown");
+ break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_8_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ /* EI_VERSION (6) */
+
+ switch (format->header.hdr32.e_ident[EI_VERSION])
+ {
+ case EV_NONE:
+ text = _("File version: invalid");
+ break;
+ case EV_CURRENT:
+ text = _("File version: current");
+ break;
+ default:
+ text = _("File version: unknown");
+ break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_8_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ /* EI_OSABI (7) */
+
+ switch (format->header.hdr32.e_ident[EI_OSABI])
+ {
+ case ELFOSABI_SYSV:
+ text = _("OS ABI: UNIX System V");
+ break;
+ case ELFOSABI_HPUX:
+ text = _("OS ABI: HP-UX");
+ break;
+ case ELFOSABI_NETBSD:
+ text = _("OS ABI: NetBSD");
+ break;
+ case ELFOSABI_GNU:
+ text = _("OS ABI: object uses GNU ELF extensions");
+ break;
+ case ELFOSABI_SOLARIS:
+ text = _("OS ABI: Sun Solaris");
+ break;
+ case ELFOSABI_AIX:
+ text = _("OS ABI: IBM AIX");
+ break;
+ case ELFOSABI_IRIX:
+ text = _("OS ABI: SGI Irix");
+ break;
+ case ELFOSABI_FREEBSD:
+ text = _("OS ABI: FreeBSD");
+ break;
+ case ELFOSABI_TRU64:
+ text = _("OS ABI: Compaq TRU64 UNIX");
+ break;
+ case ELFOSABI_MODESTO:
+ text = _("OS ABI: Novell Modesto");
+ break;
+ case ELFOSABI_OPENBSD:
+ text = _("OS ABI: OpenBSD");
+ break;
+ case ELFOSABI_ARM_AEABI:
+ text = _("OS ABI: ARM EABI");
+ break;
+ case ELFOSABI_ARM:
+ text = _("OS ABI: ARM");
+ break;
+ case ELFOSABI_STANDALONE:
+ text = _("OS ABI: standalone (embedded) application");
+ break;
+ default:
+ text = _("OS ABI: unknown");
+ break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_8_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ /* EI_ABIVERSION (8) */
+
+ instr = g_raw_instruction_new_array(content, MDS_8_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("ABI version"));
+
+ /* Padding */
+
+ instr = g_raw_instruction_new_array(content, MDS_8_BITS, 7, pos, length, format->endian);
+
+ g_raw_instruction_mark_as_padding(G_RAW_INSTRUCTION(instr), true);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Padding"));
+
+ /* Champ "e_type" */
+
+ switch (format->header.hdr32.e_ident[EI_DATA])
+ {
+ case ET_NONE:
+ text = _("Object file type: no file type");
+ break;
+ case ET_REL:
+ text = _("Object file type: relocatable file");
+ break;
+ case ET_EXEC:
+ text = _("Object file type: executable file");
+ break;
+ case ET_DYN:
+ text = _("Object file type: shared object file");
+ break;
+ case ET_CORE:
+ text = _("Object file type: core file");
+ break;
+ case ET_LOOS ... ET_HIOS:
+ text = _("Object file type: OS-specific");
+ break;
+ case ET_LOPROC ... ET_HIPROC:
+ text = _("Object file type: processor-specific");
+ break;
+ default:
+ text = _("Object file type: unkown");
+ break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ /* Champ "e_machine" */
+
+ switch (format->header.hdr32.e_machine)
+ {
+ case EM_NONE: text = _("Architecture: No machine"); break;
+ case EM_M32: text = _("Architecture: AT&T WE 32100"); break;
+ case EM_SPARC: text = _("Architecture: SUN SPARC"); break;
+ case EM_386: text = _("Architecture: Intel 80386"); break;
+ case EM_68K: text = _("Architecture: Motorola m68k family"); break;
+ case EM_88K: text = _("Architecture: Motorola m88k family"); break;
+ case EM_860: text = _("Architecture: Intel 80860"); break;
+ case EM_MIPS: text = _("Architecture: MIPS R3000 big-endian"); break;
+ case EM_S370: text = _("Architecture: IBM System/370"); break;
+ case EM_MIPS_RS3_LE:text = _("Architecture: MIPS R3000 little-endian"); break;
+ case EM_PARISC: text = _("Architecture: HPPA"); break;
+ case EM_VPP500: text = _("Architecture: Fujitsu VPP500"); break;
+ case EM_SPARC32PLUS:text = _("Architecture: Sun's \"v8plus\""); break;
+ case EM_960: text = _("Architecture: Intel 80960"); break;
+ case EM_PPC: text = _("Architecture: PowerPC"); break;
+ case EM_PPC64: text = _("Architecture: PowerPC 64-bit"); break;
+ case EM_S390: text = _("Architecture: IBM S390"); break;
+ case EM_V800: text = _("Architecture: NEC V800 series"); break;
+ case EM_FR20: text = _("Architecture: Fujitsu FR20"); break;
+ case EM_RH32: text = _("Architecture: TRW RH-32"); break;
+ case EM_RCE: text = _("Architecture: Motorola RCE"); break;
+ case EM_ARM: text = _("Architecture: ARM"); break;
+ case EM_FAKE_ALPHA: text = _("Architecture: Digital Alpha"); break;
+ case EM_SH: text = _("Architecture: Hitachi SH"); break;
+ case EM_SPARCV9: text = _("Architecture: SPARC v9 64-bit"); break;
+ case EM_TRICORE: text = _("Architecture: Siemens Tricore"); break;
+ case EM_ARC: text = _("Architecture: Argonaut RISC Core"); break;
+ case EM_H8_300: text = _("Architecture: Hitachi H8/300"); break;
+ case EM_H8_300H: text = _("Architecture: Hitachi H8/300H"); break;
+ case EM_H8S: text = _("Architecture: Hitachi H8S"); break;
+ case EM_H8_500: text = _("Architecture: Hitachi H8/500"); break;
+ case EM_IA_64: text = _("Architecture: Intel Merced"); break;
+ case EM_MIPS_X: text = _("Architecture: Stanford MIPS-X"); break;
+ case EM_COLDFIRE: text = _("Architecture: Motorola Coldfire"); break;
+ case EM_68HC12: text = _("Architecture: Motorola M68HC12"); break;
+ case EM_MMA: text = _("Architecture: Fujitsu MMA Multimedia Accelerator"); break;
+ case EM_PCP: text = _("Architecture: Siemens PCP"); break;
+ case EM_NCPU: text = _("Architecture: Sony nCPU embeeded RISC"); break;
+ case EM_NDR1: text = _("Architecture: Denso NDR1 microprocessor"); break;
+ case EM_STARCORE: text = _("Architecture: Motorola Start*Core processor"); break;
+ case EM_ME16: text = _("Architecture: Toyota ME16 processor"); break;
+ case EM_ST100: text = _("Architecture: STMicroelectronic ST100 processor"); break;
+ case EM_TINYJ: text = _("Architecture: Advanced Logic Corp. Tinyj emb.fam"); break;
+ case EM_X86_64: text = _("Architecture: AMD x86-64 architecture"); break;
+ case EM_PDSP: text = _("Architecture: Sony DSP Processor"); break;
+ case EM_FX66: text = _("Architecture: Siemens FX66 microcontroller"); break;
+ case EM_ST9PLUS: text = _("Architecture: STMicroelectronics ST9+ 8/16 mc"); break;
+ case EM_ST7: text = _("Architecture: STmicroelectronics ST7 8 bit mc"); break;
+ case EM_68HC16: text = _("Architecture: Motorola MC68HC16 microcontroller"); break;
+ case EM_68HC11: text = _("Architecture: Motorola MC68HC11 microcontroller"); break;
+ case EM_68HC08: text = _("Architecture: Motorola MC68HC08 microcontroller"); break;
+ case EM_68HC05: text = _("Architecture: Motorola MC68HC05 microcontroller"); break;
+ case EM_SVX: text = _("Architecture: Silicon Graphics SVx"); break;
+ case EM_ST19: text = _("Architecture: STMicroelectronics ST19 8 bit mc"); break;
+ case EM_VAX: text = _("Architecture: Digital VAX"); break;
+ case EM_CRIS: text = _("Architecture: Axis Communications 32-bit embedded processor"); break;
+ case EM_JAVELIN: text = _("Architecture: Infineon Technologies 32-bit embedded processor"); break;
+ case EM_FIREPATH: text = _("Architecture: Element 14 64-bit DSP Processor"); break;
+ case EM_ZSP: text = _("Architecture: LSI Logic 16-bit DSP Processor"); break;
+ case EM_MMIX: text = _("Architecture: Donald Knuth's educational 64-bit processor"); break;
+ case EM_HUANY: text = _("Architecture: Harvard University machine-independent object files"); break;
+ case EM_PRISM: text = _("Architecture: SiTera Prism"); break;
+ case EM_AVR: text = _("Architecture: Atmel AVR 8-bit microcontroller"); break;
+ case EM_FR30: text = _("Architecture: Fujitsu FR30"); break;
+ case EM_D10V: text = _("Architecture: Mitsubishi D10V"); break;
+ case EM_D30V: text = _("Architecture: Mitsubishi D30V"); break;
+ case EM_V850: text = _("Architecture: NEC v850"); break;
+ case EM_M32R: text = _("Architecture: Mitsubishi M32R"); break;
+ case EM_MN10300: text = _("Architecture: Matsushita MN10300"); break;
+ case EM_MN10200: text = _("Architecture: Matsushita MN10200"); break;
+ case EM_PJ: text = _("Architecture: picoJava"); break;
+ case EM_OPENRISC: text = _("Architecture: OpenRISC 32-bit embedded processor"); break;
+ case EM_ARC_A5: text = _("Architecture: ARC Cores Tangent-A5"); break;
+ case EM_XTENSA: text = _("Architecture: Tensilica Xtensa Architecture"); break;
+ case EM_AARCH64: text = _("Architecture: ARM AARCH64"); break;
+ case EM_TILEPRO: text = _("Architecture: Tilera TILEPro"); break;
+ case EM_MICROBLAZE: text = _("Architecture: Xilinx MicroBlaze"); break;
+ case EM_TILEGX: text = _("Architecture: Tilera TILE-Gx"); break;
+ default: text = _("Architecture: unknown"); break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ /* Champ "e_version" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Object file version"));
+
+ if (format->header.hdr32.e_ident[EI_CLASS] == ELFCLASS32)
+ {
+ /* Champ "e_entry" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Entry point virtual address"));
+
+ /* Champ "e_phoff" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Program header table file offset"));
+
+ /* Champ "e_shoff" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Section header table file offset"));
+
+ }
+
+ else if (format->header.hdr32.e_ident[EI_CLASS] == ELFCLASS64)
+ {
+ /* Champ "e_entry" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Entry point virtual address"));
+
+ /* Champ "e_phoff" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Program header table file offset"));
+
+ /* Champ "e_shoff" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Section header table file offset"));
+
+ }
+
+ else return false;
+
+ /* Champ "e_flags" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ //SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Processor-specific flags"));
+
+ /* Champ "e_ehsize" */
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("ELF header size in bytes"));
+
+ /* Champ "e_phentsize" */
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Program header table entry size"));
+
+ /* Champ "e_phnum" */
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Program header table entry count"));
+
+ /* Champ "e_shentsize" */
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Section header table entry size"));
+
+ /* Champ "e_shnum" */
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Section header table entry count"));
+
+ /* Champ "e_shstrndx" */
+
+ instr = g_raw_instruction_new_array(content, MDS_16_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Section header string table index"));
+
+ return true;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : format = description de l'exécutable à compléter. *
+* *
+* Description : Charge tous les symboles liés aux en-têtes de programme ELF. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static bool annotate_elf_program_header_table(GElfFormat *format)
+{
+ const bin_t *content; /* Contenu binaire à lire */
+ off_t length; /* Taille totale du contenu */
+ off_t offset; /* Tête de lecture du bbinaire */
+ vmpa2t *pos; /* Localisation des symboles */
+ uint16_t e_phnum; /* Nombre d'éléments 'Program' */
+ uint16_t i; /* Boucle de parcours */
+ elf_phdr phdr; /* En-tête de programme ELF */
+ ImmOperandDisplay disp; /* Afficahge de valeur */
+ const char *text; /* Texte constant à insérer */
+ GArchInstruction *instr; /* Instruction décodée */
+ GArchOperand *operand; /* Opérande à venir modifier */
+ GDbComment *comment; /* Définition de commentaire */
+ GBinSymbol *symbol; /* Symbole à intégrer */
+ char *dtext; /* Texte dynamique à créer */
+ bool filled; /* Suivi de mise en place */
+
+ content = G_BIN_FORMAT(format)->content;
+ length = G_BIN_FORMAT(format)->length;
+
+ offset = ELF_HDR(format, format->header, e_phoff);
+
+ pos = make_vmpa(offset, 0x5500);
+
+ e_phnum = ELF_HDR(format, format->header, e_phnum);
+
+ for (i = 0; i < e_phnum; i++)
+ {
+ if (!read_elf_program_header(format, &offset, &phdr))
+ break;
+
+ /* Champ "p_type" */
+
+ disp = IOD_DEC;
+
+ switch (ELF_PHDR(format, phdr, p_type))
+ {
+ case PT_NULL:
+ text = _("Segment type: unused");
+ break;
+ case PT_LOAD:
+ text = _("Segment type: loadable program segment");
+ break;
+ case PT_DYNAMIC:
+ text = _("Segment type: dynamic linking information");
+ break;
+ case PT_INTERP:
+ text = _("Segment type: program interpreter");
+ break;
+ case PT_NOTE:
+ text = _("Segment type: auxiliary information");
+ break;
+ case PT_SHLIB:
+ text = _("Segment type: reserved");
+ break;
+ case PT_PHDR:
+ text = _("Segment type: entry for header table itself");
+ break;
+ case PT_TLS:
+ text = _("Segment type: thread-local storage segment");
+ break;
+ case PT_LOOS ... PT_HIOS:
+ disp = IOD_HEX;
+ switch (ELF_PHDR(format, phdr, p_type))
+ {
+ case PT_GNU_EH_FRAME:
+ text = _("Segment type: GCC .eh_frame_hdr segment");
+ break;
+ case PT_GNU_STACK:
+ text = _("Segment type: indicates stack executability");
+ break;
+ case PT_GNU_RELRO:
+ text = _("Segment type: read-only after relocation");
+ break;
+ case PT_LOSUNW ... PT_HISUNW:
+ switch (ELF_PHDR(format, phdr, p_type))
+ {
+ case PT_SUNWSTACK:
+ text = _("Segment type: Sun Stack segment");
+ break;
+ default:
+ text = _("Segment type: Sun specific segment");
+ break;
+ }
+ break;
+ default:
+ text = _("Segment type: OS-specific");
+ break;
+ }
+ break;
+ case PT_LOPROC ... PT_HIPROC:
+ disp = IOD_HEX;
+ text = _("Segment type: processor-specific");
+ break;
+ default:
+ disp = IOD_HEX;
+ text = _("Segment type: unknown");
+ break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, disp);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ if (format->is_32b)
+ {
+ /* Champ "p_offset" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment file offset"));
+
+ /* Champ "p_vaddr" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment virtual address"));
+
+ /* Champ "p_paddr" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment physical address"));
+
+ /* Champ "p_filesz" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment size in file"));
+
+ /* Champ "p_memsz" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment size in memory"));
+
+ /* Champ "p_flags" */
+
+ dtext = strdup(_("Segment flags: "));
+ filled = false;
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_R)
+ {
+ dtext = stradd(dtext, "R");
+ filled = true;
+ }
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_W)
+ {
+ dtext = stradd(dtext, "W");
+ filled = true;
+ }
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_X)
+ {
+ dtext = stradd(dtext, "X");
+ filled = true;
+ }
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_MASKOS)
+ /* TODO */;
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_MASKPROC)
+ /* TODO */;
+
+ if (!filled)
+ dtext = stradd(dtext, _("none"));
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, dtext);
+
+ free(dtext);
+
+ /* Champ "p_align" */
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment alignment"));
+
+ }
+ else
+ {
+ /* Champ "p_flags" */
+
+ dtext = strdup(_("Segment flags: "));
+ filled = false;
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_R)
+ {
+ dtext = stradd(dtext, "R");
+ filled = true;
+ }
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_W)
+ {
+ dtext = stradd(dtext, "W");
+ filled = true;
+ }
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_X)
+ {
+ dtext = stradd(dtext, "X");
+ filled = true;
+ }
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_MASKOS)
+ /* TODO */;
+
+ if (ELF_PHDR(format, phdr, p_flags) & PF_MASKPROC)
+ /* TODO */;
+
+ if (!filled)
+ dtext = stradd(dtext, _("none"));
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, dtext);
+
+ free(dtext);
+
+ /* Champ "p_offset" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment file offset"));
+
+ /* Champ "p_vaddr" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment virtual address"));
+
+ /* Champ "p_paddr" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment physical address"));
+
+ /* Champ "p_filesz" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment size in file"));
+
+ /* Champ "p_memsz" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment size in memory"));
+
+ /* Champ "p_align" */
+
+ instr = g_raw_instruction_new_array(content, MDS_64_BITS, 1, pos, length, format->endian);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, _("Segment alignment"));
+
+ }
+
+ }
+
+ return true;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : format = description de l'exécutable à compléter. *
+* *
+* Description : Charge tous les symboles liés aux en-têtes de section ELF. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static bool annotate_elf_section_header_table(GElfFormat *format)
+{
+ const bin_t *content; /* Contenu binaire à lire */
+ off_t length; /* Taille totale du contenu */
+ off_t offset; /* Tête de lecture du bbinaire */
+ vmpa2t *pos; /* Localisation des symboles */
+ uint16_t e_shnum; /* Nombre d'éléments 'Program' */
+ uint16_t i; /* Boucle de parcours */
+ elf_shdr shdr; /* En-tête de programme ELF */
+ ImmOperandDisplay disp; /* Afficahge de valeur */
+ const char *text; /* Texte constant à insérer */
+ GArchInstruction *instr; /* Instruction décodée */
+ GArchOperand *operand; /* Opérande à venir modifier */
+ GDbComment *comment; /* Définition de commentaire */
+ GBinSymbol *symbol; /* Symbole à intégrer */
+ char *dtext; /* Texte dynamique à créer */
+ bool filled; /* Suivi de mise en place */
+
+ content = G_BIN_FORMAT(format)->content;
+ length = G_BIN_FORMAT(format)->length;
+
+ offset = ELF_HDR(format, format->header, e_shoff);
+
+ pos = make_vmpa(offset, 0x9900);
+
+ e_shnum = ELF_HDR(format, format->header, e_shnum);
+
+ for (i = 0; i < e_shnum; i++)
+ {
+ if (!read_elf_section_header(format, offset, &shdr))
+ break;
+
+ /* Champ "sh_name" */
+
+ text = _("Section name");
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, IOD_DEC);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+ /* Champ "sh_type" */
+
+ disp = IOD_DEC;
+
+ switch (ELF_SHDR(format, shdr, sh_type))
+ {
+ case SHT_NULL:
+ text = _("Section type: unused");
+ break;
+ case SHT_PROGBITS:
+ text = _("Section type: program data");
+ break;
+ case SHT_SYMTAB:
+ text = _("Section type: symbol table");
+ break;
+ case SHT_STRTAB:
+ text = _("Section type: string table");
+ break;
+ case SHT_RELA:
+ text = _("Section type: relocation entries with addends");
+ break;
+ case SHT_HASH:
+ text = _("Section type: symbol hash table");
+ break;
+ case SHT_DYNAMIC:
+ text = _("Section type: dynamic linking information");
+ break;
+ case SHT_NOTE:
+ text = _("Section type: notes");
+ break;
+ case SHT_NOBITS:
+ text = _("Section type: program space with no data (bss)");
+ break;
+ case SHT_REL:
+ text = _("Section type: relocation entries, no addends");
+ break;
+ case SHT_SHLIB:
+ text = _("Section type: reserved");
+ break;
+ case SHT_DYNSYM:
+ text = _("Section type: dynamic linker symbol table");
+ break;
+ case SHT_INIT_ARRAY:
+ text = _("Section type: array of constructors");
+ break;
+ case SHT_FINI_ARRAY:
+ text = _("Section type: array of destructors");
+ break;
+ case SHT_PREINIT_ARRAY:
+ text = _("Section type: array of pre-constructors");
+ break;
+ case SHT_GROUP:
+ text = _("Section type: section group");
+ break;
+ case SHT_SYMTAB_SHNDX:
+ text = _("Section type: extended section indeces");
+ break;
+ case SHT_LOOS ... SHT_HIOS:
+ disp = IOD_HEX;
+ switch (ELF_SHDR(format, shdr, sh_type))
+ {
+ case SHT_GNU_ATTRIBUTES:
+ text = _("Section type: object attributes");
+ break;
+ case SHT_GNU_HASH:
+ text = _("Section type: GNU-style hash table");
+ break;
+ case SHT_GNU_LIBLIST:
+ text = _("Section type: prelink library list");
+ break;
+ case SHT_CHECKSUM:
+ text = _("Section type: checksum for DSO content");
+ break;
+ case SHT_LOSUNW ... SHT_HISUNW:
+ switch (ELF_SHDR(format, shdr, sh_type))
+ {
+ case SHT_SUNW_move:
+ text = _("Section type: SHT_SUNW_move");
+ break;
+ case SHT_SUNW_COMDAT:
+ text = _("Section type: SHT_SUNW_COMDAT");
+ break;
+ case SHT_SUNW_syminfo:
+ text = _("Section type: SHT_SUNW_syminfo");
+ break;
+ case SHT_GNU_verdef:
+ text = _("Section type: version definition section");
+ break;
+ case SHT_GNU_verneed:
+ text = _("Section type: version needs section");
+ break;
+ case SHT_GNU_versym:
+ text = _("Section type: version symbol table");
+ break;
+ default:
+ text = _("Section type: Sun-specific");
+ break;
+ }
+ break;
+ default:
+ text = _("Section type: OS-specific");
+ break;
+ }
+ break;
+ case SHT_LOPROC ... SHT_HIPROC:
+ disp = IOD_HEX;
+ text = _("Section type: processor-specific");
+ break;
+ case SHT_LOUSER ... SHT_HIUSER:
+ disp = IOD_HEX;
+ text = _("Section type: application-specific");
+ break;
+ }
+
+ instr = g_raw_instruction_new_array(content, MDS_32_BITS, 1, pos, length, format->endian);
+
+ SET_IMM_DISPLAY(instr, operand, 0, disp);
+
+ ADD_RAW_AS_SYM(format, symbol, pos, instr, comment, text);
+
+
+
+
+
+
+
+
+
+
+
+ }
+
+ return true;
+
+}
+
+
+
/* ---------------------------------------------------------------------------------- */
/* DETAIL DES SYMBOLES INTERNES */
/* ---------------------------------------------------------------------------------- */
diff --git a/src/format/format.c b/src/format/format.c
index 8771c46..4b5dfb5 100644
--- a/src/format/format.c
+++ b/src/format/format.c
@@ -193,9 +193,6 @@ const bin_t *g_binary_format_get_content(const GBinFormat *format, off_t *length
void g_binary_format_add_symbol(GBinFormat *format, GBinSymbol *symbol)
{
-
- printf("current :: %d (%p)\n", (int)format->symbols_count, format->symbols);
-
format->symbols = (GBinSymbol **)realloc(format->symbols,
++format->symbols_count * sizeof(GBinSymbol *));
diff --git a/src/format/symbol.c b/src/format/symbol.c
index b478dc7..f1183cb 100644
--- a/src/format/symbol.c
+++ b/src/format/symbol.c
@@ -47,6 +47,8 @@ struct _GBinSymbol
} extra;
+ GDbComment *comment; /* Eventuel commentaire lié */
+
};
/* Symbole d'exécutable (classe) */
@@ -203,14 +205,25 @@ const vmpa2t *g_binary_symbol_get_address2(const GBinSymbol *symbol)
{
const vmpa2t *result; /* Localisation à retourner */
+ result = NULL;
+
switch (symbol->type)
{
case STP_DATA:
result = g_arch_instruction_get_location2(symbol->extra.instr, NULL);
break;
+ default:
+ result = NULL;
+ break;
+
}
+
+ if (result == NULL)
+ printf("got addr=%p for symbol=%p (data=%d)\n", result, symbol, symbol->type == STP_DATA);
+
+
return result;
}
@@ -293,7 +306,7 @@ void g_binary_symbol_attach_routine(GBinSymbol *symbol, GBinRoutine *routine)
/******************************************************************************
* *
-* Paramètres : symbol = symbole à venir consulter. *
+* Paramètres : symbol = symbole à venir manipuler. *
* instr = représentation du symbole associé. *
* *
* Description : Attache l'instruction associée au symbole. *
@@ -330,3 +343,42 @@ GArchInstruction *g_binary_symbol_get_instruction(const GBinSymbol *symbol)
return symbol->extra.instr;
}
+
+
+/******************************************************************************
+* *
+* Paramètres : symbol = symbole à venir manipuler. *
+* comment = commentaire construit à propos du symbole. *
+* *
+* Description : Ajoute un commentaire facultatif au symbole. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+void g_binary_symbol_set_comment(GBinSymbol *symbol, GDbComment *comment)
+{
+ symbol->comment = comment;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : symbol = symbole à venir consulter. *
+* *
+* Description : Fournit l'éventuel commentaire associé au symbole. *
+* *
+* Retour : - *
+* *
+* Remarques : Il n'y a pas de transfert de propriété ici ! *
+* *
+******************************************************************************/
+
+GDbComment *g_binary_symbol_get_comment(const GBinSymbol *symbol)
+{
+ return symbol->comment;
+
+}
diff --git a/src/format/symbol.h b/src/format/symbol.h
index bfbf541..407375f 100644
--- a/src/format/symbol.h
+++ b/src/format/symbol.h
@@ -29,6 +29,7 @@
#include "../analysis/routine.h"
+#include "../analysis/db/items/comment.h"
@@ -92,6 +93,36 @@ void g_binary_symbol_attach_instruction(GBinSymbol *, GArchInstruction *);
/* Fournit l'éventuelle instruction associée au symbole. */
GArchInstruction *g_binary_symbol_get_instruction(const GBinSymbol *);
+/* Ajoute un commentaire facultatif au symbole. */
+void g_binary_symbol_set_comment(GBinSymbol *, GDbComment *);
+
+/* Fournit l'éventuel commentaire associé au symbole. */
+GDbComment *g_binary_symbol_get_comment(const GBinSymbol *);
+
+
+/**
+ * Confort pour l'ajout de symboles basés sur des formats.
+ */
+
+#define SET_IMM_DISPLAY(_ins, _op, _idx, _dsp) \
+ do \
+ { \
+ _op = g_arch_instruction_get_operand(_ins, _idx); \
+ g_imm_operand_set_display(G_IMM_OPERAND(_op), _dsp); \
+ } \
+ while (0)
+
+#define ADD_RAW_AS_SYM(_fmt, _sym, _pos, _ins, _cmt, _txt) \
+ do \
+ { \
+ _cmt = g_db_comment_new(_pos, _txt, true); \
+ _sym = g_binary_symbol_new(STP_DATA, NULL, 0); \
+ g_binary_symbol_attach_instruction(_sym, _ins); \
+ g_binary_symbol_set_comment(_sym, _cmt); \
+ g_binary_format_add_symbol(G_BIN_FORMAT(_fmt), _sym); \
+ } \
+ while (0)
+
#endif /* _FORMAT_SYMBOL_H */