summaryrefslogtreecommitdiff
path: root/src/gtkext/graph/node.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/gtkext/graph/node.c')
-rw-r--r--src/gtkext/graph/node.c313
1 files changed, 280 insertions, 33 deletions
diff --git a/src/gtkext/graph/node.c b/src/gtkext/graph/node.c
index 879139a..bb8403f 100644
--- a/src/gtkext/graph/node.c
+++ b/src/gtkext/graph/node.c
@@ -29,7 +29,9 @@
#include <string.h>
-#include "../gtkbufferview.h"
+#include "node-int.h"
+#include "nodes/flow.h"
+#include "nodes/virtual.h"
#include "../../common/extstr.h"
@@ -37,30 +39,6 @@
/* -------------------------- GESTION DES NOEUDS A L'UNITE -------------------------- */
-/* Intermédiaire entre le noeud dot et la bribe de code (instance) */
-struct _GGraphNode
-{
- GObject parent; /* A laisser en premier */
-
- GtkWidget *view; /* Morceau de code représenté */
- char *name; /* Adresse sous forme humaine */
-
- GtkAllocation alloc; /* Emplacement du bloc rattaché*/
-
-};
-
-
-/* Intermédiaire entre le noeud dot et la bribe de code (classe) */
-struct _GGraphNodeClass
-{
- GObjectClass parent; /* A laisser en premier */
-
- double dpi_x; /* Résolution en abscisse */
- double dpi_y; /* Résolution en ordonnée */
-
-};
-
-
/* Taille maximale des lignes de description de noeud */
#define NODE_DESC_LEN 128
@@ -205,8 +183,6 @@ static void g_graph_node_dispose(GGraphNode *node)
static void g_graph_node_finalize(GGraphNode *node)
{
- free(node->name);
-
G_OBJECT_CLASS(g_graph_node_parent_class)->finalize(G_OBJECT(node));
}
@@ -227,23 +203,159 @@ static void g_graph_node_finalize(GGraphNode *node)
GGraphNode *g_graph_node_new(GtkWidget *view)
{
GGraphNode *result; /* Structure à retourner */
- size_t len; /* Taille du nom */
result = g_object_new(G_TYPE_GRAPH_NODE, NULL);
result->view = view;
g_object_ref(G_OBJECT(view));
- len = 3 + sizeof(GtkWidget *) * 2 + 1;
-
- result->name = (char *)calloc(len, sizeof(char));
- snprintf(result->name, len, "_%p", result->view);
+ snprintf(result->name, NODE_NAME_LEN, "_%p", result->view);
return result;
}
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : node = noeud graphique à consulter. *
+* *
+* Description : Fournit le rang du noeud dans le graphique. *
+* *
+* Retour : Indice supérieur ou égal à zéro. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+unsigned int g_graph_node_get_rank(const GGraphNode *node)
+{
+ return node->get_rank(node);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : node = noeud graphique à manipuler. *
+* x = éventuelle abscisse à intégrer ou NULL. *
+* y = éventuelle ordonnée à intégrer ou NULL. *
+* *
+* Description : Altère la position du noeud d'encapsulation. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+void g_graph_node_set_position(GGraphNode *node, gint *x, gint *y)
+{
+ node->set_pos(node, x, y);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : node = noeud graphique à consulter. *
+* x = éventuelle abscisse à recevoir ou NULL. [OUT] *
+* y = éventuelle ordonnée à recevoir ou NULL. [OUT] *
+* *
+* Description : Fournit la position du noeud d'encapsulation. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+void g_graph_node_get_position(const GGraphNode *node, gint *x, gint *y)
+{
+ node->get_pos(node, x, y);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : node = noeud graphique à consulter. *
+* *
+* Description : Indique l'espace requis pour un noeud d'encapsulation. *
+* *
+* Retour : Espace constitué, entièrement ou non. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GtkAllocation g_graph_node_get_allocation(const GGraphNode *node)
+{
+ return node->get_alloc(node);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : node = noeud graphique démarrant la visite. *
+* callback = ensemble de blocs à parcourir. *
+* data = donnée utilisateur à associer au parcours. *
+* *
+* Description : Parcourt tous les noeuds graphiques dans un ordre donné. *
+* *
+* Retour : true si le parcours a été jusqu'à son terme, false sinon. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool g_graph_node_visit_flow_nodes(GGraphNode *node, graph_node_visitor_cb callback, void *data)
+{
+ return node->visit(node, callback, data);
+
+}
+
+
+
+
+
+
+
+
+/******************************************************************************
+* *
+* Paramètres : node = intermédiaire à consulter. *
+* rank = description pour dot à compléter. *
+* *
+* Description : Inscrit le noeud au rang donné. *
+* *
+* Retour : Description dûment complétée. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+char *g_graph_node_append_name_to_rank(const GGraphNode *node, char *rank)
+{
+ char buffer[NODE_DESC_LEN]; /* Tampon pour les commandes */
+
+ snprintf(buffer, NODE_DESC_LEN, " %s;", node->name);
+
+ if (rank == NULL)
+ rank = strdup(buffer);
+ else
+ rank = stradd(rank, buffer);
+
+ return rank;
+
+}
+
+
/******************************************************************************
* *
* Paramètres : node = intermédiaire à consulter. *
@@ -318,7 +430,7 @@ char *g_graph_node_register_for_dot(const GGraphNode *node, char *cmds, unsigned
* *
******************************************************************************/
-void g_graph_node_place(GGraphNode *node, GtkGraphView *view, gint x, gint y)
+void g_graph_node_place_old(GGraphNode *node, GtkGraphView *view, gint x, gint y)
{
GtkRequisition requisition; /* Taille à l'écran actuelle */
@@ -396,6 +508,141 @@ void g_graph_node_connect(const GGraphNode *node, gint x, gint y, GdkPoint **poi
/******************************************************************************
* *
+* Paramètres : views = liste de vues à parcourir. *
+* count = taille de la liste. *
+* addrt = adresse de début du noeud recherché. *
+* *
+* Description : Recherche une vue donnée dans une série de vues. *
+* *
+* Retour : Vue trouvée ou NULL si aucun. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GtkBufferView *find_graph_view_by_start_address(GtkBufferView **views, size_t count, vmpa_t addr)
+{
+ GtkBufferView *result; /* Trouvaille à remonter */
+ size_t i; /* Boucle de parcours */
+ GBufferView *buffer; /* Tampon d'une partie de code */
+ vmpa_t start; /* Adresse de départ du tampon */
+
+ result = NULL;
+
+ for (i = 0; i < count && result == NULL; i++)
+ {
+ buffer = gtk_buffer_view_get_buffer(GTK_BUFFER_VIEW(views[i]));
+ g_buffer_view_get_restrictions(buffer, &start, NULL);
+
+ if (start == addr)
+ result = views[i];
+
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : block = ensemble des blocs basiques déjà découpés. *
+* views = morceaux de code à afficher de façon organisée. *
+* count = quantité de ces morceaux de code. *
+* *
+* Description : Réalise une conversion de blocs en noeuds. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GGraphNode *convert_blocks_into_nodes(GInstrBlock *block, GtkBufferView **views, size_t count)
+{
+ GGraphNode *result; /* Instance nouvelle à renvoyer*/
+ vmpa_t start; /* Adresse de départ */
+ GtkBufferView *view; /* Vue existante à retrouver */
+ size_t max; /* Nombre de blocs à gérer */
+ size_t i; /* Boucle de parcours */
+ GInstrBlock *sub_block; /* Sous-bloc intégré */
+ GGraphNode *child; /* Conversion à mémoriser */
+
+ result = NULL;
+
+ if (G_IS_FLOW_BLOCK(block))
+ {
+ g_flow_block_get_boundary_addresses(G_FLOW_BLOCK(block), &start, NULL);
+ view = find_graph_view_by_start_address(views, count, start);
+
+ result = g_flow_node_new(G_FLOW_BLOCK(block), view);
+
+ }
+ else if (G_IS_VIRTUAL_BLOCK(block))
+ {
+ result = g_virtual_node_new(G_VIRTUAL_BLOCK(block));
+
+ max = g_virtual_block_count_children(G_VIRTUAL_BLOCK(block));
+
+ for (i = 0; i < max; i++)
+ {
+ sub_block = g_virtual_block_get_child(G_VIRTUAL_BLOCK(block), i);
+ child = convert_blocks_into_nodes(sub_block, views, count);
+
+ g_virtual_node_add_child(G_VIRTUAL_NODE(result), child);
+
+ }
+
+ }
+ /*else BUG_ON(1); */
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : nodes = noeud au sommet de la hiérarchie. *
+* instr = instruction à retrouver. *
+* *
+* Description : Recherche le noeud contenant une instruction donnée. *
+* *
+* Retour : Noeud trouvé ou NULL. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GGraphNode *find_node_for_instruction(GGraphNode *nodes, GArchInstruction *instr)
+{
+ GGraphNode *result; /* Trouvaille à retourner */
+ struct visit_params {
+ GArchInstruction *instr; /* Instruction recherchée */
+ GGraphNode *found; /* Remontée du noeud trouvé */
+ } params; /* Paramètres pour le parcours */
+
+ params.instr = instr;
+ params.found = NULL;
+
+ bool _find_node_cb(GFlowNode *node, struct visit_params *params)
+ {
+ if (g_flow_node_start_with(node, params->instr))
+ params->found = G_GRAPH_NODE(node);
+ return (params->found == NULL);
+ }
+
+ g_graph_node_visit_flow_nodes(nodes, (graph_node_visitor_cb)_find_node_cb, &params);
+
+ result = params.found;
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : nodes = liste de noeuds à parcourir. *
* count = taille de la liste. *
* addrt = adresse de début du noeud recherché. *