summaryrefslogtreecommitdiff
path: root/src/arch/operands/register.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/arch/operands/register.c')
-rw-r--r--src/arch/operands/register.c198
1 files changed, 81 insertions, 117 deletions
diff --git a/src/arch/operands/register.c b/src/arch/operands/register.c
index 9a6de17..4615a99 100644
--- a/src/arch/operands/register.c
+++ b/src/arch/operands/register.c
@@ -24,6 +24,9 @@
#include "register.h"
+#include <assert.h>
+
+
#include "register-int.h"
#include "../storage.h"
@@ -44,22 +47,25 @@ static void g_register_operand_dispose(GRegisterOperand *);
/* Procède à la libération totale de la mémoire. */
static void g_register_operand_finalize(GRegisterOperand *);
-/* Compare un opérande avec un autre. */
-static int g_register_operand_compare(const GRegisterOperand *, const GRegisterOperand *);
-/* Traduit un opérande en version humainement lisible. */
-static void g_register_operand_print(const GRegisterOperand *, GBufferLine *);
+/* --------------------- IMPLEMENTATION DES FONCTIONS DE CLASSE --------------------- */
-/* --------------------- TRANSPOSITIONS VIA CACHE DES OPERANDES --------------------- */
+/* Compare un opérande avec un autre. */
+static int g_register_operand_compare(const GRegisterOperand *, const GRegisterOperand *, bool);
+/* Traduit un opérande en version humainement lisible. */
+static void g_register_operand_print(const GRegisterOperand *, GBufferLine *);
+
+/* Fournit l'empreinte d'un candidat à une centralisation. */
+static guint g_register_operand_hash(const GRegisterOperand *, bool);
-/* Charge un opérande depuis une mémoire tampon. */
-static bool g_register_operand_unserialize(GRegisterOperand *, GAsmStorage *, GBinFormat *, packed_buffer_t *);
+/* Charge un contenu depuis une mémoire tampon. */
+static bool g_register_operand_load(GRegisterOperand *, GObjectStorage *, packed_buffer_t *);
-/* Sauvegarde un opérande dans une mémoire tampon. */
-static bool g_register_operand_serialize(const GRegisterOperand *, GAsmStorage *, packed_buffer_t *);
+/* Sauvegarde un contenu dans une mémoire tampon. */
+static bool g_register_operand_store(GRegisterOperand *, GObjectStorage *, packed_buffer_t *);
@@ -100,8 +106,10 @@ static void g_register_operand_class_init(GRegisterOperandClass *klass)
operand->compare = (operand_compare_fc)g_register_operand_compare;
operand->print = (operand_print_fc)g_register_operand_print;
- operand->unserialize = (unserialize_operand_fc)g_register_operand_unserialize;
- operand->serialize = (serialize_operand_fc)g_register_operand_serialize;
+ operand->hash = (operand_hash_fc)g_register_operand_hash;
+
+ operand->load = (load_operand_fc)g_register_operand_load;
+ operand->store = (store_operand_fc)g_register_operand_store;
}
@@ -122,8 +130,6 @@ static void g_register_operand_init(GRegisterOperand *operand)
{
operand->reg = NULL;
- INIT_REG_OP_EXTRA(operand);
-
}
@@ -169,68 +175,61 @@ static void g_register_operand_finalize(GRegisterOperand *operand)
/******************************************************************************
* *
-* Paramètres : a = premier opérande à consulter. *
-* b = second opérande à consulter. *
+* Paramètres : operand = opérande représentant un registre. *
* *
-* Description : Compare un opérande avec un autre. *
+* Description : Fournit le registre associé à l'opérande. *
* *
-* Retour : Bilan de la comparaison. *
+* Retour : Représentation interne du registre. *
* *
* Remarques : - *
* *
******************************************************************************/
-static int g_register_operand_compare(const GRegisterOperand *a, const GRegisterOperand *b)
+GArchRegister *g_register_operand_get_register(const GRegisterOperand *operand)
{
- int result; /* Bilan à retourner */
+ GArchRegister *result; /* Instance à retourner */
- result = g_arch_register_compare(a->reg, b->reg);
+ result = operand->reg;
+
+ g_object_ref(G_OBJECT(result));
return result;
}
-/******************************************************************************
-* *
-* Paramètres : operand = opérande à traiter. *
-* line = ligne tampon où imprimer l'opérande donné. *
-* *
-* Description : Traduit un opérande en version humainement lisible. *
-* *
-* Retour : - *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-static void g_register_operand_print(const GRegisterOperand *operand, GBufferLine *line)
-{
- g_arch_register_print(operand->reg, line);
-}
+/* ---------------------------------------------------------------------------------- */
+/* IMPLEMENTATION DES FONCTIONS DE CLASSE */
+/* ---------------------------------------------------------------------------------- */
/******************************************************************************
* *
-* Paramètres : operand = opérande représentant un registre. *
+* Paramètres : a = premier opérande à consulter. *
+* b = second opérande à consulter. *
+* lock = précise le besoin en verrouillage. *
* *
-* Description : Fournit le registre associé à l'opérande. *
+* Description : Compare un opérande avec un autre. *
* *
-* Retour : Représentation interne du registre. *
+* Retour : Bilan de la comparaison. *
* *
* Remarques : - *
* *
******************************************************************************/
-GArchRegister *g_register_operand_get_register(const GRegisterOperand *operand)
+static int g_register_operand_compare(const GRegisterOperand *a, const GRegisterOperand *b, bool lock)
{
- GArchRegister *result; /* Instance à retourner */
+ int result; /* Bilan à retourner */
+ GArchOperandClass *class; /* Classe parente normalisée */
- result = operand->reg;
+ result = g_arch_register_compare(a->reg, b->reg);
- if (result != NULL)
- g_object_ref(G_OBJECT(result));
+ if (result == 0)
+ {
+ class = G_ARCH_OPERAND_CLASS(g_register_operand_parent_class);
+ result = class->compare(G_ARCH_OPERAND(a), G_ARCH_OPERAND(b), false);
+ }
return result;
@@ -239,9 +238,10 @@ GArchRegister *g_register_operand_get_register(const GRegisterOperand *operand)
/******************************************************************************
* *
-* Paramètres : operand = opérande représentant un registre à mettre à jour. *
+* Paramètres : operand = opérande à traiter. *
+* line = ligne tampon où imprimer l'opérande donné. *
* *
-* Description : Marque l'opérande comme étant écrit plutôt que consulté. *
+* Description : Traduit un opérande en version humainement lisible. *
* *
* Retour : - *
* *
@@ -249,65 +249,53 @@ GArchRegister *g_register_operand_get_register(const GRegisterOperand *operand)
* *
******************************************************************************/
-void g_register_operand_mark_as_written(GRegisterOperand *operand)
+static void g_register_operand_print(const GRegisterOperand *operand, GBufferLine *line)
{
- regop_obj_extra *extra; /* Données insérées à modifier */
-
- extra = GET_REG_OP_EXTRA(operand);
-
- g_bit_lock(&extra->lock, HOLE_LOCK_BIT);
-
- extra->is_written = true;
-
- g_bit_unlock(&extra->lock, HOLE_LOCK_BIT);
+ g_arch_register_print(operand->reg, line);
}
/******************************************************************************
* *
-* Paramètres : operand = opérande représentant un registre à consulter. *
+* Paramètres : operand = objet dont l'instance se veut unique. *
+* lock = précise le besoin en verrouillage. *
* *
-* Description : Indique le type d'accès réalisé sur l'opérande. *
+* Description : Fournit l'empreinte d'un candidat à une centralisation. *
* *
-* Retour : Type d'accès : true en cas d'écriture, false sinon. *
+* Retour : Empreinte de l'élément représenté. *
* *
* Remarques : - *
* *
******************************************************************************/
-bool g_register_operand_is_written(const GRegisterOperand *operand)
+static guint g_register_operand_hash(const GRegisterOperand *operand, bool lock)
{
- bool result; /* Statut à retourner */
- regop_obj_extra *extra; /* Données insérées à modifier */
+ guint result; /* Valeur à retourner */
+ GArchOperandClass *class; /* Classe parente normalisée */
+ GArchRegister *reg; /* Registre visé par l'opérande*/
- extra = GET_REG_OP_EXTRA(operand);
+ class = G_ARCH_OPERAND_CLASS(g_register_operand_parent_class);
+ result = class->hash(G_ARCH_OPERAND(operand), false);
- g_bit_lock(&extra->lock, HOLE_LOCK_BIT);
+ reg = g_register_operand_get_register(operand);
- result = extra->is_written;
+ result ^= g_arch_register_hash(reg);
- g_bit_unlock(&extra->lock, HOLE_LOCK_BIT);
+ g_object_unref(G_OBJECT(reg));
return result;
}
-
-/* ---------------------------------------------------------------------------------- */
-/* TRANSPOSITIONS VIA CACHE DES OPERANDES */
-/* ---------------------------------------------------------------------------------- */
-
-
/******************************************************************************
* *
-* Paramètres : operand = opérande d'assemblage à constituer. *
-* storage = mécanisme de sauvegarde à manipuler. *
-* format = format binaire chargé associé à l'architecture. *
-* pbuf = zone tampon à remplir. *
+* Paramètres : operand = élément GLib à constuire. *
+* storage = conservateur de données à manipuler ou NULL. *
+* pbuf = zone tampon à lire. *
* *
-* Description : Charge un opérande depuis une mémoire tampon. *
+* Description : Charge un contenu depuis une mémoire tampon. *
* *
* Retour : Bilan de l'opération. *
* *
@@ -315,37 +303,24 @@ bool g_register_operand_is_written(const GRegisterOperand *operand)
* *
******************************************************************************/
-static bool g_register_operand_unserialize(GRegisterOperand *operand, GAsmStorage *storage, GBinFormat *format, packed_buffer_t *pbuf)
+static bool g_register_operand_load(GRegisterOperand *operand, GObjectStorage *storage, packed_buffer_t *pbuf)
{
bool result; /* Bilan à retourner */
GArchOperandClass *parent; /* Classe parente à consulter */
- off64_t pos; /* Position dans le flux */
- packed_buffer_t reg_pbuf; /* Tampon des données à écrire */
- GArchRegister *reg; /* Registre restauré */
+ GSerializableObject *reg; /* Registre manipulé */
parent = G_ARCH_OPERAND_CLASS(g_register_operand_parent_class);
- result = parent->unserialize(G_ARCH_OPERAND(operand), storage, format, pbuf);
-
- if (result)
- result = extract_packed_buffer(pbuf, &pos, sizeof(off64_t), true);
+ result = parent->load(G_ARCH_OPERAND(operand), storage, pbuf);
if (result)
{
- init_packed_buffer(&reg_pbuf);
-
- result = g_asm_storage_load_register_data(storage, &reg_pbuf, pos);
+ reg = g_object_storage_unpack_object(storage, "registers", pbuf);
- if (result)
- {
- reg = g_arch_register_load(storage, &reg_pbuf);
- result = (reg != NULL);
- }
+ result = (reg != NULL);
if (result)
- operand->reg = reg;
-
- exit_packed_buffer(&reg_pbuf);
+ operand->reg = G_ARCH_REGISTER(reg);
}
@@ -356,11 +331,11 @@ static bool g_register_operand_unserialize(GRegisterOperand *operand, GAsmStorag
/******************************************************************************
* *
-* Paramètres : operand = opérande d'assemblage à consulter. *
-* storage = mécanisme de sauvegarde à manipuler. *
+* Paramètres : operand = élément GLib à consulter. *
+* storage = conservateur de données à manipuler ou NULL. *
* pbuf = zone tampon à remplir. *
* *
-* Description : Sauvegarde un opérande dans une mémoire tampon. *
+* Description : Sauvegarde un contenu dans une mémoire tampon. *
* *
* Retour : Bilan de l'opération. *
* *
@@ -368,31 +343,20 @@ static bool g_register_operand_unserialize(GRegisterOperand *operand, GAsmStorag
* *
******************************************************************************/
-static bool g_register_operand_serialize(const GRegisterOperand *operand, GAsmStorage *storage, packed_buffer_t *pbuf)
+static bool g_register_operand_store(GRegisterOperand *operand, GObjectStorage *storage, packed_buffer_t *pbuf)
{
bool result; /* Bilan à retourner */
- GArchOperandClass *parent; /* Classe parente à consulter */
- off64_t pos; /* Position dans le flux */
- packed_buffer_t reg_pbuf; /* Tampon des données à écrire */
+ GArchOperandClass *parent; /* Classe parente à consulter */
+ GSerializableObject *reg; /* Registre manipulé */
parent = G_ARCH_OPERAND_CLASS(g_register_operand_parent_class);
- result = parent->serialize(G_ARCH_OPERAND(operand), storage, pbuf);
+ result = parent->store(G_ARCH_OPERAND(operand), storage, pbuf);
if (result)
{
- init_packed_buffer(&reg_pbuf);
-
- result = g_arch_register_store(operand->reg, storage, &reg_pbuf);
-
- if (result)
- result = g_asm_storage_store_register_data(storage, &reg_pbuf, &pos);
-
- if (result)
- result = extend_packed_buffer(pbuf, &pos, sizeof(off64_t), true);
-
- exit_packed_buffer(&reg_pbuf);
-
+ reg = G_SERIALIZABLE_OBJECT(operand->reg);
+ result = g_object_storage_pack_object(storage, "registers", reg, pbuf);
}
return result;