Войти
Life Engine

Hardcore wanted::Начал писать эмулятор Famicom (DENDY)

Автор:

Софтрендеры, рейтрейсеры и прочее раньше казались весьма хардкорными!  Казались.. до того, пока в них не разобрался и не написал.  После написания  они стали казаться весьма и весьма простыми : \ 

Подумал я, что надо написать что-то чуть более хардкорное : )  Да не просто потратить на это время, а выучить что-то новое. В этот момент пришла в голову безуслоооовно гениальная идея - написать эмулятор NES (DENDY).    Я не застал ZxSpectrum и подобные "компьютеры" - поэтому NES для меня была самой первой и самой "слабой" игровой приставкой.  Вот и решил, что надо начинать с простого, с денди )

С простого.. ага, щас.  Железо.. процессор.. какието прерывания.. страницы памяти.. memory mapping, memory mirroring, какието опкоды, циклы, PPU, APU  и прочая куча всяких мтерных слов.  ЧТОЭТО!?  ААА!! - такое было первое впечатление.  Начал писать я позавчера ^^

Но не всё так плохо ) То, что я чего-то не знаю - вообще ничего не решает, ведь под рукой есть инет и теперь книги Владислава Пирогова :D  Узнать можно что угодно в считанные секунды/минуты. С пониманием информации вроде всё ок.  Так, понемногу раскуриваю ассемблер, принципы работы железа и саму игровую приставку : ) Раскуривание пошло весьма удачно, надо отметить )

Сегодня в голове собрался весь паззл (асм, железо, устройство денди) и, придя под вечер домой начал писать )

Сейчас есть загрузка ROM-а игры. Есть базовая структура классов. Накидал работу с памятью (scratch ram, save ram, prg_rom, chr_rom) , работу со стеком (кстати он зачемто развёрнут в денди! Ну тоесть push в стек  сопровождается _декрементом указателя на память стека, а pop инкрементом >_<), написал пустые функции обработки опкодов, заполнил массив lookup-а функций обработки опкодов (самое мозговыносящее блин), написал обработку некоторых опкодов и прерываний!


функция апдейта процессора выглядит сейчас так:

void CPU::Update()
{
  //store previous opcode
  opcode_previous = opcode_current;
  //read next opcode
  opcode_current = pNes->ReadMemory8(reg_pc);
  //execute opcode
  (this->*opcodes[opcode_current])();

  //count cycles
  cycle_total += cycle_local;

  if(cycle_local >= pNes->cyclesPerScanline)
  {
    //render scan line HERE
    //push PC register to stack
    //push state register to stack

    //process NMI interrupt
    reg_pc = pNes->ReadMemory16(0xFFFA);

    cycle_local -= pNes->cyclesPerScanline;
  }
}


Я обязательно допилю этот эмулятор : )  Не знаю насколько он будет совместим с большинством игр, но в марио на нём точно можно будет играть ))

Ладно, сейчас надо идти спать, а завтра если будет время - описать работу почти 150 опкодов  : ((((

17 сентября 2011

Комментарии [249]