|
|
1.1 root 1: //
2: // nono
3: // Copyright (C) 2018 [email protected]
4: //
5:
6: #include "crtc2.h"
7: #include "renderer.h"
8:
9: CRTC2Device::CRTC2Device()
10: {
11: logname = "crtc2";
12: devname = "CRTC2";
13: devaddr = 0xd1000000;
14:
15: vdisp_event.dev = this;
16: vdisp_event.func = (DeviceCallback_t)&CRTC2Device::VDispCallback;
1.1.1.2 root 17: vdisp_event.SetName("CRTC2 V-DISP");
1.1 root 18: }
19:
20: CRTC2Device::~CRTC2Device()
21: {
22: }
23:
24: void
25: CRTC2Device::ResetHard()
26: {
27: // リセット信号で初期化されるレジスタ (他は維持)
28: reg[30] = 0;
29: reg[31] = 0;
30: reg[32] = 0;
31:
32: // 未確認
33: ar = 0;
34:
35: // XXX 適当
36: // すぐに垂直帰線期間を開始する
37: vdisp_event.time = 0;
38: vdisp_event.code = 1;
1.1.1.3 ! root 39: vdisp_event.Start();
1.1 root 40: }
41:
42: uint64
1.1.1.3 ! root 43: CRTC2Device::Read(uint32 addr)
1.1 root 44: {
45: uint32 data;
46:
1.1.1.3 ! root 47: switch (addr) {
1.1 root 48: case 0: // アドレスレジスタ
49: // アドレスレジスタは書き込み専用
50: // XXX 何が読めるか
51: data = 0xff;
52: putlog(1, "書き込み専用レジスタ AR の読み出し");
53: break;
54:
55: case 1: // データレジスタ
56: switch (ar) {
57: case 12 ... 25: // 読み出し可能
58: case 28 ... 31:
59: case 33:
60: case 36 ... 39:
61: data = reg[ar];
62: putlog(2, "R%02d -> $%02x", ar, data);
63: break;
64:
65: case 40 ... 63: // 範囲外
66: // 未使用レジスタの読み出しは $00 (p.17)
67: data = 0;
68: putlog(1, "未使用レジスタ読み込み R%02d", ar);
69: break;
70:
71: default: // 書き込み専用レジスタ
72: // 読み出しは 0 になる (p.112)
73: data = 0;
74: putlog(1, "書き込み専用レジスタ R%02d の読み出し", ar);
75: break;
76: }
77: break;
78:
79: default:
1.1.1.3 ! root 80: __unreachable();
1.1 root 81: }
82: return data;
83: }
84:
85: uint64
1.1.1.3 ! root 86: CRTC2Device::Write(uint32 addr, uint32 data)
1.1 root 87: {
1.1.1.3 ! root 88: switch (addr) {
1.1 root 89: case 0: // アドレスレジスタ
90: ar = data & 0x3f;
91: putlog(3, "アドレスレジスタ <- $%02x", ar);
92: return 0;
93:
94: case 1: // データレジスタ
95: switch (ar) {
96: case 16 ... 17: // 読み出し専用レジスタ
97: case 28:
98: putlog(1, "読み出し専用レジスタへの書き込み R%02d <- $%02x",
99: ar, data);
100: break;
101:
102: case 40 ... 63: // 範囲外
103: putlog(1, "未使用レジスタ書き込み R%02d <- $%02x", ar, data);
104: break;
105:
106: default: // 書き込み可能レジスタ
107: reg[ar] = data;
108: putlog(2, "R%02d <- $%02x", ar, data);
109: break;
110: }
111: return 0;
112:
113: default:
1.1.1.3 ! root 114: __unreachable();
1.1 root 115: }
116: }
117:
118: uint64
1.1.1.3 ! root 119: CRTC2Device::Peek(uint32 addr)
1.1 root 120: {
1.1.1.3 ! root 121: switch (addr) {
1.1 root 122: case 0: // アドレスレジスタ
123: return ar;
124:
125: case 1: // データレジスタ
126: return reg[ar];
127:
128: default:
1.1.1.3 ! root 129: __unreachable();
1.1 root 130: }
131: }
132:
133: // 垂直表示・帰線イベント
134: // arg == 1 なら表示期間開始、arg == 0 なら帰線期間開始。
135: void
136: CRTC2Device::VDispCallback(int arg)
137: {
138: // 今はここで1画面まるごと作成
139: if (arg) {
140: // Render に作画指示
141: gRenderer->Render();
142: }
143:
144: // 次のタイミングを計算
145: // XXX まだ CRTC から計算していない
146: if (arg) {
147: // 垂直表示期間
148: vdisp_event.time = 16234.496_usec; // 1024*Ht
149: } else {
150: // 垂直帰線期間
151: vdisp_event.time = 507.328_usec; // 32*Ht
152: }
153: vdisp_event.code = 1 - arg;
1.1.1.3 ! root 154: vdisp_event.Start();
1.1 root 155: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.