[導(dǎo)讀]一直以來都是使用串口進行調(diào)試,非常方便,最近將命令工具進行了重新,將支持的命令與通信接口,處理等進行了分離,可移植性更強,并且不依賴通信接口,可以使用串口,網(wǎng)口,433等等通信接口,只需要實現(xiàn)一個pr
一直以來都是使用串口進行調(diào)試,非常方便,最近將命令工具進行了重新,將支持的命令與通信接口,處理等進行了分離,可移植性更強,并且不依賴通信接口,可以使用串口,網(wǎng)口,433等等通信接口,只需要實現(xiàn)一個printf類似的函數(shù)即可,因為串口是字符流,不像其它通信接口,一次傳輸一個塊,因此在使用非串口的時候,建議發(fā)送的時候?qū)?shù)據(jù)用sprntf緩存到一個buff中,一次傳輸。
//sys_cmd.c
/************************************************************************************************************* ?*?文件名: sys_cmd.c ?*?功能: 自定義的系統(tǒng)命令接口 ?*?作者: cp1300@139.com ?*?創(chuàng)建時間: 2014-06-07 ?*?最后修改時間: 2018-01-14 ?*?詳細: 分離底層,將命令緩沖區(qū)與接口句柄進行分離,并且命令可以自行控制添加,增加命令是否顯示狀態(tài) *************************************************************************************************************/ #include?"SYSTEM.H" #include?"sys_cmd.h" #include?"string.h" //命令緩沖區(qū)是否初始化ID #define?SYS_CMD_BUFF_INIT_ID 0x86877F9D //管理密碼狀態(tài) #define?PASSWORD_STR? "123456" static?u32?sg_PASSWORD_HASH=0; u32?BKDRHash(const?char?*str); //BKDR?哈希算法 void?SYS_CMD_Help(SYS_CMD_HANDLE?*pHandle,?char?*pStr); //幫助命令 void?SYS_CMD_Exit(SYS_CMD_HANDLE?*pHandle,?char?*pStr); //退出命令 //支持的命令定義 const?SYS_CMD_TYPE??CMD_GET_HELP = {"?",?SYS_CMD_Help,?"tt幫助",?TRUE}; //幫助 const?SYS_CMD_TYPE??CMD_EXIT = {"EXIT",?SYS_CMD_Exit,?"tt退出,再次輸入需要密碼",?TRUE}; //退出登錄 /************************************************************************************************************************* *函數(shù)???????? : void?SYS_CMD_Init(SYS_CMD_BUFF_TYPE?*pCmdBuff) *功能???????? : 初始化系統(tǒng)命令(會初始化系統(tǒng)命令緩沖區(qū),并添加幫助命令) *參數(shù)???????? : pCmdBuff:系統(tǒng)命令緩沖區(qū) *返回???????? : 無 *依賴???????? : 無 *作者???????? : cp1300@139.com *時間???????? : 2018-01-14 *最后修改時間 : 2018-01-14 *說明???????? : *************************************************************************************************************************/ void?SYS_CMD_Init(SYS_CMD_BUFF_TYPE?*pCmdBuff) { if(sg_PASSWORD_HASH?==?0)?sg_PASSWORD_HASH?=?BKDRHash(PASSWORD_STR); //初始化密碼的哈希值 pCmdBuff->CmdCount?=?0; //清空命令 pCmdBuff->InitId?=?0; //初始化為無效狀態(tài) SYS_CMD_Add(pCmdBuff,?&CMD_GET_HELP); //添加幫助命令 SYS_CMD_Add(pCmdBuff,?&CMD_EXIT); //添加退出命令 } /************************************************************************************************************************* *函數(shù)???????? : bool?SYS_CMD_Add(SYS_CMD_BUFF_TYPE?*pCmdBuff,?const?SYS_CMD_TYPE?*pCmd) *功能???????? : 添加一個命令到命令緩沖區(qū)中 *參數(shù)???????? : pCmdBuff:當(dāng)前使用的命令緩沖區(qū)指針;pCmd:當(dāng)前要添加的命令 *返回???????? : TRUE:添加成功;FALSE:添加失敗 *依賴???????? : 無 *作者???????? : cp1300@139.com *時間???????? : 2018-01-14 *最后修改時間 : 2018-01-14 *說明???????? : 用于添加并初始化命令緩沖區(qū) *************************************************************************************************************************/ bool?SYS_CMD_Add(SYS_CMD_BUFF_TYPE?*pCmdBuff,?const?SYS_CMD_TYPE?*pCmd) { if(pCmdBuff->InitId?!=?SYS_CMD_BUFF_INIT_ID) //沒有被初始化過 { pCmdBuff->CmdCount?=?0; //命令數(shù)量清零 pCmdBuff->InitId?=?SYS_CMD_BUFF_INIT_ID; //初始化ID有效 } if(pCmdBuff->CmdCount?>=?SYS_MAX_CMD_COUNT)?return?FALSE; //命令已經(jīng)滿了,無法添加了 pCmdBuff->CmdPointerBuff[pCmdBuff->CmdCount]?=?pCmd; //添加命令到命令緩沖區(qū)中 pCmdBuff->CmdBKDHashBuff[pCmdBuff->CmdCount]?=?BKDRHash(pCmd->pCmdStr); //計算當(dāng)前命令的哈希值 pCmdBuff->CmdCount?++; //命令數(shù)量增加 return?TRUE; } /************************************************************************************************************************* *函數(shù)???????? : void?SYS_CMD_InterfaceInit(SYS_CMD_HANDLE?*pHandle,?int?(*DataPrintf)(const?char?*?format,?...)) *功能???????? : 初始化通訊句柄 *參數(shù)???????? : pHandle:句柄;DataPrintf:字符串打印接口 *返回???????? : 無 *依賴???????? : 底層 *作者???????? : cp1300@139.com *時間???????? : 2018-01-14 *最后修改時間 : 2018-01-14 *說明???????? : 用于初始化底層通訊接口 *************************************************************************************************************************/ void?SYS_CMD_InterfaceInit(SYS_CMD_HANDLE?*pHandle,?int?(*DataPrintf)(const?char?*?format,?...)) { pHandle->pCmdBuff?=?NULL; //初始化命令緩沖區(qū)為無效狀態(tài) pHandle->DataPrintf?=?DataPrintf; //初始化通訊接口 pHandle->isInputPassword?=?FALSE; //密碼輸入狀態(tài)無效 } /************************************************************************************************************************* *函數(shù)???????? : void?SYS_CMD_Help(SYS_CMD_HANDLE?*pHandle,char?*pStr) *功能???????? : 幫助命令 *參數(shù)???????? : pHandle:句柄;pStr:當(dāng)前輸入的命令字符串 *返回???????? : 無 *依賴???????? : 底層 *作者???????? : cp1300@139.com *時間???????? : 2018-01-14 *最后修改時間 : 2018-01-14 *說明???????? : 用于初始化底層通訊接口 *************************************************************************************************************************/ void?SYS_CMD_Help(SYS_CMD_HANDLE?*pHandle,char?*pStr) { u16?i; u16?cnt?=?0; if(pHandle->pCmdBuff?==?NULL)?return; pHandle->DataPrintf("rnrn=============================命令列表=============================rn"); pHandle->DataPrintf("[編號]t[命令]ttt[功能]rnrn"); for(i?=?0;i?<?((SYS_CMD_BUFF_TYPE?*)pHandle->pCmdBuff)->CmdCount;i?++) { if(((SYS_CMD_BUFF_TYPE?*)pHandle->pCmdBuff)->CmdPointerBuff[i]->isShow?==?TRUE) //需要顯示才進行打印 { cnt?++; pHandle->DataPrintf("??%02dt%st%srn",cnt,((SYS_CMD_BUFF_TYPE?*)pHandle->pCmdBuff)->CmdPointerBuff[i]->pCmdStr,((SYS_CMD_BUFF_TYPE?*)pHandle->pCmdBuff)->CmdPointerBuff[i]->pFunExp); } } pHandle->DataPrintf("===================================================================rn"); pHandle->DataPrintf("rn"); } /************************************************************************************************************************* *函數(shù)???????? : void?SYS_CMD_Exit(SYS_CMD_HANDLE?*pHandle,char?*pStr) *功能???????? : 退出命令 *參數(shù)???????? : pHandle:句柄;pStr:當(dāng)前輸入的命令字符串 *返回???????? : 無 *依賴???????? : 底層 *作者???????? : cp1300@139.com *時間???????? : 2018-01-14 *最后修改時間 : 2018-01-14 *說明???????? : 用于退出命令,退出后下次必須輸入密碼才能使用 *************************************************************************************************************************/ void?SYS_CMD_Exit(SYS_CMD_HANDLE?*pHandle,char?*pStr) { pHandle->isInputPassword?=?FALSE; //輸入密碼無效 pHandle->DataPrintf("[退出登錄成功]:下次需要輸入密碼才能操作!rn"); } /************************************************************************************************************************* *函數(shù)???????? : bool?SYS_CMD_Handle(SYS_CMD_HANDLE?*pHandle,?SYS_CMD_BUFF_TYPE?*pCmdBuff,?char?*pStr) *功能???????? : 系統(tǒng)命令處理 *參數(shù)???????? : pHandle:句柄;pCmdBuff:當(dāng)前所使用的命令緩沖區(qū);pStr:當(dāng)前輸入的命令字符串 *返回???????? : TRUE:命令有效;FALSE:無效的命令 *依賴???????? : 底層 *作者???????? : cp1300@139.com *時間???????? : 2018-01-14 *最后修改時間 : 2018-01-14 *說明???????? : 用于核心的命令處理函數(shù) *************************************************************************************************************************/ bool?SYS_CMD_Handle(SYS_CMD_HANDLE?*pHandle,?SYS_CMD_BUFF_TYPE?*pCmdBuff,?char?*pStr) { u8?len; u8?i; u32?CmdHash; char?*p; if(pHandle?==?NULL?||?pCmdBuff?==?NULL?||?pStr?==?NULL)?return?FALSE; pHandle->pCmdBuff?=?pCmdBuff; //記錄當(dāng)前的命令緩沖區(qū)指針 len?=?strlen(pStr); //檢測是否輸入過密碼 if(pHandle->isInputPassword==FALSE) //沒有輸入過密碼 { for(i?=?0;i?<?len;i?++) { if((pStr[i]>='a')?&&?(pStr[i]isInputPassword?=?TRUE; //密碼輸入成功 pHandle->DataPrintf("[密碼正確]:可以繼續(xù)操作!rn>"); return?TRUE; } pHandle->DataPrintf("[密碼錯誤]:請輸入管理密碼!rn>"); return?FALSE; } pHandle->DataPrintf("%srn",?pStr); if(len?>?200) //檢測參數(shù)的長度 { pHandle->DataPrintf("[錯誤]:命令超出長度(>(%d))!rn>",200); return?FALSE; } //檢查命令的結(jié)束符-rn for(i?=?0;i?<?len;i?++) { if((pStr[i]?==?'r')||((pStr[i]?==?'n'))) { pStr[i]?=?0; len?=?i; if(len?==?0) { pHandle->DataPrintf("rn>"); return?FALSE; } break; } } //檢測是否含有非法字符 for(i?=?0;i?<?len;i?++) { if((pStr[i]?<?32)?||?(pStr[i]?>?126)) { pHandle->DataPrintf("[錯誤]:含有非法字符!rn>"); return?FALSE; } if((pStr[i]>='a')?&&?(pStr[i]?CMD_PARAMETER_STR_LEN) //檢測參數(shù)的長度 { pHandle->DataPrintf("[錯誤]:命令參數(shù)超出長度(>(%d))!rn>",CMD_PARAMETER_STR_LEN); return?FALSE; } strcpy(pHandle->CmdPara,p); //復(fù)制參數(shù) p[0]?=?'