blob: 417e82403abf2d9e61954e57524839680b68ebf2 [file] [log] [blame]
Dmitry Skiba01971112015-07-10 14:54:00 -04001//
2// Copyright (c) 2015 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
7// Cache.cpp: Implements a cache for various commonly created objects.
8
9#include <limits>
10
11#include "common/angleutils.h"
12#include "common/debug.h"
13#include "compiler/translator/Cache.h"
14
Jamie Madill45bcc782016-11-07 13:58:48 -050015namespace sh
16{
17
Dmitry Skiba01971112015-07-10 14:54:00 -040018namespace
19{
20
21class TScopedAllocator : angle::NonCopyable
22{
23 public:
Jamie Madilld7b1ab52016-12-12 14:42:19 -050024 TScopedAllocator(TPoolAllocator *allocator) : mPreviousAllocator(GetGlobalPoolAllocator())
Dmitry Skiba01971112015-07-10 14:54:00 -040025 {
26 SetGlobalPoolAllocator(allocator);
27 }
Jamie Madilld7b1ab52016-12-12 14:42:19 -050028 ~TScopedAllocator() { SetGlobalPoolAllocator(mPreviousAllocator); }
Dmitry Skiba01971112015-07-10 14:54:00 -040029
30 private:
31 TPoolAllocator *mPreviousAllocator;
32};
33
34} // namespace
35
36TCache::TypeKey::TypeKey(TBasicType basicType,
37 TPrecision precision,
38 TQualifier qualifier,
39 unsigned char primarySize,
40 unsigned char secondarySize)
41{
Jamie Madilld7b1ab52016-12-12 14:42:19 -050042 static_assert(sizeof(components) <= sizeof(value), "TypeKey::value is too small");
Dmitry Skiba01971112015-07-10 14:54:00 -040043
44 const size_t MaxEnumValue = std::numeric_limits<EnumComponentType>::max();
Dmitry Skiba01971112015-07-10 14:54:00 -040045
46 // TODO: change to static_assert() once we deprecate MSVC 2013 support
Jamie Madilld7b1ab52016-12-12 14:42:19 -050047 ASSERT(MaxEnumValue >= EbtLast && MaxEnumValue >= EbpLast && MaxEnumValue >= EvqLast &&
Dmitry Skiba01971112015-07-10 14:54:00 -040048 "TypeKey::EnumComponentType is too small");
49
Jamie Madilld7b1ab52016-12-12 14:42:19 -050050 value = 0;
51 components.basicType = static_cast<EnumComponentType>(basicType);
52 components.precision = static_cast<EnumComponentType>(precision);
53 components.qualifier = static_cast<EnumComponentType>(qualifier);
54 components.primarySize = primarySize;
Dmitry Skiba01971112015-07-10 14:54:00 -040055 components.secondarySize = secondarySize;
56}
57
58TCache *TCache::sCache = nullptr;
59
Jamie Madillacf2f3a2017-11-21 19:22:44 -050060TCache::TCache()
61{
62}
63
Dmitry Skiba01971112015-07-10 14:54:00 -040064void TCache::initialize()
65{
66 if (sCache == nullptr)
67 {
68 sCache = new TCache();
69 }
70}
71
72void TCache::destroy()
73{
74 SafeDelete(sCache);
75}
76
77const TType *TCache::getType(TBasicType basicType,
78 TPrecision precision,
79 TQualifier qualifier,
80 unsigned char primarySize,
81 unsigned char secondarySize)
82{
Jamie Madilld7b1ab52016-12-12 14:42:19 -050083 TypeKey key(basicType, precision, qualifier, primarySize, secondarySize);
Dmitry Skiba01971112015-07-10 14:54:00 -040084 auto it = sCache->mTypes.find(key);
85 if (it != sCache->mTypes.end())
86 {
87 return it->second;
88 }
89
90 TScopedAllocator scopedAllocator(&sCache->mAllocator);
91
Jamie Madilld7b1ab52016-12-12 14:42:19 -050092 TType *type = new TType(basicType, precision, qualifier, primarySize, secondarySize);
Dmitry Skiba01971112015-07-10 14:54:00 -040093 type->realize();
94 sCache->mTypes.insert(std::make_pair(key, type));
95
96 return type;
97}
Jamie Madill45bcc782016-11-07 13:58:48 -050098
99} // namespace sh