1a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 2a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved. 3a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// Use of this source code is governed by a BSD-style license that can be 4a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// found in the LICENSE file. 5a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 6a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 7a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block#include "compiler/localintermediate.h" 8a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 9a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 10a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// Two purposes: 11a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 1. Show an example of how to iterate tree. Functions can 12a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// also directly call Traverse() on children themselves to 13a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// have finer grained control over the process than shown here. 14a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// See the last function for how to get started. 15a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 2. Print out a text based description of the tree. 16a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 17a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 18a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 19a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// Use this class to carry along data from node to node in 20a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// the traversal 21a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 22a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockclass TOutputTraverser : public TIntermTraverser { 23a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockpublic: 24ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TOutputTraverser(TInfoSinkBase& i) : sink(i) { } 25ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& sink; 26a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 27a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockprotected: 28a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block void visitSymbol(TIntermSymbol*); 29a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block void visitConstantUnion(TIntermConstantUnion*); 30a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block bool visitBinary(Visit visit, TIntermBinary*); 31a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block bool visitUnary(Visit visit, TIntermUnary*); 32a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block bool visitSelection(Visit visit, TIntermSelection*); 33a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block bool visitAggregate(Visit visit, TIntermAggregate*); 34a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block bool visitLoop(Visit visit, TIntermLoop*); 35a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block bool visitBranch(Visit visit, TIntermBranch*); 36a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block}; 37a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 38a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve BlockTString TType::getCompleteString() const 39a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 40a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block TStringStream stream; 41a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 42a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (qualifier != EvqTemporary && qualifier != EvqGlobal) 43a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block stream << getQualifierString() << " " << getPrecisionString() << " "; 44a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (array) 45a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block stream << "array of "; 46a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (matrix) 47a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block stream << size << "X" << size << " matrix of "; 48a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block else if (size > 1) 49a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block stream << size << "-component vector of "; 50a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 51a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block stream << getBasicString(); 52a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return stream.str(); 53a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 54a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 55a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 56a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// Helper functions for printing, not part of traversing. 57a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 58a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 59ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdochvoid OutputTreeText(TInfoSinkBase& sink, TIntermNode* node, const int depth) 60a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 61a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block int i; 62a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 63ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch sink.location(node->getLine()); 64a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 65a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block for (i = 0; i < depth; ++i) 66ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch sink << " "; 67a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 68a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 69a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 70a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// The rest of the file are the traversal functions. The last one 71a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// is the one that starts the traversal. 72a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 73a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// Return true from interior nodes to have the external traversal 74a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// continue on to children. If you process children yourself, 75a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// return false. 76a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 77a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 78a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockvoid TOutputTraverser::visitSymbol(TIntermSymbol* node) 79a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 80ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch OutputTreeText(sink, node, depth); 81a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 82ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch sink << "'" << node->getSymbol() << "' "; 83ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch sink << "(" << node->getCompleteString() << ")\n"; 84a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 85a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 86a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockbool TOutputTraverser::visitBinary(Visit visit, TIntermBinary* node) 87a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 88ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& out = sink; 89a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 90a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block OutputTreeText(out, node, depth); 91a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 92a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block switch (node->getOp()) { 93ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAssign: out << "move second child to first child"; break; 94ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpInitialize: out << "initialize first child with second child"; break; 95ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAddAssign: out << "add second child into first child"; break; 96ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpSubAssign: out << "subtract second child into first child"; break; 97ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMulAssign: out << "multiply second child into first child"; break; 98ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpVectorTimesMatrixAssign: out << "matrix mult second child into first child"; break; 99ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpVectorTimesScalarAssign: out << "vector scale second child into first child"; break; 100ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMatrixTimesScalarAssign: out << "matrix scale second child into first child"; break; 101ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMatrixTimesMatrixAssign: out << "matrix mult second child into first child"; break; 102ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpDivAssign: out << "divide second child into first child"; break; 103ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpIndexDirect: out << "direct index"; break; 104ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpIndexIndirect: out << "indirect index"; break; 105ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpIndexDirectStruct: out << "direct index for structure"; break; 106ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpVectorSwizzle: out << "vector swizzle"; break; 107ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 108ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAdd: out << "add"; break; 109ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpSub: out << "subtract"; break; 110ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMul: out << "component-wise multiply"; break; 111ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpDiv: out << "divide"; break; 112ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpEqual: out << "Compare Equal"; break; 113ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpNotEqual: out << "Compare Not Equal"; break; 114ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLessThan: out << "Compare Less Than"; break; 115ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpGreaterThan: out << "Compare Greater Than"; break; 116ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLessThanEqual: out << "Compare Less Than or Equal"; break; 117ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpGreaterThanEqual: out << "Compare Greater Than or Equal"; break; 118ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 119ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpVectorTimesScalar: out << "vector-scale"; break; 120ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpVectorTimesMatrix: out << "vector-times-matrix"; break; 121ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMatrixTimesVector: out << "matrix-times-vector"; break; 122ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMatrixTimesScalar: out << "matrix-scale"; break; 123ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMatrixTimesMatrix: out << "matrix-multiply"; break; 124ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 125ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLogicalOr: out << "logical-or"; break; 126ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLogicalXor: out << "logical-xor"; break; 127ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLogicalAnd: out << "logical-and"; break; 128ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch default: out << "<unknown op>"; 129a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 130a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 131ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " (" << node->getCompleteString() << ")"; 132a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 133ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "\n"; 134a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 135a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return true; 136a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 137a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 138a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockbool TOutputTraverser::visitUnary(Visit visit, TIntermUnary* node) 139a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 140ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& out = sink; 141a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 142a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block OutputTreeText(out, node, depth); 143a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 144a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block switch (node->getOp()) { 145ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpNegative: out << "Negate value"; break; 146a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block case EOpVectorLogicalNot: 147ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLogicalNot: out << "Negate conditional"; break; 148ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 149ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpPostIncrement: out << "Post-Increment"; break; 150ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpPostDecrement: out << "Post-Decrement"; break; 151ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpPreIncrement: out << "Pre-Increment"; break; 152ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpPreDecrement: out << "Pre-Decrement"; break; 153ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 154ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConvIntToBool: out << "Convert int to bool"; break; 155ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConvFloatToBool:out << "Convert float to bool";break; 156ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConvBoolToFloat:out << "Convert bool to float";break; 157ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConvIntToFloat: out << "Convert int to float"; break; 158ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConvFloatToInt: out << "Convert float to int"; break; 159ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConvBoolToInt: out << "Convert bool to int"; break; 160ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 161ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpRadians: out << "radians"; break; 162ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpDegrees: out << "degrees"; break; 163ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpSin: out << "sine"; break; 164ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpCos: out << "cosine"; break; 165ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpTan: out << "tangent"; break; 166ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAsin: out << "arc sine"; break; 167ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAcos: out << "arc cosine"; break; 168ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAtan: out << "arc tangent"; break; 169ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 170ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpExp: out << "exp"; break; 171ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLog: out << "log"; break; 172ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpExp2: out << "exp2"; break; 173ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLog2: out << "log2"; break; 174ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpSqrt: out << "sqrt"; break; 175ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpInverseSqrt: out << "inverse sqrt"; break; 176ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 177ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAbs: out << "Absolute value"; break; 178ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpSign: out << "Sign"; break; 179ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpFloor: out << "Floor"; break; 180ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpCeil: out << "Ceiling"; break; 181ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpFract: out << "Fraction"; break; 182ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 183ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLength: out << "length"; break; 184ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpNormalize: out << "normalize"; break; 185ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch // case EOpDPdx: out << "dPdx"; break; 186ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch // case EOpDPdy: out << "dPdy"; break; 187ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch // case EOpFwidth: out << "fwidth"; break; 188ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 189ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAny: out << "any"; break; 190ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAll: out << "all"; break; 191ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 192ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch default: out.message(EPrefixError, "Bad unary op"); 193a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 194a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 195ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " (" << node->getCompleteString() << ")"; 196a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 197ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "\n"; 198a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 199a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return true; 200a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 201a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 202a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockbool TOutputTraverser::visitAggregate(Visit visit, TIntermAggregate* node) 203a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 204ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& out = sink; 205a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 206a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (node->getOp() == EOpNull) { 207ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out.message(EPrefixError, "node is still EOpNull!"); 208a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return true; 209a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 210a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 211a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block OutputTreeText(out, node, depth); 212a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 213a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block switch (node->getOp()) { 214ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpSequence: out << "Sequence\n"; return true; 215ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpComma: out << "Comma\n"; return true; 216ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpFunction: out << "Function Definition: " << node->getName(); break; 217ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpFunctionCall: out << "Function Call: " << node->getName(); break; 218ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpParameters: out << "Function Parameters: "; break; 219ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 220ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructFloat: out << "Construct float"; break; 221ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructVec2: out << "Construct vec2"; break; 222ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructVec3: out << "Construct vec3"; break; 223ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructVec4: out << "Construct vec4"; break; 224ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructBool: out << "Construct bool"; break; 225ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructBVec2: out << "Construct bvec2"; break; 226ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructBVec3: out << "Construct bvec3"; break; 227ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructBVec4: out << "Construct bvec4"; break; 228ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructInt: out << "Construct int"; break; 229ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructIVec2: out << "Construct ivec2"; break; 230ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructIVec3: out << "Construct ivec3"; break; 231ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructIVec4: out << "Construct ivec4"; break; 232ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructMat2: out << "Construct mat2"; break; 233ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructMat3: out << "Construct mat3"; break; 234ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructMat4: out << "Construct mat4"; break; 235ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpConstructStruct: out << "Construct structure"; break; 236ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 237ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLessThan: out << "Compare Less Than"; break; 238ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpGreaterThan: out << "Compare Greater Than"; break; 239ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpLessThanEqual: out << "Compare Less Than or Equal"; break; 240ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpGreaterThanEqual: out << "Compare Greater Than or Equal"; break; 241ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpVectorEqual: out << "Equal"; break; 242ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpVectorNotEqual: out << "NotEqual"; break; 243ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 244ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMod: out << "mod"; break; 245ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpPow: out << "pow"; break; 246ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 247ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpAtan: out << "arc tangent"; break; 248ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 249ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMin: out << "min"; break; 250ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMax: out << "max"; break; 251ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpClamp: out << "clamp"; break; 252ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMix: out << "mix"; break; 253ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpStep: out << "step"; break; 254ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpSmoothStep: out << "smoothstep"; break; 255ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 256ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpDistance: out << "distance"; break; 257ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpDot: out << "dot-product"; break; 258ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpCross: out << "cross-product"; break; 259ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpFaceForward: out << "face-forward"; break; 260ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpReflect: out << "reflect"; break; 261ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpRefract: out << "refract"; break; 262ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpMul: out << "component-wise multiply"; break; 263ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch 264ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch default: out.message(EPrefixError, "Bad aggregation op"); 265a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 266a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 267a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (node->getOp() != EOpSequence && node->getOp() != EOpParameters) 268ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " (" << node->getCompleteString() << ")"; 269a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 270ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "\n"; 271a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 272a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return true; 273a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 274a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 275a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockbool TOutputTraverser::visitSelection(Visit visit, TIntermSelection* node) 276a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 277ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& out = sink; 278a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 279a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block OutputTreeText(out, node, depth); 280a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 281ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "Test condition and select"; 282ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " (" << node->getCompleteString() << ")\n"; 283a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 284a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block ++depth; 285a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 286ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch OutputTreeText(sink, node, depth); 287ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "Condition\n"; 288a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block node->getCondition()->traverse(this); 289a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 290ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch OutputTreeText(sink, node, depth); 291a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (node->getTrueBlock()) { 292ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "true case\n"; 293a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block node->getTrueBlock()->traverse(this); 294a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } else 295ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "true case is null\n"; 296a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 297a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (node->getFalseBlock()) { 298ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch OutputTreeText(sink, node, depth); 299ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "false case\n"; 300a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block node->getFalseBlock()->traverse(this); 301a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 302a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 303a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block --depth; 304a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 305a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return false; 306a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 307a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 308a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockvoid TOutputTraverser::visitConstantUnion(TIntermConstantUnion* node) 309a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 310ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& out = sink; 311a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 312a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block int size = node->getType().getObjectSize(); 313a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 314a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block for (int i = 0; i < size; i++) { 315a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block OutputTreeText(out, node, depth); 316a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block switch (node->getUnionArrayPointer()[i].getType()) { 317a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block case EbtBool: 318a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (node->getUnionArrayPointer()[i].getBConst()) 319ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "true"; 320a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block else 321ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "false"; 322a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 323ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " (" << "const bool" << ")"; 324ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "\n"; 325a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block break; 326a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block case EbtFloat: 327ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << node->getUnionArrayPointer()[i].getFConst(); 328ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " (const float)\n"; 329a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block break; 330a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block case EbtInt: 331ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << node->getUnionArrayPointer()[i].getIConst(); 332ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " (const int)\n"; 333a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block break; 334a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block default: 335ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out.message(EPrefixInternalError, "Unknown constant", node->getLine()); 336a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block break; 337a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 338a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 339a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 340a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 341a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockbool TOutputTraverser::visitLoop(Visit visit, TIntermLoop* node) 342a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 343ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& out = sink; 344a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 345a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block OutputTreeText(out, node, depth); 346a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 347ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "Loop with condition "; 348ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch if (node->getType() == ELoopDoWhile) 349ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "not "; 350ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "tested first\n"; 351a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 352a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block ++depth; 353a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 354ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch OutputTreeText(sink, node, depth); 355ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch if (node->getCondition()) { 356ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "Loop Condition\n"; 357ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch node->getCondition()->traverse(this); 358a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } else 359ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "No loop condition\n"; 360a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 361ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch OutputTreeText(sink, node, depth); 362a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (node->getBody()) { 363ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "Loop Body\n"; 364a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block node->getBody()->traverse(this); 365a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } else 366ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "No loop body\n"; 367a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 368ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch if (node->getExpression()) { 369ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch OutputTreeText(sink, node, depth); 370ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "Loop Terminal Expression\n"; 371ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch node->getExpression()->traverse(this); 372a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 373a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 374a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block --depth; 375a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 376a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return false; 377a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 378a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 379a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockbool TOutputTraverser::visitBranch(Visit visit, TIntermBranch* node) 380a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 381ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TInfoSinkBase& out = sink; 382a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 383a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block OutputTreeText(out, node, depth); 384a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 385a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block switch (node->getFlowOp()) { 386ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpKill: out << "Branch: Kill"; break; 387ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpBreak: out << "Branch: Break"; break; 388ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpContinue: out << "Branch: Continue"; break; 389ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch case EOpReturn: out << "Branch: Return"; break; 390ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch default: out << "Branch: Unknown Branch"; break; 391a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } 392a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 393a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (node->getExpression()) { 394ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << " with expression\n"; 395a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block ++depth; 396a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block node->getExpression()->traverse(this); 397a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block --depth; 398a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block } else 399ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch out << "\n"; 400a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 401a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return false; 402a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 403a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 404a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 405a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// This function is the one to call externally to start the traversal. 406a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// Individual functions can be initialized to 0 to skip processing of that 407a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// type of node. It's children will still be processed. 408a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block// 409a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Blockvoid TIntermediate::outputTree(TIntermNode* root) 410a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block{ 411a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block if (root == 0) 412a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block return; 413a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 414ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch TOutputTraverser it(infoSink.info); 415a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block 416a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block root->traverse(&it); 417a9bfd6c4a32dfd9cc032cb67c6ccb8d09c16f579Steve Block} 418