VSU fixes
This commit is contained in:
parent
a285065102
commit
0a57ef0faf
|
@ -509,7 +509,7 @@ VBAPI vbOnRead vbGetReadCallback(VB *sim) {
|
|||
|
||||
/* Retrieve the audio samples buffer */
|
||||
VBAPI void* vbGetSamples(VB *sim, uint32_t *capacity, uint32_t *position) {
|
||||
if (capacity == NULL) {
|
||||
if (sim->vsu.out.samples == NULL) {
|
||||
if (capacity != NULL)
|
||||
*capacity = 0;
|
||||
if (position != NULL)
|
||||
|
|
62
core/vsu.c
62
core/vsu.c
|
@ -77,6 +77,7 @@ static void vsuNextFreqMod(VB *sim, Channel *chan) {
|
|||
static void vsuEmulateChannel(VB *sim, int index, uint32_t clocks) {
|
||||
uint32_t bit; /* Pseudorandom bit */
|
||||
Channel *chan; /* Channel handle */
|
||||
int freqmod; /* Frequency modifications enabled */
|
||||
uint32_t level; /* Stereo output level */
|
||||
uint32_t sample; /* Input sample */
|
||||
uint32_t until; /* Clocks to process sub-channel components */
|
||||
|
@ -107,39 +108,42 @@ static void vsuEmulateChannel(VB *sim, int index, uint32_t clocks) {
|
|||
/* Process all clocks */
|
||||
do {
|
||||
|
||||
/* Clocks until next state change */
|
||||
until = clocks;
|
||||
if (chan->clocks < until) /* Next sample */
|
||||
until = chan->clocks;
|
||||
if (
|
||||
chan->env.enb && /* Modifications enabled */
|
||||
chan->env.clocks < until /* Next modification */
|
||||
) until = chan->env.clocks;
|
||||
if (
|
||||
chan->int_.auto_ && /* Shutoff enabled */
|
||||
chan->int_.clocks < until /* Shutoff */
|
||||
) until = chan->int_.clocks;
|
||||
if (
|
||||
/* Frequency modifications are active */
|
||||
freqmod =
|
||||
index == 4 && /* Channel 5 */
|
||||
sim->vsu.freqmod.enb && /* Modifications enabled */
|
||||
sim->vsu.freqmod.interval != 0 && /* Modifications valid */
|
||||
sim->vsu.freqmod.clocks < until /* Next modification */
|
||||
) until = sim->vsu.freqmod.clocks;
|
||||
sim->vsu.freqmod.interval != 0 /* Modifications valid */
|
||||
;
|
||||
|
||||
/* Clocks until next state change */
|
||||
until = clocks;
|
||||
if (chan->clocks < until)
|
||||
until = chan->clocks;
|
||||
if (chan->env.enb && chan->env.clocks < until)
|
||||
until = chan->env.clocks;
|
||||
if (chan->int_.auto_ && chan->int_.clocks < until)
|
||||
until = chan->int_.clocks;
|
||||
if (freqmod && sim->vsu.freqmod.clocks < until)
|
||||
until = sim->vsu.freqmod.clocks;
|
||||
|
||||
/* Manage clocks */
|
||||
clocks -= until;
|
||||
chan->clocks -= until;
|
||||
if (chan->env.enb)
|
||||
chan->env.clocks -= until;
|
||||
if (chan->int_.auto_)
|
||||
chan->int_.clocks -= until;
|
||||
if (freqmod)
|
||||
sim->vsu.freqmod.clocks -= until;
|
||||
|
||||
/* Automatic shutoff */
|
||||
if (
|
||||
chan->int_.auto_ && /* Shutoff enabled */
|
||||
chan->int_.clocks == until
|
||||
) {
|
||||
if (chan->int_.auto_ && chan->int_.clocks == 0) {
|
||||
chan->int_.enb = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
/* Next sample */
|
||||
if (chan->clocks == until) {
|
||||
if (chan->clocks == 0) {
|
||||
|
||||
/* Wave */
|
||||
if (index != 5) {
|
||||
|
@ -161,10 +165,7 @@ static void vsuEmulateChannel(VB *sim, int index, uint32_t clocks) {
|
|||
}
|
||||
|
||||
/* Envelope modification */
|
||||
if (
|
||||
chan->env.enb && /* Modifications enabled */
|
||||
chan->env.clocks == until
|
||||
) {
|
||||
if (chan->env.enb && chan->env.clocks == 0) {
|
||||
if (chan->env.dir == 0 && chan->env.value != 0)
|
||||
chan->env.value--;
|
||||
else if (chan->env.dir == 1 && chan->env.value != 15)
|
||||
|
@ -172,16 +173,11 @@ static void vsuEmulateChannel(VB *sim, int index, uint32_t clocks) {
|
|||
else if (chan->env.rep)
|
||||
chan->env.value = chan->env.reload;
|
||||
else chan->env.enb = 0;
|
||||
chan->env.clocks = (uint32_t) chan->env.interval * 307220;
|
||||
chan->env.clocks = ((uint32_t) chan->env.interval + 1) * 307220;
|
||||
}
|
||||
|
||||
/* Frequency modification */
|
||||
if (
|
||||
index == 4 && /* Channel 5 */
|
||||
sim->vsu.freqmod.enb && /* Modifications enabled */
|
||||
sim->vsu.freqmod.interval != 0 && /* Modifications valid */
|
||||
sim->vsu.freqmod.clocks == until
|
||||
) {
|
||||
if (freqmod && sim->vsu.freqmod.clocks == 0) {
|
||||
chan->freq.current = sim->vsu.freqmod.next;
|
||||
vsuNextFreqMod(sim, chan);
|
||||
if (!chan->int_.enb)
|
||||
|
@ -222,7 +218,7 @@ static void vsuWriteEV1(VB *sim, int index, uint8_t value) {
|
|||
case 4: /* Channel 5 */
|
||||
sim->vsu.freqmod.enb = value >> 6 & 1;
|
||||
sim->vsu.freqmod.func = value >> 4 & 1;
|
||||
sim->vsu.freqmod.rep = value >> 4 & 1;
|
||||
sim->vsu.freqmod.rep = value >> 5 & 1;
|
||||
vsuNextFreqMod(sim, chan);
|
||||
break;
|
||||
|
||||
|
|
Loading…
Reference in New Issue