Annotation of uae/src/gayle.c, revision 1.1

1.1     ! root        1:  /*
        !             2:   * UAE - The Un*x Amiga Emulator
        !             3:   *
        !             4:   * Gayle (and motherboard resources) memory bank
        !             5:   *
        !             6:   * (c) 2006 - 2007 Toni Wilen
        !             7:   */
        !             8: 
        !             9: #define GAYLE_LOG 0
        !            10: #define IDE_LOG 0
        !            11: #define MBRES_LOG 0
        !            12: 
        !            13: #include "sysconfig.h"
        !            14: #include "sysdeps.h"
        !            15: 
        !            16: #include "options.h"
        !            17: 
        !            18: #include "memory.h"
        !            19: #include "custom.h"
        !            20: #include "newcpu.h"
        !            21: #include "gayle.h"
        !            22: #include "zfile.h"
        !            23: #include "filesys.h"
        !            24: #include "savestate.h"
        !            25: #include "gui.h"
        !            26: 
        !            27: /*
        !            28: D80000 to D8FFFF               64 KB SPARE chip select
        !            29: D90000 to D9FFFF               64 KB ARCNET chip select
        !            30: DA0000 to DA3FFF               16 KB IDE drive
        !            31: DA4000 to DA4FFF               16 KB IDE reserved
        !            32: DA8000 to DAFFFF               32 KB Credit Card and IDE configregisters
        !            33: DB0000 to DBFFFF               64 KB Not used(reserved for external IDE)
        !            34: * DC0000 to DCFFFF             64 KB Real Time Clock(RTC)
        !            35: DD0000 to DDFFFF               64 KB A3000 DMA controller
        !            36: DD0000 to DD1FFF                      A4000 DMAC
        !            37: DD2000 to DDFFFF                      A4000 IDE
        !            38: DE0000 to DEFFFF               64 KB Motherboard resources
        !            39: */
        !            40: 
        !            41: #define NCR_OFFSET 0x40
        !            42: 
        !            43: /* Gayle definitions from Linux drivers */
        !            44: 
        !            45: /* PCMCIA stuff */
        !            46: 
        !            47: #define GAYLE_RAM               (0x600000+zTwoBase)
        !            48: #define GAYLE_RAMSIZE           (0x400000)
        !            49: #define GAYLE_ATTRIBUTE         (0xa00000+zTwoBase)
        !            50: #define GAYLE_ATTRIBUTESIZE     (0x020000)
        !            51: #define GAYLE_IO                (0xa20000+zTwoBase)     /* 16bit and even 8bit registers */
        !            52: #define GAYLE_IOSIZE            (0x010000)
        !            53: #define GAYLE_IO_8BITODD        (0xa30000+zTwoBase)     /* odd 8bit registers */
        !            54: /* offset for accessing odd IO registers */
        !            55: #define GAYLE_ODD               (GAYLE_IO_8BITODD-GAYLE_IO-1)
        !            56: 
        !            57: #define GAYLE_ADDRESS   (0xda8000)      /* gayle main registers base address */
        !            58: #define GAYLE_RESET     (0xa40000)      /* write 0x00 to start reset,
        !            59:                                           read 1 byte to stop reset */
        !            60: /* GAYLE_CARDSTATUS bit def */
        !            61: #define GAYLE_CS_CCDET          0x40    /* credit card detect */
        !            62: #define GAYLE_CS_BVD1           0x20    /* battery voltage detect 1 */
        !            63: #define GAYLE_CS_SC             0x20    /* credit card status change */
        !            64: #define GAYLE_CS_BVD2           0x10    /* battery voltage detect 2 */
        !            65: #define GAYLE_CS_DA             0x10    /* digital audio */
        !            66: #define GAYLE_CS_WR             0x08    /* write enable (1 == enabled) */
        !            67: #define GAYLE_CS_BSY            0x04    /* credit card busy */
        !            68: #define GAYLE_CS_IRQ            0x04    /* interrupt request */
        !            69: 
        !            70: /* GAYLE_CONFIG bit def
        !            71:    (bit 0-1 for program voltage, bit 2-3 for access speed */
        !            72: #define GAYLE_CFG_0V            0x00
        !            73: #define GAYLE_CFG_5V            0x01
        !            74: #define GAYLE_CFG_12V           0x02
        !            75: 
        !            76: #define GAYLE_CFG_100NS         0x08
        !            77: #define GAYLE_CFG_150NS         0x04
        !            78: #define GAYLE_CFG_250NS         0x00
        !            79: #define GAYLE_CFG_720NS         0x0c
        !            80: 
        !            81: /* IDE stuff */
        !            82: 
        !            83: /*  Bases of the IDE interfaces */
        !            84: #define GAYLE_BASE_4000 0xdd2020    /* A4000/A4000T */
        !            85: #define GAYLE_BASE_1200 0xda0000    /* A1200/A600 and E-Matrix 530 */
        !            86: /* IDE drive registers */
        !            87: #define IDE_DATA       0x00
        !            88: #define IDE_ERROR      0x01        /* see err-bits */
        !            89: #define IDE_NSECTOR    0x02        /* nr of sectors to read/write */
        !            90: #define IDE_SECTOR     0x03        /* starting sector */
        !            91: #define IDE_LCYL       0x04        /* starting cylinder */
        !            92: #define IDE_HCYL       0x05        /* high byte of starting cyl */
        !            93: #define IDE_SELECT     0x06        /* 101dhhhh , d=drive, hhhh=head */
        !            94: #define IDE_STATUS     0x07        /* see status-bits */
        !            95: #define IDE_DEVCON     0x0406
        !            96: #define IDE_DRVADDR    0x0407
        !            97: /* STATUS bits */
        !            98: #define IDE_STATUS_ERR 0x01
        !            99: #define IDE_STATUS_IDX 0x02
        !           100: #define IDE_STATUS_DRQ 0x08
        !           101: #define IDE_STATUS_DSC 0x10
        !           102: #define IDE_STATUS_DRDY 0x40
        !           103: #define IDE_STATUS_BSY 0x80
        !           104: /* ERROR bits */
        !           105: #define IDE_ERR_ABRT 0x04
        !           106: 
        !           107: /*
        !           108:  *  These are at different offsets from the base
        !           109:  */
        !           110: #define GAYLE_IRQ_4000  0x3020    /* MSB = 1, Harddisk is source of interrupt */
        !           111: #define GAYLE_IRQ_1200  0x9000
        !           112: #define GAYLE_INT_1200  0xA000
        !           113: 
        !           114: /* GAYLE_IRQ bit def */
        !           115: #define GAYLE_IRQ_IDE  0x80
        !           116: #define GAYLE_IRQ_CCDET        0x40
        !           117: #define GAYLE_IRQ_BVD1 0x20
        !           118: #define GAYLE_IRQ_SC   0x20
        !           119: #define GAYLE_IRQ_BVD2 0x10
        !           120: #define GAYLE_IRQ_DA   0x10
        !           121: #define GAYLE_IRQ_WR   0x08
        !           122: #define GAYLE_IRQ_BSY  0x04
        !           123: #define GAYLE_IRQ_IRQ  0x04
        !           124: #define GAYLE_IRQ_IDEACK1 0x02
        !           125: #define GAYLE_IRQ_IDEACK0 0x01
        !           126: 
        !           127: struct ide_hdf
        !           128: {
        !           129:     uae_u8 secbuf[512 * 256];
        !           130:     uae_u8 multiple_mode;
        !           131:     uae_u8 status;
        !           132:     int irq_delay;
        !           133:     int num;
        !           134: };
        !           135: 
        !           136: static struct ide_hdf idedrive[4];
        !           137: 
        !           138: static int gayle_id_cnt;
        !           139: static uae_u8 gayle_irq, gayle_intena;
        !           140: static uae_u8 ide_select, ide_nsector, ide_sector, ide_lcyl, ide_hcyl, ide_devcon, ide_error, ide_feat;
        !           141: static uae_u8 ide_nsector2, ide_sector2, ide_lcyl2, ide_hcyl2, ide_feat2;
        !           142: static int ide_drv, ide2, ide_splitter;
        !           143: 
        !           144: static struct ide_hdf *ide;
        !           145: 
        !           146: STATIC_INLINE void pw (int offset, uae_u16 w)
        !           147: {
        !           148:     ide->secbuf[offset * 2 + 0] = (uae_u8)w;
        !           149:     ide->secbuf[offset * 2 + 1] = w >> 8;
        !           150: }
        !           151: 
        !           152: static void ps (int offset, char *s, int max)
        !           153: {
        !           154:     int i, len;
        !           155: 
        !           156:     offset *= 2;
        !           157:     len = strlen(s);
        !           158:     for (i = 0; i < max; i++) {
        !           159:        char c = ' ';
        !           160:        if (i < len)
        !           161:            c = s[i];
        !           162:        ide->secbuf[offset ^ 1] = c;
        !           163:        offset++;
        !           164:     }
        !           165: }
        !           166: 
        !           167: static void ide_interrupt(void)
        !           168: {
        !           169:     ide->status |= IDE_STATUS_BSY;
        !           170:     ide->irq_delay = 2;
        !           171: }
        !           172: 
        !           173: static void ide_interrupt_do(struct ide_hdf *ide)
        !           174: {
        !           175:     ide->status &= ~IDE_STATUS_BSY;
        !           176:     if (gayle_intena & GAYLE_IRQ_IDE) {
        !           177:        gayle_irq |= GAYLE_IRQ_IDE;
        !           178:        INTREQ (0x8000 | 0x0008);
        !           179:     }
        !           180: }
        !           181: 
        !           182: static void ide_fail(void)
        !           183: {
        !           184:     ide_error |= IDE_ERR_ABRT;
        !           185: #if 0
        !           186:     if (ide_drv == 1 && idedrive[ide2 + 1].hdhfd.size == 0)
        !           187:        idedrive[ide2].status |= IDE_STATUS_ERR;
        !           188: #endif
        !           189:     ide->status |= IDE_STATUS_ERR;
        !           190:     ide_interrupt();
        !           191: }
        !           192: 
        !           193: static void ide_recalibrate(void)
        !           194: {
        !           195:     write_log ("IDE%d recalibrate\n", ide->num);
        !           196:     ide_sector = 0;
        !           197:     ide_lcyl = ide_hcyl = 0;
        !           198:     ide_interrupt();
        !           199: }
        !           200: 
        !           201: static void ide_identify_drive(void)
        !           202: {
        !           203:     int totalsecs;
        !           204:     int v;
        !           205: 
        !           206:     ide_fail();
        !           207:     return;
        !           208: }
        !           209: 
        !           210: static void ide_initialize_drive_parameters(void)
        !           211: {
        !           212:     ide_error |= IDE_ERR_ABRT;
        !           213:     ide->status |= IDE_STATUS_ERR;
        !           214:     ide_interrupt();
        !           215: }
        !           216: 
        !           217: static void ide_set_multiple_mode(void)
        !           218: {
        !           219:     write_log ("IDE%d drive multiple mode = %d\n", ide->num, ide_nsector);
        !           220:     ide->multiple_mode = ide_nsector;
        !           221:     ide_interrupt();
        !           222: }
        !           223: 
        !           224: static void ide_set_features(void)
        !           225: {
        !           226:     write_log ("IDE%d set features %02.2X (%02.2X)\n", ide->num, ide_feat, ide_nsector);
        !           227:     ide_fail();
        !           228: }
        !           229: 
        !           230: static void ide_read_sectors(int multi)
        !           231: {
        !           232:     ide_fail();
        !           233: }
        !           234: 
        !           235: static void ide_write_sectors(int multi)
        !           236: {
        !           237:     ide_fail();
        !           238: }
        !           239: 
        !           240: static void ide_do_command(uae_u8 cmd)
        !           241: {
        !           242:     if (IDE_LOG > 1)
        !           243:        write_log ("**** IDE%d command %02.2X\n", ide->num, cmd);
        !           244:     ide->status &= ~(IDE_STATUS_DRDY | IDE_STATUS_DRQ | IDE_STATUS_ERR);
        !           245:     ide_error = 0;
        !           246: 
        !           247:     if (cmd == 0x10) { /* recalibrate */
        !           248:        ide_recalibrate();
        !           249:     } else if (cmd == 0xec) { /* identify drive */
        !           250:        ide_identify_drive();
        !           251:     } else if (cmd == 0x91) { /* initialize drive parameters */
        !           252:        ide_initialize_drive_parameters();
        !           253:     } else if (cmd == 0xc6) { /* set multiple mode */
        !           254:        ide_set_multiple_mode();
        !           255:     } else if (cmd == 0x20 || cmd == 0x21) { /* read sectors */
        !           256:        ide_read_sectors(0);
        !           257:     } else if (cmd == 0x30 || cmd == 0x31) { /* write sectors */
        !           258:        ide_write_sectors(0);
        !           259:     } else if (cmd == 0xc4) { /* read multiple */
        !           260:        ide_read_sectors(1);
        !           261:     } else if (cmd == 0xc5) { /* write multiple */
        !           262:        ide_write_sectors(1);
        !           263:     } else if (cmd == 0x50) { /* format track (nop) */
        !           264:        ide_interrupt();
        !           265:     } else if (cmd == 0xa1) { /* ATAPI identify (IDE HD is not ATAPI) */
        !           266:        ide_fail();
        !           267:     } else if (cmd == 0xef) { /* set features  */
        !           268:        ide_set_features();
        !           269:     } else {
        !           270:        ide_fail();
        !           271:        write_log ("IDE: unknown command %x\n", cmd);
        !           272:     }
        !           273: }
        !           274: 
        !           275: static uae_u16 ide_get_data (void)
        !           276: {
        !           277:     if (IDE_LOG > 0)
        !           278:        write_log ("IDE%d DATA read without DRQ!?\n", ide->num);
        !           279:     return 0xffff;
        !           280: }
        !           281: 
        !           282: static void ide_put_data (uae_u16 v)
        !           283: {
        !           284:     if (IDE_LOG > 0)
        !           285:        write_log ("IDE%d DATA write without DRQ!?\n", ide->num);
        !           286: }
        !           287: 
        !           288: static int get_ide_reg (uaecptr addr)
        !           289: {
        !           290:     uaecptr a = addr;
        !           291:     addr &= 0xffff;
        !           292:     if (addr >= 0x3020 && addr <= 0x3021 && currprefs.cs_ide == 2)
        !           293:        return -1;
        !           294:     addr &= ~0x2020;
        !           295:     addr >>= 2;
        !           296:     ide2 = 0;
        !           297:     if (addr & 0x400) {
        !           298:        if (ide_splitter) {
        !           299:            ide2 = 2;
        !           300:            addr &= ~0x400;
        !           301:        }
        !           302:     }
        !           303:     ide = &idedrive[ide_drv + ide2];
        !           304:     return addr;
        !           305: }
        !           306: 
        !           307: static uae_u32 ide_read (uaecptr addr)
        !           308: {
        !           309:     int ide_reg;
        !           310:     uae_u8 v = 0;
        !           311: 
        !           312:     addr &= 0xffff;
        !           313:     if (IDE_LOG > 1 && addr != 0x2000 && addr != 0x2001 && addr != 0x2020 && addr != 0x2021 && addr != GAYLE_IRQ_1200)
        !           314:        write_log ("IDE_READ %08.8X PC=%X\n", addr, m68k_getpc ());
        !           315:     if (currprefs.cs_ide <= 0) {
        !           316:        if (addr == 0x201c) // AR1200 IDE detection hack
        !           317:            return 0x7f;
        !           318:        return 0xff;
        !           319:     }
        !           320:     if (addr >= GAYLE_IRQ_4000 && addr <= GAYLE_IRQ_4000 + 1 && currprefs.cs_ide == 2) {
        !           321:        uae_u8 v = gayle_irq;
        !           322:        gayle_irq = 0;
        !           323:        return v;
        !           324:     }
        !           325:     if (addr >= 0x4000) {
        !           326:        if (addr == GAYLE_IRQ_1200) {
        !           327:            if (currprefs.cs_ide == 1)
        !           328:                return gayle_irq;
        !           329:            return 0;
        !           330:        } else if (addr == GAYLE_INT_1200) {
        !           331:            if (currprefs.cs_ide == 1)
        !           332:                return gayle_intena;
        !           333:            return 0;
        !           334:        }
        !           335:        return 0;
        !           336:     }
        !           337:     ide_reg = get_ide_reg(addr);
        !           338:     /* Emulated "ide killer". Prevents long KS boot delay if no drives installed */
        !           339:     if (ide_reg == IDE_STATUS)
        !           340:        return 0x7f;
        !           341:     return 0xff;
        !           342: 
        !           343: }
        !           344: 
        !           345: static void ide_write (uaecptr addr, uae_u32 val)
        !           346: {
        !           347:     int ide_reg;
        !           348: 
        !           349:     addr &= 0xffff;
        !           350:     ide_devcon &= ~0x80;
        !           351:     if (IDE_LOG > 1 && addr != 0x2000 && addr != 0x2001 && addr != 0x2020 && addr != 0x2021 && addr != GAYLE_IRQ_1200)
        !           352:        write_log ("IDE_WRITE %08.8X=%02.2X PC=%X\n", addr, (uae_u32)val & 0xff, m68k_getpc ());
        !           353:     if (currprefs.cs_ide <= 0)
        !           354:        return;
        !           355:     if (currprefs.cs_ide == 1) {
        !           356:        if (addr == GAYLE_IRQ_1200) {
        !           357:            gayle_irq = 0;
        !           358:            return;
        !           359:        }
        !           360:        if (addr == GAYLE_INT_1200) {
        !           361:            gayle_intena = val;
        !           362:            return;
        !           363:        }
        !           364:     }
        !           365:     if (addr >= 0x4000)
        !           366:        return;
        !           367:     ide_reg = get_ide_reg(addr);
        !           368:     if (IDE_LOG > 2 && ide_reg > 0)
        !           369:        write_log ("IDE%d register %d=%02.2X\n", ide->num, ide_reg, (uae_u32)val & 0xff);
        !           370:     switch (ide_reg)
        !           371:     {
        !           372:        case IDE_DRVADDR:
        !           373:        break;
        !           374:        case IDE_DEVCON:
        !           375:            ide_devcon = val;
        !           376:        break;
        !           377:        case IDE_DATA:
        !           378:        break;
        !           379:        case IDE_ERROR:
        !           380:            ide_feat2 = ide_feat;
        !           381:            ide_feat = val;
        !           382:        break;
        !           383:        case IDE_NSECTOR:
        !           384:            ide_nsector2 = ide_nsector;
        !           385:            ide_nsector = val;
        !           386:        break;
        !           387:        case IDE_SECTOR:
        !           388:            ide_sector2 = ide_sector;
        !           389:            ide_sector = val;
        !           390:        break;
        !           391:        case IDE_LCYL:
        !           392:            ide_lcyl2 = ide_lcyl;
        !           393:            ide_lcyl = val;
        !           394:        break;
        !           395:        case IDE_HCYL:
        !           396:            ide_hcyl2 = ide_hcyl;
        !           397:            ide_hcyl = val;
        !           398:        break;
        !           399:        case IDE_SELECT:
        !           400:            ide_select = val;
        !           401:            ide_drv = (val & 0x10) ? 1 : 0;
        !           402:        break;
        !           403:        case IDE_STATUS:
        !           404:            ide_do_command (val);
        !           405:        break;
        !           406:     }
        !           407: }
        !           408: 
        !           409: static int gayle_read (uaecptr addr)
        !           410: {
        !           411:     uaecptr oaddr = addr;
        !           412:     uae_u32 v = 0;
        !           413: #ifdef JIT
        !           414:     special_mem |= S_READ;
        !           415: #endif
        !           416:     v = ide_read(addr);
        !           417:     if (GAYLE_LOG)
        !           418:        write_log ("GAYLE_READ %08.8X=%02.2X PC=%08.8X\n", oaddr, (uae_u32)v & 0xff, m68k_getpc ());
        !           419:     return v;
        !           420: }
        !           421: static void gayle_write (uaecptr addr, int val)
        !           422: {
        !           423: #ifdef JIT
        !           424:     special_mem |= S_WRITE;
        !           425: #endif
        !           426:     if (GAYLE_LOG)
        !           427:        write_log ("GAYLE_WRITE %08.8X=%02.2X PC=%08.8X\n", addr, (uae_u32)val & 0xff, m68k_getpc ());
        !           428:     ide_write(addr, val);
        !           429: }
        !           430: 
        !           431: static uae_u32 gayle_lget (uaecptr) REGPARAM;
        !           432: static uae_u32 gayle_wget (uaecptr) REGPARAM;
        !           433: static uae_u32 gayle_bget (uaecptr) REGPARAM;
        !           434: static void gayle_lput (uaecptr, uae_u32) REGPARAM;
        !           435: static void gayle_wput (uaecptr, uae_u32) REGPARAM;
        !           436: static void gayle_bput (uaecptr, uae_u32) REGPARAM;
        !           437: 
        !           438: addrbank gayle_bank = {
        !           439:     gayle_lget, gayle_wget, gayle_bget,
        !           440:     gayle_lput, gayle_wput, gayle_bput,
        !           441:     default_xlate, default_check, NULL, "Gayle (low)"
        !           442: };
        !           443: 
        !           444: #if 0
        !           445: static int isa4000t (uaecptr addr)
        !           446: {
        !           447:     if (currprefs.cs_mbdmac != 2)
        !           448:        return 0;
        !           449:     if ((addr & 0xffff) >= (GAYLE_BASE_4000 & 0xffff))
        !           450:        return 0;
        !           451:     return 1;
        !           452: }
        !           453: #endif
        !           454: 
        !           455: static uae_u32 REGPARAM2 gayle_lget (uaecptr addr)
        !           456: {
        !           457:     uae_u32 v;
        !           458: #ifdef JIT
        !           459:     special_mem |= S_READ;
        !           460: #endif
        !           461:     v = gayle_wget (addr) << 16;
        !           462:     v |= gayle_wget (addr + 2);
        !           463:     return v;
        !           464: }
        !           465: static uae_u32 REGPARAM2 gayle_wget (uaecptr addr)
        !           466: {
        !           467:     int ide_reg;
        !           468:     uae_u16 v;
        !           469: #ifdef JIT
        !           470:     special_mem |= S_READ;
        !           471: #endif
        !           472: #if 0
        !           473:     if (isa4000t(addr)) {
        !           474:        addr -= NCR_OFFSET;
        !           475:        return (ncr_bget2 (addr) << 8) | ncr_bget2 (addr + 1);
        !           476:     }
        !           477: #endif
        !           478:     ide_reg = get_ide_reg (addr);
        !           479:     if (ide_reg == IDE_DATA)
        !           480:        return ide_get_data ();
        !           481:     v = gayle_bget (addr) << 8;
        !           482:     v |= gayle_bget (addr + 1);
        !           483:     return v;
        !           484: }
        !           485: static uae_u32 REGPARAM2 gayle_bget (uaecptr addr)
        !           486: {
        !           487: #ifdef JIT
        !           488:     special_mem |= S_READ;
        !           489: #endif
        !           490: #if 0
        !           491:     if (isa4000t(addr)) {
        !           492:        addr -= NCR_OFFSET;
        !           493:        return ncr_bget2(addr);
        !           494:     }
        !           495: #endif
        !           496:     return gayle_read (addr);
        !           497: }
        !           498: 
        !           499: static void REGPARAM2 gayle_lput (uaecptr addr, uae_u32 value)
        !           500: {
        !           501: #ifdef JIT
        !           502:     special_mem |= S_WRITE;
        !           503: #endif
        !           504:     gayle_wput (addr, value >> 16);
        !           505:     gayle_wput (addr + 2, value & 0xffff);
        !           506: }
        !           507: static void REGPARAM2 gayle_wput (uaecptr addr, uae_u32 value)
        !           508: {
        !           509:     int ide_reg;
        !           510: #ifdef JIT
        !           511:     special_mem |= S_WRITE;
        !           512: #endif
        !           513: #if 0
        !           514:     if (isa4000t (addr)) {
        !           515:        addr -= NCR_OFFSET;
        !           516:        ncr_bput2 (addr, value >> 8);
        !           517:        ncr_bput2 (addr + 1, value);
        !           518:        return;
        !           519:     }
        !           520: #endif
        !           521:     ide_reg = get_ide_reg (addr);
        !           522:     if (ide_reg == IDE_DATA) {
        !           523:        ide_put_data(value);
        !           524:        return;
        !           525:     }
        !           526:     gayle_bput (addr, value >> 8);
        !           527:     gayle_bput (addr + 1, value & 0xff);
        !           528: }
        !           529: 
        !           530: static void REGPARAM2 gayle_bput (uaecptr addr, uae_u32 value)
        !           531: {
        !           532: #ifdef JIT
        !           533:     special_mem |= S_WRITE;
        !           534: #endif
        !           535: #if 0
        !           536:     if (isa4000t(addr)) {
        !           537:        addr -= NCR_OFFSET;
        !           538:        ncr_bput2(addr, value);
        !           539:        return;
        !           540:     }
        !           541: #endif
        !           542:     gayle_write (addr, value);
        !           543: }
        !           544: 
        !           545: static void gayle2_write(uaecptr addr, uae_u32 v)
        !           546: {
        !           547:     gayle_id_cnt = 0;
        !           548: }
        !           549: 
        !           550: static uae_u32 gayle2_read(uaecptr addr)
        !           551: {
        !           552:     uae_u8 v = 0;
        !           553:     addr &= 0xffff;
        !           554:     if (addr == 0x1000) {
        !           555:        /* Gayle ID */
        !           556:        if ((gayle_id_cnt & 3) == 2)
        !           557:            v = 0x7f;
        !           558:        else
        !           559:            v = 0x80;
        !           560:        gayle_id_cnt++;
        !           561:     }
        !           562:     return v;
        !           563: }
        !           564: 
        !           565: static uae_u32 gayle2_lget (uaecptr) REGPARAM;
        !           566: static uae_u32 gayle2_wget (uaecptr) REGPARAM;
        !           567: static uae_u32 gayle2_bget (uaecptr) REGPARAM;
        !           568: static void gayle2_lput (uaecptr, uae_u32) REGPARAM;
        !           569: static void gayle2_wput (uaecptr, uae_u32) REGPARAM;
        !           570: static void gayle2_bput (uaecptr, uae_u32) REGPARAM;
        !           571: 
        !           572: addrbank gayle2_bank = {
        !           573:     gayle2_lget, gayle2_wget, gayle2_bget,
        !           574:     gayle2_lput, gayle2_wput, gayle2_bput,
        !           575:     default_xlate, default_check, NULL, "Gayle (high)"
        !           576: };
        !           577: 
        !           578: static uae_u32 REGPARAM2 gayle2_lget (uaecptr addr)
        !           579: {
        !           580:     uae_u32 v;
        !           581: #ifdef JIT
        !           582:     special_mem |= S_READ;
        !           583: #endif
        !           584:     v = gayle2_wget (addr) << 16;
        !           585:     v |= gayle2_wget (addr + 2);
        !           586:     return v;
        !           587: }
        !           588: static uae_u32 REGPARAM2 gayle2_wget (uaecptr addr)
        !           589: {
        !           590:     uae_u16 v;
        !           591: #ifdef JIT
        !           592:     special_mem |= S_READ;
        !           593: #endif
        !           594:     v = gayle2_bget (addr) << 8;
        !           595:     v |= gayle2_bget (addr + 1);
        !           596:     return v;
        !           597: }
        !           598: static uae_u32 REGPARAM2 gayle2_bget (uaecptr addr)
        !           599: {
        !           600: #ifdef JIT
        !           601:     special_mem |= S_READ;
        !           602: #endif
        !           603:     return gayle2_read (addr);
        !           604: }
        !           605: 
        !           606: static void REGPARAM2 gayle2_lput (uaecptr addr, uae_u32 value)
        !           607: {
        !           608: #ifdef JIT
        !           609:     special_mem |= S_WRITE;
        !           610: #endif
        !           611:     gayle2_wput (addr, value >> 16);
        !           612:     gayle2_wput (addr + 2, value & 0xffff);
        !           613: }
        !           614: 
        !           615: static void REGPARAM2 gayle2_wput (uaecptr addr, uae_u32 value)
        !           616: {
        !           617: #ifdef JIT
        !           618:     special_mem |= S_WRITE;
        !           619: #endif
        !           620:     gayle2_bput (addr, value >> 8);
        !           621:     gayle2_bput (addr + 1, value & 0xff);
        !           622: }
        !           623: 
        !           624: static void REGPARAM2 gayle2_bput (uaecptr addr, uae_u32 value)
        !           625: {
        !           626: #ifdef JIT
        !           627:     special_mem |= S_WRITE;
        !           628: #endif
        !           629:     gayle2_write (addr, value);
        !           630: }
        !           631: 
        !           632: static uae_u8 ramsey_config;
        !           633: static int gary_coldboot, gary_toenb, gary_timeout;
        !           634: static int garyidoffset;
        !           635: 
        !           636: static void mbres_write (uaecptr addr, uae_u32 val, int size)
        !           637: {
        !           638:     addr &= 0xffff;
        !           639: 
        !           640:     if (MBRES_LOG > 0)
        !           641:        write_log ("MBRES_WRITE %08X=%08X (%d) PC=%08X S=%d\n", addr, val, size, m68k_getpc (), regs.s);
        !           642:     if (regs.s) { /* CPU FC = supervisor only */
        !           643:        if (addr == 0x1002)
        !           644:            garyidoffset = -1;
        !           645:        if (addr == 0x03)
        !           646:            ramsey_config = val;
        !           647:        if (addr == 0x02)
        !           648:            gary_coldboot = (val & 0x80) ? 1 : 0;
        !           649:        if (addr == 0x01)
        !           650:            gary_toenb = (val & 0x80) ? 1 : 0;
        !           651:        if (addr == 0x00)
        !           652:            gary_timeout = (val & 0x80) ? 1 : 0;
        !           653:     } else {
        !           654:        custom_bank.wput (addr, val);
        !           655:     }
        !           656: }
        !           657: 
        !           658: static uae_u32 mbres_read (uaecptr addr, int size)
        !           659: {
        !           660:     uae_u32 v = 0;
        !           661:     addr &= 0xffff;
        !           662: 
        !           663:     if (regs.s) { /* CPU FC = supervisor only */
        !           664:        /* Gary ID (I don't think this exists in real chips..) */
        !           665:        if (addr == 0x1002 && currprefs.cs_fatgaryrev >= 0) {
        !           666:            garyidoffset++;
        !           667:            garyidoffset &= 7;
        !           668:            v = (currprefs.cs_fatgaryrev << garyidoffset) & 0x80;
        !           669:        }
        !           670:        if (addr == 0x43) { /* RAMSEY revision */
        !           671:            if (currprefs.cs_ramseyrev >= 0)
        !           672:                v = currprefs.cs_ramseyrev;
        !           673:        }
        !           674:        if (addr == 0x03) { /* RAMSEY config */
        !           675:            if (currprefs.cs_ramseyrev >= 0)
        !           676:                v = ramsey_config;
        !           677:        }
        !           678:        if (addr == 0x02) { /* coldreboot flag */
        !           679:            if (currprefs.cs_fatgaryrev >= 0)
        !           680:                v = gary_coldboot ? 0x80 : 0x00;
        !           681:        }
        !           682:        if (addr == 0x01) { /* toenb flag */
        !           683:            if (currprefs.cs_fatgaryrev >= 0)
        !           684:                v = gary_toenb ? 0x80 : 0x00;
        !           685:        }
        !           686:        if (addr == 0x00) { /* timeout flag */
        !           687:            if (currprefs.cs_fatgaryrev >= 0)
        !           688:                 v = gary_timeout ? 0x80 : 0x00;
        !           689:        }
        !           690:     } else {
        !           691:        v = custom_bank.wget (addr);
        !           692:     }
        !           693:     if (MBRES_LOG > 0)
        !           694:        write_log ("MBRES_READ %08X=%08X (%d) PC=%08X S=%d\n", addr, v, size, m68k_getpc (), regs.s);
        !           695:     return v;
        !           696: }
        !           697: 
        !           698: static uae_u32 mbres_lget (uaecptr) REGPARAM;
        !           699: static uae_u32 mbres_wget (uaecptr) REGPARAM;
        !           700: static uae_u32 mbres_bget (uaecptr) REGPARAM;
        !           701: static void mbres_lput (uaecptr, uae_u32) REGPARAM;
        !           702: static void mbres_wput (uaecptr, uae_u32) REGPARAM;
        !           703: static void mbres_bput (uaecptr, uae_u32) REGPARAM;
        !           704: 
        !           705: static uae_u32 REGPARAM2 mbres_lget (uaecptr addr)
        !           706: {
        !           707:     uae_u32 v;
        !           708: #ifdef JIT
        !           709:     special_mem |= S_READ;
        !           710: #endif
        !           711:     v = mbres_wget (addr) << 16;
        !           712:     v |= mbres_wget (addr + 2);
        !           713:     return v;
        !           714: }
        !           715: static uae_u32 REGPARAM2 mbres_wget (uaecptr addr)
        !           716: {
        !           717: #ifdef JIT
        !           718:     special_mem |= S_READ;
        !           719: #endif
        !           720:     return mbres_read (addr, 2);
        !           721: }
        !           722: static uae_u32 REGPARAM2 mbres_bget (uaecptr addr)
        !           723: {
        !           724: #ifdef JIT
        !           725:     special_mem |= S_READ;
        !           726: #endif
        !           727:     return mbres_read (addr, 1);
        !           728: }
        !           729: 
        !           730: static void REGPARAM2 mbres_lput (uaecptr addr, uae_u32 value)
        !           731: {
        !           732: #ifdef JIT
        !           733:     special_mem |= S_WRITE;
        !           734: #endif
        !           735:     mbres_wput (addr, value >> 16);
        !           736:     mbres_wput (addr + 2, value & 0xffff);
        !           737: }
        !           738: 
        !           739: static void REGPARAM2 mbres_wput (uaecptr addr, uae_u32 value)
        !           740: {
        !           741: #ifdef JIT
        !           742:     special_mem |= S_WRITE;
        !           743: #endif
        !           744:     mbres_write (addr, value, 2);
        !           745: }
        !           746: 
        !           747: static void REGPARAM2 mbres_bput (uaecptr addr, uae_u32 value)
        !           748: {
        !           749: #ifdef JIT
        !           750:     special_mem |= S_WRITE;
        !           751: #endif
        !           752:     mbres_write (addr, value, 1);
        !           753: }
        !           754: 
        !           755: addrbank mbres_bank = {
        !           756:     mbres_lget, mbres_wget, mbres_bget,
        !           757:     mbres_lput, mbres_wput, mbres_bput,
        !           758:     default_xlate, default_check, NULL, "Motherboard Resources"
        !           759: };
        !           760: 
        !           761: void gayle_hsync (void)
        !           762: {
        !           763:     int i;
        !           764: 
        !           765:     for (i = 0; i < 4; i++) {
        !           766:        struct ide_hdf *ide = &idedrive[i];
        !           767:        if (ide->irq_delay > 0) {
        !           768:            ide->irq_delay--;
        !           769:            if (ide->irq_delay == 0)
        !           770:                ide_interrupt_do (ide);
        !           771:        }
        !           772:     }
        !           773: }
        !           774: 
        !           775: static uae_u32 gayle_attr_read (uaecptr addr)
        !           776: {
        !           777:     uae_u8 v = 0;
        !           778:     write_log ("R: %x %x\n", addr, m68k_getpc ());
        !           779:     addr &= 262144 - 1;
        !           780:     switch (addr)
        !           781:     {
        !           782:     case 0:
        !           783:        v = 0x91;
        !           784:        break;
        !           785:     case 2:
        !           786:        v = 0x05;
        !           787:        break;
        !           788:     case 4:
        !           789:        v = 0x23;
        !           790:        break;
        !           791:     }
        !           792:     return v;
        !           793: }
        !           794: static void gayle_attr_write (uaecptr addr, uae_u32 v)
        !           795: {
        !           796:     write_log ("W: %x=%x %x\n", addr, v, m68k_getpc ());
        !           797:     addr &= 262144 - 1;
        !           798:     if (addr == 0x40000) {
        !           799:        if (v)
        !           800:            write_log ("GAYLE: Reset active\n");
        !           801:        else
        !           802:            write_log ("GAYLE: Reset non-active\n");
        !           803:     }
        !           804: }
        !           805: 
        !           806: static uae_u32 gayle_attr_lget (uaecptr) REGPARAM;
        !           807: static uae_u32 gayle_attr_wget (uaecptr) REGPARAM;
        !           808: static uae_u32 gayle_attr_bget (uaecptr) REGPARAM;
        !           809: static void gayle_attr_lput (uaecptr, uae_u32) REGPARAM;
        !           810: static void gayle_attr_wput (uaecptr, uae_u32) REGPARAM;
        !           811: static void gayle_attr_bput (uaecptr, uae_u32) REGPARAM;
        !           812: 
        !           813: addrbank gayle_attr_bank = {
        !           814:     gayle_attr_lget, gayle_attr_wget, gayle_attr_bget,
        !           815:     gayle_attr_lput, gayle_attr_wput, gayle_attr_bput,
        !           816:     default_xlate, default_check, NULL, "Gayle PCMCIA attribute"
        !           817: };
        !           818: 
        !           819: static uae_u32 REGPARAM2 gayle_attr_lget (uaecptr addr)
        !           820: {
        !           821:     uae_u32 v;
        !           822: #ifdef JIT
        !           823:     special_mem |= S_READ;
        !           824: #endif
        !           825:     v = gayle_attr_wget (addr) << 16;
        !           826:     v |= gayle_attr_wget (addr + 2);
        !           827:     return v;
        !           828: }
        !           829: static uae_u32 REGPARAM2 gayle_attr_wget (uaecptr addr)
        !           830: {
        !           831:     uae_u16 v;
        !           832: #ifdef JIT
        !           833:     special_mem |= S_READ;
        !           834: #endif
        !           835:     v = gayle_attr_bget (addr) << 8;
        !           836:     v |= gayle_attr_bget (addr + 1);
        !           837:     return v;
        !           838: }
        !           839: static uae_u32 REGPARAM2 gayle_attr_bget (uaecptr addr)
        !           840: {
        !           841: #ifdef JIT
        !           842:     special_mem |= S_READ;
        !           843: #endif
        !           844:     return gayle_attr_read (addr);
        !           845: }
        !           846: 
        !           847: static void REGPARAM2 gayle_attr_lput (uaecptr addr, uae_u32 value)
        !           848: {
        !           849: #ifdef JIT
        !           850:     special_mem |= S_WRITE;
        !           851: #endif
        !           852:     gayle_attr_wput (addr, value >> 16);
        !           853:     gayle_attr_wput (addr + 2, value & 0xffff);
        !           854: }
        !           855: 
        !           856: static void REGPARAM2 gayle_attr_wput (uaecptr addr, uae_u32 value)
        !           857: {
        !           858: #ifdef JIT
        !           859:     special_mem |= S_WRITE;
        !           860: #endif
        !           861:     gayle_attr_bput (addr, value >> 8);
        !           862:     gayle_attr_bput (addr + 1, value & 0xff);
        !           863: }
        !           864: 
        !           865: static void REGPARAM2 gayle_attr_bput (uaecptr addr, uae_u32 value)
        !           866: {
        !           867: #ifdef JIT
        !           868:     special_mem |= S_WRITE;
        !           869: #endif
        !           870:     gayle_attr_write (addr, value);
        !           871: }
        !           872: 
        !           873: static void initide (void)
        !           874: {
        !           875:     int i;
        !           876: 
        !           877:     if (savestate_state == STATE_RESTORE)
        !           878:        return;
        !           879:     ide_error = 1;
        !           880:     ide_sector = ide_nsector = 1;
        !           881:     ide_select = 0;
        !           882:     ide_lcyl = ide_hcyl = ide_devcon = ide_feat = 0;
        !           883:     ide_drv = 0;
        !           884:     ide_splitter = 0;
        !           885:     gayle_irq = gayle_intena = 0;
        !           886:     if (currprefs.cs_ide == 2)
        !           887:        gayle_intena = 0xff;
        !           888: 
        !           889: }
        !           890: 
        !           891: void gayle_reset (int hardreset)
        !           892: {
        !           893:     static char bankname[100];
        !           894:     initide ();
        !           895:     if (hardreset) {
        !           896:        ramsey_config = 0;
        !           897:        gary_coldboot = 1;
        !           898:        gary_timeout = 0;
        !           899:        gary_toenb = 0;
        !           900:     }
        !           901:     strcpy (bankname, "Gayle (low)");
        !           902:     if (currprefs.cs_ide == 2)
        !           903:        strcpy (bankname, "A4000 IDE");
        !           904: #if 0
        !           905:     if (currprefs.cs_mbdmac == 2) {
        !           906:        strcat (bankname," + NCR53C710 SCSI");
        !           907:        ncr_reset ();
        !           908:     }
        !           909: #endif
        !           910:     gayle_bank.name = bankname;
        !           911: }
        !           912: 
        !           913: const uae_u8 *restore_gayle (const uae_u8 *src)
        !           914: {
        !           915:     changed_prefs.cs_ide = restore_u8();
        !           916:     gayle_intena = restore_u8();
        !           917:     gayle_irq = restore_u8();
        !           918:     ide_error = 0;
        !           919:     return src;
        !           920: }
        !           921: 
        !           922: uae_u8 *save_gayle (int *len)
        !           923: {
        !           924:     uae_u8 *dstbak, *dst;
        !           925: 
        !           926:     if (currprefs.cs_ide <= 0)
        !           927:        return NULL;
        !           928:     dstbak = dst = (uae_u8*)malloc (1000);
        !           929:     save_u8 (currprefs.cs_ide);
        !           930:     save_u8 (gayle_intena);
        !           931:     save_u8 (gayle_irq);
        !           932:     *len = dst - dstbak;
        !           933:     return dstbak;
        !           934: }

unix.superglobalmegacorp.com

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