summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/devices/cpu/sparc/mb86901.cpp8
-rw-r--r--src/devices/cpu/sparc/sparc.h33
-rw-r--r--src/devices/machine/timekpr.cpp16
-rw-r--r--src/devices/machine/timekpr.h11
-rw-r--r--src/mame/drivers/sun4.cpp779
-rw-r--r--src/osd/modules/render/bgfx/shaders/chains/crt/fs_crt-caligari.sc123
-rw-r--r--src/osd/modules/render/bgfx/shaders/chains/crt/varying.def.sc7
-rw-r--r--src/osd/modules/render/bgfx/shaders/chains/crt/vs_crt-caligari.sc45
8 files changed, 792 insertions, 230 deletions
diff --git a/src/devices/cpu/sparc/mb86901.cpp b/src/devices/cpu/sparc/mb86901.cpp
index ee08106e260..8ed13db2778 100644
--- a/src/devices/cpu/sparc/mb86901.cpp
+++ b/src/devices/cpu/sparc/mb86901.cpp
@@ -641,6 +641,10 @@ void mb86901_device::execute_set_input(int inputnum, int state)
case SPARC_MAE:
m_mae = (state != 0) ? 1 : 0;
break;
+
+ case SPARC_RESET:
+ m_bp_reset_in = (state != 0) ? 1 : 0;
+ break;
}
}
@@ -2558,7 +2562,6 @@ void mb86901_device::select_trap()
if (m_reset_trap)
{
- m_reset_trap = 0;
m_trap = 0;
return;
}
@@ -2958,7 +2961,9 @@ void mb86901_device::execute_step()
if (m_bp_reset_in)
{
m_execute_mode = 0;
+ m_error_mode = 0;
m_reset_mode = 1;
+ printf("Entering reset mode\n");
return;
}
else if ((PSR & PSR_ET_MASK) && (m_bp_irl == 15 || m_bp_irl > ((PSR & PSR_PIL_MASK) >> PSR_PIL_SHIFT)))
@@ -3045,6 +3050,7 @@ void mb86901_device::reset_step()
m_execute_mode = 1;
m_trap = 1;
m_reset_trap = 1;
+ printf("m_bp_reset_in is false, resetting\n");
}
}
diff --git a/src/devices/cpu/sparc/sparc.h b/src/devices/cpu/sparc/sparc.h
index d23f032fe9a..fa8b9dd234b 100644
--- a/src/devices/cpu/sparc/sparc.h
+++ b/src/devices/cpu/sparc/sparc.h
@@ -18,36 +18,6 @@
#include <map>
#endif
-#define SPARC_NO_TRAP 256
-#define SPARC_RESET 0
-#define SPARC_INSTRUCTION_ACCESS_EXCEPTION 1
-#define SPARC_ILLEGAL_INSTRUCTION 2
-#define SPARC_PRIVILEGED_INSTRUCTION 3
-#define SPARC_FP_DISABLED 4
-#define SPARC_WINDOW_OVERFLOW 5
-#define SPARC_WINDOW_UNDERFLOW 6
-#define SPARC_MEM_ADDRESS_NOT_ALIGNED 7
-#define SPARC_FLOATING_POINT_EXCEPTION 8
-#define SPARC_DATA_ACCESS_EXCEPTION 9
-#define SPARC_TAG_OVERFLOW 10
-#define SPARC_INT1 17
-#define SPARC_INT2 18
-#define SPARC_INT3 19
-#define SPARC_INT4 20
-#define SPARC_INT5 21
-#define SPARC_INT6 22
-#define SPARC_INT7 23
-#define SPARC_INT8 24
-#define SPARC_INT9 25
-#define SPARC_INT10 26
-#define SPARC_INT11 27
-#define SPARC_INT12 28
-#define SPARC_INT13 29
-#define SPARC_INT14 30
-#define SPARC_INT15 31
-#define SPARC_TRAP_INSTRUCTION 128
-
-#define SPARC_FPU_SEQUENCE_ERROR
// TODO: when there are more SPARC CPUs, move setter to a base class
#define MCFG_SPARC_ADD_ASI_DESC(desc) \
mb86901_device::add_asi_desc(*device, desc);
@@ -316,7 +286,8 @@ enum
SPARC_IRQ13,
SPARC_IRQ14,
SPARC_NMI,
- SPARC_MAE
+ SPARC_MAE,
+ SPARC_RESET
};
#endif /* __SPARC_H__ */
diff --git a/src/devices/machine/timekpr.cpp b/src/devices/machine/timekpr.cpp
index 06aba0b7221..4b87d43ff69 100644
--- a/src/devices/machine/timekpr.cpp
+++ b/src/devices/machine/timekpr.cpp
@@ -10,6 +10,7 @@
- M48T37
- M48T58
- MK48T08
+ - MK48T12
***************************************************************************/
@@ -23,6 +24,7 @@ const device_type M48T35 = &device_creator<m48t35_device>;
const device_type M48T37 = &device_creator<m48t37_device>;
const device_type M48T58 = &device_creator<m48t58_device>;
const device_type MK48T08 = &device_creator<mk48t08_device>;
+const device_type MK48T12 = &device_creator<mk48t12_device>;
/***************************************************************************
@@ -202,6 +204,20 @@ mk48t08_device::mk48t08_device(const machine_config &mconfig, const char *tag, d
m_offset_flags = 0x1ff0;
}
+mk48t12_device::mk48t12_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
+ : timekeeper_device(mconfig, MK48T12, "MK48T12 Timekeeper", tag, owner, clock, "m48t12", __FILE__, 0x2000)
+{
+ m_offset_control = 0x7f8;
+ m_offset_seconds = 0x7f9;
+ m_offset_minutes = 0x7fa;
+ m_offset_hours = 0x7fb;
+ m_offset_day = 0x7fc;
+ m_offset_date = 0x7fd;
+ m_offset_month = 0x7fe;
+ m_offset_year = 0x7ff;
+ m_offset_century = -1;
+}
+
//-------------------------------------------------
// device_start - device-specific startup
diff --git a/src/devices/machine/timekpr.h b/src/devices/machine/timekpr.h
index 3d96d2f394a..f6ecb8dcbfc 100644
--- a/src/devices/machine/timekpr.h
+++ b/src/devices/machine/timekpr.h
@@ -10,6 +10,7 @@
- M48T37
- M48T58
- MK48T08
+ - MK48T12
***************************************************************************/
@@ -41,6 +42,9 @@
#define MCFG_MK48T08_ADD(_tag) \
MCFG_DEVICE_ADD(_tag, MK48T08, 0)
+#define MCFG_MK48T12_ADD(_tag) \
+ MCFG_DEVICE_ADD(_tag, MK48T12, 0)
+
//**************************************************************************
@@ -134,11 +138,18 @@ public:
mk48t08_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
};
+class mk48t12_device : public timekeeper_device
+{
+public:
+ mk48t12_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
+};
+
// device type definition
extern const device_type M48T02;
extern const device_type M48T35;
extern const device_type M48T37;
extern const device_type M48T58;
extern const device_type MK48T08;
+extern const device_type MK48T12;
#endif // __TIMEKPR_H__
diff --git a/src/mame/drivers/sun4.cpp b/src/mame/drivers/sun4.cpp
index 406b8e36681..086a28bae6c 100644
--- a/src/mame/drivers/sun4.cpp
+++ b/src/mame/drivers/sun4.cpp
@@ -419,6 +419,10 @@
#include "bus/rs232/rs232.h"
#include "bus/sunkbd/sunkbd.h"
#include "machine/timekpr.h"
+#include "machine/nscsi_bus.h"
+#include "machine/nscsi_cd.h"
+#include "machine/nscsi_hd.h"
+#include "machine/ncr5390.h"
#include "machine/upd765.h"
#include "formats/pc_dsk.h"
#include "formats/mfi_dsk.h"
@@ -436,7 +440,6 @@
#define RS232A_TAG "rs232a"
#define RS232B_TAG "rs232b"
#define FDC_TAG "fdc"
-#define SCSI_TAG "ncr5390"
#define ENA_NOTBOOT (0x80)
#define ENA_SDVMA (0x20)
@@ -445,13 +448,41 @@
#define ENA_DIAG (0x01)
// page table entry constants
-#define PM_VALID (0x80000000) // page is valid
-#define PM_WRITEMASK (0x40000000) // writable?
-#define PM_SYSMASK (0x20000000) // system use only?
-#define PM_CACHE (0x10000000) // cachable?
-#define PM_TYPEMASK (0x0c000000) // type mask
-#define PM_ACCESSED (0x02000000) // accessed flag
-#define PM_MODIFIED (0x01000000) // modified flag
+#define PM_VALID (0x80000000) // page is valid
+#define PM_WRITEMASK (0x40000000) // writable?
+#define PM_SYSMASK (0x20000000) // system use only?
+#define PM_CACHE (0x10000000) // cachable?
+#define PM_TYPEMASK (0x0c000000) // type mask
+#define PM_ACCESSED (0x02000000) // accessed flag
+#define PM_MODIFIED (0x01000000) // modified flag
+
+#define PAGE_SIZE (0x00000400)
+
+// DMA controller constants
+#define DMA_DEV_ID (0x80000000)
+#define DMA_L (0x00008000) // use ILACC
+#define DMA_TC (0x00004000) // terminal count
+#define DMA_EN_CNT (0x00002000) // enable count
+#define DMA_BYTE_ADDR (0x00001800) // next byte number to be accessed
+#define DMA_BYTE_ADDR_SHIFT (11)
+#define DMA_REQ_PEND (0x00000400) // request pending
+#define DMA_EN_DMA (0x00000200) // enable DMA
+#define DMA_WRITE (0x00000100) // DMA device->mem if 1, otherwise mem->device
+#define DMA_RESET (0x00000080) // DMA hardware reset
+#define DMA_DRAIN (0x00000040) // force remaining pack bytes to memory
+#define DMA_FLUSH (0x00000020) // force PACK_CNT and ERR_PEND to 0
+#define DMA_INT_EN (0x00000010) // interrupt enable
+#define DMA_PACK_CNT (0x0000000c) // number of bytes in pack register
+#define DMA_PACK_CNT_SHIFT (2)
+#define DMA_ERR_PEND (0x00000002) // error pending, set when memory exception occurs
+#define DMA_INT_PEND (0x00000001) // interrupt pending, set when TC=1
+#define DMA_READ_ONLY (DMA_TC | DMA_BYTE_ADDR | DMA_REQ_PEND | DMA_PACK_CNT | DMA_ERR_PEND | DMA_INT_PEND)
+#define DMA_WRITE_ONLY (DMA_FLUSH)
+#define DMA_READ_WRITE (DMA_EN_CNT | DMA_EN_DMA | DMA_WRITE | DMA_RESET | DMA_INT_EN)
+#define DMA_CTRL (0)
+#define DMA_ADDR (1)
+#define DMA_BYTE_COUNT (2)
+#define DMA_XTAL (XTAL_25MHz)
namespace
{
@@ -501,9 +532,12 @@ public:
sun4_state(const machine_config &mconfig, device_type type, const char *tag)
: driver_device(mconfig, type, tag)
, m_maincpu(*this, "maincpu")
+ , m_timekpr(*this, TIMEKEEPER_TAG)
, m_scc1(*this, SCC1_TAG)
, m_scc2(*this, SCC2_TAG)
, m_fdc(*this, FDC_TAG)
+ , m_scsibus(*this, "scsibus")
+ , m_scsi(*this, "scsibus:7:ncr5390")
, m_type0space(*this, "type0")
, m_type1space(*this, "type1")
, m_ram(*this, RAM_TAG)
@@ -520,6 +554,8 @@ public:
static const device_timer_id TIMER_0 = 0;
static const device_timer_id TIMER_1 = 1;
+ static const device_timer_id TIMER_DMA = 2;
+ static const device_timer_id TIMER_RESET = 3;
DECLARE_READ32_MEMBER( sun4_mmu_r );
DECLARE_WRITE32_MEMBER( sun4_mmu_w );
@@ -535,6 +571,11 @@ public:
DECLARE_WRITE8_MEMBER( irq_w );
DECLARE_READ8_MEMBER( fdc_r );
DECLARE_WRITE8_MEMBER( fdc_w );
+ DECLARE_READ32_MEMBER( dma_r );
+ DECLARE_WRITE32_MEMBER( dma_w );
+
+ DECLARE_WRITE_LINE_MEMBER( scsi_irq );
+ DECLARE_WRITE_LINE_MEMBER( scsi_drq );
DECLARE_WRITE_LINE_MEMBER( scc1_int );
DECLARE_WRITE_LINE_MEMBER( scc2_int );
@@ -549,9 +590,16 @@ public:
protected:
required_device<mb86901_device> m_maincpu;
+
+ required_device<mk48t12_device> m_timekpr;
+
required_device<z80scc_device> m_scc1;
required_device<z80scc_device> m_scc2;
+
required_device<n82077aa_device> m_fdc;
+ required_device<nscsi_bus_device> m_scsibus;
+ required_device<ncr5390_device> m_scsi;
+
optional_device<address_map_bank_device> m_type0space, m_type1space;
required_device<ram_device> m_ram;
required_memory_region m_rom;
@@ -562,6 +610,9 @@ protected:
UINT8 m_system_enable;
UINT32 m_buserr[4];
UINT32 m_counter[4];
+ UINT32 m_dma[4];
+ int m_scsi_irq;
+ int m_scsi_drq;
private:
UINT32 *m_ram_ptr;
@@ -578,8 +629,21 @@ private:
int m_arch;
emu_timer *m_c0_timer, *m_c1_timer;
+ emu_timer *m_dma_timer;
+ emu_timer *m_reset_timer;
+
+ UINT32 read_insn_data(UINT8 asi, address_space &space, UINT32 offset, UINT32 mem_mask);
+ void write_insn_data(UINT8 asi, address_space &space, UINT32 offset, UINT32 data, UINT32 mem_mask);
+ UINT32 read_insn_data_4c(UINT8 asi, address_space &space, UINT32 offset, UINT32 mem_mask);
+ void write_insn_data_4c(UINT8 asi, address_space &space, UINT32 offset, UINT32 data, UINT32 mem_mask);
+
+ void dma_set_int_pend(int state);
+ void dma_update_irq();
+ void dma_tick();
+ void dma_setup_timer(bool continuing);
void start_timer(int num);
+
void l2p_command(int ref, int params, const char **param);
void fcodes_command(int ref, int params, const char **param);
};
@@ -613,6 +677,102 @@ UINT32 sun4_state::bw2_update(screen_device &screen, bitmap_rgb32 &bitmap, const
return 0;
}
+UINT32 sun4_state::read_insn_data_4c(UINT8 asi, address_space &space, UINT32 offset, UINT32 mem_mask)
+{
+ // it's translation time
+ UINT8 pmeg = m_segmap[m_context & m_ctx_mask][(offset >> 16) & 0xfff] & m_pmeg_mask;
+ UINT32 entry = (pmeg << 6) + ((offset >> 10) & 0x3f);
+
+ if (m_pagemap[entry] & PM_VALID)
+ {
+ m_pagemap[entry] |= PM_ACCESSED;
+
+ UINT32 tmp = (m_pagemap[entry] & 0xffff) << 10;
+ tmp |= (offset & 0x3ff);
+
+ //printf("sun4: read translated vaddr %08x to phys %08x type %d, PTE %08x, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], m_maincpu->pc());
+
+ switch ((m_pagemap[entry] >> 26) & 3)
+ {
+ case 0: // type 0 space
+ return m_type0space->read32(space, tmp, mem_mask);
+
+ case 1: // type 1 space
+ // magic EPROM bypass
+ if ((tmp >= (0x6000000>>2)) && (tmp <= (0x6ffffff>>2)))
+ {
+ return m_rom_ptr[offset & 0x1ffff];
+ }
+ //printf("Read type 1 @ VA %08x, phys %08x\n", offset<<2, tmp<<2);
+ return m_type1space->read32(space, tmp, mem_mask);
+
+ default:
+ printf("sun4c: access to memory type not defined in sun4c\n");
+ return 0;
+ }
+ }
+ else
+ {
+ if (!space.debugger_access())
+ {
+ printf("sun4c: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
+ //m_maincpu->trap(SPARC_DATA_ACCESS_EXCEPTION);
+ //m_buserr[0] = 0x88; // read, invalid PTE
+ //m_buserr[1] = offset<<2;
+ }
+ return 0;
+ }
+}
+
+void sun4_state::write_insn_data_4c(UINT8 asi, address_space &space, UINT32 offset, UINT32 data, UINT32 mem_mask)
+{
+ // it's translation time
+ UINT8 pmeg = m_segmap[m_context & m_ctx_mask][(offset >> 16) & 0xfff] & m_pmeg_mask;
+ UINT32 entry = (pmeg << 6) + ((offset >> 10) & 0x3f);
+
+ if (m_pagemap[entry] & PM_VALID)
+ {
+ if ((!(m_pagemap[entry] & PM_WRITEMASK)) || ((m_pagemap[entry] & PM_SYSMASK) && !(asi & 1)))
+ {
+ printf("sun4c: write protect MMU error (PC=%x)\n", m_maincpu->pc());
+ m_buserr[0] = 0x8040; // write, protection error
+ m_buserr[1] = offset<<2;
+ m_maincpu->set_input_line(SPARC_MAE, ASSERT_LINE);
+ return;
+ }
+
+ m_pagemap[entry] |= (PM_ACCESSED | PM_MODIFIED);
+
+ UINT32 tmp = (m_pagemap[entry] & 0xffff) << 10;
+ tmp |= (offset & 0x3ff);
+
+ //printf("sun4: write translated vaddr %08x to phys %08x type %d, PTE %08x, ASI %d, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], asi, m_maincpu->pc());
+
+ switch ((m_pagemap[entry] >> 26) & 3)
+ {
+ case 0: // type 0
+ m_type0space->write32(space, tmp, data, mem_mask);
+ return;
+
+ case 1: // type 1
+ //printf("write device space @ %x\n", tmp<<1);
+ m_type1space->write32(space, tmp, data, mem_mask);
+ return;
+ default:
+ printf("sun4c: access to memory type not defined\n");
+ return;
+ }
+ }
+ else
+ {
+ printf("sun4c: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
+ //m_maincpu->trap(SPARC_DATA_ACCESS_EXCEPTION);
+ //m_buserr[0] = 0x8; // invalid PTE
+ //m_buserr[1] = offset<<2;
+ }
+}
+
+
READ32_MEMBER( sun4_state::sun4c_mmu_r )
{
UINT8 asi = m_maincpu->get_asi();
@@ -691,58 +851,12 @@ READ32_MEMBER( sun4_state::sun4c_mmu_r )
page += (offset >> 10) & 0x3f;
//printf("sun4: read page map @ %x (entry %d, seg %d, PMEG %d, mem_mask %08x, PC=%x)\n", offset << 2, page, (offset >> 16) & 0xfff, m_segmap[m_context & m_ctx_mask][(offset >> 16) & 0xfff] & m_pmeg_mask, mem_mask, m_maincpu->pc());
return m_pagemap[page];
- break;
case 8:
case 9:
case 10:
case 11:
- {
- // it's translation time
- UINT8 pmeg = m_segmap[m_context & m_ctx_mask][(offset >> 16) & 0xfff] & m_pmeg_mask;
- UINT32 entry = (pmeg << 6) + ((offset >> 10) & 0x3f);
-
- if (m_pagemap[entry] & PM_VALID)
- {
- m_pagemap[entry] |= PM_ACCESSED;
-
- UINT32 tmp = (m_pagemap[entry] & 0xffff) << 10;
- tmp |= (offset & 0x3ff);
-
- //printf("sun4: read translated vaddr %08x to phys %08x type %d, PTE %08x, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], m_maincpu->pc());
-
- switch ((m_pagemap[entry] >> 26) & 3)
- {
- case 0: // type 0 space
- return m_type0space->read32(space, tmp, mem_mask);
-
- case 1: // type 1 space
- // magic EPROM bypass
- if ((tmp >= (0x6000000>>2)) && (tmp <= (0x6ffffff>>2)))
- {
- return m_rom_ptr[offset & 0x1ffff];
- }
- //printf("Read type 1 @ VA %08x, phys %08x\n", offset<<2, tmp<<2);
- return m_type1space->read32(space, tmp, mem_mask);
-
- default:
- printf("sun4c: access to memory type not defined in sun4c\n");
- return 0;
- }
- }
- else
- {
- if (!space.debugger_access())
- {
- printf("sun4c: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
- //m_maincpu->trap(SPARC_DATA_ACCESS_EXCEPTION);
- //m_buserr[0] = 0x88; // read, invalid PTE
- //m_buserr[1] = offset<<2;
- }
- return 0;
- }
- }
- break;
+ return read_insn_data_4c(asi, space, offset, mem_mask);
default:
if (!space.debugger_access()) printf("sun4c: ASI %d unhandled read @ %x (PC=%x)\n", asi, offset<<2, m_maincpu->pc());
@@ -773,6 +887,13 @@ WRITE32_MEMBER( sun4_state::sun4c_mmu_w )
case 4: // system enable reg
m_system_enable = data>>24;
+
+ if (m_system_enable & ENA_RESET)
+ {
+ m_reset_timer->adjust(attotime::from_usec(1));
+ m_maincpu->set_input_line(SPARC_RESET, ASSERT_LINE);
+ printf("Asserting reset line\n");
+ }
//printf("%08x to system enable, mask %08x\n", data, mem_mask);
if (m_system_enable & ENA_RESET)
{
@@ -781,7 +902,7 @@ WRITE32_MEMBER( sun4_state::sun4c_mmu_w )
m_maincpu->set_input_line(INPUT_LINE_RESET, CLEAR_LINE);
}
return;
-
+
case 6: // bus error
printf("%08x to bus error @ %x, mask %08x\n", data, offset, mem_mask);
m_buserr[offset & 0xf] = data;
@@ -832,64 +953,107 @@ WRITE32_MEMBER( sun4_state::sun4c_mmu_w )
COMBINE_DATA(&m_pagemap[page]);
m_pagemap[page] &= 0xff00ffff; // these 8 bits are cleared when written and tested as such
return;
+
case 8:
case 9:
case 10:
case 11:
- // it's translation time
- UINT8 pmeg = m_segmap[m_context & m_ctx_mask][(offset >> 16) & 0xfff] & m_pmeg_mask;
- UINT32 entry = (pmeg << 6) + ((offset >> 10) & 0x3f);
+ write_insn_data_4c(asi, space, offset, data, mem_mask);
+ return;
- if (m_pagemap[entry] & PM_VALID)
- {
- if ((!(m_pagemap[entry] & PM_WRITEMASK)) ||
- ((m_pagemap[entry] & PM_SYSMASK) && !(asi & 1)))
- {
- printf("sun4c: write protect MMU error (PC=%x)\n", m_maincpu->pc());
- m_buserr[0] = 0x8040; // write, protection error
- m_buserr[1] = offset<<2;
- m_maincpu->set_input_line(SPARC_MAE, ASSERT_LINE);
- return;
- }
+ }
- m_pagemap[entry] |= (PM_ACCESSED | PM_MODIFIED);
+ printf("sun4c: %08x to asi %d byte offset %x, PC = %x, mask = %08x\n", data, asi, offset << 2, m_maincpu->pc(), mem_mask);
+}
- UINT32 tmp = (m_pagemap[entry] & 0xffff) << 10;
- tmp |= (offset & 0x3ff);
+// -----------------------------------------------------------------
- //printf("sun4: write translated vaddr %08x to phys %08x type %d, PTE %08x, ASI %d, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], asi, m_maincpu->pc());
+UINT32 sun4_state::read_insn_data(UINT8 asi, address_space &space, UINT32 offset, UINT32 mem_mask)
+{
+ // it's translation time
+ UINT8 pmeg = m_segmap[m_context][(offset >> 16) & 0xfff];
+ UINT32 entry = (pmeg << 5) + ((offset >> 11) & 0x1f);
- switch ((m_pagemap[entry] >> 26) & 3)
- {
- case 0: // type 0
- m_type0space->write32(space, tmp, data, mem_mask);
- return;
+ if (m_pagemap[entry] & PM_VALID)
+ {
+ m_pagemap[entry] |= PM_ACCESSED;
- case 1: // type 1
- //printf("write device space @ %x\n", tmp<<1);
- m_type1space->write32(space, tmp, data, mem_mask);
- return;
- default:
- printf("sun4c: access to memory type not defined\n");
- return;
+ UINT32 tmp = (m_pagemap[entry] & 0x7ffff) << 11;
+ tmp |= (offset & 0x7ff);
+
+ //printf("sun4: read translated vaddr %08x to phys %08x type %d, PTE %08x, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], m_maincpu->pc());
+
+ switch ((m_pagemap[entry] >> 26) & 3)
+ {
+ case 0: // type 0 space
+ return m_type0space->read32(space, tmp, mem_mask);
+
+ case 1: // type 1 space
+ // magic EPROM bypass
+ if ((tmp >= (0x6000000>>2)) && (tmp <= (0x6ffffff>>2)))
+ {
+ return m_rom_ptr[offset & 0x1ffff];
}
+ //printf("Read type 1 @ VA %08x, phys %08x\n", offset<<2, tmp<<2);
+ return m_type1space->read32(space, tmp, mem_mask);
+
+ default:
+ printf("sun4: access to unhandled memory type\n");
+ return 0;
}
- else
+ }
+ else
+ {
+ if (!space.debugger_access())
{
- printf("sun4c: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
+ printf("sun4: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
//m_maincpu->trap(SPARC_DATA_ACCESS_EXCEPTION);
- //m_buserr[0] = 0x8; // invalid PTE
+ //m_buserr[0] = 0x88; // read, invalid PTE
//m_buserr[1] = offset<<2;
- return;
}
- break;
-
+ return 0;
}
-
- printf("sun4c: %08x to asi %d byte offset %x, PC = %x, mask = %08x\n", data, asi, offset << 2, m_maincpu->pc(), mem_mask);
}
-// -----------------------------------------------------------------
+void sun4_state::write_insn_data(UINT8 asi, address_space &space, UINT32 offset, UINT32 data, UINT32 mem_mask)
+{
+ // it's translation time
+ UINT8 pmeg = m_segmap[m_context][(offset >> 16) & 0xfff];
+ UINT32 entry = (pmeg << 5) + ((offset >> 11) & 0x1f);
+
+ if (m_pagemap[entry] & PM_VALID)
+ {
+ m_pagemap[entry] |= PM_ACCESSED;
+
+ UINT32 tmp = (m_pagemap[entry] & 0x7ffff) << 11;
+ tmp |= (offset & 0x7ff);
+
+ //printf("sun4: write translated vaddr %08x to phys %08x type %d, PTE %08x, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], m_maincpu->pc());
+
+ switch ((m_pagemap[entry] >> 26) & 3)
+ {
+ case 0: // type 0
+ m_type0space->write32(space, tmp, data, mem_mask);
+ return;
+
+ case 1: // type 1
+ //printf("write device space @ %x\n", tmp<<1);
+ m_type1space->write32(space, tmp, data, mem_mask);
+ return;
+
+ default:
+ printf("sun4: access to memory type not defined in sun4c\n");
+ return;
+ }
+ }
+ else
+ {
+ printf("sun4: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
+ //m_maincpu->trap(SPARC_DATA_ACCESS_EXCEPTION);
+ //m_buserr[0] = 0x8; // invalid PTE
+ //m_buserr[1] = offset<<2;
+ }
+}
READ32_MEMBER( sun4_state::sun4_mmu_r )
{
@@ -973,52 +1137,7 @@ READ32_MEMBER( sun4_state::sun4_mmu_r )
case 9:
case 10:
case 11:
- {
- // it's translation time
- UINT8 pmeg = m_segmap[m_context][(offset >> 16) & 0xfff];
- UINT32 entry = (pmeg << 5) + ((offset >> 11) & 0x1f);
-
- if (m_pagemap[entry] & PM_VALID)
- {
- m_pagemap[entry] |= PM_ACCESSED;
-
- UINT32 tmp = (m_pagemap[entry] & 0x7ffff) << 11;
- tmp |= (offset & 0x7ff);
-
- //printf("sun4: read translated vaddr %08x to phys %08x type %d, PTE %08x, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], m_maincpu->pc());
-
- switch ((m_pagemap[entry] >> 26) & 3)
- {
- case 0: // type 0 space
- return m_type0space->read32(space, tmp, mem_mask);
-
- case 1: // type 1 space
- // magic EPROM bypass
- if ((tmp >= (0x6000000>>2)) && (tmp <= (0x6ffffff>>2)))
- {
- return m_rom_ptr[offset & 0x1ffff];
- }
- //printf("Read type 1 @ VA %08x, phys %08x\n", offset<<2, tmp<<2);
- return m_type1space->read32(space, tmp, mem_mask);
-
- default:
- printf("sun4: access to unhandled memory type\n");
- return 0;
- }
- }
- else
- {
- if (!space.debugger_access())
- {
- printf("sun4: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
- //m_maincpu->trap(SPARC_DATA_ACCESS_EXCEPTION);
- //m_buserr2qor[0] = 0x88; // read, invalid PTE
- //m_buserr[1] = offset<<2;
- }
- return 0;
- }
- }
- break;
+ return read_insn_data(asi, space, offset, mem_mask);
default:
if (!space.debugger_access()) printf("sun4: ASI %d unhandled read @ %x (PC=%x)\n", asi, offset<<2, m_maincpu->pc());
@@ -1049,6 +1168,12 @@ WRITE32_MEMBER( sun4_state::sun4_mmu_w )
case 4: // system enable reg
m_system_enable = data>>24;
+
+ if (m_system_enable & ENA_RESET)
+ {
+ m_reset_timer->adjust(attotime::from_usec(1));
+ m_maincpu->set_input_line(SPARC_RESET, ASSERT_LINE);
+ }
//printf("%08x to system enable, mask %08x\n", data, mem_mask);
if (m_system_enable & ENA_RESET)
{
@@ -1129,42 +1254,7 @@ WRITE32_MEMBER( sun4_state::sun4_mmu_w )
case 9:
case 10:
case 11:
- // it's translation time
- UINT8 pmeg = m_segmap[m_context][(offset >> 16) & 0xfff];
- UINT32 entry = (pmeg << 5) + ((offset >> 11) & 0x1f);
-
- if (m_pagemap[entry] & PM_VALID)
- {
- m_pagemap[entry] |= PM_ACCESSED;
-
- UINT32 tmp = (m_pagemap[entry] & 0x7ffff) << 11;
- tmp |= (offset & 0x7ff);
-
- //printf("sun4: write translated vaddr %08x to phys %08x type %d, PTE %08x, PC=%x\n", offset<<2, tmp<<2, (m_pagemap[entry]>>26) & 3, m_pagemap[entry], m_maincpu->pc());
-
- switch ((m_pagemap[entry] >> 26) & 3)
- {
- case 0: // type 0
- m_type0space->write32(space, tmp, data, mem_mask);
- return;
-
- case 1: // type 1
- //printf("write device space @ %x\n", tmp<<1);
- m_type1space->write32(space, tmp, data, mem_mask);
- return;
- default:
- printf("sun4: access to memory type not defined in sun4c\n");
- return;
- }
- }
- else
- {
- printf("sun4: INVALID PTE entry %d %08x accessed! vaddr=%x PC=%x\n", entry, m_pagemap[entry], offset <<2, m_maincpu->pc());
- //m_maincpu->trap(SPARC_DATA_ACCESS_EXCEPTION);
- //m_buserror[0] = 0x8; // invalid PTE
- //m_buserror[1] = offset<<2;
- return;
- }
+ write_insn_data(asi, space, offset, data, mem_mask);
break;
}
@@ -1249,7 +1339,28 @@ void sun4_state::machine_reset()
m_system_enable = 0;
m_irq_reg = 0;
m_scc1_int = m_scc2_int = 0;
+ m_scsi_irq = 0;
+ m_scsi_drq = 0;
+
+ for (UINT32 i = 0; i < (0x7f8 - 0x7d7); i++)
+ {
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7d7 + i, 0);
+ }
+
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7d9, 0x12);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7e4, 0x34);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7e5, 0x56);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7e6, 0x78);
+
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7da, 0x11);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7db, 0x22);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7dc, 0x33);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7dd, 0x44);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7de, 0x55);
+ m_timekpr->write(m_maincpu->space(AS_PROGRAM), 0x7df, 0x66);
+
memset(m_counter, 0, sizeof(m_counter));
+ memset(m_dma, 0, sizeof(m_dma));
}
void sun4_state::machine_start()
@@ -1273,6 +1384,14 @@ void sun4_state::machine_start()
m_c1_timer = timer_alloc(TIMER_1);
m_c0_timer->adjust(attotime::never);
m_c1_timer->adjust(attotime::never);
+
+ // allocate timer for system reset
+ m_reset_timer = timer_alloc(TIMER_RESET);
+ m_reset_timer->adjust(attotime::never);
+
+ // allocate timer for DMA controller
+ m_dma_timer = timer_alloc(TIMER_DMA);
+ m_dma_timer->adjust(attotime::never);
}
READ32_MEMBER( sun4_state::ram_r )
@@ -1363,6 +1482,8 @@ static ADDRESS_MAP_START(type1space_map, AS_PROGRAM, 32, sun4_state)
AM_RANGE(0x06000000, 0x0607ffff) AM_ROM AM_REGION("user1", 0)
AM_RANGE(0x07200000, 0x07200003) AM_READWRITE8(fdc_r, fdc_w, 0xffffffff)
AM_RANGE(0x08000000, 0x08000003) AM_READ(ss1_sl0_id) // slot 0 contains SCSI/DMA/Ethernet
+ AM_RANGE(0x08400000, 0x0840000f) AM_READWRITE(dma_r, dma_w)
+ AM_RANGE(0x08800000, 0x0880001f) AM_DEVICE8("scsibus:7:ncr5390", ncr5390_device, map, 0xff0000)
AM_RANGE(0x0e000000, 0x0e000003) AM_READ(ss1_sl3_id) // slot 3 contains video board
AM_RANGE(0x0e800000, 0x0e8fffff) AM_RAM AM_SHARE("bw2_vram")
ADDRESS_MAP_END
@@ -1470,6 +1591,16 @@ void sun4_state::device_timer(emu_timer &timer, device_timer_id id, int param, v
//printf("Taking INT14\n");
}
break;
+
+ case TIMER_DMA:
+ dma_tick();
+ break;
+
+ case TIMER_RESET:
+ m_reset_timer->adjust(attotime::never);
+ m_maincpu->set_input_line(SPARC_RESET, CLEAR_LINE);
+ printf("Clearing reset line\n");
+ break;
}
}
@@ -1551,6 +1682,246 @@ WRITE32_MEMBER( sun4_state::timer_w )
}
}
+void sun4_state::dma_set_int_pend(int state)
+{
+ if (!state)
+ {
+ m_dma[DMA_CTRL] &= ~DMA_INT_PEND;
+ }
+ else
+ {
+ m_dma[DMA_CTRL] |= DMA_INT_PEND;
+ }
+
+ dma_update_irq();
+}
+
+void sun4_state:: dma_update_irq()
+{
+ int irq_or_err_pending = (m_dma[DMA_CTRL] & (DMA_INT_PEND | DMA_ERR_PEND)) ? 1 : 0;
+ int irq_enabled = (m_dma[DMA_CTRL] & DMA_INT_EN) ? 1 : 0;
+ if (irq_or_err_pending && irq_enabled)
+ {
+ m_maincpu->set_input_line(SPARC_IRQ3, ASSERT_LINE);
+ }
+ else
+ {
+ m_maincpu->set_input_line(SPARC_IRQ3, CLEAR_LINE);
+ }
+}
+
+void sun4_state::dma_tick()
+{
+ UINT32 transfer_size = (m_dma[DMA_BYTE_COUNT] > PAGE_SIZE ? PAGE_SIZE : m_dma[DMA_BYTE_COUNT]);
+ address_space &space = m_maincpu->space(AS_PROGRAM);
+
+ if (m_dma[DMA_CTRL] & DMA_WRITE)
+ {
+ UINT32 data = 0;
+ UINT32 byte_cnt = 3;
+ UINT32 mem_mask = 0;
+ while (transfer_size > 0)
+ {
+ UINT8 value = m_scsi->dma_r();
+ data |= value << (byte_cnt * 8);
+ mem_mask |= 0xff << (byte_cnt * 8);
+ transfer_size--;
+
+ if (byte_cnt == 0)
+ {
+ if (m_arch == ARCH_SUN4C)
+ {
+ write_insn_data_4c(11, space, m_dma[DMA_ADDR] >> 2, data, mem_mask);
+ }
+ else
+ {
+ write_insn_data(11, space, m_dma[DMA_ADDR] >> 2, data, mem_mask);
+ }
+ m_dma[DMA_ADDR] += 4;
+ m_dma[DMA_BYTE_COUNT] -= 4;
+
+ byte_cnt = 3;
+ data = 0;
+ mem_mask = 0;
+ }
+ else
+ {
+ byte_cnt--;
+ }
+ }
+
+ if (byte_cnt != 0)
+ {
+ if (m_arch == ARCH_SUN4C)
+ {
+ write_insn_data_4c(11, space, m_dma[DMA_ADDR] >> 2, data, mem_mask);
+ }
+ else
+ {
+ write_insn_data(11, space, m_dma[DMA_ADDR] >> 2, data, mem_mask);
+ }
+
+ m_dma[DMA_ADDR] += byte_cnt;
+ m_dma[DMA_BYTE_COUNT] -= byte_cnt;
+ }
+ }
+ else
+ {
+ UINT32 byte_cnt = 3;
+ UINT32 mem_mask = 0;
+ while (transfer_size > 0)
+ {
+ mem_mask |= 0xff << (byte_cnt * 8);
+ transfer_size--;
+
+ if (byte_cnt == 0)
+ {
+ UINT32 data = 0;
+ if (m_arch == ARCH_SUN4C)
+ {
+ data = read_insn_data_4c(11, space, m_dma[DMA_ADDR] >> 2, mem_mask);
+ }
+ else
+ {
+ data = read_insn_data(11, space, m_dma[DMA_ADDR] >> 2, mem_mask);
+ }
+
+ for (int i = 24; i >= 0; i -= 8)
+ {
+ m_scsi->dma_w((data >> i) & 0xff);
+ m_dma[DMA_BYTE_COUNT]--;
+ }
+
+ byte_cnt = 3;
+ mem_mask = 0;
+ }
+ else
+ {
+ byte_cnt--;
+ }
+ }
+
+ if (byte_cnt != 0)
+ {
+ byte_cnt++;
+ UINT32 data = 0;
+ if (m_arch == ARCH_SUN4C)
+ {
+ data = read_insn_data_4c(11, space, m_dma[DMA_ADDR] >> 2, mem_mask);
+ }
+ else
+ {
+ data = read_insn_data(11, space, m_dma[DMA_ADDR] >> 2, mem_mask);
+ }
+
+ UINT32 initial_cnt = byte_cnt;
+ for (int i = 0; i < 4 - initial_cnt; i++)
+ {
+ UINT8 byte_val = (data >> (byte_cnt * 8)) & 0xff;
+ m_scsi->dma_w(byte_val);
+
+ m_dma[DMA_BYTE_COUNT]--;
+ byte_cnt--;
+ }
+ }
+ }
+
+ if (m_dma[DMA_BYTE_COUNT] == 0)
+ {
+ m_dma[DMA_CTRL] |= DMA_TC;
+ dma_set_int_pend(1);
+ m_dma_timer->adjust(attotime::never);
+ }
+ else
+ {
+ dma_setup_timer(true);
+ }
+}
+
+void sun4_state::dma_setup_timer(bool continuing)
+{
+ const UINT32 remaining_bytes = m_dma[DMA_BYTE_COUNT];
+ const UINT64 latency = (continuing ? 0 : 40);
+ const UINT64 transfer_size = (remaining_bytes < PAGE_SIZE ? remaining_bytes : PAGE_SIZE);
+ const UINT64 transfer_duration = ((transfer_size + 15) / 16) * 8; // 16 byte groupings, 8 clock cycles per group
+ const UINT64 total_ticks = latency + transfer_duration;
+
+ m_dma_timer->adjust(attotime::from_ticks(total_ticks, DMA_XTAL));
+
+ if (!continuing)
+ {
+ m_dma[DMA_CTRL] &= DMA_TC;
+ }
+}
+
+READ32_MEMBER( sun4_state::dma_r )
+{
+ return m_dma[offset];
+}
+
+WRITE32_MEMBER( sun4_state::dma_w )
+{
+ switch (offset)
+ {
+ case DMA_CTRL:
+ {
+ // clear write-only bits
+ UINT32 old_ctrl = m_dma[DMA_CTRL];
+
+ m_dma[DMA_CTRL] &= (DMA_READ_ONLY | DMA_READ_WRITE);
+
+ m_dma[DMA_CTRL] |= (data & (DMA_WRITE_ONLY | DMA_READ_WRITE));
+
+ if (data & DMA_FLUSH)
+ {
+ m_dma[DMA_CTRL] &= ~DMA_PACK_CNT;
+ m_dma[DMA_CTRL] &= ~DMA_ERR_PEND;
+ m_dma[DMA_CTRL] &= ~DMA_TC;
+
+ if (!m_scsi_irq)
+ {
+ dma_set_int_pend(0);
+ }
+ }
+
+ if (data & DMA_EN_DMA && !(old_ctrl & DMA_EN_DMA))
+ {
+ dma_setup_timer(false);
+ }
+ break;
+ }
+
+ case DMA_ADDR:
+ case DMA_BYTE_COUNT:
+ m_dma[offset] = data;
+ break;
+
+ default:
+ break;
+ }
+}
+
+WRITE_LINE_MEMBER( sun4_state::scsi_irq )
+{
+ if (!(m_dma[DMA_CTRL] & DMA_TC))
+ {
+ dma_set_int_pend(state);
+ }
+ m_scsi_irq = state;
+}
+
+WRITE_LINE_MEMBER( sun4_state::scsi_drq )
+{
+ if (state)
+ {
+ if (m_dma[DMA_CTRL] & DMA_EN_DMA)
+ {
+ dma_setup_timer(false);
+ }
+ }
+ m_scsi_drq = state;
+}
+
// indicate 4/60 SCSI/DMA/Ethernet card exists
READ32_MEMBER( sun4_state::ss1_sl0_id )
{
@@ -1571,17 +1942,17 @@ static SLOT_INTERFACE_START( sun_floppies )
SLOT_INTERFACE( "35hd", FLOPPY_35_HD )
SLOT_INTERFACE_END
-//static SLOT_INTERFACE_START( sun_scsi_devices )
- //SLOT_INTERFACE("cdrom", NSCSI_CDROM)
- //SLOT_INTERFACE("harddisk", NSCSI_HARDDISK)
- //SLOT_INTERFACE_INTERNAL("ncr5390", NCR5390)
-//SLOT_INTERFACE_END
+static SLOT_INTERFACE_START( sun_scsi_devices )
+ SLOT_INTERFACE("cdrom", NSCSI_CDROM)
+ SLOT_INTERFACE("harddisk", NSCSI_HARDDISK)
+ SLOT_INTERFACE_INTERNAL("ncr5390", NCR5390)
+SLOT_INTERFACE_END
-//static MACHINE_CONFIG_FRAGMENT( ncr5390 )
- //MCFG_DEVICE_CLOCK(10000000)
- //MCFG_NCR5390_IRQ_HANDLER(DEVWRITELINE(":", next_state, scsi_irq))
- //MCFG_NCR5390_DRQ_HANDLER(DEVWRITELINE(":", next_state, scsi_drq))
-//MACHINE_CONFIG_END
+static MACHINE_CONFIG_FRAGMENT( ncr5390 )
+ MCFG_DEVICE_CLOCK(10000000)
+ MCFG_NCR5390_IRQ_HANDLER(DEVWRITELINE(":", sun4_state, scsi_irq))
+ MCFG_NCR5390_DRQ_HANDLER(DEVWRITELINE(":", sun4_state, scsi_drq))
+MACHINE_CONFIG_END
static MACHINE_CONFIG_START( sun4, sun4_state )
/* basic machine hardware */
@@ -1593,7 +1964,7 @@ static MACHINE_CONFIG_START( sun4, sun4_state )
MCFG_RAM_DEFAULT_SIZE("16M")
MCFG_RAM_DEFAULT_VALUE(0x00)
- MCFG_M48T02_ADD(TIMEKEEPER_TAG)
+ MCFG_MK48T12_ADD(TIMEKEEPER_TAG)
MCFG_N82077AA_ADD(FDC_TAG, n82077aa_device::MODE_PS2)
MCFG_FLOPPY_DRIVE_ADD("fdc:0", sun_floppies, "35hd", sun4_state::floppy_formats)
@@ -1636,15 +2007,16 @@ static MACHINE_CONFIG_START( sun4, sun4_state )
MCFG_RS232_DCD_HANDLER(DEVWRITELINE(SCC2_TAG, z80scc_device, dcdb_w))
MCFG_RS232_CTS_HANDLER(DEVWRITELINE(SCC2_TAG, z80scc_device, ctsb_w))
- //MCFG_NSCSI_ADD("scsibus:0", next_scsi_devices, "harddisk", false)
- //MCFG_NSCSI_ADD("scsibus:1", next_scsi_devices, "cdrom", false)
- //MCFG_NSCSI_ADD("scsibus:2", next_scsi_devices, nullptr, false)
- //MCFG_NSCSI_ADD("scsibus:3", next_scsi_devices, nullptr, false)
- //MCFG_NSCSI_ADD("scsibus:4", next_scsi_devices, nullptr, false)
- //MCFG_NSCSI_ADD("scsibus:5", next_scsi_devices, nullptr, false)
- //MCFG_NSCSI_ADD("scsibus:6", next_scsi_devices, nullptr, false)
- //MCFG_NSCSI_ADD("scsibus:7", next_scsi_devices, SCSI_TAG, true)
- //MCFG_DEVICE_CARD_MACHINE_CONFIG(SCSI_TAG, ncr5390)
+ MCFG_NSCSI_BUS_ADD("scsibus")
+ MCFG_NSCSI_ADD("scsibus:0", sun_scsi_devices, "harddisk", false)
+ MCFG_NSCSI_ADD("scsibus:1", sun_scsi_devices, "cdrom", false)
+ MCFG_NSCSI_ADD("scsibus:2", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:3", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:4", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:5", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:6", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:7", sun_scsi_devices, "ncr5390", true)
+ MCFG_DEVICE_CARD_MACHINE_CONFIG("ncr5390", ncr5390)
MACHINE_CONFIG_END
static MACHINE_CONFIG_START( sun4c, sun4_state )
@@ -1657,7 +2029,7 @@ static MACHINE_CONFIG_START( sun4c, sun4_state )
MCFG_RAM_DEFAULT_SIZE("16M")
MCFG_RAM_DEFAULT_VALUE(0x00)
- MCFG_M48T02_ADD(TIMEKEEPER_TAG)
+ MCFG_MK48T12_ADD(TIMEKEEPER_TAG)
MCFG_N82077AA_ADD(FDC_TAG, n82077aa_device::MODE_PS2)
MCFG_FLOPPY_DRIVE_ADD("fdc:0", sun_floppies, "35hd", sun4_state::floppy_formats)
@@ -1700,6 +2072,17 @@ static MACHINE_CONFIG_START( sun4c, sun4_state )
MCFG_RS232_DCD_HANDLER(DEVWRITELINE(SCC2_TAG, z80scc_device, dcdb_w))
MCFG_RS232_CTS_HANDLER(DEVWRITELINE(SCC2_TAG, z80scc_device, ctsb_w))
+ MCFG_NSCSI_BUS_ADD("scsibus")
+ MCFG_NSCSI_ADD("scsibus:0", sun_scsi_devices, "harddisk", false)
+ MCFG_NSCSI_ADD("scsibus:1", sun_scsi_devices, "cdrom", false)
+ MCFG_NSCSI_ADD("scsibus:2", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:3", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:4", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:5", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:6", sun_scsi_devices, nullptr, false)
+ MCFG_NSCSI_ADD("scsibus:7", sun_scsi_devices, "ncr5390", true)
+ MCFG_DEVICE_CARD_MACHINE_CONFIG("ncr5390", ncr5390)
+
MCFG_SCREEN_ADD("bwtwo", RASTER)
MCFG_SCREEN_UPDATE_DRIVER(sun4_state, bw2_update)
MCFG_SCREEN_SIZE(1152,900)
diff --git a/src/osd/modules/render/bgfx/shaders/chains/crt/fs_crt-caligari.sc b/src/osd/modules/render/bgfx/shaders/chains/crt/fs_crt-caligari.sc
new file mode 100644
index 00000000000..68d9908983f
--- /dev/null
+++ b/src/osd/modules/render/bgfx/shaders/chains/crt/fs_crt-caligari.sc
@@ -0,0 +1,123 @@
+$input v_color0, v_texcoord0, v_texcoord1
+
+// license:BSD-3-Clause
+// copyright-holders:caligari
+
+/*
+ Phosphor shader - Copyright (C) 2011 caligari.
+
+ Ported by Hyllian.
+
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License
+ as published by the Free Software Foundation; either version 2
+ of the License, or (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+
+*/
+
+#define onex v_texcoord1.xy
+#define oney v_texcoord1.zw
+
+#include "common.sh"
+
+// Autos
+uniform vec4 u_source_size;
+
+// User-supplied
+uniform vec4 SPOT_WIDTH;
+uniform vec4 SPOT_HEIGHT;
+uniform vec4 COLOR_BOOST;
+uniform vec4 InputGamma;
+uniform vec4 OutputGamma;
+
+// Samplers
+SAMPLER2D(s_p, 0);
+
+#define GAMMA_IN(color) pow(color, InputGamma.xxxx)
+#define GAMMA_OUT(color) pow(color, 1.0 / OutputGamma.xxxx)
+
+#define TEX2D(coords) GAMMA_IN( texture2D(s_p, coords) )
+
+// Macro for weights computing
+#define WEIGHT(w) \
+ if(w > 1.0) w = 1.0; \
+ w = 1.0 - w * w; \
+ w = w * w;
+
+void main()
+{
+ vec2 coords = v_texcoord0 * u_source_size.xy;
+ vec2 pixel_center = floor(coords) + vec2(0.5, 0.5);
+ vec2 texture_coords = pixel_center / u_source_size.xy;
+
+ vec4 color = TEX2D(texture_coords);
+
+ float dx = coords.x - pixel_center.x;
+
+ float h_weight_00 = dx / SPOT_WIDTH.x;
+ WEIGHT(h_weight_00);
+
+ color *= vec4(h_weight_00, h_weight_00, h_weight_00, h_weight_00 );
+
+ // get closest horizontal neighbour to blend
+ vec2 coords01;
+ if (dx > 0.0)
+ {
+ coords01 = onex;
+ dx = 1.0 - dx;
+ }
+ else
+ {
+ coords01 = -onex;
+ dx = 1.0 + dx;
+ }
+ vec4 colorNB = TEX2D(texture_coords + coords01);
+
+ float h_weight_01 = dx / SPOT_WIDTH.x;
+ WEIGHT(h_weight_01);
+
+ color = color + colorNB * vec4(h_weight_01, h_weight_01, h_weight_01, h_weight_01);
+
+ //////////////////////////////////////////////////////
+ // Vertical Blending
+ float dy = coords.y - pixel_center.y;
+ float v_weight_00 = dy / SPOT_HEIGHT.x;
+ WEIGHT(v_weight_00);
+ color *= vec4(v_weight_00, v_weight_00, v_weight_00, v_weight_00);
+
+ // get closest vertical neighbour to blend
+ vec2 coords10;
+ if (dy > 0.0)
+ {
+ coords10 = oney;
+ dy = 1.0 - dy;
+ }
+ else
+ {
+ coords10 = -oney;
+ dy = 1.0 + dy;
+ }
+ colorNB = TEX2D(texture_coords + coords10);
+
+ float v_weight_10 = dy / SPOT_HEIGHT.x;
+ WEIGHT(v_weight_10);
+
+ color = color + colorNB * vec4(v_weight_10 * h_weight_00, v_weight_10 * h_weight_00, v_weight_10 * h_weight_00, v_weight_10 * h_weight_00);
+
+ colorNB = TEX2D(texture_coords + coords01 + coords10);
+
+ color = color + colorNB * vec4(v_weight_10 * h_weight_01, v_weight_10 * h_weight_01, v_weight_10 * h_weight_01, v_weight_10 * h_weight_01);
+
+ color *= COLOR_BOOST.xxxx;
+
+ gl_FragColor = clamp(GAMMA_OUT(color), 0.0, 1.0);
+}
diff --git a/src/osd/modules/render/bgfx/shaders/chains/crt/varying.def.sc b/src/osd/modules/render/bgfx/shaders/chains/crt/varying.def.sc
new file mode 100644
index 00000000000..8404fc635e1
--- /dev/null
+++ b/src/osd/modules/render/bgfx/shaders/chains/crt/varying.def.sc
@@ -0,0 +1,7 @@
+vec4 v_color0 : COLOR0 = vec4(1.0, 0.0, 0.0, 1.0);
+vec2 v_texcoord0 : TEXCOORD0 = vec2(0.0, 0.0);
+vec4 v_texcoord1 : TEXCOORD1 = vec4(0.0, 0.0, 0.0, 0.0);
+
+vec3 a_position : POSITION;
+vec4 a_color0 : COLOR0;
+vec2 a_texcoord0 : TEXCOORD0;
diff --git a/src/osd/modules/render/bgfx/shaders/chains/crt/vs_crt-caligari.sc b/src/osd/modules/render/bgfx/shaders/chains/crt/vs_crt-caligari.sc
new file mode 100644
index 00000000000..37a119ec7d4
--- /dev/null
+++ b/src/osd/modules/render/bgfx/shaders/chains/crt/vs_crt-caligari.sc
@@ -0,0 +1,45 @@
+$input a_position, a_texcoord0, a_color0
+$output v_texcoord0, v_texcoord1, v_color0
+
+// license:BSD-3-Clause
+// copyright-holders:caligari
+
+/*
+ Phosphor shader - Copyright (C) 2011 caligari.
+
+ Ported by Hyllian.
+
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License
+ as published by the Free Software Foundation; either version 2
+ of the License, or (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+
+*/
+
+#define onex v_texcoord1.xy
+#define oney v_texcoord1.zw
+
+#include "common.sh"
+
+// Autos
+uniform vec4 u_source_size;
+
+void main()
+{
+ gl_Position = mul(u_viewProj, vec4(a_position.xy, 0.0, 1.0));
+ v_texcoord0 = a_texcoord0;
+
+ onex = vec2(1.0 / u_source_size.x, 0.0);
+ oney = vec2(0.0, 1.0 / u_source_size.y);
+
+ v_color0 = a_color0;
+}