find_replace_window.c

Go to the documentation of this file.
00001 /* -*- Mode: C; tab-width: 4; indent-tabs-mode: t; c-basic-offset: 4 -*- */
00002 /*
00003   find_replace_window.c
00004   find_replace_window.c - Windows used to find text and find and replace text in
00005                           the opened hex documents.
00006 
00007 
00008   (C) Copyright 2010 - 2011 Olivier Delhomme
00009   e-mail : heraia@delhomme.org
00010   URL    : http://heraia.tuxfamily.org
00011 
00012   This program is free software; you can redistribute it and/or modify
00013   it under the terms of the GNU General Public License as published by
00014   the Free Software Foundation; either version 2, or  (at your option)
00015   any later version.
00016 
00017   This program is distributed in the hope that it will be useful,
00018   but WITHOUT ANY WARRANTY;  without even the implied warranty of
00019   MERCHANTABILITY  or  FITNESS FOR A PARTICULAR PURPOSE.  See the
00020   GNU General Public License for more details.
00021 
00022   You should have received a copy of the GNU General Public License
00023   along with this program; if not, write to the Free Software
00024   Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00025 */
00026 /**
00027  * @file find_replace_window.c
00028  * Windows used to find text and find and replace text in the opened hex
00029  * documents.
00030  */
00031 #include <libheraia.h>
00032 
00033 /*** common stuff ***/
00034 static guchar *fr_get_search_string(heraia_struct_t * main_struct, doc_t *doc, guint *buffer_size);
00035 static doc_t *create_find_or_replace_doc_t(void);
00036 static void find_replace_add_ghex_widget(xml_t *xmls, gchar *widget_name, doc_t *entry);
00037 static void fr_search_forward(heraia_struct_t *main_struct, doc_t *search_doc, goffset offset);
00038 
00039 /*** find window ***/
00040 static gboolean delete_find_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data);
00041 static void destroy_find_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data);
00042 static void find_window_close(GtkWidget *widget, gpointer data);
00043 static void find_window_connect_signal(heraia_struct_t *main_struct);
00044 static void find_all_bt_clicked(GtkWidget *widget, gpointer data);
00045 static void find_next_bt_clicked(GtkWidget *widget, gpointer data);
00046 static void find_prev_bt_clicked(GtkWidget *widget, gpointer data);
00047 
00048 /*** find and replace window ***/
00049 static gboolean delete_fr_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data);
00050 static void destroy_fr_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data);
00051 static void fr_window_close(GtkWidget *widget, gpointer data);
00052 static void fr_window_connect_signal(heraia_struct_t *main_struct);
00053 static void fr_search_bt_clicked(GtkWidget *widget, gpointer data);
00054 static void fr_replace_bt_clicked(GtkWidget *widget, gpointer data);
00055 static void fr_replace_search_bt_clicked(GtkWidget *widget, gpointer data);
00056 static goffset fr_replace_data(heraia_struct_t *main_struct);
00057 
00058 
00059 /*** fdft window ***/
00060 static gboolean delete_fdft_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data);
00061 static void destroy_fdft_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data);
00062 static fdft_t *fdft_window_init_widgets(heraia_struct_t * main_struct);
00063 static void fdft_window_close(GtkWidget *widget, gpointer data);
00064 static void fdft_window_connect_signal(heraia_struct_t *main_struct);
00065 
00066 /**
00067  * Show find window
00068  * @param widget : the widget that issued the signal
00069  * @param data : user data MUST be heraia_struct_t *main_struct main structure
00070  */
00071 void find_window_show(GtkWidget *widget, gpointer data)
00072 {
00073     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00074     GtkWidget *window = NULL;      /**< find window */
00075 
00076     if (main_struct != NULL && main_struct->current_doc != NULL)
00077         {
00078             window = heraia_get_widget(main_struct->xmls->main, "find_window");
00079             show_hide_widget(window, TRUE, main_struct->win_prop->find_window);
00080         }
00081 }
00082 
00083 
00084 /**
00085  * Call back function for the find window destruction
00086  * @param widget : calling widget (may be NULL as we don't use this here)
00087  * @param event : event associated (may be NULL as we don't use this here)
00088  * @param data :  MUST be heraia_struct_t *main_struct main structure
00089  */
00090 static gboolean delete_find_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data)
00091 {
00092     find_window_close(widget, data);
00093 
00094     return TRUE;
00095 }
00096 
00097 
00098 /**
00099  * Call back function for the find window destruction
00100  * @param widget : calling widget (may be NULL as we don't use this here)
00101  * @param event : event associated (may be NULL as we don't use this here)
00102  * @param data : user data - MUST be heraia_struct_t *main_struct main structure and not NULL
00103  */
00104 static void destroy_find_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data)
00105 {
00106     find_window_close(widget, data);
00107 }
00108 
00109 
00110 /**
00111  * Close button has been clicked we want to hide the window
00112  * @param widget : calling widget (may be NULL as we don't use this here)
00113  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00114  */
00115 static void find_window_close(GtkWidget *widget, gpointer data)
00116 {
00117     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00118     GtkWidget *window = NULL;     /**< find window */
00119 
00120     if (main_struct != NULL)
00121         {
00122             window = heraia_get_widget(main_struct->xmls->main, "find_window");
00123             show_hide_widget(window, FALSE, main_struct->win_prop->find_window);
00124         }
00125 
00126 }
00127 
00128 
00129 /**
00130  * Tries to find, in the document, what the user entered in the GtkHex entry in
00131  * the find window (forward from the current position)
00132  * @param widget : calling widget (may be NULL as we don't use this here)
00133  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00134  */
00135 static void find_next_bt_clicked(GtkWidget *widget, gpointer data)
00136 {
00137     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00138 
00139     if (main_struct != NULL && main_struct->find_doc != NULL)
00140         {
00141             fr_search_forward(main_struct, main_struct->find_doc, 0);
00142         }
00143 }
00144 
00145 
00146 /**
00147  * Tries to find, in the document, what the user entered in the GtkHex entry in
00148  * the find window (backward from the current position)
00149  * @param widget : calling widget (may be NULL as we don't use this here)
00150  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00151  */
00152 static void find_prev_bt_clicked(GtkWidget *widget, gpointer data)
00153 {
00154     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00155     guchar *buffer = NULL;     /**< Buffer that contains the search string             */
00156     doc_t *current_doc = NULL; /**< Current doc where we want to search for the string */
00157     gboolean result = FALSE;
00158     guint64 position = 0;
00159     guint buffer_size = 0;
00160 
00161     if (main_struct != NULL)
00162         {
00163             buffer = fr_get_search_string(main_struct, main_struct->find_doc, &buffer_size);
00164 
00165             if (buffer != NULL)
00166                 {
00167                     current_doc = main_struct->current_doc;
00168                     position = ghex_get_cursor_position(current_doc->hex_widget) + 1 ;
00169                     result = ghex_find_backward(current_doc, buffer, buffer_size, &position);
00170 
00171                     if (result == TRUE)
00172                         {
00173                             ghex_set_cursor_position(current_doc->hex_widget, position);
00174                         }
00175                 }
00176         }
00177 }
00178 
00179 
00180 /**
00181  * Tries to find, in the document, what the user entered in the GtkHex entry in
00182  * the find window (all positions from 0)
00183  * @param widget : calling widget (may be NULL as we don't use this here)
00184  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00185  */
00186 static void find_all_bt_clicked(GtkWidget *widget, gpointer data)
00187 {
00188     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00189     guchar *buffer = NULL;     /**< Buffer that contains the search string             */
00190     doc_t *current_doc = NULL; /**< Current doc where we want to search for the string */
00191     gboolean result = FALSE;
00192     guint64 position = 0;
00193     guint buffer_size = 0;
00194     GArray *all_pos = NULL;    /**< All positions of the searched string               */
00195 
00196     if (main_struct != NULL)
00197         {
00198             buffer = fr_get_search_string(main_struct, main_struct->find_doc, &buffer_size);
00199 
00200             if (buffer != NULL)
00201                 {
00202                     all_pos = g_array_new(TRUE, TRUE, sizeof(guint64));
00203                     current_doc = main_struct->current_doc;
00204                     position = 0;
00205                     result = ghex_find_forward(current_doc, buffer, buffer_size, &position);
00206 
00207                     while (result == TRUE)
00208                         {
00209                             all_pos = g_array_append_val(all_pos, position);
00210                             result = ghex_find_forward(current_doc, buffer, buffer_size, &position);
00211                         }
00212                 }
00213         }
00214 
00215     if (all_pos != NULL)
00216         {
00217             rw_add_one_tab_from_find_all_bt(main_struct, all_pos, buffer_size, NULL);
00218             g_array_free(all_pos, TRUE);
00219         }
00220 }
00221 
00222 
00223 /**
00224  * Signal connections for the find window
00225  * @param main_struct : heraia's main structure
00226  */
00227 static void find_window_connect_signal(heraia_struct_t *main_struct)
00228 {
00229     /* Close button */
00230     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "find_close_bt")), "clicked",
00231                      G_CALLBACK(find_window_close), main_struct);
00232 
00233     /* Next button */
00234     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "find_next_bt")), "clicked",
00235                      G_CALLBACK(find_next_bt_clicked), main_struct);
00236 
00237     /* Prev button */
00238     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "find_prev_bt")), "clicked",
00239                      G_CALLBACK(find_prev_bt_clicked), main_struct);
00240 
00241     /* Find all button */
00242     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "find_all_bt")), "clicked",
00243                      G_CALLBACK(find_all_bt_clicked), main_struct);
00244 
00245     /* When find window is killed or destroyed */
00246     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "find_window")), "delete_event",
00247                      G_CALLBACK(delete_find_window_event), main_struct);
00248 
00249     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "find_window")), "destroy",
00250                      G_CALLBACK(destroy_find_window_event), main_struct);
00251 }
00252 
00253 
00254 /**
00255  * Inits all the things in the find window (signal and such)
00256  * @param main_struct : heraia's main structure
00257  */
00258 void find_window_init_interface(heraia_struct_t * main_struct)
00259 {
00260 
00261     if (main_struct != NULL && main_struct->xmls != NULL && main_struct->xmls->main != NULL)
00262         {
00263             find_window_connect_signal(main_struct);
00264 
00265             main_struct->find_doc = create_find_or_replace_doc_t();
00266 
00267             if (main_struct->find_doc != NULL)
00268                 {
00269                    find_replace_add_ghex_widget(main_struct->xmls, "find_al", main_struct->find_doc);
00270                 }
00271         }
00272 }
00273 
00274 
00275 /******************************************************************************/
00276 /******************************* common stuff *********************************/
00277 /******************************************************************************/
00278 
00279 /**
00280  * Gets the string from the document doc
00281  * @param main_struct : main structure, needed here to compute endianness
00282  * @param doc : the document (HexDocument and HexWidget) used to defined the
00283  *              search string
00284  * @return a newly allocated guchar string that may be g_free'ed when no longer
00285  *         needed
00286  */
00287 static guchar *fr_get_search_string(heraia_struct_t * main_struct, doc_t *doc, guint *buffer_size)
00288 {
00289     guint size = 0;          /**< size of the search string (we hope that this value is small) */
00290     guchar *buffer = NULL;   /**< buffer for the search string                                 */
00291     guint endianness = 0;    /**< endianness as selected in data interpretor's window          */
00292     gboolean result = FALSE;
00293 
00294 
00295     size = ghex_file_size(GTK_HEX(doc->hex_widget));
00296 
00297     if (size > 0 && size < 4096)  /* Here fixes some limits ! */
00298         {
00299             buffer = (guchar *) g_malloc0(sizeof(guchar) * size);
00300             endianness = which_endianness(main_struct);
00301             result = ghex_get_data_position(doc->hex_widget, 0, size, endianness, buffer);
00302 
00303             if (result == TRUE)
00304                 {
00305                     *buffer_size = size;
00306                     return buffer;
00307                 }
00308             else
00309                 {
00310                     *buffer_size = 0;
00311                     return NULL;
00312                 }
00313         }
00314     else
00315         {
00316             *buffer_size = 0;
00317             return NULL;
00318         }
00319 }
00320 
00321 
00322 /**
00323  * Creates the HexDocument and the GtkHex widget with the right properties and
00324  * Fills a doc_t structure with them.
00325  * @return a newly allocated doc_t structure with HexDocument and GtkHex widget
00326  *         correctly configured to fit in the find and find and replace windows
00327  */
00328 static doc_t *create_find_or_replace_doc_t(void)
00329 {
00330     Heraia_Document *find_hex_doc = NULL;
00331     GtkWidget *find_hex_widget = NULL;
00332 
00333     find_hex_doc = hex_document_new();
00334 
00335     if (find_hex_doc != NULL)
00336         {
00337             /* creating a new view to this new document */
00338             find_hex_widget = hex_document_add_view(find_hex_doc);
00339 
00340             /* Sets some options : no offests, insert mode and 4 lines of 16 chars */
00341             gtk_hex_show_offsets(GTK_HEX(find_hex_widget), FALSE);
00342             gtk_hex_set_insert_mode(GTK_HEX(find_hex_widget), TRUE);
00343             gtk_hex_set_geometry(GTK_HEX(find_hex_widget), 16, 4);
00344 
00345             /* joining those two new structures in one */
00346             return new_doc_t(find_hex_doc, find_hex_widget);
00347         }
00348     else
00349         {
00350             return NULL;
00351         }
00352 }
00353 
00354 
00355 /**
00356  * Adds the GtkHex widget to the right frame
00357  * @param xmls : xmls structure
00358  * @param widget_name : the widget that will receive the GtkHex widget (a frame)
00359  * @param entry : the doc_t structure that contains document and gtkhex widget
00360  *                used as an entry field
00361  */
00362 static void find_replace_add_ghex_widget(xml_t *xmls, gchar *widget_name, doc_t *entry)
00363 {
00364     GtkWidget *al = NULL;
00365 
00366     al = heraia_get_widget(xmls->main, widget_name);
00367     gtk_container_add(GTK_CONTAINER(al), entry->hex_widget);
00368     gtk_container_set_border_width(GTK_CONTAINER(al), 3);
00369 
00370 
00371 }
00372 
00373 
00374 /**
00375  * Searches the string entered in the search document in the current one (from
00376  * the currenty position + offset) in the main window.
00377  * @param main_struct : heraia's main structure
00378  * @param search_doc : the document used to enter the searched string
00379  * @param offset : the offset from the current position to begin the search.
00380  */
00381 static void fr_search_forward(heraia_struct_t *main_struct, doc_t *search_doc, goffset offset)
00382 {
00383     guchar *buffer = NULL;     /**< Buffer that contains the search string             */
00384     doc_t *current_doc = NULL; /**< Current doc where we want to search for the string */
00385     gboolean result = FALSE;
00386     guint64 position = 0;
00387     guint buffer_size = 0;
00388 
00389     buffer = fr_get_search_string(main_struct, search_doc, &buffer_size);
00390 
00391     if (buffer != NULL)
00392         {
00393             current_doc = main_struct->current_doc;
00394             position = ghex_get_cursor_position(current_doc->hex_widget);
00395             position = position + offset;
00396             result = ghex_find_forward(current_doc, buffer, buffer_size, &position);
00397 
00398             if (result == TRUE)
00399                 {
00400                     ghex_set_cursor_position(current_doc->hex_widget, position);
00401                 }
00402         }
00403 }
00404 
00405 
00406 /******************************************************************************/
00407 /************************** find and replace window ***************************/
00408 /******************************************************************************/
00409 
00410 
00411 /**
00412  * Show find and replace window
00413  * @param widget : the widget that issued the signal
00414  * @param data : user data MUST be heraia_struct_t *main_struct main structure
00415  */
00416 void fr_window_show(GtkWidget *widget, gpointer data)
00417 {
00418     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00419     GtkWidget *window = NULL;      /**< find window */
00420 
00421     if (main_struct != NULL && main_struct->current_doc != NULL)
00422         {
00423             window = heraia_get_widget(main_struct->xmls->main, "fr_window");
00424             show_hide_widget(window, TRUE, main_struct->win_prop->fr_window);
00425         }
00426 }
00427 
00428 
00429 /**
00430  * Call back function for the find and replace window destruction
00431  * @param widget : calling widget (may be NULL as we don't use this here)
00432  * @param event : event associated (may be NULL as we don't use this here)
00433  * @param data :  MUST be heraia_struct_t *main_struct main structure
00434  */
00435 static gboolean delete_fr_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data)
00436 {
00437     fr_window_close(widget, data);
00438 
00439     return TRUE;
00440 }
00441 
00442 
00443 /**
00444  * Call back function for the find and replace window destruction
00445  * @param widget : calling widget (may be NULL as we don't use this here)
00446  * @param event : event associated (may be NULL as we don't use this here)
00447  * @param data : user data - MUST be heraia_struct_t *main_struct main structure and not NULL
00448  */
00449 static void destroy_fr_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data)
00450 {
00451     fr_window_close(widget, data);
00452 }
00453 
00454 
00455 /**
00456  * Close button has been clicked we want to hide the window
00457  * @param widget : calling widget (may be NULL as we don't use this here)
00458  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00459  */
00460 static void fr_window_close(GtkWidget *widget, gpointer data)
00461 {
00462     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00463      GtkWidget *window = NULL;     /**< find window */
00464 
00465     if (main_struct != NULL)
00466         {
00467              window = heraia_get_widget(main_struct->xmls->main, "fr_window");
00468              show_hide_widget(window, FALSE, main_struct->win_prop->fr_window);
00469         }
00470 }
00471 
00472 
00473 /**
00474  * Signal connections for the find and replace window
00475  * @param main_struct : heraia's main structure
00476  */
00477 static void fr_window_connect_signal(heraia_struct_t *main_struct)
00478 {
00479     /* Close button */
00480     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fr_close_bt")), "clicked",
00481                      G_CALLBACK(fr_window_close), main_struct);
00482 
00483     /* When find and replace  window is killed or destroyed */
00484     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fr_window")), "delete_event",
00485                      G_CALLBACK(delete_fr_window_event), main_struct);
00486 
00487     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fr_window")), "destroy",
00488                      G_CALLBACK(destroy_fr_window_event), main_struct);
00489 
00490     /* Search button */
00491     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fr_find_bt")), "clicked",
00492                      G_CALLBACK(fr_search_bt_clicked), main_struct);
00493 
00494     /* Replace button */
00495     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fr_replace_bt")), "clicked",
00496                      G_CALLBACK(fr_replace_bt_clicked), main_struct);
00497 
00498     /* Replace and search button */
00499     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fr_replace_search_bt")), "clicked",
00500                      G_CALLBACK(fr_replace_search_bt_clicked), main_struct);
00501 }
00502 
00503 
00504 /**
00505  * Tries to find, in the document, what the user entered in the GtkHex entry in
00506  * the fr window in the find hexwidget (forward from the current position)
00507  * @param widget : calling widget (may be NULL as we don't use this here)
00508  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00509  */
00510 static void fr_search_bt_clicked(GtkWidget *widget, gpointer data)
00511 {
00512     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00513 
00514     if (main_struct != NULL && main_struct->fr_find_doc != NULL)
00515         {
00516            fr_search_forward(main_struct, main_struct->fr_find_doc, 0);
00517         }
00518 }
00519 
00520 
00521 /**
00522  * Tries to replace, in the document, what the user entered in the GtkHex entry
00523  * in the fr window in the find hexwidget by what the user entered in the
00524  * replace entry in that same window and then goes to the next position (if any)
00525  * @param widget : calling widget (may be NULL as we don't use this here)
00526  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00527  */
00528 static void fr_replace_search_bt_clicked(GtkWidget *widget, gpointer data)
00529 {
00530     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00531     goffset offset = 0;
00532 
00533     if (main_struct != NULL && main_struct->fr_find_doc != NULL)
00534         {
00535             offset = fr_replace_data(main_struct);
00536             /* fprintf(stdout, "offset : %ld\n", offset); */
00537             fr_search_forward(main_struct, main_struct->fr_find_doc, offset);
00538         }
00539 }
00540 
00541 
00542 /**
00543  * Tries to replace, in the document, what the user entered in the GtkHex entry
00544  * in the fr window in the find hexwidget by what the user entered in the
00545  * replace entry in that same window
00546  * @param main_struct : main structure
00547  * @return a goffset that indicates the length difference between the length of
00548  *         the replaced data and the length of the inserted data
00549  */
00550 static goffset fr_replace_data(heraia_struct_t *main_struct)
00551 {
00552     guchar *buffer = NULL;     /**< Buffer that contains the search string             */
00553     guchar *rep_buffer = NULL; /**< Buffer that contains the replace string            */
00554     doc_t *current_doc = NULL; /**< Current doc where we want to search for the string */
00555     guint buffer_size = 0;     /**< Size of the searched string                        */
00556     guint rep_buf_size = 0;    /**< Size of the replace string                         */
00557     guint64 position = 0;      /**< Current position in the current document !         */
00558     goffset length = 0;        /**< length of the result of that replace               */
00559 
00560     if (main_struct != NULL && main_struct->current_doc != NULL && main_struct->fr_find_doc != NULL && main_struct->fr_replace_doc != NULL)
00561         {
00562             current_doc = main_struct->current_doc;
00563             buffer = fr_get_search_string(main_struct, main_struct->fr_find_doc, &buffer_size);
00564             rep_buffer = fr_get_search_string(main_struct, main_struct->fr_replace_doc, &rep_buf_size);
00565             position = ghex_get_cursor_position(current_doc->hex_widget);
00566             if (ghex_compare_data(current_doc, buffer, buffer_size, position) == 0)
00567                 {
00568                     /* The strings are equal and can be replaced in the current document */
00569                     ghex_set_data(current_doc, position, buffer_size, rep_buf_size, rep_buffer);
00570                     length = (goffset) rep_buf_size - buffer_size;
00571                     return length;
00572                 }
00573             else
00574                 {
00575                     return length;
00576                 }
00577         }
00578     else
00579         {
00580             return length;
00581         }
00582 }
00583 
00584 
00585 /**
00586  * @param widget : calling widget (may be NULL as we don't use this here)
00587  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00588  */
00589 static void fr_replace_bt_clicked(GtkWidget *widget, gpointer data)
00590 {
00591     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00592     goffset offset = 0;
00593 
00594     offset = fr_replace_data(main_struct);
00595 }
00596 
00597 
00598 /**
00599  * Inits all the things in the find and replace window (signal and such)
00600  * @param main_struct : heraia's main structure
00601  */
00602 void fr_window_init_interface(heraia_struct_t * main_struct)
00603 {
00604 
00605       if (main_struct != NULL && main_struct->xmls != NULL && main_struct->xmls->main != NULL)
00606         {
00607             fr_window_connect_signal(main_struct);
00608 
00609             /* Creating a new hex document */
00610             main_struct->fr_find_doc = create_find_or_replace_doc_t();
00611             main_struct->fr_replace_doc = create_find_or_replace_doc_t();
00612 
00613             if (main_struct->fr_replace_doc != NULL && main_struct->fr_find_doc != NULL)
00614                 {
00615                     find_replace_add_ghex_widget(main_struct->xmls, "fr_find_al", main_struct->fr_find_doc);
00616                     find_replace_add_ghex_widget(main_struct->xmls, "fr_replace_al", main_struct->fr_replace_doc);
00617                 }
00618 
00619         }
00620 }
00621 
00622 
00623 /******************************************************************************/
00624 /**************************** Find data from type *****************************/
00625 /******************************************************************************/
00626 
00627 
00628 /***
00629  * Populates the category combobox from the structures of the data interpretor
00630  * window
00631  * @param main_struct : main structure of the program
00632  */
00633 static void fdft_window_populate_category_cb(heraia_struct_t *main_struct)
00634 {
00635     GtkWidget *cb = NULL;  /**< category's combobox */
00636     GtkWidget *label = NULL;
00637     tab_t *tab = NULL;
00638     gint i = 0;
00639     const gchar *text = NULL;
00640 
00641     if (main_struct != NULL)
00642         {
00643             cb = main_struct->fdft->category_cb;
00644 
00645             for (i = 0; i < main_struct->current_DW->nb_tabs; i++)
00646                 {
00647                     tab = g_ptr_array_index(main_struct->current_DW->tabs, i);
00648                     label = tab->label;
00649                     text = gtk_label_get_text(GTK_LABEL(label));
00650                     gtk_combo_box_append_text(GTK_COMBO_BOX(cb), text);
00651                 }
00652         }
00653 }
00654 
00655 
00656 /**
00657  * Show find data from type window
00658  * @param widget : the widget that issued the signal
00659  * @param data : user data MUST be heraia_struct_t *main_struct main structure
00660  */
00661 void fdft_window_show(GtkWidget *widget, gpointer data)
00662 {
00663     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00664     GtkWidget *window = NULL;      /**< find data from type window */
00665 
00666     if (main_struct != NULL && main_struct->current_doc != NULL)
00667         {
00668             window = heraia_get_widget(main_struct->xmls->main, "fdft_window");
00669             show_hide_widget(window, TRUE, main_struct->win_prop->fdft_window);
00670         }
00671 }
00672 
00673 
00674 /**
00675  * Call back function for the find data from type window destruction
00676  * @param widget : calling widget (may be NULL as we don't use this here)
00677  * @param event : event associated (may be NULL as we don't use this here)
00678  * @param data :  MUST be heraia_struct_t *main_struct main structure
00679  */
00680 static gboolean delete_fdft_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data)
00681 {
00682     fdft_window_close(widget, data);
00683 
00684     return TRUE;
00685 }
00686 
00687 
00688 /**
00689  * Call back function for the find data from type window destruction
00690  * @param widget : calling widget (may be NULL as we don't use this here)
00691  * @param event : event associated (may be NULL as we don't use this here)
00692  * @param data : user data - MUST be heraia_struct_t *main_struct main structure and not NULL
00693  */
00694 static void destroy_fdft_window_event(GtkWidget *widget, GdkEvent  *event, gpointer data)
00695 {
00696     fdft_window_close(widget, data);
00697 }
00698 
00699 
00700 /**
00701  * Close button has been clicked we want to hide the window
00702  * @param widget : calling widget (may be NULL as we don't use this here)
00703  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00704  */
00705 static void fdft_window_close(GtkWidget *widget, gpointer data)
00706 {
00707     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00708     GtkWidget *window = NULL;     /**< find window */
00709 
00710     if (main_struct != NULL)
00711         {
00712             window = heraia_get_widget(main_struct->xmls->main, "fdft_window");
00713             show_hide_widget(window, FALSE, main_struct->win_prop->fdft_window);
00714         }
00715 }
00716 
00717 /**
00718  * return the decode structure that corresponds to the indexes from category,
00719  * type and feature as stated in the parameters
00720  * @param main_struct : heraia's main structure
00721  * @param cat_index : category index (tab's number in the data interpertor's window
00722  * @param typ_index : type index (the row number in the category's tab)
00723  * @param fea_index : feature index (column number in the row of the tab of the data
00724  *                    interpretor's window
00725  * @param[out] data_size : size of the data to be filled to the decoding function
00726  * @return the correspondinf decode structure that contains, the function, the
00727  *         entry (gtkwidget) and an error message to be displayed in case of an error
00728  */
00729 static decode_t *get_decode_struct(heraia_struct_t *main_struct, gint cat_index, gint typ_index, gint fea_index, guint *data_size)
00730 {
00731     decode_generic_t *decod = NULL; /**< stores row structure (boxes, labels, entries and functions)                 */
00732     tab_t *tab = NULL;              /**< stores description for one tab                                              */
00733 
00734     /* Everything is selected and we know what data type the user is looking for */
00735     if (cat_index >= 0 && typ_index >= 0 && fea_index >= 0)
00736         {
00737             tab = g_ptr_array_index(main_struct->current_DW->tabs, cat_index);
00738             if (tab != NULL)
00739                 {
00740                     decod = g_ptr_array_index(tab->rows, typ_index);
00741                     if (decod  != NULL)
00742                         {
00743                             *data_size = decod->data_size;
00744                             return g_ptr_array_index(decod->decode_array, fea_index);
00745                         }
00746                     else
00747                         {
00748                             return NULL;
00749                         }
00750                 }
00751             else
00752                 {
00753                     return NULL;
00754                 }
00755         }
00756     else
00757         {
00758             return NULL;
00759         }
00760 }
00761 
00762 /**
00763  * Searches the string entered in the search document in the current one (from
00764  * the currenty position + offset) in the main window.
00765  * @param main_struct : heraia's main structure
00766  * @param dircetion : says wether we should go forward or backward
00767  * @param decode_struct : the decoding structure
00768  * @param data_size : the size of the data to be send to the decode function
00769  * @param buffer : Buffer that contains the string to look for
00770  */
00771 static void fdft_search_direction(heraia_struct_t *main_struct, gint direction, decode_t *decode_struct, gint data_size, gchar *buffer)
00772 {
00773     decode_parameters_t *decode_parameters = NULL;
00774     doc_t *current_doc = NULL; /**< Current doc where we want to search for the string */
00775     gboolean result = FALSE;
00776     guint64 position = 0;
00777     guint endianness = 0;
00778     guint stream_size = 0;
00779     GArray *all_pos = NULL;    /**< All positions of the searched string               */
00780 
00781 
00782     endianness = which_endianness(main_struct);    /** Endianness is computed only once here  */
00783     stream_size =  which_stream_size(main_struct); /** stream size is computed only once here */
00784 
00785     decode_parameters = new_decode_parameters_t(endianness, stream_size);
00786 
00787 
00788     if (buffer != NULL)
00789         {
00790             current_doc = main_struct->current_doc;
00791 
00792             if (direction == HERAIA_FIND_FORWARD || direction == HERAIA_FIND_BACKWARD)
00793                 {
00794                     position = ghex_get_cursor_position(current_doc->hex_widget);
00795                     result = ghex_find_decode(direction, current_doc, decode_struct->func, decode_parameters, data_size, buffer, &position);
00796 
00797                     log_message(main_struct, G_LOG_LEVEL_DEBUG, "endianness : %d ; stream_size : %d - result : %d", endianness, stream_size, result);
00798 
00799                     if (result == TRUE)
00800                         {
00801                             ghex_set_cursor_position(current_doc->hex_widget, position);
00802                         }
00803                 }
00804             else if (direction == HERAIA_FIND_ALL)
00805                 {
00806                     all_pos = g_array_new(TRUE, TRUE, sizeof(guint64));
00807 
00808                     position = 0;
00809                     result = ghex_find_decode(HERAIA_FIND_ALL, current_doc, decode_struct->func, decode_parameters, data_size, buffer, &position);
00810 
00811                     log_message(main_struct, G_LOG_LEVEL_DEBUG, "endianness : %d ; stream_size : %d - result : %d", endianness, stream_size, result);
00812 
00813                     while (result == TRUE)
00814                         {
00815                             all_pos = g_array_append_val(all_pos, position);
00816                             result = ghex_find_decode(HERAIA_FIND_FORWARD, current_doc, decode_struct->func, decode_parameters, data_size, buffer, &position);
00817                         }
00818 
00819                     if (all_pos != NULL)
00820                         {
00821                             rw_add_one_tab_from_find_all_bt(main_struct, all_pos, data_size, (guchar *) buffer);
00822                             g_array_free(all_pos, TRUE);
00823                         }
00824                 }
00825         }
00826 
00827     g_free(decode_parameters);
00828 }
00829 
00830 
00831 /**
00832  * Searches data from the selected type (if any) in the current document (if any)
00833  * and returns the results in the result window
00834  * @param widget : Calling widget (Is used to determine the direction of the search)
00835  * @param data : MUST be heraia_struct_t *main_struct main structure and not NULL
00836  */
00837 static void fdft_prev_next_bt_clicked(GtkWidget *widget, gpointer data)
00838 {
00839     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00840     gint cat_index = 0;   /**< index for the selected category in the combo box */
00841     gint typ_index = 0;   /**< index for the selected type in the combo box     */
00842     gint fea_index = 0;   /**< index for the selected feature in the combo box  */
00843     GtkWidget *cb = NULL; /**< represents the combo boxes (category, type and feature combo boxes) */
00844     decode_t *decode_struct = NULL;  /**< The structure that contains the function we need */
00845     const gchar *buffer = NULL; /**< contains what the user enterer in the search window */
00846     guint data_size = 0;
00847     GtkWidget *button = NULL;
00848 
00849     if (main_struct != NULL && main_struct->current_doc != NULL && main_struct->current_DW != NULL && main_struct->fdft != NULL)
00850         {
00851             cb = main_struct->fdft->category_cb;
00852             cat_index = gtk_combo_box_get_active(GTK_COMBO_BOX(cb));
00853 
00854             cb = main_struct->fdft->type_cb;
00855             typ_index = gtk_combo_box_get_active(GTK_COMBO_BOX(cb));
00856 
00857             cb = main_struct->fdft->feature_cb;
00858             fea_index = gtk_combo_box_get_active(GTK_COMBO_BOX(cb));
00859 
00860             decode_struct = get_decode_struct(main_struct, cat_index, typ_index, fea_index, &data_size);
00861 
00862             buffer = gtk_entry_buffer_get_text(gtk_entry_get_buffer(GTK_ENTRY(heraia_get_widget(main_struct->xmls->main, "fdft_value_entry"))));
00863 
00864             log_message(main_struct, G_LOG_LEVEL_DEBUG, "cat : %d, typ : %d, fea : %d - decode_struct : %p , data_size : %d ; buffer : %s", cat_index, typ_index, fea_index, decode_struct, data_size, buffer);
00865 
00866             if (decode_struct != NULL && buffer != NULL && data_size > 0)
00867                 {
00868                     button = heraia_get_widget(main_struct->xmls->main, "fdft_next_bt");
00869 
00870                     if (widget == button)
00871                         {
00872                             fdft_search_direction(main_struct, HERAIA_FIND_FORWARD, decode_struct, data_size, (gchar *) buffer);
00873                         }
00874                     else
00875                         {
00876                             button = heraia_get_widget(main_struct->xmls->main, "fdft_prev_bt");
00877                             if (widget == button)
00878                                 {
00879                                     fdft_search_direction(main_struct, HERAIA_FIND_BACKWARD, decode_struct, data_size, (gchar *) buffer);
00880                                 }
00881                             else
00882                                 {
00883                                     fdft_search_direction(main_struct, HERAIA_FIND_ALL, decode_struct, data_size, (gchar *) buffer);
00884                                 }
00885                         }
00886                 }
00887         }
00888 }
00889 
00890 
00891 /**
00892  * Signal connections for the find data from type window
00893  * @param main_struct : heraia's main structure
00894  */
00895 static void fdft_window_connect_signal(heraia_struct_t *main_struct)
00896 {
00897     /* Close button */
00898     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fdft_close_bt")), "clicked",
00899                      G_CALLBACK(fdft_window_close), main_struct);
00900 
00901     /* When fdft window is killed or destroyed */
00902     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fdft_window")), "delete_event",
00903                      G_CALLBACK(delete_fdft_window_event), main_struct);
00904 
00905     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fdft_window")), "destroy",
00906                      G_CALLBACK(destroy_fdft_window_event), main_struct);
00907 
00908     /* next button */
00909     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fdft_next_bt")), "clicked",
00910                      G_CALLBACK(fdft_prev_next_bt_clicked), main_struct);
00911 
00912     /* prev button */
00913     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fdft_prev_bt")), "clicked",
00914                      G_CALLBACK(fdft_prev_next_bt_clicked), main_struct);
00915 
00916     /* find all button */
00917     g_signal_connect(G_OBJECT(heraia_get_widget(main_struct->xmls->main, "fdft_all_bt")), "clicked",
00918                      G_CALLBACK(fdft_prev_next_bt_clicked), main_struct);
00919 }
00920 
00921 
00922 /**
00923  * Fills the type ComboBox with the right values
00924  * @param widget : the combobox that issued the changed signal
00925  * @param data : must be heraia_struct_t *main_struct
00926  */
00927 static void fdft_category_cb_changed(GtkWidget *widget, gpointer data)
00928 {
00929     heraia_struct_t *main_struct = (heraia_struct_t *) data;
00930     decode_generic_t *decod = NULL; /**< stores row structure (boxes, labels, entries and functions)                 */
00931     tab_t *tab = NULL;              /**< stores description for one tab                                              */
00932     GtkWidget *cb = NULL;           /**< represents the combo boxes (category, type and feature combo boxes)         */
00933     gint index = 0;                 /**< active index of the category combo box                                      */
00934     gint i = 0;
00935     GtkWidget *label = NULL;        /**< used to retrieve labels from the GtkLabel widgets                           */
00936     const gchar *text = NULL;       /**< contains text from the labels                                               */
00937     GtkTreeModel *model = NULL;     /**< the models from the combo box (used to delete everything in the combo boxes */
00938 
00939     if (main_struct != NULL && main_struct->fdft != NULL)
00940         {
00941             /* retrieve the selected category  */
00942             cb = main_struct->fdft->category_cb;
00943             index = gtk_combo_box_get_active(GTK_COMBO_BOX(cb));
00944             tab = g_ptr_array_index(main_struct->current_DW->tabs, index);
00945 
00946             /* Type combobox                   */
00947             /* First delete all entries if any */
00948             cb = main_struct->fdft->type_cb;
00949             model = gtk_combo_box_get_model(GTK_COMBO_BOX(cb));
00950             gtk_list_store_clear(GTK_LIST_STORE(model));
00951 
00952             /* Second fill the combobox with the values */
00953             for (i = 0; i < tab->nb_rows; i++)
00954                 {
00955                     decod = g_ptr_array_index(tab->rows, i);
00956                     label = decod->label;
00957                     text = gtk_label_get_text(GTK_LABEL(label));
00958                     gtk_combo_box_append_text(GTK_COMBO_BOX(cb), text);
00959                 }
00960 
00961             /* Feature combobox                */
00962             /* First delete all entries if any */
00963             cb = main_struct->fdft->feature_cb;
00964             model = gtk_combo_box_get_model(GTK_COMBO_BOX(cb));
00965             gtk_list_store_clear(GTK_LIST_STORE(model));
00966 
00967             /* Second fill the combobox with the values */
00968             /* Here we start from 1, because column 0 is the row's title column */
00969             for (i = 1; i < tab->nb_cols; i++)
00970                 {
00971                     label = g_ptr_array_index(tab->col_labels, i);
00972                     text = gtk_label_get_text(GTK_LABEL(label));
00973                     gtk_combo_box_append_text(GTK_COMBO_BOX(cb), text);
00974                 }
00975         }
00976 }
00977 
00978 
00979 /**
00980  * Inits the fdft structure and adds the widgets to the window
00981  * @param main_struct : heraia's main structure
00982  */
00983 static fdft_t *fdft_window_init_widgets(heraia_struct_t * main_struct)
00984 {
00985     fdft_t *fdft = NULL;
00986     GtkWidget *vbox = NULL;
00987 
00988     if (main_struct != NULL && main_struct->fdft == NULL)
00989         {
00990             fdft = (fdft_t *) g_malloc0 (sizeof(fdft_t));
00991 
00992             fdft->category_cb = gtk_combo_box_new_text();
00993             fdft->type_cb = gtk_combo_box_new_text();
00994             fdft->feature_cb = gtk_combo_box_new_text();
00995 
00996             main_struct->fdft = fdft;
00997 
00998             vbox = heraia_get_widget(main_struct->xmls->main, "fdft_category_vbox");
00999             gtk_box_pack_end(GTK_BOX(vbox), fdft->category_cb, FALSE, FALSE, 0);
01000 
01001             vbox = heraia_get_widget(main_struct->xmls->main, "fdft_type_vbox");
01002             gtk_box_pack_end(GTK_BOX(vbox), fdft->type_cb, FALSE, FALSE, 0);
01003 
01004             vbox = heraia_get_widget(main_struct->xmls->main, "fdft_feature_vbox");
01005             gtk_box_pack_end(GTK_BOX(vbox), fdft->feature_cb, FALSE, FALSE, 0);
01006 
01007             /* Combo box button */
01008             g_signal_connect(G_OBJECT(fdft->category_cb), "changed",
01009                              G_CALLBACK(fdft_category_cb_changed), main_struct);
01010 
01011             return fdft;
01012         }
01013     else
01014         {
01015             return NULL;
01016         }
01017 }
01018 
01019 
01020 /**
01021  * Inits all the things in the find data from type window (signal and such)
01022  * @param main_struct : heraia's main structure
01023  */
01024 void fdft_window_init_interface(heraia_struct_t * main_struct)
01025 {
01026 
01027     if (main_struct != NULL && main_struct->xmls != NULL && main_struct->xmls->main != NULL)
01028         {
01029             fdft_window_connect_signal(main_struct);
01030             main_struct->fdft = fdft_window_init_widgets(main_struct);
01031             fdft_window_populate_category_cb(main_struct);
01032         }
01033 }
Generated on Mon May 2 21:04:49 2011 for Heraia by  doxygen 1.6.3