OXYGENHUB
◆ main openmsx / src / sound / opll.cc
45.6 KiB · C++ · last changed chore(): initial commit 1 month ago source blame history raw
e8555c89 Andy McCall 1
/*
2
 * Copyright (C) 2019 Nuke.YKT
3
 *
4
 * This program is free software; you can redistribute it and/or
5
 * modify it under the terms of the GNU General Public License
6
 * as published by the Free Software Foundation; either version 2
7
 * of the License, or (at your option) any later version.
8
 *
9
 * This program is distributed in the hope that it will be useful,
10
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
 * GNU General Public License for more details.
13
 *
14
 *
15
 *  Yamaha YM2413 emulator
16
 *  Thanks:
17
 *      siliconpr0n.org(digshadow, John McMaster):
18
 *          VRC VII decap and die shot.
19
 *
20
 *  version: 1.0.1
21
 */
22
23
#include "opll.hh"
24
#include <cstring>
25
26
enum : uint8_t {
27
    eg_num_attack = 0,
28
    eg_num_decay = 1,
29
    eg_num_sustain = 2,
30
    eg_num_release = 3
31
};
32
33
enum : uint8_t {
34
    rm_num_bd0 = 0,
35
    rm_num_hh = 1,
36
    rm_num_tom = 2,
37
    rm_num_bd1 = 3,
38
    rm_num_sd = 4,
39
    rm_num_tc = 5
40
};
41
42
/* logsin table */
43
static const uint16_t logsinrom[256] = {
44
    0x859, 0x6c3, 0x607, 0x58b, 0x52e, 0x4e4, 0x4a6, 0x471,
45
    0x443, 0x41a, 0x3f5, 0x3d3, 0x3b5, 0x398, 0x37e, 0x365,
46
    0x34e, 0x339, 0x324, 0x311, 0x2ff, 0x2ed, 0x2dc, 0x2cd,
47
    0x2bd, 0x2af, 0x2a0, 0x293, 0x286, 0x279, 0x26d, 0x261,
48
    0x256, 0x24b, 0x240, 0x236, 0x22c, 0x222, 0x218, 0x20f,
49
    0x206, 0x1fd, 0x1f5, 0x1ec, 0x1e4, 0x1dc, 0x1d4, 0x1cd,
50
    0x1c5, 0x1be, 0x1b7, 0x1b0, 0x1a9, 0x1a2, 0x19b, 0x195,
51
    0x18f, 0x188, 0x182, 0x17c, 0x177, 0x171, 0x16b, 0x166,
52
    0x160, 0x15b, 0x155, 0x150, 0x14b, 0x146, 0x141, 0x13c,
53
    0x137, 0x133, 0x12e, 0x129, 0x125, 0x121, 0x11c, 0x118,
54
    0x114, 0x10f, 0x10b, 0x107, 0x103, 0x0ff, 0x0fb, 0x0f8,
55
    0x0f4, 0x0f0, 0x0ec, 0x0e9, 0x0e5, 0x0e2, 0x0de, 0x0db,
56
    0x0d7, 0x0d4, 0x0d1, 0x0cd, 0x0ca, 0x0c7, 0x0c4, 0x0c1,
57
    0x0be, 0x0bb, 0x0b8, 0x0b5, 0x0b2, 0x0af, 0x0ac, 0x0a9,
58
    0x0a7, 0x0a4, 0x0a1, 0x09f, 0x09c, 0x099, 0x097, 0x094,
59
    0x092, 0x08f, 0x08d, 0x08a, 0x088, 0x086, 0x083, 0x081,
60
    0x07f, 0x07d, 0x07a, 0x078, 0x076, 0x074, 0x072, 0x070,
61
    0x06e, 0x06c, 0x06a, 0x068, 0x066, 0x064, 0x062, 0x060,
62
    0x05e, 0x05c, 0x05b, 0x059, 0x057, 0x055, 0x053, 0x052,
63
    0x050, 0x04e, 0x04d, 0x04b, 0x04a, 0x048, 0x046, 0x045,
64
    0x043, 0x042, 0x040, 0x03f, 0x03e, 0x03c, 0x03b, 0x039,
65
    0x038, 0x037, 0x035, 0x034, 0x033, 0x031, 0x030, 0x02f,
66
    0x02e, 0x02d, 0x02b, 0x02a, 0x029, 0x028, 0x027, 0x026,
67
    0x025, 0x024, 0x023, 0x022, 0x021, 0x020, 0x01f, 0x01e,
68
    0x01d, 0x01c, 0x01b, 0x01a, 0x019, 0x018, 0x017, 0x017,
69
    0x016, 0x015, 0x014, 0x014, 0x013, 0x012, 0x011, 0x011,
70
    0x010, 0x00f, 0x00f, 0x00e, 0x00d, 0x00d, 0x00c, 0x00c,
71
    0x00b, 0x00a, 0x00a, 0x009, 0x009, 0x008, 0x008, 0x007,
72
    0x007, 0x007, 0x006, 0x006, 0x005, 0x005, 0x005, 0x004,
73
    0x004, 0x004, 0x003, 0x003, 0x003, 0x002, 0x002, 0x002,
74
    0x002, 0x001, 0x001, 0x001, 0x001, 0x001, 0x001, 0x001,
75
    0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000
76
};
77
78
/* exp table */
79
static const uint16_t exprom[256] = {
80
    0x7fa, 0x7f5, 0x7ef, 0x7ea, 0x7e4, 0x7df, 0x7da, 0x7d4,
81
    0x7cf, 0x7c9, 0x7c4, 0x7bf, 0x7b9, 0x7b4, 0x7ae, 0x7a9,
82
    0x7a4, 0x79f, 0x799, 0x794, 0x78f, 0x78a, 0x784, 0x77f,
83
    0x77a, 0x775, 0x770, 0x76a, 0x765, 0x760, 0x75b, 0x756,
84
    0x751, 0x74c, 0x747, 0x742, 0x73d, 0x738, 0x733, 0x72e,
85
    0x729, 0x724, 0x71f, 0x71a, 0x715, 0x710, 0x70b, 0x706,
86
    0x702, 0x6fd, 0x6f8, 0x6f3, 0x6ee, 0x6e9, 0x6e5, 0x6e0,
87
    0x6db, 0x6d6, 0x6d2, 0x6cd, 0x6c8, 0x6c4, 0x6bf, 0x6ba,
88
    0x6b5, 0x6b1, 0x6ac, 0x6a8, 0x6a3, 0x69e, 0x69a, 0x695,
89
    0x691, 0x68c, 0x688, 0x683, 0x67f, 0x67a, 0x676, 0x671,
90
    0x66d, 0x668, 0x664, 0x65f, 0x65b, 0x657, 0x652, 0x64e,
91
    0x649, 0x645, 0x641, 0x63c, 0x638, 0x634, 0x630, 0x62b,
92
    0x627, 0x623, 0x61e, 0x61a, 0x616, 0x612, 0x60e, 0x609,
93
    0x605, 0x601, 0x5fd, 0x5f9, 0x5f5, 0x5f0, 0x5ec, 0x5e8,
94
    0x5e4, 0x5e0, 0x5dc, 0x5d8, 0x5d4, 0x5d0, 0x5cc, 0x5c8,
95
    0x5c4, 0x5c0, 0x5bc, 0x5b8, 0x5b4, 0x5b0, 0x5ac, 0x5a8,
96
    0x5a4, 0x5a0, 0x59c, 0x599, 0x595, 0x591, 0x58d, 0x589,
97
    0x585, 0x581, 0x57e, 0x57a, 0x576, 0x572, 0x56f, 0x56b,
98
    0x567, 0x563, 0x560, 0x55c, 0x558, 0x554, 0x551, 0x54d,
99
    0x549, 0x546, 0x542, 0x53e, 0x53b, 0x537, 0x534, 0x530,
100
    0x52c, 0x529, 0x525, 0x522, 0x51e, 0x51b, 0x517, 0x514,
101
    0x510, 0x50c, 0x509, 0x506, 0x502, 0x4ff, 0x4fb, 0x4f8,
102
    0x4f4, 0x4f1, 0x4ed, 0x4ea, 0x4e7, 0x4e3, 0x4e0, 0x4dc,
103
    0x4d9, 0x4d6, 0x4d2, 0x4cf, 0x4cc, 0x4c8, 0x4c5, 0x4c2,
104
    0x4be, 0x4bb, 0x4b8, 0x4b5, 0x4b1, 0x4ae, 0x4ab, 0x4a8,
105
    0x4a4, 0x4a1, 0x49e, 0x49b, 0x498, 0x494, 0x491, 0x48e,
106
    0x48b, 0x488, 0x485, 0x482, 0x47e, 0x47b, 0x478, 0x475,
107
    0x472, 0x46f, 0x46c, 0x469, 0x466, 0x463, 0x460, 0x45d,
108
    0x45a, 0x457, 0x454, 0x451, 0x44e, 0x44b, 0x448, 0x445,
109
    0x442, 0x43f, 0x43c, 0x439, 0x436, 0x433, 0x430, 0x42d,
110
    0x42a, 0x428, 0x425, 0x422, 0x41f, 0x41c, 0x419, 0x416,
111
    0x414, 0x411, 0x40e, 0x40b, 0x408, 0x406, 0x403, 0x400
112
};
113
114
static const opll_patch_t patch_ds1001[opll_patch_max] = {
115
    { 0x05, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x03, 0x01 },{ 0x00, 0x00 },{ 0x0e, 0x08 },{ 0x08, 0x01 },{ 0x04, 0x02 },{ 0x02, 0x07 } },
