Annotation of hatari/src/debug/debugInfo.c, revision 1.1

1.1     ! root        1: /*
        !             2:   Hatari - debuginfo.c
        !             3: 
        !             4:   This file is distributed under the GNU Public License, version 2 or at
        !             5:   your option any later version. Read the file gpl.txt for details.
        !             6: 
        !             7:   debuginfo.c - functions needed to show info about the atari HW & OS
        !             8:    components and "lock" that info to be shown on entering the debugger.
        !             9: */
        !            10: const char DebugInfo_fileid[] = "Hatari debuginfo.c : " __DATE__ " " __TIME__;
        !            11: 
        !            12: #include <stdio.h>
        !            13: #include <assert.h>
        !            14: #include "main.h"
        !            15: #include "configuration.h"
        !            16: #include "debugInfo.h"
        !            17: #include "debugcpu.h"
        !            18: #include "debugdsp.h"
        !            19: #include "debugui.h"
        !            20: #include "dsp.h"
        !            21: #include "evaluate.h"
        !            22: #include "ioMem.h"
        !            23: #include "m68000.h"
        !            24: #include "stMemory.h"
        !            25: #include "tos.h"
        !            26: #include "video.h"
        !            27: 
        !            28: 
        !            29: /* ------------------------------------------------------------------
        !            30:  * TOS information
        !            31:  */
        !            32: #define OS_SYSBASE 0x4F2
        !            33: #define OS_HEADER_SIZE 0x30
        !            34: 
        !            35: #define COOKIE_JAR 0x5A0
        !            36: 
        !            37: #define BASEPAGE_SIZE 0x100
        !            38: 
        !            39: #define GEM_MAGIC 0x87654321
        !            40: #define GEM_MUPB_SIZE 0xC
        !            41: 
        !            42: #define RESET_MAGIC 0x31415926
        !            43: #define RESET_VALID 0x426
        !            44: #define RESET_VECTOR 0x42A
        !            45: 
        !            46: #define COUNTRY_SPAIN 4
        !            47: 
        !            48: /**
        !            49:  * DebugInfo_GetSysbase: set osversion to given argument.
        !            50:  * return sysbase address on success and zero on failure.
        !            51:  */
        !            52: static Uint32 DebugInfo_GetSysbase(Uint16 *osversion)
        !            53: {
        !            54:        Uint32 sysbase = STMemory_ReadLong(OS_SYSBASE);
        !            55: 
        !            56:        if (!STMemory_ValidArea(sysbase, OS_HEADER_SIZE)) {
        !            57:                fprintf(stderr, "Invalid TOS base address!\n");
        !            58:                return 0;
        !            59:        }
        !            60:        if (sysbase != TosAddress || sysbase != STMemory_ReadLong(sysbase+0x08)) {
        !            61:                fprintf(stderr, "Sysbase and os_beg address in OS header mismatch!\n");
        !            62:                return 0;
        !            63:        }
        !            64:        *osversion = STMemory_ReadWord(sysbase+0x02);
        !            65:        return sysbase;
        !            66: }
        !            67: 
        !            68: /**
        !            69:  * DebugInfo_CurrentBasepage: get currently running TOS program basepage
        !            70:  */
        !            71: static Uint32 DebugInfo_CurrentBasepage(void)
        !            72: {
        !            73:        Uint32 basepage, sysbase;
        !            74:        Uint16 osversion, osconf;
        !            75: 
        !            76:        sysbase = DebugInfo_GetSysbase(&osversion);
        !            77:        if (!sysbase) {
        !            78:                return 0;
        !            79:        }
        !            80:        if (osversion >= 0x0102) {
        !            81:                basepage = STMemory_ReadLong(sysbase+0x28);
        !            82:        } else {
        !            83:                osconf = STMemory_ReadWord(sysbase+0x1C);
        !            84:                if((osconf>>1) == COUNTRY_SPAIN) {
        !            85:                        basepage = 0x873C;
        !            86:                } else {
        !            87:                        basepage = 0x602C;
        !            88:                }
        !            89:        }
        !            90:        if (STMemory_ValidArea(basepage, 4)) {
        !            91:                return STMemory_ReadLong(basepage);
        !            92:        }
        !            93:        fprintf(stderr, "Pointer 0x%06x to basepage address is invalid!\n", basepage);
        !            94:        return 0;
        !            95: }
        !            96: 
        !            97: /**
        !            98:  * DebugInfo_Basepage: show TOS process basepage information
        !            99:  * at given address.
        !           100:  */
        !           101: static void DebugInfo_Basepage(Uint32 basepage)
        !           102: {
        !           103:        Uint8 cmdlen;
        !           104:        Uint32 env;
        !           105: 
        !           106:        if (!basepage) {
        !           107:                /* default to current process basepage */
        !           108:                basepage = DebugInfo_CurrentBasepage();
        !           109:                if (!basepage) {
        !           110:                        return;
        !           111:                }
        !           112:        }
        !           113:        fprintf(stderr, "Process basepage information:\n");
        !           114:        if (!STMemory_ValidArea(basepage, BASEPAGE_SIZE) ||
        !           115:            STMemory_ReadLong(basepage) != basepage) {
        !           116:                fprintf(stderr, "- address 0x%06x is invalid!\n", basepage);
        !           117:                return;
        !           118:        }
        !           119:        fprintf(stderr, "- TPA start      : 0x%06x\n", STMemory_ReadLong(basepage));
        !           120:        fprintf(stderr, "- TPA end +1     : 0x%06x\n", STMemory_ReadLong(basepage+0x04));
        !           121:        fprintf(stderr, "- Text segment   : 0x%06x\n", STMemory_ReadLong(basepage+0x08));
        !           122:        fprintf(stderr, "- Text size      : 0x%x\n",   STMemory_ReadLong(basepage+0x0C));
        !           123:        fprintf(stderr, "- Data segment   : 0x%06x\n", STMemory_ReadLong(basepage+0x10));
        !           124:        fprintf(stderr, "- Data size      : 0x%x\n",   STMemory_ReadLong(basepage+0x14));
        !           125:        fprintf(stderr, "- BSS segment    : 0x%06x\n", STMemory_ReadLong(basepage+0x18));
        !           126:        fprintf(stderr, "- BSS size       : 0x%x\n",   STMemory_ReadLong(basepage+0x1C));
        !           127:        fprintf(stderr, "- Process DTA    : 0x%06x\n", STMemory_ReadLong(basepage+0x20));
        !           128:        fprintf(stderr, "- Parent basepage: 0x%06x\n", STMemory_ReadLong(basepage+0x24));
        !           129: 
        !           130:        env = STMemory_ReadLong(basepage+0x2C);
        !           131:        fprintf(stderr, "- Environment    : 0x%06x\n", env);
        !           132:        if (STMemory_ValidArea(env, 4096)) {
        !           133:                Uint32 end = env + 4096;
        !           134:                while (env < end && *(STRam+env)) {
        !           135:                        fprintf(stderr, "'%s'\n", STRam+env);
        !           136:                        env += strlen((const char *)(STRam+env)) + 1;
        !           137:                }
        !           138:        }
        !           139:        cmdlen = STMemory_ReadByte(basepage+0x80);
        !           140:        fprintf(stderr, "- Command argslen: %d\n", cmdlen);
        !           141:        if (cmdlen) {
        !           142:                int offset = 0;
        !           143:                while (offset < cmdlen) {
        !           144:                        fprintf(stderr, " '%s'", STRam+basepage+0x81+offset);
        !           145:                        offset += strlen((const char *)(STRam+basepage+0x81+offset)) + 1;
        !           146:                }
        !           147:                fprintf(stderr, "\n");
        !           148:        }
        !           149: }
        !           150: 
        !           151: /**
        !           152:  * DebugInfo_OSHeader: display TOS OS Header
        !           153:  */
        !           154: static void DebugInfo_OSHeader(Uint32 dummy)
        !           155: {
        !           156:        Uint32 sysbase, gemblock, basepage;
        !           157:        Uint16 osversion, osconf;
        !           158: 
        !           159:        sysbase = DebugInfo_GetSysbase(&osversion);
        !           160:        if (!sysbase) {
        !           161:                return;
        !           162:        }
        !           163:        fprintf(stderr, "OS base addr : 0x%06x\n", sysbase);
        !           164:        fprintf(stderr, "OS RAM end+1 : 0x%06x\n", STMemory_ReadLong(sysbase+0x0C));
        !           165:        fprintf(stderr, "TOS version  : 0x%x\n", osversion);
        !           166: 
        !           167:        fprintf(stderr, "Reset handler: 0x%06x\n", STMemory_ReadLong(sysbase+0x04));
        !           168:        fprintf(stderr, "Reset vector : 0x%06x\n", STMemory_ReadLong(RESET_VECTOR));
        !           169:        fprintf(stderr, "Reset valid  : 0x%x (valid=0x%x)\n", STMemory_ReadLong(RESET_VALID), RESET_MAGIC);
        !           170: 
        !           171:        gemblock = STMemory_ReadLong(sysbase+0x14);
        !           172:        fprintf(stderr, "GEM Memory Usage Parameter Block:\n");
        !           173:        if (STMemory_ValidArea(gemblock, GEM_MUPB_SIZE)) {
        !           174:                fprintf(stderr, "- Block addr : 0x%06x\n", gemblock);
        !           175:                fprintf(stderr, "- GEM magic  : 0x%x (valid=0x%x)\n", STMemory_ReadLong(gemblock), GEM_MAGIC);
        !           176:                fprintf(stderr, "- GEM entry  : 0x%06x\n", STMemory_ReadLong(gemblock+4));
        !           177:                fprintf(stderr, "- GEM end    : 0x%06x\n", STMemory_ReadLong(gemblock+8));
        !           178:        } else {
        !           179:                fprintf(stderr, "- is at INVALID 0x%06x address.\n", gemblock);
        !           180:        }
        !           181: 
        !           182:        fprintf(stderr, "OS date      : 0x%x\n", STMemory_ReadLong(sysbase+0x14));
        !           183:        fprintf(stderr, "OS DOS date  : 0x%x\n", STMemory_ReadLong(sysbase+0x1E));
        !           184: 
        !           185:        osconf = STMemory_ReadWord(sysbase+0x1C);
        !           186:        fprintf(stderr, "OS Conf bits : lang=%d, %s\n", osconf>>1, osconf&1 ? "PAL":"NTSC");
        !           187:        fprintf(stderr, "Cookie Jar   : 0x%06x\n", STMemory_ReadLong(COOKIE_JAR));
        !           188: 
        !           189:        /* last 3 OS header fields are only available as of TOS 1.02 */
        !           190:        if (osversion >= 0x0102) {
        !           191:                fprintf(stderr, "Memory pool  : 0x%06x\n", STMemory_ReadLong(sysbase+0x20));
        !           192:                fprintf(stderr, "Kbshift addr : 0x%06x\n", STMemory_ReadLong(sysbase+0x24));
        !           193:        } else {
        !           194:                /* TODO: GEMDOS memory pool address for TOS 1.0? */
        !           195:                fprintf(stderr, "Kbshift addr : 0x000E1B\n");
        !           196:        }
        !           197:        basepage = DebugInfo_CurrentBasepage();
        !           198:        if (basepage) {
        !           199:                fprintf(stderr, "Basepage     : 0x%06x\n", basepage);
        !           200:        }
        !           201: }
        !           202: 
        !           203: 
        !           204: /* ------------------------------------------------------------------
        !           205:  * Falcon HW information
        !           206:  */
        !           207: 
        !           208: /**
        !           209:  * DebugInfo_Videl : display the Videl registers values.
        !           210:  */
        !           211: static void DebugInfo_Videl(Uint32 dummy)
        !           212: {
        !           213:        if (ConfigureParams.System.nMachineType != MACHINE_FALCON) {
        !           214:                fprintf(stderr, "Not Falcon - no Videl!\n");
        !           215:                return;
        !           216:        }
        !           217: 
        !           218:        fprintf(stderr, "$FF8006 : monitor type                     : %02x\n", IoMem_ReadByte(0xff8006));
        !           219:        fprintf(stderr, "$FF820E : offset to next line              : %04x\n", IoMem_ReadWord(0xff820e));
        !           220:        fprintf(stderr, "$FF8210 : VWRAP - line width               : %04x\n", IoMem_ReadWord(0xff8210));
        !           221:        fprintf(stderr, "$FF8260 : ST shift mode                    : %02x\n", IoMem_ReadByte(0xff8260));
        !           222:        fprintf(stderr, "$FF8265 : Horizontal scroll register       : %02x\n", IoMem_ReadByte(0xff8265));
        !           223:        fprintf(stderr, "$FF8266 : Falcon shift mode                : %04x\n", IoMem_ReadWord(0xff8266));
        !           224:        fprintf(stderr, "\n");
        !           225:        fprintf(stderr, "$FF8280 : HHC - Horizontal Hold Counter    : %04x\n", IoMem_ReadWord(0xff8280));
        !           226:        fprintf(stderr, "$FF8282 : HHT - Horizontal Hold Timer      : %04x\n", IoMem_ReadWord(0xff8282));
        !           227:        fprintf(stderr, "$FF8284 : HBB - Horizontal Border Begin    : %04x\n", IoMem_ReadWord(0xff8284));
        !           228:        fprintf(stderr, "$FF8286 : HBE - Horizontal Border End      : %04x\n", IoMem_ReadWord(0xff8286));
        !           229:        fprintf(stderr, "$FF8288 : HDB - Horizontal Display Begin   : %04x\n", IoMem_ReadWord(0xff8288));
        !           230:        fprintf(stderr, "$FF828A : HDE - Horizontal Display End     : %04x\n", IoMem_ReadWord(0xff828a));
        !           231:        fprintf(stderr, "$FF828C : HSS - Horizontal SS              : %04x\n", IoMem_ReadWord(0xff828c));
        !           232:        fprintf(stderr, "$FF828E : HFS - Horizontal FS              : %04x\n", IoMem_ReadWord(0xff828e));
        !           233:        fprintf(stderr, "$FF8290 : HEE - Horizontal EE              : %04x\n", IoMem_ReadWord(0xff8290));
        !           234:        fprintf(stderr, "\n");
        !           235:        fprintf(stderr, "$FF82A0 : VFC - Vertical Frequency Counter : %04x\n", IoMem_ReadWord(0xff82a0));
        !           236:        fprintf(stderr, "$FF82A2 : VFT - Vertical Frequency Timer   : %04x\n", IoMem_ReadWord(0xff82a2));
        !           237:        fprintf(stderr, "$FF82A4 : VBB - Vertical Border Begin      : %04x\n", IoMem_ReadWord(0xff82a4));
        !           238:        fprintf(stderr, "$FF82A6 : VBE - Vertical Border End        : %04x\n", IoMem_ReadWord(0xff82a6));
        !           239:        fprintf(stderr, "$FF82A8 : VDB - Vertical Display Begin     : %04x\n", IoMem_ReadWord(0xff82a8));
        !           240:        fprintf(stderr, "$FF82AA : VDE - Vertical Display End       : %04x\n", IoMem_ReadWord(0xff82aa));
        !           241:        fprintf(stderr, "$FF82AC : VSS - Vertical SS                : %04x\n", IoMem_ReadWord(0xff82ac));
        !           242:        fprintf(stderr, "\n");
        !           243:        fprintf(stderr, "$FF82C0 : VCO - Video control              : %04x\n", IoMem_ReadWord(0xff82c0));
        !           244:        fprintf(stderr, "$FF82C2 : VMD - Video mode                 : %04x\n", IoMem_ReadWord(0xff82c2));
        !           245:        fprintf(stderr, "\n");
        !           246: }
        !           247: 
        !           248: /**
        !           249:  * DebugInfo_Crossbar : display the Crossbar registers values.
        !           250:  */
        !           251: static void DebugInfo_Crossbar(Uint32 dummy)
        !           252: {
        !           253:        char matrixDMA[5], matrixDAC[5], matrixDSP[5], matrixEXT[5];
        !           254:        char frqDMA[11], frqDAC[11], frqDSP[11], frqEXT[11];
        !           255:        char dataSize[15];
        !           256:        
        !           257:        if (ConfigureParams.System.nMachineType != MACHINE_FALCON) {
        !           258:                fprintf(stderr, "Not Falcon - no Crossbar!\n");
        !           259:                return;
        !           260:        }
        !           261: 
        !           262:        fprintf(stderr, "$FF8900 : Sound DMA control                     : %02x\n", IoMem_ReadByte(0xff8900));
        !           263:        fprintf(stderr, "$FF8901 : Sound DMA control                     : %02x\n", IoMem_ReadByte(0xff8901));
        !           264:        fprintf(stderr, "$FF8903 : Frame Start High                      : %02x\n", IoMem_ReadByte(0xff8903));
        !           265:        fprintf(stderr, "$FF8905 : Frame Start middle                    : %02x\n", IoMem_ReadByte(0xff8905));
        !           266:        fprintf(stderr, "$FF8907 : Frame Start low                       : %02x\n", IoMem_ReadByte(0xff8907));
        !           267:        fprintf(stderr, "$FF8909 : Frame Count High                      : %02x\n", IoMem_ReadByte(0xff8909));
        !           268:        fprintf(stderr, "$FF890B : Frame Count middle                    : %02x\n", IoMem_ReadByte(0xff890b));
        !           269:        fprintf(stderr, "$FF890D : Frame Count low                       : %02x\n", IoMem_ReadByte(0xff890d));
        !           270:        fprintf(stderr, "$FF890f : Frame End High                        : %02x\n", IoMem_ReadByte(0xff890f));
        !           271:        fprintf(stderr, "$FF8911 : Frame End middle                      : %02x\n", IoMem_ReadByte(0xff8911));
        !           272:        fprintf(stderr, "$FF8913 : Frame End low                         : %02x\n", IoMem_ReadByte(0xff8913));
        !           273:        fprintf(stderr, "\n");
        !           274:        fprintf(stderr, "$FF8920 : Sound Mode Control                    : %02x\n", IoMem_ReadByte(0xff8920));
        !           275:        fprintf(stderr, "$FF8921 : Sound Mode Control                    : %02x\n", IoMem_ReadByte(0xff8921));
        !           276:        fprintf(stderr, "$FF8930 : DMA Crossbar Input Select Controller  : %04x\n", IoMem_ReadWord(0xff8930));
        !           277:        fprintf(stderr, "$FF8932 : DMA Crossbar Output Select Controller : %04x\n", IoMem_ReadWord(0xff8932));
        !           278:        fprintf(stderr, "\n");
        !           279:        fprintf(stderr, "$FF8934 : External Sync Frequency Divider       : %02x\n", IoMem_ReadByte(0xff8934));
        !           280:        fprintf(stderr, "$FF8935 : Internal Sync Frequency Divider       : %02x\n", IoMem_ReadByte(0xff8935));
        !           281:        fprintf(stderr, "$FF8936 : Record Track select                   : %02x\n", IoMem_ReadByte(0xff8936));
        !           282:        fprintf(stderr, "$FF8937 : Codec Input Source                    : %02x\n", IoMem_ReadByte(0xff8937));
        !           283:        fprintf(stderr, "$FF8938 : Codec ADC Input                       : %02x\n", IoMem_ReadByte(0xff8938));
        !           284:        fprintf(stderr, "$FF8939 : Gain Settings Per Channel             : %02x\n", IoMem_ReadByte(0xff8939));
        !           285:        fprintf(stderr, "$FF893A : Attenuation Settings Per Channel      : %02x\n", IoMem_ReadByte(0xff893a));
        !           286:        fprintf(stderr, "$FF893C : Codec Status                          : %04x\n", IoMem_ReadWord(0xff893c));
        !           287:        fprintf(stderr, "$FF8940 : GPIO Data Direction                   : %04x\n", IoMem_ReadWord(0xff8940));
        !           288:        fprintf(stderr, "$FF8942 : GPIO Data                             : %04x\n", IoMem_ReadWord(0xff8942));
        !           289:        fprintf(stderr, "\n");
        !           290:        
        !           291:        /* DAC connexion */
        !           292:        switch ((IoMem_ReadWord(0xff8932) >> 13) & 3) {
        !           293:                case 0 : strcpy(matrixDAC, "OOXO"); break;
        !           294:                case 1 : strcpy(matrixDAC, "OXOO"); break;
        !           295:                case 2 : strcpy(matrixDAC, "XOOO"); break;
        !           296:                case 3 : strcpy(matrixDAC, "OOOX"); break;
        !           297:        }
        !           298:                
        !           299:        /* DMA connexion */
        !           300:        switch ((IoMem_ReadWord(0xff8932) >> 1) & 3) {
        !           301:                case 0 : strcpy(matrixDMA, "OOXO"); break;
        !           302:                case 1 : strcpy(matrixDMA, "OXOO"); break;
        !           303:                case 2 : strcpy(matrixDMA, "XOOO"); break;
        !           304:                case 3 : strcpy(matrixDMA, "OOOX"); break;
        !           305:        }
        !           306: 
        !           307:        /* DSP connexion */
        !           308:        switch ((IoMem_ReadWord(0xff8932) >> 5) & 3) {
        !           309:                case 0 : strcpy(matrixDSP, "OOXO"); break;
        !           310:                case 1 : strcpy(matrixDSP, "OXOO"); break;
        !           311:                case 2 : strcpy(matrixDSP, "XOOO"); break;
        !           312:                case 3 : strcpy(matrixDSP, "OOOX"); break;
        !           313:        }
        !           314: 
        !           315:        /* External input connexion */
        !           316:        switch ((IoMem_ReadWord(0xff8932) >> 9) & 3) {
        !           317:                case 0 : strcpy(matrixEXT, "OOXO"); break;
        !           318:                case 1 : strcpy(matrixEXT, "OXOO"); break;
        !           319:                case 2 : strcpy(matrixEXT, "XOOO"); break;
        !           320:                case 3 : strcpy(matrixEXT, "OOOX"); break;
        !           321:        }
        !           322: 
        !           323:        /* HandShake mode test */
        !           324:        if ((IoMem_ReadWord(0xff8932) & 7) == 2) {
        !           325:                matrixDMA[1] = 'H';
        !           326:        }
        !           327: 
        !           328:        /* HandShake mode test */
        !           329:        if ((IoMem_ReadWord(0xff8932) & 0xf) == 2) {
        !           330:                matrixDSP[2] = 'H';
        !           331:        }
        !           332: 
        !           333:        /* DSP Frequency */
        !           334:        if ((IoMem_ReadByte(0xff8935) & 0xf) == 0) {
        !           335:                strcpy(frqDSP, "(STe Freq)");
        !           336:        }else {
        !           337:                switch ((IoMem_ReadWord(0xff8930) >> 5) & 0x3) {
        !           338:                        case 0: strcpy(frqDSP, " (25 Mhz) "); break;
        !           339:                        case 1: strcpy(frqDSP, "(External)"); break;
        !           340:                        case 2: strcpy(frqDSP, " (32 Mhz) "); break;
        !           341:                        default:  strcpy(frqDSP, "undefined "); break;break;
        !           342:                }
        !           343:        }
        !           344: 
        !           345:        /* DMA Frequency */
        !           346:        if ((IoMem_ReadByte(0xff8935) & 0xf) == 0) {
        !           347:                strcpy(frqDMA, "(STe Freq)");
        !           348:        }else {
        !           349:                switch ((IoMem_ReadWord(0xff8930) >> 1) & 0x3) {
        !           350:                        case 0: strcpy(frqDMA, " (25 Mhz) "); break;
        !           351:                        case 1: strcpy(frqDMA, "(External)"); break;
        !           352:                        case 2: strcpy(frqDMA, " (32 Mhz) "); break;
        !           353:                        default:  strcpy(frqDMA, "undefined "); break;break;
        !           354:                }
        !           355:        }
        !           356: 
        !           357:        /* External Frequency */
        !           358:        if ((IoMem_ReadByte(0xff8935) & 0xf) == 0) {
        !           359:                strcpy(frqEXT, "(STe Freq)");
        !           360:        }else {
        !           361:                switch ((IoMem_ReadWord(0xff8930) >> 9) & 0x3) {
        !           362:                        case 0: strcpy(frqEXT, " (25 Mhz) "); break;
        !           363:                        case 1: strcpy(frqEXT, "(External)"); break;
        !           364:                        case 2: strcpy(frqEXT, " (32 Mhz) "); break;
        !           365:                        default:  strcpy(frqEXT, "undefined "); break;break;
        !           366:                }
        !           367:        }
        !           368: 
        !           369:        /* DAC Frequency */
        !           370:        if ((IoMem_ReadByte(0xff8935) & 0xf) == 0) {
        !           371:                strcpy(frqDAC, "(STe Freq)");
        !           372:        }else {
        !           373:                strcpy(frqDAC, " (25 Mhz) ");
        !           374:        }
        !           375: 
        !           376:        /* data size */
        !           377:        switch ((IoMem_ReadByte(0xff8921) >> 6) & 0x3) {
        !           378:                case 0: strcpy (dataSize, "8 bits stereo"); break;
        !           379:                case 1: strcpy (dataSize, "16 bits stereo"); break;
        !           380:                case 2: strcpy (dataSize, "8 bits mono"); break;
        !           381:                default: strcpy (dataSize, "undefined"); break;
        !           382:        }
        !           383: 
        !           384:        /* Display the crossbar Matrix */
        !           385:        fprintf(stderr, "           INPUT\n");
        !           386:        fprintf(stderr, "External Imp  ---%c------%c------%c------%c\n", matrixDAC[0], matrixDMA[0], matrixDSP[0], matrixEXT[0]);
        !           387:        fprintf(stderr, "%s       |      |      |      |    O = no connexion\n", frqEXT);
        !           388:        fprintf(stderr, "                 |      |      |      |    X = connexion\n");
        !           389:        fprintf(stderr, "Dsp Transmit  ---%c------%c------%c------%c    H = Handshake connexion\n", matrixDAC[1], matrixDMA[1], matrixDSP[1], matrixEXT[1]);
        !           390:        fprintf(stderr, "%s       |      |      |      |\n", frqDSP);
        !           391:        fprintf(stderr, "                 |      |      |      |    %s\n", dataSize);
        !           392:        fprintf(stderr, "DMA PlayBack  ---%c------%c------%c------%c\n", matrixDAC[2], matrixDMA[2], matrixDSP[2], matrixEXT[2]);
        !           393:        fprintf(stderr, "%s       |      |      |      |\n", frqDMA);
        !           394:        fprintf(stderr, "                 |      |      |      |\n");
        !           395:        fprintf(stderr, "ADC           ---%c------%c------%c------%c\n", matrixDAC[3], matrixDMA[3], matrixDSP[3], matrixEXT[3]);
        !           396:        fprintf(stderr, "%s       |      |      |      |\n", frqDAC);
        !           397:        fprintf(stderr, "                DAC    DMA    DSP   External     OUTPUT\n");
        !           398:        fprintf(stderr, "                     Record  Record   Out\n");
        !           399:        fprintf(stderr, "\n");
        !           400: }
        !           401: 
        !           402: 
        !           403: /* ------------------------------------------------------------------
        !           404:  * CPU and DSP information wrappers
        !           405:  */
        !           406: 
        !           407: /**
        !           408:  * Helper to call debugcpu.c and debugdsp.c debugger commands
        !           409:  */
        !           410: static void DebugInfo_CallCommand(int (*func)(int, char* []), const char *command, Uint32 arg)
        !           411: {
        !           412:        char cmdbuffer[16], argbuffer[12];
        !           413:        char *argv[] = { cmdbuffer, NULL };
        !           414:        int argc = 1;
        !           415: 
        !           416:        assert(strlen(command) < sizeof(cmdbuffer));
        !           417:        strcpy(cmdbuffer, command);
        !           418:        if (arg) {
        !           419:                sprintf(argbuffer, "$%x", arg);
        !           420:                argv[argc++] = argbuffer;
        !           421:        }
        !           422:        func(argc, argv);
        !           423: }
        !           424: 
        !           425: static void DebugInfo_CpuRegister(Uint32 arg)
        !           426: {
        !           427:        DebugInfo_CallCommand(DebugCpu_Register, "register", arg);
        !           428: }
        !           429: static void DebugInfo_CpuDisAsm(Uint32 arg)
        !           430: {
        !           431:        DebugInfo_CallCommand(DebugCpu_DisAsm, "disasm", arg);
        !           432: }
        !           433: static void DebugInfo_CpuMemDump(Uint32 arg)
        !           434: {
        !           435:        DebugInfo_CallCommand(DebugCpu_MemDump, "memdump", arg);
        !           436: }
        !           437: 
        !           438: #if ENABLE_DSP_EMU
        !           439: 
        !           440: static void DebugInfo_DspRegister(Uint32 arg)
        !           441: {
        !           442:        DebugInfo_CallCommand(DebugDsp_Register, "dspreg", arg);
        !           443: }
        !           444: static void DebugInfo_DspDisAsm(Uint32 arg)
        !           445: {
        !           446:        DebugInfo_CallCommand(DebugDsp_DisAsm, "dspdisasm", arg);
        !           447: }
        !           448: 
        !           449: static void DebugInfo_DspMemDump(Uint32 arg)
        !           450: {
        !           451:        char cmdbuf[] = "dspmemdump";
        !           452:        char addrbuf[6], spacebuf[2] = "X";
        !           453:        char *argv[] = { cmdbuf, spacebuf, addrbuf };
        !           454:        spacebuf[0] = (arg>>16)&0xff;
        !           455:        sprintf(addrbuf, "$%x", (Uint16)(arg&0xffff));
        !           456:        DebugDsp_MemDump(3, argv);
        !           457: }
        !           458: 
        !           459: /**
        !           460:  * Convert arguments to Uint32 arg suitable for DSP memdump callback
        !           461:  */
        !           462: static Uint32 DebugInfo_DspMemArgs(int argc, char *argv[])
        !           463: {
        !           464:        Uint32 value;
        !           465:        char space;
        !           466:        if (argc != 2) {
        !           467:                return 0;
        !           468:        }
        !           469:        space = toupper(argv[0][0]);
        !           470:        if ((space != 'X' && space != 'Y' && space != 'P') || argv[0][1]) {
        !           471:                fprintf(stderr, "ERROR: invalid DSP address space '%s'!\n", argv[0]);
        !           472:                return 0;
        !           473:        }
        !           474:        if (!Eval_Number(argv[1], &value) || value > 0xffff) {
        !           475:                fprintf(stderr, "ERROR: invalid DSP address '%s'!\n", argv[1]);
        !           476:                return 0;
        !           477:        }
        !           478:        return ((Uint32)space<<16) | value;
        !           479: }
        !           480: 
        !           481: #endif  /* ENABLE_DSP_EMU */
        !           482: 
        !           483: 
        !           484: static void DebugInfo_RegAddr(Uint32 arg)
        !           485: {
        !           486:        bool forDsp;
        !           487:        char regname[3];
        !           488:        Uint32 *regvalue, mask;
        !           489:        char cmdbuf[12], addrbuf[6];
        !           490:        char *argv[] = { cmdbuf, addrbuf };
        !           491:        
        !           492:        regname[0] = (arg>>24)&0xff;
        !           493:        regname[1] = (arg>>16)&0xff;
        !           494:        regname[2] = '\0';
        !           495: 
        !           496:        if (DebugCpu_GetRegisterAddress(regname, &regvalue)) {
        !           497:                mask = 0xffffffff;
        !           498:                forDsp = false;
        !           499:        } else {
        !           500:                if (!DSP_GetRegisterAddress(regname, &regvalue, &mask)) {
        !           501:                        fprintf(stderr, "ERROR: invalid address/data register '%s'!\n", regname);
        !           502:                        return;
        !           503:                }
        !           504:                forDsp = true;
        !           505:        }
        !           506:                sprintf(addrbuf, "$%x", *regvalue & mask);
        !           507: 
        !           508:        if ((arg & 0xff) == 'D') {
        !           509:                strcpy(cmdbuf, "disasm");
        !           510:                if (forDsp) {
        !           511: #if ENABLE_DSP_EMU
        !           512:                        DebugDsp_DisAsm(2, argv);
        !           513: #endif
        !           514:                } else {
        !           515:                        DebugCpu_DisAsm(2, argv);
        !           516:                }
        !           517:        } else {
        !           518:                strcpy(cmdbuf, "memdump");
        !           519:                if (forDsp) {
        !           520: #if ENABLE_DSP_EMU
        !           521:                        DebugDsp_MemDump(2, argv);
        !           522: #endif
        !           523:                } else {
        !           524:                        DebugCpu_MemDump(2, argv);
        !           525:                }
        !           526:        }
        !           527: }
        !           528: 
        !           529: /**
        !           530:  * Convert arguments to Uint32 arg suitable for RegAddr callback
        !           531:  */
        !           532: static Uint32 DebugInfo_RegAddrArgs(int argc, char *argv[])
        !           533: {
        !           534:        Uint32 value, *regaddr;
        !           535:        if (argc != 2) {
        !           536:                return 0;
        !           537:        }
        !           538: 
        !           539:        if (strcmp(argv[0], "disasm") == 0) {
        !           540:                value = 'D';
        !           541:        } else if (strcmp(argv[0], "memdump") == 0) {
        !           542:                value = 'M';
        !           543:        } else {
        !           544:                fprintf(stderr, "ERROR: regaddr operation can be only 'disasm' or 'memdump', not '%s'!\n", argv[0]);
        !           545:                return 0;
        !           546:        }
        !           547: 
        !           548:        if (strlen(argv[1]) != 2 ||
        !           549:            (!DebugCpu_GetRegisterAddress(argv[1], &regaddr) &&
        !           550:             (toupper(argv[1][0]) != 'R' || !isdigit(argv[1][1]) || argv[1][2]))) {
        !           551:                /* not CPU register or Rx DSP register */
        !           552:                fprintf(stderr, "ERROR: invalid address/data register '%s'!\n", argv[1]);
        !           553:                return 0;
        !           554:        }
        !           555:        
        !           556:        value |= argv[1][0] << 24;
        !           557:        value |= argv[1][1] << 16;
        !           558:        value &= 0xffff00ff;
        !           559:        return value;
        !           560: }
        !           561: 
        !           562: 
        !           563: /* ------------------------------------------------------------------
        !           564:  * Debugger & readline TAB completion integration
        !           565:  */
        !           566: 
        !           567: /**
        !           568:  * Default information on entering the debugger
        !           569:  */
        !           570: static void DebugInfo_Default(Uint32 dummy)
        !           571: {
        !           572:        int hbl, fcycles, lcycles;
        !           573:        Video_GetPosition(&fcycles, &hbl, &lcycles);
        !           574:        fprintf(stderr, "\nCPU=$%x, VBL=%d, FrameCycles=%d, HBL=%d, LineCycles=%d, DSP=",
        !           575:                M68000_GetPC(), nVBLs, fcycles, hbl, lcycles);
        !           576:        if (bDspEnabled)
        !           577:                fprintf(stderr, "$%x\n", DSP_GetPC());
        !           578:        else
        !           579:                fprintf(stderr, "N/A\n");
        !           580: }
        !           581: 
        !           582: static const struct {
        !           583:        /* whether callback is used only for locking */
        !           584:        bool lock;
        !           585:        const char *name;
        !           586:        void (*func)(Uint32 arg);
        !           587:        /* convert args in argv into single Uint32 for func */
        !           588:        Uint32 (*args)(int argc, char *argv[]);
        !           589:        const char *info;
        !           590: } infotable[] = {
        !           591:        { false,"basepage",  DebugInfo_Basepage,   NULL, "Show program basepage info at given <address>" },
        !           592:        { false,"crossbar",  DebugInfo_Crossbar,   NULL, "Show Falcon crossbar HW register values" },
        !           593:        { true, "default",   DebugInfo_Default,    NULL, "Show default debugger entry information" },
        !           594:        { true, "disasm",    DebugInfo_CpuDisAsm,  NULL, "Disasm CPU from PC or given <address>" },
        !           595: #if ENABLE_DSP_EMU
        !           596:        { true, "dspdisasm", DebugInfo_DspDisAsm,  NULL, "Disasm DSP from given <address>" },
        !           597:        { true, "dspmemdump",DebugInfo_DspMemDump, DebugInfo_DspMemArgs, "Dump DSP memory from given <space> <address>" },
        !           598:        { true, "dspregs",   DebugInfo_DspRegister,NULL, "Show DSP register values" },
        !           599: #endif
        !           600:        { true, "memdump",   DebugInfo_CpuMemDump, NULL, "Dump CPU memory from given <address>" },
        !           601:        { false,"osheader",  DebugInfo_OSHeader,   NULL, "Show TOS OS header information" },
        !           602:        { true, "regaddr",   DebugInfo_RegAddr, DebugInfo_RegAddrArgs, "Show <disasm|memdump> from CPU/DSP address pointed by <register>" },
        !           603:        { true, "registers", DebugInfo_CpuRegister,NULL, "Show CPU register values" },
        !           604:        { false,"videl",     DebugInfo_Videl,      NULL, "Show Falcon Videl HW register values" }
        !           605: };
        !           606: 
        !           607: static int LockedFunction = 2; /* index for the "default" function */
        !           608: static Uint32 LockedArgument;
        !           609: 
        !           610: /**
        !           611:  * Show selected debugger session information
        !           612:  * (when debugger is (again) entered)
        !           613:  */
        !           614: void DebugInfo_ShowSessionInfo(void)
        !           615: {
        !           616:        infotable[LockedFunction].func(LockedArgument);
        !           617: }
        !           618: 
        !           619: 
        !           620: /**
        !           621:  * Readline match callback for info subcommand name completion.
        !           622:  * STATE = 0 -> different text from previous one.
        !           623:  * Return next match or NULL if no matches.
        !           624:  */
        !           625: static char *DebugInfo_Match(const char *text, int state, bool lock)
        !           626: {
        !           627:        static int i, len;
        !           628:        const char *name;
        !           629:        
        !           630:        if (!state) {
        !           631:                /* first match */
        !           632:                len = strlen(text);
        !           633:                i = 0;
        !           634:        }
        !           635:        /* next match */
        !           636:        while (i++ < ARRAYSIZE(infotable)) {
        !           637:                if (!lock && infotable[i-1].lock) {
        !           638:                        continue;
        !           639:                }
        !           640:                name = infotable[i-1].name;
        !           641:                if (strncmp(name, text, len) == 0)
        !           642:                        return (strdup(name));
        !           643:        }
        !           644:        return NULL;
        !           645: }
        !           646: char *DebugInfo_MatchLock(const char *text, int state)
        !           647: {
        !           648:        return DebugInfo_Match(text, state, true);
        !           649: }
        !           650: char *DebugInfo_MatchInfo(const char *text, int state)
        !           651: {
        !           652:        return DebugInfo_Match(text, state, false);
        !           653: }
        !           654: 
        !           655: 
        !           656: /**
        !           657:  * Show requested command information.
        !           658:  */
        !           659: int DebugInfo_Command(int nArgc, char *psArgs[])
        !           660: {
        !           661:        Uint32 value;
        !           662:        const char *cmd;
        !           663:        bool ok, lock;
        !           664:        int i, sub;
        !           665: 
        !           666:        sub = -1;
        !           667:        if (nArgc > 1) {
        !           668:                cmd = psArgs[1];                
        !           669:                /* which subcommand? */
        !           670:                for (i = 0; i < ARRAYSIZE(infotable); i++) {
        !           671:                        if (strcmp(cmd, infotable[i].name) == 0) {
        !           672:                                sub = i;
        !           673:                                break;
        !           674:                        }
        !           675:                }
        !           676:        }
        !           677: 
        !           678:        if (infotable[sub].args) {
        !           679:                /* value needs callback specific conversion */
        !           680:                value = infotable[sub].args(nArgc-2, psArgs+2);
        !           681:                ok = !!value;
        !           682:        } else {
        !           683:                if (nArgc > 2) {
        !           684:                        /* value is normal number */
        !           685:                        ok = Eval_Number(psArgs[2], &value);
        !           686:                } else {
        !           687:                        value = 0;
        !           688:                        ok = true;
        !           689:                }
        !           690:        }
        !           691: 
        !           692:        lock = (strcmp(psArgs[0], "lock") == 0);
        !           693:        
        !           694:        if (sub < 0 || !ok) {
        !           695:                /* no subcommand or something wrong with value, show info */
        !           696:                fprintf(stderr, "%s subcommands are:\n", psArgs[0]);
        !           697:                for (i = 0; i < ARRAYSIZE(infotable); i++) {
        !           698:                        if (!lock && infotable[i].lock) {
        !           699:                                continue;
        !           700:                        }
        !           701:                        fprintf(stderr, "- %s: %s\n",
        !           702:                                infotable[i].name, infotable[i].info);
        !           703:                }
        !           704:                return DEBUGGER_CMDDONE;
        !           705:        }
        !           706: 
        !           707:        if (lock) {
        !           708:                /* lock given subcommand and value */
        !           709:                LockedFunction = sub;
        !           710:                LockedArgument = value;
        !           711:                fprintf(stderr, "Locked %s output.\n", psArgs[1]);
        !           712:        } else {
        !           713:                /* do actual work */
        !           714:                infotable[sub].func(value);
        !           715:        }
        !           716:        return DEBUGGER_CMDDONE;
        !           717: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.