7 #include "debugtools.h"
11 /* ---------------------------------------------------------------------- */
15 char *str_pos
; /* current position in strings buffer */
16 char *out_pos
; /* current position in output buffer */
17 char strings
[500]; /* buffer for temporary strings */
18 char output
[500]; /* current output line */
21 static struct debug_info tmp
;
23 static inline struct debug_info
*get_info(void)
25 struct debug_info
*info
= NtCurrentTeb()->debug_info
;
28 /* setup the temp structure in case HeapAlloc wants to print something */
29 NtCurrentTeb()->debug_info
= &tmp
;
30 tmp
.str_pos
= tmp
.strings
;
31 tmp
.out_pos
= tmp
.output
;
32 info
= HeapAlloc( GetProcessHeap(), 0, sizeof(*info
) );
33 info
->str_pos
= info
->strings
;
34 info
->out_pos
= info
->output
;
35 NtCurrentTeb()->debug_info
= info
;
40 /* ---------------------------------------------------------------------- */
45 struct debug_info
*info
= get_info();
46 char *res
= info
->str_pos
;
48 if (res
+ n
>= &info
->strings
[sizeof(info
->strings
)]) res
= info
->strings
;
49 info
->str_pos
= res
+ n
;
53 /* ---------------------------------------------------------------------- */
55 LPCSTR
debugstr_an (LPCSTR src
, int n
)
59 if (!src
) return "(null)";
61 dst
= res
= gimme1 (n
* 4 + 6);
63 while (n
-- > 0 && *src
)
68 case '\n': *dst
++ = '\\'; *dst
++ = 'n'; break;
69 case '\r': *dst
++ = '\\'; *dst
++ = 'r'; break;
70 case '\t': *dst
++ = '\\'; *dst
++ = 't'; break;
71 case '"': *dst
++ = '\\'; *dst
++ = '"'; break;
72 case '\\': *dst
++ = '\\'; *dst
++ = '\\'; break;
74 if (c
>= ' ' && c
<= 126)
79 *dst
++ = '0' + ((c
>> 6) & 7);
80 *dst
++ = '0' + ((c
>> 3) & 7);
81 *dst
++ = '0' + ((c
>> 0) & 7);
96 /* ---------------------------------------------------------------------- */
98 LPCSTR
debugstr_wn (LPCWSTR src
, int n
)
102 if (!src
) return "(null)";
104 dst
= res
= gimme1 (n
* 5 + 7);
107 while (n
-- > 0 && *src
)
112 case '\n': *dst
++ = '\\'; *dst
++ = 'n'; break;
113 case '\r': *dst
++ = '\\'; *dst
++ = 'r'; break;
114 case '\t': *dst
++ = '\\'; *dst
++ = 't'; break;
115 case '"': *dst
++ = '\\'; *dst
++ = '"'; break;
116 case '\\': *dst
++ = '\\'; *dst
++ = '\\'; break;
118 if (c
>= ' ' && c
<= 126)
123 sprintf(dst
,"%04x",c
);
139 /* ---------------------------------------------------------------------- */
140 /* This routine returns a nicely formated name of the resource res
141 If the resource name is a string, it will return '<res-name>'
142 If it is a number, it will return #<4-digit-hex-number> */
143 LPCSTR
debugres_a( LPCSTR res
)
146 if (HIWORD(res
)) return debugstr_a(res
);
148 sprintf(resname
, "#%04x", LOWORD(res
) );
152 LPCSTR
debugres_w( LPCWSTR res
)
155 if (HIWORD(res
)) return debugstr_w(res
);
157 sprintf( resname
, "#%04x", LOWORD(res
) );
161 /* ---------------------------------------------------------------------- */
163 LPCSTR
debugstr_guid( const GUID
*id
)
167 if (!id
) return "(null)";
171 sprintf( str
, "<guid-0x%04x>", LOWORD(id
) );
176 sprintf( str
, "{%08lx-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",
177 id
->Data1
, id
->Data2
, id
->Data3
,
178 id
->Data4
[0], id
->Data4
[1], id
->Data4
[2], id
->Data4
[3],
179 id
->Data4
[4], id
->Data4
[5], id
->Data4
[6], id
->Data4
[7] );
184 /* ---------------------------------------------------------------------- */
186 int dbg_vprintf( const char *format
, va_list args
)
188 struct debug_info
*info
= get_info();
190 int ret
= vsprintf( info
->out_pos
, format
, args
);
191 char *p
= strrchr( info
->out_pos
, '\n' );
192 if (!p
) info
->out_pos
+= ret
;
195 char *pos
= info
->output
;
197 write( 2, pos
, p
- pos
);
198 /* move beginning of next line to start of buffer */
199 while ((*pos
= *p
++)) pos
++;
205 /* ---------------------------------------------------------------------- */
207 int dbg_printf(const char *format
, ...)
212 va_start(valist
, format
);
213 ret
= dbg_vprintf( format
, valist
);
219 /*--< Function >---------------------------------------------------------
224 ** This function creates a hex dump, with a readable ascii
225 ** section, for displaying memory.
228 ** 1. ptr Pointer to memory
229 ** 2. len How much to dump.
232 ** Temporarily allocated buffer, with the hex dump in it.
233 ** Don't rely on this pointer being around for very long, just
234 ** long enough to use it in a TRACE statement; e.g.:
235 ** TRACE("struct dump is \n%s", debugstr_hex_dump(&x, sizeof(x)));
237 **-------------------------------------------------------------------------*/
238 LPCSTR
debugstr_hex_dump (const void *ptr
, int len
)
250 /* Begin function dbg_hex_dump */
252 /*-----------------------------------------------------------------------
253 ** Allocate an output buffer
254 ** A reasonable value is one line overhand (80 chars), and
255 ** then one line (80) for every 16 bytes.
256 **---------------------------------------------------------------------*/
257 outptr
= dst
= gimme1 ((len
* (80 / 16)) + 80);
259 /*-----------------------------------------------------------------------
260 ** Loop throught the input buffer, one character at a time
261 **---------------------------------------------------------------------*/
262 for (i
= 0, p
= ptr
; (i
< len
); i
++, p
++)
265 /*-------------------------------------------------------------------
266 ** If we're just starting a line,
267 ** we need to possibly flush the old line, and then
268 ** intialize the line buffer.
269 **-----------------------------------------------------------------*/
274 sprintf(outptr
, " %-43.43s %-16.16s\n", dumpbuf
, charbuf
);
275 outptr
+= strlen(outptr
);
277 sprintf (dumpbuf
, "%04x: ", i
);
278 strcpy (charbuf
, "");
281 /*-------------------------------------------------------------------
282 ** Add the current data byte to the dump section.
283 **-----------------------------------------------------------------*/
284 nosign
= (unsigned char) *p
;
285 sprintf (tempbuf
, "%02X", nosign
);
287 /*-------------------------------------------------------------------
288 ** If we're two DWORDS through, add a hyphen for readability,
289 ** if it's a DWORD boundary, add a space for more
291 **-----------------------------------------------------------------*/
293 strcat(tempbuf
, " - ");
294 else if ( (i
% 4) == 3)
295 strcat(tempbuf
, " ");
296 strcat (dumpbuf
, tempbuf
);
298 /*-------------------------------------------------------------------
299 ** Add the current byte to the character display part of the
301 **-----------------------------------------------------------------*/
302 sprintf (tempbuf
, "%c", isprint(*p
) ? *p
: '.');
303 strcat (charbuf
, tempbuf
);
306 /*-----------------------------------------------------------------------
307 ** Flush the last line, if any
308 **---------------------------------------------------------------------*/
311 sprintf(outptr
, " %-43.43s %-16.16s\n", dumpbuf
, charbuf
);
312 outptr
+= strlen(outptr
);
316 } /* End function dbg_hex_dump */