116
    { 0x14, 0x00, 0x01, 0x05,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x03, 0x01 },{ 0x00, 0x00 },{ 0x0d, 0x0f },{ 0x08, 0x06 },{ 0x02, 0x01 },{ 0x03, 0x02 } },
117
    { 0x08, 0x00, 0x01, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0f, 0x0b },{ 0x0a, 0x02 },{ 0x02, 0x01 },{ 0x00, 0x02 } },
118
    { 0x0c, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x06 },{ 0x08, 0x04 },{ 0x06, 0x02 },{ 0x01, 0x07 } },
119
    { 0x1e, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x02, 0x01 },{ 0x00, 0x00 },{ 0x0e, 0x07 },{ 0x01, 0x06 },{ 0x00, 0x02 },{ 0x01, 0x08 } },
120
    { 0x06, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x02, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x0e },{ 0x03, 0x02 },{ 0x0f, 0x0f },{ 0x04, 0x04 } },
121
    { 0x1d, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x08, 0x08 },{ 0x02, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x07 } },
122
    { 0x22, 0x01, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x03, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x07 },{ 0x02, 0x02 },{ 0x00, 0x01 },{ 0x01, 0x07 } },
123
    { 0x25, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x05, 0x01 },{ 0x00, 0x00 },{ 0x04, 0x07 },{ 0x00, 0x03 },{ 0x07, 0x00 },{ 0x02, 0x01 } },
124
    { 0x0f, 0x00, 0x01, 0x07,{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x00 },{ 0x05, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x0a },{ 0x08, 0x05 },{ 0x05, 0x00 },{ 0x01, 0x02 } },
125
    { 0x24, 0x00, 0x00, 0x07,{ 0x00, 0x01 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x07, 0x01 },{ 0x00, 0x00 },{ 0x0f, 0x0f },{ 0x08, 0x08 },{ 0x02, 0x01 },{ 0x02, 0x02 } },
126
    { 0x11, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x03 },{ 0x00, 0x00 },{ 0x06, 0x07 },{ 0x05, 0x04 },{ 0x01, 0x01 },{ 0x08, 0x06 } },
127
    { 0x13, 0x00, 0x00, 0x05,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x02 },{ 0x03, 0x00 },{ 0x0c, 0x09 },{ 0x09, 0x05 },{ 0x00, 0x00 },{ 0x03, 0x02 } },
128
    { 0x0c, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x03 },{ 0x00, 0x00 },{ 0x09, 0x0c },{ 0x04, 0x00 },{ 0x03, 0x0f },{ 0x03, 0x06 } },
129
    { 0x0d, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x01 },{ 0x01, 0x02 },{ 0x00, 0x00 },{ 0x0c, 0x0d },{ 0x01, 0x05 },{ 0x05, 0x00 },{ 0x06, 0x06 } },
130
131
    { 0x18, 0x00, 0x01, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0d, 0x00 },{ 0x0f, 0x00 },{ 0x06, 0x00 },{ 0x0a, 0x00 } },
132
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0c, 0x00 },{ 0x08, 0x00 },{ 0x0a, 0x00 },{ 0x07, 0x00 } },
133
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x05, 0x00 },{ 0x00, 0x00 },{ 0x0f, 0x00 },{ 0x08, 0x00 },{ 0x05, 0x00 },{ 0x09, 0x00 } },
134
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0f },{ 0x00, 0x08 },{ 0x00, 0x06 },{ 0x00, 0x0d } },
135
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0d },{ 0x00, 0x08 },{ 0x00, 0x06 },{ 0x00, 0x08 } },
136
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0a },{ 0x00, 0x0a },{ 0x00, 0x05 },{ 0x00, 0x05 } }
137
};
138
139
static const opll_patch_t patch_ym2413[opll_patch_max] = {
140
    { 0x1e, 0x01, 0x00, 0x07,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0d, 0x07 },{ 0x00, 0x08 },{ 0x00, 0x01 },{ 0x00, 0x07 } },
141
    { 0x1a, 0x00, 0x01, 0x05,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x03, 0x01 },{ 0x00, 0x00 },{ 0x0d, 0x0f },{ 0x08, 0x07 },{ 0x02, 0x01 },{ 0x03, 0x03 } },
142
    { 0x19, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x03, 0x01 },{ 0x02, 0x00 },{ 0x0f, 0x0c },{ 0x02, 0x04 },{ 0x01, 0x02 },{ 0x01, 0x03 } },
143
    { 0x0e, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x06 },{ 0x08, 0x04 },{ 0x07, 0x02 },{ 0x00, 0x07 } },
144
    { 0x1e, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x02, 0x01 },{ 0x00, 0x00 },{ 0x0e, 0x07 },{ 0x00, 0x06 },{ 0x00, 0x02 },{ 0x00, 0x08 } },
145
    { 0x16, 0x00, 0x00, 0x05,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x02 },{ 0x00, 0x00 },{ 0x0e, 0x07 },{ 0x00, 0x01 },{ 0x00, 0x01 },{ 0x00, 0x08 } },
146
    { 0x1d, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x08, 0x08 },{ 0x02, 0x01 },{ 0x01, 0x00 },{ 0x00, 0x07 } },
147
    { 0x2d, 0x01, 0x00, 0x04,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x03, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x07 },{ 0x02, 0x02 },{ 0x00, 0x00 },{ 0x00, 0x07 } },
148
    { 0x1b, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x06, 0x06 },{ 0x04, 0x05 },{ 0x01, 0x01 },{ 0x00, 0x07 } },
149
    { 0x0b, 0x01, 0x01, 0x00,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x08, 0x0f },{ 0x05, 0x07 },{ 0x07, 0x00 },{ 0x01, 0x07 } },
150
    { 0x03, 0x01, 0x00, 0x01,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x03, 0x01 },{ 0x02, 0x00 },{ 0x0f, 0x0e },{ 0x0a, 0x04 },{ 0x01, 0x00 },{ 0x00, 0x04 } },
151
    { 0x24, 0x00, 0x00, 0x07,{ 0x00, 0x01 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x07, 0x01 },{ 0x00, 0x00 },{ 0x0f, 0x0f },{ 0x08, 0x08 },{ 0x02, 0x01 },{ 0x02, 0x02 } },
