Added XTAL clocks to zaxxon.c.

Cleaned up jaguar driver:
 * proper video timing, configured by the chipset
 * 32-bit rendering, removing 16bpp hacks
 * support for borders
 * proper object processor timing, including multiple passes per line
 * added R3041 as a clone of the R3000
 * fixed XTALs based on documentation
This commit is contained in:
Aaron Giles 2008-01-13 01:15:32 +00:00
parent cb740fd78b
commit f44732e5af
12 changed files with 286 additions and 204 deletions

View File

@ -766,8 +766,9 @@ $(CPUOBJ)/pic16c5x/pic16c5x.o: $(CPUSRC)/pic16c5x/pic16c5x.c \
#-------------------------------------------------
CPUDEFS += -DHAS_R3000=$(if $(filter R3000,$(CPUS)),1,0)
CPUDEFS += -DHAS_R3041=$(if $(filter R3041,$(CPUS)),1,0)
ifneq ($(filter R3000,$(CPUS)),)
ifneq ($(filter R3000 R3041,$(CPUS)),)
OBJDIRS += $(CPUOBJ)/mips
CPUOBJS += $(CPUOBJ)/mips/r3000.o
DBGOBJS += $(CPUOBJ)/mips/r3kdasm.o

View File

@ -1377,3 +1377,39 @@ void r3000le_get_info(UINT32 state, cpuinfo *info)
default: r3000_get_info(state, info); break;
}
}
void r3041be_get_info(UINT32 state, cpuinfo *info)
{
switch (state)
{
/* --- the following bits of info are returned as 64-bit signed integers --- */
case CPUINFO_INT_ENDIANNESS: info->i = CPU_IS_BE; break;
/* --- the following bits of info are returned as pointers to data or functions --- */
case CPUINFO_PTR_RESET: info->reset = r3000be_reset; break;
/* --- the following bits of info are returned as NULL-terminated strings --- */
case CPUINFO_STR_NAME: strcpy(info->s, "R3041 (big)"); break;
default: r3000_get_info(state, info); break;
}
}
void r3041le_get_info(UINT32 state, cpuinfo *info)
{
switch (state)
{
/* --- the following bits of info are returned as 64-bit signed integers --- */
case CPUINFO_INT_ENDIANNESS: info->i = CPU_IS_LE; break;
/* --- the following bits of info are returned as pointers to data or functions --- */
case CPUINFO_PTR_RESET: info->reset = r3000le_reset; break;
/* --- the following bits of info are returned as NULL-terminated strings --- */
case CPUINFO_STR_NAME: strcpy(info->s, "R3041 (little)"); break;
default: r3000_get_info(state, info); break;
}
}

View File

@ -62,4 +62,7 @@ struct r3000_config
extern void r3000be_get_info(UINT32 state, cpuinfo *info);
extern void r3000le_get_info(UINT32 state, cpuinfo *info);
extern void r3041be_get_info(UINT32 state, cpuinfo *info);
extern void r3041le_get_info(UINT32 state, cpuinfo *info);
#endif /* _JAGUAR_H */

View File

@ -118,6 +118,8 @@ enum _cpu_type
CPU_JAGUARDSP,
CPU_R3000BE,
CPU_R3000LE,
CPU_R3041BE,
CPU_R3041LE,
CPU_R4600BE,
CPU_R4600LE,
CPU_R4650BE,

View File

