Editing PSP Emulation

Jump to navigation Jump to search
Warning: You are not logged in. Your IP address will be publicly visible if you make any edits. If you log in or create an account, your edits will be attributed to your username, along with other benefits.

The edit can be undone. Please check the comparison below to verify that this is what you want to do, and then publish the changes below to finish undoing the edit.

Latest revision Your text
Line 1: Line 1:
== Official games ==
=='''PSPHD'''==
 
The new ps plus psp emulator has a lot of undiscovered functionalities, it even allows patches directly to the emulated Allegrex cpu.
=== PSP Demos on PS4 ===
Sadly sony has not made it easy for users to use CLI commands because sony mostly uses lua patches for the psp releases, thus, not many cli commands were needed to be added. Very few commands have a description to their usage inside of the eboot.bin, everything else is just guesswork from the scene. The psp emulator has not gained the same popularity as the ps2 emulator because currently, there is an unofficial PPSSPP core in the unofficial retroarch port for the ps4. and as far as the compatibility and performance goes, the retroarch core is second to no one. This emulator may still hold potential, though sadly it does not seem to have support for gamedata installation and that has led to render many games unplayable.
 
* LocoRoco™2 Remastered Retail Kiosk Demo UP9000-CUSA10806_00-LOCOROCO2DEMO001 or JP9000-CUSA10952_00-LOCOROCO2DEMO001 DRM Free with license, removed from PS Store, present on PS4 IDU Disc
* PaRappa The Rapper™ Remastered 20th Anniversary Demo JP9000-CUSA07156_00-UCJS10046PSXDEMO or UP9000-CUSA07045_00-UCUS98702PSXDEMO or EP9000-CUSA07203_00-UCES00775PSXDEMO DRM Free with license, present on Japan, US and Europe PS Store, present on PS4 IDU Disc
 
=== PSP games available on PS4 PS Store ===
 
* Castlevania Requiem UP0101-CUSA13434_00-CASTLEVANIA00001 2018-10-26. The Dracula X Chronicles versions of Symphony of the Night and Rondo of Blood were re-released for the PlayStation 4 on October 26, 2018 as part of the Castlevania Requiem compilation. A port of Castlevania: Symphony of the Night was included as unlockable bonus content in Castlevania: The Dracula X Chronicles for the PlayStation Portable, which was released in North America on October 23, 2007, in Japan on November 8, 2007, and in Europe on February 18, 2008. Except for the Japanese release, the English translation features a new script and newly recorded voice acting, with the option to use the original Japanese voices. The PSP release is a port of the PlayStation version, but contains some additions and changes.
* Jeanne d'Arc (2006) UP9000-CUSA41018_00-UCUS987000000000 (PS5: UP9000-PPSA13995_00-UCUS987000000000) 2024-07-16
* Ratchet & Clank: Size Matters (2007) UP9000-CUSA41395_00-UCUS986330000000 (PS5: UP9000-PPSA14431_00-UCUS986330000000) 2024-07-16 PS4 11.50
* LEGO Star Wars II: The Original Trilogy UP1082-CUSA41250_00-ULUS101550000000 or EP1006-CUSA41251_00-ULES004790000000 (PS5: UP1082-PPSA14300_00-ULUS101550000000 or UP1082-PPSA14300_00-0804842924824650) 2024-06-18 patch 1.01 requires PS4 11.50 or PS5 9.20
* GODS EATER BURST PS4® & PS5® (PS5: UP0700-PPSA07715_00-GODEATERBURST000 or JP0700-PPSA07713_00-GODEATERBURST000) 2024-03-19
* Daxter UP9000-CUSA36097_00-NPUG803290000000 (PS5: UP9000-PPSA09695_00-NPUG803290000000) 2024-06-18 patch 1.01 requires PS4 11.50 or PS5 9.20
* Jak and Daxter: The Lost Frontier UP9000-CUSA41282_00-NPUG803300000000 (PS5: UP9000-PPSA14325_00-NPUG803300000000) 2024-03-19 patch 1.02 requires PS4 11.50 or PS5 9.00
* Thrillville EP1006-CUSA41330_00-ULES006460000000 or UP1082-CUSA41329_00-ULUS101910000000 (PS5: UP1082-PPSA14358_00-0724668029168071) 2023-12-19
* Thrillville: Off the Rails (PS5: UP1082-PPSA14360_00-0645898243839752) 2023-12-19
* Tekken 6 PS4® & PS5® UP0700-CUSA33754_00-TEKKEN6000000000 or JP0700-CUSA33752_00-TEKKEN6000000000 (PS5: UP0700-PPSA07707_00-ULUS104660000000) 2023-10-17
* Soulcalibur: Broken Destiny PS4® & PS5® UP0700-CUSA33758_00-SOULCALIBURBD000 or JP0700-CUSA33756_00-SOULCALIBURBD000 2023-10-17
* Disney•Pixar Up UP1082-CUSA41345_00-0227660722516578 2023-11-21
* MediEvil Resurrection™ UP9000-CUSA33589_00-UCUS986200000000 2023-08-15
* Ridge Racer 2 PS4 & PS5 UP0700-CUSA33740_00-RIDGERACER200000 or JP0700-CUSA33738_00-RIDGERACER200000 2022-12-20
* Gravity Crash Portable UP9000-CUSA40479_00-NPUG803210000000 or JP9000-CUSA40480_00-NPJG000440000000 2023-07-18
* Killzone: Liberation (2006) EP9000-CUSA37875_00-UCES002790000000 or UP9000-CUSA37874_00-UCUS986460000000 (PS5: UP9000-PPSA11141_00-UCUS986460000000) 2023-06-20 PS5 7.40
* Pursuit Force (2005) UP9000-CUSA37191_00-UCUS986400000000 or EP9000-CUSA37192_00-UCES000190000000 or JP9000-CUSA37932_00-ULJM050970000000 or HP9000-CUSA37193_00-UCKS450160000000 (PS5: UP9000-PPSA10609_00-UCUS986400000000) 2023-05-16
* Pursuit Force: Extreme Justice UP9000-CUSA34853_00-UCUS987030000000 (PS5: UP9000-PPSA08696_00-UCUS987030000000) 2023-08-15
* Blade Dancer: Lineage of Light UP9000-CUSA37870_00-ULUS101240000000 or JP9000-CUSA37872_00-UCJS100210000000 2023-05-16
* Pinball Heroes UP9000-CUSA33617_00-0000000000000000 2022-12-20
* Disney•Pixar Toy Story 3 UP1082-CUSA33343_00-4838282977086414 2022-09-20
* Kingdom of Paradise UP9000-CUSA33573_00-UCUS986230000000 or JP9000-CUSA33575_00-UCJS100100000000 or HP9000-CUSA34893_00-UCAS400230000000 2022-09-20
* No Heroes Allowed! UP9000-CUSA33595_00-NPUG804600000000 2022-07-19
* LocoRoco Midnight Carnival UP9000-CUSA32639_00-0000000000000000 or JP9000-CUSA32641_00-0000000000000000 or EP9000-CUSA32640_00-0000000000000000 2022-07-19
* Ape Escape: On the Loose UP9000-CUSA37860_00-UCUS986090000000 or EP9000-CUSA37861_00-UCES000450000000 or JP9000-CUSA37862_00-UCJS100040000000 2023-08-15 PS4 10.70
* Ape Escape Academy UP9000-CUSA33020_00-UCUS986190000000 or JP9000-CUSA33022_00-UCJS100030000000 2023-10-17
* Ape Academy 2 UP9000-CUSA37900_00-UCES003020000000 or JP9000-CUSA37866_00-UCJS100200000000 2023-03-21
* Secret Agent Clank UP9000-CUSA41276_00-UCUS986970000000 (PS5: UP9000-PPSA14319_00-UCUS986970000000) 2024-09-17
* Syphon Filter: Logan's Shadow (2007) EP9000-CUSA32631_00-UCES007100000000 or UP9000-CUSA32630_00-UCUS986060000000 (PS5: UP9000-PPSA06782_00-UCUS986060000000) 2023-05-16 PS5 9.00
* Syphon Filter: Dark Mirror UP9000-CUSA32633_00-UCUS986410000000 2023-03-21
* echochrome UP9000-CUSA32644_00-NPUG801350000000 or JP9000-CUSA32646_00-UCJS100810000000 2022-06-13
* Super Stardust Portable (2007) EP9000-CUSA33036_00-NPEG000080000000 or UP9000-CUSA33035_00-NPUG802210000000 or JP9000-CUSA33037_00-NPJG000130000000 (PS5: UP9000-PPSA07135_00-NPUG802210000000 or EP9000-PPSA07136_00-NPEG000080000000) 2022-06-13
* echoshift UP9000-CUSA33585_00-NPUG803030000000 or JP9000-CUSA33587_00-UCJS100960000000 2022-07-19
* Resistance: Retribution (2009) EP9000-CUSA32637_00-UCES011840000000 or UP9000-CUSA32636_00-UCUS986680000000 (PS5: EP9000-PPSA06789_00-UCES011840000000 or UP9000-PPSA06788_00-UCUS986680000000 or JP9000-PPSA06790_00-UCJS100900000000) 2024-02-20
* 勇者のくせになまいきだ:3D (What Did I Do to Deserve This, My Lord? 3D) JP9000-CUSA33597_00-UCJS101090000000 2022-07-19
* Coded Soul JP9000-CUSA33571_00-UCJS100610000000 or HP9000-CUSA34502_00-UCAS401800000000 2023-06-20
* Ore no Shikabane o Koete Yuke (PS5: JP9000-PPSA09382_00-UCJS101170000000) 2024-04-16
 
=== PSP remaster games available on PS4 PS Store ===
 
Note that some of these remastered games like LocoRoco™ 2 Remastered use a PSP emulator and most original files, but with additional files like replacement textures for example. There are even some features like 60 fps that are available only on PS4 Pro but not on standard PS4.
 
* LocoRoco™ Remastered UP9000-CUSA06090_00-UCUS986620000001 or EP9000-CUSA07286_00-UCES003040000001 or JP9000-CUSA06933_00-UCUS986620000001 2017-05-09
* LocoRoco™ 2 Remastered UP9000-CUSA06091_00-UCUS987310000001 or EP9000-CUSA07695_00-LOCOROCO2HD00001 or JP9000-CUSA06934_00-LOCOROCO2HD00001 2017-12-09
* LUMINES REMASTERED UP0751-CUSA11624_00-LUMINESREMASTERE or JP1049-CUSA11673_00-LUMINESREMASTERE or EP0748-CUSA11647_00-LUMINESREMASTERE 2018-07-10
* Patapon™ Remastered UP9000-CUSA06171_00-UCUS987110000001 or EP9000-CUSA07285_00-UCES009950000001 or JP9000-CUSA06935_00-PATAPON100000001 2017-08-01
* Patapon 2 Remastered UP9000-CUSA07321_00-UCES011770000001 or EP9000-CUSA07694_00-UCES009950000001 or JP9000-CUSA08178_00-PATAPON200000001 2020-01-30
* Patapon 3 UP9000-CUSA41279_00-UCUS987510000000 2025-01-15. Enhanced with up-rendering, rewind, quick save, and custom video filters.
* Metal Slug Double X JP0576-CUSA11717_00-METALSLUGXX00001 or EP0576-CUSA11740_00-METALSLUGXX00001 or UP0576-CUSA11667_00-METALSLUGXX00001 2018-05-30
* PaRappa The Rapper™ Remastered JP9000-CUSA06932_00-UCJS100460000001 or UP9000-CUSA05289_00-UCUS987020000001 or EP9000-CUSA07172_00-UCES007750000001 2017-04-04
 
