Skip to main content

nom_kconfig/attribute/expression/
compare.rs

1use crate::attribute::Atom;
2use crate::attribute::{parse_function_call, FunctionCall};
3use crate::symbol::parse_symbol;
4use crate::util::wsi;
5use crate::{KconfigInput, Symbol};
6use nom::branch::alt;
7use nom::bytes::complete::tag;
8use nom::combinator::{map, value};
9use nom::{IResult, Parser};
10#[cfg(feature = "deserialize")]
11use serde::Deserialize;
12#[cfg(feature = "serialize")]
13use serde::Serialize;
14#[cfg(feature = "display")]
15use std::fmt::Display;
16
17#[derive(Debug, PartialEq, Clone)]
18#[cfg_attr(feature = "hash", derive(Hash))]
19#[cfg_attr(feature = "serialize", derive(Serialize))]
20#[cfg_attr(feature = "deserialize", derive(Deserialize))]
21pub enum CompareOperator {
22    GreaterThan,
23    GreaterOrEqual,
24    LowerThan,
25    LowerOrEqual,
26    Equal,
27    NotEqual,
28}
29
30#[derive(Debug, PartialEq, Clone)]
31#[cfg_attr(feature = "hash", derive(Hash))]
32#[cfg_attr(feature = "serialize", derive(Serialize))]
33#[cfg_attr(feature = "deserialize", derive(Deserialize))]
34#[cfg_attr(feature = "serialize", serde(rename = "Compare"))]
35pub struct CompareExpression {
36    pub left: CompareOperand,
37    pub operator: CompareOperator,
38    pub right: CompareOperand,
39}
40
41#[derive(Debug, PartialEq, Clone)]
42#[cfg_attr(feature = "hash", derive(Hash))]
43#[cfg_attr(feature = "serialize", derive(Serialize))]
44#[cfg_attr(feature = "deserialize", derive(Deserialize))]
45#[cfg_attr(feature = "serialize", serde(rename = "CompareOperand"))]
46pub enum CompareOperand {
47    Symbol(Symbol),
48    Macro(FunctionCall),
49}
50
51#[cfg(feature = "display")]
52impl Display for CompareOperand {
53    fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
54        match self {
55            CompareOperand::Symbol(symbol) => write!(f, "{}", symbol),
56            CompareOperand::Macro(function_call) => write!(f, "{}", function_call),
57        }
58    }
59}
60
61pub fn parse_compare_operand(input: KconfigInput) -> IResult<KconfigInput, CompareOperand> {
62    alt((
63        map(parse_function_call, CompareOperand::Macro),
64        map(parse_symbol, CompareOperand::Symbol),
65    ))
66    .parse(input)
67}
68
69#[cfg(feature = "display")]
70impl Display for CompareExpression {
71    fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
72        write!(f, "{} {} {}", self.left, self.operator, self.right)
73    }
74}
75
76#[cfg(feature = "display")]
77impl Display for CompareOperator {
78    fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
79        match self {
80            CompareOperator::GreaterThan => write!(f, ">"),
81            CompareOperator::GreaterOrEqual => write!(f, ">="),
82            CompareOperator::LowerThan => write!(f, "<"),
83            CompareOperator::LowerOrEqual => write!(f, "<="),
84            CompareOperator::Equal => write!(f, "="),
85            CompareOperator::NotEqual => write!(f, "!="),
86        }
87    }
88}
89
90pub fn parse_compare_operator(input: KconfigInput) -> IResult<KconfigInput, CompareOperator> {
91    alt((
92        value(CompareOperator::GreaterOrEqual, tag(">=")),
93        value(CompareOperator::LowerOrEqual, tag("<=")),
94        value(CompareOperator::GreaterThan, tag(">")),
95        value(CompareOperator::LowerThan, tag("<")),
96        value(CompareOperator::Equal, tag("=")),
97        value(CompareOperator::NotEqual, tag("!=")),
98    ))
99    .parse(input)
100}
101
102pub fn parse_compare(input: KconfigInput) -> IResult<KconfigInput, Atom> {
103    map(
104        (
105            wsi(parse_compare_operand),
106            wsi(parse_compare_operator),
107            wsi(parse_compare_operand),
108        ),
109        |(l, o, r)| {
110            Atom::Compare(CompareExpression {
111                left: l,
112                operator: o,
113                right: r,
114            })
115        },
116    )
117    .parse(input)
118}