diff options
| -rw-r--r-- | ChangeLog | 36 | ||||
| -rw-r--r-- | Makefile.am | 2 | ||||
| -rw-r--r-- | configure.ac | 2 | ||||
| -rw-r--r-- | plugins/Makefile.am | 2 | ||||
| -rw-r--r-- | plugins/stackvars/Makefile.am | 15 | ||||
| -rw-r--r-- | plugins/stackvars/operand.c | 158 | ||||
| -rw-r--r-- | plugins/stackvars/operand.h | 57 | ||||
| -rw-r--r-- | plugins/stackvars/stackvars.c | 260 | ||||
| -rw-r--r-- | plugins/stackvars/stackvars.h | 49 | ||||
| -rw-r--r-- | src/analysis/binary.c | 72 | ||||
| -rw-r--r-- | src/arch/instruction.c | 47 | ||||
| -rw-r--r-- | src/arch/instruction.h | 6 | ||||
| -rw-r--r-- | src/arch/x86/operand.c | 61 | ||||
| -rw-r--r-- | src/arch/x86/operand.h | 14 | ||||
| -rw-r--r-- | src/plugins/pglist.c | 35 | ||||
| -rw-r--r-- | src/plugins/pglist.h | 3 | ||||
| -rw-r--r-- | src/plugins/plugin-def.h | 11 | ||||
| -rw-r--r-- | src/plugins/plugin.c | 19 | ||||
| -rw-r--r-- | src/plugins/plugin.h | 4 | 
19 files changed, 794 insertions, 59 deletions
| @@ -1,3 +1,39 @@ +09-07-20  Cyrille Bagard <nocbos@gmail.com> + +	* configure.ac: +	Add the new Makefiles from the 'plugins' and 'plugins/stackvars' +	directories to AC_CONFIG_FILES. + +	* Makefile.am: +	Add plugins to SUBDIRS. + +	* plugins/Makefile.am: +	* plugins/stackvars/Makefile.am: +	* plugins/stackvars/operand.c: +	* plugins/stackvars/operand.h: +	* plugins/stackvars/stackvars.c: +	* plugins/stackvars/stackvars.h: +	New entries: encapsulate all recognized variables in the stack using a +	new plugin (need to be continued). + +	* src/analysis/binary.c: +	Remove code and run plugins after disassembling. + +	* src/arch/instruction.c: +	* src/arch/instruction.h: +	Add functions to count or replace operands. + +	* src/arch/x86/operand.c: +	* src/arch/x86/operand.h: +	Provide functions to access the internal fields of the ModRM operands. + +	* src/plugins/pglist.c: +	* src/plugins/pglist.h: +	* src/plugins/plugin.c: +	* src/plugins/plugin-def.h: +	* src/plugins/plugin.h: +	Change a little bit the way plugins are loaded and managed. +  09-07-18  Cyrille Bagard <nocbos@gmail.com>  	* src/analysis/binary.c: diff --git a/Makefile.am b/Makefile.am index ea7183a..b0caf58 100644 --- a/Makefile.am +++ b/Makefile.am @@ -1,6 +1,6 @@  EXTRA_DIST = config.rpath  config.rpath  config.rpath  ChangeLog -SUBDIRS = pixmaps src +SUBDIRS = pixmaps plugins src  ACLOCAL_AMFLAGS = -I m4 diff --git a/configure.ac b/configure.ac index 350cea1..88b680d 100644 --- a/configure.ac +++ b/configure.ac @@ -229,6 +229,8 @@ AC_CONFIG_COMMANDS([marshal], [echo "VOID:UINT64,UINT64" > src/gtkext/iodamarsha  AC_CONFIG_FILES([Makefile                   pixmaps/Makefile +                 plugins/Makefile +                 plugins/stackvars/Makefile                   src/Makefile                   src/analysis/Makefile                   src/arch/Makefile diff --git a/plugins/Makefile.am b/plugins/Makefile.am new file mode 100644 index 0000000..f2c6152 --- /dev/null +++ b/plugins/Makefile.am @@ -0,0 +1,2 @@ + +SUBDIRS = stackvars diff --git a/plugins/stackvars/Makefile.am b/plugins/stackvars/Makefile.am new file mode 100644 index 0000000..a29c58a --- /dev/null +++ b/plugins/stackvars/Makefile.am @@ -0,0 +1,15 @@ + +lib_LTLIBRARIES = libstackvars.la + +libstackvars_la_SOURCES =				\ +	operand.h operand.c					\ +	stackvars.h stackvars.c + +libstackvars_la_CFLAGS = $(AM_CFLAGS) + + +INCLUDES = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS) -I../../src + +AM_CPPFLAGS =  + +AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS) diff --git a/plugins/stackvars/operand.c b/plugins/stackvars/operand.c new file mode 100644 index 0000000..321312a --- /dev/null +++ b/plugins/stackvars/operand.c @@ -0,0 +1,158 @@ + +/* OpenIDA - Outil d'analyse de fichiers binaires + * operand.c - opérandes de substitution pour variables + * + * Copyright (C) 2009 Cyrille Bagard + * + *  This file is part of OpenIDA. + * + *  OpenIDA 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. + * + *  OpenIDA 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 "operand.h" + + +#include <malloc.h> +#include <stdio.h> + + +#include <arch/operand-int.h> + + + +/* Définition d'un opérande de substitution pour variable de pile (instance) */ +struct _GStackVarOperand +{ +    GArchOperand parent;                    /* Instance parente            */ + +    const GArchOperand *child;              /* Opérand d'origine substitué */ + +}; + + +/* Définition d'un opérande de substitution pour variable de pile (classe) */ +struct _GStackVarOperandClass +{ +    GArchOperandClass parent;               /* Classe parente              */ + +}; + + +/* Initialise la classe des opérandes de substitution. */ +static void g_stack_var_operand_class_init(GStackVarOperandClass *); + +/* Initialise l'instande d'un opérandes de substitution. */ +static void g_stack_var_operand_init(GStackVarOperand *); + +/* Traduit un opérande en version humainement lisible. */ +static char *g_stack_var_operand_get_text(const GStackVarOperand *, const exe_format *, AsmSyntax); + + +/* Indique le type défini pour un opérande de substitution pour variable de pile. */ +G_DEFINE_TYPE(GStackVarOperand, g_stack_var_operand, G_TYPE_ARCH_OPERAND); + + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : klass = classe à initialiser.                                * +*                                                                             * +*  Description : Initialise la classe des opérandes de substitution.          * +*                                                                             * +*  Retour      : -                                                            * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +static void g_stack_var_operand_class_init(GStackVarOperandClass *klass) +{ + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : operand = instance à initialiser.                            * +*                                                                             * +*  Description : Initialise l'instande d'un opérandes de substitution.        * +*                                                                             * +*  Retour      : -                                                            * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +static void g_stack_var_operand_init(GStackVarOperand *operand) +{ +    GArchOperand *parent;                   /* Instance parente            */ + +    parent = G_ARCH_OPERAND(operand); + +    parent->get_text = (get_operand_text_fc)g_stack_var_operand_get_text; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : child = opérande d'origine à substituer.                     * +*                                                                             * +*  Description : Crée un opérande de substitution pour variable de pile.      * +*                                                                             * +*  Retour      : Instruction mise en place.                                   * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +GArchOperand *g_stack_var_operand_new(const GArchOperand *child) +{ +    GStackVarOperand *result;                    /* Opérande à retourner        */ + +    result = g_object_new(G_TYPE_STACK_VAR_OPERAND, NULL); + +    result->child = child; + +    return result; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : operand = opérande à traiter.                                * +*                format  = format du binaire manipulé.                        * +*                syntax  = type de représentation demandée.                   * +*                                                                             * +*  Description : Traduit un opérande en version humainement lisible.          * +*                                                                             * +*  Retour      : Chaîne de caractères à libérer de la mémoire.                * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +static char *g_stack_var_operand_get_text(const GStackVarOperand *operand, const exe_format *format, AsmSyntax syntax) +{ +    char *result;                           /* Chaîne à retourner          */ + +    result = (char *)calloc(19, sizeof(char)); + +    snprintf(result, 19, "[<b>varX</b>]"); + +    return result; + +} diff --git a/plugins/stackvars/operand.h b/plugins/stackvars/operand.h new file mode 100644 index 0000000..d0f8120 --- /dev/null +++ b/plugins/stackvars/operand.h @@ -0,0 +1,57 @@ + +/* OpenIDA - Outil d'analyse de fichiers binaires + * operand.h - prototypes pour les opérandes de substitution pour variables + * + * Copyright (C) 2009 Cyrille Bagard + * + *  This file is part of OpenIDA. + * + *  OpenIDA 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. + * + *  OpenIDA 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/>. + */ + + +#ifndef _PLUGINS_STACKVARS_OPERAND_H +#define _PLUGINS_STACKVARS_OPERAND_H + + +#include <glib-object.h> +#include <stdbool.h> + + +#include <arch/operand.h> + + + +#define G_TYPE_STACK_VAR_OPERAND                  g_stack_var_operand_get_type() +#define G_STACK_VAR_OPERAND(obj)                  (G_TYPE_CHECK_INSTANCE_CAST((obj), g_stack_var_operand_get_type(), GStackVarOperand)) +#define G_IS_STACK_VAR_OPERAND(obj)               (G_TYPE_CHECK_INSTANCE_TYPE((obj), g_stack_var_operand_get_type())) +#define G_STACK_VAR_OPERAND_GET_IFACE(inst)       (G_TYPE_INSTANCE_GET_INTERFACE((inst), g_stack_var_operand_get_type(), GStackVarOperandIface)) + + +/* Définition d'un opérande de substitution pour variable de pile (instance) */ +typedef struct _GStackVarOperand GStackVarOperand; + +/* Définition d'un opérande de substitution pour variable de pile (classe) */ +typedef struct _GStackVarOperandClass GStackVarOperandClass; + + +/* Indique le type défini pour un opérande de substitution pour variable de pile. */ +GType g_stack_var_operand_get_type(void); + +/* Crée un opérande de substitution pour variable de pile. */ +GArchOperand *g_stack_var_operand_new(const GArchOperand *); + + + +#endif  /* _PLUGINS_STACKVARS_OPERAND_H */ diff --git a/plugins/stackvars/stackvars.c b/plugins/stackvars/stackvars.c new file mode 100644 index 0000000..5f34119 --- /dev/null +++ b/plugins/stackvars/stackvars.c @@ -0,0 +1,260 @@ + +/* OpenIDA - Outil d'analyse de fichiers binaires + * stackvars.c - substitution des emplacements de pile par des variables + * + * Copyright (C) 2009 Cyrille Bagard + * + *  This file is part of OpenIDA. + * + *  OpenIDA 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. + * + *  OpenIDA 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 "stackvars.h" + + +#include <analysis/line_code.h> +#include <analysis/prototype.h> +#include <arch/x86/operand.h> +#include <format/exe_format.h> + + +#include "operand.h" + + + +/* Effectue tous les remplacements possibles dans une routine. */ +static bool replace_stack_vars_in_routine(GBinRoutine *, GRenderingLine *); + +/* Effectue d'éventuels remplacements dans une instruction. */ +static bool replace_stack_vars_in_instruction(GArchInstruction *); + +/* Effectue d'éventuels remplacements dans un opérande. */ +static GArchOperand *replace_stack_vars_in_operand(const GArchOperand *); + + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : ref = espace de référencement global.                        * +*                                                                             * +*  Description : Initialise le greffon pour les bornes de routine.            * +*                                                                             * +*  Retour      : true.                                                        * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +G_MODULE_EXPORT bool init_plugin(GObject *ref) +{ +    return true; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : -                                                            * +*                                                                             * +*  Description : Fournit une indication sur le type d'opération(s) menée(s).  * +*                                                                             * +*  Retour      : Description d'une action.                                    * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +G_MODULE_EXPORT PluginAction get_plugin_action(void) +{ +    return PGA_CODE_PROCESS; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : binary = représentation binaire à traiter.                   * +*                action = action attendue.                                    * +*                                                                             * +*  Description : Exécute une action définie sur un binaire chargé.            * +*                                                                             * +*  Retour      : true si une action a été menée, false sinon.                 * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +G_MODULE_EXPORT bool execute_action_on_binary(openida_binary *binary, PluginAction action) +{ +    bool result;                            /* Bilan à retourner           */ +    GRenderingLine *lines;                  /* Lignes de rendu             */ +    exe_format *format;                     /* Format du binaire fourni    */ +    GBinRoutine **routines;                 /* Liste des routines trouvées */ +    size_t routines_count;                  /* Nombre de ces routines      */ +    size_t i;                               /* Boucle de parcours          */ + +    result = false; + +    printf(" ------------- exec stackvars !!!\n"); + +    lines = get_openida_binary_lines(binary); + +    format = get_openida_binary_format(binary); +    routines = get_all_exe_routines(format, &routines_count); + +    for (i = 0; i < routines_count; i++) +        result |= replace_stack_vars_in_routine(routines[i], lines); + +    return result; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : routine = routine dont le code est à analyser.               * +*                lines   = ensemble des lignes de rendu.                      * +*                                                                             * +*  Description : Effectue tous les remplacements possibles dans une routine.  * +*                                                                             * +*  Retour      : true si une action a été menée, false sinon.                 * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +static bool replace_stack_vars_in_routine(GBinRoutine *routine, GRenderingLine *lines) +{ +    bool result;                            /* Bilan à retourner           */ +    vmpa_t start;                           /* Adresse de début de routine */ +    vmpa_t end;                             /* Adresse de fin de routine   */ +    GRenderingLine *iter;                   /* Boucle de parcours          */ +    GArchInstruction *instr;                /* Instruction à ausculter     */ + +    result = false; + +    start = g_binary_routine_get_address(routine); +    end = start + g_binary_routine_get_size(routine); + +     + +    printf(" +++ processing '%s'\n", g_binary_routine_get_name(routine)); + + + +    for (iter = g_rendering_line_find_by_address(lines, NULL, start); +         iter != NULL && get_rendering_line_address(iter) < end; +         iter = g_rendering_line_get_next_iter(lines, iter, NULL)) +    { +        if (!G_IS_CODE_LINE(iter)) continue; + +        instr = g_code_line_get_instruction(G_CODE_LINE(iter)); + +        result |= replace_stack_vars_in_instruction(instr); + +    } + +    return result; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : instr = instruction dont le contenu peut être modifié.       * +*                                                                             * +*  Description : Effectue d'éventuels remplacements dans une instruction.     * +*                                                                             * +*  Retour      : true si une action a été menée, false sinon.                 * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +static bool replace_stack_vars_in_instruction(GArchInstruction *instr) +{ +    bool result;                            /* Bilan à renvoyer            */ +    size_t opcount;                         /* Nombre d'opérandes          */ +    size_t i;                               /* Boucle de parcours          */ +    const GArchOperand *operand;            /* Opérande de l'instruction   */ +    GArchOperand *new;                      /* Opérande d'encapsulation    */ + +    result = false; + +    opcount = g_arch_instruction_count_operands(instr); + +    for (i = 0; i < opcount; i++) +    { +        operand = g_arch_instruction_get_operand(instr, i); +        new = replace_stack_vars_in_operand(operand); + +        if (new != NULL) +        { +            g_arch_instruction_replace_operand(instr, new, operand); + +            result = true; + +        } + +    } + +    return result; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : operand = opérande dont le contenu est à analyser.           * +*                                                                             * +*  Description : Effectue d'éventuels remplacements dans un opérande.         * +*                                                                             * +*  Retour      : Nouvel opérande de remplacemet ou NULL si aucun besoin.      * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +static GArchOperand *replace_stack_vars_in_operand(const GArchOperand *operand) +{ +    GArchOperand *result;                   /* Encapsulation à retourner   */ +    uint8_t scale;                          /* Puissance de deux           */ +    x86_register *index;                    /* Registre servant d'indice   */ +    x86_register *base;                     /* Registre de base            */ +    GImmOperand *displacement;              /* Décallage supplémentaire    */ + +    result = NULL; + +    if (G_IS_X86_MOD_RM_OPERAND(operand)) +    { +        g_x86_mod_rm_operand_get_scale_and_index(G_X86_MOD_RM_OPERAND(operand), &scale, &index); +        base = g_x86_mod_rm_operand_get_base(G_X86_MOD_RM_OPERAND(operand)); +        displacement = g_x86_mod_rm_operand_get_displacement(G_X86_MOD_RM_OPERAND(operand)); + +        if (scale == 0 && is_x86_register_base_pointer(index) && base == NULL) +        { + +            printf(" [+] found one ebp !!\n"); +            result = g_stack_var_operand_new(operand); + +        } + + + +    } + +    return result; + +} diff --git a/plugins/stackvars/stackvars.h b/plugins/stackvars/stackvars.h new file mode 100644 index 0000000..ef7e548 --- /dev/null +++ b/plugins/stackvars/stackvars.h @@ -0,0 +1,49 @@ + +/* OpenIDA - Outil d'analyse de fichiers binaires + * stackvars.h - prototypes pour la substitution des emplacements de pile par des variables + * + * Copyright (C) 2009 Cyrille Bagard + * + *  This file is part of OpenIDA. + * + *  OpenIDA 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. + * + *  OpenIDA 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/>. + */ + + +#ifndef _PLUGINS_STACKVARS_STACKVARS_H +#define _PLUGINS_STACKVARS_STACKVARS_H + + +#include <glib-object.h> +#include <gmodule.h> +#include <stdbool.h> + + +#include <analysis/binary.h> +#include <plugins/plugin-def.h> + + + +/* Initialise le greffon pour les bornes de routine. */ +G_MODULE_EXPORT bool init_plugin(GObject *); + +/* Fournit une indication sur le type d'opération(s) menée(s). */ +G_MODULE_EXPORT PluginAction get_plugin_action(void); + +/* Exécute une action définie sur un binaire chargé. */ +G_MODULE_EXPORT bool execute_action_on_binary(openida_binary *, PluginAction); + + + +#endif  /* _PLUGINS_STACKVARS_STACKVARS_H */ diff --git a/src/analysis/binary.c b/src/analysis/binary.c index 396dbe0..a24c3d3 100644 --- a/src/analysis/binary.c +++ b/src/analysis/binary.c @@ -566,10 +566,10 @@ void disassemble_openida_binary(openida_binary *binary)      uint64_t routine_offset;                /* Point de départ de routine  */      char *routine_desc;                     /* Prototype d'une routine     */ +    GPluginModule **pglist;                 /* Liste de greffons           */ +    size_t pgcount;                         /* Taille de cette liste       */ -    GPluginModule *disass;                  /* Eventuel greffon de désass. */ -      binary->lines = build_binary_prologue(binary->filename, binary->bin_data, binary->bin_length); @@ -579,56 +579,46 @@ void disassemble_openida_binary(openida_binary *binary) +    parts = /* !!! */get_elf_default_code_parts(binary->format, &parts_count); +    qsort(parts, parts_count, sizeof(bin_part *), compare_bin_parts); -    disass = get_one_plugin_for_action(PGA_DISASSEMBLE); - -    if (0 && disass != NULL) -        binary->lines = g_plugin_module_disassemble_binary_parts(disass, binary); +    printf("PARTS COUNT :: %d\n", parts_count); -    else +    for (i = 0; i < parts_count; i++)      { -        parts = /* !!! */get_elf_default_code_parts(binary->format, &parts_count); -        qsort(parts, parts_count, sizeof(bin_part *), compare_bin_parts); - -        printf("PARTS COUNT :: %d\n", parts_count); - -        for (i = 0; i < parts_count; i++) -        { -            get_bin_part_values(parts[i], &pos, &len, &base); +        get_bin_part_values(parts[i], &pos, &len, &base); -            /* Décodage des instructions */ +        /* Décodage des instructions */ -            start = pos; -            pos = 0; - -            while (pos < len) -            { -                addr = base + pos; +        start = pos; +        pos = 0; +        while (pos < len) +        { +            addr = base + pos; -                instr = g_arch_processor_decode_instruction(binary->proc, &binary->bin_data[start], &pos, len, start, addr); -                line = g_code_line_new(addr, instr, binary->options); -                g_rendering_line_add_to_lines(&binary->lines, line); +            instr = g_arch_processor_decode_instruction(binary->proc, &binary->bin_data[start], &pos, len, start, addr); -            } +            line = g_code_line_new(addr, instr, binary->options); +            g_rendering_line_add_to_lines(&binary->lines, line); -            /* Ajout des prototypes de fonctions */ +        } -            for (k = 0; k < routines_count; k++) -            { -                routine_offset = g_binary_routine_get_address(routines[k]); +        /* Ajout des prototypes de fonctions */ -                if (!(base <= routine_offset && routine_offset < (base + len))) continue; +        for (k = 0; k < routines_count; k++) +        { +            routine_offset = g_binary_routine_get_address(routines[k]); -                routine_desc = g_binary_routine_to_string(routines[k]); +            if (!(base <= routine_offset && routine_offset < (base + len))) continue; -                line = g_comment_line_new(routine_offset, routine_desc, binary->options); -                g_rendering_line_insert_into_lines(&binary->lines, line, true); +            routine_desc = g_binary_routine_to_string(routines[k]); -                free(routine_desc); +            line = g_comment_line_new(routine_offset, routine_desc, binary->options); +            g_rendering_line_insert_into_lines(&binary->lines, line, true); -            } +            free(routine_desc);          } @@ -640,8 +630,18 @@ void disassemble_openida_binary(openida_binary *binary)      line = g_rendering_line_find_by_address(binary->lines, NULL, get_exe_entry_point(binary->format));      if (line != NULL) g_rendering_line_add_flag(line, RLF_ENTRY_POINT); +    /* Action post-désassemblage */ +    pglist = get_all_plugins_for_action(PGA_CODE_PROCESS, &pgcount); +    if (pgcount > 0) +    { +        for (i = 0; i < pgcount; i++) +            g_plugin_module_execute_action_on_binary(pglist[i], binary, PGA_CODE_PROCESS); + +        free(pglist); + +    }  } diff --git a/src/arch/instruction.c b/src/arch/instruction.c index e0cea9f..37b2147 100644 --- a/src/arch/instruction.c +++ b/src/arch/instruction.c @@ -202,6 +202,25 @@ void g_arch_instruction_attach_extra_operand(GArchInstruction *instr, GArchOpera  /******************************************************************************  *                                                                             * +*  Paramètres  : instr = instance à consulter.                                * +*                                                                             * +*  Description : Indique la quantité d'opérandes présents dans l'instruction. * +*                                                                             * +*  Retour      : Nombre d'opérandes attachés.                                 * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +size_t g_arch_instruction_count_operands(const GArchInstruction *instr) +{ +    return instr->operands_count; + +} + + +/****************************************************************************** +*                                                                             *  *  Paramètres  : instr = instance à mettre à jour.                            *  *                index = indice de l'opérande concernée.                      *  *                                                                             * @@ -227,6 +246,34 @@ const GArchOperand *g_arch_instruction_get_operand(GArchInstruction *instr, size  /******************************************************************************  *                                                                             * +*  Paramètres  : instr = instance à mettre à jour.                            * +*                new   = nouvelle opérande à attacher.                        * +*                old   = ancienne opérande à détacher.                        * +*                                                                             * +*  Description : Replace un opérande d'une instruction par un autre.          * +*                                                                             * +*  Retour      : -                                                            * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +void g_arch_instruction_replace_operand(GArchInstruction *instr, GArchOperand *new, const GArchOperand *old) +{ +    size_t i;                               /* Boucle de parcours          */ + +    for (i = 0; i < instr->operands_count; i++) +        if (instr->operands[i] == old) +            break; + +    if (i < instr->operands_count) +        instr->operands[i] = new; + +} + + +/****************************************************************************** +*                                                                             *  *  Paramètres  : instr     = instance à mettre à jour.                        *  *                opererand = instruction à venir dissocier.                   *  *                                                                             * diff --git a/src/arch/instruction.h b/src/arch/instruction.h index c0cb9f6..0e6444b 100644 --- a/src/arch/instruction.h +++ b/src/arch/instruction.h @@ -79,9 +79,15 @@ void g_arch_instruction_attach_two_operands(GArchInstruction *, GArchOperand *,  /* Attache un opérande supplémentaire à une instruction. */  void g_arch_instruction_attach_extra_operand(GArchInstruction *, GArchOperand *); +/* Indique la quantité d'opérandes présents dans l'instruction. */ +size_t g_arch_instruction_count_operands(const GArchInstruction *); +  /* Fournit un opérande donné d'une instruction. */  const GArchOperand *g_arch_instruction_get_operand(GArchInstruction *, size_t); +/* Replace un opérande d'une instruction par un autre. */ +void g_arch_instruction_replace_operand(GArchInstruction *, GArchOperand *, const GArchOperand *); +  /* Détache un opérande liée d'une instruction. */  void g_arch_instruction_detach_operand(GArchInstruction *, GArchOperand *); diff --git a/src/arch/x86/operand.c b/src/arch/x86/operand.c index 8f218fc..24613cf 100644 --- a/src/arch/x86/operand.c +++ b/src/arch/x86/operand.c @@ -29,7 +29,6 @@  #include <stdio.h> -#include "registers.h"  #include "../operand.h"  #include "../operand-int.h"  #include "../../common/extstr.h" @@ -654,6 +653,66 @@ static char *g_x86_mod_rm_operand_get_text(const GX86ModRMOperand *operand, cons  } +/****************************************************************************** +*                                                                             * +*  Paramètres  : operand = opérande à consulter.                              * +*                scale   = facteur sous forme de puissance de deux. [OUT      * +*                index   = register principal de l'opérande. [OUT]            * +*                                                                             * +*  Description : Fournit l'indice et l'échelle d'un opérande x86 ModRM.       * +*                                                                             * +*  Retour      : -                                                            * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +void g_x86_mod_rm_operand_get_scale_and_index(const GX86ModRMOperand *operand, uint8_t *scale, const x86_register **index) +{ +    *scale = operand->scale; +    *index = operand->index; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : operand = opérande à consulter.                              * +*                                                                             * +*  Description : Fournit le registre de base d'un opérande x86 ModRM.         * +*                                                                             * +*  Retour      : Registre de base de l'opérande.                              * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +const x86_register *g_x86_mod_rm_operand_get_base(const GX86ModRMOperand *operand) +{ +    return operand->base; + +} + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : operand = opérande à consulter.                              * +*                                                                             * +*  Description : Fournit le décallage supplémentaire d'un opérande x86 ModRM. * +*                                                                             * +*  Retour      : Décallage numérique pour l'opérande.                         * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +const GImmOperand *g_x86_mod_rm_operand_get_displacement(const GX86ModRMOperand *operand) +{ +    return operand->displacement; + +} + +  /* ---------------------------------------------------------------------------------- */  /*                           OPERANDES D'ADRESSES RELATIVES                           */ diff --git a/src/arch/x86/operand.h b/src/arch/x86/operand.h index 9f4db09..cbf2ed2 100644 --- a/src/arch/x86/operand.h +++ b/src/arch/x86/operand.h @@ -30,6 +30,7 @@  #include "../immediate.h"  #include "../instruction.h" +#include "registers.h" @@ -88,9 +89,9 @@ GArchOperand *g_x86_register_operand_new_from_index(bin_t, AsmOperandSize);  #define G_TYPE_X86_MOD_RM_OPERAND                  g_x86_mod_rm_operand_get_type() -#define G_X86_MOD_RM_OPERAND(obj)                  (G_TYPE_CHECK_INSTANCE_CAST((obj), g_x86_mod_rm_operand_get_type(), GX86ModRmOperand)) +#define G_X86_MOD_RM_OPERAND(obj)                  (G_TYPE_CHECK_INSTANCE_CAST((obj), g_x86_mod_rm_operand_get_type(), GX86ModRMOperand))  #define G_IS_X86_MOD_RM_OPERAND(obj)               (G_TYPE_CHECK_INSTANCE_TYPE((obj), g_x86_mod_rm_operand_get_type())) -#define G_X86_MOD_RM_OPERAND_GET_IFACE(inst)       (G_TYPE_INSTANCE_GET_INTERFACE((inst), g_x86_mod_rm_operand_get_type(), GX86ModRmOperandIface)) +#define G_X86_MOD_RM_OPERAND_GET_IFACE(inst)       (G_TYPE_INSTANCE_GET_INTERFACE((inst), g_x86_mod_rm_operand_get_type(), GX86ModRMOperandIface))  /* Définition d'un opérande x86 de type ModRM (instance) */ @@ -106,6 +107,15 @@ GType g_x86_mod_rm_operand_get_type(void);  /* Crée un opérande x86 de type ModRM. */  GArchOperand *g_x86_mod_rm_operand_new(const bin_t *, off_t *, off_t, AsmOperandSize); +/* Fournit l'indice et l'échelle d'un opérande x86 ModRM. */ +void g_x86_mod_rm_operand_get_scale_and_index(const GX86ModRMOperand *operand, uint8_t *, const x86_register **); + +/* Fournit le registre de base d'un opérande x86 ModRM. */ +const x86_register *g_x86_mod_rm_operand_get_base(const GX86ModRMOperand *); + +/* Fournit le décallage supplémentaire d'un opérande x86 ModRM. */ +const GImmOperand *g_x86_mod_rm_operand_get_displacement(const GX86ModRMOperand *); +  /* ------------------------- OPERANDES D'ADRESSES RELATIVES ------------------------- */ diff --git a/src/plugins/pglist.c b/src/plugins/pglist.c index 85421e6..6d47f57 100644 --- a/src/plugins/pglist.c +++ b/src/plugins/pglist.c @@ -77,7 +77,7 @@ bool init_all_plugins(GObject *ref)  {      _list.ref = ref; -    browse_directory_for_plugins(&_list, PACKAGE_SOURCE_DIR "/src/plugins"); +    browse_directory_for_plugins(&_list, PACKAGE_SOURCE_DIR "/plugins");      return true; @@ -200,3 +200,36 @@ GPluginModule *get_one_plugin_for_action(PluginAction action)      return result;  } + + +/****************************************************************************** +*                                                                             * +*  Paramètres  : action = fonctionnalité recherchée.                          * +*                count  = nombre de greffons trouvés. [OUT]                   * +*                                                                             * +*  Description : Founit less greffons offrant le service demandé.             * +*                                                                             * +*  Retour      : Liste de greffons correspondants à libérer de la mémoire.    * +*                                                                             * +*  Remarques   : -                                                            * +*                                                                             * +******************************************************************************/ + +GPluginModule **get_all_plugins_for_action(PluginAction action, size_t *count) +{ +    GPluginModule **result;                 /* Greffon à retourner         */ +    size_t i;                               /* Boucle de parcours          */ + +    result = NULL; +    *count = 0; + +    for (i = 0; i < _list.plugins_count; i++) +        if (g_plugin_module_get_action(_list.plugins[i]) & action) +        { +            result = (GPluginModule **)realloc(result, ++(*count) * sizeof(GPluginModule *)); +            result[*count - 1] = _list.plugins[i]; +        } + +    return result; + +} diff --git a/src/plugins/pglist.h b/src/plugins/pglist.h index 4aa77cd..36b998e 100644 --- a/src/plugins/pglist.h +++ b/src/plugins/pglist.h @@ -41,6 +41,9 @@ bool init_all_plugins(GObject *);  /* Founit un greffon offrant le service demandé. */  GPluginModule *get_one_plugin_for_action(PluginAction); +/* Founit less greffons offrant le service demandé. */ +GPluginModule **get_all_plugins_for_action(PluginAction, size_t *); +  #endif  /* _PLUGINS_PGLIST_H */ diff --git a/src/plugins/plugin-def.h b/src/plugins/plugin-def.h index 68167e2..44dd3fa 100644 --- a/src/plugins/plugin-def.h +++ b/src/plugins/plugin-def.h @@ -27,14 +27,15 @@  #include "../analysis/binary.h" -#include "../analysis/line.h"  /* Action(s) menée(s) par le greffon */  typedef enum _PluginAction  { -    PGA_DISASSEMBLE     = (1 << 0)          /* Désassemblage (non trivial) */ +    PGA_DISASSEMBLE     = (1 << 0),         /* Désassemblage (non trivial) */ + +    PGA_CODE_PROCESS    = (1 << 1)          /* Traitement du code existant */  } PluginAction; @@ -45,10 +46,8 @@ typedef enum _PluginAction  /* Fournit une indication sur le type d'opération(s) menée(s). */  typedef PluginAction (* get_plugin_action_fc) (void); - - -/* S'occupe du désassemblage (pur) de code binaire. */ -typedef GRenderingLine * (* disassemble_binary_parts_fc) (openida_binary *); +/* Exécute une action définie sur un binaire chargé. */ +typedef bool (* execute_action_on_binary_fc) (openida_binary *, PluginAction); diff --git a/src/plugins/plugin.c b/src/plugins/plugin.c index 80daa74..0165dfa 100644 --- a/src/plugins/plugin.c +++ b/src/plugins/plugin.c @@ -48,7 +48,7 @@ struct _GPluginModule      init_plugin_fc init;                    /* Procédure d'initialisation  */ -    disassemble_binary_parts_fc disassemble;/* Fonction de désassemblage   */ +    execute_action_on_binary_fc exec_on_bin;/* Action sur un binaire       */  }; @@ -145,11 +145,9 @@ GPluginModule *g_plugin_module_new(const gchar *filename, GObject *ref)      result->action = __get_action(); - -    /* ... */ -    if (result->action & PGA_DISASSEMBLE) +    if (result->action & (PGA_DISASSEMBLE | PGA_CODE_PROCESS))      { -        if (!g_module_symbol(result->module, "disassemble_binary_parts", (gpointer *)&result->disassemble)) +        if (!g_module_symbol(result->module, "execute_action_on_binary", (gpointer *)&result->exec_on_bin))          {              printf("Err plugin disass sym\n");              //g_object_destroy(result); @@ -202,18 +200,19 @@ PluginAction g_plugin_module_get_action(const GPluginModule *plugin)  /******************************************************************************  *                                                                             *  *  Paramètres  : plugin = greffon à consulter.                                * -*                binary = binaire dont le contenu est à désassembler.         * +*                binary = binaire dont le contenu est à traiter.              * +*                action = action attendue.                                    *  *                                                                             * -*  Description : S'occupe du désassemblage (pur) de code binaire.             * +*  Description : Exécute une action définie sur un binaire chargé.            *  *                                                                             * -*  Retour      : Lignes de code pour la représentation à insérer.             * +*  Retour      : true si une action a été menée, false sinon.                 *  *                                                                             *  *  Remarques   : -                                                            *  *                                                                             *  ******************************************************************************/ -GRenderingLine *g_plugin_module_disassemble_binary_parts(const GPluginModule *plugin, openida_binary *binary) +bool g_plugin_module_execute_action_on_binary(const GPluginModule *plugin, openida_binary *binary, PluginAction action)  { -    return plugin->disassemble(binary); +    return plugin->exec_on_bin(binary, action);  } diff --git a/src/plugins/plugin.h b/src/plugins/plugin.h index 455f17c..032f699 100644 --- a/src/plugins/plugin.h +++ b/src/plugins/plugin.h @@ -57,8 +57,8 @@ GPluginModule *g_plugin_module_new(const gchar *, GObject *);  /* Indique les opérations offertes par un greffon donné. */  PluginAction g_plugin_module_get_action(const GPluginModule *); -/* S'occupe du désassemblage (pur) de code binaire. */ -GRenderingLine *g_plugin_module_disassemble_binary_parts(const GPluginModule *, openida_binary *); +/* Exécute une action définie sur un binaire chargé. */ +bool g_plugin_module_execute_action_on_binary(const GPluginModule *, openida_binary *, PluginAction); | 