152
    { 0x0c, 0x00, 0x00, 0x05,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0c, 0x0f },{ 0x02, 0x05 },{ 0x02, 0x04 },{ 0x00, 0x02 } },
153
    { 0x15, 0x00, 0x00, 0x03,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x0c, 0x09 },{ 0x09, 0x05 },{ 0x00, 0x00 },{ 0x03, 0x02 } },
154
    { 0x09, 0x00, 0x00, 0x03,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x02, 0x00 },{ 0x0f, 0x0e },{ 0x01, 0x04 },{ 0x04, 0x01 },{ 0x00, 0x03 } },
155
156
    { 0x18, 0x00, 0x01, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0d, 0x00 },{ 0x0f, 0x00 },{ 0x06, 0x00 },{ 0x0a, 0x00 } },
157
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0c, 0x00 },{ 0x08, 0x00 },{ 0x0a, 0x00 },{ 0x07, 0x00 } },
158
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x05, 0x00 },{ 0x00, 0x00 },{ 0x0f, 0x00 },{ 0x08, 0x00 },{ 0x05, 0x00 },{ 0x09, 0x00 } },
159
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0f },{ 0x00, 0x08 },{ 0x00, 0x06 },{ 0x00, 0x0d } },
160
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0d },{ 0x00, 0x08 },{ 0x00, 0x04 },{ 0x00, 0x08 } },
161
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0a },{ 0x00, 0x0a },{ 0x00, 0x05 },{ 0x00, 0x05 } }
162
};
163
164
static const opll_patch_t patch_ymf281[opll_patch_max] = {
165
    { 0x1a, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x02, 0x01 },{ 0x00, 0x00 },{ 0x0f, 0x06 },{ 0x0f, 0x07 },{ 0x00, 0x01 },{ 0x00, 0x06 } },
166
    { 0x05, 0x00, 0x00, 0x01,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x0f, 0x08 },{ 0x06, 0x03 },{ 0x08, 0x00 },{ 0x00, 0x03 } },
167
    { 0x16, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x03, 0x01 },{ 0x02, 0x00 },{ 0x0f, 0x0d },{ 0x02, 0x03 },{ 0x01, 0x00 },{ 0x01, 0x03 } },
168
    { 0x0b, 0x00, 0x01, 0x07,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x06 },{ 0x08, 0x04 },{ 0x07, 0x01 },{ 0x00, 0x07 } },
169
    { 0x1e, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x02, 0x01 },{ 0x00, 0x00 },{ 0x0e, 0x07 },{ 0x01, 0x06 },{ 0x00, 0x02 },{ 0x00, 0x08 } },
170
    { 0x02, 0x00, 0x01, 0x06,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x02, 0x00 },{ 0x09, 0x06 },{ 0x0a, 0x01 },{ 0x02, 0x02 },{ 0x00, 0x07 } },
171
    { 0x1b, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x08, 0x08 },{ 0x04, 0x03 },{ 0x01, 0x00 },{ 0x00, 0x07 } },
172
    { 0x0a, 0x00, 0x00, 0x02,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x07, 0x02 },{ 0x03, 0x00 },{ 0x06, 0x06 },{ 0x06, 0x04 },{ 0x04, 0x02 },{ 0x00, 0x07 } },
173
    { 0x07, 0x00, 0x00, 0x03,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0c, 0x07 },{ 0x05, 0x07 },{ 0x05, 0x00 },{ 0x01, 0x07 } },
174
    { 0x1e, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x00 },{ 0x06, 0x01 },{ 0x01, 0x00 },{ 0x0f, 0x0f },{ 0x02, 0x03 },{ 0x0f, 0x0f },{ 0x00, 0x03 } },
175
    { 0x18, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x0f, 0x0e },{ 0x05, 0x03 },{ 0x02, 0x01 },{ 0x00, 0x03 } },
176
    { 0x24, 0x00, 0x00, 0x07,{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x07, 0x01 },{ 0x00, 0x00 },{ 0x0f, 0x0f },{ 0x08, 0x08 },{ 0x02, 0x00 },{ 0x02, 0x03 } },
177
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x00 },{ 0x05, 0x04 },{ 0x00, 0x00 },{ 0x0f, 0x0f },{ 0x0f, 0x03 },{ 0x07, 0x0f },{ 0x00, 0x05 } },
178
    { 0x03, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x01 },{ 0x0f, 0x01 },{ 0x00, 0x00 },{ 0x0f, 0x0e },{ 0x0c, 0x03 },{ 0x03, 0x0f },{ 0x0f, 0x0c } },
179
    { 0x00, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0a, 0x01 },{ 0x00, 0x00 },{ 0x0b, 0x08 },{ 0x0f, 0x04 },{ 0x00, 0x0f },{ 0x00, 0x05 } },
180
181
    { 0x18, 0x00, 0x01, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0d, 0x00 },{ 0x0f, 0x00 },{ 0x06, 0x00 },{ 0x0a, 0x00 } },
182
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0c, 0x00 },{ 0x08, 0x00 },{ 0x0a, 0x00 },{ 0x07, 0x00 } },
183
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x05, 0x00 },{ 0x00, 0x00 },{ 0x0f, 0x00 },{ 0x08, 0x00 },{ 0x05, 0x00 },{ 0x09, 0x00 } },
184
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0f },{ 0x00, 0x08 },{ 0x00, 0x06 },{ 0x00, 0x0d } },
185
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0d },{ 0x00, 0x08 },{ 0x00, 0x04 },{ 0x00, 0x08 } },
186
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0a },{ 0x00, 0x0a },{ 0x00, 0x05 },{ 0x00, 0x05 } }
187
};
188
189
static const opll_patch_t patch_ym2423[opll_patch_max] = {
190
    { 0x1b, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x09, 0x05 },{ 0x04, 0x04 },{ 0x01, 0x00 },{ 0x00, 0x05 } },
191
    { 0x12, 0x00, 0x00, 0x04,{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x03, 0x01 },{ 0x01, 0x00 },{ 0x0f, 0x0f },{ 0x03, 0x02 },{ 0x0a, 0x0e },{ 0x00, 0x09 } },
192
    { 0x11, 0x00, 0x00, 0x05,{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x02 },{ 0x0f, 0x0f },{ 0x02, 0x02 },{ 0x05, 0x07 },{ 0x00, 0x05 } },
193
    { 0x28, 0x00, 0x00, 0x07,{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x03, 0x02 },{ 0x00, 0x00 },{ 0x0f, 0x0f },{ 0x03, 0x02 },{ 0x09, 0x0b },{ 0x00, 0x04 } },
194
    { 0x17, 0x00, 0x00, 0x05,{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x02, 0x01 },{ 0x02, 0x00 },{ 0x05, 0x06 },{ 0x01, 0x0f },{ 0x07, 0x00 },{ 0x00, 0x09 } },
195
    { 0x18, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x03, 0x00 },{ 0x00, 0x00 },{ 0x0f, 0x0f },{ 0x07, 0x04 },{ 0x05, 0x08 },{ 0x00, 0x05 } },
196
    { 0x1c, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x05, 0x07 },{ 0x01, 0x01 },{ 0x02, 0x02 },{ 0x00, 0x06 } },
197
    { 0x1b, 0x00, 0x00, 0x07,{ 0x00, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x04 },{ 0x00, 0x00 },{ 0x07, 0x03 },{ 0x03, 0x0f },{ 0x00, 0x00 },{ 0x00, 0x06 } },
198
    { 0x0d, 0x00, 0x00, 0x03,{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x04, 0x06 },{ 0x02, 0x0f },{ 0x02, 0x00 },{ 0x00, 0x06 } },
199
    { 0x10, 0x00, 0x00, 0x05,{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x02 },{ 0x0f, 0x0f },{ 0x03, 0x03 },{ 0x02, 0x00 },{ 0x00, 0x04 } },
