1 /* Copyright (c) 2013-2016 Jeffrey Pfau
2  *
3  * This Source Code Form is subject to the terms of the Mozilla Public
4  * License, v. 2.0. If a copy of the MPL was not distributed with this
5  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #include <mgba/internal/gb/io.h>
7 
8 #include <mgba/internal/gb/gb.h>
9 #include <mgba/internal/gb/sio.h>
10 #include <mgba/internal/gb/serialize.h>
11 
12 mLOG_DEFINE_CATEGORY(GB_IO, "GB I/O", "gb.io");
13 
14 MGBA_EXPORT const char* const GBIORegisterNames[] = {
15 	[GB_REG_JOYP] = "JOYP",
16 	[GB_REG_SB] = "SB",
17 	[GB_REG_SC] = "SC",
18 	[GB_REG_DIV] = "DIV",
19 	[GB_REG_TIMA] = "TIMA",
20 	[GB_REG_TMA] = "TMA",
21 	[GB_REG_TAC] = "TAC",
22 	[GB_REG_IF] = "IF",
23 	[GB_REG_NR10] = "NR10",
24 	[GB_REG_NR11] = "NR11",
25 	[GB_REG_NR12] = "NR12",
26 	[GB_REG_NR13] = "NR13",
27 	[GB_REG_NR14] = "NR14",
28 	[GB_REG_NR21] = "NR21",
29 	[GB_REG_NR22] = "NR22",
30 	[GB_REG_NR23] = "NR23",
31 	[GB_REG_NR24] = "NR24",
32 	[GB_REG_NR30] = "NR30",
33 	[GB_REG_NR31] = "NR31",
34 	[GB_REG_NR32] = "NR32",
35 	[GB_REG_NR33] = "NR33",
36 	[GB_REG_NR34] = "NR34",
37 	[GB_REG_NR41] = "NR41",
38 	[GB_REG_NR42] = "NR42",
39 	[GB_REG_NR43] = "NR43",
40 	[GB_REG_NR44] = "NR44",
41 	[GB_REG_NR50] = "NR50",
42 	[GB_REG_NR51] = "NR51",
43 	[GB_REG_NR52] = "NR52",
44 	[GB_REG_LCDC] = "LCDC",
45 	[GB_REG_STAT] = "STAT",
46 	[GB_REG_SCY] = "SCY",
47 	[GB_REG_SCX] = "SCX",
48 	[GB_REG_LY] = "LY",
49 	[GB_REG_LYC] = "LYC",
50 	[GB_REG_DMA] = "DMA",
51 	[GB_REG_BGP] = "BGP",
52 	[GB_REG_OBP0] = "OBP0",
53 	[GB_REG_OBP1] = "OBP1",
54 	[GB_REG_WY] = "WY",
55 	[GB_REG_WX] = "WX",
56 	[GB_REG_KEY0] = "KEY0",
57 	[GB_REG_KEY1] = "KEY1",
58 	[GB_REG_VBK] = "VBK",
59 	[GB_REG_BANK] = "BANK",
60 	[GB_REG_HDMA1] = "HDMA1",
61 	[GB_REG_HDMA2] = "HDMA2",
62 	[GB_REG_HDMA3] = "HDMA3",
63 	[GB_REG_HDMA4] = "HDMA4",
64 	[GB_REG_HDMA5] = "HDMA5",
65 	[GB_REG_RP] = "RP",
66 	[GB_REG_BCPS] = "BCPS",
67 	[GB_REG_BCPD] = "BCPD",
68 	[GB_REG_OCPS] = "OCPS",
69 	[GB_REG_OCPD] = "OCPD",
70 	[GB_REG_OPRI] = "OPRI",
71 	[GB_REG_SVBK] = "SVBK",
72 	[GB_REG_IE] = "IE",
73 };
74 
75 static const uint8_t _registerMask[] = {
76 	[GB_REG_SC]   = 0x7E, // TODO: GBC differences
77 	[GB_REG_IF]   = 0xE0,
78 	[GB_REG_TAC]  = 0xF8,
79 	[GB_REG_NR10] = 0x80,
80 	[GB_REG_NR11] = 0x3F,
81 	[GB_REG_NR12] = 0x00,
82 	[GB_REG_NR13] = 0xFF,
83 	[GB_REG_NR14] = 0xBF,
84 	[GB_REG_NR21] = 0x3F,
85 	[GB_REG_NR22] = 0x00,
86 	[GB_REG_NR23] = 0xFF,
87 	[GB_REG_NR24] = 0xBF,
88 	[GB_REG_NR30] = 0x7F,
89 	[GB_REG_NR31] = 0xFF,
90 	[GB_REG_NR32] = 0x9F,
91 	[GB_REG_NR33] = 0xFF,
92 	[GB_REG_NR34] = 0xBF,
93 	[GB_REG_NR41] = 0xFF,
94 	[GB_REG_NR42] = 0x00,
95 	[GB_REG_NR43] = 0x00,
96 	[GB_REG_NR44] = 0xBF,
97 	[GB_REG_NR50] = 0x00,
98 	[GB_REG_NR51] = 0x00,
99 	[GB_REG_NR52] = 0x70,
100 	[GB_REG_STAT] = 0x80,
101 	[GB_REG_KEY1] = 0x7E,
102 	[GB_REG_VBK]  = 0xFE,
103 	[GB_REG_OCPS] = 0x40,
104 	[GB_REG_BCPS] = 0x40,
105 	[GB_REG_OPRI] = 0xFE,
106 	[GB_REG_SVBK] = 0xF8,
107 	[GB_REG_UNK75] = 0x8F,
108 	[GB_REG_IE]   = 0xE0,
109 };
110 
111 static uint8_t _readKeys(struct GB* gb);
112 static uint8_t _readKeysFiltered(struct GB* gb);
113 
_writeSGBBits(struct GB * gb,int bits)114 static void _writeSGBBits(struct GB* gb, int bits) {
115 	if (!bits) {
116 		gb->sgbBit = -1;
117 		memset(gb->sgbPacket, 0, sizeof(gb->sgbPacket));
118 	}
119 	if (bits == gb->currentSgbBits) {
120 		return;
121 	}
122 	switch (bits) {
123 	case 0:
124 	case 1:
125 		if (gb->currentSgbBits & 2) {
126 			gb->sgbIncrement = !gb->sgbIncrement;
127 		}
128 		break;
129 	case 3:
130 		if (gb->sgbIncrement) {
131 			gb->sgbIncrement = false;
132 			gb->sgbCurrentController = (gb->sgbCurrentController + 1) & gb->sgbControllers;
133 		}
134 		break;
135 	}
136 	gb->currentSgbBits = bits;
137 	if (gb->sgbBit == 128 && bits == 2) {
138 		GBVideoWriteSGBPacket(&gb->video, gb->sgbPacket);
139 		++gb->sgbBit;
140 	}
141 	if (gb->sgbBit >= 128) {
142 		return;
143 	}
144 	switch (bits) {
145 	case 1:
146 		if (gb->sgbBit < 0) {
147 			return;
148 		}
149 		gb->sgbPacket[gb->sgbBit >> 3] |= 1 << (gb->sgbBit & 7);
150 		break;
151 	case 3:
152 		++gb->sgbBit;
153 	default:
154 		break;
155 	}
156 }
157 
GBIOInit(struct GB * gb)158 void GBIOInit(struct GB* gb) {
159 	memset(gb->memory.io, 0, sizeof(gb->memory.io));
160 }
161 
GBIOReset(struct GB * gb)162 void GBIOReset(struct GB* gb) {
163 	memset(gb->memory.io, 0, sizeof(gb->memory.io));
164 
165 	GBIOWrite(gb, GB_REG_TIMA, 0);
166 	GBIOWrite(gb, GB_REG_TMA, 0);
167 	GBIOWrite(gb, GB_REG_TAC, 0);
168 	GBIOWrite(gb, GB_REG_IF, 1);
169 	gb->audio.playingCh1 = false;
170 	gb->audio.playingCh2 = false;
171 	gb->audio.playingCh3 = false;
172 	gb->audio.playingCh4 = false;
173 	GBIOWrite(gb, GB_REG_NR52, 0xF1);
174 	GBIOWrite(gb, GB_REG_NR14, 0x3F);
175 	GBIOWrite(gb, GB_REG_NR10, 0x80);
176 	GBIOWrite(gb, GB_REG_NR11, 0xBF);
177 	GBIOWrite(gb, GB_REG_NR12, 0xF3);
178 	GBIOWrite(gb, GB_REG_NR13, 0xF3);
179 	GBIOWrite(gb, GB_REG_NR24, 0x3F);
180 	GBIOWrite(gb, GB_REG_NR21, 0x3F);
181 	GBIOWrite(gb, GB_REG_NR22, 0x00);
182 	GBIOWrite(gb, GB_REG_NR34, 0x3F);
183 	GBIOWrite(gb, GB_REG_NR30, 0x7F);
184 	GBIOWrite(gb, GB_REG_NR31, 0xFF);
185 	GBIOWrite(gb, GB_REG_NR32, 0x9F);
186 	GBIOWrite(gb, GB_REG_NR44, 0x3F);
187 	GBIOWrite(gb, GB_REG_NR41, 0xFF);
188 	GBIOWrite(gb, GB_REG_NR42, 0x00);
189 	GBIOWrite(gb, GB_REG_NR43, 0x00);
190 	GBIOWrite(gb, GB_REG_NR50, 0x77);
191 	GBIOWrite(gb, GB_REG_NR51, 0xF3);
192 	if (!gb->biosVf) {
193 		GBIOWrite(gb, GB_REG_LCDC, 0x91);
194 		gb->memory.io[GB_REG_BANK] = 1;
195 	} else {
196 		GBIOWrite(gb, GB_REG_LCDC, 0x00);
197 		gb->memory.io[GB_REG_BANK] = 0xFF;
198 	}
199 	GBIOWrite(gb, GB_REG_SCY, 0x00);
200 	GBIOWrite(gb, GB_REG_SCX, 0x00);
201 	GBIOWrite(gb, GB_REG_LYC, 0x00);
202 	gb->memory.io[GB_REG_DMA] = 0xFF;
203 	GBIOWrite(gb, GB_REG_BGP, 0xFC);
204 	if (gb->model < GB_MODEL_CGB) {
205 		GBIOWrite(gb, GB_REG_OBP0, 0xFF);
206 		GBIOWrite(gb, GB_REG_OBP1, 0xFF);
207 	}
208 	GBIOWrite(gb, GB_REG_WY, 0x00);
209 	GBIOWrite(gb, GB_REG_WX, 0x00);
210 	if (gb->model & GB_MODEL_CGB) {
211 		GBIOWrite(gb, GB_REG_KEY0, 0);
212 		GBIOWrite(gb, GB_REG_JOYP, 0xFF);
213 		GBIOWrite(gb, GB_REG_VBK, 0);
214 		GBIOWrite(gb, GB_REG_BCPS, 0x80);
215 		GBIOWrite(gb, GB_REG_OCPS, 0);
216 		GBIOWrite(gb, GB_REG_SVBK, 1);
217 		GBIOWrite(gb, GB_REG_HDMA1, 0xFF);
218 		GBIOWrite(gb, GB_REG_HDMA2, 0xFF);
219 		GBIOWrite(gb, GB_REG_HDMA3, 0xFF);
220 		GBIOWrite(gb, GB_REG_HDMA4, 0xFF);
221 		gb->memory.io[GB_REG_HDMA5] = 0xFF;
222 	} else {
223 		memset(&gb->memory.io[GB_REG_KEY0], 0xFF, GB_REG_PCM34 - GB_REG_KEY0 + 1);
224 	}
225 
226 	if (gb->model & GB_MODEL_SGB) {
227 		GBIOWrite(gb, GB_REG_JOYP, 0xFF);
228 	}
229 	GBIOWrite(gb, GB_REG_IE, 0x00);
230 }
231 
GBIOWrite(struct GB * gb,unsigned address,uint8_t value)232 void GBIOWrite(struct GB* gb, unsigned address, uint8_t value) {
233 	switch (address) {
234 	case GB_REG_SB:
235 		GBSIOWriteSB(&gb->sio, value);
236 		break;
237 	case GB_REG_SC:
238 		GBSIOWriteSC(&gb->sio, value);
239 		break;
240 	case GB_REG_DIV:
241 		GBTimerDivReset(&gb->timer);
242 		return;
243 	case GB_REG_NR10:
244 		if (gb->audio.enable) {
245 			GBAudioWriteNR10(&gb->audio, value);
246 		} else {
247 			value = 0;
248 		}
249 		break;
250 	case GB_REG_NR11:
251 		if (gb->audio.enable) {
252 			GBAudioWriteNR11(&gb->audio, value);
253 		} else {
254 			if (gb->audio.style == GB_AUDIO_DMG) {
255 				GBAudioWriteNR11(&gb->audio, value & _registerMask[GB_REG_NR11]);
256 			}
257 			value = 0;
258 		}
259 		break;
260 	case GB_REG_NR12:
261 		if (gb->audio.enable) {
262 			GBAudioWriteNR12(&gb->audio, value);
263 		} else {
264 			value = 0;
265 		}
266 		break;
267 	case GB_REG_NR13:
268 		if (gb->audio.enable) {
269 			GBAudioWriteNR13(&gb->audio, value);
270 		} else {
271 			value = 0;
272 		}
273 		break;
274 	case GB_REG_NR14:
275 		if (gb->audio.enable) {
276 			GBAudioWriteNR14(&gb->audio, value);
277 		} else {
278 			value = 0;
279 		}
280 		break;
281 	case GB_REG_NR21:
282 		if (gb->audio.enable) {
283 			GBAudioWriteNR21(&gb->audio, value);
284 		} else {
285 			if (gb->audio.style == GB_AUDIO_DMG) {
286 				GBAudioWriteNR21(&gb->audio, value & _registerMask[GB_REG_NR21]);
287 			}
288 			value = 0;
289 		}
290 		break;
291 	case GB_REG_NR22:
292 		if (gb->audio.enable) {
293 			GBAudioWriteNR22(&gb->audio, value);
294 		} else {
295 			value = 0;
296 		}
297 		break;
298 	case GB_REG_NR23:
299 		if (gb->audio.enable) {
300 			GBAudioWriteNR23(&gb->audio, value);
301 		} else {
302 			value = 0;
303 		}
304 		break;
305 	case GB_REG_NR24:
306 		if (gb->audio.enable) {
307 			GBAudioWriteNR24(&gb->audio, value);
308 		} else {
309 			value = 0;
310 		}
311 		break;
312 	case GB_REG_NR30:
313 		if (gb->audio.enable) {
314 			GBAudioWriteNR30(&gb->audio, value);
315 		} else {
316 			value = 0;
317 		}
318 		break;
319 	case GB_REG_NR31:
320 		if (gb->audio.enable || gb->audio.style == GB_AUDIO_DMG) {
321 			GBAudioWriteNR31(&gb->audio, value);
322 		} else {
323 			value = 0;
324 		}
325 		break;
326 	case GB_REG_NR32:
327 		if (gb->audio.enable) {
328 			GBAudioWriteNR32(&gb->audio, value);
329 		} else {
330 			value = 0;
331 		}
332 		break;
333 	case GB_REG_NR33:
334 		if (gb->audio.enable) {
335 			GBAudioWriteNR33(&gb->audio, value);
336 		} else {
337 			value = 0;
338 		}
339 		break;
340 	case GB_REG_NR34:
341 		if (gb->audio.enable) {
342 			GBAudioWriteNR34(&gb->audio, value);
343 		} else {
344 			value = 0;
345 		}
346 		break;
347 	case GB_REG_NR41:
348 		if (gb->audio.enable || gb->audio.style == GB_AUDIO_DMG) {
349 			GBAudioWriteNR41(&gb->audio, value);
350 		} else {
351 			value = 0;
352 		}
353 		break;
354 	case GB_REG_NR42:
355 		if (gb->audio.enable) {
356 			GBAudioWriteNR42(&gb->audio, value);
357 		} else {
358 			value = 0;
359 		}
360 		break;
361 	case GB_REG_NR43:
362 		if (gb->audio.enable) {
363 			GBAudioWriteNR43(&gb->audio, value);
364 		} else {
365 			value = 0;
366 		}
367 		break;
368 	case GB_REG_NR44:
369 		if (gb->audio.enable) {
370 			GBAudioWriteNR44(&gb->audio, value);
371 		} else {
372 			value = 0;
373 		}
374 		break;
375 	case GB_REG_NR50:
376 		if (gb->audio.enable) {
377 			GBAudioWriteNR50(&gb->audio, value);
378 		} else {
379 			value = 0;
380 		}
381 		break;
382 	case GB_REG_NR51:
383 		if (gb->audio.enable) {
384 			GBAudioWriteNR51(&gb->audio, value);
385 		} else {
386 			value = 0;
387 		}
388 		break;
389 	case GB_REG_NR52:
390 		GBAudioWriteNR52(&gb->audio, value);
391 		value &= 0x80;
392 		value |= gb->memory.io[GB_REG_NR52] & 0x0F;
393 		break;
394 	case GB_REG_WAVE_0:
395 	case GB_REG_WAVE_1:
396 	case GB_REG_WAVE_2:
397 	case GB_REG_WAVE_3:
398 	case GB_REG_WAVE_4:
399 	case GB_REG_WAVE_5:
400 	case GB_REG_WAVE_6:
401 	case GB_REG_WAVE_7:
402 	case GB_REG_WAVE_8:
403 	case GB_REG_WAVE_9:
404 	case GB_REG_WAVE_A:
405 	case GB_REG_WAVE_B:
406 	case GB_REG_WAVE_C:
407 	case GB_REG_WAVE_D:
408 	case GB_REG_WAVE_E:
409 	case GB_REG_WAVE_F:
410 		if (!gb->audio.playingCh3 || gb->audio.style != GB_AUDIO_DMG) {
411 			gb->audio.ch3.wavedata8[address - GB_REG_WAVE_0] = value;
412 		} else if(gb->audio.ch3.readable) {
413 			gb->audio.ch3.wavedata8[gb->audio.ch3.window >> 1] = value;
414 		}
415 		break;
416 	case GB_REG_JOYP:
417 		gb->memory.io[GB_REG_JOYP] = value | 0x0F;
418 		_readKeys(gb);
419 		if (gb->model & GB_MODEL_SGB) {
420 			_writeSGBBits(gb, (value >> 4) & 3);
421 		}
422 		return;
423 	case GB_REG_TIMA:
424 		if (value && mTimingUntil(&gb->timing, &gb->timer.irq) > 2 - (int) gb->doubleSpeed) {
425 			mTimingDeschedule(&gb->timing, &gb->timer.irq);
426 		}
427 		if (mTimingUntil(&gb->timing, &gb->timer.irq) == (int) gb->doubleSpeed - 2) {
428 			return;
429 		}
430 		break;
431 	case GB_REG_TMA:
432 		if (mTimingUntil(&gb->timing, &gb->timer.irq) == (int) gb->doubleSpeed - 2) {
433 			gb->memory.io[GB_REG_TIMA] = value;
434 		}
435 		break;
436 	case GB_REG_TAC:
437 		value = GBTimerUpdateTAC(&gb->timer, value);
438 		break;
439 	case GB_REG_IF:
440 		gb->memory.io[GB_REG_IF] = value | 0xE0;
441 		GBUpdateIRQs(gb);
442 		return;
443 	case GB_REG_LCDC:
444 		// TODO: handle GBC differences
445 		GBVideoProcessDots(&gb->video, 0);
446 		value = gb->video.renderer->writeVideoRegister(gb->video.renderer, address, value);
447 		GBVideoWriteLCDC(&gb->video, value);
448 		break;
449 	case GB_REG_LYC:
450 		GBVideoWriteLYC(&gb->video, value);
451 		break;
452 	case GB_REG_DMA:
453 		GBMemoryDMA(gb, value << 8);
454 		break;
455 	case GB_REG_SCY:
456 	case GB_REG_SCX:
457 	case GB_REG_WY:
458 	case GB_REG_WX:
459 		GBVideoProcessDots(&gb->video, 0);
460 		value = gb->video.renderer->writeVideoRegister(gb->video.renderer, address, value);
461 		break;
462 	case GB_REG_BGP:
463 	case GB_REG_OBP0:
464 	case GB_REG_OBP1:
465 		GBVideoProcessDots(&gb->video, 0);
466 		GBVideoWritePalette(&gb->video, address, value);
467 		break;
468 	case GB_REG_STAT:
469 		GBVideoWriteSTAT(&gb->video, value);
470 		value = gb->video.stat;
471 		break;
472 	case GB_REG_BANK:
473 		if (gb->memory.io[GB_REG_BANK] != 0xFF) {
474 			break;
475 		}
476 		GBUnmapBIOS(gb);
477 		if (gb->model >= GB_MODEL_CGB && gb->memory.io[GB_REG_KEY0] < 0x80) {
478 			gb->model = GB_MODEL_DMG;
479 			GBVideoDisableCGB(&gb->video);
480 		}
481 		break;
482 	case GB_REG_IE:
483 		gb->memory.ie = value;
484 		GBUpdateIRQs(gb);
485 		return;
486 	default:
487 		if (gb->model >= GB_MODEL_CGB) {
488 			switch (address) {
489 			case GB_REG_KEY0:
490 				break;
491 			case GB_REG_KEY1:
492 				value &= 0x1;
493 				value |= gb->memory.io[address] & 0x80;
494 				break;
495 			case GB_REG_VBK:
496 				GBVideoSwitchBank(&gb->video, value);
497 				break;
498 			case GB_REG_HDMA1:
499 			case GB_REG_HDMA2:
500 			case GB_REG_HDMA3:
501 			case GB_REG_HDMA4:
502 				// Handled transparently by the registers
503 				break;
504 			case GB_REG_HDMA5:
505 				value = GBMemoryWriteHDMA5(gb, value);
506 				break;
507 			case GB_REG_BCPS:
508 				gb->video.bcpIndex = value & 0x3F;
509 				gb->video.bcpIncrement = value & 0x80;
510 				gb->memory.io[GB_REG_BCPD] = gb->video.palette[gb->video.bcpIndex >> 1] >> (8 * (gb->video.bcpIndex & 1));
511 				break;
512 			case GB_REG_BCPD:
513 				if (gb->video.mode != 3) {
514 					GBVideoProcessDots(&gb->video, 0);
515 				}
516 				GBVideoWritePalette(&gb->video, address, value);
517 				return;
518 			case GB_REG_OCPS:
519 				gb->video.ocpIndex = value & 0x3F;
520 				gb->video.ocpIncrement = value & 0x80;
521 				gb->memory.io[GB_REG_OCPD] = gb->video.palette[8 * 4 + (gb->video.ocpIndex >> 1)] >> (8 * (gb->video.ocpIndex & 1));
522 				break;
523 			case GB_REG_OCPD:
524 				if (gb->video.mode != 3) {
525 					GBVideoProcessDots(&gb->video, 0);
526 				}
527 				GBVideoWritePalette(&gb->video, address, value);
528 				return;
529 			case GB_REG_SVBK:
530 				GBMemorySwitchWramBank(&gb->memory, value);
531 				value = gb->memory.wramCurrentBank;
532 				break;
533 			default:
534 				goto failed;
535 			}
536 			goto success;
537 		}
538 		failed:
539 		mLOG(GB_IO, GAME_ERROR, "Writing to unknown register FF%02X:%02X", address, value);
540 		return;
541 	}
542 	success:
543 	gb->memory.io[address] = value;
544 }
545 
_readKeys(struct GB * gb)546 static uint8_t _readKeys(struct GB* gb) {
547 	uint8_t keys = *gb->keySource;
548 	if (gb->sgbCurrentController != 0) {
549 		keys = 0;
550 	}
551 	uint8_t joyp = gb->memory.io[GB_REG_JOYP];
552 	switch (joyp & 0x30) {
553 	case 0x30:
554 		keys = gb->sgbCurrentController;
555 		break;
556 	case 0x20:
557 		keys >>= 4;
558 		break;
559 	case 0x10:
560 		break;
561 	case 0x00:
562 		keys |= keys >> 4;
563 		break;
564 	}
565 	gb->memory.io[GB_REG_JOYP] = (0xCF | joyp) ^ (keys & 0xF);
566 	if (joyp & ~gb->memory.io[GB_REG_JOYP] & 0xF) {
567 		gb->memory.io[GB_REG_IF] |= (1 << GB_IRQ_KEYPAD);
568 		GBUpdateIRQs(gb);
569 	}
570 	return gb->memory.io[GB_REG_JOYP];
571 }
572 
_readKeysFiltered(struct GB * gb)573 static uint8_t _readKeysFiltered(struct GB* gb) {
574 	uint8_t keys = _readKeys(gb);
575 	if (!gb->allowOpposingDirections && (keys & 0x30) == 0x20) {
576 		unsigned rl = keys & 0x03;
577 		unsigned ud = keys & 0x0C;
578 		if (!rl) {
579 			keys |= 0x03;
580 		}
581 		if (!ud) {
582 			keys |= 0x0C;
583 		}
584 	}
585 	return keys;
586 }
587 
GBIORead(struct GB * gb,unsigned address)588 uint8_t GBIORead(struct GB* gb, unsigned address) {
589 	switch (address) {
590 	case GB_REG_JOYP:
591 		{
592 			size_t c;
593 			for (c = 0; c < mCoreCallbacksListSize(&gb->coreCallbacks); ++c) {
594 				struct mCoreCallbacks* callbacks = mCoreCallbacksListGetPointer(&gb->coreCallbacks, c);
595 				if (callbacks->keysRead) {
596 					callbacks->keysRead(callbacks->context);
597 				}
598 			}
599 		}
600 		return _readKeysFiltered(gb);
601 	case GB_REG_IE:
602 		return gb->memory.ie;
603 	case GB_REG_WAVE_0:
604 	case GB_REG_WAVE_1:
605 	case GB_REG_WAVE_2:
606 	case GB_REG_WAVE_3:
607 	case GB_REG_WAVE_4:
608 	case GB_REG_WAVE_5:
609 	case GB_REG_WAVE_6:
610 	case GB_REG_WAVE_7:
611 	case GB_REG_WAVE_8:
612 	case GB_REG_WAVE_9:
613 	case GB_REG_WAVE_A:
614 	case GB_REG_WAVE_B:
615 	case GB_REG_WAVE_C:
616 	case GB_REG_WAVE_D:
617 	case GB_REG_WAVE_E:
618 	case GB_REG_WAVE_F:
619 		if (gb->audio.playingCh3) {
620 			if (gb->audio.ch3.readable || gb->audio.style != GB_AUDIO_DMG) {
621 				return gb->audio.ch3.wavedata8[gb->audio.ch3.window >> 1];
622 			} else {
623 				return 0xFF;
624 			}
625 		} else {
626 			return gb->audio.ch3.wavedata8[address - GB_REG_WAVE_0];
627 		}
628 		break;
629 	case GB_REG_PCM12:
630 		if (gb->model < GB_MODEL_CGB) {
631 			mLOG(GB_IO, GAME_ERROR, "Reading from CGB register FF%02X in DMG mode", address);
632 		} else if (gb->audio.enable) {
633 			return (gb->audio.ch1.sample) | (gb->audio.ch2.sample << 4);
634 		}
635 		break;
636 	case GB_REG_PCM34:
637 		if (gb->model < GB_MODEL_CGB) {
638 			mLOG(GB_IO, GAME_ERROR, "Reading from CGB register FF%02X in DMG mode", address);
639 		} else if (gb->audio.enable) {
640 			GBAudioUpdateChannel4(&gb->audio);
641 			return (gb->audio.ch3.sample) | (gb->audio.ch4.sample << 4);
642 		}
643 		break;
644 	case GB_REG_SB:
645 	case GB_REG_SC:
646 	case GB_REG_IF:
647 	case GB_REG_NR10:
648 	case GB_REG_NR11:
649 	case GB_REG_NR12:
650 	case GB_REG_NR14:
651 	case GB_REG_NR21:
652 	case GB_REG_NR22:
653 	case GB_REG_NR24:
654 	case GB_REG_NR30:
655 	case GB_REG_NR32:
656 	case GB_REG_NR34:
657 	case GB_REG_NR41:
658 	case GB_REG_NR42:
659 	case GB_REG_NR43:
660 	case GB_REG_NR44:
661 	case GB_REG_NR50:
662 	case GB_REG_NR51:
663 	case GB_REG_NR52:
664 	case GB_REG_DIV:
665 	case GB_REG_TIMA:
666 	case GB_REG_TMA:
667 	case GB_REG_TAC:
668 	case GB_REG_STAT:
669 	case GB_REG_LCDC:
670 	case GB_REG_SCY:
671 	case GB_REG_SCX:
672 	case GB_REG_LY:
673 	case GB_REG_LYC:
674 	case GB_REG_DMA:
675 	case GB_REG_BGP:
676 	case GB_REG_OBP0:
677 	case GB_REG_OBP1:
678 	case GB_REG_WY:
679 	case GB_REG_WX:
680 		// Handled transparently by the registers
681 		break;
682 	case GB_REG_KEY1:
683 	case GB_REG_VBK:
684 	case GB_REG_HDMA1:
685 	case GB_REG_HDMA2:
686 	case GB_REG_HDMA3:
687 	case GB_REG_HDMA4:
688 	case GB_REG_HDMA5:
689 	case GB_REG_BCPS:
690 	case GB_REG_BCPD:
691 	case GB_REG_OCPS:
692 	case GB_REG_OCPD:
693 	case GB_REG_SVBK:
694 	case GB_REG_UNK72:
695 	case GB_REG_UNK73:
696 	case GB_REG_UNK75:
697 		// Handled transparently by the registers
698 		if (gb->model < GB_MODEL_CGB) {
699 			// In DMG mode, these all get initialized to 0xFF during reset
700 			// But in DMG-on-CGB mode, they get initialized by the CGB reset so they can be non-zero
701 			mLOG(GB_IO, GAME_ERROR, "Reading from CGB register FF%02X in DMG mode", address);
702 		}
703 		break;
704 	default:
705 		mLOG(GB_IO, STUB, "Reading from unknown register FF%02X", address);
706 		return 0xFF;
707 	}
708 	return gb->memory.io[address] | _registerMask[address];
709 }
710 
GBTestKeypadIRQ(struct GB * gb)711 void GBTestKeypadIRQ(struct GB* gb) {
712 	_readKeys(gb);
713 }
714 
715 struct GBSerializedState;
GBIOSerialize(const struct GB * gb,struct GBSerializedState * state)716 void GBIOSerialize(const struct GB* gb, struct GBSerializedState* state) {
717 	memcpy(state->io, gb->memory.io, GB_SIZE_IO);
718 	state->ie = gb->memory.ie;
719 }
720 
GBIODeserialize(struct GB * gb,const struct GBSerializedState * state)721 void GBIODeserialize(struct GB* gb, const struct GBSerializedState* state) {
722 	memcpy(gb->memory.io, state->io, GB_SIZE_IO);
723 	gb->memory.ie = state->ie;
724 
725 	gb->audio.enable = GBAudioEnableGetEnable(*gb->audio.nr52);
726 	if (gb->audio.enable) {
727 		gb->audio.playingCh1 = false;
728 		GBIOWrite(gb, GB_REG_NR10, gb->memory.io[GB_REG_NR10]);
729 		GBIOWrite(gb, GB_REG_NR11, gb->memory.io[GB_REG_NR11]);
730 		GBIOWrite(gb, GB_REG_NR12, gb->memory.io[GB_REG_NR12]);
731 		GBIOWrite(gb, GB_REG_NR13, gb->memory.io[GB_REG_NR13]);
732 		gb->audio.ch1.control.frequency &= 0xFF;
733 		gb->audio.ch1.control.frequency |= GBAudioRegisterControlGetFrequency(gb->memory.io[GB_REG_NR14] << 8);
734 		gb->audio.ch1.control.stop = GBAudioRegisterControlGetStop(gb->memory.io[GB_REG_NR14] << 8);
735 		gb->audio.playingCh2 = false;
736 		GBIOWrite(gb, GB_REG_NR21, gb->memory.io[GB_REG_NR21]);
737 		GBIOWrite(gb, GB_REG_NR22, gb->memory.io[GB_REG_NR22]);
738 		GBIOWrite(gb, GB_REG_NR23, gb->memory.io[GB_REG_NR23]);
739 		gb->audio.ch2.control.frequency &= 0xFF;
740 		gb->audio.ch2.control.frequency |= GBAudioRegisterControlGetFrequency(gb->memory.io[GB_REG_NR24] << 8);
741 		gb->audio.ch2.control.stop = GBAudioRegisterControlGetStop(gb->memory.io[GB_REG_NR24] << 8);
742 		gb->audio.playingCh3 = false;
743 		GBIOWrite(gb, GB_REG_NR30, gb->memory.io[GB_REG_NR30]);
744 		GBIOWrite(gb, GB_REG_NR31, gb->memory.io[GB_REG_NR31]);
745 		GBIOWrite(gb, GB_REG_NR32, gb->memory.io[GB_REG_NR32]);
746 		GBIOWrite(gb, GB_REG_NR33, gb->memory.io[GB_REG_NR33]);
747 		gb->audio.ch3.rate &= 0xFF;
748 		gb->audio.ch3.rate |= GBAudioRegisterControlGetRate(gb->memory.io[GB_REG_NR34] << 8);
749 		gb->audio.ch3.stop = GBAudioRegisterControlGetStop(gb->memory.io[GB_REG_NR34] << 8);
750 		gb->audio.playingCh4 = false;
751 		GBIOWrite(gb, GB_REG_NR41, gb->memory.io[GB_REG_NR41]);
752 		GBIOWrite(gb, GB_REG_NR42, gb->memory.io[GB_REG_NR42]);
753 		GBIOWrite(gb, GB_REG_NR43, gb->memory.io[GB_REG_NR43]);
754 		gb->audio.ch4.stop = GBAudioRegisterNoiseControlGetStop(gb->memory.io[GB_REG_NR44]);
755 		GBIOWrite(gb, GB_REG_NR50, gb->memory.io[GB_REG_NR50]);
756 		GBIOWrite(gb, GB_REG_NR51, gb->memory.io[GB_REG_NR51]);
757 	}
758 
759 	gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_LCDC, state->io[GB_REG_LCDC]);
760 	gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_SCY, state->io[GB_REG_SCY]);
761 	gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_SCX, state->io[GB_REG_SCX]);
762 	gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_WY, state->io[GB_REG_WY]);
763 	gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_WX, state->io[GB_REG_WX]);
764 	if (gb->model & GB_MODEL_SGB) {
765 		gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_BGP, state->io[GB_REG_BGP]);
766 		gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_OBP0, state->io[GB_REG_OBP0]);
767 		gb->video.renderer->writeVideoRegister(gb->video.renderer, GB_REG_OBP1, state->io[GB_REG_OBP1]);
768 	}
769 	gb->video.stat = state->io[GB_REG_STAT];
770 }
771