"Fossies" - the Fresh Open Source Software Archive

Member "stella-6.0.2/src/emucore/Cart3F.cxx" (11 Oct 2019, 5173 Bytes) of package /linux/privat/stella-6.0.2-src.tar.xz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "Cart3F.cxx" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 6.0.1_vs_6.0.2.

    1 //============================================================================
    2 //
    3 //   SSSS    tt          lll  lll
    4 //  SS  SS   tt           ll   ll
    5 //  SS     tttttt  eeee   ll   ll   aaaa
    6 //   SSSS    tt   ee  ee  ll   ll      aa
    7 //      SS   tt   eeeeee  ll   ll   aaaaa  --  "An Atari 2600 VCS Emulator"
    8 //  SS  SS   tt   ee      ll   ll  aa  aa
    9 //   SSSS     ttt  eeeee llll llll  aaaaa
   10 //
   11 // Copyright (c) 1995-2019 by Bradford W. Mott, Stephen Anthony
   12 // and the Stella Team
   13 //
   14 // See the file "License.txt" for information on usage and redistribution of
   15 // this file, and for a DISCLAIMER OF ALL WARRANTIES.
   16 //============================================================================
   17 
   18 #include "System.hxx"
   19 #include "TIA.hxx"
   20 #include "Cart3F.hxx"
   21 
   22 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
   23 Cartridge3F::Cartridge3F(const BytePtr& image, uInt32 size,
   24                          const string& md5, const Settings& settings)
   25   : Cartridge(settings, md5),
   26     mySize(size),
   27     myCurrentBank(0)
   28 {
   29   // Allocate array for the ROM image
   30   myImage = make_unique<uInt8[]>(mySize);
   31 
   32   // Copy the ROM image into my buffer
   33   memcpy(myImage.get(), image.get(), mySize);
   34   createCodeAccessBase(mySize);
   35 }
   36 
   37 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
   38 void Cartridge3F::reset()
   39 {
   40   initializeStartBank(bankCount() - 1);
   41 
   42   bank(startBank());
   43 }
   44 
   45 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
   46 void Cartridge3F::install(System& system)
   47 {
   48   mySystem = &system;
   49 
   50   System::PageAccess access(this, System::PA_READWRITE);
   51 
   52   // The hotspot ($3F) is in TIA address space, so we claim it here
   53   for(uInt16 addr = 0x00; addr < 0x40; addr += System::PAGE_SIZE)
   54     mySystem->setPageAccess(addr, access);
   55 
   56   // Setup the second segment to always point to the last ROM slice
   57   access.type = System::PA_READ;
   58   for(uInt16 addr = 0x1800; addr < 0x2000; addr += System::PAGE_SIZE)
   59   {
   60     access.directPeekBase = &myImage[(mySize - 2048) + (addr & 0x07FF)];
   61     access.codeAccessBase = &myCodeAccessBase[(mySize - 2048) + (addr & 0x07FF)];
   62     mySystem->setPageAccess(addr, access);
   63   }
   64 
   65   bank(startBank());
   66 }
   67 
   68 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
   69 uInt8 Cartridge3F::peek(uInt16 address)
   70 {
   71   address &= 0x0FFF;
   72 
   73   if(address < 0x0800)
   74     return myImage[(address & 0x07FF) + (myCurrentBank << 11)];
   75   else
   76     return myImage[(address & 0x07FF) + mySize - 2048];
   77 }
   78 
   79 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
   80 bool Cartridge3F::poke(uInt16 address, uInt8 value)
   81 {
   82   address &= 0x0FFF;
   83 
   84   // Switch banks if necessary
   85   if(address <= 0x003F)
   86     bank(value);
   87 
   88   // Handle TIA space that we claimed above
   89   mySystem->tia().poke(address, value);
   90 
   91   return false;
   92 }
   93 
   94 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
   95 bool Cartridge3F::bank(uInt16 bank)
   96 {
   97   if(bankLocked())
   98     return false;
   99 
  100   // Make sure the bank they're asking for is reasonable
  101   if((uInt32(bank) << 11) < mySize)
  102   {
  103     myCurrentBank = bank;
  104   }
  105   else
  106   {
  107     // Oops, the bank they're asking for isn't valid so let's wrap it
  108     // around to a valid bank number
  109     myCurrentBank = bank % (mySize >> 11);
  110   }
  111 
  112   uInt32 offset = myCurrentBank << 11;
  113 
  114   // Setup the page access methods for the current bank
  115   System::PageAccess access(this, System::PA_READ);
  116 
  117   // Map ROM image into the system
  118   for(uInt16 addr = 0x1000; addr < 0x1800; addr += System::PAGE_SIZE)
  119   {
  120     access.directPeekBase = &myImage[offset + (addr & 0x07FF)];
  121     access.codeAccessBase = &myCodeAccessBase[offset + (addr & 0x07FF)];
  122     mySystem->setPageAccess(addr, access);
  123   }
  124   return myBankChanged = true;
  125 }
  126 
  127 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  128 uInt16 Cartridge3F::getBank() const
  129 {
  130   return myCurrentBank;
  131 }
  132 
  133 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  134 uInt16 Cartridge3F::bankCount() const
  135 {
  136   return mySize >> 11;
  137 }
  138 
  139 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  140 bool Cartridge3F::patch(uInt16 address, uInt8 value)
  141 {
  142   address &= 0x0FFF;
  143 
  144   if(address < 0x0800)
  145     myImage[(address & 0x07FF) + (myCurrentBank << 11)] = value;
  146   else
  147     myImage[(address & 0x07FF) + mySize - 2048] = value;
  148 
  149   return myBankChanged = true;
  150 }
  151 
  152 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  153 const uInt8* Cartridge3F::getImage(uInt32& size) const
  154 {
  155   size = mySize;
  156   return myImage.get();
  157 }
  158 
  159 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  160 bool Cartridge3F::save(Serializer& out) const
  161 {
  162   try
  163   {
  164     out.putShort(myCurrentBank);
  165   }
  166   catch(...)
  167   {
  168     cerr << "ERROR: Cartridge3F::save" << endl;
  169     return false;
  170   }
  171 
  172   return true;
  173 }
  174 
  175 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  176 bool Cartridge3F::load(Serializer& in)
  177 {
  178   try
  179   {
  180     myCurrentBank = in.getShort();
  181   }
  182   catch(...)
  183   {
  184     cerr << "ERROR: Cartridge3F::load" << endl;
  185     return false;
  186   }
  187 
  188   // Now, go to the current bank
  189   bank(myCurrentBank);
  190 
  191   return true;
  192 }