mirror of
				https://github.com/PabloMK7/citra.git
				synced 2025-10-30 21:30:04 +00:00 
			
		
		
		
	android: Port yuzu system info logging (#7431)
This commit is contained in:
		
							parent
							
								
									749a721aa2
								
							
						
					
					
						commit
						da5aa70fc9
					
				
					 8 changed files with 174 additions and 27 deletions
				
			
		|  | @ -9,10 +9,13 @@ import android.app.Application | |||
| import android.app.NotificationChannel | ||||
| import android.app.NotificationManager | ||||
| import android.content.Context | ||||
| import android.os.Build | ||||
| import org.citra.citra_emu.utils.DirectoryInitialization | ||||
| import org.citra.citra_emu.utils.DocumentsTree | ||||
| import org.citra.citra_emu.utils.GpuDriverHelper | ||||
| import org.citra.citra_emu.utils.PermissionsHandler | ||||
| import org.citra.citra_emu.utils.Log | ||||
| import org.citra.citra_emu.utils.MemoryUtil | ||||
| 
 | ||||
| class CitraApplication : Application() { | ||||
|     private fun createNotificationChannel() { | ||||
|  | @ -53,9 +56,20 @@ class CitraApplication : Application() { | |||
|         } | ||||
| 
 | ||||
|         NativeLibrary.logDeviceInfo() | ||||
|         logDeviceInfo() | ||||
|         createNotificationChannel() | ||||
|     } | ||||
| 
 | ||||
|     fun logDeviceInfo() { | ||||
|         Log.info("Device Manufacturer - ${Build.MANUFACTURER}") | ||||
|         Log.info("Device Model - ${Build.MODEL}") | ||||
|         if (Build.VERSION.SDK_INT > Build.VERSION_CODES.R) { | ||||
|             Log.info("SoC Manufacturer - ${Build.SOC_MANUFACTURER}") | ||||
|             Log.info("SoC Model - ${Build.SOC_MODEL}") | ||||
|         } | ||||
|         Log.info("Total System Memory - ${MemoryUtil.getDeviceRAM()}") | ||||
|     } | ||||
| 
 | ||||
|     companion object { | ||||
|         private var application: CitraApplication? = null | ||||
| 
 | ||||
|  |  | |||
|  | @ -413,12 +413,12 @@ object NativeLibrary { | |||
|     } | ||||
| 
 | ||||
|     fun setEmulationActivity(emulationActivity: EmulationActivity?) { | ||||
|         Log.verbose("[NativeLibrary] Registering EmulationActivity.") | ||||
|         Log.debug("[NativeLibrary] Registering EmulationActivity.") | ||||
|         sEmulationActivity = WeakReference(emulationActivity) | ||||
|     } | ||||
| 
 | ||||
|     fun clearEmulationActivity() { | ||||
|         Log.verbose("[NativeLibrary] Unregistering EmulationActivity.") | ||||
|         Log.debug("[NativeLibrary] Unregistering EmulationActivity.") | ||||
|         sEmulationActivity.clear() | ||||
|     } | ||||
| 
 | ||||
|  |  | |||
|  | @ -94,14 +94,14 @@ object DirectoryInitialization { | |||
|         val dataPath = PermissionsHandler.citraDirectory | ||||
|         if (dataPath.toString().isNotEmpty()) { | ||||
|             userPath = dataPath.toString() | ||||
|             Log.debug("[DirectoryInitialization] User Dir: $userPath") | ||||
|             android.util.Log.d("[Citra Frontend]", "[DirectoryInitialization] User Dir: $userPath") | ||||
|             return true | ||||
|         } | ||||
|         return false | ||||
|     } | ||||
| 
 | ||||
|     private fun copyAsset(asset: String, output: File, overwrite: Boolean, context: Context) { | ||||
|         Log.verbose("[DirectoryInitialization] Copying File $asset to $output") | ||||
|         Log.debug("[DirectoryInitialization] Copying File $asset to $output") | ||||
|         try { | ||||
|             if (!output.exists() || overwrite) { | ||||
|                 val inputStream = context.assets.open(asset) | ||||
|  | @ -121,7 +121,7 @@ object DirectoryInitialization { | |||
|         overwrite: Boolean, | ||||
|         context: Context | ||||
|     ) { | ||||
|         Log.verbose("[DirectoryInitialization] Copying Folder $assetFolder to $outputFolder") | ||||
|         Log.debug("[DirectoryInitialization] Copying Folder $assetFolder to $outputFolder") | ||||
|         try { | ||||
|             var createdFolder = false | ||||
|             for (file in context.assets.list(assetFolder)!!) { | ||||
|  |  | |||
|  | @ -4,34 +4,17 @@ | |||
| 
 | ||||
| package org.citra.citra_emu.utils | ||||
| 
 | ||||
| import android.util.Log | ||||
| import org.citra.citra_emu.BuildConfig | ||||
| 
 | ||||
| /** | ||||
|  * Contains methods that call through to [android.util.Log], but | ||||
|  * with the same TAG automatically provided. Also no-ops VERBOSE and DEBUG log | ||||
|  * levels in release builds. | ||||
|  */ | ||||
| object Log { | ||||
|     // Tracks whether we should share the old log or the current log | ||||
|     var gameLaunched = false | ||||
|     private const val TAG = "Citra Frontend" | ||||
| 
 | ||||
|     fun verbose(message: String?) { | ||||
|         if (BuildConfig.DEBUG) { | ||||
|             Log.v(TAG, message!!) | ||||
|         } | ||||
|     } | ||||
|     external fun debug(message: String) | ||||
| 
 | ||||
|     fun debug(message: String?) { | ||||
|         if (BuildConfig.DEBUG) { | ||||
|             Log.d(TAG, message!!) | ||||
|         } | ||||
|     } | ||||
|     external fun warning(message: String) | ||||
| 
 | ||||
|     fun info(message: String?) = Log.i(TAG, message!!) | ||||
|     external fun info(message: String) | ||||
| 
 | ||||
|     fun warning(message: String?) = Log.w(TAG, message!!) | ||||
|     external fun error(message: String) | ||||
| 
 | ||||
|     fun error(message: String?) = Log.e(TAG, message!!) | ||||
|     external fun critical(message: String) | ||||
| } | ||||
|  |  | |||
|  | @ -0,0 +1,108 @@ | |||
| // SPDX-FileCopyrightText: 2023 yuzu Emulator Project | ||||
| // SPDX-License-Identifier: GPL-2.0-or-later | ||||
| 
 | ||||
| package org.citra.citra_emu.utils | ||||
| 
 | ||||
| import android.app.ActivityManager | ||||
| import android.content.Context | ||||
| import android.os.Build | ||||
| import org.citra.citra_emu.CitraApplication | ||||
| import org.citra.citra_emu.R | ||||
| import java.util.Locale | ||||
| import kotlin.math.ceil | ||||
| 
 | ||||
| object MemoryUtil { | ||||
|     private val context get() = CitraApplication.appContext | ||||
| 
 | ||||
|     private val Float.hundredths: String | ||||
|         get() = String.format(Locale.ROOT, "%.2f", this) | ||||
| 
 | ||||
|     const val Kb: Float = 1024F | ||||
|     const val Mb = Kb * 1024 | ||||
|     const val Gb = Mb * 1024 | ||||
|     const val Tb = Gb * 1024 | ||||
|     const val Pb = Tb * 1024 | ||||
|     const val Eb = Pb * 1024 | ||||
| 
 | ||||
|     fun bytesToSizeUnit(size: Float, roundUp: Boolean = false): String = | ||||
|         when { | ||||
|             size < Kb -> { | ||||
|                 context.getString( | ||||
|                     R.string.memory_formatted, | ||||
|                     size.hundredths, | ||||
|                     context.getString(R.string.memory_byte_shorthand) | ||||
|                 ) | ||||
|             } | ||||
|             size < Mb -> { | ||||
|                 context.getString( | ||||
|                     R.string.memory_formatted, | ||||
|                     if (roundUp) ceil(size / Kb) else (size / Kb).hundredths, | ||||
|                     context.getString(R.string.memory_kilobyte) | ||||
|                 ) | ||||
|             } | ||||
|             size < Gb -> { | ||||
|                 context.getString( | ||||
|                     R.string.memory_formatted, | ||||
|                     if (roundUp) ceil(size / Mb) else (size / Mb).hundredths, | ||||
|                     context.getString(R.string.memory_megabyte) | ||||
|                 ) | ||||
|             } | ||||
|             size < Tb -> { | ||||
|                 context.getString( | ||||
|                     R.string.memory_formatted, | ||||
|                     if (roundUp) ceil(size / Gb) else (size / Gb).hundredths, | ||||
|                     context.getString(R.string.memory_gigabyte) | ||||
|                 ) | ||||
|             } | ||||
|             size < Pb -> { | ||||
|                 context.getString( | ||||
|                     R.string.memory_formatted, | ||||
|                     if (roundUp) ceil(size / Tb) else (size / Tb).hundredths, | ||||
|                     context.getString(R.string.memory_terabyte) | ||||
|                 ) | ||||
|             } | ||||
|             size < Eb -> { | ||||
|                 context.getString( | ||||
|                     R.string.memory_formatted, | ||||
|                     if (roundUp) ceil(size / Pb) else (size / Pb).hundredths, | ||||
|                     context.getString(R.string.memory_petabyte) | ||||
|                 ) | ||||
|             } | ||||
|             else -> { | ||||
|                 context.getString( | ||||
|                     R.string.memory_formatted, | ||||
|                     if (roundUp) ceil(size / Eb) else (size / Eb).hundredths, | ||||
|                     context.getString(R.string.memory_exabyte) | ||||
|                 ) | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|     val totalMemory: Float | ||||
|         get() { | ||||
|             val memInfo = ActivityManager.MemoryInfo() | ||||
|             with(context.getSystemService(Context.ACTIVITY_SERVICE) as ActivityManager) { | ||||
|                 getMemoryInfo(memInfo) | ||||
|             } | ||||
| 
 | ||||
|             return if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.UPSIDE_DOWN_CAKE) { | ||||
|                 memInfo.advertisedMem.toFloat() | ||||
|             } else { | ||||
|                 memInfo.totalMem.toFloat() | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|     fun isLessThan(minimum: Int, size: Float): Boolean = | ||||
|         when (size) { | ||||
|             Kb -> totalMemory < Mb && totalMemory < minimum | ||||
|             Mb -> totalMemory < Gb && (totalMemory / Mb) < minimum | ||||
|             Gb -> totalMemory < Tb && (totalMemory / Gb) < minimum | ||||
|             Tb -> totalMemory < Pb && (totalMemory / Tb) < minimum | ||||
|             Pb -> totalMemory < Eb && (totalMemory / Pb) < minimum | ||||
|             Eb -> totalMemory / Eb < minimum | ||||
|             else -> totalMemory < Kb && totalMemory < minimum | ||||
|         } | ||||
| 
 | ||||
|     // Devices are unlikely to have 0.5GB increments of memory so we'll just round up to account for | ||||
|     // the potential error created by memInfo.totalMem | ||||
|     fun getDeviceRAM(): String = bytesToSizeUnit(totalMemory, true) | ||||
| } | ||||
|  | @ -28,6 +28,7 @@ add_library(citra-android SHARED | |||
|     ndk_motion.cpp | ||||
|     ndk_motion.h | ||||
|     system_save_game.cpp | ||||
|     native_log.cpp | ||||
| ) | ||||
| 
 | ||||
| target_link_libraries(citra-android PRIVATE audio_core citra_common citra_core input_common network) | ||||
|  |  | |||
							
								
								
									
										30
									
								
								src/android/app/src/main/jni/native_log.cpp
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										30
									
								
								src/android/app/src/main/jni/native_log.cpp
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,30 @@ | |||
| // SPDX-FileCopyrightText: 2023 yuzu Emulator Project
 | ||||
| // SPDX-License-Identifier: GPL-2.0-or-later
 | ||||
| 
 | ||||
| #include <common/logging/log.h> | ||||
| #include <jni.h> | ||||
| #include "android_common/android_common.h" | ||||
| 
 | ||||
| extern "C" { | ||||
| 
 | ||||
| void Java_org_citra_citra_1emu_utils_Log_debug(JNIEnv* env, jobject obj, jstring jmessage) { | ||||
|     LOG_DEBUG(Frontend, "{}", GetJString(env, jmessage)); | ||||
| } | ||||
| 
 | ||||
| void Java_org_citra_citra_1emu_utils_Log_warning(JNIEnv* env, jobject obj, jstring jmessage) { | ||||
|     LOG_WARNING(Frontend, "{}", GetJString(env, jmessage)); | ||||
| } | ||||
| 
 | ||||
| void Java_org_citra_citra_1emu_utils_Log_info(JNIEnv* env, jobject obj, jstring jmessage) { | ||||
|     LOG_INFO(Frontend, "{}", GetJString(env, jmessage)); | ||||
| } | ||||
| 
 | ||||
| void Java_org_citra_citra_1emu_utils_Log_error(JNIEnv* env, jobject obj, jstring jmessage) { | ||||
|     LOG_ERROR(Frontend, "{}", GetJString(env, jmessage)); | ||||
| } | ||||
| 
 | ||||
| void Java_org_citra_citra_1emu_utils_Log_critical(JNIEnv* env, jobject obj, jstring jmessage) { | ||||
|     LOG_CRITICAL(Frontend, "{}", GetJString(env, jmessage)); | ||||
| } | ||||
| 
 | ||||
| } // extern "C"
 | ||||
|  | @ -442,6 +442,17 @@ | |||
|     <string name="cia_install_error_encrypted">\"%s\" must be decrypted before being used with Citra.\n A real 3DS is required</string> | ||||
|     <string name="cia_install_error_unknown">An unknown error occurred while installing \"%s\".\n Please see the log for more details</string> | ||||
| 
 | ||||
|     <!-- Memory Sizes --> | ||||
|     <string name="memory_formatted">%1$s %2$s</string> | ||||
|     <string name="memory_byte">Byte</string> | ||||
|     <string name="memory_byte_shorthand">B</string> | ||||
|     <string name="memory_kilobyte">KB</string> | ||||
|     <string name="memory_megabyte">MB</string> | ||||
|     <string name="memory_gigabyte">GB</string> | ||||
|     <string name="memory_terabyte">TB</string> | ||||
|     <string name="memory_petabyte">PB</string> | ||||
|     <string name="memory_exabyte">EB</string> | ||||
| 
 | ||||
|     <!-- Theme Modes --> | ||||
|     <string name="change_theme_mode">Change Theme Mode</string> | ||||
|     <string name="theme_mode_follow_system">Follow System</string> | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue