• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2016 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef SKSL_MODIFIERS
9 #define SKSL_MODIFIERS
10 
11 #include "include/private/SkSLLayout.h"
12 
13 #include <vector>
14 
15 namespace SkSL {
16 
17 class Context;
18 
19 /**
20  * A set of modifier keywords (in, out, uniform, etc.) appearing before a declaration.
21  */
22 struct Modifiers {
23     /**
24      * OpenGL requires modifiers to be in a strict order:
25      * - invariant-qualifier:     (invariant)
26      * - interpolation-qualifier: flat, noperspective, (smooth)
27      * - storage-qualifier:       const, uniform
28      * - parameter-qualifier:     in, out, inout
29      * - precision-qualifier:     highp, mediump, lowp
30      *
31      * SkSL does not have `invariant` or `smooth`.
32      */
33 
34     enum Flag {
35         kNo_Flag             =       0,
36         // Real GLSL modifiers
37         kFlat_Flag           = 1 <<  0,
38         kNoPerspective_Flag  = 1 <<  1,
39         kConst_Flag          = 1 <<  2,
40         kUniform_Flag        = 1 <<  3,
41         kIn_Flag             = 1 <<  4,
42         kOut_Flag            = 1 <<  5,
43         kHighp_Flag          = 1 <<  6,
44         kMediump_Flag        = 1 <<  7,
45         kLowp_Flag           = 1 <<  8,
46         // SkSL extensions, not present in GLSL
47         kES3_Flag            = 1 <<  9,
48         kHasSideEffects_Flag = 1 <<  10,
49         kInline_Flag         = 1 <<  11,
50         kNoInline_Flag       = 1 <<  12,
51     };
52 
ModifiersModifiers53     Modifiers()
54     : fLayout(Layout())
55     , fFlags(0) {}
56 
ModifiersModifiers57     Modifiers(const Layout& layout, int flags)
58     : fLayout(layout)
59     , fFlags(flags) {}
60 
descriptionModifiers61     String description() const {
62         String result = fLayout.description();
63 
64         // SkSL extensions
65         if (fFlags & kES3_Flag) {
66             result += "$es3 ";
67         }
68         if (fFlags & kHasSideEffects_Flag) {
69             result += "sk_has_side_effects ";
70         }
71         if (fFlags & kNoInline_Flag) {
72             result += "noinline ";
73         }
74 
75         // Real GLSL qualifiers (must be specified in order in GLSL 4.1 and below)
76         if (fFlags & kFlat_Flag) {
77             result += "flat ";
78         }
79         if (fFlags & kNoPerspective_Flag) {
80             result += "noperspective ";
81         }
82         if (fFlags & kConst_Flag) {
83             result += "const ";
84         }
85         if (fFlags & kUniform_Flag) {
86             result += "uniform ";
87         }
88         if ((fFlags & kIn_Flag) && (fFlags & kOut_Flag)) {
89             result += "inout ";
90         } else if (fFlags & kIn_Flag) {
91             result += "in ";
92         } else if (fFlags & kOut_Flag) {
93             result += "out ";
94         }
95         if (fFlags & kHighp_Flag) {
96             result += "highp ";
97         }
98         if (fFlags & kMediump_Flag) {
99             result += "mediump ";
100         }
101         if (fFlags & kLowp_Flag) {
102             result += "lowp ";
103         }
104 
105         return result;
106     }
107 
108     bool operator==(const Modifiers& other) const {
109         return fLayout == other.fLayout && fFlags == other.fFlags;
110     }
111 
112     bool operator!=(const Modifiers& other) const {
113         return !(*this == other);
114     }
115 
116     /**
117      * Verifies that only permitted modifiers and layout flags are included. Reports errors and
118      * returns false in the event of a violation.
119      */
120     bool checkPermitted(const Context& context, int line, int permittedModifierFlags,
121             int permittedLayoutFlags) const;
122 
123     Layout fLayout;
124     int fFlags;
125 };
126 
127 } // namespace SkSL
128 
129 namespace std {
130 
131 template <>
132 struct hash<SkSL::Modifiers> {
133     size_t operator()(const SkSL::Modifiers& key) const {
134         return (size_t) key.fFlags ^ ((size_t) key.fLayout.fFlags << 8) ^
135                ((size_t) key.fLayout.fBuiltin << 16);
136     }
137 };
138 
139 } // namespace std
140 
141 #endif
142