blob: e1166e8d64bfa8df769ab0d29dd4ac978e0e9b12 [file] [log] [blame]
Jamie Madill4f86d052017-06-05 12:59:26 -04001//
2// Copyright 2017 The ANGLE Project Authors. All rights reserved.
3// Use of this source code is governed by a BSD-style license that can be
4// found in the LICENSE file.
5//
6// MemoryProgramCache: Stores compiled and linked programs in memory so they don't
7// always have to be re-compiled. Can be used in conjunction with the platform
8// layer to warm up the cache from disk.
9
10#ifndef LIBANGLE_MEMORY_PROGRAM_CACHE_H_
11#define LIBANGLE_MEMORY_PROGRAM_CACHE_H_
12
Jamie Madill32447362017-06-28 14:53:52 -040013#include <array>
14
Jamie Madill4f86d052017-06-05 12:59:26 -040015#include "common/MemoryBuffer.h"
16#include "libANGLE/Error.h"
Jamie Madill32447362017-06-28 14:53:52 -040017#include "libANGLE/SizedMRUCache.h"
18
19namespace gl
20{
Jamie Madill360daee2017-06-29 10:36:19 -040021// 160-bit SHA-1 hash key.
Jamie Madillc43be722017-07-13 16:22:14 -040022constexpr size_t kProgramHashLength = 20;
23using ProgramHash = std::array<uint8_t, kProgramHashLength>;
Jamie Madill32447362017-06-28 14:53:52 -040024} // namespace gl
25
26namespace std
27{
28template <>
29struct hash<gl::ProgramHash>
30{
31 // Simple routine to hash four ints.
32 size_t operator()(const gl::ProgramHash &programHash) const
33 {
34 unsigned int hash = 0;
35 for (uint32_t num : programHash)
36 {
37 hash *= 37;
38 hash += num;
39 }
40 return hash;
41 }
42};
43} // namespace std
Jamie Madill4f86d052017-06-05 12:59:26 -040044
45namespace gl
46{
47class Context;
48class InfoLog;
49class Program;
50class ProgramState;
51
52class MemoryProgramCache final : angle::NonCopyable
53{
54 public:
Jamie Madill32447362017-06-28 14:53:52 -040055 MemoryProgramCache(size_t maxCacheSizeBytes);
56 ~MemoryProgramCache();
57
Jamie Madill4f86d052017-06-05 12:59:26 -040058 // Writes a program's binary to the output memory buffer.
59 static void Serialize(const Context *context,
60 const Program *program,
61 angle::MemoryBuffer *binaryOut);
62
63 // Loads program state according to the specified binary blob.
64 static LinkResult Deserialize(const Context *context,
65 const Program *program,
66 ProgramState *state,
67 const uint8_t *binary,
68 size_t length,
69 InfoLog &infoLog);
Jamie Madill32447362017-06-28 14:53:52 -040070
71 static void ComputeHash(const Context *context, const Program *program, ProgramHash *hashOut);
72
73 // Check if the cache contains a binary matching the specified program.
74 bool get(const ProgramHash &programHash, const angle::MemoryBuffer **programOut);
75
Jamie Madillc43be722017-07-13 16:22:14 -040076 // For querying the contents of the cache.
77 bool getAt(size_t index, ProgramHash *hashOut, const angle::MemoryBuffer **programOut);
78
Jamie Madill32447362017-06-28 14:53:52 -040079 // Evict a program from the binary cache.
80 void remove(const ProgramHash &programHash);
81
82 // Helper method that serializes a program.
83 void putProgram(const ProgramHash &programHash, const Context *context, const Program *program);
84
Jamie Madill4c19a8a2017-07-24 11:46:06 -040085 // Same as putProgram but computes the hash.
86 void updateProgram(const Context *context, const Program *program);
87
Jamie Madillc43be722017-07-13 16:22:14 -040088 // Store a binary directly.
89 void putBinary(const ProgramHash &programHash, const uint8_t *binary, size_t length);
Jamie Madill32447362017-06-28 14:53:52 -040090
91 // Check the cache, and deserialize and load the program if found. Evict existing hash if load
92 // fails.
93 LinkResult getProgram(const Context *context,
94 const Program *program,
95 ProgramState *state,
96 ProgramHash *hashOut);
97
98 // Empty the cache.
99 void clear();
100
Jamie Madillc43be722017-07-13 16:22:14 -0400101 // Resize the cache. Discards current contents.
102 void resize(size_t maxCacheSizeBytes);
103
104 // Returns the number of entries in the cache.
105 size_t entryCount() const;
106
107 // Reduces the current cache size and returns the number of bytes freed.
108 size_t trim(size_t limit);
109
110 // Returns the current cache size in bytes.
111 size_t size() const;
112
113 // Returns the maximum cache size in bytes.
114 size_t maxSize() const;
115
Jamie Madill32447362017-06-28 14:53:52 -0400116 private:
117 // Insert or update a binary program. Program contents are transferred.
Jamie Madill360daee2017-06-29 10:36:19 -0400118 void put(const ProgramHash &programHash,
Jamie Madill360daee2017-06-29 10:36:19 -0400119 angle::MemoryBuffer &&binaryProgram);
Jamie Madill32447362017-06-28 14:53:52 -0400120
121 angle::SizedMRUCache<ProgramHash, angle::MemoryBuffer> mProgramBinaryCache;
122 unsigned int mIssuedWarnings;
Jamie Madill4f86d052017-06-05 12:59:26 -0400123};
124
125} // namespace gl
126
127#endif // LIBANGLE_MEMORY_PROGRAM_CACHE_H_