23namespace YM2413Okazaki {
26static constexpr int PM_FP_BITS = 8;
29static constexpr int DB_BITS = 8;
30static constexpr int DB_MUTE = 1 << DB_BITS;
31static constexpr int DBTABLEN = 4 * DB_MUTE;
33static constexpr double DB_STEP = 48.0 / DB_MUTE;
34static constexpr double EG_STEP = 0.375;
35static constexpr double TL_STEP = 0.75;
38static constexpr int DP_BITS = 18;
39static constexpr int DP_BASE_BITS = DP_BITS -
PG_BITS;
42static constexpr int EG_BITS = 7;
45static constexpr int DB2LIN_AMP_BITS = 8;
46static constexpr int SLOT_AMP_BITS = DB2LIN_AMP_BITS;
49static constexpr int AM_PG_BITS = 8;
50static constexpr int AM_PG_WIDTH = 1 << AM_PG_BITS;
51static constexpr int AM_DP_BITS = 16;
52static constexpr int AM_DP_WIDTH = 1 << AM_DP_BITS;
53static constexpr int AM_DP_MASK = AM_DP_WIDTH - 1;
70static constexpr unsigned LFO_AM_TAB_ELEMENTS = 210;
77static constexpr std::array pmTable = {
78 std::array<int8_t, 8>{0, 0, 0, 0, 0, 0, 0, 0},
79 std::array<int8_t, 8>{0, 0, 1, 0, 0, 0,-1, 0},
80 std::array<int8_t, 8>{0, 1, 2, 1, 0,-1,-2,-1},
81 std::array<int8_t, 8>{0, 1, 3, 1, 0,-1,-3,-1},
82 std::array<int8_t, 8>{0, 2, 4, 2, 0,-2,-4,-2},
83 std::array<int8_t, 8>{0, 2, 5, 2, 0,-2,-5,-2},
84 std::array<int8_t, 8>{0, 3, 6, 3, 0,-3,-6,-3},
85 std::array<int8_t, 8>{0, 3, 7, 3, 0,-3,-7,-3},
89static constexpr std::array<uint8_t, LFO_AM_TAB_ELEMENTS> lfo_am_table = {
145static constexpr std::array<uint8_t, 16> mlTable = {
146 1, 1*2, 2*2, 3*2, 4*2, 5*2, 6*2, 7*2,
147 8*2, 9*2, 10*2, 10*2, 12*2, 12*2, 15*2, 15*2
156static constexpr auto dB2LinTab = [] {
157 std::array<int, 2 * DBTABLEN> result = {};
158 for (
int i :
xrange(DB_MUTE - 1)) {
159 result[i] = int(
double((1 << DB2LIN_AMP_BITS) - 1) *
160 cstd::pow<5, 3>(10, -
double(i) * DB_STEP / 20));
162 result[DB_MUTE - 1] = 0;
163 for (
auto i :
xrange(DB_MUTE, DBTABLEN)) {
166 for (
auto i :
xrange(DBTABLEN)) {
167 result[i + DBTABLEN] = -result[i];
173static constexpr auto arAdjustTab = [] {
174 std::array<unsigned, 1 << EG_BITS> result = {};
175 result[0] = (1 << EG_BITS) - 1;
176 constexpr double l127 = cstd::log<5, 4>(127.0);
177 for (
int i :
xrange(1, 1 << EG_BITS)) {
178 result[i] = unsigned(
double(1 << EG_BITS) - 1 -
179 ((1 << EG_BITS) - 1) * cstd::log<5, 4>(
double(i)) / l127);
185static constexpr auto tllTab = [] {
186 std::array<std::array<uint8_t, 16 * 8>, 4> result = {};
189 constexpr std::array<int, 16> klTable = {
190 0, 24, 32, 37, 40, 43, 45, 47, 48, 50, 51, 52, 53, 54, 55, 56
196 for (
auto freq :
xrange(16 * 8)) {
197 int fnum = freq % 16;
198 int block = freq / 16;
199 int tmp = 2 * klTable[fnum] - 16 * (7 - block);
200 for (
auto KL :
xrange(4)) {
201 unsigned t = (tmp <= 0 || KL == 0) ? 0 : (tmp >> (3 - KL));
203 result[KL][freq] = narrow<uint8_t>(
t);
212static constexpr auto fullSinTable = [] {
213 auto lin2db = [](
double d) {
217 : std::min(-
int(20.0 * cstd::log10<5, 2>(d) / DB_STEP), DB_MUTE - 1);
220 std::array<unsigned, PG_WIDTH> result = {};
225 result[
PG_WIDTH / 2 - 1 - i] = result[i];
228 result[
PG_WIDTH / 2 + i] = DBTABLEN + result[i];
232static constexpr auto halfSinTable = [] {
233 std::array<unsigned, PG_WIDTH> result = {};
235 result[i] = fullSinTable[i];
238 result[i] = fullSinTable[0];
242static constexpr std::array<std::span<const unsigned, PG_WIDTH>, 2> waveform = {
243 fullSinTable, halfSinTable
250static constexpr auto dPhaseDrTab = [] {
251 std::array<std::array<int, 16>, 16> result = {};
252 for (
auto Rks :
xrange(16)) {
254 for (
auto DR :
xrange(1, 16)) {
255 int RM = std::min(DR + (Rks >> 2), 15);
265static constexpr auto slTab = [] {
266 std::array<unsigned, 16> result = {};
268 for (
int i = 0; i < 16; ++i) {
269 double x = (i == 15) ? 48.0 : (3.0 * i);
278static constexpr unsigned EG2DB(
unsigned d)
280 return d * narrow_cast<unsigned>(EG_STEP / DB_STEP);
282static constexpr unsigned TL2EG(
unsigned d)
285 return d * narrow_cast<unsigned>(TL_STEP / EG_STEP);
288static constexpr unsigned DB_POS(
double x)
290 auto result = int(x / DB_STEP);
292 assert(result < DB_MUTE);
295static constexpr unsigned DB_NEG(
double x)
297 return DBTABLEN + DB_POS(x);
303static constexpr int BIT(
unsigned s,
unsigned b)
305 return narrow<int>((s >> b) & 1);
312 : WF(waveform[0]), KL(tllTab[0])
323 AMPM = (data[0] >> 6) & 3;
324 EG = (data[0] >> 5) & 1;
325 setKR ((data[0] >> 4) & 1);
326 setML ((data[0] >> 0) & 15);
327 setKL ((data[2] >> 6) & 3);
328 setTL ((data[2] >> 0) & 63);
329 setWF ((data[3] >> 3) & 1);
330 setFB ((data[3] >> 0) & 7);
331 AR = (data[4] >> 4) & 15;
332 DR = (data[4] >> 0) & 15;
333 setSL ((data[6] >> 4) & 15);
334 RR = (data[6] >> 0) & 15;
339 AMPM = (data[1] >> 6) & 3;
340 EG = (data[1] >> 5) & 1;
341 setKR ((data[1] >> 4) & 1);
342 setML ((data[1] >> 0) & 15);
343 setKL ((data[3] >> 6) & 3);
345 setWF ((data[3] >> 4) & 1);
347 AR = (data[5] >> 4) & 15;
348 DR = (data[5] >> 0) & 15;
349 setSL ((data[7] >> 4) & 15);
350 RR = (data[7] >> 0) & 15;
368 TL = narrow<uint8_t>(TL2EG(value));
372 WF = waveform[value];
376 FB = value ? 8 - value : 0;
389 : dPhaseDRTableRks(dPhaseDrTab[0])
415 unsigned fnum = freq & 511;
416 unsigned block = freq / 512;
418 unsigned tmp = ((2 * fnum + pmTable[fnum >> 6][pm]) *
patch.
ML) << block;
419 dP = tmp >> (21 - DP_BITS);
430 unsigned rks = freq >>
patch.
KR;
568 volume = TL2EG(value << 2);
600 if (modActAsCarrier) {
637static constexpr std::array inst_data = {
638 std::array<uint8_t, 8>{ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00 },
639 std::array<uint8_t, 8>{ 0x61,0x61,0x1e,0x17,0xf0,0x7f,0x00,0x17 },
640 std::array<uint8_t, 8>{ 0x13,0x41,0x16,0x0e,0xfd,0xf4,0x23,0x23 },
641 std::array<uint8_t, 8>{ 0x03,0x01,0x9a,0x04,0xf3,0xf3,0x13,0xf3 },
642 std::array<uint8_t, 8>{ 0x11,0x61,0x0e,0x07,0xfa,0x64,0x70,0x17 },
643 std::array<uint8_t, 8>{ 0x22,0x21,0x1e,0x06,0xf0,0x76,0x00,0x28 },
644 std::array<uint8_t, 8>{ 0x21,0x22,0x16,0x05,0xf0,0x71,0x00,0x18 },
645 std::array<uint8_t, 8>{ 0x21,0x61,0x1d,0x07,0x82,0x80,0x17,0x17 },
646 std::array<uint8_t, 8>{ 0x23,0x21,0x2d,0x16,0x90,0x90,0x00,0x07 },
647 std::array<uint8_t, 8>{ 0x21,0x21,0x1b,0x06,0x64,0x65,0x10,0x17 },
648 std::array<uint8_t, 8>{ 0x21,0x21,0x0b,0x1a,0x85,0xa0,0x70,0x07 },
649 std::array<uint8_t, 8>{ 0x23,0x01,0x83,0x10,0xff,0xb4,0x10,0xf4 },
650 std::array<uint8_t, 8>{ 0x97,0xc1,0x20,0x07,0xff,0xf4,0x22,0x22 },
651 std::array<uint8_t, 8>{ 0x61,0x00,0x0c,0x05,0xc2,0xf6,0x40,0x44 },
652 std::array<uint8_t, 8>{ 0x01,0x01,0x56,0x03,0x94,0xc2,0x03,0x12 },
653 std::array<uint8_t, 8>{ 0x21,0x01,0x89,0x03,0xf1,0xe4,0xf0,0x23 },
654 std::array<uint8_t, 8>{ 0x07,0x21,0x14,0x00,0xee,0xf8,0xff,0xf8 },
655 std::array<uint8_t, 8>{ 0x01,0x31,0x00,0x00,0xf8,0xf7,0xf8,0xf7 },
656 std::array<uint8_t, 8>{ 0x25,0x11,0x00,0x00,0xf8,0xfa,0xf8,0x55 }
662 for (
const auto& e : dB2LinTab) std::cout << e <<
' ';
665 for (
const auto& e : arAdjustTab) std::cout << e <<
' ';
668 for (
auto i :
xrange(4)) {
669 for (
auto j :
xrange(16 * 8)) {
670 std::cout << int(tllTab[i][j]) <<
' ';
676 for (
const auto& e : fullSinTable) std::cout << e <<
' ';
678 for (
const auto& e : halfSinTable) std::cout << e <<
' ';
681 for (
auto i :
xrange(16)) {
682 for (
auto j :
xrange(16)) {
683 std::cout << dPhaseDrTab[i][j] <<
' ';
689 for (
const auto& e : slTab) std::cout << e <<
' ';
695 for (
auto i :
xrange(16 + 3)) {
696 patches[i][0].initModulator(inst_data[i]);
697 patches[i][1].initCarrier (inst_data[i]);
710 for (
auto& ch : channels) {
713 for (
auto i :
xrange(uint8_t(0x40))) {
720void YM2413::keyOn_BD()
730void YM2413::keyOn_HH()
733 Channel& ch7 = channels[7];
734 if (!ch7.mod.slot_on_flag) {
737 ch7.mod.slot_on_flag |= 2;
739void YM2413::keyOn_SD()
741 Channel& ch7 = channels[7];
742 if (!ch7.car.slot_on_flag) {
745 ch7.car.slot_on_flag |= 2;
747void YM2413::keyOn_TOM()
749 Channel& ch8 = channels[8];
750 if (!ch8.mod.slot_on_flag) {
753 ch8.mod.slot_on_flag |= 2;
755void YM2413::keyOn_CYM()
757 Channel& ch8 = channels[8];
758 if (!ch8.car.slot_on_flag) {
761 ch8.car.slot_on_flag |= 2;
765void YM2413::keyOff_BD()
767 Channel& ch6 = channels[6];
768 if (ch6.car.slot_on_flag) {
769 ch6.car.slot_on_flag &= ~2;
770 ch6.mod.slot_on_flag &= ~2;
771 if (!ch6.car.slot_on_flag) {
776void YM2413::keyOff_HH()
778 Channel& ch7 = channels[7];
779 if (ch7.mod.slot_on_flag) {
780 ch7.mod.slot_on_flag &= ~2;
781 if (!ch7.mod.slot_on_flag) {
786void YM2413::keyOff_SD()
788 Channel& ch7 = channels[7];
789 if (ch7.car.slot_on_flag) {
790 ch7.car.slot_on_flag &= ~2;
791 if (!ch7.car.slot_on_flag) {
796void YM2413::keyOff_TOM()
798 Channel& ch8 = channels[8];
799 if (ch8.mod.slot_on_flag) {
800 ch8.mod.slot_on_flag &= ~2;
801 if (!ch8.mod.slot_on_flag) {
806void YM2413::keyOff_CYM()
808 Channel& ch8 = channels[8];
809 if (ch8.car.slot_on_flag) {
810 ch8.car.slot_on_flag &= ~2;
811 if (!ch8.car.slot_on_flag) {
817void YM2413::setRhythmFlags(uint8_t old)
819 Channel& ch6 = channels[6];
820 Channel& ch7 = channels[7];
821 Channel& ch8 = channels[8];
824 uint8_t flags = reg[0x0E];
825 if ((flags ^ old) & 0x20) {
828 ch6.setPatch(16, *
this);
829 ch7.setPatch(17, *
this);
830 ch7.mod.setVolume(reg[0x37] >> 4);
831 ch8.setPatch(18, *
this);
832 ch8.mod.setVolume(reg[0x38] >> 4);
835 ch6.setPatch(reg[0x36] >> 4, *
this);
837 ch7.setPatch(reg[0x37] >> 4, *
this);
840 ch8.setPatch(reg[0x38] >> 4, *
this);
846 if (flags & 0x10) keyOn_BD();
else keyOff_BD();
847 if (flags & 0x08) keyOn_SD();
else keyOff_SD();
848 if (flags & 0x04) keyOn_TOM();
else keyOff_TOM();
849 if (flags & 0x02) keyOn_CYM();
else keyOff_CYM();
850 if (flags & 0x01) keyOn_HH();
else keyOff_HH();
853 unsigned freq6 = getFreq(6);
854 ch6.mod.updateAll(freq6,
false);
855 ch6.car.updateAll(freq6,
true);
856 unsigned freq7 = getFreq(7);
857 ch7.mod.updateAll(freq7, isRhythm());
858 ch7.car.updateAll(freq7,
true);
859 unsigned freq8 = getFreq(8);
860 ch8.mod.updateAll(freq8, isRhythm());
861 ch8.car.updateAll(freq8,
true);
864void YM2413::update_key_status()
866 for (
auto [i, ch] :
enumerate(channels)) {
867 uint8_t slot_on = (reg[0x20 + i] & 0x10) ? 1 : 0;
868 ch.mod.slot_on_flag = slot_on;
869 ch.car.slot_on_flag = slot_on;
872 Channel& ch6 = channels[6];
873 ch6.mod.slot_on_flag |= uint8_t((reg[0x0e] & 0x10) ? 2 : 0);
874 ch6.car.slot_on_flag |= uint8_t((reg[0x0e] & 0x10) ? 2 : 0);
875 Channel& ch7 = channels[7];
876 ch7.mod.slot_on_flag |= uint8_t((reg[0x0e] & 0x01) ? 2 : 0);
877 ch7.car.slot_on_flag |= uint8_t((reg[0x0e] & 0x08) ? 2 : 0);
878 Channel& ch8 = channels[8];
879 ch8.mod.slot_on_flag |= uint8_t((reg[0x0e] & 0x04) ? 2 : 0);
880 ch8.car.slot_on_flag |= uint8_t((reg[0x0e] & 0x02) ? 2 : 0);
885static constexpr int wave2_8pi(
int e)
887 int shift = SLOT_AMP_BITS -
PG_BITS - 2;
899 return cPhase >> DP_BASE_BITS;
933template<
bool HAS_AM,
bool FIXED_ENV>
938 if constexpr (FIXED_ENV) {
939 unsigned out = fixed_env;
940 if constexpr (HAS_AM) {
950 out = arAdjustTab[out];
956 out = EG2DB(out +
tll);
957 if constexpr (HAS_AM) {
968 out = EG2DB(out +
tll);
969 if constexpr (!HAS_AM) {
976template<
bool HAS_AM,
bool FIXED_ENV>
979 int phase = narrow<int>(
calc_phase(lfo_pm)) + wave2_8pi(fm);
980 unsigned egOut = calc_envelope<HAS_AM, FIXED_ENV>(lfo_am, fixed_env);
987template<
bool HAS_AM,
bool HAS_FB,
bool FIXED_ENV>
990 assert((
patch.
FB != 0) == HAS_FB);
992 unsigned egOut = calc_envelope<HAS_AM, FIXED_ENV>(lfo_am, fixed_env);
993 if constexpr (HAS_FB) {
1006 unsigned egOut = calc_envelope<false, false>(0, 0);
1014 unsigned egOut = calc_envelope<false, false>(0, 0);
1015 return BIT(phase, 7)
1016 ? dB2LinTab[(noise ? DB_POS(0.0) : DB_POS(15.0)) + egOut]
1017 : dB2LinTab[(noise ? DB_NEG(0.0) : DB_NEG(15.0)) + egOut];
1023 unsigned egOut = calc_envelope<false, false>(0, 0);
1024 unsigned dbOut = (((BIT(phase7,
PG_BITS - 8) ^
1031 return dB2LinTab[dbOut + egOut];
1037 unsigned egOut = calc_envelope<false, false>(0, 0);
1038 unsigned dbOut = (((BIT(phase7,
PG_BITS - 8) ^
1043 ? (noise ? DB_NEG(12.0) : DB_NEG(24.0))
1044 : (noise ? DB_POS(12.0) : DB_POS(24.0));
1045 return dB2LinTab[dbOut + egOut];
1050 return 1.0f / (1 << DB2LIN_AMP_BITS);
1053bool YM2413::isRhythm()
const
1055 return (reg[0x0E] & 0x20) != 0;
1058unsigned YM2413::getFreq(
unsigned channel)
const
1061 assert(channel < 9);
1062 return reg[0x10 + channel] | ((reg[0x20 + channel] & 0x0F) << 8);
1067 return patches[instrument][carrier];
1070template<
unsigned FLAGS>
1074 const bool HAS_CAR_PM = (FLAGS & 1) != 0;
1075 const bool HAS_CAR_AM = (FLAGS & 2) != 0;
1076 const bool HAS_MOD_PM = (FLAGS & 4) != 0;
1077 const bool HAS_MOD_AM = (FLAGS & 8) != 0;
1078 const bool HAS_MOD_FB = (FLAGS & 16) != 0;
1079 const bool HAS_CAR_FIXED_ENV = (FLAGS & 32) != 0;
1080 const bool HAS_MOD_FIXED_ENV = (FLAGS & 64) != 0;
1087 unsigned tmp_pm_phase = pm_phase;
1088 unsigned tmp_am_phase = am_phase;
1089 unsigned car_fixed_env = 0;
1090 unsigned mod_fixed_env = 0;
1091 if constexpr (HAS_CAR_FIXED_ENV) {
1094 if constexpr (HAS_MOD_FIXED_ENV) {
1098 for (
auto& b : buf) {
1099 unsigned lfo_pm = 0;
1100 if constexpr (HAS_CAR_PM || HAS_MOD_PM) {
1106 lfo_pm = (tmp_pm_phase >> 10) & 7;
1109 if constexpr (HAS_CAR_AM || HAS_MOD_AM) {
1111 if (tmp_am_phase == (LFO_AM_TAB_ELEMENTS * 64)) {
1114 lfo_am = lfo_am_table[tmp_am_phase / 64];
1117 HAS_MOD_PM ? lfo_pm : 0, lfo_am, mod_fixed_env);
1118 b += narrow_cast<float>(ch.
car.
calc_slot_car<HAS_CAR_AM, HAS_CAR_FIXED_ENV>(
1119 HAS_CAR_PM ? lfo_pm : 0, lfo_am, fm, car_fixed_env));
1127 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1137 modFixedEnv =
false;
1142 ( carFixedEnv << 5) |
1143 ( modFixedEnv << 6);
1145 case 0: calcChannel< 0>(ch, {bufs[i], num});
break;
1146 case 1: calcChannel< 1>(ch, {bufs[i], num});
break;
1147 case 2: calcChannel< 2>(ch, {bufs[i], num});
break;
1148 case 3: calcChannel< 3>(ch, {bufs[i], num});
break;
1149 case 4: calcChannel< 4>(ch, {bufs[i], num});
break;
1150 case 5: calcChannel< 5>(ch, {bufs[i], num});
break;
1151 case 6: calcChannel< 6>(ch, {bufs[i], num});
break;
1152 case 7: calcChannel< 7>(ch, {bufs[i], num});
break;
1153 case 8: calcChannel< 8>(ch, {bufs[i], num});
break;
1154 case 9: calcChannel< 9>(ch, {bufs[i], num});
break;
1155 case 10: calcChannel< 10>(ch, {bufs[i], num});
break;
1156 case 11: calcChannel< 11>(ch, {bufs[i], num});
break;
1157 case 12: calcChannel< 12>(ch, {bufs[i], num});
break;
1158 case 13: calcChannel< 13>(ch, {bufs[i], num});
break;
1159 case 14: calcChannel< 14>(ch, {bufs[i], num});
break;
1160 case 15: calcChannel< 15>(ch, {bufs[i], num});
break;
1161 case 16: calcChannel< 16>(ch, {bufs[i], num});
break;
1162 case 17: calcChannel< 17>(ch, {bufs[i], num});
break;
1163 case 18: calcChannel< 18>(ch, {bufs[i], num});
break;
1164 case 19: calcChannel< 19>(ch, {bufs[i], num});
break;
1165 case 20: calcChannel< 20>(ch, {bufs[i], num});
break;
1166 case 21: calcChannel< 21>(ch, {bufs[i], num});
break;
1167 case 22: calcChannel< 22>(ch, {bufs[i], num});
break;
1168 case 23: calcChannel< 23>(ch, {bufs[i], num});
break;
1169 case 24: calcChannel< 24>(ch, {bufs[i], num});
break;
1170 case 25: calcChannel< 25>(ch, {bufs[i], num});
break;
1171 case 26: calcChannel< 26>(ch, {bufs[i], num});
break;
1172 case 27: calcChannel< 27>(ch, {bufs[i], num});
break;
1173 case 28: calcChannel< 28>(ch, {bufs[i], num});
break;
1174 case 29: calcChannel< 29>(ch, {bufs[i], num});
break;
1175 case 30: calcChannel< 30>(ch, {bufs[i], num});
break;
1176 case 31: calcChannel< 31>(ch, {bufs[i], num});
break;
1177 case 32: calcChannel< 32>(ch, {bufs[i], num});
break;
1178 case 33: calcChannel< 33>(ch, {bufs[i], num});
break;
1179 case 34: calcChannel< 34>(ch, {bufs[i], num});
break;
1180 case 35: calcChannel< 35>(ch, {bufs[i], num});
break;
1181 case 36: calcChannel< 36>(ch, {bufs[i], num});
break;
1182 case 37: calcChannel< 37>(ch, {bufs[i], num});
break;
1183 case 38: calcChannel< 38>(ch, {bufs[i], num});
break;
1184 case 39: calcChannel< 39>(ch, {bufs[i], num});
break;
1185 case 40: calcChannel< 40>(ch, {bufs[i], num});
break;
1186 case 41: calcChannel< 41>(ch, {bufs[i], num});
break;
1187 case 42: calcChannel< 42>(ch, {bufs[i], num});
break;
1188 case 43: calcChannel< 43>(ch, {bufs[i], num});
break;
1189 case 44: calcChannel< 44>(ch, {bufs[i], num});
break;
1190 case 45: calcChannel< 45>(ch, {bufs[i], num});
break;
1191 case 46: calcChannel< 46>(ch, {bufs[i], num});
break;
1192 case 47: calcChannel< 47>(ch, {bufs[i], num});
break;
1193 case 48: calcChannel< 48>(ch, {bufs[i], num});
break;
1194 case 49: calcChannel< 49>(ch, {bufs[i], num});
break;
1195 case 50: calcChannel< 50>(ch, {bufs[i], num});
break;
1196 case 51: calcChannel< 51>(ch, {bufs[i], num});
break;
1197 case 52: calcChannel< 52>(ch, {bufs[i], num});
break;
1198 case 53: calcChannel< 53>(ch, {bufs[i], num});
break;
1199 case 54: calcChannel< 54>(ch, {bufs[i], num});
break;
1200 case 55: calcChannel< 55>(ch, {bufs[i], num});
break;
1201 case 56: calcChannel< 56>(ch, {bufs[i], num});
break;
1202 case 57: calcChannel< 57>(ch, {bufs[i], num});
break;
1203 case 58: calcChannel< 58>(ch, {bufs[i], num});
break;
1204 case 59: calcChannel< 59>(ch, {bufs[i], num});
break;
1205 case 60: calcChannel< 60>(ch, {bufs[i], num});
break;
1206 case 61: calcChannel< 61>(ch, {bufs[i], num});
break;
1207 case 62: calcChannel< 62>(ch, {bufs[i], num});
break;
1208 case 63: calcChannel< 63>(ch, {bufs[i], num});
break;
1209 case 64: calcChannel< 64>(ch, {bufs[i], num});
break;
1210 case 65: calcChannel< 65>(ch, {bufs[i], num});
break;
1211 case 66: calcChannel< 66>(ch, {bufs[i], num});
break;
1212 case 67: calcChannel< 67>(ch, {bufs[i], num});
break;
1213 case 68: calcChannel< 68>(ch, {bufs[i], num});
break;
1214 case 69: calcChannel< 69>(ch, {bufs[i], num});
break;
1215 case 70: calcChannel< 70>(ch, {bufs[i], num});
break;
1216 case 71: calcChannel< 71>(ch, {bufs[i], num});
break;
1217 case 72: calcChannel< 72>(ch, {bufs[i], num});
break;
1218 case 73: calcChannel< 73>(ch, {bufs[i], num});
break;
1219 case 74: calcChannel< 74>(ch, {bufs[i], num});
break;
1220 case 75: calcChannel< 75>(ch, {bufs[i], num});
break;
1221 case 76: calcChannel< 76>(ch, {bufs[i], num});
break;
1222 case 77: calcChannel< 77>(ch, {bufs[i], num});
break;
1223 case 78: calcChannel< 78>(ch, {bufs[i], num});
break;
1224 case 79: calcChannel< 79>(ch, {bufs[i], num});
break;
1225 case 80: calcChannel< 80>(ch, {bufs[i], num});
break;
1226 case 81: calcChannel< 81>(ch, {bufs[i], num});
break;
1227 case 82: calcChannel< 82>(ch, {bufs[i], num});
break;
1228 case 83: calcChannel< 83>(ch, {bufs[i], num});
break;
1229 case 84: calcChannel< 84>(ch, {bufs[i], num});
break;
1230 case 85: calcChannel< 85>(ch, {bufs[i], num});
break;
1231 case 86: calcChannel< 86>(ch, {bufs[i], num});
break;
1232 case 87: calcChannel< 87>(ch, {bufs[i], num});
break;
1233 case 88: calcChannel< 88>(ch, {bufs[i], num});
break;
1234 case 89: calcChannel< 89>(ch, {bufs[i], num});
break;
1235 case 90: calcChannel< 90>(ch, {bufs[i], num});
break;
1236 case 91: calcChannel< 91>(ch, {bufs[i], num});
break;
1237 case 92: calcChannel< 92>(ch, {bufs[i], num});
break;
1238 case 93: calcChannel< 93>(ch, {bufs[i], num});
break;
1239 case 94: calcChannel< 94>(ch, {bufs[i], num});
break;
1240 case 95: calcChannel< 95>(ch, {bufs[i], num});
break;
1241 case 96: calcChannel< 96>(ch, {bufs[i], num});
break;
1242 case 97: calcChannel< 97>(ch, {bufs[i], num});
break;
1243 case 98: calcChannel< 98>(ch, {bufs[i], num});
break;
1244 case 99: calcChannel< 99>(ch, {bufs[i], num});
break;
1245 case 100: calcChannel<100>(ch, {bufs[i], num});
break;
1246 case 101: calcChannel<101>(ch, {bufs[i], num});
break;
1247 case 102: calcChannel<102>(ch, {bufs[i], num});
break;
1248 case 103: calcChannel<103>(ch, {bufs[i], num});
break;
1249 case 104: calcChannel<104>(ch, {bufs[i], num});
break;
1250 case 105: calcChannel<105>(ch, {bufs[i], num});
break;
1251 case 106: calcChannel<106>(ch, {bufs[i], num});
break;
1252 case 107: calcChannel<107>(ch, {bufs[i], num});
break;
1253 case 108: calcChannel<108>(ch, {bufs[i], num});
break;
1254 case 109: calcChannel<109>(ch, {bufs[i], num});
break;
1255 case 110: calcChannel<110>(ch, {bufs[i], num});
break;
1256 case 111: calcChannel<111>(ch, {bufs[i], num});
break;
1257 case 112: calcChannel<112>(ch, {bufs[i], num});
break;
1258 case 113: calcChannel<113>(ch, {bufs[i], num});
break;
1259 case 114: calcChannel<114>(ch, {bufs[i], num});
break;
1260 case 115: calcChannel<115>(ch, {bufs[i], num});
break;
1261 case 116: calcChannel<116>(ch, {bufs[i], num});
break;
1262 case 117: calcChannel<117>(ch, {bufs[i], num});
break;
1263 case 118: calcChannel<118>(ch, {bufs[i], num});
break;
1264 case 119: calcChannel<119>(ch, {bufs[i], num});
break;
1265 case 120: calcChannel<120>(ch, {bufs[i], num});
break;
1266 case 121: calcChannel<121>(ch, {bufs[i], num});
break;
1267 case 122: calcChannel<122>(ch, {bufs[i], num});
break;
1268 case 123: calcChannel<123>(ch, {bufs[i], num});
break;
1269 case 124: calcChannel<124>(ch, {bufs[i], num});
break;
1270 case 125: calcChannel<125>(ch, {bufs[i], num});
break;
1271 case 126: calcChannel<126>(ch, {bufs[i], num});
break;
1272 case 127: calcChannel<127>(ch, {bufs[i], num});
break;
1281 am_phase = (am_phase + num) % (LFO_AM_TAB_ELEMENTS * 64);
1292 unsigned old_noise = noise_seed;
1297 for (
auto sample :
xrange(num)) {
1298 bufs[ 9][sample] += narrow_cast<float>(
1301 false,
false,
false>(0, 0, 0), 0));
1308 for (
auto sample :
xrange(num)) {
1310 bool noise_bit = noise_seed & 1;
1311 if (noise_bit) noise_seed ^= 0x8003020;
1312 bufs[10][sample] += narrow_cast<float>(
1320 for (
auto sample :
xrange(num)) {
1323 bufs[11][sample] += narrow_cast<float>(
1332 noise_seed = old_noise;
1335 for (
auto sample :
xrange(num)) {
1337 bool noise_bit = noise_seed & 1;
1338 if (noise_bit) noise_seed ^= 0x8003020;
1341 bufs[12][sample] += narrow_cast<float>(
1349 for (
auto sample :
xrange(num)) {
1350 bufs[13][sample] += narrow_cast<float>(
1368 registerLatch = value;
1370 writeReg(registerLatch & 0x3f, value);
1379void YM2413::writeReg(uint8_t r, uint8_t data)
1387 patches[0][0].AMPM = (data >> 6) & 3;
1388 patches[0][0].EG = (data >> 5) & 1;
1389 patches[0][0].setKR ((data >> 4) & 1);
1390 patches[0][0].setML ((data >> 0) & 15);
1391 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1392 if ((reg[0x30 + i] & 0xF0) == 0) {
1395 unsigned freq = getFreq(i);
1405 patches[0][1].AMPM = (data >> 6) & 3;
1406 patches[0][1].EG = (data >> 5) & 1;
1407 patches[0][1].setKR ((data >> 4) & 1);
1408 patches[0][1].setML ((data >> 0) & 15);
1409 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1410 if ((reg[0x30 + i] & 0xF0) == 0) {
1411 Channel& ch = channels[i];
1412 ch.setPatch(0, *
this);
1413 unsigned freq = getFreq(i);
1414 ch.car.updatePG (freq);
1415 ch.car.updateRKS(freq);
1423 patches[0][0].setKL((data >> 6) & 3);
1424 patches[0][0].setTL((data >> 0) & 63);
1425 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1426 if ((reg[0x30 + i] & 0xF0) == 0) {
1427 Channel& ch = channels[i];
1428 ch.setPatch(0, *
this);
1429 bool actAsCarrier = (i >= 7) && isRhythm();
1430 assert(!actAsCarrier); (void)actAsCarrier;
1431 ch.mod.updateTLL(getFreq(i),
false);
1438 patches[0][1].setKL((data >> 6) & 3);
1439 patches[0][1].setWF((data >> 4) & 1);
1440 patches[0][0].setWF((data >> 3) & 1);
1441 patches[0][0].setFB((data >> 0) & 7);
1442 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1443 if ((reg[0x30 + i] & 0xF0) == 0) {
1444 Channel& ch = channels[i];
1445 ch.setPatch(0, *
this);
1452 patches[0][0].AR = (data >> 4) & 15;
1453 patches[0][0].DR = (data >> 0) & 15;
1454 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1455 if ((reg[0x30 + i] & 0xF0) == 0) {
1456 Channel& ch = channels[i];
1457 ch.setPatch(0, *
this);
1459 if (ch.mod.state == ATTACK) {
1460 ch.mod.setEnvelopeState(ATTACK);
1468 patches[0][1].AR = (data >> 4) & 15;
1469 patches[0][1].DR = (data >> 0) & 15;
1470 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1471 if ((reg[0x30 + i] & 0xF0) == 0) {
1472 Channel& ch = channels[i];
1473 ch.setPatch(0, *
this);
1475 if (ch.car.state == ATTACK) {
1476 ch.car.setEnvelopeState(ATTACK);
1484 patches[0][0].setSL((data >> 4) & 15);
1485 patches[0][0].RR = (data >> 0) & 15;
1486 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1487 if ((reg[0x30 + i] & 0xF0) == 0) {
1488 Channel& ch = channels[i];
1489 ch.setPatch(0, *
this);
1491 if (ch.mod.state == DECAY) {
1492 ch.mod.setEnvelopeState(DECAY);
1500 patches[0][1].setSL((data >> 4) & 15);
1501 patches[0][1].RR = (data >> 0) & 15;
1502 for (
auto i :
xrange(isRhythm() ? 6 : 9)) {
1503 if ((reg[0x30 + i] & 0xF0) == 0) {
1504 Channel& ch = channels[i];
1505 ch.setPatch(0, *
this);
1507 if (ch.car.state == DECAY) {
1508 ch.car.setEnvelopeState(DECAY);
1515 uint8_t old = reg[r];
1517 setRhythmFlags(old);
1520 case 0x19:
case 0x1A:
case 0x1B:
case 0x1C:
1521 case 0x1D:
case 0x1E:
case 0x1F:
1524 case 0x10:
case 0x11:
case 0x12:
case 0x13:
case 0x14:
1525 case 0x15:
case 0x16:
case 0x17:
case 0x18: {
1527 unsigned cha = r & 0x0F; assert(cha < 9);
1528 Channel& ch = channels[cha];
1529 bool actAsCarrier = (cha >= 7) && isRhythm();
1530 unsigned freq = getFreq(cha);
1531 ch.mod.updateAll(freq, actAsCarrier);
1532 ch.car.updateAll(freq,
true);
1535 case 0x29:
case 0x2A:
case 0x2B:
case 0x2C:
1536 case 0x2D:
case 0x2E:
case 0x2F:
1539 case 0x20:
case 0x21:
case 0x22:
case 0x23:
case 0x24:
1540 case 0x25:
case 0x26:
case 0x27:
case 0x28: {
1542 unsigned cha = r & 0x0F; assert(cha < 9);
1543 Channel& ch = channels[cha];
1544 bool modActAsCarrier = (cha >= 7) && isRhythm();
1545 ch.setSustain((data >> 5) & 1, modActAsCarrier);
1551 unsigned freq = getFreq(cha);
1552 ch.mod.updateAll(freq, modActAsCarrier);
1553 ch.car.updateAll(freq,
true);
1556 case 0x39:
case 0x3A:
case 0x3B:
case 0x3C:
1557 case 0x3D:
case 0x3E:
case 0x3F:
1560 case 0x30:
case 0x31:
case 0x32:
case 0x33:
case 0x34:
1561 case 0x35:
case 0x36:
case 0x37:
case 0x38: {
1563 unsigned cha = r & 0x0F; assert(cha < 9);
1564 Channel& ch = channels[cha];
1565 if (isRhythm() && (cha >= 6)) {
1568 ch.mod.setVolume(data >> 4);
1571 ch.setPatch(data >> 4, *
this);
1573 ch.car.setVolume(data & 15);
1574 bool actAsCarrier = (cha >= 7) && isRhythm();
1575 unsigned freq = getFreq(cha);
1576 ch.mod.updateAll(freq, actAsCarrier);
1577 ch.car.updateAll(freq,
true);