== '''PSPHD''' ==
 
The PSP emulator for PlayStation 4 includes plenty of undiscovered functionalities. It even allows patches directly to the emulated Allegrex CPU. Not many CLI commands were added this time around. Very few commands have a description to their usage inside of the eboot.bin, everything else is just guesswork from the scene. Plenty of Lua commands need to be understood before the compatibility of games can improve. The PSP emulator has not gained the same popularity in the scene as the PS2 emulator due to the existence of an unofficial PPSSPP core in the unofficial Retroarch port for hacked PS4. As far as the compatibility and performance go, the Retroarch core is yet to be bested. This official emulator may hold potential, but the potential can only go so far as it seems not to have support for gamedata installation, which in turn will render many games unplayable.


== Commands ==
== Commands ==
'''Known functions:''' Require cleanup.
'''Known functions:''' Require cleanup.
 
<br>The rest of the cli and lua commands can all be found inside of an emu's decrypted '''eboot.bin'''.
<br>The rest of the CLI and Lua commands can all be found inside of any PSP emulator's decrypted '''eboot.bin'''.
 
=== CLI commands ===
=== CLI commands ===
These commands can be added to any of these files:
These commands can be added to any of these files:
Line 157: Line 94:
|-
|-
|-style="background-color:#7698FF"
|-style="background-color:#7698FF"
|  || Speedhacks / Possible duplicates|| ||
|  || Speedhacks || ||
|-
|-
| --antialias || off || Turning Anti-Alias Off Improves Performance||--antialias=off
| --antialias || off || Turning Anti-Alias Off Improves Performance||--antialias=off
Line 177: Line 114:
| --texrecent || true || Optimize texture hashes ||--texrecent=true
| --texrecent || true || Optimize texture hashes ||--texrecent=true
|}
|}
====Syphon Filter Dark Mirror====
 
====Texture replacement====
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Command !! Values !! Notes !! Usage   
! Command !! Values !! Notes !! Usage   
|-
|-
| --force-native-aspect-ratio || || ||
| --texswitch||true, false|| Enables Texture replacement || --texswitch=true
|-
|-
| --use-higher-precision-depth || || ||
| --texsave || || ||
|-
|-
| --optimize-fb-self-resolves || || ||
| --texmissingsave || || ||
|-
|-
| --force-dsf-present || || ||
| --autoresampler || true, false|| Turns on the auto-resampler. Assumes textures in texreplace are at 8x resolution and resamples them at load, May only work on new LocoRoco Midnight Carnival emu || --autoresampler=true
|-
|-
| --bend-30hz-lock|| || ||
| --texreplace || Directory || Set directory of texture replacement folder || --texreplace="host0:texreplace"
|-
|-
| --setframebuf-auto-vblank-wait-threshold|| || ||
| --replacementfilter || true, false || This forces alpha blending to on for replaced textures. || --replacementfilter=true
|-
|-
| --gpu-renderthread|| || ||
| --replacementalpha || true, false || || --replacementalpha=true
|-
|-
| --force-triangle-clip-off|| || ||
|}
 
===XXXXYYYYY_patches.lua===
Your lua can be placed as '''scripts\XXXXYYYYY_patches.lua'''
<br>'''Requires Cleanup'''.
 
====Emulator commands====
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Command !! Usage !! Notes - Example
|-
|-
| --hack-use-sku-vms|| || ||
|getEmuObject || '''local emuObj = getEmuObject()''' || Required for all functions using emuObj
|-
|-
| --active-sku || || ||
|LoadSlideshow ||emuObj.LoadSlideshow()||
|-
|-
| --psp-right-stick-action || 0,1 || ||--psp-right-stick-action=1
|StartSlideshow ||emuObj.StartSlideshow()||
|-
|-
| --psp-right-stick-deadzone-x || || ||--psp-right-stick-deadzone-x=15
|Log ||emuObj.Log()||
|-
|-
| --psp-right-stick-deadzone-y || || ||--psp-right-stick-deadzone-y=15
| GetLanguage ||emuObj.GetLanguage()|| Get the language the ps4 is using
|-
|-
| --psp-right-stick-deadzone-semicircle-arc || || ||--psp-right-stick-deadzone-semicircle-arc=40
| GetNativeLanguage ||emuObj.GetNativeLanguage()||
|-
|-
|}
|DisplayManual || emuObj.DisplayManual()||
 
====Resistance====
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Command !! Values !! Notes !! Usage 
|-
|-
| --fb-tex-detection-mode || first-line, full, exact || ? ||
| DisplayProduct||emuObj.DisplayProduct()||
|-
|-
| --enable-infected-mode || || ? ||
|LoadConfig ||emuObj.LoadConfig()||
|-
|-
| --enable-resistance-retribution-plus-mode || || ? ||
| SaveConfig||emuObj.SaveConfig()||
|-
|-
| --psp-slower-disc-io || %s(%s, %08x) || ? ||
| LoadMIDI ||emuObj.LoadMIDI()||
|-
|-
| --force-flip-on-vblank || ? ||
| GetMIDINotesAtTick ||emuObj.GetMIDINotesAtTick()||
|-
|-
|}
|LoadState ||emuObj.LoadState()||
 
====Texture replacement====
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Command !! Values !! Notes !! Usage 
|-
|-
| --texswitch||true, false|| Enables Texture replacement || --texswitch=true
| SaveState ||emuObj.SaveState()||  
|-
|-
| --texsave || || ||
| SetFDExtraDelay ||emuObj.SetFDExtraDelay()|| 0? 1?
|-
|-
| --texmissingsave || || ||
| MeshSmooth ||emuObj.MeshSmooth()||
|-
|-
| --autoresampler || true, false|| Turns on the auto-resampler. Assumes textures in texreplace are at 8x resolution and resamples them at load, May only work on new LocoRoco Midnight Carnival emu || --autoresampler=true
| SetHue ||emuObj.SetHue()||
|-
|-
| --texreplace || Directory || Set directory of texture replacement folder || --texreplace="host0:texreplace"
| SetSaturation ||emuObj.SetSaturation()||
|-
|-
| --replacementfilter || true, false || This forces alpha blending to on for replaced textures. || --replacementfilter=true
| SetBrightness ||emuObj.SetBrightness()||
|-
|-
| --replacementalpha || true, false || || --replacementalpha=true
| SetContrast ||emuObj.SetContrast()||
|-
|-
|}
| VideoScale ||emuObj.VideoScale()||
 
===XXXXYYYYY_patches.lua===
 
The lua can be placed as: '''scripts\XXXXYYYYY_patches.lua'''
 
====Emulator commands====
 
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Command !! Usage !! Notes - Example
|-
|-
|getEmuObject || '''local emuObj = getEmuObject()''' || Required for all functions using emuObj
| SetOverlay ||emuObj.SetOverlay()||
|-
|-
|LoadSlideshow ||emuObj.LoadSlideshow()||
| DisplayUIOverlay ||emuObj.DisplayUIOverlay()||
|-
|-
|StartSlideshow ||emuObj.StartSlideshow()||
| CRC32 ||emuObj.CRC32()||
|-
|-
|Log ||emuObj.Log()||
| SASGetCRC ||emuObj.SASGetCRC()||
|-
|-
| GetLanguage ||emuObj.GetLanguage()|| Get the language the ps4 is using
| SASGetSampleRate ||emuObj.SASGetSampleRate()
|-
|-
| GetNativeLanguage ||emuObj.GetNativeLanguage()||
| GetAppName ||emuObj.GetAppName()||
|-
|-
|DisplayManual || emuObj.DisplayManual()||
| ReadFile ||emuObj.ReadFile()||
|-
|-
| DisplayProduct||emuObj.DisplayProduct()||
| RemapFB ||emuObj.RemapFB()||
|-
|-
|LoadConfig ||emuObj.LoadConfig()||
| InvalFB ||emuObj.InvalFB()||
|-
|-
| SaveConfig||emuObj.SaveConfig()||
| PlayVideo||emuObj.PlayVideo()||
|-
|-
| LoadMIDI ||emuObj.LoadMIDI()||
| RescaleUForUpscale ||emuObj.RescaleUForUpscale()||
|-
|-
| GetMIDINotesAtTick ||emuObj.GetMIDINotesAtTick()||
| RescaleVForUpscale||emuObj.RescaleVForUpscale()||
|-
|-
|LoadState ||emuObj.LoadState()||
| ShrinkUVRect ||emuObj.ShrinkUVRect()||
|-
|-
| SaveState ||emuObj.SaveState()||  
| ScalePosition ||emuObj.ScalePosition()||
|-
|-
| SetFDExtraDelay ||emuObj.SetFDExtraDelay()|| 0? 1?
| AdjustUVJitter ||emuObj.AdjustUVJitter()||
|-
|-
| MeshSmooth ||emuObj.MeshSmooth()||
| OverrideFBSize||emuObj.OverrideFBSize()|| Override framebuffer size ?
|-
|-
| SetHue ||emuObj.SetHue()||
|RemapSavedata || emuObj.RemapSavedata() ||emuObj.RemapSavedata("UCUS98711", "CUSA06171", "504e802b04a1838c32b616abbe0b475fbea1c823825ef0df06cc2bad129ce2f7")
|-
|-
| SetSaturation ||emuObj.SetSaturation()||
| NeoMode || emuObj.NeoMode() || Checks whether or not the ps4 is pro
|-
|-
| SetBrightness ||emuObj.SetBrightness()||
| ThrottleMax || emuObj.ThrottleMax() || Disable framelimiter during loading screens. This setting can sometimes be harmful when used globally in config files. Loading times are faster, but the game also runs faster than it should when the PS4 has enough free cpu power.
|-
|-
| SetContrast ||emuObj.SetContrast()||
| ThrottleFast|| emuObj.ThrottleFast() || Faster than default, but exact value is unknown.
|-
|-
| VideoScale ||emuObj.VideoScale()||
| ThrottleNorm ||emuObj.ThrottleNorm() || Enable default framelimiter (50/60 fps depend on region)
|-
|-
| SetOverlay ||emuObj.SetOverlay()||
|SetTextureHashMode||emuObj.SetTextureHashMode()||
|-
|-
| DisplayUIOverlay ||emuObj.DisplayUIOverlay()||
|SetTextureScaleOffset||emuObj.SetTextureScaleOffset()||
|-
|-
| CRC32 ||emuObj.CRC32()||
|SetTextureSaveSubdir||emuObj.SetTextureSaveSubdir()||
|-
|-
| SASGetCRC ||emuObj.SASGetCRC()||
| SetDrawEDRam || emuObj.SetDrawEDRam() ||
|-
|-
| SASGetSampleRate ||emuObj.SASGetSampleRate()
|SetSampleTitle||emuObj.SetSampleTitle()||
|-
|-
| GetAppName ||emuObj.GetAppName()||
|ToggleTextures||emuObj.ToggleTextures()||
|-
|-
| ReadFile ||emuObj.ReadFile()||
| CopyFB || emuObj.CopyFB() ||
|-style="background-color:#c6ecd9"
| Hooks  || ||
|-
|-
| RemapFB ||emuObj.RemapFB()||
| AddVsyncHook ||emuObj.AddVsyncHook()|| Set function to be done on every vsync
|-
|-
| InvalFB ||emuObj.InvalFB()||
| RemoveVsyncHook ||emuObj.RemoveVsyncHook()|| Remove vsynchook
|-
|-
| PlayVideo||emuObj.PlayVideo()||
| AddBootHook ||emuObj.AddBootHook()|| Set function to be done when the game boots up
|-
|-
| RescaleUForUpscale ||emuObj.RescaleUForUpscale()||
|RemoveBootHook||emuObj.RemoveBootHook()|| remove function to be done when the game boots up
|-
|-
| RescaleVForUpscale||emuObj.RescaleVForUpscale()||
| AddGPUHook ||emuObj.AddGPUHook()||
|-
|-
| ShrinkUVRect ||emuObj.ShrinkUVRect()||
|-style="background-color:#D7EF54"
|  Pad || ||  
|-
|-
| ScalePosition ||emuObj.ScalePosition()||
| Pad require ||'''local pad = require("pad")''' || Required for all commands that rely on pad
|-
|-
| AdjustUVJitter ||emuObj.AdjustUVJitter()||
|PadRead || emuObj.PadRead() ||
<br>L3        = 0x00000002
<br>R3        = 0x00000004
<br>OPTIONS  = 0x00000008
<br>UP        = 0x00000010
<br>RIGHT    = 0x00000020
<br>DOWN      = 0x00000040
<br>LEFT      = 0x00000080
<br>L2        = 0x00000100
<br>R2        = 0x00000200
<br>L1        = 0x00000400
<br>R1        = 0x00000800
<br>TRIANGLE  = 0x00001000
<br>CIRCLE    = 0x00002000
<br>CROSS    = 0x00004000
<br>SQUARE    = 0x00008000
<br>SELECT    = 0x00010000
<br>START    = 0x00020000
|-
|-
| OverrideFBSize||emuObj.OverrideFBSize()|| Override framebuffer size ?
|PadReadPitch || emuObj.PadReadPitch() ||
|-
|-
|RemapSavedata || emuObj.RemapSavedata() ||emuObj.RemapSavedata("UCUS98711", "CUSA06171", "504e802b04a1838c32b616abbe0b475fbea1c823825ef0df06cc2bad129ce2f7")
|PadReadRoll || emuObj.PadReadRoll()||
|-
|-
| NeoMode || emuObj.NeoMode() || Checks whether or not the ps4 is pro
|PadRegisterSamples || emuObj.PadRegisterSamples()||
|-
|-
| ThrottleMax || emuObj.ThrottleMax() || Disable framelimiter during loading screens. This setting can sometimes be harmful when used globally in config files. Loading times are faster, but the game also runs faster than it should when the PS4 has enough free cpu power.
| PadSetButtonsMode || emuObj.PadSetButtonsMode() ||  
<br>0 = Touch bar is split in two for Start/Select. Option is unmapped (default behaviour)
<br>1 = Touch bar is Start. Option is Select
<br>2 = Touch bar is Select. Option is Start
|-
|-
| ThrottleFast|| emuObj.ThrottleFast() || Faster than default, but exact value is unknown.
| PadVibrate|| emuObj.PadVibrate() || emuObj.PadVibrate(5,180,180)
|-
|-
| ThrottleNorm ||emuObj.ThrottleNorm() || Enable default framelimiter (50/60 fps depend on region)
|}
 
====Allegrex commands====
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Command !! Usage !! Notes - Example
|-
|-
|SetTextureHashMode||emuObj.SetTextureHashMode()||
| getAXObject ||'''local axObj = getAXObject()''' || Required for all functions using AXObject
|-
|-
|SetTextureScaleOffset||emuObj.SetTextureScaleOffset()||
| AddHook || axObj.AddHook() ||
|-
|-
|SetTextureSaveSubdir||emuObj.SetTextureSaveSubdir()||
| RemoveHook || axObj.RemoveHook() ||
|-
|-
| SetDrawEDRam || emuObj.SetDrawEDRam() ||
| BurnCycles|| axobj.BurnCycles() || Could be an option to overclock cpu at a hooked offset
|-
|-
|SetSampleTitle||emuObj.SetSampleTitle()||
|AddAOTBlock ||axObj.AddAOTBlock()|| Ahead of time compilation block ?
|-
|-
|ToggleTextures||emuObj.ToggleTextures()||
|Overlay ||axObj.Overlay()||
|-style="background-color:#ff8080"
| GPR || ||  
|-
|-
| CopyFB || emuObj.CopyFB() ||
| gpr require || '''local gpr = require("ax-gpr-alias")''' || Required for any command that includes gpr registers
|-style="background-color:#c6ecd9"
| Hooks  || ||
|-
|-
| AddVsyncHook ||emuObj.AddVsyncHook()|| Set function to be done on every vsync
|SetPC|| axObj.SetPC() ||
|-
|-
| RemoveVsyncHook ||emuObj.RemoveVsyncHook()|| Remove vsynchook
|GetPC|| axObj.GetPC() ||
|-
|-
| AddBootHook ||emuObj.AddBootHook()|| Set function to be done when the game boots up
| GetGpr || axObj.GetGpr() ||
|-
|-
|RemoveBootHook||emuObj.RemoveBootHook()|| remove function to be done when the game boots up
| SetGpr ||axObj.SetGpr() ||
|-
|-
| AddGPUHook ||emuObj.AddGPUHook()||
|SetFpr|| axObj.SetFpr() ||axObj.SetFpr(0)
|-
|-
|-style="background-color:#D7EF54"
|GetFpr || axObj.GetFpr() ||
|  Pad || ||  
|-
|-
| Pad require ||'''local pad = require("pad")''' || Required for all commands that rely on pad
|SetHi|| axObj.SetHi()||
|-
|-
|PadRead || emuObj.PadRead() ||
|GetHi|| axObj.GetHi()||
<br>L3        = 0x00000002
<br>R3        = 0x00000004
<br>OPTIONS  = 0x00000008
<br>UP        = 0x00000010
<br>RIGHT    = 0x00000020
<br>DOWN      = 0x00000040
<br>LEFT      = 0x00000080
<br>L2        = 0x00000100
<br>R2        = 0x00000200
<br>L1        = 0x00000400
<br>R1        = 0x00000800
<br>TRIANGLE  = 0x00001000
<br>CIRCLE    = 0x00002000
<br>CROSS    = 0x00004000
<br>SQUARE    = 0x00008000
<br>SELECT    = 0x00010000
<br>START    = 0x00020000
|-
|-
|PadReadPitch || emuObj.PadReadPitch() ||
| SetLo || axObj.SetLo()||
|-
|-
|PadReadRoll || emuObj.PadReadRoll()||
| GetLo ||axObj.GetLo()||
|-
| SetReg||axObj.SetReg()||
|-
|-
|PadRegisterSamples || emuObj.PadRegisterSamples()||
|GetReg||axObj.GetReg()||
|-style="background-color:#D7EF54"
| Memory editing || || Do note that the offsets on PPSSPP are different than the ones on the PS4
|-
|-
| PadSetButtonsMode || emuObj.PadSetButtonsMode() ||  
| ReadMem32 || axObj.ReadMem32() || Read 4 bytes from offset
<br>0 = Touch bar is split in two for Start/Select. Option is unmapped (default behaviour)
<br>1 = Touch bar is Start. Option is Select
<br>2 = Touch bar is Select. Option is Start
|-
|-
| PadVibrate|| emuObj.PadVibrate() || emuObj.PadVibrate(5,180,180)
| WriteMem32 || axObj.WriteMem32() || Write 4 bytes to offset
|-
|-
|}
| ReadMem16 || axObj.ReadMem16() || Read 2 bytes from offset
 
====Allegrex commands====
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Command !! Usage !! Notes - Example
|-
|-
| getAXObject ||'''local axObj = getAXObject()''' || Required for all functions using AXObject
| WriteMem16 || axObj.WriteMem16() || Write 2 bytes to offset
|-
|-
| AddHook || axObj.AddHook() ||
| ReadMem8 || axObj.ReadMem8() || Read 1 byte from offset
|-
|-
| RemoveHook || axObj.RemoveHook() ||
| WriteMem8 || axObj.WriteMem8() || Write 1 byte to offset
|-
|-
| BurnCycles|| axobj.BurnCycles() || Could be an option to overclock cpu at a hooked offset
| ReadMemString || axObj.ReadMemString() ||
|-
|-
|AddAOTBlock ||axObj.AddAOTBlock()|| Ahead of time compilation block ?
| WriteMemString || axObj.WriteMemString() ||
|-
|-
|Overlay ||axObj.Overlay()||
| WriteMemStr16 || axObj.WriteMemStr16() ||
|-style="background-color:#ff8080"
| GPR || ||  
|-
|-
| gpr require || '''local gpr = require("ax-gpr-alias")''' || Required for any command that includes gpr registers
|WriteMemStr16Z  ||axObj.WriteMemStr16Z() ||
|-
|-
|SetPC|| axObj.SetPC() ||
| WriteMemStringZ ||axobj.WriteMemStringZ ||
|-
|-
|GetPC|| axObj.GetPC() ||
|ReadMemFloat || axObj.ReadMemFloat() ||
|-
|-
| GetGpr || axObj.GetGpr() ||
|WriteMemFloat || axObj.WriteMemFloat() ||
|-
|-
| SetGpr ||axObj.SetGpr() ||
! !! Other/Unknown/Standalone Commands !!
|-
|-
|SetFpr|| axObj.SetFpr() ||axObj.SetFpr(0)
|FuncReplace || axFuncReplace() || axFuncReplace(0x8804670, "__ptmf_scall") Replace allegrex function.
|-
|-
|GetFpr || axObj.GetFpr() ||
| InsnReplace || axInsnReplace() || Replace allegrex memory
|-
|-
|SetHi|| axObj.SetHi()||
|}
|-
 
|GetHi|| axObj.GetHi()||
====Examples====
|-
<br>'''''LUA example:'''''
| SetLo || axObj.SetLo()||
<br>
|-
<br>Coconut Dodge "NPEZ00164"
| GetLo ||axObj.GetLo()||
<pre>
|-
local axObj = getAXObject()
| SetReg||axObj.SetReg()||
local emuObj = getEmuObject()
|-
 
|GetReg||axObj.GetReg()||
local patcher = function()
|-style="background-color:#D7EF54"
--Infinite lives
| Memory editing || || Do note that the offsets on PPSSPP are mapped differently than the ones on the PS4  
axObj.WriteMem32(0x8ACA1A4, 0x3) --0x08ACE1A4 on PPSSPP, PPSSPP addresses need to be reduced by 0x4000 in order to work on PS4
|-
end
| ReadMem32 || axObj.ReadMem32() || Read 4 bytes from offset
 
|-
emuObj.AddVsyncHook(patcher)
| WriteMem32 || axObj.WriteMem32() || Write 4 bytes to offset
</pre>
|-
 
| ReadMem16 || axObj.ReadMem16() || Read 2 bytes from offset
[https://www.psdevwiki.com/ps4/Talk:PSP_Emulator_Compatibility_List#Official_PSPemu_Configuration_Files More patches can be found here]
|-
=====Patches.lua=====
| WriteMem16 || axObj.WriteMem16() || Write 2 bytes to offset
'''An official lua created by sony for Patapon 2'''
|-
<pre>
| ReadMem8 || axObj.ReadMem8() || Read 1 byte from offset
-- Lua 5.3
|-
-- Title:  Patapon 2 PSP - UCUS-98732 (USA)
| WriteMem8 || axObj.WriteMem8() || Write 1 byte to offset
 
|-
apiRequest(1.0) -- request version 1.0 API. Calling apiRequest() is mandatory.
| ReadMemString || axObj.ReadMemString() ||
 
|-
local gpr = require( "ax-gpr-alias" ) -- you can access Allegrex GPR by alias (gpr.a0 / gpr["a0"])
| WriteMemString || axObj.WriteMemString() ||
local emuObj = getEmuObject() -- emulator
|-
local axObj = getAXObject() -- allegrex
| WriteMemStr16 || axObj.WriteMemStr16() ||
local pad = require("pad")
|-
|WriteMemStr16Z  ||axObj.WriteMemStr16Z() ||
|-
| WriteMemStringZ ||axobj.WriteMemStringZ ||
|-
|ReadMemFloat || axObj.ReadMemFloat() ||
|-
|WriteMemFloat || axObj.WriteMemFloat() ||
|-
! !! Other/Unknown/Standalone Commands !!
|-
|FuncReplace || axFuncReplace() || axFuncReplace(0x8804670, "__ptmf_scall") Replace allegrex function.
|-
| InsnReplace || axInsnReplace() || Replace allegrex memory
|-
|}


=====User-made examples=====
-- Hook memcpy to catch framebuffer effects
<br>'''Coconut Dodge'''
axFuncReplace(0x881D194, "patapon_memcpy")
<br>"NPEZ00164"
<pre>
local axObj = getAXObject()
local emuObj = getEmuObject()


local patcher = function()
-- Accelerate some functions
--Infinite lives
axFuncReplace(0x8804670, "__ptmf_scall")
axObj.WriteMem32(0x8ACA1A4, 0x3) --0x08ACE1A4 on PPSSPP. PPSSPP addresses need to be reduced by 0x4000 in order to work on PS4
axFuncReplace(0x8892230, "Renderer__makeWorldMatrix__4psysFv")
end
axFuncReplace(0x88209A8, "patapon_strcmp")
 
axFuncReplace(0x8815130, "sceGupSetStatus")
emuObj.AddVsyncHook(patcher)
axFuncReplace(0x8851D84, "FMtx44__setRow__3PydFv")
</pre>
axFuncReplace(0x88437F0, "Script__Talk__Controller__setDeltaTime__3PydFv")
<br>'''Daxter'''
axFuncReplace(0x8843B6C, "Script__Talk__Controller__setCmdId__3PydFv")
<br>"NPUG80329"
axFuncReplace(0x88441DC, "Script__Talk__Controller__getArgValuePtr__3PydFv_0")
<pre>
axFuncReplace(0x89B25B0, "sceGmoCol4Multiply")
local axObj = getAXObject()
axFuncReplace(0x8910A60, "Gfx__CacheModel__getNodeMtx__6SystemFv")
local emuObj = getEmuObject()
axFuncReplace(0x8911440, "Gfx__StaticGmoModel__getNodeIdx__6SystemFv")
 
axFuncReplace(0x89114C8, "Gfx__StaticGmoModel__getNodeMtx__6SystemFv")
local patcher = function()
axFuncReplace(0x891157C, "Gfx__StaticGmoModel__getNodeMtx__6SystemFv_0")
--Performance patch
axFuncReplace(0x881462C, "sceGuEnable", 0x8B3C050) -- param = gupbase pointer
axObj.WriteMem32(0x08862E40, 0x10000019) --0x08866E40 on PPSSPP. PPSSPP addresses need to be reduced by 0x4000 in order to work on PS4
axFuncReplace(0x8814684, "sceGuDisable", 0x8B3C050) -- param = gupbase pointer
axObj.WriteMem32(0x08862EAC, 0x0) --0x08866EAC on PPSSPP. PPSSPP addresses need to be reduced by 0x4000 in order to work on PS4
axFuncReplace(0x89B2D84, "sceGmoFCurveEval_fastpath", 0x89B2D88) -- param = function entry if not fast path
end
--axFuncReplace(0x88D0788, "Game__Map__Weather__WindLocus__update__4LaboFv_loop", 0x88D0864) -- param = continue address
 
axFuncReplace(0x890FCBC, "convertLowerString__6SystemFv")
emuObj.AddVsyncHook(patcher)
axFuncReplace(0x8877104, "convertLowerString__6SystemFv") -- convertLowerString__21@unnamed@BNDFile_cpp@Fv, same functionality
</pre>
axFuncReplace(0x897927C, "__extendsfdf2")
axFuncReplace(0x8979AF8, "__muldf3")
axFuncReplace(0x8979A8C, "__adddf3")
axFuncReplace(0x897A750, "__truncdfsf2")
axFuncReplace(0x88CBD64, "RemapPacket", 0x8ACC394) -- param comes from RemapPacketAddr24 & RemapPacketAddr16
axFuncReplace(0x890FEA0, "patapon_strcmp") -- strcmpFast__6SystemFv ('fast' strcmp)


[https://www.psdevwiki.com/ps4/Talk:PSP_Emulator_Compatibility_List#Official_PSPemu_Configuration_Files More patches can be found here]
-- Switch Select command to "Options" button.
emuObj.PadSetButtonsMode(pad.BUTTONS_MODE_OPTION_IS_SELECT)


====Patches.lua====
-- Remove "Transfer Patapon Saved Data" option from New Game option
--axInsnReplace(0x8A46660, 0x24070002, 0x24070001) -- li  a3,0x2  (change 2 menu options to 1)
emuObj.RemapSavedata("UCUS98711", "CUSA06171", "504e802b04a1838c32b616abbe0b475fbea1c823825ef0df06cc2bad129ce2f7")


======Syphon Filter: Dark Mirror======
-- Fix "Tree of Life" unaligned lines and shadows
 
axObj.AddHook(0x884600C, 0x8c850010, function() -- PSP::Gfx::PrimitiveContext::setVertex2f
<pre>
local context = axObj.GetGpr(gpr.a0)
-- Lua 5.3
local cmdCount = axObj.ReadMem32(context + 0x14)
-- Title: Syphon Filter: Dark Mirror
if (cmdCount & 1) == 1 then -- we have at least 2 commands
 
local cmdBuffer = axObj.ReadMem32(context + 0x10)
-- Patches for fixing issues with post fx in games using the Syphon Filter/Resistance engine
local cx = axObj.GetFpr(12)
 
local cy = axObj.GetFpr(13)
apiRequest(1.0) -- request version 1.0 API. Calling apiRequest() is mandatory.
local ox = axObj.ReadMemFloat(cmdBuffer-12)
 
local oy = axObj.ReadMemFloat(cmdBuffer-8)
local emuObj = getEmuObject()
local cpu = getAXObject()
if cx == ox then
 
axObj.SetFpr(12, cx + 0.5)
-- The bloom filter uses 1.5 pixel jitter to make a ghetto blur. When up-ressed, this doesn't look good.
axObj.WriteMemFloat(cmdBuffer-12, ox + 0.5)
-- To compensate, reduce the jitter amount before rendering.
elseif cy == oy then
function BloomJitterPlusAdjust()
axObj.SetFpr(13, cy + 0.5)
-- 1.5 pixel "+" pattern
axObj.WriteMemFloat(cmdBuffer-8, oy + 0.5)
emuObj.AdjustUVJitter(0, 4, 0.0, 1.5)
emuObj.AdjustUVJitter(4, 4, 0.0, -1.5)
emuObj.AdjustUVJitter(8, 4, 1.5, 0.0)
emuObj.AdjustUVJitter(12, 4, -1.5, 0.0)
end
 
function BloomJitterCrossAdjust()
-- 1.5 pixel "x" pattern
emuObj.AdjustUVJitter(0, 4, 1.5, 1.5)
emuObj.AdjustUVJitter(4, 4, -1.5, 1.5)
emuObj.AdjustUVJitter(8, 4, 1.5, -1.5)
emuObj.AdjustUVJitter(12, 4, -1.5, -1.5)
end
 
local jitterFixPlus = emuObj.AddGPUHook(0x40dc000, 0, 16, 0x40d4000, BloomJitterPlusAdjust)
local jitterFixCross = emuObj.AddGPUHook(0x40d4000, 0, 16, 0x40dc000, BloomJitterCrossAdjust)
 
function depthquery()
local querystruct = 0x8eda968 -- this is always in a fixed location
-- the depth query struct is fixed to 24 entries
-- 0..15 seem to be always used for lights, 16..23 are for npcs
for i=0,23 do
local querytype = cpu.ReadMem32(querystruct+0)
local valid = cpu.ReadMem32(querystruct+1*4)
if valid ~= 0xffffffff then
--local queryx = cpu.ReadMem32(querystruct+2*4)
--local queryy = cpu.ReadMem32(querystruct+3*4)
--local querydepth = cpu.ReadMem32(querystruct+4*4)
--local querywidth = cpu.ReadMem32(querystruct+5*4)
--local queryheight = cpu.ReadMem32(querystruct+6*4)
--local param1c = cpu.ReadMem32(querystruct+7*4)
--local param20 = cpu.ReadMem32(querystruct+8*4)
local param24 = cpu.ReadMem32(querystruct+9*4)
--local result = cpu.ReadMemFloat(querystruct+10*4)
if param24 <= 0 then
cpu.WriteMem32(querystruct+1*4, 0xffffffff) -- to be removed from the list -> mark as invalid
else
if querytype == 3 then -- n x n coverage based occlusion used by lights. Object opacity is set to (visible_samples / total_samples)
cpu.WriteMemFloat(querystruct+10*4, 0.0) -- always hide lights
else -- Enemies use a 5-point (corners + center) occlusion check. Object is visible if any of the points is visible.
cpu.WriteMemFloat(querystruct+10*4, 1.0) -- set always visible
end
end
end
end
querystruct = querystruct + 0x2c
end
end
end
end)


cpu.AddHook(0x8c163d4, 0x27bdff80, depthquery) -- = addiu sp, sp, -0x80
-- LANGUAGES --
-- the hook code replaces the occlusion function, so just adjust the stack and return
local langCode = "us" -- default
cpu.InsnReplace(0x8c163d8, 0x34040000, 0x27bd0080) -- addiu sp, sp, 0x80
--local languageList = {"Japanese","English","UK","Italian","German","Spanish","French","Korean","Chinese","ns","nf","Dutch","Portuguese","gr","Belgium"}
cpu.InsnReplace(0x8c163dc, 0xafa40048, 0x03e00008) -- jr ra
--local gameLanguageCode = {"jp","us","uk","it","de","sp","fr","kr","cn","ns","nf","nl","pt","gr","be"}
cpu.InsnReplace(0x8c163e0, 0x3c0408ee, 0x00000000) -- nop
local languageList = {"","English","","","","","","","","Spanish","French","","","",""}
</pre>
local gameLanguageCode = {"","us","","","","","","","","ns","nf","","","",""}
 
======Patapon 2'''======


