summaryrefslogtreecommitdiff
path: root/apu.c
blob: 3c0393c8975d4b48e4702a3abd6813139f4267f4 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
#include <stdio.h>
#include <string.h>

#include "apu.h"

struct apu apu = {0};

void
apu_init(void)
{
	memset(&apu, 0, sizeof(apu));
}

uint8_t
apu_read(uint16_t addr)
{
	switch (addr) {
	/* pulse1 */
	case 0x4000:
		return (apu.pulse1.duty << 6) | (apu.pulse1.envelope << 5)
		    | (apu.pulse1.const_vol << 4) | apu.pulse1.envelope_vol;
	case 0x4001:
		return (apu.pulse1.sweep_enable << 7) | (apu.pulse1.sweep_period << 4)
		    | (apu.pulse1.sweep_negative << 3) | apu.pulse1.sweep_shift_count;
	case 0x4002:
		return apu.pulse1.timer_low;
	case 0x4003:
		return (apu.pulse1.length_counter_load << 3) | apu.pulse1.timer_high;
	/* pulse2 */
	case 0x4004:
		return (apu.pulse2.duty << 6) | (apu.pulse2.envelope << 5)
		    | (apu.pulse2.const_vol << 4) | apu.pulse2.envelope_vol;
	case 0x4005:
		return (apu.pulse1.sweep_enable << 7) | (apu.pulse1.sweep_period << 4)
		    | (apu.pulse1.sweep_negative << 3) | apu.pulse1.sweep_shift_count;
	case 0x4006:
		return apu.pulse1.timer_low;
	case 0x4007:
		return (apu.pulse1.length_counter_load << 3) | apu.pulse1.timer_high;
	/* status */
	case 0x4015:
		return (apu.status.dmc_int << 7) | (apu.status.frame_int << 6)
		    | (apu.status.dmc_active << 4) | (apu.status.lc_noise << 3)
		    | (apu.status.lc_triangle << 2) | (apu.status.lc_pulse2 << 1)
		    | apu.status.lc_pulse1;
	default:
		fprintf(stderr, "Invalid APU read at $%04X!\n", addr);
		return 0;
	};
}

void
apu_write(uint16_t addr, uint8_t byte)
{
}