summaryrefslogtreecommitdiffstatshomepage
path: root/src/devices/sound/ad1848.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/devices/sound/ad1848.cpp')
-rw-r--r--src/devices/sound/ad1848.cpp52
1 files changed, 32 insertions, 20 deletions
diff --git a/src/devices/sound/ad1848.cpp b/src/devices/sound/ad1848.cpp
index 5db5b3ded2d..b9395d23360 100644
--- a/src/devices/sound/ad1848.cpp
+++ b/src/devices/sound/ad1848.cpp
@@ -5,9 +5,8 @@
// TODO: Emulate pin-compatible Crystal Semiconductor CS4231 and its extra Mode 2 features
#include "emu.h"
-#include "sound/ad1848.h"
+#include "ad1848.h"
-#include "sound/volt_reg.h"
#include "speaker.h"
@@ -24,27 +23,21 @@ ad1848_device::ad1848_device(const machine_config &mconfig, const char *tag, dev
void ad1848_device::device_add_mconfig(machine_config &config)
{
- SPEAKER(config, "lspeaker").front_left();
- SPEAKER(config, "rspeaker").front_right();
- DAC_16BIT_R2R(config, m_ldac, 0).add_route(ALL_OUTPUTS, "lspeaker", 0.5); // unknown DAC
- DAC_16BIT_R2R(config, m_rdac, 0).add_route(ALL_OUTPUTS, "rspeaker", 0.5); // unknown DAC
- voltage_regulator_device &vref(VOLTAGE_REGULATOR(config, "vref", 0));
- vref.add_route(0, "ldac", 1.0, DAC_VREF_POS_INPUT);
- vref.add_route(0, "ldac", -1.0, DAC_VREF_NEG_INPUT);
- vref.add_route(0, "rdac", 1.0, DAC_VREF_POS_INPUT);
- vref.add_route(0, "rdac", -1.0, DAC_VREF_NEG_INPUT);
+ SPEAKER(config, "speaker", 2).front();
+ DAC_16BIT_R2R(config, m_ldac, 0).add_route(ALL_OUTPUTS, "speaker", 0.5, 0); // unknown DAC
+ DAC_16BIT_R2R(config, m_rdac, 0).add_route(ALL_OUTPUTS, "speaker", 0.5, 1); // unknown DAC
}
void ad1848_device::device_start()
{
- m_timer = timer_alloc(0, nullptr);
- m_irq_cb.resolve_safe();
- m_drq_cb.resolve_safe();
+ m_timer = timer_alloc(FUNC(ad1848_device::update_tick), this);
+
save_item(NAME(m_regs.idx));
save_item(NAME(m_addr));
save_item(NAME(m_stat));
save_item(NAME(m_sam_cnt));
+ save_item(NAME(m_calibration_cycles));
save_item(NAME(m_samples));
save_item(NAME(m_count));
save_item(NAME(m_play));
@@ -59,12 +52,13 @@ void ad1848_device::device_reset()
m_addr = 0;
m_stat = 0;
m_sam_cnt = 0;
+ m_calibration_cycles = 0;
m_samples = 0;
m_play = false;
m_irq = false;
}
-READ8_MEMBER(ad1848_device::read)
+uint8_t ad1848_device::read(offs_t offset)
{
switch(offset)
{
@@ -80,7 +74,7 @@ READ8_MEMBER(ad1848_device::read)
return 0;
}
-WRITE8_MEMBER(ad1848_device::write)
+void ad1848_device::write(offs_t offset, uint8_t data)
{
static constexpr int div_factor[] = {3072, 1536, 896, 768, 448, 384, 512, 2560};
switch(offset)
@@ -103,9 +97,17 @@ WRITE8_MEMBER(ad1848_device::write)
break;
case 9:
{
+ // auto-calibration
+ if (m_mce && BIT(data, 3))
+ {
+ logerror("set auto-calibration\n");
+ m_regs.init |= 0x20;
+ m_calibration_cycles = 384;
+ }
+
m_play = (data & 1) ? true : false;
// FIXME: provide external configuration for XTAL1 (24.576 MHz) and XTAL2 (16.9344 MHz) inputs
- attotime rate = m_play ? attotime::from_hz(((m_regs.dform & 1) ? 16.9344_MHz_XTAL : 24.576_MHz_XTAL)
+ attotime rate = (m_play || BIT(m_regs.init, 5)) ? attotime::from_hz(((m_regs.dform & 1) ? 16.9344_MHz_XTAL : 24.576_MHz_XTAL)
/ div_factor[(m_regs.dform >> 1) & 7]) : attotime::never;
m_timer->adjust(rate, 0 , rate);
m_drq_cb(m_play ? ASSERT_LINE : CLEAR_LINE);
@@ -127,13 +129,13 @@ WRITE8_MEMBER(ad1848_device::write)
}
}
-READ8_MEMBER(ad1848_device::dack_r)
+uint8_t ad1848_device::dack_r()
{
m_drq_cb(CLEAR_LINE);
return 0; // not implemented
}
-WRITE8_MEMBER(ad1848_device::dack_w)
+void ad1848_device::dack_w(uint8_t data)
{
if(!m_play)
return;
@@ -162,8 +164,18 @@ WRITE8_MEMBER(ad1848_device::dack_w)
m_drq_cb(CLEAR_LINE);
}
-void ad1848_device::device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr)
+TIMER_CALLBACK_MEMBER(ad1848_device::update_tick)
{
+ // auto-calibration
+ if (BIT(m_regs.init, 5))
+ {
+ if (--m_calibration_cycles == 0)
+ {
+ logerror("calibration finished\n");
+ m_regs.init &= ~0x20;
+ }
+ }
+
if(!m_play)
return;
switch(m_regs.dform >> 4)