<pre>
-- US: english = 1, spanish = 9, french = 0xA (from Localize__Manager__setDefaultLangage)
-- Lua 5.3
-- EU: uk = 2, italian = 3, german = 4, spanish = 5, french = 6
-- Title:   Patapon 2 PSP - UCUS-98732 (USA)
-- JP: jp = 0
-- HP: ko = 7, ch = 8,
-- GLOBAL FUNCTIONS --


apiRequest(1.0) -- request version 1.0 API. Calling apiRequest() is mandatory.
local GLOBAL = 0x8B7D088 -- reawakeDeathUnit - offset 0x88A95E8 in $v1


local gpr = require( "ax-gpr-alias" ) -- you can access Allegrex GPR by alias (gpr.a0 / gpr["a0"])
function getGlobalAddr() -- gets Global to user data.
local emuObj = getEmuObject() -- emulator
-- address comes from: Labo::Bases::Camp::Controller::reawakeDeathUnit - offset 0x88A95E8 in $v1
local axObj = getAXObject() -- allegrex
-- add 0x20 to address to align it with the word "none"
local pad = require("pad")
local main = axObj.ReadMem32(GLOBAL) -- fixed Global address from: 0x88A95E8 -> 0x8c9fbc0
if main == 0xFFFFFFFF or main == 0 then
return 0xFFFFFFFF
end
local ptr = axObj.ReadMem32(main + 0x10c0) --> sets to: 0x8d07840
if ptr == 0xFFFFFFFF or ptr == 0 then
return 0xFFFFFFFF
end