@ -115,6 +115,8 @@ void jaguargpu_get_info(UINT32 state, cpuinfo *info);
void jaguardsp_get_info(UINT32 state, cpuinfo *info);
void r3000be_get_info(UINT32 state, cpuinfo *info);
void r3000le_get_info(UINT32 state, cpuinfo *info);
void r3041be_get_info(UINT32 state, cpuinfo *info);
void r3041le_get_info(UINT32 state, cpuinfo *info);
void r4600be_get_info(UINT32 state, cpuinfo *info);
void r4600le_get_info(UINT32 state, cpuinfo *info);
void r4650be_get_info(UINT32 state, cpuinfo *info);
@ -549,6 +551,10 @@ static const struct
{ CPU_R3000BE, r3000be_get_info },
{ CPU_R3000LE, r3000le_get_info },
#endif
#if (HAS_R3041)
{ CPU_R3041BE, r3041be_get_info },
{ CPU_R3041LE, r3041le_get_info },
#endif
#if (HAS_R4600)
{ CPU_R4600BE, r4600be_get_info },
{ CPU_R4600LE, r4600le_get_info },

View File

@ -104,6 +104,7 @@ enum
XTAL_45MHz = 45000000, /* Eolith with Hyperstone CPUs */
XTAL_45_158MHz = 45158000, /* Sega Model 2A video board, Model 3 CPU board */
XTAL_48MHz = 48000000,
XTAL_48_66MHz = 48660000, /* Zaxxon */
XTAL_49_152MHz = 49152000, /* Used on some Namco PCBs, Baraduke h/w, System 21, Super System 22 */
XTAL_50MHz = 50000000,
XTAL_52MHz = 52000000, /* Cojag */

View File

