libsidplayfp 1.0.3
mos6510.h
00001 /*
00002  * This file is part of libsidplayfp, a SID player engine.
00003  *
00004  * Copyright 2011-2013 Leandro Nini <drfiemost@users.sourceforge.net>
00005  * Copyright 2007-2010 Antti Lankila
00006  * Copyright 2000 Simon White
00007  *
00008  * This program is free software; you can redistribute it and/or modify
00009  * it under the terms of the GNU General Public License as published by
00010  * the Free Software Foundation; either version 2 of the License, or
00011  * (at your option) any later version.
00012  *
00013  * This program is distributed in the hope that it will be useful,
00014  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00015  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00016  * GNU General Public License for more details.
00017  *
00018  * You should have received a copy of the GNU General Public License
00019  * along with this program; if not, write to the Free Software
00020  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
00021  */
00022 
00023 #ifndef MOS6510_H
00024 #define MOS6510_H
00025 
00026 #include <stdio.h>
00027 #include <stdint.h>
00028 
00029 #include "sidplayfp/sidendian.h"
00030 #include "sidplayfp/component.h"
00031 #include "sidplayfp/EventScheduler.h"
00032 
00033 #ifdef HAVE_CONFIG_H
00034 #  include "config.h"
00035 #endif
00036 
00046 class MOS6510
00047 {
00048     friend class MOS6510Debug;
00049 private:
00050     static const char *credit;
00051 
00052 private:
00058     static const int MAX = 65536;
00059 
00061     static const uint8_t SP_PAGE = 0x01;
00062 
00063 public:
00065     static const int SR_INTERRUPT = 2;
00066 
00067 protected:
00068     struct ProcessorCycle
00069     {
00070         void (MOS6510::*func)();
00071         bool nosteal;
00072         ProcessorCycle () :
00073             func(0),
00074             nosteal(false) {}
00075     };
00076 
00077 protected:
00079     EventContext &eventContext;
00080 
00082     int cycleCount;
00083 
00085     int interruptCycle;
00086 
00088     bool irqAssertedOnPin;
00089 
00091     bool nmiFlag;
00092 
00094     bool rstFlag;
00095 
00097     bool rdy;
00098 
00099     bool flagN;
00100     bool flagC;
00101     bool flagD;
00102     bool flagZ;
00103     bool flagV;
00104     bool flagI;
00105     bool flagB;
00106 
00108     uint_least16_t Register_ProgramCounter;
00109     uint_least16_t Cycle_EffectiveAddress;
00110     uint_least16_t Cycle_HighByteWrongEffectiveAddress;
00111     uint_least16_t Cycle_Pointer;
00112 
00113     uint8_t Cycle_Data;
00114     uint8_t Register_StackPointer;
00115     uint8_t Register_Accumulator;
00116     uint8_t Register_X;
00117     uint8_t Register_Y;
00118 
00119 #ifdef DEBUG
00120 
00121     uint_least16_t instrStartPC;
00122     uint_least16_t instrOperand;
00123 
00124     FILE *m_fdbg;
00125 
00126     bool dodump;
00127 #endif
00128 
00130     struct ProcessorCycle  instrTable[0x101 << 3];
00131 
00132 protected:
00133     MOS6510(EventContext *context);
00134     ~MOS6510() {}
00135 
00137     EventCallback<MOS6510> m_nosteal;
00138 
00140     EventCallback<MOS6510> m_steal;
00141 
00142     void eventWithoutSteals();
00143     void eventWithSteals();
00144 
00145     void Initialise();
00146 
00147     // Flag utility functions
00148     inline void setFlagsNZ(uint8_t value);
00149     inline uint8_t getStatusRegister();
00150     inline void setStatusRegister(uint8_t sr);
00151 
00152     // Declare Interrupt Routines
00153     inline void IRQLoRequest();
00154     inline void IRQHiRequest();
00155     inline void interruptsAndNextOpcode();
00156     inline void calculateInterruptTriggerCycle();
00157 
00158     // Declare Instruction Routines
00159     inline void fetchNextOpcode();
00160     inline void throwAwayFetch();
00161     inline void throwAwayRead();
00162     inline void FetchDataByte();
00163     inline void FetchLowAddr();
00164     inline void FetchLowAddrX();
00165     inline void FetchLowAddrY();
00166     inline void FetchHighAddr();
00167     inline void FetchHighAddrX();
00168     inline void FetchHighAddrX2();
00169     inline void FetchHighAddrY();
00170     inline void FetchHighAddrY2();
00171     inline void FetchLowEffAddr();
00172     inline void FetchHighEffAddr();
00173     inline void FetchHighEffAddrY();
00174     inline void FetchHighEffAddrY2();
00175     inline void FetchLowPointer();
00176     inline void FetchLowPointerX();
00177     inline void FetchHighPointer();
00178     inline void FetchEffAddrDataByte ();
00179     inline void PutEffAddrDataByte();
00180     inline void PushLowPC();
00181     inline void PushHighPC();
00182     inline void PushSR();
00183     inline void PopLowPC();
00184     inline void PopHighPC();
00185     inline void PopSR();
00186     inline void brkPushLowPC();
00187     inline void WasteCycle();
00188 
00189     // Delcare Instruction Operation Routines
00190     inline void adc_instr();
00191     inline void alr_instr();
00192     inline void anc_instr();
00193     inline void and_instr();
00194     inline void ane_instr();
00195     inline void arr_instr();
00196     inline void asl_instr();
00197     inline void asla_instr();
00198     inline void aso_instr();
00199     inline void axa_instr();
00200     inline void axs_instr();
00201     inline void bcc_instr();
00202     inline void bcs_instr();
00203     inline void beq_instr();
00204     inline void bit_instr();
00205     inline void bmi_instr();
00206     inline void bne_instr();
00207     inline void branch_instr(bool condition);
00208     inline void bpl_instr();
00209     inline void brk_instr();
00210     inline void bvc_instr();
00211     inline void bvs_instr();
00212     inline void clc_instr();
00213     inline void cld_instr();
00214     inline void cli_instr();
00215     inline void clv_instr();
00216     inline void cmp_instr();
00217     inline void cpx_instr();
00218     inline void cpy_instr();
00219     inline void dcm_instr();
00220     inline void dec_instr();
00221     inline void dex_instr();
00222     inline void dey_instr();
00223     inline void eor_instr();
00224     inline void inc_instr();
00225     inline void ins_instr();
00226     inline void inx_instr();
00227     inline void iny_instr();
00228     inline void jmp_instr();
00229     inline void las_instr();
00230     inline void lax_instr();
00231     inline void lda_instr();
00232     inline void ldx_instr();
00233     inline void ldy_instr();
00234     inline void lse_instr();
00235     inline void lsr_instr();
00236     inline void lsra_instr();
00237     inline void oal_instr();
00238     inline void ora_instr();
00239     inline void pha_instr();
00240     inline void pla_instr();
00241     inline void plp_instr();
00242     inline void rla_instr();
00243     inline void rol_instr();
00244     inline void rola_instr();
00245     inline void ror_instr();
00246     inline void rora_instr();
00247     inline void rra_instr();
00248     inline void rti_instr();
00249     inline void rts_instr();
00250     inline void sbx_instr();
00251     inline void say_instr();
00252     inline void sbc_instr();
00253     inline void sec_instr();
00254     inline void sed_instr();
00255     inline void sei_instr();
00256     inline void shs_instr();
00257     inline void sta_instr();
00258     inline void stx_instr();
00259     inline void sty_instr();
00260     inline void tax_instr();
00261     inline void tay_instr();
00262     inline void tsx_instr();
00263     inline void txa_instr();
00264     inline void txs_instr();
00265     inline void tya_instr();
00266     inline void xas_instr();
00267 
00268     void  illegal_instr();
00269 
00270     // Declare Arithmetic Operations
00271     inline void doADC();
00272     inline void doSBC();
00273 
00274     inline void doJSR();
00275 
00276 public:
00283     virtual uint8_t cpuRead(uint_least16_t addr) =0;
00284 
00291     virtual void cpuWrite(uint_least16_t addr, uint8_t data) =0;
00292 
00293 #ifdef PC64_TESTSUITE
00294     virtual void   loadFile (const char *file) =0;
00295 #endif
00296 
00297     virtual void reset();
00298 
00299     const char  *credits() const { return credit; }
00300 
00301     void debug(bool enable, FILE *out);
00302     void setRDY(bool newRDY);
00303 
00304     // Non-standard functions
00305     void triggerRST();
00306     void triggerNMI();
00307     void triggerIRQ();
00308     void clearIRQ();
00309 };
00310 
00311 #endif // MOS6510_H