200
    { 0x1b, 0x00, 0x00, 0x07,{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x0c, 0x09 },{ 0x05, 0x06 },{ 0x0f, 0x0f },{ 0x00, 0x06 } },
201
    { 0x1b, 0x00, 0x00, 0x00,{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x09, 0x01 },{ 0x03, 0x00 },{ 0x0f, 0x0f },{ 0x05, 0x03 },{ 0x07, 0x0f },{ 0x00, 0x02 } },
202
    { 0x11, 0x00, 0x00, 0x03,{ 0x00, 0x01 },{ 0x01, 0x00 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x02 },{ 0x02, 0x00 },{ 0x09, 0x0b },{ 0x04, 0x01 },{ 0x0e, 0x0f },{ 0x00, 0x07 } },
203
    { 0x17, 0x00, 0x00, 0x06,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x0d, 0x0e },{ 0x03, 0x01 },{ 0x0b, 0x0e },{ 0x00, 0x0b } },
204
    { 0x0d, 0x00, 0x00, 0x05,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x01 },{ 0x01, 0x01 },{ 0x01, 0x06 },{ 0x00, 0x00 },{ 0x0f, 0x0f },{ 0x02, 0x04 },{ 0x02, 0x09 },{ 0x00, 0x09 } },
205
206
    { 0x18, 0x00, 0x01, 0x07,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0d, 0x00 },{ 0x0f, 0x00 },{ 0x06, 0x00 },{ 0x0a, 0x00 } },
207
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x01, 0x00 },{ 0x00, 0x00 },{ 0x0c, 0x00 },{ 0x08, 0x00 },{ 0x0a, 0x00 },{ 0x07, 0x00 } },
208
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x05, 0x00 },{ 0x00, 0x00 },{ 0x0f, 0x00 },{ 0x08, 0x00 },{ 0x05, 0x00 },{ 0x09, 0x00 } },
209
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0f },{ 0x00, 0x08 },{ 0x00, 0x06 },{ 0x00, 0x0d } },
210
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0d },{ 0x00, 0x08 },{ 0x00, 0x04 },{ 0x00, 0x08 } },
211
    { 0x00, 0x00, 0x00, 0x00,{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x00 },{ 0x00, 0x01 },{ 0x00, 0x00 },{ 0x00, 0x0a },{ 0x00, 0x0a },{ 0x00, 0x05 },{ 0x00, 0x05 } }