-- Hook memcpy to catch framebuffer effects
return ptr
axFuncReplace(0x881D194, "patapon_memcpy")
end


-- Accelerate some functions
-- MAIN FUNCTIONS --
axFuncReplace(0x8804670, "__ptmf_scall")
axFuncReplace(0x8892230, "Renderer__makeWorldMatrix__4psysFv")
axFuncReplace(0x88209A8, "patapon_strcmp")
axFuncReplace(0x8815130, "sceGupSetStatus")
axFuncReplace(0x8851D84, "FMtx44__setRow__3PydFv")
axFuncReplace(0x88437F0, "Script__Talk__Controller__setDeltaTime__3PydFv")
axFuncReplace(0x8843B6C, "Script__Talk__Controller__setCmdId__3PydFv")
axFuncReplace(0x88441DC, "Script__Talk__Controller__getArgValuePtr__3PydFv_0")
axFuncReplace(0x89B25B0, "sceGmoCol4Multiply")
axFuncReplace(0x8910A60, "Gfx__CacheModel__getNodeMtx__6SystemFv")
axFuncReplace(0x8911440, "Gfx__StaticGmoModel__getNodeIdx__6SystemFv")
axFuncReplace(0x89114C8, "Gfx__StaticGmoModel__getNodeMtx__6SystemFv")
axFuncReplace(0x891157C, "Gfx__StaticGmoModel__getNodeMtx__6SystemFv_0")
axFuncReplace(0x881462C, "sceGuEnable", 0x8B3C050) -- param = gupbase pointer
axFuncReplace(0x8814684, "sceGuDisable", 0x8B3C050) -- param = gupbase pointer
axFuncReplace(0x89B2D84, "sceGmoFCurveEval_fastpath", 0x89B2D88) -- param = function entry if not fast path
--axFuncReplace(0x88D0788, "Game__Map__Weather__WindLocus__update__4LaboFv_loop", 0x88D0864) -- param = continue address
axFuncReplace(0x890FCBC, "convertLowerString__6SystemFv")
axFuncReplace(0x8877104, "convertLowerString__6SystemFv") -- convertLowerString__21@unnamed@BNDFile_cpp@Fv, same functionality
axFuncReplace(0x897927C, "__extendsfdf2")
axFuncReplace(0x8979AF8, "__muldf3")
axFuncReplace(0x8979A8C, "__adddf3")
axFuncReplace(0x897A750, "__truncdfsf2")
axFuncReplace(0x88CBD64, "RemapPacket", 0x8ACC394) -- param comes from RemapPacketAddr24 & RemapPacketAddr16
axFuncReplace(0x890FEA0, "patapon_strcmp") -- strcmpFast__6SystemFv ('fast' strcmp)


