Annotation of nono/vm/pedec.cpp, revision 1.1.1.11

1.1       root        1: //
                      2: // nono
                      3: // Copyright (C) 2020 nono project
                      4: // Licensed under nono-license.txt
                      5: //
                      6: 
1.1.1.5   root        7: //
                      8: // PEDEC
                      9: //
                     10: 
                     11: // IODevice
                     12: //    |
                     13: //    +-- InterruptDevice (割り込みコントローラの共通部)
                     14: //          |
                     15: //          +-- M680x0Interrupt (m68k 割り込みコントローラの共通部)
                     16: //          |     |
                     17: //          |     +-- X68030Interrupt  (X68030 の割り込みコントローラ)
                     18: //          |     +-- LunaInterrupt    (LUNA-I の割り込みコントローラ)
                     19: //          |
                     20: //          |  +-------------+
                     21: //          +--| PEDECDevice | (X68030 の Lv1 担当コントローラ)
                     22: //          |  +-------------+
                     23: //          |
1.1.1.7   root       24: //          +-- SysCtlrDevice  (LUNA-88K の割り込みコントローラ)
1.1.1.5   root       25: 
1.1       root       26: #include "pedec.h"
                     27: #include "fdc.h"
1.1.1.6   root       28: #include "fdd.h"
1.1.1.11! root       29: #include "mainapp.h"
1.1       root       30: #include "spc.h"
                     31: 
1.1.1.5   root       32: // コンストラクタ
1.1       root       33: PEDECDevice::PEDECDevice()
1.1.1.7   root       34:        : inherited(OBJ_PEDEC)
1.1       root       35: {
                     36: }
                     37: 
1.1.1.5   root       38: // デストラクタ
1.1       root       39: PEDECDevice::~PEDECDevice()
                     40: {
1.1.1.7   root       41: }
                     42: 
                     43: // 初期化
                     44: bool
                     45: PEDECDevice::Init()
                     46: {
                     47:        if (inherited::Init() == false) {
                     48:                return false;
                     49:        }
                     50: 
                     51:        interrupt = GetInterruptDevice();
1.1.1.9   root       52: 
                     53:        // 検索順
                     54:        RegistINT(IntmapSPC,  "SPC",  GetSPCDevice());
                     55:        RegistINT(IntmapFDC,  "FDC",  GetFDCDevice());
                     56:        RegistINT(IntmapHDD,  "HDD",  NULL);
                     57:        RegistINT(IntmapPRT,  "PRT",  NULL);
                     58:        // FDD は4本を共有しているのでいろいろ特別扱い。
                     59:        RegistINT(IntmapFDD0, "FDD0", gMainApp.FindObject<FDDDevice>(OBJ_FDD(0)));
                     60:        RegistINT(IntmapFDD1, "FDD1", gMainApp.FindObject<FDDDevice>(OBJ_FDD(1)));
                     61:        RegistINT(IntmapFDD2, "FDD2", gMainApp.FindObject<FDDDevice>(OBJ_FDD(2)));
                     62:        RegistINT(IntmapFDD3, "FDD3", gMainApp.FindObject<FDDDevice>(OBJ_FDD(3)));
                     63:        // 名前表示用
                     64:        RegistINT(IntmapFDD,  "FDD",  NULL);
                     65: 
                     66:        // 表示順
                     67:        disp_list = {
                     68:                IntmapSPC,
                     69:                IntmapFDC,
                     70:                IntmapFDD,
                     71:                IntmapHDD,
                     72:                IntmapPRT,
                     73:        };
1.1.1.7   root       74: 
                     75:        return true;
1.1       root       76: }
                     77: 
1.1.1.5   root       78: // リセット
1.1       root       79: void
1.1.1.5   root       80: PEDECDevice::ResetHard(bool poweron)
1.1       root       81: {
1.1.1.5   root       82:        inherited::ResetHard(poweron);
1.1.1.4   root       83: 
1.1.1.9   root       84:        intmap_enable = IntmapSPC;
                     85:        ChangeInterrupt();
                     86: 
1.1       root       87:        // XXX vector
                     88: }
                     89: 