212
};
213
214
static const uint32_t ch_offset[18] = {
215
    1, 2, 0, 1, 2, 3, 4, 5, 3, 4, 5, 6, 7, 8, 6, 7, 8, 0
216
};
217
218
static const uint32_t pg_multi[16] = {
219
    1, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 20, 24, 24, 30, 30
220
};
221
222
static const uint32_t eg_stephi[4][4] = {
223
    { 0, 0, 0, 0 },
224
    { 1, 0, 0, 0 },
225
    { 1, 0, 1, 0 },
226
    { 1, 1, 1, 0 }
227
};
228
229
static const uint32_t eg_ksltable[16] = {
230
    0, 32, 40, 45, 48, 51, 53, 55, 56, 58, 59, 60, 61, 62, 63, 64
231
};
232
233
static void OPLL_DoIO(opll_t *chip) {
234
    /* Write signal check */
235
    chip->write_a_en = (chip->write_a & 0x03) == 0x01;
236
    chip->write_d_en = (chip->write_d & 0x03) == 0x01;
237
    chip->write_a <<= 1;
238
    chip->write_d <<= 1;
239
}
240
241
static void OPLL_DoModeWrite(opll_t *chip) {
242
    if ((chip->write_mode_address & 0x10) && chip->write_d_en) {
243
        uint8_t slot = chip->write_mode_address & 0x01;
244
        switch (chip->write_mode_address & 0x0f) {
245
        case 0x00:
246
        case 0x01:
247
            chip->patch.multi[slot] = chip->write_data & 0x0f;
248
            chip->patch.ksr[slot] = (chip->write_data >> 4) & 0x01;
249
            chip->patch.et[slot] = (chip->write_data >> 5) & 0x01;
250
            chip->patch.vib[slot] = (chip->write_data >> 6) & 0x01;
251
            chip->patch.am[slot] = (chip->write_data >> 7) & 0x01;
252
            break;
253
254
        case 0x02:
255
            chip->patch.ksl[0] = (chip->write_data >> 6) & 0x03;
256
            chip->patch.tl = chip->write_data & 0x3f;
257
            break;
258
259
        case 0x03:
260
            chip->patch.ksl[1] = (chip->write_data >> 6) & 0x03;
261
            chip->patch.dc = (chip->write_data >> 4) & 0x01;
262
            chip->patch.dm = (chip->write_data >> 3) & 0x01;
263
            chip->patch.fb = chip->write_data & 0x07;
264
            break;
265
266
        case 0x04:
267
        case 0x05:
268
            chip->patch.dr[slot] = chip->write_data & 0x0f;
269
            chip->patch.ar[slot] = (chip->write_data >> 4) & 0x0f;
270
            break;
271
272
        case 0x06:
273
        case 0x07:
274
            chip->patch.rr[slot] = chip->write_data & 0x0f;
275
            chip->patch.sl[slot] = (chip->write_data >> 4) & 0x0f;
276
            break;
277
278
        case 0x0e:
279
            chip->rhythm = chip->write_data & 0x3f;
280
            if (chip->chip_type == opll_type_ds1001) {
281
                chip->rhythm |= 0x20;
282
            }
283
            chip->rm_enable = int8_t((chip->rm_enable & 0x7f) | ((chip->rhythm << 2) & 0x80));
284
            break;
285
286
        case 0x0f:
287
            chip->testmode = chip->write_data & 0x0f;
288
            break;
289
        }
290
    }
291
}
292
293
void OPLL_Reset(opll_t *chip, uint32_t chip_type) {
294
    uint32_t i;
295
    memset(chip, 0, sizeof(opll_t));
296
    chip->chip_type = chip_type;
297
    if (chip_type == opll_type_ds1001) {
298
        /* Rhythm mode is always on */
299
        chip->rhythm = 0x20;
300
        chip->rm_enable = int8_t(0x80);
301
    }
302
    switch (chip_type) {
303
    case opll_type_ds1001:
304
        chip->patchrom = patch_ds1001;
305
        break;
306
    case opll_type_ymf281:
307
    case opll_type_ymf281b:
308
        chip->patchrom = patch_ymf281;
309
        break;
310
    case opll_type_ym2423:
311
        chip->patchrom = patch_ym2423;
312
        break;
313
    case opll_type_ym2413:
314
    case opll_type_ym2413b:
315
    case opll_type_ym2420:
316
    default:
317
        chip->patchrom = patch_ym2413;
318
        break;
319
    }
320
    for (i = 0; i < 18; i++) {
321
        chip->eg_state[i] = eg_num_release;
322
        chip->eg_level[i] = 0x7f;
323
        chip->eg_out = 0x7f;
324
    }
325
    chip->rm_select = rm_num_tc + 1;
326
}
327
328
static void OPLL_DoRegWrite(opll_t *chip) {
329
    /* Address */
330
    if (chip->write_a_en) {
331
        if ((chip->write_data & 0xc0) == 0x00) {
332
            /* FM Write */
333
            chip->write_fm_address = 1;
334
            chip->address = chip->write_data;
335
        } else {
336
            chip->write_fm_address = 0;
337
        }
338
    }
339
    /* Data */
340
    if (chip->write_fm_address && chip->write_d_en) {
341
        chip->data = chip->write_data;
342
    }
343
344
    /* Update registers */
345
    if (chip->write_fm_data && !chip->write_a_en) {
346
        if (uint32_t(chip->address & 0x0f) == chip->cycles && chip->cycles < 16) {
347
            uint32_t channel = chip->cycles % 9;
348
            switch (chip->address & 0xf0) {
349
            case 0x10:
350
                if (chip->chip_type == opll_type_ym2420)
351
                {
352
                    chip->fnum[channel] = uint16_t((chip->fnum[channel] & 0x0f) | ((chip->data & 0x1f) << 4));
353
                    chip->block[channel] = (chip->data >> 5) & 0x07;
354
                }
355
                else
356
                    chip->fnum[channel] = (chip->fnum[channel] & 0x100) | chip->data;
357
                break;
358
            case 0x20:
359
                if (chip->chip_type == opll_type_ym2420)
360
                    chip->fnum[channel] = (chip->fnum[channel] & 0x1f0) | (chip->data & 0x0f);
361
                else
362
                {
363
                    chip->fnum[channel] = uint16_t((chip->fnum[channel] & 0xff) | ((chip->data & 0x01) << 8));
364
                    chip->block[channel] = (chip->data >> 1) & 0x07;
365
                }
366
                chip->kon[channel] = (chip->data >> 4) & 0x01;
367
                chip->son[channel] = (chip->data >> 5) & 0x01;
368
                break;
369
            case 0x30:
370
                chip->vol[channel] = chip->data & 0x0f;
371
                chip->inst[channel] = (chip->data >> 4) & 0x0f;
372
                break;
373
            }
374
        }
375
    }
376
377
378
    if (chip->write_a_en) {
379
        chip->write_fm_data = 0;
380
    }
381
    if (chip->write_fm_address && chip->write_d_en) {
382
        chip->write_fm_data = 1;
383
    }
384
    if (chip->write_a_en) {
385
        if ((chip->write_data & 0xf0) == 0x00) {
386
            chip->write_mode_address = 0x10 | (chip->write_data & 0x0f);
387
        } else {
388
            chip->write_mode_address = 0x00;
389
        }
390
    }
391
392
}
393
394
static void OPLL_PreparePatch1(opll_t *chip) {
395
    uint8_t instr;
396
    uint32_t mcsel = ((chip->cycles + 1) / 3) & 0x01;
397
    uint32_t instr_index;
398
    uint32_t ch = ch_offset[chip->cycles];
399
    const opll_patch_t *patch;
400
    instr = chip->inst[ch];
401
    if (instr > 0) {
402
        instr_index = opll_patch_1 + instr - 1;
403
    }
404
    if (chip->rm_select <= rm_num_tc) {
405
        instr_index = opll_patch_drum_0 + chip->rm_select;
406
    }
407
    if (chip->rm_select <= rm_num_tc || instr > 0) {
408
        patch = &chip->patchrom[instr_index];
409
    } else {
410
        patch = &chip->patch;
411
    }
412
    if (chip->rm_select == rm_num_hh || chip->rm_select == rm_num_tom) {
413
        chip->c_tl = uint8_t(chip->inst[ch] << 2);
414
    } else if (mcsel == 1) {
415
        chip->c_tl = uint8_t(chip->vol[ch] << 2);
416
    } else {
417
        chip->c_tl = patch->tl;
418
    }
419
420
    chip->c_adrr[0] = patch->ar[mcsel];
421
    chip->c_adrr[1] = patch->dr[mcsel];
422
    chip->c_adrr[2] = patch->rr[mcsel];
423
    chip->c_et = patch->et[mcsel];
424
    chip->c_ksr = patch->ksr[mcsel];
425
    chip->c_ksl = patch->ksl[mcsel];
426
    chip->c_ksr_freq = uint8_t((chip->block[ch] << 1) | (chip->fnum[ch] >> 8));
427
    chip->c_ksl_freq = uint8_t(chip->fnum[ch]>>5);
428
    chip->c_ksl_block = (chip->block[ch]);
429
}
430
431
static void OPLL_PreparePatch2(opll_t *chip) {
432
    uint8_t instr;
433
    uint32_t mcsel = ((chip->cycles + 1) / 3) & 0x01;
434
    uint32_t instr_index;
435
    const opll_patch_t *patch;
436
    instr = chip->inst[ch_offset[chip->cycles]];
437
    if (instr > 0) {
438
        instr_index = opll_patch_1 + instr - 1;
439
    }
440
    if (chip->rm_select <= rm_num_tc) {
441
        instr_index = opll_patch_drum_0 + chip->rm_select;
442
    }
443
    if (chip->rm_select <= rm_num_tc || instr > 0) {
444
        patch = &chip->patchrom[instr_index];
445
    } else {
446
        patch = &chip->patch;
447
    }
448
449
    chip->c_fnum = chip->fnum[ch_offset[chip->cycles]];
450
    chip->c_block = chip->block[ch_offset[chip->cycles]];
451
452
    chip->c_multi = patch->multi[mcsel];
453
    chip->c_sl = patch->sl[mcsel];
454
    chip->c_fb = patch->fb;
455
    chip->c_vib = patch->vib[mcsel];
456
    chip->c_am = patch->am[mcsel];
457
    chip->c_dc <<= 1;
458
    chip->c_dm <<= 1;
459
    chip->c_dc |= patch->dc;
460
    chip->c_dm |= patch->dm;
461
}
462
463
static void OPLL_PhaseGenerate(opll_t *chip) {
464
    uint32_t ismod;
465
    uint32_t phase;
466
    uint16_t pg_out;
467
468
    chip->pg_phase[(chip->cycles + 17) % 18] = chip->pg_phase_next + chip->pg_inc;
469
470
    if ((chip->rm_enable & 0x40) && (chip->cycles == 13 || chip->cycles == 14)) {
471
        ismod = 0;
472
    } else {
473
        ismod = ((chip->cycles + 3) / 3) & 1;
474
    }
475
    phase = chip->pg_phase[chip->cycles];
476
    /* KeyOn event check */
477
    if ((chip->testmode & 0x04)
478
     || (ismod && (chip->eg_dokon & 0x8000)) || (!ismod && (chip->eg_dokon & 0x01))) {
479
        chip->pg_phase_next = 0;
480
    } else {
481
        chip->pg_phase_next = phase;
482
    }
483
    /* Rhythm mode */
484
    if (chip->cycles == 13) {
485
        chip->rm_hh_bit2 = (phase >> (2 + 9)) & 1;
486
        chip->rm_hh_bit3 = (phase >> (3 + 9)) & 1;
487
        chip->rm_hh_bit7 = (phase >> (7 + 9)) & 1;
488
        chip->rm_hh_bit8 = (phase >> (8 + 9)) & 1;
489
    } else if (chip->cycles == 17 && (chip->rm_enable & 0x80)) {
490
        chip->rm_tc_bit3 = (phase >> (3 + 9)) & 1;
491
        chip->rm_tc_bit5 = (phase >> (5 + 9)) & 1;
492
    }
493
    if (chip->rm_enable & 0x80) {
494
        switch (chip->cycles) {
495
        case 13: {
496
            /* HH */
497
            uint8_t rm_bit = (chip->rm_hh_bit2 ^ chip->rm_hh_bit7)
498
                   | (chip->rm_hh_bit3 ^ chip->rm_tc_bit5)
499
                   | (chip->rm_tc_bit3 ^ chip->rm_tc_bit5);
500
            pg_out = uint16_t(rm_bit << 9);
501
            if (rm_bit ^ (chip->rm_noise & 1)) {
502
                pg_out |= 0xd0;
503
            } else {
504
                pg_out |= 0x34;
505
            }
506
            break;
507
	}
508
        case 16:
509
            /* SD */
510
            pg_out = uint16_t((chip->rm_hh_bit8 << 9)
511
                   | ((chip->rm_hh_bit8 ^ (chip->rm_noise & 1)) << 8));
512
            break;
513
        case 17: {
514
            /* TC */
515
            uint8_t rm_bit = (chip->rm_hh_bit2 ^ chip->rm_hh_bit7)
516
                   | (chip->rm_hh_bit3 ^ chip->rm_tc_bit5)
517
                   | (chip->rm_tc_bit3 ^ chip->rm_tc_bit5);
518
            pg_out = uint16_t((rm_bit << 9) | 0x100);
519
            break;
520
	}
521
        default:
522
            pg_out = uint16_t(phase >> 9);
523
        }
524
    } else {
525
        pg_out = uint16_t(phase >> 9);
526
    }
527
    chip->pg_out = pg_out;
528
}
529
530
static void OPLL_PhaseCalcIncrement(opll_t *chip) {
531
    uint32_t freq;
532
    uint16_t block;
533
    freq = chip->c_fnum << 1;
534
    block = chip->c_block;
535
    /* Apply vibrato */
536
    if (chip->c_vib) {
537
        switch (chip->lfo_vib_counter) {
538
        case 0:
539
        case 4:
540
            break;
541
        case 1:
542
        case 3:
543
            freq += freq >> 8;
544
            break;
545
        case 2:
546
            freq += freq >> 7;
547
            break;
548
        case 5:
549
        case 7:
550
            freq -= freq >> 8;
551
            break;
552
        case 6:
553
            freq -= freq >> 7;
554
            break;
555
        }
556
    }
557
    /* Apply block */
558
    freq = (freq << block) >> 1;
559
560
    chip->pg_inc = (freq * pg_multi[chip->c_multi]) >> 1;
561
}
562
563
static void OPLL_EnvelopeKSLTL(opll_t *chip)
564
{
565
    int32_t ksl;
566
567
    ksl = eg_ksltable[chip->c_ksl_freq]-((8-chip->c_ksl_block)<<3);
568
    if (ksl < 0) {
569
        ksl = 0;
570
    }
571
572
    ksl <<= 1;
573
574
    if (chip->c_ksl) {
575
        ksl = ksl >> (3-chip->c_ksl);
576
    } else {
577
        ksl = 0;
578
    }
579
580
    chip->eg_ksltl = uint16_t(ksl + (chip->c_tl<<1));
581
}
582
583
static void OPLL_EnvelopeOutput(opll_t *chip)
584
{
585
    int32_t level = chip->eg_level[(chip->cycles+17)%18];
586
587
    level += chip->eg_ksltl;
588
589
    if (chip->c_am) {
590
        level += chip->lfo_am_out;
591
    }
592
593
    if (level >= 128) {
594
        level = 127;
595
    }
596
597
    if (chip->testmode & 0x01) {
598
        level = 0;
599
    }
600
601
    chip->eg_out = uint8_t(level);
602
}
603
604
static void OPLL_EnvelopeGenerate(opll_t *chip) {
605
    uint8_t timer_inc;
606
    uint8_t timer_bit;
607
    uint8_t timer_low;
608
    uint8_t rate;
609
    uint8_t state_rate;
610
    uint8_t ksr;
611
    uint8_t sum;
612
    uint8_t rate_hi;
613
    uint8_t rate_lo;
614
    int32_t level;
615
    int32_t next_level;
616
    uint8_t zero;
617
    uint8_t state;
618
    uint8_t next_state;
619
    int32_t step;
620
    int32_t sl;
621
    uint32_t mcsel = ((chip->cycles + 1) / 3) & 0x01;
622
623
624
    /* EG timer */
625
    if ((chip->eg_counter_state & 3) != 3) {
626
        timer_inc = 0;
627
    } else if (chip->cycles == 0) {
628
        timer_inc = 1;
629
    } else {
630
        timer_inc = chip->eg_timer_carry;
631
    }
632
    timer_low = chip->eg_timer & 3;
633
    timer_bit = chip->eg_timer & 1;
634
    timer_bit += timer_inc;
635
    chip->eg_timer_carry = timer_bit >> 1;
636
    chip->eg_timer = ((timer_bit & 1) << 17) | (chip->eg_timer >> 1);
637
    if (chip->testmode & 0x08) {
638
        chip->eg_timer &= 0x2ffff;
639
        chip->eg_timer |= (chip->write_data << (16 - 2)) & 0x10000;
640
    }
641
    if (!chip->eg_timer_shift_stop && ((chip->eg_timer >> 16) & 1)) {
642
        chip->eg_timer_shift = uint8_t(chip->cycles);
643
    }
644
    if (chip->cycles == 0 && (chip->eg_counter_state_prev & 1) == 1) {
645
        chip->eg_timer_low_lock = timer_low;
646
        chip->eg_timer_shift_lock = chip->eg_timer_shift;
647
        if (chip->eg_timer_shift_lock > 13)
648
            chip->eg_timer_shift_lock = 0;
649
650
        chip->eg_timer_shift = 0;
651
    }
652
    chip->eg_timer_shift_stop |= (chip->eg_timer >> 16) & 1;
653
    if (chip->cycles == 0) {
654
        chip->eg_timer_shift_stop = 0;
655
    }
656
    chip->eg_counter_state_prev = chip->eg_counter_state;
657
    if (chip->cycles == 17) {
658
        chip->eg_counter_state++;
659
    }
660
661
    level = chip->eg_level[(chip->cycles+16)%18];
662
    next_level = level;
663
    zero = level == 0;
664
    chip->eg_silent = level == 0x7f;
665
666
    if (chip->eg_state[(chip->cycles+16)%18] != eg_num_attack && (chip->eg_off&2) && !(chip->eg_dokon&2)) {
667
        next_level = 0x7f;
668
    }
669
670
    if (chip->eg_maxrate && (chip->eg_dokon&2)) {
671
        next_level = 0x00;
672
    }
673
674
675
    state = chip->eg_state[(chip->cycles+16)%18];
676
    next_state = eg_num_attack;
677
678
    step = 0;
679
    sl = chip->eg_sl;
680
681
    switch (state) {
682
    case eg_num_attack:
683
        if (!chip->eg_maxrate && (chip->eg_kon & 2) && !zero) {
684
            int32_t shift = (chip->eg_rate_hi < 12) ? chip->eg_inc_lo : (chip->eg_rate_hi - 11 + chip->eg_inc_hi);
685
            if (shift > 0) {
686
                step = ~level >> (5 - shift);
687
            }
688
        }
689
        if (zero) {
690
            next_state = eg_num_decay;
691
        } else {
692
            next_state = eg_num_attack;
693
        }
694
        break;
695
    case eg_num_decay:
696
        if (!(chip->eg_off & 2) && !(chip->eg_dokon & 2) && (level >> 3) != sl)
697
        {
698
            uint8_t i0 = chip->eg_rate_hi == 15 || (chip->eg_rate_hi == 14 && chip->eg_inc_hi);
699
            uint8_t i1 = (chip->eg_rate_hi == 14 && !chip->eg_inc_hi) || (chip->eg_rate_hi == 13 && chip->eg_inc_hi) ||
700
                (chip->eg_rate_hi == 13 && !chip->eg_inc_hi && (chip->eg_counter_state_prev & 1))
701
                || (chip->eg_rate_hi == 12 && chip->eg_inc_hi && (chip->eg_counter_state_prev & 1))
702
                || (chip->eg_rate_hi == 12 && !chip->eg_inc_hi && ((chip->eg_counter_state_prev & 3) == 3))
703
                || (chip->eg_inc_lo && ((chip->eg_counter_state_prev & 3) == 3));
704
            step = (i0<<1) | i1;
705
        }
706
        if ((level >> 3) == sl) {
707
            next_state = eg_num_sustain;
708
        } else {
709
            next_state = eg_num_decay;
710
        }
711
        break;
712
    case eg_num_sustain:
713
    case eg_num_release:
714
        if (!(chip->eg_off & 2) && !(chip->eg_dokon & 2))
715
        {
716
            uint8_t i0 = chip->eg_rate_hi == 15 || (chip->eg_rate_hi == 14 && chip->eg_inc_hi);
717
            uint8_t i1 = (chip->eg_rate_hi == 14 && !chip->eg_inc_hi) || (chip->eg_rate_hi == 13 && chip->eg_inc_hi) ||
718
                (chip->eg_rate_hi == 13 && !chip->eg_inc_hi && (chip->eg_counter_state_prev & 1))
719
                || (chip->eg_rate_hi == 12 && chip->eg_inc_hi && (chip->eg_counter_state_prev & 1))
720
                || (chip->eg_rate_hi == 12 && !chip->eg_inc_hi && ((chip->eg_counter_state_prev & 3) == 3))
721
                || (chip->eg_inc_lo && ((chip->eg_counter_state_prev & 3) == 3));
722
            step = (i0<<1) | i1;
723
        }
724
        next_state = state;
725
        break;
726
    }
727
728
    if (!(chip->eg_kon & 2)) {
729
        next_state = eg_num_release;
730
    }
731
    if (chip->eg_dokon & 2) {
732
        next_state = eg_num_attack;
733
    }
734
735
    chip->eg_level[(chip->cycles+16)%18] = uint8_t(next_level+step);
736
    chip->eg_state[(chip->cycles+16)%18] = next_state;
737
738
    rate_hi = chip->eg_rate >> 2;
739
    rate_lo = chip->eg_rate & 3;
740
    chip->eg_inc_hi = uint8_t(eg_stephi[rate_lo][chip->eg_timer_low_lock]);
741
    sum = (chip->eg_timer_shift_lock + rate_hi) & 0x0f;
742
    chip->eg_inc_lo = 0;
743
    if (rate_hi < 12 && !chip->eg_zerorate) {
744
        switch (sum) {
745
        case 12:
746
            chip->eg_inc_lo = 1;
747
            break;
748
        case 13:
749
            chip->eg_inc_lo = (rate_lo >> 1) & 1;
750
            break;
751
        case 14:
752
            chip->eg_inc_lo = rate_lo & 1;
753
            break;
754
        }
755
    }
756
    chip->eg_maxrate = rate_hi == 0x0f;
757
758
    chip->eg_rate_hi = rate_hi;
759
760
    chip->eg_kon <<= 1;
761
    chip->eg_kon |= chip->kon[ch_offset[chip->cycles]];
762
    chip->eg_off <<= 1;
763
    chip->eg_off |= (chip->eg_level[chip->cycles] >> 2) == 0x1f;
764
    switch (chip->rm_select) {
765
    case rm_num_bd0:
766
    case rm_num_bd1:
767
        chip->eg_kon |= (chip->rhythm >> 4) & 1;
768
        break;
769
    case rm_num_sd:
770
        chip->eg_kon |= (chip->rhythm >> 3) & 1;
771
        break;
772
    case rm_num_tom:
773
        chip->eg_kon |= (chip->rhythm >> 2) & 1;
774
        break;
775
    case rm_num_tc:
776
        chip->eg_kon |= (chip->rhythm >> 1) & 1;
777
        break;
778
    case rm_num_hh:
779
        chip->eg_kon |= chip->rhythm & 1;
780
        break;
781
    }
782
783
    /* Calculate rate */
784
    rate = 0;
785
    chip->eg_dokon <<= 1;
786
    state_rate = chip->eg_state[chip->cycles];
787
    if (state_rate == eg_num_release && (chip->eg_kon&1) && (chip->eg_off&1)) {
788
        state_rate = eg_num_attack;
789
        chip->eg_dokon |= 1;
790
    }
791
    switch (state_rate) {
792
    case eg_num_attack:
793
        rate = chip->c_adrr[0];
794
        break;
795
    case eg_num_decay:
796
        rate = chip->c_adrr[1];
797
        break;
798
    case eg_num_sustain:
799
        if (!chip->c_et) {
800
            rate = chip->c_adrr[2];
801
        }
802
        break;
803
    case eg_num_release:
804
        if (chip->son[ch_offset[chip->cycles]]) {
805
            rate = 5;
806
        } else {
807
            rate = chip->c_adrr[2];
808
        }
809
        break;
810
    }
811
    if (!(chip->eg_kon&1) && !mcsel && chip->rm_select != rm_num_tom && chip->rm_select != rm_num_hh) {
812
        rate = 0;
813
    }
814
    if ((chip->eg_kon&1) && chip->eg_state[chip->cycles] == eg_num_release && !(chip->eg_off&1)) {
815
        rate = 12;
816
    }
817
    if (!(chip->eg_kon&1) && !chip->son[ch_offset[chip->cycles]] && mcsel == 1 && !chip->c_et) {
818
        rate = 7;
819
    }
820
    chip->eg_zerorate = rate == 0;
821
    ksr = chip->c_ksr_freq;
822
    if (!chip->c_ksr)
823
        ksr >>= 2;
824
    chip->eg_rate = uint8_t((rate << 2) + ksr);
825
    if (chip->eg_rate & 0x40) {
826
        chip->eg_rate = 0x3c | (ksr & 3);
827
    }
828
    chip->eg_sl = chip->c_sl;
829
}
830
831
static void OPLL_Channel(opll_t *chip) {
832
    int16_t ch_out = chip->ch_out;
833
    uint8_t ismod = (chip->cycles / 3) & 1;
834
    uint8_t mute_m = ismod || ((chip->rm_enable&0x40) && (chip->cycles+15)%18 >= 12);
835
    if (chip->chip_type == opll_type_ds1001) {
836
        chip->output_m = ch_out;
837
        if (chip->output_m >= 0) {
838
            chip->output_m++;
839
        }
840
        if (mute_m) {
841
            chip->output_m = 0;
842
        }
843
        chip->output_r = 0;
844
        return;
845
    } else {
846
        uint8_t mute_r = 1;
847
        /* TODO: This might be incorrect */
848
        if (chip->rm_enable & 0x40) {
849
            switch (chip->cycles) {
850
            case 16: /* HH */
851
            case 17: /* TOM */
852
            case 0: /* BD */
853
            case 1: /* SD */
854
            case 2: /* TC */
855
            case 3: /* HH */
856
            case 4: /* TOM */
857
            case 5: /* BD */
858
            case 9: /* TOM */
859
            case 10: /* TOM */
860
                mute_r = 0;
861
                break;
862
            }
863
        }
864
        if (chip->chip_type == opll_type_ym2413b || chip->chip_type == opll_type_ymf281b) {
865
            if (mute_m)
866
                chip->output_m = 0;
867
            else
868
                chip->output_m = ch_out;
869
            if (mute_r)
870
                chip->output_r = 0;
871
            else
872
                chip->output_r = ch_out;
873
        } else {
874
            int16_t sign = ch_out >> 8;
875
            if (ch_out >= 0) {
876
                ch_out++;
877
                sign++;
878
            }
879
            if (mute_m)
880
                chip->output_m = sign;
881
            else
882
                chip->output_m = ch_out;
883
            if (mute_r)
884
                chip->output_r = sign;
885
            else
886
                chip->output_r = ch_out;
887
        }
888
    }
889
}
890
891
static void OPLL_Operator(opll_t *chip) {
892
    uint8_t ismod1, ismod2, ismod3;
893
    uint32_t op_mod;
894
    uint16_t exp_shift;
895
    int16_t output;
896
    uint32_t level;
897
    uint32_t phase;
898
    int16_t routput;
899
    if ((chip->rm_enable & 0x80) && (chip->cycles == 15 || chip->cycles == 16)) {
900
        ismod1 = 0;
901
    } else {
902
        ismod1 = ((chip->cycles + 1) / 3) & 1;
903
    }
904
    if ((chip->rm_enable & 0x40) && (chip->cycles == 13 || chip->cycles == 14)) {
905
        ismod2 = 0;
906
    } else {
907
        ismod2 = ((chip->cycles + 3) / 3) & 1;
908
    }
909
    if ((chip->rm_enable & 0x40) && (chip->cycles == 16 || chip->cycles == 17)) {
910
        ismod3 = 0;
911
    } else {
912
        ismod3 = (chip->cycles / 3) & 1;
913
    }
914
915
    op_mod = 0;
916
917
    if (ismod3) {
918
        op_mod |= chip->op_mod << 1;
919
    }
920
921
    if (ismod2 && chip->c_fb) {
922
        op_mod |= chip->op_fbsum >> (7 - chip->c_fb);
923
    }
924
925
    exp_shift = chip->op_exp_s;
926
    if (chip->eg_silent || ((chip->op_neg&2) && (ismod1 ? (chip->c_dm&4) : (chip->c_dc&4)))) {
927
        exp_shift |= 12;
928
    }
929
930
    output = int16_t(chip->op_exp_m>>exp_shift);
931
    if (!chip->eg_silent && (chip->op_neg&2)) {
932
        output = ~output;
933
    }
934
935
    level = chip->op_logsin+(chip->eg_out<<4);
936
    if (level >= 4096) {
937
        level = 4095;
938
    }
939
940
    chip->op_exp_m = exprom[level & 0xff];
941
    chip->op_exp_s = uint16_t(level >> 8);
942
943
    phase = (op_mod + chip->pg_out) & 0x3ff;
944
    if (phase & 0x100) {
945
        phase ^= 0xff;
946
    }
947
    chip->op_logsin = logsinrom[phase & 0xff];
948
    chip->op_neg <<= 1;
949
    chip->op_neg |= uint8_t(phase >> 9);
950
    chip->op_fbsum = int16_t((chip->op_fb1[(chip->cycles + 3) % 9] + chip->op_fb2[(chip->cycles + 3) % 9]) >> 1);
951
952
    if (ismod1) {
953
        chip->op_fb2[chip->cycles%9] = chip->op_fb1[chip->cycles%9];
954
        chip->op_fb1[chip->cycles%9] = output;
955
    }
956
    chip->op_mod = output&0x1ff;
957
958
    if (chip->chip_type == opll_type_ds1001) {
959
        routput = 0;
960
    } else {
961
        switch (chip->cycles) {
962
        case 2:
963
            routput = chip->ch_out_hh;
964
            break;
965
        case 3:
966
            routput = chip->ch_out_tm;
967
            break;
968
        case 4:
969
            routput = chip->ch_out_bd;
970
            break;
971
        case 8:
972
            routput = chip->ch_out_sd;
973
            break;
974
        case 9:
975
            routput = chip->ch_out_tc;
976
            break;
977
        default:
978
            routput = 0; /* TODO: Not quite true */
979
            break;
980
        }
981
        switch (chip->cycles) {
982
        case 15:
983
            chip->ch_out_hh = output>>3;
984
            break;
985
        case 16:
986
            chip->ch_out_tm = output>>3;
987
            break;
988
        case 17:
989
            chip->ch_out_bd = output>>3;
990
            break;
991
        case 0:
992
            chip->ch_out_sd = output>>3;
993
            break;
994
        case 1:
995
            chip->ch_out_tc = output>>3;
996
            break;
997
        default:
998
            break;
999
        }
1000
    }
1001
1002
    chip->ch_out = ismod1 ? routput : (output>>3);
1003
}
1004
1005
static void OPLL_DoRhythm(opll_t *chip) {
1006
    uint8_t nbit;
1007
1008
    /* Noise */
1009
    nbit = (chip->rm_noise ^ (chip->rm_noise >> 14)) & 0x01;
1010
    nbit |= (chip->rm_noise == 0x00) | ((chip->testmode >> 1) & 0x01);
1011
    chip->rm_noise = (nbit << 22) | (chip->rm_noise >> 1);
1012
}
1013
1014
static void OPLL_DoLFO(opll_t *chip) {
1015
    uint8_t am_inc = 0;
1016
    uint8_t am_bit;
1017
1018
    /* Update counter */
1019
    if (chip->cycles == 17) {
1020
        auto vib_step = uint8_t(((chip->lfo_counter & 0x3ff) + 1) >> 10);
1021
        chip->lfo_am_step = uint8_t(((chip->lfo_counter & 0x3f) + 1) >> 6);
1022
        vib_step |= (chip->testmode >> 3) & 0x01;
1023
        chip->lfo_vib_counter += vib_step;
1024
        chip->lfo_vib_counter &= 0x07;
1025
        chip->lfo_counter++;
1026
    }
1027
1028
    /* LFO AM */
1029
    if ((chip->lfo_am_step || (chip->testmode & 0x08)) && chip->cycles < 9) {
1030
        am_inc = chip->lfo_am_dir | (chip->cycles == 0);
1031
    }
1032
1033
    if (chip->cycles >= 9) {
1034
        chip->lfo_am_car = 0;
1035
    }
1036
1037
    if (chip->cycles == 0) {
1038
        if (chip->lfo_am_dir && (chip->lfo_am_counter & 0x7f) == 0) {
1039
            chip->lfo_am_dir = 0;
1040
        } else if (!chip->lfo_am_dir && (chip->lfo_am_counter & 0x69) == 0x69) {
1041
            chip->lfo_am_dir = 1;
1042
        }
1043
    }
1044
1045
    am_bit = chip->lfo_am_counter & 0x01;
1046
    am_bit += uint8_t(am_inc + chip->lfo_am_car);
1047
    chip->lfo_am_car = am_bit >> 1;
1048
    am_bit &= 0x01;
1049
    chip->lfo_am_counter = uint16_t((am_bit << 8) | (chip->lfo_am_counter >> 1));
1050
1051
1052
    /* Reset LFO */
1053
    if (chip->testmode & 0x02) {
1054
        chip->lfo_vib_counter = 0;
1055
        chip->lfo_counter = 0;
1056
        chip->lfo_am_dir = 0;
1057
        chip->lfo_am_counter &= 0xff;
1058
    }
1059
}
1060
1061
1062
void OPLL_Clock(opll_t *chip, int32_t *buffer) {
1063
    buffer[0] = chip->output_m;
1064
    buffer[1] = chip->output_r;
1065
    if (chip->cycles == 0) {
1066
        chip->lfo_am_out = (chip->lfo_am_counter >> 3) & 0x0f;
1067
    }
1068
    chip->rm_enable >>= 1;
1069
    OPLL_DoModeWrite(chip);
1070
    chip->rm_select++;
1071
    if (chip->rm_select > rm_num_tc) {
1072
        chip->rm_select = rm_num_tc + 1;
1073
    }
1074
    if (chip->cycles == 11 && (chip->rm_enable & 0x80) == 0x80) {
1075
        chip->rm_select = rm_num_bd0;
1076
    }
1077
    OPLL_PreparePatch1(chip);
1078
1079
    OPLL_Channel(chip);
1080
1081
    OPLL_PhaseGenerate(chip);
1082
1083
    OPLL_Operator(chip);
1084
1085
    OPLL_PhaseCalcIncrement(chip);
1086
1087
    OPLL_EnvelopeOutput(chip);
1088
    OPLL_EnvelopeKSLTL(chip);
1089
    OPLL_EnvelopeGenerate(chip);
1090
1091
    OPLL_DoLFO(chip);
1092
    OPLL_DoRhythm(chip);
1093
    OPLL_PreparePatch2(chip);
1094
    OPLL_DoRegWrite(chip);
1095
    OPLL_DoIO(chip);
1096
    chip->cycles = (chip->cycles + 1) % 18;
1097
1098
}
1099
1100
1101
void OPLL_Write(opll_t *chip, uint32_t port, uint8_t data) {
1102
    chip->write_data = data;
1103
    if (port & 1) {
1104
        /* Data */
1105
        chip->write_d |= 1;
1106
    } else {
1107
        /* Address */
1108
        chip->write_a |= 1;
1109
    }
1110
}