From f6d88558b1780df25088042771a75ab174f0a06c Mon Sep 17 00:00:00 2001 From: Mary Date: Tue, 1 Dec 2020 22:48:31 +0100 Subject: salieri: Fix missing guest GPU accessor missing on hashes (#1759) This adds the guest GPU accessor to hashes computation. As this change all the hashes from the cache, I added some migration logic. This is required for #1755. --- .../Shader/Cache/CacheCollection.cs | 121 +++------------------ 1 file changed, 14 insertions(+), 107 deletions(-) (limited to 'Ryujinx.Graphics.Gpu/Shader/Cache/CacheCollection.cs') diff --git a/Ryujinx.Graphics.Gpu/Shader/Cache/CacheCollection.cs b/Ryujinx.Graphics.Gpu/Shader/Cache/CacheCollection.cs index 0f4db4f3..9b61ef4a 100644 --- a/Ryujinx.Graphics.Gpu/Shader/Cache/CacheCollection.cs +++ b/Ryujinx.Graphics.Gpu/Shader/Cache/CacheCollection.cs @@ -125,26 +125,26 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache /// Get the temp path to the cache data directory. /// /// The temp path to the cache data directory - private string GetCacheTempDataPath() => Path.Combine(_cacheDirectory, "temp"); + private string GetCacheTempDataPath() => CacheHelper.GetCacheTempDataPath(_cacheDirectory); /// /// The path to the cache archive file. /// /// The path to the cache archive file - private string GetArchivePath() => Path.Combine(_cacheDirectory, "cache.zip"); + private string GetArchivePath() => CacheHelper.GetArchivePath(_cacheDirectory); /// /// The path to the cache manifest file. /// /// The path to the cache manifest file - private string GetManifestPath() => Path.Combine(_cacheDirectory, "cache.info"); + private string GetManifestPath() => CacheHelper.GetManifestPath(_cacheDirectory); /// /// Create a new temp path to the given cached file via its hash. /// /// The hash of the cached data /// New path to the given cached file - private string GenCacheTempFilePath(Hash128 key) => Path.Combine(GetCacheTempDataPath(), key.ToString()); + private string GenCacheTempFilePath(Hash128 key) => CacheHelper.GenCacheTempFilePath(_cacheDirectory, key); /// /// Create a new cache collection. @@ -162,7 +162,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache throw new NotImplementedException($"{hashType}"); } - _cacheDirectory = GenerateCachePath(baseCacheDirectory, graphicsApi, shaderProvider, cacheName); + _cacheDirectory = CacheHelper.GenerateCachePath(baseCacheDirectory, graphicsApi, shaderProvider, cacheName); _graphicsApi = graphicsApi; _hashType = hashType; _version = version; @@ -178,13 +178,9 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache /// private void Load() { - bool isInvalid = false; + bool isValid = false; - if (!Directory.Exists(_cacheDirectory)) - { - isInvalid = true; - } - else + if (Directory.Exists(_cacheDirectory)) { string manifestPath = GetManifestPath(); @@ -196,9 +192,9 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache { Memory hashTableRaw = rawManifest.Slice(Unsafe.SizeOf()); - isInvalid = !manifestHeader.IsValid(_version, _graphicsApi, _hashType, hashTableRaw.Span); + isValid = manifestHeader.IsValid(_graphicsApi, _hashType, hashTableRaw.Span) && _version == manifestHeader.Version; - if (!isInvalid) + if (isValid) { ReadOnlySpan hashTable = MemoryMarshal.Cast(hashTableRaw.Span); @@ -209,13 +205,9 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache } } } - else - { - isInvalid = true; - } } - if (isInvalid) + if (!isValid) { Logger.Warning?.Print(LogClass.Gpu, $"Shader collection \"{_cacheDirectory}\" got invalidated, cache will need to be rebuilt."); @@ -324,22 +316,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache // Update the content of the zip. lock (_hashTable) { - foreach (Hash128 hash in _hashTable) - { - string cacheTempFilePath = GenCacheTempFilePath(hash); - - if (File.Exists(cacheTempFilePath)) - { - string cacheHash = $"{hash}"; - - ZipArchiveEntry entry = _cacheArchive.GetEntry(cacheHash); - - entry?.Delete(); - - _cacheArchive.CreateEntryFromFile(cacheTempFilePath, cacheHash); - File.Delete(cacheTempFilePath); - } - } + CacheHelper.EnsureArchiveUpToDate(_cacheDirectory, _cacheArchive, _hashTable); // Close the instance to force a flush. _cacheArchive.Dispose(); @@ -362,56 +339,16 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache /// private void SaveManifest() { - CacheManifestHeader manifestHeader = new CacheManifestHeader(_version, _graphicsApi, _hashType); - byte[] data; lock (_hashTable) { - data = new byte[Unsafe.SizeOf() + _hashTable.Count * Unsafe.SizeOf()]; - - // CacheManifestHeader has the same size as a Hash128. - Span dataSpan = MemoryMarshal.Cast(data.AsSpan()).Slice(1); - - int i = 0; - - foreach (Hash128 hash in _hashTable) - { - dataSpan[i++] = hash; - } + data = CacheHelper.ComputeManifest(_version, _graphicsApi, _hashType, _hashTable); } - manifestHeader.UpdateChecksum(data.AsSpan().Slice(Unsafe.SizeOf())); - - MemoryMarshal.Write(data, ref manifestHeader); - File.WriteAllBytes(GetManifestPath(), data); } - /// - /// Generate the path to the cache directory. - /// - /// The base of the cache directory - /// The graphics api in use - /// The name of the shader provider in use - /// The name of the cache - /// The path to the cache directory - private static string GenerateCachePath(string baseCacheDirectory, CacheGraphicsApi graphicsApi, string shaderProvider, string cacheName) - { - string graphicsApiName = graphicsApi switch - { - CacheGraphicsApi.OpenGL => "opengl", - CacheGraphicsApi.OpenGLES => "opengles", - CacheGraphicsApi.Vulkan => "vulkan", - CacheGraphicsApi.DirectX => "directx", - CacheGraphicsApi.Metal => "metal", - CacheGraphicsApi.Guest => "guest", - _ => throw new NotImplementedException(graphicsApi.ToString()), - }; - - return Path.Combine(baseCacheDirectory, graphicsApiName, shaderProvider, cacheName); - } - /// /// Get a cached file with the given hash. /// @@ -438,27 +375,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache if (found) { - ZipArchiveEntry archiveEntry = _cacheArchive.GetEntry($"{keyHash}"); - - if (archiveEntry != null) - { - try - { - byte[] result = new byte[archiveEntry.Length]; - - using (Stream archiveStream = archiveEntry.Open()) - { - archiveStream.Read(result); - - return result; - } - } - catch (Exception e) - { - Logger.Error?.Print(LogClass.Gpu, $"Cannot load cache file {keyHash} from archive"); - Logger.Error?.Print(LogClass.Gpu, e.ToString()); - } - } + return CacheHelper.ReadFromArchive(_cacheArchive, keyHash); } return null; @@ -480,17 +397,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.Cache if (found) { - string cacheTempFilePath = GenCacheTempFilePath(keyHash); - - try - { - return File.ReadAllBytes(GenCacheTempFilePath(keyHash)); - } - catch (Exception e) - { - Logger.Error?.Print(LogClass.Gpu, $"Cannot load cache file at {cacheTempFilePath}"); - Logger.Error?.Print(LogClass.Gpu, e.ToString()); - } + return CacheHelper.ReadFromFile(GetCacheTempDataPath(), keyHash); } return null; -- cgit v1.2.3