Skip to content
Snippets Groups Projects
Select Git revision
  • fd9e432b85d18a1534df37a59c24f1865c52049e
  • master default protected
  • 2.0.0 protected
  • 1.0.0 protected
4 results

SupervisedIDStateMachine.cpp

Blame
  • alarm_grammar.h 10.94 KiB
    /*
     * alarm_grammar.h
     *
     * $Author:  $
     *
     * $Revision:  $
     *
     * $Log: alarm_grammar.h,v $
     *
     *
     * copyleft: Sincrotrone Trieste S.C.p.A. di interesse nazionale
     *           Strada Statale 14 - km 163,5 in AREA Science Park
     *           34012 Basovizza, Trieste ITALY
     */
    
    
    #ifndef ALARM_GRAMMAR_H_
    #define ALARM_GRAMMAR_H_
    
    //--------------------------NOTE!!---------------------------------
    //----if a grammar is intended to be used in multithreaded code----
    //----it is required to "#define BOOST_SPIRIT_THREADSAFE" and------
    //----to link against Boost.Threads--------------------------------
    //-----------------------------------------------------------------
    #if BOOST_VERSION  < 103600 
    #ifndef BOOST_SPIRIT_THREADSAFE 
    #define BOOST_SPIRIT_THREADSAFE 
    #endif
    
    #ifndef PHOENIX_THREADSAFE
    #define PHOENIX_THREADSAFE
    #endif
    #endif
    
    #if BOOST_VERSION  < 103600    
    #include <boost/spirit/core.hpp>
    #include <boost/spirit/actor/assign_actor.hpp>			//for assign_a
    #include <boost/spirit/actor/push_back_actor.hpp>		//for push_back_a
    #include <boost/spirit/actor/insert_at_actor.hpp>		//for insert_at_a
    #include <boost/spirit/actor/clear_actor.hpp>			//for clear_a
    #include <boost/spirit/symbols/symbols.hpp>				//for symbol table
    #include <boost/spirit/utility/confix.hpp>				//for confix
    #include <boost/spirit/phoenix/primitives.hpp>			//needed for "var" in group rule
    #include <boost/spirit/phoenix/operators.hpp>			//needed for "var" in group rule
    #include <boost/spirit/phoenix/functions.hpp>
    #else
    #include <boost/spirit/include/classic_core.hpp>
    #include <boost/spirit/include/classic_assign_actor.hpp>			//for assign_a
    #include <boost/spirit/include/classic_push_back_actor.hpp>		//for push_back_a
    #include <boost/spirit/include/classic_insert_at_actor.hpp>		//for insert_at_a
    #include <boost/spirit/include/classic_clear_actor.hpp>			//for clear_a
    #include <boost/spirit/include/classic_symbols.hpp>				//for symbol table
    #include <boost/spirit/include/classic_confix.hpp>				//for confix
    #include <boost/spirit/include/phoenix1_primitives.hpp>			//needed for "var" in group rule
    #include <boost/spirit/include/phoenix1_operators.hpp>			//needed for "var" in group rule
    #include <boost/spirit/include/phoenix1_functions.hpp>
    #endif
    
    //#include <boost/spirit/attribute.hpp>					//for closure
    
    //#include <boost/spirit/tree/ast.hpp>					//for ast parse trees (in tree_formula)
    
    #include <iostream>
    #include <string>
    #include <map>
    
    #include "event_table.h"
    #include "formula_grammar.h"
    
    #define NAME_KEY			"name"
    #define FORMULA_KEY			"formula"
    #define ONDELAY_KEY			"on_delay"
    #define OFFDELAY_KEY		"off_delay"
    #define LEVEL_KEY			"level"
    #define SILENT_TIME_KEY		"silent_time"
    #define GROUP_KEY			"group"
    #define MESSAGE_KEY			"message"
    #define ON_COMMAND_KEY		"on_command"
    #define OFF_COMMAND_KEY		"off_command"
    #define ENABLED_KEY			"enabled"
    
    #define SILENT_TIME_REMAINING_KEY		"silent_time_remaining"
    #define SHELVED_KEY			"shelved"
    #define ACKNOWLEDGED_KEY	"ack"
    #define ATTR_VALUES_KEY		"attr_values"
    #define VALUE_KEY			"value"
    #define ON_COUNTER_KEY		"on_counter"
    #define OFF_COUNTER_KEY		"off_counter"
    #define QUALITY_KEY			"quality"
    #define EXCEPTION_KEY		"exception"
    #define AUDIBLE_KEY			"audible"
    #define FREQ_COUNTER_KEY	"freq_counter"
    #define ALARM_TIME_KEY		"alarm_time"
    #define KEY(S_VAL)  		S_VAL "="
    
    #define SEP					";"
    
    ////////////////////////////////////////////////////////////////////////////
    using namespace std; 
    #if BOOST_VERSION  < 103600 
    using namespace boost::spirit;
    #else
    using namespace boost::spirit::classic;
    #endif
    using namespace phoenix;								//needed for "var" in group rule
    
    ////////////////////////////////////////////////////////////////////////////
    //
    //  Semantic actions for alarm gramamr
    //
    ////////////////////////////////////////////////////////////////////////////
    #if 0
    struct push_back_impl
    {
        template <typename Container, typename Item>
        struct result
        {
            typedef void type;
        };
    
        template <typename Container, typename Item>
        void operator()(Container& c, Item const& item) const
        {
            c.push_back(item);
        }
    };
    
    function<push_back_impl> const push_back = push_back_impl();
    
    struct insert_map_impl
    {
        template <typename Container, typename Item1, typename Item2>
        struct result
        {
            typedef void type;
        };
    
        template <typename Container, typename Item1, typename Item2>
        void operator()(Container& c, Item1 const& item1, Item2 const& item2) const
        {
            c.insert(make_pair(item1, item2));
        }
    };
    
    function<insert_map_impl> const insert_map = insert_map_impl();
    #endif
    ////////////////////////////////////////////////////////////////////////////
    //
    //  alarm grammar
    //
    ////////////////////////////////////////////////////////////////////////////
    struct alarm_parse : public grammar<alarm_parse>
    {
    	alarm_t &m_alarm;
    	
    	symbols<unsigned int> sym_grp;
    	
    	alarm_parse(alarm_t &a) \
    		: m_alarm(a) 
    		{
    			//init symbol table with group defined in alarm_t::grp_str
    			map<string,unsigned int>::iterator i = m_alarm.grp_str.begin();
    			while(i != m_alarm.grp_str.end())
    			{
    				sym_grp.add(i->first.c_str(), i->second);
    				i++;
    			}		
    		}   
       
        template <typename ScannerT>
        struct definition
        {
            definition(alarm_parse const& self)
            {
    		//-------BOOST.SPIRIT GLOSSARY-------  
    		// >>			: sequence
    		// |			: union (i.e. alternative)
    		// -			: difference
    		// *			: kleene star (matches 0 or more times)
    		// +			: positive (matches 1 or more times)
    		// !			: optional (matches 0 or 1 time)
    		// str_p		: matches string
    		// ch_p			: matches char
    		// hex_p		: 
    		// alnum_p		: matches alpha-numeric characters
    		// anychar_p	: matches any single character (including the null terminator: '\0')
    		// lexemd_d		: turns off white space skipping
    		// confix		: recognize a sequence of: an opening, an expression and a closing
    		// assign_a		:
    		// push_back_a	:
        	
    		//std::pair<string, vector<string> > temp;    	
        	
                expression
                	=	no_node_d[str_p(KEY(NAME_KEY))] >>
    				no_node_d
                		[
                		name_alm
                			[
                				assign_a(self.m_alarm.name)			//save name in alarm_t
    						]
    					]		//discard_node_d					
                		>> 
    					no_node_d[separator]
    					>>
    					no_node_d[str_p(KEY(FORMULA_KEY))] >>
                			root_node_d
                			[ 
                			formula	
                				[
                					assign_a(self.m_alarm.formula)	//save formula in alarm_t
                				]
                			]		//root_node_d
    					>> *(no_node_d[option])
    			;
    
                option
    				=	no_node_d[separator] >> no_node_d[on_delay] |
    					no_node_d[separator] >> no_node_d[off_delay] |
    					no_node_d[separator] >> no_node_d[level] |
    					no_node_d[separator] >> no_node_d[silent_time] |
    					no_node_d[separator] >> no_node_d[group] |
    					no_node_d[separator] >> no_node_d[msg] |
    					no_node_d[separator] >> no_node_d[on_command] |
    					no_node_d[separator] >> no_node_d[off_command] |
    					no_node_d[separator] >> no_node_d[enabled]
    			;
    
                //------------------------------ALARM NAME--------------------------------------            
                symbol
                	=	alnum_p | '.' | '_'  | '-' | '+'				//any alpha numeric char plus '.', '_', '-', '+'
                	;	
                symbol_attr_name
                	=	alnum_p | '_'									//any alpha numeric char plus '_'
                	;
                name
                	=	(+symbol) >> '/' >> (+symbol) 
                		>> '/' >> (+symbol) >> '/' >> (+symbol_attr_name)
                	;
                name_alm
                	=	(+symbol_attr_name)
                	; 
    			//------------------------------LEVEL--------------------------------------	
    			level
    				=	discard_node_d[str_p(KEY(LEVEL_KEY))] >>
    					//lexeme_d[(+alnum_p)]		//match only possible levels?? (fault, log, ...)
    					//(+(alnum_p-'\t'))
    					(str_p("fault") | str_p("warning") | str_p("log"))
    					[
    						assign_a(self.m_alarm.lev)		//save level in alarm_t
    					]
    				;
    			//------------------------------GROUP--------------------------------------	
    			group
    				=	discard_node_d[str_p(KEY(GROUP_KEY))] >>
    					self.sym_grp				//match only group defined in sym_grp symbol table
    					[
    						var(self.m_alarm.grp) |= arg1			//using phoenix::var
    					]
    					>> *(
    						ch_p('|') 
    						>> self.sym_grp			//match only group defined in sym_grp symbol table
    							[
    								var(self.m_alarm.grp) |= arg1	//using phoenix::var
    							]
    						)
    				;
    			//------------------------------MESSAGE--------------------------------------	
    			msg
    				=	discard_node_d[str_p(KEY(MESSAGE_KEY))]
    					//>> ch_p('"')
    					>> (+(anychar_p - ';')) 		//one ore more char except ';'
    							[
    								assign_a(self.m_alarm.msg)
    							]					
    					//>> '"'
    				;
    			//---------------------------ON DELAY----------------------------------------
    			on_delay
    				=	discard_node_d[str_p(KEY(ONDELAY_KEY))] >>
    					(uint_p
    					[
    						assign_a(self.m_alarm.on_delay)
    					]
    					| epsilon_p)
    				;
    			//---------------------------OFF DELAY---------------------------------------
    			off_delay
    				=	discard_node_d[str_p(KEY(OFFDELAY_KEY))] >>
    					(uint_p
    					[
    						assign_a(self.m_alarm.off_delay)
    					]
    					| epsilon_p)
    				;
    			//-----------------------------SILENT TIME------------------------------------
    			silent_time
    				= discard_node_d[str_p(KEY(SILENT_TIME_KEY))] >>
    					(int_p
    					[
    						assign_a(self.m_alarm.silent_time)
    					]
    					| epsilon_p)
    				;
    			//-----------------------------ON COMMAND------------------------------------
    			on_command
    				= discard_node_d[str_p(KEY(ON_COMMAND_KEY))] >>
    						(discard_node_d
    						[
    							name
    							[
    								assign_a(self.m_alarm.cmd_name_a)		//save cmd_name_a in alarm_t
    							]
    						]		//discard_node_d
    						| epsilon_p)
    				;
    			//-----------------------------OFF COMMAND------------------------------------
    			off_command
    				= discard_node_d[str_p(KEY(OFF_COMMAND_KEY))] >>
    						(discard_node_d
    						[
    							name
    							[
    								assign_a(self.m_alarm.cmd_name_n)		//save cmd_name_a in alarm_t
    							]
    						]		//discard_node_d
    						| epsilon_p)
    				;
    			//------------------------------ENABLED----------------------------------------
    			enabled
    				=	discard_node_d[str_p(KEY(ENABLED_KEY))] >>
    					//lexeme_d[(+alnum_p)]		//match only possible levels?? (fault, log, ...)
    					//(+(alnum_p-'\t'))
    					//(ch_p('0') | ch_p('1'))
    					bin_p
    					[
    						assign_a(self.m_alarm.enabled)		//save enabled in alarm_t
    					]
    				;
    			//------------------------------SEPARATOR--------------------------------------
    			separator = ch_p(SEP);
            }
            
    		typedef rule<ScannerT> rule_t;	
    		rule_t expression, event, option;
            rule<typename lexeme_scanner<ScannerT>::type> symbol;					//needed to use lexeme_d in rule name
            rule<typename lexeme_scanner<ScannerT>::type> symbol_attr_name;		//needed to use lexeme_d in rule name
            rule_t name, name_alm, val, token, oper, msg, group, level, on_delay, off_delay, silent_time, on_command, off_command, enabled, separator;
    		formula_grammar formula;
    		
    		rule_t const&					
            start() const { return expression; }
        };
    };
    
    
    #endif /*ALARM_GRAMMAR_H_*/