shithub: riscv

Download patch

ref: 4abb38f1778a60e8d3ae14af928b0192ff3a5ed2
parent: 49ecfb6689b2a2dbe465dd8a98d5448add57831b
author: aiju <devnull@localhost>
date: Fri Mar 21 12:55:16 EDT 2014

games/snes: bug fixes

--- a/sys/src/games/snes/mem.c
+++ b/sys/src/games/snes/mem.c
@@ -38,9 +38,19 @@
 }
 
 static void
+vramread(void)
+{
+	u16int b;
+
+	b = vrammap(reg[0x2116] | reg[0x2117] << 8);
+	vramlatch = vram[b++];
+	vramlatch |= vram[b] << 8;
+}
+
+static void
 incvram(int i, int r)
 {
-	u16int a, b;
+	u16int a;
 	int c;
 	
 	c = reg[0x2115];
@@ -47,11 +57,8 @@
 	if((c >> 7) != i)
 		return;
 	a = reg[0x2116] | reg[0x2117] << 8;
-	if(r){
-		b = vrammap(a);
-		vramlatch = vram[b++];
-		vramlatch |= vram[b] << 8;
-	}
+	if(r)
+		vramread();
 	switch(c & 3){
 	case 0: a++; break;
 	case 1: a += 32; break;
@@ -162,14 +169,14 @@
 			return reg[OPVCTH] | mdr2 & 0xfe;
 		return mdr2 = reg[p];
 	case 0x213e:
-		return (mdr1 = reg[p]) | mdr & 0x10;
+		return mdr1 = reg[p] | mdr1 & 0x10;
 	case 0x213f:
-		v = 2 | reg[OPCTLATCH] & 0x40;
+		v = reg[OPCTLATCH] & 0x40;
 		if((reg[0x4201] & 0x80) != 0)
 			reg[OPCTLATCH] &= ~0x43;
 		else
 			reg[OPCTLATCH] &= ~3;
-		return mdr2 = v | mdr2 & 0x20;
+		return mdr2 = reg[p] | v | mdr2 & 0x20;
 	case 0x2180:
 		v = memread(0x7e0000 | reg[0x2181] | reg[0x2182] << 8 | (reg[0x2183] & 1) << 16);
 		incwram();
@@ -189,7 +196,9 @@
 	case 0x4017:
 		return 0x1f | mdr & 0xe0;
 	case 0x4210:
-		return reg[p] | mdr & 0x70;
+		v = reg[p];
+		reg[p] &= ~VBLANK;
+		return v | mdr & 0x70;
 	case 0x4211:
 		v = irq;
 		irq &= ~IRQPPU;
@@ -209,6 +218,10 @@
 	case 0x4219: case 0x421a: case 0x421b: case 0x421c: case 0x421d:
 	case 0x421e: case 0x421f:
 		return reg[p];
+	case 0x2104: case 0x2105: case 0x2106: case 0x2108: case 0x2109: case 0x210a:
+	case 0x2114: case 0x2115: case 0x2116: case 0x2118: case 0x2119: case 0x211a:
+	case 0x2124: case 0x2125: case 0x2126: case 0x2128: case 0x2129: case 0x212a:
+		return mdr1;
 	}
 	if((p & 0xff80) == 0x4300)
 		return reg[p];
@@ -270,11 +283,12 @@
 		vofs[(p - 0x210e) >> 1] = v << 8 | reg[OFSPREV];
 		reg[OFSPREV] = v;
 		break;
-	case 0x2116:
-		break;
 	case 0x2117:
 		v &= 0x7f;
-		break;
+	case 0x2116:
+		reg[p] = v;
+		vramread();
+		return;
 	case 0x2118:
 		a = vrammap(reg[0x2116] | reg[0x2117] << 8);
 		vram[a] = v;
@@ -620,6 +634,7 @@
 memreset(void)
 {
 	reg[0x213e] = 1;
+	reg[0x213f] = 2;
 	reg[0x4201] = 0xff;
 	reg[0x4210] = 2;
 }
--- a/sys/src/games/snes/ppu.c
+++ b/sys/src/games/snes/ppu.c
@@ -618,7 +618,7 @@
 		u32int *ch;
 	} t[32], *tp;
 	static u32int ch[34];
-	static u8int *p, q, over;
+	static u8int *p, q;
 	static int n, m;
 	static int *sz;
 	static int szs[] = {
@@ -635,7 +635,6 @@
 
 	if(rx == 0){
 		n = 0;
-		over = 1;
 		sp = s;
 		sz = szs + ((reg[OBSEL] & 0xe0) >> 3);
 		base[0] = (reg[OBSEL] & 0x07) << 14;
@@ -654,10 +653,10 @@
 		sp->x = p[0];
 		if((q & 1) != 0)
 			sp->x |= 0xff00;
-		if(sp->x < -(short)sp->sx && sp->x != -256)
+		if(sp->x <= -(short)sp->sx && sp->x != -256)
 			goto nope;
 		if(n == 32){
-			over |= 0x40;
+			reg[0x213e] |= 0x40;
 			goto nope;
 		}
 		sp->i = rx >> 1;
@@ -742,7 +741,7 @@
 						*cp++ = w;
 						tp->sx += 8;
 					}else
-						over |= 0x80;
+						reg[0x213e] |= 0x80;
 				}
 			}else
 				for(i = 0; i < nt; i++){
@@ -755,7 +754,7 @@
 						tp->sx += 8;
 						a += 15;
 					}else
-						over |= 0x80;
+						reg[0x213e] |= 0x80;
 				}
 			if(sp->x < 0 && (i = (-sp->x) & 7) != 0)
 				if((sp->c & 0x40) != 0)
@@ -763,7 +762,6 @@
 				else
 					*tp->ch <<= i;
 		}
-		reg[0x213e] = over;
 	}
 }
 
@@ -868,6 +866,8 @@
 		if(++ppuy >= 262){
 			ppuy = 0;
 			reg[RDNMI] &= ~VBLANK;
+			reg[0x213e] = 1;
+			reg[0x213f] ^= 0x80;
 			hdma = reg[0x420c]<<8;
 			flush();
 		}