summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog140
-rw-r--r--configure.ac3
-rw-r--r--plugins/pychrysa/Makefile.am17
-rw-r--r--plugins/pychrysa/analysis/Makefile.am19
-rw-r--r--plugins/pychrysa/analysis/binaries/file.c2
-rw-r--r--plugins/pychrysa/analysis/binaries/module.c24
-rw-r--r--plugins/pychrysa/analysis/binary.c276
-rw-r--r--plugins/pychrysa/analysis/block.c99
-rw-r--r--plugins/pychrysa/analysis/block.h5
-rw-r--r--plugins/pychrysa/analysis/blocks/flow.c103
-rw-r--r--plugins/pychrysa/analysis/blocks/flow.h3
-rw-r--r--plugins/pychrysa/analysis/blocks/module.c37
-rw-r--r--plugins/pychrysa/analysis/blocks/module.h2
-rw-r--r--plugins/pychrysa/analysis/blocks/virtual.c74
-rw-r--r--plugins/pychrysa/analysis/blocks/virtual.h3
-rw-r--r--plugins/pychrysa/analysis/db/Makefile.am3
-rw-r--r--plugins/pychrysa/analysis/db/items/comment.c5
-rw-r--r--plugins/pychrysa/analysis/db/items/module.c18
-rw-r--r--plugins/pychrysa/analysis/db/module.c19
-rw-r--r--plugins/pychrysa/analysis/module.c104
-rw-r--r--plugins/pychrysa/analysis/roptions.c276
-rw-r--r--plugins/pychrysa/analysis/routine.c190
-rw-r--r--plugins/pychrysa/analysis/routine.h5
-rw-r--r--plugins/pychrysa/arch/Makefile.am7
-rw-r--r--plugins/pychrysa/arch/arm/Makefile.am20
-rw-r--r--plugins/pychrysa/arch/arm/instruction.c120
-rw-r--r--plugins/pychrysa/arch/arm/instruction.h42
-rw-r--r--plugins/pychrysa/arch/arm/module.c96
-rw-r--r--plugins/pychrysa/arch/arm/module.h39
-rw-r--r--plugins/pychrysa/arch/arm/processor.c120
-rw-r--r--plugins/pychrysa/arch/arm/processor.h42
-rw-r--r--plugins/pychrysa/arch/arm/v7/Makefile.am16
-rw-r--r--plugins/pychrysa/arch/arm/v7/instruction.c117
-rw-r--r--plugins/pychrysa/arch/arm/v7/instruction.h42
-rw-r--r--plugins/pychrysa/arch/arm/v7/module.c93
-rw-r--r--plugins/pychrysa/arch/arm/v7/module.h39
-rw-r--r--plugins/pychrysa/arch/arm/v7/processor.c117
-rw-r--r--plugins/pychrysa/arch/arm/v7/processor.h42
-rw-r--r--plugins/pychrysa/arch/instruction.c409
-rw-r--r--plugins/pychrysa/arch/instruction.h12
-rw-r--r--plugins/pychrysa/arch/module.c24
-rw-r--r--plugins/pychrysa/arch/processor.c342
-rw-r--r--plugins/pychrysa/arch/processor.h13
-rw-r--r--plugins/pychrysa/arch/vmpa.c660
-rw-r--r--plugins/pychrysa/arch/vmpa.h20
-rw-r--r--plugins/pychrysa/common/Makefile.am15
-rw-r--r--plugins/pychrysa/common/fnv1a.c145
-rw-r--r--plugins/pychrysa/common/fnv1a.h42
-rw-r--r--plugins/pychrysa/common/module.c91
-rw-r--r--plugins/pychrysa/common/module.h39
-rw-r--r--plugins/pychrysa/core/module.c18
-rw-r--r--plugins/pychrysa/core/params.c29
-rw-r--r--plugins/pychrysa/format/Makefile.am3
-rw-r--r--plugins/pychrysa/format/dex/class.c91
-rw-r--r--plugins/pychrysa/format/dex/class.h3
-rw-r--r--plugins/pychrysa/format/dex/dex.c99
-rw-r--r--plugins/pychrysa/format/dex/dex.h5
-rw-r--r--plugins/pychrysa/format/dex/module.c36
-rw-r--r--plugins/pychrysa/format/elf/elf.c94
-rw-r--r--plugins/pychrysa/format/elf/elf.h5
-rw-r--r--plugins/pychrysa/format/elf/module.c36
-rw-r--r--plugins/pychrysa/format/executable.c97
-rw-r--r--plugins/pychrysa/format/executable.h5
-rw-r--r--plugins/pychrysa/format/format.c505
-rw-r--r--plugins/pychrysa/format/format.h19
-rw-r--r--plugins/pychrysa/format/module.c42
-rw-r--r--plugins/pychrysa/format/symbol.c720
-rw-r--r--plugins/pychrysa/format/symbol.h42
-rw-r--r--plugins/pychrysa/glibext/Makefile.am8
-rw-r--r--plugins/pychrysa/glibext/bincontent.c267
-rw-r--r--plugins/pychrysa/glibext/bincontent.h (renamed from plugins/pychrysa/analysis/roptions.h)21
-rw-r--r--plugins/pychrysa/glibext/bufferline.c300
-rw-r--r--plugins/pychrysa/glibext/bufferline.h3
-rw-r--r--plugins/pychrysa/glibext/codebuffer.c87
-rw-r--r--plugins/pychrysa/glibext/codebuffer.h3
-rw-r--r--plugins/pychrysa/glibext/configuration.c44
-rw-r--r--plugins/pychrysa/glibext/module.c16
-rw-r--r--plugins/pychrysa/gtkext/Makefile.am1
-rw-r--r--plugins/pychrysa/gtkext/blockview.c109
-rw-r--r--plugins/pychrysa/gtkext/blockview.h9
-rw-r--r--plugins/pychrysa/gtkext/bufferview.c117
-rw-r--r--plugins/pychrysa/gtkext/bufferview.h42
-rw-r--r--plugins/pychrysa/gtkext/module.c39
-rw-r--r--plugins/pychrysa/gtkext/viewpanel.c126
-rw-r--r--plugins/pychrysa/gtkext/viewpanel.h9
-rw-r--r--plugins/pychrysa/gui/editem.c69
-rw-r--r--plugins/pychrysa/gui/editem.h5
-rw-r--r--plugins/pychrysa/gui/module.c43
-rw-r--r--plugins/pychrysa/gui/panels/log.c108
-rw-r--r--plugins/pychrysa/gui/panels/log.h5
-rw-r--r--plugins/pychrysa/gui/panels/module.c43
-rw-r--r--plugins/pychrysa/gui/panels/module.h2
-rw-r--r--plugins/pychrysa/gui/panels/panel.c85
-rw-r--r--plugins/pychrysa/gui/panels/panel.h10
-rw-r--r--plugins/pychrysa/helpers.c89
-rw-r--r--plugins/pychrysa/helpers.h25
-rwxr-xr-xplugins/pychrysa/linsyscalls/oidapgi.py28
-rw-r--r--plugins/pychrysa/pychrysa.c214
-rw-r--r--src/analysis/binary.c4
-rw-r--r--src/analysis/disass/area.c21
-rw-r--r--src/arch/instruction.c5
-rw-r--r--src/arch/processor.c3
-rw-r--r--src/arch/vmpa.c2
-rw-r--r--src/arch/vmpa.h2
-rwxr-xr-xsrc/format/dex/dex.h9
-rw-r--r--src/format/symbol.c14
-rw-r--r--src/format/symbol.h4
-rw-r--r--src/glibext/delayed.c5
-rw-r--r--src/glibext/gbufferline.h4
-rw-r--r--src/gtkext/gtkextstatusbar.c14
110 files changed, 6243 insertions, 1811 deletions
diff --git a/ChangeLog b/ChangeLog
index 5dd7374..49e3073 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,143 @@
+15-07-17 Cyrille Bagard <nocbos@gmail.com>
+
+ * configure.ac:
+ * plugins/pychrysa/analysis/binaries/file.c:
+ * plugins/pychrysa/analysis/binaries/module.c:
+ * plugins/pychrysa/analysis/binary.c:
+ * plugins/pychrysa/analysis/block.c:
+ * plugins/pychrysa/analysis/block.h:
+ * plugins/pychrysa/analysis/blocks/flow.c:
+ * plugins/pychrysa/analysis/blocks/flow.h:
+ * plugins/pychrysa/analysis/blocks/module.c:
+ * plugins/pychrysa/analysis/blocks/module.h:
+ * plugins/pychrysa/analysis/blocks/virtual.c:
+ * plugins/pychrysa/analysis/blocks/virtual.h:
+ * plugins/pychrysa/analysis/db/items/comment.c:
+ * plugins/pychrysa/analysis/db/items/module.c:
+ * plugins/pychrysa/analysis/db/Makefile.am:
+ * plugins/pychrysa/analysis/db/module.c:
+ * plugins/pychrysa/analysis/Makefile.am:
+ * plugins/pychrysa/analysis/module.c:
+ Update the Python bindings.
+
+ * plugins/pychrysa/analysis/roptions.c:
+ * plugins/pychrysa/analysis/roptions.h:
+ Deleted entries.
+
+ * plugins/pychrysa/analysis/routine.c:
+ * plugins/pychrysa/analysis/routine.h:
+ Update the Python bindings.
+
+ * plugins/pychrysa/arch/arm/instruction.c:
+ * plugins/pychrysa/arch/arm/instruction.h:
+ * plugins/pychrysa/arch/arm/Makefile.am:
+ * plugins/pychrysa/arch/arm/module.c:
+ * plugins/pychrysa/arch/arm/module.h:
+ * plugins/pychrysa/arch/arm/processor.c:
+ * plugins/pychrysa/arch/arm/processor.h:
+ * plugins/pychrysa/arch/arm/v7/instruction.c:
+ * plugins/pychrysa/arch/arm/v7/instruction.h:
+ * plugins/pychrysa/arch/arm/v7/Makefile.am:
+ * plugins/pychrysa/arch/arm/v7/module.c:
+ * plugins/pychrysa/arch/arm/v7/module.h:
+ * plugins/pychrysa/arch/arm/v7/processor.c:
+ * plugins/pychrysa/arch/arm/v7/processor.h:
+ Added entries.
+
+ * plugins/pychrysa/arch/instruction.c:
+ * plugins/pychrysa/arch/instruction.h:
+ * plugins/pychrysa/arch/Makefile.am:
+ * plugins/pychrysa/arch/module.c:
+ * plugins/pychrysa/arch/processor.c:
+ * plugins/pychrysa/arch/processor.h:
+ * plugins/pychrysa/arch/vmpa.c:
+ * plugins/pychrysa/arch/vmpa.h:
+ Update the Python bindings.
+
+ * plugins/pychrysa/common/fnv1a.c:
+ * plugins/pychrysa/common/fnv1a.h:
+ * plugins/pychrysa/common/Makefile.am:
+ * plugins/pychrysa/common/module.c:
+ * plugins/pychrysa/common/module.h:
+ Added entries.
+
+ * plugins/pychrysa/core/module.c:
+ * plugins/pychrysa/core/params.c:
+ * plugins/pychrysa/format/dex/class.c:
+ * plugins/pychrysa/format/dex/class.h:
+ * plugins/pychrysa/format/dex/dex.c:
+ * plugins/pychrysa/format/dex/dex.h:
+ * plugins/pychrysa/format/dex/module.c:
+ * plugins/pychrysa/format/elf/elf.c:
+ * plugins/pychrysa/format/elf/elf.h:
+ * plugins/pychrysa/format/elf/module.c:
+ * plugins/pychrysa/format/executable.c:
+ * plugins/pychrysa/format/executable.h:
+ * plugins/pychrysa/format/format.c:
+ * plugins/pychrysa/format/format.h:
+ * plugins/pychrysa/format/Makefile.am:
+ * plugins/pychrysa/format/module.c:
+ Update the Python bindings.
+
+ * plugins/pychrysa/format/symbol.c:
+ * plugins/pychrysa/format/symbol.h:
+ * plugins/pychrysa/glibext/bincontent.c:
+ * plugins/pychrysa/glibext/bincontent.h:
+ Added entries.
+
+ * plugins/pychrysa/glibext/bufferline.c:
+ * plugins/pychrysa/glibext/bufferline.h:
+ * plugins/pychrysa/glibext/codebuffer.c:
+ * plugins/pychrysa/glibext/codebuffer.h:
+ * plugins/pychrysa/glibext/configuration.c:
+ * plugins/pychrysa/glibext/Makefile.am:
+ * plugins/pychrysa/glibext/module.c:
+ * plugins/pychrysa/gtkext/blockview.c:
+ * plugins/pychrysa/gtkext/blockview.h:
+ Update the Python bindings.
+
+ * plugins/pychrysa/gtkext/bufferview.c:
+ * plugins/pychrysa/gtkext/bufferview.h:
+ Added entries.
+
+ * plugins/pychrysa/gtkext/Makefile.am:
+ * plugins/pychrysa/gtkext/module.c:
+ * plugins/pychrysa/gtkext/viewpanel.c:
+ * plugins/pychrysa/gtkext/viewpanel.h:
+ * plugins/pychrysa/gui/editem.c:
+ * plugins/pychrysa/gui/editem.h:
+ * plugins/pychrysa/gui/module.c:
+ * plugins/pychrysa/gui/panels/log.c:
+ * plugins/pychrysa/gui/panels/log.h:
+ * plugins/pychrysa/gui/panels/module.c:
+ * plugins/pychrysa/gui/panels/module.h:
+ * plugins/pychrysa/gui/panels/panel.c:
+ * plugins/pychrysa/gui/panels/panel.h:
+ * plugins/pychrysa/helpers.c:
+ * plugins/pychrysa/helpers.h:
+ Update the Python bindings.
+
+ * plugins/pychrysa/linsyscalls/oidapgi.py:
+ Deleted entry.
+
+ * plugins/pychrysa/Makefile.am:
+ * plugins/pychrysa/pychrysa.c:
+ Update the Python bindings.
+
+ * src/analysis/binary.c:
+ * src/analysis/disass/area.c:
+ * src/arch/instruction.c:
+ * src/arch/processor.c:
+ * src/arch/vmpa.c:
+ * src/arch/vmpa.h:
+ * src/format/dex/dex.h:
+ * src/format/symbol.c:
+ * src/format/symbol.h:
+ * src/glibext/delayed.c:
+ * src/glibext/gbufferline.h:
+ * src/gtkext/gtkextstatusbar.c:
+ Update code.
+
15-07-16 Cyrille Bagard <nocbos@gmail.com>
* plugins/ropgadgets/finder.c:
diff --git a/configure.ac b/configure.ac
index bd15448..eed6c5b 100644
--- a/configure.ac
+++ b/configure.ac
@@ -272,6 +272,9 @@ AC_CONFIG_FILES([Makefile
plugins/pychrysa/analysis/db/Makefile
plugins/pychrysa/analysis/db/items/Makefile
plugins/pychrysa/arch/Makefile
+ plugins/pychrysa/arch/arm/Makefile
+ plugins/pychrysa/arch/arm/v7/Makefile
+ plugins/pychrysa/common/Makefile
plugins/pychrysa/core/Makefile
plugins/pychrysa/debug/Makefile
plugins/pychrysa/format/Makefile
diff --git a/plugins/pychrysa/Makefile.am b/plugins/pychrysa/Makefile.am
index 8c59c10..e4b9739 100644
--- a/plugins/pychrysa/Makefile.am
+++ b/plugins/pychrysa/Makefile.am
@@ -1,6 +1,7 @@
-pkglib_LTLIBRARIES = pychrysa.la pychrysalide.la
+pkglib_LTLIBRARIES = pychrysalide.la
+# -------- %< -------- %< -------- %< -------- %< --------
pychrysa_la_SOURCES = \
helpers.h helpers.c \
plugin.h plugin.c \
@@ -20,20 +21,25 @@ pychrysa_la_LDFLAGS = -module -avoid-version $(LIBGTK_LIBS) $(LIBXML_LIBS) $(LIB
$(LIBPYGOBJECT_LIBS) \
-L../../src/.libs -L../../src/gui/.libs -lchrysagui -lchrysadisass -lchrysagtkext \
-L../../src/plugins/.libs -lplugins
-
+# -------- %< -------- %< -------- %< -------- %< --------
pychrysalide_la_SOURCES = \
+ helpers.h helpers.c \
pychrysa.h pychrysa.c
pychrysalide_la_LIBADD = \
analysis/libpychrysaanalysis.la \
arch/libpychrysaarch.la \
+ common/libpychrysacommon.la \
core/libpychrysacore.la \
- glibext/libpychrysaglibext.la
+ format/libpychrysaformat.la \
+ glibext/libpychrysaglibext.la \
+ gtkext/libpychrysagtkext.la \
+ gui/libpychrysagui.la
pychrysalide_la_LDFLAGS = -module -avoid-version \
$(LIBPYTHON_LIBS) $(LIBSQLITE_LIBS) $(LIBARCHIVE_LIBS) \
- -L../../src/.libs -lchrysadisass -lchrysagtkext -lchrysacore \
+ -L../../src/.libs -lchrysadisass -lchrysagui -lchrysagtkext -lchrysacore \
-L../../src/plugins/.libs -lplugins
@@ -43,4 +49,5 @@ AM_CPPFLAGS = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS) $(LIBPYTHON_CFLAGS) $(LIBPYGOBJE
AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS)
-SUBDIRS = analysis arch core debug format glibext gtkext gui
+SUBDIRS = analysis arch common core format glibext gtkext gui
+#SUBDIRS = analysis arch common core debug format glibext gtkext gui
diff --git a/plugins/pychrysa/analysis/Makefile.am b/plugins/pychrysa/analysis/Makefile.am
index 7e18757..8b0609d 100644
--- a/plugins/pychrysa/analysis/Makefile.am
+++ b/plugins/pychrysa/analysis/Makefile.am
@@ -3,21 +3,14 @@ noinst_LTLIBRARIES = libpychrysaanalysis.la
libpychrysaanalysis_la_SOURCES = \
binary.h binary.c \
- module.h module.c
+ block.h block.c \
+ module.h module.c \
+ routine.h routine.c
libpychrysaanalysis_la_LIBADD = \
- binaries/libpychrysaanalysisbinaries.la
-
-# libpychrysaanalysis_la_SOURCES = \
-# binary.h binary.c \
-# block.h block.c \
-# module.h module.c \
-# roptions.h roptions.c \
-# routine.h routine.c
-
-# libpychrysaanalysis_la_LIBADD = \
-# binaries/libpychrysaanalysisbinaries.la \
-# blocks/libpychrysaanalysisblocks.la
+ binaries/libpychrysaanalysisbinaries.la \
+ blocks/libpychrysaanalysisblocks.la \
+ db/libpychrysaanalysisdb.la
libpychrysaanalysis_la_LDFLAGS =
diff --git a/plugins/pychrysa/analysis/binaries/file.c b/plugins/pychrysa/analysis/binaries/file.c
index af285d9..40463ba 100644
--- a/plugins/pychrysa/analysis/binaries/file.c
+++ b/plugins/pychrysa/analysis/binaries/file.c
@@ -60,7 +60,7 @@ static PyObject *py_binary_file_get_filename(PyObject *, void *);
static PyObject *py_binary_file_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
{
PyObject *result; /* Instance à retourner */
- char *filename; /* Nom du fichier à charger */
+ const char *filename; /* Nom du fichier à charger */
int ret; /* Bilan de lecture des args. */
GLoadedBinary *binary; /* Version GLib du format */
diff --git a/plugins/pychrysa/analysis/binaries/module.c b/plugins/pychrysa/analysis/binaries/module.c
index c2adddf..b43d24f 100644
--- a/plugins/pychrysa/analysis/binaries/module.c
+++ b/plugins/pychrysa/analysis/binaries/module.c
@@ -25,6 +25,9 @@
#include "module.h"
+#include <assert.h>
+
+
#include "file.h"
@@ -47,7 +50,7 @@ bool add_analysis_binaries_module_to_python_module(PyObject *super)
PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyModuleDef py_chrysalide_arch_module = {
+ static PyModuleDef py_chrysalide_binaries_module = {
.m_base = PyModuleDef_HEAD_INIT,
@@ -60,31 +63,26 @@ bool add_analysis_binaries_module_to_python_module(PyObject *super)
result = false;
- module = PyModule_Create(&py_chrysalide_arch_module);
+ module = PyModule_Create(&py_chrysalide_binaries_module);
if (module == NULL) return false;
- ret = PyState_AddModule(super, &py_chrysalide_arch_module);
- if (ret != 0) goto aabmtpm_exit;
+ ret = PyState_AddModule(super, &py_chrysalide_binaries_module);
+ if (ret != 0) goto loading_failed;
ret = _PyImport_FixupBuiltin(module, "pychrysalide.analysis.binaries");
- if (ret != 0) goto aabmtpm_exit;
+ if (ret != 0) goto loading_failed;
Py_INCREF(module);
ret = PyModule_AddObject(super, "binaries", module);
- if (ret != 0) goto aabmtpm_exit;
+ if (ret != 0) goto loading_failed;
result = true;
result &= register_python_binary_file(module);
- aabmtpm_exit:
-
- if (!result)
- {
- printf("something went wrong in %s...\n", __FUNCTION__);
- /* ... */
+ loading_failed:
- }
+ assert(result);
return result;
diff --git a/plugins/pychrysa/analysis/binary.c b/plugins/pychrysa/analysis/binary.c
index 1a513eb..fad84cd 100644
--- a/plugins/pychrysa/analysis/binary.c
+++ b/plugins/pychrysa/analysis/binary.c
@@ -28,138 +28,62 @@
#include <pygobject.h>
+#include <analysis/binary.h>
+#include "../helpers.h"
+/* Lance l'analyse d'un élément binaire chargé. */
+static PyObject *py_loaded_binary_analyse(PyObject *, PyObject *);
+/* Fournit le nom associé à l'élément binaire. */
+static PyObject *py_loaded_binary_get_name(PyObject *, void *);
-/******************************************************************************
-* *
-* Paramètres : - *
-* *
-* Description : Fournit un accès à une définition de type à diffuser. *
-* *
-* Retour : Définition d'objet pour Python. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-PyTypeObject *get_python_loaded_binary_type(void)
-{
- static PyTypeObject py_loaded_binary_type = {
-
- PyVarObject_HEAD_INIT(NULL, 0)
-
- .tp_name = "pychrysalide.analysis.LoadedBinary",
-
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
-
- .tp_doc = "PyChrysalide loaded binary",
-
- };
-
- return &py_loaded_binary_type;
-
-}
-
+/* Fournit le format de fichier reconnu dans le contenu binaire. */
+static PyObject *py_loaded_binary_get_format(PyObject *, void *);
+/* Fournit le processeur de l'architecture liée au binaire. */
+static PyObject *py_loaded_binary_get_processor(PyObject *, void *);
-#include <analysis/binary.h>
-
+/* Fournit le tampon associé au contenu assembleur d'un binaire. */
+static PyObject *py_loaded_binary_get_disassembled_buffer(PyObject *, void *);
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : self = contenu binaire à manipuler. *
+* args = non utilisé ici. *
* *
-* Description : Prend en charge l'objet 'pychrysalide.arch.loaded_binary'. *
+* Description : Lance l'analyse d'un élément binaire chargé. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Rien (None). *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_loaded_binary(PyObject *module)
+static PyObject *py_loaded_binary_analyse(PyObject *self, PyObject *args)
{
- PyTypeObject *py_loaded_binary_type; /* Type Python 'LoadedBinary' */
- int ret; /* Bilan d'un appel */
- PyObject *dict; /* Dictionnaire du module */
+ GLoadedBinary *binary; /* Version GLib du format */
- py_loaded_binary_type = get_python_loaded_binary_type();
-
- py_loaded_binary_type->tp_base = &PyGObject_Type;
- py_loaded_binary_type->tp_basicsize = py_loaded_binary_type->tp_base->tp_basicsize;
+ binary = G_LOADED_BINARY(pygobject_get(self));
- if (PyType_Ready(py_loaded_binary_type) != 0)
- return false;
+ g_loaded_binary_analyse(binary);
- Py_INCREF(py_loaded_binary_type);
- ret = PyModule_AddObject(module, "LoadedBinary", (PyObject *)py_loaded_binary_type);
- if (ret != 0) return false;
-
- dict = PyModule_GetDict(module);
- pygobject_register_class(dict, "LoadedBinary", G_TYPE_LOADED_BINARY, py_loaded_binary_type,
- Py_BuildValue("(O)", py_loaded_binary_type->tp_base));
-
- return true;
+ Py_RETURN_NONE;
}
-
-
-
-
-
-
-
-
-
-
-#if 0
-
-
-#include <pygobject.h>
-
-
-#include <analysis/binary.h>
-
-
-#include "../quirks.h"
-#include "../arch/instruction.h"
-#include "../format/executable.h"
-#include "../glibext/codebuffer.h"
-
-
-
-/* Fournit le fichier correspondant à l'élément binaire. */
-static PyObject *py_loaded_binary_get_filename(PyObject *self, PyObject *args);
-
-/* Fournit le format de fichier reconnu dans le contenu binaire. */
-static PyObject *py_loaded_binary_get_format(PyObject *, PyObject *);
-
-/* Fournit les instructions issues du désassemblage. */
-static PyObject *py_loaded_binary_get_instructions(PyObject *, PyObject *);
-
-
-
-/* Fournit le tampon associé au contenu assembleur d'un binaire. */
-static PyObject *py_loaded_binary_get_disassembled_buffer(PyObject *, void *);
-
-
-
-
/******************************************************************************
* *
-* Paramètres : self = classe représentant un binaire. *
-* args = arguments fournis à l'appel. *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
* *
-* Description : Fournit le fichier correspondant à l'élément binaire. *
+* Description : Fournit le nom associé à l'élément binaire. *
* *
* Retour : Nom de fichier avec chemin absolu. *
* *
@@ -167,17 +91,17 @@ static PyObject *py_loaded_binary_get_disassembled_buffer(PyObject *, void *);
* *
******************************************************************************/
-static PyObject *py_loaded_binary_get_name(PyObject *self, PyObject *args)
+static PyObject *py_loaded_binary_get_name(PyObject *self, void *closure)
{
PyObject *result; /* Trouvailles à retourner */
GLoadedBinary *binary; /* Version native */
- const char *filename; /* Fichier associé au binaire */
+ const char *name; /* Désignation du binaire */
binary = G_LOADED_BINARY(pygobject_get(self));
- filename = g_loaded_binary_get_name(binary, true);
+ name = g_loaded_binary_get_name(binary, true);
- result = PyString_FromString(filename);
+ result = PyUnicode_FromString(name);
return result;
@@ -186,28 +110,30 @@ static PyObject *py_loaded_binary_get_name(PyObject *self, PyObject *args)
/******************************************************************************
* *
-* Paramètres : self = classe représentant un binaire. *
-* args = arguments fournis à l'appel. *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
* *
* Description : Fournit le format de fichier reconnu dans le contenu binaire.*
* *
-* Retour : Nom de fichier avec chemin absolu. *
+* Retour : Instance du format reconnu. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_loaded_binary_get_format(PyObject *self, PyObject *args)
+static PyObject *py_loaded_binary_get_format(PyObject *self, void *closure)
{
- PyObject *result; /* Trouvailles à retourner */
- GLoadedBinary *binary; /* Version native */
- GExeFormat *format; /* Format du binaire physique */
+ PyObject *result; /* Instance Python à retourner */
+ GLoadedBinary *binary; /* Binaire en cours d'analyse */
+ GExeFormat *format; /* Format du binaire lié */
binary = G_LOADED_BINARY(pygobject_get(self));
format = g_loaded_binary_get_format(binary);
result = pygobject_new(G_OBJECT(format));
+ //g_object_unref(G_OBJECT(format));
+
return result;
}
@@ -215,37 +141,35 @@ static PyObject *py_loaded_binary_get_format(PyObject *self, PyObject *args)
/******************************************************************************
* *
-* Paramètres : self = classe représentant un binaire. *
-* args = arguments fournis à l'appel. *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
* *
-* Description : Fournit les instructions issues du désassemblage. *
+* Description : Fournit le processeur de l'architecture liée au binaire. *
* *
-* Retour : Instructions issues du désassemblage. *
+* Retour : Instance du processeur associé. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_loaded_binary_get_instructions(PyObject *self, PyObject *args)
+static PyObject *py_loaded_binary_get_processor(PyObject *self, void *closure)
{
- PyObject *result; /* Trouvailles à retourner */
- GLoadedBinary *binary; /* Version native */
- GArchInstruction *instr; /* Première instruction */
+ PyObject *result; /* Instance Python à retourner */
+ GLoadedBinary *binary; /* Binaire en cours d'analyse */
+ GArchProcessor *proc; /* Architecture visée */
binary = G_LOADED_BINARY(pygobject_get(self));
+ proc = g_loaded_binary_get_processor(binary);
- instr = g_loaded_binary_get_instructions(binary);
+ result = pygobject_new(G_OBJECT(proc));
- result = pygobject_new(G_OBJECT(instr));
+ g_object_unref(G_OBJECT(proc));
return result;
}
-
-
-
/******************************************************************************
* *
* Paramètres : self = classe représentant une instruction. *
@@ -275,88 +199,106 @@ static PyObject *py_loaded_binary_get_disassembled_buffer(PyObject *self, void *
}
-
-
-
-
-
-
-
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.analysis.LoadedBinary'.*
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_loaded_binary(PyObject *module)
+PyTypeObject *get_python_loaded_binary_type(void)
{
- PyObject *pygobj_mod; /* Module Python-GObject */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_loaded_binary_methods[] = {
{
- "get_filename", (PyCFunction)py_loaded_binary_get_filename,
+ "analyse", py_loaded_binary_analyse,
METH_NOARGS,
- "Provide the filename of the loaded binary."
- },
- {
- "get_format", (PyCFunction)py_loaded_binary_get_format,
- METH_NOARGS,
- "Provide the file format recognized in the binary content."
- },
- {
- "get_instructions", (PyCFunction)py_loaded_binary_get_instructions,
- METH_NOARGS,
- "Give access to all disassembled instructions."
+ "analyse(/)\n--\n\nStart the analysis of the loaded binary and " \
+ "send a \"disassembly-done\" signal when done."
},
{ NULL }
};
static PyGetSetDef py_loaded_binary_getseters[] = {
{
- "disassembled_buffer", (getter)py_loaded_binary_get_disassembled_buffer, (setter)NULL,
- "Give access to the disassembled code buffer.", NULL
+ "name", py_loaded_binary_get_name, NULL,
+ "Name of the loaded binary.", NULL
+ },
+ {
+ "format", py_loaded_binary_get_format, NULL,
+ "File format recognized in the binary content.", NULL
+ },
+ {
+ "processor", py_loaded_binary_get_processor, NULL,
+ "Handler for the current binary processor.", NULL
+ },
+ {
+ "disassembled_buffer", py_loaded_binary_get_disassembled_buffer, NULL,
+ "Disassembled code buffer.", NULL
},
{ NULL }
};
static PyTypeObject py_loaded_binary_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.analysis.LoadedBinary",
- .tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IS_ABSTRACT | Py_TPFLAGS_BASETYPE,
.tp_doc = "PyChrysalide loaded binary",
.tp_methods = py_loaded_binary_methods,
- .tp_getset = py_loaded_binary_getseters
+ .tp_getset = py_loaded_binary_getseters,
};
- pygobj_mod = PyImport_ImportModule("gobject");
- if (pygobj_mod == NULL) return false;
+ return &py_loaded_binary_type;
- py_loaded_binary_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(pygobj_mod, "GObject");
- Py_DECREF(pygobj_mod);
+}
- if (PyType_Ready(&py_loaded_binary_type) < 0)
- return false;
- Py_INCREF(&py_loaded_binary_type);
- ret = PyModule_AddObject(module, "LoadedBinary", (PyObject *)&py_loaded_binary_type);
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.analysis.LoadedBinary'.*
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
- return (ret == 0);
+bool register_python_loaded_binary(PyObject *module)
+{
+ PyTypeObject *py_loaded_binary_type; /* Type Python 'LoadedBinary' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
-}
+ py_loaded_binary_type = get_python_loaded_binary_type();
+
+ py_loaded_binary_type->tp_base = &PyGObject_Type;
+ py_loaded_binary_type->tp_basicsize = py_loaded_binary_type->tp_base->tp_basicsize;
+
+ APPLY_ABSTRACT_FLAG(py_loaded_binary_type);
+
+ if (PyType_Ready(py_loaded_binary_type) != 0)
+ return false;
-#endif
+ Py_INCREF(py_loaded_binary_type);
+ ret = PyModule_AddObject(module, "LoadedBinary", (PyObject *)py_loaded_binary_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "LoadedBinary", G_TYPE_LOADED_BINARY, py_loaded_binary_type,
+ Py_BuildValue("(O)", py_loaded_binary_type->tp_base));
+ return true;
+
+}
diff --git a/plugins/pychrysa/analysis/block.c b/plugins/pychrysa/analysis/block.c
index bd8684d..4cbc353 100644
--- a/plugins/pychrysa/analysis/block.c
+++ b/plugins/pychrysa/analysis/block.c
@@ -54,7 +54,7 @@ static PyObject *py_instructions_block_visit(PyObject *, PyObject *);
static PyObject *py_instructions_block_get_links_block(PyObject *, PyObject *);
/* Définit les constantes pour les blocs basiques. */
-static bool py_instructions_block_define_constants(PyObject *);
+static bool py_instructions_block_define_constants(PyTypeObject *);
@@ -82,7 +82,7 @@ static bool py_block_visitor_glue(GInstrBlock *block, BlockVisitOrder order, py_
args = PyTuple_New(3);
PyTuple_SetItem(args, 0, pygobject_new(G_OBJECT(block)));
- PyTuple_SetItem(args, 1, PyInt_FromLong(order));
+ PyTuple_SetItem(args, 1, PyLong_FromLong(order));
PyTuple_SetItem(args, 2, data->user);
value = _run_python_method(data->func, args);
@@ -96,6 +96,7 @@ static bool py_block_visitor_glue(GInstrBlock *block, BlockVisitOrder order, py_
}
+
/******************************************************************************
* *
* Paramètres : self = classe représentant un binaire. *
@@ -120,6 +121,8 @@ static PyObject *py_instructions_block_visit(PyObject *self, PyObject *args)
ret = PyArg_ParseTuple(args, "OO", &data.func, &data.user);
if (!ret) Py_RETURN_NONE;
+ if (PyCallable_Check(data.func) != 1) return NULL;
+
block = G_INSTR_BLOCK(pygobject_get(self));
status = g_instr_block_visit(block, (instr_block_visitor_cb)py_block_visitor_glue, &data);
@@ -162,7 +165,7 @@ static PyObject *py_instructions_block_get_links_block(PyObject *self, PyObject
/******************************************************************************
* *
-* Paramètres : dict = dictionnaire à compléter. *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
* *
* Description : Définit les constantes pour les blocs basiques. *
* *
@@ -172,90 +175,110 @@ static PyObject *py_instructions_block_get_links_block(PyObject *self, PyObject
* *
******************************************************************************/
-static bool py_instructions_block_define_constants(PyObject *dict)
+static bool py_instructions_block_define_constants(PyTypeObject *obj_type)
{
- int ret; /* Bilan d'un ajout */
-
- ret = PyDict_SetItemString(dict, "BVO_IN", PyInt_FromLong(BVO_IN));
- if (ret == -1) return false;
+ bool result; /* Bilan à retourner */
- ret = PyDict_SetItemString(dict, "BVO_PENDING", PyInt_FromLong(BVO_PENDING));
- if (ret == -1) return false;
+ result = true;
- ret = PyDict_SetItemString(dict, "BVO_OUT", PyInt_FromLong(BVO_OUT));
- if (ret == -1) return false;
+ result &= PyDict_AddIntMacro(obj_type, BVO_IN);
+ result &= PyDict_AddIntMacro(obj_type, BVO_PENDING);
+ result &= PyDict_AddIntMacro(obj_type, BVO_OUT);
- return true;
+ return result;
}
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.analysis.InstrBlock'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_instructions_block(PyObject *module)
+PyTypeObject *get_python_instr_block_type(void)
{
- PyObject *parent_mod; /* Module de la classe parente */
- int ret; /* Bilan d'un appel */
-
- static PyMethodDef py_instructions_block_methods[] = {
+ static PyMethodDef py_instr_block_methods[] = {
{
"visit", (PyCFunction)py_instructions_block_visit,
METH_VARARGS,
- "Visit all the basic blocks, starting at the provided one."
+ "visit($self, cb, data, /)\n--\n\nVisit all the basic blocks, starting at the provided one."
},
{
"get_links_block", (PyCFunction)py_instructions_block_get_links_block,
METH_VARARGS,
- "Get the block containing all blocks linked to the caller."
+ "get_links_block($self, /)\n--\n\nGet the block containing all blocks linked to the caller."
},
{ NULL }
};
- static PyGetSetDef py_instructions_block_getseters[] = {
+ static PyGetSetDef py_instr_block_getseters[] = {
{ NULL }
};
- static PyTypeObject py_instructions_block_type = {
+ static PyTypeObject py_instr_block_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.analysis.InstrBlock",
- .tp_basicsize = sizeof(PyGObject),
.tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
.tp_doc = "PyChrysalide basic block",
- .tp_methods = py_instructions_block_methods,
- .tp_getset = py_instructions_block_getseters
+ .tp_methods = py_instr_block_methods,
+ .tp_getset = py_instr_block_getseters,
};
- parent_mod = PyImport_ImportModule("gobject");
- if (parent_mod == NULL) return false;
+ return &py_instr_block_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.analysis.InstrBlock'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_instr_block(PyObject *module)
+{
+ PyTypeObject *py_instr_block_type; /* Type Python 'InstrBlock' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_instr_block_type = get_python_instr_block_type();
- py_instructions_block_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "GObject");
- Py_DECREF(parent_mod);
+ py_instr_block_type->tp_base = &PyGObject_Type;
+ py_instr_block_type->tp_basicsize = py_instr_block_type->tp_base->tp_basicsize;
- if (PyType_Ready(&py_instructions_block_type) < 0)
+ if (PyType_Ready(py_instr_block_type) != 0)
return false;
- if (!py_instructions_block_define_constants(py_instructions_block_type.tp_dict))
+ if (!py_instructions_block_define_constants(py_instr_block_type))
return false;
- Py_INCREF(&py_instructions_block_type);
- ret = PyModule_AddObject(module, "InstrBlock", (PyObject *)&py_instructions_block_type);
+ Py_INCREF(py_instr_block_type);
+ ret = PyModule_AddObject(module, "InstrBlock", (PyObject *)py_instr_block_type);
+ if (ret != 0) return false;
- return (ret == 0);
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "InstrBlock", G_TYPE_INSTR_BLOCK, py_instr_block_type,
+ Py_BuildValue("(O)", py_instr_block_type->tp_base));
+
+ return true;
}
diff --git a/plugins/pychrysa/analysis/block.h b/plugins/pychrysa/analysis/block.h
index 4752b9a..71e3160 100644
--- a/plugins/pychrysa/analysis/block.h
+++ b/plugins/pychrysa/analysis/block.h
@@ -31,8 +31,11 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_instr_block_type(void);
+
/* Prend en charge l'objet 'pychrysalide.analysis.InstrBlock'. */
-bool register_python_instructions_block(PyObject *);
+bool register_python_instr_block(PyObject *);
diff --git a/plugins/pychrysa/analysis/blocks/flow.c b/plugins/pychrysa/analysis/blocks/flow.c
index a5ee99c..626d5c8 100644
--- a/plugins/pychrysa/analysis/blocks/flow.c
+++ b/plugins/pychrysa/analysis/blocks/flow.c
@@ -31,12 +31,15 @@
#include <analysis/blocks/flow.h>
+#include "../block.h"
+#if 0
+
/* Fournit les adresses limites d'un bloc d'exécution. */
static PyObject *py_flow_block_get_boundary_addresses(PyObject *, void *);
@@ -180,3 +183,103 @@ bool register_python_flow_block(PyObject *module)
return (ret == 0);
}
+
+#endif
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_flow_block_type(void)
+{
+ static PyMethodDef py_flow_block_methods[] = {
+ { NULL }
+ };
+
+ static PyGetSetDef py_flow_block_getseters[] = {
+ { NULL }
+ };
+
+ static PyTypeObject py_flow_block_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.analysis.blocks.FlowBlock",
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "PyChrysalide flow block",
+
+ .tp_methods = py_flow_block_methods,
+ .tp_getset = py_flow_block_getseters,
+
+ };
+
+ return &py_flow_block_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide...blocks.FlowBlock'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_flow_block(PyObject *module)
+{
+ PyTypeObject *py_flow_block_type; /* Type Python 'FlowBlock' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_flow_block_type = get_python_flow_block_type();
+
+ py_flow_block_type->tp_base = get_python_instr_block_type();
+ py_flow_block_type->tp_basicsize = py_flow_block_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_flow_block_type) != 0)
+ return false;
+
+ Py_INCREF(py_flow_block_type);
+ ret = PyModule_AddObject(module, "FlowBlock", (PyObject *)py_flow_block_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "FlowBlock", G_TYPE_FLOW_BLOCK, py_flow_block_type,
+ Py_BuildValue("(O)", py_flow_block_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/analysis/blocks/flow.h b/plugins/pychrysa/analysis/blocks/flow.h
index 20d649e..69b6c24 100644
--- a/plugins/pychrysa/analysis/blocks/flow.h
+++ b/plugins/pychrysa/analysis/blocks/flow.h
@@ -31,6 +31,9 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_flow_block_type(void);
+
/* Prend en charge l'objet 'pychrysalide.analysis.blocks.FlowBlock'. */
bool register_python_flow_block(PyObject *);
diff --git a/plugins/pychrysa/analysis/blocks/module.c b/plugins/pychrysa/analysis/blocks/module.c
index 881ebc7..4968e90 100644
--- a/plugins/pychrysa/analysis/blocks/module.c
+++ b/plugins/pychrysa/analysis/blocks/module.c
@@ -25,6 +25,9 @@
#include "module.h"
+#include <assert.h>
+
+
#include "flow.h"
#include "virtual.h"
@@ -42,27 +45,47 @@
* *
******************************************************************************/
-bool add_blocks_module_to_python_module(PyObject *super)
+bool add_analysis_blocks_module_to_python_module(PyObject *super)
{
bool result; /* Bilan à retourner */
- PyObject *module; /* Module Python mis en place */
+ PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyMethodDef py_blocks_methods[] = {
- { NULL }
+ static PyModuleDef py_chrysalide_blocks_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.analysis.blocks",
+ .m_doc = "Python module for Chrysalide.analysis.blocks",
+
+ .m_size = -1,
+
};
- module = Py_InitModule("pychrysalide.analysis.blocks", py_blocks_methods);
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_blocks_module);
if (module == NULL) return false;
+ ret = PyState_AddModule(super, &py_chrysalide_blocks_module);
+ if (ret != 0) goto loading_failed;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.analysis.blocks");
+ if (ret != 0) goto loading_failed;
+
Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.analysis.blocks", module);
+ ret = PyModule_AddObject(super, "blocks", module);
+ if (ret != 0) goto loading_failed;
- result = (ret == 0);
+ result = true;
result &= register_python_flow_block(module);
result &= register_python_virtual_block(module);
+ loading_failed:
+
+ assert(result);
+
return result;
}
diff --git a/plugins/pychrysa/analysis/blocks/module.h b/plugins/pychrysa/analysis/blocks/module.h
index 395be19..dc2d17c 100644
--- a/plugins/pychrysa/analysis/blocks/module.h
+++ b/plugins/pychrysa/analysis/blocks/module.h
@@ -32,7 +32,7 @@
/* Ajoute le module 'blocks' au module Python. */
-bool add_blocks_module_to_python_module(PyObject *);
+bool add_analysis_blocks_module_to_python_module(PyObject *);
diff --git a/plugins/pychrysa/analysis/blocks/virtual.c b/plugins/pychrysa/analysis/blocks/virtual.c
index 4f15371..bdc81b0 100644
--- a/plugins/pychrysa/analysis/blocks/virtual.c
+++ b/plugins/pychrysa/analysis/blocks/virtual.c
@@ -31,35 +31,24 @@
#include <analysis/blocks/virtual.h>
-
-
-
-
-
-
-
-
-
+#include "../block.h"
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.....VirtualBlock'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_virtual_block(PyObject *module)
+PyTypeObject *get_python_virtual_block_type(void)
{
- PyObject *parent_mod; /* Module de la classe parente */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_virtual_block_methods[] = {
{ NULL }
};
@@ -70,35 +59,58 @@ bool register_python_virtual_block(PyObject *module)
static PyTypeObject py_virtual_block_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.analysis.blocks.VirtualBlock",
- .tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT,
- .tp_doc = "PyChrysalide basic virtual block",
+ .tp_doc = "PyChrysalide virtual block",
.tp_methods = py_virtual_block_methods,
- .tp_getset = py_virtual_block_getseters
+ .tp_getset = py_virtual_block_getseters,
};
- parent_mod = PyImport_ImportModule("pychrysalide.analysis");
- if (parent_mod == NULL) return false;
+ return &py_virtual_block_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide...blocks.VirtualBlock'.*
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_virtual_block(PyObject *module)
+{
+ PyTypeObject *py_virtual_block_type; /* Type Python 'VirtualBlock' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_virtual_block_type = get_python_virtual_block_type();
- py_virtual_block_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "InstrBlock");
- Py_DECREF(parent_mod);
+ py_virtual_block_type->tp_base = get_python_instr_block_type();
+ py_virtual_block_type->tp_basicsize = py_virtual_block_type->tp_base->tp_basicsize;
- if (PyType_Ready(&py_virtual_block_type) < 0)
+ if (PyType_Ready(py_virtual_block_type) != 0)
return false;
- Py_INCREF(&py_virtual_block_type);
- ret = PyModule_AddObject(module, "VirtualBlock", (PyObject *)&py_virtual_block_type);
+ Py_INCREF(py_virtual_block_type);
+ ret = PyModule_AddObject(module, "VirtualBlock", (PyObject *)py_virtual_block_type);
+ if (ret != 0) return false;
- pygobject_register_class(module, "GVirtualBlock", G_TYPE_VIRTUAL_BLOCK, &py_virtual_block_type,
- Py_BuildValue("(O)", py_virtual_block_type.tp_base));
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "VirtualBlock", G_TYPE_VIRTUAL_BLOCK, py_virtual_block_type,
+ Py_BuildValue("(O)", py_virtual_block_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/analysis/blocks/virtual.h b/plugins/pychrysa/analysis/blocks/virtual.h
index 1c70b34..0bfaf82 100644
--- a/plugins/pychrysa/analysis/blocks/virtual.h
+++ b/plugins/pychrysa/analysis/blocks/virtual.h
@@ -31,6 +31,9 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_virtual_block_type(void);
+
/* Prend en charge l'objet 'pychrysalide.analysis.blocks.VirtualBlock'. */
bool register_python_virtual_block(PyObject *);
diff --git a/plugins/pychrysa/analysis/db/Makefile.am b/plugins/pychrysa/analysis/db/Makefile.am
index e33130f..2de2a16 100644
--- a/plugins/pychrysa/analysis/db/Makefile.am
+++ b/plugins/pychrysa/analysis/db/Makefile.am
@@ -6,7 +6,8 @@ libpychrysaanalysisdb_la_SOURCES = \
item.h item.c \
module.h module.c
-libpychrysaanalysisdb_la_LDFLAGS =
+libpychrysaanalysisdb_la_LDFLAGS = \
+ items/libpychrysaanalysisdbitems.la
AM_CPPFLAGS = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS) $(LIBPYTHON_CFLAGS) $(LIBPYGOBJECT_CFLAGS) \
diff --git a/plugins/pychrysa/analysis/db/items/comment.c b/plugins/pychrysa/analysis/db/items/comment.c
index 1bb2863..951f6ce 100644
--- a/plugins/pychrysa/analysis/db/items/comment.c
+++ b/plugins/pychrysa/analysis/db/items/comment.c
@@ -75,6 +75,9 @@ static PyObject *py_db_comment_new(PyTypeObject *type, PyObject *args, PyObject
ret = PyArg_ParseTuple(args, "Osp", &py_vmpa, &text, &is_volatile);
if (!ret) Py_RETURN_NONE;
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
addr = get_internal_vmpa(py_vmpa);
if (py_vmpa == NULL) Py_RETURN_NONE;
@@ -114,7 +117,7 @@ static PyObject *py_db_comment_get_text(PyObject *self, void *closure)
}
-/*********************d*********************************************************
+/******************************************************************************
* *
* Paramètres : self = objet Python concerné par l'appel. *
* value = valeur fournie à intégrer ou prendre en compte. *
diff --git a/plugins/pychrysa/analysis/db/items/module.c b/plugins/pychrysa/analysis/db/items/module.c
index 3c634e3..009e823 100644
--- a/plugins/pychrysa/analysis/db/items/module.c
+++ b/plugins/pychrysa/analysis/db/items/module.c
@@ -25,6 +25,9 @@
#include "module.h"
+#include <assert.h>
+
+
#include "comment.h"
@@ -64,27 +67,22 @@ bool add_analysis_db_items_module_to_python_module(PyObject *super)
if (module == NULL) return false;
ret = PyState_AddModule(super, &py_chrysalide_items_module);
- if (ret != 0) goto aadimtpm_exit;
+ if (ret != 0) goto loading_failed;
ret = _PyImport_FixupBuiltin(module, "pychrysalide.analysis.db.items");
- if (ret != 0) goto aadimtpm_exit;
+ if (ret != 0) goto loading_failed;
Py_INCREF(module);
ret = PyModule_AddObject(super, "items", module);
- if (ret != 0) goto aadimtpm_exit;
+ if (ret != 0) goto loading_failed;
result = true;
result &= register_python_db_comment(module);
- aadimtpm_exit:
-
- if (!result)
- {
- printf("something went wrong in %s...\n", __FUNCTION__);
- /* ... */
+ loading_failed:
- }
+ assert(result);
return result;
diff --git a/plugins/pychrysa/analysis/db/module.c b/plugins/pychrysa/analysis/db/module.c
index 8c527a9..08c408c 100644
--- a/plugins/pychrysa/analysis/db/module.c
+++ b/plugins/pychrysa/analysis/db/module.c
@@ -25,8 +25,12 @@
#include "module.h"
+#include <assert.h>
+
+
#include "collection.h"
#include "item.h"
+#include "items/module.h"
@@ -65,28 +69,25 @@ bool add_analysis_db_module_to_python_module(PyObject *super)
if (module == NULL) return false;
ret = PyState_AddModule(super, &py_chrysalide_db_module);
- if (ret != 0) goto aadmtpm_exit;
+ if (ret != 0) goto loading_failed;
ret = _PyImport_FixupBuiltin(module, "pychrysalide.analysis.db");
- if (ret != 0) goto aadmtpm_exit;
+ if (ret != 0) goto loading_failed;
Py_INCREF(module);
ret = PyModule_AddObject(super, "db", module);
- if (ret != 0) goto aadmtpm_exit;
+ if (ret != 0) goto loading_failed;
result = true;
result &= register_python_db_collection(module);
result &= register_python_db_item(module);
- aadmtpm_exit:
+ result &= add_analysis_db_items_module_to_python_module(module);
- if (!result)
- {
- printf("something went wrong in %s...\n", __FUNCTION__);
- /* ... */
+ loading_failed:
- }
+ assert(result);
return result;
diff --git a/plugins/pychrysa/analysis/module.c b/plugins/pychrysa/analysis/module.c
index e13c8f8..d45a3f1 100644
--- a/plugins/pychrysa/analysis/module.c
+++ b/plugins/pychrysa/analysis/module.c
@@ -25,8 +25,15 @@
#include "module.h"
+#include <assert.h>
+
+
#include "binary.h"
+#include "block.h"
+#include "routine.h"
#include "binaries/module.h"
+#include "blocks/module.h"
+#include "db/module.h"
@@ -48,7 +55,7 @@ bool add_analysis_module_to_python_module(PyObject *super)
PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyModuleDef py_chrysalide_arch_module = {
+ static PyModuleDef py_chrysalide_analysis_module = {
.m_base = PyModuleDef_HEAD_INIT,
@@ -61,106 +68,33 @@ bool add_analysis_module_to_python_module(PyObject *super)
result = false;
- module = PyModule_Create(&py_chrysalide_arch_module);
+ module = PyModule_Create(&py_chrysalide_analysis_module);
if (module == NULL) return false;
- ret = PyState_AddModule(super, &py_chrysalide_arch_module);
- if (ret != 0) goto aamtpm_exit;
+ ret = PyState_AddModule(super, &py_chrysalide_analysis_module);
+ if (ret != 0) goto loading_failed;
ret = _PyImport_FixupBuiltin(module, "pychrysalide.analysis");
- if (ret != 0) goto aamtpm_exit;
+ if (ret != 0) goto loading_failed;
Py_INCREF(module);
ret = PyModule_AddObject(super, "analysis", module);
- if (ret != 0) goto aamtpm_exit;
+ if (ret != 0) goto loading_failed;
result = true;
result &= register_python_loaded_binary(module);
+ result &= register_python_instr_block(module);
+ result &= register_python_binary_routine(module);
result &= add_analysis_binaries_module_to_python_module(module);
+ result &= add_analysis_blocks_module_to_python_module(module);
+ result &= add_analysis_db_module_to_python_module(module);
- aamtpm_exit:
-
- if (!result)
- {
- printf("something went wrong in %s...\n", __FUNCTION__);
- /* ... */
-
- }
-
- return result;
-
-}
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+ loading_failed:
-#if 0
-#include "binary.h"
-#include "block.h"
-#include "routine.h"
-#include "binaries/module.h"
-#include "blocks/module.h"
-
-
-
-/******************************************************************************
-* *
-* Paramètres : module = module dont la définition est à compléter. *
-* *
-* Description : Ajoute le module 'analysis' au module Python. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-bool add_analysis_module_to_python_module(PyObject *super)
-{
- bool result;
- PyObject *module;
- int ret; /* Bilan d'un appel */
-
- static PyMethodDef py_analysis_methods[] = {
- { NULL }
- };
-
- module = Py_InitModule("pychrysalide.analysis", py_analysis_methods);
- if (module == NULL) return false;
-
- Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.analysis", module);
-
- result = (ret == 0);
-
- result &= register_python_loaded_binary(module);
- result &= register_python_binary_routine(module);
- result &= register_python_instructions_block(module);
- result &= add_binaries_module_to_python_module(module);
- result &= add_blocks_module_to_python_module(module);
+ assert(result);
return result;
}
-#endif
diff --git a/plugins/pychrysa/analysis/roptions.c b/plugins/pychrysa/analysis/roptions.c
deleted file mode 100644
index 72e99e5..0000000
--- a/plugins/pychrysa/analysis/roptions.c
+++ /dev/null
@@ -1,276 +0,0 @@
-
-/* Chrysalide - Outil d'analyse de fichiers binaires
- * roptions.c - équivalent Python du fichier "analysis/roptions.h"
- *
- * Copyright (C) 2010-2013 Cyrille Bagard
- *
- * This file is part of Chrysalide.
- *
- * 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 this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-
-#include "roptions.h"
-
-
-#include <pygobject.h>
-
-
-#include "../format/executable.h"
-
-
-
-
-/* Classe 'analysis.roptions' pour Python */
-typedef struct _py_rendering_options
-{
- PyObject_HEAD
-
- GRenderingOptions *glib; /* Options réelles manipulées */
-
-} py_rendering_options;
-
-
-
-
-/* Crée un nouvel objet Python de type 'py_rendering_options'. */
-static PyObject *py_rendering_options_new(PyTypeObject *, PyObject *, PyObject *);
-
-
-
-/* Indique si les adresses des instructions sont à afficher. */
-static PyObject *py_rendering_options_get_show_address(PyObject *, void *);
-
-/* Affiche (ou non) les adresses des instructions. */
-static int py_rendering_options_set_show_address(PyObject *, PyObject *, void *);
-
-
-
-
-/* Affiche (ou non) le code des instructions. */
-static PyObject *py_rendering_options_show_code(PyObject *, PyObject *);
-
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : type = type de l'objet à instancier. *
-* args = arguments fournis à l'appel. *
-* kwds = arguments de type key=val fournis. *
-* *
-* Description : Crée un nouvel objet Python de type 'py_rendering_options'. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static PyObject *py_rendering_options_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
-{
- py_rendering_options *result; /* Instance à retourner */
- PyObject *executable; /* Format d'exécutable joint */
- int ret; /* Bilan de lecture des args. */
- GExeFormat *_executable; /* Version GLib du format */
-
- ret = PyArg_ParseTuple(args, "O", &executable);
- if (!ret) Py_RETURN_NONE;
-
- result = (py_rendering_options *)type->tp_alloc(type, 0);
-
- _executable = G_EXE_FORMAT(pygobject_get(executable));
- if (_executable == NULL) return NULL;
-
- g_object_ref(G_OBJECT(_executable));
- result->glib = g_rendering_options_new(_executable);
-
- return (PyObject *)result;
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : roptions = instance Python dont la référence est à donner. *
-* *
-* Description : Fournit l'instance GLib d'une instance Python. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-GRenderingOptions *py_rendering_options_get_glib_instance(PyObject *roptions)
-{
- return ((py_rendering_options *)roptions)->glib;
-
-}
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : self = classe présentant des options de représentation. *
-* data = adresse non utilisée ici. *
-* *
-* Description : Indique si les adresses des instructions sont à afficher. *
-* *
-* Retour : Valeur booléenne indiquant le statut d'une option. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static PyObject *py_rendering_options_get_show_address(PyObject *self, void *data)
-{
-
- printf(" -->> get address\n");
-
- return Py_BuildValue("i", true);
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : self = classe présentant des options de représentation. *
-* value = nouvelle valeur affectée. *
-* data = adresse non utilisée ici. *
-* *
-* Description : Affiche (ou non) les adresses des instructions. *
-* *
-* Retour : Bilan de la mise à jour. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static int py_rendering_options_set_show_address(PyObject *self, PyObject *value, void *data)
-{
- printf(" -->> set address\n");
-
- return 0;
-
-}
-
-
-
-
-
-
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : self = classe assurant le lien avec l'éditeur de messages. *
-* args = arguments fournis à l'appel. *
-* *
-* Description : Affiche (ou non) le code des instructions. *
-* *
-* Retour : Rien en équivalent Python. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static PyObject *py_rendering_options_show_code(PyObject *self, PyObject *args)
-{
- int state; /* Nouveau statut d'affichage */
-
- if (!PyArg_ParseTuple(args, "i", &state))
- return NULL;
-
-
-
-
- printf("show code :: %d\n", state);
-
- Py_RETURN_NONE;
-
-}
-
-
-
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : module = module dont la définition est à compléter. *
-* *
-* Description : Ajoute l'objet 'analysis.roptions' au module Python. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-bool add_analysis_roptions_to_python_module(PyObject *module)
-{
- int ret; /* Bilan d'un appel */
-
- static PyMethodDef py_rendering_options_methods[] = {
- {
- "show_code", (PyCFunction)py_rendering_options_show_code,
- METH_VARARGS,
- "Define if the binary code has to be processed or not."
- },
- { NULL }
- };
-
- static PyGetSetDef py_rendering_options_getset[] = {
- {
- "show_address",
- (getter)py_rendering_options_get_show_address,
- (setter)py_rendering_options_set_show_address,
- "Define or retrieve if the instruction address need to be shown."
- },
- { NULL }
- };
-
- static PyTypeObject py_rendering_options_type = {
-
- PyObject_HEAD_INIT(NULL)
-
- .tp_name = "pyoida.analysis.RenderingOptions",
- .tp_basicsize = sizeof(py_rendering_options),
-
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
-
- .tp_doc = "PyOIDA rendering options",
-
- .tp_methods = py_rendering_options_methods,
- .tp_getset = py_rendering_options_getset,
- .tp_new = (newfunc)py_rendering_options_new
-
- };
-
- if (PyType_Ready(&py_rendering_options_type) < 0)
- return false;
-
- Py_INCREF(&py_rendering_options_type);
- ret = PyModule_AddObject(module, "RenderingOptions", (PyObject *)&py_rendering_options_type);
-
- return (ret == 0);
-
-}
diff --git a/plugins/pychrysa/analysis/routine.c b/plugins/pychrysa/analysis/routine.c
index 5cd56f5..2ca3560 100644
--- a/plugins/pychrysa/analysis/routine.c
+++ b/plugins/pychrysa/analysis/routine.c
@@ -25,25 +25,31 @@
#include "routine.h"
+#include <string.h>
#include <pygobject.h>
-#include <analysis/routine.h>
+#include <i18n.h>
+#include <analysis/routine.h>
-/* Crée un nouvel objet Python de type 'BinaryRoutine'. */
-static PyObject *py_binary_routine_new(PyTypeObject *, PyObject *, PyObject *);
+#include "block.h"
-/* Fournit les blocs basiques de la routine. */
-static PyObject *py_binary_routine_get_basic_blocks(PyObject *, void *);
+/* Crée un nouvel objet Python de type 'BinRoutine'. */
+static PyObject *py_binary_routine_new(PyTypeObject *, PyObject *, PyObject *);
-/* Décrit le prototype de la routine sous forme de caractères. */
-static PyObject *py_binary_routine_str(PyObject *);
+/* Fournit le nom humain d'une routine. */
+static PyObject *py_binary_routine_get_name(PyObject *, void *);
+/* Définit le nom humain d'une routine. */
+static int py_binary_routine_set_name(PyObject *, PyObject *, void *);
+
+/* Fournit les blocs basiques de la routine. */
+static PyObject *py_binary_routine_get_basic_blocks(PyObject *, void *);
@@ -72,7 +78,75 @@ static PyObject *py_binary_routine_new(PyTypeObject *type, PyObject *args, PyObj
}
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Fournit le nom humain d'une routine. *
+* *
+* Retour : Désignation humainement lisible ou None si non définie. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_routine_get_name(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBinRoutine *routine; /* Elément à consulter */
+ const char *name; /* Désignation courante */
+
+ routine = G_BIN_ROUTINE(pygobject_get(self));
+ name = g_binary_routine_get_name(routine);
+
+ if (name != NULL)
+ result = PyUnicode_FromString(name);
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* value = valeur fournie à intégrer ou prendre en compte. *
+* closure = non utilisé ici. *
+* *
+* Description : Définit le nom humain d'une routine. *
+* *
+* Retour : Bilan de l'opération pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static int py_binary_routine_set_name(PyObject *self, PyObject *value, void *closure)
+{
+ GBinRoutine *routine; /* Elément à consulter */
+
+ if (!PyUnicode_Check(value) && value != Py_None)
+ {
+ PyErr_SetString(PyExc_TypeError, _("The attribute value must be a string."));
+ return -1;
+ }
+
+ routine = G_BIN_ROUTINE(pygobject_get(self));
+
+ if (!PyUnicode_Check(value))
+ g_binary_routine_set_name(routine, strdup(PyUnicode_DATA(value)));
+ else
+ g_binary_routine_set_name(routine, NULL);
+ return 0;
+
+}
/******************************************************************************
@@ -104,78 +178,76 @@ static PyObject *py_binary_routine_get_basic_blocks(PyObject *self, void *closur
}
-
-
-
/******************************************************************************
* *
-* Paramètres : self = classe représentant une routine binaire. *
+* Paramètres : self = objet Python concerné par l'appel. *
+* value = valeur fournie à intégrer ou prendre en compte. *
+* closure = non utilisé ici. *
* *
-* Description : Décrit le prototype de la routine sous forme de caractères. *
+* Description : Définit les blocs basiques de la routine. *
* *
-* Retour : Chaîne de caractères. *
+* Retour : Bilan de l'opération pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_binary_routine_str(PyObject *self)
+static int py_binary_routine_set_basic_blocks(PyObject *self, PyObject *value, void *closure)
{
- PyObject *result; /* Chaîne à retourner */
- GBinRoutine *routine; /* Version native */
- char *string; /* Description à libérer */
+ GBinRoutine *routine; /* Elément à consulter */
+ int ret; /* Bilan de lecture des args. */
+ GInstrBlock *blocks; /* Blocs basiques à intégrer */
- routine = G_BIN_ROUTINE(pygobject_get(self));
- string = g_binary_routine_to_string(routine);
+ ret = PyObject_IsInstance(value, (PyObject *)get_python_instr_block_type());
+ if (!ret) return -1;
- result = PyString_FromString(string);
+ routine = G_BIN_ROUTINE(pygobject_get(self));
+ blocks = G_INSTR_BLOCK(pygobject_get(value));
- free(string);
+ g_binary_routine_set_basic_blocks(routine, blocks);
- return result;
+ return 0;
}
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.analysis.LoadedBinary'.*
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_binary_routine(PyObject *module)
+PyTypeObject *get_python_binary_routine_type(void)
{
- PyObject *pygobj_mod; /* Module Python-GObject */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_binary_routine_methods[] = {
{ NULL }
};
static PyGetSetDef py_binary_routine_getseters[] = {
{
- "basic_blocks", (getter)py_binary_routine_get_basic_blocks, (setter)NULL,
- "Provide the basic blocks of the binary routine.", NULL
+ "name", py_binary_routine_get_name, py_binary_routine_set_name,
+ "Name of the current routine.", NULL
+ },
+ {
+ "basic_blocks", py_binary_routine_get_basic_blocks, py_binary_routine_set_basic_blocks,
+ "Basic blocks of the binary routine.", NULL
},
{ NULL }
};
static PyTypeObject py_binary_routine_type = {
- PyObject_HEAD_INIT(NULL)
-
- .tp_name = "pychrysalide.analysis.BinaryRoutine",
- .tp_basicsize = sizeof(PyGObject),
+ PyVarObject_HEAD_INIT(NULL, 0)
- .tp_str = py_binary_routine_str,
+ .tp_name = "pychrysalide.analysis.BinRoutine",
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT,
.tp_doc = "PyChrysalide binary routine",
@@ -185,21 +257,45 @@ bool register_python_binary_routine(PyObject *module)
};
- pygobj_mod = PyImport_ImportModule("gobject");
- if (pygobj_mod == NULL) return false;
+ return &py_binary_routine_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.analysis.BinRoutine'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_binary_routine(PyObject *module)
+{
+ PyTypeObject *py_binary_routine_type; /* Type Python 'BinRoutine' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_binary_routine_type = get_python_binary_routine_type();
- py_binary_routine_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(pygobj_mod, "GObject");
- Py_DECREF(pygobj_mod);
+ py_binary_routine_type->tp_base = &PyGObject_Type;
+ py_binary_routine_type->tp_basicsize = py_binary_routine_type->tp_base->tp_basicsize;
- if (PyType_Ready(&py_binary_routine_type) < 0)
+ if (PyType_Ready(py_binary_routine_type) != 0)
return false;
- Py_INCREF(&py_binary_routine_type);
- ret = PyModule_AddObject(module, "BinaryRoutine", (PyObject *)&py_binary_routine_type);
+ Py_INCREF(py_binary_routine_type);
+ ret = PyModule_AddObject(module, "BinRoutine", (PyObject *)py_binary_routine_type);
+ if (ret != 0) return false;
- pygobject_register_class(module, "GBinRoutine", G_TYPE_BIN_ROUTINE, &py_binary_routine_type,
- Py_BuildValue("(O)", py_binary_routine_type.tp_base));
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "BinRoutine", G_TYPE_BIN_ROUTINE, py_binary_routine_type,
+ Py_BuildValue("(O)", py_binary_routine_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/analysis/routine.h b/plugins/pychrysa/analysis/routine.h
index 7c72fa4..ec61466 100644
--- a/plugins/pychrysa/analysis/routine.h
+++ b/plugins/pychrysa/analysis/routine.h
@@ -31,7 +31,10 @@
-/* Prend en charge l'objet 'pychrysalide.analysis.BinaryRoutine'. */
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_binary_routine_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.analysis.BinRoutine'. */
bool register_python_binary_routine(PyObject *);
diff --git a/plugins/pychrysa/arch/Makefile.am b/plugins/pychrysa/arch/Makefile.am
index 54b9261..7607ed8 100644
--- a/plugins/pychrysa/arch/Makefile.am
+++ b/plugins/pychrysa/arch/Makefile.am
@@ -2,9 +2,14 @@
noinst_LTLIBRARIES = libpychrysaarch.la
libpychrysaarch_la_SOURCES = \
+ instruction.h instruction.c \
module.h module.c \
+ processor.h processor.c \
vmpa.h vmpa.c
+libpychrysaarch_la_LIBADD = \
+ arm/libpychrysaarcharm.la
+
# libpychrysaarch_la_SOURCES = \
# archbase.h archbase.c \
# instruction.h instruction.c \
@@ -19,3 +24,5 @@ AM_CPPFLAGS = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS) $(LIBPYTHON_CFLAGS) $(LIBPYGOBJE
-I../../../src
AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS)
+
+SUBDIRS = arm
diff --git a/plugins/pychrysa/arch/arm/Makefile.am b/plugins/pychrysa/arch/arm/Makefile.am
new file mode 100644
index 0000000..b081061
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/Makefile.am
@@ -0,0 +1,20 @@
+
+noinst_LTLIBRARIES = libpychrysaarcharm.la
+
+libpychrysaarcharm_la_SOURCES = \
+ instruction.h instruction.c \
+ module.h module.c \
+ processor.h processor.c
+
+libpychrysaarcharm_la_LIBADD = \
+ v7/libpychrysaarcharmv7.la
+
+libpychrysaarcharm_la_LDFLAGS =
+
+
+AM_CPPFLAGS = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS) $(LIBPYTHON_CFLAGS) $(LIBPYGOBJECT_CFLAGS) \
+ -I../../../../src
+
+AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS)
+
+SUBDIRS = v7
diff --git a/plugins/pychrysa/arch/arm/instruction.c b/plugins/pychrysa/arch/arm/instruction.c
new file mode 100644
index 0000000..ed53386
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/instruction.c
@@ -0,0 +1,120 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * instruction.c - équivalent Python du fichier "arch/arm/instruction.c"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "instruction.h"
+
+
+#include <pygobject.h>
+
+
+#include <arch/arm/instruction.h>
+
+
+#include "../instruction.h"
+#include "../../helpers.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_arm_instruction_type(void)
+{
+ static PyMethodDef py_arm_instruction_methods[] = {
+ { NULL }
+ };
+
+ static PyGetSetDef py_arm_instruction_getseters[] = {
+ { NULL }
+ };
+
+ static PyTypeObject py_arm_instruction_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.arch.arm.ArmInstruction",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+
+ .tp_doc = "PyChrysalide instruction for an ARM architecture.",
+
+ .tp_methods = py_arm_instruction_methods,
+ .tp_getset = py_arm_instruction_getseters,
+
+ };
+
+ return &py_arm_instruction_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide....arm.ArmInstruction'.*
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_arm_instruction(PyObject *module)
+{
+ PyTypeObject *py_arm_instruction_type; /* Type Python 'BinContent' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_arm_instruction_type = get_python_arm_instruction_type();
+
+ py_arm_instruction_type->tp_base = get_python_arch_instruction_type();
+ py_arm_instruction_type->tp_basicsize = py_arm_instruction_type->tp_base->tp_basicsize;
+
+ APPLY_ABSTRACT_FLAG(py_arm_instruction_type);
+
+ if (PyType_Ready(py_arm_instruction_type) != 0)
+ return false;
+
+ Py_INCREF(py_arm_instruction_type);
+ ret = PyModule_AddObject(module, "ArmInstruction", (PyObject *)py_arm_instruction_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ArmInstruction", G_TYPE_ARM_INSTRUCTION, py_arm_instruction_type,
+ Py_BuildValue("(O)", py_arm_instruction_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/arch/arm/instruction.h b/plugins/pychrysa/arch/arm/instruction.h
new file mode 100644
index 0000000..daec429
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/instruction.h
@@ -0,0 +1,42 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * instruction.h - prototypes pour l'équivalent Python du fichier "arch/arm/instruction.h"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_ARCH_ARM_INSTRUCTION_H
+#define _PLUGINS_PYCHRYSALIDE_ARCH_ARM_INSTRUCTION_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_arm_instruction_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.arch.arm.ArmInstruction'. */
+bool register_python_arm_instruction(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_ARM_INSTRUCTION_H */
diff --git a/plugins/pychrysa/arch/arm/module.c b/plugins/pychrysa/arch/arm/module.c
new file mode 100644
index 0000000..d1d7adc
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/module.c
@@ -0,0 +1,96 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * module.c - intégration du répertoire arm en tant que module
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "module.h"
+
+
+#include "instruction.h"
+#include "processor.h"
+#include "v7/module.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Ajoute le module 'arm' au module Python. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool add_arch_arm_module_to_python_module(PyObject *super)
+{
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
+ int ret; /* Bilan d'un appel */
+
+ static PyModuleDef py_chrysalide_arm_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.arch.arm",
+ .m_doc = "Python module for Chrysalide.arch.arm",
+
+ .m_size = -1,
+
+ };
+
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_arm_module);
+ if (module == NULL) return false;
+
+ ret = PyState_AddModule(super, &py_chrysalide_arm_module);
+ if (ret != 0) goto aaamtpm_exit;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.arch.arm");
+ if (ret != 0) goto aaamtpm_exit;
+
+ Py_INCREF(module);
+ ret = PyModule_AddObject(super, "arm", module);
+ if (ret != 0) goto aaamtpm_exit;
+
+ result = true;
+
+ result &= register_python_arm_instruction(module);
+ result &= register_python_arm_processor(module);
+
+ result &= add_arch_arm_v7_module_to_python_module(module);
+
+ aaamtpm_exit:
+
+ if (!result)
+ {
+ printf("something went wrong in %s...\n", __FUNCTION__);
+ /* ... */
+
+ }
+
+ return result;
+
+}
diff --git a/plugins/pychrysa/arch/arm/module.h b/plugins/pychrysa/arch/arm/module.h
new file mode 100644
index 0000000..eed753f
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/module.h
@@ -0,0 +1,39 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * module.h - prototypes pour l'intégration du répertoire arm en tant que module
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_ARCH_ARM_MODULE_H
+#define _PLUGINS_PYCHRYSALIDE_ARCH_ARM_MODULE_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Ajoute le module 'arm' au module Python. */
+bool add_arch_arm_module_to_python_module(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_ARM_MODULE_H */
diff --git a/plugins/pychrysa/arch/arm/processor.c b/plugins/pychrysa/arch/arm/processor.c
new file mode 100644
index 0000000..049dcb3
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/processor.c
@@ -0,0 +1,120 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * processor.c - équivalent Python du fichier "arch/arm/processor.c"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "processor.h"
+
+
+#include <pygobject.h>
+
+
+#include <arch/arm/processor.h>
+
+
+#include "../processor.h"
+#include "../../helpers.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_arm_processor_type(void)
+{
+ static PyMethodDef py_arm_processor_methods[] = {
+ { NULL }
+ };
+
+ static PyGetSetDef py_arm_processor_getseters[] = {
+ { NULL }
+ };
+
+ static PyTypeObject py_arm_processor_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.arch.arm.ArmProcessor",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+
+ .tp_doc = "PyChrysalide processor for an ARM architecture.",
+
+ .tp_methods = py_arm_processor_methods,
+ .tp_getset = py_arm_processor_getseters,
+
+ };
+
+ return &py_arm_processor_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.arch.arm.ArmProcessor'.*
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_arm_processor(PyObject *module)
+{
+ PyTypeObject *py_arm_processor_type; /* Type Python 'BinContent' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_arm_processor_type = get_python_arm_processor_type();
+
+ py_arm_processor_type->tp_base = get_python_arch_processor_type();
+ py_arm_processor_type->tp_basicsize = py_arm_processor_type->tp_base->tp_basicsize;
+
+ APPLY_ABSTRACT_FLAG(py_arm_processor_type);
+
+ if (PyType_Ready(py_arm_processor_type) != 0)
+ return false;
+
+ Py_INCREF(py_arm_processor_type);
+ ret = PyModule_AddObject(module, "ArmProcessor", (PyObject *)py_arm_processor_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ArmProcessor", G_TYPE_ARM_PROCESSOR, py_arm_processor_type,
+ Py_BuildValue("(O)", py_arm_processor_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/arch/arm/processor.h b/plugins/pychrysa/arch/arm/processor.h
new file mode 100644
index 0000000..594f0e6
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/processor.h
@@ -0,0 +1,42 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * processor.h - prototypes pour l'équivalent Python du fichier "arch/arm/processor.h"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_ARCH_ARM_PROCESSOR_H
+#define _PLUGINS_PYCHRYSALIDE_ARCH_ARM_PROCESSOR_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_arm_processor_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.arch.arm.ArmProcessor'. */
+bool register_python_arm_processor(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_ARM_PROCESSOR_H */
diff --git a/plugins/pychrysa/arch/arm/v7/Makefile.am b/plugins/pychrysa/arch/arm/v7/Makefile.am
new file mode 100644
index 0000000..d95aff3
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/v7/Makefile.am
@@ -0,0 +1,16 @@
+
+noinst_LTLIBRARIES = libpychrysaarcharmv7.la
+
+libpychrysaarcharmv7_la_SOURCES = \
+ instruction.h instruction.c \
+ module.h module.c \
+ processor.h processor.c
+
+
+libpychrysaarcharmv7_la_LDFLAGS =
+
+
+AM_CPPFLAGS = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS) $(LIBPYTHON_CFLAGS) $(LIBPYGOBJECT_CFLAGS) \
+ -I../../../../../src
+
+AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS)
diff --git a/plugins/pychrysa/arch/arm/v7/instruction.c b/plugins/pychrysa/arch/arm/v7/instruction.c
new file mode 100644
index 0000000..8a19259
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/v7/instruction.c
@@ -0,0 +1,117 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * instruction.c - équivalent Python du fichier "arch/arm/v7/instruction.c"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "instruction.h"
+
+
+#include <pygobject.h>
+
+
+#include <arch/arm/v7/instruction.h>
+
+
+#include "../instruction.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_armv7_instruction_type(void)
+{
+ static PyMethodDef py_armv7_instruction_methods[] = {
+ { NULL }
+ };
+
+ static PyGetSetDef py_armv7_instruction_getseters[] = {
+ { NULL }
+ };
+
+ static PyTypeObject py_armv7_instruction_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.arch.arm.v7.ArmV7Instruction",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "PyChrysalide instruction for an ARMv7 architecture.",
+
+ .tp_methods = py_armv7_instruction_methods,
+ .tp_getset = py_armv7_instruction_getseters,
+
+ };
+
+ return &py_armv7_instruction_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide....arm.ArmInstruction'.*
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_armv7_instruction(PyObject *module)
+{
+ PyTypeObject *py_armv7_instruction_type;/* Type Python 'BinContent' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_armv7_instruction_type = get_python_armv7_instruction_type();
+
+ py_armv7_instruction_type->tp_base = get_python_arm_instruction_type();
+ py_armv7_instruction_type->tp_basicsize = py_armv7_instruction_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_armv7_instruction_type) != 0)
+ return false;
+
+ Py_INCREF(py_armv7_instruction_type);
+ ret = PyModule_AddObject(module, "ArmV7Instruction", (PyObject *)py_armv7_instruction_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ArmV7Instruction", G_TYPE_ARMV7_INSTRUCTION, py_armv7_instruction_type,
+ Py_BuildValue("(O)", py_armv7_instruction_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/arch/arm/v7/instruction.h b/plugins/pychrysa/arch/arm/v7/instruction.h
new file mode 100644
index 0000000..9eac361
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/v7/instruction.h
@@ -0,0 +1,42 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * instruction.h - prototypes pour l'équivalent Python du fichier "arch/arm/v7/instruction.h"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_INSTRUCTION_H
+#define _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_INSTRUCTION_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_armv7_instruction_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.arch.arm.v7.ArmV7Instruction'. */
+bool register_python_armv7_instruction(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_INSTRUCTION_H */
diff --git a/plugins/pychrysa/arch/arm/v7/module.c b/plugins/pychrysa/arch/arm/v7/module.c
new file mode 100644
index 0000000..7c0aabf
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/v7/module.c
@@ -0,0 +1,93 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * module.c - intégration du répertoire v7 en tant que module
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "module.h"
+
+
+#include "instruction.h"
+#include "processor.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Ajoute le module 'arm' au module Python. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool add_arch_arm_v7_module_to_python_module(PyObject *super)
+{
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
+ int ret; /* Bilan d'un appel */
+
+ static PyModuleDef py_chrysalide_v7_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.arch.arm.v7",
+ .m_doc = "Python module for Chrysalide.arch.arm.v7",
+
+ .m_size = -1,
+
+ };
+
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_v7_module);
+ if (module == NULL) return false;
+
+ ret = PyState_AddModule(super, &py_chrysalide_v7_module);
+ if (ret != 0) goto aaamtpm_exit;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.arch.arm.v7");
+ if (ret != 0) goto aaamtpm_exit;
+
+ Py_INCREF(module);
+ ret = PyModule_AddObject(super, "v7", module);
+ if (ret != 0) goto aaamtpm_exit;
+
+ result = true;
+
+ result &= register_python_armv7_instruction(module);
+ result &= register_python_armv7_processor(module);
+
+ aaamtpm_exit:
+
+ if (!result)
+ {
+ printf("something went wrong in %s...\n", __FUNCTION__);
+ /* ... */
+
+ }
+
+ return result;
+
+}
diff --git a/plugins/pychrysa/arch/arm/v7/module.h b/plugins/pychrysa/arch/arm/v7/module.h
new file mode 100644
index 0000000..61ad126
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/v7/module.h
@@ -0,0 +1,39 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * module.h - prototypes pour l'intégration du répertoire v7 en tant que module
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_MODULE_H
+#define _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_MODULE_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Ajoute le module 'arm' au module Python. */
+bool add_arch_arm_v7_module_to_python_module(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_MODULE_H */
diff --git a/plugins/pychrysa/arch/arm/v7/processor.c b/plugins/pychrysa/arch/arm/v7/processor.c
new file mode 100644
index 0000000..1844066
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/v7/processor.c
@@ -0,0 +1,117 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * processor.c - équivalent Python du fichier "arch/arm/v7/processor.c"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "processor.h"
+
+
+#include <pygobject.h>
+
+
+#include <arch/arm/v7/processor.h>
+
+
+#include "../processor.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_armv7_processor_type(void)
+{
+ static PyMethodDef py_armv7_processor_methods[] = {
+ { NULL }
+ };
+
+ static PyGetSetDef py_armv7_processor_getseters[] = {
+ { NULL }
+ };
+
+ static PyTypeObject py_armv7_processor_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.arch.arm.v7.ArmV7Processor",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "PyChrysalide processor for an ARMv7 architecture.",
+
+ .tp_methods = py_armv7_processor_methods,
+ .tp_getset = py_armv7_processor_getseters,
+
+ };
+
+ return &py_armv7_processor_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.arch.arm.ArmProcessor'.*
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_armv7_processor(PyObject *module)
+{
+ PyTypeObject *py_armv7_processor_type; /* Type Python 'BinContent' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_armv7_processor_type = get_python_armv7_processor_type();
+
+ py_armv7_processor_type->tp_base = get_python_arm_processor_type();
+ py_armv7_processor_type->tp_basicsize = py_armv7_processor_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_armv7_processor_type) != 0)
+ return false;
+
+ Py_INCREF(py_armv7_processor_type);
+ ret = PyModule_AddObject(module, "ArmV7Processor", (PyObject *)py_armv7_processor_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ArmV7Processor", G_TYPE_ARMV7_PROCESSOR, py_armv7_processor_type,
+ Py_BuildValue("(O)", py_armv7_processor_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/arch/arm/v7/processor.h b/plugins/pychrysa/arch/arm/v7/processor.h
new file mode 100644
index 0000000..268a025
--- /dev/null
+++ b/plugins/pychrysa/arch/arm/v7/processor.h
@@ -0,0 +1,42 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * processor.h - prototypes pour l'équivalent Python du fichier "arch/arm/v7/processor.h"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_PROCESSOR_H
+#define _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_PROCESSOR_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_armv7_processor_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.arch.arm.v7.ArmV7Processor'. */
+bool register_python_armv7_processor(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_ARM_V7_PROCESSOR_H */
diff --git a/plugins/pychrysa/arch/instruction.c b/plugins/pychrysa/arch/instruction.c
index efbdaa5..d675226 100644
--- a/plugins/pychrysa/arch/instruction.c
+++ b/plugins/pychrysa/arch/instruction.c
@@ -25,6 +25,384 @@
#include "instruction.h"
+#include <assert.h>
+#include <pygobject.h>
+
+
+#include <arch/instruction.h>
+
+
+#include "vmpa.h"
+#include "../helpers.h"
+
+
+
+
+/* ------------------- DEFINITION DES LIAISONS ENTRE INSTRUCTIONS ------------------- */
+
+
+
+
+
+/* --------------------- INSTRUCTIONS D'ARCHITECTURES EN PYTHON --------------------- */
+
+
+
+/* Fournit la place mémoire d'une instruction. */
+static PyObject *py_arch_instruction_get_range(PyObject *, void *);
+
+/* Définit la localisation d'une instruction. */
+static int py_arch_instruction_set_range(PyObject *, PyObject *, void *);
+
+
+
+/* Fournit le nom humain de l'instruction manipulée. */
+static PyObject *py_arch_instruction_get_keyword(PyObject *, void *);
+
+
+
+
+
+
+
+
+
+
+
+
+/* ---------------------------------------------------------------------------------- */
+/* DEFINITION DES LIAISONS ENTRE INSTRUCTIONS */
+/* ---------------------------------------------------------------------------------- */
+
+
+
+
+/* Fournit les origines d'une instruction donnée. */
+static PyObject *py_arch_instruction_get_sources(PyObject *, PyObject *);
+
+/* Fournit les destinations d'une instruction donnée. */
+static PyObject *py_arch_instruction_get_destinations(PyObject *, PyObject *);
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : self = instruction d'architecture à manipuler. *
+* args = liste d'arguments non utilisée ici. *
+* *
+* Description : Fournit les origines d'une instruction donnée. *
+* *
+* Retour : Nombre de ces origines. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_arch_instruction_get_sources(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ GArchInstruction *instr; /* Version native */
+ GArchInstruction **dests; /* Destination des liens */
+ InstructionLinkType *types; /* Nature de ces liens */
+ size_t count; /* Nombre de liens présents */
+ size_t i; /* Boucle de parcours */
+ PyObject *dest; /* Destination de lien Python */
+ PyObject *type; /* Nature du lien en Python */
+ int ret; /* Bilan d'une écriture d'arg. */
+
+ instr = G_ARCH_INSTRUCTION(pygobject_get(self));
+
+ count = g_arch_instruction_get_sources(instr, &dests, &types);
+
+ result = PyTuple_New(count);
+
+ for (i = 0; i < count; i++)
+ {
+ dest = pygobject_new(G_OBJECT(dests[i]));
+ type = PyLong_FromLong(types[i]);
+
+ ret = PyTuple_SetItem(result, i, Py_BuildValue("(OO)", dest, type));
+ assert(ret == 0);
+
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = instruction d'architecture à manipuler. *
+* args = liste d'arguments non utilisée ici. *
+* *
+* Description : Fournit les destinations d'une instruction donnée. *
+* *
+* Retour : Nombre de ces destinations. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_arch_instruction_get_destinations(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ GArchInstruction *instr; /* Version native */
+ GArchInstruction **dests; /* Destination des liens */
+ InstructionLinkType *types; /* Nature de ces liens */
+ size_t count; /* Nombre de liens présents */
+ size_t i; /* Boucle de parcours */
+ PyObject *dest; /* Destination de lien Python */
+ PyObject *type; /* Nature du lien en Python */
+ int ret; /* Bilan d'une écriture d'arg. */
+
+ instr = G_ARCH_INSTRUCTION(pygobject_get(self));
+
+ count = g_arch_instruction_get_destinations(instr, &dests, &types, NULL);
+
+ result = PyTuple_New(count);
+
+ for (i = 0; i < count; i++)
+ {
+ dest = pygobject_new(G_OBJECT(dests[i]));
+ type = PyLong_FromLong(types[i]);
+
+ ret = PyTuple_SetItem(result, i, Py_BuildValue("(OO)", dest, type));
+ assert(ret == 0);
+
+ }
+
+ return result;
+
+}
+
+
+
+
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant une instruction. *
+* closure = adresse non utilisée ici. *
+* *
+* Description : Fournit la place mémoire d'une instruction. *
+* *
+* Retour : Valeur associée à la propriété consultée. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_arch_instruction_get_range(PyObject *self, void *closure)
+{
+ PyObject *result; /* Conversion à retourner */
+ GArchInstruction *instr; /* Version native */
+ const mrange_t *range; /* Espace mémoire à exporter */
+
+ instr = G_ARCH_INSTRUCTION(pygobject_get(self));
+ range = g_arch_instruction_get_range(instr);
+
+ result = build_from_internal_mrange(range);
+
+ return result;
+
+}
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* value = valeur fournie à intégrer ou prendre en compte. *
+* closure = adresse non utilisée ici. *
+* *
+* Description : Définit la localisation d'une instruction. *
+* *
+* Retour : Bilan de l'opération pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static int py_arch_instruction_set_range(PyObject *self, PyObject *value, void *closure)
+{
+ int ret; /* Bilan d'analyse */
+ mrange_t *range; /* Espace mémoire à manipuler */
+ GArchInstruction *instr; /* Version native */
+
+ ret = PyObject_IsInstance(value, (PyObject *)get_python_mrange_type());
+ if (!ret) return -1;
+
+ range = get_internal_mrange(value);
+
+ instr = G_ARCH_INSTRUCTION(pygobject_get(self));
+ g_arch_instruction_set_range(instr, range);
+
+ return 0;
+
+}
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant une instruction. *
+* unused = adresse non utilisée ici. *
+* *
+* Description : Fournit le nom humain de l'instruction manipulée. *
+* *
+* Retour : Valeur associée à la propriété consultée. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_arch_instruction_get_keyword(PyObject *self, void *unused)
+{
+ PyObject *result; /* Trouvailles à retourner */
+ GArchInstruction *instr; /* Version native */
+ const char *kw; /* Valeur récupérée */
+
+ instr = G_ARCH_INSTRUCTION(pygobject_get(self));
+ kw = g_arch_instruction_get_keyword(instr, 0/* FIXME*/);
+
+ result = PyUnicode_FromString(kw);
+
+ return result;
+
+}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_arch_instruction_type(void)
+{
+ static PyMethodDef py_arch_instruction_methods[] = {
+ { "get_sources", py_arch_instruction_get_sources,
+ METH_NOARGS,
+ "get_sources(, /)\n--\n\nProvide the instructions list driving to the current instruction."
+ },
+ { "get_destinations", py_arch_instruction_get_destinations,
+ METH_NOARGS,
+ "get_destinations(, /)\n--\n\nProvide the instructions list following the current instruction."
+ },
+ { NULL }
+ };
+
+ static PyGetSetDef py_arch_instruction_getseters[] = {
+ {
+ "range", py_arch_instruction_get_range, py_arch_instruction_set_range,
+ "Give access to the memory range covered by the current instruction.", NULL
+ },
+ {
+ "keyword", (getter)py_arch_instruction_get_keyword, (setter)NULL,
+ "Give le name of the assembly instruction.", NULL
+ },
+ { NULL }
+ };
+
+ static PyTypeObject py_arch_instruction_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.arch.ArchInstruction",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IS_ABSTRACT | Py_TPFLAGS_BASETYPE,
+
+ .tp_doc = "PyChrysalide instruction for a given architecture.",
+
+ .tp_methods = py_arch_instruction_methods,
+ .tp_getset = py_arch_instruction_getseters,
+
+ };
+
+ return &py_arch_instruction_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.arch.ArchInstruction'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_arch_instruction(PyObject *module)
+{
+ PyTypeObject *py_arch_instruction_type; /* Type Python 'BinContent' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_arch_instruction_type = get_python_arch_instruction_type();
+
+ py_arch_instruction_type->tp_base = &PyGObject_Type;
+ py_arch_instruction_type->tp_basicsize = py_arch_instruction_type->tp_base->tp_basicsize;
+
+ APPLY_ABSTRACT_FLAG(py_arch_instruction_type);
+
+ if (PyType_Ready(py_arch_instruction_type) != 0)
+ return false;
+
+ Py_INCREF(py_arch_instruction_type);
+ ret = PyModule_AddObject(module, "ArchInstruction", (PyObject *)py_arch_instruction_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ArchInstruction", G_TYPE_ARCH_INSTRUCTION, py_arch_instruction_type,
+ Py_BuildValue("(O)", py_arch_instruction_type->tp_base));
+
+ return true;
+
+}
+
+
+
+
+
+
+
+#if 0
+
+
#include <pygobject.h>
#include <stdbool.h>
#include <string.h>
@@ -330,34 +708,6 @@ static PyObject *py_arch_instruction_get_location(PyObject *self, char *name)
}
-/******************************************************************************
-* *
-* Paramètres : self = classe représentant une instruction. *
-* unused = adresse non utilisée ici. *
-* *
-* Description : Fournit le nom humain de l'instruction manipulée. *
-* *
-* Retour : Valeur associée à la propriété consultée. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static PyObject *py_arch_instruction_get_keyword(PyObject *self, void *unused)
-{
- PyObject *result; /* Trouvailles à retourner */
- GArchInstruction *instr; /* Version native */
- const char *kw; /* Valeur récupérée */
-
- instr = G_ARCH_INSTRUCTION(pygobject_get(self));
- kw = g_arch_instruction_get_keyword(instr);
-
- result = PyString_FromString(kw);
-
- return result;
-
-}
-
/******************************************************************************
* *
@@ -438,3 +788,6 @@ bool register_python_arch_instruction(PyObject *module)
return (ret == 0);
}
+
+
+#endif
diff --git a/plugins/pychrysa/arch/instruction.h b/plugins/pychrysa/arch/instruction.h
index 7b81d65..c3f8bd9 100644
--- a/plugins/pychrysa/arch/instruction.h
+++ b/plugins/pychrysa/arch/instruction.h
@@ -31,16 +31,8 @@
-/* --------------------- ITERATEUR POUR BOUCLE SUR INSTRUCTIONS --------------------- */
-
-
-/* Permet une itération de 'pychrysalide.arch.ArchInstruction'. */
-bool register_python_arch_instruction_iterator(PyObject *);
-
-
-
-/* --------------------- INSTRUCTIONS D'ARCHITECTURES EN PYTHON --------------------- */
-
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_arch_instruction_type(void);
/* Prend en charge l'objet 'pychrysalide.arch.ArchInstruction'. */
bool register_python_arch_instruction(PyObject *);
diff --git a/plugins/pychrysa/arch/module.c b/plugins/pychrysa/arch/module.c
index 92172e0..6df56a9 100644
--- a/plugins/pychrysa/arch/module.c
+++ b/plugins/pychrysa/arch/module.c
@@ -25,7 +25,13 @@
#include "module.h"
+#include <assert.h>
+
+
+#include "instruction.h"
+#include "processor.h"
#include "vmpa.h"
+#include "arm/module.h"
@@ -64,27 +70,27 @@ bool add_arch_module_to_python_module(PyObject *super)
if (module == NULL) return false;
ret = PyState_AddModule(super, &py_chrysalide_arch_module);
- if (ret != 0) goto aamtpm_exit;
+ if (ret != 0) goto loading_failed;
ret = _PyImport_FixupBuiltin(module, "pychrysalide.arch");
- if (ret != 0) goto aamtpm_exit;
+ if (ret != 0) goto loading_failed;
Py_INCREF(module);
ret = PyModule_AddObject(super, "arch", module);
- if (ret != 0) goto aamtpm_exit;
+ if (ret != 0) goto loading_failed;
result = true;
+ result &= register_python_arch_instruction(module);
+ result &= register_python_arch_processor(module);
result &= register_python_vmpa(module);
+ result &= register_python_mrange(module);
- aamtpm_exit:
+ result &= add_arch_arm_module_to_python_module(module);
- if (!result)
- {
- printf("something went wrong in %s...\n", __FUNCTION__);
- /* ... */
+ loading_failed:
- }
+ assert(result);
return result;
diff --git a/plugins/pychrysa/arch/processor.c b/plugins/pychrysa/arch/processor.c
index 6a275d4..0a9ae3a 100644
--- a/plugins/pychrysa/arch/processor.c
+++ b/plugins/pychrysa/arch/processor.c
@@ -1,8 +1,8 @@
/* Chrysalide - Outil d'analyse de fichiers binaires
- * processor.h - prototypes pour l'équivalent Python du fichier "arch/processor.h"
+ * processor.c - équivalent Python du fichier "arch/processor.c"
*
- * Copyright (C) 2010-2013 Cyrille Bagard
+ * Copyright (C) 2015 Cyrille Bagard
*
* This file is part of Chrysalide.
*
@@ -25,22 +25,21 @@
#include "processor.h"
-#include "../../../src/arch/processor.h"
+#include <pygobject.h>
+#include <i18n.h>
-/* ------------------------- TYPAGE DES ENUMERATIONS PYTHON ------------------------- */
+#include <arch/processor.h>
-/* Définit les constantes pour les types de processeur. */
-bool py_arch_processor_type_define_constants(PyObject *);
-/* Ajoute l'objet 'arch.processor.ArchProcessorType' au module. */
-bool add_arch_processor_type_to_python_module(PyObject *);
+#include "instruction.h"
+#include "vmpa.h"
+#include "../helpers.h"
-/* ------------------------- PARTIE STATIQUE DE PROCESSEURS ------------------------- */
@@ -48,12 +47,7 @@ bool add_arch_processor_type_to_python_module(PyObject *);
-/* Classe 'analysis.roptions' pour Python */
-typedef struct _py_processor
-{
- PyObject_HEAD
-} py_processor;
@@ -63,120 +57,246 @@ typedef struct _py_processor
+/* ------------------ MANIPULATIONS DES INSTRUCTIONS DESASSEMBLEES ------------------ */
+
+
+
+/* Fournit les instructions désassemblées pour une architecture. */
+static PyObject *py_arch_processor_get_disass_instrs(PyObject *, void *);
+
+/* Recherche une instruction d'après son adresse. */
+static PyObject *py_arch_processor_find_instr_by_addr(PyObject *, PyObject *);
+
+/* Fournit l'instruction qui en précède une autre. */
+static PyObject *py_arch_processor_get_prev_instr(PyObject *, PyObject *);
+
+/* Fournit l'instruction qui en suit une autre. */
+static PyObject *py_arch_processor_get_next_instr(PyObject *, PyObject *);
+
+
+
+
/* ---------------------------------------------------------------------------------- */
-/* TYPAGE DES ENUMERATIONS PYTHON */
+/* MANIPULATIONS DES INSTRUCTIONS DESASSEMBLEES */
/* ---------------------------------------------------------------------------------- */
/******************************************************************************
* *
-* Paramètres : dict = dictionnaire à compléter. *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
* *
-* Description : Définit les constantes pour les types de processeur. *
+* Description : Fournit les instructions désassemblées pour une architecture.*
* *
-* Retour : - *
+* Retour : Liste des instructions désassemblées ou None si aucune. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool py_arch_processor_type_define_constants(PyObject *dict)
+static PyObject *py_arch_processor_get_disass_instrs(PyObject *self, void *closure)
{
- int ret; /* Bilan d'un ajout */
+ PyObject *result; /* Instance Python à retourner */
+ GArchProcessor *proc; /* Architecture visée */
+ GArchInstruction *instrs; /* Série d'instructions liées */
- ret = PyDict_SetItemString(dict, "APT_JVM", PyInt_FromLong(APT_JVM));
- if (ret == -1) return false;
+ proc = G_ARCH_PROCESSOR(pygobject_get(self));
+ instrs = g_arch_processor_get_disassembled_instructions(proc);
- ret = PyDict_SetItemString(dict, "APT_MIPS", PyInt_FromLong(APT_MIPS));
- if (ret == -1) return false;
+ if (instrs != NULL)
+ result = pygobject_new(G_OBJECT(instrs));
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
- ret = PyDict_SetItemString(dict, "APT_386", PyInt_FromLong(APT_386));
- if (ret == -1) return false;
-
- ret = PyDict_SetItemString(dict, "APT_COUNT", PyInt_FromLong(APT_COUNT));
- if (ret == -1) return false;
-
- return true;
+ return result;
}
-PyObject *__test;
+
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : self = objet Python concerné par l'appel. *
+* value = valeur fournie à intégrer ou prendre en compte. *
+* closure = non utilisé ici. *
* *
-* Description : Ajoute l'objet 'arch.processor.ArchProcessorType' au module. *
+* Description : Note les instructions désassemblées avec une architecture. *
* *
-* Retour : - *
+* Retour : Bilan de l'opération pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool add_arch_processor_type_to_python_module(PyObject *module)
+static int py_arch_processor_set_disass_instrs(PyObject *self, PyObject *value, void *closure)
{
- int ret; /* Bilan d'un appel */
+ GArchProcessor *proc; /* Architecture visée */
+ GArchInstruction *instrs; /* Série d'instructions liées */
- static PyTypeObject py_arch_processor_type_type = {
+ if (!PyObject_TypeCheck(value, get_python_arch_instruction_type()))
+ {
+ PyErr_SetString(PyExc_TypeError, _("The attribute value must be an instruction."));
+ return -1;
+ }
- PyObject_HEAD_INIT(NULL)
+ proc = G_ARCH_PROCESSOR(pygobject_get(self));
+ instrs = G_ARCH_INSTRUCTION(pygobject_get(value));
- .tp_name = "pyoida.arch.processor.ArchProcessorType",
+ g_arch_processor_set_disassembled_instructions(proc, instrs);
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ return 0;
- .tp_doc = "PyOIDA version of the ArchProcessorType enumeration",
+}
- };
- if (PyType_Ready(&py_arch_processor_type_type) < 0)
- return false;
+/******************************************************************************
+* *
+* Paramètres : self = processeur d'architecture à manipuler. *
+* args = instruction représentant le point de départ. *
+* *
+* Description : Recherche une instruction d'après son adresse. *
+* *
+* Retour : Instruction trouvée à l'adresse donnée, None si aucune. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_arch_processor_find_instr_by_addr(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ PyObject *addr_obj; /* Objet pour une localisation */
+ int ret; /* Bilan de lecture des args. */
+ GArchProcessor *proc; /* Processeur manipulé */
+ vmpa2t *addr; /* Localisation à retrouver */
+ GArchInstruction *found; /* Instruction liée trouvée */
+
+ ret = PyArg_ParseTuple(args, "O", &addr_obj);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(addr_obj, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
+ proc = G_ARCH_PROCESSOR(pygobject_get(self));
+ addr = get_internal_vmpa(addr_obj);
- py_arch_processor_type_define_constants(py_arch_processor_type_type.tp_dict);
+ found = g_arch_processor_find_instr_by_address(proc, addr);
- Py_INCREF(&py_arch_processor_type_type);
- ret = PyModule_AddObject(module, "ArchProcessorType", (PyObject *)&py_arch_processor_type_type);
+ if (found != NULL)
+ result = pygobject_new(G_OBJECT(found));
- __test = (PyObject *)&py_arch_processor_type_type;
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
- return (ret == 0);
+ return result;
}
+/******************************************************************************
+* *
+* Paramètres : self = processeur d'architecture à manipuler. *
+* args = instruction représentant le point de départ. *
+* *
+* Description : Fournit l'instruction qui en précède une autre. *
+* *
+* Retour : Instruction précédente trouvée, ou NULL. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
-/* ---------------------------------------------------------------------------------- */
-/* PARTIE STATIQUE DE PROCESSEURS */
-/* ---------------------------------------------------------------------------------- */
+static PyObject *py_arch_processor_get_prev_instr(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ PyObject *instr_obj; /* Objet pour une instruction */
+ int ret; /* Bilan de lecture des args. */
+ GArchProcessor *proc; /* Processeur manipulé */
+ GArchInstruction *instr; /* Instruction de référence */
+ GArchInstruction *found; /* Instruction liée trouvée */
+ ret = PyArg_ParseTuple(args, "O", &instr_obj);
+ if (!ret) return NULL;
+ ret = PyObject_IsInstance(instr_obj, (PyObject *)get_python_arch_instruction_type());
+ if (!ret) return NULL;
+ proc = G_ARCH_PROCESSOR(pygobject_get(self));
+ instr = G_ARCH_INSTRUCTION(pygobject_get(instr_obj));
+ found = g_arch_processor_get_prev_instr(proc, instr);
+ if (found != NULL)
+ result = pygobject_new(G_OBJECT(found));
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
+ return result;
+}
+/******************************************************************************
+* *
+* Paramètres : self = processeur d'architecture à manipuler. *
+* args = instruction représentant le point de départ. *
+* *
+* Description : Fournit l'instruction qui en suit une autre. *
+* *
+* Retour : Instruction suivante trouvée, ou NULL. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+static PyObject *py_arch_processor_get_next_instr(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ PyObject *instr_obj; /* Objet pour une instruction */
+ int ret; /* Bilan de lecture des args. */
+ GArchProcessor *proc; /* Processeur manipulé */
+ GArchInstruction *instr; /* Instruction de référence */
+ GArchInstruction *found; /* Instruction liée trouvée */
+ ret = PyArg_ParseTuple(args, "O", &instr_obj);
+ if (!ret) return NULL;
+ ret = PyObject_IsInstance(instr_obj, (PyObject *)get_python_arch_instruction_type());
+ if (!ret) return NULL;
+ proc = G_ARCH_PROCESSOR(pygobject_get(self));
+ instr = G_ARCH_INSTRUCTION(pygobject_get(instr_obj));
+ found = g_arch_processor_get_next_instr(proc, instr);
+ if (found != NULL)
+ result = pygobject_new(G_OBJECT(found));
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
+ return result;
+}
-/* ---------------------------------------------------------------------------------- */
-/* PARTIE GRAPHIQUE DES [DE]CHARGEMENTS */
-/* ---------------------------------------------------------------------------------- */
@@ -186,103 +306,107 @@ bool add_arch_processor_type_to_python_module(PyObject *module)
-/* Crée un nouvel objet Python de type 'py_processor'. */
-static PyObject *py_processor_new(PyTypeObject *, PyObject *, PyObject *);
/******************************************************************************
* *
-* Paramètres : type = type de l'objet à instancier. *
-* args = arguments fournis à l'appel. *
-* kwds = arguments de type key=val fournis. *
+* Paramètres : - *
* *
-* Description : Crée un nouvel objet Python de type 'py_processor'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : - *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_processor_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+PyTypeObject *get_python_arch_processor_type(void)
{
- py_processor *result; /* Instance à retourner */
-
- result = (py_processor *)type->tp_alloc(type, 0);
-
- return (PyObject *)result;
-
-}
-
-
+ static PyMethodDef py_arch_processor_methods[] = {
+ {
+ "find_instr_by_addr", py_arch_processor_find_instr_by_addr,
+ METH_VARARGS,
+ "find_instr_by_addr($self, addr, /)\n--\n\nLook for an instruction located at a given address."
+ },
+ {
+ "get_prev_instr", py_arch_processor_get_prev_instr,
+ METH_VARARGS,
+ "get_prev_instr($self, instr, /)\n--\n\nProvide the instruction preceding a given instruction."
+ },
+ {
+ "get_next_instr", py_arch_processor_get_next_instr,
+ METH_VARARGS,
+ "get_next_instr($self, instr, /)\n--\n\nProvide the instruction following a given instruction."
+ },
+ { NULL }
+ };
+ static PyGetSetDef py_arch_processor_getseters[] = {
+ {
+ "disass_instrs", py_arch_processor_get_disass_instrs, py_arch_processor_set_disass_instrs,
+ "Give access to the disassembled instructions run by the current processor.", NULL
+ },
+ { NULL }
+ };
+ static PyTypeObject py_arch_processor_type = {
+ PyVarObject_HEAD_INIT(NULL, 0)
+ .tp_name = "pychrysalide.arch.ArchProcessor",
+ .tp_basicsize = sizeof(PyGObject),
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IS_ABSTRACT | Py_TPFLAGS_BASETYPE,
+ .tp_doc = "PyChrysalide processor for a given architecture.",
+ .tp_methods = py_arch_processor_methods,
+ .tp_getset = py_arch_processor_getseters,
+ };
+ return &py_arch_processor_type;
+}
/******************************************************************************
* *
* Paramètres : module = module dont la définition est à compléter. *
* *
-* Description : Ajoute l'objet 'analysis.roptions' au module Python. *
+* Description : Prend en charge l'objet 'pychrysalide.arch.ArchProcessor'. *
* *
-* Retour : - *
+* Retour : Bilan de l'opération. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool add_arch_processor_to_python_module(PyObject *module)
+bool register_python_arch_processor(PyObject *module)
{
- bool result; /* Bilan à retourner */
+ PyTypeObject *py_arch_processor_type; /* Type Python 'BinContent' */
int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
- static PyMethodDef py_processor_methods[] = {
- { NULL }
- };
-
- static PyGetSetDef py_processor_getset[] = {
- { NULL }
- };
-
- static PyTypeObject py_processor_type = {
+ py_arch_processor_type = get_python_arch_processor_type();
- PyObject_HEAD_INIT(NULL)
+ py_arch_processor_type->tp_base = &PyGObject_Type;
+ py_arch_processor_type->tp_basicsize = py_arch_processor_type->tp_base->tp_basicsize;
- .tp_name = "pyoida.arch.Processor",
- .tp_basicsize = sizeof(py_processor),
+ APPLY_ABSTRACT_FLAG(py_arch_processor_type);
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
-
- .tp_doc = "PyOIDA processor for a given architecture",
-
- .tp_methods = py_processor_methods,
- .tp_getset = py_processor_getset,
- .tp_new = (newfunc)py_processor_new
-
- };
-
- if (PyType_Ready(&py_processor_type) < 0)
+ if (PyType_Ready(py_arch_processor_type) != 0)
return false;
- //printf("ret import = %p\n", PyImport_ImportModule("pyoida.arch.processor.ArchProcessorType"));
+ Py_INCREF(py_arch_processor_type);
+ ret = PyModule_AddObject(module, "ArchProcessor", (PyObject *)py_arch_processor_type);
+ if (ret != 0) return false;
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ArchProcessor", G_TYPE_ARCH_PROCESSOR, py_arch_processor_type,
+ Py_BuildValue("(O)", py_arch_processor_type->tp_base));
-
- Py_INCREF(&py_processor_type);
- ret = PyModule_AddObject(module, "Processor", (PyObject *)&py_processor_type);
-
- result = add_arch_processor_type_to_python_module(module);
-
-
- return (ret == 0 && result);
+ return true;
}
diff --git a/plugins/pychrysa/arch/processor.h b/plugins/pychrysa/arch/processor.h
index 6a74176..26837cb 100644
--- a/plugins/pychrysa/arch/processor.h
+++ b/plugins/pychrysa/arch/processor.h
@@ -22,8 +22,8 @@
*/
-#ifndef _PLUGINS_PYOIDA_ARCH_PROCESSOR_H
-#define _PLUGINS_PYOIDA_ARCH_PROCESSOR_H
+#ifndef _PLUGINS_PYCHRYSALIDE_ARCH_PROCESSOR_H
+#define _PLUGINS_PYCHRYSALIDE_ARCH_PROCESSOR_H
#include <Python.h>
@@ -31,9 +31,12 @@
-/* Ajoute l'objet 'arch.processor' au module Python. */
-bool add_arch_processor_to_python_module(PyObject *);
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_arch_processor_type(void);
+/* Prend en charge l'objet 'pychrysalide.arch.ArchProcessor'. */
+bool register_python_arch_processor(PyObject *);
-#endif /* _PLUGINS_PYOIDA_ARCH_PROCESSOR_H */
+
+#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_PROCESSOR_H */
diff --git a/plugins/pychrysa/arch/vmpa.c b/plugins/pychrysa/arch/vmpa.c
index 43131b5..350f61b 100644
--- a/plugins/pychrysa/arch/vmpa.c
+++ b/plugins/pychrysa/arch/vmpa.c
@@ -28,11 +28,14 @@
#include <string.h>
+#include "../helpers.h"
+/* ---------------------- DEFINITION D'UNE POSITION EN MEMOIRE ---------------------- */
+
typedef struct _py_vmpa_t
@@ -49,7 +52,7 @@ typedef struct _py_vmpa_t
/* Fournit une représentation d'une variable 'vmpa_t'. */
static PyObject *py_vmpa_to_str(PyObject *);
-/* Effectue une conversion d'un objet Python en type 'vmpa_t'. */
+/* Effectue une comparaison avec un objet Python 'vmpa_t'. */
static PyObject *py_vmpa_richcompare(PyObject *, PyObject *, int);
/* Fournit une partie du contenu de la position représentée. */
@@ -67,12 +70,74 @@ static bool convert_pyobj_to_vmpa(PyObject *, vmpa2t *);
/* Effectue une opération de type 'add' avec le type 'vmpa'. */
static PyObject *py_vmpa_nb_add(PyObject *, PyObject *);
+/* Définit les constantes pour les localisations. */
+static bool py_vmpa_define_constants(PyTypeObject *);
+
+
+
+/* ------------------------ DEFINITION D'UNE ZONE EN MEMOIRE ------------------------ */
+
+
+/* Couverture mémoire */
+typedef struct _py_mrange_t
+{
+ PyObject_HEAD /* Préambule Python */
+
+ mrange_t range; /* Informations internes */
+
+} py_mrange_t;
+
+
+/* Fournit une représentation d'une variable 'mrange_t'. */
+static PyObject *py_mrange_to_str(PyObject *);
+
+
+
+/* Effectue une comparaison avec un objet Python 'mrange_t'. */
+static PyObject *py_mrange_richcompare(PyObject *, PyObject *, int);
+
+
+
+/* Indique si une zone en contient une autre ou non. */
+static PyObject *py_mrange_contains(PyObject *, PyObject *);
+
+
+
+
+/* Fournit la position de départ de la zone mémoire représentée. */
+static PyObject *py_mrange_get_addr(PyObject *, void *);
+
+/* Définit la position de départ de la zone mémoire représentée. */
+static int py_mrange_set_addr(PyObject *, PyObject *, void *);
+
+/* Fournit la taille de la zone mémoire représentée. */
+static PyObject *py_mrange_get_length(PyObject *, void *);
+
+/* Définit la taille de la zone mémoire représentée. */
+static int py_mrange_set_length(PyObject *, PyObject *, void *);
+
+/* Calcule la position extérieure finale d'une couverture. */
+static PyObject *py_mrange_get_end_addr(PyObject *, void *);
+
+
+
+/* Crée un nouvel objet Python de type 'mrange'. */
+static PyObject *py_mrange_new(PyTypeObject *, PyObject *, PyObject *);
+
+
+/* ---------------------------------------------------------------------------------- */
+/* DEFINITION D'UNE POSITION EN MEMOIRE */
+/* ---------------------------------------------------------------------------------- */
+
+
+
+
/******************************************************************************
* *
* Paramètres : obj = objet Python à traiter. *
@@ -119,7 +184,7 @@ static PyObject *py_vmpa_to_str(PyObject *obj)
* Paramètres : obj = objet Python à tenter de convertir. *
* addr = structure équivalente pour Chrysalide. *
* *
-* Description : Effectue une conversion d'un objet Python en type 'vmpa_t'. *
+* Description : Effectue une comparaison avec un objet Python 'vmpa_t'. *
* *
* Retour : Bilan de l'opération. *
* *
@@ -184,7 +249,7 @@ static PyObject *py_vmpa_get_value(PyObject *self, void *closure)
key = (char *)closure;
- if (strcmp(key, "phy") == 0)
+ if (strcmp(key, "phys") == 0)
{
if (get_phy_addr(&vmpa->addr) == VMPA_NO_PHYSICAL)
{
@@ -236,7 +301,7 @@ static int py_vmpa_set_value(PyObject *self, PyObject *value, void *closure)
key = (char *)closure;
- if (strcmp(key, "phy") == 0)
+ if (strcmp(key, "phys") == 0)
{
if (value == Py_None)
init_vmpa(&vmpa->addr, VMPA_NO_PHYSICAL, get_virt_addr(&vmpa->addr));
@@ -296,7 +361,7 @@ static int py_vmpa_set_value(PyObject *self, PyObject *value, void *closure)
static PyObject *py_vmpa_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
{
- py_vmpa_t *result; /* Instance à retourner */
+ py_vmpa_t *result; /* Instance à retourner */
unsigned long long phy; /* Position physique */
unsigned long long virt; /* Adresse en mémoire virtuelle*/
int ret; /* Bilan de lecture des args. */
@@ -442,6 +507,32 @@ void change_editor_items_current_view_content(void/*GtkViewPanel*/ *view)
/******************************************************************************
* *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
+* *
+* Description : Définit les constantes pour les localisations. *
+* *
+* Retour : true en cas de succès de l'opération, false sinon. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static bool py_vmpa_define_constants(PyTypeObject *obj_type)
+{
+ bool result; /* Bilan à retourner */
+
+ result = true;
+
+ result &= PyDict_AddIntMacro(obj_type, VMPA_NO_PHYSICAL);
+ result &= PyDict_AddIntMacro(obj_type, VMPA_NO_VIRTUAL);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : - *
* *
* Description : Fournit un accès à une définition de type à diffuser. *
@@ -504,13 +595,13 @@ PyTypeObject *get_python_vmpa_type(void)
static PyGetSetDef py_vmpa_getseters[] = {
{
- "phy", py_vmpa_get_value, py_vmpa_set_value,
- "Give access to the physical offset of the location", "phy"
+ "phys", py_vmpa_get_value, py_vmpa_set_value,
+ "Give access to the physical offset of the location.", "phys"
},
{
"virt", py_vmpa_get_value, py_vmpa_set_value,
- "Give access to the virtual address of the location", "virt"
+ "Give access to the virtual address of the location.", "virt"
},
{ NULL }
@@ -529,7 +620,7 @@ PyTypeObject *get_python_vmpa_type(void)
.tp_flags = Py_TPFLAGS_DEFAULT,
- .tp_doc = "Python object for vmpa_t",
+ .tp_doc = "Python object for vmpa_t.",
.tp_richcompare = py_vmpa_richcompare,
@@ -565,6 +656,9 @@ bool register_python_vmpa(PyObject *module)
if (PyType_Ready(py_vmpa_type) != 0)
return false;
+ if (!py_vmpa_define_constants(py_vmpa_type))
+ return false;
+
Py_INCREF(py_vmpa_type);
ret = PyModule_AddObject(module, "vmpa", (PyObject *)py_vmpa_type);
@@ -595,3 +689,551 @@ vmpa2t *get_internal_vmpa(PyObject *obj)
return &((py_vmpa_t *)obj)->addr;
}
+
+
+/******************************************************************************
+* *
+* Paramètres : addr = structure interne à copier en objet Python. *
+* *
+* Description : Convertit une structure de type 'vmpa2t' en objet Python. *
+* *
+* Retour : Object Python résultant de la conversion opérée. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyObject *build_from_internal_vmpa(const vmpa2t *addr)
+{
+ py_vmpa_t *result; /* Instance à retourner */
+ PyTypeObject *type; /* Type à instancier */
+
+ type = get_python_vmpa_type();
+
+ result = (py_vmpa_t *)type->tp_alloc(type, 0);
+
+ copy_vmpa(&result->addr, addr);
+
+ return (PyObject *)result;
+
+}
+
+
+
+/* ---------------------------------------------------------------------------------- */
+/* DEFINITION D'UNE ZONE EN MEMOIRE */
+/* ---------------------------------------------------------------------------------- */
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : obj = objet Python à traiter. *
+* *
+* Description : Fournit une représentation d'une variable 'mrange_t'. *
+* *
+* Retour : Chaîne de caractère pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_mrange_to_str(PyObject *obj)
+{
+ PyObject *result; /* Chaîne à retourner */
+
+ result = PyUnicode_FromFormat("<TODO!>");
+
+ return result;
+
+}
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : obj = objet Python à tenter de convertir. *
+* addr = structure équivalente pour Chrysalide. *
+* *
+* Description : Effectue une comparaison avec un objet Python 'mrange_t'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_mrange_richcompare(PyObject *a, PyObject *b, int op)
+{
+ PyObject *result; /* Chaîne à retourner */
+ mrange_t *range_a; /* Premier espace à traiter */
+ mrange_t *range_b; /* Second espace à traiter */
+ int status; /* Résultat d'une comparaison */
+
+ range_a = get_internal_mrange(a);
+
+ range_b = get_internal_mrange(b);
+ if (range_b == NULL) return NULL;
+
+ status = cmp_mrange(range_a, range_b);
+
+ switch (op)
+ {
+ case Py_LT:
+ result = status < 0 ? Py_True : Py_False;
+ break;
+
+ case Py_LE:
+ result = status <= 0 ? Py_True : Py_False;
+ break;
+
+ case Py_EQ:
+ result = status == 0 ? Py_True : Py_False;
+ break;
+
+ case Py_NE:
+ result = status != 0 ? Py_True : Py_False;
+ break;
+
+ case Py_GT:
+ result = status > 0 ? Py_True : Py_False;
+ break;
+
+ case Py_GE:
+ result = status >= 0 ? Py_True : Py_False;
+ break;
+
+ default:
+ result = Py_NotImplemented;
+ break;
+
+ }
+
+ Py_INCREF(result);
+
+ return result;
+
+}
+
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : self = contenu binaire à manipuler. *
+* args = non utilisé ici. *
+* *
+* Description : Indique si une zone en contient une autre ou non. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_mrange_contains(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Bilan à faire remonter */
+ int ret; /* Bilan de lecture des args. */
+ PyObject *range_obj; /* Objet pour un intervale */
+ mrange_t *range; /* Région mémoire de contenance*/
+ mrange_t *sub; /* Région mémoire contenue ? */
+
+ ret = PyArg_ParseTuple(args, "O", &range_obj);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(range_obj, (PyObject *)get_python_mrange_type());
+ if (!ret) return NULL;
+
+ range = get_internal_mrange(self);
+ sub = get_internal_mrange(range_obj);
+
+ result = (mrange_contains_mrange(range, sub) ? Py_True : Py_False);
+
+ Py_INCREF(result);
+
+ return result;
+
+}
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : self = définition de l'espace visé par la procédure. *
+* closure = élément non utilisé ici. *
+* *
+* Description : Fournit la position de départ de la zone mémoire représentée.*
+* *
+* Retour : Nouvelle objet mis en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_mrange_get_addr(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ mrange_t *range; /* Espace mémoire à manipuler */
+
+ range = get_internal_mrange(self);
+
+ result = build_from_internal_vmpa(get_mrange_addr(range));
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = définition de l'espace visé par la procédure. *
+* value = valeur fournie à intégrer ou prendre en compte. *
+* closure = élément non utilisé ici. *
+* *
+* Description : Définit la position de départ de la zone mémoire représentée.*
+* *
+* Retour : Bilan de l'opération pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static int py_mrange_set_addr(PyObject *self, PyObject *value, void *closure)
+{
+ int result; /* Bilan à faire remonter */
+ vmpa2t *addr; /* Localisation version C */
+ mrange_t *range; /* Espace mémoire à manipuler */
+
+ result = 0;
+
+ addr = get_internal_vmpa(value);
+ if (addr == NULL) return -1;
+
+ range = get_internal_mrange(self);
+
+ init_mrange(range, addr, get_mrange_length(range));
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = définition de l'espace visé par la procédure. *
+* closure = élément non utilisé ici. *
+* *
+* Description : Fournit la taille de la zone mémoire représentée. *
+* *
+* Retour : Nouvelle objet mis en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_mrange_get_length(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ mrange_t *range; /* Espace mémoire à manipuler */
+
+ range = get_internal_mrange(self);
+
+ result = Py_BuildValue("K", get_mrange_length(range));
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = définition de l'espace visé par la procédure. *
+* value = valeur fournie à intégrer ou prendre en compte. *
+* closure = élément non utilisé ici. *
+* *
+* Description : Définit la taille de la zone mémoire représentée. *
+* *
+* Retour : Bilan de l'opération pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static int py_mrange_set_length(PyObject *self, PyObject *value, void *closure)
+{
+ int result; /* Bilan à faire remonter */
+ mrange_t *range; /* Espace mémoire à manipuler */
+ PY_LONG_LONG val; /* Valeur traduite génériquemt */
+ int overflow; /* Détection d'une grosse val. */
+ vmpa2t tmp; /* Copie pour recopie */
+
+ result = 0;
+
+ range = get_internal_mrange(self);
+
+ val = PyLong_AsLongLongAndOverflow(value, &overflow);
+
+ if (val == -1 && (overflow == 1 || PyErr_Occurred()))
+ {
+ result = -1;
+ PyErr_Clear();
+ }
+ else
+ {
+ copy_vmpa(&tmp, get_mrange_addr(range));
+ init_mrange(range, &tmp, val);
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = définition de l'espace visé par la procédure. *
+* closure = élément non utilisé ici. *
+* *
+* Description : Calcule la position extérieure finale d'une couverture. *
+* *
+* Retour : Nouvelle objet mis en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_mrange_get_end_addr(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ mrange_t *range; /* Espace mémoire à manipuler */
+ vmpa2t end; /* Adresse à reproduire */
+
+ range = get_internal_mrange(self);
+ compute_mrange_end_addr(range, &end);
+
+ result = build_from_internal_vmpa(&end);
+
+ return result;
+
+}
+
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : type = type de l'objet à instancier. *
+* args = arguments fournis à l'appel. *
+* kwds = arguments de type key=val fournis. *
+* *
+* Description : Crée un nouvel objet Python de type 'mrange'. *
+* *
+* Retour : Instance Python mise en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_mrange_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+{
+ py_mrange_t *result; /* Instance à retourner */
+ PyObject *py_vmpa; /* Localisation version Python */
+ unsigned long long length; /* Taille physique */
+ int ret; /* Bilan de lecture des args. */
+ vmpa2t *addr; /* Localisation version C */
+
+ ret = PyArg_ParseTuple(args, "OK", &py_vmpa, &length);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
+ addr = get_internal_vmpa(py_vmpa);
+ if (addr == NULL) return NULL;
+
+ result = (py_mrange_t *)type->tp_alloc(type, 0);
+
+ init_mrange(&result->range, addr, length);
+
+ return (PyObject *)result;
+
+}
+
+
+
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_mrange_type(void)
+{
+ static PyMethodDef py_mrange_methods[] = {
+ { "contains", py_mrange_contains,
+ METH_VARARGS,
+ "contains($self, other, /)\n--\nTell if the current range contains another given range or address."
+ },
+#if 0
+ { "read_u8", py_arch_instruction_read_u8,
+ METH_VARARGS,
+ "read_u8($self, addr, /)\n--\n\nRead an unsigned byte from a given position."
+ },
+#endif
+ { NULL }
+ };
+
+ static PyGetSetDef py_mrange_getseters[] = {
+ {
+ "addr", py_mrange_get_addr, py_mrange_set_addr,
+ "Give access to the start location of the memory range.", NULL
+ },
+ {
+ "length", py_mrange_get_length, py_mrange_set_length,
+ "Give access to the length of the memory range.", NULL
+ },
+ {
+ "end", py_mrange_get_end_addr, NULL,
+ "Provide the final external point of the memory range.", NULL
+ },
+ { NULL }
+ };
+
+ static PyTypeObject py_mrange_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.arch.mrange",
+ .tp_basicsize = sizeof(py_mrange_t),
+
+ .tp_str = py_mrange_to_str,
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "Python object for mrange_t.",
+
+ .tp_richcompare = py_mrange_richcompare,
+
+ .tp_methods = py_mrange_methods,
+ .tp_getset = py_mrange_getseters,
+ .tp_new = (newfunc)py_mrange_new
+
+ };
+
+ return &py_mrange_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.arch.mrange'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_mrange(PyObject *module)
+{
+ PyTypeObject *py_mrange_type; /* Type Python pour 'mrange' */
+ int ret; /* Bilan d'un appel */
+
+ py_mrange_type = get_python_mrange_type();
+
+ if (PyType_Ready(py_mrange_type) != 0)
+ return false;
+
+ Py_INCREF(py_mrange_type);
+ ret = PyModule_AddObject(module, "mrange", (PyObject *)py_mrange_type);
+
+ return (ret == 0);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : obj = objet Python à traiter. *
+* *
+* Description : Donne accès au coeur d'un objet 'pychrysalide.arch.mrange'. *
+* *
+* Retour : Localistion réelle ou NULL en cas de mauvaise conversion. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+mrange_t *get_internal_mrange(PyObject *obj)
+{
+ int ret; /* Bilan d'analyse */
+
+ ret = PyObject_IsInstance(obj, (PyObject *)get_python_mrange_type());
+ if (!ret) return NULL;
+
+ return &((py_mrange_t *)obj)->range;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : range = structure interne à copier en objet Python. *
+* *
+* Description : Convertit une structure de type 'mrange_t' en objet Python. *
+* *
+* Retour : Object Python résultant de la conversion opérée. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyObject *build_from_internal_mrange(const mrange_t *range)
+{
+ py_mrange_t *result; /* Instance à retourner */
+ PyTypeObject *type; /* Type à instancier */
+
+ type = get_python_mrange_type();
+
+ result = (py_mrange_t *)type->tp_alloc(type, 0);
+
+ copy_mrange(&result->range, range);
+
+ return (PyObject *)result;
+
+}
diff --git a/plugins/pychrysa/arch/vmpa.h b/plugins/pychrysa/arch/vmpa.h
index 8635b51..6c51d3e 100644
--- a/plugins/pychrysa/arch/vmpa.h
+++ b/plugins/pychrysa/arch/vmpa.h
@@ -43,6 +43,26 @@ bool register_python_vmpa(PyObject *);
/* Donne accès au coeur d'un objet 'pychrysalide.arch.vmpa'. */
vmpa2t *get_internal_vmpa(PyObject *);
+/* Convertit une structure de type 'vmpa2t' en objet Python. */
+PyObject *build_from_internal_vmpa(const vmpa2t *);
+
+
+
+/* ------------------------ DEFINITION D'UNE ZONE EN MEMOIRE ------------------------ */
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_mrange_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.arch.mrange'. */
+bool register_python_mrange(PyObject *);
+
+/* Donne accès au coeur d'un objet 'pychrysalide.arch.mrange'. */
+mrange_t *get_internal_mrange(PyObject *);
+
+/* Convertit une structure de type 'mrange_t' en objet Python. */
+PyObject *build_from_internal_mrange(const mrange_t *);
+
#endif /* _PLUGINS_PYCHRYSALIDE_ARCH_VMPA_H */
diff --git a/plugins/pychrysa/common/Makefile.am b/plugins/pychrysa/common/Makefile.am
new file mode 100644
index 0000000..38d1697
--- /dev/null
+++ b/plugins/pychrysa/common/Makefile.am
@@ -0,0 +1,15 @@
+
+noinst_LTLIBRARIES = libpychrysacommon.la
+
+libpychrysacommon_la_SOURCES = \
+ fnv1a.h fnv1a.c \
+ module.h module.c
+
+
+libpychrysacommon_la_LDFLAGS =
+
+
+AM_CPPFLAGS = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS) $(LIBPYTHON_CFLAGS) $(LIBPYGOBJECT_CFLAGS) \
+ -I../../../src
+
+AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS)
diff --git a/plugins/pychrysa/common/fnv1a.c b/plugins/pychrysa/common/fnv1a.c
new file mode 100644
index 0000000..2befcbe
--- /dev/null
+++ b/plugins/pychrysa/common/fnv1a.c
@@ -0,0 +1,145 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * fnv1a.c - équivalent Python du fichier "common/fnv1a.c"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "fnv1a.h"
+
+
+#include <pygobject.h>
+
+
+#include <common/fnv1a.h>
+
+
+
+/* Détermine l'empreinte FNV1a d'une chaîne de caractères. */
+static PyObject *py_fnv1a_hash(PyObject *, PyObject *);
+
+
+
+/******************************************************************************
+* *
+* Paramètres : self = NULL car méthode statique. *
+* args = non utilisé ici. *
+* *
+* Description : Détermine l'empreinte FNV1a d'une chaîne de caractères. *
+* *
+* Retour : Numéro de révision. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_fnv1a_hash(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ const char *str; /* Chaîne à traiter. */
+ int ret; /* Bilan de lecture des args. */
+ fnv64_t value; /* Empreinte calculée */
+
+ ret = PyArg_ParseTuple(args, "s", &str);
+ if (!ret) Py_RETURN_NONE;
+
+ value = fnv_64a_hash(str);
+
+ result = Py_BuildValue("K", (unsigned long long)value);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_fnv1a_type(void)
+{
+ static PyMethodDef py_fnv1a_methods[] = {
+
+ { "hash", py_fnv1a_hash,
+ METH_VARARGS | METH_STATIC,
+ "hash(str, /)\n--\n\nCompute the FNV-1a hash from a given string."
+ },
+ { NULL }
+
+ };
+
+ static PyTypeObject py_fnv1a_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.core.fnv1a",
+ .tp_basicsize = sizeof(PyObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IS_ABSTRACT,
+
+ .tp_doc = "Python version for Chrysalide of the Fowler-Noll-Vo hash function.",
+
+ .tp_methods = py_fnv1a_methods
+
+ };
+
+ return &py_fnv1a_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.core.fnv1a'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_fnv1a(PyObject *module)
+{
+ PyTypeObject *py_fnv1a_type; /* Type Python pour 'fnv1a' */
+ int ret; /* Bilan d'un appel */
+
+ py_fnv1a_type = get_python_fnv1a_type();
+
+ //py_fnv1a_type->tp_new = PyType_GenericNew;
+
+ if (PyType_Ready(py_fnv1a_type) != 0)
+ return false;
+
+ Py_INCREF(py_fnv1a_type);
+ ret = PyModule_AddObject(module, "fnv1a", (PyObject *)py_fnv1a_type);
+
+ return (ret == 0);
+
+}
diff --git a/plugins/pychrysa/common/fnv1a.h b/plugins/pychrysa/common/fnv1a.h
new file mode 100644
index 0000000..535abf1
--- /dev/null
+++ b/plugins/pychrysa/common/fnv1a.h
@@ -0,0 +1,42 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * fnv1a.h - prototypes pour l'équivalent Python du fichier "common/fnv1a.c"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_COMMON_FNV1A_H
+#define _PLUGINS_PYCHRYSALIDE_COMMON_FNV1A_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_fnv1a_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.common.fnv1a'. */
+bool register_python_fnv1a(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_COMMON_FNV1A_H */
diff --git a/plugins/pychrysa/common/module.c b/plugins/pychrysa/common/module.c
new file mode 100644
index 0000000..bb4d47f
--- /dev/null
+++ b/plugins/pychrysa/common/module.c
@@ -0,0 +1,91 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * module.c - intégration du répertoire common en tant que module
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "module.h"
+
+
+#include "fnv1a.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Ajoute le module 'common' au module Python. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool add_common_module_to_python_module(PyObject *super)
+{
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
+ int ret; /* Bilan d'un appel */
+
+ static PyModuleDef py_chrysalide_common_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.common",
+ .m_doc = "Python module for Chrysalide.common",
+
+ .m_size = -1,
+
+ };
+
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_common_module);
+ if (module == NULL) return false;
+
+ ret = PyState_AddModule(super, &py_chrysalide_common_module);
+ if (ret != 0) goto acmtpm_exit;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.common");
+ if (ret != 0) goto acmtpm_exit;
+
+ Py_INCREF(module);
+ ret = PyModule_AddObject(super, "common", module);
+ if (ret != 0) goto acmtpm_exit;
+
+ result = true;
+
+ result &= register_python_fnv1a(module);
+
+ acmtpm_exit:
+
+ if (!result)
+ {
+ printf("something went wrong in %s...\n", __FUNCTION__);
+ /* ... */
+
+ }
+
+ return result;
+
+}
diff --git a/plugins/pychrysa/common/module.h b/plugins/pychrysa/common/module.h
new file mode 100644
index 0000000..f1c1aa6
--- /dev/null
+++ b/plugins/pychrysa/common/module.h
@@ -0,0 +1,39 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * module.h - prototypes pour l'intégration du répertoire common en tant que module
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSALIDE_COMMON_MODULE_H
+#define _PLUGINS_PYCHRYSALIDE_COMMON_MODULE_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Ajoute le module 'common' au module Python. */
+bool add_common_module_to_python_module(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSALIDE_COMMON_MODULE_H */
diff --git a/plugins/pychrysa/core/module.c b/plugins/pychrysa/core/module.c
index 489f173..a866c05 100644
--- a/plugins/pychrysa/core/module.c
+++ b/plugins/pychrysa/core/module.c
@@ -25,6 +25,9 @@
#include "module.h"
+#include <assert.h>
+
+
#include "params.h"
@@ -64,27 +67,22 @@ bool add_core_module_to_python_module(PyObject *super)
if (module == NULL) return false;
ret = PyState_AddModule(super, &py_chrysalide_core_module);
- if (ret != 0) goto acmtpm_exit;
+ if (ret != 0) goto loading_failed;
ret = _PyImport_FixupBuiltin(module, "pychrysalide.core");
- if (ret != 0) goto acmtpm_exit;
+ if (ret != 0) goto loading_failed;
Py_INCREF(module);
ret = PyModule_AddObject(super, "core", module);
- if (ret != 0) goto acmtpm_exit;
+ if (ret != 0) goto loading_failed;
result = true;
result &= register_python_params(module);
- acmtpm_exit:
-
- if (!result)
- {
- printf("something went wrong in %s...\n", __FUNCTION__);
- /* ... */
+ loading_failed:
- }
+ assert(result);
return result;
diff --git a/plugins/pychrysa/core/params.c b/plugins/pychrysa/core/params.c
index 987bca6..5029304 100644
--- a/plugins/pychrysa/core/params.c
+++ b/plugins/pychrysa/core/params.c
@@ -31,12 +31,15 @@
#include <core/params.h>
+#include "../helpers.h"
+
+
/* Fournit la version du programme global. */
static PyObject *py_params_get_main_configuration(PyObject *, PyObject *);
/* Définit les constantes pour les paramètres. */
-static bool py_params_define_constants(PyObject *);
+static bool py_params_define_constants(PyTypeObject *);
@@ -114,7 +117,7 @@ PyTypeObject *get_python_params_type(void)
/******************************************************************************
* *
-* Paramètres : dict = dictionnaire à compléter. *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
* *
* Description : Définit les constantes pour les paramètres. *
* *
@@ -124,21 +127,19 @@ PyTypeObject *get_python_params_type(void)
* *
******************************************************************************/
-static bool py_params_define_constants(PyObject *dict)
+static bool py_params_define_constants(PyTypeObject *obj_type)
{
- int ret; /* Bilan d'un ajout */
+ bool result; /* Bilan à retourner */
-#define DEF_STR_CONST(name) \
- ret = PyDict_SetItemString(dict, #name, PyUnicode_FromString(name)); \
- if (ret == -1) return false;
+ result = true;
- DEF_STR_CONST(MPK_LAST_PROJECT);
- DEF_STR_CONST(MPK_ELLIPSIS_HEADER);
- DEF_STR_CONST(MPK_ELLIPSIS_TAB);
- DEF_STR_CONST(MPK_KEYBINDINGS_EDIT);
- DEF_STR_CONST(MPK_AUTO_SAVE);
+ result &= PyDict_AddStringMacro(obj_type, MPK_LAST_PROJECT);
+ result &= PyDict_AddStringMacro(obj_type, MPK_ELLIPSIS_HEADER);
+ result &= PyDict_AddStringMacro(obj_type, MPK_ELLIPSIS_TAB);
+ result &= PyDict_AddStringMacro(obj_type, MPK_KEYBINDINGS_EDIT);
+ result &= PyDict_AddStringMacro(obj_type, MPK_AUTO_SAVE);
- return true;
+ return result;
}
@@ -167,7 +168,7 @@ bool register_python_params(PyObject *module)
if (PyType_Ready(py_params_type) != 0)
return false;
- if (!py_params_define_constants(py_params_type->tp_dict))
+ if (!py_params_define_constants(py_params_type))
return false;
Py_INCREF(py_params_type);
diff --git a/plugins/pychrysa/format/Makefile.am b/plugins/pychrysa/format/Makefile.am
index 0adbe0f..5733e39 100644
--- a/plugins/pychrysa/format/Makefile.am
+++ b/plugins/pychrysa/format/Makefile.am
@@ -4,7 +4,8 @@ noinst_LTLIBRARIES = libpychrysaformat.la
libpychrysaformat_la_SOURCES = \
executable.h executable.c \
format.h format.c \
- module.h module.c
+ module.h module.c \
+ symbol.h symbol.c
libpychrysaformat_la_LIBADD = \
dex/libpychrysaformatdex.la \
diff --git a/plugins/pychrysa/format/dex/class.c b/plugins/pychrysa/format/dex/class.c
index 538fd25..1741b52 100644
--- a/plugins/pychrysa/format/dex/class.c
+++ b/plugins/pychrysa/format/dex/class.c
@@ -31,48 +31,48 @@
#include <format/dex/class.h>
-#include "../../quirks.h"
-
-
-
-/* Crée un nouvel objet Python de type 'DexClass'. */
-static PyObject *py_dex_class_new(PyTypeObject *, PyObject *, PyObject *);
-
-
/******************************************************************************
* *
-* Paramètres : type = type de l'objet à instancier. *
-* args = arguments fournis à l'appel. *
-* kwds = arguments de type key=val fournis. *
+* Paramètres : - *
* *
-* Description : Crée un nouvel objet Python de type 'DexClass'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Instance Python mise en place. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_dex_class_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+PyTypeObject *get_python_dex_class_type(void)
{
- Py_RETURN_NONE;
-
-}
-
-
-
-
+ static PyMethodDef py_dex_class_methods[] = {
+ { NULL }
+ };
+ static PyGetSetDef py_dex_class_getseters[] = {
+ { NULL }
+ };
+ static PyTypeObject py_dex_class_type = {
+ PyVarObject_HEAD_INIT(NULL, 0)
+ .tp_name = "pychrysalide.format.dex.DexClass",
+ .tp_basicsize = sizeof(PyGObject),
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+ .tp_doc = "PyChrysalide Dex class.",
+ .tp_methods = py_dex_class_methods,
+ .tp_getset = py_dex_class_getseters
+ };
+ return &py_dex_class_type;
+}
/******************************************************************************
@@ -89,49 +89,26 @@ static PyObject *py_dex_class_new(PyTypeObject *type, PyObject *args, PyObject *
bool register_python_dex_class(PyObject *module)
{
- PyObject *pygobj_mod; /* Module Python-GObject */
+ PyTypeObject *py_dex_class_type; /* Type Python 'DexClass' */
int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
- static PyMethodDef py_dex_class_methods[] = {
- { NULL }
- };
-
- static PyGetSetDef py_dex_class_getseters[] = {
- { NULL }
- };
-
- static PyTypeObject py_dex_class_type = {
-
- PyObject_HEAD_INIT(NULL)
-
- .tp_name = "pychrysalide.format.dex.DexClass",
- .tp_basicsize = sizeof(PyGObject),
-
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
-
- .tp_doc = "PyChrysalide Dex class",
-
- .tp_methods = py_dex_class_methods,
- .tp_getset = py_dex_class_getseters,
- .tp_new = (newfunc)py_dex_class_new
-
- };
-
- pygobj_mod = PyImport_ImportModule("gobject");
- if (pygobj_mod == NULL) return false;
+ py_dex_class_type = get_python_dex_class_type();
- py_dex_class_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(pygobj_mod, "GObject");
- Py_DECREF(pygobj_mod);
+ py_dex_class_type->tp_base = &PyGObject_Type;
+ py_dex_class_type->tp_basicsize = py_dex_class_type->tp_base->tp_basicsize;
- if (PyType_Ready(&py_dex_class_type) < 0)
+ if (PyType_Ready(py_dex_class_type) != 0)
return false;
- Py_INCREF(&py_dex_class_type);
- ret = PyModule_AddObject(module, "DexClass", (PyObject *)&py_dex_class_type);
+ Py_INCREF(py_dex_class_type);
+ ret = PyModule_AddObject(module, "DexClass", (PyObject *)py_dex_class_type);
+ if (ret != 0) return false;
- pygobject_register_class(module, "GDexClass", G_TYPE_DEX_CLASS, &py_dex_class_type,
- Py_BuildValue("(O)", py_dex_class_type.tp_base));
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "DexClass", G_TYPE_DEX_CLASS, py_dex_class_type,
+ Py_BuildValue("(O)", py_dex_class_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/format/dex/class.h b/plugins/pychrysa/format/dex/class.h
index d767d12..9bfcde2 100644
--- a/plugins/pychrysa/format/dex/class.h
+++ b/plugins/pychrysa/format/dex/class.h
@@ -31,6 +31,9 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_dex_class_type(void);
+
/* Prend en charge l'objet 'pychrysalide.format.dex.DexClass'. */
bool register_python_dex_class(PyObject *module);
diff --git a/plugins/pychrysa/format/dex/dex.c b/plugins/pychrysa/format/dex/dex.c
index 6f422a4..a11af52 100644
--- a/plugins/pychrysa/format/dex/dex.c
+++ b/plugins/pychrysa/format/dex/dex.c
@@ -28,11 +28,12 @@
#include <pygobject.h>
-#include <format/dex/dex-int.h>
+#include <format/dex/class.h>
+#include <format/dex/dex.h>
-#include "class.h"
-#include "../../quirks.h"
+#include "../executable.h"
+#include "../../glibext/bincontent.h"
@@ -64,19 +65,23 @@ static PyObject *py_dex_format_get_class(PyObject *, PyObject *);
static PyObject *py_dex_format_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
{
PyObject *result; /* Instance à retourner */
- const bin_t *content; /* Données binaires */
- int length; /* Quantité de ces données */
+ PyObject *content_obj; /* Objet pour le contenu */
int ret; /* Bilan de lecture des args. */
- GBinFormat *format; /* Version GLib du format */
+ GBinContent *content; /* Instance GLib correspondante*/
+ GBinFormat *format; /* Création GLib à transmettre */
- ret = PyArg_ParseTuple(args, "s#", &content, &length);
- if (!ret) Py_RETURN_NONE;
+ ret = PyArg_ParseTuple(args, "O", &content_obj);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(content_obj, (PyObject *)get_python_binary_content_type());
+ if (!ret) return NULL;
- format = g_dex_format_new(content, length);
- if (format == NULL) Py_RETURN_NONE;
+ content = G_BIN_CONTENT(pygobject_get(content_obj));
+ format = g_dex_format_new(/* FIXME */(bin_t *)content, 0/*content*/);
result = pygobject_new(G_OBJECT(format));
- //g_object_unref(format);
+
+ g_object_unref(format);
return (PyObject *)result;
@@ -149,38 +154,30 @@ static PyObject *py_dex_format_get_class(PyObject *self, PyObject *args)
}
-
-
-
-
-
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.format.dex.DexFormat'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_dex_format(PyObject *module)
+PyTypeObject *get_python_dex_format_type(void)
{
- PyObject *parent_mod; /* Accès au module parent */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_dex_format_methods[] = {
{
"count_classes", (PyCFunction)py_dex_format_count_classes,
METH_NOARGS,
- "Count the quantity of loaded Dex classes."
+ "count_classes($self, /)\n--\n\nCount the quantity of loaded Dex classes."
},
{
"get_class", (PyCFunction)py_dex_format_get_class,
METH_VARARGS,
- "Provide a given loaded Dex class."
+ "get_class($self, index, /)\n--\n\nProvide a given loaded Dex class."
},
{ NULL }
};
@@ -191,12 +188,12 @@ bool register_python_dex_format(PyObject *module)
static PyTypeObject py_dex_format_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.format.dex.DexFormat",
.tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT,
.tp_doc = "PyChrysalide Dex format",
@@ -206,27 +203,45 @@ bool register_python_dex_format(PyObject *module)
};
- parent_mod = PyImport_ImportModule("pychrysalide.format");
- if (parent_mod == NULL) return false;
+ return &py_dex_format_type;
+
+}
- py_dex_format_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "ExeFormat");
- Py_DECREF(parent_mod);
- if (PyType_Ready(&py_dex_format_type) < 0)
- return false;
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.format.dex.DexFormat'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_dex_format(PyObject *module)
+{
+ PyTypeObject *py_dex_format_type; /* Type Python 'DexFormat' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
- Py_INCREF(&py_dex_format_type);
- ret = PyModule_AddObject(module, "DexFormat", (PyObject *)&py_dex_format_type);
+ py_dex_format_type = get_python_dex_format_type();
- parent_mod = PyImport_ImportModule("pychrysalide.format");
- if (parent_mod == NULL) return false;
+ py_dex_format_type->tp_base = get_python_executable_format_type();
+ py_dex_format_type->tp_basicsize = py_dex_format_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_dex_format_type) != 0)
+ return false;
- pygobject_register_class(module, "GDexFormat", G_TYPE_DEX_FORMAT, &py_dex_format_type,
- Py_BuildValue("(OO)", py_dex_format_type.tp_base,
- PyObject_GetAttrString(parent_mod, "BinFormat")));
+ Py_INCREF(py_dex_format_type);
+ ret = PyModule_AddObject(module, "DexFormat", (PyObject *)py_dex_format_type);
+ if (ret != 0) return false;
- Py_DECREF(parent_mod);
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "DexFormat", G_TYPE_DEX_FORMAT, py_dex_format_type,
+ Py_BuildValue("(O)", py_dex_format_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/format/dex/dex.h b/plugins/pychrysa/format/dex/dex.h
index 9a4c481..9d524bb 100644
--- a/plugins/pychrysa/format/dex/dex.h
+++ b/plugins/pychrysa/format/dex/dex.h
@@ -31,8 +31,11 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_dex_format_type(void);
+
/* Prend en charge l'objet 'pychrysalide.format.dex.DexFormat'. */
-bool register_python_dex_format(PyObject *module);
+bool register_python_dex_format(PyObject *);
diff --git a/plugins/pychrysa/format/dex/module.c b/plugins/pychrysa/format/dex/module.c
index 43f0dbb..41f48c4 100644
--- a/plugins/pychrysa/format/dex/module.c
+++ b/plugins/pychrysa/format/dex/module.c
@@ -44,27 +44,43 @@
bool add_format_dex_module_to_python_module(PyObject *super)
{
- bool result;
- PyObject *module;
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyMethodDef py_format_dex_methods[] = {
- { NULL }
+ static PyModuleDef py_chrysalide_dex_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.format.dex",
+ .m_doc = "Python module for Chrysalide.format.dex",
+
+ .m_size = -1,
+
};
- module = Py_InitModule("pychrysalide.format.dex", py_format_dex_methods);
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_dex_module);
if (module == NULL) return false;
- Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.format.dex", module);
+ ret = PyState_AddModule(super, &py_chrysalide_dex_module);
+ if (ret != 0) goto loading_failed;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.format.dex");
+ if (ret != 0) goto loading_failed;
- result = (ret == 0);
+ Py_INCREF(module);
+ ret = PyModule_AddObject(super, "dex", module);
+ if (ret != 0) goto loading_failed;
- if (ret != 0) /* ... */;
+ result = true;
result &= register_python_dex_class(module);
result &= register_python_dex_format(module);
- return true;
+ loading_failed:
+
+ return result;
}
diff --git a/plugins/pychrysa/format/elf/elf.c b/plugins/pychrysa/format/elf/elf.c
index 3ae8f53..87988ee 100644
--- a/plugins/pychrysa/format/elf/elf.c
+++ b/plugins/pychrysa/format/elf/elf.c
@@ -28,10 +28,11 @@
#include <pygobject.h>
-#include <format/elf/elf-int.h>
+#include <format/elf/elf.h>
-#include "../../quirks.h"
+#include "../executable.h"
+#include "../../glibext/bincontent.h"
@@ -57,48 +58,43 @@ static PyObject *py_elf_format_new(PyTypeObject *, PyObject *, PyObject *);
static PyObject *py_elf_format_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
{
PyObject *result; /* Instance à retourner */
- const bin_t *content; /* Données binaires */
- int length; /* Quantité de ces données */
+ PyObject *content_obj; /* Objet pour le contenu */
int ret; /* Bilan de lecture des args. */
- GBinFormat *format; /* Version GLib du format */
+ GBinContent *content; /* Instance GLib correspondante*/
+ GBinFormat *format; /* Création GLib à transmettre */
- ret = PyArg_ParseTuple(args, "s#", &content, &length);
- if (!ret) Py_RETURN_NONE;
+ ret = PyArg_ParseTuple(args, "O", &content_obj);
+ if (!ret) return NULL;
- format = NULL;//g_elf_format_new(content, length);
- if (format == NULL) Py_RETURN_NONE;
+ ret = PyObject_IsInstance(content_obj, (PyObject *)get_python_binary_content_type());
+ if (!ret) return NULL;
+
+ content = G_BIN_CONTENT(pygobject_get(content_obj));
+ format = g_elf_format_new(content);
result = pygobject_new(G_OBJECT(format));
- //g_object_unref(format);
+
+ g_object_unref(format);
return (PyObject *)result;
}
-
-
-
-
-
-
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.format.elf.ElfFormat'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_elf_format(PyObject *module)
+PyTypeObject *get_python_elf_format_type(void)
{
- PyObject *parent_mod; /* Accès au module parent */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_elf_format_methods[] = {
{ NULL }
};
@@ -109,12 +105,12 @@ bool register_python_elf_format(PyObject *module)
static PyTypeObject py_elf_format_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.format.elf.ElfFormat",
.tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT,
.tp_doc = "PyChrysalide Elf format",
@@ -124,27 +120,45 @@ bool register_python_elf_format(PyObject *module)
};
- parent_mod = PyImport_ImportModule("pychrysalide.format");
- if (parent_mod == NULL) return false;
+ return &py_elf_format_type;
+
+}
- py_elf_format_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "ExeFormat");
- Py_DECREF(parent_mod);
- if (PyType_Ready(&py_elf_format_type) < 0)
- return false;
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.format.elf.ElfFormat'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_elf_format(PyObject *module)
+{
+ PyTypeObject *py_elf_format_type; /* Type Python 'ElfFormat' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
- Py_INCREF(&py_elf_format_type);
- ret = PyModule_AddObject(module, "ElfFormat", (PyObject *)&py_elf_format_type);
+ py_elf_format_type = get_python_elf_format_type();
- parent_mod = PyImport_ImportModule("pychrysalide.format");
- if (parent_mod == NULL) return false;
+ py_elf_format_type->tp_base = get_python_executable_format_type();
+ py_elf_format_type->tp_basicsize = py_elf_format_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_elf_format_type) != 0)
+ return false;
- pygobject_register_class(module, "GElfFormat", G_TYPE_ELF_FORMAT, &py_elf_format_type,
- Py_BuildValue("(OO)", py_elf_format_type.tp_base,
- PyObject_GetAttrString(parent_mod, "BinFormat")));
+ Py_INCREF(py_elf_format_type);
+ ret = PyModule_AddObject(module, "ElfFormat", (PyObject *)py_elf_format_type);
+ if (ret != 0) return false;
- Py_DECREF(parent_mod);
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ElfFormat", G_TYPE_ELF_FORMAT, py_elf_format_type,
+ Py_BuildValue("(O)", py_elf_format_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/format/elf/elf.h b/plugins/pychrysa/format/elf/elf.h
index 658e58b..d037942 100644
--- a/plugins/pychrysa/format/elf/elf.h
+++ b/plugins/pychrysa/format/elf/elf.h
@@ -31,8 +31,11 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_elf_format_type(void);
+
/* Prend en charge l'objet 'pychrysalide.format.elf.ElfFormat'. */
-bool register_python_elf_format(PyObject *module);
+bool register_python_elf_format(PyObject *);
diff --git a/plugins/pychrysa/format/elf/module.c b/plugins/pychrysa/format/elf/module.c
index d701cfd..ebd34d9 100644
--- a/plugins/pychrysa/format/elf/module.c
+++ b/plugins/pychrysa/format/elf/module.c
@@ -43,26 +43,42 @@
bool add_format_elf_module_to_python_module(PyObject *super)
{
- bool result;
- PyObject *module;
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyMethodDef py_format_elf_methods[] = {
- { NULL }
+ static PyModuleDef py_chrysalide_elf_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.format.elf",
+ .m_doc = "Python module for Chrysalide.format.elf",
+
+ .m_size = -1,
+
};
- module = Py_InitModule("pychrysalide.format.elf", py_format_elf_methods);
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_elf_module);
if (module == NULL) return false;
- Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.format.elf", module);
+ ret = PyState_AddModule(super, &py_chrysalide_elf_module);
+ if (ret != 0) goto loading_failed;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.format.elf");
+ if (ret != 0) goto loading_failed;
- result = (ret == 0);
+ Py_INCREF(module);
+ ret = PyModule_AddObject(super, "elf", module);
+ if (ret != 0) goto loading_failed;
- if (ret != 0) /* ... */;
+ result = true;
result &= register_python_elf_format(module);
- return true;
+ loading_failed:
+
+ return result;
}
diff --git a/plugins/pychrysa/format/executable.c b/plugins/pychrysa/format/executable.c
index 21da818..e7e218d 100644
--- a/plugins/pychrysa/format/executable.c
+++ b/plugins/pychrysa/format/executable.c
@@ -31,55 +31,58 @@
#include <format/format.h>
-#include "../quirks.h"
-
-
-
-/* Crée un nouvel objet Python de type 'BinFormat'. */
-static PyObject *py_executable_format_new(PyTypeObject *, PyObject *, PyObject *);
-
-
-
-
-#define _(str) str
-
+#include "format.h"
/******************************************************************************
* *
-* Paramètres : type = type de l'objet à instancier. *
-* args = arguments fournis à l'appel. *
-* kwds = arguments de type key=val fournis. *
+* Paramètres : - *
* *
-* Description : Crée un nouvel objet Python de type 'BinFormat'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Instance Python mise en place. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_executable_format_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+PyTypeObject *get_python_executable_format_type(void)
{
- PyErr_SetString(PyExc_ValueError,
- _("pychrysalide.format.ExeFormat can not be instanciated directly"));
+ static PyMethodDef py_exe_format_methods[] = {
+ { NULL }
+ };
- return NULL;
+ static PyGetSetDef py_exe_format_getseters[] = {
+ { NULL }
+ };
-}
+ static PyTypeObject py_exe_format_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.format.ExeFormat",
+ .tp_basicsize = sizeof(PyGObject),
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_doc = "PyChrysalide executable format",
+ .tp_methods = py_exe_format_methods,
+ .tp_getset = py_exe_format_getseters,
+ };
+ return &py_exe_format_type;
+
+}
/******************************************************************************
* *
* Paramètres : module = module dont la définition est à compléter. *
* *
-* Description : Prend en charge l'objet 'pychrysalide.gui.panels.BinFormat'. *
+* Description : Prend en charge l'objet 'pychrysalide.format.ExeFormat'. *
* *
* Retour : Bilan de l'opération. *
* *
@@ -89,46 +92,26 @@ static PyObject *py_executable_format_new(PyTypeObject *type, PyObject *args, Py
bool register_python_executable_format(PyObject *module)
{
- PyObject *parent_mod; /* Accès au module parent */
+ PyTypeObject *py_exe_format_type; /* Type Python 'ExeFormat' */
int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
- static PyMethodDef py_executable_format_methods[] = {
- { NULL }
- };
-
- static PyGetSetDef py_executable_format_getseters[] = {
- { NULL }
- };
-
- static PyTypeObject py_executable_format_type = {
-
- PyObject_HEAD_INIT(NULL)
-
- .tp_name = "pychrysalide.format.ExeFormat",
- .tp_basicsize = sizeof(PyGObject),
-
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
-
- .tp_doc = "PyChrysalide executable format",
-
- .tp_methods = py_executable_format_methods,
- .tp_getset = py_executable_format_getseters,
- .tp_new = (newfunc)py_executable_format_new
-
- };
+ py_exe_format_type = get_python_executable_format_type();
- parent_mod = PyImport_ImportModule("pychrysalide.format");
- if (parent_mod == NULL) return false;
+ py_exe_format_type->tp_base = get_python_binary_format_type();
+ py_exe_format_type->tp_basicsize = py_exe_format_type->tp_base->tp_basicsize;
- py_executable_format_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "BinFormat");
- Py_DECREF(parent_mod);
-
- if (PyType_Ready(&py_executable_format_type) < 0)
+ if (PyType_Ready(py_exe_format_type) != 0)
return false;
- Py_INCREF(&py_executable_format_type);
- ret = PyModule_AddObject(module, "ExeFormat", (PyObject *)&py_executable_format_type);
+ Py_INCREF(py_exe_format_type);
+ ret = PyModule_AddObject(module, "ExeFormat", (PyObject *)py_exe_format_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ExeFormat", G_TYPE_EXE_FORMAT, py_exe_format_type,
+ Py_BuildValue("(O)", py_exe_format_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/format/executable.h b/plugins/pychrysa/format/executable.h
index 40b5dcf..64b03f7 100644
--- a/plugins/pychrysa/format/executable.h
+++ b/plugins/pychrysa/format/executable.h
@@ -31,8 +31,11 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_executable_format_type(void);
+
/* Prend en charge l'objet 'pychrysalide.format.ExeFormat'. */
-bool register_python_executable_format(PyObject *module);
+bool register_python_executable_format(PyObject *);
diff --git a/plugins/pychrysa/format/format.c b/plugins/pychrysa/format/format.c
index 423e94e..290b189 100644
--- a/plugins/pychrysa/format/format.c
+++ b/plugins/pychrysa/format/format.c
@@ -31,39 +31,139 @@
#include <format/format.h>
-#include "../quirks.h"
+#include "../helpers.h"
+#include "../arch/vmpa.h"
+/* ------------------------ PARCOURS DE SYMBOLES DE BINAIRES ------------------------ */
+/* Parcours des symboles présents dans un binaire */
+typedef struct _pyBinSymbolIterator
+{
+ PyObject_HEAD /* A laisser en premier */
+
+ GBinFormat *format; /* Format binaire à consulter */
+ size_t next; /* Symbole binaire à présenter */
+
+} pyBinSymbolIterator;
+
+
+/* Prend acte d'un compteur de référence à 0. */
+static void py_binary_symbol_iterator_dealloc(PyObject *);
+
+/* Fournit un itérateur pour symboles de format binaire. */
+static PyObject *py_binary_symbol_iterator_next(PyObject *);
+
+/* Initialise un objet Python de type 'BinSymbolIterator'. */
+static int py_binary_symbol_iterator_init(PyObject *, PyObject *, PyObject *);
+
+
+
+/* ---------------------------- FORMAT BINAIRE GENERIQUE ---------------------------- */
+
+
+/* Recherche le symbole correspondant à une étiquette. */
+static PyObject *py_binary_format_find_symbol_by_label(PyObject *, PyObject *);
+
+/* Recherche le symbole suivant celui lié à une adresse. */
+static PyObject *py_binary_format_find_symbol_at(PyObject *, PyObject *);
+
+/* Recherche le symbole suivant celui lié à une adresse. */
+static PyObject *py_binary_format_find_next_symbol_at(PyObject *, PyObject *);
+
+/* Recherche le symbole correspondant à une adresse. */
+static PyObject *py_binary_format_resolve_symbol(PyObject *, PyObject *);
+
+/* Fournit la liste de tous les symboles détectés. */
+static PyObject *py_binary_format_get_symbols(PyObject *, void *);
+
+
+
+/* ---------------------------------------------------------------------------------- */
+/* PARCOURS DE SYMBOLES DE BINAIRES */
+/* ---------------------------------------------------------------------------------- */
+
+
+/******************************************************************************
+* *
+* Paramètres : self = instance Python à libérer de la mémoire. *
+* *
+* Description : Prend acte d'un compteur de référence à 0. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
-#define _(str) str
+static void py_binary_symbol_iterator_dealloc(PyObject *self)
+{
+ pyBinSymbolIterator *iterator; /* Références pour le parcours */
+ /**
+ * Il aurait été sans doute mieux de reposer ici sur .tp_finalize,
+ * mais cela semble impliquer de mettre en place tous les mécanismes de GC...
+ *
+ * cf. https://docs.python.org/3/extending/newtypes.html#finalization-and-de-allocation
+ */
+ iterator = (pyBinSymbolIterator *)self;
+ g_object_unref(G_OBJECT(iterator->format));
+ Py_TYPE(self)->tp_free((PyObject *)self);
-/* Crée un nouvel objet Python de type 'BinFormat'. */
-static PyObject *py_binary_format_new(PyTypeObject *, PyObject *, PyObject *);
+}
-/* Recherche une position dans une routine selon une adresse. */
-static PyObject *py_binary_format_resolve_relative_routine(PyObject *, PyObject *);
+/******************************************************************************
+* *
+* Paramètres : self = itérateur à manipuler. *
+* *
+* Description : Fournit un itérateur pour symboles de format binaire. *
+* *
+* Retour : Instance Python prête à emploi. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
-/* Fournit le prototype de toutes les routines détectées. */
-static PyObject *py_binary_format_get_routines(PyObject *, void *);
+static PyObject *py_binary_symbol_iterator_next(PyObject *self)
+{
+ PyObject *result; /* Instance à retourner */
+ pyBinSymbolIterator *iterator; /* Références pour le parcours */
+ size_t count; /* Nombre de symboles présents */
+ GBinSymbol **symbols; /* Liste de ces mêmes symboles */
+
+ iterator = (pyBinSymbolIterator *)self;
+
+ symbols = g_binary_format_get_symbols(iterator->format, &count);
+
+ if (iterator->next < count)
+ {
+ result = pygobject_new(G_OBJECT(symbols[iterator->next]));
+ iterator->next++;
+ }
+ else
+ {
+ PyErr_SetNone(PyExc_StopIteration);
+ result = NULL;
+ }
+ return result;
+}
/******************************************************************************
* *
-* Paramètres : type = type de l'objet à instancier. *
+* Paramètres : self = objet instancié à initialiser. *
* args = arguments fournis à l'appel. *
* kwds = arguments de type key=val fournis. *
* *
-* Description : Crée un nouvel objet Python de type 'BinFormat'. *
+* Description : Initialise un objet Python de type 'BinSymbolIterator'. *
* *
* Retour : Instance Python mise en place. *
* *
@@ -71,168 +171,431 @@ static PyObject *py_binary_format_get_routines(PyObject *, void *);
* *
******************************************************************************/
-static PyObject *py_binary_format_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+static int py_binary_symbol_iterator_init(PyObject *self, PyObject *args, PyObject *kwds)
+{
+ pyBinSymbolIterator *iterator; /* Références pour le parcours */
+ PyObject *format; /* Format binaire en Python */
+ int ret; /* Bilan de lecture des args. */
+
+ ret = PyArg_ParseTuple(args, "O", &format);
+ if (!ret) return -1;
+
+ ret = PyObject_IsInstance(format, (PyObject *)get_python_binary_format_type());
+ if (!ret) return -1;
+
+ iterator = (pyBinSymbolIterator *)self;
+
+ iterator->format = G_BIN_FORMAT(pygobject_get(format));
+ g_object_ref(G_OBJECT(iterator->format));
+
+ iterator->next = 0;
+
+ return 0;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_binary_symbol_iterator_type(void)
{
- PyErr_SetString(PyExc_ValueError,
- _("pychrysalide.format.BinFormat can not be instanciated directly"));
+ static PyTypeObject py_binary_symbol_iterator_type = {
- return NULL;
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.format.BinSymbolIterator",
+ .tp_basicsize = sizeof(pyBinSymbolIterator),
+
+ .tp_dealloc = py_binary_symbol_iterator_dealloc,
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "Iterator for binary symbols",
+
+ .tp_iter = PyObject_SelfIter,
+ .tp_iternext = py_binary_symbol_iterator_next,
+
+ .tp_init = py_binary_symbol_iterator_init,
+
+ .tp_new = PyType_GenericNew,
+
+ };
+
+ return &py_binary_symbol_iterator_type;
}
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide...BinSymbolIterator'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_binary_symbol_iterator(PyObject *module)
+{
+ PyTypeObject *py_binary_symbol_iterator_type; /* Type Python 'BinSymbolIterator' */
+ int ret; /* Bilan d'un appel */
+
+ py_binary_symbol_iterator_type = get_python_binary_symbol_iterator_type();
+ py_binary_symbol_iterator_type->tp_base = &PyBaseObject_Type;
+ if (PyType_Ready(py_binary_symbol_iterator_type) != 0)
+ return false;
+ Py_INCREF(py_binary_symbol_iterator_type);
+ ret = PyModule_AddObject(module, "BinSymbolIterator", (PyObject *)py_binary_symbol_iterator_type);
+ if (ret != 0) return false;
+ return true;
+}
+/* ---------------------------------------------------------------------------------- */
+/* FORMAT BINAIRE GENERIQUE */
+/* ---------------------------------------------------------------------------------- */
/******************************************************************************
* *
-* Paramètres : self = classe représentant un format binaire. *
+* Paramètres : self = classe représentant un binaire. *
* args = arguments fournis à l'appel. *
* *
-* Description : Recherche une position dans une routine selon une adresse. *
+* Description : Recherche le symbole correspondant à une étiquette. *
* *
-* Retour : Tuple (nom, décallage) ou Py_None. *
+* Retour : Symbol trouvé si l'opération a été un succès, None sinon. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_binary_format_resolve_relative_routine(PyObject *self, PyObject *args)
+static PyObject *py_binary_format_find_symbol_by_label(PyObject *self, PyObject *args)
{
- PyObject *result; /* Tuple à retourner */
- GBinFormat *format; /* Format à manipuler */
- vmpa_t addr; /* Adresse demandée en visuel */
+ PyObject *result; /* Valeur à retourner */
+ PyObject *label; /* Etiquette à retrouver */
int ret; /* Bilan de lecture des args. */
- bool found; /* Bilan de la résolution */
- const char *label; /* Désignation de la trouvaille*/
+ GBinFormat *format; /* Format de binaire manipulé */
+ GBinSymbol *symbol; /* Enventuel symbole trouvé */
+ bool found;
- format = G_BIN_FORMAT(pygobject_get(self));
+ ret = PyArg_ParseTuple(args, "O", &label);
+ if (!ret) return NULL;
+
+ ret = PyUnicode_Check(label);
+ if (!ret) return NULL;
- ret = PyArg_ParseTuple(args, "K", &addr);
- if (!ret) Py_RETURN_NONE;
+ format = G_BIN_FORMAT(pygobject_get(self));
- found = g_binary_format_resolve_relative_routine(format, &label, &addr);
- if (!found) Py_RETURN_NONE;
+ found = g_binary_format_find_symbol_by_label(format, PyUnicode_DATA(label), &symbol);
- result = PyTuple_New(2);
- PyTuple_SetItem(result, 0, PyString_FromString(label));
- PyTuple_SetItem(result, 1, PyLong_FromLongLong(addr));
+ if (found)
+ result = pygobject_new(G_OBJECT(symbol));
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
return result;
}
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant un binaire. *
+* args = arguments fournis à l'appel. *
+* *
+* Description : Recherche le symbole suivant celui lié à une adresse. *
+* *
+* Retour : Symbol trouvé si l'opération a été un succès, None sinon. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+static PyObject *py_binary_format_find_symbol_at(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Valeur à retourner */
+ PyObject *py_vmpa; /* Localisation version Python */
+ int ret; /* Bilan de lecture des args. */
+ GBinFormat *format; /* Format de binaire manipulé */
+ GBinSymbol *symbol; /* Enventuel symbole trouvé */
+ bool found;
+
+ ret = PyArg_ParseTuple(args, "O", &py_vmpa);
+ if (!ret) return NULL;
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
+ format = G_BIN_FORMAT(pygobject_get(self));
+
+ found = g_binary_format_find_symbol_at(format, get_internal_vmpa(py_vmpa), &symbol);
+
+ if (found)
+ result = pygobject_new(G_OBJECT(symbol));
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
+
+ return result;
+
+}
/******************************************************************************
* *
-* Paramètres : self = classe représentant un format binaire. *
-* closure = adresse non utilisée ici. *
+* Paramètres : self = classe représentant un binaire. *
+* args = arguments fournis à l'appel. *
* *
-* Description : Fournit le prototype de toutes les routines détectées. *
+* Description : Recherche le symbole suivant celui lié à une adresse. *
* *
-* Retour : Liste de routine, vide ou non. *
+* Retour : Symbol trouvé si l'opération a été un succès, None sinon. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_binary_format_get_routines(PyObject *self, void *closure)
+static PyObject *py_binary_format_find_next_symbol_at(PyObject *self, PyObject *args)
{
- PyObject *result; /* Tuple à retourner */
- GBinFormat *format; /* Format à manipuler */
- GBinRoutine **routines; /* Routines binaires présentes */
- size_t count; /* Quantité de ces routines */
- size_t i; /* Boucle de parcours */
+ PyObject *result; /* Valeur à retourner */
+ PyObject *py_vmpa; /* Localisation version Python */
+ int ret; /* Bilan de lecture des args. */
+ GBinFormat *format; /* Format de binaire manipulé */
+ GBinSymbol *symbol; /* Enventuel symbole trouvé */
+ bool found;
+
+ ret = PyArg_ParseTuple(args, "O", &py_vmpa);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
format = G_BIN_FORMAT(pygobject_get(self));
- routines = g_binary_format_get_routines(format, &count);
- result = PyTuple_New(count);
+ found = g_binary_format_find_next_symbol_at(format, get_internal_vmpa(py_vmpa), &symbol);
- for (i = 0; i < count; i++)
- PyTuple_SetItem(result, i, pygobject_new(G_OBJECT(routines[i])));
+ if (found)
+ result = pygobject_new(G_OBJECT(symbol));
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
return result;
}
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant un format binaire. *
+* args = arguments fournis à l'appel. *
+* *
+* Description : Recherche le symbole correspondant à une adresse. *
+* *
+* Retour : Tuple (nom, décallage) ou Py_None. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_format_resolve_symbol(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Valeur à retourner */
+ PyObject *py_vmpa; /* Localisation version Python */
+ int ret; /* Bilan de lecture des args. */
+ GBinFormat *format; /* Format de binaire manipulé */
+ GBinSymbol *symbol; /* Enventuel symbole trouvé */
+ phys_t diff; /* Décallage éventuel mesuré */
+ bool found;
+
+ ret = PyArg_ParseTuple(args, "O", &py_vmpa);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
+ format = G_BIN_FORMAT(pygobject_get(self));
+
+ found = g_binary_format_resolve_symbol(format, get_internal_vmpa(py_vmpa), &symbol, &diff);
+
+ if (found)
+ {
+ result = PyTuple_New(2);
+ PyTuple_SetItem(result, 0, pygobject_new(G_OBJECT(symbol)));
+ PyTuple_SetItem(result, 1, PyLong_FromUnsignedLongLong(diff));
+ }
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
+
+ return result;
+
+}
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : self = classe représentant un format binaire. *
+* closure = adresse non utilisée ici. *
* *
-* Description : Prend en charge l'objet 'pychrysalide.gui.panels.BinFormat'. *
+* Description : Fournit la liste de tous les symboles détectés. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Tableau créé ou NULL si aucun symbole trouvé. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_binary_format(PyObject *module)
+static PyObject *py_binary_format_get_symbols(PyObject *self, void *closure)
{
- PyObject *parent_mod; /* Module Python-GObject */
- int ret; /* Bilan d'un appel */
+ PyObject *result; /* Instance à retourner */
+ PyTypeObject *iterator_type; /* Type Python de l'itérateur */
+ PyObject *args_list; /* Arguments de mise en place */
- static PyMethodDef py_binary_format_methods[] = {
+ iterator_type = get_python_binary_symbol_iterator_type();
+
+ Py_INCREF(self);
+
+ args_list = Py_BuildValue("(O)", self);
+ result = PyObject_CallObject((PyObject *)iterator_type, args_list);
+
+ Py_DECREF(args_list);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_binary_format_type(void)
+{
+ static PyMethodDef py_bin_format_methods[] = {
+ {
+ "find_symbol_by_label", py_binary_format_find_symbol_by_label,
+ METH_VARARGS,
+ "find_symbol_by_label($self, label, /)\n--\n\nFind a symbol by its label."
+ },
+ {
+ "find_symbol_at", py_binary_format_find_symbol_at,
+ METH_VARARGS,
+ "find_symbol_at($self, addr, /)\n--\n\nFind a symbol at a given address."
+ },
{
- "resolve_relative_routine", (PyCFunction)py_binary_format_resolve_relative_routine,
+ "find_next_symbol_at", py_binary_format_find_next_symbol_at,
METH_VARARGS,
- "Search a position inside a routine by a given address."
+ "find_next_symbol_at($self, addr, /)\n--\n\nFind the symbol next to the one found at a given address."
+ },
+ {
+ "resolve_symbol", py_binary_format_resolve_symbol,
+ METH_VARARGS,
+ "resolve_symbol($self, addr, /)\n--\n\nSearch a position inside a routine by a given address."
},
{ NULL }
};
- static PyGetSetDef py_binary_format_getseters[] = {
+ static PyGetSetDef py_bin_format_getseters[] = {
{
- "routines", (getter)py_binary_format_get_routines, (setter)NULL,
- "Provide the list of all detected routines in the binary format.", NULL
+ "symbols", py_binary_format_get_symbols, NULL,
+ "Iterable list of all symbols found in the binary format.", NULL
},
{ NULL }
};
- static PyTypeObject py_binary_format_type = {
+ static PyTypeObject py_bin_format_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.format.BinFormat",
.tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IS_ABSTRACT | Py_TPFLAGS_BASETYPE,
.tp_doc = "PyChrysalide binary format",
- .tp_methods = py_binary_format_methods,
- .tp_getset = py_binary_format_getseters,
- .tp_new = (newfunc)py_binary_format_new
+ .tp_methods = py_bin_format_methods,
+ .tp_getset = py_bin_format_getseters
};
- parent_mod = PyImport_ImportModule("gobject");
- if (parent_mod == NULL) return false;
+ return &py_bin_format_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.format.BinFormat'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_binary_format(PyObject *module)
+{
+ PyTypeObject *py_bin_format_type; /* Type Python 'BinFormat' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
- py_binary_format_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "GObject");
- Py_DECREF(parent_mod);
+ py_bin_format_type = get_python_binary_format_type();
- if (PyType_Ready(&py_binary_format_type) < 0)
+ py_bin_format_type->tp_base = &PyGObject_Type;
+ py_bin_format_type->tp_basicsize = py_bin_format_type->tp_base->tp_basicsize;
+
+ APPLY_ABSTRACT_FLAG(py_bin_format_type);
+
+ if (PyType_Ready(py_bin_format_type) != 0)
return false;
- Py_INCREF(&py_binary_format_type);
- ret = PyModule_AddObject(module, "BinFormat", (PyObject *)&py_binary_format_type);
+ Py_INCREF(py_bin_format_type);
+ ret = PyModule_AddObject(module, "BinFormat", (PyObject *)py_bin_format_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "BinFormat", G_TYPE_BIN_FORMAT, py_bin_format_type,
+ Py_BuildValue("(O)", py_bin_format_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/format/format.h b/plugins/pychrysa/format/format.h
index 3a2c401..50ec47a 100644
--- a/plugins/pychrysa/format/format.h
+++ b/plugins/pychrysa/format/format.h
@@ -31,8 +31,25 @@
+/* ------------------------ PARCOURS DE SYMBOLES DE BINAIRES ------------------------ */
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_binary_symbol_iterator_type(void);
+
+/* Prend en charge l'objet 'pychrysalide...BinSymbolIterator'. */
+bool register_python_binary_symbol_iterator(PyObject *);
+
+
+
+/* ---------------------------- FORMAT BINAIRE GENERIQUE ---------------------------- */
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_binary_format_type(void);
+
/* Prend en charge l'objet 'pychrysalide.format.BinFormat'. */
-bool register_python_binary_format(PyObject *module);
+bool register_python_binary_format(PyObject *);
diff --git a/plugins/pychrysa/format/module.c b/plugins/pychrysa/format/module.c
index efaade6..bd81187 100644
--- a/plugins/pychrysa/format/module.c
+++ b/plugins/pychrysa/format/module.c
@@ -25,15 +25,17 @@
#include "module.h"
+#include <assert.h>
+
+
#include "executable.h"
#include "format.h"
+#include "symbol.h"
#include "dex/module.h"
#include "elf/module.h"
-
-
/******************************************************************************
* *
* Paramètres : module = module dont la définition est à compléter. *
@@ -48,28 +50,50 @@
bool add_format_module_to_python_module(PyObject *super)
{
- bool result;
- PyObject *module;
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyMethodDef py_format_methods[] = {
- { NULL }
+ static PyModuleDef py_chrysalide_format_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.format",
+ .m_doc = "Python module for Chrysalide.format",
+
+ .m_size = -1,
+
};
- module = Py_InitModule("pychrysalide.format", py_format_methods);
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_format_module);
if (module == NULL) return false;
+ ret = PyState_AddModule(super, &py_chrysalide_format_module);
+ if (ret != 0) goto loading_failed;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.format");
+ if (ret != 0) goto loading_failed;
+
Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.format", module);
+ ret = PyModule_AddObject(super, "format", module);
+ if (ret != 0) goto loading_failed;
- result = (ret == 0);
+ result = true;
+ result &= register_python_binary_symbol_iterator(module);
result &= register_python_binary_format(module);
result &= register_python_executable_format(module);
+ result &= register_python_binary_symbol(module);
result &= add_format_dex_module_to_python_module(module);
result &= add_format_elf_module_to_python_module(module);
+ loading_failed:
+
+ assert(result);
+
return result;
}
diff --git a/plugins/pychrysa/format/symbol.c b/plugins/pychrysa/format/symbol.c
new file mode 100644
index 0000000..1fc868e
--- /dev/null
+++ b/plugins/pychrysa/format/symbol.c
@@ -0,0 +1,720 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * symbol.c - équivalent Python du fichier "format/symbol.h"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "symbol.h"
+
+
+#include <pygobject.h>
+
+
+#include <i18n.h>
+
+
+#include <format/symbol.h>
+
+
+#include "../helpers.h"
+#include "../analysis/routine.h"
+#include "../analysis/db/items/comment.h"
+#include "../arch/instruction.h"
+#include "../arch/vmpa.h"
+
+
+
+/* Effectue une comparaison avec un objet Python 'BinSymbol'. */
+static PyObject *py_binary_symbol_richcompare(PyObject *, PyObject *, int);
+
+/* Définit un autre nom pour le symbole. */
+static PyObject *py_binary_symbol_set_alt_label(PyObject *, PyObject *);
+
+/* Raffine la définition de l'emplacement d'un symbole. */
+static PyObject *py_binary_symbol_fix_range(PyObject *, PyObject *);
+
+/* Attache la routine associée au symbole. */
+static PyObject *py_binary_symbol_attach_routine(PyObject *, PyObject *);
+
+/* Attache l'instruction associée au symbole. */
+static PyObject *py_binary_symbol_attach_instruction(PyObject *, PyObject *);
+
+/* Fournit le type du symbole. */
+static PyObject *py_binary_symbol_get_target_type(PyObject *, void *);
+
+/* Fournit un étiquette pour viser un symbole. */
+static PyObject *py_binary_symbol_get_label(PyObject *, void *);
+
+/* Fournit l'emplacement où se situe un symbole. */
+static PyObject *py_binary_symbol_get_range(PyObject *, void *);
+
+/* Fournit l'éventuelle routine associée au symbole. */
+static PyObject *py_binary_symbol_get_routine(PyObject *, void *);
+
+/* Fournit l'éventuelle instruction associée au symbole. */
+static PyObject *py_binary_symbol_get_instruction(PyObject *, void *);
+
+/* Fournit l'éventuel commentaire associé au symbole. */
+static PyObject *py_binary_symbol_get_comment(PyObject *, void *);
+
+/* Ajoute un commentaire facultatif au symbole. */
+static int py_binary_symbol_set_comment(PyObject *, PyObject *, void *);
+
+/* Définit les constantes pour les symboles binaires. */
+static bool py_binary_symbol_define_constants(PyTypeObject *);
+
+
+
+/******************************************************************************
+* *
+* Paramètres : obj = objet Python à tenter de convertir. *
+* addr = structure équivalente pour Chrysalide. *
+* *
+* Description : Effectue une comparaison avec un objet Python 'BinSymbol'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_richcompare(PyObject *a, PyObject *b, int op)
+{
+ PyObject *result; /* Chaîne à retourner */
+ int ret; /* Bilan de lecture des args. */
+ const GBinSymbol *sym_a; /* Premier élément à traiter */
+ const GBinSymbol *sym_b; /* Second élément à traiter */
+ int status; /* Résultat d'une comparaison */
+
+ ret = PyObject_IsInstance(b, (PyObject *)get_python_binary_symbol_type());
+ if (!ret)
+ {
+ result = Py_NotImplemented;
+ goto cmp_done;
+ }
+
+ sym_a = G_BIN_SYMBOL(pygobject_get(a));
+ sym_a = G_BIN_SYMBOL(pygobject_get(b));
+
+ status = g_binary_symbol_cmp(&sym_a, &sym_b);
+
+ switch (op)
+ {
+ case Py_LT:
+ result = status < 0 ? Py_True : Py_False;
+ break;
+
+ case Py_LE:
+ result = status <= 0 ? Py_True : Py_False;
+ break;
+
+ case Py_EQ:
+ result = status == 0 ? Py_True : Py_False;
+ break;
+
+ case Py_NE:
+ result = status != 0 ? Py_True : Py_False;
+ break;
+
+ case Py_GT:
+ result = status > 0 ? Py_True : Py_False;
+ break;
+
+ case Py_GE:
+ result = status >= 0 ? Py_True : Py_False;
+ break;
+
+ default:
+ result = Py_NotImplemented;
+ break;
+
+ }
+
+ cmp_done:
+
+ Py_INCREF(result);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : type = type de l'objet à instancier. *
+* args = arguments fournis à l'appel. *
+* kwds = arguments de type key=val fournis. *
+* *
+* Description : Crée un nouvel objet Python de type 'DbComment'. *
+* *
+* Retour : Instance Python mise en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+{
+ PyObject *result; /* Bilan à retourner */
+ SymbolType stype; /* Type prévu pour le symbole */
+ int ret; /* Bilan de lecture des args. */
+ GBinSymbol *symbol; /* Version GLib du symble */
+
+ ret = PyArg_ParseTuple(args, "l", &stype);
+ if (!ret) return NULL;
+
+ if (stype >= STP_COUNT)
+ {
+ PyErr_SetString(PyExc_ValueError, _("Invalid type of message"));
+ return NULL;
+ }
+
+ symbol = g_binary_symbol_new(stype);
+
+ result = pygobject_new(G_OBJECT(symbol));
+ g_object_unref(symbol);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant un binaire. *
+* args = arguments fournis à l'appel. *
+* *
+* Description : Définit un autre nom pour le symbole. *
+* *
+* Retour : None. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_set_alt_label(PyObject *self, PyObject *args)
+{
+ const char *alt; /* Etiquette alternative */
+ int ret; /* Bilan de lecture des args. */
+ GBinSymbol *symbol; /* Elément à consulter */
+
+ ret = PyArg_ParseTuple(args, "s", &alt);
+ if (!ret) return NULL;
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+
+ g_binary_symbol_set_alt_label(symbol, alt);
+
+ Py_RETURN_NONE;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant un binaire. *
+* args = arguments fournis à l'appel. *
+* *
+* Description : Raffine la définition de l'emplacement d'un symbole. *
+* *
+* Retour : None. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_fix_range(PyObject *self, PyObject *args)
+{
+ PyObject *py_vmpa; /* Localisation version Python */
+ int ret; /* Bilan de lecture des args. */
+ GBinSymbol *symbol; /* Elément à consulter */
+
+ ret = PyArg_ParseTuple(args, "O", &py_vmpa);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ g_binary_symbol_fix_range(symbol, get_internal_vmpa(py_vmpa));
+
+ Py_RETURN_NONE;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant un binaire. *
+* args = arguments fournis à l'appel. *
+* *
+* Description : Attache la routine associée au symbole. *
+* *
+* Retour : None. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_attach_routine(PyObject *self, PyObject *args)
+{
+ PyObject *py_routine; /* Routine version Python */
+ int ret; /* Bilan de lecture des args. */
+ GBinSymbol *symbol; /* Elément à consulter */
+ GBinRoutine *routine; /* Routine à attacher */
+
+ ret = PyArg_ParseTuple(args, "O", &py_routine);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(py_routine, (PyObject *)get_python_binary_routine_type());
+ if (!ret) return NULL;
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ routine = G_BIN_ROUTINE(pygobject_get(py_routine));
+
+ g_binary_symbol_attach_routine(symbol, routine);
+
+ Py_RETURN_NONE;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant un binaire. *
+* args = arguments fournis à l'appel. *
+* *
+* Description : Attache l'instruction associée au symbole. *
+* *
+* Retour : None. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_attach_instruction(PyObject *self, PyObject *args)
+{
+ PyObject *py_instr; /* Instruction version Python */
+ int ret; /* Bilan de lecture des args. */
+ GBinSymbol *symbol; /* Elément à consulter */
+ GArchInstruction *instr; /* Instruction à attacher */
+
+ ret = PyArg_ParseTuple(args, "O", &py_instr);
+ if (!ret) return NULL;
+
+ ret = PyObject_IsInstance(py_instr, (PyObject *)get_python_arch_instruction_type());
+ if (!ret) return NULL;
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ instr = G_ARCH_INSTRUCTION(pygobject_get(py_instr));
+
+ g_binary_symbol_attach_instruction(symbol, instr);
+
+ Py_RETURN_NONE;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Fournit le type du symbole. *
+* *
+* Retour : Type de symbole représenté. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_get_target_type(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBinSymbol *symbol; /* Elément à consulter */
+ SymbolType type; /* Type de symbole représenté */
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ type = g_binary_symbol_get_target_type(symbol);
+
+ result = PyLong_FromLong(type);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Fournit un étiquette pour viser un symbole. *
+* *
+* Retour : Chaîne de caractères renvoyant au symbole. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_get_label(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBinSymbol *symbol; /* Elément à consulter */
+ const char *label; /* Désignation courante */
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ label = g_binary_symbol_get_label(symbol);
+
+ result = PyUnicode_FromString(label);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Fournit l'emplacement où se situe un symbole. *
+* *
+* Retour : Zone mémoire couverte par le symbole. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_get_range(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBinSymbol *symbol; /* Elément à consulter */
+ const mrange_t *range; /* Couverture courante */
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ range = g_binary_symbol_get_range(symbol);
+
+ result = build_from_internal_mrange(range);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Fournit l'éventuelle routine associée au symbole. *
+* *
+* Retour : Instance en place ou None si aucune. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_get_routine(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBinSymbol *symbol; /* Elément à consulter */
+ GBinRoutine *routine; /* Routine attachée */
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ routine = g_binary_symbol_get_routine(symbol);
+
+ result = pygobject_new(G_OBJECT(routine));
+
+ return result;
+
+}
+
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Fournit l'éventuelle instruction associée au symbole. *
+* *
+* Retour : Instance en place ou None si aucune. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_get_instruction(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBinSymbol *symbol; /* Elément à consulter */
+ GArchInstruction *instr; /* Routine attachée */
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ instr = g_binary_symbol_get_instruction(symbol);
+
+ result = pygobject_new(G_OBJECT(instr));
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Fournit l'éventuel commentaire associé au symbole. *
+* *
+* Retour : Instance Python du commentaire GLib ou None si aucun. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_symbol_get_comment(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBinSymbol *symbol; /* Elément à consulter */
+ GDbComment *comment; /* Commentaire à associé */
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+ comment = g_binary_symbol_get_comment(symbol);
+
+ if (comment != NULL)
+ result = pygobject_new(G_OBJECT(comment));
+ else
+ {
+ result = Py_None;
+ Py_INCREF(result);
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* value = valeur fournie à intégrer ou prendre en compte. *
+* closure = non utilisé ici. *
+* *
+* Description : Ajoute un commentaire facultatif au symbole. *
+* *
+* Retour : Bilan de l'opération pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static int py_binary_symbol_set_comment(PyObject *self, PyObject *value, void *closure)
+{
+ GBinSymbol *symbol; /* Elément à consulter */
+ int ret; /* Bilan de lecture des args. */
+ GDbComment *comment; /* Commentaire à associer */
+
+ symbol = G_BIN_SYMBOL(pygobject_get(self));
+
+ if (value == Py_None)
+ g_binary_symbol_set_comment(symbol, NULL);
+
+ else
+ {
+ ret = PyObject_IsInstance(value, (PyObject *)get_python_db_comment_type());
+ if (!ret) return -1;
+
+ comment = G_DB_COMMENT(pygobject_get(value));
+
+ g_binary_symbol_set_comment(symbol, comment);
+
+ }
+
+ return 0;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
+* *
+* Description : Définit les constantes pour les symboles binaires. *
+* *
+* Retour : true en cas de succès de l'opération, false sinon. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static bool py_binary_symbol_define_constants(PyTypeObject *obj_type)
+{
+ bool result; /* Bilan à retourner */
+
+ result = true;
+
+ result &= PyDict_AddIntMacro(obj_type, STP_DATA);
+ result &= PyDict_AddIntMacro(obj_type, STP_ROUTINE);
+ result &= PyDict_AddIntMacro(obj_type, STP_CODE_LABEL);
+ result &= PyDict_AddIntMacro(obj_type, STP_OBJECT);
+ result &= PyDict_AddIntMacro(obj_type, STP_FUNCTION);
+ result &= PyDict_AddIntMacro(obj_type, STP_ENTRY_POINT);
+ result &= PyDict_AddIntMacro(obj_type, STP_STRING);
+ result &= PyDict_AddIntMacro(obj_type, STP_RO_STRING);
+ result &= PyDict_AddIntMacro(obj_type, STP_COUNT);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_binary_symbol_type(void)
+{
+ static PyMethodDef py_bin_symbol_methods[] = {
+ {
+ "set_alt_label", py_binary_symbol_set_alt_label,
+ METH_VARARGS,
+ "set_alt_label($self, alt, /)\n--\n\nSet an alternative label for the symbol."
+ },
+ {
+ "fix_range", py_binary_symbol_fix_range,
+ METH_VARARGS,
+ "fix_range($self, range, /)\n--\n\nRefine the location of the current symbol."
+ },
+ {
+ "attach_routine", py_binary_symbol_attach_routine,
+ METH_VARARGS,
+ "attach_routine($self, instr, /)\n--\n\nAttach a provided routine to the current symbol."
+ },
+ {
+ "attach_instruction", py_binary_symbol_attach_instruction,
+ METH_VARARGS,
+ "attach_instruction($self, instr, /)\n--\n\nAttach a provided instruction to the current symbol."
+ },
+ { NULL }
+ };
+
+ static PyGetSetDef py_bin_symbol_getseters[] = {
+ {
+ "target_type", py_binary_symbol_get_target_type, NULL,
+ "Type of the current symbol.", NULL
+ },
+ {
+ "label", py_binary_symbol_get_label, NULL,
+ "Label of the symbol, provided by the internal component or by an alternative label.", NULL
+ },
+ {
+ "range", py_binary_symbol_get_range, NULL,
+ "Range covered by the symbol.", NULL
+ },
+ {
+ "routine", py_binary_symbol_get_routine, NULL,
+ "Potential routine attached to the symbol.", NULL
+ },
+ {
+ "instruction", py_binary_symbol_get_instruction, NULL,
+ "Potential instruction attached to the symbol.", NULL
+ },
+ {
+ "comment", py_binary_symbol_get_comment, py_binary_symbol_set_comment,
+ "Optional comment linked to the symbol.", NULL
+ },
+ { NULL }
+ };
+
+ static PyTypeObject py_bin_symbol_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.format.BinSymbol",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "PyChrysalide binary symbol",
+
+ .tp_richcompare = py_binary_symbol_richcompare,
+
+ .tp_methods = py_bin_symbol_methods,
+ .tp_getset = py_bin_symbol_getseters,
+ .tp_new = (newfunc)py_binary_symbol_new
+
+ };
+
+ return &py_bin_symbol_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.format.BinSymbol'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_binary_symbol(PyObject *module)
+{
+ PyTypeObject *py_bin_symbol_type; /* Type Python 'BinSymbol' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_bin_symbol_type = get_python_binary_symbol_type();
+
+ py_bin_symbol_type->tp_base = &PyGObject_Type;
+ py_bin_symbol_type->tp_basicsize = py_bin_symbol_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_bin_symbol_type) != 0)
+ return false;
+
+ if (!py_binary_symbol_define_constants(py_bin_symbol_type))
+ return false;
+
+ Py_INCREF(py_bin_symbol_type);
+ ret = PyModule_AddObject(module, "BinSymbol", (PyObject *)py_bin_symbol_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "BinSymbol", G_TYPE_BIN_SYMBOL, py_bin_symbol_type,
+ Py_BuildValue("(O)", py_bin_symbol_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/format/symbol.h b/plugins/pychrysa/format/symbol.h
new file mode 100644
index 0000000..c094c75
--- /dev/null
+++ b/plugins/pychrysa/format/symbol.h
@@ -0,0 +1,42 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * symbol.h - prototypes pour l'équivalent Python du fichier "format/symbol.h"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSA_FORMAT_SYMBOL_H
+#define _PLUGINS_PYCHRYSA_FORMAT_SYMBOL_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_binary_symbol_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.format.BinSymbol'. */
+bool register_python_binary_symbol(PyObject *);
+
+
+
+#endif /* _PLUGINS_PYCHRYSA_FORMAT_EXECUTABLE_H */
diff --git a/plugins/pychrysa/glibext/Makefile.am b/plugins/pychrysa/glibext/Makefile.am
index 8383434..0a61da2 100644
--- a/plugins/pychrysa/glibext/Makefile.am
+++ b/plugins/pychrysa/glibext/Makefile.am
@@ -1,12 +1,10 @@
noinst_LTLIBRARIES = libpychrysaglibext.la
-# libpychrysaglibext_la_SOURCES = \
-# bufferline.h bufferline.c \
-# codebuffer.h codebuffer.c \
-# module.h module.c
-
libpychrysaglibext_la_SOURCES = \
+ bincontent.h bincontent.c \
+ bufferline.h bufferline.c \
+ codebuffer.h codebuffer.c \
configuration.h configuration.c \
module.h module.c
diff --git a/plugins/pychrysa/glibext/bincontent.c b/plugins/pychrysa/glibext/bincontent.c
new file mode 100644
index 0000000..5c9856e
--- /dev/null
+++ b/plugins/pychrysa/glibext/bincontent.c
@@ -0,0 +1,267 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * bincontent.c - prototypes pour l'équivalent Python du fichier "glibext/gbincontent.c"
+ *
+ * Copyright (C) 2015 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "bincontent.h"
+
+
+#include <pygobject.h>
+
+
+#include <glibext/gbincontent.h>
+
+
+#include "../arch/vmpa.h"
+
+
+/* Crée un nouvel objet Python de type 'BinContent'. */
+static PyObject *py_binary_content_new(PyTypeObject *, PyObject *, PyObject *);
+
+/* Fournit une empreinte unique (SHA256) pour les données. */
+static PyObject *py_binary_content_get_checksum(PyObject *, PyObject *);
+
+/* Lit un nombre non signé sur un octet. */
+static PyObject *py_binary_content_read_u8(PyObject *, PyObject *);
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : type = type de l'objet à instancier. *
+* args = arguments fournis à l'appel. *
+* kwds = arguments de type key=val fournis. *
+* *
+* Description : Crée un nouvel objet Python de type 'BinContent'. *
+* *
+* Retour : Instance Python mise en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_content_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+{
+ PyObject *result; /* Instance à retourner */
+ const char *filename; /* Nom du fichier à charger */
+ int ret; /* Bilan de lecture des args. */
+ GBinContent *content; /* Version GLib du contenu */
+
+ ret = PyArg_ParseTuple(args, "s", &filename);
+ if (!ret) Py_RETURN_NONE;
+
+ content = g_binary_content_new_from_file(filename);
+
+ result = pygobject_new(G_OBJECT(content));
+ g_object_unref(content);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = contenu binaire à manipuler. *
+* args = non utilisé ici. *
+* *
+* Description : Fournit une empreinte unique (SHA256) pour les données. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_content_get_checksum(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ GBinContent *content; /* Version GLib du format */
+ const gchar *checksum; /* Empreinte fournie */
+
+ content = G_BIN_CONTENT(pygobject_get(self));
+
+ checksum = g_binary_content_get_cheksum(content);
+
+ result = PyUnicode_FromString(checksum);
+ Py_INCREF(result);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = contenu binaire à manipuler. *
+* args = non utilisé ici. *
+* *
+* Description : Lit un nombre non signé sur un octet. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_binary_content_read_u8(PyObject *self, PyObject *args)
+{
+ PyObject *result; /* Instance à retourner */
+ GBinContent *content; /* Version GLib du format */
+ int ret; /* Bilan de lecture des args. */
+ PyObject *addr_obj; /* Objet pour une position */
+ vmpa2t *addr; /* Position interne associée */
+ uint8_t val; /* Valeur lue à faire suivre */
+ bool status; /* Bilan de l'opération */
+
+ content = G_BIN_CONTENT(pygobject_get(self));
+
+ printf("Passage\n");
+
+ ret = PyArg_ParseTuple(args, "O", &addr_obj);
+
+ printf("ret == %d\n", ret);
+
+ if (!ret) return NULL;
+
+ addr = get_internal_vmpa(addr_obj);
+ if (addr == NULL) /* ... */;
+
+ status = g_binary_content_read_u8(content, addr, /*SourceEndian endian*/0, &val);
+ if (!status) return NULL;
+
+ printf("val :: 0x%02hhx\n", val);
+
+ result = PyBytes_FromStringAndSize((char *)&val, 1);;
+ //Py_INCREF(result);
+
+ return result;
+
+}
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_binary_content_type(void)
+{
+ static PyMethodDef py_binary_content_methods[] = {
+ { "get_cheksum", py_binary_content_get_checksum,
+ METH_NOARGS,
+ "Compute a SHA256 hash as chechsum of handled data."
+ },
+ { "read_u8", py_binary_content_read_u8,
+ METH_VARARGS,
+ "read_u8($self, addr, /)\n--\n\nRead an unsigned byte from a given position."
+ },
+ { NULL }
+ };
+
+ static PyGetSetDef py_binary_content_getseters[] = {
+ { NULL }
+ };
+
+ static PyTypeObject py_binary_content_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.glibext.BinContent",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "PyChrysalide binary content",
+
+ .tp_methods = py_binary_content_methods,
+ .tp_getset = py_binary_content_getseters,
+ .tp_new = (newfunc)py_binary_content_new
+
+ };
+
+ return &py_binary_content_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.glibext.BinContent'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_binary_content(PyObject *module)
+{
+ PyTypeObject *py_binary_content_type; /* Type Python 'BinContent' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_binary_content_type = get_python_binary_content_type();
+
+ py_binary_content_type->tp_base = &PyGObject_Type;
+ py_binary_content_type->tp_basicsize = py_binary_content_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_binary_content_type) != 0)
+ return false;
+
+ Py_INCREF(py_binary_content_type);
+ ret = PyModule_AddObject(module, "BinContent", (PyObject *)py_binary_content_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "BinContent", G_TYPE_BIN_CONTENT, py_binary_content_type,
+ Py_BuildValue("(O)", py_binary_content_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/analysis/roptions.h b/plugins/pychrysa/glibext/bincontent.h
index 76ad2fe..b6ae9a5 100644
--- a/plugins/pychrysa/analysis/roptions.h
+++ b/plugins/pychrysa/glibext/bincontent.h
@@ -1,8 +1,8 @@
/* Chrysalide - Outil d'analyse de fichiers binaires
- * roptions.h - prototypes pour l'équivalent Python du fichier "analysis/roptions.h"
+ * bincontent.h - prototypes pour l'équivalent Python du fichier "glibext/gbincontent.h"
*
- * Copyright (C) 2010-2012 Cyrille Bagard
+ * Copyright (C) 2015 Cyrille Bagard
*
* This file is part of Chrysalide.
*
@@ -22,24 +22,21 @@
*/
-#ifndef _PLUGINS_PYOIDA_ANALYSIS_ROPTIONS_H
-#define _PLUGINS_PYOIDA_ANALYSIS_ROPTIONS_H
+#ifndef _PLUGINS_PYCHRYSA_GLIBEXT_BINCONTENT_H
+#define _PLUGINS_PYCHRYSA_GLIBEXT_BINCONTENT_H
#include <Python.h>
#include <stdbool.h>
-#include <analysis/roptions.h>
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_binary_content_type(void);
+/* Prend en charge l'objet 'pychrysalide.glibext.BinContent'. */
+bool register_python_binary_content(PyObject *);
-/* Fournit l'instance GLib d'une instance Python. */
-GRenderingOptions *py_rendering_options_get_glib_instance(PyObject *);
-/* Ajoute l'objet 'analysis.roptions' au module Python. */
-bool add_analysis_roptions_to_python_module(PyObject *);
-
-
-#endif /* _PLUGINS_PYOIDA_ANALYSIS_ROPTIONS_H */
+#endif /* _PLUGINS_PYCHRYSA_GLIBEXT_BINCONTENT_H */
diff --git a/plugins/pychrysa/glibext/bufferline.c b/plugins/pychrysa/glibext/bufferline.c
index d5b8b13..ce85cfb 100644
--- a/plugins/pychrysa/glibext/bufferline.c
+++ b/plugins/pychrysa/glibext/bufferline.c
@@ -29,16 +29,35 @@
#include <pygobject.h>
+#include <i18n.h>
+
+
#include <glibext/gbufferline.h>
-#include "../quirks.h"
+#include "../helpers.h"
+#include "../arch/vmpa.h"
/* Reconstruit et fournit le texte présent sur une ligne tampon. */
static PyObject *py_buffer_line_get_text(PyObject *, PyObject *);
+/* Ajoute une propriété particulière à une ligne donnée. */
+static PyObject *py_buffer_line_add_flag(PyObject *, PyObject *);
+
+/* Retire une propriété particulière à une ligne donnée. */
+static PyObject *py_buffer_line_remove_flag(PyObject *, PyObject *);
+
+/* Fournit l'emplacement où se situe un symbole. */
+static PyObject *py_buffer_line_get_range(PyObject *, void *);
+
+/* Renseigne sur les propriétés particulières liées à une ligne. */
+static PyObject *py_buffer_line_get_flags(PyObject *, void *);
+
+/* Définit les constantes pour les lignes de tampon. */
+static bool py_buffer_line_define_constants(PyTypeObject *);
+
/******************************************************************************
@@ -57,13 +76,26 @@ static PyObject *py_buffer_line_get_text(PyObject *, PyObject *);
static PyObject *py_buffer_line_get_text(PyObject *self, PyObject *args)
{
PyObject *result; /* Trouvailles à retourner */
+ BufferLineColumn first; /* Première colonne à parcourir*/
+ BufferLineColumn end; /* Dernière colonne à parcourir*/
+ int markup; /* Besoin de décorations ? */
+ int ret; /* Bilan de lecture des args. */
GBufferLine *line; /* Version native */
char *text; /* Texte reconstruit à libérer */
+ ret = PyArg_ParseTuple(args, "IIp", &first, &end, &markup);
+ if (!ret) return NULL;
+
+ if (first >= BLC_COUNT || end >= BLC_COUNT)
+ {
+ PyErr_SetString(PyExc_ValueError, _("Invalid range in arguments"));
+ return NULL;
+ }
+
line = G_BUFFER_LINE(pygobject_get(self));
- text = "";//g_buffer_line_get_text(line);
+ text = g_buffer_line_get_text(line, first, end, markup);
- result = PyString_FromString(text);
+ result = PyUnicode_FromString(text);
free(text);
@@ -74,60 +106,278 @@ static PyObject *py_buffer_line_get_text(PyObject *self, PyObject *args)
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : self = classe représentant une ligne de tampon. *
+* args = arguments fournis à l'appel. *
* *
-* Description : Prend en charge l'objet 'pychrysalide.glibext.BufferLine'. *
+* Description : Ajoute une propriété particulière à une ligne donnée. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : - *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_buffer_line(PyObject *module)
+static PyObject *py_buffer_line_add_flag(PyObject *self, PyObject *args)
{
- PyObject *pygobj_mod; /* Module Python-GObject */
- int ret; /* Bilan d'un appel */
+ BufferLineFlags flag; /* Drapeau à considérer */
+ int ret; /* Bilan de lecture des args. */
+ GBufferLine *line; /* Version native */
+
+ ret = PyArg_ParseTuple(args, "I", &flag);
+ if (!ret) return NULL;
+
+ if ((flag & ~BLF_ALL) != 0)
+ {
+ PyErr_SetString(PyExc_ValueError, _("Invalid flag"));
+ return NULL;
+ }
+
+ line = G_BUFFER_LINE(pygobject_get(self));
+ g_buffer_line_add_flag(line, flag);
+
+ Py_RETURN_NONE;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = classe représentant une ligne de tampon. *
+* args = arguments fournis à l'appel. *
+* *
+* Description : Retire une propriété particulière à une ligne donnée. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_buffer_line_remove_flag(PyObject *self, PyObject *args)
+{
+ BufferLineFlags flag; /* Drapeau à considérer */
+ int ret; /* Bilan de lecture des args. */
+ GBufferLine *line; /* Version native */
+
+ ret = PyArg_ParseTuple(args, "I", &flag);
+ if (!ret) return NULL;
+
+ if ((flag & ~BLF_ALL) != 0)
+ {
+ PyErr_SetString(PyExc_ValueError, _("Invalid flag"));
+ return NULL;
+ }
+
+ line = G_BUFFER_LINE(pygobject_get(self));
+ g_buffer_line_remove_flag(line, flag);
+
+ Py_RETURN_NONE;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Indique la zone mémoire où se situe la ligne. *
+* *
+* Retour : Emplacement mémoire virtuel ou physique. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_buffer_line_get_range(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBufferLine *line; /* Elément à consulter */
+ const mrange_t *range; /* Couverture courante */
+
+ line = G_BUFFER_LINE(pygobject_get(self));
+ range = g_buffer_line_get_range(line);
+
+ result = build_from_internal_mrange(range);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : self = objet Python concerné par l'appel. *
+* closure = non utilisé ici. *
+* *
+* Description : Renseigne sur les propriétés particulières liées à une ligne.*
+* *
+* Retour : Propriétés intégrées. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static PyObject *py_buffer_line_get_flags(PyObject *self, void *closure)
+{
+ PyObject *result; /* Valeur à retourner */
+ GBufferLine *line; /* Elément à consulter */
+ BufferLineFlags flags; /* Drapeaux à exporter */
+
+ line = G_BUFFER_LINE(pygobject_get(self));
+ flags = g_buffer_line_get_flags(line);
+
+ result = PyLong_FromLong(flags);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
+* *
+* Description : Définit les constantes pour les lignes de tampon. *
+* *
+* Retour : true en cas de succès de l'opération, false sinon. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static bool py_buffer_line_define_constants(PyTypeObject *obj_type)
+{
+ bool result; /* Bilan à retourner */
+
+ result = true;
+
+ result &= PyDict_AddIntMacro(obj_type, BLC_PHYSICAL);
+ result &= PyDict_AddIntMacro(obj_type, BLC_VIRTUAL);
+ result &= PyDict_AddIntMacro(obj_type, BLC_BINARY);
+ result &= PyDict_AddIntMacro(obj_type, BLC_ASSEMBLY_HEAD);
+ result &= PyDict_AddIntMacro(obj_type, BLC_ASSEMBLY);
+ result &= PyDict_AddIntMacro(obj_type, BLC_COMMENTS);
+ result &= PyDict_AddIntMacro(obj_type, BLC_COUNT);
+ result &= PyDict_AddIntMacro(obj_type, BLC_LAST_USED);
+ result &= PyDict_AddIntMacro(obj_type, BLC_INVALID);
+ result &= PyDict_AddIntMacro(obj_type, BLC_MAIN);
+ result &= PyDict_AddIntMacro(obj_type, BLC_FIRST);
+ result &= PyDict_AddIntMacro(obj_type, BLC_DISPLAY);
+
+ result &= PyDict_AddIntMacro(obj_type, BLF_NONE);
+ result &= PyDict_AddIntMacro(obj_type, BLF_HAS_CODE);
+ result &= PyDict_AddIntMacro(obj_type, BLF_ENTRYPOINT);
+ result &= PyDict_AddIntMacro(obj_type, BLF_BOOKMARK);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+PyTypeObject *get_python_buffer_line_type(void)
+{
static PyMethodDef py_buffer_line_methods[] = {
{
- "get_text", (PyCFunction)py_buffer_line_get_text,
- METH_NOARGS,
- "Rebuild and provide the text of a buffer line."
+ "get_text", py_buffer_line_get_text,
+ METH_VARARGS,
+ "get_text($self, first_col, last_col, markup, /)\n--\n\nProvide the text of a buffer line."
+ },
+ {
+ "add_flag", py_buffer_line_add_flag,
+ METH_VARARGS,
+ "add_flag($self, flag, /)\n--\n\nAdd a flag to the buffer line."
+ },
+ {
+ "remove_flag", py_buffer_line_remove_flag,
+ METH_VARARGS,
+ "remove_flag($self, flag, /)\n--\n\nRemove a flag from the buffer line."
+ },
+ { NULL }
+ };
+
+ static PyGetSetDef py_buffer_line_getseters[] = {
+ {
+ "range", py_buffer_line_get_range, NULL,
+ "Range covered by the line.", NULL
+ },
+ {
+ "flags", py_buffer_line_get_flags, NULL,
+ "Current flags of the buffer line.", NULL
},
{ NULL }
};
static PyTypeObject py_buffer_line_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.glibext.BufferLine",
.tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT,
.tp_doc = "PyChrysalide buffer line",
- .tp_methods = py_buffer_line_methods
+ .tp_methods = py_buffer_line_methods,
+ .tp_getset = py_buffer_line_getseters,
};
- pygobj_mod = PyImport_ImportModule("gobject");
- if (pygobj_mod == NULL) return false;
+ return &py_buffer_line_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.glibext.BufferLine'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
- py_buffer_line_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(pygobj_mod, "GObject");
- Py_DECREF(pygobj_mod);
+bool register_python_buffer_line(PyObject *module)
+{
+ PyTypeObject *py_buffer_line_type; /* Type Python 'BufferLine' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_buffer_line_type = get_python_buffer_line_type();
+
+ py_buffer_line_type->tp_base = &PyGObject_Type;
+ py_buffer_line_type->tp_basicsize = py_buffer_line_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_buffer_line_type) != 0)
+ return false;
- if (PyType_Ready(&py_buffer_line_type) < 0)
+ if (!py_buffer_line_define_constants(py_buffer_line_type))
return false;
- Py_INCREF(&py_buffer_line_type);
- ret = PyModule_AddObject(module, "BufferLine", (PyObject *)&py_buffer_line_type);
+ Py_INCREF(py_buffer_line_type);
+ ret = PyModule_AddObject(module, "BufferLine", (PyObject *)py_buffer_line_type);
+ if (ret != 0) return false;
- pygobject_register_class(module, "GBufferLine", G_TYPE_BUFFER_LINE, &py_buffer_line_type,
- Py_BuildValue("(O)", py_buffer_line_type.tp_base));
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "BufferLine", G_TYPE_BUFFER_LINE, py_buffer_line_type,
+ Py_BuildValue("(O)", py_buffer_line_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/glibext/bufferline.h b/plugins/pychrysa/glibext/bufferline.h
index 282a61a..e02b05f 100644
--- a/plugins/pychrysa/glibext/bufferline.h
+++ b/plugins/pychrysa/glibext/bufferline.h
@@ -31,6 +31,9 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_buffer_line_type(void);
+
/* Prend en charge l'objet 'pychrysalide.glibext.BufferLine'. */
bool register_python_buffer_line(PyObject *);
diff --git a/plugins/pychrysa/glibext/codebuffer.c b/plugins/pychrysa/glibext/codebuffer.c
index 6368ee7..9d9bc96 100644
--- a/plugins/pychrysa/glibext/codebuffer.c
+++ b/plugins/pychrysa/glibext/codebuffer.c
@@ -31,7 +31,7 @@
#include <glibext/gcodebuffer.h>
-#include "../quirks.h"
+#include "../arch/vmpa.h"
@@ -56,15 +56,22 @@ static PyObject *py_code_buffer_find_line_by_addr(PyObject *, PyObject *);
static PyObject *py_code_buffer_find_line_by_addr(PyObject *self, PyObject *args)
{
PyObject *result; /* Trouvailles à retourner */
- GCodeBuffer *buffer; /* Version native */
- vmpa_t addr; /* Adresse visée par l'opérat° */
+ PyObject *py_vmpa; /* Localisation version Python */
int ret; /* Bilan de lecture des args. */
+ vmpa2t *addr; /* Adresse visée par l'opérat° */
+ GCodeBuffer *buffer; /* Version native */
GBufferLine *line; /* Ligne trouvée */
- buffer = G_CODE_BUFFER(pygobject_get(self));
+ ret = PyArg_ParseTuple(args, "O", &py_vmpa);
+ if (!ret) return NULL;
- ret = PyArg_ParseTuple(args, "K", &addr);
- if (!ret) Py_RETURN_NONE;
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
+ addr = get_internal_vmpa(py_vmpa);
+ if (addr == NULL) return NULL;
+
+ buffer = G_CODE_BUFFER(pygobject_get(self));
line = g_code_buffer_find_line_by_addr(buffer, addr, 0, NULL);
if (line == NULL) Py_RETURN_NONE;
@@ -78,60 +85,86 @@ static PyObject *py_code_buffer_find_line_by_addr(PyObject *self, PyObject *args
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.glibext.Codebuffer'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_code_buffer(PyObject *module)
+PyTypeObject *get_python_code_buffer_type(void)
{
- PyObject *pygobj_mod; /* Module Python-GObject */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_code_buffer_methods[] = {
{
"find_line_by_addr", (PyCFunction)py_code_buffer_find_line_by_addr,
METH_VARARGS,
- "Find a buffer line with a given address."
+ "find_line_by_addr($self, addr, /)\n--\n\nFind a buffer line with a given address."
},
{ NULL }
};
+ static PyGetSetDef py_code_buffer_getseters[] = {
+ { NULL }
+ };
+
static PyTypeObject py_code_buffer_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.glibext.CodeBuffer",
.tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT,
.tp_doc = "PyChrysalide code buffer",
- .tp_methods = py_code_buffer_methods
+ .tp_methods = py_code_buffer_methods,
+ .tp_getset = py_code_buffer_getseters,
};
- pygobj_mod = PyImport_ImportModule("gobject");
- if (pygobj_mod == NULL) return false;
+ return &py_code_buffer_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.glibext.CodeBuffer'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_code_buffer(PyObject *module)
+{
+ PyTypeObject *py_code_buffer_type; /* Type Python 'CodeBuffer' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_code_buffer_type = get_python_code_buffer_type();
- py_code_buffer_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(pygobj_mod, "GObject");
- Py_DECREF(pygobj_mod);
+ py_code_buffer_type->tp_base = &PyGObject_Type;
+ py_code_buffer_type->tp_basicsize = py_code_buffer_type->tp_base->tp_basicsize;
- if (PyType_Ready(&py_code_buffer_type) < 0)
+ if (PyType_Ready(py_code_buffer_type) != 0)
return false;
- Py_INCREF(&py_code_buffer_type);
- ret = PyModule_AddObject(module, "CodeBuffer", (PyObject *)&py_code_buffer_type);
+ Py_INCREF(py_code_buffer_type);
+ ret = PyModule_AddObject(module, "CodeBuffer", (PyObject *)py_code_buffer_type);
+ if (ret != 0) return false;
- pygobject_register_class(module, "GCodeBuffer", G_TYPE_CODE_BUFFER, &py_code_buffer_type,
- Py_BuildValue("(O)", py_code_buffer_type.tp_base));
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "CodeBuffer", G_TYPE_CODE_BUFFER, py_code_buffer_type,
+ Py_BuildValue("(O)", py_code_buffer_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/glibext/codebuffer.h b/plugins/pychrysa/glibext/codebuffer.h
index e921e36..83ec508 100644
--- a/plugins/pychrysa/glibext/codebuffer.h
+++ b/plugins/pychrysa/glibext/codebuffer.h
@@ -31,6 +31,9 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_code_buffer_type(void);
+
/* Prend en charge l'objet 'pychrysalide.glibext.CodeBuffer'. */
bool register_python_code_buffer(PyObject *);
diff --git a/plugins/pychrysa/glibext/configuration.c b/plugins/pychrysa/glibext/configuration.c
index 9820af3..fd35b19 100644
--- a/plugins/pychrysa/glibext/configuration.c
+++ b/plugins/pychrysa/glibext/configuration.c
@@ -67,15 +67,10 @@ static bool py_config_param_define_constants(PyObject *);
/* ----------------------------- PARCOURS DE PARAMETRES ----------------------------- */
-
+/* Parcours des éléments de configuration */
typedef struct _pyConfigParamIterator
{
-
- PyObject_HEAD
- long int m;
- long int i;
-
-
+ PyObject_HEAD /* A laisser en premier */
GGenConfig *config; /* Configuration à parcourir */
GList *params; /* Liste de paramètres */
@@ -85,15 +80,10 @@ typedef struct _pyConfigParamIterator
} pyConfigParamIterator;
-
-
/* Prend acte d'un compteur de référence à 0. */
static void py_config_param_iterator_dealloc(PyObject *);
/* Fournit un itérateur pour paramètres de configuration. */
-static PyObject *py_config_param_iterator_iter(PyObject *);
-
-/* Fournit un itérateur pour paramètres de configuration. */
static PyObject *py_config_param_iterator_next(PyObject *);
/* Initialise un objet Python de type 'ConfigParamIterator'. */
@@ -646,28 +636,7 @@ static void py_config_param_iterator_dealloc(PyObject *self)
g_generic_config_runlock(iterator->config);
g_object_unref(G_OBJECT(iterator->config));
- Py_TYPE(self)->tp_free((PyObject*)self);
-
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : self = itérateur à manipuler. *
-* *
-* Description : Fournit un itérateur pour paramètres de configuration. *
-* *
-* Retour : Instance Python prête à emploi. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static PyObject *py_config_param_iterator_iter(PyObject *self)
-{
- Py_INCREF(self);
-
- return self;
+ Py_TYPE(self)->tp_free((PyObject *)self);
}
@@ -700,7 +669,7 @@ static PyObject *py_config_param_iterator_next(PyObject *self)
if (item != NULL)
{
result = pygobject_new(G_OBJECT(item->data));
- Py_XINCREF(result);
+ Py_INCREF(result);
}
else
{
@@ -782,7 +751,7 @@ PyTypeObject *get_python_config_param_iterator_type(void)
.tp_doc = "Iterator for configuration parameters",
- .tp_iter = py_config_param_iterator_iter,
+ .tp_iter = PyObject_SelfIter,
.tp_iternext = py_config_param_iterator_next,
.tp_init = py_config_param_iterator_init,
@@ -816,7 +785,6 @@ bool register_python_config_param_iterator(PyObject *module)
py_config_param_iterator_type = get_python_config_param_iterator_type();
py_config_param_iterator_type->tp_base = &PyBaseObject_Type;
- py_config_param_iterator_type->tp_basicsize = py_config_param_iterator_type->tp_base->tp_basicsize;
if (PyType_Ready(py_config_param_iterator_type) != 0)
return false;
@@ -1063,7 +1031,7 @@ static PyObject *py_generic_config_list_params(PyObject *self, PyObject *args)
PyObject *args_list; /* Arguments de mise en place */
iterator_type = get_python_config_param_iterator_type();
-
+
Py_INCREF(self);
args_list = Py_BuildValue("(O)", self);
diff --git a/plugins/pychrysa/glibext/module.c b/plugins/pychrysa/glibext/module.c
index 9f3d3a8..0cb96a7 100644
--- a/plugins/pychrysa/glibext/module.c
+++ b/plugins/pychrysa/glibext/module.c
@@ -25,6 +25,12 @@
#include "module.h"
+#include <assert.h>
+
+
+#include "bincontent.h"
+#include "bufferline.h"
+#include "codebuffer.h"
#include "configuration.h"
@@ -75,18 +81,16 @@ bool add_glibext_module_to_python_module(PyObject *super)
result = true;
+ result &= register_python_binary_content(module);
+ result &= register_python_buffer_line(module);
+ result &= register_python_code_buffer(module);
result &= register_python_config_param(module);
result &= register_python_config_param_iterator(module);
result &= register_python_generic_config(module);
agmtpm_exit:
- if (!result)
- {
- printf("something went wrong in %s...\n", __FUNCTION__);
- /* ... */
-
- }
+ assert(result);
return result;
diff --git a/plugins/pychrysa/gtkext/Makefile.am b/plugins/pychrysa/gtkext/Makefile.am
index 4849c7b..958f000 100644
--- a/plugins/pychrysa/gtkext/Makefile.am
+++ b/plugins/pychrysa/gtkext/Makefile.am
@@ -3,6 +3,7 @@ noinst_LTLIBRARIES = libpychrysagtkext.la
libpychrysagtkext_la_SOURCES = \
blockview.h blockview.c \
+ bufferview.h bufferview.c \
viewpanel.h viewpanel.c \
module.h module.c
diff --git a/plugins/pychrysa/gtkext/blockview.c b/plugins/pychrysa/gtkext/blockview.c
index e076e3c..973538b 100644
--- a/plugins/pychrysa/gtkext/blockview.c
+++ b/plugins/pychrysa/gtkext/blockview.c
@@ -31,66 +31,51 @@
#include <gtkext/gtkblockview.h>
-#include "../quirks.h"
-
-
-
-/* Crée un nouvel objet Python de type 'ViewPanel'. */
-static PyObject *py_block_view_new(PyTypeObject *, PyObject *, PyObject *);
+#include "bufferview.h"
/******************************************************************************
* *
-* Paramètres : type = type de l'objet à instancier. *
-* args = arguments fournis à l'appel. *
-* kwds = arguments de type key=val fournis. *
+* Paramètres : - *
* *
-* Description : Crée un nouvel objet Python de type 'ViewPanel'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Instance Python mise en place. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-static PyObject *py_block_view_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+PyTypeObject *get_python_block_view_type(void)
{
-#if 0
- PyObject *result; /* Instance à retourner */
- const char *name; /* Désignation humaine */
- const char *lname; /* Nom version longue */
- PyGObject *widget; /* Composant visuel du panneau */
- const char *path; /* Placement à l'affichage */
- int ret; /* Bilan de lecture des args. */
- GEditorItem *item; /* Version GLib du format */
-
- ret = PyArg_ParseTuple(args, "ssOs", &name, &lname, &widget, &path);
- if (!ret) Py_RETURN_NONE;
-
- item = g_block_view_new(get_internal_ref(), name, lname,
- GTK_WIDGET(pygobject_get(widget)), path);
-
- result = py_block_view_from_c(G_BLOCK_VIEW(item));
- g_object_unref(item);
-
- return (PyObject *)result;
-#endif
-
- /* FIXME */
-
+ static PyMethodDef py_block_view_methods[] = {
+ { NULL }
+ };
- Py_RETURN_NONE;
+ static PyGetSetDef py_block_view_getseters[] = {
+ { NULL }
+ };
-}
+ static PyTypeObject py_block_view_type = {
+ PyVarObject_HEAD_INIT(NULL, 0)
+ .tp_name = "pychrysalide.gtkext.BlockView",
+ .tp_basicsize = sizeof(PyGObject),
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+ .tp_doc = "PyChrysalide block view.",
+ .tp_methods = py_block_view_methods,
+ .tp_getset = py_block_view_getseters
+ };
+ return &py_block_view_type;
+}
/******************************************************************************
@@ -107,50 +92,26 @@ static PyObject *py_block_view_new(PyTypeObject *type, PyObject *args, PyObject
bool register_python_block_view(PyObject *module)
{
- PyObject *parent_mod; /* Module Python-EditorItem */
+ PyTypeObject *py_block_view_type; /* Type Python 'BlockView' */
int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
- static PyMethodDef py_block_view_methods[] = {
- { NULL }
- };
-
- static PyGetSetDef py_block_view_getseters[] = {
- { NULL }
- };
-
- static PyTypeObject py_block_view_type = {
-
- PyObject_HEAD_INIT(NULL)
-
- .tp_name = "pychrysalide.gtkext.BlockView",
- .tp_basicsize = sizeof(PyGObject),
-
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
-
- .tp_doc = "PyChrysalide view panel",
-
- .tp_methods = py_block_view_methods,
- .tp_getset = py_block_view_getseters,
- .tp_new = (newfunc)py_block_view_new,
- .tp_init = (initproc)pychrysalide_allow_args_for_gobjects
-
- };
-
- parent_mod = PyImport_ImportModule("pychrysalide.gtkext");
- if (parent_mod == NULL) return false;
+ py_block_view_type = get_python_block_view_type();
- py_block_view_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "ViewPanel");
- Py_DECREF(parent_mod);
+ py_block_view_type->tp_base = get_python_buffer_view_type();
+ py_block_view_type->tp_basicsize = py_block_view_type->tp_base->tp_basicsize;
- if (PyType_Ready(&py_block_view_type) < 0)
+ if (PyType_Ready(py_block_view_type) != 0)
return false;
- Py_INCREF(&py_block_view_type);
- ret = PyModule_AddObject(module, "BlockView", (PyObject *)&py_block_view_type);
+ Py_INCREF(py_block_view_type);
+ ret = PyModule_AddObject(module, "BlockView", (PyObject *)py_block_view_type);
+ if (ret != 0) return false;
- pygobject_register_class(module, "GtkBlockView", GTK_TYPE_BLOCK_VIEW, &py_block_view_type,
- Py_BuildValue("(O)", py_block_view_type.tp_base));
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "BlockView", GTK_TYPE_BLOCK_VIEW, py_block_view_type,
+ Py_BuildValue("(O)", py_block_view_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/gtkext/blockview.h b/plugins/pychrysa/gtkext/blockview.h
index a6cf3a0..1735ac3 100644
--- a/plugins/pychrysa/gtkext/blockview.h
+++ b/plugins/pychrysa/gtkext/blockview.h
@@ -22,8 +22,8 @@
*/
-#ifndef _PLUGINS_PYCHRYSA_GTKEXT_MODULE_BLOCK_VIEW_H
-#define _PLUGINS_PYCHRYSA_GTKEXT_MODULE_BLOCK_VIEW_H
+#ifndef _PLUGINS_PYCHRYSA_GTKEXT_BLOCKVIEW_H
+#define _PLUGINS_PYCHRYSA_GTKEXT_BLOCKVIEW_H
#include <Python.h>
@@ -31,9 +31,12 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_block_view_type(void);
+
/* Prend en charge l'objet 'pychrysalide.gtkext.BlockView'. */
bool register_python_block_view(PyObject *module);
-#endif /* _PLUGINS_PYCHRYSA_GTKEXT_MODULE_BLOCK_VIEW_H */
+#endif /* _PLUGINS_PYCHRYSA_GTKEXT_BLOCKVIEW_H */
diff --git a/plugins/pychrysa/gtkext/bufferview.c b/plugins/pychrysa/gtkext/bufferview.c
new file mode 100644
index 0000000..a8b86e8
--- /dev/null
+++ b/plugins/pychrysa/gtkext/bufferview.c
@@ -0,0 +1,117 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * bufferview.c - prototypes pour l'équivalent Python du fichier "gtkext/gtkbufferview.c"
+ *
+ * Copyright (C) 2012 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "bufferview.h"
+
+
+#include <pygobject.h>
+
+
+#include <gtkext/gtkbufferview.h>
+
+
+#include "viewpanel.h"
+
+
+
+/******************************************************************************
+* *
+* Paramètres : - *
+* *
+* Description : Fournit un accès à une définition de type à diffuser. *
+* *
+* Retour : Définition d'objet pour Python. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyTypeObject *get_python_buffer_view_type(void)
+{
+ static PyMethodDef py_buffer_view_methods[] = {
+ { NULL }
+ };
+
+ static PyGetSetDef py_buffer_view_getseters[] = {
+ { NULL }
+ };
+
+ static PyTypeObject py_buffer_view_type = {
+
+ PyVarObject_HEAD_INIT(NULL, 0)
+
+ .tp_name = "pychrysalide.gtkext.Bufferview",
+ .tp_basicsize = sizeof(PyGObject),
+
+ .tp_flags = Py_TPFLAGS_DEFAULT,
+
+ .tp_doc = "PyChrysalide buffer view.",
+
+ .tp_methods = py_buffer_view_methods,
+ .tp_getset = py_buffer_view_getseters
+
+ };
+
+ return &py_buffer_view_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.gtkext.Bufferview'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_buffer_view(PyObject *module)
+{
+ PyTypeObject *py_buffer_view_type; /* Type Python 'Bufferview' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_buffer_view_type = get_python_buffer_view_type();
+
+ py_buffer_view_type->tp_base = get_python_view_panel_type();
+ py_buffer_view_type->tp_basicsize = py_buffer_view_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_buffer_view_type) != 0)
+ return false;
+
+ Py_INCREF(py_buffer_view_type);
+ ret = PyModule_AddObject(module, "Bufferview", (PyObject *)py_buffer_view_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "Bufferview", GTK_TYPE_BUFFER_VIEW, py_buffer_view_type,
+ Py_BuildValue("(O)", py_buffer_view_type->tp_base));
+
+ return true;
+
+}
diff --git a/plugins/pychrysa/gtkext/bufferview.h b/plugins/pychrysa/gtkext/bufferview.h
new file mode 100644
index 0000000..7ef9995
--- /dev/null
+++ b/plugins/pychrysa/gtkext/bufferview.h
@@ -0,0 +1,42 @@
+
+/* Chrysalide - Outil d'analyse de fichiers binaires
+ * bufferview.h - prototypes pour l'équivalent Python du fichier "gtkext/gtkbufferview.h"
+ *
+ * Copyright (C) 2012 Cyrille Bagard
+ *
+ * This file is part of Chrysalide.
+ *
+ * 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#ifndef _PLUGINS_PYCHRYSA_GTKEXT_BUFFERVIEW_H
+#define _PLUGINS_PYCHRYSA_GTKEXT_BUFFERVIEW_H
+
+
+#include <Python.h>
+#include <stdbool.h>
+
+
+
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_buffer_view_type(void);
+
+/* Prend en charge l'objet 'pychrysalide.gtkext.Bufferview'. */
+bool register_python_buffer_view(PyObject *module);
+
+
+
+#endif /* _PLUGINS_PYCHRYSA_GTKEXT_BUFFERVIEW_H */
diff --git a/plugins/pychrysa/gtkext/module.c b/plugins/pychrysa/gtkext/module.c
index ef006e2..507b3cb 100644
--- a/plugins/pychrysa/gtkext/module.c
+++ b/plugins/pychrysa/gtkext/module.c
@@ -25,7 +25,11 @@
#include "module.h"
+#include <assert.h>
+
+
#include "blockview.h"
+#include "bufferview.h"
#include "viewpanel.h"
@@ -44,25 +48,46 @@
bool add_gtkext_module_to_python_module(PyObject *super)
{
- bool result;
- PyObject *module;
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyMethodDef py_gtkext_methods[] = {
- { NULL }
+ static PyModuleDef py_chrysalide_gtkext_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.gtkext",
+ .m_doc = "Python module for Chrysalide.gtkext",
+
+ .m_size = -1,
+
};
- module = Py_InitModule("pychrysalide.gtkext", py_gtkext_methods);
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_gtkext_module);
if (module == NULL) return false;
+ ret = PyState_AddModule(super, &py_chrysalide_gtkext_module);
+ if (ret != 0) goto agmtpm_exit;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.gtkext");
+ if (ret != 0) goto agmtpm_exit;
+
Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.gtkext", module);
+ ret = PyModule_AddObject(super, "gtkext", module);
+ if (ret != 0) goto agmtpm_exit;
- result = (ret == 0);
+ result = true;
result &= register_python_view_panel(module);
+ result &= register_python_buffer_view(module);
result &= register_python_block_view(module);
+ agmtpm_exit:
+
+ assert(result);
+
return result;
}
diff --git a/plugins/pychrysa/gtkext/viewpanel.c b/plugins/pychrysa/gtkext/viewpanel.c
index f680487..8c85fbd 100644
--- a/plugins/pychrysa/gtkext/viewpanel.c
+++ b/plugins/pychrysa/gtkext/viewpanel.c
@@ -31,16 +31,22 @@
#include <gtkext/gtkviewpanel.h>
-#include "../quirks.h"
+#include "../helpers.h"
+#include "../arch/vmpa.h"
/* Crée un nouvel objet Python de type 'ViewPanel'. */
+#if 0
static PyObject *py_view_panel_new(PyTypeObject *, PyObject *, PyObject *);
+#endif
/* S'assure qu'une adresse donnée est visible à l'écran. */
static PyObject *py_view_panel_scroll_to_address(PyObject *, PyObject *);
+/* Définit les constantes pour les panneaux de vue. */
+static bool py_view_panel_define_constants(PyTypeObject *);
+
/******************************************************************************
@@ -56,7 +62,7 @@ static PyObject *py_view_panel_scroll_to_address(PyObject *, PyObject *);
* Remarques : - *
* *
******************************************************************************/
-
+#if 0
static PyObject *py_view_panel_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
{
#if 0
@@ -86,10 +92,7 @@ static PyObject *py_view_panel_new(PyTypeObject *type, PyObject *args, PyObject
Py_RETURN_NONE;
}
-
-
-
-
+#endif
/******************************************************************************
@@ -108,47 +111,75 @@ static PyObject *py_view_panel_new(PyTypeObject *type, PyObject *args, PyObject
static PyObject *py_view_panel_scroll_to_address(PyObject *self, PyObject *args)
{
GtkViewPanel *panel; /* Panneau à manipuler */
- vmpa_t addr; /* Adresse demandée en visuel */
+ PyObject *py_vmpa; /* Localisation version Python */
int ret; /* Bilan de lecture des args. */
+ vmpa2t *addr; /* Adresse visée par l'opérat° */
- panel = GTK_VIEW_PANEL(pygobject_get(self));
+ ret = PyArg_ParseTuple(args, "O", &py_vmpa);
+ if (!ret) return NULL;
- ret = PyArg_ParseTuple(args, "K", &addr);
- if (!ret) Py_RETURN_NONE;
+ ret = PyObject_IsInstance(py_vmpa, (PyObject *)get_python_vmpa_type());
+ if (!ret) return NULL;
+
+ addr = get_internal_vmpa(py_vmpa);
+ if (addr == NULL) return NULL;
+
+ panel = GTK_VIEW_PANEL(pygobject_get(self));
- //gtk_view_panel_scroll_to_address(panel, addr);
+ gtk_view_panel_scroll_to_address(panel, addr, SPT_RAW);
Py_RETURN_NONE;
}
+/******************************************************************************
+* *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
+* *
+* Description : Définit les constantes pour les panneaux de vue. *
+* *
+* Retour : true en cas de succès de l'opération, false sinon. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static bool py_view_panel_define_constants(PyTypeObject *obj_type)
+{
+ bool result; /* Bilan à retourner */
+ result = true;
+ result &= PyDict_AddIntMacro(obj_type, SPT_RAW);
+ result &= PyDict_AddIntMacro(obj_type, SPT_TOP);
+ result &= PyDict_AddIntMacro(obj_type, SPT_CENTER);
+ result &= PyDict_AddIntMacro(obj_type, SPT_BOTTOM);
+
+ return result;
+
+}
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.gtkext.ViewPanel'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_view_panel(PyObject *module)
+PyTypeObject *get_python_view_panel_type(void)
{
- PyObject *parent_mod; /* Module Python-EditorItem */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_view_panel_methods[] = {
{
"scroll_to_address", (PyCFunction)py_view_panel_scroll_to_address,
METH_VARARGS,
- "Ensure a given address is displayed in the view panel."
+ "scroll_to_address($self, addr, tweak, /)\n--\n\nEnsure a given address is displayed in the view panel."
},
{ NULL }
};
@@ -159,37 +190,70 @@ bool register_python_view_panel(PyObject *module)
static PyTypeObject py_view_panel_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.gtkext.ViewPanel",
.tp_basicsize = sizeof(PyGObject),
.tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
- .tp_doc = "PyChrysalide view panel",
+ .tp_doc = "PyChrysalide view panel.",
.tp_methods = py_view_panel_methods,
.tp_getset = py_view_panel_getseters,
- .tp_new = (newfunc)py_view_panel_new,
- .tp_init = (initproc)pychrysalide_allow_args_for_gobjects
+ //.tp_new = (newfunc)py_view_panel_new,
+ //.tp_init = (initproc)pychrysalide_allow_args_for_gobjects
};
- parent_mod = PyImport_ImportModule("gtk");
+ return &py_view_panel_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.gtkext.ViewPanel'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_view_panel(PyObject *module)
+{
+ PyTypeObject *py_view_panel_type; /* Type Python 'ViewPanel' */
+ PyObject *parent_mod; /* Module Python Fixed */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_view_panel_type = get_python_view_panel_type();
+
+ parent_mod = PyImport_ImportModule("gi.repository.Gtk");
if (parent_mod == NULL) return false;
- py_view_panel_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "Fixed");
+ py_view_panel_type->tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "Fixed");
Py_DECREF(parent_mod);
- if (PyType_Ready(&py_view_panel_type) < 0)
+ py_view_panel_type->tp_basicsize = py_view_panel_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_view_panel_type) != 0)
+ return false;
+
+ if (!py_view_panel_define_constants(py_view_panel_type))
return false;
- Py_INCREF(&py_view_panel_type);
- ret = PyModule_AddObject(module, "ViewPanel", (PyObject *)&py_view_panel_type);
+ Py_INCREF(py_view_panel_type);
+ ret = PyModule_AddObject(module, "ViewPanel", (PyObject *)py_view_panel_type);
+ if (ret != 0) return false;
- pygobject_register_class(module, "GtkViewPanel", GTK_TYPE_VIEW_PANEL, &py_view_panel_type,
- Py_BuildValue("(O)", py_view_panel_type.tp_base));
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "ViewPanel", GTK_TYPE_VIEW_PANEL, py_view_panel_type,
+ Py_BuildValue("(O)", py_view_panel_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/gtkext/viewpanel.h b/plugins/pychrysa/gtkext/viewpanel.h
index 175546b..7a349f8 100644
--- a/plugins/pychrysa/gtkext/viewpanel.h
+++ b/plugins/pychrysa/gtkext/viewpanel.h
@@ -22,8 +22,8 @@
*/
-#ifndef _PLUGINS_PYCHRYSA_GTKEXT_MODULE_VIEW_PANEL_H
-#define _PLUGINS_PYCHRYSA_GTKEXT_MODULE_VIEW_PANEL_H
+#ifndef _PLUGINS_PYCHRYSA_GTKEXT_VIEWPANEL_H
+#define _PLUGINS_PYCHRYSA_GTKEXT_VIEWPANEL_H
#include <Python.h>
@@ -31,9 +31,12 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_view_panel_type(void);
+
/* Prend en charge l'objet 'pychrysalide.gtkext.ViewPanel'. */
bool register_python_view_panel(PyObject *module);
-#endif /* _PLUGINS_PYCHRYSA_GTKEXT_MODULE_VIEW_PANEL_H */
+#endif /* _PLUGINS_PYCHRYSA_GTKEXT_VIEWPANEL_H */
diff --git a/plugins/pychrysa/gui/editem.c b/plugins/pychrysa/gui/editem.c
index 7a40a04..6db03ce 100644
--- a/plugins/pychrysa/gui/editem.c
+++ b/plugins/pychrysa/gui/editem.c
@@ -90,7 +90,7 @@ static void _update_editor_item_for_binary_python_wrapper(GEditorItem *item, GLo
* des éléments d'éditeur, via py_editor_item_register(), donc son compteur
* de références doit le maintenir en vie.
*
- * On peut donc le récupérer directement depuis l'instane GLib, sans passer
+ * On peut donc le récupérer directement depuis l'instance GLib, sans passer
* par la procédure de pygobject, qui obligerait à connaître le type précis
* de l'instance GLib manipulée.
*/
@@ -355,21 +355,18 @@ static PyObject *py_editor_item_register(PyObject *self, PyObject *args)
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.gui.EditorItem'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_editor_item(PyObject *module)
+PyTypeObject *get_python_editor_item_type(void)
{
- PyObject *parent_mod; /* Module Python-GObject */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_editor_item_methods[] = {
{
"update_for_binary", (PyCFunction)py_editor_item_update_for_binary,
@@ -387,19 +384,19 @@ bool register_python_editor_item(PyObject *module)
"Called by Chrysalide on each view content change, if the item is registered."
},
{
- "get_current_binary", (PyCFunction)py_editor_item_get_current_binary,
+ "get_current_binary()", (PyCFunction)py_editor_item_get_current_binary,
METH_NOARGS,
- "Provide the current binary."
+ "get_current_binary($self, /)\n--\n\nProvide the current binary."
},
{
"get_current_view", (PyCFunction)py_editor_item_get_current_view,
METH_NOARGS,
- "Provide the current binary view."
+ "get_current_view($self, /)\n--\n\nProvide the current binary view."
},
{
"register", (PyCFunction)py_editor_item_register,
METH_NOARGS,
- "Register the item as editor item."
+ "register($self, /)\n--\n\nRegister the item as editor item."
},
{ NULL }
};
@@ -410,32 +407,58 @@ bool register_python_editor_item(PyObject *module)
static PyTypeObject py_editor_item_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.gui.EditorItem",
- .tp_basicsize = sizeof(PyGObject),
.tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
.tp_doc = "PyChrysalide editor item",
.tp_methods = py_editor_item_methods,
- .tp_getset = py_editor_item_getseters
+ .tp_getset = py_editor_item_getseters,
};
- parent_mod = PyImport_ImportModule("gobject");
- if (parent_mod == NULL) return false;
+ return &py_editor_item_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.gui.EditorItem'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_editor_item(PyObject *module)
+{
+ PyTypeObject *py_editor_item_type; /* Type Python 'LoadedBinary' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_editor_item_type = get_python_editor_item_type();
- py_editor_item_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "GObject");
- Py_DECREF(parent_mod);
+ py_editor_item_type->tp_base = &PyGObject_Type;
+ py_editor_item_type->tp_basicsize = py_editor_item_type->tp_base->tp_basicsize;
- if (PyType_Ready(&py_editor_item_type) < 0)
+ if (PyType_Ready(py_editor_item_type) != 0)
return false;
- Py_INCREF(&py_editor_item_type);
- ret = PyModule_AddObject(module, "EditorItem", (PyObject *)&py_editor_item_type);
+ Py_INCREF(py_editor_item_type);
+ ret = PyModule_AddObject(module, "EditorItem", (PyObject *)py_editor_item_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "EditorItem", G_TYPE_EDITOR_ITEM, py_editor_item_type,
+ Py_BuildValue("(O)", py_editor_item_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/gui/editem.h b/plugins/pychrysa/gui/editem.h
index 197efd5..329a79e 100644
--- a/plugins/pychrysa/gui/editem.h
+++ b/plugins/pychrysa/gui/editem.h
@@ -31,8 +31,11 @@
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_editor_item_type(void);
+
/* Prend en charge l'objet 'pychrysalide.gui.EditorItem'. */
-bool register_python_editor_item(PyObject *module);
+bool register_python_editor_item(PyObject *);
diff --git a/plugins/pychrysa/gui/module.c b/plugins/pychrysa/gui/module.c
index 605877f..0c5403e 100644
--- a/plugins/pychrysa/gui/module.c
+++ b/plugins/pychrysa/gui/module.c
@@ -25,6 +25,10 @@
#include "module.h"
+#include <assert.h>
+
+
+
#include "editem.h"
#include "panels/module.h"
@@ -44,27 +48,46 @@
bool add_gui_module_to_python_module(PyObject *super)
{
- bool result;
- PyObject *module;
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyMethodDef py_gui_methods[] = {
- { NULL }
+ static PyModuleDef py_chrysalide_gui_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "pychrysalide.gui",
+ .m_doc = "Python module for the Chrysalide GUI",
+
+ .m_size = -1,
+
};
- module = Py_InitModule("pychrysalide.gui", py_gui_methods);
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_gui_module);
if (module == NULL) return false;
- Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.gui", module);
+ ret = PyState_AddModule(super, &py_chrysalide_gui_module);
+ if (ret != 0) goto loading_failed;
- result = (ret == 0);
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.gui");
+ if (ret != 0) goto loading_failed;
+
+ Py_INCREF(module);
+ ret = PyModule_AddObject(super, "gui", module);
+ if (ret != 0) goto loading_failed;
- if (ret != 0) /* ... */;
+ result = true;
result &= register_python_editor_item(module);
+
result &= add_gui_panels_module_to_python_module(module);
- return true;
+ loading_failed:
+
+ assert(result);
+
+ return result;
}
diff --git a/plugins/pychrysa/gui/panels/log.c b/plugins/pychrysa/gui/panels/log.c
index 00f4e9e..ba68fe9 100644
--- a/plugins/pychrysa/gui/panels/log.c
+++ b/plugins/pychrysa/gui/panels/log.c
@@ -25,11 +25,14 @@
#include "log.h"
-
#include <pygobject.h>
-#include "../../quirks.h"
+#include <gui/panels/log.h>
+
+
+#include "panel.h"
+#include "../../helpers.h"
@@ -37,7 +40,7 @@
static PyObject *py_log_panel_log_message(PyObject *, PyObject *);
/* Définit les constantes pour les types de message. */
-static bool define_python_log_constants(PyObject *);
+static bool define_python_log_constants(PyTypeObject *);
@@ -90,7 +93,7 @@ static PyObject *py_log_panel_log_message(PyObject *self, PyObject *args)
/******************************************************************************
* *
-* Paramètres : dict = dictionnaire à compléter. *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
* *
* Description : Définit les constantes pour les types de message. *
* *
@@ -100,52 +103,42 @@ static PyObject *py_log_panel_log_message(PyObject *self, PyObject *args)
* *
******************************************************************************/
-static bool define_python_log_constants(PyObject *dict)
+static bool define_python_log_constants(PyTypeObject *obj_type)
{
- int ret; /* Bilan d'un ajout */
-
- ret = PyDict_SetItemString(dict, "LMT_INFO", PyInt_FromLong(LMT_INFO));
- if (ret == -1) return false;
-
- ret = PyDict_SetItemString(dict, "LMT_BAD_BINARY", PyInt_FromLong(LMT_BAD_BINARY));
- if (ret == -1) return false;
+ bool result; /* Bilan à retourner */
- ret = PyDict_SetItemString(dict, "LMT_PROCESS", PyInt_FromLong(LMT_PROCESS));
- if (ret == -1) return false;
+ result = true;
- ret = PyDict_SetItemString(dict, "LMT_ERROR", PyInt_FromLong(LMT_ERROR));
- if (ret == -1) return false;
+ result &= PyDict_AddIntMacro(obj_type, LMT_INFO);
+ result &= PyDict_AddIntMacro(obj_type, LMT_BAD_BINARY);
+ result &= PyDict_AddIntMacro(obj_type, LMT_PROCESS);
+ result &= PyDict_AddIntMacro(obj_type, LMT_ERROR);
+ result &= PyDict_AddIntMacro(obj_type, LMT_WARNING);
- ret = PyDict_SetItemString(dict, "LMT_WARNING", PyInt_FromLong(LMT_WARNING));
- if (ret == -1) return false;
-
- return true;
+ return result;
}
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.gui.panels.LogPanel'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_log_panel(PyObject *module)
+PyTypeObject *get_python_log_panel_type(void)
{
- //PyObject *parent_mod; /* Module Python-EditorItem */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_log_panel_methods[] = {
{
"log_message", (PyCFunction)py_log_panel_log_message,
METH_VARARGS | METH_STATIC,
- "Display a message in the log window."
+ "log_message(type, msg, /)\n--\n\nDisplay a message in the log window, if any."
},
{ NULL }
};
@@ -156,35 +149,62 @@ bool register_python_log_panel(PyObject *module)
static PyTypeObject py_log_panel_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.gui.panels.LogPanel",
- .tp_basicsize = sizeof(PyObject),
+ .tp_basicsize = sizeof(PyGObject),
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
+ .tp_flags = Py_TPFLAGS_DEFAULT,
.tp_doc = "PyChrysalide log panel",
.tp_methods = py_log_panel_methods,
- .tp_getset = py_log_panel_getseters,
+ .tp_getset = py_log_panel_getseters
};
- /*
- parent_mod = PyImport_ImportModule("pychrysalide.gui.panels");
- if (parent_mod == NULL) return false;
-
- py_log_panel_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "PanelItem");
- Py_DECREF(parent_mod);
- */
- if (PyType_Ready(&py_log_panel_type) < 0)
+
+ return &py_log_panel_type;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.gui.panels.LogPanel'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_log_panel(PyObject *module)
+{
+ PyTypeObject *py_log_panel_type; /* Type Python 'LoadedBinary' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_log_panel_type = get_python_log_panel_type();
+
+ py_log_panel_type->tp_base = get_python_panel_item_type();
+ py_log_panel_type->tp_basicsize = py_log_panel_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_log_panel_type) != 0)
return false;
- if (!define_python_log_constants(py_log_panel_type.tp_dict))
+ if (!define_python_log_constants(py_log_panel_type))
return false;
- Py_INCREF(&py_log_panel_type);
- ret = PyModule_AddObject(module, "LogPanel", (PyObject *)&py_log_panel_type);
+ Py_INCREF(py_log_panel_type);
+ ret = PyModule_AddObject(module, "LogPanel", (PyObject *)py_log_panel_type);
+ if (ret != 0) return false;
- return (ret == 0);
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "LogPanel", G_TYPE_LOG_PANEL, py_log_panel_type,
+ Py_BuildValue("(O)", py_log_panel_type->tp_base));
+
+ return true;
}
diff --git a/plugins/pychrysa/gui/panels/log.h b/plugins/pychrysa/gui/panels/log.h
index 08b1ae2..9b67e5a 100644
--- a/plugins/pychrysa/gui/panels/log.h
+++ b/plugins/pychrysa/gui/panels/log.h
@@ -29,12 +29,13 @@
#include <Python.h>
#include <stdbool.h>
-#include <gui/panels/log.h>
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_log_panel_type(void);
/* Prend en charge l'objet 'pychrysalide.gui.panels.LogPanel'. */
-bool register_python_log_panel(PyObject *module);
+bool register_python_log_panel(PyObject *);
diff --git a/plugins/pychrysa/gui/panels/module.c b/plugins/pychrysa/gui/panels/module.c
index bd13cd9..ca8845d 100644
--- a/plugins/pychrysa/gui/panels/module.c
+++ b/plugins/pychrysa/gui/panels/module.c
@@ -1,6 +1,6 @@
/* Chrysalide - Outil d'analyse de fichiers binaires
- * module.c - intégration du répertoire arch en tant que module
+ * module.c - intégration du répertoire panels en tant que module
*
* Copyright (C) 2012-2013 Cyrille Bagard
*
@@ -25,6 +25,9 @@
#include "module.h"
+#include <assert.h>
+
+
#include "log.h"
#include "panel.h"
@@ -44,27 +47,45 @@
bool add_gui_panels_module_to_python_module(PyObject *super)
{
- bool result;
- PyObject *module;
+ bool result; /* Bilan à retourner */
+ PyObject *module; /* Sous-module mis en place */
int ret; /* Bilan d'un appel */
- static PyMethodDef py_gui_panels_methods[] = {
- { NULL }
+ static PyModuleDef py_chrysalide_panels_module = {
+
+ .m_base = PyModuleDef_HEAD_INIT,
+
+ .m_name = "gui.analysis.panels",
+ .m_doc = "Python module for Chrysalide.gui.panels",
+
+ .m_size = -1,
+
};
- module = Py_InitModule("pychrysalide.gui.panels", py_gui_panels_methods);
+ result = false;
+
+ module = PyModule_Create(&py_chrysalide_panels_module);
if (module == NULL) return false;
- Py_INCREF(module);
- ret = PyModule_AddObject(super, "pychrysalide.gui.panels", module);
+ ret = PyState_AddModule(super, &py_chrysalide_panels_module);
+ if (ret != 0) goto loading_failed;
+
+ ret = _PyImport_FixupBuiltin(module, "pychrysalide.gui.panels");
+ if (ret != 0) goto loading_failed;
- result = (ret == 0);
+ Py_INCREF(module);
+ ret = PyModule_AddObject(super, "panels", module);
+ if (ret != 0) goto loading_failed;
- if (ret != 0) /* ... */;
+ result = true;
result &= register_python_panel_item(module);
result &= register_python_log_panel(module);
- return true;
+ loading_failed:
+
+ assert(result);
+
+ return result;
}
diff --git a/plugins/pychrysa/gui/panels/module.h b/plugins/pychrysa/gui/panels/module.h
index c75a475..15d46a5 100644
--- a/plugins/pychrysa/gui/panels/module.h
+++ b/plugins/pychrysa/gui/panels/module.h
@@ -1,6 +1,6 @@
/* Chrysalide - Outil d'analyse de fichiers binaires
- * module.h - prototypes pour l'intégration du répertoire gui.panels en tant que module
+ * module.h - prototypes pour l'intégration du répertoire panels en tant que module
*
* Copyright (C) 2012 Cyrille Bagard
*
diff --git a/plugins/pychrysa/gui/panels/panel.c b/plugins/pychrysa/gui/panels/panel.c
index 826982f..e713cc0 100644
--- a/plugins/pychrysa/gui/panels/panel.c
+++ b/plugins/pychrysa/gui/panels/panel.c
@@ -28,18 +28,24 @@
#include <pygobject.h>
-#include "../../quirks.h"
+#include <gui/panels/panel.h>
+
+
+#include "../editem.h"
/* Crée un nouvel objet Python de type 'PanelItem'. */
+#if 0
static PyObject *py_panel_item_new(PyTypeObject *, PyObject *, PyObject *);
+#endif
/* Place un panneau dans l'ensemble affiché. */
static PyObject *py_panel_item_dock(PyObject *, PyObject *);
+#if 0
/******************************************************************************
* *
* Paramètres : type = type de l'objet à instancier. *
@@ -110,6 +116,7 @@ PyObject *_py_panel_item_from_c(GPanelItem *item, PyTypeObject *type)
return pygobject_new(G_OBJECT(item));
}
+#endif
/******************************************************************************
@@ -138,40 +145,25 @@ static PyObject *py_panel_item_dock(PyObject *self, PyObject *args)
}
-
-
-
-
-
-
-
-
-
-
-
-
/******************************************************************************
* *
-* Paramètres : module = module dont la définition est à compléter. *
+* Paramètres : - *
* *
-* Description : Prend en charge l'objet 'pychrysalide.gui.panels.PanelItem'. *
+* Description : Fournit un accès à une définition de type à diffuser. *
* *
-* Retour : Bilan de l'opération. *
+* Retour : Définition d'objet pour Python. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool register_python_panel_item(PyObject *module)
+PyTypeObject *get_python_panel_item_type(void)
{
- PyObject *parent_mod; /* Module Python-EditorItem */
- int ret; /* Bilan d'un appel */
-
static PyMethodDef py_panel_item_methods[] = {
{
"dock", (PyCFunction)py_panel_item_dock,
METH_NOARGS,
- "Display the panel item in the right place."
+ "dock($self, /)\n--\n\nDisplay the panel item in the right place."
},
{ NULL }
};
@@ -182,34 +174,61 @@ bool register_python_panel_item(PyObject *module)
static PyTypeObject py_panel_item_type = {
- PyObject_HEAD_INIT(NULL)
+ PyVarObject_HEAD_INIT(NULL, 0)
.tp_name = "pychrysalide.gui.panels.PanelItem",
.tp_basicsize = sizeof(PyGObject),
.tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
- .tp_doc = "PyChrysalide panel item",
+ .tp_doc = "PyChrysalide panel item.",
.tp_methods = py_panel_item_methods,
.tp_getset = py_panel_item_getseters,
- .tp_new = (newfunc)py_panel_item_new,
- .tp_init = (initproc)pychrysalide_allow_args_for_gobjects
+ //.tp_new = (newfunc)py_panel_item_new,
+ //.tp_init = (initproc)pychrysalide_allow_args_for_gobjects
};
- parent_mod = PyImport_ImportModule("pychrysalide.gui");
- if (parent_mod == NULL) return false;
+ return &py_panel_item_type;
- py_panel_item_type.tp_base = (PyTypeObject *)PyObject_GetAttrString(parent_mod, "EditorItem");
- Py_DECREF(parent_mod);
+}
- if (PyType_Ready(&py_panel_item_type) < 0)
+
+/******************************************************************************
+* *
+* Paramètres : module = module dont la définition est à compléter. *
+* *
+* Description : Prend en charge l'objet 'pychrysalide.gui.panels.PanelItem'. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool register_python_panel_item(PyObject *module)
+{
+ PyTypeObject *py_panel_item_type; /* Type Python 'LoadedBinary' */
+ int ret; /* Bilan d'un appel */
+ PyObject *dict; /* Dictionnaire du module */
+
+ py_panel_item_type = get_python_panel_item_type();
+
+ py_panel_item_type->tp_base = get_python_editor_item_type();
+ py_panel_item_type->tp_basicsize = py_panel_item_type->tp_base->tp_basicsize;
+
+ if (PyType_Ready(py_panel_item_type) != 0)
return false;
- Py_INCREF(&py_panel_item_type);
- ret = PyModule_AddObject(module, "PanelItem", (PyObject *)&py_panel_item_type);
+ Py_INCREF(py_panel_item_type);
+ ret = PyModule_AddObject(module, "PanelItem", (PyObject *)py_panel_item_type);
+ if (ret != 0) return false;
+
+ dict = PyModule_GetDict(module);
+ pygobject_register_class(dict, "PanelItem", G_TYPE_PANEL_ITEM, py_panel_item_type,
+ Py_BuildValue("(O)", py_panel_item_type->tp_base));
- return (ret == 0);
+ return true;
}
diff --git a/plugins/pychrysa/gui/panels/panel.h b/plugins/pychrysa/gui/panels/panel.h
index 4c678b1..ecbee78 100644
--- a/plugins/pychrysa/gui/panels/panel.h
+++ b/plugins/pychrysa/gui/panels/panel.h
@@ -29,17 +29,13 @@
#include <Python.h>
#include <stdbool.h>
-#include <gui/panels/panel.h>
-
-/* Crée un nouvel objet Python de type 'PanelItem'. */
-PyObject *_py_panel_item_from_c(GPanelItem *, PyTypeObject *);
-
-#define py_panel_item_from_c(item) _py_panel_item_from_c(item, NULL)
+/* Fournit un accès à une définition de type à diffuser. */
+PyTypeObject *get_python_panel_item_type(void);
/* Prend en charge l'objet 'pychrysalide.gui.panels.PanelItem'. */
-bool register_python_panel_item(PyObject *module);
+bool register_python_panel_item(PyObject *);
diff --git a/plugins/pychrysa/helpers.c b/plugins/pychrysa/helpers.c
index e2fc13a..d344a7f 100644
--- a/plugins/pychrysa/helpers.c
+++ b/plugins/pychrysa/helpers.c
@@ -27,6 +27,37 @@
/******************************************************************************
* *
+* Paramètres : func = fonction Python à appeler. *
+* args = arguments à associer à l'opération. *
+* *
+* Description : Appelle une routine Python. *
+* *
+* Retour : Retour obtenu ou NULL si erreur. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+PyObject *_run_python_method(PyObject *func, PyObject *args)
+{
+ PyObject *result; /* Bilan à retourner */
+
+ result = NULL;
+
+ if (PyCallable_Check(func))
+ {
+ result = PyObject_CallObject(func, args);
+ if (result == NULL) PyErr_Print();
+ }
+ else if (PyErr_Occurred()) PyErr_Print();
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : target = propriétaire de la routine visée. *
* method = désignation de la fonction à appeler. *
* args = arguments à associer à l'opération. *
@@ -58,32 +89,64 @@ PyObject *run_python_method(PyObject *module, const char *method, PyObject *args
}
+/******************************************************************************
+* *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
+* key = désignation de la constante à intégrer. *
+* value = valeur de la constante à intégrer. *
+* *
+* Description : Ajoute une constante au dictionnaire d'un type Python donné. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool PyDict_AddIntConstant(PyTypeObject *obj_type, const char *key, long value)
+{
+ bool result; /* Bilan à retourner */
+ PyObject *item; /* Nouvel élément à insérer */
+ int ret; /* Bilan d'un ajout */
+
+ item = PyLong_FromLong(value);
+
+ ret = PyDict_SetItemString(obj_type->tp_dict, key, item);
+ result = (ret != -1);
+
+ Py_DECREF(item);
+
+ return result;
+
+}
+
/******************************************************************************
* *
-* Paramètres : func = fonction Python à appeler. *
-* args = arguments à associer à l'opération. *
+* Paramètres : obj_type = type dont le dictionnaire est à compléter. *
+* key = désignation de la constante à intégrer. *
+* value = valeur de la constante à intégrer. *
* *
-* Description : Appelle une routine Python. *
+* Description : Ajoute une constante au dictionnaire d'un type Python donné. *
* *
-* Retour : Retour obtenu ou NULL si erreur. *
+* Retour : Bilan de l'opération. *
* *
* Remarques : - *
* *
******************************************************************************/
-PyObject *_run_python_method(PyObject *func, PyObject *args)
+bool PyDict_AddStringConstant(PyTypeObject *obj_type, const char *key, const char *value)
{
- PyObject *result; /* Bilan à retourner */
+ bool result; /* Bilan à retourner */
+ PyObject *item; /* Nouvel élément à insérer */
+ int ret; /* Bilan d'un ajout */
- result = NULL;
+ item = PyUnicode_FromString(value);
- if (PyCallable_Check(func))
- {
- result = PyObject_CallObject(func, args);
- if (result == NULL) PyErr_Print();
- }
- else if (PyErr_Occurred()) PyErr_Print();
+ ret = PyDict_SetItemString(obj_type->tp_dict, key, item);
+ result = (ret != -1);
+
+ Py_DECREF(item);
return result;
diff --git a/plugins/pychrysa/helpers.h b/plugins/pychrysa/helpers.h
index f957b9d..d47d8e7 100644
--- a/plugins/pychrysa/helpers.h
+++ b/plugins/pychrysa/helpers.h
@@ -26,14 +26,35 @@
#include <Python.h>
+#include <stdbool.h>
/* Appelle une routine Python. */
-PyObject *run_python_method(PyObject *, const char *, PyObject *);
+PyObject *_run_python_method(PyObject *, PyObject *);
/* Appelle une routine Python. */
-PyObject *_run_python_method(PyObject *, PyObject *);
+PyObject *run_python_method(PyObject *, const char *, PyObject *);
+
+/* Ajoute une constante au dictionnaire d'un type Python donné. */
+bool PyDict_AddIntConstant(PyTypeObject *, const char *, long);
+
+/* Ajoute une constante au dictionnaire d'un type Python donné. */
+bool PyDict_AddStringConstant(PyTypeObject *, const char *, const char *);
+
+
+#define PyDict_AddIntMacro(tp, c) PyDict_AddIntConstant(tp, #c, c)
+#define PyDict_AddStringMacro(tp, c) PyDict_AddStringConstant(tp, #c, c)
+
+
+/**
+ * Quelque chose est mal fait au niveau de l'abstraction GObject.
+ * Du coup, Py_TPFLAGS_IS_ABSTRACT n'est pas pris en compte.
+ * On force alors la méthode de base pour obtenir un traitement correct.
+ *
+ * Cf. http://stackoverflow.com/questions/20432335/can-python-abstract-base-classes-inherit-from-c-extensions
+ */
+#define APPLY_ABSTRACT_FLAG(tp) tp->tp_new = PyBaseObject_Type.tp_new
diff --git a/plugins/pychrysa/linsyscalls/oidapgi.py b/plugins/pychrysa/linsyscalls/oidapgi.py
deleted file mode 100755
index dd4e010..0000000
--- a/plugins/pychrysa/linsyscalls/oidapgi.py
+++ /dev/null
@@ -1,28 +0,0 @@
-#!/usr/bin/python
-
-import pyoida
-#import oidaline
-from pyoida import Noddy
-
-
-class OpenIDAPlugin:
- """A simple example class"""
-
-
-
-
-
-if __name__ == "__main__":
- print "OpenIDA PlugIn"
-
-
- print "Hello World\n",
-
- pyoida.system("ls -lh")
-
- test = Noddy("first", "last")
-
- print test.name()
-
- #oidaline.echo()
-
diff --git a/plugins/pychrysa/pychrysa.c b/plugins/pychrysa/pychrysa.c
index 00856f3..367895d 100644
--- a/plugins/pychrysa/pychrysa.c
+++ b/plugins/pychrysa/pychrysa.c
@@ -24,6 +24,8 @@
#include "pychrysa.h"
+
+
#if 0
#include <dirent.h>
@@ -57,32 +59,6 @@
-static PyMethodDef SpamMethods[] = {
- {NULL, NULL, 0, NULL} /* Sentinel */
-};
-
-
-
-
-
-/******************************************************************************
-* *
-* Paramètres : - *
-* *
-* Description : Précise le nom associé au greffon. *
-* *
-* Retour : Nom à libérer de la mémoire. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-char *get_plugin_name(void)
-{
- return strdup("PyChrysalide");
-
-}
-
/******************************************************************************
* *
@@ -193,146 +169,8 @@ bool init_plugin(GPluginModule *plugin, GObject *ref)
}
-/******************************************************************************
-* *
-* Paramètres : plugin = instance représentant le greffon en déchargement. *
-* *
-* Description : Libère le greffon permettant l'usage de Python. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-void exit_plugin(GPluginModule *plugin)
-{
- /* FIXME */
- //Py_Finalize();
-}
-
-
-/******************************************************************************
-* *
-* Paramètres : plugin = greffon à consulter. *
-* *
-* Description : Indique les opérations offertes par un greffon donné. *
-* *
-* Retour : Action(s) offerte(s) par le greffon. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-PluginAction get_plugin_action(const GPluginModule *plugin)
-{
- PluginAction result; /* Combinaison à retourner */
-
- //result = PGA_NONE;
-
- return result;
-
-}
-
-
-
-
-
-#if PY_VERSION_HEX >= 0x03000000
-
-/******************************************************************************
-* *
-* Paramètres : - *
-* *
-* Description : Point d'entrée pour l'initialisation de Python. *
-* *
-* Retour : ? *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-PyMODINIT_FUNC initpychrysa/*PyInit_pychrysa*/(void)
-{
- PyObject *module;
-
- //init_pygobject();
- //init_pygtk();
-
- pychrysalide_init_quirks();
-
- module = Py_InitModule("pychrysalide", SpamMethods);
-
- //add_analysis_roptions_to_python_module(module);
- add_analysis_module_to_python_module(module);
- add_arch_module_to_python_module(module);
- add_debug_module_to_python_module(module);
- add_format_module_to_python_module(module);
- add_glibext_module_to_python_module(module);
- add_gtkext_module_to_python_module(module);
- add_gui_module_to_python_module(module);
-
- add_plugin_to_python_module(module);
-
-
- /*
-
-
-
- static struct PyModuleDef spammodule = {
- PyModuleDef_HEAD_INIT,
- "pychrysalide",
- "pychrysalide_doc",
- -1,
- SpamMethods
- };
-
- PyModule_Create(&spammodule);
-
- */
-
-}
-
-#else
-
-/******************************************************************************
-* *
-* Paramètres : - *
-* *
-* Description : Point d'entrée pour l'initialisation de Python. *
-* *
-* Retour : ? *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-PyMODINIT_FUNC initpychrysa(void)
-{
- PyObject *module;
-
- init_pygobject();
- //init_pygtk();
-
- pychrysalide_init_quirks();
-
- module = Py_InitModule("pychrysalide", SpamMethods);
-
- //add_analysis_roptions_to_python_module(module);
- add_analysis_module_to_python_module(module);
- add_arch_module_to_python_module(module);
- add_debug_module_to_python_module(module);
- add_format_module_to_python_module(module);
- add_glibext_module_to_python_module(module);
- add_gtkext_module_to_python_module(module);
- add_gui_module_to_python_module(module);
-
- add_plugin_to_python_module(module);
-
-}
-
-#endif
@@ -356,8 +194,12 @@ PyMODINIT_FUNC initpychrysa(void)
#include "analysis/module.h"
#include "arch/module.h"
+#include "common/module.h"
#include "core/module.h"
+#include "format/module.h"
#include "glibext/module.h"
+#include "gtkext/module.h"
+#include "gui/module.h"
@@ -537,6 +379,20 @@ static bool is_current_abi_suitable(void)
* Remarques : - *
* *
******************************************************************************/
+#include <gtkext/support.h> // REMME
+#include <glibext/delayed.h>
+
+#define PYCHRYSALIDE_DOC \
+ "PyChrysalide is a module containing Chrysalide's features and designed for Python users.\n" \
+ "\n" \
+ "The whole API is defined in a single library named 'pychrysalide.so' and can be used in two ways:\n" \
+ "* either from the Chrysalide's GUI, by registering hooks or GLib signals.\n" \
+ "* or from a shell command line, by setting PYTHONPATH to point to the directory containing the library.\n" \
+ "\n" \
+ "In both cases, it is a good start point to have a look at already existing plugins to quickly learn " \
+ "how the API works.\n" \
+ "\n" \
+ "These plugins are located in the 'plugins/python' directory."
PyMODINIT_FUNC PyInit_pychrysalide(void)
{
@@ -548,11 +404,11 @@ PyMODINIT_FUNC PyInit_pychrysalide(void)
{ "version", py_chrysalide_version,
METH_NOARGS,
- "Provide the revision number of Chrysalide."
+ "version(/)\n--\n\nProvide the revision number of Chrysalide."
},
{ "mod_version", py_chrysalide_mod_version,
METH_NOARGS,
- "Provide the revision number of Chrysalide module for Python."
+ "mod_version(/)\n--\n\nProvide the revision number of Chrysalide module for Python."
},
{ NULL }
@@ -563,7 +419,7 @@ PyMODINIT_FUNC PyInit_pychrysalide(void)
.m_base = PyModuleDef_HEAD_INIT,
.m_name = "pychrysalide",
- .m_doc = "Python module for Chrysalide",
+ .m_doc = PYCHRYSALIDE_DOC,
.m_size = -1,
@@ -576,6 +432,26 @@ PyMODINIT_FUNC PyInit_pychrysalide(void)
//init_all_processors();
//init_all_formats();
+ do
+ {
+ int argc = 0;
+ //char *argv[] = { NULL };
+
+ /* Initialisation de GTK */
+ g_set_prgname("Chrysalide");
+ setlocale (LC_ALL, "");
+ gtk_init(&argc, NULL/*&argv-*/);
+
+ } while (0);
+
+ add_pixmap_directory(PACKAGE_DATA_DIR);
+ add_pixmap_directory(PACKAGE_SOURCE_DIR G_DIR_SEPARATOR_S "pixmaps");
+
+ init_work_queue(NULL/* !! */);
+
+
+ ////////////////////////
+
if (!is_current_abi_suitable())
return NULL;
@@ -606,8 +482,12 @@ PyMODINIT_FUNC PyInit_pychrysalide(void)
status &= add_analysis_module_to_python_module(result);
status &= add_arch_module_to_python_module(result);
+ status &= add_common_module_to_python_module(result);
status &= add_core_module_to_python_module(result);
+ status &= add_format_module_to_python_module(result);
status &= add_glibext_module_to_python_module(result);
+ status &= add_gtkext_module_to_python_module(result);
+ status &= add_gui_module_to_python_module(result);
if (!status)
{
diff --git a/src/analysis/binary.c b/src/analysis/binary.c
index e5b9a46..d7682cd 100644
--- a/src/analysis/binary.c
+++ b/src/analysis/binary.c
@@ -941,7 +941,7 @@ const char *g_loaded_binary_get_name(const GLoadedBinary *binary, bool full)
* *
* Description : Fournit le format de fichier reconnu dans le contenu binaire.*
* *
-* Retour : Adresse du format reconnu. *
+* Retour : Instance du format reconnu. *
* *
* Remarques : - *
* *
@@ -962,7 +962,7 @@ GExeFormat *g_loaded_binary_get_format(const GLoadedBinary *binary)
* *
* Description : Fournit le processeur de l'architecture liée au binaire. *
* *
-* Retour : Adresse du processeur associé. *
+* Retour : Instance du processeur associé. *
* *
* Remarques : - *
* *
diff --git a/src/analysis/disass/area.c b/src/analysis/disass/area.c
index a7c44c0..dd35eaa 100644
--- a/src/analysis/disass/area.c
+++ b/src/analysis/disass/area.c
@@ -1568,27 +1568,6 @@ size_t find_memory_area_by_addr(mem_area *list, size_t count, const vmpa2t *addr
}
- /*
- if (addr->virtual == 0x8540)
- {
- size_t i;
-
- for (i = 0; i < count; i++)
- printf("[%zu] AREAS :: 0x%08x + %x\n", i,
- (unsigned int)list[i].range.addr.virtual,
- (unsigned int)list[i].range.length);
-
-
-
-
- printf(" == CMP == 0x%08x / 0x%08x\n",
- (unsigned int)addr->physical,
- (unsigned int)addr->virtual);
-
- }
- */
-
-
found = bsearch(addr, list, count, sizeof(mem_area), (__compar_fn_t)find_mem_area);
result = (found != NULL ? found - list : count);
diff --git a/src/arch/instruction.c b/src/arch/instruction.c
index b895af0..d6bf183 100644
--- a/src/arch/instruction.c
+++ b/src/arch/instruction.c
@@ -250,9 +250,6 @@ void g_arch_instruction_set_hook(GArchInstruction *instr, InstrProcessHook type,
void g_arch_instruction_call_hook(GArchInstruction *instr, InstrProcessHook type, GArchProcessor *proc, GProcContext *context, GBinFormat *format)
{
- if (instr->range.addr.virtual == 0x83c2)
- printf(" [%u] HAS BRANCH ? %p\n", (unsigned int)type, instr->hooks[type]);
-
assert(type < IPH_COUNT);
if (instr->hooks[type] != NULL)
@@ -671,7 +668,7 @@ bool g_arch_instruction_has_sources(const GArchInstruction *instr)
* *
* Description : Fournit les origines d'une instruction donnée. *
* *
-* Retour : Nombre de ces destinations. *
+* Retour : Nombre de ces origines. *
* *
* Remarques : - *
* *
diff --git a/src/arch/processor.c b/src/arch/processor.c
index 86e7845..95176e9 100644
--- a/src/arch/processor.c
+++ b/src/arch/processor.c
@@ -327,6 +327,9 @@ void g_arch_processor_set_disassembled_instructions(GArchProcessor *proc, GArchI
{
GArchInstruction *iter; /* Boucle de parcours */
+ /* TODO : vider une éventuelle liste existante */
+ /* TODO : incrémenter les références (cf. code Python) */
+
ainstr_list_for_each(iter, list)
{
/* Mise à disposition de d'avantage d'espace */
diff --git a/src/arch/vmpa.c b/src/arch/vmpa.c
index b10b007..d966341 100644
--- a/src/arch/vmpa.c
+++ b/src/arch/vmpa.c
@@ -913,7 +913,7 @@ bool mrange_contains_addr_inclusive(const mrange_t *range, const vmpa2t *addr)
* Paramètres : range = zone mémoire à consulter. *
* addr = localisation mémoire à déterminer. *
* *
-* Description : Calcule la position extérieure final d'une couverture. *
+* Description : Calcule la position extérieure finale d'une couverture. *
* *
* Retour : - *
* *
diff --git a/src/arch/vmpa.h b/src/arch/vmpa.h
index 4611ebf..368b765 100644
--- a/src/arch/vmpa.h
+++ b/src/arch/vmpa.h
@@ -193,7 +193,7 @@ bool mrange_contains_addr(const mrange_t *, const vmpa2t *);
/* Indique si une localisation est incluse dans une zone ou non. */
bool mrange_contains_addr_inclusive(const mrange_t *, const vmpa2t *);
-/* Calcule la position extérieure final d'une couverture. */
+/* Calcule la position extérieure finale d'une couverture. */
void compute_mrange_end_addr(const mrange_t *, vmpa2t *);
/* Transforme un emplacement physique en chaîne de caractères. */
diff --git a/src/format/dex/dex.h b/src/format/dex/dex.h
index aca6cef..7f427a3 100755
--- a/src/format/dex/dex.h
+++ b/src/format/dex/dex.h
@@ -57,6 +57,15 @@ GType g_dex_format_get_type(void);
/* Prend en charge un nouveau format DEX. */
GBinFormat *g_dex_format_new(const bin_t *, off_t);
+/* Redéfinition : classe issue du code source (instance) */
+typedef struct _GDexClass GDexClass;
+
+/* Dénombre le nombre de classes trouvées. */
+size_t g_dex_format_count_classes(const GDexFormat *);
+
+/* Fournit une classe du format chargée en mémoire. */
+GDexClass *g_dex_format_get_class(const GDexFormat *, size_t);
+
#endif /* _FORMAT_DEX_DEX_H */
diff --git a/src/format/symbol.c b/src/format/symbol.c
index 898f00d..70a1d24 100644
--- a/src/format/symbol.c
+++ b/src/format/symbol.c
@@ -310,7 +310,13 @@ const char *g_binary_symbol_get_label(const GBinSymbol *symbol)
void g_binary_symbol_set_alt_label(GBinSymbol *symbol, const char *alt)
{
- symbol->alt = strdup(alt);
+ if (symbol->alt != NULL)
+ free(symbol->alt);
+
+ if (alt == NULL)
+ symbol->alt = NULL;
+ else
+ symbol->alt = strdup(alt);
}
@@ -493,7 +499,7 @@ void g_binary_symbol_attach_instruction(GBinSymbol *symbol, GArchInstruction *in
* *
* Description : Fournit l'éventuelle routine associée au symbole. *
* *
-* Retour : - *
+* Retour : Instance GLib en place ou NULL si aucune. *
* *
* Remarques : Il n'y a pas de transfert de propriété ici ! *
* *
@@ -512,7 +518,7 @@ GBinRoutine *g_binary_symbol_get_routine(const GBinSymbol *symbol)
* *
* Description : Fournit l'éventuelle instruction associée au symbole. *
* *
-* Retour : - *
+* Retour : Instance GLib en place ou NULL si aucune. *
* *
* Remarques : Il n'y a pas de transfert de propriété ici ! *
* *
@@ -551,7 +557,7 @@ void g_binary_symbol_set_comment(GBinSymbol *symbol, GDbComment *comment)
* *
* Description : Fournit l'éventuel commentaire associé au symbole. *
* *
-* Retour : - *
+* Retour : Instance GLib en place ou NULL si aucune. *
* *
* Remarques : Il n'y a pas de transfert de propriété ici ! *
* *
diff --git a/src/format/symbol.h b/src/format/symbol.h
index e0b657d..1368691 100644
--- a/src/format/symbol.h
+++ b/src/format/symbol.h
@@ -44,7 +44,9 @@ typedef enum _SymbolType
STP_FUNCTION, /* Simple morceau de code */
STP_ENTRY_POINT, /* Morceau de code en entrée */
STP_STRING, /* Chaîne de caractères */
- STP_RO_STRING /* Chaîne de caractères */
+ STP_RO_STRING, /* Chaîne de caractères */
+
+ STP_COUNT
} SymbolType;
diff --git a/src/glibext/delayed.c b/src/glibext/delayed.c
index 455cc03..32a3d16 100644
--- a/src/glibext/delayed.c
+++ b/src/glibext/delayed.c
@@ -561,7 +561,10 @@ bool init_work_queue(GObject *ref)
queue = g_object_new(G_TYPE_WORK_QUEUE, NULL);
- queue->statusbar = g_object_get_data(ref, "statusbar");
+ if (ref != NULL)
+ queue->statusbar = g_object_get_data(ref, "statusbar");
+ else
+ queue->statusbar = NULL;
if (queue != NULL)
_get_work_queue(queue);
diff --git a/src/glibext/gbufferline.h b/src/glibext/gbufferline.h
index 6da36af..3a47ee7 100644
--- a/src/glibext/gbufferline.h
+++ b/src/glibext/gbufferline.h
@@ -89,7 +89,9 @@ typedef enum _BufferLineFlags
BLF_NONE = 0 << 0, /* Aucune */
BLF_HAS_CODE = 1 << 0, /* La ligne contient du code */
BLF_ENTRYPOINT = 1 << 1, /* Représentation d'une entrée */
- BLF_BOOKMARK = 1 << 2 /* Signet associé */
+ BLF_BOOKMARK = 1 << 2, /* Signet associé */
+
+ BLF_ALL = ((1 << 3) - 1)
} BufferLineFlags;
diff --git a/src/gtkext/gtkextstatusbar.c b/src/gtkext/gtkextstatusbar.c
index 5fd37fe..74c23bd 100644
--- a/src/gtkext/gtkextstatusbar.c
+++ b/src/gtkext/gtkextstatusbar.c
@@ -223,6 +223,8 @@ bstatus_id_t gtk_extended_status_bar_push(GtkExtStatusBar *bar, const char *mess
size_t index; /* Indice du nouvel élément */
bar_update_info *info; /* Informations à mémoriser */
+ if (bar == NULL) return 0;
+
/* Mise à jour de la pile */
g_mutex_lock(&bar->stack_access);
@@ -274,6 +276,8 @@ void gtk_extended_status_bar_update_activity(GtkExtStatusBar *bar, bstatus_id_t
{
bar_update_info *info; /* Informations à mémoriser */
+ if (bar == NULL) return;
+
/* Mise à jour de la pile */
g_mutex_lock(&bar->stack_access);
@@ -315,6 +319,8 @@ void gtk_extended_status_bar_remove(GtkExtStatusBar *bar, bstatus_id_t id)
size_t i; /* Boucle de parcours */
bar_update_info *info; /* Informations à mémoriser */
+ if (bar == NULL) return;
+
/* Mise à jour de la pile */
g_mutex_lock(&bar->stack_access);
@@ -402,6 +408,8 @@ static gboolean gtk_extended_status_update(bar_update_info *info)
static void free_bar_update_info(bar_update_info *info)
{
+ if (info->bar != NULL)
+
g_object_unref(G_OBJECT(info->bar));
free(info);
@@ -425,6 +433,8 @@ static void _gtk_extended_status_bar_change_content(GtkExtStatusBar *bar)
{
size_t top; /* Indice de l'élément visé */
+ if (bar == NULL) return;
+
g_mutex_lock(&bar->stack_access);
if (bar->cur_msg > 0)
@@ -470,6 +480,8 @@ static void _gtk_extended_status_bar_update_activity(GtkExtStatusBar *bar)
double value; /* Valeur à prendre en compte */
gchar percent[5]; /* Pourcentage en version txt. */
+ if (bar == NULL) return;
+
g_mutex_lock(&bar->stack_access);
if (bar->stack_size > 0)
@@ -556,6 +568,8 @@ void fini_progessive_status(status_blob_info *info)
{
gtk_extended_status_bar_remove(info->bar, info->id);
+ if (info->bar != NULL)
+
g_object_unref(G_OBJECT(info->bar));
free(info);