/// binoprhs /// ::= ('+' primary)* static ExprAST *ParseBinOpRHS(int ExprPrec, ExprAST *LHS) { // If this is a binop, find its precedence. while (1) { int TokPrec = GetTokPrecedence(); // If this is a binop that binds at least as tightly as the current binop, // consume it, otherwise we are done. if (TokPrec < ExprPrec) return LHS; // Okay, we know this is a binop. int BinOp = CurTok; getNextToken(); // eat binop // Parse the primary expression after the binary operator. ExprAST *RHS = ParsePrimary(); if (!RHS) return 0; // If BinOp binds less tightly with RHS than the operator after RHS, let // the pending operator take RHS as its LHS. int NextPrec = GetTokPrecedence(); if (TokPrec < NextPrec) { RHS = ParseBinOpRHS(TokPrec+1, RHS); if (RHS == 0) return 0; } // Merge LHS/RHS. LHS = new BinaryExprAST(BinOp, LHS, RHS); } }
/// binoprhs /// ::= ('+' primary)* static std::unique_ptr<ExprAST> ParseBinOpRHS(int ExprPrec, std::unique_ptr<ExprAST> LHS) { // If this is a binop, find its precedence. while (1) { int TokPrec = GetTokPrecedence(); // If this is a binop that binds at least as tightly as the current binop, // consume it, otherwise we are done. if (TokPrec < ExprPrec) return LHS; // Okay, we know this is a binop. int BinOp = CurTok; getNextToken(); // eat binop // Parse the primary expression after the binary operator. auto RHS = ParsePrimary(); if (!RHS) return nullptr; // If BinOp binds less tightly with RHS than the operator after RHS, let // the pending operator take RHS as its LHS. int NextPrec = GetTokPrecedence(); if (TokPrec < NextPrec) { RHS = ParseBinOpRHS(TokPrec + 1, std::move(RHS)); if (!RHS) return nullptr; } // Merge LHS/RHS. LHS = helper::make_unique<BinaryExprAST>(BinOp, std::move(LHS), std::move(RHS)); } }
/// binoprhs /// ::= ('+' primary)* std::unique_ptr<ExprAST> UDFParser::ParseBinOpRHS( int expr_prec, std::unique_ptr<ExprAST> lhs) { // If this is a binop, find its precedence. while (true) { int tok_prec = GetTokPrecedence(); // If this is a binop that binds at least as tightly as the current binop, // consume it, otherwise we are done. if (tok_prec < expr_prec) { return lhs; } // Okay, we know this is a binop. int bin_op = cur_tok_; GetNextToken(); // eat binop // Parse the primary expression after the binary operator. auto rhs = ParsePrimary(); if (!rhs) { return nullptr; } // If BinOp binds less tightly with rhs than the operator after rhs, let // the pending operator take rhs as its lhs. int next_prec = GetTokPrecedence(); if (tok_prec < next_prec) { rhs = ParseBinOpRHS(tok_prec + 1, std::move(rhs)); if (!rhs) { return nullptr; } } // Merge lhs/rhs. lhs = llvm::make_unique<BinaryExprAST>(bin_op, std::move(lhs), std::move(rhs)); } }
/* * Handle the rhs of a binary operation, where * binoprhs ::= (binop primary)* */ static std::unique_ptr<ExprAST> ParseBinOpRHS(int minExprPrec, std::unique_ptr<ExprAST> lhs) { while (1) { int tokPrec = GetTokPrecedence(); // token's precedence is too low to do anything with so we're done if (tokPrec < minExprPrec) { return lhs; } // otherwise, precedence it high enough so we should handle the binop int binOp = CurTok; getNextToken(); // advance past the binop // parse the primary expression after the operator auto rhs = ParsePrimary(); if (!rhs) { return nullptr; } // determine the direction of associativity int nextPrec = GetTokPrecedence(); if (tokPrec < nextPrec) { rhs = ParseBinOpRHS(tokPrec + 1, std::move(rhs)); if (!rhs) { return nullptr; } } // merge the lhs and rhs lhs = llvm::make_unique<BinaryExprAST>(binOp, std::move(lhs), std::move(rhs)); } }