-- Switch Select command to "Options" button.
local H1 = function() -- Labo::Bases::Camp::Scene::updateTips
emuObj.PadSetButtonsMode(pad.BUTTONS_MODE_OPTION_IS_SELECT)
local v0 = axObj.GetGpr(gpr.v0)
if v0 > 0 then
emuObj.ThrottleMax()
else
emuObj.ThrottleNormal()
end
end


-- Remove "Transfer Patapon Saved Data" option from New Game option
local H2 = function() -- GameSystem__SaveDataController__setStateMessage
--axInsnReplace(0x8A46660, 0x24070002, 0x24070001) -- li  a3,0x2  (change 2 menu options to 1)
local ptr = axObj.GetGpr(gpr.a2)
emuObj.RemapSavedata("UCUS98711", "CUSA06171", "504e802b04a1838c32b616abbe0b475fbea1c823825ef0df06cc2bad129ce2f7")
local str = axObj.ReadMemStr16(ptr)
 
local newStr = "Now loading. Do not turn off the power."
-- Fix "Tree of Life" unaligned lines and shadows
-- english: Now loading./Do not remove the Memory Stick Duo™ /or turn off the system power.
axObj.AddHook(0x884600C, 0x8c850010, function() -- PSP::Gfx::PrimitiveContext::setVertex2f
-- spanish: Cargando./No extraigas el Memory Stick Duo™ /ni apagues el sistema.
local context = axObj.GetGpr(gpr.a0)
-- french: Chargement./Ne pas retirer le Memory Stick Duo™ /ou éteindre le système.
local cmdCount = axObj.ReadMem32(context + 0x14)
-- italian: Caricamento in corso.../Non rimuovere il Memory Stick Duo™ /e non spegnere il sistema.
if (cmdCount & 1) == 1 then -- we have at least 2 commands
-- german: Lädt./Bitte den Memory Stick Duo™ nicht entfernen /und das System nicht ausschalten.
local cmdBuffer = axObj.ReadMem32(context + 0x10)
-- japanese: システムデータをロード中です。/Memory Stick Duo™を抜き挿ししたり、/電源を切ったりしないでください。
local cx = axObj.GetFpr(12)
-- chinese: 系統資料載入中。/請勿插拔Memory Stick Duo™/或是關閉主機的電源。
local cy = axObj.GetFpr(13)
-- korean: 시스템 데이터를 불러오는 중입니다./Memory Stick Duo™를 빼거나/전원을 끄지 마십시오.
local ox = axObj.ReadMemFloat(cmdBuffer-12)
local oy = axObj.ReadMemFloat(cmdBuffer-8)
if cx == ox then
axObj.SetFpr(12, cx + 0.5)
axObj.WriteMemFloat(cmdBuffer-12, ox + 0.5)
elseif cy == oy then
axObj.SetFpr(13, cy + 0.5)
axObj.WriteMemFloat(cmdBuffer-8, oy + 0.5)
end
end
end)
 
-- LANGUAGES --
local langCode = "us" -- default
--local languageList = {"Japanese","English","UK","Italian","German","Spanish","French","Korean","Chinese","ns","nf","Dutch","Portuguese","gr","Belgium"}
--local gameLanguageCode = {"jp","us","uk","it","de","sp","fr","kr","cn","ns","nf","nl","pt","gr","be"}
local languageList = {"","English","","","","","","","","Spanish","French","","","",""}
local gameLanguageCode = {"","us","","","","","","","","ns","nf","","","",""}
 
-- US: english = 1, spanish = 9, french = 0xA (from Localize__Manager__setDefaultLangage)
-- EU: uk = 2, italian = 3, german = 4, spanish = 5, french = 6
-- JP: jp = 0
-- HP: ko = 7, ch = 8,
-- GLOBAL FUNCTIONS --
if string.find(str, "Now loading") then
 
newStr = "Now loading." -- English: Now loading./Do not remove the Memory Stick Duo™ /or turn off the system power.
local GLOBAL = 0x8B7D088 -- reawakeDeathUnit - offset 0x88A95E8 in $v1
axObj.WriteMemStr16Z(ptr, newStr)
 
elseif string.find(str, "Checking Memory Stick") then
function getGlobalAddr() -- gets Global to user data.
newStr = "Please wait." -- English: Checking Memory Stick Duo™.
-- address comes from: Labo::Bases::Camp::Controller::reawakeDeathUnit - offset 0x88A95E8 in $v1
axObj.WriteMemStr16Z(ptr, newStr)
-- add 0x20 to address to align it with the word "none"
elseif string.find(str, "Now saving")then
newStr = "Now saving." -- English: Now saving./Do not remove the Memory Stick Duo™ /or turn off the system power.
local main = axObj.ReadMem32(GLOBAL) -- fixed Global address from: 0x88A95E8 -> 0x8c9fbc0
axObj.WriteMemStr16Z(ptr, newStr)
if main == 0xFFFFFFFF or main == 0 then
--
return 0xFFFFFFFF
elseif string.find(str, "Cargando.") then
end
newStr = "Cargando..." -- Spanish: Cargando./No extraigas el Memory Stick Duo™ /ni apagues el sistema.
local ptr = axObj.ReadMem32(main + 0x10c0) --> sets to: 0x8d07840
axObj.WriteMemStr16Z(ptr, newStr)
if ptr == 0xFFFFFFFF or ptr == 0 then
elseif string.find(str, "Guardando...")then
return 0xFFFFFFFF
newStr = "Espera..." -- Spanish: Guardando.../No extraigas el Memory Stick Duo™ /ni apagues el sistema.
end
axObj.WriteMemStr16Z(ptr, newStr)
 
elseif string.find(str, "Comprobando el Memory Stick") then
return ptr
newStr = "Guardando..." -- Spanish: Comprobando el Memory Stick Duo™.
end
axObj.WriteMemStr16Z(ptr, newStr)
 
--
-- MAIN FUNCTIONS --
elseif string.find(str, "Chargement.") then
 
newStr = "Chargement." -- French: Chargement./Ne pas retirer le Memory Stick Duo™ /ou éteindre le système.
local H1 = function() -- Labo::Bases::Camp::Scene::updateTips
axObj.WriteMemStr16Z(ptr, newStr)
local v0 = axObj.GetGpr(gpr.v0)
elseif string.find(str, "Vérification du Memory Stick")then
if v0 > 0 then
newStr = "Veuillez patienter." -- French: Vérification du Memory Stick Duo™.
emuObj.ThrottleMax()
axObj.WriteMemStr16Z(ptr, newStr)
else
elseif string.find(str, "Sauvegarde.") then
emuObj.ThrottleNormal()
newStr = "Sauvegarde en cours." -- French: Sauvegarde./Ne pas retirer le Memory Stick Duo™ /ou éteindre le système.
end
axObj.WriteMemStr16Z(ptr, newStr)
end
--
 
