1 /*
2  *    TTTTTTTTTTTTTT  EEEEEEEEEEEEEE  OOOOOOOOOOOOOO
3  *    TTTTTTTTTTTTTT  EEEEEEEEEEEEEE  OOOOOOOOOOOOOO
4  *          TT        EE              OO          OO
5  *          TT        EE              OO          OO
6  *          TT        EE              OO          OO
7  *          TT        EEEEEEEEEE      OO          OO
8  *          TT        EEEEEEEEEE      OO          OO
9  *          TT        EE              OO          OO
10  *          TT        EE              OO          OO
11  *          TT        EE              OO          OO
12  *          TT        EEEEEEEEEEEEEE  OOOOOOOOOOOOOO
13  *          TT        EEEEEEEEEEEEEE  OOOOOOOOOOOOOO
14  *
15  *                  L'�mulateur Thomson TO8
16  *
17  *  Copyright (C) 1997-2017 Gilles F�tis, Eric Botcazou, Alexandre Pukall,
18  *                          J�r�mie Guillaume, Fran�ois Mouret
19  *
20  *  This program is free software; you can redistribute it and/or modify
21  *  it under the terms of the GNU General Public License as published by
22  *  the Free Software Foundation; either version 2 of the License, or
23  *  (at your option) any later version.
24  *
25  *  This program is distributed in the hope that it will be useful,
26  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
27  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
28  *  GNU General Public License for more details.
29  *
30  *  You should have received a copy of the GNU General Public License
31  *  along with this program; if not, write to the Free Software
32  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
33  */
34 
35 /*
36  *  Module     : linux/udebug/udreg.c
37  *  Version    : 1.8.4
38  *  Cr�� par   : Fran�ois Mouret 14/07/2016
39  *  Modifi� par:
40  *
41  *  D�bogueur 6809 - Affichage des registres.
42  */
43 
44 
45 #ifndef SCAN_DEPEND
46    #include <stdio.h>
47    #include <stdlib.h>
48    #include <gtk/gtk.h>
49 #endif
50 
51 #include "defs.h"
52 #include "teo.h"
53 #include "std.h"
54 #include "hardware.h"
55 #include "mc68xx/mc6821.h"
56 #include "mc68xx/dasm6809.h"
57 #include "media/disk.h"
58 #include "debug.h"
59 #include "debug/debug.h"
60 #include "linux/gui.h"
61 
62 static GtkWidget *text_view;
63 static GtkTextBuffer *text_buffer;
64 static GtkTextMark *text_mark;
65 
get_first_visible_line_number(void)66 static int get_first_visible_line_number (void)
67 {
68     int y;
69     int height;
70     GdkRectangle rect;
71     GtkTextIter iter;
72     GtkTextView *view = GTK_TEXT_VIEW (text_view);
73 
74     gtk_text_view_get_visible_rect (view, &rect);
75     gtk_text_view_get_iter_at_location (view, &iter, 0, rect.y);
76     gtk_text_view_get_line_yrange (view, &iter, &y, &height);
77 
78     return (height != 0) ? y/height : y;
79 }
80 
81 
82 
83 /* scroll_to_mark :
84  *  Scroll to the mark in the textview
85  */
scroll_to_mark(GtkTextView * view)86 static void scroll_to_mark (GtkTextView *view)
87 {
88     GtkTextIter iter;
89     GdkRectangle rect_view;
90     GdkRectangle rect_iter;
91     GtkTextBuffer *buffer = gtk_text_view_get_buffer (view);
92 
93     do
94     {
95         gtk_text_view_scroll_to_mark (view, text_mark, 0.0, TRUE, 0.0, 0.0);
96 
97         /* Wait for end of GTK work */
98         while (gtk_events_pending ())
99             gtk_main_iteration ();
100 
101         gtk_text_buffer_get_iter_at_mark (buffer, &iter, text_mark);
102         gtk_text_view_get_iter_location (view, &iter, &rect_iter);
103         gtk_text_view_get_visible_rect (view, &rect_view);
104 
105     } while (((rect_view.y + rect_view.height) < (rect_iter.y+rect_iter.height))
106            || (rect_view.y > rect_iter.y));
107 }
108 
109 
110 
111 /* add_mark:
112  *  Add/Move a mark in the textview.
113  */
add_mark(GtkTextMark * mark,int line,int char_pos)114 static void add_mark (GtkTextMark *mark, int line, int char_pos)
115 {
116     GtkTextIter iter;
117     GtkTextBuffer *buff = GTK_TEXT_BUFFER (text_buffer);
118 
119     gtk_text_buffer_get_iter_at_line_offset (buff, &iter, line, char_pos);
120     if (gtk_text_mark_get_deleted (mark) == TRUE)
121     {
122         gtk_text_buffer_add_mark (buff, mark, &iter);
123     }
124     else
125     {
126         gtk_text_buffer_move_mark (buff, mark, &iter);
127     }
128 }
129 
130 
131 
132 /* scroll_text:
133  *  Scroll the text in the textview.
134  */
scroll_text(int value_line)135 static void scroll_text (int value_line)
136 {
137     int count;
138 
139     count = gtk_text_buffer_get_line_count (GTK_TEXT_BUFFER (text_buffer));
140     if (count > 0)
141     {
142         add_mark (text_mark, value_line, 0);
143         scroll_to_mark (GTK_TEXT_VIEW (text_view));
144     }
145 }
146 
147 
148 
set_text(void)149 static void set_text (void)
150 {
151     char *text = NULL;
152 
153     text = dreg_GetText ("\n");
154     if (text != NULL)
155     {
156         /* Wait for end of GTK work */
157         while (gtk_events_pending ())
158             gtk_main_iteration ();
159 
160         gtk_text_buffer_set_text (GTK_TEXT_BUFFER (text_buffer), text, -1);
161 
162         /* Wait for end of GTK work */
163         while (gtk_events_pending ())
164             gtk_main_iteration ();
165 
166         std_free(text);
167     }
168 }
169 
170 
171 /* ------------------------------------------------------------------------- */
172 
173 
174 /* udreg_Free:
175  *  Free the memory used by the register area.
176  */
udreg_Free(void)177 void udreg_Free(void)
178 {
179 }
180 
181 
182 
183 /* udreg_Init:
184  *  Init register area.
185  */
udreg_Init(void)186 GtkWidget *udreg_Init(void)
187 {
188     GtkWidget *box;
189     GtkWidget *scrolled_window;
190 
191     text_buffer = gtk_text_buffer_new (NULL);
192     text_mark = gtk_text_mark_new ("teo_dreg_mark_first", FALSE);
193 
194     /* Create source view */
195     text_view = gtk_text_view_new_with_buffer (text_buffer);
196     gtk_text_view_set_editable (GTK_TEXT_VIEW(text_view), FALSE);
197     gtk_text_view_set_cursor_visible (GTK_TEXT_VIEW(text_view), FALSE);
198 
199     /* Create scroll window */
200     scrolled_window = gtk_scrolled_window_new (NULL, NULL);
201     gtk_scrolled_window_set_policy (
202         GTK_SCROLLED_WINDOW (scrolled_window),
203         GTK_POLICY_AUTOMATIC,
204         GTK_POLICY_AUTOMATIC);
205     gtk_scrolled_window_set_min_content_height (
206         GTK_SCROLLED_WINDOW (scrolled_window),
207         80);
208 
209     /* Set Courier font */
210     gtk_widget_set_name (scrolled_window, COURIER_DEBUG);
211 
212     /* Pack text view */
213     gtk_container_add (GTK_CONTAINER (scrolled_window), text_view);
214 
215     /* Pack everything in box */
216     box = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0);
217     gtk_box_pack_start (GTK_BOX(box), scrolled_window, FALSE, FALSE, 0);
218 
219     return box;
220 }
221 
222 
223 
224 /* udreg_Display:
225  *  Display extra registers.
226  */
udreg_Display(void)227 void udreg_Display(void)
228 {
229     teo.debug.extra_first_line = get_first_visible_line_number ();
230     udreg_UpdateText ();
231 }
232 
233 
234 
235 /* udreg_UpdateText:
236  *  Set and ccroll text.
237  */
udreg_UpdateText(void)238 void udreg_UpdateText(void)
239 {
240     set_text ();
241     scroll_text (teo.debug.extra_first_line);
242 }
243