1 #include "joy.h"
2 
3 #include <cassert>
4 #include <cstdio>
5 
read(u16 addr)6 u8 JOY::read(u16 addr) {
7   // Why | 0x40?
8   // On the NES and Famicom, the top three (or five) bits are Open Bus.
9   // Usually, the last value on the bus prior to accessing the controlleris is
10   // the byte of the controller port address, i.e: 0x40.
11   // Certain games (such as Paperboy) rely on this behavior and require that
12   // reads from the controller ports return exactly $40 or $41 as appropriate.
13   if (addr == 0x4016) return this->joy[0] ? this->joy[0]->read(addr) | 0x40 : 0;
14   if (addr == 0x4017) return this->joy[1] ? this->joy[1]->read(addr) | 0x40 : 0;
15 
16   fprintf(stderr,
17     "[JOY] Should not be able to read from 0x%04X! Check MMU!\n", addr
18   );
19 
20   assert(false);
21   return 0x00;
22 }
23 
peek(u16 addr) const24 u8 JOY::peek(u16 addr) const {
25   if (addr == 0x4016) return this->joy[0] ? this->joy[0]->peek(addr) | 0x40 : 0;
26   if (addr == 0x4017) return this->joy[1] ? this->joy[1]->peek(addr) | 0x40 : 0;
27 
28   fprintf(stderr,
29     "[JOY] Should not be able to peek from 0x%04X! Check MMU!\n", addr
30   );
31 
32   assert(false);
33   return 0x00;
34 }
35 
write(u16 addr,u8 val)36 void JOY::write(u16 addr, u8 val) {
37   if (addr == 0x4016) {
38     if (this->joy[0]) return this->joy[0]->write(addr, val);
39     if (this->joy[1]) return this->joy[1]->write(addr, val);
40   }
41 
42   fprintf(stderr,
43     "[JOY] Should not be able to write to 0x%04X! Check MMU!\n", addr
44   );
45   assert(false);
46 }
47 
attach_joy(uint port,Memory * joy)48 void JOY::attach_joy(uint port, Memory* joy) {
49   assert(port < 2);
50   this->joy[port] = joy;
51 }
52 
detach_joy(uint port)53 void JOY::detach_joy(uint port) {
54   assert(port < 2);
55   this->joy[port] = nullptr;
56 }
57