1.1.1.9   root       90: busdata
1.1.1.10  root       91: PEDECDevice::ReadPort(uint32 offset)
1.1       root       92: {
1.1.1.9   root       93:        busdata data;
                     94: 
1.1.1.2   root       95:        switch (offset) {
1.1       root       96:         case 0:        // $E9C001 割り込みステータス
1.1.1.9   root       97:                data = GetStat();
                     98:                break;
1.1       root       99: 
                    100:         case 1:        // $E9C003 割り込みベクタ
                    101:                // 書き込み専用
1.1.1.9   root      102:                data = 0xff;
                    103:                break;
1.1       root      104: 
                    105:         default:
1.1.1.9   root      106:                data = 0xff;
                    107:                break;
1.1       root      108:        }
1.1.1.9   root      109: 
                    110:        // XXX wait?
1.1.1.10  root      111:        data |= BusData::Size1;
1.1.1.9   root      112:        return data;
1.1       root      113: }
                    114: 
1.1.1.9   root      115: busdata
1.1.1.10  root      116: PEDECDevice::WritePort(uint32 offset, uint32 data)
1.1       root      117: {
1.1.1.2   root      118:        switch (offset) {
1.1       root      119:         case 0:        // $E9C001 割り込みマスク
1.1.1.9   root      120:                intmap_enable = IntmapSPC;
                    121:                intmap_enable |= (data & 0x08) ? IntmapHDD : 0;
                    122:                intmap_enable |= (data & 0x04) ? IntmapFDC : 0;
                    123:                intmap_enable |= (data & 0x02) ? IntmapFDD : 0;
                    124:                intmap_enable |= (data & 0x01) ? IntmapPRT : 0;
1.1       root      125: 
1.1.1.10  root      126:                putlog(1, "Set Interrupt Mask HDD=%u FDC=%u FDD=%u PRT=%u",
1.1.1.9   root      127:                        ((intmap_enable & IntmapHDD) ? 1 : 0),
                    128:                        ((intmap_enable & IntmapFDC) ? 1 : 0),
                    129:                        ((intmap_enable & IntmapFDD) ? 1 : 0),
                    130:                        ((intmap_enable & IntmapPRT) ? 1 : 0));
                    131:                break;
1.1       root      132: 
                    133:         case 1:        // $E9C003 割り込みベクタ
                    134:                vector = data & 0xfc;
1.1.1.6   root      135:                putlog(1, "Set Interrupt Vector $%02x", vector);
1.1.1.9   root      136:                break;
1.1       root      137: 
                    138:         default:
1.1.1.9   root      139:                break;
1.1       root      140:        }
1.1.1.9   root      141: 
                    142:        // XXX wait?
1.1.1.10  root      143:        busdata r = BusData::Size1;
                    144:        return r;
1.1       root      145: }
                    146: 
1.1.1.9   root      147: busdata
1.1.1.10  root      148: PEDECDevice::PeekPort(uint32 offset)
1.1       root      149: {
1.1.1.2   root      150:        switch (offset) {
1.1       root      151:         case 0:
                    152:                return GetStat();
                    153: 
                    154:         case 1:
                    155:                // 書き込み専用
                    156:                return 0xff;
                    157: 
                    158:         default:
                    159:                return 0xff;
                    160:        }
                    161: }
                    162: 
1.1.1.10  root      163: bool
                    164: PEDECDevice::PokePort(uint32 offset, uint32 data)
                    165: {
                    166:        return false;
                    167: }
                    168: 
