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_FIELDACCESS 9 #define SKSL_FIELDACCESS 10 11 #include "include/core/SkSpan.h" 12 #include "src/sksl/SkSLPosition.h" 13 #include "src/sksl/ir/SkSLExpression.h" 14 #include "src/sksl/ir/SkSLIRNode.h" 15 #include "src/sksl/ir/SkSLType.h" 16 17 #include <cstddef> 18 #include <cstdint> 19 #include <memory> 20 #include <string> 21 #include <string_view> 22 #include <utility> 23 24 namespace SkSL { 25 26 class Context; 27 enum class OperatorPrecedence : uint8_t; 28 29 enum class FieldAccessOwnerKind : int8_t { 30 kDefault, 31 // this field access is to a field of an anonymous interface block (and thus, the field name 32 // is actually in global scope, so only the field name needs to be written in GLSL) 33 kAnonymousInterfaceBlock 34 }; 35 36 /** 37 * An expression which extracts a field from a struct, as in 'foo.bar'. 38 */ 39 class FieldAccess final : public Expression { 40 public: 41 using OwnerKind = FieldAccessOwnerKind; 42 43 inline static constexpr Kind kIRNodeKind = Kind::kFieldAccess; 44 45 FieldAccess(Position pos, std::unique_ptr<Expression> base, int fieldIndex, 46 OwnerKind ownerKind = OwnerKind::kDefault) 47 : INHERITED(pos, kIRNodeKind, base->type().fields()[fieldIndex].fType) 48 , fFieldIndex(fieldIndex) 49 , fOwnerKind(ownerKind) 50 , fBase(std::move(base)) {} 51 52 // Returns a field-access expression; reports errors via the ErrorReporter. 53 static std::unique_ptr<Expression> Convert(const Context& context, 54 Position pos, 55 std::unique_ptr<Expression> base, 56 std::string_view field); 57 58 // Returns a field-access expression; reports errors via ASSERT. 59 static std::unique_ptr<Expression> Make(const Context& context, 60 Position pos, 61 std::unique_ptr<Expression> base, 62 int fieldIndex, 63 OwnerKind ownerKind = OwnerKind::kDefault); 64 base()65 std::unique_ptr<Expression>& base() { 66 return fBase; 67 } 68 base()69 const std::unique_ptr<Expression>& base() const { 70 return fBase; 71 } 72 fieldIndex()73 int fieldIndex() const { 74 return fFieldIndex; 75 } 76 ownerKind()77 OwnerKind ownerKind() const { 78 return fOwnerKind; 79 } 80 clone(Position pos)81 std::unique_ptr<Expression> clone(Position pos) const override { 82 return std::make_unique<FieldAccess>(pos, 83 this->base()->clone(), 84 this->fieldIndex(), 85 this->ownerKind()); 86 } 87 88 size_t initialSlot() const; 89 90 std::string description(OperatorPrecedence) const override; 91 92 private: 93 int fFieldIndex; 94 FieldAccessOwnerKind fOwnerKind; 95 std::unique_ptr<Expression> fBase; 96 97 using INHERITED = Expression; 98 }; 99 100 } // namespace SkSL 101 102 #endif 103