Removed unsupported PC speaker sound types

This commit is contained in:
tomcw 2016-09-07 22:20:15 +01:00
parent 034faa04b9
commit efcf06c285
6 changed files with 37 additions and 240 deletions

View File

@ -24,6 +24,7 @@ Changes:
. Unit tests added for 6502 and 65C02 opcodes
. Added -load-state <savestate.yaml> command line option
. New repo created with test save-state images: https://github.com/AppleWin/AppleWin-Test
. Remove unsupported PC speaker sound types
Fixes:
. [Bug #129] Tight loop page-flipping causing heavy CPU load (fixed by NTSC / cycle-accurate video emulation)

View File

@ -19,15 +19,8 @@ This option allows you to choose how sound is output for the
system.&nbsp;Your choices are:<br>
<ul>
<li>Disabled</li>
<li>PC Speaker (direct)</li>
<li>PC Speaker (translated)</li>
<li>Sound Card (recommended)</li>
</ul>
<strong>Volume Control:</strong><br>

View File

@ -510,7 +510,20 @@ void LoadConfiguration(void)
else
LoadConfigOldJoystick(JN_JOYSTICK1);
REGLOAD(TEXT("Sound Emulation") ,&soundtype);
DWORD dwSoundType;
REGLOAD(TEXT("Sound Emulation"), &dwSoundType);
switch (dwSoundType)
{
case REG_SOUNDTYPE_NONE:
case REG_SOUNDTYPE_DIRECT: // Not supported from 1.26
case REG_SOUNDTYPE_SMART: // Not supported from 1.26
default:
soundtype = SOUND_NONE;
break;
case REG_SOUNDTYPE_WAVE:
soundtype = SOUND_WAVE;
break;
}
char aySerialPortName[ CSuperSerialCard::SIZEOF_SERIALCHOICE_ITEM ];
if (RegLoadString( TEXT("Configuration"),

View File

@ -35,8 +35,6 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
CPageSound* CPageSound::ms_this = 0; // reinit'd in ctor
const TCHAR CPageSound::m_soundchoices[] = TEXT("Disabled\0")
TEXT("PC Speaker (direct)\0")
TEXT("PC Speaker (translated)\0")
TEXT("Sound Card\0");
@ -106,7 +104,7 @@ BOOL CPageSound::DlgProcInternal(HWND hWnd, UINT message, WPARAM wparam, LPARAM
case WM_INITDIALOG:
{
m_PropertySheetHelper.FillComboBox(hWnd,IDC_SOUNDTYPE,m_soundchoices,soundtype);
m_PropertySheetHelper.FillComboBox(hWnd,IDC_SOUNDTYPE, m_soundchoices, (int)soundtype);
SendDlgItemMessage(hWnd,IDC_SPKR_VOLUME,TBM_SETRANGE,1,MAKELONG(VOLUME_MIN,VOLUME_MAX));
SendDlgItemMessage(hWnd,IDC_SPKR_VOLUME,TBM_SETPAGESIZE,0,10);
@ -134,14 +132,15 @@ BOOL CPageSound::DlgProcInternal(HWND hWnd, UINT message, WPARAM wparam, LPARAM
void CPageSound::DlgOK(HWND hWnd)
{
const DWORD dwNewSoundType = (DWORD) SendDlgItemMessage(hWnd, IDC_SOUNDTYPE, CB_GETCURSEL, 0, 0);
const SoundType_e newSoundType = (SoundType_e) SendDlgItemMessage(hWnd, IDC_SOUNDTYPE, CB_GETCURSEL, 0, 0);
const DWORD dwSpkrVolume = SendDlgItemMessage(hWnd, IDC_SPKR_VOLUME, TBM_GETPOS, 0, 0);
const DWORD dwMBVolume = SendDlgItemMessage(hWnd, IDC_MB_VOLUME, TBM_GETPOS, 0, 0);
if (SpkrSetEmulationType(hWnd, dwNewSoundType))
if (SpkrSetEmulationType(hWnd, newSoundType))
{
REGSAVE(TEXT("Sound Emulation"), soundtype);
DWORD dwSoundType = (soundtype == SOUND_NONE) ? REG_SOUNDTYPE_NONE : REG_SOUNDTYPE_WAVE;
REGSAVE(TEXT("Sound Emulation"), dwSoundType);
}
// NB. Volume: 0=Loudest, VOLUME_MAX=Silence

View File

@ -70,7 +70,7 @@ static UINT g_nRemainderBufferSize; // Setup in SpkrInitialize()
static UINT g_nRemainderBufferIdx; // Setup in SpkrInitialize()
// Application-wide globals:
DWORD soundtype = SOUND_WAVE;
SoundType_e soundtype = SOUND_WAVE;
double g_fClksPerSpkrSample; // Setup in SetClksPerSpkrSample()
// Allow temporary quietening of speaker (8 bit DAC)
@ -85,14 +85,6 @@ static bool g_bSpkrToggleFlag = false;
static VOICE SpeakerVoice = {0};
static bool g_bSpkrAvailable = false;
// Globals (SOUND_DIRECT/SOUND_SMART)
static BOOL directio = 0;
static DWORD lastdelta[2] = {0,0};
static DWORD quietcycles = 0;
static DWORD soundeffect = 0;
static DWORD totaldelta = 0;
//-----------------------------------------------------------------------------
// Forward refs:
@ -119,63 +111,6 @@ static void DisplayBenchmarkResults ()
//=============================================================================
static void InternalBeep (DWORD frequency, DWORD duration)
{
#ifdef _X86_
if (directio)
if (duration) {
frequency = 1193180/frequency;
__asm {
push eax
mov al,0B6h
out 43h,al
mov eax,frequency
out 42h,al
mov al,ah
out 42h,al
in al,61h
or al,3
out 61h,al
pop eax
}
}
else
__asm {
push eax
in al,61h
and al,0FCh
out 61h,al
pop eax
}
else
#endif
Beep(frequency,duration);
}
//=============================================================================
static void InternalClick ()
{
#ifdef _X86_
if (directio)
__asm {
push eax
in al,0x61
xor al,2
out 0x61,al
pop eax
}
else {
#endif
Beep(37,(DWORD)-1);
Beep(0,0);
#ifdef _X86_
}
#endif
}
//=============================================================================
static void SetClksPerSpkrSample()
{
// // 23.191 clks for 44.1Khz (when 6502 CLK=1.0Mhz)
@ -224,10 +159,6 @@ void SpkrDestroy ()
g_pSpeakerBuffer = NULL;
g_pRemainderBuffer = NULL;
}
else if (soundtype == SOUND_DIRECT || soundtype == SOUND_SMART)
{
InternalBeep(0,0);
}
}
//=============================================================================
@ -240,8 +171,6 @@ void SpkrInitialize ()
switch(soundtype)
{
case SOUND_NONE: fprintf(g_fh, "(NONE)\n"); break;
case SOUND_DIRECT: fprintf(g_fh, "(DIRECT)\n"); break;
case SOUND_SMART: fprintf(g_fh, "(SMART)\n"); break;
case SOUND_WAVE: fprintf(g_fh, "(WAVE)\n"); break;
default: fprintf(g_fh, "(UNDEFINED!)\n"); break;
}
@ -264,37 +193,6 @@ void SpkrInitialize ()
g_pSpeakerBuffer = new short [SPKR_SAMPLE_RATE]; // Buffer can hold a max of 1 seconds worth of samples
}
//
// IF NONE IS, THEN DETERMINE WHETHER WE HAVE DIRECT ACCESS TO THE PC SPEAKER PORT
if (soundtype != SOUND_WAVE) // *** TO DO: Need way of determining if DirectX init failed ***
{
if (soundtype == SOUND_WAVE)
soundtype = SOUND_SMART;
#ifdef _X86_
_try
{
__asm {
in al,0x61
xor al,2
out 0x61,al
xor al,2
out 0x61,al
}
directio = 1;
}
_except (EXCEPTION_EXECUTE_HANDLER)
{
directio = 0;
}
#else
directio = 0;
#endif
if ((!directio) && (soundtype == SOUND_DIRECT))
soundtype = SOUND_SMART;
}
}
//=============================================================================
@ -324,25 +222,17 @@ void SpkrReset()
//=============================================================================
BOOL SpkrSetEmulationType (HWND window, DWORD newtype)
BOOL SpkrSetEmulationType (HWND window, SoundType_e newtype)
{
SpkrDestroy(); // GH#295: Destroy for all types (even SOUND_NONE)
soundtype = newtype;
if (soundtype != SOUND_NONE)
SpkrInitialize();
if (soundtype != newtype)
switch (newtype) {
case SOUND_DIRECT:
MessageBox(window,
TEXT("Direct emulation is not available because the ")
TEXT("operating system you are using does not allow ")
TEXT("direct control of the speaker."),
TEXT("Configuration"),
MB_ICONEXCLAMATION | MB_SETFOREGROUND);
return 0;
case SOUND_WAVE:
MessageBox(window,
TEXT("The emulator is unable to initialize a waveform ")
@ -356,6 +246,7 @@ BOOL SpkrSetEmulationType (HWND window, DWORD newtype)
return 0;
}
return 1;
}
@ -461,56 +352,6 @@ BYTE __stdcall SpkrToggle (WORD, WORD, BYTE, BYTE, ULONG nCyclesLeft)
g_nSpeakerData = SPKR_DATA_INIT;
}
}
else if (soundtype != SOUND_NONE)
{
// IF WE ARE CURRENTLY PLAYING A SOUND EFFECT OR ARE IN DIRECT
// EMULATION MODE, TOGGLE THE SPEAKER
if ((soundeffect > 2) || (soundtype == SOUND_DIRECT))
{
if (directio)
{
__asm
{
push eax
in al,0x61
xor al,2
out 0x61,al
pop eax
}
}
else
{
Beep(37,(DWORD)-1);
Beep(0,0);
}
}
// SAVE INFORMATION ABOUT THE FREQUENCY OF SPEAKER TOGGLING FOR POSSIBLE
// LATER USE BY SOUND AVERAGING
if (lastcyclenum)
{
toggles++;
//DWORD delta = cyclenum-lastcyclenum; // [TC: 14/09/2014] Looks broken, since 'cyclenum' is cycles executed in previous call to CpuExecute()
CpuCalcCycles(nCyclesLeft);
DWORD delta = (DWORD)g_nCumulativeCycles - lastcyclenum;
// DETERMINE WHETHER WE ARE PLAYING A SOUND EFFECT
if (directio &&
((delta < 250) ||
(lastdelta[0] && lastdelta[1] &&
(delta-lastdelta[0] > 250) && (lastdelta[0]-delta > 250) &&
(delta-lastdelta[1] > 250) && (lastdelta[1]-delta > 250))))
soundeffect = MIN(35,soundeffect+2);
lastdelta[1] = lastdelta[0];
lastdelta[0] = delta;
totaldelta += delta;
}
//lastcyclenum = cyclenum;
lastcyclenum = (DWORD)g_nCumulativeCycles;
}
return MemReadFloatingBus(nCyclesLeft);
}
@ -555,63 +396,6 @@ void SpkrUpdate (DWORD totalcycles)
memmove(g_pSpeakerBuffer, &g_pSpeakerBuffer[nSamplesUsed], g_nBufferIdx-nSamplesUsed); // FIXME-TC: _Size * 2
g_nBufferIdx -= nSamplesUsed;
}
else
{
// IF WE ARE NOT PLAYING A SOUND EFFECT, PERFORM FREQUENCY AVERAGING
static DWORD currenthertz = 0;
static BOOL lastfull = 0;
static DWORD lasttoggles = 0;
static DWORD lastval = 0;
if ((soundeffect > 2) || (soundtype == SOUND_DIRECT)) {
lastval = 0;
if (currenthertz && (soundeffect > 4)) {
InternalBeep(0,0);
currenthertz = 0;
}
}
else if (toggles && totaldelta) {
DWORD newval = 1000000*toggles/totaldelta;
if (lastval && lastfull &&
(newval-currenthertz > 50) &&
(currenthertz-newval > 50)) {
InternalBeep(newval,(DWORD)-1);
currenthertz = newval;
lasttoggles = 0;
}
lastfull = (totaldelta+((totaldelta/toggles) << 1) >= totalcycles);
lasttoggles += toggles;
lastval = newval;
}
else if (currenthertz) {
InternalBeep(0,0);
currenthertz = 0;
lastfull = 0;
lasttoggles = 0;
lastval = 0;
}
else if (lastval) {
currenthertz = (lasttoggles > 4) ? lastval : 0;
if (currenthertz)
InternalBeep(lastval,(DWORD)-1);
else
InternalClick();
lastfull = 0;
lasttoggles = 0;
lastval = 0;
}
// RESET THE FREQUENCY GATHERING VARIABLES
lastcyclenum = 0;
lastdelta[0] = 0;
lastdelta[1] = 0;
quietcycles = toggles ? 0 : (quietcycles+totalcycles);
toggles = 0;
totaldelta = 0;
if (soundeffect)
soundeffect--;
}
}
// Called from SoundCore_TimerFunc() for FADE_OUT

View File

@ -1,11 +1,18 @@
#pragma once
#define SOUND_NONE 0
#define SOUND_DIRECT 1
#define SOUND_SMART 2
#define SOUND_WAVE 3
// Registry soundtype:
#define REG_SOUNDTYPE_NONE 0
#define REG_SOUNDTYPE_DIRECT 1 // Not supported from 1.26
#define REG_SOUNDTYPE_SMART 2 // Not supported from 1.26
#define REG_SOUNDTYPE_WAVE 3
extern DWORD soundtype;
enum SoundType_e
{
SOUND_NONE = 0,
SOUND_WAVE
};
extern SoundType_e soundtype;
extern double g_fClksPerSpkrSample;
extern bool g_bQuieterSpeaker;
extern short g_nSpeakerData;
@ -14,7 +21,7 @@ void SpkrDestroy ();
void SpkrInitialize ();
void SpkrReinitialize ();
void SpkrReset();
BOOL SpkrSetEmulationType (HWND,DWORD);
BOOL SpkrSetEmulationType (HWND window, SoundType_e newSoundType);
void SpkrUpdate (DWORD);
void SpkrUpdate_Timer();
void Spkr_SetErrorInc(const int nErrorInc);