2025-06-27 00:32:57 +08:00
|
|
|
|
#include "main.h"
|
|
|
|
|
#include "stm32f4xx.h"
|
|
|
|
|
#include "nes_main.h"
|
|
|
|
|
#include "nes_ppu.h"
|
|
|
|
|
#include "nes_mapper.h"
|
|
|
|
|
#include "nes_apu.h"
|
|
|
|
|
#include "mymem.h"
|
|
|
|
|
#include "dac.h"
|
|
|
|
|
|
|
|
|
|
#include "ff.h"
|
|
|
|
|
#include "string.h"
|
|
|
|
|
//////////////////////////////////////////////////////////////////////////////////
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ֲ<EFBFBD><D6B2><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ye781205<30><35>NESģ<53><C4A3><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
//ALIENTEK STM32F407<30><37><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
//NES<45><53><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>
|
|
|
|
|
//<2F><><EFBFBD><EFBFBD>ԭ<EFBFBD><D4AD>@ALIENTEK
|
|
|
|
|
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>̳:www.openedv.com
|
|
|
|
|
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>:2014/7/1
|
|
|
|
|
//<2F>汾<EFBFBD><E6B1BE>V1.0
|
2025-06-27 00:32:57 +08:00
|
|
|
|
//////////////////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
u8 nes_frame_cnt; //nes֡<73><D6A1><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
int MapperNo; //map<61><70><EFBFBD><EFBFBD>
|
|
|
|
|
int NES_scanline; //nesɨ<73><C9A8><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
int VROM_1K_SIZE;
|
|
|
|
|
int VROM_8K_SIZE;
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
u8 PADdata; //<2F>ֱ<EFBFBD>1<EFBFBD><31>ֵ [7:0]<5D><>7 <20><>6 <20><>5 <20><>4 Start3 Select2 B1 A0
|
|
|
|
|
u8 PADdata1; //<2F>ֱ<EFBFBD>2<EFBFBD><32>ֵ [7:0]<5D><>7 <20><>6 <20><>5 <20><>4 Start3 Select2 B1 A0
|
|
|
|
|
u8 *NES_RAM; //<2F><><EFBFBD><EFBFBD>1024<32>ֽڶ<D6BD><DAB6><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u8 *NES_SRAM;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
NES_header *RomHeader; //rom<6F>ļ<EFBFBD>ͷ
|
2025-06-27 00:32:57 +08:00
|
|
|
|
MAPPER *NES_Mapper;
|
|
|
|
|
MapperCommRes *MAPx;
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
u8* spr_ram; //<2F><><EFBFBD><EFBFBD>RAM,256<35>ֽ<EFBFBD>
|
|
|
|
|
ppu_data* ppu; //ppuָ<75><D6B8>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u8* VROM_banks;
|
|
|
|
|
u8* VROM_tiles;
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
apu_t *apu; //apuָ<75><D6B8>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u16 *wave_buffers;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
u16 *i2sbuf1; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>֡,ռ<><D5BC><EFBFBD>ڴ<EFBFBD><DAB4><EFBFBD> 367*4 <20>ֽ<EFBFBD>@22050Hz
|
|
|
|
|
u16 *i2sbuf2; //<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>֡,ռ<><D5BC><EFBFBD>ڴ<EFBFBD><DAB4><EFBFBD> 367*4 <20>ֽ<EFBFBD>@22050Hz
|
2025-06-27 00:32:57 +08:00
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
u8* romfile; //nes<65>ļ<EFBFBD>ָ<EFBFBD><D6B8>,ָ<><D6B8><EFBFBD><EFBFBD><EFBFBD><EFBFBD>nes<65>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD><EFBFBD>ʼ<EFBFBD><CABC>ַ.
|
2025-06-27 00:32:57 +08:00
|
|
|
|
//////////////////////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><>¼nes<65>Ƿ<EFBFBD><C7B7><EFBFBD>Ҫ<EFBFBD><D2AA><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
static u8 g_nes_break=0;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><><EFBFBD><EFBFBD>ROM
|
|
|
|
|
//<2F><><EFBFBD><EFBFBD>ֵ:0,<2C>ɹ<EFBFBD>
|
|
|
|
|
// 1,<2C>ڴ<EFBFBD><DAB4><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
// 3,map<61><70><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u8 nes_load_rom(void)
|
|
|
|
|
{
|
|
|
|
|
u8* p;
|
|
|
|
|
u8 i;
|
|
|
|
|
u8 res=0;
|
|
|
|
|
p=(u8*)romfile;
|
|
|
|
|
if(strncmp((char*)p,"NES",3)==0)
|
|
|
|
|
{
|
|
|
|
|
RomHeader->ctrl_z=p[3];
|
|
|
|
|
RomHeader->num_16k_rom_banks=p[4];
|
|
|
|
|
RomHeader->num_8k_vrom_banks=p[5];
|
|
|
|
|
RomHeader->flags_1=p[6];
|
|
|
|
|
RomHeader->flags_2=p[7];
|
2025-07-05 19:47:28 +08:00
|
|
|
|
if(RomHeader->flags_1&0x04)p+=512; //<2F><>512<31>ֽڵ<D6BD>trainer:
|
|
|
|
|
if(RomHeader->num_8k_vrom_banks>0) //<2F><><EFBFBD><EFBFBD>VROM,<2C><><EFBFBD><EFBFBD>Ԥ<EFBFBD><D4A4><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
{
|
|
|
|
|
VROM_banks=p+16+(RomHeader->num_16k_rom_banks*0x4000);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
#if NES_RAM_SPEED==1 //1:<3A>ڴ<EFBFBD>ռ<EFBFBD><D5BC>С 0:<3A>ٶȿ<D9B6>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
VROM_tiles=VROM_banks;
|
|
|
|
|
#else
|
2025-07-05 19:47:28 +08:00
|
|
|
|
VROM_tiles=mymalloc(RomHeader->num_8k_vrom_banks*8*1024);//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>1MB<4D>ڴ<EFBFBD>!!!
|
|
|
|
|
if(VROM_tiles==0)VROM_tiles=VROM_banks;//<2F>ڴ治<DAB4><E6B2BB><EFBFBD>õ<EFBFBD><C3B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>,<2C><><EFBFBD><EFBFBD>VROM_titles<65><73>VROM_banks<6B><73><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
compile(RomHeader->num_8k_vrom_banks*8*1024/16,VROM_banks,VROM_tiles);
|
|
|
|
|
#endif
|
|
|
|
|
}else
|
|
|
|
|
{
|
|
|
|
|
VROM_banks=mymalloc(8*1024);
|
|
|
|
|
VROM_tiles=mymalloc(8*1024);
|
|
|
|
|
if(!VROM_banks||!VROM_tiles)res=1;
|
|
|
|
|
}
|
|
|
|
|
VROM_1K_SIZE = RomHeader->num_8k_vrom_banks * 8;
|
|
|
|
|
VROM_8K_SIZE = RomHeader->num_8k_vrom_banks;
|
|
|
|
|
MapperNo=(RomHeader->flags_1>>4)|(RomHeader->flags_2&0xf0);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
if(RomHeader->flags_2 & 0x0E)MapperNo=RomHeader->flags_1>>4;//<2F><><EFBFBD>Ը<EFBFBD><D4B8><EFBFBD>λ<EFBFBD><CEBB><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ͷ<EFBFBD><CDB7><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
//printf("use map:%d\r\n",MapperNo);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
for(i=0;i<255;i++) // <20><><EFBFBD><EFBFBD>֧<EFBFBD>ֵ<EFBFBD>Mapper<65><72>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
{
|
|
|
|
|
if (MapTab[i]==MapperNo)break;
|
|
|
|
|
if (MapTab[i]==-1)res=3;
|
|
|
|
|
}
|
|
|
|
|
if(res==0)
|
|
|
|
|
{
|
|
|
|
|
switch(MapperNo)
|
|
|
|
|
{
|
|
|
|
|
case 1:
|
|
|
|
|
MAP1=mymalloc(sizeof(Mapper1Res));
|
|
|
|
|
if(!MAP1)res=1;
|
|
|
|
|
break;
|
|
|
|
|
case 4:
|
|
|
|
|
case 6:
|
|
|
|
|
case 16:
|
|
|
|
|
case 17:
|
|
|
|
|
case 18:
|
|
|
|
|
case 19:
|
|
|
|
|
case 21:
|
|
|
|
|
case 23:
|
|
|
|
|
case 24:
|
|
|
|
|
case 25:
|
|
|
|
|
case 64:
|
|
|
|
|
case 65:
|
|
|
|
|
case 67:
|
|
|
|
|
case 69:
|
|
|
|
|
case 85:
|
|
|
|
|
case 189:
|
|
|
|
|
MAPx=mymalloc(sizeof(MapperCommRes));
|
|
|
|
|
if(!MAPx)res=1;
|
|
|
|
|
break;
|
|
|
|
|
default:
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
return res; //<2F><><EFBFBD><EFBFBD>ִ<EFBFBD>н<EFBFBD><D0BD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><><EFBFBD><EFBFBD>NES_RAM<41><4D><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD>ʱ<EFBFBD>ĸ<EFBFBD><C4B8><EFBFBD>ָ<EFBFBD><D6B8>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void *nes_ram_alignment;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F>ͷ<EFBFBD><CDB7>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void nes_sram_free(void)
|
|
|
|
|
{
|
|
|
|
|
//myfree(NES_RAM);
|
|
|
|
|
myfree(nes_ram_alignment);
|
|
|
|
|
myfree(NES_SRAM);
|
|
|
|
|
myfree(RomHeader);
|
|
|
|
|
myfree(NES_Mapper);
|
|
|
|
|
myfree(spr_ram);
|
|
|
|
|
myfree(ppu);
|
|
|
|
|
myfree(apu);
|
|
|
|
|
myfree(wave_buffers);
|
|
|
|
|
myfree(i2sbuf1);
|
|
|
|
|
myfree(i2sbuf2);
|
|
|
|
|
myfree(romfile);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
if((VROM_tiles!=VROM_banks)&&VROM_banks&&VROM_tiles)//<2F><><EFBFBD><EFBFBD><EFBFBD>ֱ<EFBFBD>ΪVROM_banks<6B><73>VROM_tiles<65><73><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD>,<2C><><EFBFBD>ͷ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
{
|
|
|
|
|
myfree(VROM_banks);
|
|
|
|
|
myfree(VROM_tiles);
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
switch (MapperNo)//<2F>ͷ<EFBFBD>map<61>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
{
|
2025-07-05 19:47:28 +08:00
|
|
|
|
case 1: //<2F>ͷ<EFBFBD><CDB7>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
myfree(MAP1);
|
|
|
|
|
break;
|
|
|
|
|
case 4:
|
|
|
|
|
case 6:
|
|
|
|
|
case 16:
|
|
|
|
|
case 17:
|
|
|
|
|
case 18:
|
|
|
|
|
case 19:
|
|
|
|
|
case 21:
|
|
|
|
|
case 23:
|
|
|
|
|
case 24:
|
|
|
|
|
case 25:
|
|
|
|
|
case 64:
|
|
|
|
|
case 65:
|
|
|
|
|
case 67:
|
|
|
|
|
case 69:
|
|
|
|
|
case 85:
|
|
|
|
|
case 189:
|
2025-07-05 19:47:28 +08:00
|
|
|
|
myfree(MAPx);break; //<2F>ͷ<EFBFBD><CDB7>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
default:break;
|
|
|
|
|
}
|
|
|
|
|
NES_RAM=0;
|
|
|
|
|
NES_SRAM=0;
|
|
|
|
|
RomHeader=0;
|
|
|
|
|
NES_Mapper=0;
|
|
|
|
|
spr_ram=0;
|
|
|
|
|
ppu=0;
|
|
|
|
|
apu=0;
|
|
|
|
|
wave_buffers=0;
|
|
|
|
|
i2sbuf1=0;
|
|
|
|
|
i2sbuf2=0;
|
|
|
|
|
romfile=0;
|
|
|
|
|
VROM_banks=0;
|
|
|
|
|
VROM_tiles=0;
|
|
|
|
|
MAP1=0;
|
|
|
|
|
MAPx=0;
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//ΪNES<45><53><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD>
|
|
|
|
|
//romsize:nes<65>ļ<EFBFBD><C4BC><EFBFBD>С
|
|
|
|
|
//<2F><><EFBFBD><EFBFBD>ֵ:0,<2C><><EFBFBD><EFBFBD><EFBFBD>ɹ<EFBFBD>
|
|
|
|
|
// 1,<2C><><EFBFBD><EFBFBD>ʧ<EFBFBD><CAA7>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u8 nes_sram_malloc(u32 romsize)
|
|
|
|
|
{
|
|
|
|
|
u16 i=0;
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//NES_RAM<41><4D>Ҫ0x800<30><30>С<EFBFBD><D0A1><EFBFBD>ڴ棬<DAB4><E6A3AC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>0x400<30><30><EFBFBD>ڴ棬<DAB4><E6A3AC><EFBFBD><EFBFBD>1024<32>ֽڶ<D6BD><DAB6><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
nes_ram_alignment=mymalloc(0x800+0x400);
|
|
|
|
|
NES_RAM=(void*)(((u32)nes_ram_alignment+0x400)&0xfffffc00);
|
|
|
|
|
|
|
|
|
|
NES_SRAM=mymalloc(0X2000);
|
|
|
|
|
RomHeader=mymalloc(sizeof(NES_header));
|
|
|
|
|
NES_Mapper=mymalloc(sizeof(MAPPER));
|
|
|
|
|
spr_ram=mymalloc(0X100);
|
|
|
|
|
ppu=mymalloc(sizeof(ppu_data));
|
|
|
|
|
apu=mymalloc(sizeof(apu_t)); //sizeof(apu_t)= 12588
|
|
|
|
|
wave_buffers=mymalloc(APU_PCMBUF_SIZE*2);
|
|
|
|
|
i2sbuf1=mymalloc(APU_PCMBUF_SIZE*4+10);
|
|
|
|
|
i2sbuf2=mymalloc(APU_PCMBUF_SIZE*4+10);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
romfile=mymalloc(romsize); //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϸrom<6F>ռ<EFBFBD>,<2C><><EFBFBD><EFBFBD>nes<65>ļ<EFBFBD><C4BC><EFBFBD>С
|
2025-06-27 00:32:57 +08:00
|
|
|
|
if(i==64||!NES_RAM||!NES_SRAM||!RomHeader||!NES_Mapper||!spr_ram||!ppu||!apu||!wave_buffers||!i2sbuf1||!i2sbuf2||!romfile)
|
|
|
|
|
{
|
|
|
|
|
nes_sram_free();
|
|
|
|
|
return 1;
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
memset(NES_SRAM,0,0X2000); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(RomHeader,0,sizeof(NES_header)); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(NES_Mapper,0,sizeof(MAPPER)); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(spr_ram,0,0X100); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(ppu,0,sizeof(ppu_data)); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(apu,0,sizeof(apu_t)); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(wave_buffers,0,APU_PCMBUF_SIZE*2);//<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(i2sbuf1,0,APU_PCMBUF_SIZE*4+10); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(i2sbuf2,0,APU_PCMBUF_SIZE*4+10); //<2F><><EFBFBD><EFBFBD>
|
|
|
|
|
memset(romfile,0,romsize); //<2F><><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
return 0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
int nes_xoff=0; //<2F><>ʾ<EFBFBD><CABE>x<EFBFBD>᷽<EFBFBD><E1B7BD><EFBFBD><EFBFBD>ƫ<EFBFBD><C6AB><EFBFBD><EFBFBD>(ʵ<><CAB5><EFBFBD><EFBFBD>ʾ<EFBFBD><CABE><EFBFBD><EFBFBD>=256-2*nes_xoff)
|
2025-06-27 00:32:57 +08:00
|
|
|
|
int nes_yoff=0;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><>ʼnes<65><73>Ϸ
|
|
|
|
|
//pname:nes<65><73>Ϸ·<CFB7><C2B7>
|
|
|
|
|
//<2F><><EFBFBD><EFBFBD>ֵ:
|
|
|
|
|
//0,<2C><><EFBFBD><EFBFBD><EFBFBD>˳<EFBFBD>
|
|
|
|
|
//1,<2C>ڴ<EFBFBD><DAB4><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
//2,<2C>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
//3,<2C><>֧<EFBFBD>ֵ<EFBFBD>map
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u8 nes_load(u8* pname,void *lcd_addr,int x,int y)
|
|
|
|
|
{
|
|
|
|
|
nes_xoff=x;
|
|
|
|
|
nes_yoff=y;
|
|
|
|
|
FIL *file;
|
|
|
|
|
FILINFO *file_info;
|
|
|
|
|
UINT br;
|
|
|
|
|
u8 res=0;
|
|
|
|
|
// app_wm8978_volset(wm8978set.mvol);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
// WM8978_ADDA_Cfg(1,0); //<2F><><EFBFBD><EFBFBD>DAC
|
|
|
|
|
// WM8978_Input_Cfg(0,0,0);//<2F>ر<EFBFBD><D8B1><EFBFBD><EFBFBD><EFBFBD>ͨ<EFBFBD><CDA8>
|
|
|
|
|
// WM8978_Output_Cfg(1,0); //<2F><><EFBFBD><EFBFBD>DAC<41><43><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
g_nes_break=0;
|
|
|
|
|
file=mymalloc(sizeof(FIL));
|
|
|
|
|
file_info= mymalloc(sizeof(FILINFO));
|
2025-07-05 19:47:28 +08:00
|
|
|
|
if(file==0)return 1; //<2F>ڴ<EFBFBD><DAB4><EFBFBD><EFBFBD><EFBFBD>ʧ<EFBFBD><CAA7>.
|
2025-06-27 00:32:57 +08:00
|
|
|
|
|
|
|
|
|
res=f_stat((char*)pname,file_info);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
if(res!=FR_OK) //<2F><><EFBFBD><EFBFBD><EFBFBD>ļ<EFBFBD>ʧ<EFBFBD><CAA7>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
{
|
|
|
|
|
myfree(file);
|
|
|
|
|
myfree(file_info);
|
|
|
|
|
return 2;
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
res=nes_sram_malloc(file_info->fsize); //<2F><><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
if(res==0)
|
|
|
|
|
{
|
|
|
|
|
f_open(file,(char*)pname,FA_READ);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
f_read(file,romfile,file_info->fsize,&br); //<2F><>ȡnes<65>ļ<EFBFBD>
|
|
|
|
|
res=nes_load_rom(); //<2F><><EFBFBD><EFBFBD>ROM
|
2025-06-27 00:32:57 +08:00
|
|
|
|
if(res==0)
|
|
|
|
|
{
|
2025-07-05 19:47:28 +08:00
|
|
|
|
Mapper_Init(); //map<61><70>ʼ<EFBFBD><CABC>
|
|
|
|
|
cpu6502_init(); //<2F><>ʼ<EFBFBD><CABC>6502,<2C><><EFBFBD><EFBFBD>λ
|
|
|
|
|
PPU_reset(lcd_addr); //ppu<70><75>λ
|
|
|
|
|
apu_init(); //apu<70><75>ʼ<EFBFBD><CABC>
|
|
|
|
|
nes_sound_open(0,APU_SAMPLE_RATE); //<2F><>ʼ<EFBFBD><CABC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>豸
|
|
|
|
|
nes_emulate_frame(); //<2F><><EFBFBD><EFBFBD>NESģ<53><C4A3><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѭ<EFBFBD><D1AD>
|
|
|
|
|
nes_sound_close(); //<2F>ر<EFBFBD><D8B1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
f_close(file);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
myfree(file);//<2F>ͷ<EFBFBD><CDB7>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
myfree(file_info);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
nes_sram_free(); //<2F>ͷ<EFBFBD><CDB7>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
return res;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><><EFBFBD><EFBFBD><EFBFBD>Ѿ<EFBFBD><D1BE><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD><DAB4>е<EFBFBD><D0B5><EFBFBD>Ϸ
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u8 nes_start(u8* file,int fileSize,void *lcd_addr,int x,int y)
|
|
|
|
|
{
|
|
|
|
|
nes_xoff=x;
|
|
|
|
|
nes_yoff=y;
|
|
|
|
|
u8 res=0;
|
|
|
|
|
g_nes_break=0;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
res=nes_sram_malloc(fileSize); //<2F><><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
|
|
|
|
|
if(res==0)
|
|
|
|
|
{
|
2025-07-05 19:47:28 +08:00
|
|
|
|
mymemcpy (romfile,file,fileSize);//<2F><><EFBFBD><EFBFBD>һ<EFBFBD><D2BB><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>пռ<D0BF>
|
|
|
|
|
res=nes_load_rom(); //<2F><><EFBFBD><EFBFBD>ROM
|
2025-06-27 00:32:57 +08:00
|
|
|
|
if(res==0)
|
|
|
|
|
{
|
2025-07-05 19:47:28 +08:00
|
|
|
|
Mapper_Init(); //map<61><70>ʼ<EFBFBD><CABC>
|
|
|
|
|
cpu6502_init(); //<2F><>ʼ<EFBFBD><CABC>6502,<2C><><EFBFBD><EFBFBD>λ
|
|
|
|
|
PPU_reset(lcd_addr); //ppu<70><75>λ
|
|
|
|
|
apu_init(); //apu<70><75>ʼ<EFBFBD><CABC>
|
|
|
|
|
nes_sound_open(0,APU_SAMPLE_RATE); //<2F><>ʼ<EFBFBD><CABC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>豸
|
|
|
|
|
nes_emulate_frame(); //<2F><><EFBFBD><EFBFBD>NESģ<53><C4A3><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѭ<EFBFBD><D1AD>
|
|
|
|
|
nes_sound_close(); //<2F>ر<EFBFBD><D8B1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
}
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
nes_sram_free(); //<2F>ͷ<EFBFBD><CDB7>ڴ<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
return res;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7>ʾ<EFBFBD><CABE><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void nes_set_window(void)
|
|
|
|
|
{
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><>ȡ<EFBFBD><C8A1>Ϸ<EFBFBD>ֱ<EFBFBD><D6B1><EFBFBD><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void nes_get_gamepadval(void)
|
|
|
|
|
{
|
|
|
|
|
#include "usart.h"
|
|
|
|
|
PADdata=USART3_GetKey();
|
|
|
|
|
PADdata1=0;
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//nesģ<73><C4A3><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѭ<EFBFBD><D1AD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void nes_emulate_frame(void)
|
|
|
|
|
{
|
|
|
|
|
u8 nes_frame;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//TIM3_Int_Init(10000-1,8400-1);//<2F><><EFBFBD><EFBFBD>TIM3 ,1s<31>ж<EFBFBD>һ<EFBFBD><D2BB>
|
|
|
|
|
nes_set_window();//<2F><><EFBFBD>ô<EFBFBD><C3B4><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
while(1)
|
|
|
|
|
{
|
|
|
|
|
// LINES 0-239
|
|
|
|
|
PPU_start_frame();
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//LCD_SwitchLayerBuff();//<2F>л<EFBFBD>֡
|
2025-06-27 00:32:57 +08:00
|
|
|
|
for(NES_scanline = 0; NES_scanline< 240; NES_scanline++)
|
|
|
|
|
{
|
|
|
|
|
run6502(113*256);
|
|
|
|
|
NES_Mapper->HSync(NES_scanline);
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//ɨ<><C9A8>һ<EFBFBD><D2BB>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
if(nes_frame==0)scanline_draw(NES_scanline);
|
|
|
|
|
else do_scanline_and_dont_draw(NES_scanline);
|
|
|
|
|
}
|
|
|
|
|
//LCD_ExitLayerBuff ();
|
|
|
|
|
|
|
|
|
|
NES_scanline=240;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
run6502(113*256);//<2F><><EFBFBD><EFBFBD>1<EFBFBD><31>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
NES_Mapper->HSync(NES_scanline);
|
|
|
|
|
start_vblank();
|
|
|
|
|
if(NMI_enabled())
|
|
|
|
|
{
|
|
|
|
|
cpunmi=1;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
run6502(7*256);//<2F><><EFBFBD><EFBFBD><EFBFBD>ж<EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
}
|
|
|
|
|
NES_Mapper->VSync();
|
|
|
|
|
// LINES 242-261
|
|
|
|
|
for(NES_scanline=241;NES_scanline<262;NES_scanline++)
|
|
|
|
|
{
|
|
|
|
|
run6502(113*256);
|
|
|
|
|
NES_Mapper->HSync(NES_scanline);
|
|
|
|
|
}
|
|
|
|
|
end_vblank();
|
2025-07-05 19:47:28 +08:00
|
|
|
|
nes_get_gamepadval();//ÿ3֡<33><D6A1>ѯһ<D1AF><D2BB>USB
|
|
|
|
|
apu_soundoutput();//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
nes_frame_cnt++;
|
|
|
|
|
nes_frame++;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
if(nes_frame>NES_SKIP_FRAME)nes_frame=0;//<2F><>֡
|
2025-06-27 00:32:57 +08:00
|
|
|
|
u8 nesBreak (void);
|
|
|
|
|
if (nesBreak()) break;
|
|
|
|
|
if (Touch_GetState()->x[1]!=0) break;
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//TIM3->CR1&=~(1<<0);//<2F>رն<D8B1>ʱ<EFBFBD><CAB1>3
|
2025-06-27 00:32:57 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
u8 nesBreak (void)
|
|
|
|
|
{
|
|
|
|
|
u8 t=0;
|
|
|
|
|
if ((PADdata&0x0c)==0x0c)
|
|
|
|
|
{
|
|
|
|
|
g_nes_break=0x0c;
|
|
|
|
|
}
|
|
|
|
|
if ((g_nes_break)&&(t=USART3_GetKeyPressed(),t&0x0c))
|
|
|
|
|
{
|
|
|
|
|
g_nes_break&=~t;
|
|
|
|
|
if (g_nes_break==0)
|
|
|
|
|
return 1;
|
|
|
|
|
}
|
|
|
|
|
return 0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><>6502.s<><73><EFBFBD>汻<EFBFBD><E6B1BB><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void debug_6502(u16 reg0,u8 reg1)
|
|
|
|
|
{
|
|
|
|
|
//printf("6502 error:%x,%d\r\n",reg0,reg1);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//////////////////////////////////////////////////////////////////////////////////
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//nes,<2C><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>֧<EFBFBD>ֲ<EFBFBD><D6B2><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
static vu8 g_buff_Invalid=0; //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ЧʱҪ<CAB1><D2AA><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
|
|
|
|
static vu8 g_buff_useing; //<2F><>ǰDMA<4D><41>ʹ<EFBFBD><CAB9><EFBFBD>ĸ<EFBFBD><C4B8><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
static DAC_UserStruct g_dac;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static void dma_tx_callback(DAC_UserStruct *dac)
|
|
|
|
|
{
|
|
|
|
|
u16 i;
|
|
|
|
|
g_buff_useing=dac->buff_useing;
|
|
|
|
|
g_buff_Invalid=1;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//NES<45><53><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
int nes_sound_open(int samples_per_sync,int sample_rate)
|
|
|
|
|
{
|
|
|
|
|
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><>ʼ<EFBFBD><CABC>DAC
|
2025-06-27 00:32:57 +08:00
|
|
|
|
g_dac.buff1=(u32 *)i2sbuf1;
|
|
|
|
|
g_dac.buff2=(u32 *)i2sbuf2;
|
|
|
|
|
g_dac.buff_size=APU_PCMBUF_SIZE*4;
|
|
|
|
|
g_dac.rate=RATE22050;
|
|
|
|
|
g_dac.call_back=dma_tx_callback;
|
|
|
|
|
DAC_NormalInit (&g_dac);
|
|
|
|
|
return 1;
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//NES<45>ر<EFBFBD><D8B1><EFBFBD>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void nes_sound_close(void)
|
|
|
|
|
{
|
|
|
|
|
DAC_NormalDeInit (&g_dac);
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//NES<45><53>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>I2S<32><53><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
void nes_apu_fill_buffer(int samples,u16* wavebuf)
|
|
|
|
|
{
|
|
|
|
|
|
|
|
|
|
if (DAC_GetDacHander()!=&g_dac) return;
|
|
|
|
|
u16 i;
|
|
|
|
|
u16 *p;
|
2025-07-05 19:47:28 +08:00
|
|
|
|
while(g_buff_Invalid==0)//<2F>ȴ<EFBFBD><C8B4><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
2025-06-27 00:32:57 +08:00
|
|
|
|
{
|
|
|
|
|
rt_thread_delay(5);//
|
|
|
|
|
};
|
|
|
|
|
if(g_buff_useing==0)
|
|
|
|
|
{
|
|
|
|
|
p=(u16*)i2sbuf2;
|
|
|
|
|
}else
|
|
|
|
|
{
|
|
|
|
|
p=(u16*)i2sbuf1;
|
|
|
|
|
}
|
|
|
|
|
{
|
|
|
|
|
for(i=0;i<APU_PCMBUF_SIZE;i++)
|
|
|
|
|
{
|
|
|
|
|
p[2*i]=((wavebuf[i]+0x8000)>>4);
|
|
|
|
|
p[2*i+1]=p[2*i];
|
|
|
|
|
}
|
|
|
|
|
}
|
2025-07-05 19:47:28 +08:00
|
|
|
|
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>֮<EFBFBD><D6AE><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϊ<EFBFBD><CEAA>Ч
|
2025-06-27 00:32:57 +08:00
|
|
|
|
g_buff_Invalid=0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|