mb8877.cpp
ym2203.cpp
- wav_sounder.cpp
+
prnfile.cpp
datarec.cpp
disk.cpp
io.cpp
memory.cpp
prnfile.cpp
-
- wav_sounder.cpp
)
set(BUILD_SHARED_LIBS OFF)
memory.cpp
datarec.cpp
prnfile.cpp
-
- wav_sounder.cpp
)
set(BUILD_SHARED_LIBS OFF)
io.cpp
memory.cpp
prnfile.cpp
-
- wav_sounder.cpp
)
+
set(BUILD_SHARED_LIBS OFF)
set(BUILD_PC8001SR OFF CACHE BOOL "Build for PC8001SR")
memory.cpp
prnfile.cpp
mz1p17.cpp
-
- wav_sounder.cpp
)
set(BUILD_X1 OFF CACHE BOOL "Build for X1")
#endif
}
+
+
void cur_time_t::increment()
{
if(++second >= 60) {
}
trigger = signal;
}
+#if defined(USE_SOUND_FILES)
+ else if((id >= SIG_SOUNDER_MUTE) && (id < (SIG_SOUNDER_MUTE + DATAREC_SNDFILE_END))) {
+ snd_mute[id - SIG_SOUNDER_MUTE] = signal;
+ } else if((id >= SIG_SOUNDER_RELOAD) && (id < (SIG_SOUNDER_RELOAD + DATAREC_SNDFILE_END))) {
+ reload_sound_data(id - SIG_SOUNDER_RELOAD);
+ } else if((id >= SIG_SOUNDER_ADD) && (id < (SIG_SOUNDER_ADD + DATAREC_SNDFILE_END))) {
+ add_sound(id - SIG_SOUNDER_ADD);
+ }
+#endif
}
void DATAREC::event_frame()
void DATAREC::set_remote(bool value)
{
if(remote != value) {
+ if(value) {
+ add_sound(DATAREC_SNDFILE_RELAY_ON);
+ } else {
+ add_sound(DATAREC_SNDFILE_RELAY_OFF);
+ }
remote = value;
update_event();
}
free(bytes);
return samples_pos;
}
+#if defined(USE_SOUND_FILES)
+void DATAREC::add_sound(int type)
+{
+ int *p;
+ if((type < 0) || (type >= DATAREC_SNDFILE_END)) return;
+ p = snd_mix_tbls[type];
+ for(int i = 0; i < DATAREC_SND_TBL_MAX; i++) {
+ if(p[i] < 0) {
+ p[i] = 0;
+ break;
+ }
+ }
+}
+
+bool DATAREC::load_sound_data(int type, const _TCHAR *pathname)
+{
+ if((type < 0) || (type >= DATAREC_SNDFILE_END)) return false;
+ int16_t *data = NULL;
+ int dst_size = 0;
+ int id = (this_device_id << 8) + type;
+ const _TCHAR *sp;
+ sp = create_local_path(pathname);
+ emu->load_sound_file(id, sp, &data, &dst_size);
+ if((dst_size <= 0) || (data == NULL)) { // Failed
+ this->out_debug_log("ID=%d : Failed to load SOUND FILE for TYPE=%d:%s", id, type ,pathname);
+ snd_datas[type] = NULL;
+ snd_samples[type] = 0;
+ return false;
+ } else {
+ int utl_size = dst_size * 2 * sizeof(int16_t);
+ int alloc_size = utl_size + 64;
+ snd_datas[type] = (int16_t *)malloc(alloc_size);
+ memcpy(snd_datas[type], data, utl_size);
+ strncpy(snd_file_names[type], pathname, 511);
+ snd_samples[type] = dst_size;
+ this->out_debug_log("ID=%d : Success to load SOUND FILE for TYPE %d:%s",
+ id, type , pathname);
+ }
+ return true;
+}
+
+void DATAREC::release_sound_data(int type)
+{
+ if((type < 0) || (type >= DATAREC_SNDFILE_END)) return;
+ if(snd_datas[type] != NULL) free(snd_datas[type]);
+ snd_datas[type] = NULL;
+ memset(snd_file_names[type], 0x00, sizeof(_TCHAR) * 512);
+}
+
+bool DATAREC::reload_sound_data(int type)
+{
+ if((type < 0) || (type >= DATAREC_SNDFILE_END)) return false;
+ if(snd_datas[type] != NULL) free(snd_datas[type]);
+ _TCHAR *p = snd_file_names[type];
+ _TCHAR tmps[512];
+ strncpy(tmps, p, 511);
+ return load_sound_data(type, tmps);
+}
+void DATAREC::mix_sndfiles(int ch, int32_t *dst, int cnt, int16_t *src, int samples)
+{
+ int ptr, pp;
+ int i, j, k;
+ int32_t data[2];
+ int32_t *dst_tmp;
+ int *table = snd_mix_tbls[ch];
+ for(i=0; i < DATAREC_SND_TBL_MAX; i++) {
+ ptr = table[i];
+ if(ptr >= 0) {
+ if(ptr < samples) {
+ if(!snd_mute[ch]) {
+ pp = ptr << 1;
+ dst_tmp = dst;
+ k = 0;
+ for(j = 0; j < cnt; j++) {
+ if(ptr >= samples) {
+ break;
+ }
+ data[0] = (int32_t)src[pp + 0];
+ data[1] = (int32_t)src[pp + 1];
+ dst_tmp[k + 0] += apply_volume((int32_t)data[0], snd_level_l[ch]);
+ dst_tmp[k + 1] += apply_volume((int32_t)data[1], snd_level_r[ch]);
+ k += 2;
+ pp += 2;
+ ptr++;
+ }
+ } else {
+ ptr += cnt;
+ }
+ }
+ }
+ if(ptr >= samples) {
+ table[i] = -1;
+ } else {
+ table[i] = ptr;
+ }
+ }
+}
+#endif
void DATAREC::mix(int32_t* buffer, int cnt)
{
int32_t* buffer_tmp = buffer;
}
}
#endif
+#if defined(USE_SOUND_FILES)
+ for(int j = 0; j < DATAREC_SNDFILE_END; j++) {
+ if(snd_datas[j] != NULL) mix_sndfiles(j, buffer, cnt,
+ snd_datas[j], snd_samples[j]);
+ }
+#endif
}
void DATAREC::set_volume(int ch, int decibel_l, int decibel_r)
sound_volume_r = decibel_to_volume(decibel_r);
#endif
}
+#if defined(USE_SOUND_FILES)
+ else if((ch >= 2) && (ch < (DATAREC_SNDFILE_END + 2))) {
+ snd_level_l[ch - 2] = decibel_to_volume(decibel_l);
+ snd_level_r[ch - 2] = decibel_to_volume(decibel_r);
+ }
+#endif
}
double DATAREC::get_ave_hi_freq()
return ave_hi_freq;
}
-#define STATE_VERSION 6
+#define STATE_VERSION 7
void DATAREC::save_state(FILEIO* state_fio)
{
state_fio->FputUint32(pcm_prev_clock);
state_fio->FputInt32(pcm_positive_clocks);
state_fio->FputInt32(pcm_negative_clocks);
+#if defined(USE_SOUND_FILES)
+ for(int j = 0; j < DATAREC_SNDFILE_END; j++) {
+ state_fio->Fwrite(snd_file_names[j], sizeof(_TCHAR) * 512, 1);
+ state_fio->Fwrite(snd_mix_tbls[j], sizeof(int) * DATAREC_SND_TBL_MAX, 1);
+ state_fio->FputInt32(snd_samples[j]);
+ state_fio->FputInt32(snd_level_l[j]);
+ state_fio->FputInt32(snd_level_r[j]);
+ }
+#endif
}
bool DATAREC::load_state(FILEIO* state_fio)
#ifdef DATAREC_SOUND
sound_last_vol_l = sound_last_vol_r = 0;
#endif
+#if defined(USE_SOUND_FILES)
+ for(int j = 0; j < DATAREC_SNDFILE_END; j++) {
+ if(snd_datas[j] != NULL) free(snd_datas[j]);
+ state_fio->Fread(snd_file_names[j], sizeof(_TCHAR) * 512, 1);
+ state_fio->Fread(snd_mix_tbls[j], sizeof(int) * DATAREC_SND_TBL_MAX, 1);
+ snd_samples[j] = state_fio->FgetInt32();
+ snd_level_l[j] = state_fio->FgetInt32();
+ snd_level_r[j] = state_fio->FgetInt32();
+ if(strlen(snd_file_names[j]) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_file_names[j], 511);
+ load_sound_data(j, (const _TCHAR *)tmps);
+ }
+ }
+#endif
return true;
}
#define SIG_DATAREC_REMOTE 1
#define SIG_DATAREC_TRIG 2
+#if defined(USE_SOUND_FILES)
+#ifndef SIG_SOUNDER_MUTE
+#define SIG_SOUNDER_MUTE (65536 + 0)
+#endif
+#ifndef SIG_SOUNDER_RELOAD
+#define SIG_SOUNDER_RELOAD (65536 + 32)
+#endif
+#ifndef SIG_SOUNDER_ADD
+#define SIG_SOUNDER_ADD (65536 + 64)
+#endif
+enum {
+ DATAREC_SNDFILE_RELAY_ON = 0,
+ DATAREC_SNDFILE_RELAY_OFF,
+ DATAREC_SNDFILE_PLAY,
+ DATAREC_SNDFILE_STOP,
+ DATAREC_SNDFILE_EJECT,
+ DATAREC_SNDFILE_FF,
+ DATAREC_SNDFILE_REW,
+ DATAREC_SNDFILE_END,
+};
+#define DATAREC_SND_TBL_MAX 256
+#endif
+
class FILEIO;
class DATAREC : public DEVICE
int sound_buffer_length;
int16_t *sound_buffer, sound_sample;
#endif
+#if defined(USE_SOUND_FILES)
+ _TCHAR snd_file_names[DATAREC_SNDFILE_END][512];
+ int snd_mix_tbls[DATAREC_SNDFILE_END][DATAREC_SND_TBL_MAX];
+ int16_t *snd_datas[DATAREC_SNDFILE_END];
+ int snd_samples[DATAREC_SNDFILE_END];
+ bool snd_mute[DATAREC_SNDFILE_END];
+ int snd_level_l[DATAREC_SNDFILE_END], snd_level_r[DATAREC_SNDFILE_END];
+
+ virtual void mix_sndfiles(int ch, int32_t *dst, int cnt, int16_t *src, int samples);
+ void add_sound(int type);
+#endif
+
bool is_wav, is_tap;
double ave_hi_freq;
#ifdef DATAREC_SOUND
sound_volume_l = sound_volume_r = 1024;
#endif
+#if defined(USE_SOUND_FILES)
+ for(int j = 0; j < DATAREC_SNDFILE_END; j++) {
+ for(int i = 0; i < DATAREC_SND_TBL_MAX; i++) {
+ snd_mix_tbls[j][i] = -1;
+ }
+ snd_datas[j] = NULL;
+ snd_samples[j] = 0;
+ snd_mute[j] = false;
+ snd_level_l[j] = snd_level_r[j] = decibel_to_volume(0);
+ memset(snd_file_names[j], 0x00, sizeof(_TCHAR) * 512);
+ }
+#endif
set_device_name(_T("DATA RECORDER"));
}
~DATAREC() {}
}
void event_frame();
void event_callback(int event_id, int err);
+#if defined(USE_SOUND_FILES)
+ // Around SOUND. 20161004 K.O
+ bool load_sound_data(int type, const _TCHAR *pathname);
+ void release_sound_data(int type);
+ bool reload_sound_data(int type);
+
+#endif
void mix(int32_t* buffer, int cnt);
void set_volume(int ch, int decibel_l, int decibel_r);
void save_state(FILEIO* state_fio);
#define DISK_BUFFER_SIZE 0x380000 // 3.5MB
#define TRACK_BUFFER_SIZE 0x080000 // 0.5MB
-
class FILEIO;
class DISK
// solid image decoder (fdi/tfd/2d/img/sf7)
bool solid_to_d88(FILEIO *fio, int type, int ncyl, int nside, int nsec, int size, bool mfm);
-
public:
#ifndef _ANY2D88
DISK(EMU* parent_emu) : emu(parent_emu)
#define SIG_DUMMYDEVICE_BIT1 1
#define SIG_DUMMYDEVICE_BIT2 2
#endif
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-#endif
#include "./fm7_mainio.h"
#include "./fm7_mainmem.h"
#include "./fm7_display.h"
#else
led_terminate = new DEVICE(this, emu);
#endif
-#if defined(USE_SOUND_FILES)
- fdd_seek = new WAV_SOUNDER(this, emu);
- cmt_relay_on = new WAV_SOUNDER(this, emu);
- cmt_relay_off = new WAV_SOUNDER(this, emu);
-#endif
#if defined(_USE_QT)
event->set_device_name(_T("EVENT"));
dummy->set_device_name(_T("1st Dummy"));
# endif
event->set_context_sound(drec);
#if defined(USE_SOUND_FILES)
- fdd_seek->load_data(_T("FDDSEEK.WAV"));
- event->set_context_sound(fdd_seek);
-
- cmt_relay_on->load_data(_T("RELAY_ON.WAV"));
- cmt_relay_off->load_data(_T("RELAYOFF.WAV"));
- event->set_context_sound(cmt_relay_on);
- event->set_context_sound(cmt_relay_off);
+ if(fdc->load_sound_data(MB8877_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(fdc);
+ }
+ drec->load_sound_data(DATAREC_SNDFILE_RELAY_ON, _T("RELAY_ON.WAV"));
+ drec->load_sound_data(DATAREC_SNDFILE_RELAY_OFF, _T("RELAYOFF.WAV"));
#endif
# if defined(_FM77AV_VARIANTS)
event->set_context_sound(keyboard_beep);
fdc->set_context_irq(mainio, FM7_MAINIO_FDC_IRQ, 0x1);
fdc->set_context_drq(mainio, FM7_MAINIO_FDC_DRQ, 0x1);
mainio->set_context_fdc(fdc);
-#if defined(USE_SOUND_FILES)
- fdc->set_context_seek(fdd_seek);
- mainio->set_context_relay_on(cmt_relay_on);
- mainio->set_context_relay_off(cmt_relay_off);
-#endif
#if defined(_FM8) || (_FM7) || (_FMNEW7)
}
#endif
#endif
#if defined(USE_SOUND_FILES)
else if(ch-- == 0) {
- fdd_seek->set_volume(0, decibel_l, decibel_r);
+ fdc->set_volume(0, decibel_l, decibel_r);
} else if(ch-- == 0) {
- cmt_relay_on->set_volume(0, decibel_l, decibel_r);
- cmt_relay_off->set_volume(0, decibel_l, decibel_r);
+ for(int i = 0; i < DATAREC_SNDFILE_END; i++) {
+ drec->set_volume(i + 2, decibel_l, decibel_r);
+ }
}
#endif
}
#if WITH_Z80
class Z80;
#endif
-#if defined(USE_SOUND_FILES)
-class WAV_SOUNDER;
-#endif
class VM {
protected:
EMU* emu;
#ifdef CAPABLE_KANJI_CLASS2
KANJIROM *kanjiclass2;
#endif
-#if defined(USE_SOUND_FILES)
- WAV_SOUNDER *fdd_seek;
- WAV_SOUNDER *cmt_relay_on;
- WAV_SOUNDER *cmt_relay_off;
-#endif
bool connect_320kfdc;
bool connect_1Mfdc;
public:
#if defined(_FM8)
#include "bubblecasette.h"
#endif
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-#endif
FM7_MAINIO::FM7_MAINIO(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu)
{
bubble_casette[0] = NULL;
bubble_casette[1] = NULL;
#endif
-#if defined(USE_SOUND_FILES)
- dev_relay_sound_on = NULL;
- dev_relay_sound_off = NULL;
-#endif
// FD00
clock_fast = true;
lpt_strobe = false; // bit6
// FD00
drec->write_signal(SIG_DATAREC_MIC, 0x00, 0x01);
drec->write_signal(SIG_DATAREC_REMOTE, 0x00, 0x02);
-#if defined(USE_SOUND_FILES)
- if(drec_flag != 0x00) {
- if(dev_relay_sound_off != NULL) {
- dev_relay_sound_off->write_signal(SIG_WAV_SOUNDER_ADD, 0x01, 0x01);
- }
- }
-#endif
drec_flag = 0x00;
reset_fdc();
reset_sound();
uint8_t drec_flag_b = data & 0x02;
drec->write_signal(SIG_DATAREC_REMOTE, drec_flag_b, 0x02);
-#if defined(USE_SOUND_FILES)
- if(drec_flag != drec_flag_b) {
- if(drec_flag_b == 0x02) {
- if(dev_relay_sound_on != NULL) {
- dev_relay_sound_on->write_signal(SIG_WAV_SOUNDER_ADD, 0x01, 0x01);
- }
- } else {
- if(dev_relay_sound_off != NULL) {
- dev_relay_sound_off->write_signal(SIG_WAV_SOUNDER_ADD, 0x01, 0x01);
- }
- }
- }
-#endif
drec_flag = drec_flag_b;
lpt_slctin = ((data & 0x80) == 0);
#if defined(_FM8)
BUBBLECASETTE *bubble_casette[2];
#endif
-#if defined(USE_SOUND_FILES)
- DEVICE *dev_relay_sound_on;
- DEVICE *dev_relay_sound_off;
-#endif
public:
FM7_MAINIO(VM* parent_vm, EMU* parent_emu);
~FM7_MAINIO();
void set_context_printer_select(DEVICE *p, int id, uint32_t mask) {
register_output_signal(&printer_select_bus, p, id, mask);
}
-#if defined(USE_SOUND_FILES)
- void set_context_relay_on(DEVICE *p) {
- dev_relay_sound_on = p;
- }
- void set_context_relay_off(DEVICE *p) {
- dev_relay_sound_off = p;
- }
-#endif
#if defined(_FM8)
void set_context_bubble(BUBBLECASETTE *p, int drive) {
if(drive > 2) return;
#include "mb8877.h"
#include "disk.h"
-#if defined(USE_SOUND_FILES)
-#include "wav_sounder.h"
-#endif
+
#define FDC_ST_BUSY 0x01 // busy
#define FDC_ST_INDEX 0x02 // index hole
#define FDC_ST_DRQ 0x02 // data request
} else if(id == SIG_MB8877_MOTOR) {
motor_on = ((data & mask) != 0);
}
+#if defined(USE_SOUND_FILES)
+ else if((id >= SIG_SOUNDER_MUTE) && (id < (SIG_SOUNDER_MUTE + 2))) {
+ snd_mute = ((data & mask) != 0);
+ } else if((id >= SIG_SOUNDER_RELOAD) && (id < (SIG_SOUNDER_RELOAD + 2))) {
+ reload_sound_data(id - SIG_SOUNDER_RELOAD);
+ }
+#endif
}
uint32_t MB8877::read_signal(int ch)
if(seektrk > fdc[drvreg].track) {
fdc[drvreg].track++;
#if defined(USE_SOUND_FILES)
- if(d_seek_sound != NULL) d_seek_sound->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ add_sound(MB8877_SND_TYPE_SEEK);
#endif
} else if(seektrk < fdc[drvreg].track) {
fdc[drvreg].track--;
#if defined(USE_SOUND_FILES)
- if(d_seek_sound != NULL) d_seek_sound->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ add_sound(MB8877_SND_TYPE_SEEK);
#endif
}
if((cmdreg & 0x10) || ((cmdreg & 0xf0) == 0)) {
#endif
}
-#define STATE_VERSION 5
+// Set sound data.
+// TYPE=
+// 0: FDD SEEK
+// 1: HEAD ENGAGE (Optional?)
+#if defined(USE_SOUND_FILES)
+void MB8877::add_sound(int type)
+{
+ int *p;
+ if(type == MB8877_SND_TYPE_SEEK) {
+ p = snd_seek_mix_tbl;
+ } else if(type == MB8877_SND_TYPE_HEAD) {
+ p = snd_head_mix_tbl;
+ } else {
+ return;
+ }
+ for(int i = 0; i < MB8877_SND_TBL_MAX; i++) {
+ if(p[i] < 0) {
+ p[i] = 0;
+ break;
+ }
+ }
+}
+
+bool MB8877::load_sound_data(int type, const _TCHAR *pathname)
+{
+ if((type < 0) || (type > 1)) return false;
+ int16_t *data = NULL;
+ int dst_size = 0;
+ int id = (this_device_id << 8) + type;
+ const _TCHAR *sp;
+ sp = create_local_path(pathname);
+ emu->load_sound_file(id, sp, &data, &dst_size);
+ if((dst_size <= 0) || (data == NULL)) { // Failed
+ this->out_debug_log("ID=%d : Failed to load SOUND FILE for %s:%s", id, (type == 0) ? _T("SEEK") : _T("HEAD") ,pathname);
+ return false;
+ } else {
+ int utl_size = dst_size * 2 * sizeof(int16_t);
+ int alloc_size = utl_size + 64;
+ switch(type) {
+ case MB8877_SND_TYPE_SEEK: // SEEK
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_seek_data, data, utl_size);
+ strncpy(snd_seek_name, pathname, 511);
+ snd_seek_samples_size = dst_size;
+ break;
+ case MB8877_SND_TYPE_HEAD: // HEAD
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_head_data, data, utl_size);
+ strncpy(snd_head_name, pathname, 511);
+ snd_head_samples_size = dst_size;
+ break;
+ default:
+ this->out_debug_log("ID=%d : Illegal type (%d): 0 (SEEK SOUND) or 1 (HEAD SOUND) is available.",
+ id, type);
+ return false;
+ }
+ this->out_debug_log("ID=%d : Success to load SOUND FILE for %s:%s",
+ id, (type == 0) ? _T("SEEK") : _T("HEAD") ,
+ pathname);
+ }
+ return true;
+}
+
+void MB8877::release_sound_data(int type)
+{
+ switch(type) {
+ case MB8877_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ snd_seek_data = NULL;
+ break;
+ case MB8877_SND_TYPE_HEAD: // HEAD
+ if(snd_head_data != NULL) free(snd_head_data);
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
+ snd_head_data = NULL;
+ break;
+ default:
+ break;
+ }
+}
+
+bool MB8877::reload_sound_data(int type)
+{
+ switch(type) {
+ case MB8877_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ case MB8877_SND_TYPE_HEAD:
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ default:
+ return false;
+ break;
+ }
+ _TCHAR *p = (type == MB8877_SND_TYPE_SEEK) ? snd_seek_name : snd_head_name;
+ _TCHAR tmps[512];
+ strncpy(tmps, p, 511);
+ return load_sound_data(type, tmps);
+}
+
+void MB8877::mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples)
+{
+ int ptr, pp;
+ int i, j, k;
+ int32_t data[2];
+ int32_t *dst_tmp;
+ for(i=0; i < MB8877_SND_TBL_MAX; i++) {
+ ptr = table[i];
+ if(ptr >= 0) {
+ if(ptr < samples) {
+ if(!snd_mute) {
+ pp = ptr << 1;
+ dst_tmp = dst;
+ k = 0;
+ for(j = 0; j < count; j++) {
+ if(ptr >= samples) {
+ break;
+ }
+ data[0] = (int32_t)src[pp + 0];
+ data[1] = (int32_t)src[pp + 1];
+ dst_tmp[k + 0] += apply_volume((int32_t)data[0], snd_level_l);
+ dst_tmp[k + 1] += apply_volume((int32_t)data[1], snd_level_r);
+ k += 2;
+ pp += 2;
+ ptr++;
+ }
+ } else {
+ ptr += count;
+ }
+ }
+ if(ptr >= samples) {
+ table[i] = -1;
+ } else {
+ table[i] = ptr;
+ }
+ }
+ }
+}
+
+void MB8877::mix(int32_t *buffer, int cnt)
+{
+ if(snd_seek_data != NULL) mix_main(buffer, cnt, snd_seek_data, snd_seek_mix_tbl, snd_seek_samples_size);
+ if(snd_head_data != NULL) mix_main(buffer, cnt, snd_head_data, snd_head_mix_tbl, snd_head_samples_size);
+}
+
+void MB8877::set_volume(int ch, int decibel_l, int decibel_r)
+{
+ snd_level_l = decibel_to_volume(decibel_l);
+ snd_level_r = decibel_to_volume(decibel_r);
+}
+#endif
+
+#define STATE_VERSION 7
void MB8877::save_state(FILEIO* state_fio)
{
state_fio->FputBool(drive_sel);
state_fio->FputUint32(prev_drq_clock);
state_fio->FputUint32(seekend_clock);
+#if defined(USE_SOUND_FILES)
+ state_fio->Fwrite(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fwrite(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < MB8877_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_seek_mix_tbl[i]);
+ }
+ for(int i = 0; i < MB8877_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_head_mix_tbl[i]);
+ }
+ state_fio->FputBool(snd_mute);
+ state_fio->FputInt32(snd_level_l);
+ state_fio->FputInt32(snd_level_r);
+#endif
}
bool MB8877::load_state(FILEIO* state_fio)
drive_sel = state_fio->FgetBool();
prev_drq_clock = state_fio->FgetUint32();
seekend_clock = state_fio->FgetUint32();
+#if defined(USE_SOUND_FILES)
+ state_fio->Fread(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fread(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < MB8877_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ for(int i = 0; i < MB8877_SND_TBL_MAX; i++) {
+ snd_head_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ snd_mute = state_fio->FgetBool();
+ snd_level_l = state_fio->FgetInt32();
+ snd_level_r = state_fio->FgetInt32();
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ if(snd_head_data != NULL) free(snd_head_data);
+ if(strlen(snd_seek_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_seek_name, 511);
+ load_sound_data(MB8877_SND_TYPE_SEEK, (const _TCHAR *)tmps);
+ }
+ if(strlen(snd_head_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_head_name, 511);
+ load_sound_data(MB8877_SND_TYPE_HEAD, (const _TCHAR *)tmps);
+ }
+#endif
return true;
}
#include "../emu.h"
#include "device.h"
+
#define SIG_MB8877_DRIVEREG 0
#define SIG_MB8877_SIDEREG 1
#define SIG_MB8877_MOTOR 2
+#if defined(USE_SOUND_FILES)
+#define MB8877_SND_TBL_MAX 256
+#ifndef SIG_SOUNDER_MUTE
+#define SIG_SOUNDER_MUTE (65536 + 0)
+#endif
+#ifndef SIG_SOUNDER_RELOAD
+#define SIG_SOUNDER_RELOAD (65536 + 32)
+#endif
+#ifndef SIG_SOUNDER_ADD
+#define SIG_SOUNDER_ADD (65536 + 64)
+#endif
+
+#define MB8877_SND_TYPE_SEEK 0
+#define MB8877_SND_TYPE_HEAD 1
+#endif
class DISK;
#if defined(USE_SOUND_FILES)
class WAV_SOUNDER;
uint32_t prev_clock;
} fdc[MAX_DRIVE];
DISK* disk[MAX_DRIVE];
-#if defined(USE_SOUND_FILES)
- DEVICE *d_seek_sound;
-#endif
// registor
uint8_t status, status_tmp;
uint8_t cmdreg, cmdreg_tmp;
void set_irq(bool val);
void set_drq(bool val);
+#if defined(USE_SOUND_FILES)
+protected:
+ _TCHAR snd_seek_name[512];
+ _TCHAR snd_head_name[512];
+ int snd_seek_mix_tbl[MB8877_SND_TBL_MAX];
+ int snd_head_mix_tbl[MB8877_SND_TBL_MAX];
+ int16_t *snd_seek_data; // Read only
+ int16_t *snd_head_data; // Read only
+ int snd_seek_samples_size;
+ int snd_head_samples_size;
+ bool snd_mute;
+ int snd_level_l, snd_level_r;
+ virtual void mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples);
+ void add_sound(int type);
+#endif
public:
MB8877(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu)
{
initialize_output_signals(&outputs_drq);
motor_on = false;
#if defined(USE_SOUND_FILES)
- d_seek_sound = NULL;
+ for(int i = 0; i < MB8877_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = -1;
+ snd_head_mix_tbl[i] = -1;
+ }
+ snd_seek_data = snd_head_data = NULL;
+ snd_seek_samples_size = snd_head_samples_size = 0;
+ snd_mute = false;
+ snd_level_l = snd_level_r = decibel_to_volume(0);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
#endif
set_device_name(_T("MB8877 FDC"));
}
{
register_output_signal(&outputs_drq, device, id, mask);
}
-#if defined(USE_SOUND_FILES)
- void set_context_seek(DEVICE* device)
- {
- d_seek_sound = device;
- }
-#endif
DISK* get_disk_handler(int drv)
{
return disk[drv];
}
+#if defined(USE_SOUND_FILES)
+ // Around SOUND. 20161004 K.O
+ bool load_sound_data(int type, const _TCHAR *pathname);
+ void release_sound_data(int type);
+ bool reload_sound_data(int type);
+
+ void mix(int32_t *buffer, int cnt);
+ void set_volume(int ch, int decibel_l, int decibel_r);
+#endif
void open_disk(int drv, const _TCHAR* file_path, int bank);
void close_disk(int drv);
bool is_disk_inserted(int drv);
#include "floppy.h"
#include "../disk.h"
#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-
#define EVENT_SEEK_SOUND 2
#endif
} else {
seek_event_id[drvno] = -1;
}
- if(d_seek_sound != NULL) d_seek_sound->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ add_sound(FLOPPY_SND_TYPE_SEEK);
}
#endif
}
return false;
}
+#if defined(USE_SOUND_FILES)
+void FLOPPY::add_sound(int type)
+{
+ int *p;
+ if(type == FLOPPY_SND_TYPE_SEEK) {
+ p = snd_seek_mix_tbl;
+ } else if(type == FLOPPY_SND_TYPE_HEAD) {
+ p = snd_head_mix_tbl;
+ } else {
+ return;
+ }
+ for(int i = 0; i < FLOPPY_SND_TBL_MAX; i++) {
+ if(p[i] < 0) {
+ p[i] = 0;
+ break;
+ }
+ }
+}
+
+bool FLOPPY::load_sound_data(int type, const _TCHAR *pathname)
+{
+ if((type < 0) || (type > 1)) return false;
+ int16_t *data = NULL;
+ int dst_size = 0;
+ int id = (this_device_id << 8) + type;
+ const _TCHAR *sp;
+ sp = create_local_path(pathname);
+ emu->load_sound_file(id, sp, &data, &dst_size);
+ if((dst_size <= 0) || (data == NULL)) { // Failed
+ this->out_debug_log("ID=%d : Failed to load SOUND FILE for %s:%s", id, (type == 0) ? _T("SEEK") : _T("HEAD") ,pathname);
+ return false;
+ } else {
+ int utl_size = dst_size * 2 * sizeof(int16_t);
+ int alloc_size = utl_size + 64;
+ switch(type) {
+ case FLOPPY_SND_TYPE_SEEK: // SEEK
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_seek_data, data, utl_size);
+ strncpy(snd_seek_name, pathname, 511);
+ snd_seek_samples_size = dst_size;
+ break;
+ case FLOPPY_SND_TYPE_HEAD: // HEAD
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_head_data, data, utl_size);
+ strncpy(snd_head_name, pathname, 511);
+ snd_head_samples_size = dst_size;
+ break;
+ default:
+ this->out_debug_log("ID=%d : Illegal type (%d): 0 (SEEK SOUND) or 1 (HEAD SOUND) is available.",
+ id, type);
+ return false;
+ }
+ this->out_debug_log("ID=%d : Success to load SOUND FILE for %s:%s",
+ id, (type == 0) ? _T("SEEK") : _T("HEAD") ,
+ pathname);
+ }
+ return true;
+}
+
+void FLOPPY::release_sound_data(int type)
+{
+ switch(type) {
+ case FLOPPY_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ snd_seek_data = NULL;
+ break;
+ case FLOPPY_SND_TYPE_HEAD: // HEAD
+ if(snd_head_data != NULL) free(snd_head_data);
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
+ snd_head_data = NULL;
+ break;
+ default:
+ break;
+ }
+}
+
+bool FLOPPY::reload_sound_data(int type)
+{
+ switch(type) {
+ case FLOPPY_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ case FLOPPY_SND_TYPE_HEAD:
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ default:
+ return false;
+ break;
+ }
+ _TCHAR *p = (type == FLOPPY_SND_TYPE_SEEK) ? snd_seek_name : snd_head_name;
+ _TCHAR tmps[512];
+ strncpy(tmps, p, 511);
+ return load_sound_data(type, tmps);
+}
+
+void FLOPPY::mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples)
+{
+ int ptr, pp;
+ int i, j, k;
+ int32_t data[2];
+ int32_t *dst_tmp;
+ for(i=0; i < FLOPPY_SND_TBL_MAX; i++) {
+ ptr = table[i];
+ if(ptr >= 0) {
+ if(ptr < samples) {
+ if(!snd_mute) {
+ pp = ptr << 1;
+ dst_tmp = dst;
+ k = 0;
+ for(j = 0; j < count; j++) {
+ if(ptr >= samples) {
+ break;
+ }
+ data[0] = (int32_t)src[pp + 0];
+ data[1] = (int32_t)src[pp + 1];
+ dst_tmp[k + 0] += apply_volume((int32_t)data[0], snd_level_l);
+ dst_tmp[k + 1] += apply_volume((int32_t)data[1], snd_level_r);
+ k += 2;
+ pp += 2;
+ ptr++;
+ }
+ } else {
+ ptr += count;
+ }
+ }
+ if(ptr >= samples) {
+ table[i] = -1;
+ } else {
+ table[i] = ptr;
+ }
+ }
+ }
+}
+
+void FLOPPY::mix(int32_t *buffer, int cnt)
+{
+ if(snd_seek_data != NULL) mix_main(buffer, cnt, snd_seek_data, snd_seek_mix_tbl, snd_seek_samples_size);
+ if(snd_head_data != NULL) mix_main(buffer, cnt, snd_head_data, snd_head_mix_tbl, snd_head_samples_size);
+}
+
+void FLOPPY::set_volume(int ch, int decibel_l, int decibel_r)
+{
+ snd_level_l = decibel_to_volume(decibel_l);
+ snd_level_r = decibel_to_volume(decibel_r);
+}
+#endif
+
#define STATE_VERSION 2
void FLOPPY::save_state(FILEIO* state_fio)
state_fio->FputUint8(SendSectors);
state_fio->FputInt32(DIO);
state_fio->FputUint8(Status);
+#if defined(USE_SOUND_FILES)
for(int i = 0; i < 2; i++) {
state_fio->FputInt32(seek_event_id[i]);
state_fio->FputInt32(seek_track_num[i]);
}
+ state_fio->Fwrite(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fwrite(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < FLOPPY_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_seek_mix_tbl[i]);
+ }
+ for(int i = 0; i < FLOPPY_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_head_mix_tbl[i]);
+ }
+ state_fio->FputBool(snd_mute);
+ state_fio->FputInt32(snd_level_l);
+ state_fio->FputInt32(snd_level_r);
+#endif
}
bool FLOPPY::load_state(FILEIO* state_fio)
SendSectors = state_fio->FgetUint8();
DIO = state_fio->FgetInt32();
Status = state_fio->FgetUint8();
+#if defined(USE_SOUND_FILES)
for(int i = 0; i < 2; i++) {
seek_event_id[i] = state_fio->FgetInt32();
seek_track_num[i] = state_fio->FgetInt32();
}
+ state_fio->Fread(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fread(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < FLOPPY_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ for(int i = 0; i < FLOPPY_SND_TBL_MAX; i++) {
+ snd_head_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ snd_mute = state_fio->FgetBool();
+ snd_level_l = state_fio->FgetInt32();
+ snd_level_r = state_fio->FgetInt32();
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ if(snd_head_data != NULL) free(snd_head_data);
+ if(strlen(snd_seek_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_seek_name, 511);
+ load_sound_data(FLOPPY_SND_TYPE_SEEK, (const _TCHAR *)tmps);
+ }
+ if(strlen(snd_head_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_head_name, 511);
+ load_sound_data(FLOPPY_SND_TYPE_HEAD, (const _TCHAR *)tmps);
+ }
+#endif
return true;
}
#include "../../emu.h"
#include "../device.h"
-class DISK;
#if defined(USE_SOUND_FILES)
-class WAV_SOUNDER;
+#define FLOPPY_SND_TBL_MAX 256
+#ifndef SIG_SOUNDER_MUTE
+#define SIG_SOUNDER_MUTE (65536 + 0)
+#endif
+#ifndef SIG_SOUNDER_RELOAD
+#define SIG_SOUNDER_RELOAD (65536 + 32)
+#endif
+#ifndef SIG_SOUNDER_ADD
+#define SIG_SOUNDER_ADD (65536 + 64)
+#endif
+
+#define FLOPPY_SND_TYPE_SEEK 0
+#define FLOPPY_SND_TYPE_HEAD 1
#endif
+class DISK;
class FLOPPY : public DEVICE
{
private:
unsigned char io_B1H;
DISK* disk[2];
-#if defined(USE_SOUND_FILES)
- DEVICE *d_seek_sound;
-#endif
int cur_trk[2];
int cur_sct[2];
int cur_pos[2];
unsigned char InDCH_66();
unsigned char InDDH_66();
+#if defined(USE_SOUND_FILES)
+protected:
+ _TCHAR snd_seek_name[512];
+ _TCHAR snd_head_name[512];
+ int snd_seek_mix_tbl[FLOPPY_SND_TBL_MAX];
+ int snd_head_mix_tbl[FLOPPY_SND_TBL_MAX];
+ int16_t *snd_seek_data; // Read only
+ int16_t *snd_head_data; // Read only
+ int snd_seek_samples_size;
+ int snd_head_samples_size;
+ bool snd_mute;
+ int snd_level_l, snd_level_r;
+ virtual void mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples);
+ void add_sound(int type);
+#endif
public:
FLOPPY(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu)
{
#if defined(USE_SOUND_FILES)
- seek_track_num[0] = seek_track_num[1] = 0;
- cur_trk[0] = cur_trk[1] = 0;
- seek_event_id[0] = seek_event_id[1] = -1;
- d_seek_sound = NULL;
+ seek_track_num[0] = seek_track_num[1] = 0;
+ cur_trk[0] = cur_trk[1] = 0;
+ seek_event_id[0] = seek_event_id[1] = -1;
+ for(int i = 0; i < FLOPPY_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = -1;
+ snd_head_mix_tbl[i] = -1;
+ }
+ snd_seek_data = snd_head_data = NULL;
+ snd_seek_samples_size = snd_head_samples_size = 0;
+ snd_mute = false;
+ snd_level_l = snd_level_r = decibel_to_volume(0);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
#endif
}
~FLOPPY() {}
{
d_ext = device;
}
-#if defined(USE_SOUND_FILES)
- void set_context_seek(DEVICE *d)
- {
- d_seek_sound = d;
- }
-#endif
DISK* get_disk_handler(int drv)
{
return disk[drv];
}
+#if defined(USE_SOUND_FILES)
+ // Around SOUND. 20161004 K.O
+ bool load_sound_data(int type, const _TCHAR *pathname);
+ void release_sound_data(int type);
+ bool reload_sound_data(int type);
+
+ void mix(int32_t *buffer, int cnt);
+ void set_volume(int ch, int decibel_l, int decibel_r);
+#endif
void open_disk(int drv, const _TCHAR* file_path, int bank);
void close_disk(int drv);
bool is_disk_inserted(int drv);
#include "../datarec.h"
#include "../mcs48.h"
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-#endif
#ifdef USE_DEBUGGER
#include "../debugger.h"
drec = new DATAREC(this, emu);
event->set_context_cpu(cpu_sub, 8000000);
event->set_context_sound(drec);
+#if defined(USE_SOUND_FILES)
+ drec->load_sound_data(DATAREC_SNDFILE_RELAY_ON, _T("RELAY_ON.WAV"));
+ drec->load_sound_data(DATAREC_SNDFILE_RELAY_OFF, _T("RELAY_OFF.WAV"));
+#endif
cpu_sub->set_context_mem(new MCS48MEM(this, emu));
cpu_sub->set_context_io(sub);
#ifdef USE_DEBUGGER
cpu_pc80s31k->set_device_name(_T("Z80 CPU(PC-80S31K)"));
#endif
#if defined(USE_SOUND_FILES)
- d_pc80s31k_seek = new WAV_SOUNDER(this, emu);
- if(d_pc80s31k_seek->load_data(_T("FDDSEEK.WAV"))) {
- event->set_context_sound(d_pc80s31k_seek);
- fdc_pc80s31k->set_context_seek(d_pc80s31k_seek);
+ if(fdc_pc80s31k->load_sound_data(UPD765A_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(fdc_pc80s31k);
}
#endif
event->set_context_cpu(cpu_pc80s31k, 4000000);
floppy->set_context_ext(pc6031);
#endif
#if defined(USE_SOUND_FILES)
- d_pc6031_seek = new WAV_SOUNDER(this, emu);
- if(d_pc6031_seek->load_data(_T("FDDSEEK.WAV"))) {
- event->set_context_sound(d_pc6031_seek);
- pc6031->set_context_seek(d_pc6031_seek);
+ if(pc6031->load_sound_data(PC6031_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(pc6031);
}
- d_floppy_seek = new WAV_SOUNDER(this, emu);
- if(d_floppy_seek->load_data(_T("FDDSEEK.WAV"))) {
- event->set_context_sound(d_floppy_seek);
- floppy->set_context_seek(d_floppy_seek);
+ if(floppy->load_sound_data(FLOPPY_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(floppy);
}
#endif
cpu_pc80s31k = NULL;
}
#if defined(USE_SOUND_FILES)
else if(ch-- == 0) {
- if(d_pc80s31k_seek != NULL) d_pc80s31k_seek->set_volume(0, decibel_l, decibel_r);
- if(d_pc6031_seek != NULL) d_pc6031_seek->set_volume(0, decibel_l, decibel_r);
- if(d_floppy_seek != NULL) d_floppy_seek->set_volume(0, decibel_l, decibel_r);
+ if(support_pc80s31k) {
+ if(fdc_pc80s31k != NULL) fdc_pc80s31k->set_volume(0, decibel_l, decibel_r);
+ } else {
+ if(pc6031 != NULL) pc6031->set_volume(0, decibel_l, decibel_r);
+ if(floppy != NULL) floppy->set_volume(0, decibel_l, decibel_r);
+ }
}
#endif
}
#include "pc6031.h"
#include "disk.h"
#if defined(USE_SOUND_FILES)
-#include "wav_sounder.h"
-#endif
-#if defined(USE_SOUND_FILES)
#define EVENT_SEEK_SOUND 2
#endif
} else {
seek_event_id[drvno] = -1;
}
- if(d_seek_sound != NULL) d_seek_sound->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ add_sound(PC6031_SND_TYPE_SEEK);
}
#endif
}
return false;
}
+#if defined(USE_SOUND_FILES)
+void PC6031::add_sound(int type)
+{
+ int *p;
+ if(type == PC6031_SND_TYPE_SEEK) {
+ p = snd_seek_mix_tbl;
+ } else if(type == PC6031_SND_TYPE_HEAD) {
+ p = snd_head_mix_tbl;
+ } else {
+ return;
+ }
+ for(int i = 0; i < PC6031_SND_TBL_MAX; i++) {
+ if(p[i] < 0) {
+ p[i] = 0;
+ break;
+ }
+ }
+}
+
+bool PC6031::load_sound_data(int type, const _TCHAR *pathname)
+{
+ if((type < 0) || (type > 1)) return false;
+ int16_t *data = NULL;
+ int dst_size = 0;
+ int id = (this_device_id << 8) + type;
+ const _TCHAR *sp;
+ sp = create_local_path(pathname);
+ emu->load_sound_file(id, sp, &data, &dst_size);
+ if((dst_size <= 0) || (data == NULL)) { // Failed
+ this->out_debug_log("ID=%d : Failed to load SOUND FILE for %s:%s", id, (type == 0) ? _T("SEEK") : _T("HEAD") ,pathname);
+ return false;
+ } else {
+ int utl_size = dst_size * 2 * sizeof(int16_t);
+ int alloc_size = utl_size + 64;
+ switch(type) {
+ case PC6031_SND_TYPE_SEEK: // SEEK
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_seek_data, data, utl_size);
+ strncpy(snd_seek_name, pathname, 511);
+ snd_seek_samples_size = dst_size;
+ break;
+ case PC6031_SND_TYPE_HEAD: // HEAD
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_head_data, data, utl_size);
+ strncpy(snd_head_name, pathname, 511);
+ snd_head_samples_size = dst_size;
+ break;
+ default:
+ this->out_debug_log("ID=%d : Illegal type (%d): 0 (SEEK SOUND) or 1 (HEAD SOUND) is available.",
+ id, type);
+ return false;
+ }
+ this->out_debug_log("ID=%d : Success to load SOUND FILE for %s:%s",
+ id, (type == 0) ? _T("SEEK") : _T("HEAD") ,
+ pathname);
+ }
+ return true;
+}
+
+void PC6031::release_sound_data(int type)
+{
+ switch(type) {
+ case PC6031_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ snd_seek_data = NULL;
+ break;
+ case PC6031_SND_TYPE_HEAD: // HEAD
+ if(snd_head_data != NULL) free(snd_head_data);
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
+ snd_head_data = NULL;
+ break;
+ default:
+ break;
+ }
+}
+
+bool PC6031::reload_sound_data(int type)
+{
+ switch(type) {
+ case PC6031_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ case PC6031_SND_TYPE_HEAD:
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ default:
+ return false;
+ break;
+ }
+ _TCHAR *p = (type == PC6031_SND_TYPE_SEEK) ? snd_seek_name : snd_head_name;
+ _TCHAR tmps[512];
+ strncpy(tmps, p, 511);
+ return load_sound_data(type, tmps);
+}
+
+void PC6031::mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples)
+{
+ int ptr, pp;
+ int i, j, k;
+ int32_t data[2];
+ int32_t *dst_tmp;
+ for(i=0; i < PC6031_SND_TBL_MAX; i++) {
+ ptr = table[i];
+ if(ptr >= 0) {
+ if(ptr < samples) {
+ if(!snd_mute) {
+ pp = ptr << 1;
+ dst_tmp = dst;
+ k = 0;
+ for(j = 0; j < count; j++) {
+ if(ptr >= samples) {
+ break;
+ }
+ data[0] = (int32_t)src[pp + 0];
+ data[1] = (int32_t)src[pp + 1];
+ dst_tmp[k + 0] += apply_volume((int32_t)data[0], snd_level_l);
+ dst_tmp[k + 1] += apply_volume((int32_t)data[1], snd_level_r);
+ k += 2;
+ pp += 2;
+ ptr++;
+ }
+ } else {
+ ptr += count;
+ }
+ }
+ if(ptr >= samples) {
+ table[i] = -1;
+ } else {
+ table[i] = ptr;
+ }
+ }
+ }
+}
+
+void PC6031::mix(int32_t *buffer, int cnt)
+{
+ if(snd_seek_data != NULL) mix_main(buffer, cnt, snd_seek_data, snd_seek_mix_tbl, snd_seek_samples_size);
+ if(snd_head_data != NULL) mix_main(buffer, cnt, snd_head_data, snd_head_mix_tbl, snd_head_samples_size);
+}
+
+void PC6031::set_volume(int ch, int decibel_l, int decibel_r)
+{
+ snd_level_l = decibel_to_volume(decibel_l);
+ snd_level_r = decibel_to_volume(decibel_r);
+}
+#endif
+
#define STATE_VERSION 2
void PC6031::save_state(FILEIO* state_fio)
state_fio->FputUint8(old_D2H);
state_fio->FputUint8(io_D3H);
state_fio->FputInt32(DrvNum);
+#if defined(USE_SOUND_FILES)
for(int i = 0; i < 2; i++) {
state_fio->FputInt32(seek_event_id[i]);
state_fio->FputInt32(seek_track_num[i]);
}
+ state_fio->Fwrite(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fwrite(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < PC6031_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_seek_mix_tbl[i]);
+ }
+ for(int i = 0; i < PC6031_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_head_mix_tbl[i]);
+ }
+ state_fio->FputBool(snd_mute);
+ state_fio->FputInt32(snd_level_l);
+ state_fio->FputInt32(snd_level_r);
+#endif
}
bool PC6031::load_state(FILEIO* state_fio)
old_D2H = state_fio->FgetUint8();
io_D3H = state_fio->FgetUint8();
DrvNum = state_fio->FgetInt32();
+#if defined(USE_SOUND_FILES)
for(int i = 0; i < 2; i++) {
seek_event_id[i] = state_fio->FgetInt32();
seek_track_num[i] = state_fio->FgetInt32();
}
+ state_fio->Fread(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fread(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < PC6031_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ for(int i = 0; i < PC6031_SND_TBL_MAX; i++) {
+ snd_head_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ snd_mute = state_fio->FgetBool();
+ snd_level_l = state_fio->FgetInt32();
+ snd_level_r = state_fio->FgetInt32();
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ if(snd_head_data != NULL) free(snd_head_data);
+ if(strlen(snd_seek_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_seek_name, 511);
+ load_sound_data(PC6031_SND_TYPE_SEEK, (const _TCHAR *)tmps);
+ }
+ if(strlen(snd_head_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_head_name, 511);
+ load_sound_data(PC6031_SND_TYPE_HEAD, (const _TCHAR *)tmps);
+ }
+#endif
return true;
}
#include "../emu.h"
#include "device.h"
+#if defined(USE_SOUND_FILES)
+#define PC6031_SND_TBL_MAX 256
+#ifndef SIG_SOUNDER_MUTE
+#define SIG_SOUNDER_MUTE (65536 + 0)
+#endif
+#ifndef SIG_SOUNDER_RELOAD
+#define SIG_SOUNDER_RELOAD (65536 + 32)
+#endif
+#ifndef SIG_SOUNDER_ADD
+#define SIG_SOUNDER_ADD (65536 + 64)
+#endif
+
+#define PC6031_SND_TYPE_SEEK 0
+#define PC6031_SND_TYPE_HEAD 1
+#endif
class DISK;
class PC6031 : public DEVICE
private:
DISK* disk[2];
#if defined(USE_SOUND_FILES)
- DEVICE *d_seek_sound;
int seek_event_id[2];
int seek_track_num[2];
#endif
unsigned char InD2H_60();
unsigned char InD3H_60();
+#if defined(USE_SOUND_FILES)
+protected:
+ _TCHAR snd_seek_name[512];
+ _TCHAR snd_head_name[512];
+ int snd_seek_mix_tbl[PC6031_SND_TBL_MAX];
+ int snd_head_mix_tbl[PC6031_SND_TBL_MAX];
+ int16_t *snd_seek_data; // Read only
+ int16_t *snd_head_data; // Read only
+ int snd_seek_samples_size;
+ int snd_head_samples_size;
+ bool snd_mute;
+ int snd_level_l, snd_level_r;
+ virtual void mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples);
+ void add_sound(int type);
+#endif
public:
PC6031(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu) {
set_device_name(_T("PSEUDO PC-6031 FDD"));
#if defined(USE_SOUND_FILES)
- d_seek_sound = NULL;
seek_event_id[0] = seek_event_id[1] = -1;
seek_track_num[0] = seek_track_num[1] = 0;
+ for(int i = 0; i < PC6031_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = -1;
+ snd_head_mix_tbl[i] = -1;
+ }
+ snd_seek_data = snd_head_data = NULL;
+ snd_seek_samples_size = snd_head_samples_size = 0;
+ snd_mute = false;
+ snd_level_l = snd_level_r = decibel_to_volume(0);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
#endif
}
~PC6031() {}
void event_callback(int event_id, int err);
// unique functions
-#if defined(USE_SOUND_FILES)
- void set_context_seek(DEVICE *d)
- {
- d_seek_sound = d;
- }
-#endif
DISK* get_disk_handler(int drv)
{
return disk[drv];
}
+#if defined(USE_SOUND_FILES)
+ // Around SOUND. 20161004 K.O
+ bool load_sound_data(int type, const _TCHAR *pathname);
+ void release_sound_data(int type);
+ bool reload_sound_data(int type);
+
+ void mix(int32_t *buffer, int cnt);
+ void set_volume(int ch, int decibel_l, int decibel_r);
+#endif
void open_disk(int drv, const _TCHAR* file_path, int bank);
void close_disk(int drv);
bool is_disk_inserted(int drv);
#ifdef SUPPORT_PC88_PCG8100
#include "../i8253.h"
#endif
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-#endif
#include "pc88.h"
pc88fdc_sub->set_device_name(_T("uPD765A FDC(FDD)"));
pc88cpu_sub->set_device_name(_T("Z80 CPU(FDD)"));
#endif
-#if defined(USE_SOUND_FILES)
- pc88fdc_seeksnd = new WAV_SOUNDER(this, emu);
-#endif
#ifdef SUPPORT_PC88_PCG8100
pc88pit = new I8253(this, emu);
// pc88pit->set_context_event_manager(pc88event);
pc88event->set_context_sound(pc88pcm2);
#endif
#if defined(USE_SOUND_FILES)
- if(pc88fdc_seeksnd->load_data(_T("FDDSEEK.WAV"))) {
- pc88event->set_context_sound(pc88fdc_seeksnd);
- pc88fdc_sub->set_context_seek(pc88fdc_seeksnd);
+ if(pc88fdc_sub->load_sound_data(UPD765A_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ pc88event->set_context_sound(pc88fdc_sub);
}
#endif
pc88->set_context_cpu(pc88cpu);
}
#if defined(USE_SOUND_FILES)
else if(ch-- == 0) {
- if(pc88fdc_seeksnd != NULL) pc88fdc_seeksnd->set_volume(0, decibel_l, decibel_r);
- }
+ pc88fdc_sub->set_volume(0, decibel_l, decibel_r);
+ }
#endif
}
#endif
#ifdef SUPPORT_PC88_PCG8100
class I8253;
#endif
-#if defined(USE_SOUND_FILES)
-class WAV_SOUNDER;
-#endif
class PC88;
class VM
I8255* pc88pio_sub;
UPD765A* pc88fdc_sub;
Z80* pc88cpu_sub;
-#if defined(USE_SOUND_FILES)
- WAV_SOUNDER* pc88fdc_seeksnd;
-#endif
#ifdef SUPPORT_PC88_PCG8100
I8253* pc88pit;
PCM1BIT* pc88pcm0;
#include "../upd7220.h"
#include "../upd765a.h"
#include "../ym2203.h"
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-#endif
#ifdef USE_DEBUGGER
#include "../debugger.h"
#if defined(_USE_QT)
fdc_2hd->set_device_name(_T("uPD765A FDC(2HD I/F)"));
#endif
- #if defined(USE_SOUND_FILES)
- fdc_2hd_seeksnd = new WAV_SOUNDER(this, emu);
- #endif
#endif
#if defined(SUPPORT_2DD_FDD_IF)
fdc_2dd = new UPD765A(this, emu);
#if defined(_USE_QT)
fdc_2dd->set_device_name(_T("uPD765A FDC(2DD I/F)"));
#endif
- #if defined(USE_SOUND_FILES)
- fdc_2dd_seeksnd = new WAV_SOUNDER(this, emu);
- #endif
#endif
#if defined(SUPPORT_2HD_2DD_FDD_IF)
fdc = new UPD765A(this, emu);
#if defined(_USE_QT)
fdc->set_device_name(_T("uPD765A FDC(2DD/2HD I/F)"));
#endif
- #if defined(USE_SOUND_FILES)
- fdc_seeksnd = new WAV_SOUNDER(this, emu);
- #endif
#endif
gdc_chr = new UPD7220(this, emu);
gdc_gfx = new UPD7220(this, emu);
fdc_sub->set_device_name(_T("uPD765A FDC(320KB FDD)"));
cpu_sub->set_device_name(_T("Z80 CPU(320KB FDD)"));
#endif
- #if defined(USE_SOUND_FILES)
- fdc_sub_seeksnd = new WAV_SOUNDER(this, emu);
- #endif
#endif
#if defined(SUPPORT_ITF_ROM)
itf = new ITF(this, emu);
}
#if defined(USE_SOUND_FILES)
#if defined(SUPPORT_2HD_FDD_IF)
- if(fdc_2hd_seeksnd->load_data(_T("FDDSEEK.WAV"))) {
- event->set_context_sound(fdc_2hd_seeksnd);
- fdc_2hd->set_context_seek(fdc_2hd_seeksnd);
+ if(fdc_2hd->load_sound_data(UPD765A_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(fdc_2hd);
}
#endif
#if defined(SUPPORT_2DD_FDD_IF)
- if(fdc_2dd_seeksnd->load_data(_T("FDDSEEK.WAV"))) {
- event->set_context_sound(fdc_2dd_seeksnd);
- fdc_2dd->set_context_seek(fdc_2dd_seeksnd);
+ if(fdc_2dd->load_sound_data(UPD765A_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(fdc_2dd);
}
#endif
#if defined(SUPPORT_2HD_2DD_FDD_IF)
- if(fdc_seeksnd->load_data(_T("FDDSEEK.WAV"))) {
- event->set_context_sound(fdc_seeksnd);
- fdc->set_context_seek(fdc_seeksnd);
+ if(fdc->load_sound_data(UPD765A_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(fdc);
}
#endif
#if defined(SUPPORT_320KB_FDD_IF)
- if(fdc_sub_seeksnd->load_data(_T("FDDSEEK.WAV"))) {
- event->set_context_sound(fdc_sub_seeksnd);
- fdc_sub->set_context_seek(fdc_sub_seeksnd);
+ if(fdc_sub->load_sound_data(UPD765A_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(fdc_sub);
}
#endif
#endif
pc88fdc_sub->set_device_name(_T("uPD765A FDC(PC8801 FDD)"));
pc88cpu_sub->set_device_name(_T("Z80 CPU(PC8801 FDD)"));
#endif
-#if defined(USE_SOUND_FILES)
- pc88fdc_sub_seeksnd = new WAV_SOUNDER(this, emu);
-#endif
pc88event->set_context_cpu(pc88cpu, (config.cpu_type != 0) ? 3993624 : 7987248);
pc88event->set_context_cpu(pc88cpu_sub, 3993624);
pc88event->set_context_sound(pc88opn);
pc88event->set_context_sound(pc88pcm);
#if defined(USE_SOUND_FILES)
- if(pc88fdc_sub_seeksnd->load_data(_T("FDDSEEK.WAV"))) {
- pc88event->set_context_sound(pc88fdc_sub_seeksnd);
- pc88fdc_sub->set_context_seek(pc88fdc_sub_seeksnd);
+ if(pc88fdc_sub->load_sound_data(UPD765A_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ pc88event->set_context_sound(pc88fdc_sub);
}
#endif
#if defined(USE_SOUND_FILES)
else if(ch-- == 0) {
#if defined(SUPPORT_2HD_FDD_IF)
- fdc_2hd_seeksnd->set_volume(0, decibel_l, decibel_r);
+ fdc_2hd->set_volume(0, decibel_l, decibel_r);
#endif
#if defined(SUPPORT_2DD_FDD_IF)
- fdc_2dd_seeksnd->set_volume(0, decibel_l, decibel_r);
+ fdc_2dd->set_volume(0, decibel_l, decibel_r);
#endif
#if defined(SUPPORT_2HD_2DD_FDD_IF)
- fdc_seeksnd->set_volume(0, decibel_l, decibel_r);
+ fdc->set_volume(0, decibel_l, decibel_r);
#endif
#if defined(SUPPORT_320KB_FDD_IF)
- fdc_sub_seeksnd->set_volume(0, decibel_l, decibel_r);
+ fdc_sub->set_volume(0, decibel_l, decibel_r);
#endif
#if defined(_PC98DO) || defined(_PC98DOPLUS)
- pc88fdc_sub_seeksnd->set_volume(0, decibel_l, decibel_r);
+ pc88fdc_sub->set_volume(0, decibel_l, decibel_r);
#endif
#endif
}
#include "upd765a.h"
#include "disk.h"
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-#endif
#define EVENT_PHASE 0
#define EVENT_DRQ 1
// for NEC PC-98x1 series
force_ready = ((data & mask) != 0);
}
+#if defined(USE_SOUND_FILES)
+ else if((id >= SIG_SOUNDER_MUTE) && (id < (SIG_SOUNDER_MUTE + 2))) {
+ snd_mute = ((data & mask) != 0);
+ } else if((id >= SIG_SOUNDER_RELOAD) && (id < (SIG_SOUNDER_RELOAD + 2))) {
+ reload_sound_data(id - SIG_SOUNDER_RELOAD);
+ }
+#endif
}
uint32_t UPD765A::read_signal(int ch)
} else {
seek_snd_id[drv] = -1;
}
- if(d_seek_sound != NULL) d_seek_sound->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ add_sound(UPD765A_SND_TYPE_SEEK);
}
}
#endif
fdc[drv].track = trk;
#ifdef UPD765A_DONT_WAIT_SEEK
seek_event(drv);
- if(d_seek_sound != NULL) d_seek_sound->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ add_sound(UPD765A_SND_TYPE_SEEK);
#else
if(seek_id[drv] != -1) {
cancel_event(this, seek_id[drv]);
disk[drv]->drive_mfm = mfm;
}
}
+#if defined(USE_SOUND_FILES)
+void UPD765A::add_sound(int type)
+{
+ int *p;
+ if(type == UPD765A_SND_TYPE_SEEK) {
+ p = snd_seek_mix_tbl;
+ } else if(type == UPD765A_SND_TYPE_HEAD) {
+ p = snd_head_mix_tbl;
+ } else {
+ return;
+ }
+ for(int i = 0; i < UPD765A_SND_TBL_MAX; i++) {
+ if(p[i] < 0) {
+ p[i] = 0;
+ break;
+ }
+ }
+}
-#define STATE_VERSION 2
+bool UPD765A::load_sound_data(int type, const _TCHAR *pathname)
+{
+ if((type < 0) || (type > 1)) return false;
+ int16_t *data = NULL;
+ int dst_size = 0;
+ int id = (this_device_id << 8) + type;
+ const _TCHAR *sp;
+ sp = create_local_path(pathname);
+ emu->load_sound_file(id, sp, &data, &dst_size);
+ if((dst_size <= 0) || (data == NULL)) { // Failed
+ this->out_debug_log("ID=%d : Failed to load SOUND FILE for %s:%s", id, (type == 0) ? _T("SEEK") : _T("HEAD") ,pathname);
+ return false;
+ } else {
+ int utl_size = dst_size * 2 * sizeof(int16_t);
+ int alloc_size = utl_size + 64;
+ switch(type) {
+ case UPD765A_SND_TYPE_SEEK: // SEEK
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_seek_data, data, utl_size);
+ strncpy(snd_seek_name, pathname, 511);
+ snd_seek_samples_size = dst_size;
+ break;
+ case UPD765A_SND_TYPE_HEAD: // HEAD
+ snd_seek_data = (int16_t *)malloc(alloc_size);
+ memcpy(snd_head_data, data, utl_size);
+ strncpy(snd_head_name, pathname, 511);
+ snd_head_samples_size = dst_size;
+ break;
+ default:
+ this->out_debug_log("ID=%d : Illegal type (%d): 0 (SEEK SOUND) or 1 (HEAD SOUND) is available.",
+ id, type);
+ return false;
+ }
+ this->out_debug_log("ID=%d : Success to load SOUND FILE for %s:%s",
+ id, (type == 0) ? _T("SEEK") : _T("HEAD") ,
+ pathname);
+ }
+ return true;
+}
+
+void UPD765A::release_sound_data(int type)
+{
+ switch(type) {
+ case UPD765A_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ snd_seek_data = NULL;
+ break;
+ case UPD765A_SND_TYPE_HEAD: // HEAD
+ if(snd_head_data != NULL) free(snd_head_data);
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
+ snd_head_data = NULL;
+ break;
+ default:
+ break;
+ }
+}
+
+bool UPD765A::reload_sound_data(int type)
+{
+ switch(type) {
+ case UPD765A_SND_TYPE_SEEK: // SEEK
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ case UPD765A_SND_TYPE_HEAD:
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ break;
+ default:
+ return false;
+ break;
+ }
+ _TCHAR *p = (type == UPD765A_SND_TYPE_SEEK) ? snd_seek_name : snd_head_name;
+ _TCHAR tmps[512];
+ strncpy(tmps, p, 511);
+ return load_sound_data(type, tmps);
+}
+
+void UPD765A::mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples)
+{
+ int ptr, pp;
+ int i, j, k;
+ int32_t data[2];
+ int32_t *dst_tmp;
+ for(i=0; i < UPD765A_SND_TBL_MAX; i++) {
+ ptr = table[i];
+ if(ptr >= 0) {
+ if(ptr < samples) {
+ if(!snd_mute) {
+ pp = ptr << 1;
+ dst_tmp = dst;
+ k = 0;
+ for(j = 0; j < count; j++) {
+ if(ptr >= samples) {
+ break;
+ }
+ data[0] = (int32_t)src[pp + 0];
+ data[1] = (int32_t)src[pp + 1];
+ dst_tmp[k + 0] += apply_volume((int32_t)data[0], snd_level_l);
+ dst_tmp[k + 1] += apply_volume((int32_t)data[1], snd_level_r);
+ k += 2;
+ pp += 2;
+ ptr++;
+ }
+ } else {
+ ptr += count;
+ }
+ }
+ if(ptr >= samples) {
+ table[i] = -1;
+ } else {
+ table[i] = ptr;
+ }
+ }
+ }
+}
+
+void UPD765A::mix(int32_t *buffer, int cnt)
+{
+ if(snd_seek_data != NULL) mix_main(buffer, cnt, snd_seek_data, snd_seek_mix_tbl, snd_seek_samples_size);
+ if(snd_head_data != NULL) mix_main(buffer, cnt, snd_head_data, snd_head_mix_tbl, snd_head_samples_size);
+}
+
+void UPD765A::set_volume(int ch, int decibel_l, int decibel_r)
+{
+ snd_level_l = decibel_to_volume(decibel_l);
+ snd_level_r = decibel_to_volume(decibel_r);
+}
+#endif
+
+#define STATE_VERSION 3
void UPD765A::save_state(FILEIO* state_fio)
{
state_fio->FputInt32(seek_snd_id[i]);
}
#endif
+#if defined(USE_SOUND_FILES)
+ state_fio->Fwrite(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fwrite(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < UPD765A_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_seek_mix_tbl[i]);
+ }
+ for(int i = 0; i < UPD765A_SND_TBL_MAX; i++) {
+ state_fio->FputInt32(snd_head_mix_tbl[i]);
+ }
+ state_fio->FputBool(snd_mute);
+ state_fio->FputInt32(snd_level_l);
+ state_fio->FputInt32(snd_level_r);
+#endif
}
bool UPD765A::load_state(FILEIO* state_fio)
seek_snd_id[i] = state_fio->FgetInt32();
}
#endif
+#if defined(USE_SOUND_FILES)
+ state_fio->Fread(snd_seek_name, sizeof(snd_seek_name), 1);
+ state_fio->Fread(snd_head_name, sizeof(snd_head_name), 1);
+ for(int i = 0; i < UPD765A_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ for(int i = 0; i < UPD765A_SND_TBL_MAX; i++) {
+ snd_head_mix_tbl[i] = state_fio->FgetInt32();
+ }
+ snd_mute = state_fio->FgetBool();
+ snd_level_l = state_fio->FgetInt32();
+ snd_level_r = state_fio->FgetInt32();
+ if(snd_seek_data != NULL) free(snd_seek_data);
+ if(snd_head_data != NULL) free(snd_head_data);
+ if(strlen(snd_seek_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_seek_name, 511);
+ load_sound_data(UPD765A_SND_TYPE_SEEK, (const _TCHAR *)tmps);
+ }
+ if(strlen(snd_head_name) > 0) {
+ _TCHAR tmps[512];
+ strncpy(tmps, snd_head_name, 511);
+ load_sound_data(UPD765A_SND_TYPE_HEAD, (const _TCHAR *)tmps);
+ }
+#endif
return true;
}
#define SIG_UPD765A_DRQ_MASK 6
#define SIG_UPD765A_FREADY 7
+#if defined(USE_SOUND_FILES)
+#define UPD765A_SND_TBL_MAX 256
+#ifndef SIG_SOUNDER_MUTE
+#define SIG_SOUNDER_MUTE (65536 + 0)
+#endif
+#ifndef SIG_SOUNDER_RELOAD
+#define SIG_SOUNDER_RELOAD (65536 + 32)
+#endif
+#ifndef SIG_SOUNDER_ADD
+#define SIG_SOUNDER_ADD (65536 + 64)
+#endif
+
+#define UPD765A_SND_TYPE_SEEK 0
+#define UPD765A_SND_TYPE_HEAD 1
+#endif
+
class DISK;
class UPD765A : public DEVICE
} fdc[4];
DISK* disk[4];
#if defined(USE_SOUND_FILES)
- DEVICE *d_seek_sound;
int seek_snd_trk[4];
- int sddk_snd_id[4];
+ int seek_snd_id[4];
#endif
uint8_t hdu, hdue, id[4], eot, gpl, dtl;
int count;
int event_phase;
int phase_id, drq_id, lost_id, result7_id, seek_id[4];
-#if defined(USE_SOUND_FILES)
- int seek_snd_id[4];
-#endif
+
bool force_ready;
bool reset_signal;
bool prev_index;
void cmd_specify();
void cmd_invalid();
+#if defined(USE_SOUND_FILES)
+protected:
+ _TCHAR snd_seek_name[512];
+ _TCHAR snd_head_name[512];
+ int snd_seek_mix_tbl[UPD765A_SND_TBL_MAX];
+ int snd_head_mix_tbl[UPD765A_SND_TBL_MAX];
+ int16_t *snd_seek_data; // Read only
+ int16_t *snd_head_data; // Read only
+ int snd_seek_samples_size;
+ int snd_head_samples_size;
+ bool snd_mute;
+ int snd_level_l, snd_level_r;
+ virtual void mix_main(int32_t *dst, int count, int16_t *src, int *table, int samples);
+ void add_sound(int type);
+#endif
public:
UPD765A(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu)
{
raise_irq_when_media_changed = false;
set_device_name(_T("uPD765A FDC"));
#if defined(USE_SOUND_FILES)
- d_seek_sound = NULL;
+ for(int i = 0; i < UPD765A_SND_TBL_MAX; i++) {
+ snd_seek_mix_tbl[i] = -1;
+ snd_head_mix_tbl[i] = -1;
+ }
+ snd_seek_data = snd_head_data = NULL;
+ snd_seek_samples_size = snd_head_samples_size = 0;
+ snd_mute = false;
+ snd_level_l = snd_level_r = decibel_to_volume(0);
+ memset(snd_seek_name, 0x00, sizeof(snd_seek_name));
+ memset(snd_head_name, 0x00, sizeof(snd_head_name));
#endif
}
~UPD765A() {}
{
register_output_signal(&outputs_index, device, id, mask);
}
-#if defined(USE_SOUND_FILES)
- void set_context_seek(DEVICE* device)
- {
- d_seek_sound = device;
- }
-#endif
DISK* get_disk_handler(int drv)
{
return disk[drv];
}
+#if defined(USE_SOUND_FILES)
+ // Around SOUND. 20161004 K.O
+ bool load_sound_data(int type, const _TCHAR *pathname);
+ void release_sound_data(int type);
+ bool reload_sound_data(int type);
+
+ void mix(int32_t *buffer, int cnt);
+ void set_volume(int ch, int decibel_l, int decibel_r);
+#endif
void open_disk(int drv, const _TCHAR* file_path, int bank);
void close_disk(int drv);
bool is_disk_inserted(int drv);
#include "../datarec.h"
#include "../i8255.h"
#include "../../fifo.h"
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.h"
-#endif
//#define DEBUG_COMMAND
#define EVENT_1SEC 0
play = rec = false;
d_drec->set_remote(false);
#if defined(USE_SOUND_FILES)
- if(d_cmt_eject != NULL) d_cmt_eject->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_EJECT, 1, 1);
#endif
}
}
d_drec->set_ff_rew(0);
d_drec->set_remote(true);
#if defined(USE_SOUND_FILES)
- if(d_cmt_play != NULL) d_cmt_play->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_PLAY, 1, 1);
#endif
} else if(rec) {
new_status = CMT_STOP;
d_drec->set_ff_rew(1);
d_drec->set_remote(true);
#if defined(USE_SOUND_FILES)
- //if(d_cmt_ffrew != NULL) d_cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ //d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_FF, 1, 1);
#endif
} else if(rec) {
new_status = CMT_STOP;
d_drec->set_ff_rew(-1);
d_drec->set_remote(true);
#if defined(USE_SOUND_FILES)
- //if(d_cmt_ffrew != NULL) d_cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ //d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_REW, 1, 1);
#endif
} else if(rec) {
new_status = CMT_STOP;
case CMT_APSS_MINUS:
if(play) {
#if defined(USE_SOUND_FILES)
- //if(d_cmt_ffrew != NULL) d_cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ //d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_REW, 1, 1);
#endif
d_drec->do_apss((databuf[0x19][0] == CMT_APSS_PLUS) ? 1 : -1);
new_status = CMT_STOP;
new_status = CMT_STOP;
} else if(rec) {
#if defined(USE_SOUND_FILES)
- if(d_cmt_play != NULL) d_cmt_play->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_PLAY, 1, 1);
#endif
d_drec->set_remote(true);
} else {
}
#if defined(USE_SOUND_FILES)
if(new_status == CMT_EJECT) {
- if(d_cmt_eject != NULL) d_cmt_eject->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_EJECT, 1, 1);
} else if(new_status == CMT_STOP) {
- if(d_cmt_stop != NULL) d_cmt_stop->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_STOP, 1, 1);
}
#endif
private:
DEVICE *d_cpu, *d_pio;
DATAREC *d_drec;
-#if defined(USE_SOUND_FILES)
- DEVICE *d_cmt_eject;
- //DEVICE *d_cmt_ffrew;
- DEVICE *d_cmt_play;
- DEVICE *d_cmt_stop;
-#endif
cur_time_t cur_time;
int time_register_id;
public:
PSUB(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu) {
set_device_name(_T("PSEUDO SUBSYSTEM"));
-#if defined(USE_SOUND_FILES)
- d_cmt_eject = NULL;
- //d_cmt_ffrew = NULL;
- d_cmt_play = NULL;
- d_cmt_stop = NULL;
-#endif
}
~PSUB() {}
{
d_drec = device;
}
-#if defined(USE_SOUND_FILES)
- void set_context_cmt_eject(DEVICE* device)
- {
- d_cmt_eject = device;
- }
- //void set_context_cmt_ffrew(DEVICE* device)
- //{
- // d_cmt_ffrew = device;
- //}
- void set_context_cmt_play(DEVICE* device)
- {
- d_cmt_play = device;
- }
- void set_context_cmt_stop(DEVICE* device)
- {
- d_cmt_stop = device;
- }
-#endif
void key_down(int code, bool repeat);
void key_up(int code);
void play_tape(bool value);
if((p2_out & 0x10) && !(data & 0x10)) {
d_drec->set_remote(false);
#if defined(USE_SOUND_FILES)
- if(d_cmt_stop != NULL) d_cmt_stop->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_STOP, 1, 1);
#endif
}
#if defined(USE_SOUND_FILES)
if(ffrew_comp) {
- //if(d_cmt_ffrew != NULL) d_cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_FF, 1, 1);
}
#endif
intr = ((data & 0x40) == 0);
{
bool f = ((data & mask) != 0);
if((f != tape_eot) && (f)) {
- if(d_cmt_stop != NULL) d_cmt_stop->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_STOP, 1, 1);
}
}
#endif
#if defined(USE_SOUND_FILES)
if(tape_play != value) {
if(value) {
- if(d_cmt_play != NULL) d_cmt_play->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_PLAY, 1, 1);
} else {
- if(d_cmt_stop != NULL) d_cmt_stop->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_STOP, 1, 1);
}
}
#endif
#if defined(USE_SOUND_FILES)
if(tape_rec != value) {
if(value) {
- if(d_cmt_play != NULL) d_cmt_play->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_PLAY, 1, 1);
} else {
- if(d_cmt_stop != NULL) d_cmt_stop->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_STOP, 1, 1);
}
}
#endif
void SUB::close_tape()
{
#if defined(USE_SOUND_FILES)
- if(d_cmt_eject != NULL) d_cmt_eject->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
+ d_drec->write_signal(SIG_SOUNDER_ADD + DATAREC_SNDFILE_EJECT, 1, 1);
#endif
tape_play = tape_rec = tape_eot = tape_apss = false;
update_tape();
private:
DEVICE *d_pio, *d_rtc;
DATAREC *d_drec;
-#if defined(USE_SOUND_FILES)
- DEVICE *d_cmt_eject;
- //DEVICE *d_cmt_ffrew;
- DEVICE *d_cmt_play;
- DEVICE *d_cmt_stop;
-#endif
uint8_t p1_out, p1_in, p2_out, p2_in;
uint8_t portc;
public:
SUB(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu) {
set_device_name(_T("SUB SYSTEM"));
-#if defined(USE_SOUND_FILES)
- d_cmt_eject = NULL;
- //d_cmt_ffrew = NULL;
- d_cmt_play = NULL;
- d_cmt_stop = NULL;
-#endif
}
~SUB() {}
{
d_drec = device;
}
-#if defined(USE_SOUND_FILES)
- void set_context_cmt_eject(DEVICE* device)
- {
- d_cmt_eject = device;
- }
- //void set_context_cmt_ffrew(DEVICE* device)
- //{
- // d_cmt_ffrew = device;
- //}
- void set_context_cmt_play(DEVICE* device)
- {
- d_cmt_play = device;
- }
- void set_context_cmt_stop(DEVICE* device)
- {
- d_cmt_stop = device;
- }
-#endif
void play_tape(bool value);
void rec_tape(bool value);
void close_tape();
#include "../huc6280.h"
#include "../pcengine/pce.h"
#endif
-#if defined(USE_SOUND_FILES)
-#include "../wav_sounder.cpp"
-#endif
// ----------------------------------------------------------------------------
// initialize
mouse->set_device_name(_T("MOUSE I/F"));
#endif
#if defined(USE_SOUND_FILES)
- fdd_seek = new WAV_SOUNDER(this, emu);
- if(fdd_seek->load_data(_T("FDDSEEK.WAV"))) {
- fdc->set_context_seek(fdd_seek);
- event->set_context_sound(fdd_seek);
- }
-#endif
-#if defined(USE_SOUND_FILES)
- cmt_eject = new WAV_SOUNDER(this, emu);
- //cmt_ffrew = new WAV_SOUNDER(this, emu);
- cmt_play = new WAV_SOUNDER(this, emu);
- cmt_stop = new WAV_SOUNDER(this, emu);
- if(cmt_eject->load_data(_T("CMTEJECT.WAV"))) {
- event->set_context_sound(cmt_eject);
- }
- //if(cmt_ffrew->load_data(_T("CMTFF.WAV"))) {
- // event->set_context_sound(cmt_ffrew);
- //}
- if(cmt_play->load_data(_T("CMTPLAY.WAV"))) {
- event->set_context_sound(cmt_play);
- }
- if(cmt_stop->load_data(_T("CMTSTOP.WAV"))) {
- event->set_context_sound(cmt_stop);
+ if(fdc->load_sound_data(MB8877_SND_TYPE_SEEK, _T("FDDSEEK.WAV"))) {
+ event->set_context_sound(fdc);
}
+ drec->load_sound_data(DATAREC_SNDFILE_EJECT, _T("CMTEJECT.WAV"));
+ drec->load_sound_data(DATAREC_SNDFILE_PLAY, _T("CMTPLAY.WAV"));
+ drec->load_sound_data(DATAREC_SNDFILE_STOP, _T("CMTSTOP.WAV"));
#endif
if(pseudo_sub_cpu) {
psub = new PSUB(this, emu);
#if defined(_USE_QT)
psub->set_device_name(_T("PSEUDO SUB SYSTEM"));
#endif
-#if defined(USE_SOUND_FILES)
- psub->set_context_cmt_eject(cmt_eject);
- //psub->set_context_cmt_ffrew(cmt_ffrew);
- psub->set_context_cmt_play(cmt_play);
- psub->set_context_cmt_stop(cmt_stop);
-#endif
} else {
// sub cpu
cpu_sub = new MCS48(this, emu);
rtc_sub->set_device_name(_T("RTC(SUB SYSTEM)"));
sub->set_device_name(_T("SUB SYSTEM"));
#endif
-#if defined(USE_SOUND_FILES)
- sub->set_context_cmt_eject(cmt_eject);
- //sub->set_context_cmt_ffrew(cmt_ffrew);
- sub->set_context_cmt_play(cmt_play);
- sub->set_context_cmt_stop(cmt_stop);
-#endif
// keyboard
cpu_kbd = new MCS48(this, emu);
#if defined(USE_SOUND_FILES)
# if defined(_X1TWIN)
} else if(ch == 5) {
- if(fdd_seek != NULL) fdd_seek->set_volume(0, decibel_l, decibel_r);
+ fdc->set_volume(0, decibel_l, decibel_r);
} else if(ch == 6) {
- if(cmt_eject != NULL) cmt_eject->set_volume(0, decibel_l, decibel_r);
- //if(cmt_ffrew != NULL) cmt_ffrew->set_volume(0, decibel_l, decibel_r);
- if(cmt_play != NULL) cmt_play->set_volume(0, decibel_l, decibel_r);
- if(cmt_stop != NULL) cmt_stop->set_volume(0, decibel_l, decibel_r);
+ for(int i = 0; i < DATAREC_SNDFILE_END; i++) {
+ drec->set_volume(i + 2, decibel_l, decibel_r);
+ }
# else
} else if(ch == 4) {
- if(fdd_seek != NULL) fdd_seek->set_volume(0, decibel_l, decibel_r);
+ fdc->set_volume(0, decibel_l, decibel_r);
} else if(ch == 5) {
- if(cmt_eject != NULL) cmt_eject->set_volume(0, decibel_l, decibel_r);
- //if(cmt_ffrew != NULL) cmt_ffrew->set_volume(0, decibel_l, decibel_r);
- if(cmt_play != NULL) cmt_play->set_volume(0, decibel_l, decibel_r);
- if(cmt_stop != NULL) cmt_stop->set_volume(0, decibel_l, decibel_r);
+ for(int i = 0; i < DATAREC_SNDFILE_END; i++) {
+ drec->set_volume(i + 2, decibel_l, decibel_r);
+ }
# endif
#endif
}
{
drec->set_ff_rew(0);
drec->set_remote(true);
-#if defined(USE_SOUND_FILES)
- if(cmt_play != NULL) cmt_play->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
-#endif
}
void VM::push_stop()
{
drec->set_remote(false);
-#if defined(USE_SOUND_FILES)
- if(cmt_stop != NULL) cmt_stop->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
-#endif
}
void VM::push_fast_forward()
{
drec->set_ff_rew(1);
drec->set_remote(true);
-#if defined(USE_SOUND_FILES)
- //if(cmt_ffrew != NULL) cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
-#endif
}
void VM::push_fast_rewind()
{
drec->set_ff_rew(-1);
drec->set_remote(true);
-#if defined(USE_SOUND_FILES)
- //if(cmt_ffrew != NULL) cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
-#endif
}
void VM::push_apss_forward()
{
drec->do_apss(1);
-#if defined(USE_SOUND_FILES)
- //if(cmt_ffrew != NULL) cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
-#endif
}
void VM::push_apss_rewind()
{
drec->do_apss(-1);
-#if defined(USE_SOUND_FILES)
- //if(cmt_ffrew != NULL) cmt_ffrew->write_signal(SIG_WAV_SOUNDER_ADD, 1, 1);
-#endif
}
bool VM::is_frame_skippable()
class HUC6280;
class PCE;
#endif
-#if defined(USE_SOUND_FILES)
-class WAV_SOUNDER;
-#endif
class VM
{
protected:
#ifdef _X1TURBO_FEATURE
Z80DMA* dma;
#endif
-#if defined(USE_SOUND_FILES)
- WAV_SOUNDER *fdd_seek;
- WAV_SOUNDER *cmt_eject;
- //WAV_SOUNDER *cmt_ffrew;
- WAV_SOUNDER *cmt_play;
- WAV_SOUNDER *cmt_stop;
-#endif
DISPLAY* display;
EMM* emm;
FLOPPY* floppy;