mirror of
https://git.eden-emu.dev/archive/citron
synced 2026-03-23 01:56:08 -04:00
Merge pull request 'feature/android-astc-crt-settings' (#119) from feature/android-astc-crt-settings into main
Reviewed-on: https://git.citron-emu.org/Citron/Emulator/pulls/119
This commit is contained in:
@@ -6,8 +6,13 @@ package org.citron.citron_emu.features.settings.model
|
||||
import org.citron.citron_emu.utils.NativeConfig
|
||||
|
||||
enum class FloatSetting(override val key: String) : AbstractFloatSetting {
|
||||
// No float settings currently exist
|
||||
EMPTY_SETTING("");
|
||||
// CRT Shader Settings
|
||||
CRT_SCANLINE_STRENGTH("crt_scanline_strength"),
|
||||
CRT_CURVATURE("crt_curvature"),
|
||||
CRT_GAMMA("crt_gamma"),
|
||||
CRT_BLOOM("crt_bloom"),
|
||||
CRT_BRIGHTNESS("crt_brightness"),
|
||||
CRT_ALPHA("crt_alpha");
|
||||
|
||||
override fun getFloat(needsGlobal: Boolean): Float = NativeConfig.getFloat(key, false)
|
||||
|
||||
|
||||
@@ -39,6 +39,10 @@ enum class IntSetting(override val key: String) : AbstractIntSetting {
|
||||
SHADER_BACKEND("shader_backend"),
|
||||
VRAM_USAGE_MODE("vram_usage_mode"),
|
||||
EXTENDED_DYNAMIC_STATE("extended_dynamic_state"),
|
||||
ANDROID_ASTC_MODE("android_astc_mode"),
|
||||
|
||||
// CRT Shader Settings
|
||||
CRT_MASK_TYPE("crt_mask_type"),
|
||||
|
||||
// VRAM Management settings (FIXED: VRAM leak prevention)
|
||||
VRAM_LIMIT_MB("vram_limit_mb"),
|
||||
|
||||
@@ -14,6 +14,7 @@ import org.citron.citron_emu.features.settings.model.AbstractBooleanSetting
|
||||
import org.citron.citron_emu.features.settings.model.AbstractSetting
|
||||
import org.citron.citron_emu.features.settings.model.BooleanSetting
|
||||
import org.citron.citron_emu.features.settings.model.ByteSetting
|
||||
import org.citron.citron_emu.features.settings.model.FloatSetting
|
||||
import org.citron.citron_emu.features.settings.model.IntSetting
|
||||
import org.citron.citron_emu.features.settings.model.LongSetting
|
||||
import org.citron.citron_emu.features.settings.model.ShortSetting
|
||||
@@ -425,6 +426,15 @@ abstract class SettingsItem(
|
||||
valuesId = R.array.astcRecompressionValues
|
||||
)
|
||||
)
|
||||
put(
|
||||
SingleChoiceSetting(
|
||||
IntSetting.ANDROID_ASTC_MODE,
|
||||
titleId = R.string.android_astc_mode,
|
||||
descriptionId = R.string.android_astc_mode_description,
|
||||
choicesId = R.array.androidAstcModeNames,
|
||||
valuesId = R.array.androidAstcModeValues
|
||||
)
|
||||
)
|
||||
put(
|
||||
SingleChoiceSetting(
|
||||
IntSetting.SHADER_BACKEND,
|
||||
@@ -534,6 +544,83 @@ abstract class SettingsItem(
|
||||
)
|
||||
)
|
||||
|
||||
// CRT Shader Settings (shown conditionally in Zep Zone when CRT filter is selected)
|
||||
put(
|
||||
SliderSetting(
|
||||
FloatSetting.CRT_SCANLINE_STRENGTH,
|
||||
titleId = R.string.crt_scanline_strength,
|
||||
descriptionId = R.string.crt_scanline_strength_description,
|
||||
min = 0,
|
||||
max = 200,
|
||||
units = "%",
|
||||
scale = 100.0f
|
||||
)
|
||||
)
|
||||
put(
|
||||
SliderSetting(
|
||||
FloatSetting.CRT_CURVATURE,
|
||||
titleId = R.string.crt_curvature,
|
||||
descriptionId = R.string.crt_curvature_description,
|
||||
min = 0,
|
||||
max = 100,
|
||||
units = "%",
|
||||
scale = 100.0f
|
||||
)
|
||||
)
|
||||
put(
|
||||
SliderSetting(
|
||||
FloatSetting.CRT_GAMMA,
|
||||
titleId = R.string.crt_gamma,
|
||||
descriptionId = R.string.crt_gamma_description,
|
||||
min = 100,
|
||||
max = 300,
|
||||
units = "%",
|
||||
scale = 100.0f
|
||||
)
|
||||
)
|
||||
put(
|
||||
SliderSetting(
|
||||
FloatSetting.CRT_BLOOM,
|
||||
titleId = R.string.crt_bloom,
|
||||
descriptionId = R.string.crt_bloom_description,
|
||||
min = 0,
|
||||
max = 100,
|
||||
units = "%",
|
||||
scale = 100.0f
|
||||
)
|
||||
)
|
||||
put(
|
||||
SingleChoiceSetting(
|
||||
IntSetting.CRT_MASK_TYPE,
|
||||
titleId = R.string.crt_mask_type,
|
||||
descriptionId = R.string.crt_mask_type_description,
|
||||
choicesId = R.array.crtMaskTypeNames,
|
||||
valuesId = R.array.crtMaskTypeValues
|
||||
)
|
||||
)
|
||||
put(
|
||||
SliderSetting(
|
||||
FloatSetting.CRT_BRIGHTNESS,
|
||||
titleId = R.string.crt_brightness,
|
||||
descriptionId = R.string.crt_brightness_description,
|
||||
min = 0,
|
||||
max = 200,
|
||||
units = "%",
|
||||
scale = 100.0f
|
||||
)
|
||||
)
|
||||
put(
|
||||
SliderSetting(
|
||||
FloatSetting.CRT_ALPHA,
|
||||
titleId = R.string.crt_alpha,
|
||||
descriptionId = R.string.crt_alpha_description,
|
||||
min = 0,
|
||||
max = 100,
|
||||
units = "%",
|
||||
scale = 100.0f
|
||||
)
|
||||
)
|
||||
|
||||
// Applet Mode Settings
|
||||
put(
|
||||
SingleChoiceSetting(
|
||||
|
||||
@@ -19,7 +19,8 @@ class SliderSetting(
|
||||
descriptionString: String = "",
|
||||
val min: Int = 0,
|
||||
val max: Int = 100,
|
||||
val units: String = ""
|
||||
val units: String = "",
|
||||
val scale: Float = 1.0f // Scale factor for float settings (e.g., 100.0 means UI value 100 = C++ value 1.0)
|
||||
) : SettingsItem(setting, titleId, titleString, descriptionId, descriptionString) {
|
||||
override val type = TYPE_SLIDER
|
||||
|
||||
@@ -28,7 +29,7 @@ class SliderSetting(
|
||||
is AbstractByteSetting -> setting.getByte(needsGlobal).toInt()
|
||||
is AbstractShortSetting -> setting.getShort(needsGlobal).toInt()
|
||||
is AbstractIntSetting -> setting.getInt(needsGlobal)
|
||||
is AbstractFloatSetting -> setting.getFloat(needsGlobal).roundToInt()
|
||||
is AbstractFloatSetting -> (setting.getFloat(needsGlobal) * scale).roundToInt()
|
||||
else -> -1
|
||||
}
|
||||
|
||||
@@ -36,7 +37,7 @@ class SliderSetting(
|
||||
when (setting) {
|
||||
is AbstractByteSetting -> setting.setByte(value.toByte())
|
||||
is AbstractShortSetting -> setting.setShort(value.toShort())
|
||||
is AbstractFloatSetting -> setting.setFloat(value.toFloat())
|
||||
is AbstractFloatSetting -> setting.setFloat(value.toFloat() / scale)
|
||||
else -> (setting as AbstractIntSetting).setInt(value)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ import org.citron.citron_emu.features.settings.model.AbstractBooleanSetting
|
||||
import org.citron.citron_emu.features.settings.model.AbstractIntSetting
|
||||
import org.citron.citron_emu.features.settings.model.BooleanSetting
|
||||
import org.citron.citron_emu.features.settings.model.ByteSetting
|
||||
import org.citron.citron_emu.features.settings.model.FloatSetting
|
||||
import org.citron.citron_emu.features.settings.model.IntSetting
|
||||
import org.citron.citron_emu.features.settings.model.LongSetting
|
||||
import org.citron.citron_emu.features.settings.model.Settings
|
||||
@@ -1026,6 +1027,7 @@ class SettingsFragmentPresenter(
|
||||
add(HeaderSetting(R.string.astc_settings_header))
|
||||
add(IntSetting.ASTC_DECODE_MODE.key)
|
||||
add(IntSetting.ASTC_RECOMPRESSION.key)
|
||||
add(IntSetting.ANDROID_ASTC_MODE.key)
|
||||
|
||||
add(HeaderSetting(R.string.advanced_graphics_header))
|
||||
add(IntSetting.SHADER_BACKEND.key)
|
||||
@@ -1045,6 +1047,20 @@ class SettingsFragmentPresenter(
|
||||
add(IntSetting.BUFFER_EVICTION_FRAMES.key)
|
||||
add(BooleanSetting.SPARSE_TEXTURE_PRIORITY_EVICTION.key)
|
||||
add(BooleanSetting.LOG_VRAM_USAGE.key)
|
||||
|
||||
// CRT Shader Settings (only shown when CRT filter is enabled)
|
||||
// CRTEasyMode = 9, CRTRoyale = 10
|
||||
val scalingFilter = IntSetting.RENDERER_SCALING_FILTER.getInt(false)
|
||||
if (scalingFilter == 9 || scalingFilter == 10) {
|
||||
add(HeaderSetting(R.string.crt_shader_header))
|
||||
add(FloatSetting.CRT_SCANLINE_STRENGTH.key)
|
||||
add(FloatSetting.CRT_CURVATURE.key)
|
||||
add(FloatSetting.CRT_GAMMA.key)
|
||||
add(FloatSetting.CRT_BLOOM.key)
|
||||
add(IntSetting.CRT_MASK_TYPE.key)
|
||||
add(FloatSetting.CRT_BRIGHTNESS.key)
|
||||
add(FloatSetting.CRT_ALPHA.key)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -400,6 +400,18 @@
|
||||
<item>2</item>
|
||||
</integer-array>
|
||||
|
||||
<string-array name="androidAstcModeNames">
|
||||
<item>@string/android_astc_mode_auto</item>
|
||||
<item>@string/android_astc_mode_native</item>
|
||||
<item>@string/android_astc_mode_decompress</item>
|
||||
</string-array>
|
||||
|
||||
<integer-array name="androidAstcModeValues">
|
||||
<item>0</item>
|
||||
<item>1</item>
|
||||
<item>2</item>
|
||||
</integer-array>
|
||||
|
||||
<string-array name="shaderBackendNames">
|
||||
<item>GLSL</item>
|
||||
<item>GLASM</item>
|
||||
@@ -458,4 +470,17 @@
|
||||
<item>1</item>
|
||||
</integer-array>
|
||||
|
||||
<!-- CRT Shader setting arrays -->
|
||||
<string-array name="crtMaskTypeNames">
|
||||
<item>@string/crt_mask_none</item>
|
||||
<item>@string/crt_mask_aperture</item>
|
||||
<item>@string/crt_mask_shadow</item>
|
||||
</string-array>
|
||||
|
||||
<integer-array name="crtMaskTypeValues">
|
||||
<item>0</item>
|
||||
<item>1</item>
|
||||
<item>2</item>
|
||||
</integer-array>
|
||||
|
||||
</resources>
|
||||
|
||||
@@ -1259,6 +1259,11 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
<string name="astc_decode_mode_description">Controls how ASTC textures are decoded. GPU decoding is faster but may cause issues on some devices.</string>
|
||||
<string name="astc_recompression">ASTC Recompression Method</string>
|
||||
<string name="astc_recompression_description">Controls how ASTC textures are recompressed when GPU doesn\'t support them natively.</string>
|
||||
<string name="android_astc_mode">Android ASTC Eviction</string>
|
||||
<string name="android_astc_mode_description">Controls texture cache eviction on Android devices with native ASTC support (Adreno 740+). Native mode uses compressed sizes for eviction, allowing more textures to be cached.</string>
|
||||
<string name="android_astc_mode_auto">Auto (Detect Hardware)</string>
|
||||
<string name="android_astc_mode_native">Native (Adreno 740+ Optimized)</string>
|
||||
<string name="android_astc_mode_decompress">Decompress (Legacy)</string>
|
||||
<string name="shader_backend">Shader Backend</string>
|
||||
<string name="shader_backend_description">Controls which shader backend to use for rendering.</string>
|
||||
<string name="vram_usage_mode">VRAM Usage Mode</string>
|
||||
@@ -1293,4 +1298,24 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
<string name="gc_aggressiveness_light">Light (Recommended)</string>
|
||||
<string name="frame_skipping_header">Frame Skipping</string>
|
||||
|
||||
<!-- CRT Shader Settings -->
|
||||
<string name="crt_shader_header">CRT Shader Settings</string>
|
||||
<string name="crt_scanline_strength">Scanline Strength</string>
|
||||
<string name="crt_scanline_strength_description">Controls the intensity of CRT scanlines. Higher values create darker, more visible scanlines.</string>
|
||||
<string name="crt_curvature">Screen Curvature</string>
|
||||
<string name="crt_curvature_description">Simulates the curved glass of old CRT monitors. 0 is flat, higher values add more curve.</string>
|
||||
<string name="crt_gamma">Gamma</string>
|
||||
<string name="crt_gamma_description">Adjusts the brightness curve of the image. Lower values make the image darker, higher values make it brighter.</string>
|
||||
<string name="crt_bloom">Bloom</string>
|
||||
<string name="crt_bloom_description">Adds a soft glow around bright areas. Creates a phosphor bloom effect typical of CRT displays.</string>
|
||||
<string name="crt_mask_type">Mask Type</string>
|
||||
<string name="crt_mask_type_description">Simulates the shadow mask or aperture grille of CRT displays. Affects how subpixels are rendered.</string>
|
||||
<string name="crt_brightness">Brightness</string>
|
||||
<string name="crt_brightness_description">Overall brightness adjustment. Values below 1.0 darken the image, above 1.0 brighten it.</string>
|
||||
<string name="crt_alpha">Shader Intensity</string>
|
||||
<string name="crt_alpha_description">Blends between the CRT effect and original image. 1.0 is full CRT effect, lower values show more of the original.</string>
|
||||
<string name="crt_mask_none">None</string>
|
||||
<string name="crt_mask_aperture">Aperture Grille</string>
|
||||
<string name="crt_mask_shadow">Shadow Mask</string>
|
||||
|
||||
</resources>
|
||||
|
||||
@@ -560,6 +560,16 @@ struct Values {
|
||||
SwitchableSetting<bool> log_vram_usage{linkage, false, "log_vram_usage",
|
||||
Category::RendererAdvanced};
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Controls texture cache eviction strategy on Android devices with native ASTC support
|
||||
// Auto = detect based on GPU, Native = use compressed size, Decompress = use decompressed size
|
||||
SwitchableSetting<AndroidAstcMode, true> android_astc_mode{linkage,
|
||||
AndroidAstcMode::Auto,
|
||||
AndroidAstcMode::Auto,
|
||||
AndroidAstcMode::Decompress,
|
||||
"android_astc_mode",
|
||||
Category::RendererAdvanced};
|
||||
|
||||
SwitchableSetting<bool> async_presentation{linkage,
|
||||
#ifdef ANDROID
|
||||
true,
|
||||
|
||||
@@ -896,6 +896,28 @@ inline u32 EnumMetadata<GCAggressiveness>::Index() {
|
||||
return 27;
|
||||
}
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Controls texture cache eviction strategy on Android devices with native ASTC support
|
||||
enum class AndroidAstcMode : u32 {
|
||||
Auto = 0, // Auto-detect based on GPU capabilities (recommended)
|
||||
Native = 1, // Force native ASTC - use compressed size for eviction
|
||||
Decompress = 2, // Force decompression - use decompressed size (PC-style eviction)
|
||||
};
|
||||
|
||||
template <>
|
||||
inline std::vector<std::pair<std::string, AndroidAstcMode>>
|
||||
EnumMetadata<AndroidAstcMode>::Canonicalizations() {
|
||||
return {
|
||||
{"Auto", AndroidAstcMode::Auto},
|
||||
{"Native", AndroidAstcMode::Native},
|
||||
{"Decompress", AndroidAstcMode::Decompress},
|
||||
};
|
||||
}
|
||||
|
||||
template <>
|
||||
inline u32 EnumMetadata<AndroidAstcMode>::Index() {
|
||||
return 28;
|
||||
}
|
||||
|
||||
template <typename Type>
|
||||
inline std::string CanonicalizeEnum(Type id) {
|
||||
|
||||
@@ -145,6 +145,12 @@ public:
|
||||
// OpenGL does not require a barrier for attachment feedback loops.
|
||||
}
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// OpenGL does not have the same Adreno-specific optimizations as Vulkan
|
||||
[[nodiscard]] bool SupportsNativeAstc() const noexcept {
|
||||
return false; // No Adreno-specific detection in OpenGL
|
||||
}
|
||||
|
||||
private:
|
||||
const Device& device;
|
||||
StateTracker& state_tracker;
|
||||
|
||||
@@ -113,6 +113,12 @@ public:
|
||||
|
||||
void BarrierFeedbackLoop();
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Returns true if the device supports native ASTC and compressed size eviction
|
||||
[[nodiscard]] bool SupportsNativeAstc() const noexcept {
|
||||
return device.SupportsNativeAstc();
|
||||
}
|
||||
|
||||
const Device& device;
|
||||
Scheduler& scheduler;
|
||||
MemoryAllocator& memory_allocator;
|
||||
|
||||
@@ -60,7 +60,14 @@ namespace {
|
||||
ImageBase::ImageBase(const ImageInfo& info_, GPUVAddr gpu_addr_, VAddr cpu_addr_)
|
||||
: info{info_}, guest_size_bytes{CalculateGuestSizeInBytes(info)},
|
||||
unswizzled_size_bytes{CalculateUnswizzledSizeBytes(info)},
|
||||
converted_size_bytes{CalculateConvertedSizeBytes(info)}, scale_rating{}, scale_tick{},
|
||||
converted_size_bytes{CalculateConvertedSizeBytes(info)},
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// For ASTC textures, compressed size = guest_size_bytes (raw ASTC blocks remain compressed)
|
||||
// For non-ASTC, compressed_size = unswizzled_size_bytes (needs full decompression)
|
||||
compressed_size_bytes{VideoCore::Surface::IsPixelFormatASTC(info.format)
|
||||
? guest_size_bytes
|
||||
: unswizzled_size_bytes},
|
||||
scale_rating{}, scale_tick{},
|
||||
has_scaled{}, gpu_addr{gpu_addr_}, cpu_addr{cpu_addr_},
|
||||
cpu_addr_end{cpu_addr + guest_size_bytes}, mip_level_offsets{CalculateMipLevelOffsets(info)} {
|
||||
if (info.type == ImageType::e3D) {
|
||||
|
||||
@@ -89,6 +89,9 @@ struct ImageBase {
|
||||
u32 guest_size_bytes = 0;
|
||||
u32 unswizzled_size_bytes = 0;
|
||||
u32 converted_size_bytes = 0;
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Size in VRAM when using native ASTC (compressed) vs when decompressed
|
||||
u32 compressed_size_bytes = 0;
|
||||
u32 scale_rating = 0;
|
||||
u64 scale_tick = 0;
|
||||
bool has_scaled = false;
|
||||
|
||||
@@ -89,6 +89,32 @@ TextureCache<P>::TextureCache(Runtime& runtime_, Tegra::MaxwellDeviceMemoryManag
|
||||
"VRAM Management initialized: limit={}MB, expected={}MB, critical={}MB, gc_level={}",
|
||||
vram_limit_bytes / 1_MiB, expected_memory / 1_MiB, critical_memory / 1_MiB,
|
||||
static_cast<u32>(gc_level));
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Determine eviction strategy based on android_astc_mode setting and device capabilities
|
||||
const auto astc_mode = Settings::values.android_astc_mode.GetValue();
|
||||
if (astc_mode == Settings::AndroidAstcMode::Native) {
|
||||
use_compressed_eviction = true;
|
||||
} else if (astc_mode == Settings::AndroidAstcMode::Decompress) {
|
||||
use_compressed_eviction = false;
|
||||
} else {
|
||||
// Auto mode: detect based on runtime device capabilities
|
||||
use_compressed_eviction = runtime.SupportsNativeAstc();
|
||||
}
|
||||
|
||||
if (use_compressed_eviction) {
|
||||
// Android devices with native ASTC can use higher VRAM budget (90% instead of 80%)
|
||||
// since textures stay compressed in GPU memory
|
||||
const u64 android_vram_limit = static_cast<u64>(static_cast<double>(runtime.GetDeviceLocalMemory()) * 0.90);
|
||||
if (configured_limit_mb == 0 && android_vram_limit > vram_limit_bytes) {
|
||||
vram_limit_bytes = android_vram_limit;
|
||||
expected_memory = static_cast<u64>(static_cast<f32>(vram_limit_bytes) * expected_ratio);
|
||||
critical_memory = static_cast<u64>(static_cast<f32>(vram_limit_bytes) * critical_ratio);
|
||||
}
|
||||
LOG_INFO(Render_Vulkan,
|
||||
"Android native ASTC enabled: using compressed size eviction, VRAM budget={}MB",
|
||||
vram_limit_bytes / 1_MiB);
|
||||
}
|
||||
} else {
|
||||
vram_limit_bytes = configured_limit_mb > 0 ? static_cast<u64>(configured_limit_mb) * 1_MiB
|
||||
: 6_GiB; // Default 6GB if no info
|
||||
@@ -171,9 +197,13 @@ void TextureCache<P>::RunGarbageCollector() {
|
||||
return false;
|
||||
}
|
||||
|
||||
// FIXED: VRAM leak prevention - Prioritize sparse textures if enabled
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Prioritize sparse textures if enabled
|
||||
const bool is_sparse = True(image.flags & ImageFlagBits::Sparse);
|
||||
const u64 image_size = std::max(image.guest_size_bytes, image.unswizzled_size_bytes);
|
||||
// Use compressed size for eviction on Android with native ASTC support
|
||||
const u64 image_size = use_compressed_eviction
|
||||
? image.compressed_size_bytes
|
||||
: std::max(image.guest_size_bytes, image.unswizzled_size_bytes);
|
||||
const bool is_large = image_size >= LARGE_TEXTURE_THRESHOLD;
|
||||
|
||||
// Skip costly loads unless aggressive/emergency mode, unless it's a large sparse texture
|
||||
@@ -426,7 +456,11 @@ u64 TextureCache<P>::EvictToFreeMemory(u64 target_bytes) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const u64 image_size = std::max(image.guest_size_bytes, image.unswizzled_size_bytes);
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Use compressed size for eviction on Android with native ASTC support
|
||||
const u64 image_size = use_compressed_eviction
|
||||
? image.compressed_size_bytes
|
||||
: std::max(image.guest_size_bytes, image.unswizzled_size_bytes);
|
||||
|
||||
if (True(image.flags & ImageFlagBits::Tracked)) {
|
||||
UntrackImage(image, image_id);
|
||||
@@ -455,7 +489,11 @@ u64 TextureCache<P>::EvictSparseTexturesPriority(u64 target_bytes) {
|
||||
auto& image = slot_images[image_id];
|
||||
if (True(image.flags & ImageFlagBits::Sparse) &&
|
||||
False(image.flags & ImageFlagBits::IsDecoding)) {
|
||||
const u64 size = std::max(image.guest_size_bytes, image.unswizzled_size_bytes);
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Use compressed size for eviction on Android with native ASTC support
|
||||
const u64 size = use_compressed_eviction
|
||||
? image.compressed_size_bytes
|
||||
: std::max(image.guest_size_bytes, image.unswizzled_size_bytes);
|
||||
sparse_textures.emplace_back(image_id, size);
|
||||
}
|
||||
return false;
|
||||
|
||||
@@ -506,6 +506,10 @@ public:
|
||||
u64 last_gc_frame = 0; // Last frame GC was run
|
||||
bool emergency_gc_triggered = false; // Emergency GC flag
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// When true, use compressed_size_bytes for eviction calculations on Android + Adreno 7xx
|
||||
bool use_compressed_eviction = false;
|
||||
|
||||
struct BufferDownload {
|
||||
GPUVAddr address;
|
||||
size_t size;
|
||||
|
||||
@@ -441,6 +441,22 @@ Device::Device(VkInstance instance_, vk::PhysicalDevice physical_, VkSurfaceKHR
|
||||
nvidia_arch = GetNvidiaArchitecture(physical, supported_extensions);
|
||||
}
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
// Detect Adreno GPUs and check for native ASTC support
|
||||
is_adreno = is_qualcomm || is_turnip;
|
||||
if (is_adreno) {
|
||||
// Adreno 7xx series devices (Adreno 730, 740, 750+) support native ASTC
|
||||
// Device IDs: 0x43050a01 (SD8 Gen 2), 0x43052c01 (SD8 Elite), etc.
|
||||
// Generally 0x43050000+ indicates Adreno 7xx series
|
||||
is_adreno_7xx_or_newer = (device_id >= 0x43050000);
|
||||
supports_native_astc = is_adreno_7xx_or_newer && is_optimal_astc_supported;
|
||||
|
||||
if (supports_native_astc) {
|
||||
LOG_INFO(Render_Vulkan,
|
||||
"Adreno 7xx detected — using native ASTC, eviction on compressed size");
|
||||
}
|
||||
}
|
||||
|
||||
SetupFamilies(surface);
|
||||
const auto queue_cis = GetDeviceQueueCreateInfos();
|
||||
|
||||
|
||||
@@ -722,6 +722,22 @@ public:
|
||||
return nvidia_arch;
|
||||
}
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
/// Returns true if the device is an Adreno GPU (Qualcomm or Turnip driver)
|
||||
[[nodiscard]] bool IsAdrenoGpu() const noexcept {
|
||||
return is_adreno;
|
||||
}
|
||||
|
||||
/// Returns true if the device is Adreno 7xx series or newer (Adreno 730, 740, 750+)
|
||||
[[nodiscard]] bool IsAdreno7xxOrNewer() const noexcept {
|
||||
return is_adreno_7xx_or_newer;
|
||||
}
|
||||
|
||||
/// Returns true if the device supports native ASTC decoding and compressed size eviction
|
||||
[[nodiscard]] bool SupportsNativeAstc() const noexcept {
|
||||
return supports_native_astc;
|
||||
}
|
||||
|
||||
private:
|
||||
/// Checks if the physical device is suitable and configures the object state
|
||||
/// with all necessary info about its properties.
|
||||
@@ -843,6 +859,11 @@ private:
|
||||
u32 sets_per_pool{}; ///< Sets per Description Pool
|
||||
NvidiaArchitecture nvidia_arch{NvidiaArchitecture::Arch_AmpereOrNewer};
|
||||
|
||||
// FIXED: Android Adreno 740 native ASTC eviction
|
||||
bool is_adreno{}; ///< Is Adreno GPU (Qualcomm or Turnip driver)
|
||||
bool is_adreno_7xx_or_newer{}; ///< Is Adreno 7xx series or newer
|
||||
bool supports_native_astc{}; ///< Supports native ASTC with compressed eviction
|
||||
|
||||
// Telemetry parameters
|
||||
std::set<std::string, std::less<>> supported_extensions; ///< Reported Vulkan extensions.
|
||||
std::set<std::string, std::less<>> loaded_extensions; ///< Loaded Vulkan extensions.
|
||||
|
||||
Reference in New Issue
Block a user