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_GLSLCODEGENERATOR 9 #define SKSL_GLSLCODEGENERATOR 10 11 #include <stack> 12 #include <tuple> 13 #include <unordered_map> 14 15 #include "SkSLCodeGenerator.h" 16 #include "SkSLStringStream.h" 17 #include "ir/SkSLBinaryExpression.h" 18 #include "ir/SkSLBoolLiteral.h" 19 #include "ir/SkSLConstructor.h" 20 #include "ir/SkSLDoStatement.h" 21 #include "ir/SkSLExtension.h" 22 #include "ir/SkSLFloatLiteral.h" 23 #include "ir/SkSLIfStatement.h" 24 #include "ir/SkSLIndexExpression.h" 25 #include "ir/SkSLInterfaceBlock.h" 26 #include "ir/SkSLIntLiteral.h" 27 #include "ir/SkSLFieldAccess.h" 28 #include "ir/SkSLForStatement.h" 29 #include "ir/SkSLFunctionCall.h" 30 #include "ir/SkSLFunctionDeclaration.h" 31 #include "ir/SkSLFunctionDefinition.h" 32 #include "ir/SkSLPrefixExpression.h" 33 #include "ir/SkSLPostfixExpression.h" 34 #include "ir/SkSLProgramElement.h" 35 #include "ir/SkSLReturnStatement.h" 36 #include "ir/SkSLSetting.h" 37 #include "ir/SkSLStatement.h" 38 #include "ir/SkSLSwitchStatement.h" 39 #include "ir/SkSLSwizzle.h" 40 #include "ir/SkSLTernaryExpression.h" 41 #include "ir/SkSLVarDeclarations.h" 42 #include "ir/SkSLVarDeclarationsStatement.h" 43 #include "ir/SkSLVariableReference.h" 44 #include "ir/SkSLWhileStatement.h" 45 46 namespace SkSL { 47 48 #define kLast_Capability SpvCapabilityMultiViewport 49 50 /** 51 * Converts a Program into GLSL code. 52 */ 53 class GLSLCodeGenerator : public CodeGenerator { 54 public: 55 enum Precedence { 56 kParentheses_Precedence = 1, 57 kPostfix_Precedence = 2, 58 kPrefix_Precedence = 3, 59 kMultiplicative_Precedence = 4, 60 kAdditive_Precedence = 5, 61 kShift_Precedence = 6, 62 kRelational_Precedence = 7, 63 kEquality_Precedence = 8, 64 kBitwiseAnd_Precedence = 9, 65 kBitwiseXor_Precedence = 10, 66 kBitwiseOr_Precedence = 11, 67 kLogicalAnd_Precedence = 12, 68 kLogicalXor_Precedence = 13, 69 kLogicalOr_Precedence = 14, 70 kTernary_Precedence = 15, 71 kAssignment_Precedence = 16, 72 kSequence_Precedence = 17, 73 kTopLevel_Precedence = kSequence_Precedence 74 }; 75 76 GLSLCodeGenerator(const Context* context, const Program* program, ErrorReporter* errors, 77 OutputStream* out) 78 : INHERITED(program, errors, out) 79 , fLineEnding("\n") 80 , fContext(*context) 81 , fProgramKind(program->fKind) {} 82 83 bool generateCode() override; 84 85 protected: 86 void write(const char* s); 87 88 void writeLine(); 89 90 void writeLine(const char* s); 91 92 void write(const String& s); 93 94 void write(StringFragment s); 95 96 void writeLine(const String& s); 97 98 virtual void writeHeader(); 99 100 virtual bool usesPrecisionModifiers() const; 101 102 virtual String getTypeName(const Type& type); 103 104 void writeType(const Type& type); 105 106 void writeExtension(const String& name); 107 108 void writeExtension(const String& name, bool require); 109 110 void writeInterfaceBlock(const InterfaceBlock& intf); 111 112 void writeFunctionStart(const FunctionDeclaration& f); 113 114 void writeFunctionDeclaration(const FunctionDeclaration& f); 115 116 virtual void writeFunction(const FunctionDefinition& f); 117 118 void writeLayout(const Layout& layout); 119 120 void writeModifiers(const Modifiers& modifiers, bool globalContext); 121 122 virtual void writeInputVars(); 123 124 virtual void writeVarInitializer(const Variable& var, const Expression& value); 125 126 const char* getTypePrecision(const Type& type); 127 128 void writeTypePrecision(const Type& type); 129 130 void writeVarDeclarations(const VarDeclarations& decl, bool global); 131 132 void writeFragCoord(); 133 134 virtual void writeVariableReference(const VariableReference& ref); 135 136 void writeExpression(const Expression& expr, Precedence parentPrecedence); 137 138 void writeIntrinsicCall(const FunctionCall& c); 139 140 void writeMinAbsHack(Expression& absExpr, Expression& otherExpr); 141 142 void writeDeterminantHack(const Expression& mat); 143 144 void writeInverseHack(const Expression& mat); 145 146 void writeTransposeHack(const Expression& mat); 147 148 void writeInverseSqrtHack(const Expression& x); 149 150 virtual void writeFunctionCall(const FunctionCall& c); 151 152 void writeConstructor(const Constructor& c, Precedence parentPrecedence); 153 154 virtual void writeFieldAccess(const FieldAccess& f); 155 156 virtual void writeSwizzle(const Swizzle& swizzle); 157 158 static Precedence GetBinaryPrecedence(Token::Kind op); 159 160 virtual void writeBinaryExpression(const BinaryExpression& b, Precedence parentPrecedence); 161 void writeShortCircuitWorkaroundExpression(const BinaryExpression& b, 162 Precedence parentPrecedence); 163 164 void writeTernaryExpression(const TernaryExpression& t, Precedence parentPrecedence); 165 166 virtual void writeIndexExpression(const IndexExpression& expr); 167 168 void writePrefixExpression(const PrefixExpression& p, Precedence parentPrecedence); 169 170 void writePostfixExpression(const PostfixExpression& p, Precedence parentPrecedence); 171 172 void writeBoolLiteral(const BoolLiteral& b); 173 174 virtual void writeIntLiteral(const IntLiteral& i); 175 176 void writeFloatLiteral(const FloatLiteral& f); 177 178 virtual void writeSetting(const Setting& s); 179 180 void writeStatement(const Statement& s); 181 182 void writeStatements(const std::vector<std::unique_ptr<Statement>>& statements); 183 184 void writeBlock(const Block& b); 185 186 virtual void writeIfStatement(const IfStatement& stmt); 187 188 void writeForStatement(const ForStatement& f); 189 190 void writeWhileStatement(const WhileStatement& w); 191 192 void writeDoStatement(const DoStatement& d); 193 194 virtual void writeSwitchStatement(const SwitchStatement& s); 195 196 virtual void writeReturnStatement(const ReturnStatement& r); 197 198 virtual void writeProgramElement(const ProgramElement& e); 199 200 const char* fLineEnding; 201 const Context& fContext; 202 StringStream fExtensions; 203 StringStream fGlobals; 204 StringStream fExtraFunctions; 205 String fFunctionHeader; 206 Program::Kind fProgramKind; 207 int fVarCount = 0; 208 int fIndentation = 0; 209 bool fAtLineStart = false; 210 // Keeps track of which struct types we have written. Given that we are unlikely to ever write 211 // more than one or two structs per shader, a simple linear search will be faster than anything 212 // fancier. 213 std::vector<const Type*> fWrittenStructs; 214 std::set<String> fWrittenIntrinsics; 215 // true if we have run into usages of dFdx / dFdy 216 bool fFoundDerivatives = false; 217 bool fFoundImageDecl = false; 218 bool fFoundExternalSamplerDecl = false; 219 bool fFoundGSInvocations = false; 220 bool fSetupFragPositionGlobal = false; 221 bool fSetupFragPositionLocal = false; 222 bool fSetupFragCoordWorkaround = false; 223 224 // We map function names to function class so we can quickly deal with function calls that need 225 // extra processing 226 enum class FunctionClass { 227 kAbs, 228 kAtan, 229 kDeterminant, 230 kDerivative, 231 kFMA, 232 kFract, 233 kInverse, 234 kInverseSqrt, 235 kMin, 236 kPow, 237 kSaturate, 238 kTexture, 239 kTranspose 240 }; 241 static std::unordered_map<StringFragment, FunctionClass>* fFunctionClasses; 242 243 typedef CodeGenerator INHERITED; 244 }; 245 246 } 247 248 #endif 249