From adb940c07ecb28bcd5732e95a6eeb64c6e8b948f Mon Sep 17 00:00:00 2001 From: ZoweZilsio <208832798+ZoweZilsio@users.noreply.github.com> Date: Sat, 23 Aug 2025 18:08:38 +0000 Subject: [PATCH 1/3] Refactor repetitive code --- .../kr/co/iefriends/pcsx2/MainActivity.java | 348 +++++------------- 1 file changed, 97 insertions(+), 251 deletions(-) diff --git a/app/src/main/java/kr/co/iefriends/pcsx2/MainActivity.java b/app/src/main/java/kr/co/iefriends/pcsx2/MainActivity.java index c9a982c..8d419cc 100644 --- a/app/src/main/java/kr/co/iefriends/pcsx2/MainActivity.java +++ b/app/src/main/java/kr/co/iefriends/pcsx2/MainActivity.java @@ -1,5 +1,6 @@ package kr.co.iefriends.pcsx2; +import android.annotation.SuppressLint; import android.app.Activity; import android.content.Context; import android.content.Intent; @@ -15,6 +16,7 @@ import android.widget.FrameLayout; import androidx.activity.result.ActivityResultLauncher; import androidx.activity.result.contract.ActivityResultContracts; +import androidx.annotation.IdRes; import androidx.annotation.NonNull; import androidx.appcompat.app.AppCompatActivity; @@ -59,161 +61,83 @@ public class MainActivity extends AppCompatActivity { } // Buttons + void configureOnClickListener(@IdRes int id, View.OnClickListener onClickListener) { + View view = findViewById(id); + if (view != null) { + view.setOnClickListener(onClickListener); + } + } + + @SuppressLint("ClickableViewAccessibility") + void configureOnTouchListener(@IdRes int id, int... keyCodes) { + View view = findViewById(id); + if (view != null) { + view.setOnTouchListener((v, event) -> { + for (int keyCode : keyCodes) { + sendKeyAction(v, event.getAction(), keyCode); + } + return true; + }); + } + } + private void makeButtonTouch() { // Game file - MaterialButton btn_file = findViewById(R.id.btn_file); - if(btn_file != null) { - btn_file.setOnClickListener(v -> { - // Internal storage - Intent intent = new Intent(Intent.ACTION_GET_CONTENT); - intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); - intent.putExtra(Intent.EXTRA_ALLOW_MULTIPLE, false); - intent.setType("*/*"); - startActivityResultLocalFilePlay.launch(intent); - }); - } + configureOnClickListener(R.id.btn_file, v -> { + // Internal storage + Intent intent = new Intent(Intent.ACTION_GET_CONTENT); + intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); + intent.putExtra(Intent.EXTRA_ALLOW_MULTIPLE, false); + intent.setType("*/*"); + startActivityResultLocalFilePlay.launch(intent); + }); // Game save - MaterialButton btn_save = findViewById(R.id.btn_save); - if(btn_save != null) { - btn_save.setOnClickListener(v -> { - if(NativeApp.saveStateToSlot(1)) { - // Success - } else { - // Failed - } - NativeApp.resume(); - }); - } + configureOnClickListener(R.id.btn_save, v -> { + if (NativeApp.saveStateToSlot(1)) { + // Success + } else { + // Failed + } + NativeApp.resume(); + }); // Game load - MaterialButton btn_load = findViewById(R.id.btn_load); - if(btn_load != null) { - btn_load.setOnClickListener(v -> { - if(NativeApp.loadStateFromSlot(1)) { - // Success - } else { - // Failed - } - NativeApp.resume(); - }); - } + configureOnClickListener(R.id.btn_load, v -> { + if (NativeApp.loadStateFromSlot(1)) { + // Success + } else { + // Failed + } + NativeApp.resume(); + }); ////// // RENDERER - - MaterialButton btn_ogl = findViewById(R.id.btn_ogl); - if(btn_ogl != null) { - btn_ogl.setOnClickListener(v -> { - NativeApp.renderGpu(12); - }); - } - MaterialButton btn_vulkan = findViewById(R.id.btn_vulkan); - if(btn_vulkan != null) { - btn_vulkan.setOnClickListener(v -> { - NativeApp.renderGpu(14); - }); - } - MaterialButton btn_sw = findViewById(R.id.btn_sw); - if(btn_sw != null) { - btn_sw.setOnClickListener(v -> { - NativeApp.renderGpu(13); - }); - } + configureOnClickListener(R.id.btn_ogl, v -> NativeApp.renderGpu(12)); + configureOnClickListener(R.id.btn_vulkan, v -> NativeApp.renderGpu(14)); + configureOnClickListener(R.id.btn_sw, v -> NativeApp.renderGpu(13)); ////// // PAD + configureOnTouchListener(R.id.btn_pad_select, KeyEvent.KEYCODE_BUTTON_SELECT); - MaterialButton btn_pad_select = findViewById(R.id.btn_pad_select); - if(btn_pad_select != null) { - btn_pad_select.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_SELECT); - return true; - }); - } - MaterialButton btn_pad_start = findViewById(R.id.btn_pad_start); - if(btn_pad_start != null) { - btn_pad_start.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_START); - return true; - }); - } + configureOnTouchListener(R.id.btn_pad_start, KeyEvent.KEYCODE_BUTTON_START); - MaterialButton btn_pad_a = findViewById(R.id.btn_pad_a); - if(btn_pad_a != null) { - btn_pad_a.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_A); - return true; - }); - } - MaterialButton btn_pad_b = findViewById(R.id.btn_pad_b); - if(btn_pad_b != null) { - btn_pad_b.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_B); - return true; - }); - } - MaterialButton btn_pad_x = findViewById(R.id.btn_pad_x); - if(btn_pad_x != null) { - btn_pad_x.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_X); - return true; - }); - } - MaterialButton btn_pad_y = findViewById(R.id.btn_pad_y); - if(btn_pad_y != null) { - btn_pad_y.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_Y); - return true; - }); - } + configureOnTouchListener(R.id.btn_pad_a, KeyEvent.KEYCODE_BUTTON_A); + configureOnTouchListener(R.id.btn_pad_b, KeyEvent.KEYCODE_BUTTON_B); + configureOnTouchListener(R.id.btn_pad_x, KeyEvent.KEYCODE_BUTTON_X); + configureOnTouchListener(R.id.btn_pad_y, KeyEvent.KEYCODE_BUTTON_Y); //// + configureOnTouchListener(R.id.btn_pad_l1, KeyEvent.KEYCODE_BUTTON_L1); + configureOnTouchListener(R.id.btn_pad_r1, KeyEvent.KEYCODE_BUTTON_R1); - MaterialButton btn_pad_l1 = findViewById(R.id.btn_pad_l1); - if(btn_pad_l1 != null) { - btn_pad_l1.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_L1); - return true; - }); - } - MaterialButton btn_pad_r1 = findViewById(R.id.btn_pad_r1); - if(btn_pad_r1 != null) { - btn_pad_r1.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_R1); - return true; - }); - } + configureOnTouchListener(R.id.btn_pad_l2, KeyEvent.KEYCODE_BUTTON_L2); + configureOnTouchListener(R.id.btn_pad_r2, KeyEvent.KEYCODE_BUTTON_R2); - MaterialButton btn_pad_l2 = findViewById(R.id.btn_pad_l2); - if(btn_pad_l2 != null) { - btn_pad_l2.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_L2); - return true; - }); - } - MaterialButton btn_pad_r2 = findViewById(R.id.btn_pad_r2); - if(btn_pad_r2 != null) { - btn_pad_r2.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_R2); - return true; - }); - } - - MaterialButton btn_pad_l3 = findViewById(R.id.btn_pad_l3); - if(btn_pad_l3 != null) { - btn_pad_l3.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_THUMBL); - return true; - }); - } - MaterialButton btn_pad_r3 = findViewById(R.id.btn_pad_r3); - if(btn_pad_r3 != null) { - btn_pad_r3.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_BUTTON_THUMBR); - return true; - }); - } + configureOnTouchListener(R.id.btn_pad_l3, KeyEvent.KEYCODE_BUTTON_THUMBL); + configureOnTouchListener(R.id.btn_pad_r3, KeyEvent.KEYCODE_BUTTON_THUMBR); //// @@ -227,112 +151,36 @@ public class MainActivity extends AppCompatActivity { final int PAD_R_DOWN = 122; final int PAD_R_LEFT = 123; - MaterialButton btn_pad_joy_lt = findViewById(R.id.btn_pad_joy_lt); - if(btn_pad_joy_lt != null) { - btn_pad_joy_lt.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_UP); - sendKeyAction(v, event.getAction(), PAD_L_LEFT); - return true; - }); - } - MaterialButton btn_pad_joy_t = findViewById(R.id.btn_pad_joy_t); - if(btn_pad_joy_t != null) { - btn_pad_joy_t.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_UP); - return true; - }); - } - MaterialButton btn_pad_joy_rt = findViewById(R.id.btn_pad_joy_rt); - if(btn_pad_joy_rt != null) { - btn_pad_joy_rt.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_UP); - sendKeyAction(v, event.getAction(), PAD_L_RIGHT); - return true; - }); - } - MaterialButton btn_pad_joy_l = findViewById(R.id.btn_pad_joy_l); - if(btn_pad_joy_l != null) { - btn_pad_joy_l.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_LEFT); - return true; - }); - } - MaterialButton btn_pad_joy_r = findViewById(R.id.btn_pad_joy_r); - if(btn_pad_joy_r != null) { - btn_pad_joy_r.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_RIGHT); - return true; - }); - } - MaterialButton btn_pad_joy_lb = findViewById(R.id.btn_pad_joy_lb); - if(btn_pad_joy_lb != null) { - btn_pad_joy_lb.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_LEFT); - sendKeyAction(v, event.getAction(), PAD_L_DOWN); - return true; - }); - } - MaterialButton btn_pad_joy_b = findViewById(R.id.btn_pad_joy_b); - if(btn_pad_joy_b != null) { - btn_pad_joy_b.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_DOWN); - return true; - }); - } - MaterialButton btn_pad_joy_rb = findViewById(R.id.btn_pad_joy_rb); - if(btn_pad_joy_rb != null) { - btn_pad_joy_rb.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), PAD_L_RIGHT); - sendKeyAction(v, event.getAction(), PAD_L_DOWN); - return true; - }); - } + configureOnTouchListener(R.id.btn_pad_joy_lt, PAD_L_UP, PAD_L_LEFT); + configureOnTouchListener(R.id.btn_pad_joy_t, PAD_L_UP); + configureOnTouchListener(R.id.btn_pad_joy_rt, PAD_L_UP, PAD_L_RIGHT); + configureOnTouchListener(R.id.btn_pad_joy_r, PAD_L_RIGHT); + configureOnTouchListener(R.id.btn_pad_joy_rb, PAD_L_DOWN, PAD_L_RIGHT); + configureOnTouchListener(R.id.btn_pad_joy_b, PAD_L_DOWN); + configureOnTouchListener(R.id.btn_pad_joy_lb, PAD_L_DOWN, PAD_L_LEFT); + configureOnTouchListener(R.id.btn_pad_joy_l, PAD_L_LEFT); //// - - MaterialButton btn_pad_dir_top = findViewById(R.id.btn_pad_dir_top); - if(btn_pad_dir_top != null) { - btn_pad_dir_top.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_DPAD_UP); - return true; - }); - } - MaterialButton btn_pad_dir_bottom = findViewById(R.id.btn_pad_dir_bottom); - if(btn_pad_dir_bottom != null) { - btn_pad_dir_bottom.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_DPAD_DOWN); - return true; - }); - } - MaterialButton btn_pad_dir_left = findViewById(R.id.btn_pad_dir_left); - if(btn_pad_dir_left != null) { - btn_pad_dir_left.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_DPAD_LEFT); - return true; - }); - } - MaterialButton btn_pad_dir_right = findViewById(R.id.btn_pad_dir_right); - if(btn_pad_dir_right != null) { - btn_pad_dir_right.setOnTouchListener((v, event) -> { - sendKeyAction(v, event.getAction(), KeyEvent.KEYCODE_DPAD_RIGHT); - return true; - }); - } + configureOnTouchListener(R.id.btn_pad_dir_top, KeyEvent.KEYCODE_DPAD_UP); + configureOnTouchListener(R.id.btn_pad_dir_bottom, KeyEvent.KEYCODE_DPAD_DOWN); + configureOnTouchListener(R.id.btn_pad_dir_left, KeyEvent.KEYCODE_DPAD_LEFT); + configureOnTouchListener(R.id.btn_pad_dir_right, KeyEvent.KEYCODE_DPAD_RIGHT); } public final ActivityResultLauncher startActivityResultLocalFilePlay = registerForActivityResult( new ActivityResultContracts.StartActivityForResult(), result -> { - if(result.getResultCode() == Activity.RESULT_OK) { + if (result.getResultCode() == Activity.RESULT_OK) { try { Intent _intent = result.getData(); - if(_intent != null) { + if (_intent != null) { m_szGamefile = _intent.getDataString(); - if(!TextUtils.isEmpty(m_szGamefile)) { + if (!TextUtils.isEmpty(m_szGamefile)) { restartEmuThread(); } } - } catch (Exception ignored) {} + } catch (Exception ignored) { + } } }); @@ -375,15 +223,15 @@ public class MainActivity extends AppCompatActivity { try { mEmulationThread.join(); mEmulationThread = null; + } catch (InterruptedException ignored) { } - catch (InterruptedException ignored) {} } int appPid = android.os.Process.myPid(); android.os.Process.killProcess(appPid); } - ////////////////////////////////////////////////////////////////////////////////////////////// + /// /////////////////////////////////////////////////////////////////////////////////////////// public void Initialize() { NativeApp.initializeOnce(getApplicationContext()); @@ -399,19 +247,19 @@ public class MainActivity extends AppCompatActivity { private void setSurfaceView(Object p_value) { FrameLayout fl_board = findViewById(R.id.fl_board); - if(fl_board != null) { - if(fl_board.getChildCount() > 0) { + if (fl_board != null) { + if (fl_board.getChildCount() > 0) { fl_board.removeAllViews(); } //// - if(p_value instanceof SDLSurface) { - fl_board.addView((SDLSurface)p_value); + if (p_value instanceof SDLSurface) { + fl_board.addView((SDLSurface) p_value); } } } public void startEmuThread() { - if(!isThread()) { + if (!isThread()) { mEmulationThread = new Thread(() -> NativeApp.runVMThread(m_szGamefile)); mEmulationThread.start(); } @@ -423,14 +271,14 @@ public class MainActivity extends AppCompatActivity { try { mEmulationThread.join(); mEmulationThread = null; + } catch (InterruptedException ignored) { } - catch (InterruptedException ignored) {} } //// startEmuThread(); } - ////////////////////////////////////////////////////////////////////////////////////////////// + /// /////////////////////////////////////////////////////////////////////////////////////////// @Override public boolean onGenericMotionEvent(MotionEvent event) { @@ -448,8 +296,7 @@ public class MainActivity extends AppCompatActivity { SDLControllerManager.onNativePadDown(p_event.getDeviceId(), p_keyCode); return true; } - } - else { + } else { if (p_keyCode == KeyEvent.KEYCODE_BACK) { finish(); return true; @@ -470,22 +317,22 @@ public class MainActivity extends AppCompatActivity { } public static void sendKeyAction(View p_view, int p_action, int p_keycode) { - if(p_action == MotionEvent.ACTION_DOWN) { + if (p_action == MotionEvent.ACTION_DOWN) { p_view.setPressed(true); int pad_force = 0; - if(p_keycode >= 110) { + if (p_keycode >= 110) { float _abs = 90; // Joystic test value _abs = Math.min(_abs, 100); pad_force = (int) (_abs * 32766.0f / 100); } NativeApp.setPadButton(p_keycode, pad_force, true); - } else if(p_action == MotionEvent.ACTION_UP || p_action == MotionEvent.ACTION_CANCEL) { + } else if (p_action == MotionEvent.ACTION_UP || p_action == MotionEvent.ACTION_CANCEL) { p_view.setPressed(false); NativeApp.setPadButton(p_keycode, 0, false); } } - ////////////////////////////////////////////////////////////////////////////////////////////// + /// /////////////////////////////////////////////////////////////////////////////////////////// public static void copyAssetAll(Context p_context, String srcPath) { AssetManager assetMgr = p_context.getAssets(); @@ -493,7 +340,7 @@ public class MainActivity extends AppCompatActivity { try { String destPath = p_context.getExternalFilesDir(null) + File.separator + srcPath; assets = assetMgr.list(srcPath); - if(assets != null) { + if (assets != null) { if (assets.length == 0) { copyFile(p_context, srcPath, destPath); } else { @@ -505,8 +352,8 @@ public class MainActivity extends AppCompatActivity { } } } + } catch (IOException ignored) { } - catch (IOException ignored) {} } public static void copyFile(Context p_context, String srcFile, String destFile) { @@ -517,11 +364,10 @@ public class MainActivity extends AppCompatActivity { try { is = assetMgr.open(srcFile); boolean _exists = new File(destFile).exists(); - if(srcFile.contains("shaders")) { + if (srcFile.contains("shaders")) { _exists = false; } - if(!_exists) - { + if (!_exists) { os = new FileOutputStream(destFile); byte[] buffer = new byte[1024]; @@ -533,7 +379,7 @@ public class MainActivity extends AppCompatActivity { os.flush(); os.close(); } + } catch (IOException ignored) { } - catch (IOException ignored) {} } } From 8f6bcc1c0bdc7007c8f5245b687b5747a2bd3e20 Mon Sep 17 00:00:00 2001 From: k2154 Date: Sun, 24 Aug 2025 04:55:16 +0900 Subject: [PATCH 2/3] Android project - Modifying recompiler related code --- app/src/main/cpp/pcsx2/vtlb.cpp | 11 ++- app/src/main/cpp/pcsx2/x86/BaseblockEx.h | 67 ++++++++-------- app/src/main/cpp/pcsx2/x86/ix86-32/iR5900.cpp | 78 ++++++++++++------- .../main/cpp/pcsx2/x86/microVU_Compile.inl | 13 +++- 4 files changed, 100 insertions(+), 69 deletions(-) diff --git a/app/src/main/cpp/pcsx2/vtlb.cpp b/app/src/main/cpp/pcsx2/vtlb.cpp index ee2c044..5fbf386 100644 --- a/app/src/main/cpp/pcsx2/vtlb.cpp +++ b/app/src/main/cpp/pcsx2/vtlb.cpp @@ -854,10 +854,11 @@ void vtlb_Mirror(u32 new_region, u32 start, u32 size) __fi void* vtlb_GetPhyPtr(u32 paddr) { - if (paddr >= VTLB_PMAP_SZ || vtlbdata.pmap[paddr >> VTLB_PAGE_BITS].isHandler()) - return NULL; - else - return reinterpret_cast(vtlbdata.pmap[paddr >> VTLB_PAGE_BITS].assumePtr() + (paddr & VTLB_PAGE_MASK)); + auto pmap_value = vtlbdata.pmap[paddr >> VTLB_PAGE_BITS]; + if (paddr >= VTLB_PMAP_SZ || pmap_value.isHandler()) + return NULL; + else + return reinterpret_cast(pmap_value.assumePtr() + (paddr & VTLB_PAGE_MASK)); } __fi u32 vtlb_V2P(u32 vaddr) @@ -1523,10 +1524,12 @@ void mmap_MarkCountedRamPage(u32 paddr) if (m_PageProtectInfo[rampage].Mode == ProtMode_Write) return; // skip town if we're already protected. +#ifdef PCSX2_DEVBUILD eeRecPerfLog.Write((m_PageProtectInfo[rampage].Mode == ProtMode_Manual) ? "Re-protecting page @ 0x%05x" : "Protected page @ 0x%05x", paddr >> __pageshift); +#endif m_PageProtectInfo[rampage].Mode = ProtMode_Write; HostSys::MemProtect(&eeMem->Main[rampage << __pageshift], __pagesize, PageAccess_ReadOnly()); diff --git a/app/src/main/cpp/pcsx2/x86/BaseblockEx.h b/app/src/main/cpp/pcsx2/x86/BaseblockEx.h index 06b0d48..29d4233 100644 --- a/app/src/main/cpp/pcsx2/x86/BaseblockEx.h +++ b/app/src/main/cpp/pcsx2/x86/BaseblockEx.h @@ -37,53 +37,56 @@ struct BASEBLOCKEX class BaseBlockArray { - s32 _Reserved; - s32 _Size; + s32 mReserved; + s32 mSize; BASEBLOCKEX* blocks; __fi void resize(s32 size) { pxAssert(size > 0); - BASEBLOCKEX* newMem = new BASEBLOCKEX[size]; + auto* newMem = new BASEBLOCKEX[size]; if (blocks) { - memcpy(newMem, blocks, _Reserved * sizeof(BASEBLOCKEX)); + memcpy(newMem, blocks, mReserved * sizeof(BASEBLOCKEX)); delete[] blocks; + blocks = nullptr; } blocks = newMem; pxAssert(blocks != NULL); } - void reserve(u32 size) + void reserve(s32 size) { resize(size); - _Reserved = size; + mReserved = size; } public: ~BaseBlockArray() { - if (blocks) - delete[] blocks; + if (blocks) { + delete[] blocks; + blocks = nullptr; + } } - BaseBlockArray(s32 size) - : _Reserved(0) - , _Size(0) - , blocks(NULL) + explicit BaseBlockArray(s32 size) + : mReserved(0) + , mSize(0) + , blocks(nullptr) { reserve(size); } BASEBLOCKEX* insert(u32 startpc, uptr fnptr) { - if (_Size + 1 >= _Reserved) + if (mSize + 1 >= mReserved) { - reserve(_Reserved + 0x2000); // some games requires even more! + reserve(mReserved + 0x2000); // some games requires even more! } // Insert the the new BASEBLOCKEX by startpc order - int imin = 0, imax = _Size, imid; + int imin = 0, imax = mSize, imid; while (imin < imax) { @@ -95,19 +98,19 @@ public: imin = imid + 1; } - pxAssert(imin == _Size || blocks[imin].startpc > startpc); + pxAssert(imin == mSize || blocks[imin].startpc > startpc); - if (imin < _Size) + if (imin < mSize) { // make a hole for a new block. - memmove(blocks + imin + 1, blocks + imin, (_Size - imin) * sizeof(BASEBLOCKEX)); + memmove(blocks + imin + 1, blocks + imin, (mSize - imin) * sizeof(BASEBLOCKEX)); } memset((blocks + imin), 0, sizeof(BASEBLOCKEX)); blocks[imin].startpc = startpc; blocks[imin].fnptr = fnptr; - _Size++; + mSize++; return &blocks[imin]; } @@ -118,24 +121,24 @@ public: void clear() { - _Size = 0; + mSize = 0; } - __fi u32 size() const + [[nodiscard]] __fi u32 size() const { - return _Size; + return mSize; } __fi void erase(s32 first, s32 last) { int range = last - first; - if (last < _Size) + if (last < mSize) { - memmove(blocks + first, blocks + last, (_Size - last) * sizeof(BASEBLOCKEX)); + memmove(blocks + first, blocks + last, (mSize - last) * sizeof(BASEBLOCKEX)); } - _Size -= range; + mSize -= range; } }; @@ -162,15 +165,17 @@ public: } BASEBLOCKEX* New(u32 startpc, uptr fnptr); - int LastIndex(u32 startpc) const; + [[nodiscard]] int LastIndex(u32 startpc) const; //BASEBLOCKEX* GetByX86(uptr ip); - __fi int Index(u32 startpc) const + [[nodiscard]] __fi int Index(u32 startpc) const { int idx = LastIndex(startpc); + u32 block_startpc = blocks[idx].startpc; + u32 block_size = (blocks[idx].size); - if ((idx == -1) || (startpc < blocks[idx].startpc) || - ((blocks[idx].size) && (startpc >= blocks[idx].startpc + blocks[idx].size * 4))) + if ((idx == -1) || (startpc < block_startpc) || + (block_size && (startpc >= block_startpc + block_size << 2))) // blocks[idx].size * 4 return -1; else return idx; @@ -179,7 +184,7 @@ public: __fi BASEBLOCKEX* operator[](int idx) { if (idx < 0 || idx >= (int)blocks.size()) - return 0; + return nullptr; return &blocks[idx]; } @@ -198,7 +203,7 @@ public: pxAssert(idx <= last); //u32 startpc = blocks[idx].startpc; - std::pair range = links.equal_range(blocks[idx].startpc); + auto range = links.equal_range(blocks[idx].startpc); for (auto i = range.first; i != range.second; ++i) { // *(u32 *) i->second = recompiler - (i->second + 4); armEmitJmpPtr((void*)i->second, (void*)recompiler, true); diff --git a/app/src/main/cpp/pcsx2/x86/ix86-32/iR5900.cpp b/app/src/main/cpp/pcsx2/x86/ix86-32/iR5900.cpp index b5cc385..21ec511 100644 --- a/app/src/main/cpp/pcsx2/x86/ix86-32/iR5900.cpp +++ b/app/src/main/cpp/pcsx2/x86/ix86-32/iR5900.cpp @@ -490,9 +490,9 @@ static const void* _DynGen_EnterRecompiledCode() #endif // From memory to registry + armMoveAddressToReg(RSTATE_x29, &recLUT); armMoveAddressToReg(RSTATE_PSX, &psxRegs); armMoveAddressToReg(RSTATE_CPU, &g_cpuRegistersPack); - armMoveAddressToReg(RSTATE_x29, &recLUT); if (CHECK_FASTMEM) { // xMOV(RFASTMEMBASE, ptrNative[&vtlb_private::vtlbdata.fastmem_base]); @@ -802,14 +802,16 @@ void recClear(u32 addr, u32 size) { if ((addr) >= maxrecmem || !(recLUT[(addr) >> 16] + (addr & ~0xFFFFUL))) return; + addr = HWADDR(addr); - int blockidx = recBlocks.LastIndex(addr + size * 4 - 4); + u32 addr_size = addr + (size << 2); // // size * 4 + int blockidx = recBlocks.LastIndex(addr_size - 4); if (blockidx == -1) return; - u32 lowerextent = static_cast(-1), upperextent = 0, ceiling = static_cast(-1); + u32 lowerextent = 0xFFFFFFFF, upperextent = 0, ceiling = 0xFFFFFFFF; // 0xFFFFFFFF == -1 BASEBLOCKEX* pexblock = recBlocks[blockidx + 1]; if (pexblock) @@ -817,11 +819,12 @@ void recClear(u32 addr, u32 size) int toRemoveLast = blockidx; + u32 blockstart, blockend; while ((pexblock = recBlocks[blockidx])) { - u32 blockstart = pexblock->startpc; - u32 blockend = pexblock->startpc + pexblock->size * 4; - BASEBLOCK* pblock = PC_GETBLOCK(blockstart); + blockstart = pexblock->startpc; + blockend = pexblock->startpc + (pexblock->size << 2); // pexblock->size * 4 + BASEBLOCK* pblock = PC_GETBLOCK(blockstart); if (pblock == s_pCurBlock) { @@ -853,12 +856,12 @@ void recClear(u32 addr, u32 size) upperextent = std::min(upperextent, ceiling); - for (int i = 0; (pexblock = recBlocks[i]); i++) + for (int i = 0; (pexblock = recBlocks[i]); ++i) { if (s_pCurBlock == PC_GETBLOCK(pexblock->startpc)) continue; - u32 blockend = pexblock->startpc + pexblock->size * 4; - if ((pexblock->startpc >= addr && pexblock->startpc < addr + size * 4) || (pexblock->startpc < addr && blockend > addr)) [[unlikely]] + blockend = pexblock->startpc + (pexblock->size << 2); // pexblock->size * 4 + if ((pexblock->startpc >= addr && pexblock->startpc < addr_size) || (pexblock->startpc < addr && blockend > addr)) [[unlikely]] { Console.Error("[EE] Impossible block clearing failure"); pxFail("[EE] Impossible block clearing failure"); @@ -2118,7 +2121,9 @@ static void PreBlockCheck(u32 blockpc) // less likely, self-modifying code) void dyna_block_discard(u32 start, u32 sz) { +#ifdef PCSX2_DEVBUILD eeRecPerfLog.Write(Color_StrongGray, "Clearing Manual Block @ 0x%08X [size=%d]", start, sz * 4); +#endif recClear(start, sz); } @@ -2135,11 +2140,12 @@ void dyna_page_reset(u32 start, u32 sz) static void memory_protect_recompiled_code(u32 startpc, u32 size) { u32 inpage_ptr = HWADDR(startpc); - const u32 inpage_sz = size * 4; + const u32 inpage_sz = size << 2; // size * 4 // The kernel context register is stored @ 0x800010C0-0x80001300 // The EENULL thread context register is stored @ 0x81000-.... - const bool contains_thread_stack = ((startpc >> 12) == 0x81) || ((startpc >> 12) == 0x80001); + u32 startpc_lsr_12 = (startpc >> 12); + const bool contains_thread_stack = (startpc_lsr_12 == 0x81) || (startpc_lsr_12 == 0x80001); // note: blocks are guaranteed to reside within the confines of a single page. const vtlb_ProtectionMode PageType = contains_thread_stack ? ProtMode_Manual : mmap_GetRamPageInfo(inpage_ptr); @@ -2159,16 +2165,24 @@ static void memory_protect_recompiled_code(u32 startpc, u32 size) // xMOV(arg1regd, inpage_ptr); armAsm->Mov(EAX, inpage_ptr); // xMOV(arg2regd, inpage_sz / 4); - armAsm->Mov(ECX, inpage_sz / 4); + armAsm->Mov(ECX, inpage_sz >> 2); //xMOV( eax, startpc ); // uncomment this to access startpc (as eax) in dyna_block_discard + u32 lpc_addr; u32 lpc = inpage_ptr; u32 stg = inpage_sz; + armAsm->Ldr(RSCRATCHADDR, PTR_CPU(vtlbdata.pmap)); + while (stg > 0) { // xCMP(ptr32[PSM(lpc)], *(u32*)PSM(lpc)); - armAsm->Cmp(armLoadPtr(PSM(lpc)), *(u32*)PSM(lpc)); + + lpc_addr = lpc & 0x1fffffff; + armAsm->Add(RXVIXLSCRATCH, RSCRATCHADDR, lpc_addr); + armAsm->Ldr(EDX, a64::MemOperand(RXVIXLSCRATCH)); + armAsm->Cmp(EDX, *(u32*)vtlb_GetPhyPtr(lpc_addr)); + // xJNE(DispatchBlockDiscard); armEmitCondBranch(a64::Condition::ne, DispatchBlockDiscard); @@ -2207,15 +2221,19 @@ static void memory_protect_recompiled_code(u32 startpc, u32 size) // xJC(DispatchPageReset); armEmitCondBranch(a64::Condition::cs, DispatchPageReset); +#ifdef PCSX2_DEVBUILD // note: clearcnt is measured per-page, not per-block! eeRecPerfLog.Write("Manual block @ %08X : size =%3d page/offs = 0x%05X/0x%03X inpgsz = %d clearcnt = %d", startpc, size, inpage_ptr >> 12, inpage_ptr & 0xfff, inpage_sz, manual_counter[inpage_ptr >> 12]); +#endif } +#ifdef PCSX2_DEVBUILD else { eeRecPerfLog.Write("Uncounted Manual block @ 0x%08X : size =%3d page/offs = 0x%05X/0x%03X inpgsz = %d", startpc, size, inpage_ptr >> 12, inpage_ptr & 0xfff, inpage_sz); } +#endif break; } } @@ -2462,7 +2480,7 @@ static void recRecompile(const u32 startpc) const int n = std::max(n1, n2); if (n != 0) { - s_nEndBlock = i + n * 4; + s_nEndBlock = i + (n << 2); // n * 4 goto StartRecomp; } @@ -2484,7 +2502,9 @@ static void recRecompile(const u32 startpc) willbranch3 = 1; s_nEndBlock = i; +#ifdef PCSX2_DEVBUILD eeRecPerfLog.Write("Pagesplit @ %08X : size=%d insts", startpc, (i - startpc) / 4); +#endif break; } @@ -2541,7 +2561,7 @@ static void recRecompile(const u32 startpc) if (_Rt_ < 4 || (_Rt_ >= 16 && _Rt_ < 20)) { // branches - s_branchTo = _Imm_ * 4 + i + 4; + s_branchTo = (_Imm_ << 2) + i + 4; // _Imm_ * 4 if (s_branchTo > startpc && s_branchTo < i) s_nEndBlock = s_branchTo; else @@ -2566,7 +2586,7 @@ static void recRecompile(const u32 startpc) case 21: case 22: case 23: - s_branchTo = _Imm_ * 4 + i + 4; + s_branchTo = (_Imm_ << 2) + i + 4; // _Imm_ * 4 if (s_branchTo > startpc && s_branchTo < i) s_nEndBlock = s_branchTo; else @@ -2592,7 +2612,7 @@ static void recRecompile(const u32 startpc) { // BC1F, BC1T, BC1FL, BC1TL // BC2F, BC2T, BC2FL, BC2TL - s_branchTo = _Imm_ * 4 + i + 4; + s_branchTo = (_Imm_ << 2) + i + 4; // _Imm_ * 4 if (s_branchTo > startpc && s_branchTo < i) s_nEndBlock = s_branchTo; else @@ -2698,10 +2718,11 @@ StartRecomp: // rec info // bool has_cop2_instructions = false; { - if (s_nInstCacheSize < (s_nEndBlock - startpc) / 4 + 1) + u32 block_offset = (s_nEndBlock - startpc) >> 2; // (s_nEndBlock - startpc) / 4 + if (s_nInstCacheSize < block_offset + 1) { - const u32 required_size = (s_nEndBlock - startpc) / 4 + 10; - const u32 new_size = std::max(required_size, s_nInstCacheSize * 2); + const u32 required_size = block_offset + 10; + const u32 new_size = std::max(required_size, s_nInstCacheSize << 1); // s_nInstCacheSize * 2 EEINST* new_cache = (EEINST*)malloc(sizeof(EEINST) * new_size); if (!new_cache) @@ -2717,7 +2738,7 @@ StartRecomp: s_nInstCacheSize = new_size; } - EEINST* pcur = s_pInstCache + (s_nEndBlock - startpc) / 4; + EEINST* pcur = s_pInstCache + block_offset; _recClearInst(pcur); pcur->info = 0; @@ -2811,29 +2832,26 @@ StartRecomp: if (HWADDR(pc) <= Ps2MemSize::ExposedRam) { BASEBLOCKEX* oldBlock; - int i; - - i = recBlocks.LastIndex(HWADDR(pc) - 4); - while ((oldBlock = recBlocks[i--])) + int ii = recBlocks.LastIndex(HWADDR(pc) - 4); + while ((oldBlock = recBlocks[ii--])) { if (oldBlock == s_pCurBlockEx) continue; if (oldBlock->startpc >= HWADDR(pc)) continue; - if ((oldBlock->startpc + oldBlock->size * 4) <= HWADDR(startpc)) + if ((oldBlock->startpc + (oldBlock->size << 2)) <= HWADDR(startpc)) // oldBlock->size * 4 break; - if (memcmp(&recRAMCopy[oldBlock->startpc / 4], PSM(oldBlock->startpc), - oldBlock->size * 4)) + if (memcmp(&recRAMCopy[oldBlock->startpc >> 2], PSM(oldBlock->startpc), oldBlock->size << 2)) // oldBlock->startpc / 4, oldBlock->size * 4 { - recClear(startpc, (pc - startpc) / 4); + recClear(startpc, (pc - startpc) >> 2); // (pc - startpc) / 4 s_pCurBlockEx = recBlocks.Get(HWADDR(startpc)); pxAssert(s_pCurBlockEx->startpc == HWADDR(startpc)); break; } } - memcpy(&recRAMCopy[HWADDR(startpc) / 4], PSM(startpc), pc - startpc); + memcpy(&recRAMCopy[HWADDR(startpc) >> 2], PSM(startpc), pc - startpc); // HWADDR(startpc) / 4 } s_pCurBlock->SetFnptr((uptr)recPtr); diff --git a/app/src/main/cpp/pcsx2/x86/microVU_Compile.inl b/app/src/main/cpp/pcsx2/x86/microVU_Compile.inl index 52fa537..bcc6e10 100644 --- a/app/src/main/cpp/pcsx2/x86/microVU_Compile.inl +++ b/app/src/main/cpp/pcsx2/x86/microVU_Compile.inl @@ -973,14 +973,19 @@ void* mVUcompile(microVU& mVU, u32 startPC, uptr pState) mVUsetupBranch(mVU, mFC); // Make sure we save the current state so it can come back to it - u32* cpS = (u32*)&mVUregs; - u32* lpS = (u32*)&mVU.prog.lpState; +// u32* cpS = (u32*)&mVUregs; +// u32* lpS = (u32*)&mVU.prog.lpState; + + auto cpS = armMemOperandPtr((u32*)&mVUregs); + auto lpS = armMemOperandPtr((u32*)&mVU.prog.lpState); + size_t i, e = (sizeof(microRegInfo) - 4) >> 2; // sizeof(microRegInfo) - 4 - for (i = 0; i < e; ++i, ++lpS, ++cpS) + for (i = 0; i < e; ++i) { // xMOV(ptr32[lpS], cpS[0]); - armStorePtr(cpS[0], lpS); + armAsm->Str(armOffsetMemOperand(cpS, 1).GetRegisterOffset(), armOffsetMemOperand(lpS, 1)); } + incPC(2); mVUsetupRange(mVU, xPC, false); if (EmuConfig.Gamefixes.VUSyncHack || EmuConfig.Gamefixes.FullVU0SyncHack) { From a1ac39012a310aaa9ea8fd01ea33970346cb8fc6 Mon Sep 17 00:00:00 2001 From: k2154 Date: Mon, 25 Aug 2025 01:42:46 +0900 Subject: [PATCH 3/3] Android project - VKShaderCache.cpp => CompileShaderToSPV() performance degradation has been fixed --- .../GS/Renderers/Vulkan/VKShaderCache.cpp | 99 ++++++++++++------- 1 file changed, 63 insertions(+), 36 deletions(-) diff --git a/app/src/main/cpp/pcsx2/GS/Renderers/Vulkan/VKShaderCache.cpp b/app/src/main/cpp/pcsx2/GS/Renderers/Vulkan/VKShaderCache.cpp index 0fb4021..af0eb8e 100644 --- a/app/src/main/cpp/pcsx2/GS/Renderers/Vulkan/VKShaderCache.cpp +++ b/app/src/main/cpp/pcsx2/GS/Renderers/Vulkan/VKShaderCache.cpp @@ -29,6 +29,9 @@ std::unique_ptr g_vulkan_shader_cache; static u32 s_next_bad_shader_id = 0; +static shaderc_compiler_t g_s_compiler = nullptr; +static shaderc_compile_options_t g_options = nullptr; + namespace { #pragma pack(push, 4) @@ -228,54 +231,69 @@ std::optional VKShaderCache::CompileShaderToSPV( { std::optional ret; #ifdef ANDROID - shaderc_compiler_t s_compiler = shaderc_compiler_initialize(); - if(s_compiler == nullptr) { + if(g_s_compiler == nullptr) + { + g_s_compiler = shaderc_compiler_initialize(); + } + if(g_s_compiler == nullptr) { return ret; } - shaderc_compile_options_t options = shaderc_compile_options_initialize(); - pxAssertRel(options, "shaderc_compile_options_initialize() failed"); + //// == OPTIONS == + if(g_options == nullptr) + { + g_options = shaderc_compile_options_initialize(); - shaderc_compile_options_set_source_language(options, shaderc_source_language_glsl); - shaderc_compile_options_set_target_env(options, shaderc_target_env_vulkan, 0); + pxAssertRel(g_options, "shaderc_compile_options_initialize() failed"); + + shaderc_compile_options_set_source_language(g_options, shaderc_source_language_glsl); + shaderc_compile_options_set_target_env(g_options, shaderc_target_env_vulkan, 0); #ifdef SHADERC_PCSX2_CUSTOM - shaderc_compile_options_set_generate_debug_info(options, debug, - debug && GSDeviceVK::GetInstance()->GetOptionalExtensions().vk_khr_shader_non_semantic_info); + shaderc_compile_options_set_generate_debug_info(options, debug, + debug && GSDeviceVK::GetInstance()->GetOptionalExtensions().vk_khr_shader_non_semantic_info); #else - if (debug) - shaderc_compile_options_set_generate_debug_info(options); + if (debug) + shaderc_compile_options_set_generate_debug_info(g_options); #endif - shaderc_compile_options_set_optimization_level( - options, debug ? shaderc_optimization_level_zero : shaderc_optimization_level_performance); - - const shaderc_compilation_result_t result = shaderc_compile_into_spv( - s_compiler, source.data(), source.length(), static_cast(stage), "source", - "main", options); - - shaderc_compilation_status status = shaderc_compilation_status_null_result_object; - if (!result || (status = shaderc_result_get_compilation_status(result)) != shaderc_compilation_status_success) - { - const std::string_view errors(result ? shaderc_result_get_error_message(result) - : "null result object"); - ERROR_LOG("Failed to compile shader to SPIR-V: {}\n{}", compilation_status_to_string(status), errors); - DumpBadShader(source, errors); + shaderc_compile_options_set_optimization_level( + g_options, + debug ? shaderc_optimization_level_zero : shaderc_optimization_level_performance); } - else + if(g_options == nullptr) { + return ret; + } + + //// == RESULT == + shaderc_compilation_result_t result = shaderc_compile_into_spv( + g_s_compiler, source.data(), source.length(), static_cast(stage), "source", + "main", g_options); + if(result != nullptr) { - const size_t num_warnings = shaderc_result_get_num_warnings(result); - if (num_warnings > 0) - WARNING_LOG("Shader compiled with warnings:\n{}", shaderc_result_get_error_message(result)); + shaderc_compilation_status status = shaderc_compilation_status_null_result_object; + if (!result || (status = shaderc_result_get_compilation_status(result)) != + shaderc_compilation_status_success) { + const std::string_view errors(result ? shaderc_result_get_error_message(result) + : "null result object"); + ERROR_LOG("Failed to compile shader to SPIR-V: {}\n{}", + compilation_status_to_string(status), errors); + DumpBadShader(source, errors); + } else { + const size_t num_warnings = shaderc_result_get_num_warnings(result); + if (num_warnings > 0) + WARNING_LOG("Shader compiled with warnings:\n{}", + shaderc_result_get_error_message(result)); - const size_t spirv_size = shaderc_result_get_length(result); - const char* bytes = shaderc_result_get_bytes(result); - pxAssert(spirv_size > 0 && ((spirv_size % sizeof(u32)) == 0)); - ret = VKShaderCache::SPIRVCodeVector(reinterpret_cast(bytes), - reinterpret_cast(bytes + spirv_size)); + const size_t spirv_size = shaderc_result_get_length(result); + const char *bytes = shaderc_result_get_bytes(result); + pxAssert(spirv_size > 0 && ((spirv_size % sizeof(u32)) == 0)); + ret = VKShaderCache::SPIRVCodeVector(reinterpret_cast(bytes), + reinterpret_cast(bytes + spirv_size)); + } + //// + shaderc_result_release(result); + result = nullptr; } - shaderc_result_release(result); - shaderc_compiler_release(s_compiler); - shaderc_compile_options_release(options); #else if (!dyn_shaderc::Open()) return ret; @@ -333,6 +351,15 @@ VKShaderCache::~VKShaderCache() CloseShaderCache(); FlushPipelineCache(); ClosePipelineCache(); + //// + if(g_options != nullptr) { + shaderc_compile_options_release(g_options); + g_options = nullptr; + } + if(g_s_compiler != nullptr) { + shaderc_compiler_release(g_s_compiler); + g_s_compiler = nullptr; + } } bool VKShaderCache::CacheIndexKey::operator==(const CacheIndexKey& key) const