VERA: get rid of rand() and adapt code

This commit is contained in:
tildearrow 2022-03-10 16:52:59 -05:00
parent 9bd15bd513
commit 2f02e24a2f
3 changed files with 20 additions and 8 deletions

View file

@ -20,6 +20,8 @@ void
psg_reset(struct VERA_PSG* psg)
{
memset(psg->channels, 0, sizeof(psg->channels));
psg->noiseState=1;
psg->noiseOut=0;
}
void
@ -52,13 +54,18 @@ render(struct VERA_PSG* psg, int16_t *left, int16_t *right)
{
int l = 0;
int r = 0;
// TODO this is a currently speculated noise generation
// as the hardware and sources for it are not out in the public
// and the official emulator just uses rand()
psg->noiseOut=((psg->noiseOut<<1)|(psg->noiseState&1))&63;
psg->noiseState=(psg->noiseState<<1)|(((psg->noiseState>>1)^(psg->noiseState>>2)^(psg->noiseState>>4)^(psg->noiseState>>15))&1);
for (int i = 0; i < 16; i++) {
struct VERAChannel *ch = &psg->channels[i];
unsigned new_phase = (ch->phase + ch->freq) & 0x1FFFF;
if ((ch->phase & 0x10000) != (new_phase & 0x10000)) {
ch->noiseval = rand() & 63;
ch->noiseval = psg->noiseOut;
}
ch->phase = new_phase;
@ -89,10 +96,11 @@ render(struct VERA_PSG* psg, int16_t *left, int16_t *right)
}
void
psg_render(struct VERA_PSG* psg, int16_t *buf, unsigned num_samples)
psg_render(struct VERA_PSG* psg, int16_t *bufL, int16_t *bufR, unsigned num_samples)
{
while (num_samples--) {
render(psg, &buf[0], &buf[1]);
buf += 2;
render(psg, bufL, bufR);
bufL++;
bufR++;
}
}

View file

@ -19,9 +19,10 @@ struct VERAChannel {
};
struct VERA_PSG {
unsigned int noiseState, noiseOut;
struct VERAChannel channels[16];
};
void psg_reset(struct VERA_PSG* psg);
void psg_writereg(struct VERA_PSG* psg, uint8_t reg, uint8_t val);
void psg_render(struct VERA_PSG* psg, int16_t *buf, unsigned num_samples);
void psg_render(struct VERA_PSG* psg, int16_t *bufL, int16_t *bufR, unsigned num_samples);

View file

@ -22,10 +22,12 @@
#include <string.h>
#include <math.h>
#include "sound/vera_psg.h"
#include "sound/vera_pcm.h"
extern "C" {
#include "sound/vera_psg.h"
#include "sound/vera_pcm.h"
}
#define rWrite(c,a,d) {regPool[(c)*4+(a)]=(d);}
#define rWrite(c,a,d) {regPool[(c)*4+(a)]=(d); psg_writereg(psg,((c)*4+(a)),(d));}
#define rWriteLo(c,a,d) rWrite(c,a,(regPool[(c)*4+(a)]&(~0x3f))|((d)&0x3f))
#define rWriteHi(c,a,d) rWrite(c,a,(regPool[(c)*4+(a)]&(~0xc0))|(((d)<<6)&0xc0))
#define rWriteFIFOVol(d) rWrite(16,0,(regPool[64]&(~0x3f))|((d)&0x3f))
@ -58,6 +60,7 @@ const char* DivPlatformVERA::getEffectName(unsigned char effect) {
}
void DivPlatformVERA::acquire(short* bufL, short* bufR, size_t start, size_t len) {
psg_render(psg,bufL+start,bufR+start,len);
}
void DivPlatformVERA::reset() {