summaryrefslogtreecommitdiffstatshomepage
path: root/scripts/src/formats.lua
diff options
context:
space:
mode:
author cracyc <cracyc@users.noreply.github.com>2016-11-02 12:14:39 -0500
committer cracyc <cracyc@users.noreply.github.com>2016-11-02 12:16:10 -0500
commitbfc49b0974e4d040122dc8e546992d0ebdc418aa (patch)
tree14384314d7a5dc49aedbdf11d7e9c1b4270f9ad4 /scripts/src/formats.lua
parent431f8d361140dff4b2990a0845d8958281c90162 (diff)
luaengine: bugfixes (nw)
Diffstat (limited to 'scripts/src/formats.lua')
0 files changed, 0 insertions, 0 deletions
ref='#n103'>103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394
// license:BSD-3-Clause
// copyright-holders:Vas Crabb
/***************************************************************************

    WE|AT&T DSP16 series emulator

***************************************************************************/
#ifndef MAME_CPU_DSP16_DSP16_H
#define MAME_CPU_DSP16_DSP16_H

#pragma once

#include "dsp16dis.h"

#include "cpu/drccache.h"

#include <memory>
#include <utility>

class dsp16_device_base : public cpu_device, protected dsp16_disassembler::cpu
{
public:
	DECLARE_WRITE_LINE_MEMBER(exm_w);

	// interrupt output callbacks
	auto iack_cb() { return m_iack_cb.bind(); }

	// serial output callbacks
	auto ick_cb() { return m_ick_cb.bind(); }
	auto ild_cb() { return m_ild_cb.bind(); }
	auto do_cb() { return m_do_cb.bind(); }
	auto ock_cb() { return m_ock_cb.bind(); }
	auto old_cb() { return m_old_cb.bind(); }
	auto ose_cb() { return m_ose_cb.bind(); }

	// high-level active parallel I/O callbacks
	auto pio_r_cb() { return m_pio_r_cb.bind(); }
	auto pio_w_cb() { return m_pio_w_cb.bind(); }

	// low-level parallel I/O callbacks
	auto pdb_w_cb() { return m_pdb_w_cb.bind(); }
	auto psel_cb() { return m_psel_cb.bind(); }
	auto pids_cb() { return m_pids_cb.bind(); }
	auto pods_cb() { return m_pods_cb.bind(); }

	// interrupt outputs
	DECLARE_READ_LINE_MEMBER(iack_r) { return m_iack_out; }

	// serial outputs
	DECLARE_READ_LINE_MEMBER(ick_r) { return sio_ick_active() ? m_sio_clk : 1; }
	DECLARE_READ_LINE_MEMBER(ild_r) { return sio_ild_active() ? m_sio_ld : 1; }
	DECLARE_READ_LINE_MEMBER(do_r) { return m_do_out; }
	DECLARE_READ_LINE_MEMBER(ock_r) { return sio_ock_active() ? m_sio_clk : 1; }
	DECLARE_READ_LINE_MEMBER(old_r) { return sio_old_active() ? m_sio_ld : 1; }
	DECLARE_READ_LINE_MEMBER(ose_r) { return m_ose_out; }

	// high-level passive parallel I/O handlers
	DECLARE_READ16_MEMBER(pio_r);
	DECLARE_WRITE16_MEMBER(pio_w);

	// parallel I/O outputs
	DECLARE_READ_LINE_MEMBER(psel_r) { return m_psel_out; }
	DECLARE_READ_LINE_MEMBER(pids_r) { return m_pids_out; }
	DECLARE_READ_LINE_MEMBER(pods_r) { return m_pods_out; }

protected:
	// construction/destruction
	dsp16_device_base(
			machine_config const &mconfig,
			device_type type,
			char const *tag,
			device_t *owner,
			u32 clock,
			u8 yaau_bits,
			address_map_constructor &&data_map);

	// device_t implementation
	virtual void device_resolve_objects() override;
	virtual void device_start() override;
	virtual void device_stop() override;
	virtual void device_reset() override;

	// device_execute_interface implementation
	virtual u64 execute_clocks_to_cycles(u64 clocks) const override { return (clocks + 2 - 1) >> 1; }
	virtual u64 execute_cycles_to_clocks(u64 cycles) const override { return cycles << 1; }
	virtual u32 execute_input_lines() const override { return 5U; }
	virtual void execute_run() override;
	virtual void execute_set_input(int inputnum, int state) override;

	// device_memory_interface implementation
	virtual space_config_vector memory_space_config() const override;

	// device_state_interface implementation
	virtual void state_import(device_state_entry const &entry) override;
	virtual void state_export(device_state_entry const &entry) override;
	virtual void state_string_export(device_state_entry const &entry, std::string &str) const override;

	// device_disasm_interface implementation
	virtual std::unique_ptr<util::disasm_interface> create_disassembler() override;

	// dsp16_disassembler::cpu implementation
	virtual predicate check_con(offs_t pc, u16 op) const override;
	virtual predicate check_branch(offs_t pc) const override;

	// for specialisations to override
	virtual void external_memory_enable(address_space &space, bool enable) = 0;

	template <offs_t Base> DECLARE_READ16_MEMBER(external_memory_r);

private:
	// state registration indices
	enum
	{
		DSP16_PT = 1, DSP16_PR, DSP16_PI, DSP16_I,
		DSP16_R0, DSP16_R1, DSP16_R2, DSP16_R3, DSP16_RB, DSP16_RE, DSP16_J, DSP16_K,
		DSP16_X, DSP16_Y, DSP16_P, DSP16_A0, DSP16_A1, DSP16_C0, DSP16_C1, DSP16_C2, DSP16_AUC, DSP16_PSW,
		DSP16_YH, DSP16_A0H, DSP16_A1H, DSP16_YL, DSP16_A0L, DSP16_A1L
	};

	// recompiler setup
	enum : size_t
	{
		CACHE_SIZE = 1U * 1024 * 1024
	};

	// masks for registers that aren't power-of-two sizes
	enum : s16
	{
		XAAU_I_SIGN = s16(1) << (12 - 1),
		XAAU_I_MASK = (s16(1) << 12) - 1,
		XAAU_I_EXT = ~XAAU_I_MASK
	};
	enum : s64
	{
		DAU_A_SIGN = s64(1) << (36 - 1),
		DAU_A_MASK = (s64(1) << 36) - 1,
		DAU_A_EXT = ~DAU_A_MASK
	};

	// execution state
	enum class cache : u8 { NONE, LOAD, EXECUTE };
	enum class phase : u8 { PURGE, OP1, OP2, PREFETCH };
	enum flags : u8
	{
		FLAGS_PRED_NONE     = 0x00U,
		FLAGS_PRED_TRUE     = 0x01U,
		FLAGS_PRED_FALSE    = 0x02U,
		FLAGS_PRED_MASK     = 0x03U,

		FLAGS_IACK_NONE     = 0x00U,
		FLAGS_IACK_SET      = 0x04U,
		FLAGS_IACK_CLEAR    = 0x08U,
		FLAGS_IACK_MASK     = 0x0cU,

		FLAGS_NONE          = FLAGS_PRED_NONE | FLAGS_IACK_NONE
	};
	friend constexpr flags operator~(flags);
	friend constexpr flags operator&(flags, flags);
	friend constexpr flags operator|(flags, flags);
	friend flags &operator&=(flags &, flags);
	friend flags &operator|=(flags &, flags);

	// serial I/O state
	enum sio_flags : u8
	{
		SIO_FLAGS_NONE      = 0x00U,
		SIO_FLAGS_ILD       = 0x01U,
		SIO_FLAGS_OLD       = 0x02U
	};
	friend constexpr sio_flags operator~(sio_flags);
	friend constexpr sio_flags operator&(sio_flags, sio_flags);
	friend constexpr sio_flags operator|(sio_flags, sio_flags);
	friend sio_flags &operator&=(sio_flags &, sio_flags);
	friend sio_flags &operator|=(sio_flags &, sio_flags);

	// recompiler helpers
	class core_state;
	class frontend;
	class recompiler;
	using core_state_ptr = std::unique_ptr<core_state, void (*)(core_state *)>;
	using recompiler_ptr = std::unique_ptr<recompiler>;

	// internal address maps
	void program_map(address_map &map);

	// instruction execution
	template <bool Debugger, bool Caching> void execute_some_rom();
	template <bool Debugger> void execute_some_cache();
	void overlap_rom_data_read();
	void yaau_short_immediate_load(u16 op);
	template <bool Debugger> s16 yaau_read(u16 op);
	template <bool Debugger> void yaau_write(u16 op, s16 value);
	template <bool Debugger> void yaau_write_z(u16 op);

