Line data Source code
1 : //
2 : // Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
3 : // Use of this source code is governed by a BSD-style license that can be
4 : // found in the LICENSE file.
5 : //
6 :
7 : #include "compiler/translator/AddAndTrueToLoopCondition.h"
8 :
9 : #include "compiler/translator/IntermNode.h"
10 :
11 : namespace sh
12 : {
13 :
14 : namespace
15 : {
16 :
17 : // An AST traverser that rewrites for and while loops by replacing "condition" with
18 : // "condition && true" to work around condition bug on Intel Mac.
19 0 : class AddAndTrueToLoopConditionTraverser : public TIntermTraverser
20 : {
21 : public:
22 0 : AddAndTrueToLoopConditionTraverser() : TIntermTraverser(true, false, false) {}
23 :
24 0 : bool visitLoop(Visit, TIntermLoop *loop) override
25 : {
26 : // do-while loop doesn't have this bug.
27 0 : if (loop->getType() != ELoopFor && loop->getType() != ELoopWhile)
28 : {
29 0 : return true;
30 : }
31 :
32 : // For loop may not have a condition.
33 0 : if (loop->getCondition() == nullptr)
34 : {
35 0 : return true;
36 : }
37 :
38 : // Constant true.
39 0 : TConstantUnion *trueConstant = new TConstantUnion();
40 0 : trueConstant->setBConst(true);
41 0 : TIntermTyped *trueValue = new TIntermConstantUnion(trueConstant, TType(EbtBool));
42 :
43 : // CONDITION && true.
44 0 : TIntermBinary *andOp = new TIntermBinary(EOpLogicalAnd, loop->getCondition(), trueValue);
45 0 : loop->setCondition(andOp);
46 :
47 0 : return true;
48 : }
49 : };
50 :
51 : } // anonymous namespace
52 :
53 0 : void AddAndTrueToLoopCondition(TIntermNode *root)
54 : {
55 0 : AddAndTrueToLoopConditionTraverser traverser;
56 0 : root->traverse(&traverser);
57 0 : }
58 :
59 : } // namespace sh
|