|
发表于 2012-12-9 15:22:58
|
显示全部楼层
本帖最后由 ifree64 于 2012-12-9 16:04 编辑
在这几个宏上做了修改才能通过编译,请傻孩子看一下,是否修改正确
END_PARAM_INIT(__VAR)
NO_PARAM_INIT(__VAR)
END_CALL_TINY_FSM(__NAME)
PS:使用宏把C编程一种方言后,我的编辑器已经无法对源代码自动作出正确的缩进了,这恐怕可以作为另一个尽量少使用宏的理由。
- typedef unsigned char uint8_t;
- typedef unsigned char bool;
- #define false 0
- #define true (!false)
- #define NULL 0
- #define DEF_TINY_FSM(__NAME) \
- typedef struct tiny_fsm_##__NAME##_arg tiny_fsm_##__NAME##_arg_t; \
- typedef void *(*tiny_fsm_##__NAME##_task)(tiny_fsm_##__NAME##_arg_t *pArg); \
- struct tiny_fsm_##__NAME##_arg
- #define DEF_PARAM {
- #define END_DEF_PARAM };
- #define END_DEF_TINY_FSM
- #define NEW_TINY_FSM(__NAME, __VAR) \
- tiny_fsm_##__NAME##_task s_TinyFSM##__VAR = NULL;
- #define TINY_STATE(__NAME, __STATE_NAME) \
- void *tiny_fsm_state_##__STATE_NAME(tiny_fsm_##__NAME##_arg_t *pArg)
- #define BEGIN {
- #define END }
- #define PRIVATE static
- #define PUBLIC
- #define INTERNAL static
- #define PARAM pArg
- #define TINY_FSM_END return NULL;
- #define TINY_FSM_TRANSFER_TO(__STATE_NAME) return (void *)&tiny_fsm_state_##__STATE_NAME;
- #define IS_TINY_FSM_CPL(__VAR) (NULL == s_TinyFSM##__VAR)
- #define CALL_TINY_FSM(__NAME,__VAR, __START_STATE) do { \
- tiny_fsm_##__NAME##_task *s_ptTinyFSM##__NAME##Temp = &s_TinyFSM##__VAR; \
- bool bReset = IS_TINY_FSM_CPL(__VAR); \
- tiny_fsm_##__NAME##_task s_TinyFSMStart = &(tiny_fsm_state_##__START_STATE); \
- static tiny_fsm_##__NAME##_arg_t tParam, tResetParam =
- #define PARAM_INIT {
- #define END_PARAM_INIT(__VAR) }; \
- if (bReset) { \
- tParam = tResetParam; \
- s_TinyFSM##__VAR = s_TinyFSMStart; \
- }
- #define NO_PARAM_INIT(__VAR) {0}; \
- if (bReset) { \
- tParam = tResetParam; \
- s_TinyFSM##__VAR = s_TinyFSMStart; \
- }
- #define SET_PARAM(__FIELD,__VALUE) do {tParam.__FIELD = (__VALUE);} while(false);
- #define END_CALL_TINY_FSM(__NAME) \
- *s_ptTinyFSM##__NAME##Temp = (tiny_fsm_##__NAME##_task)(*s_ptTinyFSM##__NAME##Temp)( &tParam ); \
- } while(false);
- typedef void frame_parser(uint8_t *pchBuffer, uint8_t chLength);
- DEF_TINY_FSM(Frame_Decoding)
- DEF_PARAM
- frame_parser *fnParser;
- uint8_t chBuffer[20]; //!< data buffer
- uint8_t chByte;
- uint8_t chXOR;
- uint8_t chLength;
- uint8_t chCounter;
- END_DEF_PARAM
-
- PRIVATE TINY_STATE(Frame_Decoding, FD_Wait_Head);
- PRIVATE TINY_STATE(Frame_Decoding, FD_Wait_Length);
- PRIVATE TINY_STATE(Frame_Decoding, FD_Receive_Data);
- PRIVATE TINY_STATE(Frame_Decoding, FD_Check_XOR);
- END_DEF_TINY_FSM
- PRIVATE TINY_STATE(Frame_Decoding, FD_Wait_Head) BEGIN
- if (0xAA == PARAM->chByte) {
- //! head received
- PARAM->chXOR = 0xAA;
- TINY_FSM_TRANSFER_TO(FD_Wait_Length);
- }
- TINY_FSM_TRANSFER_TO(FD_Wait_Head)
- END
- PRIVATE TINY_STATE(Frame_Decoding, FD_Wait_Length) BEGIN
- if (PARAM->chByte > 20 || PARAM->chByte < 1) {
- //! illegal length
- TINY_FSM_END; //!< reset fsm
- }
- PARAM->chLength = PARAM->chByte;
- PARAM->chCounter = 0;
- PARAM->chXOR ^= PARAM->chByte;
-
- TINY_FSM_TRANSFER_TO(FD_Receive_Data);
-
- END
- PRIVATE TINY_STATE(Frame_Decoding, FD_Receive_Data) BEGIN
- //! save byte to buffer
- PARAM->chBuffer[PARAM->chCounter++] = PARAM->chByte;
- //! calculate XOR check sum
- PARAM->chXOR ^= PARAM->chByte;
- if (PARAM->chCounter >= PARAM->chLength) {
- //! all data received
- TINY_FSM_TRANSFER_TO(FD_Check_XOR);
- }
- TINY_FSM_TRANSFER_TO( FD_Receive_Data );
- END
- PRIVATE TINY_STATE(Frame_Decoding, FD_Check_XOR) BEGIN
- //! check XOR check SUM
- if (PARAM->chXOR == PARAM->chByte) {
- if (NULL != PARAM->fnParser) {
- PARAM->fnParser(PARAM->chBuffer, PARAM->chLength); //!< call parser
- }
- }
- TINY_FSM_END; //!< reset fsm
- END
- extern void add_frame_to_queue(uint8_t *, uint8_t);
- void usart_rxc_isr_handler(uint8_t chByte)
- {
- NEW_TINY_FSM(Frame_Decoding, tFrameDeocoder)
- CALL_TINY_FSM(Frame_Decoding, tFrameDeocoder, FD_Wait_Head)
- PARAM_INIT
- &add_frame_to_queue, //!< register frame parser handler
- 0
- END_PARAM_INIT(tFrameDeocoder)
-
- SET_PARAM(chByte, chByte)
- END_CALL_TINY_FSM(Frame_Decoding)
- }
-
- void add_frame_to_queue(uint8_t *pchData, uint8_t chLength)
- {
- //! add received data block to command chain list
- // ...
- }
- void process_command_chain(void)
- {
- //! get command from chain list and try to parse it.
- //...
- }
-
- int main(void)
- {
- //...
- while(true) {
- // ...
- process_command_chain();
- }
- return 0;
- }
复制代码 最后在调用状态机函数的部分
- NEW_TINY_FSM(Frame_Decoding, tFrameDeocoder)
- CALL_TINY_FSM(Frame_Decoding, tFrameDeocoder, FD_Wait_Head)
- PARAM_INIT
- &add_frame_to_queue, //!< register frame parser handler
- 0
- END_PARAM_INIT(tFrameDeocoder) // [color=Red]我对这个宏做了小小修改方能通过编译[/color]
-
- SET_PARAM(chByte, chByte)
- END_CALL_TINY_FSM(Frame_Decoding)
复制代码 这段代码用NEW_TINY_FSM宏,定义了一个“状态机”,但从宏的实现上来看,并没有定义为static静态变量;
那么真正调用“状态机”的宏END_CALL_TINY_FSM,实际上不能“保存”状态,是不是应该在NEW_TINY_FSM宏
中加一个static呢?
|
|