//============================================================================//
// //
// artichoke programming language //
// //
// Copyright (C) 2025 Erick Saul Guzman Ramos, whoami.artichoke.dev //
// //
// //
// This program is free software: you can redistribute it and/or modify //
// it under the terms of the GNU Affero General Public License as published //
// by the Free Software Foundation, either version 3 of the License, or //
// (at your option) any later version. //
// //
// This program is distributed in the hope that it will be useful, //
// but WITHOUT ANY WARRANTY; without even the implied warranty of //
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the //
// GNU Affero General Public License for more details. //
// //
// You should have received a copy of the GNU Affero General Public License //
// along with this program. If not, see . //
// //
//============================================================================//
#include
namespace arti::lang::pratt {
std::uint16_t prefixBindingPower(ast::PrefixOperator op) {
switch (op) {
// Unary operators generally bind very tightly
case ast::PrefixOperator::Not:
case ast::PrefixOperator::Minus:
case ast::PrefixOperator::BitNot:
case ast::PrefixOperator::MemPtr:
case ast::PrefixOperator::DerefPtr:
return 17; // Should be higher than most infix but lower than postfix
default: return 0;
}
}
BindingPower infixBindingPower(ast::InfixOperator op) {
switch (op) {
// Member Access (Highest)
case ast::InfixOperator::ModuleAccess: return { 23, 24 };
case ast::InfixOperator::MemberAccess:
case ast::InfixOperator::PointerMemberAccess: return { 21, 22 };
// Multiplicative
case ast::InfixOperator::Multiplication:
case ast::InfixOperator::Division:
case ast::InfixOperator::Modulo: return { 15, 16 };
// Additive
case ast::InfixOperator::Addition:
case ast::InfixOperator::Substraction: return { 13, 14 };
// Shift
case ast::InfixOperator::LeftShift:
case ast::InfixOperator::RightShift: return { 11, 12 };
// Relational
case ast::InfixOperator::LessThan:
case ast::InfixOperator::GreaterThan:
case ast::InfixOperator::LessEqual:
case ast::InfixOperator::GreaterEqual: return { 9, 10 };
// Equality
case ast::InfixOperator::Equal:
case ast::InfixOperator::NotEqual: return { 7, 8 };
// Bitwise
case ast::InfixOperator::BitAnd: return { 6, 7 };
case ast::InfixOperator::BitXor: return { 5, 6 };
case ast::InfixOperator::BitOr: return { 4, 5 };
// Logical
case ast::InfixOperator::BoolAnd: return { 3, 4 };
case ast::InfixOperator::BoolOr: return { 1, 2 };
// Assignment (Right-associative: left > right)
case ast::InfixOperator::Assignment:
case ast::InfixOperator::AdditionAssignment:
case ast::InfixOperator::SubstractionAssignment:
case ast::InfixOperator::MultiplicationAssignment:
case ast::InfixOperator::DivisionAssignment:
case ast::InfixOperator::ModuloAssignment:
case ast::InfixOperator::BitAndAssignment:
case ast::InfixOperator::BitOrAssignment:
case ast::InfixOperator::BoolAndAssignment:
case ast::InfixOperator::BoolOrAssignment:
case ast::InfixOperator::LShiftAssignment:
case ast::InfixOperator::RShiftAssignment:
return { 2, 1 };
default:
return { 0, 0 };
}
}
std::uint16_t postfixBindingPower(ast::PostfixOperator op) {
switch (op) {
// Postfix usually has the highest precedence (e.g., function calls,
// slicing)
case ast::PostfixOperator::FunctionCall:
case ast::PostfixOperator::SliceAccess:
case ast::PostfixOperator::SliceSize:
case ast::PostfixOperator::PtrToSlice:
case ast::PostfixOperator::SliceToPtr:
case ast::PostfixOperator::Reflect:
case ast::PostfixOperator::ObjectLiteral:
return 19;
default:
return 0;
}
}
} // namespace arti::lang::pratt