	// built-in peripherals
	void sio_step();
	void pio_step();

	// inline helpers
	static bool op_interruptible(u16 op);
	bool check_predicate();
	flags &set_predicate(flags predicate) { return m_flags = (m_flags & ~FLAGS_PRED_MASK) | (predicate & FLAGS_PRED_MASK); }
	flags &set_iack(flags iack) { return m_flags = (m_flags & ~FLAGS_IACK_MASK) | (iack & FLAGS_IACK_MASK); }
	u16 &set_xaau_pc_offset(u16 offset);
	s16 get_r(u16 op);
	void set_r(u16 op, s16 value);
	s64 dau_saturate(u16 a) const;
	bool op_dau_con(u16 op, bool inc);

	// opcode field handling
	static constexpr u16 op_ja(u16 op) { return op & 0x0fffU; }
	static constexpr u16 op_b(u16 op) { return (op >> 8) & 0x0007U; }
	static constexpr u16 op_d(u16 op) { return BIT(op, 10); }
	static constexpr u16 op_s(u16 op) { return BIT(op, 9); }
	static constexpr u16 op_f1(u16 op) { return (op >> 5) & 0x000fU; }
	static constexpr u16 op_f2(u16 op) { return (op >> 5) & 0x000fU; }
	static constexpr u16 op_r(u16 op) { return (op >> 4) & 0x003fU; }
	static constexpr u16 op_x(u16 op) { return BIT(op, 4); }
	static constexpr u16 op_con(u16 op) { return op & 0x001fU; }
	static constexpr u16 op_ni(u16 op) { return (op >> 7) & 0x000fU; }
	static constexpr u16 op_k(u16 op) { return op & 0x007fU; }

	// serial I/O
	bool sio_ld_ick() const { return !BIT(m_sio_sioc, 9); }
	bool sio_ld_ock() const { return bool(BIT(m_sio_sioc, 9)); }
	bool sio_lsb_first() const { return !BIT(m_sio_sioc, 6); }
	bool sio_msb_first() const { return bool(BIT(m_sio_sioc, 6)); }
	bool sio_old_active() const { return bool(BIT(m_sio_sioc, 5)); }
	bool sio_ild_active() const { return bool(BIT(m_sio_sioc, 4)); }
	bool sio_ock_active() const { return bool(BIT(m_sio_sioc, 3)); }
	bool sio_ick_active() const { return bool(BIT(m_sio_sioc, 2)); }
	unsigned sio_olen() const { return BIT(m_sio_sioc, 1) ? 8U : 16U; }
	unsigned sio_ilen() const { return BIT(m_sio_sioc, 0) ? 8U : 16U; }
	void sio_sioc_write(u16 value);
	void sio_ick_active_edge();
	void sio_ock_active_edge();
	void sio_step_ld_div();

	// parallel I/O
	u16 pio_strobe() const { return ((m_pio_pioc >> 13) & 0x0003U) + 1; }
	bool pio_pods_active() const { return bool(BIT(m_pio_pioc, 12)); }
	bool pio_pids_active() const { return bool(BIT(m_pio_pioc, 11)); }
	bool pio_sc_mode() const { return bool(BIT(m_pio_pioc, 10)); }
	bool pio_ibf_enable() const { return bool(BIT(m_pio_pioc, 9)); }
	bool pio_obe_enable() const { return bool(BIT(m_pio_pioc, 8)); }
	bool pio_pids_enable() const { return bool(BIT(m_pio_pioc, 7)); }
	bool pio_pods_enable() const { return bool(BIT(m_pio_pioc, 6)); }
	bool pio_int_enable() const { return bool(BIT(m_pio_pioc, 5)); }
	bool pio_ibf_status() const { return bool(BIT(m_pio_pioc, 4)); }
	bool pio_obe_status() const { return bool(BIT(m_pio_pioc, 3)); }
	bool pio_pids_status() const { return bool(BIT(m_pio_pioc, 2)); }
	bool pio_pods_status() const { return bool(BIT(m_pio_pioc, 1)); }
	bool pio_int_status() const { return bool(BIT(m_pio_pioc, 0)); }
	void pio_pioc_write(u16 value);
	u16 pio_pdx_read(u16 sel);
	void pio_pdx_write(u16 sel, u16 value);

	// interrupt callbacks
	devcb_write_line            m_iack_cb;

