Search
lxdream.org :: lxdream/src/gui/dump_win.c
lxdream 0.9.1
released Jun 29
Download Now
filename src/gui/dump_win.c
changeset 2:42349f6ea216
next31:495e480360d7
author nkeynes
date Thu Dec 15 13:33:14 2005 +0000 (18 years ago)
permissions -rw-r--r--
last change Implement save states
view annotate diff log raw
     1 /**
     2  * Implements the memory dump window.
     3  */
     4 #include <gnome.h>
     5 #include <ctype.h>
     6 #include <assert.h>
     7 #include "gui.h"
     8 #include "interface.h"
     9 #include "mem.h"
    11 #define MAX_DUMP_SIZE 4096
    13 #define DUMP_DATA_TAG 0xD4B9DA7A
    15 typedef struct dump_data {
    16     uint32_t _tag;
    17     uint32_t start;
    18     uint32_t end;
    19     int flags;
    20     char *data;
    22     GtkEntry *fromInput, *toInput;
    23     GtkTextView *textArea;
    24     GtkTextTag *changedTag;
    25     GtkTextBuffer *textBuffer;
    26     struct dump_data *next;
    27 } *dump_data_t;
    29 static dump_data_t dump_list_head = NULL;
    31 gboolean on_dump_win_delete_event( GtkWidget *widget, GdkEvent *event,
    32                                    gpointer user_data );
    33 void on_dump_win_button_view_clicked( GtkWidget *widget, gpointer user_data );
    34 void dump_win_set_text( dump_data_t data, char *old_data, char *new_data );
    37 void dump_window_new( void ) {
    38     GtkWidget *win = create_dump_win();
    39     GtkWidget *dump_view_button = (GtkWidget *)g_object_get_data(G_OBJECT(win), "dump_view_button");
    40     dump_data_t data = malloc( sizeof(struct dump_data) );
    41     data->_tag = DUMP_DATA_TAG;
    42     data->fromInput = (GtkEntry *)g_object_get_data(G_OBJECT(win), "dump_from");
    43     data->toInput = (GtkEntry *)g_object_get_data(G_OBJECT(win), "dump_to");
    44     data->textArea = (GtkTextView *)g_object_get_data(G_OBJECT(win), "dump_text");
    45     data->next = dump_list_head;
    46     dump_list_head = data;
    47     data->data = NULL;
    48     data->start = 0;
    49     data->end = 0;
    50     gtk_entry_set_text( data->fromInput, "" );
    51     gtk_entry_set_text( data->toInput, "" );
    52     data->textBuffer = gtk_text_buffer_new(NULL);
    53     data->changedTag = gtk_text_buffer_create_tag(data->textBuffer, "changed",
    54                                                  "foreground", "blue",
    55                                                   NULL);
    56     gtk_text_view_set_buffer(data->textArea, data->textBuffer);
    57     gtk_text_view_set_editable(data->textArea, FALSE);
    58     gtk_widget_modify_font(GTK_WIDGET(data->textArea),fixed_list_font);
    60     g_signal_connect ((gpointer) win, "delete_event",
    61                       G_CALLBACK (on_dump_win_delete_event),
    62                       data);
    63     g_signal_connect ((gpointer) dump_view_button, "clicked",
    64                       G_CALLBACK (on_dump_win_button_view_clicked),
    65                       data);
    66     gtk_widget_show( GTK_WIDGET(win) );
    67 }
    71 gboolean on_dump_win_delete_event( GtkWidget *widget, GdkEvent *event,
    72                                    gpointer user_data )
    73 {
    74     dump_data_t data = (dump_data_t)user_data;
    75     if( data->data != NULL )
    76         free( data->data );
    77     dump_data_t node = dump_list_head;
    78     if( node == data )
    79         dump_list_head = data->next;
    80     else {
    81         while( node->next != data ) {
    82             node = node->next;
    83             assert( node != NULL );
    84         }
    85         node->next = data->next;
    86     }
    87     free( data );
    88     return FALSE;
    89 }
    91 void on_dump_win_button_view_clicked( GtkWidget *widget, gpointer user_data )
    92 {
    93     dump_data_t data = (dump_data_t)user_data;
    94     uint32_t startVal, endVal;
    96     assert( data != NULL );
    97     assert( data->_tag == DUMP_DATA_TAG );
    99     startVal = gtk_entry_get_hex_value(data->fromInput, data->start);
   100     endVal = gtk_entry_get_hex_value(data->toInput, data->end);
   101     if( startVal != data->start || endVal != data->end ) {
   102         if( startVal > endVal ) {
   103             int tmp = endVal;
   104             endVal = startVal;
   105             startVal = tmp;
   106         }
   107         if( endVal > startVal + MAX_DUMP_SIZE )
   108             endVal = startVal + MAX_DUMP_SIZE;
   110         gtk_entry_set_hex_value(data->fromInput,startVal);
   111         gtk_entry_set_hex_value(data->toInput,endVal);
   112         data->start = startVal;
   113         data->end = endVal;
   115         if( data->data != NULL ) {
   116             free( data->data );
   117             data->data = NULL;
   118         }
   119         if( startVal != endVal ) {
   120             data->data = malloc( endVal - startVal );
   121             mem_copy_from_sh4( data->data, startVal, endVal-startVal );
   122             dump_win_set_text( data, data->data, data->data );
   123         }
   124     }
   125 }
   127 void dump_win_update( dump_data_t data )
   128 {
   129     if( data->data == NULL )
   130         return;
   131     char tmp[data->end-data->start];
   132     int length = data->end-data->start;
   133     memcpy( tmp, data->data, length );
   134     mem_copy_from_sh4( data->data, data->start, length );
   135     dump_win_set_text( data, tmp, data->data );
   136 }
   138 void dump_win_update_all( )
   139 {
   140     dump_data_t node = dump_list_head;
   141     while( node != NULL ) {
   142         dump_win_update(node);
   143         node = node->next;
   144     }
   145 }
   147 void dump_win_set_text( dump_data_t data, char *old_data, char *new_data )
   148 {
   149     GtkTextBuffer *buf = data->textBuffer;
   150     GtkTextTag *changedTag = data->changedTag;
   151     GtkTextIter iter, endIter;
   152     int i, j, offset;
   153     /* Clear out the buffer */
   154     gtk_text_buffer_get_start_iter(buf,&iter);
   155     gtk_text_buffer_get_end_iter(buf,&endIter);
   156     gtk_text_buffer_delete(buf,&iter,&endIter);
   157     gtk_text_buffer_get_start_iter(buf,&iter);
   159     for( offset = 0, i=data->start; i<data->end; i+=16, offset+=16 ) {
   160         char text[80];
   161         sprintf(text, "%08X:", i );
   162         gtk_text_buffer_insert( buf, &iter, text, 9 );
   163         for( j=0; j<16; j++ ) {
   164             if( j%4 == 0 )
   165                 gtk_text_buffer_insert( buf, &iter, " ", 1 );
   166             if( i+j < data->end ) {
   167                 int oldVal = ((int)old_data[offset+j])&0xFF;
   168                 int newVal = ((int)new_data[offset+j])&0xFF;
   169                 sprintf(text, "%02X ", newVal);
   170                 if( oldVal == newVal )
   171                     gtk_text_buffer_insert( buf, &iter, text, 3 );
   172                 else
   173                     gtk_text_buffer_insert_with_tags( buf, &iter, text, 3,
   174                                                       changedTag, NULL );
   175             } else {
   176                 gtk_text_buffer_insert( buf, &iter, "   ", 3 );
   177             }
   178         }
   179         gtk_text_buffer_insert( buf, &iter, "  ", 2 );
   180         for( j=0; j<16 && i+j < data->end; j++ ) {
   181             int oldVal = ((int)old_data[offset+j])&0xFF;
   182             int newVal = ((int)new_data[offset+j])&0xFF;
   183             if( isprint(newVal) )
   184                 sprintf( text, "%c", newVal );
   185             else strcpy( text, "." );
   186             if( oldVal == newVal )
   187                 gtk_text_buffer_insert( buf, &iter, text, 1 );
   188             else
   189                 gtk_text_buffer_insert_with_tags( buf, &iter, text, 1,
   190                                                   changedTag, NULL );
   191         }
   192         gtk_text_buffer_insert( buf, &iter, "\n", 1 );
   193     }
   194 }
.