From: Stefan Dösinger stefan@codeweavers.com
--- Makefile.am | 1 + libs/vkd3d/cache.c | 81 ++++++++++++++++++++++++++++++++++++++ libs/vkd3d/vkd3d_private.h | 36 +++++++++++++++++ 3 files changed, 118 insertions(+) create mode 100644 libs/vkd3d/cache.c
diff --git a/Makefile.am b/Makefile.am index 68e8642e0..86b7afdd9 100644 --- a/Makefile.am +++ b/Makefile.am @@ -351,6 +351,7 @@ libvkd3d_la_SOURCES = \ include/vkd3d_d3d12.idl \ include/vkd3d_d3dcommon.idl \ include/vkd3d_unknown.idl \ + libs/vkd3d/cache.c \ libs/vkd3d/command.c \ libs/vkd3d/device.c \ libs/vkd3d/resource.c \ diff --git a/libs/vkd3d/cache.c b/libs/vkd3d/cache.c new file mode 100644 index 000000000..7f6b712e8 --- /dev/null +++ b/libs/vkd3d/cache.c @@ -0,0 +1,81 @@ +/* + * Copyright 2024 Stefan Dösinger for CodeWeavers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#include "vkd3d_private.h" + +struct vkd3d_shader_cache +{ + unsigned int refcount; + struct vkd3d_shader_cache_info info; + char filename[]; +}; + +int vkd3d_shader_open_cache(const struct vkd3d_shader_cache_info *info, + struct vkd3d_shader_cache **cache) +{ + struct vkd3d_shader_cache *object; + size_t size = 0; + + TRACE("%p, %p.\n", info, cache); + + if (!info) + { + WARN("No cache info, returning VKD3D_ERROR_INVALID_ARGUMENT.\n"); + return VKD3D_ERROR_INVALID_ARGUMENT; + } + if (info->filename && !(size = strlen(info->filename))) + { + WARN("Filename is an empty string, returning VKD3D_ERROR_INVALID_ARGUMENT.\n"); + return VKD3D_ERROR_INVALID_ARGUMENT; + } + + size++; + object = vkd3d_calloc(1, offsetof(struct vkd3d_shader_cache, filename[size])); + if (!object) + return VKD3D_ERROR_OUT_OF_MEMORY; + + object->refcount = 1; + object->info = *info; + if (info->filename) + { + memcpy(object->filename, info->filename, size); + object->info.filename = object->filename; + } + + *cache = object; + return VKD3D_OK; +} + +unsigned int vkd3d_shader_cache_incref(struct vkd3d_shader_cache *cache) +{ + unsigned int refcount = vkd3d_atomic_increment_u32(&cache->refcount); + TRACE("cache %p refcount %u.\n", cache, refcount); + return refcount; +} + +unsigned int vkd3d_shader_cache_decref(struct vkd3d_shader_cache *cache) +{ + unsigned int refcount = vkd3d_atomic_decrement_u32(&cache->refcount); + TRACE("cache %p refcount %u.\n", cache, refcount); + + if (refcount) + return refcount; + + vkd3d_free(cache); + return 0; +} diff --git a/libs/vkd3d/vkd3d_private.h b/libs/vkd3d/vkd3d_private.h index d5e12ee3c..c9f957ce6 100644 --- a/libs/vkd3d/vkd3d_private.h +++ b/libs/vkd3d/vkd3d_private.h @@ -1927,4 +1927,40 @@ static inline void vkd3d_prepend_struct(void *header, void *structure) vkd3d_header->next = vkd3d_structure; }
+struct vkd3d_shader_cache; + +enum vkd3d_shader_cache_flags +{ + VKD3D_SHADER_CACHE_FLAGS_NONE = 0x00000000, + VKD3D_SHADER_CACHE_FLAGS_NO_SERIALIZE = 0x00000001, + VKD3D_SHADER_CACHE_FLAGS_READ_ONLY = 0x00000002, + + VKD3D_FORCE_32_BIT_ENUM(VKD3D_SHADER_CACHE_FLAGS), +}; + +struct vkd3d_shader_cache_info +{ + /*enum vkd3d_structure_type type;*/ + const void *next; + + /** File name to open, or NULL for a memory-only cache. */ + const char *filename; + /** Maximum amount of data the cache holds in memory. */ + uint64_t mem_size; + /** Maximum amount of data written to disk. Ignored if filename is NULL. */ + uint64_t disk_size; + /** Maximum number of cache entries. */ + uint64_t max_entries; + /** Random flags, what else. */ + enum vkd3d_shader_cache_flags flags; + /** An application-chosen version number. If the version of an existing + * cache on disk does not match, the old data will be discarded. */ + uint64_t version; +}; + +int vkd3d_shader_open_cache(const struct vkd3d_shader_cache_info *info, + struct vkd3d_shader_cache **cache); +unsigned int vkd3d_shader_cache_incref(struct vkd3d_shader_cache *cache); +unsigned int vkd3d_shader_cache_decref(struct vkd3d_shader_cache *cache); + #endif /* __VKD3D_PRIVATE_H */