]> git.unchartedbackwaters.co.uk Git - francis/winuae.git/commitdiff
Debug logging improved format string support.
authorToni Wilen <twilen@winuae.net>
Sun, 24 May 2020 15:23:49 +0000 (18:23 +0300)
committerToni Wilen <twilen@winuae.net>
Sun, 24 May 2020 15:23:49 +0000 (18:23 +0300)
cia.cpp
debug.cpp

diff --git a/cia.cpp b/cia.cpp
index 704a0ea392772e5c90f558b5ca5459eb0aaaf163..0043507ebe1e1c4dde3251da25187112c8538022 100644 (file)
--- a/cia.cpp
+++ b/cia.cpp
@@ -2245,9 +2245,10 @@ static uae_u32 REGPARAM2 cia_lgeti (uaecptr addr)
 
 static bool cia_debug(uaecptr addr, uae_u32 value, int size)
 {
-       if (addr == DEBUG_SPRINTF_ADDRESS || addr == DEBUG_SPRINTF_ADDRESS + 4 ||
+       if (addr == DEBUG_SPRINTF_ADDRESS || addr == DEBUG_SPRINTF_ADDRESS + 4 || addr == DEBUG_SPRINTF_ADDRESS + 8 ||
                (addr == DEBUG_SPRINTF_ADDRESS + 2 && currprefs.cpu_model < 68020) ||
-               (addr == DEBUG_SPRINTF_ADDRESS + 6 && currprefs.cpu_model < 68020)) {
+               (addr == DEBUG_SPRINTF_ADDRESS + 6 && currprefs.cpu_model < 68020) ||
+               (addr == DEBUG_SPRINTF_ADDRESS + 10 && currprefs.cpu_model < 68020)) {
                return debug_sprintf(addr, value, size);
        }
        return false;
index 5d2e11ad135f61abb74bc52cb36f181d615e3a26..1faf9d81a587b1381214d9d854d1646c24c2cc83 100644 (file)
--- a/debug.cpp
+++ b/debug.cpp
@@ -7229,6 +7229,8 @@ struct dsprintfstack
 static dsprintfstack debugsprintf_stack[DEBUGSPRINTF_SIZE];
 static uae_u16 debugsprintf_latch, debugsprintf_latched;
 static uae_u32 debugsprintf_cycles, debugsprintf_cycles_set;
+static uaecptr debugsprintf_va;
+static int debugsprintf_mode;
 
 static void read_bstring(char *out, int max, uae_u32 addr)
 {
@@ -7269,18 +7271,66 @@ static void read_string(char *out, int max, uae_u32 addr)
        }
 }
 
-static char *parse_custom(char *p, char *d)
+static void parse_custom(char *out, int buffersize, char *format, char *p, char c)
 {
+       bool gotv = false;
+       bool gots = false;
+       out[0] = 0;
+       uae_u32 v = 0;
+       char s[256];
        if (!strcmp(p, "CYCLES")) {
                if (debugsprintf_cycles_set) {
-                       uae_u32 c = (get_cycles() - debugsprintf_cycles) / CYCLE_UNIT;
-                       sprintf(d, "%u", c);
+                       v = (get_cycles() - debugsprintf_cycles) / CYCLE_UNIT;
+               } else {
+                       v = 0xffffffff;
+               }
+               gotv = true;
+       }
+       if (gotv) {
+               if (c == 'x' || c == 'X' || c == 'd' || c == 'i' || c == 'u' || c == 'o') {
+                       char *fs = format + strlen(format);
+                       *fs++ = c;
+                       *fs = 0;
+                       snprintf(out, buffersize, format, v);
+               } else {
+                       strcpy(s, "****");
+                       gots = true;
+               }
+       }
+       if (gots) {
+               char *fs = format + strlen(format);
+               *fs++ = 's';
+               *fs = 0;
+               snprintf(out, buffersize, format, s);
+       }
+}
+
+static uae_u32 get_value(struct dsprintfstack **stackp, uae_u32 *sizep, uaecptr *ptrp, uae_u32 size)
+{
+       if (debugsprintf_mode) {
+               uae_u32 v;
+               uaecptr ptr = *ptrp;
+               if (size == sz_long) {
+                       v = get_long_debug(ptr);
+                       ptr += 4;
+               } else if (size == sz_word) {
+                       v = get_word_debug(ptr);
+                       ptr += 2;
                } else {
-                       strcpy(d, "-");
+                       v = get_byte_debug(ptr);
+                       ptr++;
                }
-               d += strlen(d);
+               *ptrp = ptr;
+               *sizep = size;
+               return v;
+       } else {
+               struct dsprintfstack *stack = *stackp;
+               uae_u32 v = stack->val;
+               *sizep = stack->size;
+               stack++;
+               *stackp = stack;
+               return v;
        }
-       return d;
 }
 
 static void debug_sprintf_do(uae_u32 s)
@@ -7291,53 +7341,98 @@ static void debug_sprintf_do(uae_u32 s)
        read_string(format, MAX_DPATH - 1, s);
        char *p = format;
        char *d = out;
+       bool gotm = false;
+       bool l = false;
+       uaecptr ptr = debugsprintf_va;
        struct dsprintfstack *stack = debugsprintf_stack;
+       char fstr[100], *fstrp;
+       int buffersize = MAX_DPATH - 1;
+       fstrp = fstr;
        *d = 0;
        for (;;) {
                char c = *p++;
-               char cn = *p;
                if (c == 0)
                        break;
-               if (c == '%' && cn == '%') {
-                       *d++ = '%';
-                       p++;
-               } else if (c == '%') {
-                       if (stack >= &debugsprintf_stack[DEBUGSPRINTF_SIZE]) {
-                               *d++ = '[';
-                               *d++ = '?';
-                               *d++ = ']';
-                       } else {
-                               if (cn == 'b') {
-                                       char tmp[MAX_DPATH];
-                                       read_bstring(tmp, MAX_DPATH - 1, stack->val);
-                                       strcpy(d, tmp);
-                               } else if (cn == 's') {
-                                       char tmp[MAX_DPATH];
-                                       read_string(tmp, MAX_DPATH - 1, stack->val);
-                                       strcpy(d, tmp);
-                               } else if (cn == 'p') {
-                                       sprintf(d, "%08x", stack->val);
-                               } else if (cn == 'x') {
-                                       sprintf(d, stack->size == sz_long ? "%08x" : (stack->size == sz_word ? "%04x" : "%02x"), stack->val);
-                               } else if (cn == 'd') {
-                                       sprintf(d, "%d", stack->val);
-                               } else if (cn == 'u') {
-                                       sprintf(d, "%u", stack->val);
-                               } else if (cn == '[') {
-                                       char *next = strchr(p, ']');
-                                       if (next) {
-                                               *next = 0;
-                                               d = parse_custom(p + 1, d);
-                                               p = next;
+               if (gotm) {
+                       bool got = false;
+                       buffersize = MAX_DPATH - strlen(out);
+                       if (buffersize <= 1)
+                               break;
+                       if (c == '%') {
+                               *d++ = '%';
+                               gotm = false;
+                       } else if (c == 'l') {
+                               l = true;
+                       } else if (c == 'c') {
+                               uae_u32 size;
+                               uae_u32 val = get_value(&stack, &size, &ptr, l ? sz_long : sz_word);
+                               *fstrp++ = c;
+                               *fstrp = 0;
+                               snprintf(d, buffersize, fstr, val);
+                               got = true;
+                       } else if (c == 'b') {
+                               uae_u32 size;
+                               uae_u32 val = get_value(&stack, &size, &ptr, sz_long);
+                               char tmp[MAX_DPATH];
+                               read_bstring(tmp, MAX_DPATH - 1, val);
+                               *fstrp++ = 's';
+                               *fstrp = 0;
+                               snprintf(d, buffersize, fstr, tmp);
+                               got = true;
+                       } else if (c == 's') {
+                               uae_u32 size;
+                               uae_u32 val = get_value(&stack, &size, &ptr, sz_long);
+                               char tmp[MAX_DPATH];
+                               read_string(tmp, MAX_DPATH - 1, val);
+                               *fstrp++ = c;
+                               *fstrp = 0;
+                               snprintf(d, buffersize, fstr, tmp);
+                               got = true;
+                       } else if (c == 'p') {
+                               uae_u32 size;
+                               uae_u32 val = get_value(&stack, &size, &ptr, sz_long);
+                               snprintf(d, buffersize, "$%08x", val);
+                               got = true;
+                       } else if (c == 'x' || c == 'X' || c == 'd' || c == 'i' || c == 'u' || c == 'o') {
+                               uae_u32 size;
+                               uae_u32 val = get_value(&stack, &size, &ptr, l ? sz_long : sz_word);
+                               if (c == 'd' || c == 'i') {
+                                       if (size == sz_word && (val & 0x8000)) {
+                                               val = (uae_s32)(uae_s16)val;
                                        }
+                               }
+                               *fstrp++ = c;
+                               *fstrp = 0;
+                               snprintf(d, buffersize, fstr, val);
+                               got = true;
+                       } else if (c == '[') {
+                               char *next = strchr(p, ']');
+                               if (next && next[1]) {
+                                       char customout[MAX_DPATH];
+                                       customout[0] = 0;
+                                       *next = 0;
+                                       parse_custom(d, buffersize, fstr, p, next[1]);
+                                       p = next + 2;
+                                       got = true;
                                } else {
-                                       d[0] = '?';
-                                       d[1] = 0;
+                                       gotm = false;
                                }
-                               p++;
+                       } else {
+                               if (fstrp - fstr < sizeof(fstr) - 1) {
+                                       *fstrp++ = c;
+                                       *fstrp = 0;
+                               }
+                       }
+                       if (got) {
                                d += strlen(d);
-                               stack++;
+                               gotm = false;
                        }
+               } else if (c == '%') {
+                       l = false;
+                       fstrp = fstr;
+                       *fstrp++ = c;
+                       *fstrp = 0;
+                       gotm = true;
                } else {
                        *d++ = c;
                }
@@ -7368,7 +7463,7 @@ bool debug_sprintf(uaecptr addr, uae_u32 val, int size)
        if (size != sz_word) {
                debugsprintf_latched = 0;
        }
-       if (addr & 4) {
+       if ((addr & (8 | 4)) == 4) {
                if (size != sz_long)
                        return true;
                debug_sprintf_do(v);
@@ -7376,12 +7471,18 @@ bool debug_sprintf(uaecptr addr, uae_u32 val, int size)
                debugsprintf_latched = 0;
                debugsprintf_cycles = get_cycles();
                debugsprintf_cycles_set = 1;
+       } else if ((addr & (8 | 4)) == 8) {
+               if (size != sz_long)
+                       return true;
+               debugsprintf_va = val;
+               debugsprintf_mode = 1;
        } else {
                if (debugsprintf_cnt < DEBUGSPRINTF_SIZE) {
                        debugsprintf_stack[debugsprintf_cnt].val = v;
                        debugsprintf_stack[debugsprintf_cnt].size = size;
                        debugsprintf_cnt++;
                }
+               debugsprintf_mode = 0;
        }
        return true;
 }