-arm7: Added optional logging for Windows CE calls. [Ryan Holtz]

-uda1344: Added skeleton audio device for Philips UDA13444 Codec. [Ryan Holtz]

-sa1111: Hooked up basic L3 audio transceiver support. [Ryan Holtz]
This commit is contained in:
Ryan Holtz 2020-12-31 19:18:24 +01:00
parent eb602d3871
commit 139f044859
12 changed files with 1498 additions and 56 deletions

View File

@ -1606,3 +1606,15 @@ if (SOUNDS["TT5665"]~=null) then
MAME_DIR .. "src/devices/sound/tt5665.h",
}
end
---------------------------------------------------
--
--@src/devices/sound/uda1344.h,SOUNDS["UDA1344"] = true
---------------------------------------------------
if (SOUNDS["UDA1344"]~=null) then
files {
MAME_DIR .. "src/devices/sound/uda1344.cpp",
MAME_DIR .. "src/devices/sound/uda1344.h",
}
end

View File

@ -290,6 +290,7 @@ SOUNDS["S_DSP"] = true
SOUNDS["KS0164"] = true
SOUNDS["TT5665"] = true
--SOUNDS["RP2C33_SOUND"] = true
--SOUNDS["UDA1344"] = true
--------------------------------------------------
-- specify available video cores

View File

@ -314,6 +314,7 @@ SOUNDS["S_DSP"] = true
SOUNDS["ROLANDPCM"] = true
--SOUNDS["TT5665"] = true
SOUNDS["RP2C33_SOUND"] = true
SOUNDS["UDA1344"] = true
--------------------------------------------------
-- specify available video cores

File diff suppressed because it is too large Load Diff

View File

@ -74,7 +74,7 @@ protected:
ARM9_COPRO_ID_STEP_SA1110_A0 = 0,
ARM9_COPRO_ID_STEP_SA1110_B0 = 4,
ARM9_COPRO_ID_STEP_SA1110_B1 = 5,
ARM9_COPRO_ID_STEP_SA1110_B2 = 6,
ARM9_COPRO_ID_STEP_SA1110_B2 = 8,
ARM9_COPRO_ID_STEP_SA1110_B4 = 8,
ARM9_COPRO_ID_STEP_PXA255_A0 = 6,
@ -146,10 +146,21 @@ protected:
uint32_t m_r[/*NUM_REGS*/37];
void translate_insn_command(int ref, const std::vector<std::string> &params);
void translate_data_command(int ref, const std::vector<std::string> &params);
void translate_command(int ref, const std::vector<std::string> &params, int intention);
void update_insn_prefetch(uint32_t curr_pc);
bool insn_fetch_thumb(uint32_t pc, uint32_t &out_insn);
bool insn_fetch_arm(uint32_t pc, uint32_t &out_insn);
void add_ce_kernel_addr(offs_t addr, std::string value);
void init_ce_kernel_addrs();
void print_ce_kernel_address(const offs_t addr);
std::string m_ce_kernel_addrs[0x10400];
bool m_ce_kernel_addr_present[0x10400];
uint32_t m_insn_prefetch_depth;
uint32_t m_insn_prefetch_count;
uint32_t m_insn_prefetch_index;
@ -170,12 +181,10 @@ protected:
uint32_t base_addr;
uint8_t type;
};
tlb_entry m_dtlb_entries[64];
tlb_entry m_itlb_entries[64];
uint8_t m_dtlb_entry_start[32];
uint8_t m_itlb_entry_start[32];
uint8_t m_dtlb_entry_index[32];
uint8_t m_itlb_entry_index[32];
tlb_entry m_dtlb_entries[0x2000];
tlb_entry m_itlb_entries[0x2000];
uint8_t m_dtlb_entry_index[0x1000];
uint8_t m_itlb_entry_index[0x1000];
bool m_pendingIrq;
bool m_pendingFiq;

View File

@ -183,25 +183,24 @@ int arm7_cpu_device::loadInc(uint32_t pat, uint32_t rbv, uint32_t s, int mode)
{
if ((pat >> i) & 1)
{
if (!m_pendingAbtD) // "Overwriting of registers stops when the abort happens."
data = READ32(rbv += 4);
if (m_pendingAbtD) // "Overwriting of registers stops when the abort happens."
return result;
if (i == 15)
{
data = READ32(rbv += 4);
if (i == 15)
{
if (s) /* Pull full contents from stack */
SetModeRegister(mode, 15, data);
else if (MODE32) /* Pull only address, preserve mode & status flags */
SetModeRegister(mode, 15, data);
else
{
SetModeRegister(mode, 15, (GetModeRegister(mode, 15) & ~0x03FFFFFC) | (data & 0x03FFFFFC));
}
}
if (s) /* Pull full contents from stack */
SetModeRegister(mode, 15, data);
else if (MODE32) /* Pull only address, preserve mode & status flags */
SetModeRegister(mode, 15, data);
else
{
SetModeRegister(mode, i, data);
SetModeRegister(mode, 15, (GetModeRegister(mode, 15) & ~0x03FFFFFC) | (data & 0x03FFFFFC));
}
}
else
{
SetModeRegister(mode, i, data);
}
result++;
}
}
@ -220,25 +219,24 @@ int arm7_cpu_device::loadDec(uint32_t pat, uint32_t rbv, uint32_t s, int mode)
{
if ((pat >> i) & 1)
{
if (!m_pendingAbtD) // "Overwriting of registers stops when the abort happens."
data = READ32(rbv -= 4);
if (m_pendingAbtD) // "Overwriting of registers stops when the abort happens."
return result;
if (i == 15)
{
data = READ32(rbv -= 4);
if (i == 15)
{
if (s) /* Pull full contents from stack */
SetModeRegister(mode, 15, data);
else if (MODE32) /* Pull only address, preserve mode & status flags */
SetModeRegister(mode, 15, data);
else
{
SetModeRegister(mode, 15, (GetModeRegister(mode, 15) & ~0x03FFFFFC) | (data & 0x03FFFFFC));
}
}
if (s) /* Pull full contents from stack */
SetModeRegister(mode, 15, data);
else if (MODE32) /* Pull only address, preserve mode & status flags */
SetModeRegister(mode, 15, data);
else
{
SetModeRegister(mode, i, data);
SetModeRegister(mode, 15, (GetModeRegister(mode, 15) & ~0x03FFFFFC) | (data & 0x03FFFFFC));
}
}
else
{
SetModeRegister(mode, i, data);
}
result++;
}
}
@ -260,6 +258,8 @@ int arm7_cpu_device::storeInc(uint32_t pat, uint32_t rbv, int mode)
LOGMASKED(LOG_OPS, "%08x: StoreInc on R15\n", R15);
#endif
WRITE32(rbv += 4, GetModeRegister(mode, i));
if (m_pendingAbtD)
return result;
result++;
}
}
@ -271,6 +271,7 @@ int arm7_cpu_device::storeDec(uint32_t pat, uint32_t rbv, int mode)
{
// pre-count the # of registers being stored
int const result = population_count_32(pat & 0x0000ffff);
int actual_result = 0;
// adjust starting address
rbv -= (result << 2);
@ -284,7 +285,10 @@ int arm7_cpu_device::storeDec(uint32_t pat, uint32_t rbv, int mode)
LOGMASKED(LOG_OPS, "%08x: StoreDec on R15\n", R15);
#endif
WRITE32(rbv, GetModeRegister(mode, i));
if (m_pendingAbtD)
return actual_result;
rbv += 4;
actual_result++;
}
}
return result;
@ -815,14 +819,20 @@ void arm7_cpu_device::HandleSwap(uint32_t insn)
if (insn & 0x400000)
{
tmp = READ8(rn);
WRITE8(rn, rm);
SetRegister(rd, tmp);
if (!m_pendingAbtD)
{
WRITE8(rn, rm);
SetRegister(rd, tmp);
}
}
else
{
tmp = READ32(rn);
WRITE32(rn, rm);
SetRegister(rd, tmp);
if (!m_pendingAbtD)
{
WRITE32(rn, rm);
SetRegister(rd, tmp);
}
}
R15 += 4;

View File

