semantic_analyzer/
semantic.rs

1//! # Semantic analyzer
2//! Semantic analyzer provides algorithms to analyze AST for different
3//! rules and generate `Semantic State stack` stack results. AST represent tree
4//! nodes of language constructions and fully cover all flow of the program
5//! represented through AST. And it's **Turing-complete**.
6//!
7//! ## Semantic State
8//! Semantic State contains basic entities:
9//! - `Global State` - global state of semantic analyzer results.
10//! - `Context` - stack for `Block state` of each functions body state.
11//! - `Errors` - semantic analyzes errors.z
12
13use crate::ast::{self, CodeLocation, GetLocation, GetName, MAX_PRIORITY_LEVEL_FOR_EXPRESSIONS};
14use crate::types::block_state::BlockState;
15use crate::types::expression::{
16    Expression, ExpressionResult, ExpressionResultValue, ExpressionStructValue,
17};
18use crate::types::semantic::{
19    ExtendedExpression, GlobalSemanticContext, SemanticContext, SemanticContextInstruction,
20    SemanticStack,
21};
22use crate::types::types::{Type, TypeName};
23use crate::types::{
24    error, Binding, Constant, ConstantName, Function, FunctionCall, FunctionName,
25    FunctionParameter, FunctionStatement, InnerValueName, LabelName, LetBinding, Value,
26};
27#[cfg(feature = "codec")]
28use serde::{Deserialize, Serialize};
29use std::cell::RefCell;
30use std::collections::HashMap;
31use std::marker::PhantomData;
32use std::rc::Rc;
33
34/// # Global State
35/// Global state can contains state declarations of:
36/// - Constants
37/// - Types
38/// - Functions
39/// And Semantic State context results for Global State context:
40/// - Context
41/// The visibility of Global state limited by current module.
42/// `Context` contains results of `Semantic` stack, as result of
43/// Semantic analyzer for Global State context. It's can be used for
44/// post-verification process, linting, Codegen.
45#[derive(Debug)]
46#[cfg_attr(feature = "codec", derive(Serialize, Deserialize))]
47pub struct GlobalState<I: SemanticContextInstruction> {
48    /// Constants declarations
49    pub constants: HashMap<ConstantName, Constant>,
50    /// Types declarations
51    pub types: HashMap<TypeName, Type>,
52    /// Functions declarations
53    pub functions: HashMap<FunctionName, Function>,
54    /// Context as Semantic Stack Context results contains basic semantic
55    /// result tree for Global context state.
56    pub context: SemanticStack<I>,
57}
58
59/// # State
60/// Basic entity that contains:
61/// - `Global State` - types, constants, functions declaration and
62///   most important - context results of Semantic State stack, that can be
63///   used for post-verification and/or Codegen.
64/// - `Context` stack for `Block state` of each functions body state
65/// - `Error State` contains errors stack as result of Semantic analyzer
66#[derive(Debug)]
67#[cfg_attr(feature = "codec", derive(Serialize))]
68pub struct State<E, I>
69where
70    E: ExtendedExpression<I>,
71    I: SemanticContextInstruction,
72{
73    /// Global State for current State
74    pub global: GlobalState<I>,
75    /// Context for all `Block State` stack that related to concrete functions body.
76    #[cfg_attr(feature = "codec", serde(skip))]
77    pub context: Vec<Rc<RefCell<BlockState<I>>>>,
78    /// Error state results stack
79    pub errors: Vec<error::StateErrorResult>,
80    phantom: PhantomData<E>,
81}
82
83impl<E, I> Default for State<E, I>
84where
85    E: ExtendedExpression<I>,
86    I: SemanticContextInstruction,
87{
88    fn default() -> Self {
89        Self::new()
90    }
91}
92
93impl<E, I> State<E, I>
94where
95    E: ExtendedExpression<I>,
96    I: SemanticContextInstruction,
97{
98    /// Init new `State`
99    #[must_use]
100    pub fn new() -> Self {
101        Self {
102            global: GlobalState {
103                functions: HashMap::new(),
104                types: HashMap::new(),
105                constants: HashMap::new(),
106                context: SemanticStack::new(),
107            },
108            context: Vec::new(),
109            errors: Vec::new(),
110            phantom: PhantomData,
111        }
112    }
113
114    /// Add error to Semantic `Errors State`
115    fn add_error(&mut self, err: error::StateErrorResult) {
116        self.errors.push(err);
117    }
118
119    /// Add `State context` with body state context block
120    fn add_state_context(&mut self, state_body: Rc<RefCell<BlockState<I>>>) {
121        self.context.push(state_body);
122    }
123
124    /// Check is value type exists in `Global State`.
125    /// `Primitive` type always return true. For other cases if type doesn't
126    /// exist in `Global State`, add errors to `Error State` and return `false` result.
127    fn check_type_exists(
128        &mut self,
129        type_name: &Type,
130        val_name: &impl ToString,
131        location: &impl GetLocation,
132    ) -> bool {
133        if let Type::Primitive(_) = type_name {
134            return true;
135        }
136        if !self.global.types.contains_key(&type_name.name()) {
137            self.add_error(error::StateErrorResult::new(
138                error::StateErrorKind::TypeNotFound,
139                val_name.to_string(),
140                location.location(),
141            ));
142            return false;
143        }
144        true
145    }
146
147    /// Run semantic analyzer that covers all flow for AST.
148    /// It's do not return any results, but fill results fir the `Semantic State`.
149    ///
150    pub fn run(&mut self, data: &ast::Main<'_, I, E>) {
151        // Execute each kind of analyzing and return errors data.
152        // For functions - fetch only declaration for fast-forward
153        // identification for using it in functions body.
154
155        // First pass is Imports and Types
156        for main in data {
157            match main {
158                ast::MainStatement::Import(import) => self.import(import),
159                ast::MainStatement::Types(types) => self.types(types),
160                _ => (),
161            }
162        }
163        // Declaration pass for Constants and Functions
164        for main in data {
165            match main {
166                ast::MainStatement::Constant(constant) => self.constant(constant),
167                ast::MainStatement::Function(function) => self.function_declaration(function),
168                _ => (),
169            }
170        }
171
172        // After getting all functions declarations, fetch only functions body
173        for main in data {
174            if let ast::MainStatement::Function(function) = main {
175                self.function_body(function);
176            }
177        }
178    }
179
180    /// Import analyzer (TBD)
181    #[allow(clippy::unused_self, clippy::unnecessary_wraps)]
182    pub fn import(&self, data: &ast::ImportPath<'_>) {
183        if !data.is_empty() {
184            let _name = data[0].name();
185        }
186    }
187
188    /// Types declaration analyzer. Add types to `Global State`.
189    /// Currently only one type kind: Structs. And types can't be part of
190    /// the `Block State`.
191    pub fn types(&mut self, data: &ast::StructTypes<'_>) {
192        if self.global.types.contains_key(&data.name().into()) {
193            self.add_error(error::StateErrorResult::new(
194                error::StateErrorKind::TypeAlreadyExist,
195                data.name(),
196                data.location(),
197            ));
198            return;
199        }
200        let struct_type = Type::Struct(data.clone().into());
201        self.global.types.insert(struct_type.name(), struct_type);
202        self.global.context.types(data.clone().into());
203    }
204
205    /// Check constant value expression.
206    /// If expression contains `Constant` check is constant exists.
207    /// Values doesn't check as it's just `Primitive Values`.
208    /// Also check all expression tree branches.
209    /// If `ConstantValue` doesn't exist add error to `Error State` and `return` false result.
210    pub fn check_constant_value_expression(
211        &mut self,
212        data: &Option<(ast::ExpressionOperations, Box<ast::ConstantExpression<'_>>)>,
213    ) -> bool {
214        // For constant expression skip ExpressionOperations
215        if let Some((_, child_data)) = data {
216            // Check only Constant value
217            match child_data.value.clone() {
218                // Check is ConstantValue already exist in global state
219                ast::ConstantValue::Constant(const_name) => {
220                    if !self
221                        .global
222                        .constants
223                        .contains_key(&const_name.clone().into())
224                    {
225                        self.add_error(error::StateErrorResult::new(
226                            error::StateErrorKind::ConstantNotFound,
227                            const_name.name(),
228                            const_name.location(),
229                        ));
230                        return false;
231                    }
232                    self.check_constant_value_expression(&child_data.operation)
233                }
234                ast::ConstantValue::Value(_) => true,
235            }
236        } else {
237            true
238        }
239    }
240
241    /// Constant analyzer. Add it to `Global State`, because constants
242    /// can be only global for `Semantic state`, not for `Block state`.
243    pub fn constant(&mut self, data: &ast::Constant<'_>) {
244        if self.global.constants.contains_key(&data.name().into()) {
245            self.add_error(error::StateErrorResult::new(
246                error::StateErrorKind::ConstantAlreadyExist,
247                data.name(),
248                data.location(),
249            ));
250            return;
251        }
252        if !self.check_constant_value_expression(&data.constant_value.operation) {
253            return;
254        }
255        let const_val: Constant = data.clone().into();
256        if !self.check_type_exists(&const_val.constant_type, &const_val.name, data) {
257            return;
258        }
259        self.global
260            .constants
261            .insert(const_val.name.clone(), const_val.clone());
262        self.global.context.constant(const_val);
263    }
264
265    /// Function declaration analyze. Add it to Global State/M
266    pub fn function_declaration(&mut self, data: &ast::FunctionStatement<'_, I, E>) {
267        if self.global.functions.contains_key(&data.name().into()) {
268            self.add_error(error::StateErrorResult::new(
269                error::StateErrorKind::FunctionAlreadyExist,
270                data.name(),
271                data.location(),
272            ));
273            return;
274        }
275        let func_decl: FunctionStatement = data.clone().into();
276        let mut force_quite =
277            !self.check_type_exists(&func_decl.result_type, &func_decl.name, data);
278
279        // Fetch parameters and check types
280        let parameters = func_decl
281            .parameters
282            .iter()
283            .map(|p| {
284                force_quite = force_quite || !self.check_type_exists(&p.parameter_type, p, data);
285                p.parameter_type.clone()
286            })
287            .collect();
288        // Force quite if errors
289        if force_quite {
290            return;
291        }
292        self.global.functions.insert(
293            data.name().into(),
294            Function {
295                inner_name: func_decl.name,
296                inner_type: func_decl.result_type,
297                parameters,
298            },
299        );
300        self.global
301            .context
302            .function_declaration(data.clone().into());
303    }
304
305    /// Init function parameters.
306    /// It's init function parameters as values, same as let-binding.
307    /// And add instructions to `SemanticStack`.
308    fn init_func_params(
309        &mut self,
310        function_state: &Rc<RefCell<BlockState<I>>>,
311        fn_params: &Vec<ast::FunctionParameter<'_>>,
312    ) {
313        for fn_param in fn_params {
314            let func_param: FunctionParameter = fn_param.clone().into();
315            let arg_name = func_param.clone().to_string();
316
317            // Find value in current state and parent states
318            let value = function_state
319                .borrow()
320                .get_value_name(&arg_name.clone().into());
321            // Calculate `inner_name` as unique for current and all parent states
322            let inner_name: InnerValueName = if value.is_none() {
323                // if value not found in all states check and set
324                // `inner_value` from value name
325                // NOTE: value number not incremented
326                arg_name.clone().into()
327            } else {
328                // Function parameter name can't be with the same name.
329                // Produce error
330                self.add_error(error::StateErrorResult::new(
331                    error::StateErrorKind::FunctionArgumentNameDuplicated,
332                    arg_name,
333                    CodeLocation::new(1, 1),
334                ));
335                return;
336            };
337            // Set value parameters
338            let value = Value {
339                inner_name: inner_name.clone(),
340                inner_type: func_param.parameter_type.clone(),
341                mutable: false,
342                alloca: false,
343                malloc: false,
344            };
345            // Value inserted only to current state by Value name and Value data
346            function_state
347                .borrow_mut()
348                .values
349                .insert(arg_name.into(), value.clone());
350            // Set `inner_name` to current state and all parent states
351            function_state
352                .borrow_mut()
353                .set_inner_value_name(&inner_name);
354
355            function_state.borrow_mut().function_arg(value, func_param);
356        }
357    }
358
359    /// Function body analyze.
360    /// It is basic execution entity for program flow.
361    /// It's operate sub analyze for function elements. It's contain
362    /// Body State for current and child states.
363    pub fn function_body(&mut self, data: &ast::FunctionStatement<'_, I, E>) {
364        // Init empty function body state
365        let body_state = Rc::new(RefCell::new(BlockState::new(None)));
366        self.add_state_context(body_state.clone());
367        // Init function parameters - add to SemanticStackContext
368        self.init_func_params(&body_state, &data.parameters);
369        // Flag to indicate is function return called
370        let mut return_is_called = false;
371        // Fetch function elements and gather errors
372        for body in &data.body {
373            if return_is_called {
374                self.add_error(error::StateErrorResult::new(
375                    error::StateErrorKind::ForbiddenCodeAfterReturnDeprecated,
376                    format!("{body:?}"),
377                    CodeLocation::new(1, 1),
378                ));
379            }
380            match body {
381                ast::BodyStatement::LetBinding(bind) => {
382                    self.let_binding(bind, &body_state);
383                }
384                ast::BodyStatement::Binding(bind) => {
385                    self.binding(bind, &body_state);
386                }
387                ast::BodyStatement::FunctionCall(fn_call) => {
388                    self.function_call(fn_call, &body_state);
389                }
390                ast::BodyStatement::If(if_condition) => {
391                    self.if_condition(if_condition, &body_state, &None, None);
392                }
393                ast::BodyStatement::Loop(loop_statement) => {
394                    self.loop_statement(loop_statement, &body_state);
395                }
396                ast::BodyStatement::Expression(expression)
397                | ast::BodyStatement::Return(expression) => {
398                    let expr_result = self.expression(expression, &body_state);
399                    let expr: Expression = expression.clone().into();
400                    // Check is return statement previously called
401                    if return_is_called {
402                        self.add_error(error::StateErrorResult::new(
403                            error::StateErrorKind::ReturnAlreadyCalled,
404                            expr.to_string(),
405                            expression.location(),
406                        ));
407                    }
408                    if let Some(res) = expr_result {
409                        // Check expression type and do not exist from flow
410                        self.check_type_exists(&res.expr_type, &expr, expression);
411                        let fn_ty: Type = data.result_type.clone().into();
412                        if fn_ty != res.expr_type {
413                            self.add_error(error::StateErrorResult::new(
414                                error::StateErrorKind::WrongReturnType,
415                                expr.to_string(),
416                                expression.location(),
417                            ));
418                        }
419
420                        return_is_called = true;
421                        // Check is state contain flag of manual
422                        // return from other states, for example:
423                        // if-flow, loop-flow
424                        if body_state.borrow().manual_return {
425                            // First we put expression return calculation for case when
426                            // before in the state was return statement. So construct
427                            // return expression and jump to return label, set return
428                            // label and invoke after that read `return` value from all
429                            // previous returns and invoke return instruction itself.
430                            body_state
431                                .borrow_mut()
432                                .expression_function_return_with_label(res);
433                        } else {
434                            body_state.borrow_mut().expression_function_return(res);
435                        }
436                    }
437                }
438            }
439        }
440        // Check is function contain return
441        if !return_is_called {
442            self.add_error(error::StateErrorResult::new(
443                error::StateErrorKind::ReturnNotFound,
444                String::new(),
445                data.location(),
446            ));
447        }
448    }
449
450    /// # Let-binding statement
451    /// Analyze let-binding statement:
452    /// 1. Let value bind from expression. First should be analysed
453    ///    `expression` for binding value.
454    /// 2. Generate value for current state. Special field `inner_name`
455    ///    that used as name for `Codegen` should be unique in current
456    ///    state and for all parent states. For that `inner_name` the
457    ///    inner value name counter incremented.
458    /// 3. Set `Value` parameters: `inner_name`,  type and allocation status
459    /// 4. Insert value to current values state map: value `name` -> `Data`
460    /// 5. Store `inner_name` in current and parent states
461    /// 6. Codegen
462    pub fn let_binding(
463        &mut self,
464        data: &ast::LetBinding<'_, I, E>,
465        function_state: &Rc<RefCell<BlockState<I>>>,
466    ) {
467        // Call value analytics before putting let-value to state
468        let Some(expr_result) = self.expression(&data.value, function_state) else {
469            return;
470        };
471        let let_data: LetBinding = data.clone().into();
472
473        if let Some(ty) = &let_data.value_type {
474            if &expr_result.expr_type != ty {
475                self.add_error(error::StateErrorResult::new(
476                    error::StateErrorKind::WrongLetType,
477                    let_data.to_string(),
478                    data.location(),
479                ));
480                return;
481            }
482        }
483        let let_ty = expr_result.expr_type.clone();
484
485        // Find value in current state and parent states
486        let value = function_state.borrow().get_value_name(&let_data.name);
487        // Calculate `inner_name` as unique for current and all parent states
488        let inner_name = value.map_or_else(
489            || {
490                // if value not found in all states check and set
491                // `inner_value` from value name
492                function_state
493                    .borrow()
494                    .get_next_inner_name(&let_data.name.clone().into())
495            },
496            |val| {
497                // Increment inner value name counter for shadowed variable
498                // and check variable inner_name for and inner_values in current state
499                function_state.borrow().get_next_inner_name(&val.inner_name)
500            },
501        );
502        // Set value parameters
503        let value = Value {
504            inner_name: inner_name.clone(),
505            inner_type: let_ty,
506            mutable: let_data.mutable,
507            alloca: false,
508            malloc: false,
509        };
510        // Value inserted only to current state by Value name and Value data
511        function_state
512            .borrow_mut()
513            .values
514            .insert(let_data.name, value.clone());
515        // Set `inner_name` to current state and all parent states
516        function_state
517            .borrow_mut()
518            .set_inner_value_name(&inner_name);
519
520        function_state.borrow_mut().let_binding(value, expr_result);
521    }
522
523    /// # Binding statement
524    /// Analyze binding statement for mutable variables:
525    /// 1. Bind from expression. First should be analysed
526    ///    `expression` for binding value.
527    /// 2. Read value for current state.
528    /// 3. Update value to current values state map: value `name` -> `Data`
529    /// 4. Codegen with Store action
530    pub fn binding(
531        &mut self,
532        data: &ast::Binding<'_, I, E>,
533        function_state: &Rc<RefCell<BlockState<I>>>,
534    ) {
535        // Call value analytics before putting let-value to state
536        let Some(expr_result) = self.expression(&data.value, function_state) else {
537            return;
538        };
539        let bind_data: Binding = data.clone().into();
540
541        // Find value in current state and parent states
542        let Some(value) = function_state.borrow().get_value_name(&bind_data.name) else {
543            self.add_error(error::StateErrorResult::new(
544                error::StateErrorKind::ValueNotFound,
545                bind_data.to_string(),
546                data.location(),
547            ));
548            return;
549        };
550        // Check is value mutable
551        if !value.mutable {
552            self.add_error(error::StateErrorResult::new(
553                error::StateErrorKind::ValueIsNotMutable,
554                bind_data.to_string(),
555                data.location(),
556            ));
557            return;
558        }
559        function_state.borrow_mut().binding(value, expr_result);
560    }
561
562    /// # Function-call
563    /// Call function with function parameters arguments. Arguments is
564    /// expressions.
565    /// 1. Check is current function name exists in global state of functions
566    /// name.
567    /// 2. Analyse expressions for function parameters
568    /// 3. Inc register
569    /// 4. Generate codegen
570    /// Codegen store always result to register even for void result.
571    ///
572    /// ## Errors
573    /// Return error if function name doesn't exist in global state
574    pub fn function_call(
575        &mut self,
576        data: &ast::FunctionCall<'_, I, E>,
577        body_state: &Rc<RefCell<BlockState<I>>>,
578    ) -> Option<Type> {
579        let func_call_data: FunctionCall = data.clone().into();
580        // Check is function exists in global functions stat
581        let Some(func_data) = self.global.functions.get(&func_call_data.name).cloned() else {
582            self.add_error(error::StateErrorResult::new(
583                error::StateErrorKind::FunctionNotFound,
584                func_call_data.to_string(),
585                data.location(),
586            ));
587            return None;
588        };
589        let fn_type = func_data.inner_type.clone();
590
591        // Analyse function parameters expressions, check their types
592        // and set result to array
593        let mut params: Vec<ExpressionResult> = vec![];
594        for (i, expr) in data.parameters.iter().enumerate() {
595            // Types checked in expression, so we don't need additional check
596            let expr_result = self.expression(expr, body_state)?;
597            if expr_result.expr_type != func_data.parameters[i] {
598                self.add_error(error::StateErrorResult::new(
599                    error::StateErrorKind::FunctionParameterTypeWrong,
600                    expr_result.expr_type.to_string(),
601                    data.location(),
602                ));
603                continue;
604            }
605            params.push(expr_result);
606        }
607
608        // Result of function call is stored to register
609        body_state.borrow_mut().inc_register();
610        let last_register_number = body_state.borrow().last_register_number;
611        // Store always result to register even for void result
612        body_state
613            .borrow_mut()
614            .call(func_data, params, last_register_number);
615        Some(fn_type)
616    }
617
618    /// # condition-expression
619    /// Analyse condition operations.
620    /// ## Return
621    /// Return result register of `condition-expression` calculation.
622    pub fn condition_expression(
623        &mut self,
624        data: &ast::ExpressionLogicCondition<'_, I, E>,
625        function_body_state: &Rc<RefCell<BlockState<I>>>,
626    ) -> u64 {
627        // Analyse left expression of left condition
628        let left_expr = &data.left.left;
629        let left_res = self.expression(left_expr, function_body_state);
630
631        // Analyse right expression of left condition
632        let right_expr = &data.left.right;
633        let right_res = self.expression(right_expr, function_body_state);
634
635        // If some of the `left` or `right` expression is empty just return with error in the state
636        let (Some(left_res), Some(right_res)) = (left_res.clone(), right_res.clone()) else {
637            self.add_error(error::StateErrorResult::new(
638                error::StateErrorKind::ConditionIsEmpty,
639                format!("left={left_res:?}, right={right_res:?}"),
640                data.left.left.location(),
641            ));
642            return function_body_state.borrow().last_register_number;
643        };
644
645        // Currently strict type comparison
646        if left_res.expr_type != right_res.expr_type {
647            self.add_error(error::StateErrorResult::new(
648                error::StateErrorKind::ConditionExpressionWrongType,
649                left_res.expr_type.to_string(),
650                data.left.left.location(),
651            ));
652            return function_body_state.borrow().last_register_number;
653        }
654        if let Type::Primitive(_) = left_res.expr_type {
655        } else {
656            self.add_error(error::StateErrorResult::new(
657                error::StateErrorKind::ConditionExpressionNotSupported,
658                left_res.expr_type.to_string(),
659                data.left.left.location(),
660            ));
661            return function_body_state.borrow().last_register_number;
662        }
663
664        // Increment register
665        function_body_state.borrow_mut().inc_register();
666
667        let register_number = function_body_state.borrow_mut().last_register_number;
668        // Codegen for left condition and set result to register
669        function_body_state.borrow_mut().condition_expression(
670            left_res,
671            right_res,
672            data.left.condition.clone().into(),
673            register_number,
674        );
675
676        // Analyze right condition
677        if let Some(right) = &data.right {
678            let left_register_result = function_body_state.borrow_mut().last_register_number;
679            // Analyse recursively right part of condition
680            let right_register_result = self.condition_expression(&right.1, function_body_state);
681
682            // Increment register
683            function_body_state.borrow_mut().inc_register();
684
685            let register_number = function_body_state.borrow_mut().last_register_number;
686            // Stategen for logical condition for: left [LOGIC-OP] right
687            // The result generated from registers, and stored to
688            // new register
689            function_body_state.borrow_mut().logic_condition(
690                right.0.clone().into(),
691                left_register_result,
692                right_register_result,
693                register_number,
694            );
695        }
696        function_body_state.borrow_mut().last_register_number
697    }
698
699    /// # If-condition body
700    /// Analyze body for ant if condition:
701    /// - if, else, if-else
702    /// NOTE: `label_end` - is always already exists
703    /// ## Return
704    /// Return body statement "return" status
705    pub fn if_condition_body(
706        &mut self,
707        body: &[ast::IfBodyStatement<'_, I, E>],
708        if_body_state: &Rc<RefCell<BlockState<I>>>,
709        label_end: &LabelName,
710        label_loop: Option<(&LabelName, &LabelName)>,
711    ) -> bool {
712        let mut return_is_called = false;
713        for body in body {
714            if return_is_called {
715                self.add_error(error::StateErrorResult::new(
716                    error::StateErrorKind::ForbiddenCodeAfterReturnDeprecated,
717                    format!("{body:?}"),
718                    CodeLocation::new(1, 1),
719                ));
720            }
721            match body {
722                ast::IfBodyStatement::LetBinding(bind) => {
723                    self.let_binding(bind, if_body_state);
724                }
725                ast::IfBodyStatement::Binding(bind) => {
726                    self.binding(bind, if_body_state);
727                }
728                ast::IfBodyStatement::FunctionCall(fn_call) => {
729                    self.function_call(fn_call, if_body_state);
730                }
731                ast::IfBodyStatement::If(if_condition) => {
732                    self.if_condition(
733                        if_condition,
734                        if_body_state,
735                        &Some(label_end.clone()),
736                        label_loop,
737                    );
738                }
739                ast::IfBodyStatement::Loop(loop_statement) => {
740                    self.loop_statement(loop_statement, if_body_state);
741                }
742                ast::IfBodyStatement::Return(expression) => {
743                    let expr_result = self.expression(expression, if_body_state);
744                    if let Some(res) = expr_result {
745                        // Jump to return label in codegen and set return
746                        // status to indicate function, that it's manual
747                        // return
748                        if_body_state.borrow_mut().jump_function_return(res);
749                        if_body_state.borrow_mut().set_return();
750                        return_is_called = true;
751                    }
752                }
753            }
754        }
755        return_is_called
756    }
757
758    /// # If-condition loop body
759    /// Analyze body for ant if condition:
760    /// - if, else, if-else
761    /// ## Return
762    /// Return body statement "return" status
763    pub fn if_condition_loop_body(
764        &mut self,
765        body: &[ast::IfLoopBodyStatement<'_, I, E>],
766        if_body_state: &Rc<RefCell<BlockState<I>>>,
767        label_if_end: &LabelName,
768        label_loop_start: &LabelName,
769        label_loop_end: &LabelName,
770    ) -> bool {
771        let mut return_is_called = false;
772        let mut break_is_called = false;
773        let mut continue_is_called = false;
774        for body in body {
775            if return_is_called {
776                self.add_error(error::StateErrorResult::new(
777                    error::StateErrorKind::ForbiddenCodeAfterReturnDeprecated,
778                    format!("{body:?}"),
779                    CodeLocation::new(1, 1),
780                ));
781            }
782            if break_is_called {
783                self.add_error(error::StateErrorResult::new(
784                    error::StateErrorKind::ForbiddenCodeAfterBreakDeprecated,
785                    format!("{body:?}"),
786                    CodeLocation::new(1, 1),
787                ));
788            }
789            if continue_is_called {
790                self.add_error(error::StateErrorResult::new(
791                    error::StateErrorKind::ForbiddenCodeAfterContinueDeprecated,
792                    format!("{body:?}"),
793                    CodeLocation::new(1, 1),
794                ));
795            }
796
797            match body {
798                ast::IfLoopBodyStatement::LetBinding(bind) => {
799                    self.let_binding(bind, if_body_state);
800                }
801                ast::IfLoopBodyStatement::Binding(bind) => {
802                    self.binding(bind, if_body_state);
803                }
804                ast::IfLoopBodyStatement::FunctionCall(fn_call) => {
805                    self.function_call(fn_call, if_body_state);
806                }
807                ast::IfLoopBodyStatement::If(if_condition) => {
808                    self.if_condition(
809                        if_condition,
810                        if_body_state,
811                        &Some(label_if_end.clone()),
812                        Some((label_loop_start, label_loop_end)),
813                    );
814                }
815                ast::IfLoopBodyStatement::Loop(loop_statement) => {
816                    self.loop_statement(loop_statement, if_body_state);
817                }
818                ast::IfLoopBodyStatement::Return(expression) => {
819                    let expr_result = self.expression(expression, if_body_state);
820                    if let Some(res) = expr_result {
821                        // Jump to return label in codegen and set return
822                        // status to indicate function, that it's manual
823                        // return
824                        if_body_state.borrow_mut().jump_function_return(res);
825                        if_body_state.borrow_mut().set_return();
826                        return_is_called = true;
827                    }
828                }
829                ast::IfLoopBodyStatement::Continue => {
830                    continue_is_called = true;
831                    // Skip next loop  step and jump to the start
832                    // of loop
833                    if_body_state.borrow_mut().jump_to(label_loop_start.clone());
834                }
835                ast::IfLoopBodyStatement::Break => {
836                    break_is_called = true;
837                    // Break loop and jump to the end of loop
838                    if_body_state.borrow_mut().jump_to(label_loop_end.clone());
839                }
840            }
841        }
842        return_is_called
843    }
844
845    /// # If conditions calculations
846    /// Calculate conditions for if-condition. It can contain
847    /// simple and logic conditions.
848    pub fn if_condition_calculation(
849        &mut self,
850        condition: &ast::IfCondition<'_, I, E>,
851        if_body_state: &Rc<RefCell<BlockState<I>>>,
852        label_if_begin: &LabelName,
853        label_if_else: &LabelName,
854        label_if_end: &LabelName,
855        is_else: bool,
856    ) {
857        // Analyse if-conditions
858        match condition {
859            // if condition represented just as expression
860            ast::IfCondition::Single(expr) => {
861                // Calculate expression for single if-condition expression
862                let Some(expr_result) = self.expression(expr, if_body_state) else {
863                    return;
864                };
865
866                // State for if-condition from expression and if-body start
867                if is_else {
868                    if_body_state.borrow_mut().if_condition_expression(
869                        expr_result,
870                        label_if_begin.clone(),
871                        label_if_else.clone(),
872                    );
873                } else {
874                    if_body_state.borrow_mut().if_condition_expression(
875                        expr_result,
876                        label_if_begin.clone(),
877                        label_if_end.clone(),
878                    );
879                }
880            }
881            // If condition contains logic condition expression
882            ast::IfCondition::Logic(expr_logic) => {
883                // Analyse if-condition logic
884                let result_register = self.condition_expression(expr_logic, if_body_state);
885                // State for if-condition-logic with if-body start
886                if is_else {
887                    if_body_state.borrow_mut().if_condition_logic(
888                        label_if_begin.clone(),
889                        label_if_else.clone(),
890                        result_register,
891                    );
892                } else {
893                    if_body_state.borrow_mut().if_condition_logic(
894                        label_if_begin.clone(),
895                        label_if_end.clone(),
896                        result_register,
897                    );
898                }
899            }
900        }
901    }
902
903    /// # If-condition
904    /// Analyzing includes all variants for if statements:
905    /// 1. if
906    /// 2. if-else
907    /// 3. if-else-if
908    /// It creates own state, with parent function-state. in that case
909    /// if-state independent from parent state, but csn get access to
910    /// parent state.
911    /// If condition can't contain `else` and `if-else` on the
912    /// same time.
913    ///
914    /// Special case for `label_end` - it should be set from previous
915    /// context, and main goal is to end all of if-condition nodes in
916    /// the same flow with same `if-end` label. It's especially important
917    /// for `else-if` condition.
918    ///
919    /// ## Panics
920    /// `label_loop` is must be set, it's special case for the Loop,
921    /// when `label_loop` should always be set. If it doesn't set, it's
922    /// unexpected behavior and program algorithm error
923    pub fn if_condition(
924        &mut self,
925        data: &ast::IfStatement<'_, I, E>,
926        function_body_state: &Rc<RefCell<BlockState<I>>>,
927        label_end: &Option<LabelName>,
928        label_loop: Option<(&LabelName, &LabelName)>,
929    ) {
930        // It can't contain `else` and `if-else` on the same time
931        if let (Some(_), Some(stm)) = (&data.else_statement, &data.else_if_statement) {
932            self.add_error(error::StateErrorResult::new(
933                error::StateErrorKind::IfElseDuplicated,
934                String::from("if-condition"),
935                stm.location(),
936            ));
937        }
938        // Create state for if-body, from parent function state because
939        // if-state can contain sub-state, that can be independent from parent
940        // state
941        let if_body_state = Rc::new(RefCell::new(BlockState::new(Some(
942            function_body_state.clone(),
943        ))));
944        function_body_state
945            .borrow_mut()
946            .set_child(if_body_state.clone());
947        // Get labels name for if-begin, and if-end
948        let label_if_begin = if_body_state
949            .borrow_mut()
950            .get_and_set_next_label(&"if_begin".to_string().into());
951        let label_if_else = if_body_state
952            .borrow_mut()
953            .get_and_set_next_label(&"if_else".to_string().into());
954        // Set if-end label from previous context
955        let label_if_end = label_end.clone().map_or_else(
956            || {
957                if_body_state
958                    .borrow_mut()
959                    .get_and_set_next_label(&"if_end".to_string().into())
960            },
961            |label| label,
962        );
963        // To set if-end as single return point check is it previously set
964        let is_set_label_if_end = label_end.is_some();
965        let is_else = data.else_statement.is_some() || data.else_if_statement.is_some();
966
967        // Analyse if-conditions
968        self.if_condition_calculation(
969            &data.condition,
970            &if_body_state,
971            &label_if_begin,
972            &label_if_else,
973            &label_if_end,
974            is_else,
975        );
976
977        //== If condition main body
978        // Set if-begin label
979        if_body_state.borrow_mut().set_label(label_if_begin);
980        // Analyze if-conditions body kind.
981        // Return flag for current body state, excluding children return claims
982        let return_is_called = match &data.body {
983            ast::IfBodyStatements::If(body) => {
984                // Analyze if-statement body
985                self.if_condition_body(body, &if_body_state, &label_if_end, label_loop)
986            }
987            ast::IfBodyStatements::Loop(body) => {
988                // It's special case for the Loop, when `label_loop` should always be set.
989                // If it doesn't set, it's unexpected behavior and program algorithm error
990                let (label_loop_start, label_loop_end) =
991                    label_loop.expect("loop label should be set");
992                // Analyze if-loop-statement body
993                self.if_condition_loop_body(
994                    body,
995                    &if_body_state,
996                    &label_if_end,
997                    label_loop_start,
998                    label_loop_end,
999                )
1000            }
1001        };
1002        // Codegen for jump to if-end statement - return to program flow.
1003        // If return is set do not add jump-to-end label.
1004        if !return_is_called {
1005            if_body_state.borrow_mut().jump_to(label_if_end.clone());
1006        }
1007
1008        // Check else statements: else, else-if
1009        if is_else {
1010            // Set if-else label
1011            if_body_state.borrow_mut().set_label(label_if_else);
1012
1013            // Analyse if-else body: data.else_statement
1014            if let Some(else_body) = &data.else_statement {
1015                // if-else has own state, different from if-state
1016                let if_else_body_state = Rc::new(RefCell::new(BlockState::new(Some(
1017                    function_body_state.clone(),
1018                ))));
1019                function_body_state
1020                    .borrow_mut()
1021                    .set_child(if_else_body_state.clone());
1022
1023                let return_is_called = match else_body {
1024                    ast::IfBodyStatements::If(body) => {
1025                        // Analyze if-statement body
1026                        self.if_condition_body(body, &if_else_body_state, &label_if_end, label_loop)
1027                    }
1028                    ast::IfBodyStatements::Loop(body) => {
1029                        let (label_loop_start, label_loop_end) =
1030                            label_loop.expect("label should be set");
1031                        // Analyze if-loop-statement body
1032                        self.if_condition_loop_body(
1033                            body,
1034                            &if_else_body_state,
1035                            &label_if_end,
1036                            label_loop_start,
1037                            label_loop_end,
1038                        )
1039                    }
1040                };
1041
1042                // Codegen for jump to if-end statement -return to program flow
1043                // If return is set do not add jump-to-end label.
1044                if !return_is_called {
1045                    if_body_state.borrow_mut().jump_to(label_if_end.clone());
1046                }
1047            } else if let Some(else_if_statement) = &data.else_if_statement {
1048                // Analyse  else-if statement
1049                // Set `label_if_end` to indicate single if-end point
1050                self.if_condition(
1051                    else_if_statement,
1052                    function_body_state,
1053                    &Some(label_if_end.clone()),
1054                    label_loop,
1055                );
1056            }
1057        }
1058
1059        // End label for all if statement, should be set only once
1060        if !is_set_label_if_end {
1061            if_body_state.borrow_mut().set_label(label_if_end);
1062        }
1063    }
1064
1065    /// # Loop
1066    /// Loop statement contains logic:
1067    /// - jump to loop
1068    /// - loop body
1069    /// - end of loop
1070    /// - return, break, continue
1071    pub fn loop_statement(
1072        &mut self,
1073        data: &[ast::LoopBodyStatement<'_, I, E>],
1074        function_body_state: &Rc<RefCell<BlockState<I>>>,
1075    ) {
1076        // Create state for loop-body, from parent func state because
1077        // loop-state can contain sub-state, that can be independent from parent
1078        // state
1079        let loop_body_state = Rc::new(RefCell::new(BlockState::new(Some(
1080            function_body_state.clone(),
1081        ))));
1082        function_body_state
1083            .borrow_mut()
1084            .set_child(loop_body_state.clone());
1085        // Get labels name for loop-begin, and loop-end
1086        let label_loop_begin = loop_body_state
1087            .borrow_mut()
1088            .get_and_set_next_label(&"loop_begin".to_string().into());
1089
1090        let label_loop_end = loop_body_state
1091            .borrow_mut()
1092            .get_and_set_next_label(&"loop_end".to_string().into());
1093
1094        loop_body_state
1095            .borrow_mut()
1096            .jump_to(label_loop_begin.clone());
1097        loop_body_state
1098            .borrow_mut()
1099            .set_label(label_loop_begin.clone());
1100
1101        let mut return_is_called = false;
1102        let mut break_is_called = false;
1103        let mut continue_is_called = false;
1104        for body in data {
1105            if return_is_called {
1106                self.add_error(error::StateErrorResult::new(
1107                    error::StateErrorKind::ForbiddenCodeAfterReturnDeprecated,
1108                    format!("{body:?}"),
1109                    CodeLocation::new(1, 1),
1110                ));
1111            }
1112            if break_is_called {
1113                self.add_error(error::StateErrorResult::new(
1114                    error::StateErrorKind::ForbiddenCodeAfterBreakDeprecated,
1115                    format!("{body:?}"),
1116                    CodeLocation::new(1, 1),
1117                ));
1118            }
1119            if continue_is_called {
1120                self.add_error(error::StateErrorResult::new(
1121                    error::StateErrorKind::ForbiddenCodeAfterContinueDeprecated,
1122                    format!("{body:?}"),
1123                    CodeLocation::new(1, 1),
1124                ));
1125            }
1126
1127            match body {
1128                ast::LoopBodyStatement::LetBinding(bind) => {
1129                    self.let_binding(bind, &loop_body_state);
1130                }
1131                ast::LoopBodyStatement::Binding(bind) => {
1132                    self.binding(bind, &loop_body_state);
1133                }
1134                ast::LoopBodyStatement::FunctionCall(fn_call) => {
1135                    self.function_call(fn_call, &loop_body_state);
1136                }
1137                ast::LoopBodyStatement::If(if_condition) => self.if_condition(
1138                    if_condition,
1139                    &loop_body_state,
1140                    &None,
1141                    Some((&label_loop_begin, &label_loop_end)),
1142                ),
1143                ast::LoopBodyStatement::Loop(loop_statement) => {
1144                    self.loop_statement(loop_statement, &loop_body_state);
1145                }
1146                ast::LoopBodyStatement::Return(expression) => {
1147                    let expr_result = self.expression(expression, &loop_body_state);
1148                    if let Some(res) = expr_result {
1149                        // Jump to return label in codegen and set return
1150                        // status to indicate function, that it's manual
1151                        // return
1152                        loop_body_state.borrow_mut().jump_function_return(res);
1153                        loop_body_state.borrow_mut().set_return();
1154                        return_is_called = true;
1155                    }
1156                }
1157                ast::LoopBodyStatement::Break => {
1158                    // Break loop and jump to the end of loop
1159                    loop_body_state.borrow_mut().jump_to(label_loop_end.clone());
1160                    break_is_called = true;
1161                }
1162                ast::LoopBodyStatement::Continue => {
1163                    // Skip next loop  step and jump to the start
1164                    // of loop
1165                    loop_body_state
1166                        .borrow_mut()
1167                        .jump_to(label_loop_begin.clone());
1168                    continue_is_called = true;
1169                }
1170            }
1171        }
1172
1173        // If return is called do not set loop-specific instructions
1174        if !return_is_called {
1175            // Because it's loop jump to loop begin
1176            loop_body_state
1177                .borrow_mut()
1178                .jump_to(label_loop_begin.clone());
1179
1180            // Loop ending
1181            loop_body_state.borrow_mut().set_label(label_loop_end);
1182        }
1183    }
1184
1185    #[allow(clippy::doc_markdown)]
1186    /// ## Expression
1187    /// Is basic entity for state operation and state usage.
1188    /// State correctness verified by expressions call.
1189    /// Expressions folded by operations priority. For that
1190    /// expressions tree folded each leaf of tree by priority operation
1191    /// level. The most striking image is bracketing an expression with
1192    /// a higher priority, and build tree based on that.
1193    ///
1194    /// ## Return
1195    /// `PrimitiveValue` | `TmpRegister`
1196    ///
1197    ///  Possible algorithm conditions:
1198    ///     1. PrimitiveValue -> PrimitiveValue
1199    ///     2. Value -> load -> TmpRegister
1200    ///     3. FuncCall -> call -> TmpRegister
1201    ///     4. Operations
1202    ///         4.1. PrimitiveValue
1203    ///         - PrimitiveValue -> tmp = OP val1, val2 -> TmpRegister
1204    ///         - Value -> tmp1 = load -> OP val1, tmp1 -> TmpRegister
1205    ///         - FuncCAll -> tmp1 = call -> OP val1, tmp1 -> TmpRegister
1206    ///         4.2. TmpRegister (with name tmp1)
1207    ///         - PrimitiveValue -> tmp2 = OP tmp1, val1 -> TmpRegister
1208    ///         - Value -> tmp2 = load -> tmp3 = OP tmp1, tmp2 -> TmpRegister
1209    ///         - FuncCall -> tmp2 = call ->  tmp3 = OP tmp1, tmp2 -> TmpRegister
1210    ///         4.3. Operations -> recursively invoke 4.2.
1211    pub fn expression(
1212        &mut self,
1213        data: &ast::Expression<'_, I, E>,
1214        body_state: &Rc<RefCell<BlockState<I>>>,
1215    ) -> Option<ExpressionResult> {
1216        // Fold expression operations priority
1217        let expr = Self::expression_operations_priority(data.clone());
1218        // To analyze expression first time, we set:
1219        // left_value - as None
1220        // operation - as None
1221        // And basic expression value is `right_value`, because
1222        // it can contain sub-operations (`left_value` don't contain
1223        // and contain Expression result)
1224        self.expression_operation(None, &expr, None, body_state)
1225    }
1226
1227    /// Expression operation semantic logic:
1228    /// `OP(lhs, rhs)`
1229    /// Left-value contains optional Expression result for left side
1230    /// of expression.
1231    #[allow(clippy::too_many_lines)]
1232    pub fn expression_operation(
1233        &mut self,
1234        left_value: Option<&ExpressionResult>,
1235        right_expression: &ast::Expression<'_, I, E>,
1236        op: Option<&ast::ExpressionOperations>,
1237        body_state: &Rc<RefCell<BlockState<I>>>,
1238    ) -> Option<ExpressionResult> {
1239        // Get right side value from expression.
1240        // If expression return error immediately return error
1241        // because next analyzer should use success result.
1242        let right_value = match &right_expression.expression_value {
1243            ast::ExpressionValue::_marker(..) => unreachable!(),
1244            // Check is expression Value entity
1245            ast::ExpressionValue::ValueName(value) => {
1246                // Get value from block state
1247                let value_from_state = body_state.borrow_mut().get_value_name(&value.name().into());
1248                // Register contains result
1249                body_state.borrow_mut().inc_register();
1250                let last_register_number = body_state.borrow().last_register_number;
1251                // First check value in body state
1252                let ty = if let Some(val) = value_from_state {
1253                    body_state
1254                        .borrow_mut()
1255                        .expression_value(val.clone(), last_register_number);
1256                    val.inner_type
1257                } else if let Some(const_val) = self.global.constants.get(&value.name().into()) {
1258                    body_state
1259                        .borrow_mut()
1260                        .expression_const(const_val.clone(), last_register_number);
1261                    const_val.constant_type.clone()
1262                } else {
1263                    // If value doesn't exist in State or as Constant
1264                    self.add_error(error::StateErrorResult::new(
1265                        error::StateErrorKind::ValueNotFound,
1266                        value.name(),
1267                        value.location(),
1268                    ));
1269                    return None;
1270                };
1271                // Return result as register
1272                ExpressionResult {
1273                    expr_type: ty,
1274                    expr_value: ExpressionResultValue::Register(
1275                        body_state.borrow().last_register_number,
1276                    ),
1277                }
1278            }
1279            // Check is expression primitive value
1280            ast::ExpressionValue::PrimitiveValue(value) => {
1281                // Just return primitive value itself
1282                ExpressionResult {
1283                    expr_type: value.get_type().into(),
1284                    expr_value: ExpressionResultValue::PrimitiveValue(value.clone().into()),
1285                }
1286            }
1287            // Check is expression Function call entity
1288            ast::ExpressionValue::FunctionCall(fn_call) => {
1289                // We shouldn't increment register, because it's
1290                // inside `self.function_call`.
1291                // And result of function always stored in register.
1292                let func_call_ty = self.function_call(fn_call, body_state)?;
1293                // Return result as register
1294                body_state.borrow_mut().inc_register();
1295                ExpressionResult {
1296                    expr_type: func_call_ty,
1297                    expr_value: ExpressionResultValue::Register(
1298                        body_state.borrow().last_register_number,
1299                    ),
1300                }
1301            }
1302            ast::ExpressionValue::StructValue(value) => {
1303                let struct_value: ExpressionStructValue = value.clone().into();
1304                // Can be only Value from state, not constant
1305                // Get value from block state
1306                let val = body_state
1307                    .borrow_mut()
1308                    .get_value_name(&struct_value.name)
1309                    .or_else(|| {
1310                        // If value doesn't exist
1311                        self.add_error(error::StateErrorResult::new(
1312                            error::StateErrorKind::ValueNotFound,
1313                            value.name.name(),
1314                            value.name.location(),
1315                        ));
1316                        None
1317                    })?;
1318                // Check is value type is struct
1319                let ty = val.inner_type.get_struct().or_else(|| {
1320                    self.add_error(error::StateErrorResult::new(
1321                        error::StateErrorKind::ValueNotStruct,
1322                        value.name.name(),
1323                        value.name.location(),
1324                    ));
1325                    None
1326                })?;
1327                // Check is type exists
1328                if !self.check_type_exists(&val.inner_type, &value.name.name(), &value.name) {
1329                    return None;
1330                }
1331                if &Type::Struct(ty.clone()) != self.global.types.get(&val.inner_type.name())? {
1332                    self.add_error(error::StateErrorResult::new(
1333                        error::StateErrorKind::WrongExpressionType,
1334                        value.name.name(),
1335                        value.name.location(),
1336                    ));
1337                    return None;
1338                }
1339
1340                let attributes = ty
1341                    .attributes
1342                    .get(&struct_value.attribute)
1343                    .or_else(|| {
1344                        self.add_error(error::StateErrorResult::new(
1345                            error::StateErrorKind::ValueNotStructField,
1346                            value.name.name(),
1347                            value.name.location(),
1348                        ));
1349                        None
1350                    })?
1351                    .clone();
1352
1353                // Register contains result
1354                body_state.borrow_mut().inc_register();
1355                let last_register_number = body_state.borrow().last_register_number;
1356                body_state.borrow_mut().expression_struct_value(
1357                    val.clone(),
1358                    attributes.attr_index,
1359                    last_register_number,
1360                );
1361
1362                body_state.borrow_mut().inc_register();
1363                ExpressionResult {
1364                    expr_type: attributes.attr_type,
1365                    expr_value: ExpressionResultValue::Register(
1366                        body_state.borrow().last_register_number,
1367                    ),
1368                }
1369            }
1370            ast::ExpressionValue::Expression(expr) => {
1371                // Subexpression should be analyzed independently
1372                self.expression(expr, body_state)?
1373            }
1374            ast::ExpressionValue::ExtendedExpression(expr) => expr.expression(self, body_state),
1375        };
1376        // Check left expression side and generate expression operation code
1377        let expression_result = if let (Some(left_value), Some(op)) = (left_value, op) {
1378            if left_value.expr_type != right_value.expr_type {
1379                self.add_error(error::StateErrorResult::new(
1380                    error::StateErrorKind::WrongExpressionType,
1381                    left_value.expr_type.to_string(),
1382                    right_expression.location(),
1383                ));
1384                // Do not fetch other expression flow if type is wrong
1385                return None;
1386            }
1387            // Expression operation is set to register
1388            body_state.borrow_mut().inc_register();
1389            let last_register_number = body_state.borrow().last_register_number;
1390            // Call expression operation for: OP(left_value, right_value)
1391            body_state.borrow_mut().expression_operation(
1392                op.clone().into(),
1393                left_value.clone(),
1394                right_value.clone(),
1395                last_register_number,
1396            );
1397            // Expression result value  for Operations is always should be "register"
1398            ExpressionResult {
1399                expr_type: right_value.expr_type,
1400                expr_value: ExpressionResultValue::Register(
1401                    body_state.borrow().last_register_number,
1402                ),
1403            }
1404        } else {
1405            right_value
1406        };
1407
1408        // Check is for right value contain next operation
1409        if let Some((operation, expr)) = &right_expression.operation {
1410            // Recursively call, where current Execution result set as left
1411            // side expressionf
1412            self.expression_operation(Some(&expression_result), expr, Some(operation), body_state)
1413        } else {
1414            Some(expression_result)
1415        }
1416    }
1417
1418    /// # Expression operation priority
1419    /// Fold expression priority.
1420    /// Pass expressions tree from max priority level to minimum
1421    /// priority level. If expression priority for concrete branch
1422    /// founded, it's folded to leaf (same as bracketing).
1423    ///
1424    /// ## Return
1425    /// New folded expressions tree.
1426    fn expression_operations_priority(
1427        data: ast::Expression<'_, I, E>,
1428    ) -> ast::Expression<'_, I, E> {
1429        let mut data = data;
1430        for priority in (0..=MAX_PRIORITY_LEVEL_FOR_EXPRESSIONS).rev() {
1431            data = Self::fetch_op_priority(data, priority);
1432        }
1433        data
1434    }
1435
1436    /// Fetch expression operation priories and fold it.
1437    /// Expressions folded by operations priority. For that expressions
1438    /// tree folded each branch of tree to leaf by priority operation
1439    /// level. The most striking image is bracketing an expression with
1440    /// a higher priority, and build tree based on that.
1441    ///
1442    /// For example: expr = expr1 OP1 expr2 - it has 2 branches
1443    /// if expr2 contain subbranch (for example: `expr2 OP2 expr3`) we trying
1444    /// to find priority level for current pass. And if `priority_level == OP1`
1445    /// - fold it to leaf.
1446    /// NOTICE: expr1 can't contain subbranches by design. So we pass
1447    /// expression tree from left to right.
1448    /// If priority level not equal, we just return income expression, or
1449    /// if it has subbranch - launch fetching subbranch
1450    fn fetch_op_priority(
1451        data: ast::Expression<'_, I, E>,
1452        priority_level: u8,
1453    ) -> ast::Expression<'_, I, E> {
1454        // Check is expression contains right side with operation
1455        if let Some((op, expr)) = data.clone().operation {
1456            // Check is right expression contain subbranch (sub operation)
1457            if let Some((next_op, next_expr)) = expr.operation.clone() {
1458                // Check incoming expression operation priority level
1459                if op.priority() == priority_level {
1460                    // Fold expression to leaf - creating new expression as value
1461                    let expression_value =
1462                        ast::ExpressionValue::Expression(Box::new(ast::Expression {
1463                            expression_value: data.expression_value,
1464                            operation: Some((
1465                                op,
1466                                Box::new(ast::Expression {
1467                                    expression_value: expr.expression_value,
1468                                    operation: None,
1469                                }),
1470                            )),
1471                        }));
1472                    // Fetch next expression branch
1473                    let new_expr = Self::fetch_op_priority(*next_expr, priority_level);
1474                    // Create new expression with folded `expression_value`
1475                    ast::Expression {
1476                        expression_value,
1477                        operation: Some((next_op, Box::new(new_expr))),
1478                    }
1479                } else {
1480                    // If priority not equal for current level just
1481                    // fetch right side of expression for next branches
1482                    let new_expr =
1483                        if next_op.priority() > op.priority() && next_expr.operation.is_none() {
1484                            // Pack expression to leaf
1485                            ast::Expression {
1486                                expression_value: ast::ExpressionValue::Expression(expr),
1487                                operation: None,
1488                            }
1489                        } else {
1490                            Self::fetch_op_priority(*expr, priority_level)
1491                        };
1492                    // Rebuild expression tree
1493                    ast::Expression {
1494                        expression_value: data.expression_value,
1495                        operation: Some((op, Box::new(new_expr))),
1496                    }
1497                }
1498            } else {
1499                data
1500            }
1501        } else {
1502            data
1503        }
1504    }
1505}