summaryrefslogtreecommitdiffstats
path: root/gfx/angle/src/compiler/translator/IntermNode.cpp
diff options
context:
space:
mode:
authorwolfbeast <mcwerewolf@gmail.com>2018-07-18 08:24:24 +0200
committerwolfbeast <mcwerewolf@gmail.com>2018-07-18 08:24:24 +0200
commitfc61780b35af913801d72086456f493f63197da6 (patch)
treef85891288a7bd988da9f0f15ae64e5c63f00d493 /gfx/angle/src/compiler/translator/IntermNode.cpp
parent69f7f9e5f1475891ce11cc4f431692f965b0cd30 (diff)
parent50d3e596bbe89c95615f96eb71f6bc5be737a1db (diff)
downloadUXP-2018.07.18.tar
UXP-2018.07.18.tar.gz
UXP-2018.07.18.tar.lz
UXP-2018.07.18.tar.xz
UXP-2018.07.18.zip
Merge commit '50d3e596bbe89c95615f96eb71f6bc5be737a1db' into Basilisk-releasev2018.07.18
# Conflicts: # browser/app/profile/firefox.js # browser/components/preferences/jar.mn
Diffstat (limited to 'gfx/angle/src/compiler/translator/IntermNode.cpp')
-rwxr-xr-xgfx/angle/src/compiler/translator/IntermNode.cpp2054
1 files changed, 886 insertions, 1168 deletions
diff --git a/gfx/angle/src/compiler/translator/IntermNode.cpp b/gfx/angle/src/compiler/translator/IntermNode.cpp
index b91b43ecf..dcf47879a 100755
--- a/gfx/angle/src/compiler/translator/IntermNode.cpp
+++ b/gfx/angle/src/compiler/translator/IntermNode.cpp
@@ -21,10 +21,6 @@
#include "compiler/translator/HashNames.h"
#include "compiler/translator/IntermNode.h"
#include "compiler/translator/SymbolTable.h"
-#include "compiler/translator/util.h"
-
-namespace sh
-{
namespace
{
@@ -47,14 +43,13 @@ TConstantUnion *Vectorize(const TConstantUnion &constant, size_t size)
return constUnion;
}
-void UndefinedConstantFoldingError(const TSourceLoc &loc,
- TOperator op,
- TBasicType basicType,
- TDiagnostics *diagnostics,
- TConstantUnion *result)
+void UndefinedConstantFoldingError(const TSourceLoc &loc, TOperator op, TBasicType basicType,
+ TInfoSink &infoSink, TConstantUnion *result)
{
- diagnostics->warning(loc, "operation result is undefined for the values passed in",
- GetOperatorString(op), "");
+ std::stringstream constantFoldingErrorStream;
+ constantFoldingErrorStream << "'" << GetOperatorString(op)
+ << "' operation result is undefined for the values passed in";
+ infoSink.info.message(EPrefixWarning, loc, constantFoldingErrorStream.str().c_str());
switch (basicType)
{
@@ -96,7 +91,7 @@ float VectorDotProduct(const TConstantUnion *paramArray1,
return result;
}
-TIntermTyped *CreateFoldedNode(const TConstantUnion *constArray,
+TIntermTyped *CreateFoldedNode(TConstantUnion *constArray,
const TIntermTyped *originalNode,
TQualifier qualifier)
{
@@ -173,7 +168,7 @@ bool TIntermLoop::replaceChildNode(
REPLACE_IF_IS(mInit, TIntermNode, original, replacement);
REPLACE_IF_IS(mCond, TIntermTyped, original, replacement);
REPLACE_IF_IS(mExpr, TIntermTyped, original, replacement);
- REPLACE_IF_IS(mBody, TIntermBlock, original, replacement);
+ REPLACE_IF_IS(mBody, TIntermAggregate, original, replacement);
return false;
}
@@ -184,13 +179,6 @@ bool TIntermBranch::replaceChildNode(
return false;
}
-bool TIntermSwizzle::replaceChildNode(TIntermNode *original, TIntermNode *replacement)
-{
- ASSERT(original->getAsTyped()->getType() == replacement->getAsTyped()->getType());
- REPLACE_IF_IS(mOperand, TIntermTyped, original, replacement);
- return false;
-}
-
bool TIntermBinary::replaceChildNode(
TIntermNode *original, TIntermNode *replacement)
{
@@ -202,67 +190,42 @@ bool TIntermBinary::replaceChildNode(
bool TIntermUnary::replaceChildNode(
TIntermNode *original, TIntermNode *replacement)
{
- ASSERT(original->getAsTyped()->getType() == replacement->getAsTyped()->getType());
REPLACE_IF_IS(mOperand, TIntermTyped, original, replacement);
return false;
}
-bool TIntermFunctionDefinition::replaceChildNode(TIntermNode *original, TIntermNode *replacement)
-{
- REPLACE_IF_IS(mParameters, TIntermAggregate, original, replacement);
- REPLACE_IF_IS(mBody, TIntermBlock, original, replacement);
- return false;
-}
-
bool TIntermAggregate::replaceChildNode(
TIntermNode *original, TIntermNode *replacement)
{
- return replaceChildNodeInternal(original, replacement);
-}
-
-bool TIntermBlock::replaceChildNode(TIntermNode *original, TIntermNode *replacement)
-{
- return replaceChildNodeInternal(original, replacement);
-}
-
-bool TIntermDeclaration::replaceChildNode(TIntermNode *original, TIntermNode *replacement)
-{
- return replaceChildNodeInternal(original, replacement);
-}
-
-bool TIntermAggregateBase::replaceChildNodeInternal(TIntermNode *original, TIntermNode *replacement)
-{
- for (size_t ii = 0; ii < getSequence()->size(); ++ii)
+ for (size_t ii = 0; ii < mSequence.size(); ++ii)
{
- REPLACE_IF_IS((*getSequence())[ii], TIntermNode, original, replacement);
+ REPLACE_IF_IS(mSequence[ii], TIntermNode, original, replacement);
}
return false;
}
-bool TIntermAggregateBase::replaceChildNodeWithMultiple(TIntermNode *original,
- const TIntermSequence &replacements)
+bool TIntermAggregate::replaceChildNodeWithMultiple(TIntermNode *original, TIntermSequence replacements)
{
- for (auto it = getSequence()->begin(); it < getSequence()->end(); ++it)
+ for (auto it = mSequence.begin(); it < mSequence.end(); ++it)
{
if (*it == original)
{
- it = getSequence()->erase(it);
- getSequence()->insert(it, replacements.begin(), replacements.end());
+ it = mSequence.erase(it);
+ mSequence.insert(it, replacements.begin(), replacements.end());
return true;
}
}
return false;
}
-bool TIntermAggregateBase::insertChildNodes(TIntermSequence::size_type position,
- const TIntermSequence &insertions)
+bool TIntermAggregate::insertChildNodes(TIntermSequence::size_type position, TIntermSequence insertions)
{
- if (position > getSequence()->size())
+ if (position > mSequence.size())
{
return false;
}
- auto it = getSequence()->begin() + position;
- getSequence()->insert(it, insertions.begin(), insertions.end());
+ auto it = mSequence.begin() + position;
+ mSequence.insert(it, insertions.begin(), insertions.end());
return true;
}
@@ -320,47 +283,18 @@ void TIntermAggregate::setBuiltInFunctionPrecision()
}
// ESSL 3.0 spec section 8: textureSize always gets highp precision.
// All other functions that take a sampler are assumed to be texture functions.
- if (mFunctionInfo.getName().find("textureSize") == 0)
+ if (mName.getString().find("textureSize") == 0)
mType.setPrecision(EbpHigh);
else
mType.setPrecision(precision);
}
-void TIntermBlock::appendStatement(TIntermNode *statement)
-{
- // Declaration nodes with no children can appear if all the declarators just added constants to
- // the symbol table instead of generating code. They're no-ops so they aren't added to blocks.
- if (statement != nullptr && (statement->getAsDeclarationNode() == nullptr ||
- !statement->getAsDeclarationNode()->getSequence()->empty()))
- {
- mStatements.push_back(statement);
- }
-}
-
-void TIntermDeclaration::appendDeclarator(TIntermTyped *declarator)
-{
- ASSERT(declarator != nullptr);
- ASSERT(declarator->getAsSymbolNode() != nullptr ||
- (declarator->getAsBinaryNode() != nullptr &&
- declarator->getAsBinaryNode()->getOp() == EOpInitialize));
- ASSERT(mDeclarators.empty() ||
- declarator->getType().sameElementType(mDeclarators.back()->getAsTyped()->getType()));
- mDeclarators.push_back(declarator);
-}
-
-bool TIntermTernary::replaceChildNode(TIntermNode *original, TIntermNode *replacement)
-{
- REPLACE_IF_IS(mCondition, TIntermTyped, original, replacement);
- REPLACE_IF_IS(mTrueExpression, TIntermTyped, original, replacement);
- REPLACE_IF_IS(mFalseExpression, TIntermTyped, original, replacement);
- return false;
-}
-
-bool TIntermIfElse::replaceChildNode(TIntermNode *original, TIntermNode *replacement)
+bool TIntermSelection::replaceChildNode(
+ TIntermNode *original, TIntermNode *replacement)
{
REPLACE_IF_IS(mCondition, TIntermTyped, original, replacement);
- REPLACE_IF_IS(mTrueBlock, TIntermBlock, original, replacement);
- REPLACE_IF_IS(mFalseBlock, TIntermBlock, original, replacement);
+ REPLACE_IF_IS(mTrueBlock, TIntermNode, original, replacement);
+ REPLACE_IF_IS(mFalseBlock, TIntermNode, original, replacement);
return false;
}
@@ -368,7 +302,7 @@ bool TIntermSwitch::replaceChildNode(
TIntermNode *original, TIntermNode *replacement)
{
REPLACE_IF_IS(mInit, TIntermTyped, original, replacement);
- REPLACE_IF_IS(mStatementList, TIntermBlock, original, replacement);
+ REPLACE_IF_IS(mStatementList, TIntermAggregate, original, replacement);
return false;
}
@@ -402,100 +336,18 @@ bool TIntermTyped::isConstructorWithOnlyConstantUnionParameters()
return true;
}
-// static
-TIntermTyped *TIntermTyped::CreateIndexNode(int index)
-{
- TConstantUnion *u = new TConstantUnion[1];
- u[0].setIConst(index);
-
- TType type(EbtInt, EbpUndefined, EvqConst, 1);
- TIntermConstantUnion *node = new TIntermConstantUnion(u, type);
- return node;
-}
-
-// static
-TIntermTyped *TIntermTyped::CreateZero(const TType &type)
-{
- TType constType(type);
- constType.setQualifier(EvqConst);
-
- if (!type.isArray() && type.getBasicType() != EbtStruct)
- {
- ASSERT(type.isScalar() || type.isVector() || type.isMatrix());
-
- size_t size = constType.getObjectSize();
- TConstantUnion *u = new TConstantUnion[size];
- for (size_t i = 0; i < size; ++i)
- {
- switch (type.getBasicType())
- {
- case EbtFloat:
- u[i].setFConst(0.0f);
- break;
- case EbtInt:
- u[i].setIConst(0);
- break;
- case EbtUInt:
- u[i].setUConst(0u);
- break;
- case EbtBool:
- u[i].setBConst(false);
- break;
- default:
- UNREACHABLE();
- return nullptr;
- }
- }
-
- TIntermConstantUnion *node = new TIntermConstantUnion(u, constType);
- return node;
- }
-
- TIntermAggregate *constructor = new TIntermAggregate(sh::TypeToConstructorOperator(type));
- constructor->setType(constType);
-
- if (type.isArray())
- {
- TType elementType(type);
- elementType.clearArrayness();
-
- size_t arraySize = type.getArraySize();
- for (size_t i = 0; i < arraySize; ++i)
- {
- constructor->getSequence()->push_back(CreateZero(elementType));
- }
- }
- else
- {
- ASSERT(type.getBasicType() == EbtStruct);
-
- TStructure *structure = type.getStruct();
- for (const auto &field : structure->fields())
- {
- constructor->getSequence()->push_back(CreateZero(*field->type()));
- }
- }
-
- return constructor;
-}
-
TIntermConstantUnion::TIntermConstantUnion(const TIntermConstantUnion &node) : TIntermTyped(node)
{
mUnionArrayPointer = node.mUnionArrayPointer;
}
-void TFunctionSymbolInfo::setFromFunction(const TFunction &function)
-{
- setName(function.getMangledName());
- setId(function.getUniqueId());
-}
-
TIntermAggregate::TIntermAggregate(const TIntermAggregate &node)
: TIntermOperator(node),
+ mName(node.mName),
mUserDefined(node.mUserDefined),
+ mFunctionId(node.mFunctionId),
mUseEmulatedFunction(node.mUseEmulatedFunction),
- mGotPrecisionFromChildren(node.mGotPrecisionFromChildren),
- mFunctionInfo(node.mFunctionInfo)
+ mGotPrecisionFromChildren(node.mGotPrecisionFromChildren)
{
for (TIntermNode *child : node.mSequence)
{
@@ -506,13 +358,6 @@ TIntermAggregate::TIntermAggregate(const TIntermAggregate &node)
}
}
-TIntermSwizzle::TIntermSwizzle(const TIntermSwizzle &node) : TIntermTyped(node)
-{
- TIntermTyped *operandCopy = node.mOperand->deepCopy();
- ASSERT(operandCopy != nullptr);
- mOperand = operandCopy;
-}
-
TIntermBinary::TIntermBinary(const TIntermBinary &node)
: TIntermOperator(node), mAddIndexClamp(node.mAddIndexClamp)
{
@@ -531,15 +376,20 @@ TIntermUnary::TIntermUnary(const TIntermUnary &node)
mOperand = operandCopy;
}
-TIntermTernary::TIntermTernary(const TIntermTernary &node) : TIntermTyped(node)
+TIntermSelection::TIntermSelection(const TIntermSelection &node) : TIntermTyped(node)
{
+ // Only supported for ternary nodes, not if statements.
+ TIntermTyped *trueTyped = node.mTrueBlock->getAsTyped();
+ TIntermTyped *falseTyped = node.mFalseBlock->getAsTyped();
+ ASSERT(trueTyped != nullptr);
+ ASSERT(falseTyped != nullptr);
TIntermTyped *conditionCopy = node.mCondition->deepCopy();
- TIntermTyped *trueCopy = node.mTrueExpression->deepCopy();
- TIntermTyped *falseCopy = node.mFalseExpression->deepCopy();
+ TIntermTyped *trueCopy = trueTyped->deepCopy();
+ TIntermTyped *falseCopy = falseTyped->deepCopy();
ASSERT(conditionCopy != nullptr && trueCopy != nullptr && falseCopy != nullptr);
- mCondition = conditionCopy;
- mTrueExpression = trueCopy;
- mFalseExpression = falseCopy;
+ mCondition = conditionCopy;
+ mTrueBlock = trueCopy;
+ mFalseBlock = falseCopy;
}
bool TIntermOperator::isAssignment() const
@@ -694,187 +544,77 @@ TOperator TIntermBinary::GetMulAssignOpBasedOnOperands(const TType &left, const
// Make sure the type of a unary operator is appropriate for its
// combination of operation and operand type.
//
-void TIntermUnary::promote()
+void TIntermUnary::promote(const TType *funcReturnType)
{
- TQualifier resultQualifier = EvqTemporary;
- if (mOperand->getQualifier() == EvqConst)
- resultQualifier = EvqConst;
-
- unsigned char operandPrimarySize =
- static_cast<unsigned char>(mOperand->getType().getNominalSize());
switch (mOp)
{
- case EOpFloatBitsToInt:
- setType(TType(EbtInt, EbpHigh, resultQualifier, operandPrimarySize));
- break;
- case EOpFloatBitsToUint:
- setType(TType(EbtUInt, EbpHigh, resultQualifier, operandPrimarySize));
- break;
- case EOpIntBitsToFloat:
- case EOpUintBitsToFloat:
- setType(TType(EbtFloat, EbpHigh, resultQualifier, operandPrimarySize));
- break;
- case EOpPackSnorm2x16:
- case EOpPackUnorm2x16:
- case EOpPackHalf2x16:
- setType(TType(EbtUInt, EbpHigh, resultQualifier));
- break;
- case EOpUnpackSnorm2x16:
- case EOpUnpackUnorm2x16:
- setType(TType(EbtFloat, EbpHigh, resultQualifier, 2));
- break;
- case EOpUnpackHalf2x16:
- setType(TType(EbtFloat, EbpMedium, resultQualifier, 2));
- break;
- case EOpAny:
- case EOpAll:
- setType(TType(EbtBool, EbpUndefined, resultQualifier));
- break;
- case EOpLength:
- case EOpDeterminant:
- setType(TType(EbtFloat, mOperand->getType().getPrecision(), resultQualifier));
- break;
- case EOpTranspose:
- setType(TType(EbtFloat, mOperand->getType().getPrecision(), resultQualifier,
- static_cast<unsigned char>(mOperand->getType().getRows()),
- static_cast<unsigned char>(mOperand->getType().getCols())));
- break;
- case EOpIsInf:
- case EOpIsNan:
- setType(TType(EbtBool, EbpUndefined, resultQualifier, operandPrimarySize));
- break;
- default:
- setType(mOperand->getType());
- mType.setQualifier(resultQualifier);
- break;
- }
-}
-
-TIntermSwizzle::TIntermSwizzle(TIntermTyped *operand, const TVector<int> &swizzleOffsets)
- : TIntermTyped(TType(EbtFloat, EbpUndefined)),
- mOperand(operand),
- mSwizzleOffsets(swizzleOffsets)
-{
- ASSERT(mSwizzleOffsets.size() <= 4);
- promote();
-}
-
-TIntermUnary::TIntermUnary(TOperator op, TIntermTyped *operand)
- : TIntermOperator(op), mOperand(operand), mUseEmulatedFunction(false)
-{
- promote();
-}
-
-TIntermBinary::TIntermBinary(TOperator op, TIntermTyped *left, TIntermTyped *right)
- : TIntermOperator(op), mLeft(left), mRight(right), mAddIndexClamp(false)
-{
- promote();
-}
-
-TIntermTernary::TIntermTernary(TIntermTyped *cond,
- TIntermTyped *trueExpression,
- TIntermTyped *falseExpression)
- : TIntermTyped(trueExpression->getType()),
- mCondition(cond),
- mTrueExpression(trueExpression),
- mFalseExpression(falseExpression)
-{
- getTypePointer()->setQualifier(
- TIntermTernary::DetermineQualifier(cond, trueExpression, falseExpression));
-}
-
-// static
-TQualifier TIntermTernary::DetermineQualifier(TIntermTyped *cond,
- TIntermTyped *trueExpression,
- TIntermTyped *falseExpression)
-{
- if (cond->getQualifier() == EvqConst && trueExpression->getQualifier() == EvqConst &&
- falseExpression->getQualifier() == EvqConst)
- {
- return EvqConst;
+ case EOpFloatBitsToInt:
+ case EOpFloatBitsToUint:
+ case EOpIntBitsToFloat:
+ case EOpUintBitsToFloat:
+ case EOpPackSnorm2x16:
+ case EOpPackUnorm2x16:
+ case EOpPackHalf2x16:
+ case EOpUnpackSnorm2x16:
+ case EOpUnpackUnorm2x16:
+ mType.setPrecision(EbpHigh);
+ break;
+ case EOpUnpackHalf2x16:
+ mType.setPrecision(EbpMedium);
+ break;
+ default:
+ setType(mOperand->getType());
}
- return EvqTemporary;
-}
-void TIntermSwizzle::promote()
-{
- TQualifier resultQualifier = EvqTemporary;
- if (mOperand->getQualifier() == EvqConst)
- resultQualifier = EvqConst;
-
- auto numFields = mSwizzleOffsets.size();
- setType(TType(mOperand->getBasicType(), mOperand->getPrecision(), resultQualifier,
- static_cast<unsigned char>(numFields)));
-}
-
-bool TIntermSwizzle::hasDuplicateOffsets() const
-{
- int offsetCount[4] = {0u, 0u, 0u, 0u};
- for (const auto offset : mSwizzleOffsets)
+ if (funcReturnType != nullptr)
{
- offsetCount[offset]++;
- if (offsetCount[offset] > 1)
+ if (funcReturnType->getBasicType() == EbtBool)
{
- return true;
+ // Bool types should not have precision.
+ setType(*funcReturnType);
}
- }
- return false;
-}
-
-void TIntermSwizzle::writeOffsetsAsXYZW(TInfoSinkBase *out) const
-{
- for (const int offset : mSwizzleOffsets)
- {
- switch (offset)
+ else
{
- case 0:
- *out << "x";
- break;
- case 1:
- *out << "y";
- break;
- case 2:
- *out << "z";
- break;
- case 3:
- *out << "w";
- break;
- default:
- UNREACHABLE();
+ // Precision of the node has been set based on the operand.
+ setTypePreservePrecision(*funcReturnType);
}
}
+
+ if (mOperand->getQualifier() == EvqConst)
+ mType.setQualifier(EvqConst);
+ else
+ mType.setQualifier(EvqTemporary);
}
-TQualifier TIntermBinary::GetCommaQualifier(int shaderVersion,
- const TIntermTyped *left,
- const TIntermTyped *right)
+TIntermBinary::TIntermBinary(TOperator op, TIntermTyped *left, TIntermTyped *right)
+ : TIntermOperator(op), mLeft(left), mRight(right), mAddIndexClamp(false)
{
- // ESSL3.00 section 12.43: The result of a sequence operator is not a constant-expression.
- if (shaderVersion >= 300 || left->getQualifier() != EvqConst ||
- right->getQualifier() != EvqConst)
- {
- return EvqTemporary;
- }
- return EvqConst;
+ promote();
}
-// Establishes the type of the result of the binary operation.
+//
+// Establishes the type of the resultant operation, as well as
+// makes the operator the correct one for the operands.
+//
+// For lots of operations it should already be established that the operand
+// combination is valid, but returns false if operator can't work on operands.
+//
void TIntermBinary::promote()
{
+ ASSERT(mLeft->isArray() == mRight->isArray());
+
ASSERT(!isMultiplication() ||
mOp == GetMulOpBasedOnOperands(mLeft->getType(), mRight->getType()));
- // Comma is handled as a special case.
- if (mOp == EOpComma)
- {
- setType(mRight->getType());
- return;
- }
-
// Base assumption: just make the type the same as the left
// operand. Then only deviations from this need be coded.
setType(mLeft->getType());
+ // The result gets promoted to the highest precision.
+ TPrecision higherPrecision = GetHigherPrecision(
+ mLeft->getPrecision(), mRight->getPrecision());
+ getTypePointer()->setPrecision(higherPrecision);
+
TQualifier resultQualifier = EvqConst;
// Binary operations results in temporary variables unless both
// operands are const.
@@ -884,55 +624,6 @@ void TIntermBinary::promote()
getTypePointer()->setQualifier(EvqTemporary);
}
- // Handle indexing ops.
- switch (mOp)
- {
- case EOpIndexDirect:
- case EOpIndexIndirect:
- if (mLeft->isArray())
- {
- mType.clearArrayness();
- }
- else if (mLeft->isMatrix())
- {
- setType(TType(mLeft->getBasicType(), mLeft->getPrecision(), resultQualifier,
- static_cast<unsigned char>(mLeft->getRows())));
- }
- else if (mLeft->isVector())
- {
- setType(TType(mLeft->getBasicType(), mLeft->getPrecision(), resultQualifier));
- }
- else
- {
- UNREACHABLE();
- }
- return;
- case EOpIndexDirectStruct:
- {
- const TFieldList &fields = mLeft->getType().getStruct()->fields();
- const int i = mRight->getAsConstantUnion()->getIConst(0);
- setType(*fields[i]->type());
- getTypePointer()->setQualifier(resultQualifier);
- return;
- }
- case EOpIndexDirectInterfaceBlock:
- {
- const TFieldList &fields = mLeft->getType().getInterfaceBlock()->fields();
- const int i = mRight->getAsConstantUnion()->getIConst(0);
- setType(*fields[i]->type());
- getTypePointer()->setQualifier(resultQualifier);
- return;
- }
- default:
- break;
- }
-
- ASSERT(mLeft->isArray() == mRight->isArray());
-
- // The result gets promoted to the highest precision.
- TPrecision higherPrecision = GetHigherPrecision(mLeft->getPrecision(), mRight->getPrecision());
- getTypePointer()->setPrecision(higherPrecision);
-
const int nominalSize =
std::max(mLeft->getNominalSize(), mRight->getNominalSize());
@@ -952,8 +643,8 @@ void TIntermBinary::promote()
case EOpGreaterThan:
case EOpLessThanEqual:
case EOpGreaterThanEqual:
- setType(TType(EbtBool, EbpUndefined, resultQualifier));
- break;
+ setType(TType(EbtBool, EbpUndefined));
+ break;
//
// And and Or operate on conditionals
@@ -962,7 +653,7 @@ void TIntermBinary::promote()
case EOpLogicalXor:
case EOpLogicalOr:
ASSERT(mLeft->getBasicType() == EbtBool && mRight->getBasicType() == EbtBool);
- setType(TType(EbtBool, EbpUndefined, resultQualifier));
+ setType(TType(EbtBool, EbpUndefined));
break;
default:
@@ -1058,7 +749,8 @@ void TIntermBinary::promote()
case EOpIndexIndirect:
case EOpIndexDirectInterfaceBlock:
case EOpIndexDirectStruct:
- // These ops should be already fully handled.
+ // TODO (oetuaho): These ops could be handled here as well (should be done closer to the
+ // top of the function).
UNREACHABLE();
break;
default:
@@ -1067,105 +759,26 @@ void TIntermBinary::promote()
}
}
-const TConstantUnion *TIntermConstantUnion::foldIndexing(int index)
-{
- if (isArray())
- {
- ASSERT(index < static_cast<int>(getType().getArraySize()));
- TType arrayElementType = getType();
- arrayElementType.clearArrayness();
- size_t arrayElementSize = arrayElementType.getObjectSize();
- return &mUnionArrayPointer[arrayElementSize * index];
- }
- else if (isMatrix())
- {
- ASSERT(index < getType().getCols());
- int size = getType().getRows();
- return &mUnionArrayPointer[size * index];
- }
- else if (isVector())
- {
- ASSERT(index < getType().getNominalSize());
- return &mUnionArrayPointer[index];
- }
- else
- {
- UNREACHABLE();
- return nullptr;
- }
-}
-
-TIntermTyped *TIntermSwizzle::fold()
+TIntermTyped *TIntermBinary::fold(TDiagnostics *diagnostics)
{
- TIntermConstantUnion *operandConstant = mOperand->getAsConstantUnion();
- if (operandConstant == nullptr)
+ TIntermConstantUnion *leftConstant = mLeft->getAsConstantUnion();
+ TIntermConstantUnion *rightConstant = mRight->getAsConstantUnion();
+ if (leftConstant == nullptr || rightConstant == nullptr)
{
return nullptr;
}
+ TConstantUnion *constArray = leftConstant->foldBinary(mOp, rightConstant, diagnostics);
- TConstantUnion *constArray = new TConstantUnion[mSwizzleOffsets.size()];
- for (size_t i = 0; i < mSwizzleOffsets.size(); ++i)
- {
- constArray[i] = *operandConstant->foldIndexing(mSwizzleOffsets.at(i));
- }
- return CreateFoldedNode(constArray, this, mType.getQualifier());
-}
-
-TIntermTyped *TIntermBinary::fold(TDiagnostics *diagnostics)
-{
- TIntermConstantUnion *leftConstant = mLeft->getAsConstantUnion();
- TIntermConstantUnion *rightConstant = mRight->getAsConstantUnion();
- switch (mOp)
+ // Nodes may be constant folded without being qualified as constant.
+ TQualifier resultQualifier = EvqConst;
+ if (mLeft->getQualifier() != EvqConst || mRight->getQualifier() != EvqConst)
{
- case EOpIndexDirect:
- {
- if (leftConstant == nullptr || rightConstant == nullptr)
- {
- return nullptr;
- }
- int index = rightConstant->getIConst(0);
-
- const TConstantUnion *constArray = leftConstant->foldIndexing(index);
- return CreateFoldedNode(constArray, this, mType.getQualifier());
- }
- case EOpIndexDirectStruct:
- {
- if (leftConstant == nullptr || rightConstant == nullptr)
- {
- return nullptr;
- }
- const TFieldList &fields = mLeft->getType().getStruct()->fields();
- size_t index = static_cast<size_t>(rightConstant->getIConst(0));
-
- size_t previousFieldsSize = 0;
- for (size_t i = 0; i < index; ++i)
- {
- previousFieldsSize += fields[i]->type()->getObjectSize();
- }
-
- const TConstantUnion *constArray = leftConstant->getUnionArrayPointer();
- return CreateFoldedNode(constArray + previousFieldsSize, this, mType.getQualifier());
- }
- case EOpIndexIndirect:
- case EOpIndexDirectInterfaceBlock:
- // Can never be constant folded.
- return nullptr;
- default:
- {
- if (leftConstant == nullptr || rightConstant == nullptr)
- {
- return nullptr;
- }
- TConstantUnion *constArray =
- leftConstant->foldBinary(mOp, rightConstant, diagnostics, mLeft->getLine());
-
- // Nodes may be constant folded without being qualified as constant.
- return CreateFoldedNode(constArray, this, mType.getQualifier());
- }
+ resultQualifier = EvqTemporary;
}
+ return CreateFoldedNode(constArray, this, resultQualifier);
}
-TIntermTyped *TIntermUnary::fold(TDiagnostics *diagnostics)
+TIntermTyped *TIntermUnary::fold(TInfoSink &infoSink)
{
TIntermConstantUnion *operandConstant = mOperand->getAsConstantUnion();
if (operandConstant == nullptr)
@@ -1188,18 +801,19 @@ TIntermTyped *TIntermUnary::fold(TDiagnostics *diagnostics)
case EOpUnpackUnorm2x16:
case EOpPackHalf2x16:
case EOpUnpackHalf2x16:
- constArray = operandConstant->foldUnaryNonComponentWise(mOp);
- break;
+ constArray = operandConstant->foldUnaryWithDifferentReturnType(mOp, infoSink);
+ break;
default:
- constArray = operandConstant->foldUnaryComponentWise(mOp, diagnostics);
- break;
+ constArray = operandConstant->foldUnaryWithSameReturnType(mOp, infoSink);
+ break;
}
// Nodes may be constant folded without being qualified as constant.
- return CreateFoldedNode(constArray, this, mType.getQualifier());
+ TQualifier resultQualifier = mOperand->getQualifier() == EvqConst ? EvqConst : EvqTemporary;
+ return CreateFoldedNode(constArray, this, resultQualifier);
}
-TIntermTyped *TIntermAggregate::fold(TDiagnostics *diagnostics)
+TIntermTyped *TIntermAggregate::fold(TInfoSink &infoSink)
{
// Make sure that all params are constant before actual constant folding.
for (auto *param : *getSequence())
@@ -1211,9 +825,9 @@ TIntermTyped *TIntermAggregate::fold(TDiagnostics *diagnostics)
}
TConstantUnion *constArray = nullptr;
if (isConstructor())
- constArray = TIntermConstantUnion::FoldAggregateConstructor(this);
+ constArray = TIntermConstantUnion::FoldAggregateConstructor(this, infoSink);
else
- constArray = TIntermConstantUnion::FoldAggregateBuiltIn(this, diagnostics);
+ constArray = TIntermConstantUnion::FoldAggregateBuiltIn(this, infoSink);
// Nodes may be constant folded without being qualified as constant.
TQualifier resultQualifier = areChildrenConstQualified() ? EvqConst : EvqTemporary;
@@ -1228,13 +842,15 @@ TIntermTyped *TIntermAggregate::fold(TDiagnostics *diagnostics)
//
TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
TIntermConstantUnion *rightNode,
- TDiagnostics *diagnostics,
- const TSourceLoc &line)
+ TDiagnostics *diagnostics)
{
const TConstantUnion *leftArray = getUnionArrayPointer();
const TConstantUnion *rightArray = rightNode->getUnionArrayPointer();
- ASSERT(leftArray && rightArray);
+ if (!leftArray)
+ return nullptr;
+ if (!rightArray)
+ return nullptr;
size_t objectSize = getType().getObjectSize();
@@ -1257,12 +873,12 @@ TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
case EOpAdd:
resultArray = new TConstantUnion[objectSize];
for (size_t i = 0; i < objectSize; i++)
- resultArray[i] = TConstantUnion::add(leftArray[i], rightArray[i], diagnostics, line);
+ resultArray[i] = leftArray[i] + rightArray[i];
break;
case EOpSub:
resultArray = new TConstantUnion[objectSize];
for (size_t i = 0; i < objectSize; i++)
- resultArray[i] = TConstantUnion::sub(leftArray[i], rightArray[i], diagnostics, line);
+ resultArray[i] = leftArray[i] - rightArray[i];
break;
case EOpMul:
@@ -1270,12 +886,11 @@ TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
case EOpMatrixTimesScalar:
resultArray = new TConstantUnion[objectSize];
for (size_t i = 0; i < objectSize; i++)
- resultArray[i] = TConstantUnion::mul(leftArray[i], rightArray[i], diagnostics, line);
+ resultArray[i] = leftArray[i] * rightArray[i];
break;
case EOpMatrixTimesMatrix:
{
- // TODO(jmadll): This code should check for overflows.
ASSERT(getType().getBasicType() == EbtFloat && rightNode->getBasicType() == EbtFloat);
const int leftCols = getCols();
@@ -1334,42 +949,14 @@ TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
}
else
{
- int lhs = leftArray[i].getIConst();
- int divisor = rightArray[i].getIConst();
if (op == EOpDiv)
{
- // Check for the special case where the minimum representable number is
- // divided by -1. If left alone this leads to integer overflow in C++.
- // ESSL 3.00.6 section 4.1.3 Integers:
- // "However, for the case where the minimum representable value is
- // divided by -1, it is allowed to return either the minimum
- // representable value or the maximum representable value."
- if (lhs == -0x7fffffff - 1 && divisor == -1)
- {
- resultArray[i].setIConst(0x7fffffff);
- }
- else
- {
- resultArray[i].setIConst(lhs / divisor);
- }
+ resultArray[i].setIConst(leftArray[i].getIConst() / rightArray[i].getIConst());
}
else
{
ASSERT(op == EOpIMod);
- if (lhs < 0 || divisor < 0)
- {
- // ESSL 3.00.6 section 5.9: Results of modulus are undefined when
- // either one of the operands is negative.
- diagnostics->warning(getLine(),
- "Negative modulus operator operand "
- "encountered during constant folding",
- "%", "");
- resultArray[i].setIConst(0);
- }
- else
- {
- resultArray[i].setIConst(lhs % divisor);
- }
+ resultArray[i].setIConst(leftArray[i].getIConst() % rightArray[i].getIConst());
}
}
break;
@@ -1405,7 +992,6 @@ TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
case EOpMatrixTimesVector:
{
- // TODO(jmadll): This code should check for overflows.
ASSERT(rightNode->getBasicType() == EbtFloat);
const int matrixCols = getCols();
@@ -1428,7 +1014,6 @@ TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
case EOpVectorTimesMatrix:
{
- // TODO(jmadll): This code should check for overflows.
ASSERT(getType().getBasicType() == EbtFloat);
const int matrixCols = rightNode->getType().getCols();
@@ -1498,12 +1083,12 @@ TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
case EOpBitShiftLeft:
resultArray = new TConstantUnion[objectSize];
for (size_t i = 0; i < objectSize; i++)
- resultArray[i] = TConstantUnion::lshift(leftArray[i], rightArray[i], diagnostics, line);
+ resultArray[i] = leftArray[i] << rightArray[i];
break;
case EOpBitShiftRight:
resultArray = new TConstantUnion[objectSize];
for (size_t i = 0; i < objectSize; i++)
- resultArray[i] = TConstantUnion::rshift(leftArray[i], rightArray[i], diagnostics, line);
+ resultArray[i] = leftArray[i] >> rightArray[i];
break;
case EOpLessThan:
@@ -1561,22 +1146,29 @@ TConstantUnion *TIntermConstantUnion::foldBinary(TOperator op,
return resultArray;
}
-// The fold functions do operations on a constant at GLSL compile time, without generating run-time
-// code. Returns the constant value to keep using. Nullptr should not be returned.
-TConstantUnion *TIntermConstantUnion::foldUnaryNonComponentWise(TOperator op)
+//
+// The fold functions see if an operation on a constant can be done in place,
+// without generating run-time code.
+//
+// Returns the constant value to keep using or nullptr.
+//
+TConstantUnion *TIntermConstantUnion::foldUnaryWithDifferentReturnType(TOperator op, TInfoSink &infoSink)
{
- // Do operations where the return type may have a different number of components compared to the
- // operand type.
+ //
+ // Do operations where the return type has a different number of components compared to the operand type.
+ //
const TConstantUnion *operandArray = getUnionArrayPointer();
- ASSERT(operandArray);
+ if (!operandArray)
+ return nullptr;
size_t objectSize = getType().getObjectSize();
TConstantUnion *resultArray = nullptr;
switch (op)
{
- case EOpAny:
- ASSERT(getType().getBasicType() == EbtBool);
+ case EOpAny:
+ if (getType().getBasicType() == EbtBool)
+ {
resultArray = new TConstantUnion();
resultArray->setBConst(false);
for (size_t i = 0; i < objectSize; i++)
@@ -1588,9 +1180,16 @@ TConstantUnion *TIntermConstantUnion::foldUnaryNonComponentWise(TOperator op)
}
}
break;
+ }
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpAll:
- ASSERT(getType().getBasicType() == EbtBool);
+ case EOpAll:
+ if (getType().getBasicType() == EbtBool)
+ {
resultArray = new TConstantUnion();
resultArray->setBConst(true);
for (size_t i = 0; i < objectSize; i++)
@@ -1602,55 +1201,89 @@ TConstantUnion *TIntermConstantUnion::foldUnaryNonComponentWise(TOperator op)
}
}
break;
+ }
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpLength:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpLength:
+ if (getType().getBasicType() == EbtFloat)
+ {
resultArray = new TConstantUnion();
resultArray->setFConst(VectorLength(operandArray, objectSize));
break;
+ }
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpTranspose:
+ case EOpTranspose:
+ if (getType().getBasicType() == EbtFloat)
{
- ASSERT(getType().getBasicType() == EbtFloat);
resultArray = new TConstantUnion[objectSize];
angle::Matrix<float> result =
GetMatrix(operandArray, getType().getRows(), getType().getCols()).transpose();
SetUnionArrayFromMatrix(result, resultArray);
break;
}
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpDeterminant:
+ case EOpDeterminant:
+ if (getType().getBasicType() == EbtFloat)
{
- ASSERT(getType().getBasicType() == EbtFloat);
unsigned int size = getType().getNominalSize();
ASSERT(size >= 2 && size <= 4);
resultArray = new TConstantUnion();
resultArray->setFConst(GetMatrix(operandArray, size).determinant());
break;
}
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpInverse:
+ case EOpInverse:
+ if (getType().getBasicType() == EbtFloat)
{
- ASSERT(getType().getBasicType() == EbtFloat);
unsigned int size = getType().getNominalSize();
ASSERT(size >= 2 && size <= 4);
- resultArray = new TConstantUnion[objectSize];
+ resultArray = new TConstantUnion[objectSize];
angle::Matrix<float> result = GetMatrix(operandArray, size).inverse();
SetUnionArrayFromMatrix(result, resultArray);
break;
}
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpPackSnorm2x16:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpPackSnorm2x16:
+ if (getType().getBasicType() == EbtFloat)
+ {
ASSERT(getType().getNominalSize() == 2);
resultArray = new TConstantUnion();
- resultArray->setUConst(
- gl::packSnorm2x16(operandArray[0].getFConst(), operandArray[1].getFConst()));
+ resultArray->setUConst(gl::packSnorm2x16(operandArray[0].getFConst(), operandArray[1].getFConst()));
break;
+ }
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpUnpackSnorm2x16:
+ case EOpUnpackSnorm2x16:
+ if (getType().getBasicType() == EbtUInt)
{
- ASSERT(getType().getBasicType() == EbtUInt);
resultArray = new TConstantUnion[2];
float f1, f2;
gl::unpackSnorm2x16(operandArray[0].getUConst(), &f1, &f2);
@@ -1658,18 +1291,29 @@ TConstantUnion *TIntermConstantUnion::foldUnaryNonComponentWise(TOperator op)
resultArray[1].setFConst(f2);
break;
}
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpPackUnorm2x16:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpPackUnorm2x16:
+ if (getType().getBasicType() == EbtFloat)
+ {
ASSERT(getType().getNominalSize() == 2);
resultArray = new TConstantUnion();
- resultArray->setUConst(
- gl::packUnorm2x16(operandArray[0].getFConst(), operandArray[1].getFConst()));
+ resultArray->setUConst(gl::packUnorm2x16(operandArray[0].getFConst(), operandArray[1].getFConst()));
break;
+ }
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpUnpackUnorm2x16:
+ case EOpUnpackUnorm2x16:
+ if (getType().getBasicType() == EbtUInt)
{
- ASSERT(getType().getBasicType() == EbtUInt);
resultArray = new TConstantUnion[2];
float f1, f2;
gl::unpackUnorm2x16(operandArray[0].getUConst(), &f1, &f2);
@@ -1677,18 +1321,29 @@ TConstantUnion *TIntermConstantUnion::foldUnaryNonComponentWise(TOperator op)
resultArray[1].setFConst(f2);
break;
}
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpPackHalf2x16:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpPackHalf2x16:
+ if (getType().getBasicType() == EbtFloat)
+ {
ASSERT(getType().getNominalSize() == 2);
resultArray = new TConstantUnion();
- resultArray->setUConst(
- gl::packHalf2x16(operandArray[0].getFConst(), operandArray[1].getFConst()));
+ resultArray->setUConst(gl::packHalf2x16(operandArray[0].getFConst(), operandArray[1].getFConst()));
break;
+ }
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
- case EOpUnpackHalf2x16:
+ case EOpUnpackHalf2x16:
+ if (getType().getBasicType() == EbtUInt)
{
- ASSERT(getType().getBasicType() == EbtUInt);
resultArray = new TConstantUnion[2];
float f1, f2;
gl::unpackHalf2x16(operandArray[0].getUConst(), &f1, &f2);
@@ -1696,24 +1351,29 @@ TConstantUnion *TIntermConstantUnion::foldUnaryNonComponentWise(TOperator op)
resultArray[1].setFConst(f2);
break;
}
+ else
+ {
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
+ }
+ break;
- default:
- UNREACHABLE();
- break;
+ default:
+ break;
}
return resultArray;
}
-TConstantUnion *TIntermConstantUnion::foldUnaryComponentWise(TOperator op,
- TDiagnostics *diagnostics)
+TConstantUnion *TIntermConstantUnion::foldUnaryWithSameReturnType(TOperator op, TInfoSink &infoSink)
{
- // Do unary operations where each component of the result is computed based on the corresponding
- // component of the operand. Also folds normalize, though the divisor in that case takes all
- // components into account.
+ //
+ // Do unary operations where the return type is the same as operand type.
+ //
const TConstantUnion *operandArray = getUnionArrayPointer();
- ASSERT(operandArray);
+ if (!operandArray)
+ return nullptr;
size_t objectSize = getType().getObjectSize();
@@ -1722,232 +1382,243 @@ TConstantUnion *TIntermConstantUnion::foldUnaryComponentWise(TOperator op,
{
switch(op)
{
- case EOpNegative:
- switch (getType().getBasicType())
- {
- case EbtFloat:
- resultArray[i].setFConst(-operandArray[i].getFConst());
- break;
- case EbtInt:
- if (operandArray[i] == std::numeric_limits<int>::min())
- {
- // The minimum representable integer doesn't have a positive
- // counterpart, rather the negation overflows and in ESSL is supposed to
- // wrap back to the minimum representable integer. Make sure that we
- // don't actually let the negation overflow, which has undefined
- // behavior in C++.
- resultArray[i].setIConst(std::numeric_limits<int>::min());
- }
- else
- {
- resultArray[i].setIConst(-operandArray[i].getIConst());
- }
- break;
- case EbtUInt:
- if (operandArray[i] == 0x80000000u)
- {
- resultArray[i].setUConst(0x80000000u);
- }
- else
- {
- resultArray[i].setUConst(static_cast<unsigned int>(
- -static_cast<int>(operandArray[i].getUConst())));
- }
- break;
- default:
- UNREACHABLE();
- return nullptr;
- }
+ case EOpNegative:
+ switch (getType().getBasicType())
+ {
+ case EbtFloat:
+ resultArray[i].setFConst(-operandArray[i].getFConst());
+ break;
+ case EbtInt:
+ resultArray[i].setIConst(-operandArray[i].getIConst());
break;
+ case EbtUInt:
+ resultArray[i].setUConst(static_cast<unsigned int>(
+ -static_cast<int>(operandArray[i].getUConst())));
+ break;
+ default:
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
+ }
+ break;
- case EOpPositive:
- switch (getType().getBasicType())
- {
- case EbtFloat:
- resultArray[i].setFConst(operandArray[i].getFConst());
- break;
- case EbtInt:
- resultArray[i].setIConst(operandArray[i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setUConst(static_cast<unsigned int>(
- static_cast<int>(operandArray[i].getUConst())));
- break;
- default:
- UNREACHABLE();
- return nullptr;
- }
+ case EOpPositive:
+ switch (getType().getBasicType())
+ {
+ case EbtFloat:
+ resultArray[i].setFConst(operandArray[i].getFConst());
break;
+ case EbtInt:
+ resultArray[i].setIConst(operandArray[i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setUConst(static_cast<unsigned int>(
+ static_cast<int>(operandArray[i].getUConst())));
+ break;
+ default:
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
+ }
+ break;
- case EOpLogicalNot:
- switch (getType().getBasicType())
- {
- case EbtBool:
- resultArray[i].setBConst(!operandArray[i].getBConst());
- break;
- default:
- UNREACHABLE();
- return nullptr;
- }
+ case EOpLogicalNot:
+ // this code is written for possible future use,
+ // will not get executed currently
+ switch (getType().getBasicType())
+ {
+ case EbtBool:
+ resultArray[i].setBConst(!operandArray[i].getBConst());
break;
+ default:
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
+ }
+ break;
- case EOpBitwiseNot:
- switch (getType().getBasicType())
- {
- case EbtInt:
- resultArray[i].setIConst(~operandArray[i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setUConst(~operandArray[i].getUConst());
- break;
- default:
- UNREACHABLE();
- return nullptr;
- }
+ case EOpBitwiseNot:
+ switch (getType().getBasicType())
+ {
+ case EbtInt:
+ resultArray[i].setIConst(~operandArray[i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setUConst(~operandArray[i].getUConst());
break;
+ default:
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
+ }
+ break;
- case EOpRadians:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpRadians:
+ if (getType().getBasicType() == EbtFloat)
+ {
resultArray[i].setFConst(kDegreesToRadiansMultiplier * operandArray[i].getFConst());
break;
+ }
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
- case EOpDegrees:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpDegrees:
+ if (getType().getBasicType() == EbtFloat)
+ {
resultArray[i].setFConst(kRadiansToDegreesMultiplier * operandArray[i].getFConst());
break;
+ }
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
- case EOpSin:
- foldFloatTypeUnary(operandArray[i], &sinf, &resultArray[i]);
- break;
+ case EOpSin:
+ if (!foldFloatTypeUnary(operandArray[i], &sinf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpCos:
- foldFloatTypeUnary(operandArray[i], &cosf, &resultArray[i]);
- break;
+ case EOpCos:
+ if (!foldFloatTypeUnary(operandArray[i], &cosf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpTan:
- foldFloatTypeUnary(operandArray[i], &tanf, &resultArray[i]);
- break;
+ case EOpTan:
+ if (!foldFloatTypeUnary(operandArray[i], &tanf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpAsin:
- // For asin(x), results are undefined if |x| > 1, we are choosing to set result to
- // 0.
- if (fabsf(operandArray[i].getFConst()) > 1.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- foldFloatTypeUnary(operandArray[i], &asinf, &resultArray[i]);
- break;
+ case EOpAsin:
+ // For asin(x), results are undefined if |x| > 1, we are choosing to set result to 0.
+ if (getType().getBasicType() == EbtFloat && fabsf(operandArray[i].getFConst()) > 1.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &asinf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpAcos:
- // For acos(x), results are undefined if |x| > 1, we are choosing to set result to
- // 0.
- if (fabsf(operandArray[i].getFConst()) > 1.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- foldFloatTypeUnary(operandArray[i], &acosf, &resultArray[i]);
- break;
+ case EOpAcos:
+ // For acos(x), results are undefined if |x| > 1, we are choosing to set result to 0.
+ if (getType().getBasicType() == EbtFloat && fabsf(operandArray[i].getFConst()) > 1.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &acosf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpAtan:
- foldFloatTypeUnary(operandArray[i], &atanf, &resultArray[i]);
- break;
+ case EOpAtan:
+ if (!foldFloatTypeUnary(operandArray[i], &atanf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpSinh:
- foldFloatTypeUnary(operandArray[i], &sinhf, &resultArray[i]);
- break;
+ case EOpSinh:
+ if (!foldFloatTypeUnary(operandArray[i], &sinhf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpCosh:
- foldFloatTypeUnary(operandArray[i], &coshf, &resultArray[i]);
- break;
+ case EOpCosh:
+ if (!foldFloatTypeUnary(operandArray[i], &coshf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpTanh:
- foldFloatTypeUnary(operandArray[i], &tanhf, &resultArray[i]);
- break;
+ case EOpTanh:
+ if (!foldFloatTypeUnary(operandArray[i], &tanhf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpAsinh:
- foldFloatTypeUnary(operandArray[i], &asinhf, &resultArray[i]);
- break;
+ case EOpAsinh:
+ if (!foldFloatTypeUnary(operandArray[i], &asinhf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpAcosh:
- // For acosh(x), results are undefined if x < 1, we are choosing to set result to 0.
- if (operandArray[i].getFConst() < 1.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- foldFloatTypeUnary(operandArray[i], &acoshf, &resultArray[i]);
- break;
+ case EOpAcosh:
+ // For acosh(x), results are undefined if x < 1, we are choosing to set result to 0.
+ if (getType().getBasicType() == EbtFloat && operandArray[i].getFConst() < 1.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &acoshf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpAtanh:
- // For atanh(x), results are undefined if |x| >= 1, we are choosing to set result to
- // 0.
- if (fabsf(operandArray[i].getFConst()) >= 1.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- foldFloatTypeUnary(operandArray[i], &atanhf, &resultArray[i]);
+ case EOpAtanh:
+ // For atanh(x), results are undefined if |x| >= 1, we are choosing to set result to 0.
+ if (getType().getBasicType() == EbtFloat && fabsf(operandArray[i].getFConst()) >= 1.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &atanhf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
+
+ case EOpAbs:
+ switch (getType().getBasicType())
+ {
+ case EbtFloat:
+ resultArray[i].setFConst(fabsf(operandArray[i].getFConst()));
+ break;
+ case EbtInt:
+ resultArray[i].setIConst(abs(operandArray[i].getIConst()));
break;
+ default:
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
+ }
+ break;
- case EOpAbs:
- switch (getType().getBasicType())
+ case EOpSign:
+ switch (getType().getBasicType())
+ {
+ case EbtFloat:
{
- case EbtFloat:
- resultArray[i].setFConst(fabsf(operandArray[i].getFConst()));
- break;
- case EbtInt:
- resultArray[i].setIConst(abs(operandArray[i].getIConst()));
- break;
- default:
- UNREACHABLE();
- return nullptr;
+ float fConst = operandArray[i].getFConst();
+ float fResult = 0.0f;
+ if (fConst > 0.0f)
+ fResult = 1.0f;
+ else if (fConst < 0.0f)
+ fResult = -1.0f;
+ resultArray[i].setFConst(fResult);
}
break;
-
- case EOpSign:
- switch (getType().getBasicType())
+ case EbtInt:
{
- case EbtFloat:
- {
- float fConst = operandArray[i].getFConst();
- float fResult = 0.0f;
- if (fConst > 0.0f)
- fResult = 1.0f;
- else if (fConst < 0.0f)
- fResult = -1.0f;
- resultArray[i].setFConst(fResult);
- break;
- }
- case EbtInt:
- {
- int iConst = operandArray[i].getIConst();
- int iResult = 0;
- if (iConst > 0)
- iResult = 1;
- else if (iConst < 0)
- iResult = -1;
- resultArray[i].setIConst(iResult);
- break;
- }
- default:
- UNREACHABLE();
- return nullptr;
+ int iConst = operandArray[i].getIConst();
+ int iResult = 0;
+ if (iConst > 0)
+ iResult = 1;
+ else if (iConst < 0)
+ iResult = -1;
+ resultArray[i].setIConst(iResult);
}
break;
+ default:
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
+ }
+ break;
- case EOpFloor:
- foldFloatTypeUnary(operandArray[i], &floorf, &resultArray[i]);
- break;
+ case EOpFloor:
+ if (!foldFloatTypeUnary(operandArray[i], &floorf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpTrunc:
- foldFloatTypeUnary(operandArray[i], &truncf, &resultArray[i]);
- break;
+ case EOpTrunc:
+ if (!foldFloatTypeUnary(operandArray[i], &truncf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpRound:
- foldFloatTypeUnary(operandArray[i], &roundf, &resultArray[i]);
- break;
+ case EOpRound:
+ if (!foldFloatTypeUnary(operandArray[i], &roundf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpRoundEven:
+ case EOpRoundEven:
+ if (getType().getBasicType() == EbtFloat)
{
- ASSERT(getType().getBasicType() == EbtFloat);
float x = operandArray[i].getFConst();
float result;
float fractPart = modff(x, &result);
@@ -1958,151 +1629,197 @@ TConstantUnion *TIntermConstantUnion::foldUnaryComponentWise(TOperator op,
resultArray[i].setFConst(result);
break;
}
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
- case EOpCeil:
- foldFloatTypeUnary(operandArray[i], &ceilf, &resultArray[i]);
- break;
+ case EOpCeil:
+ if (!foldFloatTypeUnary(operandArray[i], &ceilf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpFract:
+ case EOpFract:
+ if (getType().getBasicType() == EbtFloat)
{
- ASSERT(getType().getBasicType() == EbtFloat);
float x = operandArray[i].getFConst();
resultArray[i].setFConst(x - floorf(x));
break;
}
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
- case EOpIsNan:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpIsNan:
+ if (getType().getBasicType() == EbtFloat)
+ {
resultArray[i].setBConst(gl::isNaN(operandArray[0].getFConst()));
break;
+ }
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- case EOpIsInf:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpIsInf:
+ if (getType().getBasicType() == EbtFloat)
+ {
resultArray[i].setBConst(gl::isInf(operandArray[0].getFConst()));
break;
+ }
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- case EOpFloatBitsToInt:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpFloatBitsToInt:
+ if (getType().getBasicType() == EbtFloat)
+ {
resultArray[i].setIConst(gl::bitCast<int32_t>(operandArray[0].getFConst()));
break;
+ }
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- case EOpFloatBitsToUint:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpFloatBitsToUint:
+ if (getType().getBasicType() == EbtFloat)
+ {
resultArray[i].setUConst(gl::bitCast<uint32_t>(operandArray[0].getFConst()));
break;
+ }
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- case EOpIntBitsToFloat:
- ASSERT(getType().getBasicType() == EbtInt);
+ case EOpIntBitsToFloat:
+ if (getType().getBasicType() == EbtInt)
+ {
resultArray[i].setFConst(gl::bitCast<float>(operandArray[0].getIConst()));
break;
+ }
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- case EOpUintBitsToFloat:
- ASSERT(getType().getBasicType() == EbtUInt);
+ case EOpUintBitsToFloat:
+ if (getType().getBasicType() == EbtUInt)
+ {
resultArray[i].setFConst(gl::bitCast<float>(operandArray[0].getUConst()));
break;
+ }
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- case EOpExp:
- foldFloatTypeUnary(operandArray[i], &expf, &resultArray[i]);
- break;
+ case EOpExp:
+ if (!foldFloatTypeUnary(operandArray[i], &expf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpLog:
- // For log(x), results are undefined if x <= 0, we are choosing to set result to 0.
- if (operandArray[i].getFConst() <= 0.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- foldFloatTypeUnary(operandArray[i], &logf, &resultArray[i]);
- break;
+ case EOpLog:
+ // For log(x), results are undefined if x <= 0, we are choosing to set result to 0.
+ if (getType().getBasicType() == EbtFloat && operandArray[i].getFConst() <= 0.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &logf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpExp2:
- foldFloatTypeUnary(operandArray[i], &exp2f, &resultArray[i]);
- break;
+ case EOpExp2:
+ if (!foldFloatTypeUnary(operandArray[i], &exp2f, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpLog2:
- // For log2(x), results are undefined if x <= 0, we are choosing to set result to 0.
- // And log2f is not available on some plarforms like old android, so just using
- // log(x)/log(2) here.
- if (operandArray[i].getFConst() <= 0.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- {
- foldFloatTypeUnary(operandArray[i], &logf, &resultArray[i]);
- resultArray[i].setFConst(resultArray[i].getFConst() / logf(2.0f));
- }
- break;
+ case EOpLog2:
+ // For log2(x), results are undefined if x <= 0, we are choosing to set result to 0.
+ // And log2f is not available on some plarforms like old android, so just using log(x)/log(2) here.
+ if (getType().getBasicType() == EbtFloat && operandArray[i].getFConst() <= 0.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &logf, infoSink, &resultArray[i]))
+ return nullptr;
+ else
+ resultArray[i].setFConst(resultArray[i].getFConst() / logf(2.0f));
+ break;
- case EOpSqrt:
- // For sqrt(x), results are undefined if x < 0, we are choosing to set result to 0.
- if (operandArray[i].getFConst() < 0.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- foldFloatTypeUnary(operandArray[i], &sqrtf, &resultArray[i]);
- break;
+ case EOpSqrt:
+ // For sqrt(x), results are undefined if x < 0, we are choosing to set result to 0.
+ if (getType().getBasicType() == EbtFloat && operandArray[i].getFConst() < 0.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &sqrtf, infoSink, &resultArray[i]))
+ return nullptr;
+ break;
- case EOpInverseSqrt:
- // There is no stdlib built-in function equavalent for GLES built-in inversesqrt(),
- // so getting the square root first using builtin function sqrt() and then taking
- // its inverse.
- // Also, for inversesqrt(x), results are undefined if x <= 0, we are choosing to set
- // result to 0.
- if (operandArray[i].getFConst() <= 0.0f)
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
- else
- {
- foldFloatTypeUnary(operandArray[i], &sqrtf, &resultArray[i]);
- resultArray[i].setFConst(1.0f / resultArray[i].getFConst());
- }
- break;
+ case EOpInverseSqrt:
+ // There is no stdlib built-in function equavalent for GLES built-in inversesqrt(),
+ // so getting the square root first using builtin function sqrt() and then taking its inverse.
+ // Also, for inversesqrt(x), results are undefined if x <= 0, we are choosing to set result to 0.
+ if (getType().getBasicType() == EbtFloat && operandArray[i].getFConst() <= 0.0f)
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink, &resultArray[i]);
+ else if (!foldFloatTypeUnary(operandArray[i], &sqrtf, infoSink, &resultArray[i]))
+ return nullptr;
+ else
+ resultArray[i].setFConst(1.0f / resultArray[i].getFConst());
+ break;
- case EOpVectorLogicalNot:
- ASSERT(getType().getBasicType() == EbtBool);
+ case EOpVectorLogicalNot:
+ if (getType().getBasicType() == EbtBool)
+ {
resultArray[i].setBConst(!operandArray[i].getBConst());
break;
+ }
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return nullptr;
- case EOpNormalize:
+ case EOpNormalize:
+ if (getType().getBasicType() == EbtFloat)
{
- ASSERT(getType().getBasicType() == EbtFloat);
- float x = operandArray[i].getFConst();
+ float x = operandArray[i].getFConst();
float length = VectorLength(operandArray, objectSize);
if (length)
resultArray[i].setFConst(x / length);
else
- UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(),
- diagnostics, &resultArray[i]);
+ UndefinedConstantFoldingError(getLine(), op, getType().getBasicType(), infoSink,
+ &resultArray[i]);
break;
}
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- case EOpDFdx:
- case EOpDFdy:
- case EOpFwidth:
- ASSERT(getType().getBasicType() == EbtFloat);
+ case EOpDFdx:
+ case EOpDFdy:
+ case EOpFwidth:
+ if (getType().getBasicType() == EbtFloat)
+ {
// Derivatives of constant arguments should be 0.
resultArray[i].setFConst(0.0f);
break;
+ }
+ infoSink.info.message(EPrefixInternalError, getLine(), "Unary operation not folded into constant");
+ return nullptr;
- default:
- return nullptr;
+ default:
+ return nullptr;
}
}
return resultArray;
}
-void TIntermConstantUnion::foldFloatTypeUnary(const TConstantUnion &parameter,
- FloatTypeUnaryFunc builtinFunc,
- TConstantUnion *result) const
+bool TIntermConstantUnion::foldFloatTypeUnary(const TConstantUnion &parameter, FloatTypeUnaryFunc builtinFunc,
+ TInfoSink &infoSink, TConstantUnion *result) const
{
ASSERT(builtinFunc);
- ASSERT(getType().getBasicType() == EbtFloat);
- result->setFConst(builtinFunc(parameter.getFConst()));
+ if (getType().getBasicType() == EbtFloat)
+ {
+ result->setFConst(builtinFunc(parameter.getFConst()));
+ return true;
+ }
+
+ infoSink.info.message(
+ EPrefixInternalError, getLine(),
+ "Unary operation not folded into constant");
+ return false;
}
// static
-TConstantUnion *TIntermConstantUnion::FoldAggregateConstructor(TIntermAggregate *aggregate)
+TConstantUnion *TIntermConstantUnion::FoldAggregateConstructor(TIntermAggregate *aggregate,
+ TInfoSink &infoSink)
{
ASSERT(aggregate->getSequence()->size() > 0u);
size_t resultSize = aggregate->getType().getObjectSize();
@@ -2201,8 +1918,7 @@ TConstantUnion *TIntermConstantUnion::FoldAggregateConstructor(TIntermAggregate
}
// static
-TConstantUnion *TIntermConstantUnion::FoldAggregateBuiltIn(TIntermAggregate *aggregate,
- TDiagnostics *diagnostics)
+TConstantUnion *TIntermConstantUnion::FoldAggregateBuiltIn(TIntermAggregate *aggregate, TInfoSink &infoSink)
{
TOperator op = aggregate->getOp();
TIntermSequence *sequence = aggregate->getSequence();
@@ -2243,298 +1959,284 @@ TConstantUnion *TIntermConstantUnion::FoldAggregateBuiltIn(TIntermAggregate *agg
//
switch (op)
{
- case EOpAtan:
+ case EOpAtan:
{
- ASSERT(basicType == EbtFloat);
- resultArray = new TConstantUnion[maxObjectSize];
- for (size_t i = 0; i < maxObjectSize; i++)
+ if (basicType == EbtFloat)
{
- float y = unionArrays[0][i].getFConst();
- float x = unionArrays[1][i].getFConst();
- // Results are undefined if x and y are both 0.
- if (x == 0.0f && y == 0.0f)
- UndefinedConstantFoldingError(loc, op, basicType, diagnostics,
- &resultArray[i]);
- else
- resultArray[i].setFConst(atan2f(y, x));
+ resultArray = new TConstantUnion[maxObjectSize];
+ for (size_t i = 0; i < maxObjectSize; i++)
+ {
+ float y = unionArrays[0][i].getFConst();
+ float x = unionArrays[1][i].getFConst();
+ // Results are undefined if x and y are both 0.
+ if (x == 0.0f && y == 0.0f)
+ UndefinedConstantFoldingError(loc, op, basicType, infoSink, &resultArray[i]);
+ else
+ resultArray[i].setFConst(atan2f(y, x));
+ }
}
- break;
+ else
+ UNREACHABLE();
}
+ break;
- case EOpPow:
+ case EOpPow:
{
- ASSERT(basicType == EbtFloat);
- resultArray = new TConstantUnion[maxObjectSize];
- for (size_t i = 0; i < maxObjectSize; i++)
+ if (basicType == EbtFloat)
{
- float x = unionArrays[0][i].getFConst();
- float y = unionArrays[1][i].getFConst();
- // Results are undefined if x < 0.
- // Results are undefined if x = 0 and y <= 0.
- if (x < 0.0f)
- UndefinedConstantFoldingError(loc, op, basicType, diagnostics,
- &resultArray[i]);
- else if (x == 0.0f && y <= 0.0f)
- UndefinedConstantFoldingError(loc, op, basicType, diagnostics,
- &resultArray[i]);
- else
- resultArray[i].setFConst(powf(x, y));
+ resultArray = new TConstantUnion[maxObjectSize];
+ for (size_t i = 0; i < maxObjectSize; i++)
+ {
+ float x = unionArrays[0][i].getFConst();
+ float y = unionArrays[1][i].getFConst();
+ // Results are undefined if x < 0.
+ // Results are undefined if x = 0 and y <= 0.
+ if (x < 0.0f)
+ UndefinedConstantFoldingError(loc, op, basicType, infoSink, &resultArray[i]);
+ else if (x == 0.0f && y <= 0.0f)
+ UndefinedConstantFoldingError(loc, op, basicType, infoSink, &resultArray[i]);
+ else
+ resultArray[i].setFConst(powf(x, y));
+ }
}
- break;
+ else
+ UNREACHABLE();
}
+ break;
- case EOpMod:
+ case EOpMod:
{
- ASSERT(basicType == EbtFloat);
- resultArray = new TConstantUnion[maxObjectSize];
- for (size_t i = 0; i < maxObjectSize; i++)
+ if (basicType == EbtFloat)
{
- float x = unionArrays[0][i].getFConst();
- float y = unionArrays[1][i].getFConst();
- resultArray[i].setFConst(x - y * floorf(x / y));
+ resultArray = new TConstantUnion[maxObjectSize];
+ for (size_t i = 0; i < maxObjectSize; i++)
+ {
+ float x = unionArrays[0][i].getFConst();
+ float y = unionArrays[1][i].getFConst();
+ resultArray[i].setFConst(x - y * floorf(x / y));
+ }
}
- break;
+ else
+ UNREACHABLE();
}
+ break;
- case EOpMin:
+ case EOpMin:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setFConst(std::min(unionArrays[0][i].getFConst(),
- unionArrays[1][i].getFConst()));
- break;
- case EbtInt:
- resultArray[i].setIConst(std::min(unionArrays[0][i].getIConst(),
- unionArrays[1][i].getIConst()));
- break;
- case EbtUInt:
- resultArray[i].setUConst(std::min(unionArrays[0][i].getUConst(),
- unionArrays[1][i].getUConst()));
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setFConst(std::min(unionArrays[0][i].getFConst(), unionArrays[1][i].getFConst()));
+ break;
+ case EbtInt:
+ resultArray[i].setIConst(std::min(unionArrays[0][i].getIConst(), unionArrays[1][i].getIConst()));
+ break;
+ case EbtUInt:
+ resultArray[i].setUConst(std::min(unionArrays[0][i].getUConst(), unionArrays[1][i].getUConst()));
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
+ break;
- case EOpMax:
+ case EOpMax:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setFConst(std::max(unionArrays[0][i].getFConst(),
- unionArrays[1][i].getFConst()));
- break;
- case EbtInt:
- resultArray[i].setIConst(std::max(unionArrays[0][i].getIConst(),
- unionArrays[1][i].getIConst()));
- break;
- case EbtUInt:
- resultArray[i].setUConst(std::max(unionArrays[0][i].getUConst(),
- unionArrays[1][i].getUConst()));
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setFConst(std::max(unionArrays[0][i].getFConst(), unionArrays[1][i].getFConst()));
+ break;
+ case EbtInt:
+ resultArray[i].setIConst(std::max(unionArrays[0][i].getIConst(), unionArrays[1][i].getIConst()));
+ break;
+ case EbtUInt:
+ resultArray[i].setUConst(std::max(unionArrays[0][i].getUConst(), unionArrays[1][i].getUConst()));
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
+ break;
- case EOpStep:
+ case EOpStep:
{
- ASSERT(basicType == EbtFloat);
- resultArray = new TConstantUnion[maxObjectSize];
- for (size_t i = 0; i < maxObjectSize; i++)
- resultArray[i].setFConst(
- unionArrays[1][i].getFConst() < unionArrays[0][i].getFConst() ? 0.0f
- : 1.0f);
- break;
+ if (basicType == EbtFloat)
+ {
+ resultArray = new TConstantUnion[maxObjectSize];
+ for (size_t i = 0; i < maxObjectSize; i++)
+ resultArray[i].setFConst(unionArrays[1][i].getFConst() < unionArrays[0][i].getFConst() ? 0.0f : 1.0f);
+ }
+ else
+ UNREACHABLE();
}
+ break;
- case EOpLessThan:
+ case EOpLessThan:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setBConst(unionArrays[0][i].getFConst() <
- unionArrays[1][i].getFConst());
- break;
- case EbtInt:
- resultArray[i].setBConst(unionArrays[0][i].getIConst() <
- unionArrays[1][i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setBConst(unionArrays[0][i].getUConst() <
- unionArrays[1][i].getUConst());
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setBConst(unionArrays[0][i].getFConst() < unionArrays[1][i].getFConst());
+ break;
+ case EbtInt:
+ resultArray[i].setBConst(unionArrays[0][i].getIConst() < unionArrays[1][i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setBConst(unionArrays[0][i].getUConst() < unionArrays[1][i].getUConst());
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
+ break;
- case EOpLessThanEqual:
+ case EOpLessThanEqual:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setBConst(unionArrays[0][i].getFConst() <=
- unionArrays[1][i].getFConst());
- break;
- case EbtInt:
- resultArray[i].setBConst(unionArrays[0][i].getIConst() <=
- unionArrays[1][i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setBConst(unionArrays[0][i].getUConst() <=
- unionArrays[1][i].getUConst());
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setBConst(unionArrays[0][i].getFConst() <= unionArrays[1][i].getFConst());
+ break;
+ case EbtInt:
+ resultArray[i].setBConst(unionArrays[0][i].getIConst() <= unionArrays[1][i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setBConst(unionArrays[0][i].getUConst() <= unionArrays[1][i].getUConst());
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
+ break;
- case EOpGreaterThan:
+ case EOpGreaterThan:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setBConst(unionArrays[0][i].getFConst() >
- unionArrays[1][i].getFConst());
- break;
- case EbtInt:
- resultArray[i].setBConst(unionArrays[0][i].getIConst() >
- unionArrays[1][i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setBConst(unionArrays[0][i].getUConst() >
- unionArrays[1][i].getUConst());
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setBConst(unionArrays[0][i].getFConst() > unionArrays[1][i].getFConst());
+ break;
+ case EbtInt:
+ resultArray[i].setBConst(unionArrays[0][i].getIConst() > unionArrays[1][i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setBConst(unionArrays[0][i].getUConst() > unionArrays[1][i].getUConst());
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
- case EOpGreaterThanEqual:
+ break;
+
+ case EOpGreaterThanEqual:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setBConst(unionArrays[0][i].getFConst() >=
- unionArrays[1][i].getFConst());
- break;
- case EbtInt:
- resultArray[i].setBConst(unionArrays[0][i].getIConst() >=
- unionArrays[1][i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setBConst(unionArrays[0][i].getUConst() >=
- unionArrays[1][i].getUConst());
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setBConst(unionArrays[0][i].getFConst() >= unionArrays[1][i].getFConst());
+ break;
+ case EbtInt:
+ resultArray[i].setBConst(unionArrays[0][i].getIConst() >= unionArrays[1][i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setBConst(unionArrays[0][i].getUConst() >= unionArrays[1][i].getUConst());
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
}
break;
- case EOpVectorEqual:
+ case EOpVectorEqual:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setBConst(unionArrays[0][i].getFConst() ==
- unionArrays[1][i].getFConst());
- break;
- case EbtInt:
- resultArray[i].setBConst(unionArrays[0][i].getIConst() ==
- unionArrays[1][i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setBConst(unionArrays[0][i].getUConst() ==
- unionArrays[1][i].getUConst());
- break;
- case EbtBool:
- resultArray[i].setBConst(unionArrays[0][i].getBConst() ==
- unionArrays[1][i].getBConst());
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setBConst(unionArrays[0][i].getFConst() == unionArrays[1][i].getFConst());
+ break;
+ case EbtInt:
+ resultArray[i].setBConst(unionArrays[0][i].getIConst() == unionArrays[1][i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setBConst(unionArrays[0][i].getUConst() == unionArrays[1][i].getUConst());
+ break;
+ case EbtBool:
+ resultArray[i].setBConst(unionArrays[0][i].getBConst() == unionArrays[1][i].getBConst());
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
+ break;
- case EOpVectorNotEqual:
+ case EOpVectorNotEqual:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
- resultArray[i].setBConst(unionArrays[0][i].getFConst() !=
- unionArrays[1][i].getFConst());
- break;
- case EbtInt:
- resultArray[i].setBConst(unionArrays[0][i].getIConst() !=
- unionArrays[1][i].getIConst());
- break;
- case EbtUInt:
- resultArray[i].setBConst(unionArrays[0][i].getUConst() !=
- unionArrays[1][i].getUConst());
- break;
- case EbtBool:
- resultArray[i].setBConst(unionArrays[0][i].getBConst() !=
- unionArrays[1][i].getBConst());
- break;
- default:
- UNREACHABLE();
- break;
+ case EbtFloat:
+ resultArray[i].setBConst(unionArrays[0][i].getFConst() != unionArrays[1][i].getFConst());
+ break;
+ case EbtInt:
+ resultArray[i].setBConst(unionArrays[0][i].getIConst() != unionArrays[1][i].getIConst());
+ break;
+ case EbtUInt:
+ resultArray[i].setBConst(unionArrays[0][i].getUConst() != unionArrays[1][i].getUConst());
+ break;
+ case EbtBool:
+ resultArray[i].setBConst(unionArrays[0][i].getBConst() != unionArrays[1][i].getBConst());
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
+ break;
- case EOpDistance:
+ case EOpDistance:
+ if (basicType == EbtFloat)
{
- ASSERT(basicType == EbtFloat);
TConstantUnion *distanceArray = new TConstantUnion[maxObjectSize];
- resultArray = new TConstantUnion();
+ resultArray = new TConstantUnion();
for (size_t i = 0; i < maxObjectSize; i++)
{
float x = unionArrays[0][i].getFConst();
@@ -2542,40 +2244,47 @@ TConstantUnion *TIntermConstantUnion::FoldAggregateBuiltIn(TIntermAggregate *agg
distanceArray[i].setFConst(x - y);
}
resultArray->setFConst(VectorLength(distanceArray, maxObjectSize));
- break;
}
+ else
+ UNREACHABLE();
+ break;
+
+ case EOpDot:
- case EOpDot:
- ASSERT(basicType == EbtFloat);
+ if (basicType == EbtFloat)
+ {
resultArray = new TConstantUnion();
- resultArray->setFConst(
- VectorDotProduct(unionArrays[0], unionArrays[1], maxObjectSize));
- break;
+ resultArray->setFConst(VectorDotProduct(unionArrays[0], unionArrays[1], maxObjectSize));
+ }
+ else
+ UNREACHABLE();
+ break;
- case EOpCross:
+ case EOpCross:
+ if (basicType == EbtFloat && maxObjectSize == 3)
{
- ASSERT(basicType == EbtFloat && maxObjectSize == 3);
resultArray = new TConstantUnion[maxObjectSize];
- float x0 = unionArrays[0][0].getFConst();
- float x1 = unionArrays[0][1].getFConst();
- float x2 = unionArrays[0][2].getFConst();
- float y0 = unionArrays[1][0].getFConst();
- float y1 = unionArrays[1][1].getFConst();
- float y2 = unionArrays[1][2].getFConst();
+ float x0 = unionArrays[0][0].getFConst();
+ float x1 = unionArrays[0][1].getFConst();
+ float x2 = unionArrays[0][2].getFConst();
+ float y0 = unionArrays[1][0].getFConst();
+ float y1 = unionArrays[1][1].getFConst();
+ float y2 = unionArrays[1][2].getFConst();
resultArray[0].setFConst(x1 * y2 - y1 * x2);
resultArray[1].setFConst(x2 * y0 - y2 * x0);
resultArray[2].setFConst(x0 * y1 - y0 * x1);
- break;
}
+ else
+ UNREACHABLE();
+ break;
- case EOpReflect:
+ case EOpReflect:
+ if (basicType == EbtFloat)
{
- ASSERT(basicType == EbtFloat);
// genType reflect (genType I, genType N) :
- // For the incident vector I and surface orientation N, returns the reflection
- // direction:
+ // For the incident vector I and surface orientation N, returns the reflection direction:
// I - 2 * dot(N, I) * N.
- resultArray = new TConstantUnion[maxObjectSize];
+ resultArray = new TConstantUnion[maxObjectSize];
float dotProduct = VectorDotProduct(unionArrays[1], unionArrays[0], maxObjectSize);
for (size_t i = 0; i < maxObjectSize; i++)
{
@@ -2583,40 +2292,45 @@ TConstantUnion *TIntermConstantUnion::FoldAggregateBuiltIn(TIntermAggregate *agg
2.0f * dotProduct * unionArrays[1][i].getFConst();
resultArray[i].setFConst(result);
}
- break;
}
+ else
+ UNREACHABLE();
+ break;
- case EOpMul:
+ case EOpMul:
+ if (basicType == EbtFloat && (*sequence)[0]->getAsTyped()->isMatrix() &&
+ (*sequence)[1]->getAsTyped()->isMatrix())
{
- ASSERT(basicType == EbtFloat && (*sequence)[0]->getAsTyped()->isMatrix() &&
- (*sequence)[1]->getAsTyped()->isMatrix());
// Perform component-wise matrix multiplication.
resultArray = new TConstantUnion[maxObjectSize];
- int size = (*sequence)[0]->getAsTyped()->getNominalSize();
+ int size = (*sequence)[0]->getAsTyped()->getNominalSize();
angle::Matrix<float> result =
GetMatrix(unionArrays[0], size).compMult(GetMatrix(unionArrays[1], size));
SetUnionArrayFromMatrix(result, resultArray);
- break;
}
+ else
+ UNREACHABLE();
+ break;
- case EOpOuterProduct:
+ case EOpOuterProduct:
+ if (basicType == EbtFloat)
{
- ASSERT(basicType == EbtFloat);
size_t numRows = (*sequence)[0]->getAsTyped()->getType().getObjectSize();
size_t numCols = (*sequence)[1]->getAsTyped()->getType().getObjectSize();
- resultArray = new TConstantUnion[numRows * numCols];
+ resultArray = new TConstantUnion[numRows * numCols];
angle::Matrix<float> result =
GetMatrix(unionArrays[0], static_cast<int>(numRows), 1)
.outerProduct(GetMatrix(unionArrays[1], 1, static_cast<int>(numCols)));
SetUnionArrayFromMatrix(result, resultArray);
- break;
}
-
- default:
+ else
UNREACHABLE();
- // TODO: Add constant folding support for other built-in operations that take 2
- // parameters and not handled above.
- return nullptr;
+ break;
+
+ default:
+ UNREACHABLE();
+ // TODO: Add constant folding support for other built-in operations that take 2 parameters and not handled above.
+ return nullptr;
}
}
else if (paramsCount == 3)
@@ -2626,123 +2340,124 @@ TConstantUnion *TIntermConstantUnion::FoldAggregateBuiltIn(TIntermAggregate *agg
//
switch (op)
{
- case EOpClamp:
+ case EOpClamp:
{
resultArray = new TConstantUnion[maxObjectSize];
for (size_t i = 0; i < maxObjectSize; i++)
{
switch (basicType)
{
- case EbtFloat:
+ case EbtFloat:
{
- float x = unionArrays[0][i].getFConst();
+ float x = unionArrays[0][i].getFConst();
float min = unionArrays[1][i].getFConst();
float max = unionArrays[2][i].getFConst();
// Results are undefined if min > max.
if (min > max)
- UndefinedConstantFoldingError(loc, op, basicType, diagnostics,
- &resultArray[i]);
+ UndefinedConstantFoldingError(loc, op, basicType, infoSink, &resultArray[i]);
else
resultArray[i].setFConst(gl::clamp(x, min, max));
- break;
}
-
- case EbtInt:
+ break;
+ case EbtInt:
{
- int x = unionArrays[0][i].getIConst();
+ int x = unionArrays[0][i].getIConst();
int min = unionArrays[1][i].getIConst();
int max = unionArrays[2][i].getIConst();
// Results are undefined if min > max.
if (min > max)
- UndefinedConstantFoldingError(loc, op, basicType, diagnostics,
- &resultArray[i]);
+ UndefinedConstantFoldingError(loc, op, basicType, infoSink, &resultArray[i]);
else
resultArray[i].setIConst(gl::clamp(x, min, max));
- break;
}
- case EbtUInt:
+ break;
+ case EbtUInt:
{
- unsigned int x = unionArrays[0][i].getUConst();
+ unsigned int x = unionArrays[0][i].getUConst();
unsigned int min = unionArrays[1][i].getUConst();
unsigned int max = unionArrays[2][i].getUConst();
// Results are undefined if min > max.
if (min > max)
- UndefinedConstantFoldingError(loc, op, basicType, diagnostics,
- &resultArray[i]);
+ UndefinedConstantFoldingError(loc, op, basicType, infoSink, &resultArray[i]);
else
resultArray[i].setUConst(gl::clamp(x, min, max));
- break;
}
- default:
- UNREACHABLE();
- break;
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
}
- break;
}
+ break;
- case EOpMix:
+ case EOpMix:
{
- ASSERT(basicType == EbtFloat);
- resultArray = new TConstantUnion[maxObjectSize];
- for (size_t i = 0; i < maxObjectSize; i++)
+ if (basicType == EbtFloat)
{
- float x = unionArrays[0][i].getFConst();
- float y = unionArrays[1][i].getFConst();
- TBasicType type = (*sequence)[2]->getAsTyped()->getType().getBasicType();
- if (type == EbtFloat)
+ resultArray = new TConstantUnion[maxObjectSize];
+ for (size_t i = 0; i < maxObjectSize; i++)
{
- // Returns the linear blend of x and y, i.e., x * (1 - a) + y * a.
- float a = unionArrays[2][i].getFConst();
- resultArray[i].setFConst(x * (1.0f - a) + y * a);
- }
- else // 3rd parameter is EbtBool
- {
- ASSERT(type == EbtBool);
- // Selects which vector each returned component comes from.
- // For a component of a that is false, the corresponding component of x is
- // returned.
- // For a component of a that is true, the corresponding component of y is
- // returned.
- bool a = unionArrays[2][i].getBConst();
- resultArray[i].setFConst(a ? y : x);
+ float x = unionArrays[0][i].getFConst();
+ float y = unionArrays[1][i].getFConst();
+ TBasicType type = (*sequence)[2]->getAsTyped()->getType().getBasicType();
+ if (type == EbtFloat)
+ {
+ // Returns the linear blend of x and y, i.e., x * (1 - a) + y * a.
+ float a = unionArrays[2][i].getFConst();
+ resultArray[i].setFConst(x * (1.0f - a) + y * a);
+ }
+ else // 3rd parameter is EbtBool
+ {
+ ASSERT(type == EbtBool);
+ // Selects which vector each returned component comes from.
+ // For a component of a that is false, the corresponding component of x is returned.
+ // For a component of a that is true, the corresponding component of y is returned.
+ bool a = unionArrays[2][i].getBConst();
+ resultArray[i].setFConst(a ? y : x);
+ }
}
}
- break;
+ else
+ UNREACHABLE();
}
+ break;
- case EOpSmoothStep:
+ case EOpSmoothStep:
{
- ASSERT(basicType == EbtFloat);
- resultArray = new TConstantUnion[maxObjectSize];
- for (size_t i = 0; i < maxObjectSize; i++)
+ if (basicType == EbtFloat)
{
- float edge0 = unionArrays[0][i].getFConst();
- float edge1 = unionArrays[1][i].getFConst();
- float x = unionArrays[2][i].getFConst();
- // Results are undefined if edge0 >= edge1.
- if (edge0 >= edge1)
+ resultArray = new TConstantUnion[maxObjectSize];
+ for (size_t i = 0; i < maxObjectSize; i++)
{
- UndefinedConstantFoldingError(loc, op, basicType, diagnostics,
- &resultArray[i]);
- }
- else
- {
- // Returns 0.0 if x <= edge0 and 1.0 if x >= edge1 and performs smooth
- // Hermite interpolation between 0 and 1 when edge0 < x < edge1.
- float t = gl::clamp((x - edge0) / (edge1 - edge0), 0.0f, 1.0f);
- resultArray[i].setFConst(t * t * (3.0f - 2.0f * t));
+ float edge0 = unionArrays[0][i].getFConst();
+ float edge1 = unionArrays[1][i].getFConst();
+ float x = unionArrays[2][i].getFConst();
+ // Results are undefined if edge0 >= edge1.
+ if (edge0 >= edge1)
+ {
+ UndefinedConstantFoldingError(loc, op, basicType, infoSink, &resultArray[i]);
+ }
+ else
+ {
+ // Returns 0.0 if x <= edge0 and 1.0 if x >= edge1 and performs smooth
+ // Hermite interpolation between 0 and 1 when edge0 < x < edge1.
+ float t = gl::clamp((x - edge0) / (edge1 - edge0), 0.0f, 1.0f);
+ resultArray[i].setFConst(t * t * (3.0f - 2.0f * t));
+ }
}
}
- break;
+ else
+ UNREACHABLE();
}
+ break;
- case EOpFaceForward:
+ case EOpFaceForward:
+ if (basicType == EbtFloat)
{
- ASSERT(basicType == EbtFloat);
// genType faceforward(genType N, genType I, genType Nref) :
// If dot(Nref, I) < 0 return N, otherwise return -N.
- resultArray = new TConstantUnion[maxObjectSize];
+ resultArray = new TConstantUnion[maxObjectSize];
float dotProduct = VectorDotProduct(unionArrays[2], unionArrays[1], maxObjectSize);
for (size_t i = 0; i < maxObjectSize; i++)
{
@@ -2751,42 +2466,43 @@ TConstantUnion *TIntermConstantUnion::FoldAggregateBuiltIn(TIntermAggregate *agg
else
resultArray[i].setFConst(-unionArrays[0][i].getFConst());
}
- break;
}
+ else
+ UNREACHABLE();
+ break;
- case EOpRefract:
+ case EOpRefract:
+ if (basicType == EbtFloat)
{
- ASSERT(basicType == EbtFloat);
// genType refract(genType I, genType N, float eta) :
- // For the incident vector I and surface normal N, and the ratio of indices of
- // refraction eta,
+ // For the incident vector I and surface normal N, and the ratio of indices of refraction eta,
// return the refraction vector. The result is computed by
// k = 1.0 - eta * eta * (1.0 - dot(N, I) * dot(N, I))
// if (k < 0.0)
// return genType(0.0)
// else
// return eta * I - (eta * dot(N, I) + sqrt(k)) * N
- resultArray = new TConstantUnion[maxObjectSize];
+ resultArray = new TConstantUnion[maxObjectSize];
float dotProduct = VectorDotProduct(unionArrays[1], unionArrays[0], maxObjectSize);
for (size_t i = 0; i < maxObjectSize; i++)
{
float eta = unionArrays[2][i].getFConst();
- float k = 1.0f - eta * eta * (1.0f - dotProduct * dotProduct);
+ float k = 1.0f - eta * eta * (1.0f - dotProduct * dotProduct);
if (k < 0.0f)
resultArray[i].setFConst(0.0f);
else
resultArray[i].setFConst(eta * unionArrays[0][i].getFConst() -
- (eta * dotProduct + sqrtf(k)) *
- unionArrays[1][i].getFConst());
+ (eta * dotProduct + sqrtf(k)) * unionArrays[1][i].getFConst());
}
- break;
}
-
- default:
+ else
UNREACHABLE();
- // TODO: Add constant folding support for other built-in operations that take 3
- // parameters and not handled above.
- return nullptr;
+ break;
+
+ default:
+ UNREACHABLE();
+ // TODO: Add constant folding support for other built-in operations that take 3 parameters and not handled above.
+ return nullptr;
}
}
return resultArray;
@@ -2815,12 +2531,14 @@ void TIntermTraverser::updateTree()
bool inserted = insertion.parent->insertChildNodes(insertion.position + 1,
insertion.insertionsAfter);
ASSERT(inserted);
+ UNUSED_ASSERTION_VARIABLE(inserted);
}
if (!insertion.insertionsBefore.empty())
{
bool inserted =
insertion.parent->insertChildNodes(insertion.position, insertion.insertionsBefore);
ASSERT(inserted);
+ UNUSED_ASSERTION_VARIABLE(inserted);
}
}
for (size_t ii = 0; ii < mReplacements.size(); ++ii)
@@ -2830,6 +2548,7 @@ void TIntermTraverser::updateTree()
bool replaced = replacement.parent->replaceChildNode(
replacement.original, replacement.replacement);
ASSERT(replaced);
+ UNUSED_ASSERTION_VARIABLE(replaced);
if (!replacement.originalBecomesChildOfReplacement)
{
@@ -2852,6 +2571,7 @@ void TIntermTraverser::updateTree()
bool replaced = replacement.parent->replaceChildNodeWithMultiple(
replacement.original, replacement.replacements);
ASSERT(replaced);
+ UNUSED_ASSERTION_VARIABLE(replaced);
}
clearReplacementQueue();
@@ -2879,5 +2599,3 @@ void TIntermTraverser::queueReplacementWithParent(TIntermNode *parent,
bool originalBecomesChild = (originalStatus == OriginalNode::BECOMES_CHILD);
mReplacements.push_back(NodeUpdateEntry(parent, original, replacement, originalBecomesChild));
}
-
-} // namespace sh