@ -1618,7 +1618,10 @@ uint32_t sa1110_periphs_device::intc_r(offs_t offset, uint32_t mem_mask)
switch (offset)
{
case REG_ICIP:
LOGMASKED(LOG_INTC, "%s: intc_r: Interrupt Controller IRQ Pending Register: %08x & %08x\n", machine().describe_context(), m_intc_regs.icip, mem_mask);
if (m_intc_regs.icip != 0x04000000)
{
LOGMASKED(LOG_INTC, "%s: intc_r: Interrupt Controller IRQ Pending Register: %08x & %08x\n", machine().describe_context(), m_intc_regs.icip, mem_mask);
}
return m_intc_regs.icip;
case REG_ICMR:
LOGMASKED(LOG_INTC, "%s: intc_r: Interrupt Controller Mask Register: %08x & %08x\n", machine().describe_context(), m_intc_regs.icmr, mem_mask);

View File

@ -32,6 +32,8 @@ sa1111_device::sa1111_device(const machine_config &mconfig, const char *tag, dev
: device_t(mconfig, SA1111, tag, owner, clock)
, m_gpio_out(*this)
, m_ssp_out(*this)
, m_l3_addr_out(*this)
, m_l3_data_out(*this)
{
}
@ -434,6 +436,12 @@ void sa1111_device::usb_int_test_w(offs_t offset, uint32_t data, uint32_t mem_ma
*/
WRITE_LINE_MEMBER(sa1111_device::l3wd_in)
{
if (state)
m_audio_regs.sasr0 |= (1 << SASR0_L3WD_BIT);
}
TIMER_CALLBACK_MEMBER(sa1111_device::audio_rx_callback)
{
}
@ -617,7 +625,7 @@ void sa1111_device::sacr0_w(offs_t offset, uint32_t data, uint32_t mem_mask)
void sa1111_device::sacr1_w(offs_t offset, uint32_t data, uint32_t mem_mask)
{
LOGMASKED(LOG_AUDIO, "%s: sacr1_w: Serial Audio Alternate Mode Control Register = %08x & %08x\n", machine().describe_context(), data, mem_mask);
LOGMASKED(LOG_AUDIO, "%s: Alternade Mode Operation: %s\n", machine().describe_context(), BIT(data, SACR1_AMSL_BIT) ? "MSB-Justified" : "I2S");
LOGMASKED(LOG_AUDIO, "%s: Alternate Mode Operation: %s\n", machine().describe_context(), BIT(data, SACR1_AMSL_BIT) ? "MSB-Justified" : "I2S");
LOGMASKED(LOG_AUDIO, "%s: Enable L3 Control Bus: %d\n", machine().describe_context(), BIT(data, SACR1_L3EN_BIT));
LOGMASKED(LOG_AUDIO, "%s: L3 Control Bus Data Multi-Byte Transfer: %s\n", machine().describe_context(), BIT(data, SACR1_L3MB_BIT) ? "Multiple-Byte" : "Last Byte");
LOGMASKED(LOG_AUDIO, "%s: Disable Recording Function: %d\n", machine().describe_context(), BIT(data, SACR1_DREC_BIT));
@ -676,12 +684,14 @@ void sa1111_device::l3car_w(offs_t offset, uint32_t data, uint32_t mem_mask)
{
LOGMASKED(LOG_AUDIO, "%s: l3car_w: L3 Control Bus Address Register = %08x & %08x\n", machine().describe_context(), data, mem_mask);
COMBINE_DATA(&m_audio_regs.l3car);
m_l3_addr_out((uint8_t)data);
}
void sa1111_device::l3cdr_w(offs_t offset, uint32_t data, uint32_t mem_mask)
{
LOGMASKED(LOG_AUDIO, "%s: l3cdr_w: L3 Control Bus Data Register = %08x & %08x\n", machine().describe_context(), data, mem_mask);
COMBINE_DATA(&m_audio_regs.l3cdr);
m_l3_data_out((uint8_t)data);
}
void sa1111_device::accar_w(offs_t offset, uint32_t data, uint32_t mem_mask)
@ -1633,6 +1643,8 @@ void sa1111_device::device_start()
m_gpio_out.resolve_all_safe();
m_ssp_out.resolve_safe();
m_l3_addr_out.resolve_safe();
m_l3_data_out.resolve_safe();
}
void sa1111_device::device_reset()
@ -1725,7 +1737,7 @@ void sa1111_device::device_reset()
m_card_regs.pccr = 0;
m_card_regs.pcssr = 0;
m_card_regs.pcsr = 0x0000000f;
m_card_regs.pcsr = 0x0000000c;
}
void sa1111_device::device_add_mconfig(machine_config &config)

View File

@ -28,6 +28,11 @@ public:
void ssp_in(uint16_t data) { ssp_rx_fifo_push(data); }
auto ssp_out() { return m_ssp_out.bind(); }
auto l3_addr_out() { return m_l3_addr_out.bind(); }
auto l3_data_out() { return m_l3_data_out.bind(); }
DECLARE_WRITE_LINE_MEMBER(l3wd_in);
void map(address_map &map);
protected:
@ -198,6 +203,12 @@ protected:
void gpio_update_direction(const uint32_t block, const uint32_t old_dir);
void gpio_update_outputs(const uint32_t block, const uint32_t old_latch);
// interrupt lines
enum : uint32_t
{
INT_AUDDTS = 40
};
// register contents
enum : uint32_t
{
@ -584,6 +595,8 @@ protected:
devcb_write_line::array<24> m_gpio_out;
devcb_write16 m_ssp_out;
devcb_write8 m_l3_addr_out;
devcb_write8 m_l3_data_out;
};
DECLARE_DEVICE_TYPE(SA1111, sa1111_device)

View File

@ -0,0 +1,174 @@
// license:BSD-3-Clause
// copyright-holders:Ryan Holtz
/***************************************************************************
Philips UDA1344 Stereo Audio Codec skeleton
****************************************************************************/
#include "emu.h"
#include "sound/uda1344.h"
#define LOG_ADDR (1 << 1)
#define LOG_STATUS_REG (1 << 2)
#define LOG_DATA_REG (1 << 3)
#define LOG_ALL (LOG_ADDR | LOG_STATUS_REG | LOG_DATA_REG)
#define VERBOSE (LOG_ALL)
#include "logmacro.h"
// device type definition
DEFINE_DEVICE_TYPE(UDA1344, uda1344_device, "ud1344", "Philips UDA1344 Codec")
uda1344_device::uda1344_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
: device_t(mconfig, UDA1344, tag, owner, clock)
, device_sound_interface(mconfig, *this)
, m_stream(nullptr)
, m_data_transfer_mode(0)
, m_status_reg(0)
, m_volume_reg(0)
, m_equalizer_reg(0)
, m_filter_reg(0)
, m_power_reg(0)
, m_l3_ack_out(*this)
{
}
void uda1344_device::device_start()
{
m_stream = stream_alloc(0, 2, 44100);
save_item(NAME(m_data_transfer_mode));
save_item(NAME(m_status_reg));
save_item(NAME(m_volume_reg));
save_item(NAME(m_equalizer_reg));
save_item(NAME(m_filter_reg));
save_item(NAME(m_power_reg));
m_l3_ack_out.resolve_safe();
}
void uda1344_device::device_reset()
{
m_data_transfer_mode = 0;
m_status_reg = 0;
m_volume_reg = 0;
m_equalizer_reg = 0;
m_filter_reg = 0;
m_power_reg = 0;
}
void uda1344_device::sound_stream_update(sound_stream &stream, std::vector<read_stream_view> const &inputs, std::vector<write_stream_view> &outputs)
{
auto &buffer = outputs[0];
/* fill in the samples */
for (int sampindex = 0; sampindex < buffer.samples(); sampindex++)
{
// TODO: Generate audio
buffer.put(sampindex, 0);
}
}
void uda1344_device::l3_addr_w(offs_t offset, uint8_t data)
{
// Check for L3 address match, ignore if not addressed to us
if ((data & CHIP_ADDR_MASK) != CHIP_ADDR)
{
LOGMASKED(LOG_ADDR, "%s: L3 address %02x received, ignoring due to address mismatch\n", machine().describe_context(), data);
return;
}
m_data_transfer_mode = data & ~CHIP_ADDR_MASK;
LOGMASKED(LOG_ADDR, "%s: L3 address %02x received, preparing to receive data\n", machine().describe_context(), data);
}
void uda1344_device::l3_data_w(offs_t offset, uint8_t data)
{
// Registers with bit 0 of the address set are unused
if (BIT(m_data_transfer_mode, 0))
{
LOGMASKED(LOG_DATA_REG, "%s: Data transfer mode has bit 0 set, ignoring L3 data write\n", machine().describe_context());
return;
}
if (BIT(m_data_transfer_mode, 1))
{
// Status transfer type
static const char *const s_clock_names[4] = { "512*freq", "384*freq", "256*freq", "unused" };
static const char *const s_format_names[8] =
{
"I2S-bus",
"LSB-justified 16-bits",
"LSB-justified 18-bits",
"LSB-justified 20-bits",
"MSB-justified",
"Input LSB-justified 16-bits / Output MSB-justified",
"Input LSB-justified 18-bits / Output MSB-justified",
"Input LSB-justified 20-bits / Output MSB-justified"
};
const uint8_t reg_bits = data & STATUS_REG_MASK;
LOGMASKED(LOG_STATUS_REG, "%s: Status register data: %02x (system clock: %s, format: %s, DC filtering: %s)\n", machine().describe_context(), reg_bits,
s_clock_names[(reg_bits & STATUS_SC_MASK) >> STATUS_SC_BIT],
s_format_names[(reg_bits & STATUS_IF_MASK) >> STATUS_IF_BIT],
BIT(reg_bits, STATUS_DC_BIT) ? "on" : "off");
m_status_reg = reg_bits;
}
else
{
// Data transfer type
switch ((data & REG_TYPE_MASK) >> REG_TYPE_BIT)
{
case VOLUME_REG:
{
const uint8_t reg_bits = data & VOLUME_REG_MASK;
if (reg_bits < 2)
LOGMASKED(LOG_DATA_REG, "%s: Volume register data: %02x, no attenuation\n", machine().describe_context(), reg_bits);
else if (reg_bits >= 62)
LOGMASKED(LOG_DATA_REG, "%s: Volume register data: %02x, full attenuation\n", machine().describe_context(), reg_bits);
else
LOGMASKED(LOG_DATA_REG, "%s: Volume register data: %02x, -%ddB attenuation\n", machine().describe_context(), reg_bits, reg_bits - 1);
m_volume_reg = reg_bits;
break;
}
case EQUALIZER_REG:
{
const uint8_t reg_bits = data & EQUALIZER_REG_MASK;
LOGMASKED(LOG_DATA_REG, "%s: Equalizer register data: %02x (bass boost %02x, treble %d)\n", machine().describe_context(), reg_bits,
(reg_bits & EQUALIZER_BB_MASK) >> EQUALIZER_BB_BIT, (reg_bits & EQUALIZER_TR_MASK) >> EQUALIZER_TR_BIT);
m_equalizer_reg = reg_bits;
break;
}
case FILTER_REG:
{
static const char *const s_de_names[4] = { "none", "32kHz", "44.1kHz", "48kHz" };
static const char *const s_mode_names[4] = { "flat", "min(1)", "min(2)", "max" };
const uint8_t reg_bits = data & FILTER_REG_MASK;
LOGMASKED(LOG_DATA_REG, "%s: Filter register data: %02x (de-emphasis %s, mute %d, mode %s)\n", machine().describe_context(), reg_bits,
s_de_names[(reg_bits & FILTER_DE_MASK) >> FILTER_DE_BIT], BIT(reg_bits, FILTER_MT_BIT),
s_mode_names[(reg_bits & FILTER_MODE_MASK) >> FILTER_MODE_BIT]);
m_filter_reg = reg_bits;
break;
}
case POWER_REG:
{
const uint8_t reg_bits = data & POWER_REG_MASK;
LOGMASKED(LOG_DATA_REG, "%s: Power register data: %02x (ADC %s, DAC %s)\n", machine().describe_context(), reg_bits,
BIT(reg_bits, POWER_ADC_BIT) ? "on" : "off",
BIT(reg_bits, POWER_DAC_BIT) ? "on" : "off");
m_power_reg = reg_bits;
break;
}
}
}
// Pulse acknowledge line
m_l3_ack_out(1);
m_l3_ack_out(0);
}

View File

@ -0,0 +1,85 @@
// license:BSD-3-Clause
// copyright-holders:Ryan Holtz
/***************************************************************************
Philips UDA1344 Stereo Audio Codec skeleton
****************************************************************************/
#ifndef MAME_SOUND_UDA1344_H
#define MAME_SOUND_UDA1344_H
#pragma once
class uda1344_device : public device_t, public device_sound_interface
{
public:
uda1344_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock = 0);
void l3_addr_w(offs_t offset, uint8_t data);
void l3_data_w(offs_t offset, uint8_t data);
auto l3_ack_out() { return m_l3_ack_out.bind(); }
protected:
// device-level overrides
virtual void device_start() override;
virtual void device_reset() override;
// sound stream update overrides
virtual void sound_stream_update(sound_stream &stream, std::vector<read_stream_view> const &inputs, std::vector<write_stream_view> &outputs) override;
enum : uint8_t
{
CHIP_ADDR_MASK = 0xfc,
CHIP_ADDR = 0x14,
REG_TYPE_MASK = 0xc0,
REG_TYPE_BIT = 6,
VOLUME_REG = 0x00,
VOLUME_REG_MASK = 0x3f,
EQUALIZER_REG = 0x01,
EQUALIZER_REG_MASK = 0x3f,
EQUALIZER_BB_MASK = 0x3c,
EQUALIZER_BB_BIT = 2,
EQUALIZER_TR_MASK = 0x03,
EQUALIZER_TR_BIT = 0,
FILTER_REG = 0x02,
FILTER_REG_MASK = 0x1f,
FILTER_DE_MASK = 0x18,
FILTER_DE_BIT = 3,
FILTER_MT_BIT = 2,
FILTER_MODE_MASK = 0x03,
FILTER_MODE_BIT = 0,
POWER_REG = 0x03,
POWER_REG_MASK = 0x03,
POWER_ADC_BIT = 1,
POWER_DAC_BIT = 0,
STATUS_REG_MASK = 0x3f,
STATUS_SC_MASK = 0x30,
STATUS_SC_BIT = 4,
STATUS_IF_MASK = 0xe0,
STATUS_IF_BIT = 1,
STATUS_DC_BIT = 0
};
sound_stream *m_stream;
uint8_t m_data_transfer_mode;
uint8_t m_status_reg;
uint8_t m_volume_reg;
uint8_t m_equalizer_reg;
uint8_t m_filter_reg;
uint8_t m_power_reg;
devcb_write_line m_l3_ack_out;
};
DECLARE_DEVICE_TYPE(UDA1344, uda1344_device)
#endif // MAME_SOUND_UDA1344_H

View File

@ -14,6 +14,7 @@
#include "cpu/arm7/arm7core.h"
#include "machine/sa1110.h"
#include "machine/sa1111.h"
#include "sound/uda1344.h"
#include "video/sed1356.h"
#include "screen.h"
#include "emupal.h"
@ -40,6 +41,7 @@ public:
, m_companion(*this, "companion")
, m_eeprom_data(*this, "eeprom")
, m_epson(*this, "epson")
, m_codec(*this, "codec")
, m_kbd_port(*this, "KBD0")
{ }
@ -85,6 +87,7 @@ protected:
required_device<sa1111_device> m_companion;
required_region_ptr<uint8_t> m_eeprom_data;
required_device<sed1356_device> m_epson;
required_device<uda1344_device> m_codec;
required_ioport m_kbd_port;
@ -299,6 +302,11 @@ void jornada_state::jornada720(machine_config &config)
SA1111(config, m_companion);
m_companion->ssp_out().set(FUNC(jornada_state::eeprom_cmd_received));
m_companion->l3_addr_out().set(m_codec, FUNC(uda1344_device::l3_addr_w));
m_companion->l3_data_out().set(m_codec, FUNC(uda1344_device::l3_data_w));
UDA1344(config, m_codec);
m_codec->l3_ack_out().set(m_companion, FUNC(sa1111_device::l3wd_in));
SED1356(config, m_epson);
m_epson->set_screen("screen");