8 #include "debugtools.h"
11 /* ---------------------------------------------------------------------- */
13 #define SAVE_STRING_COUNT 50
14 static void *strings
[SAVE_STRING_COUNT
];
15 static int nextstring
;
17 /* ---------------------------------------------------------------------- */
23 if (strings
[nextstring
]) free (strings
[nextstring
]);
24 res
= strings
[nextstring
] = xmalloc (n
);
25 if (++nextstring
== SAVE_STRING_COUNT
) nextstring
= 0;
29 /* ---------------------------------------------------------------------- */
32 debugstr_an (LPCSTR src
, int n
)
36 if (!src
) return "(null)";
38 dst
= res
= gimme1 (n
* 4 + 6);
40 while (n
-- > 0 && *src
)
45 case '\n': *dst
++ = '\\'; *dst
++ = 'n'; break;
46 case '\r': *dst
++ = '\\'; *dst
++ = 'r'; break;
47 case '\t': *dst
++ = '\\'; *dst
++ = 't'; break;
48 case '"': *dst
++ = '\\'; *dst
++ = '"'; break;
49 case '\\': *dst
++ = '\\'; *dst
++ = '\\'; break;
51 if (c
>= ' ' && c
<= 126)
56 *dst
++ = '0' + ((c
>> 6) & 7);
57 *dst
++ = '0' + ((c
>> 3) & 7);
58 *dst
++ = '0' + ((c
>> 0) & 7);
73 /* ---------------------------------------------------------------------- */
78 return debugstr_an (s
, 80);
81 /* ---------------------------------------------------------------------- */
84 debugstr_wn (LPCWSTR src
, int n
)
88 if (!src
) return "(null)";
90 dst
= res
= gimme1 (n
* 5 + 7);
93 while (n
-- > 0 && *src
)
98 case '\n': *dst
++ = '\\'; *dst
++ = 'n'; break;
99 case '\r': *dst
++ = '\\'; *dst
++ = 'r'; break;
100 case '\t': *dst
++ = '\\'; *dst
++ = 't'; break;
101 case '"': *dst
++ = '\\'; *dst
++ = '"'; break;
102 case '\\': *dst
++ = '\\'; *dst
++ = '\\'; break;
104 if (c
>= ' ' && c
<= 126)
109 sprintf(dst
,"%04x",c
);
125 /* ---------------------------------------------------------------------- */
128 debugstr_w (LPCWSTR s
)
130 return debugstr_wn (s
, 80);
133 /* ---------------------------------------------------------------------- */
134 /* This routine returns a nicely formated name of the resource res
135 If the resource name is a string, it will return '<res-name>'
136 If it is a number, it will return #<4-digit-hex-number> */
137 LPSTR
debugres_a( LPCSTR res
)
140 if (HIWORD(res
)) return debugstr_a(res
);
141 sprintf(resname
, "#%04x", LOWORD(res
));
142 return debugstr_a (resname
);
145 LPSTR
debugres_w( LPCWSTR res
)
148 if (HIWORD(res
)) return debugstr_w(res
);
149 sprintf(resname
, "#%04x", LOWORD(res
));
150 return debugstr_a (resname
);
153 /* ---------------------------------------------------------------------- */
155 void debug_dumpstr (LPCSTR s
)
164 fputc ('\\', stderr
);
168 fputc ('\\', stderr
);
172 fputc ('\\', stderr
);
176 fputc ('\\', stderr
);
181 fprintf (stderr
, "\\0x%02x", *s
);
190 /* ---------------------------------------------------------------------- */
192 int dbg_printf(const char *format
, ...)
197 va_start(valist
, format
);
198 ret
= vfprintf(stderr
, format
, valist
);
205 /*--< Function >---------------------------------------------------------
210 ** This function creates a hex dump, with a readable ascii
211 ** section, for displaying memory.
214 ** 1. ptr Pointer to memory
215 ** 2. len How much to dump.
218 ** Temporarily allocated buffer, with the hex dump in it.
219 ** Don't rely on this pointer being around for very long, just
220 ** long enough to use it in a TRACE statement; e.g.:
221 ** TRACE("struct dump is \n%s", debugstr_hex_dump(&x, sizeof(x)));
223 **-------------------------------------------------------------------------*/
225 debugstr_hex_dump (const void *ptr
, int len
)
237 /* Begin function dbg_hex_dump */
239 /*-----------------------------------------------------------------------
240 ** Allocate an output buffer
241 ** A reasonable value is one line overhand (80 chars), and
242 ** then one line (80) for every 16 bytes.
243 **---------------------------------------------------------------------*/
244 outptr
= dst
= gimme1 ((len
* (80 / 16)) + 80);
246 /*-----------------------------------------------------------------------
247 ** Loop throught the input buffer, one character at a time
248 **---------------------------------------------------------------------*/
249 for (i
= 0, p
= ptr
; (i
< len
); i
++, p
++)
252 /*-------------------------------------------------------------------
253 ** If we're just starting a line,
254 ** we need to possibly flush the old line, and then
255 ** intialize the line buffer.
256 **-----------------------------------------------------------------*/
261 sprintf(outptr
, " %-43.43s %-16.16s\n", dumpbuf
, charbuf
);
262 outptr
+= strlen(outptr
);
264 sprintf (dumpbuf
, "%04x: ", i
);
265 strcpy (charbuf
, "");
268 /*-------------------------------------------------------------------
269 ** Add the current data byte to the dump section.
270 **-----------------------------------------------------------------*/
271 nosign
= (unsigned char) *p
;
272 sprintf (tempbuf
, "%02X", nosign
);
274 /*-------------------------------------------------------------------
275 ** If we're two DWORDS through, add a hyphen for readability,
276 ** if it's a DWORD boundary, add a space for more
278 **-----------------------------------------------------------------*/
280 strcat(tempbuf
, " - ");
281 else if ( (i
% 4) == 3)
282 strcat(tempbuf
, " ");
283 strcat (dumpbuf
, tempbuf
);
285 /*-------------------------------------------------------------------
286 ** Add the current byte to the character display part of the
288 **-----------------------------------------------------------------*/
289 sprintf (tempbuf
, "%c", isprint(*p
) ? *p
: '.');
290 strcat (charbuf
, tempbuf
);
293 /*-----------------------------------------------------------------------
294 ** Flush the last line, if any
295 **---------------------------------------------------------------------*/
298 sprintf(outptr
, " %-43.43s %-16.16s\n", dumpbuf
, charbuf
);
299 outptr
+= strlen(outptr
);
303 } /* End function dbg_hex_dump */