sim: bfin: add hw tracing to gpio/sic port events
[deliverable/binutils-gdb.git] / gdb / tui / tui-source.c
CommitLineData
f377b406 1/* TUI display source window.
f33c6cbf 2
4c38e0a4 3 Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2007, 2008, 2009,
7b6bb8da 4 2010, 2011 Free Software Foundation, Inc.
f33c6cbf 5
f377b406
SC
6 Contributed by Hewlett-Packard Company.
7
8 This file is part of GDB.
9
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
a9762ec7 12 the Free Software Foundation; either version 3 of the License, or
f377b406
SC
13 (at your option) any later version.
14
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
19
20 You should have received a copy of the GNU General Public License
a9762ec7 21 along with this program. If not, see <http://www.gnu.org/licenses/>. */
c906108c
SS
22
23#include "defs.h"
24#include <ctype.h>
25#include "symtab.h"
26#include "frame.h"
27#include "breakpoint.h"
c2c6d25f 28#include "source.h"
a4b99e53 29#include "symtab.h"
13274fc3 30#include "objfiles.h"
c906108c 31
d7b2e967
AC
32#include "tui/tui.h"
33#include "tui/tui-data.h"
34#include "tui/tui-stack.h"
35#include "tui/tui-winsource.h"
36#include "tui/tui-source.h"
c906108c 37
88289b6e 38#include "gdb_string.h"
6a83354a 39#include "gdb_curses.h"
c906108c 40
98427f35 41/* Function to display source in the source window. */
a358af15 42enum tui_status
08ef48c5
MS
43tui_set_source_content (struct symtab *s,
44 int line_no,
45 int noerror)
c906108c 46{
22940a24 47 enum tui_status ret = TUI_FAILURE;
c906108c
SS
48
49 if (s != (struct symtab *) NULL && s->filename != (char *) NULL)
50 {
d02c80cd
AC
51 FILE *stream;
52 int i, desc, c, line_width, nlines;
53 char *src_line = 0;
c906108c 54
6d012f14 55 if ((ret = tui_alloc_source_buffer (TUI_SRC_WIN)) == TUI_SUCCESS)
c906108c 56 {
6ba8e26f 57 line_width = TUI_SRC_WIN->generic.width - 1;
1cc6d956
MS
58 /* Take hilite (window border) into account, when
59 calculating the number of lines. */
6d012f14 60 nlines = (line_no + (TUI_SRC_WIN->generic.height - 2)) - line_no;
c906108c
SS
61 desc = open_source_file (s);
62 if (desc < 0)
63 {
64 if (!noerror)
65 {
66 char *name = alloca (strlen (s->filename) + 100);
1c5313c5 67
6d012f14 68 sprintf (name, "%s:%d", s->filename, line_no);
c906108c
SS
69 print_sys_errmsg (name, errno);
70 }
71 ret = TUI_FAILURE;
72 }
73 else
74 {
75 if (s->line_charpos == 0)
76 find_source_lines (s, desc);
77
6d012f14 78 if (line_no < 1 || line_no > s->nlines)
c906108c
SS
79 {
80 close (desc);
81 printf_unfiltered (
82 "Line number %d out of range; %s has %d lines.\n",
6d012f14 83 line_no, s->filename, s->nlines);
c906108c 84 }
6d012f14 85 else if (lseek (desc, s->line_charpos[line_no - 1], 0) < 0)
c906108c
SS
86 {
87 close (desc);
88 perror_with_name (s->filename);
89 }
90 else
91 {
d02c80cd 92 int offset, cur_line_no, cur_line, cur_len, threshold;
9a2b4c1b
MS
93 struct tui_gen_win_info *locator
94 = tui_locator_win_info_ptr ();
95 struct tui_source_info *src
96 = &TUI_SRC_WIN->detail.source_info;
bc6b7f04 97
6d012f14
AC
98 if (TUI_SRC_WIN->generic.title)
99 xfree (TUI_SRC_WIN->generic.title);
100 TUI_SRC_WIN->generic.title = xstrdup (s->filename);
bc6b7f04
SC
101
102 if (src->filename)
103 xfree (src->filename);
104 src->filename = xstrdup (s->filename);
105
1cc6d956
MS
106 /* Determine the threshold for the length of the
107 line and the offset to start the display. */
6d012f14 108 offset = src->horizontal_offset;
6ba8e26f 109 threshold = (line_width - 1) + offset;
c906108c
SS
110 stream = fdopen (desc, FOPEN_RT);
111 clearerr (stream);
6ba8e26f 112 cur_line = 0;
13274fc3 113 src->gdbarch = get_objfile_arch (s->objfile);
362c05fe
AS
114 src->start_line_or_addr.loa = LOA_LINE;
115 cur_line_no = src->start_line_or_addr.u.line_no = line_no;
c906108c 116 if (offset > 0)
6ba8e26f 117 src_line = (char *) xmalloc (
c906108c 118 (threshold + 1) * sizeof (char));
6ba8e26f 119 while (cur_line < nlines)
c906108c 120 {
9a2b4c1b
MS
121 struct tui_win_element *element
122 = (struct tui_win_element *)
1c5313c5 123 TUI_SRC_WIN->generic.content[cur_line];
c906108c 124
1cc6d956 125 /* Get the first character in the line. */
c906108c
SS
126 c = fgetc (stream);
127
128 if (offset == 0)
6ba8e26f 129 src_line = ((struct tui_win_element *)
6d012f14 130 TUI_SRC_WIN->generic.content[
6ba8e26f 131 cur_line])->which_element.source.line;
1cc6d956 132 /* Init the line with the line number. */
6ba8e26f
AC
133 sprintf (src_line, "%-6d", cur_line_no);
134 cur_len = strlen (src_line);
9a2b4c1b
MS
135 i = cur_len - ((cur_len / tui_default_tab_len ())
136 * tui_default_tab_len ());
dd1abb8c 137 while (i < tui_default_tab_len ())
c906108c 138 {
6ba8e26f 139 src_line[cur_len] = ' ';
c906108c 140 i++;
6ba8e26f 141 cur_len++;
c906108c 142 }
6ba8e26f 143 src_line[cur_len] = (char) 0;
c906108c 144
1cc6d956
MS
145 /* Set whether element is the execution point
146 and whether there is a break point on it. */
362c05fe
AS
147 element->which_element.source.line_or_addr.loa =
148 LOA_LINE;
149 element->which_element.source.line_or_addr.u.line_no =
6ba8e26f 150 cur_line_no;
6d012f14 151 element->which_element.source.is_exec_point =
2a8854a7 152 (strcmp (((struct tui_win_element *)
e5908723 153 locator->content[0])->which_element.locator.file_name,
c906108c 154 s->filename) == 0
6ba8e26f 155 && cur_line_no == ((struct tui_win_element *)
e5908723 156 locator->content[0])->which_element.locator.line_no);
c906108c
SS
157 if (c != EOF)
158 {
6ba8e26f 159 i = strlen (src_line) - 1;
c906108c
SS
160 do
161 {
e5908723
MS
162 if ((c != '\n') && (c != '\r')
163 && (++i < threshold))
c906108c
SS
164 {
165 if (c < 040 && c != '\t')
166 {
6ba8e26f
AC
167 src_line[i++] = '^';
168 src_line[i] = c + 0100;
c906108c
SS
169 }
170 else if (c == 0177)
171 {
6ba8e26f
AC
172 src_line[i++] = '^';
173 src_line[i] = '?';
c906108c
SS
174 }
175 else
1cc6d956
MS
176 { /* Store the charcter in the
177 line buffer. If it is a tab,
178 then translate to the correct
179 number of chars so we don't
180 overwrite our buffer. */
c906108c
SS
181 if (c == '\t')
182 {
9a2b4c1b
MS
183 int j, max_tab_len
184 = tui_default_tab_len ();
c906108c 185
9a2b4c1b
MS
186 for (j = i - ((i / max_tab_len)
187 * max_tab_len);
e5908723
MS
188 j < max_tab_len
189 && i < threshold;
c906108c 190 i++, j++)
6ba8e26f 191 src_line[i] = ' ';
c906108c
SS
192 i--;
193 }
194 else
6ba8e26f 195 src_line[i] = c;
c906108c 196 }
6ba8e26f 197 src_line[i + 1] = 0;
c906108c
SS
198 }
199 else
1cc6d956
MS
200 { /* If we have not reached EOL, then
201 eat chars until we do. */
c906108c
SS
202 while (c != EOF && c != '\n' && c != '\r')
203 c = fgetc (stream);
861cf606 204 /* Handle non-'\n' end-of-line. */
e5908723
MS
205 if (c == '\r'
206 && (c = fgetc (stream)) != '\n'
207 && c != EOF)
861cf606
FR
208 {
209 ungetc (c, stream);
210 c = '\r';
211 }
212
c906108c
SS
213 }
214 }
e5908723
MS
215 while (c != EOF && c != '\n' && c != '\r'
216 && i < threshold
217 && (c = fgetc (stream)));
c906108c 218 }
1cc6d956
MS
219 /* Now copy the line taking the offset into
220 account. */
6ba8e26f 221 if (strlen (src_line) > offset)
9a2b4c1b
MS
222 strcpy (((struct tui_win_element *)
223 TUI_SRC_WIN->generic.content[cur_line])->which_element.source.line,
6ba8e26f 224 &src_line[offset]);
c906108c 225 else
2a8854a7 226 ((struct tui_win_element *)
6d012f14 227 TUI_SRC_WIN->generic.content[
6ba8e26f
AC
228 cur_line])->which_element.source.line[0] = (char) 0;
229 cur_line++;
230 cur_line_no++;
c906108c
SS
231 }
232 if (offset > 0)
6ba8e26f 233 xfree (src_line);
c906108c 234 fclose (stream);
6d012f14 235 TUI_SRC_WIN->generic.content_size = nlines;
c906108c
SS
236 ret = TUI_SUCCESS;
237 }
238 }
239 }
240 }
241 return ret;
98427f35 242}
c906108c
SS
243
244
1cc6d956 245/* elz: This function sets the contents of the source window to empty
c906108c 246 except for a line in the middle with a warning message about the
1cc6d956 247 source not being available. This function is called by
6ba8e26f
AC
248 tui_erase_source_contents(), which in turn is invoked when the
249 source files cannot be accessed. */
c906108c
SS
250
251void
08ef48c5
MS
252tui_set_source_content_nil (struct tui_win_info *win_info,
253 char *warning_string)
c906108c 254{
6ba8e26f
AC
255 int line_width;
256 int n_lines;
c906108c
SS
257 int curr_line = 0;
258
6ba8e26f
AC
259 line_width = win_info->generic.width - 1;
260 n_lines = win_info->generic.height - 2;
c906108c 261
1cc6d956
MS
262 /* Set to empty each line in the window, except for the one which
263 contains the message. */
6ba8e26f 264 while (curr_line < win_info->generic.content_size)
c906108c 265 {
1cc6d956
MS
266 /* Set the information related to each displayed line to null:
267 i.e. the line number is 0, there is no bp, it is not where
268 the program is stopped. */
c906108c 269
5b6fe301
MS
270 struct tui_win_element *element =
271 (struct tui_win_element *) win_info->generic.content[curr_line];
1c5313c5 272
362c05fe
AS
273 element->which_element.source.line_or_addr.loa = LOA_LINE;
274 element->which_element.source.line_or_addr.u.line_no = 0;
6d012f14
AC
275 element->which_element.source.is_exec_point = FALSE;
276 element->which_element.source.has_break = FALSE;
c906108c 277
1cc6d956 278 /* Set the contents of the line to blank. */
6d012f14 279 element->which_element.source.line[0] = (char) 0;
c906108c 280
1cc6d956 281 /* If the current line is in the middle of the screen, then we
6ba8e26f
AC
282 want to display the 'no source available' message in it.
283 Note: the 'weird' arithmetic with the line width and height
1cc6d956
MS
284 comes from the function tui_erase_source_content(). We need
285 to keep the screen and the window's actual contents in
286 synch. */
c906108c 287
6ba8e26f 288 if (curr_line == (n_lines / 2 + 1))
c906108c
SS
289 {
290 int i;
291 int xpos;
292 int warning_length = strlen (warning_string);
6ba8e26f 293 char *src_line;
c906108c 294
6ba8e26f 295 src_line = element->which_element.source.line;
c906108c 296
6ba8e26f 297 if (warning_length >= ((line_width - 1) / 2))
c906108c
SS
298 xpos = 1;
299 else
6ba8e26f 300 xpos = (line_width - 1) / 2 - warning_length;
c906108c
SS
301
302 for (i = 0; i < xpos; i++)
6ba8e26f 303 src_line[i] = ' ';
c906108c 304
6ba8e26f 305 sprintf (src_line + i, "%s", warning_string);
c906108c 306
6ba8e26f
AC
307 for (i = xpos + warning_length; i < line_width; i++)
308 src_line[i] = ' ';
c906108c 309
6ba8e26f 310 src_line[i] = '\n';
c906108c
SS
311
312 } /* end if */
313
314 curr_line++;
315
c5aa993b 316 } /* end while */
98427f35 317}
c906108c
SS
318
319
98427f35
SC
320/* Function to display source in the source window. This function
321 initializes the horizontal scroll to 0. */
c906108c 322void
13274fc3 323tui_show_symtab_source (struct gdbarch *gdbarch, struct symtab *s,
08ef48c5
MS
324 struct tui_line_or_address line,
325 int noerror)
c906108c 326{
6d012f14 327 TUI_SRC_WIN->detail.source_info.horizontal_offset = 0;
13274fc3 328 tui_update_source_window_as_is (TUI_SRC_WIN, gdbarch, s, line, noerror);
98427f35 329}
c906108c 330
c906108c 331
a358af15
AC
332/* Answer whether the source is currently displayed in the source
333 window. */
c906108c 334int
a358af15 335tui_source_is_displayed (char *fname)
c906108c 336{
e5908723 337 return (TUI_SRC_WIN->generic.content_in_use
9a2b4c1b
MS
338 && (strcmp (((struct tui_win_element *)
339 (tui_locator_win_info_ptr ())->
340 content[0])->which_element.locator.file_name,
341 fname) == 0));
98427f35 342}
c906108c
SS
343
344
98427f35 345/* Scroll the source forward or backward vertically. */
c906108c 346void
6ba8e26f
AC
347tui_vertical_source_scroll (enum tui_scroll_direction scroll_direction,
348 int num_to_scroll)
c906108c 349{
6d012f14 350 if (TUI_SRC_WIN->generic.content != NULL)
c906108c 351 {
362c05fe 352 struct tui_line_or_address l;
c906108c 353 struct symtab *s;
6d012f14 354 tui_win_content content = (tui_win_content) TUI_SRC_WIN->generic.content;
52575520 355 struct symtab_and_line cursal = get_current_source_symtab_and_line ();
c906108c 356
52575520 357 if (cursal.symtab == (struct symtab *) NULL)
206415a3 358 s = find_pc_symtab (get_frame_pc (get_selected_frame (NULL)));
c906108c 359 else
52575520 360 s = cursal.symtab;
c906108c 361
362c05fe 362 l.loa = LOA_LINE;
6ba8e26f 363 if (scroll_direction == FORWARD_SCROLL)
c906108c 364 {
362c05fe
AS
365 l.u.line_no = content[0]->which_element.source.line_or_addr.u.line_no
366 + num_to_scroll;
367 if (l.u.line_no > s->nlines)
1cc6d956
MS
368 /* line = s->nlines - win_info->generic.content_size + 1; */
369 /* elz: fix for dts 23398. */
9a2b4c1b
MS
370 l.u.line_no
371 = content[0]->which_element.source.line_or_addr.u.line_no;
c906108c
SS
372 }
373 else
374 {
362c05fe
AS
375 l.u.line_no = content[0]->which_element.source.line_or_addr.u.line_no
376 - num_to_scroll;
377 if (l.u.line_no <= 0)
378 l.u.line_no = 1;
c906108c 379 }
27229e99 380
362c05fe 381 print_source_lines (s, l.u.line_no, l.u.line_no + 1, 0);
c906108c 382 }
98427f35 383}
This page took 1.430474 seconds and 4 git commands to generate.