	// serial output callbacks
	devcb_write_line            m_ick_cb, m_ild_cb;
	devcb_write_line            m_do_cb, m_ock_cb, m_old_cb, m_ose_cb;

	// parallel I/O callbacks
	devcb_read16                m_pio_r_cb;
	devcb_write16               m_pio_w_cb;
	devcb_write16               m_pdb_w_cb;
	devcb_write_line            m_psel_cb, m_pids_cb, m_pods_cb;

	// configuration
	address_space_config const  m_space_config[3];
	u8 const                    m_yaau_bits;

	// memory system access
	required_shared_ptr<u16>    m_workram;
	address_space               *m_spaces[3];
	memory_access_cache<1, -1, ENDIANNESS_BIG> *m_pcache;
	u16                         m_workram_mask;

	// recompiler stuff
	drc_cache                   m_drc_cache;
	core_state_ptr              m_core;
	recompiler_ptr              m_recompiler;

	// execution state
	cache       m_cache_mode;
	phase       m_phase;
	u8          m_int_enable[2];
	flags       m_flags;
	u8          m_cache_ptr, m_cache_limit, m_cache_iterations;
	u16         m_cache[16];
	u16         m_rom_data;

	// line states
	u8          m_exm_in;       // internal ROM disabled when low
	u8          m_int_in;       // external interrupt request
	u8          m_iack_out;     // asserted (low) while servicing interrupt

	// serial I/O line states
	u8          m_ick_in;       // data input clock - sampled on rising edge
	u8          m_ild_in;       // data input clock - sampled on rising edge
	u8          m_do_out;       // serial data output - changes on rising edges of OCK
	u8          m_ock_in;       // data output clock - output changes on rising edge
	u8          m_old_in;       // falling edge indicates beginning of output word
	u8          m_ose_out;      // indicates the end of a serial transmission

	// parallel I/O line states
	u8          m_psel_out;     // last accessed parallel I/O data register
	u8          m_pids_out;     // parallel input data strobe (sampled on rising edge)
	u8          m_pods_out;     // parallel output data strobe

	// SIO - Serial I/O
	u16         m_sio_sioc;     // 10 bits
	u16         m_sio_obuf;     // 16 bits
	u16         m_sio_osr;      // 16 bits
	u16         m_sio_ofsr;     // 16 bits
	u8          m_sio_clk;
	u8          m_sio_clk_div;
	u8          m_sio_clk_res;
	u8          m_sio_ld;
	u8          m_sio_ld_div;
	sio_flags   m_sio_flags;

	// PIO - Parallel I/O
	u16         m_pio_pioc;     // 16 bits
	u16         m_pio_pdx_in;   // 16 bits
	u16         m_pio_pdx_out;  // 16 bits
	u8          m_pio_pids_cnt;
	u8          m_pio_pods_cnt;

	// fake registers for the debugger
	u16         m_cache_pcbase;
	u16         m_st_pcbase;
	u16         m_st_genflags;
	s16         m_st_yh, m_st_ah[2];
	u16         m_st_yl, m_st_al[2];
};


class dsp16_device : public dsp16_device_base
{
public:
	// construction/destruction
	dsp16_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock);

protected:
	// dsp16_device_base implementation
	virtual void external_memory_enable(address_space &space, bool enable) override;

	// internal address maps
	void data_map(address_map &map);

private:
	required_region_ptr<u16>    m_rom;
};


class dsp16a_device : public dsp16_device_base
{
public:
	// construction/destruction
	dsp16a_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock);

protected:
	// dsp16_device_base implementation
	virtual void external_memory_enable(address_space &space, bool enable) override;

	// internal address maps
	void data_map(address_map &map);

private:
	required_region_ptr<u16>    m_rom;
};


enum
{
	DSP16_INT_LINE = INPUT_LINE_IRQ0,
	DSP16_ICK_LINE,
	DSP16_ILD_LINE,
	DSP16_OCK_LINE,
	DSP16_OLD_LINE
};


DECLARE_ENUM_BITWISE_OPERATORS(dsp16_device_base::flags)
DECLARE_ENUM_BITWISE_OPERATORS(dsp16_device_base::sio_flags)


DECLARE_DEVICE_TYPE(DSP16, dsp16_device)
DECLARE_DEVICE_TYPE(DSP16A, dsp16a_device)

#endif // MAME_CPU_DSP16_DSP16_H