Fix elf64-ppc.c electric fence warning
[deliverable/binutils-gdb.git] / gdb / common / print-utils.c
1 /* Cell-based print utility routines for GDB, the GNU debugger.
2
3 Copyright (C) 1986-2015 Free Software Foundation, Inc.
4
5 This file is part of GDB.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
19
20 #include "common-defs.h"
21 #include "print-utils.h"
22 #include <stdint.h>
23
24 /* Temporary storage using circular buffer. */
25
26 #define NUMCELLS 16
27 #define CELLSIZE 50
28
29 /* Return the next entry in the circular buffer. */
30
31 static char *
32 get_cell (void)
33 {
34 static char buf[NUMCELLS][CELLSIZE];
35 static int cell = 0;
36
37 if (++cell >= NUMCELLS)
38 cell = 0;
39 return buf[cell];
40 }
41
42 static char *
43 decimal2str (char *sign, ULONGEST addr, int width)
44 {
45 /* Steal code from valprint.c:print_decimal(). Should this worry
46 about the real size of addr as the above does? */
47 unsigned long temp[3];
48 char *str = get_cell ();
49 int i = 0;
50
51 do
52 {
53 temp[i] = addr % (1000 * 1000 * 1000);
54 addr /= (1000 * 1000 * 1000);
55 i++;
56 width -= 9;
57 }
58 while (addr != 0 && i < (sizeof (temp) / sizeof (temp[0])));
59
60 width += 9;
61 if (width < 0)
62 width = 0;
63
64 switch (i)
65 {
66 case 1:
67 xsnprintf (str, CELLSIZE, "%s%0*lu", sign, width, temp[0]);
68 break;
69 case 2:
70 xsnprintf (str, CELLSIZE, "%s%0*lu%09lu", sign, width,
71 temp[1], temp[0]);
72 break;
73 case 3:
74 xsnprintf (str, CELLSIZE, "%s%0*lu%09lu%09lu", sign, width,
75 temp[2], temp[1], temp[0]);
76 break;
77 default:
78 internal_error (__FILE__, __LINE__,
79 _("failed internal consistency check"));
80 }
81
82 return str;
83 }
84
85 static char *
86 octal2str (ULONGEST addr, int width)
87 {
88 unsigned long temp[3];
89 char *str = get_cell ();
90 int i = 0;
91
92 do
93 {
94 temp[i] = addr % (0100000 * 0100000);
95 addr /= (0100000 * 0100000);
96 i++;
97 width -= 10;
98 }
99 while (addr != 0 && i < (sizeof (temp) / sizeof (temp[0])));
100
101 width += 10;
102 if (width < 0)
103 width = 0;
104
105 switch (i)
106 {
107 case 1:
108 if (temp[0] == 0)
109 xsnprintf (str, CELLSIZE, "%*o", width, 0);
110 else
111 xsnprintf (str, CELLSIZE, "0%0*lo", width, temp[0]);
112 break;
113 case 2:
114 xsnprintf (str, CELLSIZE, "0%0*lo%010lo", width, temp[1], temp[0]);
115 break;
116 case 3:
117 xsnprintf (str, CELLSIZE, "0%0*lo%010lo%010lo", width,
118 temp[2], temp[1], temp[0]);
119 break;
120 default:
121 internal_error (__FILE__, __LINE__,
122 _("failed internal consistency check"));
123 }
124
125 return str;
126 }
127
128 /* See print-utils.h. */
129
130 char *
131 pulongest (ULONGEST u)
132 {
133 return decimal2str ("", u, 0);
134 }
135
136 /* See print-utils.h. */
137
138 char *
139 plongest (LONGEST l)
140 {
141 if (l < 0)
142 return decimal2str ("-", -l, 0);
143 else
144 return decimal2str ("", l, 0);
145 }
146
147 /* Eliminate warning from compiler on 32-bit systems. */
148 static int thirty_two = 32;
149
150 /* See print-utils.h. */
151
152 char *
153 phex (ULONGEST l, int sizeof_l)
154 {
155 char *str;
156
157 switch (sizeof_l)
158 {
159 case 8:
160 str = get_cell ();
161 xsnprintf (str, CELLSIZE, "%08lx%08lx",
162 (unsigned long) (l >> thirty_two),
163 (unsigned long) (l & 0xffffffff));
164 break;
165 case 4:
166 str = get_cell ();
167 xsnprintf (str, CELLSIZE, "%08lx", (unsigned long) l);
168 break;
169 case 2:
170 str = get_cell ();
171 xsnprintf (str, CELLSIZE, "%04x", (unsigned short) (l & 0xffff));
172 break;
173 default:
174 str = phex (l, sizeof (l));
175 break;
176 }
177
178 return str;
179 }
180
181 /* See print-utils.h. */
182
183 char *
184 phex_nz (ULONGEST l, int sizeof_l)
185 {
186 char *str;
187
188 switch (sizeof_l)
189 {
190 case 8:
191 {
192 unsigned long high = (unsigned long) (l >> thirty_two);
193
194 str = get_cell ();
195 if (high == 0)
196 xsnprintf (str, CELLSIZE, "%lx",
197 (unsigned long) (l & 0xffffffff));
198 else
199 xsnprintf (str, CELLSIZE, "%lx%08lx", high,
200 (unsigned long) (l & 0xffffffff));
201 break;
202 }
203 case 4:
204 str = get_cell ();
205 xsnprintf (str, CELLSIZE, "%lx", (unsigned long) l);
206 break;
207 case 2:
208 str = get_cell ();
209 xsnprintf (str, CELLSIZE, "%x", (unsigned short) (l & 0xffff));
210 break;
211 default:
212 str = phex_nz (l, sizeof (l));
213 break;
214 }
215
216 return str;
217 }
218
219 /* See print-utils.h. */
220
221 char *
222 hex_string (LONGEST num)
223 {
224 char *result = get_cell ();
225
226 xsnprintf (result, CELLSIZE, "0x%s", phex_nz (num, sizeof (num)));
227 return result;
228 }
229
230 /* See print-utils.h. */
231
232 char *
233 hex_string_custom (LONGEST num, int width)
234 {
235 char *result = get_cell ();
236 char *result_end = result + CELLSIZE - 1;
237 const char *hex = phex_nz (num, sizeof (num));
238 int hex_len = strlen (hex);
239
240 if (hex_len > width)
241 width = hex_len;
242 if (width + 2 >= CELLSIZE)
243 internal_error (__FILE__, __LINE__, _("\
244 hex_string_custom: insufficient space to store result"));
245
246 strcpy (result_end - width - 2, "0x");
247 memset (result_end - width, '0', width);
248 strcpy (result_end - hex_len, hex);
249 return result_end - width - 2;
250 }
251
252 /* See print-utils.h. */
253
254 char *
255 int_string (LONGEST val, int radix, int is_signed, int width,
256 int use_c_format)
257 {
258 switch (radix)
259 {
260 case 16:
261 {
262 char *result;
263
264 if (width == 0)
265 result = hex_string (val);
266 else
267 result = hex_string_custom (val, width);
268 if (! use_c_format)
269 result += 2;
270 return result;
271 }
272 case 10:
273 {
274 if (is_signed && val < 0)
275 return decimal2str ("-", -val, width);
276 else
277 return decimal2str ("", val, width);
278 }
279 case 8:
280 {
281 char *result = octal2str (val, width);
282
283 if (use_c_format || val == 0)
284 return result;
285 else
286 return result + 1;
287 }
288 default:
289 internal_error (__FILE__, __LINE__,
290 _("failed internal consistency check"));
291 }
292 }
293
294 /* See print-utils.h. */
295
296 const char *
297 core_addr_to_string (const CORE_ADDR addr)
298 {
299 char *str = get_cell ();
300
301 strcpy (str, "0x");
302 strcat (str, phex (addr, sizeof (addr)));
303 return str;
304 }
305
306 /* See print-utils.h. */
307
308 const char *
309 core_addr_to_string_nz (const CORE_ADDR addr)
310 {
311 char *str = get_cell ();
312
313 strcpy (str, "0x");
314 strcat (str, phex_nz (addr, sizeof (addr)));
315 return str;
316 }
317
318 /* See print-utils.h. */
319
320 const char *
321 host_address_to_string (const void *addr)
322 {
323 char *str = get_cell ();
324
325 xsnprintf (str, CELLSIZE, "0x%s", phex_nz ((uintptr_t) addr, sizeof (addr)));
326 return str;
327 }
This page took 0.03562 seconds and 4 git commands to generate.