optical/NxBase/shell.c
2025-09-04 09:45:08 +08:00

346 lines
5.6 KiB
C

#include "shell.h"
#include "cpuid.h"
//-------------------------------------------------------------------------
ShellCmdItem g_cmdList[MAX_CMD_NUM];
int g_cmdNum = 0;
//-------------------------------------------------------------------------
void ChangeToUper(char * str)
{
char tmp;
while (str != NULL)
{
tmp = *str;
if (tmp == 0)
{
break;
}
if (tmp >= 'a' && tmp <= 'z')
{
tmp -= ('a'-'A');
*str = tmp;
}
str++;
}
}
int AddShellCmd(const char*pCmd, const char*pHelp, ShellFunc func)
{
if (g_cmdNum < MAX_CMD_NUM)
{
if ((strlen(pCmd) >= MAX_CMD_STR))
{
memcpy(g_cmdList[g_cmdNum].cmdstr, pCmd, MAX_CMD_STR-1);
g_cmdList[g_cmdNum].cmdstr[MAX_CMD_STR-1] = 0;
}
else
{
strcpy(g_cmdList[g_cmdNum].cmdstr, pCmd);
}
ChangeToUper(g_cmdList[g_cmdNum].cmdstr);
#if (1) // 改为指针
g_cmdList[g_cmdNum].helpstr = pHelp;
#else
if ((strlen(pHelp) >= MAX_HELP_STR))
{
memcpy(g_cmdList[g_cmdNum].helpstr, pHelp, MAX_HELP_STR-1);
g_cmdList[g_cmdNum].helpstr[MAX_HELP_STR-1] = 0;
}
else
{
strcpy(g_cmdList[g_cmdNum].helpstr, pHelp);
}
#endif
g_cmdList[g_cmdNum].shellfunc = func;
g_cmdNum++;
return g_cmdNum;
}
else
{
printf("AddShellCmd failed, g_cmdNum=%d\r\n", g_cmdNum);
return -1;
}
}
int ShellTask(void)
{
int i, j, k;
int sta;
char ch, ch1;
char command[MAX_CMD_LINE];
char cmd[MAX_CMD_LINE];
char para1[MAX_CMD_LINE];
char para2[MAX_CMD_LINE];
int cmdlen, para1len, para2len;
int cmdstrlen;
if (IsNewCommand() == 0) // 检测命令
{
return -1;
}
// 解析得到命令和参数
cmdstrlen = LockExecAndGetCmdStr(command);
sta = 0;
cmdlen = 0;
para1len = 0;
para2len = 0;
cmd[0] = 0;
para1[0] = 0;
para2[0] = 0;
for(i = 0; i < cmdstrlen; i++)
{
ch = command[i];
// printf("0x%x ", ch);
if (sta == 0)
{
if (cmdlen == 0 && ch == ' ') // 前空格
{
continue;
}
else if (cmdlen != 0 && ch == ' ') // 后空格
{
cmd[cmdlen] = 0;
sta = 1;
}
else
{
if (cmdlen < MAX_CMD_LINE-1)
{
cmd[cmdlen] = ch;
cmdlen++;
}
}
}
else if (sta == 1)
{
if (para1len == 0 && ch == ' ') // 前空格
{
continue;
}
else if (para1len != 0 && ch == ' ') // 后空格
{
para1[para1len] = 0;
sta = 2;
}
else
{
if (para1len < MAX_CMD_LINE-1)
{
para1[para1len] = ch;
para1len++;
}
}
}
else if (sta == 2)
{
if (para2len == 0 && ch == ' ') // 前空格
{
continue;
}
else if (para2len != 0 && ch == ' ') // 后空格
{
para2[para2len] = 0;
sta = 3;
}
else
{
if (para2len < MAX_CMD_LINE-1)
{
para2[para2len] = ch;
para2len++;
}
}
}
else
{
break;
}
}
cmd[cmdlen] = 0;
para1[para1len] = 0;
para2[para2len] = 0;
// printf("cmd=%s,para1=%s,para2=%s", cmd, para1, para2);
ChangeToUper(cmd);
ChangeToUper(para1);
ChangeToUper(para2);
// 执行命令
for (i = 0; i < g_cmdNum; i++)
{
if (strcmp(g_cmdList[i].cmdstr, cmd) == 0)
{
if (g_cmdList[i].shellfunc != NULL)
{
g_cmdList[i].shellfunc(para1, para2);
}
break;
}
}
if (i >= g_cmdNum) // 没有找到匹配命令,寻找局部匹配命令
{
k = -1;
for (i = 0; i < g_cmdNum; i++)
{
for (j = 0; j < cmdlen; j++)
{
ch = cmd[j];
ch1 = g_cmdList[i].cmdstr[j];
if (ch == ' ' || ch == 0 || ch1 == ' ' || ch1 == 0) // 命令结束
{
break;
}
if (ch != ch1)
{
break;
}
}
if (j == cmdlen && cmdlen != 0) // 匹配输入命令
{
k = i;
break;
}
}
if (k >= 0) // 有匹配的
{
if (g_cmdList[k].shellfunc != NULL)
{
g_cmdList[k].shellfunc(para1, para2);
}
}
}
OutNewCmdLine();
UnlockExec();
return 0;
}
//-------------------------------------------------------------------------
// 版本命令
void VersionInfo(char * para1, char * para2)
{
char buff[VERSION_LEN+1];
GetVersionStr(buff);
buff[VERSION_LEN] = 0;
printf("Software Version = %s\r\n", buff);
GetBuildStr(buff);
printf("%s\r\n", buff);
}
// 帮助命令
void HelpString(char * para1, char * para2)
{
int i;
if (para1 == para2)
{
}
for (i = 0; i < g_cmdNum; i++)
{
printf("\r\n%s\r\n", g_cmdList[i].cmdstr);
printf("\t%s\r\n", g_cmdList[i].helpstr);
}
}
// 清屏命令
void CleanScreen(char * para1, char * para2)
{
if (para1 == para2)
{
}
putchar(0x0C); // 清屏
}
void Restart(char * para1, char * para2)
{
RestartMcu();
}
void ShowHistoryCmd(char * para1, char * para2)
{
if (para1 == NULL || para2 == NULL)
{
return;
}
int num = GetHistoryNum(); // 已经存储的历史命令个数
int maxnum = GetHistoryMaxNum();
int rslt;
char ch[MAX_CMD_LINE];
printf("show all history cmd:\r\n");
if (num == maxnum)
{
int i = 0;
for (int idx = GetHistoryIdx(); idx < maxnum; idx++)
{
rslt = GetHistoryCmd(idx, &ch[0]);
if (rslt == 0)
{
printf("\t%d.%s\r\n", i+1, ch);
i++;
}
}
for (int idx = 0; idx < GetHistoryIdx(); idx++)
{
rslt = GetHistoryCmd(idx, &ch[0]);
if (rslt == 0)
{
printf("\t%d.%s\r\n", i+1, ch);
i++;
}
}
}
else if (num < maxnum)
{
for (int i = 0; i < num; i++)
{
rslt = GetHistoryCmd(i, &ch[0]);
if (rslt == 0)
{
printf("\t%d.%s\r\n", i+1, ch);
}
}
}
}
//-------------------------------------------------------------------------
void InitShell(void)
{
InitConsole(); // 初始化控制台
memset(g_cmdList, 0, sizeof(ShellCmdItem)*MAX_CMD_NUM);
g_cmdNum = 0;
// 基本命令
AddShellCmd("HELP", "show the help info", HelpString);
AddShellCmd("VERSION", "show the version info", VersionInfo);
// AddShellCmd("CLS", "clean the screen", CleanScreen);
AddShellCmd("REBOOT", "reboot the mcu", Restart);
// AddShellCmd("HISTORY", "show all history cmd", ShowHistoryCmd);
}