mirror of https://github.com/stella-emu/stella.git
Some minor tweaks which will hopefully speed things up for the GP2X
port. Resurrected the low-compatibility 6502 CPU code, since it's supposed to be somewhat faster. This is activated internally by GP2X by settings "cpu" to "low". This can also be set from the commandline, but I'm not going to document the fact. All systems that can handle hi-compat mode should be using it. git-svn-id: svn://svn.code.sf.net/p/stella/code/trunk@999 8b62c5a3-ac7e-4cc8-8f21-d9a121418aba
This commit is contained in:
parent
1018a3f349
commit
cc07a7e502
|
@ -13,7 +13,7 @@
|
|||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: Console.cxx,v 1.82 2006-01-25 01:42:46 stephena Exp $
|
||||
// $Id: Console.cxx,v 1.83 2006-02-05 02:49:47 stephena Exp $
|
||||
//============================================================================
|
||||
|
||||
#include <assert.h>
|
||||
|
@ -31,6 +31,7 @@
|
|||
#include "Joystick.hxx"
|
||||
#include "Keyboard.hxx"
|
||||
#include "M6502Hi.hxx"
|
||||
#include "M6502Low.hxx"
|
||||
#include "M6532.hxx"
|
||||
#include "MediaSrc.hxx"
|
||||
#include "Paddles.hxx"
|
||||
|
@ -156,7 +157,10 @@ Console::Console(const uInt8* image, uInt32 size, const string& md5,
|
|||
mySystem = new System(13, 6);
|
||||
|
||||
M6502* m6502;
|
||||
m6502 = new M6502High(1);
|
||||
if(myOSystem->settings().getString("cpu") == "low")
|
||||
m6502 = new M6502Low(1);
|
||||
else
|
||||
m6502 = new M6502High(1);
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
m6502->attach(myOSystem->debugger());
|
||||
#endif
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: TIA.hxx,v 1.33 2005-10-11 19:38:10 stephena Exp $
|
||||
// $Id: TIA.hxx,v 1.34 2006-02-05 02:49:47 stephena Exp $
|
||||
//============================================================================
|
||||
|
||||
#ifndef TIA_HXX
|
||||
|
@ -42,7 +42,7 @@ class Settings;
|
|||
be displayed on screen.
|
||||
|
||||
@author Bradford W. Mott
|
||||
@version $Id: TIA.hxx,v 1.33 2005-10-11 19:38:10 stephena Exp $
|
||||
@version $Id: TIA.hxx,v 1.34 2006-02-05 02:49:47 stephena Exp $
|
||||
*/
|
||||
class TIA : public Device , public MediaSource
|
||||
{
|
||||
|
@ -259,7 +259,7 @@ class TIA : public Device , public MediaSource
|
|||
|
||||
private:
|
||||
// Update the current frame buffer up to one scanline
|
||||
void updateFrameScanline(uInt32 clocksToUpdate, uInt32 hpos);
|
||||
inline void updateFrameScanline(uInt32 clocksToUpdate, uInt32 hpos);
|
||||
|
||||
// Update the current frame buffer to the specified color clock
|
||||
void updateFrame(Int32 clock);
|
||||
|
@ -273,11 +273,11 @@ class TIA : public Device , public MediaSource
|
|||
// Clear both internal TIA buffers to black (palette color 0)
|
||||
void clearBuffers();
|
||||
|
||||
// set up bookkeeping for the next frame
|
||||
void startFrame();
|
||||
// Set up bookkeeping for the next frame
|
||||
inline void startFrame();
|
||||
|
||||
// update bookkeeping at end of frame
|
||||
void endFrame();
|
||||
// Update bookkeeping at end of frame
|
||||
inline void endFrame();
|
||||
|
||||
private:
|
||||
// Console the TIA is associated with
|
||||
|
|
|
@ -3,6 +3,7 @@ MODULE := src/emucore/m6502
|
|||
MODULE_OBJS := \
|
||||
src/emucore/m6502/src/Device.o \
|
||||
src/emucore/m6502/src/M6502.o \
|
||||
src/emucore/m6502/src/M6502Low.o \
|
||||
src/emucore/m6502/src/M6502Hi.o \
|
||||
src/emucore/m6502/src/NullDev.o \
|
||||
src/emucore/m6502/src/System.o
|
||||
|
|
|
@ -0,0 +1,300 @@
|
|||
//============================================================================
|
||||
//
|
||||
// MM MM 6666 555555 0000 2222
|
||||
// MMMM MMMM 66 66 55 00 00 22 22
|
||||
// MM MMM MM 66 55 00 00 22
|
||||
// MM M MM 66666 55555 00 00 22222 -- "A 6502 Microprocessor Emulator"
|
||||
// MM MM 66 66 55 00 00 22
|
||||
// MM MM 66 66 55 55 00 00 22
|
||||
// MM MM 6666 5555 0000 222222
|
||||
//
|
||||
// Copyright (c) 1995-2005 by Bradford W. Mott and the Stella team
|
||||
//
|
||||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: M6502Low.cxx,v 1.8 2006-02-05 02:49:47 stephena Exp $
|
||||
//============================================================================
|
||||
|
||||
#include "M6502Low.hxx"
|
||||
#include "Serializer.hxx"
|
||||
#include "Deserializer.hxx"
|
||||
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
#include "Debugger.hxx"
|
||||
#endif
|
||||
|
||||
#define debugStream cout
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
M6502Low::M6502Low(uInt32 systemCyclesPerProcessorCycle)
|
||||
: M6502(systemCyclesPerProcessorCycle)
|
||||
{
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
myJustHitTrapFlag = false;
|
||||
#endif
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
M6502Low::~M6502Low()
|
||||
{
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
inline uInt8 M6502Low::peek(uInt16 address)
|
||||
{
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
if(myReadTraps != NULL && myReadTraps->isSet(address))
|
||||
{
|
||||
myJustHitTrapFlag = true;
|
||||
myHitTrapInfo.message = "Read trap: ";
|
||||
myHitTrapInfo.address = address;
|
||||
}
|
||||
#endif
|
||||
|
||||
return mySystem->peek(address);
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
inline void M6502Low::poke(uInt16 address, uInt8 value)
|
||||
{
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
if(myWriteTraps != NULL && myWriteTraps->isSet(address))
|
||||
{
|
||||
myJustHitTrapFlag = true;
|
||||
myHitTrapInfo.message = "Write trap: ";
|
||||
myHitTrapInfo.address = address;
|
||||
}
|
||||
#endif
|
||||
|
||||
mySystem->poke(address, value);
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
bool M6502Low::execute(uInt32 number)
|
||||
{
|
||||
// Clear all of the execution status bits except for the fatal error bit
|
||||
myExecutionStatus &= FatalErrorBit;
|
||||
|
||||
// Loop until execution is stopped or a fatal error occurs
|
||||
for(;;)
|
||||
{
|
||||
for(; !myExecutionStatus && (number != 0); --number)
|
||||
{
|
||||
uInt16 operandAddress = 0;
|
||||
uInt8 operand = 0;
|
||||
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
if(myJustHitTrapFlag)
|
||||
{
|
||||
if(myDebugger->start(myHitTrapInfo.message, myHitTrapInfo.address))
|
||||
{
|
||||
myJustHitTrapFlag = false;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if(myBreakPoints != NULL)
|
||||
{
|
||||
if(myBreakPoints->isSet(PC))
|
||||
{
|
||||
if(myDebugger->start("Breakpoint hit: ", PC))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
int cond = evalCondBreaks();
|
||||
if(cond > -1)
|
||||
{
|
||||
string buf = "CBP: " + myBreakCondNames[cond];
|
||||
if(myDebugger->start(buf))
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef DEBUG
|
||||
debugStream << "PC=" << hex << setw(4) << PC << " ";
|
||||
#endif
|
||||
|
||||
// Fetch instruction at the program counter
|
||||
IR = peek(PC++);
|
||||
|
||||
#ifdef DEBUG
|
||||
debugStream << "IR=" << hex << setw(2) << (int)IR << " ";
|
||||
debugStream << "<" << ourAddressingModeTable[IR] << " ";
|
||||
#endif
|
||||
|
||||
// Update system cycles
|
||||
mySystem->incrementCycles(myInstructionSystemCycleTable[IR]);
|
||||
|
||||
// Call code to execute the instruction
|
||||
switch(IR)
|
||||
{
|
||||
// 6502 instruction emulation is generated by an M4 macro file
|
||||
#include "M6502Low.ins"
|
||||
|
||||
default:
|
||||
// Oops, illegal instruction executed so set fatal error flag
|
||||
myExecutionStatus |= FatalErrorBit;
|
||||
cerr << "Illegal Instruction! " << hex << (int) IR << endl;
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
debugStream << hex << setw(4) << operandAddress << " ";
|
||||
debugStream << setw(4) << ourInstructionMnemonicTable[IR];
|
||||
debugStream << "> ";
|
||||
debugStream << "A=" << ::hex << setw(2) << (int)A << " ";
|
||||
debugStream << "X=" << ::hex << setw(2) << (int)X << " ";
|
||||
debugStream << "Y=" << ::hex << setw(2) << (int)Y << " ";
|
||||
debugStream << "PS=" << ::hex << setw(2) << (int)PS() << " ";
|
||||
debugStream << "SP=" << ::hex << setw(2) << (int)SP << " ";
|
||||
debugStream << "Cyc=" << dec << mySystem->cycles();
|
||||
debugStream << endl;
|
||||
#endif
|
||||
}
|
||||
|
||||
// See if we need to handle an interrupt
|
||||
if((myExecutionStatus & MaskableInterruptBit) ||
|
||||
(myExecutionStatus & NonmaskableInterruptBit))
|
||||
{
|
||||
// Yes, so handle the interrupt
|
||||
interruptHandler();
|
||||
}
|
||||
|
||||
// See if execution has been stopped
|
||||
if(myExecutionStatus & StopExecutionBit)
|
||||
{
|
||||
// Yes, so answer that everything finished fine
|
||||
return true;
|
||||
}
|
||||
|
||||
// See if a fatal error has occured
|
||||
if(myExecutionStatus & FatalErrorBit)
|
||||
{
|
||||
// Yes, so answer that something when wrong
|
||||
return false;
|
||||
}
|
||||
|
||||
// See if we've executed the specified number of instructions
|
||||
if(number == 0)
|
||||
{
|
||||
// Yes, so answer that everything finished fine
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
void M6502Low::interruptHandler()
|
||||
{
|
||||
// Handle the interrupt
|
||||
if((myExecutionStatus & MaskableInterruptBit) && !I)
|
||||
{
|
||||
mySystem->incrementCycles(7 * mySystemCyclesPerProcessorCycle);
|
||||
mySystem->poke(0x0100 + SP--, (PC - 1) >> 8);
|
||||
mySystem->poke(0x0100 + SP--, (PC - 1) & 0x00ff);
|
||||
mySystem->poke(0x0100 + SP--, PS() & (~0x10));
|
||||
D = false;
|
||||
I = true;
|
||||
PC = (uInt16)mySystem->peek(0xFFFE) | ((uInt16)mySystem->peek(0xFFFF) << 8);
|
||||
}
|
||||
else if(myExecutionStatus & NonmaskableInterruptBit)
|
||||
{
|
||||
mySystem->incrementCycles(7 * mySystemCyclesPerProcessorCycle);
|
||||
mySystem->poke(0x0100 + SP--, (PC - 1) >> 8);
|
||||
mySystem->poke(0x0100 + SP--, (PC - 1) & 0x00ff);
|
||||
mySystem->poke(0x0100 + SP--, PS() & (~0x10));
|
||||
D = false;
|
||||
PC = (uInt16)mySystem->peek(0xFFFA) | ((uInt16)mySystem->peek(0xFFFB) << 8);
|
||||
}
|
||||
|
||||
// Clear the interrupt bits in myExecutionStatus
|
||||
myExecutionStatus &= ~(MaskableInterruptBit | NonmaskableInterruptBit);
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
bool M6502Low::save(Serializer& out)
|
||||
{
|
||||
string CPU = name();
|
||||
|
||||
try
|
||||
{
|
||||
out.putString(CPU);
|
||||
|
||||
out.putInt(A); // Accumulator
|
||||
out.putInt(X); // X index register
|
||||
out.putInt(Y); // Y index register
|
||||
out.putInt(SP); // Stack Pointer
|
||||
out.putInt(IR); // Instruction register
|
||||
out.putInt(PC); // Program Counter
|
||||
|
||||
out.putBool(N); // N flag for processor status register
|
||||
out.putBool(V); // V flag for processor status register
|
||||
out.putBool(B); // B flag for processor status register
|
||||
out.putBool(D); // D flag for processor status register
|
||||
out.putBool(I); // I flag for processor status register
|
||||
out.putBool(notZ); // Z flag complement for processor status register
|
||||
out.putBool(C); // C flag for processor status register
|
||||
|
||||
out.putInt(myExecutionStatus);
|
||||
}
|
||||
catch(char *msg)
|
||||
{
|
||||
cerr << msg << endl;
|
||||
return false;
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
cerr << "Unknown error in save state for " << CPU << endl;
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
bool M6502Low::load(Deserializer& in)
|
||||
{
|
||||
string CPU = name();
|
||||
|
||||
try
|
||||
{
|
||||
if(in.getString() != CPU)
|
||||
return false;
|
||||
|
||||
A = (uInt8) in.getInt(); // Accumulator
|
||||
X = (uInt8) in.getInt(); // X index register
|
||||
Y = (uInt8) in.getInt(); // Y index register
|
||||
SP = (uInt8) in.getInt(); // Stack Pointer
|
||||
IR = (uInt8) in.getInt(); // Instruction register
|
||||
PC = (uInt16) in.getInt(); // Program Counter
|
||||
|
||||
N = in.getBool(); // N flag for processor status register
|
||||
V = in.getBool(); // V flag for processor status register
|
||||
B = in.getBool(); // B flag for processor status register
|
||||
D = in.getBool(); // D flag for processor status register
|
||||
I = in.getBool(); // I flag for processor status register
|
||||
notZ = in.getBool(); // Z flag complement for processor status register
|
||||
C = in.getBool(); // C flag for processor status register
|
||||
|
||||
myExecutionStatus = (uInt8) in.getInt();
|
||||
}
|
||||
catch(char *msg)
|
||||
{
|
||||
cerr << msg << endl;
|
||||
return false;
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
cerr << "Unknown error in load state for " << CPU << endl;
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
const char* M6502Low::name() const
|
||||
{
|
||||
return "M6502Low";
|
||||
}
|
|
@ -0,0 +1,119 @@
|
|||
//============================================================================
|
||||
//
|
||||
// MM MM 6666 555555 0000 2222
|
||||
// MMMM MMMM 66 66 55 00 00 22 22
|
||||
// MM MMM MM 66 55 00 00 22
|
||||
// MM M MM 66666 55555 00 00 22222 -- "A 6502 Microprocessor Emulator"
|
||||
// MM MM 66 66 55 00 00 22
|
||||
// MM MM 66 66 55 55 00 00 22
|
||||
// MM MM 6666 5555 0000 222222
|
||||
//
|
||||
// Copyright (c) 1995-2005 by Bradford W. Mott and the Stella team
|
||||
//
|
||||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: M6502Low.hxx,v 1.5 2006-02-05 02:49:47 stephena Exp $
|
||||
//============================================================================
|
||||
|
||||
#ifndef M6502LOW_HXX
|
||||
#define M6502LOW_HXX
|
||||
|
||||
class M6502Low;
|
||||
class Serializer;
|
||||
class Deserializer;
|
||||
|
||||
#include "bspf.hxx"
|
||||
#include "M6502.hxx"
|
||||
|
||||
/**
|
||||
This class provides a low compatibility 6502 microprocessor emulator.
|
||||
The memory accesses and cycle updates of this emulator are not 100%
|
||||
accurate as shown below:
|
||||
|
||||
1. Only memory accesses which are actually needed are done
|
||||
(i.e. no "false" reads and writes are performed)
|
||||
|
||||
2. Cycle counts are updated at the beginning of the instruction
|
||||
execution and not valid at the sub-instruction level
|
||||
|
||||
If speed is the most important issue then use this class, however, if
|
||||
better compatibility is neccessary use one of the other 6502 classes.
|
||||
|
||||
@author Bradford W. Mott
|
||||
@version $Id: M6502Low.hxx,v 1.5 2006-02-05 02:49:47 stephena Exp $
|
||||
*/
|
||||
class M6502Low : public M6502
|
||||
{
|
||||
public:
|
||||
/**
|
||||
Create a new low compatibility 6502 microprocessor with the specified
|
||||
cycle multiplier.
|
||||
|
||||
@param systemCyclesPerProcessorCycle The cycle multiplier
|
||||
*/
|
||||
M6502Low(uInt32 systemCyclesPerProcessorCycle);
|
||||
|
||||
/**
|
||||
Destructor
|
||||
*/
|
||||
virtual ~M6502Low();
|
||||
|
||||
public:
|
||||
/**
|
||||
Execute instructions until the specified number of instructions
|
||||
is executed, someone stops execution, or an error occurs. Answers
|
||||
true iff execution stops normally.
|
||||
|
||||
@param number Indicates the number of instructions to execute
|
||||
@return true iff execution stops normally
|
||||
*/
|
||||
virtual bool execute(uInt32 number);
|
||||
|
||||
/**
|
||||
Saves the current state of this device to the given Serializer.
|
||||
|
||||
@param out The serializer device to save to.
|
||||
@return The result of the save. True on success, false on failure.
|
||||
*/
|
||||
virtual bool save(Serializer& out);
|
||||
|
||||
/**
|
||||
Loads the current state of this device from the given Deserializer.
|
||||
|
||||
@param in The deserializer device to load from.
|
||||
@return The result of the load. True on success, false on failure.
|
||||
*/
|
||||
virtual bool load(Deserializer& in);
|
||||
|
||||
/**
|
||||
Get a null terminated string which is the processors's name (i.e. "M6532")
|
||||
|
||||
@return The name of the device
|
||||
*/
|
||||
virtual const char* name() const;
|
||||
|
||||
protected:
|
||||
/**
|
||||
Called after an interrupt has be requested using irq() or nmi()
|
||||
*/
|
||||
void interruptHandler();
|
||||
|
||||
protected:
|
||||
/*
|
||||
Get the byte at the specified address
|
||||
|
||||
@return The byte at the specified address
|
||||
*/
|
||||
inline uInt8 peek(uInt16 address);
|
||||
|
||||
/**
|
||||
Change the byte at the specified address to the given value
|
||||
|
||||
@param address The address where the value should be stored
|
||||
@param value The value to be stored at the address
|
||||
*/
|
||||
inline void poke(uInt16 address, uInt8 value);
|
||||
};
|
||||
#endif
|
||||
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,286 @@
|
|||
//============================================================================
|
||||
//
|
||||
// MM MM 6666 555555 0000 2222
|
||||
// MMMM MMMM 66 66 55 00 00 22 22
|
||||
// MM MMM MM 66 55 00 00 22
|
||||
// MM M MM 66666 55555 00 00 22222 -- "A 6502 Microprocessor Emulator"
|
||||
// MM MM 66 66 55 00 00 22
|
||||
// MM MM 66 66 55 55 00 00 22
|
||||
// MM MM 6666 5555 0000 222222
|
||||
//
|
||||
// Copyright (c) 1995-2005 by Bradford W. Mott and the Stella team
|
||||
//
|
||||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: M6502Low.m4,v 1.4 2006-02-05 02:49:47 stephena Exp $
|
||||
//============================================================================
|
||||
|
||||
/**
|
||||
Code to handle addressing modes and branch instructions for
|
||||
low compatibility emulation
|
||||
|
||||
@author Bradford W. Mott
|
||||
@version $Id: M6502Low.m4,v 1.4 2006-02-05 02:49:47 stephena Exp $
|
||||
*/
|
||||
|
||||
#ifndef NOTSAMEPAGE
|
||||
#define NOTSAMEPAGE(_addr1, _addr2) (((_addr1) ^ (_addr2)) & 0xff00)
|
||||
#endif
|
||||
|
||||
define(M6502_IMPLIED, `{
|
||||
}')
|
||||
|
||||
define(M6502_IMMEDIATE_READ, `{
|
||||
operandAddress = PC++;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTE_READ, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTE_WRITE, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTE_READMODIFYWRITE, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTEX_READ, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
|
||||
// See if we need to add one cycle for indexing across a page boundary
|
||||
if(NOTSAMEPAGE(operandAddress, operandAddress + X))
|
||||
{
|
||||
mySystem->incrementCycles(mySystemCyclesPerProcessorCycle);
|
||||
}
|
||||
|
||||
operandAddress += X;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTEX_WRITE, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
operandAddress += X;
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTEX_READMODIFYWRITE, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
operandAddress += X;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTEY_READ, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
|
||||
// See if we need to add one cycle for indexing across a page boundary
|
||||
if(NOTSAMEPAGE(operandAddress, operandAddress + Y))
|
||||
{
|
||||
mySystem->incrementCycles(mySystemCyclesPerProcessorCycle);
|
||||
}
|
||||
|
||||
operandAddress += Y;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTEY_WRITE, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
operandAddress += Y;
|
||||
}')
|
||||
|
||||
define(M6502_ABSOLUTEY_READMODIFYWRITE, `{
|
||||
operandAddress = (uInt16)peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
operandAddress += Y;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ZERO_READ, `{
|
||||
operandAddress = peek(PC++);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ZERO_WRITE, `{
|
||||
operandAddress = peek(PC++);
|
||||
}')
|
||||
|
||||
define(M6502_ZERO_READMODIFYWRITE, `{
|
||||
operandAddress = peek(PC++);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ZEROX_READ, `{
|
||||
operandAddress = (uInt8)(peek(PC++) + X);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ZEROX_WRITE, `{
|
||||
operandAddress = (uInt8)(peek(PC++) + X);
|
||||
}')
|
||||
|
||||
define(M6502_ZEROX_READMODIFYWRITE, `{
|
||||
operandAddress = (uInt8)(peek(PC++) + X);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ZEROY_READ, `{
|
||||
operandAddress = (uInt8)(peek(PC++) + Y);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_ZEROY_WRITE, `{
|
||||
operandAddress = (uInt8)(peek(PC++) + Y);
|
||||
}')
|
||||
|
||||
define(M6502_ZEROY_READMODIFYWRITE, `{
|
||||
operandAddress = (uInt8)(peek(PC++) + Y);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_INDIRECT, `{
|
||||
uInt16 addr = peek(PC) | ((uInt16)peek(PC + 1) << 8);
|
||||
PC += 2;
|
||||
|
||||
// Simulate the error in the indirect addressing mode!
|
||||
uInt16 high = NOTSAMEPAGE(addr, addr + 1) ? (addr & 0xff00) : (addr + 1);
|
||||
|
||||
operandAddress = peek(addr) | ((uInt16)peek(high) << 8);
|
||||
}')
|
||||
|
||||
define(M6502_INDIRECTX_READ, `{
|
||||
uInt8 pointer = peek(PC++) + X;
|
||||
operandAddress = peek(pointer) | ((uInt16)peek(pointer + 1) << 8);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_INDIRECTX_WRITE, `{
|
||||
uInt8 pointer = peek(PC++) + X;
|
||||
operandAddress = peek(pointer) | ((uInt16)peek(pointer + 1) << 8);
|
||||
}')
|
||||
|
||||
define(M6502_INDIRECTX_READMODIFYWRITE, `{
|
||||
uInt8 pointer = peek(PC++) + X;
|
||||
operandAddress = peek(pointer) | ((uInt16)peek(pointer + 1) << 8);
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_INDIRECTY_READ, `{
|
||||
uInt8 pointer = peek(PC++);
|
||||
operandAddress = (uInt16)peek(pointer) | ((uInt16)peek(pointer + 1) << 8);
|
||||
|
||||
if(NOTSAMEPAGE(operandAddress, operandAddress + Y))
|
||||
{
|
||||
mySystem->incrementCycles(mySystemCyclesPerProcessorCycle);
|
||||
}
|
||||
|
||||
operandAddress += Y;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
define(M6502_INDIRECTY_WRITE, `{
|
||||
uInt8 pointer = peek(PC++);
|
||||
operandAddress = (uInt16)peek(pointer) | ((uInt16)peek(pointer + 1) << 8);
|
||||
operandAddress += Y;
|
||||
}')
|
||||
|
||||
define(M6502_INDIRECTY_READMODIFYWRITE, `{
|
||||
uInt8 pointer = peek(PC++);
|
||||
operandAddress = (uInt16)peek(pointer) | ((uInt16)peek(pointer + 1) << 8);
|
||||
operandAddress += Y;
|
||||
operand = peek(operandAddress);
|
||||
}')
|
||||
|
||||
|
||||
define(M6502_BCC, `{
|
||||
if(!C)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
define(M6502_BCS, `{
|
||||
if(C)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
define(M6502_BEQ, `{
|
||||
if(!notZ)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
define(M6502_BMI, `{
|
||||
if(N)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
define(M6502_BNE, `{
|
||||
if(notZ)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
define(M6502_BPL, `{
|
||||
if(!N)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
define(M6502_BVC, `{
|
||||
if(!V)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
define(M6502_BVS, `{
|
||||
if(V)
|
||||
{
|
||||
uInt16 address = PC + (Int8)operand;
|
||||
mySystem->incrementCycles(NOTSAMEPAGE(PC, address) ?
|
||||
mySystemCyclesPerProcessorCycle << 1 : mySystemCyclesPerProcessorCycle);
|
||||
PC = address;
|
||||
}
|
||||
}')
|
||||
|
||||
|
|
@ -13,7 +13,7 @@
|
|||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: System.cxx,v 1.16 2005-12-29 21:16:28 stephena Exp $
|
||||
// $Id: System.cxx,v 1.17 2006-02-05 02:49:47 stephena Exp $
|
||||
//============================================================================
|
||||
|
||||
#include <assert.h>
|
||||
|
@ -318,8 +318,10 @@ uInt8 System::peek(uInt16 addr)
|
|||
result = access.device->peek(addr);
|
||||
}
|
||||
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
if(!myDataBusLocked)
|
||||
myDataBusState = result;
|
||||
#endif
|
||||
|
||||
return result;
|
||||
}
|
||||
|
@ -339,8 +341,10 @@ void System::poke(uInt16 addr, uInt8 value)
|
|||
access.device->poke(addr, value);
|
||||
}
|
||||
|
||||
#ifdef DEVELOPER_SUPPORT
|
||||
if(!myDataBusLocked)
|
||||
myDataBusState = value;
|
||||
#endif
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
|
@ -354,4 +358,3 @@ void System::unlockDataBus()
|
|||
{
|
||||
myDataBusLocked = false;
|
||||
}
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: System.hxx,v 1.12 2005-12-09 19:09:49 stephena Exp $
|
||||
// $Id: System.hxx,v 1.13 2006-02-05 02:49:47 stephena Exp $
|
||||
//============================================================================
|
||||
|
||||
#ifndef SYSTEM_HXX
|
||||
|
@ -47,7 +47,7 @@ class Deserializer;
|
|||
dynamic code for that page of memory.
|
||||
|
||||
@author Bradford W. Mott
|
||||
@version $Id: System.hxx,v 1.12 2005-12-09 19:09:49 stephena Exp $
|
||||
@version $Id: System.hxx,v 1.13 2006-02-05 02:49:47 stephena Exp $
|
||||
*/
|
||||
class System
|
||||
{
|
||||
|
@ -207,7 +207,7 @@ class System
|
|||
|
||||
@return The number of system cycles which have passed
|
||||
*/
|
||||
uInt32 cycles() const
|
||||
inline uInt32 cycles() const
|
||||
{
|
||||
return myCycles;
|
||||
}
|
||||
|
@ -217,7 +217,7 @@ class System
|
|||
|
||||
@param amount The amount to add to the system cycles counter
|
||||
*/
|
||||
void incrementCycles(uInt32 amount)
|
||||
inline void incrementCycles(uInt32 amount)
|
||||
{
|
||||
myCycles += amount;
|
||||
}
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
// See the file "license" for information on usage and redistribution of
|
||||
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||||
//
|
||||
// $Id: SettingsGP2X.cxx,v 1.4 2006-01-30 01:01:44 stephena Exp $
|
||||
// $Id: SettingsGP2X.cxx,v 1.5 2006-02-05 02:49:46 stephena Exp $
|
||||
// Modified on 2006/01/04 by Alex Zaballa for use on GP2X
|
||||
//============================================================================
|
||||
|
||||
|
@ -35,7 +35,8 @@ SettingsGP2X::SettingsGP2X(OSystem* osystem)
|
|||
set("tiafreq", "22050");
|
||||
set("clipvol", "false");
|
||||
set("joymouse", "true");
|
||||
set("pp", "no"); // always disable phosphor until we get a faster framebuffer
|
||||
set("pp", "no"); // always disable phosphor until we get a faster framebuffer
|
||||
set("cpu", "low"); // use lower-compatibility CPU emulation for more speed
|
||||
}
|
||||
|
||||
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
|
|
Loading…
Reference in New Issue