aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/sksl/ir
diff options
context:
space:
mode:
authorGravatar Ethan Nicholas <ethannicholas@google.com>2017-08-02 10:52:54 -0400
committerGravatar Skia Commit-Bot <skia-commit-bot@chromium.org>2017-08-02 18:47:00 +0000
commitdcba08e891f1766b047cf0dbe8bbd275d9f55d2b (patch)
treec53822e53f595ea7c886f1efb22a2835da368b79 /src/sksl/ir
parentd9971c0c20d9937f6eabbf03b7638916d8dd57d7 (diff)
Revert "Revert "support for 'half' types in sksl, plus general numeric type improvements""
This reverts commit 0e9605542444a7653359f4fc610f7620df9f6313. Bug: skia: Change-Id: Id45d091c1950887316c901ed9c9281181f346bcf Reviewed-on: https://skia-review.googlesource.com/29602 Reviewed-by: Ethan Nicholas <ethannicholas@google.com> Commit-Queue: Ethan Nicholas <ethannicholas@google.com>
Diffstat (limited to 'src/sksl/ir')
-rw-r--r--src/sksl/ir/SkSLExpression.h4
-rw-r--r--src/sksl/ir/SkSLIntLiteral.h7
-rw-r--r--src/sksl/ir/SkSLType.cpp30
-rw-r--r--src/sksl/ir/SkSLType.h66
4 files changed, 82 insertions, 25 deletions
diff --git a/src/sksl/ir/SkSLExpression.h b/src/sksl/ir/SkSLExpression.h
index 89a1a1e84a..286610f078 100644
--- a/src/sksl/ir/SkSLExpression.h
+++ b/src/sksl/ir/SkSLExpression.h
@@ -85,6 +85,10 @@ struct Expression : public IRNode {
return nullptr;
}
+ virtual int coercionCost(const Type& target) const {
+ return fType.coercionCost(target);
+ }
+
const Kind fKind;
const Type& fType;
diff --git a/src/sksl/ir/SkSLIntLiteral.h b/src/sksl/ir/SkSLIntLiteral.h
index d8eba5573a..6199f96610 100644
--- a/src/sksl/ir/SkSLIntLiteral.h
+++ b/src/sksl/ir/SkSLIntLiteral.h
@@ -40,6 +40,13 @@ struct IntLiteral : public Expression {
return fValue == i.fValue;
}
+ int coercionCost(const Type& target) const override {
+ if (target.isUnsigned()) {
+ return 0;
+ }
+ return INHERITED::coercionCost(target);
+ }
+
const int64_t fValue;
typedef Expression INHERITED;
diff --git a/src/sksl/ir/SkSLType.cpp b/src/sksl/ir/SkSLType.cpp
index 60d40cd867..1fdc9bb68a 100644
--- a/src/sksl/ir/SkSLType.cpp
+++ b/src/sksl/ir/SkSLType.cpp
@@ -10,31 +10,37 @@
namespace SkSL {
-bool Type::determineCoercionCost(const Type& other, int* outCost) const {
+int Type::coercionCost(const Type& other) const {
if (*this == other) {
- *outCost = 0;
- return true;
+ return 0;
}
if (this->kind() == kVector_Kind && other.kind() == kVector_Kind) {
if (this->columns() == other.columns()) {
- return this->componentType().determineCoercionCost(other.componentType(), outCost);
+ return this->componentType().coercionCost(other.componentType());
}
- return false;
+ return INT_MAX;
}
if (this->kind() == kMatrix_Kind) {
- if (this->columns() == other.columns() &&
- this->rows() == other.rows()) {
- return this->componentType().determineCoercionCost(other.componentType(), outCost);
+ if (this->columns() == other.columns() && this->rows() == other.rows()) {
+ return this->componentType().coercionCost(other.componentType());
}
- return false;
+ return INT_MAX;
+ }
+ if (this->isNumber() && other.isFloat()) {
+ return 1;
+ }
+ if (this->isSigned() && other.isSigned()) {
+ return 1;
+ }
+ if (this->isUnsigned() && other.isUnsigned()) {
+ return 1;
}
for (size_t i = 0; i < fCoercibleTypes.size(); i++) {
if (*fCoercibleTypes[i] == other) {
- *outCost = (int) i + 1;
- return true;
+ return (int) i + 1;
}
}
- return false;
+ return INT_MAX;
}
const Type& Type::toCompound(const Context& context, int columns, int rows) const {
diff --git a/src/sksl/ir/SkSLType.h b/src/sksl/ir/SkSLType.h
index ec91a1c52b..6ea4c5694c 100644
--- a/src/sksl/ir/SkSLType.h
+++ b/src/sksl/ir/SkSLType.h
@@ -52,37 +52,47 @@ public:
kOther_Kind
};
+ enum NumberKind {
+ kFloat_NumberKind,
+ kSigned_NumberKind,
+ kUnsigned_NumberKind,
+ kNonnumeric_NumberKind
+ };
+
// Create an "other" (special) type with the given name. These types cannot be directly
// referenced from user code.
Type(String name)
: INHERITED(Position(), kType_Kind, std::move(name))
- , fTypeKind(kOther_Kind) {}
+ , fTypeKind(kOther_Kind)
+ , fNumberKind(kNonnumeric_NumberKind) {}
// Create a generic type which maps to the listed types.
Type(String name, std::vector<const Type*> types)
: INHERITED(Position(), kType_Kind, std::move(name))
, fTypeKind(kGeneric_Kind)
+ , fNumberKind(kNonnumeric_NumberKind)
, fCoercibleTypes(std::move(types)) {}
// Create a struct type with the given fields.
Type(Position position, String name, std::vector<Field> fields)
: INHERITED(position, kType_Kind, std::move(name))
, fTypeKind(kStruct_Kind)
+ , fNumberKind(kNonnumeric_NumberKind)
, fFields(std::move(fields)) {}
// Create a scalar type.
- Type(String name, bool isNumber)
+ Type(String name, NumberKind numberKind)
: INHERITED(Position(), kType_Kind, std::move(name))
, fTypeKind(kScalar_Kind)
- , fIsNumber(isNumber)
+ , fNumberKind(numberKind)
, fColumns(1)
, fRows(1) {}
// Create a scalar type which can be coerced to the listed types.
- Type(String name, bool isNumber, std::vector<const Type*> coercibleTypes)
+ Type(String name, NumberKind numberKind, std::vector<const Type*> coercibleTypes)
: INHERITED(Position(), kType_Kind, std::move(name))
, fTypeKind(kScalar_Kind)
- , fIsNumber(isNumber)
+ , fNumberKind(numberKind)
, fCoercibleTypes(std::move(coercibleTypes))
, fColumns(1)
, fRows(1) {}
@@ -95,6 +105,7 @@ public:
Type(String name, Kind kind, const Type& componentType, int columns)
: INHERITED(Position(), kType_Kind, std::move(name))
, fTypeKind(kind)
+ , fNumberKind(kNonnumeric_NumberKind)
, fComponentType(&componentType)
, fColumns(columns)
, fRows(1)
@@ -104,6 +115,7 @@ public:
Type(String name, const Type& componentType, int columns, int rows)
: INHERITED(Position(), kType_Kind, std::move(name))
, fTypeKind(kMatrix_Kind)
+ , fNumberKind(kNonnumeric_NumberKind)
, fComponentType(&componentType)
, fColumns(columns)
, fRows(rows)
@@ -114,13 +126,14 @@ public:
bool isSampled)
: INHERITED(Position(), kType_Kind, std::move(name))
, fTypeKind(kSampler_Kind)
+ , fNumberKind(kNonnumeric_NumberKind)
, fDimensions(dimensions)
, fIsDepth(isDepth)
, fIsArrayed(isArrayed)
, fIsMultisampled(isMultisampled)
, fIsSampled(isSampled) {}
- String name() const {
+ const String& name() const {
return fName;
}
@@ -147,7 +160,35 @@ public:
* Returns true if this is a numeric scalar type.
*/
bool isNumber() const {
- return fIsNumber;
+ return fNumberKind != kNonnumeric_NumberKind;
+ }
+
+ /**
+ * Returns true if this is a floating-point scalar type (float, half, or double).
+ */
+ bool isFloat() const {
+ return fNumberKind == kFloat_NumberKind;
+ }
+
+ /**
+ * Returns true if this is a signed scalar type (int or short).
+ */
+ bool isSigned() const {
+ return fNumberKind == kSigned_NumberKind;
+ }
+
+ /**
+ * Returns true if this is an unsigned scalar type (uint or ushort).
+ */
+ bool isUnsigned() const {
+ return fNumberKind == kUnsigned_NumberKind;
+ }
+
+ /**
+ * Returns true if this is a signed or unsigned integer.
+ */
+ bool isInteger() const {
+ return isSigned() || isUnsigned();
}
/**
@@ -155,17 +196,15 @@ public:
* another type.
*/
bool canCoerceTo(const Type& other) const {
- int cost;
- return determineCoercionCost(other, &cost);
+ return coercionCost(other) != INT_MAX;
}
/**
* Determines the "cost" of coercing (implicitly converting) this type to another type. The cost
* is a number with no particular meaning other than that lower costs are preferable to higher
- * costs. Returns true if a conversion is possible, false otherwise. The value of the out
- * parameter is undefined if false is returned.
+ * costs. Returns INT_MAX if the coercion is not possible.
*/
- bool determineCoercionCost(const Type& other, int* outCost) const;
+ int coercionCost(const Type& other) const;
/**
* For matrices and vectors, returns the type of individual cells (e.g. mat2 has a component
@@ -245,7 +284,8 @@ private:
typedef Symbol INHERITED;
const Kind fTypeKind;
- const bool fIsNumber = false;
+ // always kNonnumeric_NumberKind for non-scalar values
+ const NumberKind fNumberKind;
const Type* fComponentType = nullptr;
const std::vector<const Type*> fCoercibleTypes;
const int fColumns = -1;