📄 cli_term.c
字号:
/* 输出参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* 返回值 :_U32 0: 接收到一完整命令行并准备提交该命令 */
/* 1: 只接收到一字符并准备继续接收字符 */
/* 调用函数 :CLI_CharProcess ( ) */
/* 被调函数 : */
/*==================================================================*/
_U32 CLI_EditString( PTerm_Data_S pTermStruct )
{
_U32 ulTmp ;
_U8 ucTmp ;
CLI_ASSURE_OR_FAIL( G_NULL != pTermStruct );
/* 接收到的字符串来自terminal client(串口终端) */
if ( pTermStruct->iSocket == SOCKET_FOR_SERIAL )
{
for ( ulTmp = 0 ; ulTmp < (_U32)pTermStruct->iRecvLen ; ulTmp ++ )
{
if (pTermStruct->szRecvBuf[ ulTmp ] == '\0')
return G_FAILURE ;
ucTmp = (_U8)pTermStruct->szRecvBuf[ ulTmp ] ;
if ( ! CLI_CharProcess ( pTermStruct, ucTmp ) )
return G_SUCCESS ;
}
}
/* 接收字符串来自telnet terminal client,利用telnet的有限状态机 */
/* 对其进行处理 */
else
{
#if CLI_TELNET_SUPPORT
if( G_YES == g_ul_INCLUDE_SUB_MODULE_CLI_TELNET )
{
DBG_ASSERT( G_NULL != g_pfn_CFG_CLI_TelnetEditString );
return g_pfn_CFG_CLI_TelnetEditString(pTermStruct);
}
else
{
CLI_ASSURE_OR_FAIL(0);
}
#endif
}
return G_FAILURE ;
}
/*==================================================================*/
/* 函数名 :CLI_CharProcess */
/* 函数功能 :对单个字符进行处理包括删除,插入,特殊字符处理等 */
/* 输入参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* _U8 ucTmp 待处理的字符 */
/* 输出参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* 返回值 :_U32 0: 接收到一完整命令行并准备提交该命令 */
/* 1: 只接收到一字符并准备继续接收字符 */
/* 被调函数 : */
/*==================================================================*/
_U32 CLI_CharProcess ( PTerm_Data_S pTermStruct, _U8 ucTmp )
{
CLI_ASSURE_OR_FAIL( G_NULL != pTermStruct );
if (pTermStruct->ucInputStatus == KEY_ESC)
{
if (ucTmp == '[')
{
pTermStruct->ucInputStatus = '[';
return G_FAILURE;
}
else
pTermStruct->ucInputStatus = G_NULL;
}
else if (pTermStruct->ucInputStatus == '[')
{
switch(ucTmp)
{
case 'a':
case 'A':
ucTmp = KEY_MOVE_P;
break;
case 'b':
case 'B':
ucTmp = KEY_MOVE_N;
break;
case 'd':
case 'D':
ucTmp = KEY_MOVE_L;
break;
case 'c':
case 'C':
ucTmp = KEY_MOVE_R;
break;
default:
break;
}
pTermStruct->ucInputStatus = G_NULL;
}
if (ucTmp > 0x20 && ucTmp <= 0x7E
&& ucTmp != KEY_MOVE_L && ucTmp != KEY_MOVE_R
&& ucTmp != KEY_MOVE_P && ucTmp != KEY_MOVE_N)
{
CLI_CharInsert ( pTermStruct, (_S8)ucTmp ) ;
if (pTermStruct->iEditStatus == COMMAND_INPUT && (ucTmp == '?' ))
return G_SUCCESS ;
}
else
{
switch (ucTmp)
{
case KEY_CTRL_C: /* 终止字符 */
case KEY_CTRL_Z:
pTermStruct->szEditBuf[0] = (_S8)ucTmp ;
pTermStruct->szEditBuf[1] = '\0' ;
pTermStruct->iCurrentPos = 0 ;
return G_SUCCESS ;
case KEY_ESC:
pTermStruct->ucInputStatus = KEY_ESC;
break;
case KEY_ENTER: /* 回车换行符*/
case KEY_RETURN:
/* 如果是命令编辑状态,需要进行命令输入完整的相应处理 */
if(pTermStruct->iEditStatus == COMMAND_INPUT)
{
CLI_DealWitchCommand(pTermStruct);
}
pTermStruct->iCurrentPos = 0 ;
return G_SUCCESS ;
case KEY_SPACE: /* 空格 */
/* 如果是命令编辑状态,进行命令的自动联想补全 */
if(pTermStruct->iEditStatus == COMMAND_INPUT)
{
CLI_PatchCmdWord(pTermStruct);
}
else /* 否则直接插入空格 */
{
CLI_CharInsert (pTermStruct, ' ');
}
break;
/* 以下为编辑控制字符的处理*/
case KEY_MOVE_L:
/* 光标在行首,不能再左移,警告 */
if ( pTermStruct->iCurrentPos == 0
|| (pTermStruct->szInputCmd[0] != 0 && pTermStruct->iCurrentPos <= (_S32)strlen(pTermStruct->szInputCmd)))
{
CLI_Bell ( pTermStruct ) ;
}
else
{
_S32 iLentgh = (_S32)strlen(pTermStruct->szEditBuf);
// 如果是命令编辑状态,左移时删除最后一个空格,减少
// 用户的操作失误(如果光标不在最后,解释器将拒绝联想)
if (pTermStruct->iCurrentPos == iLentgh
&& pTermStruct->szEditBuf[iLentgh - 1] == 0x20
&& pTermStruct->iEditStatus == COMMAND_INPUT)
{
CLI_DealWithBackSpace(pTermStruct);
}
else
{
/* 光标左移一格 */
pTermStruct->iCurrentPos -- ;
CLI_MoveToCurrentPos ( pTermStruct, (_U32)pTermStruct->iCurrentPos + 1 ) ;
}
}
break;
case KEY_MOVE_R:
if ( (_U32)pTermStruct->iCurrentPos < (_U32)EOS_StrLen ( pTermStruct->szEditBuf ) )
{
/* 将光标右移一格 */
pTermStruct->iCurrentPos ++ ;
CLI_MoveToCurrentPos ( pTermStruct, (_U32)pTermStruct->iCurrentPos - 1 ) ;
}
/* 光标在行首末,警告 */
else
CLI_Bell ( pTermStruct ) ;
break;
case KEY_CTRL_W:
case KEY_MOVE_P: //DOSKEY功能上一条命令
if ( pTermStruct->iEditStatus == COMMAND_INPUT )
{
CLI_PrevCmdDisp( pTermStruct );
}
else /*非命令编辑状态不能进行DOSKEY功能*/
{
CLI_Bell(pTermStruct);
}
break;
case KEY_CTRL_S:
case KEY_MOVE_N: //DOSKEY功能下一条命令
if ( pTermStruct->iEditStatus == COMMAND_INPUT )
{
CLI_NextCmdDisp( pTermStruct );
}
else /*非命令编辑状态不能进行DOSKEY功能*/
{
CLI_Bell(pTermStruct);
}
break;
default:
CLI_EditSpecialKey ( pTermStruct, (_S8)ucTmp ) ;
break;
}
}
return G_FAILURE;
}
/*==================================================================*/
/* 函数名 :CLI_CharInsert */
/* 函数功能 :在字符串编辑缓冲的当前光标位置插入一字符 */
/* 输入参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* _S8 ch 待插入的字符 */
/* 输出参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* 返回值 :无 */
/* 调用函数 :CLI_MoveToCurrentPos ( ) */
/* 被调函数 : */
/*==================================================================*/
_VOID CLI_CharInsert( PTerm_Data_S pTermStruct, _S8 ch )
{
_S32 iTmp ;
if ( pTermStruct == G_NULL )
{
MT_ERRLOG(0);
return;
}
if ( (_U32)EOS_StrLen( pTermStruct->szEditBuf ) + 1 >= (_U32)pTermStruct->iMaxLen )
{
DBG_Out(PID_CLI, MT_DBGOUT_NOTE, "\r\n 编辑缓冲濒临溢出(Term-%d).", pTermStruct->ulTermId);
CLI_Bell(pTermStruct);
return ;
}
/* 将光标后的字符向右移动一格,为待插入的字符留出插入空位*/
iTmp = (_S32)EOS_StrLen ( pTermStruct->szEditBuf ) ;
if (pTermStruct->szEditBuf[iTmp -1] == '?')
return;
while ( iTmp >= pTermStruct->iCurrentPos )
{
pTermStruct->szEditBuf[ iTmp + 1 ]
= pTermStruct->szEditBuf[ iTmp ] ;
iTmp-- ;
}
/* 在当前光标位置出入该字符 */
pTermStruct->szEditBuf[ pTermStruct->iCurrentPos ] = ch ;
/* 控制用户端的屏幕显示,刷新当前光标以后的显示字符, */
/* 即刷新发送缓冲区 */
if (pTermStruct->iSocket != SOCKET_FOR_MML) // 对透传命令不作回显
{
pTermStruct->szSendBuf[ pTermStruct->iSendLen ++ ] = ch ;
}
if ( (_U32)EOS_StrLen( pTermStruct->szEditBuf ) - 1 > (_U32)pTermStruct->iCurrentPos )
{
iTmp = pTermStruct->iCurrentPos + 1 ;
while ( pTermStruct->szEditBuf[ iTmp ] )
pTermStruct->szSendBuf[ pTermStruct->iSendLen ++ ]
= pTermStruct->szEditBuf[ iTmp ++ ] ;
}
pTermStruct->szSendBuf[ pTermStruct->iSendLen ] = '\0' ;
/* 光标位置右移一格 */
pTermStruct->iCurrentPos ++ ;
/* 将光标从行末移到当前光标所在位置 */
if ( (_U32)EOS_StrLen( pTermStruct->szEditBuf ) > (_U32)pTermStruct->iCurrentPos )
CLI_MoveToCurrentPos ( pTermStruct, EOS_StrLen ( pTermStruct->szEditBuf ) ) ;
return ;
}
/*==================================================================*/
/* 函数名 :CLI_EditSpecialKey */
/* 函数功能 :对接收到的特殊字符进行编辑处理 */
/* 输入参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* _S8 ch 待处理的特殊字符 */
/* 输出参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* 返回值 :无 */
/* 被调函数 : */
/*==================================================================*/
_VOID CLI_EditSpecialKey( PTerm_Data_S pTermStruct, _S8 ch )
{
if ( pTermStruct == G_NULL )
{
MT_ERRLOG(0);
return;
}
if ( ISESC( ch ) )
{
CLI_Bell ( pTermStruct ) ;
}
else if ( ISBACKSPACE( ch ) )
{
/*--------------------------------------------------*/
/* 如果用户输入了Backspace键,则对之进行处理 */
/*--------------------------------------------------*/
CLI_DealWithBackSpace ( pTermStruct ) ;
}
else if ( ISDELETE( ch ) )
{
/*--------------------------------------------------*/
/* 如果用户输入了Delete键,则对之进行处理 */
/*--------------------------------------------------*/
CLI_DealWithDelete ( pTermStruct ) ;
}
else if ( ISTAB( ch ) )
{
CLI_Bell ( pTermStruct ) ;
}
else if ( ISCTRLCHAR( ch ) )
{
CLI_CharInsert ( pTermStruct, '^' ) ;
CLI_CharInsert ( pTermStruct, (_S8)(ISCTRLCHAR( ch )) ) ;
}
else
{
CLI_Bell ( pTermStruct ) ;
}
return ;
}
/*==================================================================*/
/* 函数名 :CLI_DealWithBackSpace */
/* 函数功能 :对Backspace键的处理 */
/* 输入参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* 输出参数 :PTerm_Data_S pTermStruct 任务数据指针 */
/* 返回值 :无 */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -