Пример #1
0
 public override AstNode Visit(TernaryOperation node)
 {
     // Visit recursively.
     node.GetCondExpression().Accept(this);
     node.GetLeftExpression().Accept(this);
     node.GetRightExpression().Accept(this);
     return node;
 }
Пример #2
0
        public override AstNode Visit(TernaryOperation node)
        {
            // Begin the node.
            builder.BeginNode(node);

            // Get the expressions.
            Expression cond = node.GetCondExpression();
            Expression left = node.GetLeftExpression();
            Expression right = node.GetRightExpression();

            // Get the types.
            IChelaType condType = cond.GetNodeType();
            IChelaType leftType = left.GetNodeType();
            IChelaType rightType = right.GetNodeType();
            IChelaType coercionType = node.GetCoercionType();

            // Create the basic blocks.
            BasicBlock trueBlock = CreateBasicBlock();
            trueBlock.SetName("ttrue");
            BasicBlock falseBlock = CreateBasicBlock();
            falseBlock.SetName("tfalse");
            BasicBlock mergeBlock = CreateBasicBlock();
            mergeBlock.SetName("tmerge");

            // Check the condition.
            cond.Accept(this);
            if(condType != ChelaType.GetBoolType())
                Cast(node, cond.GetNodeValue(), condType, ChelaType.GetBoolType());

            // Perform branching.
            builder.CreateBr(trueBlock, falseBlock);

            // Send the "true" operand.
            builder.SetBlock(trueBlock);
            left.Accept(this);
            if(leftType != coercionType)
                Cast(node, left.GetNodeValue(), leftType, coercionType);

            builder.CreateJmp(mergeBlock); // merge.

            // Send the "false" operand
            builder.SetBlock(falseBlock);
            right.Accept(this);
            if(rightType != coercionType)
                Cast(node, right.GetNodeValue(), rightType, coercionType);

            builder.CreateJmp(mergeBlock); // merge.

            // Continue as normal.
            builder.SetBlock(mergeBlock);

            return builder.EndNode();
        }
Пример #3
0
        public override AstNode Visit(TernaryOperation node)
        {
            // Get the expressions.
            Expression cond = node.GetCondExpression();
            Expression left = node.GetLeftExpression();
            Expression right = node.GetRightExpression();

            // Visit the expressions.
            cond.Accept(this);
            left.Accept(this);
            right.Accept(this);

            // Check the types.
            IChelaType condType = cond.GetNodeType();
            IChelaType leftType = left.GetNodeType();
            IChelaType rightType = right.GetNodeType();

            // The condition must be bool.
            if(condType != ChelaType.GetBoolType() &&
               Coerce(condType, ChelaType.GetBoolType()) != ChelaType.GetBoolType())
                Error(node, "ternary operator condition must be a boolean expression.");

            // Perform coercion.
            IChelaType destType = Coerce(leftType, rightType);

            // Failed to perform ternary coercion.
            if(destType == null)
                Error(node, "failed to perform ternary operation.");

            // Set the node coercion type.
            node.SetCoercionType(destType);
            node.SetNodeType(destType);

            return node;
        }