main vdp.h
  1/*
  2 Copyright 2013 Michael Pavone
  3 This file is part of BlastEm.
  4 BlastEm is free software distributed under the terms of the GNU General Public License version 3 or greater. See COPYING for full license text.
  5*/
  6#ifndef VDP_H_
  7#define VDP_H_
  8
  9#include <stdint.h>
 10#include <stdio.h>
 11#include "system.h"
 12#include "serialize.h"
 13
 14#define VDP_REGS 24
 15#define CRAM_SIZE 64
 16#define SHADOW_OFFSET CRAM_SIZE
 17#define HIGHLIGHT_OFFSET (SHADOW_OFFSET+CRAM_SIZE)
 18#define MODE4_OFFSET (HIGHLIGHT_OFFSET+CRAM_SIZE)
 19#define VSRAM_SIZE 40
 20#define VRAM_SIZE (64*1024)
 21#define BORDER_LEFT 13
 22#define BORDER_RIGHT 14
 23#define HORIZ_BORDER (BORDER_LEFT+BORDER_RIGHT)
 24#define LINEBUF_SIZE (320+HORIZ_BORDER) //H40 + full border
 25#define SCROLL_BUFFER_SIZE 32
 26#define BORDER_BOTTOM 13 //TODO: Replace with actual value
 27#define MAX_DRAWS 40
 28#define MAX_DRAWS_H32 32
 29#define MAX_DRAWS_H32_MODE4 8
 30#define MAX_SPRITES_LINE 20
 31#define MAX_SPRITES_LINE_H32 16
 32#define MAX_SPRITES_FRAME 80
 33#define MAX_SPRITES_FRAME_H32 64
 34#define SAT_CACHE_SIZE (MAX_SPRITES_FRAME * 4)
 35
 36#define FBUF_SHADOW 0x0001
 37#define FBUF_HILIGHT 0x0010
 38#define FBUF_MODE4 0x0100
 39#define DBG_SHADOW 0x10
 40#define DBG_HILIGHT 0x20
 41#define DBG_PRIORITY 0x8
 42#define DBG_SRC_MASK 0x7
 43#define DBG_SRC_A 0x1
 44#define DBG_SRC_W 0x2
 45#define DBG_SRC_B 0x3
 46#define DBG_SRC_S 0x4
 47#define DBG_SRC_BG 0x0
 48
 49#define MCLKS_LINE 3420
 50
 51#define FLAG_DOT_OFLOW     0x01
 52#define FLAG_CAN_MASK      0x02
 53#define FLAG_MASKED        0x04
 54#define FLAG_WINDOW        0x08
 55#define FLAG_PENDING       0x10
 56#define FLAG_READ_FETCHED  0x20
 57#define FLAG_DMA_RUN       0x40
 58#define FLAG_DMA_PROG      0x80
 59
 60#define FLAG2_VINT_PENDING   0x01
 61#define FLAG2_HINT_PENDING   0x02
 62#define FLAG2_READ_PENDING   0x04
 63#define FLAG2_SPRITE_COLLIDE 0x08
 64#define FLAG2_REGION_PAL     0x10
 65#define FLAG2_EVEN_FIELD     0x20
 66#define FLAG2_BYTE_PENDING   0x40
 67#define FLAG2_PAUSE          0x80
 68
 69#define DISPLAY_ENABLE 0x40
 70
 71enum {
 72	REG_MODE_1=0,
 73	REG_MODE_2,
 74	REG_SCROLL_A,
 75	REG_WINDOW,
 76	REG_SCROLL_B,
 77	REG_SAT,
 78	REG_STILE_BASE,
 79	REG_BG_COLOR,
 80	REG_X_SCROLL,
 81	REG_Y_SCROLL,
 82	REG_HINT,
 83	REG_MODE_3,
 84	REG_MODE_4,
 85	REG_HSCROLL,
 86	REG_BGTILE_BASE,
 87	REG_AUTOINC,
 88	REG_SCROLL,
 89	REG_WINDOW_H,
 90	REG_WINDOW_V,
 91	REG_DMALEN_L,
 92	REG_DMALEN_H,
 93	REG_DMASRC_L,
 94	REG_DMASRC_M,
 95	REG_DMASRC_H
 96};
 97
 98//Mode reg 1
 99#define BIT_VSCRL_LOCK 0x80
