PSP Emulator

From Vita Developer wiki
Revision as of 16:29, 11 February 2017 by GregoryRasputin (talk | contribs)
Jump to navigation Jump to search

PSP Emulator

FLASH0

|-- codepage
|   `-- cptbl.dat
|-- data
|   `-- cert
|       `-- CA_LIST.cer
|-- font
|   |-- arib.pgf
|   |-- gb3s1518.bwfon
|   |-- imagefont.bin
|   |-- jpn0.pgf
|   |-- kr0.pgf
|   |-- ltn0.pgf
|   |-- ltn10.pgf
|   |-- ltn11.pgf
|   |-- ltn12.pgf
|   |-- ltn13.pgf
|   |-- ltn14.pgf
|   |-- ltn15.pgf
|   |-- ltn1.pgf
|   |-- ltn2.pgf
|   |-- ltn3.pgf
|   |-- ltn4.pgf
|   |-- ltn5.pgf
|   |-- ltn6.pgf
|   |-- ltn7.pgf
|   |-- ltn8.pgf
|   `-- ltn9.pgf
|-- kd
|   |-- amctrl.prx
|   |-- audiocodec_260.prx
|   |-- avcodec.prx
|   |-- cert_loader.prx
|   |-- chkreg.prx
|   |-- chnnlsv.prx
|   |-- dmacman.prx
|   |-- exceptionman.prx
|   |-- exitgame.prx
|   |-- g729.prx
|   |-- ge_2.prx
|   |-- ge.prx
|   |-- http_storage.prx
|   |-- ifhandle.prx
|   |-- impose_kermit.prx
|   |-- init.prx
|   |-- interruptman.prx
|   |-- iofilemgr_dnas.prx
|   |-- iofilemgr.prx
|   |-- isofs.prx
|   |-- kermit_2.prx
|   |-- kermit_audio.prx
|   |-- kermit_ctrl.prx
|   |-- kermit_display.prx
|   |-- kermit_flashfs.prx
|   |-- kermit_hpremote.prx
|   |-- kermit_idstorage.prx
|   |-- kermit_lowio.prx
|   |-- kermit_me_wrapper.prx
|   |-- kermit_msemu.prx
|   |-- kermit_msfs.prx
|   |-- kermit_netconf_dialog.prx
|   |-- kermit_osk_plugin.prx
|   |-- kermit_peripheral.prx
|   |-- kermit_power.prx
|   |-- kermit.prx
|   |-- kermit_rtc.prx
|   |-- kermit_usb.prx
|   |-- kermit_utility.prx
|   |-- kermit_wlan_2.prx
|   |-- kermit_wlan.prx
|   |-- libaac.prx
|   |-- libasfparser.prx
|   |-- libatrac3plus.prx
|   |-- libaudiocodec2.prx
|   |-- libdnas_core.prx
|   |-- libdnas.prx
|   |-- libgameupdate.prx
|   |-- libhttp.prx
|   |-- libmp3.prx
|   |-- libmp4.prx
|   |-- libparse_http.prx
|   |-- libparse_uri.prx
|   |-- libssl.prx
|   |-- libupdown.prx
|   |-- loadcore.prx
|   |-- loadexec_01g.prx
|   |-- mcctrl.prx
|   |-- mediasync.prx
|   |-- memab.prx
|   |-- memlmd_01g_2.prx
|   |-- memlmd_01g.prx
|   |-- mesg_led_01g.prx
|   |-- mgvideo.prx
|   |-- modulemgr.prx
|   |-- mp4msv.prx
|   |-- mpegbase_260.prx
|   |-- mpeg.prx
|   |-- np9660.prx
|   |-- np_auth.prx
|   |-- np_commerce2.prx
|   |-- np_commerce2_regcam.prx
|   |-- np_commerce2_store.prx
|   |-- np_core.prx
|   |-- npdrm.prx
|   |-- np_inst.prx
|   |-- np_matching2.prx
|   |-- np.prx
|   |-- np_service.prx
|   |-- openpsid.prx
|   |-- psheet.prx
|   |-- pspnet_adhoc_auth.prx
|   |-- pspnet_adhocctl.prx
|   |-- pspnet_adhoc_discover.prx
|   |-- pspnet_adhoc_download.prx
|   |-- pspnet_adhoc_matching.prx
|   |-- pspnet_adhoc.prx
|   |-- pspnet_adhoc_transfer_int.prx
|   |-- pspnet_apctl_2.prx
|   |-- pspnet_apctl.prx
|   |-- pspnet_inet_2.prx
|   |-- pspnet_inet.prx
|   |-- pspnet.prx
|   |-- pspnet_resolver.prx
|   |-- pspnet_upnp.prx
|   |-- pspnet_wispr.prx
|   |-- registry.prx
|   |-- resource
|   |   `-- impose_05g.rsc
|   |-- sc_sascore.prx
|   |-- sircs.prx
|   |-- sysmem.prx
|   |-- systimer.prx
|   |-- threadman.prx
|   |-- usbacc.prx
|   |-- usbcam.prx
|   |-- usbgps.prx
|   |-- usbmic.prx
|   |-- usbpspcm.prx
|   |-- usersystemlib.prx
|   |-- vaudio.prx
|   `-- videocodec_260.prx
|-- pspbtcnf.bin
|-- reboot.bin
`-- vsh
    |-- etc
    |   |-- index_01g.dat
    |   `-- version.txt
    |-- module
    |   |-- auth_plugin.prx
    |   |-- auto_connect.prx
    |   |-- common_gui.prx
    |   |-- common_util.prx
    |   |-- dd_helper.prx
    |   |-- dd_helper_utility.prx
    |   |-- dialogmain.prx
    |   |-- dnas_plugin.prx
    |   |-- file_parser_base.prx
    |   |-- game_install_plugin.prx
    |   |-- htmlviewer_ui.prx
    |   |-- htmlviewer_utility.prx
    |   |-- hvauth_r.prx
    |   |-- libfont_hv.prx
    |   |-- libslim.prx
    |   |-- libwww.prx
    |   |-- msgdialog_plugin.prx
    |   |-- netconf_plugin.prx
    |   |-- netfront.prx
    |   |-- netplay_server2_utility.prx
    |   |-- netplay_server_plus_utility.prx
    |   |-- netplay_server_utility.prx
    |   |-- npinstaller_plugin.prx
    |   |-- npsignin_plugin.prx
    |   |-- npsignup_plugin.prx
    |   |-- pafmini.prx
    |   |-- ps3scan_plugin.prx
    |   |-- psn_utility.prx
    |   |-- savedata_auto_dialog.prx
    |   |-- savedata_utility.prx
    |   |-- screenshot_plugin.prx
    |   |-- store_browser_plugin.prx
    |   |-- store_checkout_plugin.prx
    |   `-- store_checkout_utility.prx
    `-- resource
        |-- auth_plugin.rco
        |-- dd_helper.rco
        |-- dnas_plugin.rco
        |-- game_install_plugin.rco
        |-- htmlviewer.res
        |-- msgdialog_plugin.rco
        |-- netconf_dialog.rco
        |-- netplay_plugin.rco
        |-- npinstaller_plugin.rco
        |-- npsignin_plugin.rco
        |-- npsignup_plugin.rco
        |-- ps3scan_plugin.rco
        |-- psn_plugin.rco
        |-- savedata_utility.rco
        |-- screenshot_plugin.rco
        |-- store_browser_plugin.rco
        |-- store_checkout_plugin.rco
        `-- system_plugin.rco


FLASH0 1.80 changes

|-- font
|   |-- arib.pgf     removed
|-- kd
|   |-- kermit_me_wrapper_2.prx     added
|   |-- pops_01g.prx     added
|   |-- popsman.prx     added
|-- vsh
    |-- module
        |--  libpspvmc.prx added

Flash0 Dump code

Please use responsibly.



int kthread(SceSize args, void *argp)
{
	// Find File Manager Module
	SceModule2 * iofilemgr = _sceKernelFindModuleByName("sceIOFileManager");
	
	// Find required Functions
	KernelIOOpen = (void *)iofilemgr->text_addr + IOFILEMGR_IO_OPEN;
	KernelIOWrite = (void *)iofilemgr->text_addr + IOFILEMGR_IO_WRITE;
	KernelIOClose = (void *)iofilemgr->text_addr + IOFILEMGR_IO_CLOSE;
	
	flashVitaDump( GAME_SAVE_PATH "h.bin"/*"flashVitaDump.zip"*/ );
	
	return 0;
}

void initKernelThread(void)
{
	SceModule2 *threadman = _sceKernelFindModuleByName("sceThreadManager");
	
	_sceKernelCreateThread = (void *)((u32)threadman->text_addr + THREADMAN_CREATE_THREAD);
	_sceKernelStartThread = (void *)((u32)threadman->text_addr + THREADMAN_START_THREAD);
	
	SceUID kthreadID = _sceKernelCreateThread( "Kernel thread", KERNELIFY(kthread), 25, 0x10000, 0, NULL );
	
	if (kthreadID >= 0)	_sceKernelStartThread(kthreadID, 0, NULL);
	else	PRTSTR1("Error: sceKernelCreateThread -> 0x%08lX\n", kthreadID);
}

struct minZipHeader {
	char pk[2];
	unsigned nb;
	char space[12];
	unsigned fileSize;
	unsigned fileSizeClone;
	unsigned pathLen;
	/*
	path
	data
	*/
};

typedef struct{
	char *name;
	void *content;
	u32 size;
}VitaFlashBufferFile;

unsigned addWriteFile( SceUID packFileID, void *data, unsigned size, char *name, u8 found_nb )
{
	const char *root = "flash0";
	char path[256];
	
	strcpy(path, root);
	
	// If file name has no / at first, add it
	if ( name[0] != '/' )
		path[strlen(path)+1] = 0, path[strlen(path)] = '/';
		
	strcat(path, name);
	
	// If file was already dumped, add custom name suffix
	if ( found_nb > 1)	strcat(path, ".bakX"), path[strlen(path)-1] = '0'+found_nb-2;
	
	// Write Data
	struct minZipHeader zHead;
	strcpy(zHead.pk, "PK");
	zHead.nb = 0x000A0403;
	memset(zHead.space, 0, sizeof(zHead.space));
	zHead.fileSize = size;
	zHead.fileSizeClone = size;
	zHead.pathLen = strlen(path);
	
	KernelIOWrite(packFileID, &(zHead.pk), 2);
	KernelIOWrite(packFileID, &(zHead.nb), sizeof(u32));
	KernelIOWrite(packFileID, &(zHead.space), sizeof(zHead.space));
	KernelIOWrite(packFileID, &(zHead.fileSize), sizeof(u32));
	KernelIOWrite(packFileID, &(zHead.fileSizeClone), sizeof(u32));
	KernelIOWrite(packFileID, &(zHead.pathLen), sizeof(u32));
	KernelIOWrite(packFileID, path, zHead.pathLen);
	
	unsigned written = KernelIOWrite(packFileID, data, size);
	
	return written;
}

int findFlashIndex( const VitaFlashBufferFile *f0, void *origContent )
{
	int flash0_filecount = 0;
	
	while ( origContent != f0[flash0_filecount].content && f0[flash0_filecount].name != NULL )
		++flash0_filecount;
	
	if ( f0[flash0_filecount].name == NULL )	return -1;
	else	return flash0_filecount;
}

void flashVitaDump( char *packName )
{
	uint32_t sonyF0 = 0x8B000000;
	uint32_t sonyF0Backup = 0x8BF00000;
	int flash0_fileindex = 0;
	uint32_t totalwrite = 0;
	int isValid, i;
	int dummy_count = 0;
	int backup_count = 0;
	char *name = NULL;
	u8 found_f0[512];
	
	for ( i=0; i<sizeof(found_f0); ++i )	found_f0[i] = 0;
	
	const VitaFlashBufferFile * f0 = (VitaFlashBufferFile *)sonyF0;
	
	SceUID packFileID = KernelIOOpen(packName, PSP_O_WRONLY | PSP_O_CREAT, 0777);
	
	if (packFileID)
	{
		setPrintColorRGB(255, 0, 0);
		PRTSTR0("");
		PRTSTR0("Dumping flash");
		PRTSTR0("");
		setPrintColorRGB(0, 255, 255);
		
		// Write all found flash files
		while ( f0[flash0_fileindex].name != NULL )
		{
			name = f0[flash0_fileindex].name;
			isValid = 0;
			
			if ( name[strlen(name)-3] == 'p' && name[strlen(name)-2] == 'r' && name[strlen(name)-1] == 'x' )
			{
				switch ( *((int*)f0[flash0_fileindex].content) )
				{
					case 0x5053507E:
						isValid = 1;
						
						break;
						
					case 0:
						dummy_count++;
						break;
						
					default:
						PRTSTR0("Unknown prx : %08lX", name);
						isValid = 1;
						break;
				}
			}
			else	isValid = 1;
			
			if ( isValid )
			{
				found_f0[flash0_fileindex]++;
				
				PRTSTR0("Writing file ...");
				totalwrite += addWriteFile( packFileID, f0[flash0_fileindex].content, f0[flash0_fileindex].size, name, found_f0[flash0_fileindex] );
				
				PRTSTR0("File dumped");
			}
			else
			{
				//PRTSTR0("Invalid flash file : %08lX", name);
				PRTSTR0("Dummied flash file");
			}
			
			++flash0_fileindex;
		}
		
		uint32_t *curf0Backup = sonyF0Backup;
		
		setPrintColorRGB(255, 0, 0);
		PRTSTR0("");
		PRTSTR0("Dumping flash backup");
		PRTSTR0("");
		setPrintColorRGB(0, 255, 255);
		
		// Write all found flash backups
		while ( *curf0Backup != NULL )
		{
			uint32_t origContent = *curf0Backup;
			flash0_fileindex = findFlashIndex(f0, origContent);
			
			unsigned size = *(curf0Backup+1);
			curf0Backup += 2;
			
			if ( flash0_fileindex >= 0 )
			{
				found_f0[flash0_fileindex]++;
				name = f0[flash0_fileindex].name;
				
				PRTSTR0("Writing file ...");
				totalwrite += addWriteFile( packFileID, curf0Backup, size, name, found_f0[flash0_fileindex] );
				
				backup_count++;
				
				PRTSTR0("File dumped");
			}
			else
			{
				PRTSTR0("%08lX not found", origContent);
				
				// Quit because usually means a general error
				break;
			}
			
			curf0Backup += size/4 + 1;
		}
		
		KernelIOClose(packFileID);
		
		//PRTSTR0("Dummy files: %08lX, backup files: %08lX ", dummy_count, backup_count);
		setPrintColorRGB(255, 0, 0);
		PRTSTR0("");
		PRTSTR0("Flash successfully dumped");
		PRTSTR0("");
		setPrintColorRGB(0, 255, 255);
	}
}
 

PSP Memory Layout

Address Size Comments
0x00010000 0x4000 CPU Scratchpad
0x04000000 2 MB/4 MB VRAM/Framebuffer
0x08000000 64 MB Main Memory
0xBFC00000 0x1000 Shared SRAM

SceGrab

Address Size Comments
0xE8300120 4 Paddr of CDRAM base + 1, maps to 0x88000000?
0xE8300124 4 Paddr of CDRAM base + 0x1000000 + 1
0xE8300128 4 Paddr of CDRAM base + 0x2000000 + 1
0xE830012C 4 Paddr of flash0 in CDRAM (base + 0x3000000) + 1, maps to 0x3000000?

SceCompatLCDDMA

Address Size Comments
0xE5071004 4 set 1 when done
0xE5071024 4 0xFF0000
0xE5071028 4 0x0
0xE5071030 4 some status
0xE5071034 4 Width pixels
0xE5071038 4 0x0
0xE507103C 4 Hight pixels
0xE5071040 4 0x0
0xE507104C 4 DMA Paddr
0xE5071078 4 0x0
0xE5071084 4 0x0
0xE5071050 4 2048
0xE5071094 4 2
0xE5071098 4 1
0xE50710C0 4 busy status? (set 0x1000000 when done)