@ -177,6 +177,11 @@ Notes:
#include "jaguar.h"
#define JAGUAR_CLOCK XTAL_52MHz
#define R3000_CLOCK XTAL_40MHz
#define M68K_CLOCK XTAL_50MHz
/*************************************
*
@ -987,29 +992,27 @@ static const struct jaguar_config dsp_config =
static MACHINE_DRIVER_START( cojagr3k )
/* basic machine hardware */
MDRV_CPU_ADD(R3000BE, 66000000/2)
MDRV_CPU_ADD_TAG("main", R3041BE, R3000_CLOCK)
MDRV_CPU_CONFIG(config)
MDRV_CPU_PROGRAM_MAP(r3000_map,0)
MDRV_CPU_ADD(JAGUARGPU, 52000000/2)
MDRV_CPU_ADD(JAGUARGPU, JAGUAR_CLOCK/2)
MDRV_CPU_CONFIG(gpu_config)
MDRV_CPU_PROGRAM_MAP(gpu_map,0)
MDRV_CPU_ADD(JAGUARDSP, 52000000/2)
MDRV_CPU_ADD(JAGUARDSP, JAGUAR_CLOCK/2)
MDRV_CPU_CONFIG(dsp_config)
MDRV_CPU_PROGRAM_MAP(dsp_map,0)
MDRV_SCREEN_REFRESH_RATE(60)
MDRV_MACHINE_RESET(cojag)
MDRV_NVRAM_HANDLER(generic_1fill)
/* video hardware */
MDRV_VIDEO_ATTRIBUTES(VIDEO_TYPE_RASTER | VIDEO_UPDATE_BEFORE_VBLANK)
MDRV_SCREEN_FORMAT(BITMAP_FORMAT_INDEXED16)
MDRV_SCREEN_SIZE(42*8, 262) /* guess -- TOM registers should be used to configure screen */
MDRV_SCREEN_VISIBLE_AREA(0*8, 42*8-1, 0*8, 30*8-1)
MDRV_PALETTE_LENGTH(65534)
MDRV_SCREEN_ADD("main", 0)
MDRV_SCREEN_RAW_PARAMS(COJAG_PIXEL_CLOCK/2, 456, 42, 402, 262, 17, 257)
MDRV_SCREEN_FORMAT(BITMAP_FORMAT_RGB32)
MDRV_VIDEO_START(cojag)
MDRV_VIDEO_UPDATE(cojag)
@ -1025,51 +1028,12 @@ static MACHINE_DRIVER_START( cojagr3k )
MACHINE_DRIVER_END
static MACHINE_DRIVER_START( r3knarrow )
MDRV_IMPORT_FROM(cojagr3k)
/* video hardware */
MDRV_SCREEN_VISIBLE_AREA(0*8, 40*8-1, 0*8, 30*8-1)
MACHINE_DRIVER_END
static MACHINE_DRIVER_START( cojag68k )
MDRV_IMPORT_FROM(cojagr3k)
/* basic machine hardware */
MDRV_CPU_ADD(M68EC020, 50000000/2)
MDRV_CPU_REPLACE("main", M68EC020, M68K_CLOCK/2)
MDRV_CPU_PROGRAM_MAP(m68020_map,0)
MDRV_CPU_ADD(JAGUARGPU, 52000000/2)
MDRV_CPU_CONFIG(gpu_config)
MDRV_CPU_PROGRAM_MAP(gpu_map,0)
MDRV_CPU_ADD(JAGUARDSP, 52000000/2)
MDRV_CPU_CONFIG(dsp_config)
MDRV_CPU_PROGRAM_MAP(dsp_map,0)
MDRV_SCREEN_REFRESH_RATE(60)
MDRV_MACHINE_RESET(cojag)
MDRV_NVRAM_HANDLER(generic_1fill)
/* video hardware */
MDRV_VIDEO_ATTRIBUTES(VIDEO_TYPE_RASTER | VIDEO_UPDATE_BEFORE_VBLANK)
MDRV_SCREEN_FORMAT(BITMAP_FORMAT_INDEXED16)
MDRV_SCREEN_SIZE(42*8, 262) /* guess -- TOM registers should be used to configure screen */
MDRV_SCREEN_VISIBLE_AREA(0*8, 40*8-1, 0*8, 30*8-1)
MDRV_PALETTE_LENGTH(65534)
MDRV_VIDEO_START(cojag)
MDRV_VIDEO_UPDATE(cojag)
/* sound hardware */
MDRV_SPEAKER_STANDARD_STEREO("left", "right")
MDRV_SOUND_ADD(DAC, 0)
MDRV_SOUND_ROUTE(ALL_OUTPUTS, "left", 1.0)
MDRV_SOUND_ADD(DAC, 0)
MDRV_SOUND_ROUTE(ALL_OUTPUTS, "right", 1.0)
MACHINE_DRIVER_END
@ -1423,7 +1387,7 @@ ROM_END
static void cojag_common_init(running_machine *machine, UINT16 gpu_jump_offs, UINT16 spin_pc)
{
/* copy over the ROM */
cojag_is_r3000 = (machine->drv->cpu[0].type == CPU_R3000BE);
cojag_is_r3000 = (machine->drv->cpu[0].type == CPU_R3041BE);
/* install synchronization hooks for GPU */
if (cojag_is_r3000)
@ -1560,7 +1524,7 @@ static DRIVER_INIT( vcircle )
*
*************************************/
GAME( 1996, area51, 0, r3knarrow, area51, area51, ROT0, "Atari Games", "Area 51 (R3000)", 0 )
GAME( 1996, area51, 0, cojagr3k, area51, area51, ROT0, "Atari Games", "Area 51 (R3000)", 0 )
GAME( 1995, area51t, area51, cojag68k, area51, area51a, ROT0, "Time Warner", "Area 51 (Time Warner License)", 0 )
GAME( 1995, area51a, area51, cojag68k, area51, area51a, ROT0, "Atari Games", "Area 51 (Atari Games License)", 0 )
GAME( 1995, fishfren, 0, cojagr3k, fishfren, fishfren, ROT0, "Time Warner Interactive", "Fishin' Frenzy (prototype)", 0 )
@ -1571,9 +1535,9 @@ GAME( 1996, freezea3, freezeat, cojagr3k, freezeat, freezea3, ROT0, "Atari Game
GAME( 1996, freezea4, freezeat, cojagr3k, freezeat, freezea4, ROT0, "Atari Games", "Freeze (Atari) (prototype, 96/10/03)", 0 )
GAME( 1996, freezea5, freezeat, cojagr3k, freezeat, freezea5, ROT0, "Atari Games", "Freeze (Atari) (prototype, 96/09/20, AMOA-96)", 0 )
GAME( 1996, freezea6, freezeat, cojagr3k, freezeat, freezea6, ROT0, "Atari Games", "Freeze (Atari) (prototype, 96/09/07, Jamma-96)", 0 )
GAME( 1996, maxforce, 0, r3knarrow, area51, maxforce, ROT0, "Atari Games", "Maximum Force v1.05", 0 )
GAME( 1996, maxf_102, maxforce, r3knarrow, area51, maxforce, ROT0, "Atari Games", "Maximum Force v1.02", 0 )
GAME( 1996, maxf_ng, maxforce, r3knarrow, area51, maxforce, ROT0, "Atari Games", "Maximum Force (No Gore version)", 0 )
GAME( 1996, maxforce, 0, cojagr3k, area51, maxforce, ROT0, "Atari Games", "Maximum Force v1.05", 0 )
GAME( 1996, maxf_102, maxforce, cojagr3k, area51, maxforce, ROT0, "Atari Games", "Maximum Force v1.02", 0 )
GAME( 1996, maxf_ng, maxforce, cojagr3k, area51, maxforce, ROT0, "Atari Games", "Maximum Force (No Gore version)", 0 )
GAME( 1998, area51mx, 0, cojag68k, area51, area51mx, ROT0, "Atari Games", "Area 51 / Maximum Force Duo v2.0", 0 )
GAME( 1998, a51mxr3k, area51mx, r3knarrow, area51, a51mxr3k, ROT0, "Atari Games", "Area 51 / Maximum Force Duo (R3000)", 0 )
GAME( 1998, a51mxr3k, area51mx, cojagr3k, area51, a51mxr3k, ROT0, "Atari Games", "Area 51 / Maximum Force Duo (R3000)", 0 )
GAME( 1996, vcircle, 0, cojagr3k, vcircle, vcircle, ROT0, "Atari Games", "Vicious Circle (prototype)", 0 )

View File

@ -316,8 +316,8 @@
*
*************************************/
#define MASTER_CLOCK 48660000
#define SOUND_CLOCK 4000000
#define MASTER_CLOCK XTAL_48_66MHz
#define SOUND_CLOCK XTAL_4MHz
#define PIXEL_CLOCK (MASTER_CLOCK/8)

View File

@ -12,6 +12,9 @@
#endif /* MESS */
#endif
#define COJAG_PIXEL_CLOCK XTAL_14_31818MHz
/*----------- defined in drivers/cojag.c -----------*/

View File

@ -126,6 +126,7 @@ CPUS += ARM
CPUS += ARM7
CPUS += JAGUAR
CPUS += R3000
CPUS += R3041
CPUS += R4600
CPUS += R4650
CPUS += R4700

View File

@ -12,7 +12,7 @@
#define LOG_OBJECTS 0
static UINT16 scanline[360];
static UINT16 *scanline;
static UINT16 *clutbase;
static UINT8 *blend_y, *blend_cc;
@ -900,87 +900,75 @@ static UINT32 *process_branch(UINT32 *objdata, int vc, int logit)
*
*************************************/
static void process_object_list(mame_bitmap *bitmap, const rectangle *cliprect)
static void process_object_list(int vc, UINT16 *_scanline)
{
int done = 0, count = 0;
UINT32 *objdata;
int y, x, pass;
int logit;
int x;
/* loop over all scanlines */
for (y = cliprect->min_y; y <= cliprect->max_y; y++)
{
/* erase the scanline first */
for (x = 0; x < 336; x++)
scanline[x] = gpu_regs[BG];
/* erase the scanline first */
scanline = _scanline;
for (x = 0; x < 336; x++)
scanline[x] = gpu_regs[BG];
#if LOG_OBJECTS
logit = (y == cliprect->min_y);
logit = (y == cliprect->min_y);
#else
logit = 0;
logit = 0;
#endif
/* two passes per scanline */
for (pass = 0; pass < 1; pass++)
/* fetch the object pointer */
objdata = (UINT32 *)get_jaguar_memory((gpu_regs[OLP_H] << 16) | gpu_regs[OLP_L]);
while (!done && objdata && count++ < 100)
{
/* the low 3 bits determine the command */
switch (objdata[1] & 7)
{
int vc = y * 2 + pass + gpu_regs[VBE];
int done = 0, count = 0;
/* bitmap object */
case 0:
if (logit)
logerror("bitmap = %08X-%08X %08X-%08X\n", objdata[0], objdata[1], objdata[2], objdata[3]);
objdata = process_bitmap(objdata, vc, logit);
break;
/* fetch the object pointer */
objdata = (UINT32 *)get_jaguar_memory((gpu_regs[OLP_H] << 16) | gpu_regs[OLP_L]);
while (!done && objdata && count++ < 100)
/* scaled bitmap object */
case 1:
if (logit)
logerror("scaled = %08X-%08X %08X-%08X %08X-%08X\n", objdata[0], objdata[1], objdata[2], objdata[3], objdata[4], objdata[5]);
objdata = process_scaled_bitmap(objdata, vc, logit);
break;
/* branch */
case 3:
if (logit)
logerror("branch = %08X-%08X\n", objdata[0], objdata[1]);
objdata = process_branch(objdata, vc, logit);
break;
/* stop */
case 4:
{
/* the low 3 bits determine the command */
switch (objdata[1] & 7)
int interrupt = (objdata[1] >> 3) & 1;
done = 1;
if (logit)
logerror("stop = %08X-%08X\n", objdata[0], objdata[1]);
if (interrupt)
{
/* bitmap object */
case 0:
if (logit)
logerror("bitmap = %08X-%08X %08X-%08X\n", objdata[0], objdata[1], objdata[2], objdata[3]);
objdata = process_bitmap(objdata, vc, logit);
break;
/* scaled bitmap object */
case 1:
if (logit)
logerror("scaled = %08X-%08X %08X-%08X %08X-%08X\n", objdata[0], objdata[1], objdata[2], objdata[3], objdata[4], objdata[5]);
objdata = process_scaled_bitmap(objdata, vc, logit);
break;
/* branch */
case 3:
if (logit)
logerror("branch = %08X-%08X\n", objdata[0], objdata[1]);
objdata = process_branch(objdata, vc, logit);
break;
/* stop */
case 4:
{
int interrupt = (objdata[1] >> 3) & 1;
done = 1;
if (logit)
logerror("stop = %08X-%08X\n", objdata[0], objdata[1]);
if (interrupt)
{
#ifndef MESS
fprintf(stderr, "stop int=%d\n", interrupt);
fprintf(stderr, "stop int=%d\n", interrupt);
#endif
cpu_irq_state |= 4;
update_cpu_irq();
}
break;
}
default:
fprintf(stderr, "%08X %08X\n", objdata[0], objdata[1]);
done = 1;
break;
cpu_irq_state |= 4;
update_cpu_irq();
}
break;
}
}
/* render this scanline */
draw_scanline16(bitmap, 0, y, 336, scanline, pen_table, -1);
default:
fprintf(stderr, "%08X %08X\n", objdata[0], objdata[1]);
done = 1;
break;
}
}
}

View File

@ -143,6 +143,8 @@
#include "jagblit.h"
#define ENABLE_BORDERS 0
#define LOG_BLITS 0
#define LOG_BAD_BLITS 0
#define LOG_BLITTER_STATS 0
@ -190,9 +192,11 @@ enum
static UINT32 blitter_regs[BLITTER_REGS];
static UINT16 gpu_regs[GPU_REGS];
static emu_timer *vi_timer;
static emu_timer *object_timer;
static UINT8 cpu_irq_state;
static mame_bitmap *screen_bitmap;
static pen_t *pen_table;
@ -205,7 +209,7 @@ static pen_t *pen_table;
/* from jagobj.c */
static void jagobj_init(void);
static void process_object_list(mame_bitmap *bitmap, const rectangle *cliprect);
static void process_object_list(int vc, UINT16 *_scanline);
/* from jagblit.c */
static void generic_blitter(UINT32 command, UINT32 a1flags, UINT32 a2flags);
@ -229,10 +233,65 @@ static void blitter_x1800x01_xxxxxx_xxxxxx(UINT32 command, UINT32 a1flags, UINT3
*
*************************************/
INLINE void get_crosshair_xy(int player, int *x, int *y)
INLINE void get_crosshair_xy(running_machine *machine, int player, int *x, int *y)
{
*x = ((readinputport(3 + player * 2) & 0xff) * Machine->screen[0].width) >> 8;
*y = ((readinputport(4 + player * 2) & 0xff) * Machine->screen[0].height) >> 8;
int width = machine->screen[0].visarea.max_x + 1 - machine->screen[0].visarea.min_x;
int height = machine->screen[0].visarea.max_y + 1 - machine->screen[0].visarea.min_y;
*x = machine->screen[0].visarea.min_x + (((readinputport(3 + player * 2) & 0xff) * width) >> 8);
*y = machine->screen[0].visarea.min_y + (((readinputport(4 + player * 2) & 0xff) * height) >> 8);
}
/*************************************
*
* Horizontal display values
*
*************************************/
INLINE int effective_hvalue(int value)
{
if (!(value & 0x400))
return value & 0x3ff;
else
return (value & 0x3ff) + (gpu_regs[HP] & 0x3ff) + 1;
}
/*************************************
*
* Object processor timer
*
*************************************/
INLINE int adjust_object_timer(running_machine *machine, int vc)
{
int hdbpix[2];
int hdb = 0;
/* extract the display begin registers */
hdbpix[0] = (gpu_regs[HDB1] & 0x7ff) / 2;
hdbpix[1] = (gpu_regs[HDB2] & 0x7ff) / 2;
/* sort */
if (hdbpix[0] > hdbpix[1])
{
int temp = hdbpix[0];
hdbpix[0] = hdbpix[1];
hdbpix[1] = temp;
}
/* select the target one */
hdb = hdbpix[vc % 2];
/* if setting the second one in a line, make sure we will ever actually hit it */
if (vc % 2 == 1 && (hdbpix[1] == hdbpix[0] || hdbpix[1] >= machine->screen[0].width))
return FALSE;
/* adjust the timer */
timer_adjust(object_timer, video_screen_get_time_until_pos(0, vc / 2, hdb), vc | (hdb << 16), attotime_never);
return TRUE;
}
@ -271,16 +330,6 @@ static void update_cpu_irq(void)
}
static TIMER_CALLBACK( vi_callback )
{
int scanline = param;
cpu_irq_state |= 1;
update_cpu_irq();
timer_adjust(vi_timer, video_screen_get_time_until_pos(0, scanline, 0), scanline, attotime_zero);
}
void jaguar_gpu_cpu_int(void)
{
cpu_irq_state |= 2;
@ -364,45 +413,25 @@ static void jaguar_set_palette(UINT16 vmode)
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
};
int i, colors = 0;
int i;
/* switch off the mode */
switch (vmode & 0x106)
{
/* YCC full */
case 0x000:
{
/* set color 0 to black */
palette_set_color(Machine, colors++, MAKE_RGB(0, 0, 0));
/* due to the way YCC colorspace maps onto RGB, there are multiple entries for black */
/* take advantage of this so we don't have to use all 64k colors */
for (i = 0; i < 65536; i++)
{
UINT8 r = (red_lookup[i >> 8] * (i & 0xff)) >> 8;
UINT8 g = (grn_lookup[i >> 8] * (i & 0xff)) >> 8;
UINT8 b = (blu_lookup[i >> 8] * (i & 0xff)) >> 8;
if (r == 0 && g == 0 && b == 0)
pen_table[i] = 0;
else
{
pen_table[i] = colors;
palette_set_color(Machine, colors++, MAKE_RGB(r, g, b));
}
pen_table[i] = MAKE_RGB(r, g, b);
}
break;
}
/* YCC/RGB VARMOD */
case 0x100:
case 0x107:
{
/* set color 0 to black */
palette_set_color(Machine, colors++, MAKE_RGB(0, 0, 0));
/* due to the way YCC colorspace maps onto RGB, there are multiple entries for black */
/* take advantage of this so we don't have to use all 64k colors */
for (i = 0; i < 65536; i++)
{
UINT8 r = (red_lookup[i >> 8] * (i & 0xff)) >> 8;
@ -419,39 +448,15 @@ static void jaguar_set_palette(UINT16 vmode)
g = (g << 3) | (g >> 2);
b = (b << 3) | (b >> 2);
}
if (r == 0 && g == 0 && b == 0)
pen_table[i] = 0;
else
{
pen_table[i] = colors;
palette_set_color(Machine, colors++, MAKE_RGB(r, g, b));
}
pen_table[i] = MAKE_RGB(r, g, b);
}
break;
}
/* RGB full */
case 0x006:
{
/* we cheat a little here to squeeze into 65534 colors */
palette_set_color(Machine, colors++, MAKE_RGB(0, 0, 0));
palette_set_color(Machine, colors++, MAKE_RGB(0, 8, 0));
palette_set_color(Machine, colors++, MAKE_RGB(0, 16, 0));
pen_table[0] = 0;
pen_table[1] = 1;
pen_table[2] = 1;
pen_table[3] = 2;
pen_table[4] = 2;
/* map the remaining colors normally */
for (i = 5; i < 65536; i++)
{
pen_table[i] = colors;
palette_set_color_rgb(Machine, colors++, pal5bit(i >> 11), pal6bit(i >> 0), pal5bit(i >> 6));
}
for (i = 0; i < 65536; i++)
pen_table[i] = MAKE_RGB(pal5bit(i >> 11), pal6bit(i >> 0), pal5bit(i >> 6));
break;
}
/* others */
default:
@ -637,19 +642,12 @@ READ16_HANDLER( jaguar_tom_regs_r )
WRITE16_HANDLER( jaguar_tom_regs_w )
{
int scanline;
if (offset < GPU_REGS)
{
COMBINE_DATA(&gpu_regs[offset]);
switch (offset)
{
case VI:
scanline = (gpu_regs[VI] - gpu_regs[VBE]) / 2;
timer_adjust(vi_timer, video_screen_get_time_until_pos(0, scanline, 0), scanline, attotime_zero);
break;
case INT1:
cpu_irq_state &= ~(gpu_regs[INT1] >> 8);
update_cpu_irq();
@ -658,6 +656,38 @@ WRITE16_HANDLER( jaguar_tom_regs_w )
case VMODE:
jaguar_set_palette(gpu_regs[VMODE]);
break;
case HP:
case HBB:
case HBE:
case HDB1:
case HDB2:
case HDE:
case VP:
case VBB:
case VBE:
case VDB:
case VDE:
{
int hperiod = 2 * ((gpu_regs[HP] & 0x3ff) + 1);
int hbend = effective_hvalue(ENABLE_BORDERS ? gpu_regs[HBE] : MIN(gpu_regs[HDB1], gpu_regs[HDB2]));
int hbstart = effective_hvalue(gpu_regs[ENABLE_BORDERS ? HBB : HDE]);
int vperiod = (gpu_regs[VP] & 0x7ff) + 1;
int vbend = gpu_regs[VBE] & 0x7ff;
int vbstart = gpu_regs[VBB] & 0x7ff;
/* adjust for the half-lines */
if (hperiod != 0 && vperiod != 0 && hbend < hbstart && vbend < vbstart && hbstart < hperiod)
{
rectangle visarea;
visarea.min_x = hbend / 2;
visarea.max_x = hbstart / 2 - 1;
visarea.min_y = vbend / 2;
visarea.max_y = vbstart / 2 - 1;
video_screen_configure(0, hperiod / 2, vperiod / 2, &visarea, HZ_TO_ATTOSECONDS((double)COJAG_PIXEL_CLOCK * 2 / hperiod / vperiod));
}
break;
}
}
}
@ -702,15 +732,11 @@ READ32_HANDLER( cojag_gun_input_r )
switch (offset)
{
case 0:
get_crosshair_xy(1, &beamx, &beamy);
beamx += 52;
beamy += 17;
get_crosshair_xy(Machine, 1, &beamx, &beamy);
return (beamy << 16) | (beamx ^ 0x1ff);
case 1:
get_crosshair_xy(0, &beamx, &beamy);
beamx += 52;
beamy += 17;
get_crosshair_xy(Machine, 0, &beamx, &beamy);
return (beamy << 16) | (beamx ^ 0x1ff);
case 2:
@ -727,14 +753,65 @@ READ32_HANDLER( cojag_gun_input_r )
*
*************************************/
static TIMER_CALLBACK( cojag_scanline_update )
{
int vc = param & 0xffff;
int hdb = param >> 16;
/* only run if video is enabled and we are past the "display begin" */
if ((gpu_regs[VMODE] & 1) && vc >= (gpu_regs[VDB] & 0x7ff))
{
UINT32 *dest = BITMAP_ADDR32(screen_bitmap, vc / 2, 0);
int maxx = machine->screen[0].visarea.max_x;
int hde = effective_hvalue(gpu_regs[HDE]) / 2;
UINT16 scanline[360];
int x;
/* if we are first on this scanline, clear to the border color */
if (ENABLE_BORDERS && vc % 2 == 0)
{
rgb_t border = MAKE_RGB(gpu_regs[BORD1] & 0xff, gpu_regs[BORD1] >> 8, gpu_regs[BORD2] & 0xff);
for (x = machine->screen[0].visarea.min_x; x <= machine->screen[0].visarea.max_x; x++)
dest[x] = border;
}
/* process the object list for this counter value */
process_object_list(vc, scanline);
/* copy the data to the target, clipping */
for (x = 0; x < 360 && hdb <= maxx && hdb < hde; x++, hdb++)
dest[hdb] = pen_table[scanline[x]];
}
/* adjust the timer in a loop, to handle missed cases */
do
{
/* handle vertical interrupts */
if (vc == gpu_regs[VI])
{
cpu_irq_state |= 1;
update_cpu_irq();
}
/* point to the next counter value */
if (++vc / 2 >= machine->screen[0].height)
vc = 0;
} while (!adjust_object_timer(machine, vc));
}
VIDEO_START( cojag )
{
object_timer = timer_alloc(cojag_scanline_update, NULL);
adjust_object_timer(machine, 0);
screen_bitmap = auto_bitmap_alloc(720, 512, BITMAP_FORMAT_RGB32);
jagobj_init();
pen_table = auto_malloc(65536 * sizeof(pen_t));
vi_timer = timer_alloc(vi_callback, NULL);
state_save_register_global_pointer(pen_table, 65536);
state_save_register_global_array(blitter_regs);
state_save_register_global_array(gpu_regs);
@ -760,7 +837,7 @@ VIDEO_UPDATE( cojag )
}
/* render the object list */
process_object_list(bitmap, cliprect);
copybitmap(bitmap, screen_bitmap, 0, 0, 0, 0, cliprect, TRANSPARENCY_NONE, 0);
return 0;
}