elseif string.find(str, "Caricamento in corso") then
local H2 = function() -- GameSystem__SaveDataController__setStateMessage
newStr = "Caricamento in corso." -- Italian: Caricamento in corso.../Non rimuovere il Memory Stick Duo™ /e non spegnere il sistema.
local ptr = axObj.GetGpr(gpr.a2)
local str = axObj.ReadMemStr16(ptr)
local newStr = "Now loading. Do not turn off the power."
-- english: Now loading./Do not remove the Memory Stick Duo™ /or turn off the system power.
-- spanish: Cargando./No extraigas el Memory Stick Duo™ /ni apagues el sistema.
-- french: Chargement./Ne pas retirer le Memory Stick Duo™ /ou éteindre le système.
-- italian: Caricamento in corso.../Non rimuovere il Memory Stick Duo™ /e non spegnere il sistema.
-- german: Lädt./Bitte den Memory Stick Duo™ nicht entfernen /und das System nicht ausschalten.
-- japanese: システムデータをロード中です。/Memory Stick Duo™を抜き挿ししたり、/電源を切ったりしないでください。
-- chinese: 系統資料載入中。/請勿插拔Memory Stick Duo™/或是關閉主機的電源。
-- korean: 시스템 데이터를 불러오는 중입니다./Memory Stick Duo™를 빼거나/전원을 끄지 마십시오.
if string.find(str, "Now loading") then
newStr = "Now loading." -- English: Now loading./Do not remove the Memory Stick Duo™ /or turn off the system power.
axObj.WriteMemStr16Z(ptr, newStr)
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Checking Memory Stick") then
elseif string.find(str, "Controllo del Memory Stick")then
newStr = "Please wait." -- English: Checking Memory Stick Duo™.
newStr = "Attendi." -- Italian: Controllo del Memory Stick Duo™.
axObj.WriteMemStr16Z(ptr, newStr)
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Now saving")then
elseif string.find(str, "Salvataggio in corso") then
newStr = "Now saving." -- English: Now saving./Do not remove the Memory Stick Duo™ /or turn off the system power.
newStr = "Salvataggio in corso." -- Italian: Salvataggio in corso.../Non rimuovere il Memory Stick Duo™ /e non spegnere il sistema.
axObj.WriteMemStr16Z(ptr, newStr)
axObj.WriteMemStr16Z(ptr, newStr)
--
--
elseif string.find(str, "Cargando.") then
elseif string.find(str, "Lädt") then
newStr = "Cargando..." -- Spanish: Cargando./No extraigas el Memory Stick Duo™ /ni apagues el sistema.
newStr = "Lädt." -- German: Lädt./Bitte den Memory Stick Duo™ nicht entfernen /und das System nicht ausschalten.
axObj.WriteMemStr16Z(ptr, newStr)
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Guardando...")then
elseif string.find(str, "Memory Stick Duo™ wird überprüft")then
newStr = "Espera..." -- Spanish: Guardando.../No extraigas el Memory Stick Duo™ /ni apagues el sistema.
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Comprobando el Memory Stick") then
newStr = "Guardando..." -- Spanish: Comprobando el Memory Stick Duo™.
axObj.WriteMemStr16Z(ptr, newStr)
--
elseif string.find(str, "Chargement.") then
newStr = "Chargement." -- French: Chargement./Ne pas retirer le Memory Stick Duo™ /ou éteindre le système.
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Vérification du Memory Stick")then
newStr = "Veuillez patienter." -- French: Vérification du Memory Stick Duo™.
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Sauvegarde.") then
newStr = "Sauvegarde en cours." -- French: Sauvegarde./Ne pas retirer le Memory Stick Duo™ /ou éteindre le système.
axObj.WriteMemStr16Z(ptr, newStr)
--
elseif string.find(str, "Caricamento in corso") then
newStr = "Caricamento in corso." -- Italian: Caricamento in corso.../Non rimuovere il Memory Stick Duo™ /e non spegnere il sistema.
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Controllo del Memory Stick")then
newStr = "Attendi." -- Italian: Controllo del Memory Stick Duo™.
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Salvataggio in corso") then
newStr = "Salvataggio in corso." -- Italian: Salvataggio in corso.../Non rimuovere il Memory Stick Duo™ /e non spegnere il sistema.
axObj.WriteMemStr16Z(ptr, newStr)
--
elseif string.find(str, "Lädt") then
newStr = "Lädt." -- German: Lädt./Bitte den Memory Stick Duo™ nicht entfernen /und das System nicht ausschalten.
axObj.WriteMemStr16Z(ptr, newStr)
elseif string.find(str, "Memory Stick Duo™ wird überprüft")then
newStr = "Bitte warten." -- German: Memory Stick Duo™ wird überprüft.
newStr = "Bitte warten." -- German: Memory Stick Duo™ wird überprüft.
axObj.WriteMemStr16Z(ptr, newStr)
axObj.WriteMemStr16Z(ptr, newStr)
Line 997: Line 796:


== Emulators ==
== Emulators ==
 
<pre>Every emulator is programmed in a different way, sometimes choosing the right emulator is the only possible way to fix a game. Emulators are not provided pre-installed on the ps4, they have to be unpacked from a backup that's downloaded from the ps store from that specific game. this list includes The typical usage of some of The emulators.</pre>
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Emulator !! Usage !! API Version !! Similar emulators (compatibility)
! Emulator !! Usage !! API Version !! Similar emulators (compatibility)
|-
|-
| Echochrome || The default PSP emulator for PSPFPKG tool at the time of writing and the best in terms of compatibility. || ? || ?
| Echochrome || The default psp emulator for PSPFPKG tool at the time of writing and the best in terms of compatibility. || ? || ?
|-
| Resistance: Retribution ||  || ? || ?
|-
| LocoRoco Midnight Carnival || ? || ? || ?
|-
| LocoRoco Remastered || ? || ? || ?
|-
|-
| Loco Roco 2 PSP DEMO - NPJG00011 (JP) Kiosk Demo || ? || ? || ?
| LocoRoco Midnight Carnival  || ? || ? || ?
|-
|-
| Patapon 2 PSP - UCUS98732 (USA) || ? || ? || ?
| LocoRoco 1  || ? || ? || ?
|-
|-
| Castlevania Requiem || ? || ? || ?
| LocoRoco 2  || ? || ? || ?
|-
|-
| Patapon 2 || ? || ? || ?
| Castlevania Requiem  || ? || ? || ?
|-
|-
| PaRappa the Rapper Demo || An unofficial emulator developed by Sony with very bad compatibility || ? || ?
| Patapon 2 || ? || ? || ?
|-
|-
| PaRappa the Rapper || An unofficial emulator developed by Sony with very bad compatibility || ? || ?
| PaRappa the Rapper || An unofficial emulator developed by sony with very bad compatibility || ? || ?
|-
|-
| Syphon Filter: Dark Mirror || ? || ? || ?
|}
|}


== Memory mapping ==
==Memory mapping==
 
<br>'''Note''': The memory on PPSSPP is 0x4000 offsets ahead of the memory on the PS4
<br>'''Note''': The memory on PPSSPP is 0x4000 offsets ahead of the memory on the PS4
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
! Size !! Offset From -> Offset To !! Name
! Size !! Offset From -> Offset To !! Name
|-
|-
| || 1008000000 -> 10887FFFFF ||   Allegrex memory(?)
| || 1008000000 -> 10887FFFFF || ||  Allegrex memory(?)
|-
|-
|640.00MB  || 228200000 -> 250200000 ||
|640.00MB  || 228200000 -> 250200000 ||
Line 1,052: Line 843:
===Registers map===
===Registers map===
<br>Registers that are marked with '''(?)''' are untested but should be accurate.
<br>Registers that are marked with '''(?)''' are untested but should be accurate.
<br>*'''Note''': The offsets' positions change as the CLI file's content increases, but the offsets should still be somewhere nearby the offsets listed below and the layout should be the same regardless. The PC pointer script can be used to locate another PC register properly in Echochrome's emulator
<br>*'''Note''': The offsets' positions change as the CLI file's content increases, but the offsets should still be somewhere nearby the offsets below and the layout should be the same regardless.
{| class=wikitable style="border: none; background: none;"
{| class=wikitable style="border: none; background: none;"
! scope=col | GPR
! scope=col | GPR
Line 1,138: Line 929:
|-
|-
|}
|}
====PC pointer====
<br>PS4CHEATER
<br>'''PSP.cht'''
<pre>
1.5|eboot.bin|ID:|VER:01.00|FM:505
simple pointer|pointer|4 bytes|@C6B8C8_2_6B8C8+210+108|data|4 bytes|143011412|0||
</pre>
'''VFPU'''
'''VFPU'''
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
{| cellspacing="0" cellpadding="2" border="1" class="wikitable" style="text-align: center;"
Line 1,219: Line 1,003:
! Issue !! Games affected !! Solution !! Description
! Issue !! Games affected !! Solution !! Description
|-
|-
| No gamdata installation functionality (?)|| || ||
| Lack of ability to install gamedata (?)|| || ||
|-
| Highly unoptimized graphics renderer || || || Low fps
|-
| No support for some syscalls || || ||
|-
|-
|}
|}


= Lua include files =
=LUA include files=
 
<br>Files that need to be placed in the '''/lua_include/''' folder
<br>Files that need to be placed in the '''/lua_include/''' folder


'''uv-clamping.lua'''
'''ax-gpr-alias.lua'''
<pre>
<pre>
print ("Loading uv-clamping.lua from global scripts")


UV_CLAMPING_ENABLE = true
-- Recommended method to import this module:
UV_CLAMPING_DISABLE = false
--  local gpr = require("ax-gpr-alias")


UV_CLAMPING_USE_ZERO_EDGE_ALPHA = true
UV_CLAMPING_DONT_USE_ZERO_EDGE_ALPHA = false


emuObj = getEmuObject()
gpr = {}


-- Turns off UV clamping for the given list of textures.
gpr.zero = 0
-- textureTable: A list of texture base addresses.
gpr.at  = 1
DisableUvClampingForTextures = function(textureTable)
gpr.v0  = 2
gpr.v1  = 3
if emuObj.OverrideUvClampingState then
gpr.a0  = 4
for _, texAddr in ipairs(textureTable) do
gpr.a1  = 5
emuObj.OverrideUvClampingState(texAddr, UV_CLAMPING_DISABLE, UV_CLAMPING_DONT_USE_ZERO_EDGE_ALPHA);
gpr.a2  = 6
end
gpr.a3  = 7
else
gpr.t0  = 8
print ("This emulator does not support OverrideUvClampingState()")
gpr.t1  = 9
end
gpr.t2  = 10
end
gpr.t3  = 11
 
gpr.t4  = 12
</pre>
gpr.t5  = 13
'''sce-locale.lua'''
gpr.t6  = 14
<pre>
gpr.t7  = 15
print ("Loading sce-locale.lua from global scripts")
gpr.s0  = 16
gpr.s1  = 17
gpr.s2  = 18
gpr.s3  = 19
gpr.s4  = 20
gpr.s5  = 21
gpr.s6  = 22
gpr.s7  = 23
gpr.t8  = 24
gpr.t9  = 25
gpr.k0  = 26
gpr.k1  = 27
gpr.gp  = 28
gpr.sp  = 29
gpr.fp  = 30
gpr.ra  = 31


