Funpack5-1 - 用FRDM-MCXA346实现的串口shell
该项目使用了FRDM-MCXA346,实现了串口接收并控制LED灯的设计,它的主要功能为:通过串口给FRDM-MCXA346添加了个shell,可以使用命令控制LED灯的效果。
标签
嵌入式系统
LED
串口
Shell
aramy
更新2026-03-04
16

一、硬件介绍:

FRDM-MCXA346 是 NXP 推出的一款紧凑型、可扩展的开发板,基于 MCX A346 微控制器,专为工业物联网 (IoT) 和消费电子应用的快速原型设计而优化,特别擅长电机控制和混合信号处理

7749e1a185604c599c2e59797e16ed60.jpg

二、任务选择:

这次任务,任务1:串口通信。实现了使用MCXA346开发板的UART串口输出“Hello, DigiKey Funpack 5-1”;还完成了一个简单的shell。能实现一个能读取、解析并执行用户输入命令的简易命令行解释器,并能控制板载的LED灯。

三、设计思路:

image.png

系统上电后,初始化串口和LED的gpio口。然后监听串口,在串口上获得消息后,就构建命令字,遇到回车构建完成。然后解析命令字,如果解析成功就按命令字执行相应操作。

四、任务实现:

开发工具使用官方提供的MCUXpressoIDE。使用“hello world”例程做为项目的模版进行修改。

image.png

image.png

因为项目中要使用到串口和板载的LED灯,所以先检查管脚配置,确保对应功能的硬件已经被设置好。

image.png

首先完成基础任务,通过UART串口输出“Hello, DigiKey Funpack 5-1”。这里初始化板子后,将三个板载的LED灯设置为输出,并设置为关闭状态。然后再通过串口输出指定字符串。

	/* Init board hardware. */
BOARD_InitHardware();
/* Init output LED GPIO. */
GPIO_PinInit(BOARD_LED_RED_GPIO, BOARD_LED_RED_GPIO_PIN, &led_config);
GPIO_PinInit(BOARD_LED_GREEN_GPIO, BOARD_LED_GREEN_GPIO_PIN, &led_config);
GPIO_PinInit(BOARD_LED_BLUE_GPIO, BOARD_LED_BLUE_GPIO_PIN, &led_config);
PRINTF("Hello, DigiKey Funpack 5-1\r\nfunpack>$");

然后循环接收串口消息,直至收到回车或异常(超出缓冲区限定或串口异常)。


	while (1) {
receivedChar = GETCHAR();
PUTCHAR(receivedChar);
/* 处理接收到的字符 */
if (receivedChar == '\r' || receivedChar == '\n') {
/* 如果是回车或换行符,说明命令输入完成 */
PRINTF("\r\n");
/* 解析命令 */
parseCommand(cmdBuffer, &parsedCmd);
/* 处理命令 */
processCommand(&parsedCmd);
/* 重置命令缓冲区和索引 */
memset(cmdBuffer, 0, CMD_BUFFER_SIZE);
cmdIndex = 0;
/* 重新显示命令提示符 */
PRINTF("funpack>$ ");
} else if (receivedChar == '\b' || receivedChar == 127) {
/* 如果是退格键,删除最后一个字符 */
if (cmdIndex > 0) {
cmdIndex--;
cmdBuffer[cmdIndex] = '\0';
/* 重新打印命令行,覆盖旧内容 */
PRINTF("\rfunpack>$ %s", cmdBuffer);
/* 用空格清除剩余的旧字符 */
for (int i = cmdIndex; i < CMD_BUFFER_SIZE - 1; i++) {
PRINTF(" ");
}
/* 回到正确的光标位置 */
PRINTF("\rfunpack>$ %s", cmdBuffer);
}
} else {
/* 普通字符,添加到命令缓冲区 */
if (cmdIndex < CMD_BUFFER_SIZE - 1) {
cmdBuffer[cmdIndex++] = (char) receivedChar;
}
}
}

然后将缓冲区中收到的字符串去构建成命令字。

/* 命令解析结构体 */
typedef struct {
char cmd[32]; /* 命令名称 */
char params[MAX_PARAMS][16]; /* 参数数组 */
int paramCount; /* 参数数量 */
} parsed_cmd_t;


/**
* @brief 解析命令字符串
* @param buffer 输入的命令字符串
* @param cmd 解析后的命令结构体
*/
void parseCommand(char *buffer, parsed_cmd_t *cmd) {
/* 重置解析结果 */
memset(cmd, 0, sizeof(parsed_cmd_t));
cmd->paramCount = 0;
/* 跳过前导空格 */
while (*buffer == ' ') {
buffer++;
}
/* 解析命令名称 */
char *token = strtok(buffer, " ");
if (token != NULL) {
/* 复制命令名称 */
strncpy(cmd->cmd, token, sizeof(cmd->cmd) - 1);
cmd->cmd[sizeof(cmd->cmd) - 1] = '\0';
/* 解析参数 */
token = strtok(NULL, " ");
while (token != NULL && cmd->paramCount < MAX_PARAMS) {
/* 复制参数 */
strncpy(cmd->params[cmd->paramCount], token,sizeof(cmd->params[0]) - 1);
cmd->params[cmd->paramCount][sizeof(cmd->params[0]) - 1] = '\0';
cmd->paramCount++;
/* 获取下一个参数 */
token = strtok(NULL, " ");
}
}
}

最后就是根据命令字来执行相应的动作了。这里给定的动作有3个。help:显示全部命令字。echo:用来回显输入内容。led:控制led灯的状态。可以控制LED灯的颜色、亮灭。

image.png

五、效果展示:

点亮红色led灯

image.png

17aac2eea73b0ec7ccff1061490d7f8e.jpg

3e5ad1f262e05aa9b08ef3bbd5e56b52.jpg

image.png

三个颜色LED灯都点亮。

46b10995ba59f06d7f7f9655067597a3.jpg

六、心得体会:

感谢得捷和硬禾科技。这块FRDM-MCXA346开发板很好上手,自己尝试着做了个简单的shell,更进一步了解了命令字的解析和串口通讯。收获满满,也感谢各位老师的指导。






附件下载
frdmmcxa346_hello_world.zip
团队介绍
单片机业余爱好者,瞎捣鼓小能手。
团队成员
aramy
aramy
评论
0 / 100
查看更多
硬禾服务号
关注最新动态
0512-67862536
info@eetree.cn
江苏省苏州市苏州工业园区新平街388号腾飞创新园A2幢815室
苏州硬禾信息科技有限公司
Copyright © 2024 苏州硬禾信息科技有限公司 All Rights Reserved 苏ICP备19040198号