1 // license:BSD-3-Clause
2 // copyright-holders:Sven Schnelle
3 #ifndef MAME_VIDEO_TOPCAT_H
4 #define MAME_VIDEO_TOPCAT_H
5 
6 #pragma once
7 
8 class topcat_device : public device_t
9 {
10 public:
11 	topcat_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
has_changed()12 	bool has_changed() { bool ret = m_changed; m_changed = false; return ret; };
set_fb_width(int _pixels)13 	void set_fb_width(int _pixels) { m_fb_width = _pixels; }
set_fb_height(int _pixels)14 	void set_fb_height(int _pixels) { m_fb_height = _pixels; }
set_planemask(int _mask)15 	void set_planemask(int _mask) { m_plane_mask = _mask; }
16 	void get_cursor_pos(int &startx, int &starty, int &endx, int &endy);
17 
18 	uint16_t vram_r(offs_t offset, uint16_t mem_mask = ~0);
19 	void vram_w(offs_t offset, uint16_t data, uint16_t mem_mask = ~0);
20 	uint16_t ctrl_r(address_space &space, offs_t offset, uint16_t mem_mask = ~0);
21 	void ctrl_w(address_space &space, offs_t offset, uint16_t data, uint16_t mem_mask = ~0);
22 
23 	WRITE_LINE_MEMBER(vblank_w);
24 	void topcat_mem(address_map &map);
25 
26 	bool plane_enabled();
27 
irq_out_cb()28 	auto irq_out_cb() { return m_int_write_func.bind(); }
29 protected:
30 	topcat_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock);
31 
32 	virtual void device_start() override;
33 	virtual void device_reset() override;
34 
35 	TIMER_CALLBACK_MEMBER(cursor_callback);
36 
37 private:
38 
39 	typedef enum {
40 		TOPCAT_REPLACE_RULE_CLEAR, /* 0 */
41 		TOPCAT_REPLACE_RULE_SRC_AND_DST,
42 		TOPCAT_REPLACE_RULE_SRC_AND_NOT_DST,
43 		TOPCAT_REPLACE_RULE_SRC,
44 		TOPCAT_REPLACE_RULE_NOT_SRC_AND_DST,
45 		TOPCAT_REPLACE_RULE_NOP,
46 		TOPCAT_REPLACE_RULE_SRC_XOR_DST,
47 		TOPCAT_REPLACE_RULE_SRC_OR_DST,
48 		TOPCAT_REPLACE_RULE_NOT_SRC_AND_NOT_DST,
49 		TOPCAT_REPLACE_RULE_NOT_SRC_XOR_DST,
50 		TOPCAT_REPLACE_RULE_NOT_DST,
51 		TOPCAT_REPLACE_RULE_SRC_OR_NOT_DST,
52 		TOPCAT_REPLACE_RULE_NOT_SRC,
53 		TOPCAT_REPLACE_RULE_NOT_SRC_OR_DST,
54 		TOPCAT_REPLACE_RULE_NOT_SRC_OR_NOT_DST,
55 		TOPCAT_REPLACE_RULE_SET,
56 	} replacement_rule_t;
57 
58 	enum topcat_reg {
59 		TOPCAT_REG_VBLANK=0x20,
60 		TOPCAT_REG_WMOVE_ACTIVE=0x22,
61 		TOPCAT_REG_VERT_RETRACE_INTRQ=0x24,
62 		TOPCAT_REG_WMOVE_INTRQ=0x26,
63 		TOPCAT_REG_DISPLAY_PLANE_ENABLE=0x40,
64 		TOPCAT_REG_WRITE_ENABLE_PLANE=0x44,
65 		TOPCAT_REG_READ_ENABLE_PLANE=0x46,
66 		TOPCAT_REG_FB_WRITE_ENABLE=0x48,
67 		TOPCAT_REG_WMOVE_IE=0x4a,
68 		TOPCAT_REG_VBLANK_IE=0x4c,
69 		TOPCAT_REG_START_WMOVE=0x4e,
70 		TOPCAT_REG_ENABLE_BLINK_PLANES=0x50,
71 		TOPCAT_REG_ENABLE_ALT_FRAME=0x54,
72 		TOPCAT_REG_CURSOR_PLANE_ENABLE=0x56,
73 		TOPCAT_REG_PIXEL_REPLACE_RULE=0x75,
74 		TOPCAT_REG_MOVE_REPLACE_RULE=0x77,
75 		TOPCAT_REG_SOURCE_X_PIXEL=0x79,
76 		TOPCAT_REG_SOURCE_Y_PIXEL=0x7b,
77 		TOPCAT_REG_DST_X_PIXEL=0x7d,
78 		TOPCAT_REG_DST_Y_PIXEL=0x7f,
79 		TOPCAT_REG_BLOCK_MOVER_PIXEL_WIDTH=0x81,
80 		TOPCAT_REG_BLOCK_MOVER_PIXEL_HEIGHT=0x83,
81 		TOPCAT_REG_CURSOR_X_POS=0x85,
82 		TOPCAT_REG_CURSOR_Y_POS=0x87,
83 		TOPCAT_REG_CURSOR_WIDTH=0x89,
84 	};
85 
86 	void window_move();
87 
88 	void execute_rule(bool src, replacement_rule_t rule, bool &dst);
89 
90 	void update_cursor(int x, int y, uint16_t ctrl, uint8_t width);
91 
modify_vram(int x,int y,bool state)92 	void modify_vram(int x, int y, bool state) {
93 		if (state)
94 			m_vram[y * m_fb_width + x] |= m_plane_mask;
95 		else
96 			m_vram[y * m_fb_width + x] &= ~m_plane_mask;
97 	}
98 
modify_vram_offset(int offset,bool state)99 	void modify_vram_offset(int offset, bool state) {
100 		if (state)
101 			m_vram[offset] |= m_plane_mask;
102 		else
103 			m_vram[offset] &= ~m_plane_mask;
104 	}
105 
get_vram_pixel(int x,int y)106 	bool get_vram_pixel(int x, int y) const {
107 		return m_vram[y * m_fb_width + x] & m_plane_mask;
108 	}
109 
110 	void update_int();
111 
112 	devcb_write_line m_int_write_func;
113 
114 	uint16_t m_vblank = 0;
115 	uint8_t m_wmove_active = 0;
116 	uint16_t m_vert_retrace_intrq = 0;
117 	uint16_t m_wmove_intrq = 0;
118 	uint16_t m_display_enable_planes = 0;
119 	uint16_t m_fb_write_enable = 0;
120 	uint16_t m_enable_blink_planes = 0;
121 	uint16_t m_enable_alt_frame = 0;
122 	uint16_t m_cursor_plane_enable = 0;
123 	uint16_t m_move_replacement_rule = 0;
124 	uint16_t m_pixel_replacement_rule = 0;
125 	uint16_t m_source_x_pixel = 0;
126 	uint16_t m_source_y_pixel = 0;
127 	uint16_t m_dst_x_pixel = 0;
128 	uint16_t m_dst_y_pixel = 0;
129 	uint16_t m_block_mover_pixel_width = 0;
130 	uint16_t m_block_mover_pixel_height = 0;
131 	uint16_t m_unknown_reg4a = 0;
132 	uint16_t m_unknown_reg4c = 0;
133 	emu_timer *m_cursor_timer = nullptr;
134 	bool m_cursor_state = false;
135 	uint16_t m_cursor_x_pos = 0;
136 	uint16_t m_cursor_y_pos = 0;
137 	uint16_t m_cursor_width = 0;
138 
139 	int m_fb_width = 0;
140 	int m_fb_height = 0;
141 	uint8_t m_plane_mask = 0;
142 
143 	bool m_read_enable = false;
144 	bool m_write_enable = false;
145 	bool m_fb_enable = false;
146 	bool m_changed = false;
147 
148 	required_shared_ptr<uint8_t> m_vram;
149 };
150 
151 DECLARE_DEVICE_TYPE(TOPCAT, topcat_device)
152 #endif // MAME_VIDEO_TOPCAT_H
153