-- Language codes
return gpr
--
-- ja    Japanese
-- en    English (US)
-- fr    French (France)
-- es    Spanish (Spain)
-- de    German
-- it    Italian
-- nl    Dutch
-- pt    Portuguese (Portugal)
-- ru    Russian
-- ko    Korean
-- zh-TW  Chinese (traditional)
-- zh-CN  Chinese (simplified)
-- fi    Finnish
-- sv    Swedish
-- da    Danish
-- no    Norwegian
-- pl    Polish
-- pt-BR  Portuguese (Brazil)
-- en-GB  English (UK)
-- tr    Turkish
-- es-MX  Spanish (Latin America)
-- ar    Arabic
-- fr-CA  French (Canada)
-- cs    Czech
-- hu    Hungarian
-- el    Greek ("Ελληνικά" in the system language menu)
-- ro    Romanian
-- th    Thai
-- vi    Vietnamese
-- id    Indonesian
-- uk    Ukrainian


-- returns locale (en-US) and language only (us), useful for lookups with fallback.
</pre>
GetLocaleLangPair = function()
'''multiapp.lua'''
local locale, lang
<pre>
locale = AppHost_GetLocaleTag()
-- Recommended method to import this module:
lang = locale:sub(1,2)    -- grab first two digits, eg. en-US -> en
--   local mapp = require("mapp")
 
--
print ("[BOOT] App Host Langauge =", lang)
-- Multi-application support module
 
-- Wraps common hook calls to support multiple executables
if locale ~= nil then
--
print ("[BOOT] App Host Locale =", locale)
else
print ("[BOOT] Deprecated Native Language =", lang)
end


return locale, lang
local emuObj = getEmuObject() -- emulator
end
local axObj = getAXObject() -- allegrex


FindLocaleTableKey = function(table, primary, fallback, default)
mapp = {}
-- try for a specific Locale, and if that fails fallback on just a language (without region),
mapp.curAppName = emuObj.GetAppName()
-- and if that fails fallback on default.


local keyres = primary
mapp.AddBootHook = function(app, func)
if keyres == nil or table[keyres] == nil then
if mapp[app] == nil then
keyres = fallback
mapp[app] = {}
end
end


if keyres == nil or table[keyres] == nil then
mapp[app].boot = func
print ("WARNING: No table entry for locale", primary, "or language", fallback, ", using default", default);
keyres = default
else
print ("Found locale table entry", keyres);
end
 
return keyres
end
end


</pre>
mapp.AddHook = function(app, pc, verify, func)
'''disc-selection.lua'''
if mapp[app] == nil then
<pre>
mapp[app] = {}
print ("Loading disc-selection.lua from global scripts")
require "sce-locale"
 
-- Determines and sets the active SKU.
--
-- sku_map: Cannot be nil.  A table of the form
-- {
-- en = <sku dir name>,
-- fr = <sku dir name>,
-- de = <sku dir name>,
-- it = <sku dir name>,
-- es = <sku dir name>,
--  ...
-- }
--
RegisterSkus = function(sku_map, default_locale)
if default_locale == nil then
default_locale = "en"
end
end
local locale, lang = GetLocaleLangPair()
local key = FindLocaleTableKey(sku_map, locale, lang, default_locale)
if mapp[app].hooks == nil then
local sku_name = sku_map[key]
mapp[app].hooks = {}
 
mapp[app].hookids = 1
if EM_SetActiveSku == nil then
print "EM_SetActiveSku is undefined, use the stable branch of the packager or use a new version of the emulator."
end
end
EM_SetActiveSku(sku_name)
 
local localid = mapp[app].hookids
mapp[app].hookids = mapp[app].hookids + 1
local handler = { addr = pc, v = verify, f = func, id = 0 }
if mapp.curAppName == app then
handler.id = axObj.AddHook(pc, verify, func)
end
-- print(string.format("Added Hook for app: %s, pc=%08x, handler=%d", app, pc, localid))
mapp[app].hooks[localid] = handler
return localid
end
end


</pre>
mapp.RemoveHook = function(app, hookid)
 
-- print(string.format("RemoveHook for app: %s, id=%d", app, hookid))
'''ax-gpr-alias.lua'''
<pre>
if mapp[app] ~= nil then
 
if mapp[app].hooks ~= nil then
-- Recommended method to import this module:
if mapp[app].hooks[hookid] ~= nil then
--  local gpr = require("ax-gpr-alias")
local id = mapp[app].hooks[hookid].id
mapp[app].hooks[hookid] = nil -- WBD 7/6/2018
if mapp.curAppName == app and id > 0 then
axObj.RemoveHook(id)
end
end
end
end
end


mapp.GetHookPC = function(app, hookid)
if mapp[app] ~= nil then
if mapp[app].hooks ~= nil then
if mapp[app].hooks[hookid] ~= nil then
return mapp[app].hooks[hookid].addr
end
end
end
return 0
end


gpr = {}
mapp.AddVSyncHook = function(app, func)
 
if mapp[app] == nil then
gpr.zero = 0
mapp[app] = {}
gpr.at  = 1
end
gpr.v0  = 2
gpr.v1  = 3
mapp[app].vsync = func
gpr.a0  = 4
gpr.a1  = 5
if mapp.curAppName == app then
gpr.a2  = 6
emuObj.AddVsyncHook(func)
gpr.a3  = 7
end
gpr.t0  = 8
end
gpr.t1  = 9
 
gpr.t2  = 10
mapp.RemoveVSyncHook = function(app)
gpr.t3  = 11
if mapp[app] == nil then
gpr.t4  = 12
mapp[app] = {}
gpr.t5  = 13
end
gpr.t6  = 14
gpr.t7  = 15
if mapp[app].vsync ~= nil then
gpr.s0  = 16
table.remove(mapp[app].vsync)
gpr.s1  = 17
end
gpr.s2  = 18
gpr.s3  = 19
if mapp.curAppName == app then
gpr.s4  = 20
emuObj.RemoveVsyncHook(func)
gpr.s5  = 21
end
gpr.s6  = 22
end
gpr.s7  = 23
gpr.t8  = 24
gpr.t9  = 25
gpr.k0  = 26
gpr.k1  = 27
gpr.gp  = 28
gpr.sp  = 29
gpr.fp  = 30
gpr.ra  = 31


