用SPI可变位数实现模拟非标串口
做了一个项目,单片机控制700个步进电机,每个步进电机有3bit数据,每次需要连续发送2100bit数据。步进电机离单片机有十几米远,需要抗干扰能力强的通讯方式,所以选择485通讯。
但是标准串口都是8bit的,可发送两个3bit,有2bit空闲,有点可惜。
看了CW32的SPI,位数可变,最大16位,并且可以单工只发,用来做一个非标串口非常不错,一帧数据可以发送4个步进电机数据12bit。
实际又加了一个控制位,最高位为0表示数据,为1表示命令,共13位,再加上起始位0和停止位1,共15位。
没用晶振,用HSI振荡器即可满足波特率精度要求,3M波特率啊,CW32F003主频24M。 SPI初始化:
GPIOC->AFRL = 0x0300; // PC2复用SPI_MOSI输出
SPI->CR1 = 0x7A54; // 单工只发15位,高位先发,3M波特率
SPI->DR =0xFFFF; // 发送后MOSI高电平,模拟串口空闲时输出高电平 发送程序:
// SPI模拟串口发送13位数据,高位先发
// 注意这是阻塞式,非阻塞可用中断实现。
void spi_tx(u16 data)
{
while((SPI->ISR & 0x01)==0); // 等上次的发完
SPI->DR = (data<<1)+1; // 加上停止位发送
} 程序中调用:
void fsbjdjsj(u8 nms) // 发送步进电机数据
{
spi_tx(0x1811); // 发送跳行信号(同步信号)
...数据整理
for
{
spi_tx(data); // 连续发送步进电机数据
}
...
} 串口就可以了,8个电机数据24bits,刚好放在3个字节中。
页:
[1]