• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2019 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 // Feature.h: Definition of structs to hold feature/workaround information.
7 //
8 
9 #ifndef ANGLE_PLATFORM_FEATURE_H_
10 #define ANGLE_PLATFORM_FEATURE_H_
11 
12 #include <map>
13 #include <string>
14 #include <vector>
15 
16 #define ANGLE_FEATURE_CONDITION(set, feature, cond)       \
17     do                                                    \
18     {                                                     \
19         (set)->feature.enabled   = cond;                  \
20         (set)->feature.condition = ANGLE_STRINGIFY(cond); \
21     } while (0)
22 
23 namespace angle
24 {
25 
26 enum class FeatureCategory
27 {
28     FrontendFeatures,
29     FrontendWorkarounds,
30     OpenGLWorkarounds,
31     OpenGLFeatures,
32     D3DWorkarounds,
33     VulkanFeatures,
34     VulkanWorkarounds,
35     VulkanAppWorkarounds,
36     MetalFeatures,
37     MetalWorkarounds,
38 };
39 
40 constexpr char kFeatureCategoryFrontendWorkarounds[]  = "Frontend workarounds";
41 constexpr char kFeatureCategoryFrontendFeatures[]     = "Frontend features";
42 constexpr char kFeatureCategoryOpenGLWorkarounds[]    = "OpenGL workarounds";
43 constexpr char kFeatureCategoryOpenGLFeatures[]       = "OpenGL features";
44 constexpr char kFeatureCategoryD3DWorkarounds[]       = "D3D workarounds";
45 constexpr char kFeatureCategoryVulkanAppWorkarounds[] = "Vulkan app workarounds";
46 constexpr char kFeatureCategoryVulkanWorkarounds[]    = "Vulkan workarounds";
47 constexpr char kFeatureCategoryVulkanFeatures[]       = "Vulkan features";
48 constexpr char kFeatureCategoryMetalFeatures[]        = "Metal features";
49 constexpr char kFeatureCategoryMetalWorkarounds[]     = "Metal workarounds";
50 constexpr char kFeatureCategoryUnknown[]              = "Unknown";
51 
FeatureCategoryToString(const FeatureCategory & fc)52 inline const char *FeatureCategoryToString(const FeatureCategory &fc)
53 {
54     switch (fc)
55     {
56         case FeatureCategory::FrontendFeatures:
57             return kFeatureCategoryFrontendFeatures;
58             break;
59 
60         case FeatureCategory::FrontendWorkarounds:
61             return kFeatureCategoryFrontendWorkarounds;
62             break;
63 
64         case FeatureCategory::OpenGLWorkarounds:
65             return kFeatureCategoryOpenGLWorkarounds;
66             break;
67 
68         case FeatureCategory::OpenGLFeatures:
69             return kFeatureCategoryOpenGLFeatures;
70             break;
71 
72         case FeatureCategory::D3DWorkarounds:
73             return kFeatureCategoryD3DWorkarounds;
74             break;
75 
76         case FeatureCategory::VulkanFeatures:
77             return kFeatureCategoryVulkanFeatures;
78             break;
79 
80         case FeatureCategory::VulkanWorkarounds:
81             return kFeatureCategoryVulkanWorkarounds;
82             break;
83 
84         case FeatureCategory::VulkanAppWorkarounds:
85             return kFeatureCategoryVulkanAppWorkarounds;
86             break;
87 
88         case FeatureCategory::MetalFeatures:
89             return kFeatureCategoryMetalFeatures;
90             break;
91 
92         case FeatureCategory::MetalWorkarounds:
93             return kFeatureCategoryMetalWorkarounds;
94             break;
95 
96         default:
97             return kFeatureCategoryUnknown;
98             break;
99     }
100 }
101 
102 constexpr char kFeatureStatusEnabled[]  = "enabled";
103 constexpr char kFeatureStatusDisabled[] = "disabled";
104 
FeatureStatusToString(const bool & status)105 inline const char *FeatureStatusToString(const bool &status)
106 {
107     if (status)
108     {
109         return kFeatureStatusEnabled;
110     }
111     return kFeatureStatusDisabled;
112 }
113 
114 struct FeatureInfo;
115 
116 using FeatureMap  = std::map<std::string, FeatureInfo *>;
117 using FeatureList = std::vector<const FeatureInfo *>;
118 
119 struct FeatureInfo
120 {
121     FeatureInfo(const FeatureInfo &other);
122     FeatureInfo(const char *name,
123                 const FeatureCategory &category,
124                 const char *description,
125                 FeatureMap *const mapPtr,
126                 const char *bug);
127     ~FeatureInfo();
128 
129     // The name of the workaround, lowercase, camel_case
130     const char *const name;
131 
132     // The category that the workaround belongs to. Eg. "Vulkan workarounds"
133     const FeatureCategory category;
134 
135     // A short description to be read by the user.
136     const char *const description;
137 
138     // A link to the bug, if any
139     const char *const bug;
140 
141     // Whether the workaround is enabled or not. Determined by heuristics like vendor ID and
142     // version, but may be overriden to any value.
143     bool enabled = false;
144 
145     // A stringified version of the condition used to set 'enabled'. ie "IsNvidia() && IsApple()"
146     const char *condition;
147 };
148 
149 inline FeatureInfo::FeatureInfo(const FeatureInfo &other) = default;
150 inline FeatureInfo::FeatureInfo(const char *name,
151                                 const FeatureCategory &category,
152                                 const char *description,
153                                 FeatureMap *const mapPtr,
154                                 const char *bug = "")
name(name)155     : name(name),
156       category(category),
157       description(description),
158       bug(bug),
159       enabled(false),
160       condition("")
161 {
162     if (mapPtr != nullptr)
163     {
164         (*mapPtr)[std::string(name)] = this;
165     }
166 }
167 
168 inline FeatureInfo::~FeatureInfo() = default;
169 
170 struct FeatureSetBase
171 {
172   public:
173     FeatureSetBase();
174     ~FeatureSetBase();
175 
176   private:
177     // Non-copyable
178     FeatureSetBase(const FeatureSetBase &other)            = delete;
179     FeatureSetBase &operator=(const FeatureSetBase &other) = delete;
180 
181   protected:
182     FeatureMap members = FeatureMap();
183 
184   public:
185     void reset();
186     void overrideFeatures(const std::vector<std::string> &featureNames, bool enabled);
187     void populateFeatureList(FeatureList *features) const;
188 
getFeaturesFeatureSetBase189     const FeatureMap &getFeatures() const { return members; }
190 };
191 
192 inline FeatureSetBase::FeatureSetBase()  = default;
193 inline FeatureSetBase::~FeatureSetBase() = default;
194 
195 }  // namespace angle
196 
197 #endif  // ANGLE_PLATFORM_WORKAROUND_H_
198