return gpr
-- Actual switch functionality
emuObj.AddBootHook(function()
local app = emuObj.GetAppName()


</pre>
if app ~= mapp.curAppName then
'''multiapp.lua'''
-- switch out the old handlers
<pre>
-- print(string.format("Switching out handlers for app: %s", mapp.curAppName))
-- Recommended method to import this module:
if mapp[mapp.curAppName] ~= nil then
--   local mapp = require("mapp")
if mapp[mapp.curAppName].vsync ~= nil then
--
emuObj.RemoveVsyncHook()
-- Multi-application support module
end
-- Wraps common hook calls to support multiple executables
--
if mapp[mapp.curAppName].hooks ~= nil then
 
local hooks = mapp[mapp.curAppName].hooks
local emuObj = getEmuObject() -- emulator
local axObj = getAXObject() -- allegrex
-- print(string.format("hooks: %d", #hooks))
 
mapp = {}
for k,v in pairs(hooks) do
mapp.curAppName = emuObj.GetAppName()
if v.id > 0 then
 
axObj.RemoveHook(v.id)
mapp.AddBootHook = function(app, func)
v.id = 0
if mapp[app] == nil then
end
mapp[app] = {}
end
end
end
 
end
mapp[app].boot = func
end
-- switch current app name
 
mapp.curAppName = app
mapp.AddHook = function(app, pc, verify, func)
if mapp[app] == nil then
mapp[app] = {}
end
if mapp[app].hooks == nil then
mapp[app].hooks = {}
mapp[app].hookids = 1
end
local localid = mapp[app].hookids
mapp[app].hookids = mapp[app].hookids + 1
local handler = { addr = pc, v = verify, f = func, id = 0 }
if mapp.curAppName == app then
-- install the new handlers
handler.id = axObj.AddHook(pc, verify, func)
-- print(string.format("Switching in handlers for app: %s", mapp.curAppName))
end
if mapp[mapp.curAppName] ~= nil then
if mapp[mapp.curAppName].vsync ~= nil then
-- print(string.format("Added Hook for app: %s, pc=%08x, handler=%d", app, pc, localid))
emuObj.AddVsyncHook(mapp[mapp.curAppName].vsync)
end
mapp[app].hooks[localid] = handler
return localid
if mapp[mapp.curAppName].hooks ~= nil then
end
local hooks = mapp[mapp.curAppName].hooks
 
mapp.RemoveHook = function(app, hookid)
-- print(string.format("hooks: %d", #hooks))
-- print(string.format("RemoveHook for app: %s, id=%d", app, hookid))
for k,v in pairs(hooks) do
if mapp[app] ~= nil then
v.id = axObj.AddHook(v.addr, v.v, v.f)
if mapp[app].hooks ~= nil then
if mapp[app].hooks[hookid] ~= nil then
local id = mapp[app].hooks[hookid].id
mapp[app].hooks[hookid] = nil -- WBD 7/6/2018
if mapp.curAppName == app and id > 0 then
axObj.RemoveHook(id)
end
end
end
end
end
end
end
end
end
 
if mapp[mapp.curAppName] ~= nil then
mapp.GetHookPC = function(app, hookid)
if mapp[mapp.curAppName].boot ~= nil then
if mapp[app] ~= nil then
mapp[mapp.curAppName].boot()
if mapp[app].hooks ~= nil then
if mapp[app].hooks[hookid] ~= nil then
return mapp[app].hooks[hookid].addr
end
end
end
end
end
end)
return 0
end


mapp.AddVSyncHook = function(app, func)
return mapp
if mapp[app] == nil then
mapp[app] = {}
end
mapp[app].vsync = func
if mapp.curAppName == app then
emuObj.AddVsyncHook(func)
end
end


mapp.RemoveVSyncHook = function(app)
</pre>
if mapp[app] == nil then
 
mapp[app] = {}
'''pad.lua'''
end
<pre>
-- Recommended method to import this module:
if mapp[app].vsync ~= nil then
--  local pad = require("pad")
table.remove(mapp[app].vsync)
--
end
-- Buttons marked PS4 are not used by the emulator, but can be read from Lua
--
if mapp.curAppName == app then
-- Read the Pad state with getEmuObject().PadRead()
emuObj.RemoveVsyncHook(func)
-- ie:
end
-- local padstate = getEmuObject().PadRead()
end
--


-- Actual switch functionality
pad = {}
emuObj.AddBootHook(function()
local app = emuObj.GetAppName()


if app ~= mapp.curAppName then
pad.L3        = 0x00000002 -- L3 (PS4)
-- switch out the old handlers
pad.R3        = 0x00000004 -- R3 (PS4)
-- print(string.format("Switching out handlers for app: %s", mapp.curAppName))
pad.OPTIONS  = 0x00000008 -- Options (PS4)
if mapp[mapp.curAppName] ~= nil then
pad.UP        = 0x00000010 -- Up
if mapp[mapp.curAppName].vsync ~= nil then
pad.RIGHT    = 0x00000020 -- Right
emuObj.RemoveVsyncHook()
pad.DOWN      = 0x00000040 -- Down
end
pad.LEFT      = 0x00000080 -- Left
pad.L2        = 0x00000100 -- L2 (PS4)
if mapp[mapp.curAppName].hooks ~= nil then
pad.R2        = 0x00000200 -- R2 (PS4)
local hooks = mapp[mapp.curAppName].hooks
pad.L1        = 0x00000400 -- L1
pad.R1        = 0x00000800 -- R1
-- print(string.format("hooks: %d", #hooks))
pad.TRIANGLE  = 0x00001000 -- Triangle
pad.CIRCLE    = 0x00002000 -- Circle
for k,v in pairs(hooks) do
pad.CROSS    = 0x00004000 -- Cross
if v.id > 0 then
pad.SQUARE    = 0x00008000 -- Square
axObj.RemoveHook(v.id)
pad.SELECT    = 0x00010000 -- Select
v.id = 0
pad.START    = 0x00020000 -- Start
end
 
end
-- Automap SELECT or START to the Options Button, leaving the full touchar for the opposite, with getEmuObject().PadSetButtonsMode(mode)
end
-- ie:
end
-- getEmuObject().PadSetButtonsMode(pad.BUTTONS_MODE_OPTION_IS_SELECT)
 
-- switch current app name
pad.BUTTONS_MODE_NORMAL = 0 -- Touch bar is split in two for Start/Select. Option is unmapped (default behaviour)
mapp.curAppName = app
pad.BUTTONS_MODE_OPTION_IS_SELECT = 1 -- Touch bar is Start. Option is Select
pad.BUTTONS_MODE_OPTION_IS_START = 2 -- Touch bar is Select. Option is Start
-- install the new handlers
 
-- print(string.format("Switching in handlers for app: %s", mapp.curAppName))
return pad
if mapp[mapp.curAppName] ~= nil then
 
if mapp[mapp.curAppName].vsync ~= nil then
</pre>
emuObj.AddVsyncHook(mapp[mapp.curAppName].vsync)
 
end
=Information=
Note: Missing entries
if mapp[mapp.curAppName].hooks ~= nil then
==Folder/File layout==
local hooks = mapp[mapp.curAppName].hooks
-- print(string.format("hooks: %d", #hooks))
for k,v in pairs(hooks) do
v.id = axObj.AddHook(v.addr, v.v, v.f)
end
end
end
end
if mapp[mapp.curAppName] ~= nil then
if mapp[mapp.curAppName].boot ~= nil then
mapp[mapp.curAppName].boot()
end
end
end)
 
return mapp
 
</pre>
 
'''pad.lua'''
<pre>
<pre>
-- Recommended method to import this module:
├── assets
--   local pad = require("pad")
│  ├── common
--
│  └── PSPHD
-- Buttons marked PS4 are not used by the emulator, but can be read from Lua
├── app
--
│  └── USER_L0.IMG
-- Read the Pad state with getEmuObject().PadRead()
├── lua_include
-- ie:
│  ├── ax-gpr-alias.lua
-- local padstate = getEmuObject().PadRead()
│  ├── multiapp.lua
--
  └── pad.lua
├── scripts
│  ├──XXXXYYYYY_patches.lua
│  ├──XXXXYYYYY_features.lua
│  ├──XXXXYYYYY_tooling.lua
│  └──XXXXYYYYY_trophies.lua
├── sce_module
├── sce_sys
├── vms
├── trophy_data
├── usermodule
│  └──libfont.lib
├── sce_discmap.plt
├── eboot.bin
├── revision.conf
├── package-ps4.conf
└── config-title.txt
</pre>


pad = {}
==Other==
<pre>
XXXXYYYYY_config.txt
videos/
.mp4
videos/%08x.mp4
audio/%08x.ogg


pad.L3        = 0x00000002 -- L3 (PS4)
Paths:  
pad.R3        = 0x00000004 -- R3 (PS4)
pad.OPTIONS  = 0x00000008 -- Options (PS4)
pad.UP        = 0x00000010 -- Up
pad.RIGHT    = 0x00000020 -- Right
pad.DOWN      = 0x00000040 -- Down
pad.LEFT      = 0x00000080 -- Left
pad.L2        = 0x00000100 -- L2 (PS4)
pad.R2        = 0x00000200 -- R2 (PS4)
pad.L1        = 0x00000400 -- L1
pad.R1        = 0x00000800 -- R1
pad.TRIANGLE  = 0x00001000 -- Triangle
pad.CIRCLE    = 0x00002000 -- Circle
pad.CROSS    = 0x00004000 -- Cross
pad.SQUARE    = 0x00008000 -- Square
pad.SELECT    = 0x00010000 -- Select
pad.START    = 0x00020000 -- Start
 
-- Automap SELECT or START to the Options Button, leaving the full touchar for the opposite, with getEmuObject().PadSetButtonsMode(mode)
-- ie:
-- getEmuObject().PadSetButtonsMode(pad.BUTTONS_MODE_OPTION_IS_SELECT)
 
pad.BUTTONS_MODE_NORMAL = 0 -- Touch bar is split in two for Start/Select. Option is unmapped (default behaviour)
pad.BUTTONS_MODE_OPTION_IS_SELECT = 1 -- Touch bar is Start. Option is Select
pad.BUTTONS_MODE_OPTION_IS_START = 2 -- Touch bar is Select. Option is Start
 
return pad


/app0/
/download0/
/savedata
/host/
/hostapp/
/data/
</pre>
</pre>


= config-emu-ps4.txt =
==Sample==
 
Example from Loco Roco 2 Kiosk Demo:
<pre>
; Windows configuration file for PSPHD
 
; Game Image
--image="data/USER_L0.IMG"
 
; Redirect host0: to a another directory (uncomment to enable).
; By default it's mapped to the working directory where the executable starts
;--host="D:\Sony\PSPHD"
 
; To dump the original video in PMF format, uncomment the --dumpvideos line
; For example, with the current setting, it will save them in a "D:\Sony\PSPHD\videos" directory (make sure the directory exists)
;--dumpvideos="host0:videos"
 
; To dump the original audio in Atrac3 format, uncomment the --dumpaudio line
; For example, with the current setting, it will save them in a "D:\Sony\PSPHD\audio" directory (make sure the directory exists)
;--dumpaudio="host0:audio"
 
; To save the in-game textures as the game runs, uncomment the --texsave line
; For example, with the current setting, it will save them in a "D:\Sony\PSPHD\texdump" directory (make sure the directory exists)
;--texsave="host0:texdump"
;--texmissingsave="host0:texdump"
 
; To replace specific textures as the game runs, uncomment the --texreplace line
; For example, with the current setting, it will load them from the "D:\Sony\PSPHD\texreplace" directory
; If the --scale setting is set to 4 or 8, the program will also look for replacement textures on '4x' or '8x' directories within this directory
--texreplace="host0:texreplace"
 
; This forces alpha blending to on for replaced textures. (uncomment to enable)
; With this we can freely make use of a normal alpha channel on replacement textures
--replacementalpha=true
 
; This enables bilinear filtering on replaced textures. (uncomment to enable)
--replacementfilter=true
 
; Antialiasing mode. SSAA4x looks best, MSAA4x only smooths edges.
; Choices: off, SSAA4x, MSAA4x
--antialias=SSAA4x
 
; Enable switching between original and replacement textures at runtime using the L3 button on a DS4 or the 'T' key on Windows
;--texswitch=true
 
; Turns on the auto-resampler. Assumes textures in texreplace are at 8x resolution and resamples them at load
--autoresampler=true
 
; Turns on filtering of CLUT hashes to avoid repeat indexed textures
--texclutmode=filter
 
; Enable Multiple Savegames
--multisaves=true
 
; Custom locoroco2 texture hasher
--texcachemode="locoroco2"
 
; X/O button mode. "oenter" sets Circle as enter, "xenter" sets Cross as enter. If not present/enabled, it's selected by the system language (Asian
; languages default to oenter, everything else "xenter"). Notice this only works when the game queries the PSP OS for the button configuration.
--xobuttonmode="oenter"
 
; Use vector fonts for the system fonts
--fontreplace="host0:pspfonts"
 
; Enable encrypted savegames
--securesaves=true
 
; Adjust overall volume level (does not include pad speaker volume). Range from 0.0 (min) to 1.0 (max)
--volume="0.50"
 
; Use 5 cores to load textures at boot
--texloadcores=4
 
; LocoRoco mesh tesselation mode
--locorocomeshsmoothnonindexed=true
 
; Set age restriction
--agerestrict=0
 
--notrophies=true
</pre>


Example from PaRappa the Rapper:
<pre>; PS4 configuration file for PSPHD
<pre>
; PS4 configuration file for PSPHD
   
   
; Game Image
; Game Image
Line 1,746: Line 1,357:
--parappaalphahack=true
--parappaalphahack=true
</pre>
</pre>
 
==NIDs in HLE==
= Information =
 
Note: Missing entries
 
==Folder/File layout==
 
<pre>
├── assets
│  ├── common
│  └── PSPHD
├── app
│  └── USER_L0.IMG
├── lua_include
│  ├── ax-gpr-alias.lua
│  ├── multiapp.lua
│  ├── sce-locale.lua
│  ├── uv-clamping.lua
│  ├── disc-selection.lua
│  └── pad.lua
├── scripts
│  ├──XXXXYYYYY_patches.lua
│  ├──XXXXYYYYY_features.lua
│  ├──XXXXYYYYY_tooling.lua
│  └──XXXXYYYYY_trophies.lua
├── sce_module
├── sce_sys
├── vms
├── trophy_data
├── usermodule
│  └──libfont.lib
├── sce_discmap.plt
├── eboot.bin
├── revision.conf
├── package-ps4.conf
└── config-title.txt or config-emu-ps4.txt
</pre>
 
= Other files =
 
<pre>
XXXXYYYYY_config.txt
videos/
.mp4
videos/%08x.mp4
audio/%08x.ogg
</pre>
 
= Paths =
 
<pre>
/app0/
/download0/
/savedata
/host/
/hostapp/
/data/
</pre>
 
== NIDs in HLE ==
 
See also [https://www.psdevwiki.com/ps3/PSP_Emulation#4.46_PS3_PSP_HLE_NIDs 4.46 PS3 PSP HLE NIDs].
 
<pre>
<pre>
|HLEInterruptManager|
|HLEInterruptManager|
Line 2,352: Line 1,901:
* https://forums.ppsspp.org/showthread.php?tid=11961
* https://forums.ppsspp.org/showthread.php?tid=11961
* https://github.com/LunaMoo/PPSSPP_workarounds/blob/master/cheat.db
* https://github.com/LunaMoo/PPSSPP_workarounds/blob/master/cheat.db
* https://www.psdevwiki.com/ps4/PSP_Classics_Configuration_Files_(Official)
* https://www.psdevwiki.com/ps4/Talk:PSP_Emulator_Compatibility_List#Official_PSPemu_Configuration_Files
* https://www.psdevwiki.com/ps4/PSP_Classics_Configuration_Files_(Unofficial)
* https://www.psdevwiki.com/ps4/PSP_Emulator_Compatibility_List
* https://www.psdevwiki.com/ps4/PSP_Emulator_Compatibility_List


Please note that all contributions to PS4 Developer wiki are considered to be released under the GNU Free Documentation License 1.2 (see PS4 Developer wiki:Copyrights for details). If you do not want your writing to be edited mercilessly and redistributed at will, then do not submit it here.
You are also promising us that you wrote this yourself, or copied it from a public domain or similar free resource. Do not submit copyrighted work without permission!

To protect the wiki against automated edit spam, we kindly ask you to solve the following hCaptcha:

Cancel Editing help (opens in new window)