void DACUpdate(INT16* Buffer, INT32 Length) { #if defined FBA_DEBUG if (!DebugSnd_DACInitted) bprintf(PRINT_ERROR, _T("DACUpdate called without init\n")); #endif struct dac_info *ptr; for (INT32 i = 0; i < NumChips; i++) { UpdateStream(i, nBurnSoundLen); } INT16 *lbuf = lBuffer; INT16 *rbuf = rBuffer; if (bAddSignal) { while (Length--) { Buffer[0] = BURN_SND_CLIP((INT32)(lbuf[0] + Buffer[0])); Buffer[1] = BURN_SND_CLIP((INT32)(rbuf[0] + Buffer[1])); Buffer += 2; lbuf[0] = 0; // clear buffer rbuf[0] = 0; // clear buffer lbuf++; rbuf++; } } else { while (Length--) { Buffer[0] = lbuf[0]; Buffer[1] = rbuf[0]; Buffer += 2; lbuf[0] = 0; // clear buffer rbuf[0] = 0; // clear buffer lbuf++; rbuf++; } } for (INT32 i = 0; i < NumChips; i++) { ptr = &dac_table[i]; ptr->nCurrentPosition = 0; } }
static void YM2151RenderNormal(INT16* pSoundBuf, INT32 nSegmentLength) { #if defined FBA_DEBUG if (!DebugSnd_YM2151Initted) bprintf(PRINT_ERROR, _T("YM2151RenderNormal called without init\n")); #endif nBurnPosition += nSegmentLength; pYM2151Buffer[0] = pBuffer; pYM2151Buffer[1] = pBuffer + nSegmentLength; YM2151UpdateOne(0, pYM2151Buffer, nSegmentLength); for (INT32 n = 0; n < nSegmentLength; n++) { INT32 nLeftSample = 0, nRightSample = 0; if ((YM2151RouteDirs[BURN_SND_YM2151_YM2151_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(pYM2151Buffer[0][n] * YM2151Volumes[BURN_SND_YM2151_YM2151_ROUTE_1]); } if ((YM2151RouteDirs[BURN_SND_YM2151_YM2151_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(pYM2151Buffer[0][n] * YM2151Volumes[BURN_SND_YM2151_YM2151_ROUTE_1]); } if ((YM2151RouteDirs[BURN_SND_YM2151_YM2151_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(pYM2151Buffer[1][n] * YM2151Volumes[BURN_SND_YM2151_YM2151_ROUTE_2]); } if ((YM2151RouteDirs[BURN_SND_YM2151_YM2151_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(pYM2151Buffer[1][n] * YM2151Volumes[BURN_SND_YM2151_YM2151_ROUTE_2]); } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); pSoundBuf[(n << 1) + 0] = nLeftSample; pSoundBuf[(n << 1) + 1] = nRightSample; } }
void AY8910Render(INT16** buffer, INT16* dest, INT32 length, INT32 bAddSignal) { #if defined FBA_DEBUG #ifdef __GNUC__ if (!DebugSnd_AY8910Initted) bprintf(PRINT_ERROR, _T("AY8910Render called without init\n")); if (num >= 7) bprintf(PRINT_ERROR, _T("AY8910Render called with invalid number of chips %i (max is 6)\n"), num); #endif #endif INT32 i; INT16 *buf0 = buffer[0]; INT16 *buf1 = buffer[1]; INT16 *buf2 = buffer[2]; INT16 *buf3, *buf4, *buf5, *buf6, *buf7, *buf8, *buf9, *buf10, *buf11, *buf12, *buf13, *buf14, *buf15, *buf16, *buf17; INT32 n; for (i = 0; i < num; i++) { AY8910Update(i, buffer + (i * 3), length); } if (num >= 2) { buf3 = buffer[3]; buf4 = buffer[4]; buf5 = buffer[5]; } if (num >= 3) { buf6 = buffer[6]; buf7 = buffer[7]; buf8 = buffer[8]; } if (num >= 4) { buf9 = buffer[9]; buf10 = buffer[10]; buf11 = buffer[11]; } if (num >= 5) { buf12 = buffer[12]; buf13 = buffer[13]; buf14 = buffer[14]; } if (num >= 6) { buf15 = buffer[15]; buf16 = buffer[16]; buf17 = buffer[17]; } for (n = 0; n < length; n++) { INT32 nLeftSample = 0, nRightSample = 0; AY8910_ADD_SOUND(BURN_SND_AY8910_ROUTE_1, buf0) AY8910_ADD_SOUND(BURN_SND_AY8910_ROUTE_2, buf1) AY8910_ADD_SOUND(BURN_SND_AY8910_ROUTE_3, buf2) if (num >= 2) { AY8910_ADD_SOUND(3 + BURN_SND_AY8910_ROUTE_1, buf3) AY8910_ADD_SOUND(3 + BURN_SND_AY8910_ROUTE_2, buf4) AY8910_ADD_SOUND(3 + BURN_SND_AY8910_ROUTE_3, buf5) } if (num >= 3) { AY8910_ADD_SOUND(6 + BURN_SND_AY8910_ROUTE_1, buf6) AY8910_ADD_SOUND(6 + BURN_SND_AY8910_ROUTE_2, buf7) AY8910_ADD_SOUND(6 + BURN_SND_AY8910_ROUTE_3, buf8) } if (num >= 4) { AY8910_ADD_SOUND(9 + BURN_SND_AY8910_ROUTE_1, buf9) AY8910_ADD_SOUND(9 + BURN_SND_AY8910_ROUTE_2, buf10) AY8910_ADD_SOUND(9 + BURN_SND_AY8910_ROUTE_3, buf11) } if (num >= 5) { AY8910_ADD_SOUND(12 + BURN_SND_AY8910_ROUTE_1, buf12) AY8910_ADD_SOUND(12 + BURN_SND_AY8910_ROUTE_2, buf13) AY8910_ADD_SOUND(12 + BURN_SND_AY8910_ROUTE_3, buf14) } if (num >= 6) { AY8910_ADD_SOUND(15 + BURN_SND_AY8910_ROUTE_1, buf15) AY8910_ADD_SOUND(15 + BURN_SND_AY8910_ROUTE_2, buf16) AY8910_ADD_SOUND(15 + BURN_SND_AY8910_ROUTE_3, buf17) } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); if (bAddSignal) { dest[(n << 1) + 0] += nLeftSample; dest[(n << 1) + 1] += nRightSample; } else { dest[(n << 1) + 0] = nLeftSample; dest[(n << 1) + 1] = nRightSample; } } }
void BurnYMF278BUpdate(INT32 nSegmentEnd) { #if defined FBA_DEBUG if (!DebugSnd_YMF278BInitted) bprintf(PRINT_ERROR, _T("BurnYMF278BUpdate called without init\n")); #endif INT16* pSoundBuf = pBurnSoundOut; INT32 nSegmentLength = nSegmentEnd; // bprintf(PRINT_NORMAL, _T(" YMF278B render %6i -> %6i\n"), nYMF278BPosition, nSegmentEnd); if (nBurnSoundRate == 0) { return; } if (nSegmentEnd < nYMF278BPosition) { nSegmentEnd = nYMF278BPosition; } if (nSegmentLength > nBurnSoundLen) { nSegmentLength = nBurnSoundLen; } YMF278BRender(nSegmentEnd); pYMF278BBuffer[0] = pBuffer + 0 * 4096 + 4; pYMF278BBuffer[1] = pBuffer + 1 * 4096 + 4; for (INT32 n = nFractionalPosition; n < nSegmentLength; n++) { INT32 nLeftSample = 0, nRightSample = 0; if ((YMF278BRouteDirs[BURN_SND_YMF278B_YMF278B_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(pYMF278BBuffer[0][n] * YMF278BVolumes[BURN_SND_YMF278B_YMF278B_ROUTE_1]); } if ((YMF278BRouteDirs[BURN_SND_YMF278B_YMF278B_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(pYMF278BBuffer[0][n] * YMF278BVolumes[BURN_SND_YMF278B_YMF278B_ROUTE_1]); } if ((YMF278BRouteDirs[BURN_SND_YMF278B_YMF278B_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(pYMF278BBuffer[1][n] * YMF278BVolumes[BURN_SND_YMF278B_YMF278B_ROUTE_2]); } if ((YMF278BRouteDirs[BURN_SND_YMF278B_YMF278B_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(pYMF278BBuffer[1][n] * YMF278BVolumes[BURN_SND_YMF278B_YMF278B_ROUTE_2]); } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); pSoundBuf[(n << 1) + 0] = nLeftSample; pSoundBuf[(n << 1) + 1] = nRightSample; } nFractionalPosition = nSegmentLength; if (nSegmentEnd >= nBurnSoundLen) { INT32 nExtraSamples = nSegmentEnd - nBurnSoundLen; for (INT32 i = 0; i < nExtraSamples; i++) { pYMF278BBuffer[0][i] = pYMF278BBuffer[0][nBurnSoundLen + i]; pYMF278BBuffer[1][i] = pYMF278BBuffer[1][nBurnSoundLen + i]; } nFractionalPosition = 0; nYMF278BPosition = nExtraSamples; } }
void BurnSampleRender(INT16 *pDest, UINT32 pLen) { #if defined FBA_DEBUG if (!DebugSnd_SamplesInitted) bprintf(PRINT_ERROR, _T("BurnSampleRender called without init\n")); #endif if (pBurnSoundOut == NULL) return; INT32 nFirstSample = 0; UINT32 *dest = (UINT32*)pDest; if (bAddToStream == 0) { memset(dest, 0, pLen * 4); // clear buffer to get rid of unwanted noise at end of short samples - dink } for (INT32 i = 0; i < nTotalSamples; i++) { sample_ptr = &samples[i]; if (sample_ptr->playing == 0) continue; INT32 playlen = pLen; INT32 loop = sample_ptr->loop; INT32 length = sample_ptr->length; INT32 position = sample_ptr->position; UINT32 *data = (UINT32*)sample_ptr->data; if (loop) { if (bAddToStream == 0 && nFirstSample == 0) { position *= 2; length *= 2; INT16 *dst = (INT16*)dest; INT16 *dat = (INT16*)data; for (INT32 j = 0; j < playlen; j++, position+=2, dst += 2) { INT32 nLeftSample = 0, nRightSample = 0; if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[(position + 0) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[(position + 0) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[(position + 1) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[(position + 1) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); dst[0] = nLeftSample; dst[1] = nRightSample; } } else { position *= 2; length *= 2; INT16 *dst = (INT16*)dest; INT16 *dat = (INT16*)data; for (INT32 j = 0; j < playlen; j++, position+=2, dst += 2) { INT32 nLeftSample = 0, nRightSample = 0; if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[(position + 0) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[(position + 0) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[(position + 1) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[(position + 1) % length] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } nLeftSample = BURN_SND_CLIP(nLeftSample + dst[0]); nRightSample = BURN_SND_CLIP(nRightSample + dst[1]); dst[0] = nLeftSample; dst[1] = nRightSample; } } } else { length = length - position; if (length <= 0) { if (loop == 0) { sample_ptr->playing = 0; continue; } } data += position; if (playlen > length) playlen = length; if (bAddToStream == 0 && nFirstSample == 0) { INT16 *dst = (INT16*)dest; INT16 *dat = (INT16*)data; for (INT32 j = 0; j < playlen; j++, dst +=2, dat+=2) { INT32 nLeftSample = 0, nRightSample = 0; if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[0] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[0] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[1] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[1] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); dst[0] = nLeftSample; dst[1] = nRightSample; } } else { INT16 *dst = (INT16*)dest; INT16 *dat = (INT16*)data; for (INT32 j = 0; j < playlen; j++, dst +=2, dat+=2) { INT32 nLeftSample = 0, nRightSample = 0; if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[0] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[0] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_1]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(dat[1] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } if ((sample_ptr->output_dir[BURN_SND_SAMPLE_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(dat[1] * sample_ptr->gain[BURN_SND_SAMPLE_ROUTE_2]); } nLeftSample = BURN_SND_CLIP(nLeftSample + dst[0]); nRightSample = BURN_SND_CLIP(nRightSample + dst[1]); dst[0] = nLeftSample; dst[1] = nRightSample; } } } sample_ptr->position += playlen; nFirstSample++; } }
void UPD7759Update(INT32 chip, INT16 *pSoundBuf, INT32 nLength) { #if defined FBA_DEBUG if (!DebugSnd_UPD7759Initted) bprintf(PRINT_ERROR, _T("UPD7759Update called without init\n")); if (chip > nNumChips) bprintf(PRINT_ERROR, _T("UPD7759Update called with invalid chip %x\n"), chip); #endif Chip = Chips[chip]; INT32 ClocksLeft = Chip->clocks_left; INT16 Sample = Chip->sample; UINT32 Step = Chip->step; UINT32 Pos = Chip->pos; /* loop until done */ if (Chip->state != STATE_IDLE) while (nLength != 0) { /* store the current sample */ INT32 nLeftSample = 0; INT32 nRightSample = 0; if ((Chip->output_dir & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)((Sample << 7) * Chip->volume); } if ((Chip->output_dir & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)((Sample << 7) * Chip->volume); } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); pSoundBuf[0] += nLeftSample; pSoundBuf[1] += nRightSample; pSoundBuf += 2; nLength--; /* advance by the number of clocks/output sample */ Pos += Step; /* handle clocks, but only in standalone mode */ while (Chip->rom && Pos >= FRAC_ONE) { INT32 ClocksThisTime = Pos >> FRAC_BITS; if (ClocksThisTime > ClocksLeft) ClocksThisTime = ClocksLeft; /* clock once */ Pos -= ClocksThisTime * FRAC_ONE; ClocksLeft -= ClocksThisTime; /* if we're out of clocks, time to handle the next state */ if (ClocksLeft == 0) { /* advance one state; if we hit idle, bail */ UPD7759AdvanceState(); if (Chip->state == STATE_IDLE) break; /* reimport the variables that we cached */ ClocksLeft = Chip->clocks_left; Sample = Chip->sample; } } } if (SlaveMode && ClocksLeft > 0) UPD7759SlaveModeUpdate(); Chip->clocks_left = ClocksLeft; Chip->pos = Pos; }
static void YM2610UpdateNormal(INT16* pSoundBuf, INT32 nSegmentEnd) { #if defined FBA_DEBUG if (!DebugSnd_YM2610Initted) bprintf(PRINT_ERROR, _T("YM2610UpdateNormal called without init\n")); #endif INT32 nSegmentLength = nSegmentEnd; if (nSegmentEnd < nAY8910Position) { nSegmentEnd = nAY8910Position; } if (nSegmentEnd < nYM2610Position) { nSegmentEnd = nYM2610Position; } if (nSegmentLength > nBurnSoundLen) { nSegmentLength = nBurnSoundLen; } YM2610Render(nSegmentEnd); AY8910Render(nSegmentEnd); pYM2610Buffer[0] = pBuffer + 4 + 0 * 4096; pYM2610Buffer[1] = pBuffer + 4 + 1 * 4096; pYM2610Buffer[2] = pBuffer + 4 + 2 * 4096; pYM2610Buffer[3] = pBuffer + 4 + 3 * 4096; pYM2610Buffer[4] = pBuffer + 4 + 4 * 4096; for (INT32 n = nFractionalPosition; n < nSegmentLength; n++) { INT32 nAYSample, nLeftSample = 0, nRightSample = 0; nAYSample = pYM2610Buffer[2][n]; nAYSample += pYM2610Buffer[3][n]; nAYSample += pYM2610Buffer[4][n]; if (bYM2610UseSeperateVolumes) { nLeftSample += (INT32)(nAYSample * YM2610LeftVolumes[BURN_SND_YM2610_AY8910_ROUTE]); nLeftSample += (INT32)(pYM2610Buffer[0][n] * YM2610LeftVolumes[BURN_SND_YM2610_YM2610_ROUTE_1]); nLeftSample += (INT32)(pYM2610Buffer[1][n] * YM2610LeftVolumes[BURN_SND_YM2610_YM2610_ROUTE_2]); nRightSample += (INT32)(nAYSample * YM2610RightVolumes[BURN_SND_YM2610_AY8910_ROUTE]); nRightSample += (INT32)(pYM2610Buffer[0][n] * YM2610RightVolumes[BURN_SND_YM2610_YM2610_ROUTE_1]); nRightSample += (INT32)(pYM2610Buffer[1][n] * YM2610RightVolumes[BURN_SND_YM2610_YM2610_ROUTE_2]); } else { if ((YM2610RouteDirs[BURN_SND_YM2610_AY8910_ROUTE] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(nAYSample * YM2610Volumes[BURN_SND_YM2610_AY8910_ROUTE]); } if ((YM2610RouteDirs[BURN_SND_YM2610_AY8910_ROUTE] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(nAYSample * YM2610Volumes[BURN_SND_YM2610_AY8910_ROUTE]); } if ((YM2610RouteDirs[BURN_SND_YM2610_YM2610_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(pYM2610Buffer[0][n] * YM2610Volumes[BURN_SND_YM2610_YM2610_ROUTE_1]); } if ((YM2610RouteDirs[BURN_SND_YM2610_YM2610_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(pYM2610Buffer[0][n] * YM2610Volumes[BURN_SND_YM2610_YM2610_ROUTE_1]); } if ((YM2610RouteDirs[BURN_SND_YM2610_YM2610_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)(pYM2610Buffer[1][n] * YM2610Volumes[BURN_SND_YM2610_YM2610_ROUTE_2]); } if ((YM2610RouteDirs[BURN_SND_YM2610_YM2610_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)(pYM2610Buffer[1][n] * YM2610Volumes[BURN_SND_YM2610_YM2610_ROUTE_2]); } } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); if (bYM2610AddSignal) { pSoundBuf[(n << 1) + 0] += nLeftSample; pSoundBuf[(n << 1) + 1] += nRightSample; } else { pSoundBuf[(n << 1) + 0] = nLeftSample; pSoundBuf[(n << 1) + 1] = nRightSample; } } nFractionalPosition = nSegmentLength; if (nSegmentEnd >= nBurnSoundLen) { INT32 nExtraSamples = nSegmentEnd - nBurnSoundLen; for (INT32 i = 0; i < nExtraSamples; i++) { pYM2610Buffer[0][i] = pYM2610Buffer[0][nBurnSoundLen + i]; pYM2610Buffer[1][i] = pYM2610Buffer[1][nBurnSoundLen + i]; pYM2610Buffer[2][i] = pYM2610Buffer[2][nBurnSoundLen + i]; pYM2610Buffer[3][i] = pYM2610Buffer[3][nBurnSoundLen + i]; pYM2610Buffer[4][i] = pYM2610Buffer[4][nBurnSoundLen + i]; } nFractionalPosition = 0; nYM2610Position = nExtraSamples; nAY8910Position = nExtraSamples; dTime += 100.0 / nBurnFPS; } }
static void YM2612UpdateResample(INT16* pSoundBuf, INT32 nSegmentEnd) { #if defined FBA_DEBUG if (!DebugSnd_YM2612Initted) bprintf(PRINT_ERROR, _T("YM2612UpdateResample called without init\n")); #endif INT32 nSegmentLength = nSegmentEnd; INT32 nSamplesNeeded = nSegmentEnd * nBurnYM2612SoundRate / nBurnSoundRate + 1; if (nSamplesNeeded < nYM2612Position) { nSamplesNeeded = nYM2612Position; } if (nSegmentLength > nBurnSoundLen) { nSegmentLength = nBurnSoundLen; } nSegmentLength <<= 1; YM2612Render(nSamplesNeeded); pYM2612Buffer[0] = pBuffer + 0 * 4096 + 4; pYM2612Buffer[1] = pBuffer + 1 * 4096 + 4; if (nNumChips > 1) { pYM2612Buffer[2] = pBuffer + 2 * 4096 + 4; pYM2612Buffer[3] = pBuffer + 3 * 4096 + 4; } for (INT32 i = (nFractionalPosition & 0xFFFF0000) >> 15; i < nSegmentLength; i += 2, nFractionalPosition += nSampleSize) { INT32 nLeftSample[4] = {0, 0, 0, 0}; INT32 nRightSample[4] = {0, 0, 0, 0}; INT32 nTotalLeftSample, nTotalRightSample; INTERPOLATE_ADD_SOUND_LEFT (BURN_SND_YM2612_YM2612_ROUTE_1, 0) INTERPOLATE_ADD_SOUND_RIGHT (BURN_SND_YM2612_YM2612_ROUTE_1, 0) INTERPOLATE_ADD_SOUND_LEFT (BURN_SND_YM2612_YM2612_ROUTE_2, 1) INTERPOLATE_ADD_SOUND_RIGHT (BURN_SND_YM2612_YM2612_ROUTE_2, 1) if (nNumChips > 1) { INTERPOLATE_ADD_SOUND_LEFT (2 + BURN_SND_YM2612_YM2612_ROUTE_1, 2) INTERPOLATE_ADD_SOUND_RIGHT (2 + BURN_SND_YM2612_YM2612_ROUTE_1, 2) INTERPOLATE_ADD_SOUND_LEFT (2 + BURN_SND_YM2612_YM2612_ROUTE_2, 3) INTERPOLATE_ADD_SOUND_RIGHT (2 + BURN_SND_YM2612_YM2612_ROUTE_2, 3) } nTotalLeftSample = INTERPOLATE4PS_16BIT((nFractionalPosition >> 4) & 0x0fff, nLeftSample[0], nLeftSample[1], nLeftSample[2], nLeftSample[3]); nTotalRightSample = INTERPOLATE4PS_16BIT((nFractionalPosition >> 4) & 0x0fff, nRightSample[0], nRightSample[1], nRightSample[2], nRightSample[3]); nTotalLeftSample = BURN_SND_CLIP(nTotalLeftSample); nTotalRightSample = BURN_SND_CLIP(nTotalRightSample); if (bYM2612AddSignal) { pSoundBuf[i + 0] = BURN_SND_CLIP(pSoundBuf[i + 0] + nTotalLeftSample); pSoundBuf[i + 1] = BURN_SND_CLIP(pSoundBuf[i + 1] + nTotalRightSample); } else { pSoundBuf[i + 0] = nTotalLeftSample; pSoundBuf[i + 1] = nTotalRightSample; } } if (nSegmentEnd >= nBurnSoundLen) { INT32 nExtraSamples = nSamplesNeeded - (nFractionalPosition >> 16); for (INT32 i = -4; i < nExtraSamples; i++) { pYM2612Buffer[0][i] = pYM2612Buffer[0][(nFractionalPosition >> 16) + i]; pYM2612Buffer[1][i] = pYM2612Buffer[1][(nFractionalPosition >> 16) + i]; if (nNumChips > 1) { pYM2612Buffer[2][i] = pYM2612Buffer[2][(nFractionalPosition >> 16) + i]; pYM2612Buffer[3][i] = pYM2612Buffer[3][(nFractionalPosition >> 16) + i]; } }
void saa1099Update(INT32 chip, INT16 *output, INT32 samples) { #if defined FBA_DEBUG if (!DebugSnd_SAA1099Initted) bprintf(PRINT_ERROR, _T("saa1099Update called without init\n")); if (chip > nNumChips) bprintf(PRINT_ERROR, _T("saa1099Update called with invalid chip %x\n"), chip); #endif saa1099_state *saa = &chips[chip]; INT32 j, ch; /* if the channels are disabled we're done */ if (!saa->all_ch_enable) { /* init output data */ memset (output, 0, samples * sizeof(INT16) * 2); return; } for (ch = 0; ch < 2; ch++) { switch (saa->noise_params[ch]) { case 0: saa->noise[ch].freq = 31250.0 * 2; break; case 1: saa->noise[ch].freq = 15625.0 * 2; break; case 2: saa->noise[ch].freq = 7812.5 * 2; break; case 3: saa->noise[ch].freq = saa->channels[ch * 3].freq; break; } } /* fill all data needed */ for( j = 0; j < samples; j++, output+=2) { INT32 output_l = 0, output_r = 0; /* for each channel */ for (ch = 0; ch < 6; ch++) { if (saa->channels[ch].freq == 0.0) saa->channels[ch].freq = (double)((2 * 15625) << saa->channels[ch].octave) / (511.0 - (double)saa->channels[ch].frequency); /* check the actual position in the square wave */ saa->channels[ch].counter -= saa->channels[ch].freq; while (saa->channels[ch].counter < 0) { /* calculate new frequency now after the half wave is updated */ saa->channels[ch].freq = (double)((2 * 15625) << saa->channels[ch].octave) / (511.0 - (double)saa->channels[ch].frequency); saa->channels[ch].counter += saa->sample_rate; saa->channels[ch].level ^= 1; /* eventually clock the envelope counters */ if (ch == 1 && saa->env_clock[0] == 0) saa1099_envelope(saa, 0); if (ch == 4 && saa->env_clock[1] == 0) saa1099_envelope(saa, 1); } /* if the noise is enabled */ if (saa->channels[ch].noise_enable) { /* if the noise level is high (noise 0: chan 0-2, noise 1: chan 3-5) */ if (saa->noise[ch/3].level & 1) { /* subtract to avoid overflows, also use only half amplitude */ output_l -= saa->channels[ch].amplitude[ LEFT] * saa->channels[ch].envelope[ LEFT] / 16 / 2; output_r -= saa->channels[ch].amplitude[RIGHT] * saa->channels[ch].envelope[RIGHT] / 16 / 2; } } /* if the square wave is enabled */ if (saa->channels[ch].freq_enable) { /* if the channel level is high */ if (saa->channels[ch].level & 1) { output_l += saa->channels[ch].amplitude[ LEFT] * saa->channels[ch].envelope[ LEFT] / 16; output_r += saa->channels[ch].amplitude[RIGHT] * saa->channels[ch].envelope[RIGHT] / 16; } } } for (ch = 0; ch < 2; ch++) { /* check the actual position in noise generator */ saa->noise[ch].counter -= saa->noise[ch].freq; while (saa->noise[ch].counter < 0) { saa->noise[ch].counter += saa->sample_rate; if( ((saa->noise[ch].level & 0x4000) == 0) == ((saa->noise[ch].level & 0x0040) == 0) ) saa->noise[ch].level = (saa->noise[ch].level << 1) | 1; else saa->noise[ch].level <<= 1; } } /* write sound data to the buffer */ INT32 nLeftSample = 0, nRightSample = 0; if ((saa->output_dir[BURN_SND_SAA1099_ROUTE_1] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)((output_l / 6) * saa->gain[BURN_SND_SAA1099_ROUTE_1]); } if ((saa->output_dir[BURN_SND_SAA1099_ROUTE_1] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)((output_l / 6) * saa->gain[BURN_SND_SAA1099_ROUTE_1]); } if ((saa->output_dir[BURN_SND_SAA1099_ROUTE_2] & BURN_SND_ROUTE_LEFT) == BURN_SND_ROUTE_LEFT) { nLeftSample += (INT32)((output_r / 6) * saa->gain[BURN_SND_SAA1099_ROUTE_2]); } if ((saa->output_dir[BURN_SND_SAA1099_ROUTE_2] & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) { nRightSample += (INT32)((output_r / 6) * saa->gain[BURN_SND_SAA1099_ROUTE_2]); } nLeftSample = BURN_SND_CLIP(nLeftSample); nRightSample = BURN_SND_CLIP(nRightSample); output[LEFT] = nLeftSample; output[RIGHT] = nRightSample; } }
static void UpdateStream(INT32 chip, INT32 length) { dac_info *ptr; /* char toto[100]; char *titi = &toto[0]; titi=itoa(length); FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)" ",4,60); FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)titi,4,60); */ if (lBuffer == NULL) { // delay buffer allocation for cases when fps is not 60 if((lBuffer = (INT16*)malloc(nBurnSoundLen * sizeof(INT16)))==NULL) { while(1); } memset (lBuffer, 0, nBurnSoundLen * sizeof(INT16)); } if (rBuffer == NULL) { // delay buffer allocation for cases when fps is not 60 if((rBuffer = (INT16*)malloc(nBurnSoundLen * sizeof(INT16)))==NULL) { while(1); } memset (rBuffer, 0, nBurnSoundLen * sizeof(INT16)); } ptr = &dac_table[chip]; if (ptr->Initialized == 0) return; if (length > nBurnSoundLen) length = nBurnSoundLen; length -= ptr->nCurrentPosition; if (length <= 0) return; INT16 *lbuf = lBuffer + ptr->nCurrentPosition; INT16 *rbuf = rBuffer + ptr->nCurrentPosition; // INT16 lOut = ((ptr->OutputDir & BURN_SND_ROUTE_LEFT ) == BURN_SND_ROUTE_LEFT ) ? ptr->Output : 0; // INT16 rOut = ((ptr->OutputDir & BURN_SND_ROUTE_RIGHT) == BURN_SND_ROUTE_RIGHT) ? ptr->Output : 0; INT16 lOut = ptr->Output; INT16 rOut = ptr->Output; ptr->nCurrentPosition += length; if (rOut && lOut) { // FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)"a",4,10); while (length--) { // *lbuf++ = *lbuf + lOut; // *rbuf++ = *rbuf + rOut; *lbuf++ = BURN_SND_CLIP(*lbuf + lOut); *rbuf++ = BURN_SND_CLIP(*rbuf + rOut); } // FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)"b",4,10); } else if (lOut) { // FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)"c",4,10); while (length--) *lbuf++ = BURN_SND_CLIP(*lbuf + lOut); // FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)"d",4,10); } else if (rOut) { // FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)"e",4,10); while (length--) *rbuf++ = BURN_SND_CLIP(*rbuf + rOut); // FNT_Print256_2bpp((volatile unsigned char *)0x25e20000,(unsigned char *)"f",4,10); } }