1.1.1.4   root      169: void
                    170: PEDECDevice::MonitorUpdate(TextScreen& screen, uint intr_level, int y)
                    171: {
1.1.1.9   root      172:        for (uint32 map : disp_list) {
1.1.1.4   root      173:                int clz = __builtin_clz(map);
1.1.1.9   root      174:                screen.Puts(4, y, TA::OnOff(intmap_status & map), GetIntName(map));
                    175:                if (intr_level >= 1 || (intmap_enable & map) == 0) {
1.1.1.8   root      176:                        screen.Puts(11, y, "Mask");
1.1.1.4   root      177:                }
1.1.1.9   root      178:                uint64 cnt = counter[clz];
                    179:                if (__predict_false(map == IntmapFDD)) {
                    180:                        // FDD は4つの和
                    181:                        cnt += counter[clz + 1] + counter[clz + 2] + counter[clz + 3];
                    182:                }
                    183:                screen.Print(15, y, "%26s", format_number(cnt).c_str());
1.1.1.4   root      184:                y++;
                    185:        }
                    186: }
                    187: 
1.1       root      188: // 割り込みステータスレジスタの値を取得。
                    189: // (Peek からも呼ばれるので副作用を持たせてはいけない)
                    190: uint32
                    191: PEDECDevice::GetStat() const
                    192: {
                    193:        uint32 data = 0;
1.1.1.9   root      194:        data |= (intmap_status & IntmapFDC) ? 0x80 : 0;
                    195:        data |= (intmap_status & IntmapFDD) ? 0x40 : 0;
                    196:        data |= (intmap_status & IntmapPRT) ? 0x20 : 0;
                    197:        data |= (intmap_status & IntmapHDD) ? 0x10 : 0;
                    198:        data |= (intmap_enable & IntmapHDD) ? 0x08 : 0;
                    199:        data |= (intmap_enable & IntmapFDC) ? 0x04 : 0;
                    200:        data |= (intmap_enable & IntmapFDD) ? 0x02 : 0;
                    201:        data |= (intmap_enable & IntmapPRT) ? 0x01 : 0;
1.1       root      202:        return data;
                    203: }
                    204: 
1.1.1.4   root      205: // 割り込み信号線の状態を変える
1.1       root      206: void
1.1.1.4   root      207: PEDECDevice::ChangeInterrupt()
1.1       root      208: {
1.1.1.4   root      209: #if 0 // こんなログ出したいかも
1.1       root      210:                // ログ表示のためだけ
1.1.1.9   root      211:                if ((intmap_enable & IntmapFDC)) {
1.1       root      212:                        putlog(1, "FDC からの割り込み要求");
                    213:                } else {
                    214:                        putlog(2, "FDC からの割り込み要求(マスク)");
                    215:                }
1.1.1.4   root      216: #endif
1.1       root      217: 
1.1.1.9   root      218:        uint32 stat = (intmap_status & intmap_enable);
1.1.1.7   root      219:        interrupt->ChangeINT(this, stat);
1.1       root      220: }
                    221: 
                    222: // 割り込みアクノリッジ
1.1.1.9   root      223: busdata
1.1       root      224: PEDECDevice::InterruptAcknowledge(int lv)
                    225: {
1.1.1.9   root      226:        uint32 stat = (intmap_status & intmap_enable);
1.1       root      227: 
                    228:        // SPC と I/O コントローラ担当の4本どっちが優先かは分からないので
                    229:        // SPC を優先しておくのでいいだろう。
                    230:        if ((stat & IntmapSPC)) {
                    231:                // XXX PEDEC のベクタに影響されるか?
                    232:                return 0x6c;
                    233:        }
                    234: 
                    235:        if ((stat & IntmapFDC)) {
                    236:                return vector + 0;
1.1.1.6   root      237:        } else if ((stat & IntmapFDD)) {
                    238:                return vector + 1;
1.1       root      239:        } else {
1.1.1.10  root      240:                return BusData::BusErr;
1.1.1.6   root      241:        }
1.1.1.4   root      242: }

unix.superglobalmegacorp.com

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