//============================================================================// // // // 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