100#define BIT_HSCRL_LOCK 0x40
101#define BIT_COL0_MASK  0x20
102#define BIT_HINT_EN    0x10
103#define BIT_SPRITE_8PX 0x08
104#define BIT_PAL_SEL    0x04
105#define BIT_MODE_4     BIT_PAL_SEL
106#define BIT_HVC_LATCH  0x02
107#define BIT_DISP_DIS   0x01
108
109//Mode reg 2
110#define BIT_128K_VRAM  0x80
111#define BIT_DISP_EN    0x40
112#define BIT_VINT_EN    0x20
113#define BIT_DMA_ENABLE 0x10
114#define BIT_PAL        0x08
115#define BIT_MODE_5     0x04
116#define BIT_SPRITE_SZ  0x02
117
118//Mode reg 3
119#define BIT_EINT_EN    0x10
120#define BIT_VSCROLL    0x04
121
122//Mode reg 4
123#define BIT_H40        0x01
124#define BIT_HILIGHT    0x8
125#define BIT_DOUBLE_RES 0x4
126#define BIT_INTERLACE  0x2
127
128//Test register
129#define TEST_BIT_DISABLE 0x40
130
131typedef struct {
132	uint16_t address;
133	int16_t x_pos;
134	uint8_t pal_priority;
135	uint8_t h_flip;
136} sprite_draw;
137
138typedef struct {
139	uint8_t size;
140	uint8_t index;
141	int16_t y;
142} sprite_info;
143
144#define FIFO_SIZE 4
145
146typedef struct {
147	uint32_t cycle;
148	uint32_t address;
149	uint16_t value;
150	uint8_t  cd;
151	uint8_t  partial;
152} fifo_entry;
153
154enum {
155	VDP_DEBUG_PLANE,
156	VDP_DEBUG_VRAM,
157	VDP_DEBUG_CRAM,
158	VDP_DEBUG_COMPOSITE,
159	VDP_NUM_DEBUG_TYPES
160};
161
162typedef struct {
163	system_header  *system;
164	//pointer to current line in framebuffer
165	uint32_t       *output;
166	uint32_t       *done_output;
167	//pointer to current framebuffer
168	uint32_t       *fb;
169	uint32_t       *debug_fbs[VDP_NUM_DEBUG_TYPES];
170	uint32_t       output_pitch;
171	uint32_t       debug_fb_pitch[VDP_NUM_DEBUG_TYPES];
172	fifo_entry     fifo[FIFO_SIZE];
173	int32_t        fifo_write;
174	int32_t        fifo_read;
175	uint32_t       address;
176	uint32_t       serial_address;
177	uint32_t       colors[CRAM_SIZE*4];
178	uint32_t       debugcolors[1 << (3 + 1 + 1 + 1)];//3 bits for source, 1 bit for priority, 1 bit for shadow, 1 bit for hilight
179	uint16_t       cram[CRAM_SIZE];
180	uint32_t       frame;
181	uint8_t        cd;
182	uint8_t	       flags;
183	uint8_t        regs[VDP_REGS];
184	//cycle count in MCLKs
185	uint32_t       cycles;
186	uint32_t       pending_vint_start;
187	uint32_t       pending_hint_start;
188	uint16_t       vsram[VSRAM_SIZE];
189	uint16_t       vscroll_latch[2];
190	uint16_t       vcounter;
191	uint16_t       inactive_start;
192	uint16_t       border_top;
193	uint16_t       border_bot;
194	uint16_t       hscroll_a;
195	uint16_t       hscroll_b;
196	uint16_t       h40_lines;
197	uint16_t       output_lines;
198	sprite_draw    sprite_draw_list[MAX_DRAWS];
199	sprite_info    sprite_info_list[MAX_SPRITES_LINE];
200	uint8_t        sat_cache[SAT_CACHE_SIZE];
201	uint16_t       col_1;
202	uint16_t       col_2;
203	uint16_t       hv_latch;
204	uint16_t       prefetch;
205	uint16_t       test_port;
206	//stores 2-bit palette + 4-bit palette index + priority for current sprite line
207	uint8_t        linebuf[LINEBUF_SIZE];
208	uint8_t        layer_debug_buf[LINEBUF_SIZE];
209	uint8_t        hslot; //hcounter/2
210	uint8_t	       sprite_index;
211	uint8_t        sprite_draws;
212	int8_t         slot_counter;
213	int8_t         cur_slot;
214	uint8_t        max_sprites_frame;
215	uint8_t        max_sprites_line;
216	uint8_t        fetch_tmp[2];
217	uint8_t        v_offset;
218	uint8_t        hint_counter;
219	uint8_t        flags2;
220	uint8_t        double_res;
221	uint8_t        buf_a_off;
222	uint8_t        buf_b_off;
223	uint8_t        pending_byte;
224	uint8_t        state;
225	uint8_t        cur_buffer;
226	uint8_t        tmp_buf_a[SCROLL_BUFFER_SIZE];
227	uint8_t        tmp_buf_b[SCROLL_BUFFER_SIZE];
228	uint8_t        enabled_debuggers;
229	uint8_t        debug_fb_indices[VDP_NUM_DEBUG_TYPES];
230	uint8_t        debug_modes[VDP_NUM_DEBUG_TYPES];
231	uint8_t        vdpmem[];
232} vdp_context;
233
234
235
236vdp_context *init_vdp_context(uint8_t region_pal);
237void vdp_free(vdp_context *context);
238void vdp_run_context_full(vdp_context * context, uint32_t target_cycles);
239void vdp_run_context(vdp_context * context, uint32_t target_cycles);
240//runs from current cycle count to VBLANK for the current mode, returns ending cycle count
241uint32_t vdp_run_to_vblank(vdp_context * context);
242//runs until the target cycle is reached or the current DMA operation has completed, whicever comes first
243void vdp_run_dma_done(vdp_context * context, uint32_t target_cycles);
244uint8_t vdp_load_gst(vdp_context * context, FILE * state_file);
245uint8_t vdp_save_gst(vdp_context * context, FILE * outfile);
246int vdp_control_port_write(vdp_context * context, uint16_t value);
247void vdp_control_port_write_pbc(vdp_context * context, uint8_t value);
248int vdp_data_port_write(vdp_context * context, uint16_t value);
249void vdp_data_port_write_pbc(vdp_context * context, uint8_t value);
250void vdp_test_port_write(vdp_context * context, uint16_t value);
251uint16_t vdp_control_port_read(vdp_context * context);
252uint16_t vdp_data_port_read(vdp_context * context);
253uint8_t vdp_data_port_read_pbc(vdp_context * context);
254void vdp_latch_hv(vdp_context *context);
255uint16_t vdp_hv_counter_read(vdp_context * context);
256uint16_t vdp_test_port_read(vdp_context * context);
257void vdp_adjust_cycles(vdp_context * context, uint32_t deduction);
258uint32_t vdp_next_hint(vdp_context * context);
259uint32_t vdp_next_vint(vdp_context * context);
260uint32_t vdp_next_vint_z80(vdp_context * context);
261uint32_t vdp_next_nmi(vdp_context *context);
262void vdp_int_ack(vdp_context * context);
263void vdp_print_sprite_table(vdp_context * context);
264void vdp_print_reg_explain(vdp_context * context);
265void latch_mode(vdp_context * context);
266uint32_t vdp_cycles_to_frame_end(vdp_context * context);
267void write_cram_internal(vdp_context * context, uint16_t addr, uint16_t value);
268void vdp_check_update_sat_byte(vdp_context *context, uint32_t address, uint8_t value);
269void vdp_pbc_pause(vdp_context *context);
270void vdp_release_framebuffer(vdp_context *context);
271void vdp_reacquire_framebuffer(vdp_context *context);
272void vdp_serialize(vdp_context *context, serialize_buffer *buf);
273void vdp_deserialize(deserialize_buffer *buf, void *vcontext);
274void vdp_force_update_framebuffer(vdp_context *context);
275void vdp_toggle_debug_view(vdp_context *context, uint8_t debug_type);
276void vdp_inc_debug_mode(vdp_context *context);
277//to be implemented by the host system
278uint16_t read_dma_value(uint32_t address);
279
280#endif //VDP_H_