forked from sin365/AxibugEmuOnline
进行一些内联优化,还有timer对象池优化
This commit is contained in:
parent
d2cc4fa05d
commit
200ee3830b
@ -32,7 +32,7 @@ namespace cpu.m6800
|
|||||||
private ushort M6803_DDR1 = 0x00, M6803_DDR2 = 0x01, M6803_DDR3 = 0x04, M6803_DDR4 = 0x05, M6803_PORT1 = 0x100, M6803_PORT2 = 0x101, M6803_PORT3 = 0x102, M6803_PORT4 = 0x103;
|
private ushort M6803_DDR1 = 0x00, M6803_DDR2 = 0x01, M6803_DDR3 = 0x04, M6803_DDR4 = 0x05, M6803_PORT1 = 0x100, M6803_PORT2 = 0x101, M6803_PORT3 = 0x102, M6803_PORT4 = 0x103;
|
||||||
private byte M6800_RMCR_SS_MASK = 0x03, M6800_RMCR_SS_4096 = 0x03, M6800_RMCR_SS_1024 = 0x02, M6800_RMCR_SS_128 = 0x01, M6800_RMCR_SS_16 = 0x00, M6800_RMCR_CC_MASK = 0x0c;
|
private byte M6800_RMCR_SS_MASK = 0x03, M6800_RMCR_SS_4096 = 0x03, M6800_RMCR_SS_1024 = 0x02, M6800_RMCR_SS_128 = 0x01, M6800_RMCR_SS_16 = 0x00, M6800_RMCR_CC_MASK = 0x0c;
|
||||||
private byte M6800_TRCSR_RDRF = 0x80, M6800_TRCSR_ORFE = 0x40, M6800_TRCSR_TDRE = 0x20, M6800_TRCSR_RIE = 0x10, M6800_TRCSR_RE = 0x08, M6800_TRCSR_TIE = 0x04, M6800_TRCSR_TE = 0x02, M6800_TRCSR_WU = 0x01, M6800_PORT2_IO4 = 0x10, M6800_PORT2_IO3 = 0x08;
|
private byte M6800_TRCSR_RDRF = 0x80, M6800_TRCSR_ORFE = 0x40, M6800_TRCSR_TDRE = 0x20, M6800_TRCSR_RIE = 0x10, M6800_TRCSR_RE = 0x08, M6800_TRCSR_TIE = 0x04, M6800_TRCSR_TE = 0x02, M6800_TRCSR_WU = 0x01, M6800_PORT2_IO4 = 0x10, M6800_PORT2_IO3 = 0x08;
|
||||||
private int[] M6800_RMCR_SS = new int[] { 16, 128, 1024, 4096 };
|
private static int[] M6800_RMCR_SS = new int[] { 16, 128, 1024, 4096 };
|
||||||
public enum M6800_TX_STATE
|
public enum M6800_TX_STATE
|
||||||
{
|
{
|
||||||
INIT = 0,
|
INIT = 0,
|
||||||
@ -64,7 +64,7 @@ namespace cpu.m6800
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
public uint timer_next;
|
public uint timer_next;
|
||||||
public byte[] flags8i = new byte[256] /* increment */
|
public readonly static byte[] flags8i = new byte[256] /* increment */
|
||||||
{
|
{
|
||||||
0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
||||||
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
||||||
@ -83,7 +83,7 @@ namespace cpu.m6800
|
|||||||
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
|
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
|
||||||
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08
|
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08
|
||||||
};
|
};
|
||||||
private byte[] flags8d = new byte[256] /* decrement */
|
private readonly static byte[] flags8d = new byte[256] /* decrement */
|
||||||
{
|
{
|
||||||
0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
||||||
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
||||||
@ -102,7 +102,7 @@ namespace cpu.m6800
|
|||||||
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
|
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
|
||||||
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08
|
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08
|
||||||
};
|
};
|
||||||
private byte[] cycles_6800 = new byte[]
|
private readonly static byte[] cycles_6800 = new byte[]
|
||||||
{
|
{
|
||||||
/* 0 1 2 3 4 5 6 7 8 9 A B C D E F */
|
/* 0 1 2 3 4 5 6 7 8 9 A B C D E F */
|
||||||
/*0*/ 99, 2,99,99,99,99, 2, 2, 4, 4, 2, 2, 2, 2, 2, 2,
|
/*0*/ 99, 2,99,99,99,99, 2, 2, 4, 4, 2, 2, 2, 2, 2, 2,
|
||||||
|
|||||||
@ -56,7 +56,7 @@ namespace cpu.m6805
|
|||||||
0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,
|
0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,
|
||||||
0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04
|
0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x04
|
||||||
};
|
};
|
||||||
public byte[] cycles1 = new byte[]
|
public readonly static byte[] cycles1 = new byte[]
|
||||||
{
|
{
|
||||||
/* 0 1 2 3 4 5 6 7 8 9 A B C D E F */
|
/* 0 1 2 3 4 5 6 7 8 9 A B C D E F */
|
||||||
/*0*/ 10,10,10,10,10,10,10,10,10,10,10,10,10,10,10,10,
|
/*0*/ 10,10,10,10,10,10,10,10,10,10,10,10,10,10,10,10,
|
||||||
|
|||||||
@ -85,7 +85,7 @@ namespace cpu.m6809
|
|||||||
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
|
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
|
||||||
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08
|
0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08
|
||||||
};
|
};
|
||||||
private byte[] cycles_6809 = new byte[]
|
private readonly static byte[] cycles_6809 = new byte[]
|
||||||
{
|
{
|
||||||
0x06,0x06,0x02,0x06,0x06,0x02,0x06,0x06,0x06,0x06,0x06,0x02,0x06,0x06,0x03,0x06,
|
0x06,0x06,0x02,0x06,0x06,0x02,0x06,0x06,0x06,0x06,0x06,0x02,0x06,0x06,0x03,0x06,
|
||||||
0x00,0x00,0x02,0x04,0x02,0x02,0x05,0x09,0x02,0x02,0x03,0x02,0x03,0x02,0x08,0x06,
|
0x00,0x00,0x02,0x04,0x02,0x02,0x05,0x09,0x02,0x02,0x03,0x02,0x03,0x02,0x08,0x06,
|
||||||
|
|||||||
@ -449,7 +449,7 @@ namespace cpu.nec
|
|||||||
I.regs.b[Reg * 2 + 1] = (byte)((ushort)tmp1 / 0x100);
|
I.regs.b[Reg * 2 + 1] = (byte)((ushort)tmp1 / 0x100);
|
||||||
}
|
}
|
||||||
|
|
||||||
static byte[] JMP_table = new byte[] { 3, 10, 10 };
|
readonly static byte[] JMP_table = new byte[] { 3, 10, 10 };
|
||||||
//public void JMP(bool flag)
|
//public void JMP(bool flag)
|
||||||
//{
|
//{
|
||||||
// int tmp = (int)((sbyte)FETCH());
|
// int tmp = (int)((sbyte)FETCH());
|
||||||
@ -732,7 +732,7 @@ namespace cpu.nec
|
|||||||
I.regs.b[5] = (byte)((ushort)result2 / 0x100);
|
I.regs.b[5] = (byte)((ushort)result2 / 0x100);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
static byte[] ADD4S_table = new byte[] { 18, 19, 19 };
|
readonly static byte[] ADD4S_table = new byte[] { 18, 19, 19 };
|
||||||
public void ADD4S(ref int tmp, ref int tmp2)
|
public void ADD4S(ref int tmp, ref int tmp2)
|
||||||
{
|
{
|
||||||
int i, v1, v2, result;
|
int i, v1, v2, result;
|
||||||
|
|||||||
@ -15,7 +15,7 @@
|
|||||||
public byte animation_counter;
|
public byte animation_counter;
|
||||||
}
|
}
|
||||||
public static crosshair_global global;
|
public static crosshair_global global;
|
||||||
public static byte[] crosshair_raw_top = new byte[]
|
public readonly static byte[] crosshair_raw_top = new byte[]
|
||||||
{
|
{
|
||||||
0x00,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x40,0x00,
|
0x00,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x40,0x00,
|
||||||
0x00,0x70,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xe0,0x00,
|
0x00,0x70,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xe0,0x00,
|
||||||
|
|||||||
@ -1,10 +1,6 @@
|
|||||||
using cpu.m6800;
|
using cpu.m6800;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Concurrent;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Runtime.ConstrainedExecution;
|
|
||||||
using System.Threading;
|
|
||||||
using System.Timers;
|
|
||||||
using static MAME.Core.EmuTimer;
|
using static MAME.Core.EmuTimer;
|
||||||
|
|
||||||
namespace MAME.Core
|
namespace MAME.Core
|
||||||
@ -68,7 +64,6 @@ namespace MAME.Core
|
|||||||
{
|
{
|
||||||
emu_timer.RemoveToList(ref timerlist, ref timer);
|
emu_timer.RemoveToList(ref timerlist, ref timer);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Insert(int index, emu_timer timer)
|
public void Insert(int index, emu_timer timer)
|
||||||
{
|
{
|
||||||
emu_timer.InsertToList(ref timerlist, index, ref timer);
|
emu_timer.InsertToList(ref timerlist, index, ref timer);
|
||||||
@ -78,6 +73,11 @@ namespace MAME.Core
|
|||||||
{
|
{
|
||||||
return timerlist.IndexOf(timer);
|
return timerlist.IndexOf(timer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void RemoveAt(int index)
|
||||||
|
{
|
||||||
|
emu_timer.RemoveAtToList(ref timerlist, index);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public class EmuTimer
|
public class EmuTimer
|
||||||
@ -117,6 +117,11 @@ namespace MAME.Core
|
|||||||
public Atime start;
|
public Atime start;
|
||||||
public Atime expire;
|
public Atime expire;
|
||||||
|
|
||||||
|
// 引用计数字段
|
||||||
|
private int _refCount;
|
||||||
|
// 是否在检查池中
|
||||||
|
private bool _inReadyQueue;
|
||||||
|
|
||||||
internal void reset()
|
internal void reset()
|
||||||
{
|
{
|
||||||
action = default;
|
action = default;
|
||||||
@ -126,27 +131,25 @@ namespace MAME.Core
|
|||||||
start = default;
|
start = default;
|
||||||
expire = default;
|
expire = default;
|
||||||
_refCount = 0;
|
_refCount = 0;
|
||||||
|
_inReadyQueue = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
static Queue<emu_timer> _readyToRelease = new Queue<emu_timer>();
|
static Queue<emu_timer> _readyToRelease = new Queue<emu_timer>();
|
||||||
/// <summary>
|
static Queue<emu_timer> _timerPool = new Queue<emu_timer>();
|
||||||
/// 线程安全队列(因为析构函数是额外线程来的)
|
|
||||||
/// </summary>
|
|
||||||
static Queue<emu_timer> _failedDeletions = new Queue<emu_timer>();
|
|
||||||
static HashSet<emu_timer> _tempCheck = new HashSet<emu_timer>();
|
|
||||||
|
|
||||||
static int outTimerAllCount = 0;
|
static int outTimerAllCount = 0;
|
||||||
static int newTimerCount = 0;
|
static int newTimerCount = 0;
|
||||||
public static emu_timer GetEmu_timerNoRef()
|
public static emu_timer GetEmu_timerNoRef()
|
||||||
{
|
{
|
||||||
emu_timer obj;
|
emu_timer obj;
|
||||||
if (!_failedDeletions.TryDequeue(out obj))
|
if (!_timerPool.TryDequeue(out obj))
|
||||||
{
|
{
|
||||||
obj = new emu_timer();
|
obj = new emu_timer();
|
||||||
newTimerCount++;
|
newTimerCount++;
|
||||||
}
|
}
|
||||||
//这里引用计数为0,直接放入带Ready里,等待下一帧检测
|
//这里引用计数为0,直接放入带Ready里,等待下一帧检测
|
||||||
obj.reset();
|
obj.reset();
|
||||||
|
obj._inReadyQueue = true;
|
||||||
_readyToRelease.Enqueue(obj);
|
_readyToRelease.Enqueue(obj);
|
||||||
outTimerAllCount++;
|
outTimerAllCount++;
|
||||||
return obj;
|
return obj;
|
||||||
@ -157,47 +160,31 @@ namespace MAME.Core
|
|||||||
if (_readyToRelease.Count < 1)
|
if (_readyToRelease.Count < 1)
|
||||||
return;
|
return;
|
||||||
int checkcount = _readyToRelease.Count;
|
int checkcount = _readyToRelease.Count;
|
||||||
int beforpoolcount = _failedDeletions.Count;
|
int beforpoolcount = _timerPool.Count;
|
||||||
int releaseCount = 0;
|
int releaseCount = 0;
|
||||||
while(_readyToRelease.TryDequeue(out emu_timer ready))
|
while (_readyToRelease.TryDequeue(out emu_timer ready))
|
||||||
{
|
{
|
||||||
if (_tempCheck.Contains(ready))
|
ready._inReadyQueue = false;
|
||||||
continue;
|
|
||||||
_tempCheck.Add(ready);
|
|
||||||
if (ready._refCount <= 0)
|
if (ready._refCount <= 0)
|
||||||
{
|
{
|
||||||
ready.ReturnToPool();
|
ready.ReturnToPool();
|
||||||
releaseCount++;
|
releaseCount++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
//UnityEngine.Debug.Log($"CheckReadyRelaseAfterRun 检查数量{checkcount}| 出池数量{outTimerAllCount},其中new创建的数量{newTimerCount} 回收数量{releaseCount} ,处理前池数量{beforpoolcount},处理后池数量{_failedDeletions.Count}");
|
//UnityEngine.Debug.Log($"CheckReadyRelaseAfterRun 检查数量{checkcount}| 出池数量{outTimerAllCount},其中new创建的数量{newTimerCount} 回收数量{releaseCount} ,处理前池数量{beforpoolcount},处理后池数量{_timerPool.Count}");
|
||||||
outTimerAllCount = 0;
|
outTimerAllCount = 0;
|
||||||
newTimerCount = 0;
|
newTimerCount = 0;
|
||||||
_readyToRelease.Clear();
|
//_readyToRelease.Clear();
|
||||||
_tempCheck.Clear();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 引用计数字段(线程安全)
|
|
||||||
private int _refCount = 1; // 初始为1,表示创建时的引用
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 增加引用计数
|
/// 增加引用计数
|
||||||
/// </summary>
|
/// </summary>
|
||||||
void AddRef()
|
void AddRef()
|
||||||
{
|
{
|
||||||
int newCount = Interlocked.Increment(ref _refCount);
|
//int newCount = Interlocked.Increment(ref _refCount);
|
||||||
|
_refCount++;
|
||||||
////引用计数重新回到1时,移除。
|
|
||||||
////但是还是不在这里做把注释了,在每一帧开始之前统一检测
|
|
||||||
//if (newCount == 1)
|
|
||||||
//{
|
|
||||||
// UnityEngine.Debug.Log("CheckReadyRelaseAfterRun AddRef 复活");
|
|
||||||
// //if (_readyToRelease.Contains(this))
|
|
||||||
// //{
|
|
||||||
// // //UnityEngine.Debug.Log("移除ReadyToRelease");
|
|
||||||
// // _readyToRelease.Remove(this);
|
|
||||||
// //}
|
|
||||||
//}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -205,14 +192,14 @@ namespace MAME.Core
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
void ReleaseRef()
|
void ReleaseRef()
|
||||||
{
|
{
|
||||||
int newCount = Interlocked.Decrement(ref _refCount);
|
//int newCount = Interlocked.Decrement(ref _refCount);
|
||||||
if (newCount == 0)
|
_refCount--;
|
||||||
|
if (_refCount == 0)
|
||||||
{
|
{
|
||||||
//UnityEngine.Debug.Log("CheckReadyRelaseAfterRun ReleaseRef 预回收");
|
|
||||||
// 引用计数为0,释放资源并回池
|
// 引用计数为0,释放资源并回池
|
||||||
ReadyToRelease();
|
ReadyToRelease();
|
||||||
}
|
}
|
||||||
else if (newCount < 0)
|
else if (_refCount < 0)
|
||||||
{
|
{
|
||||||
// 引用计数异常,不应出现负数
|
// 引用计数异常,不应出现负数
|
||||||
throw new InvalidOperationException("引用计数出现负数");
|
throw new InvalidOperationException("引用计数出现负数");
|
||||||
@ -221,7 +208,9 @@ namespace MAME.Core
|
|||||||
|
|
||||||
void ReadyToRelease()
|
void ReadyToRelease()
|
||||||
{
|
{
|
||||||
|
if (this._inReadyQueue) return;
|
||||||
//UnityEngine.Debug.Log("ReadyToRelease");
|
//UnityEngine.Debug.Log("ReadyToRelease");
|
||||||
|
this._inReadyQueue = true;
|
||||||
_readyToRelease.Enqueue(this);
|
_readyToRelease.Enqueue(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -230,7 +219,7 @@ namespace MAME.Core
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
void ReturnToPool()
|
void ReturnToPool()
|
||||||
{
|
{
|
||||||
_failedDeletions.Enqueue(this);
|
_timerPool.Enqueue(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
#region 外部操作 间接影响引用计数
|
#region 外部操作 间接影响引用计数
|
||||||
@ -245,7 +234,6 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
if (refattr != null)
|
if (refattr != null)
|
||||||
refattr.ReleaseRef();
|
refattr.ReleaseRef();
|
||||||
|
|
||||||
refattr = emu_timer;
|
refattr = emu_timer;
|
||||||
refattr.AddRef();
|
refattr.AddRef();
|
||||||
}
|
}
|
||||||
@ -278,6 +266,11 @@ namespace MAME.Core
|
|||||||
list[i].ReleaseRef();
|
list[i].ReleaseRef();
|
||||||
list.Clear();
|
list.Clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
internal static void RemoveAtToList(ref List<emu_timer> list, int index)
|
||||||
|
{
|
||||||
|
list.RemoveAt(index);
|
||||||
|
}
|
||||||
#endregion
|
#endregion
|
||||||
/*
|
/*
|
||||||
static void EnqueueObj(emu_timer obj)
|
static void EnqueueObj(emu_timer obj)
|
||||||
@ -760,77 +753,340 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//static void timer_list_remove_and_insert(emu_timer timer)
|
||||||
|
//{
|
||||||
|
// // 包一层引用避免引用计数中间丢失
|
||||||
|
// {
|
||||||
|
// emu_timer tempref = null;
|
||||||
|
// emu_timer.SetRefUsed(ref tempref, ref timer);
|
||||||
|
|
||||||
|
// // 内联移除逻辑
|
||||||
|
// bool isSpecialAction = (timer.action == TIME_ACT.Cpuint_cpunum_empty_event_queue ||
|
||||||
|
// timer.action == TIME_ACT.setvector);
|
||||||
|
|
||||||
|
// if (isSpecialAction)
|
||||||
|
// {
|
||||||
|
// // 优化:批量移除相同action和过期时间的定时器
|
||||||
|
// for (int i = lt.Count - 1; i >= 0; i--)
|
||||||
|
// {
|
||||||
|
// emu_timer et = lt[i];
|
||||||
|
// if (et.action == timer.action &&
|
||||||
|
// Attotime.attotime_compare(et.expire, timer.expire) == 0)
|
||||||
|
// {
|
||||||
|
// lt.RemoveAt(i); // 直接从后往前移除,避免数组拷贝
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// // 优化:只移除第一个匹配的定时器
|
||||||
|
// int tempcount = lt.Count;
|
||||||
|
// for (int i = 0; i < tempcount; i++)
|
||||||
|
// {
|
||||||
|
// if (lt[i].action == timer.action)
|
||||||
|
// {
|
||||||
|
// lt.RemoveAt(i);
|
||||||
|
// break; // 找到第一个就退出
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// // 内联插入逻辑
|
||||||
|
// int insertIndex = lt.Count; // 默认插入到最后
|
||||||
|
|
||||||
|
// // 优化:只有当定时器启用时才按时间排序插入
|
||||||
|
// if (timer.enabled)
|
||||||
|
// {
|
||||||
|
// Atime expire = timer.expire;
|
||||||
|
|
||||||
|
|
||||||
|
// int tempcount = lt.Count;
|
||||||
|
// // 查找插入位置
|
||||||
|
// for (int i = 0; i < tempcount; i++)
|
||||||
|
// {
|
||||||
|
// if (Attotime.attotime_compare(lt[i].expire, expire) > 0)
|
||||||
|
// {
|
||||||
|
// insertIndex = i;
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// // 在找到的位置插入
|
||||||
|
// if (insertIndex < lt.Count)
|
||||||
|
// {
|
||||||
|
// lt.Insert(insertIndex, timer);
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// lt.Add(timer); // 添加到末尾,比Insert性能更好[8](@ref)
|
||||||
|
// }
|
||||||
|
|
||||||
|
// emu_timer.SetNull(ref tempref);
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
//static void timer_list_remove_and_insert(emu_timer timer)
|
||||||
|
//{
|
||||||
|
// {
|
||||||
|
// emu_timer tempref = null;
|
||||||
|
// emu_timer.SetRefUsed(ref tempref, ref timer);
|
||||||
|
|
||||||
|
// List<emu_timer> ltsrc = lt.GetSrcList();
|
||||||
|
// // inline remove
|
||||||
|
// if (timer.action == TIME_ACT.Cpuint_cpunum_empty_event_queue || timer.action == TIME_ACT.setvector)
|
||||||
|
// {
|
||||||
|
// int low = 0;
|
||||||
|
// int high = ltsrc.Count - 1;
|
||||||
|
// int start = -1;
|
||||||
|
// while (low <= high)
|
||||||
|
// {
|
||||||
|
// int mid = low + (high - low) / 2;
|
||||||
|
// int cmp = Attotime.attotime_compare(ltsrc[mid].expire, timer.expire);
|
||||||
|
// if (cmp < 0)
|
||||||
|
// low = mid + 1;
|
||||||
|
// else if (cmp > 0)
|
||||||
|
// high = mid - 1;
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// start = mid;
|
||||||
|
// high = mid - 1;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// if (start == -1) start = low;
|
||||||
|
// int end = start;
|
||||||
|
// int tempcount = ltsrc.Count;
|
||||||
|
// while (end < tempcount && Attotime.attotime_compare(ltsrc[end].expire, timer.expire) == 0)
|
||||||
|
// end++;
|
||||||
|
// for (int j = end - 1; j >= start; j--)
|
||||||
|
// {
|
||||||
|
// if (ltsrc[j].action == timer.action)
|
||||||
|
// lt.RemoveAt(j);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// int tempcount = lt.Count;
|
||||||
|
// for (int j = 0; j < tempcount; j++)
|
||||||
|
// {
|
||||||
|
// if (lt[j].action == timer.action)
|
||||||
|
// {
|
||||||
|
// lt.RemoveAt(j);
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// // inline insert
|
||||||
|
// int i1 = -1;
|
||||||
|
// if (timer.action == TIME_ACT.Cpuint_cpunum_empty_event_queue || timer.action == TIME_ACT.setvector)
|
||||||
|
// {
|
||||||
|
// int tempcount = ltsrc.Count;
|
||||||
|
// for (int j = 0; j < tempcount; j++)
|
||||||
|
// {
|
||||||
|
// emu_timer temptimer = ltsrc[j];
|
||||||
|
// if (temptimer.action == timer.action && Attotime.attotime_compare(temptimer.expire, global_basetime) <= 0)
|
||||||
|
// {
|
||||||
|
// i1 = j;
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// if (i1 == -1)
|
||||||
|
// {
|
||||||
|
// int low = 0;
|
||||||
|
// int high = ltsrc.Count - 1;
|
||||||
|
// int pos = ltsrc.Count;
|
||||||
|
// while (low <= high)
|
||||||
|
// {
|
||||||
|
// int mid = low + (high - low) / 2;
|
||||||
|
// if (Attotime.attotime_compare(ltsrc[mid].expire, timer.expire) > 0)
|
||||||
|
// {
|
||||||
|
// pos = mid;
|
||||||
|
// high = mid - 1;
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// low = mid + 1;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// lt.Insert(pos, timer);
|
||||||
|
// }
|
||||||
|
|
||||||
|
// emu_timer.SetNull(ref tempref);
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
//static void timer_list_insert(emu_timer timer1)
|
||||||
|
//{
|
||||||
|
// int i;
|
||||||
|
// int i1 = -1;
|
||||||
|
// if (timer1.action == TIME_ACT.Cpuint_cpunum_empty_event_queue || timer1.action == TIME_ACT.setvector)
|
||||||
|
// {
|
||||||
|
// //foreach (emu_timer et in lt)
|
||||||
|
// foreach (emu_timer et in lt.GetSrcList())
|
||||||
|
// {
|
||||||
|
// if (et.action == timer1.action && Attotime.attotime_compare(et.expire, global_basetime) <= 0)
|
||||||
|
// {
|
||||||
|
// i1 = lt.IndexOf(et);
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// if (i1 == -1)
|
||||||
|
// {
|
||||||
|
// Atime expire = timer1.enabled ? timer1.expire : Attotime.ATTOTIME_NEVER;
|
||||||
|
// for (i = 0; i < lt.Count; i++)
|
||||||
|
// {
|
||||||
|
// if (Attotime.attotime_compare(lt[i].expire, expire) > 0)
|
||||||
|
// {
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// lt.Insert(i, timer1);
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
//手动优化
|
||||||
static void timer_list_insert(emu_timer timer1)
|
static void timer_list_insert(emu_timer timer1)
|
||||||
{
|
{
|
||||||
int i;
|
TIME_ACT currAct = timer1.action;
|
||||||
int i1 = -1;
|
int i1 = -1;
|
||||||
if (timer1.action == TIME_ACT.Cpuint_cpunum_empty_event_queue || timer1.action == TIME_ACT.setvector)
|
var tlist = lt.GetSrcList();
|
||||||
|
int scanCount;
|
||||||
|
int tempMaxIdx = tlist.Count - 1;
|
||||||
|
if (currAct == TIME_ACT.Cpuint_cpunum_empty_event_queue || currAct == TIME_ACT.setvector)
|
||||||
{
|
{
|
||||||
//foreach (emu_timer et in lt)
|
//foreach (emu_timer et in lt)
|
||||||
foreach (emu_timer et in lt.GetSrcList())
|
//foreach (emu_timer et in lt.GetSrcList())
|
||||||
|
//{
|
||||||
|
// if (et.action == currAct && Attotime.attotime_compare(et.expire, global_basetime) <= 0)
|
||||||
|
// {
|
||||||
|
// i1 = lt.IndexOf(et);
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
scanCount = 0;
|
||||||
|
while (scanCount >= tempMaxIdx)
|
||||||
{
|
{
|
||||||
if (et.action == timer1.action && Attotime.attotime_compare(et.expire, global_basetime) <= 0)
|
emu_timer et = tlist[scanCount];
|
||||||
|
if (et.action == currAct && Attotime.attotime_compare(et.expire, global_basetime) <= 0)
|
||||||
{
|
{
|
||||||
i1 = lt.IndexOf(et);
|
i1 = scanCount;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
scanCount++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (i1 == -1)
|
if (i1 == -1)
|
||||||
{
|
{
|
||||||
Atime expire = timer1.enabled ? timer1.expire : Attotime.ATTOTIME_NEVER;
|
Atime expire = timer1.enabled ? timer1.expire : Attotime.ATTOTIME_NEVER;
|
||||||
for (i = 0; i < lt.Count; i++)
|
scanCount = 0;
|
||||||
|
while (scanCount <= tempMaxIdx)
|
||||||
{
|
{
|
||||||
if (Attotime.attotime_compare(lt[i].expire, expire) > 0)
|
emu_timer et = tlist[scanCount];
|
||||||
{
|
if (Attotime.attotime_compare(et.expire, expire) > 0)
|
||||||
break;
|
break;
|
||||||
}
|
scanCount++;
|
||||||
}
|
}
|
||||||
lt.Insert(i, timer1);
|
lt.Insert(scanCount, timer1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static List<emu_timer> timer_list_remove_lt1 = new List<emu_timer>();
|
static List<emu_timer> timer_list_remove_lt1 = new List<emu_timer>();
|
||||||
|
//public static void timer_list_remove(emu_timer timer1)
|
||||||
|
//{
|
||||||
|
// if (timer1.action == TIME_ACT.Cpuint_cpunum_empty_event_queue || timer1.action == TIME_ACT.setvector)
|
||||||
|
// {
|
||||||
|
// timer_list_remove_lt1.Clear();
|
||||||
|
// //foreach (emu_timer et in lt)
|
||||||
|
// foreach (emu_timer et in lt.GetSrcList())
|
||||||
|
// {
|
||||||
|
// if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) == 0)
|
||||||
|
// {
|
||||||
|
// timer_list_remove_lt1.Add(et);
|
||||||
|
// //lt.Remove(et);
|
||||||
|
// //break;
|
||||||
|
// }
|
||||||
|
// else if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) < 0)
|
||||||
|
// {
|
||||||
|
// int i1 = 1;
|
||||||
|
// }
|
||||||
|
// else if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) > 0)
|
||||||
|
// {
|
||||||
|
// int i1 = 1;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// foreach (emu_timer et1 in timer_list_remove_lt1)
|
||||||
|
// {
|
||||||
|
// lt.Remove(et1);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// //TODO MAME.NET原来这么foreach写删除是有问题的
|
||||||
|
|
||||||
|
// //foreach (emu_timer et in lt)
|
||||||
|
// foreach (emu_timer et in lt.GetSrcList())
|
||||||
|
// {
|
||||||
|
// if (et.action == timer1.action)
|
||||||
|
// {
|
||||||
|
// lt.Remove(et);
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
//修改优化
|
||||||
public static void timer_list_remove(emu_timer timer1)
|
public static void timer_list_remove(emu_timer timer1)
|
||||||
{
|
{
|
||||||
if (timer1.action == TIME_ACT.Cpuint_cpunum_empty_event_queue || timer1.action == TIME_ACT.setvector)
|
if (timer1.action == TIME_ACT.Cpuint_cpunum_empty_event_queue || timer1.action == TIME_ACT.setvector)
|
||||||
{
|
{
|
||||||
timer_list_remove_lt1.Clear();
|
//timer_list_remove_lt1.Clear();
|
||||||
//foreach (emu_timer et in lt)
|
//foreach (emu_timer et in lt.GetSrcList())
|
||||||
foreach (emu_timer et in lt.GetSrcList())
|
//{
|
||||||
|
// if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) == 0)
|
||||||
|
// timer_list_remove_lt1.Add(et);
|
||||||
|
//}
|
||||||
|
//foreach (emu_timer et1 in timer_list_remove_lt1)
|
||||||
|
// lt.Remove(et1);
|
||||||
|
|
||||||
|
var tlist = lt.GetSrcList();
|
||||||
|
int tempMaxIdx = tlist.Count - 1;
|
||||||
|
while (tempMaxIdx >= 0)
|
||||||
{
|
{
|
||||||
|
emu_timer et = tlist[tempMaxIdx];
|
||||||
if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) == 0)
|
if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) == 0)
|
||||||
{
|
lt.Remove(et);
|
||||||
timer_list_remove_lt1.Add(et);
|
tempMaxIdx--;
|
||||||
//lt.Remove(et);
|
|
||||||
//break;
|
|
||||||
}
|
|
||||||
else if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) < 0)
|
|
||||||
{
|
|
||||||
int i1 = 1;
|
|
||||||
}
|
|
||||||
else if (et.action == timer1.action && Attotime.attotime_compare(et.expire, timer1.expire) > 0)
|
|
||||||
{
|
|
||||||
int i1 = 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
foreach (emu_timer et1 in timer_list_remove_lt1)
|
|
||||||
{
|
|
||||||
lt.Remove(et1);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
//TODO MAME.NET原来这么foreach写删除是有问题的
|
//TODO MAME.NET原来这么foreach写删除是有问题的
|
||||||
|
|
||||||
//foreach (emu_timer et in lt)
|
//foreach (emu_timer et in lt)
|
||||||
foreach (emu_timer et in lt.GetSrcList())
|
//foreach (emu_timer et in lt.GetSrcList())
|
||||||
|
//{
|
||||||
|
// if (et.action == timer1.action)
|
||||||
|
// {
|
||||||
|
// lt.Remove(et);
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
var tlist = lt.GetSrcList();
|
||||||
|
int tempMaxIdx = tlist.Count - 1;
|
||||||
|
int scanCount = 0;
|
||||||
|
while (scanCount <= tempMaxIdx)
|
||||||
{
|
{
|
||||||
|
emu_timer et = tlist[scanCount];
|
||||||
if (et.action == timer1.action)
|
if (et.action == timer1.action)
|
||||||
{
|
{
|
||||||
lt.Remove(et);
|
lt.Remove(et);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
scanCount++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -544,18 +544,18 @@
|
|||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
readonly static int[] K051960_sprites_draw_xoffset = new int[] { 0, 1, 4, 5, 16, 17, 20, 21 };
|
||||||
|
readonly static int[] K051960_sprites_draw_yoffset = new int[] { 0, 2, 8, 10, 32, 34, 40, 42 };
|
||||||
|
readonly static int[] K051960_sprites_draw_width = new int[] { 1, 2, 1, 2, 4, 2, 4, 8 };
|
||||||
|
readonly static int[] K051960_sprites_draw_height = new int[] { 1, 1, 2, 2, 2, 4, 4, 8 };
|
||||||
|
static int[] K051960_sprites_draw_sortedlist = new int[128];
|
||||||
public static void K051960_sprites_draw(RECT cliprect, int min_priority, int max_priority)
|
public static void K051960_sprites_draw(RECT cliprect, int min_priority, int max_priority)
|
||||||
{
|
{
|
||||||
int ox, oy, code, color, pri, shadow, size, w, h, x, y, flipx, flipy, zoomx, zoomy, code2, color2, pri2;
|
int ox, oy, code, color, pri, shadow, size, w, h, x, y, flipx, flipy, zoomx, zoomy, code2, color2, pri2;
|
||||||
int offs, pri_code;
|
int offs, pri_code;
|
||||||
int[] sortedlist = new int[128];
|
|
||||||
int[] xoffset = new int[] { 0, 1, 4, 5, 16, 17, 20, 21 };
|
|
||||||
int[] yoffset = new int[] { 0, 2, 8, 10, 32, 34, 40, 42 };
|
|
||||||
int[] width = new int[] { 1, 2, 1, 2, 4, 2, 4, 8 };
|
|
||||||
int[] height = new int[] { 1, 1, 2, 2, 2, 4, 4, 8 };
|
|
||||||
for (offs = 0; offs < 128; offs++)
|
for (offs = 0; offs < 128; offs++)
|
||||||
{
|
{
|
||||||
sortedlist[offs] = -1;
|
K051960_sprites_draw_sortedlist[offs] = -1;
|
||||||
}
|
}
|
||||||
for (offs = 0; offs < 0x400; offs += 8)
|
for (offs = 0; offs < 0x400; offs += 8)
|
||||||
{
|
{
|
||||||
@ -563,17 +563,17 @@
|
|||||||
{
|
{
|
||||||
if (max_priority == -1)
|
if (max_priority == -1)
|
||||||
{
|
{
|
||||||
sortedlist[(K051960_ram[offs] & 0x7f) ^ 0x7f] = offs;
|
K051960_sprites_draw_sortedlist[(K051960_ram[offs] & 0x7f) ^ 0x7f] = offs;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
sortedlist[K051960_ram[offs] & 0x7f] = offs;
|
K051960_sprites_draw_sortedlist[K051960_ram[offs] & 0x7f] = offs;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (pri_code = 0; pri_code < 128; pri_code++)
|
for (pri_code = 0; pri_code < 128; pri_code++)
|
||||||
{
|
{
|
||||||
offs = sortedlist[pri_code];
|
offs = K051960_sprites_draw_sortedlist[pri_code];
|
||||||
if (offs == -1)
|
if (offs == -1)
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
@ -594,8 +594,8 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
size = (K051960_ram[offs + 1] & 0xe0) >> 5;
|
size = (K051960_ram[offs + 1] & 0xe0) >> 5;
|
||||||
w = width[size];
|
w = K051960_sprites_draw_width[size];
|
||||||
h = height[size];
|
h = K051960_sprites_draw_height[size];
|
||||||
if (w >= 2) code &= ~0x01;
|
if (w >= 2) code &= ~0x01;
|
||||||
if (h >= 2) code &= ~0x02;
|
if (h >= 2) code &= ~0x02;
|
||||||
if (w >= 4) code &= ~0x04;
|
if (w >= 4) code &= ~0x04;
|
||||||
@ -631,19 +631,19 @@
|
|||||||
sx = ox + 16 * x;
|
sx = ox + 16 * x;
|
||||||
if (flipx != 0)
|
if (flipx != 0)
|
||||||
{
|
{
|
||||||
c += xoffset[(w - 1 - x)];
|
c += K051960_sprites_draw_xoffset[(w - 1 - x)];
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
c += xoffset[x];
|
c += K051960_sprites_draw_xoffset[x];
|
||||||
}
|
}
|
||||||
if (flipy != 0)
|
if (flipy != 0)
|
||||||
{
|
{
|
||||||
c += yoffset[(h - 1 - y)];
|
c += K051960_sprites_draw_yoffset[(h - 1 - y)];
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
c += yoffset[y];
|
c += K051960_sprites_draw_yoffset[y];
|
||||||
}
|
}
|
||||||
if (max_priority == -1)
|
if (max_priority == -1)
|
||||||
{
|
{
|
||||||
@ -682,16 +682,16 @@
|
|||||||
zw = (ox + ((zoomx * (x + 1) + (1 << 11)) >> 12)) - sx;
|
zw = (ox + ((zoomx * (x + 1) + (1 << 11)) >> 12)) - sx;
|
||||||
if (flipx != 0)
|
if (flipx != 0)
|
||||||
{
|
{
|
||||||
c += xoffset[(w - 1 - x)];
|
c += K051960_sprites_draw_xoffset[(w - 1 - x)];
|
||||||
}
|
}
|
||||||
else c += xoffset[x];
|
else c += K051960_sprites_draw_xoffset[x];
|
||||||
if (flipy != 0)
|
if (flipy != 0)
|
||||||
{
|
{
|
||||||
c += yoffset[(h - 1 - y)];
|
c += K051960_sprites_draw_yoffset[(h - 1 - y)];
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
c += yoffset[y];
|
c += K051960_sprites_draw_yoffset[y];
|
||||||
}
|
}
|
||||||
if (max_priority == -1)
|
if (max_priority == -1)
|
||||||
{
|
{
|
||||||
|
|||||||
@ -153,7 +153,7 @@ namespace MAME.Core
|
|||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
|
||||||
public static byte[] airduelm72_code = new byte[] {
|
public readonly static byte[] airduelm72_code = new byte[] {
|
||||||
0x68, 0x00, 0xd0, 0x1f, 0xc6, 0x06, 0xc0, 0x1c, 0x57, 0xea, 0x69, 0x0b, 0x00, 0x00,0x00,0x00,
|
0x68, 0x00, 0xd0, 0x1f, 0xc6, 0x06, 0xc0, 0x1c, 0x57, 0xea, 0x69, 0x0b, 0x00, 0x00,0x00,0x00,
|
||||||
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
||||||
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
||||||
@ -161,7 +161,7 @@ namespace MAME.Core
|
|||||||
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
|
||||||
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
|
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
|
||||||
};
|
};
|
||||||
public static byte[] gunforce_decryption_table = new byte[256] {
|
public readonly static byte[] gunforce_decryption_table = new byte[256] {
|
||||||
0xff,0x90,0x90,0x2c,0x90,0x90,0x43,0x88, 0x90,0x13,0x0a,0xbd,0xba,0x60,0xea,0x90, /* 00 */
|
0xff,0x90,0x90,0x2c,0x90,0x90,0x43,0x88, 0x90,0x13,0x0a,0xbd,0xba,0x60,0xea,0x90, /* 00 */
|
||||||
0x90,0x90,0xf2,0x29,0xb3,0x22,0x90,0x0c, 0xa9,0x5f,0x9d,0x07,0x90,0x90,0x0b,0xbb, /* 10 */
|
0x90,0x90,0xf2,0x29,0xb3,0x22,0x90,0x0c, 0xa9,0x5f,0x9d,0x07,0x90,0x90,0x0b,0xbb, /* 10 */
|
||||||
0x8a,0x90,0x90,0x90,0x3a,0x3c,0x5a,0x38, 0x99,0x90,0xf8,0x89,0x90,0x91,0x90,0x55, /* 20 */
|
0x8a,0x90,0x90,0x90,0x3a,0x3c,0x5a,0x38, 0x99,0x90,0xf8,0x89,0x90,0x91,0x90,0x55, /* 20 */
|
||||||
|
|||||||
@ -1,66 +1,107 @@
|
|||||||
namespace MAME.Core
|
using System.Runtime.CompilerServices;
|
||||||
|
|
||||||
|
namespace MAME.Core
|
||||||
{
|
{
|
||||||
public unsafe partial class Drawgfx
|
public unsafe partial class Drawgfx
|
||||||
{
|
{
|
||||||
public static void common_drawgfx_m92(byte* bb1, int code, int color, int flipx, int flipy, int sx, int sy, RECT clip, uint primask)
|
//public static void common_drawgfx_m92(byte* bb1, int code, int color, int flipx, int flipy, int sx, int sy, RECT clip, uint primask)
|
||||||
|
//{
|
||||||
|
// int ox;
|
||||||
|
// int oy;
|
||||||
|
// int ex;
|
||||||
|
// int ey;
|
||||||
|
// ox = sx;
|
||||||
|
// oy = sy;
|
||||||
|
// ex = sx + 0x10 - 1;
|
||||||
|
// if (sx < 0)
|
||||||
|
// {
|
||||||
|
// sx = 0;
|
||||||
|
// }
|
||||||
|
// if (sx < clip.min_x)
|
||||||
|
// {
|
||||||
|
// sx = clip.min_x;
|
||||||
|
// }
|
||||||
|
// if (ex >= 0x200)
|
||||||
|
// {
|
||||||
|
// ex = 0x200 - 1;
|
||||||
|
// }
|
||||||
|
// if (ex > clip.max_x)
|
||||||
|
// {
|
||||||
|
// ex = clip.max_x;
|
||||||
|
// }
|
||||||
|
// if (sx > ex)
|
||||||
|
// {
|
||||||
|
// return;
|
||||||
|
// }
|
||||||
|
// ey = sy + 0x10 - 1;
|
||||||
|
// if (sy < 0)
|
||||||
|
// {
|
||||||
|
// sy = 0;
|
||||||
|
// }
|
||||||
|
// if (sy < clip.min_y)
|
||||||
|
// {
|
||||||
|
// sy = clip.min_y;
|
||||||
|
// }
|
||||||
|
// if (ey >= 0x100)
|
||||||
|
// {
|
||||||
|
// ey = 0x100 - 1;
|
||||||
|
// }
|
||||||
|
// if (ey > clip.max_y)
|
||||||
|
// {
|
||||||
|
// ey = clip.max_y;
|
||||||
|
// }
|
||||||
|
// if (sy > ey)
|
||||||
|
// {
|
||||||
|
// return;
|
||||||
|
// }
|
||||||
|
// int sw = 0x10;
|
||||||
|
// int sh = 0x10;
|
||||||
|
// int ls = sx - ox;
|
||||||
|
// int ts = sy - oy;
|
||||||
|
// int dw = ex - sx + 1;
|
||||||
|
// int dh = ey - sy + 1;
|
||||||
|
// int colorbase = 0x10 * color;
|
||||||
|
// blockmove_8toN_transpen_pri16_m92(bb1, code, sw, sh, 0x10, ls, ts, flipx, flipy, dw, dh, colorbase, sy, sx, primask);
|
||||||
|
//}
|
||||||
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
|
public static unsafe void common_drawgfx_m92(byte* bb1, int code, int color, int flipx, int flipy, int sx, int sy, RECT clip, uint primask)
|
||||||
{
|
{
|
||||||
int ox;
|
// 使用常量折叠和预计算[5](@ref)
|
||||||
int oy;
|
const int TEMP1 = 0x10 - 1; // 15
|
||||||
int ex;
|
const int TEMP3 = 0x100 - 1; // 255
|
||||||
int ey;
|
const int TEMP4 = 0x200 - 1; // 511
|
||||||
ox = sx;
|
|
||||||
oy = sy;
|
int ox = sx;
|
||||||
ex = sx + 0x10 - 1;
|
int oy = sy;
|
||||||
if (sx < 0)
|
int ex = sx + TEMP1;
|
||||||
{
|
|
||||||
sx = 0;
|
// 边界检查优化:减少分支预测错误[5](@ref)
|
||||||
}
|
sx = sx < 0 ? 0 : sx;
|
||||||
if (sx < clip.min_x)
|
sx = sx < clip.min_x ? clip.min_x : sx;
|
||||||
{
|
ex = ex >= 0x200 ? TEMP4 : ex;
|
||||||
sx = clip.min_x;
|
ex = ex > clip.max_x ? clip.max_x : ex;
|
||||||
}
|
|
||||||
if (ex >= 0x200)
|
if (sx > ex) return;
|
||||||
{
|
|
||||||
ex = 0x200 - 1;
|
int ey = sy + TEMP1;
|
||||||
}
|
sy = sy < 0 ? 0 : sy;
|
||||||
if (ex > clip.max_x)
|
sy = sy < clip.min_y ? clip.min_y : sy;
|
||||||
{
|
ey = ey >= 0x100 ? TEMP3 : ey;
|
||||||
ex = clip.max_x;
|
ey = ey > clip.max_y ? clip.max_y : ey;
|
||||||
}
|
|
||||||
if (sx > ex)
|
if (sy > ey) return;
|
||||||
{
|
|
||||||
return;
|
// 使用局部变量避免重复计算[2,4](@ref)
|
||||||
}
|
|
||||||
ey = sy + 0x10 - 1;
|
|
||||||
if (sy < 0)
|
|
||||||
{
|
|
||||||
sy = 0;
|
|
||||||
}
|
|
||||||
if (sy < clip.min_y)
|
|
||||||
{
|
|
||||||
sy = clip.min_y;
|
|
||||||
}
|
|
||||||
if (ey >= 0x100)
|
|
||||||
{
|
|
||||||
ey = 0x100 - 1;
|
|
||||||
}
|
|
||||||
if (ey > clip.max_y)
|
|
||||||
{
|
|
||||||
ey = clip.max_y;
|
|
||||||
}
|
|
||||||
if (sy > ey)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
int sw = 0x10;
|
|
||||||
int sh = 0x10;
|
|
||||||
int ls = sx - ox;
|
int ls = sx - ox;
|
||||||
int ts = sy - oy;
|
int ts = sy - oy;
|
||||||
int dw = ex - sx + 1;
|
int dw = ex - sx + 1;
|
||||||
int dh = ey - sy + 1;
|
int dh = ey - sy + 1;
|
||||||
int colorbase = 0x10 * color;
|
int colorbase = color << 4; // 用移位代替乘法 0x10 * color
|
||||||
blockmove_8toN_transpen_pri16_m92(bb1, code, sw, sh, 0x10, ls, ts, flipx, flipy, dw, dh, colorbase, sy, sx, primask);
|
|
||||||
|
// 内联关键函数调用
|
||||||
|
blockmove_8toN_transpen_pri16_m92(bb1, code, 0x10, 0x10, 0x10, ls, ts, flipx, flipy, dw, dh, colorbase, sy, sx, primask);
|
||||||
}
|
}
|
||||||
|
|
||||||
public unsafe static void blockmove_8toN_transpen_pri16_m92(byte* bb1, int code, int srcwidth, int srcheight, int srcmodulo, int leftskip, int topskip, int flipx, int flipy, int dstwidth, int dstheight, int colorbase, int sy, int sx, uint primask)
|
public unsafe static void blockmove_8toN_transpen_pri16_m92(byte* bb1, int code, int srcwidth, int srcheight, int srcmodulo, int leftskip, int topskip, int flipx, int flipy, int dstwidth, int dstheight, int colorbase, int sy, int sx, uint primask)
|
||||||
{
|
{
|
||||||
int ydir, xdir, col, i, j;
|
int ydir, xdir, col, i, j;
|
||||||
|
|||||||
@ -125,6 +125,7 @@ namespace MAME.Core
|
|||||||
namcos1_playfield_control[offset & 0x1f] = data;
|
namcos1_playfield_control[offset & 0x1f] = data;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
readonly static int[] draw_sprites_sprite_size = new int[] { 16, 8, 32, 4 };
|
||||||
public static void draw_sprites(int iBitmap, RECT cliprect)
|
public static void draw_sprites(int iBitmap, RECT cliprect)
|
||||||
{
|
{
|
||||||
int source_offset;
|
int source_offset;
|
||||||
@ -132,14 +133,13 @@ namespace MAME.Core
|
|||||||
int sprite_yoffs = namcos1_spriteram[0x800 + 0x07f7];
|
int sprite_yoffs = namcos1_spriteram[0x800 + 0x07f7];
|
||||||
for (source_offset = 0xfe0; source_offset >= 0x800; source_offset -= 0x10)
|
for (source_offset = 0xfe0; source_offset >= 0x800; source_offset -= 0x10)
|
||||||
{
|
{
|
||||||
int[] sprite_size = new int[] { 16, 8, 32, 4 };
|
|
||||||
int attr1 = namcos1_spriteram[source_offset + 10];
|
int attr1 = namcos1_spriteram[source_offset + 10];
|
||||||
int attr2 = namcos1_spriteram[source_offset + 14];
|
int attr2 = namcos1_spriteram[source_offset + 14];
|
||||||
int color = namcos1_spriteram[source_offset + 12];
|
int color = namcos1_spriteram[source_offset + 12];
|
||||||
int flipx = (attr1 & 0x20) >> 5;
|
int flipx = (attr1 & 0x20) >> 5;
|
||||||
int flipy = (attr2 & 0x01);
|
int flipy = (attr2 & 0x01);
|
||||||
int sizex = sprite_size[(attr1 & 0xc0) >> 6];
|
int sizex = draw_sprites_sprite_size[(attr1 & 0xc0) >> 6];
|
||||||
int sizey = sprite_size[(attr2 & 0x06) >> 1];
|
int sizey = draw_sprites_sprite_size[(attr2 & 0x06) >> 1];
|
||||||
int tx = (attr1 & 0x18) & (~(sizex - 1));
|
int tx = (attr1 & 0x18) & (~(sizex - 1));
|
||||||
int ty = (attr2 & 0x18) & (~(sizey - 1));
|
int ty = (attr2 & 0x18) & (~(sizey - 1));
|
||||||
int sx = namcos1_spriteram[source_offset + 13] + ((color & 0x01) << 8);
|
int sx = namcos1_spriteram[source_offset + 13] + ((color & 0x01) << 8);
|
||||||
@ -163,6 +163,7 @@ namespace MAME.Core
|
|||||||
Drawgfx.common_drawgfx_na(sizex, sizey, tx, ty, sprite, color, flipx, flipy, sx & 0x1ff, ((sy + 16) & 0xff) - 16, cliprect);
|
Drawgfx.common_drawgfx_na(sizex, sizey, tx, ty, sprite, color, flipx, flipy, sx & 0x1ff, ((sy + 16) & 0xff) - 16, cliprect);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
readonly static int[] video_update_namcos1_disp_x = new int[] { 25, 27, 28, 29 };
|
||||||
public static void video_update_namcos1()
|
public static void video_update_namcos1()
|
||||||
{
|
{
|
||||||
int i, j, scrollx, scrolly;
|
int i, j, scrollx, scrolly;
|
||||||
@ -195,9 +196,8 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
for (i = 0; i < 4; i++)
|
for (i = 0; i < 4; i++)
|
||||||
{
|
{
|
||||||
int[] disp_x = new int[] { 25, 27, 28, 29 };
|
|
||||||
j = i << 2;
|
j = i << 2;
|
||||||
scrollx = (namcos1_playfield_control[j + 1] + (namcos1_playfield_control[j + 0] << 8)) - disp_x[i];
|
scrollx = (namcos1_playfield_control[j + 1] + (namcos1_playfield_control[j + 0] << 8)) - video_update_namcos1_disp_x[i];
|
||||||
scrolly = (namcos1_playfield_control[j + 3] + (namcos1_playfield_control[j + 2] << 8)) + 8;
|
scrolly = (namcos1_playfield_control[j + 3] + (namcos1_playfield_control[j + 2] << 8)) + 8;
|
||||||
if (Video.flip_screen_get())
|
if (Video.flip_screen_get())
|
||||||
{
|
{
|
||||||
|
|||||||
@ -416,17 +416,94 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
//public static void MWriteByte(int address, sbyte value)
|
||||||
|
//{
|
||||||
|
// address &= 0xffffff;
|
||||||
|
// if (address >= 0x100000 && address <= 0x1fffff)
|
||||||
|
// {
|
||||||
|
// if (address == 0x100d0b && value == 0x06)//&&MC68000.m1.TotalExecutedCycles>0x3F6FC8C)
|
||||||
|
// {
|
||||||
|
// ulong l1 = MC68000.m1.TotalExecutedCycles;
|
||||||
|
// int i2 = 1;
|
||||||
|
// //m68000Form.iStatus = 1;
|
||||||
|
// }
|
||||||
|
// Memory.mainram[address & 0xffff] = (byte)value;
|
||||||
|
// }
|
||||||
|
// else if (address >= 0x2ffff0 && address <= 0x2fffff)
|
||||||
|
// {
|
||||||
|
// main_cpu_bank_select_w(value);
|
||||||
|
// }
|
||||||
|
// else if (address >= 0x300000 && address <= 0x31ffff)
|
||||||
|
// {
|
||||||
|
// if ((address & 0x01) == 0)
|
||||||
|
// {
|
||||||
|
// int i1 = 1;
|
||||||
|
// }
|
||||||
|
// else if ((address & 0x01) == 1)
|
||||||
|
// {
|
||||||
|
// watchdog_w();
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else if (address >= 0x320000 && address <= 0x33ffff)
|
||||||
|
// {
|
||||||
|
// if ((address & 0x01) == 0)
|
||||||
|
// {
|
||||||
|
// audio_command_w((byte)value);
|
||||||
|
// }
|
||||||
|
// else if ((address & 0x01) == 1)
|
||||||
|
// {
|
||||||
|
// int i1 = 1;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else if (address >= 0x380000 && address <= 0x39ffff)
|
||||||
|
// {
|
||||||
|
// io_control_w((address & 0x7f) >> 1, (byte)value);
|
||||||
|
// }
|
||||||
|
// else if (address >= 0x3a0000 && address <= 0x3bffff)
|
||||||
|
// {
|
||||||
|
// if ((address & 0x01) == 1)
|
||||||
|
// {
|
||||||
|
// system_control_w((address & 0x1f) >> 1);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else if (address >= 0x3c0000 && address <= 0x3dffff)
|
||||||
|
// {
|
||||||
|
// if ((address & 0x01) == 0)
|
||||||
|
// {
|
||||||
|
// neogeo_video_register_w((address & 0x0f) >> 1, (ushort)((value << 8) | (byte)value));
|
||||||
|
// }
|
||||||
|
// else if ((address & 0x01) == 1)
|
||||||
|
// {
|
||||||
|
// int i1 = 1;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else if (address >= 0x400000 && address <= 0x7fffff)
|
||||||
|
// {
|
||||||
|
// int i1 = 1;
|
||||||
|
// //neogeo_paletteram_w((address - 0x400000) >> 1, data, mem_mask);
|
||||||
|
// }
|
||||||
|
// else if (address >= 0xd00000 && address <= 0xdfffff)
|
||||||
|
// {
|
||||||
|
// save_ram_w(address & 0xffff, (byte)value);
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// int i1 = 1;
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
//手动优化
|
||||||
public static void MWriteByte(int address, sbyte value)
|
public static void MWriteByte(int address, sbyte value)
|
||||||
{
|
{
|
||||||
address &= 0xffffff;
|
address &= 0xffffff;
|
||||||
if (address >= 0x100000 && address <= 0x1fffff)
|
if (address >= 0x100000 && address <= 0x1fffff)
|
||||||
{
|
{
|
||||||
if (address == 0x100d0b && value == 0x06)//&&MC68000.m1.TotalExecutedCycles>0x3F6FC8C)
|
//if (address == 0x100d0b && value == 0x06)//&&MC68000.m1.TotalExecutedCycles>0x3F6FC8C)
|
||||||
{
|
//{
|
||||||
ulong l1 = MC68000.m1.TotalExecutedCycles;
|
// ulong l1 = MC68000.m1.TotalExecutedCycles;
|
||||||
int i2 = 1;
|
// int i2 = 1;
|
||||||
//m68000Form.iStatus = 1;
|
// //m68000Form.iStatus = 1;
|
||||||
}
|
//}
|
||||||
Memory.mainram[address & 0xffff] = (byte)value;
|
Memory.mainram[address & 0xffff] = (byte)value;
|
||||||
}
|
}
|
||||||
else if (address >= 0x2ffff0 && address <= 0x2fffff)
|
else if (address >= 0x2ffff0 && address <= 0x2fffff)
|
||||||
@ -435,13 +512,15 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
else if (address >= 0x300000 && address <= 0x31ffff)
|
else if (address >= 0x300000 && address <= 0x31ffff)
|
||||||
{
|
{
|
||||||
if ((address & 0x01) == 0)
|
/*if ((address & 0x01) == 0)
|
||||||
{
|
{
|
||||||
int i1 = 1;
|
int i1 = 1;
|
||||||
}
|
}
|
||||||
else if ((address & 0x01) == 1)
|
else */if ((address & 0x01) == 1)
|
||||||
{
|
{
|
||||||
watchdog_w();
|
//watchdog_w();
|
||||||
|
//减少一次堆栈 无意义套娃
|
||||||
|
Watchdog.watchdog_reset();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (address >= 0x320000 && address <= 0x33ffff)
|
else if (address >= 0x320000 && address <= 0x33ffff)
|
||||||
@ -450,10 +529,11 @@ namespace MAME.Core
|
|||||||
{
|
{
|
||||||
audio_command_w((byte)value);
|
audio_command_w((byte)value);
|
||||||
}
|
}
|
||||||
else if ((address & 0x01) == 1)
|
//无意义
|
||||||
{
|
//else if ((address & 0x01) == 1)
|
||||||
int i1 = 1;
|
//{
|
||||||
}
|
// int i1 = 1;
|
||||||
|
//}
|
||||||
}
|
}
|
||||||
else if (address >= 0x380000 && address <= 0x39ffff)
|
else if (address >= 0x380000 && address <= 0x39ffff)
|
||||||
{
|
{
|
||||||
@ -472,24 +552,28 @@ namespace MAME.Core
|
|||||||
{
|
{
|
||||||
neogeo_video_register_w((address & 0x0f) >> 1, (ushort)((value << 8) | (byte)value));
|
neogeo_video_register_w((address & 0x0f) >> 1, (ushort)((value << 8) | (byte)value));
|
||||||
}
|
}
|
||||||
else if ((address & 0x01) == 1)
|
//无意义
|
||||||
{
|
//else if ((address & 0x01) == 1)
|
||||||
int i1 = 1;
|
//{
|
||||||
}
|
// int i1 = 1;
|
||||||
}
|
//}
|
||||||
else if (address >= 0x400000 && address <= 0x7fffff)
|
|
||||||
{
|
|
||||||
int i1 = 1;
|
|
||||||
//neogeo_paletteram_w((address - 0x400000) >> 1, data, mem_mask);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//无意义
|
||||||
|
//else if (address >= 0x400000 && address <= 0x7fffff)
|
||||||
|
//{
|
||||||
|
// int i1 = 1;
|
||||||
|
// //neogeo_paletteram_w((address - 0x400000) >> 1, data, mem_mask);
|
||||||
|
//}
|
||||||
else if (address >= 0xd00000 && address <= 0xdfffff)
|
else if (address >= 0xd00000 && address <= 0xdfffff)
|
||||||
{
|
{
|
||||||
save_ram_w(address & 0xffff, (byte)value);
|
save_ram_w(address & 0xffff, (byte)value);
|
||||||
}
|
}
|
||||||
else
|
//无意义
|
||||||
{
|
//else
|
||||||
int i1 = 1;
|
//{
|
||||||
}
|
// int i1 = 1;
|
||||||
|
//}
|
||||||
}
|
}
|
||||||
public static void MWriteWord(int address, short value)
|
public static void MWriteWord(int address, short value)
|
||||||
{
|
{
|
||||||
|
|||||||
@ -96,10 +96,7 @@ namespace MAME.Core
|
|||||||
neogeo_rng = (ushort)((neogeo_rng << 1) | newbit);
|
neogeo_rng = (ushort)((neogeo_rng << 1) | newbit);
|
||||||
return old;
|
return old;
|
||||||
}
|
}
|
||||||
public static void kof99_bankswitch_w(int data)
|
readonly static int[] kof99_bankswitch_w_bankoffset = new int[]
|
||||||
{
|
|
||||||
int bankaddress;
|
|
||||||
int[] bankoffset = new int[]
|
|
||||||
{
|
{
|
||||||
0x000000, 0x100000, 0x200000, 0x300000,
|
0x000000, 0x100000, 0x200000, 0x300000,
|
||||||
0x3cc000, 0x4cc000, 0x3f2000, 0x4f2000,
|
0x3cc000, 0x4cc000, 0x3f2000, 0x4f2000,
|
||||||
@ -111,6 +108,10 @@ namespace MAME.Core
|
|||||||
0x588800, 0x581800, 0x599800, 0x594800,
|
0x588800, 0x581800, 0x599800, 0x594800,
|
||||||
0x598000
|
0x598000
|
||||||
};
|
};
|
||||||
|
public static void kof99_bankswitch_w(int data)
|
||||||
|
{
|
||||||
|
int bankaddress;
|
||||||
|
|
||||||
data =
|
data =
|
||||||
(((data >> 14) & 1) << 0) +
|
(((data >> 14) & 1) << 0) +
|
||||||
(((data >> 6) & 1) << 1) +
|
(((data >> 6) & 1) << 1) +
|
||||||
@ -118,13 +119,10 @@ namespace MAME.Core
|
|||||||
(((data >> 10) & 1) << 3) +
|
(((data >> 10) & 1) << 3) +
|
||||||
(((data >> 12) & 1) << 4) +
|
(((data >> 12) & 1) << 4) +
|
||||||
(((data >> 5) & 1) << 5);
|
(((data >> 5) & 1) << 5);
|
||||||
bankaddress = 0x100000 + bankoffset[data];
|
bankaddress = 0x100000 + kof99_bankswitch_w_bankoffset[data];
|
||||||
main_cpu_bank_address = bankaddress;
|
main_cpu_bank_address = bankaddress;
|
||||||
}
|
}
|
||||||
public static void garou_bankswitch_w(int data)
|
readonly static int[] garou_bankswitch_w_bankoffset = new int[]
|
||||||
{
|
|
||||||
int bankaddress;
|
|
||||||
int[] bankoffset = new int[]
|
|
||||||
{
|
{
|
||||||
0x000000, 0x100000, 0x200000, 0x300000, // 00
|
0x000000, 0x100000, 0x200000, 0x300000, // 00
|
||||||
0x280000, 0x380000, 0x2d0000, 0x3d0000, // 04
|
0x280000, 0x380000, 0x2d0000, 0x3d0000, // 04
|
||||||
@ -141,6 +139,10 @@ namespace MAME.Core
|
|||||||
0x5d0000, 0x5d8000, 0x5e0000, 0x5e8000, // 48
|
0x5d0000, 0x5d8000, 0x5e0000, 0x5e8000, // 48
|
||||||
0x5f0000, 0x5f8000, 0x600000
|
0x5f0000, 0x5f8000, 0x600000
|
||||||
};
|
};
|
||||||
|
public static void garou_bankswitch_w(int data)
|
||||||
|
{
|
||||||
|
int bankaddress;
|
||||||
|
|
||||||
data =
|
data =
|
||||||
(((data >> 5) & 1) << 0) +
|
(((data >> 5) & 1) << 0) +
|
||||||
(((data >> 9) & 1) << 1) +
|
(((data >> 9) & 1) << 1) +
|
||||||
@ -148,13 +150,10 @@ namespace MAME.Core
|
|||||||
(((data >> 6) & 1) << 3) +
|
(((data >> 6) & 1) << 3) +
|
||||||
(((data >> 14) & 1) << 4) +
|
(((data >> 14) & 1) << 4) +
|
||||||
(((data >> 12) & 1) << 5);
|
(((data >> 12) & 1) << 5);
|
||||||
bankaddress = 0x100000 + bankoffset[data];
|
bankaddress = 0x100000 + garou_bankswitch_w_bankoffset[data];
|
||||||
main_cpu_bank_address = bankaddress;
|
main_cpu_bank_address = bankaddress;
|
||||||
}
|
}
|
||||||
public static void garouh_bankswitch_w(int data)
|
readonly static int[] garouh_bankswitch_w_bankoffset = new int[]
|
||||||
{
|
|
||||||
int bankaddress;
|
|
||||||
int[] bankoffset = new int[]
|
|
||||||
{
|
{
|
||||||
0x000000, 0x100000, 0x200000, 0x300000, // 00
|
0x000000, 0x100000, 0x200000, 0x300000, // 00
|
||||||
0x280000, 0x380000, 0x2d0000, 0x3d0000, // 04
|
0x280000, 0x380000, 0x2d0000, 0x3d0000, // 04
|
||||||
@ -173,6 +172,10 @@ namespace MAME.Core
|
|||||||
0x000000, 0x000000, 0x000000, 0x000000, // 56
|
0x000000, 0x000000, 0x000000, 0x000000, // 56
|
||||||
0x000000, 0x000000, 0x000000, 0x000000 // 60
|
0x000000, 0x000000, 0x000000, 0x000000 // 60
|
||||||
};
|
};
|
||||||
|
public static void garouh_bankswitch_w(int data)
|
||||||
|
{
|
||||||
|
int bankaddress;
|
||||||
|
|
||||||
data =
|
data =
|
||||||
(((data >> 4) & 1) << 0) +
|
(((data >> 4) & 1) << 0) +
|
||||||
(((data >> 8) & 1) << 1) +
|
(((data >> 8) & 1) << 1) +
|
||||||
@ -180,14 +183,11 @@ namespace MAME.Core
|
|||||||
(((data >> 2) & 1) << 3) +
|
(((data >> 2) & 1) << 3) +
|
||||||
(((data >> 11) & 1) << 4) +
|
(((data >> 11) & 1) << 4) +
|
||||||
(((data >> 13) & 1) << 5);
|
(((data >> 13) & 1) << 5);
|
||||||
bankaddress = 0x100000 + bankoffset[data];
|
bankaddress = 0x100000 + garouh_bankswitch_w_bankoffset[data];
|
||||||
main_cpu_bank_address = bankaddress;
|
main_cpu_bank_address = bankaddress;
|
||||||
}
|
}
|
||||||
public static void mslug3_bankswitch_w(int data)
|
readonly static int[] mslug3_bankswitch_w_bankoffset = new int[]
|
||||||
{
|
{
|
||||||
int bankaddress;
|
|
||||||
int[] bankoffset = new int[]
|
|
||||||
{
|
|
||||||
0x000000, 0x020000, 0x040000, 0x060000, // 00
|
0x000000, 0x020000, 0x040000, 0x060000, // 00
|
||||||
0x070000, 0x090000, 0x0b0000, 0x0d0000, // 04
|
0x070000, 0x090000, 0x0b0000, 0x0d0000, // 04
|
||||||
0x0e0000, 0x0f0000, 0x120000, 0x130000, // 08
|
0x0e0000, 0x0f0000, 0x120000, 0x130000, // 08
|
||||||
@ -201,7 +201,10 @@ namespace MAME.Core
|
|||||||
0x400000, 0x410000, 0x440000, 0x450000, // 40
|
0x400000, 0x410000, 0x440000, 0x450000, // 40
|
||||||
0x460000, 0x470000, 0x4a0000, 0x4b0000, // 44
|
0x460000, 0x470000, 0x4a0000, 0x4b0000, // 44
|
||||||
0x4c0000
|
0x4c0000
|
||||||
};
|
};
|
||||||
|
public static void mslug3_bankswitch_w(int data)
|
||||||
|
{
|
||||||
|
int bankaddress;
|
||||||
data =
|
data =
|
||||||
(((data >> 14) & 1) << 0) +
|
(((data >> 14) & 1) << 0) +
|
||||||
(((data >> 12) & 1) << 1) +
|
(((data >> 12) & 1) << 1) +
|
||||||
@ -209,13 +212,10 @@ namespace MAME.Core
|
|||||||
(((data >> 6) & 1) << 3) +
|
(((data >> 6) & 1) << 3) +
|
||||||
(((data >> 3) & 1) << 4) +
|
(((data >> 3) & 1) << 4) +
|
||||||
(((data >> 9) & 1) << 5);
|
(((data >> 9) & 1) << 5);
|
||||||
bankaddress = 0x100000 + bankoffset[data];
|
bankaddress = 0x100000 + mslug3_bankswitch_w_bankoffset[data];
|
||||||
main_cpu_bank_address = bankaddress;
|
main_cpu_bank_address = bankaddress;
|
||||||
}
|
}
|
||||||
public static void kof2000_bankswitch_w(int data)
|
readonly static int[] kof2000_bankswitch_w_bankoffset = new int[]
|
||||||
{
|
|
||||||
int bankaddress;
|
|
||||||
int[] bankoffset = new int[]
|
|
||||||
{
|
{
|
||||||
0x000000, 0x100000, 0x200000, 0x300000, // 00
|
0x000000, 0x100000, 0x200000, 0x300000, // 00
|
||||||
0x3f7800, 0x4f7800, 0x3ff800, 0x4ff800, // 04
|
0x3f7800, 0x4f7800, 0x3ff800, 0x4ff800, // 04
|
||||||
@ -227,6 +227,10 @@ namespace MAME.Core
|
|||||||
0x52d000, 0x62d000, 0x52e800, 0x62e800, // 28
|
0x52d000, 0x62d000, 0x52e800, 0x62e800, // 28
|
||||||
0x618000, 0x619000, 0x61a000, 0x61a800, // 32
|
0x618000, 0x619000, 0x61a000, 0x61a800, // 32
|
||||||
};
|
};
|
||||||
|
public static void kof2000_bankswitch_w(int data)
|
||||||
|
{
|
||||||
|
int bankaddress;
|
||||||
|
|
||||||
data =
|
data =
|
||||||
(((data >> 15) & 1) << 0) +
|
(((data >> 15) & 1) << 0) +
|
||||||
(((data >> 14) & 1) << 1) +
|
(((data >> 14) & 1) << 1) +
|
||||||
@ -234,7 +238,7 @@ namespace MAME.Core
|
|||||||
(((data >> 3) & 1) << 3) +
|
(((data >> 3) & 1) << 3) +
|
||||||
(((data >> 10) & 1) << 4) +
|
(((data >> 10) & 1) << 4) +
|
||||||
(((data >> 5) & 1) << 5);
|
(((data >> 5) & 1) << 5);
|
||||||
bankaddress = 0x100000 + bankoffset[data];
|
bankaddress = 0x100000 + kof2000_bankswitch_w_bankoffset[data];
|
||||||
main_cpu_bank_address = bankaddress;
|
main_cpu_bank_address = bankaddress;
|
||||||
}
|
}
|
||||||
public static void pvc_prot1()
|
public static void pvc_prot1()
|
||||||
|
|||||||
@ -8,7 +8,7 @@
|
|||||||
public static byte kb_swap;
|
public static byte kb_swap;
|
||||||
public static ushort olds_bs, kb_cmd3;
|
public static ushort olds_bs, kb_cmd3;
|
||||||
public static byte[][] kb_source_data;
|
public static byte[][] kb_source_data;
|
||||||
public static byte[][] drgw2_source_data = new byte[0x08][]//[0xec]
|
public readonly static byte[][] drgw2_source_data = new byte[0x08][]//[0xec]
|
||||||
{
|
{
|
||||||
new byte[]{ 0, }, // Region 0, not used
|
new byte[]{ 0, }, // Region 0, not used
|
||||||
new byte[]{ // Region 1, $13A886
|
new byte[]{ // Region 1, $13A886
|
||||||
|
|||||||
@ -11,7 +11,7 @@
|
|||||||
public static byte port1_out, port2_out, port3_out, port4_out;
|
public static byte port1_out, port2_out, port3_out, port4_out;
|
||||||
public static byte portA_in, portA_out, ddrA, portB_in, portB_out, ddrB;
|
public static byte portA_in, portA_out, ddrA, portB_in, portB_out, ddrB;
|
||||||
public static int ic43_a, ic43_b;
|
public static int ic43_a, ic43_b;
|
||||||
public static byte[] tokio_prot_data = new byte[]
|
public readonly static byte[] tokio_prot_data = new byte[]
|
||||||
{
|
{
|
||||||
0x6c,
|
0x6c,
|
||||||
0x7f,0x5f,0x7f,0x6f,0x5f,0x77,0x5f,0x7f,0x5f,0x7f,0x5f,0x7f,0x5b,0x7f,0x5f,0x7f,
|
0x7f,0x5f,0x7f,0x6f,0x5f,0x77,0x5f,0x7f,0x5f,0x7f,0x5f,0x7f,0x5b,0x7f,0x5f,0x7f,
|
||||||
@ -295,10 +295,10 @@
|
|||||||
}
|
}
|
||||||
ic43_a = res;
|
ic43_a = res;
|
||||||
}
|
}
|
||||||
|
readonly static int[] boblbobl_ic43_b_w_xor = new int[] { 4, 1, 8, 2 };
|
||||||
public static void boblbobl_ic43_b_w(int offset, byte data)
|
public static void boblbobl_ic43_b_w(int offset, byte data)
|
||||||
{
|
{
|
||||||
int[] xor = new int[] { 4, 1, 8, 2 };
|
ic43_b = (data >> 4) ^ boblbobl_ic43_b_w_xor[offset];
|
||||||
ic43_b = (data >> 4) ^ xor[offset];
|
|
||||||
}
|
}
|
||||||
public static byte boblbobl_ic43_b_r(int offset)
|
public static byte boblbobl_ic43_b_r(int offset)
|
||||||
{
|
{
|
||||||
|
|||||||
@ -671,6 +671,9 @@ namespace MAME.Core
|
|||||||
{
|
{
|
||||||
current_bank = (byte)(data & 7);
|
current_bank = (byte)(data & 7);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int[] opwolf_cchip_data_w_coin_table = new int[] { 0, 0 };
|
||||||
|
static byte[] opwolf_cchip_data_w_coin_offset = new byte[2];
|
||||||
public static void opwolf_cchip_data_w(int offset, ushort data)
|
public static void opwolf_cchip_data_w(int offset, ushort data)
|
||||||
{
|
{
|
||||||
cchip_ram[(current_bank * 0x400) + offset] = (byte)(data & 0xff);
|
cchip_ram[(current_bank * 0x400) + offset] = (byte)(data & 0xff);
|
||||||
@ -680,28 +683,28 @@ namespace MAME.Core
|
|||||||
// Shouldn't we directly read the values from the ROM area ?
|
// Shouldn't we directly read the values from the ROM area ?
|
||||||
if (offset == 0x14)
|
if (offset == 0x14)
|
||||||
{
|
{
|
||||||
int[] coin_table = new int[] { 0, 0 };
|
//int[] coin_table = new int[] { 0, 0 };
|
||||||
byte[] coin_offset = new byte[2];
|
//byte[] coin_offset = new byte[2];
|
||||||
int slot;
|
int slot;
|
||||||
|
|
||||||
if ((opwolf_region == 1) || (opwolf_region == 2))
|
if ((opwolf_region == 1) || (opwolf_region == 2))
|
||||||
{
|
{
|
||||||
coin_table[0] = 0x03ffce;
|
opwolf_cchip_data_w_coin_table[0] = 0x03ffce;
|
||||||
coin_table[1] = 0x03ffce;
|
opwolf_cchip_data_w_coin_table[1] = 0x03ffce;
|
||||||
}
|
}
|
||||||
if ((opwolf_region == 3) || (opwolf_region == 4))
|
if ((opwolf_region == 3) || (opwolf_region == 4))
|
||||||
{
|
{
|
||||||
coin_table[0] = 0x03ffde;
|
opwolf_cchip_data_w_coin_table[0] = 0x03ffde;
|
||||||
coin_table[1] = 0x03ffee;
|
opwolf_cchip_data_w_coin_table[1] = 0x03ffee;
|
||||||
}
|
}
|
||||||
coin_offset[0] = (byte)(12 - (4 * ((data & 0x30) >> 4)));
|
opwolf_cchip_data_w_coin_offset[0] = (byte)(12 - (4 * ((data & 0x30) >> 4)));
|
||||||
coin_offset[1] = (byte)(12 - (4 * ((data & 0xc0) >> 6)));
|
opwolf_cchip_data_w_coin_offset[1] = (byte)(12 - (4 * ((data & 0xc0) >> 6)));
|
||||||
for (slot = 0; slot < 2; slot++)
|
for (slot = 0; slot < 2; slot++)
|
||||||
{
|
{
|
||||||
if (coin_table[slot] != 0)
|
if (opwolf_cchip_data_w_coin_table[slot] != 0)
|
||||||
{
|
{
|
||||||
cchip_coins_for_credit[slot] = (byte)((Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 0) / 2 * 2] * 0x100 + Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 0) / 2 * 2 + 1]) & 0xff);
|
cchip_coins_for_credit[slot] = (byte)((Memory.mainrom[(opwolf_cchip_data_w_coin_table[slot] + opwolf_cchip_data_w_coin_offset[slot] + 0) / 2 * 2] * 0x100 + Memory.mainrom[(opwolf_cchip_data_w_coin_table[slot] + opwolf_cchip_data_w_coin_offset[slot] + 0) / 2 * 2 + 1]) & 0xff);
|
||||||
cchip_credits_for_coin[slot] = (byte)((Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 2) / 2 * 2] * 0x100 + Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 2) / 2 * 2 + 1]) & 0xff);
|
cchip_credits_for_coin[slot] = (byte)((Memory.mainrom[(opwolf_cchip_data_w_coin_table[slot] + opwolf_cchip_data_w_coin_offset[slot] + 2) / 2 * 2] * 0x100 + Memory.mainrom[(opwolf_cchip_data_w_coin_table[slot] + opwolf_cchip_data_w_coin_offset[slot] + 2) / 2 * 2 + 1]) & 0xff);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -712,6 +715,8 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
static int[] opwolf_cchip_data_w2_coin_table = new int[] { 0, 0 };
|
||||||
|
static byte[] opwolf_cchip_data_w2_coin_offset = new byte[2];
|
||||||
public static void opwolf_cchip_data_w2(int offset, byte data)
|
public static void opwolf_cchip_data_w2(int offset, byte data)
|
||||||
{
|
{
|
||||||
cchip_ram[(current_bank * 0x400) + offset] = (byte)(data & 0xff);
|
cchip_ram[(current_bank * 0x400) + offset] = (byte)(data & 0xff);
|
||||||
@ -721,28 +726,28 @@ namespace MAME.Core
|
|||||||
// Shouldn't we directly read the values from the ROM area ?
|
// Shouldn't we directly read the values from the ROM area ?
|
||||||
if (offset == 0x14)
|
if (offset == 0x14)
|
||||||
{
|
{
|
||||||
int[] coin_table = new int[] { 0, 0 };
|
//int[] coin_table = new int[] { 0, 0 };
|
||||||
byte[] coin_offset = new byte[2];
|
//byte[] coin_offset = new byte[2];
|
||||||
int slot;
|
int slot;
|
||||||
|
|
||||||
if ((opwolf_region == 1) || (opwolf_region == 2))
|
if ((opwolf_region == 1) || (opwolf_region == 2))
|
||||||
{
|
{
|
||||||
coin_table[0] = 0x03ffce;
|
opwolf_cchip_data_w2_coin_table[0] = 0x03ffce;
|
||||||
coin_table[1] = 0x03ffce;
|
opwolf_cchip_data_w2_coin_table[1] = 0x03ffce;
|
||||||
}
|
}
|
||||||
if ((opwolf_region == 3) || (opwolf_region == 4))
|
if ((opwolf_region == 3) || (opwolf_region == 4))
|
||||||
{
|
{
|
||||||
coin_table[0] = 0x03ffde;
|
opwolf_cchip_data_w2_coin_table[0] = 0x03ffde;
|
||||||
coin_table[1] = 0x03ffee;
|
opwolf_cchip_data_w2_coin_table[1] = 0x03ffee;
|
||||||
}
|
}
|
||||||
coin_offset[0] = (byte)(12 - (4 * ((data & 0x30) >> 4)));
|
opwolf_cchip_data_w2_coin_offset[0] = (byte)(12 - (4 * ((data & 0x30) >> 4)));
|
||||||
coin_offset[1] = (byte)(12 - (4 * ((data & 0xc0) >> 6)));
|
opwolf_cchip_data_w2_coin_offset[1] = (byte)(12 - (4 * ((data & 0xc0) >> 6)));
|
||||||
for (slot = 0; slot < 2; slot++)
|
for (slot = 0; slot < 2; slot++)
|
||||||
{
|
{
|
||||||
if (coin_table[slot] != 0)
|
if (opwolf_cchip_data_w2_coin_table[slot] != 0)
|
||||||
{
|
{
|
||||||
cchip_coins_for_credit[slot] = (byte)((Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 0) / 2 * 2] * 0x100 + Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 0) / 2 * 2 + 1]) & 0xff);
|
cchip_coins_for_credit[slot] = (byte)((Memory.mainrom[(opwolf_cchip_data_w2_coin_table[slot] + opwolf_cchip_data_w2_coin_offset[slot] + 0) / 2 * 2] * 0x100 + Memory.mainrom[(opwolf_cchip_data_w2_coin_table[slot] + opwolf_cchip_data_w2_coin_offset[slot] + 0) / 2 * 2 + 1]) & 0xff);
|
||||||
cchip_credits_for_coin[slot] = (byte)((Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 2) / 2 * 2] * 0x100 + Memory.mainrom[(coin_table[slot] + coin_offset[slot] + 2) / 2 * 2 + 1]) & 0xff);
|
cchip_credits_for_coin[slot] = (byte)((Memory.mainrom[(opwolf_cchip_data_w2_coin_table[slot] + opwolf_cchip_data_w2_coin_offset[slot] + 2) / 2 * 2] * 0x100 + Memory.mainrom[(opwolf_cchip_data_w2_coin_table[slot] + opwolf_cchip_data_w2_coin_offset[slot] + 2) / 2 * 2 + 1]) & 0xff);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -286,18 +286,41 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
//private int mix_3D()
|
||||||
|
//{
|
||||||
|
// int indx = 0, chan;
|
||||||
|
// for (chan = 0; chan < 3; chan++)
|
||||||
|
// {
|
||||||
|
// if (TONE_ENVELOPE(chan) != 0)
|
||||||
|
// {
|
||||||
|
// indx |= ((1 << (chan + 15)) | ((ay8910info.vol_enabled[chan] != 0) ? ay8910info.env_volume << (chan * 5) : 0));
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// indx |= ((ay8910info.vol_enabled[chan] != 0) ? TONE_VOLUME(chan) << (chan * 5) : 0);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// return ay8910info.vol3d_table[indx];
|
||||||
|
//}
|
||||||
|
|
||||||
|
//手动内联
|
||||||
private int mix_3D()
|
private int mix_3D()
|
||||||
{
|
{
|
||||||
int indx = 0, chan;
|
int indx = 0, chan;
|
||||||
for (chan = 0; chan < 3; chan++)
|
for (chan = 0; chan < 3; chan++)
|
||||||
{
|
{
|
||||||
if (TONE_ENVELOPE(chan) != 0)
|
//if (TONE_ENVELOPE(chan) != 0)
|
||||||
|
if(((ay8910info.regs[TONE_ENVELOPE_REG_OFFSET + chan] >> TONE_ENVELOPE_MOVE) & TONE_ENVELOPE_VOLUME_MASK)!=0)
|
||||||
{
|
{
|
||||||
indx |= ((1 << (chan + 15)) | ((ay8910info.vol_enabled[chan] != 0) ? ay8910info.env_volume << (chan * 5) : 0));
|
indx |= ((1 << (chan + 15)) | ((ay8910info.vol_enabled[chan] != 0) ? ay8910info.env_volume << (chan * 5) : 0));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
indx |= ((ay8910info.vol_enabled[chan] != 0) ? TONE_VOLUME(chan) << (chan * 5) : 0);
|
indx |= ((ay8910info.vol_enabled[chan] != 0) ?
|
||||||
|
//TONE_VOLUME(chan)
|
||||||
|
(ay8910info.regs[TONE_VOLUME_REG_OFFSET + chan] & TONE_VOLUME_VOLUME_MASK)
|
||||||
|
<< (chan * 5)
|
||||||
|
: 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return ay8910info.vol3d_table[indx];
|
return ay8910info.vol3d_table[indx];
|
||||||
@ -373,6 +396,104 @@ namespace MAME.Core
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
//public void ay8910_update(int offset, int length)
|
||||||
|
//{
|
||||||
|
// int chan, i, j;
|
||||||
|
// if (ay8910info.ready == 0)
|
||||||
|
// {
|
||||||
|
// for (chan = 0; chan < ay8910info.streams; chan++)
|
||||||
|
// {
|
||||||
|
// for (j = 0; j < length; j++)
|
||||||
|
// {
|
||||||
|
// stream.streamoutput_Ptrs[chan][offset + j] = 0;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// for (i = 0; i < length; i++)
|
||||||
|
// {
|
||||||
|
// for (chan = 0; chan < 3; chan++)
|
||||||
|
// {
|
||||||
|
// ay8910info.count[chan]++;
|
||||||
|
// if (ay8910info.count[chan] >= TONE_PERIOD(chan))
|
||||||
|
// {
|
||||||
|
// ay8910info.output[chan] ^= 1;
|
||||||
|
// ay8910info.count[chan] = 0; ;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// ay8910info.count_noise++;
|
||||||
|
// if (ay8910info.count_noise >= NOISE_PERIOD())
|
||||||
|
// {
|
||||||
|
// if (((ay8910info.rng + 1) & 2) != 0)
|
||||||
|
// {
|
||||||
|
// ay8910info.output_noise ^= 1;
|
||||||
|
// }
|
||||||
|
// if ((ay8910info.rng & 1) != 0)
|
||||||
|
// {
|
||||||
|
// ay8910info.rng ^= 0x24000;
|
||||||
|
// }
|
||||||
|
// ay8910info.rng >>= 1;
|
||||||
|
// ay8910info.count_noise = 0;
|
||||||
|
// }
|
||||||
|
// for (chan = 0; chan < 3; chan++)
|
||||||
|
// {
|
||||||
|
// ay8910info.vol_enabled[chan] = (byte)((ay8910info.output[chan] | TONE_ENABLEQ(chan)) & (ay8910info.output_noise | NOISE_ENABLEQ(chan)));
|
||||||
|
// }
|
||||||
|
// if (ay8910info.holding == 0)
|
||||||
|
// {
|
||||||
|
// ay8910info.count_env++;
|
||||||
|
// if (ay8910info.count_env >= ENVELOPE_PERIOD() * ay8910info.step)
|
||||||
|
// {
|
||||||
|
// ay8910info.count_env = 0;
|
||||||
|
// ay8910info.env_step--;
|
||||||
|
// if (ay8910info.env_step < 0)
|
||||||
|
// {
|
||||||
|
// if (ay8910info.hold != 0)
|
||||||
|
// {
|
||||||
|
// if (ay8910info.alternate != 0)
|
||||||
|
// {
|
||||||
|
// ay8910info.attack ^= ay8910info.env_step_mask;
|
||||||
|
// }
|
||||||
|
// ay8910info.holding = 1;
|
||||||
|
// ay8910info.env_step = 0;
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// if (ay8910info.alternate != 0 && (ay8910info.env_step & (ay8910info.env_step_mask + 1)) != 0)
|
||||||
|
// {
|
||||||
|
// ay8910info.attack ^= ay8910info.env_step_mask;
|
||||||
|
// }
|
||||||
|
// ay8910info.env_step &= (sbyte)ay8910info.env_step_mask;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// ay8910info.env_volume = (ay8910info.env_step ^ ay8910info.attack);
|
||||||
|
// if (ay8910info.streams == 3)
|
||||||
|
// {
|
||||||
|
// for (chan = 0; chan < 3; chan++)
|
||||||
|
// {
|
||||||
|
// if (TONE_ENVELOPE(chan) != 0)
|
||||||
|
// {
|
||||||
|
// int i1 = ay8910info.env_table[chan][ay8910info.vol_enabled[chan] != 0 ? ay8910info.env_volume : 0];
|
||||||
|
// stream.streamoutput_Ptrs[chan][offset] = ay8910info.env_table[chan][ay8910info.vol_enabled[chan] != 0 ? ay8910info.env_volume : 0];
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// int i1 = ay8910info.vol_table[chan][ay8910info.vol_enabled[chan] != 0 ? TONE_VOLUME(chan) : 0];
|
||||||
|
// stream.streamoutput_Ptrs[chan][offset] = ay8910info.vol_table[chan][ay8910info.vol_enabled[chan] != 0 ? TONE_VOLUME(chan) : 0];
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// stream.streamoutput_Ptrs[0][offset] = mix_3D();
|
||||||
|
// }
|
||||||
|
// offset++;
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
|
||||||
|
|
||||||
|
//手动内联优化
|
||||||
public void ay8910_update(int offset, int length)
|
public void ay8910_update(int offset, int length)
|
||||||
{
|
{
|
||||||
int chan, i, j;
|
int chan, i, j;
|
||||||
@ -391,14 +512,16 @@ namespace MAME.Core
|
|||||||
for (chan = 0; chan < 3; chan++)
|
for (chan = 0; chan < 3; chan++)
|
||||||
{
|
{
|
||||||
ay8910info.count[chan]++;
|
ay8910info.count[chan]++;
|
||||||
if (ay8910info.count[chan] >= TONE_PERIOD(chan))
|
//if (ay8910info.count[chan] >= TONE_PERIOD(chan))
|
||||||
|
if (ay8910info.count[chan] >= (ay8910info.regs[chan << 1] | ((ay8910info.regs[(chan << 1) | 1] & 0x0f) << 8)))
|
||||||
{
|
{
|
||||||
ay8910info.output[chan] ^= 1;
|
ay8910info.output[chan] ^= 1;
|
||||||
ay8910info.count[chan] = 0; ;
|
ay8910info.count[chan] = 0; ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ay8910info.count_noise++;
|
ay8910info.count_noise++;
|
||||||
if (ay8910info.count_noise >= NOISE_PERIOD())
|
//if (ay8910info.count_noise >= NOISE_PERIOD())
|
||||||
|
if (ay8910info.count_noise >= (ay8910info.regs[6] & 0x1f))
|
||||||
{
|
{
|
||||||
if (((ay8910info.rng + 1) & 2) != 0)
|
if (((ay8910info.rng + 1) & 2) != 0)
|
||||||
{
|
{
|
||||||
@ -413,12 +536,23 @@ namespace MAME.Core
|
|||||||
}
|
}
|
||||||
for (chan = 0; chan < 3; chan++)
|
for (chan = 0; chan < 3; chan++)
|
||||||
{
|
{
|
||||||
ay8910info.vol_enabled[chan] = (byte)((ay8910info.output[chan] | TONE_ENABLEQ(chan)) & (ay8910info.output_noise | NOISE_ENABLEQ(chan)));
|
//ay8910info.vol_enabled[chan] = (byte)((ay8910info.output[chan] | TONE_ENABLEQ(chan)) & (ay8910info.output_noise | NOISE_ENABLEQ(chan)));
|
||||||
|
ay8910info.vol_enabled[chan] = (byte)((ay8910info.output[chan] |
|
||||||
|
//TONE_ENABLEQ(chan)
|
||||||
|
((ay8910info.regs[7] >> chan) & 1)
|
||||||
|
) & (ay8910info.output_noise |
|
||||||
|
//NOISE_ENABLEQ(chan)
|
||||||
|
((ay8910info.regs[7] >> (3 + chan)) & 1)
|
||||||
|
));
|
||||||
}
|
}
|
||||||
if (ay8910info.holding == 0)
|
if (ay8910info.holding == 0)
|
||||||
{
|
{
|
||||||
ay8910info.count_env++;
|
ay8910info.count_env++;
|
||||||
if (ay8910info.count_env >= ENVELOPE_PERIOD() * ay8910info.step)
|
//if (ay8910info.count_env >= ENVELOPE_PERIOD() * ay8910info.step)
|
||||||
|
if (ay8910info.count_env >=
|
||||||
|
//ENVELOPE_PERIOD()
|
||||||
|
(ay8910info.regs[11] | (ay8910info.regs[12] << 8))
|
||||||
|
* ay8910info.step)
|
||||||
{
|
{
|
||||||
ay8910info.count_env = 0;
|
ay8910info.count_env = 0;
|
||||||
ay8910info.env_step--;
|
ay8910info.env_step--;
|
||||||
@ -449,21 +583,46 @@ namespace MAME.Core
|
|||||||
{
|
{
|
||||||
for (chan = 0; chan < 3; chan++)
|
for (chan = 0; chan < 3; chan++)
|
||||||
{
|
{
|
||||||
if (TONE_ENVELOPE(chan) != 0)
|
//if (TONE_ENVELOPE(chan) != 0)
|
||||||
|
if(((ay8910info.regs[TONE_ENVELOPE_REG_OFFSET + chan] >> TONE_ENVELOPE_MOVE) & TONE_ENVELOPE_VOLUME_MASK) != 0)
|
||||||
{
|
{
|
||||||
int i1 = ay8910info.env_table[chan][ay8910info.vol_enabled[chan] != 0 ? ay8910info.env_volume : 0];
|
int i1 = ay8910info.env_table[chan][ay8910info.vol_enabled[chan] != 0 ? ay8910info.env_volume : 0];
|
||||||
stream.streamoutput_Ptrs[chan][offset] = ay8910info.env_table[chan][ay8910info.vol_enabled[chan] != 0 ? ay8910info.env_volume : 0];
|
stream.streamoutput_Ptrs[chan][offset] = ay8910info.env_table[chan][ay8910info.vol_enabled[chan] != 0 ? ay8910info.env_volume : 0];
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
int i1 = ay8910info.vol_table[chan][ay8910info.vol_enabled[chan] != 0 ? TONE_VOLUME(chan) : 0];
|
int i1 = ay8910info.vol_table[chan][ay8910info.vol_enabled[chan] != 0 ?
|
||||||
stream.streamoutput_Ptrs[chan][offset] = ay8910info.vol_table[chan][ay8910info.vol_enabled[chan] != 0 ? TONE_VOLUME(chan) : 0];
|
//TONE_VOLUME(chan)
|
||||||
|
ay8910info.regs[TONE_VOLUME_REG_OFFSET + chan] & TONE_VOLUME_VOLUME_MASK
|
||||||
|
: 0];
|
||||||
|
stream.streamoutput_Ptrs[chan][offset] = ay8910info.vol_table[chan][ay8910info.vol_enabled[chan] != 0 ?
|
||||||
|
//TONE_VOLUME(chan)
|
||||||
|
ay8910info.regs[TONE_VOLUME_REG_OFFSET + chan] & TONE_VOLUME_VOLUME_MASK
|
||||||
|
: 0];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
stream.streamoutput_Ptrs[0][offset] = mix_3D();
|
//stream.streamoutput_Ptrs[0][offset] = mix_3D();
|
||||||
|
{
|
||||||
|
int indx = 0, tempchan;
|
||||||
|
for (tempchan = 0; tempchan < 3; tempchan++)
|
||||||
|
{
|
||||||
|
if (((ay8910info.regs[TONE_ENVELOPE_REG_OFFSET + tempchan] >> TONE_ENVELOPE_MOVE) & TONE_ENVELOPE_VOLUME_MASK) != 0)
|
||||||
|
{
|
||||||
|
indx |= ((1 << (tempchan + 15)) | ((ay8910info.vol_enabled[tempchan] != 0) ? ay8910info.env_volume << (tempchan * 5) : 0));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
indx |= ((ay8910info.vol_enabled[tempchan] != 0) ?
|
||||||
|
(ay8910info.regs[TONE_VOLUME_REG_OFFSET + tempchan] & TONE_VOLUME_VOLUME_MASK)
|
||||||
|
<< (tempchan * 5)
|
||||||
|
: 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
stream.streamoutput_Ptrs[0][offset] = ay8910info.vol3d_table[indx];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
offset++;
|
offset++;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -287,7 +287,7 @@ namespace MAME.Core
|
|||||||
6, 3, 0,-3,-6,-3, 0, 3,
|
6, 3, 0,-3,-6,-3, 0, 3,
|
||||||
7, 3, 0,-3,-7,-3, 0, 3,
|
7, 3, 0,-3,-7,-3, 0, 3,
|
||||||
};
|
};
|
||||||
private static byte[][] table = new byte[19][]
|
private readonly static byte[][] table = new byte[19][]
|
||||||
{
|
{
|
||||||
new byte[]{0x49, 0x4c, 0x4c, 0x12, 0x00, 0x00, 0x00, 0x00 },
|
new byte[]{0x49, 0x4c, 0x4c, 0x12, 0x00, 0x00, 0x00, 0x00 },
|
||||||
|
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user