DSP28335与simulink进行串口中断模式通信并收发double类型数据
- 一、DSP28335串口中断模式通信
- 1.1、main函数
- 1.2、UARTa_Init()函数
- 1.3、运行结果
- 二、与simulink进行串口通讯并收发double类型数据
- 2.1 matlab中的模块
- 2.2 DSP28335程序
- 2.3、运行结果
- 2.4、错误提示
- 总结
一、DSP28335串口中断模式通信
本程序是DSP28335中的串口程序,其原理是DSP28335接收到8个单字节(注意是8个数据,每个数据是1个字节(8bit))的数据后,触发中断;然后将每个数据加1后返回。里面我没说到的函数可以在TI官网上的例程里给出,可以下一个TI给的SCI例程,在此基础上结合我给的函数修改。
1.1、main函数
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80#include "DSP2833x_Device.h" // DSP2833x Headerfile Include File #include "DSP2833x_Examples.h" // DSP2833x Examples Include File #include "uart.h" Uint16 sdataA[8]; // Send data for SCI-A Uint16 rdataA[8]; // Received data for SCI-A __interrupt void sciaTxFifoIsr(void); __interrupt void sciaRxFifoIsr(void); /******************************************************************************* * 函 数 名 : main * 函数功能 : 主函数 * 输 入 : 无 * 输 出 : 无 *******************************************************************************/ void main() { InitSysCtrl(); InitPieCtrl(); IER = 0x0000; IFR = 0x0000; InitPieVectTable(); EALLOW; // This is needed to write to EALLOW protected registers PieVectTable.SCIRXINTA = &sciaRxFifoIsr;//接收中断函数 PieVectTable.SCITXINTA = &sciaTxFifoIsr;//发送中断函数 // PieVectTable.SCIRXINTB = &scibRxFifoIsr; // PieVectTable.SCITXINTB = &scibTxFifoIsr; EDIS; UARTa_Init(4800);//设置波特率为4800 PieCtrlRegs.PIECTRL.bit.ENPIE = 1; // Enable the PIE block PieCtrlRegs.PIEIER9.bit.INTx1=1; // PIE Group 9, int1,使能scia的RX中断 PieCtrlRegs.PIEIER9.bit.INTx2=1; // PIE Group 9, INT2,使能scia的TX中断 // PieCtrlRegs.PIEIER9.bit.INTx3=1; // PIE Group 9, INT3 // PieCtrlRegs.PIEIER9.bit.INTx4=1; // PIE Group 9, INT4 IER = 0x100; // Enable CPU INT EINT; while(1) { } } __interrupt void sciaTxFifoIsr(void) { //这个发送中断函数只是在发送完中断后置位,使其可以重复发送,如果想不要这个函数,应该是需要设置为禁止发送中断触发(我个人理解) SciaRegs.SCIFFTX.bit.TXFFINTCLR=1; PieCtrlRegs.PIEACK.all|=0x100; //要想在接收数据后重新发送回去,相应的发送中断必须复位,否则无法再次发送数据(中断占用) } // // sciaRxFifoIsr - // __interrupt void sciaRxFifoIsr(void) { Uint16 i; for(i=0;i<8;i++) { rdataA[i]=SciaRegs.SCIRXBUF.all; // Read data } for(i=0; i< 8; i++) { SciaRegs.SCITXBUF=rdataA[i]+1; //对接收到的数据+1 } SciaRegs.SCIFFRX.bit.RXFFOVRCLR=1; // Clear Overflow flag SciaRegs.SCIFFRX.bit.RXFFINTCLR=1; // Clear Interrupt flag PieCtrlRegs.PIEACK.all|=0x100; // Issue PIE ack }
1.2、UARTa_Init()函数
以下程序是我在
http://www.prechin.net/forum.phpmod=viewthread&tid=35264&extra中的DSP云盘里的资料找的,并进行了修改,主要是修改了TX和RX中断使能。输入的是波特率,对SCIA进行配置。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40void UARTa_Init(Uint32 baud) { unsigned char scihbaud=0; unsigned char scilbaud=0; Uint16 scibaud=0; scibaud=37500000/(8*baud)-1; scihbaud=scibaud>>8; scilbaud=scibaud&0xff; EALLOW; SysCtrlRegs.PCLKCR0.bit.SCIAENCLK = 1; // SCI-A EDIS; InitSciaGpio(); //Initalize the SCI FIFO SciaRegs.SCIFFTX.all=0xE068;//8个int深度的发送和接收数据 SciaRegs.SCIFFRX.all=0x2068;//反正我的理解是接收和发送深度必须相同 SciaRegs.SCIFFCT.all=0x0; // Note: Clocks were turned on to the SCIA peripheral // in the InitSysCtrl() function SciaRegs.SCICCR.all =0x0007; // 1 stop bit, No loopback // No parity,8 char bits, // async mode, idle-line protocol SciaRegs.SCICTL1.all =0x0003; // enable TX, RX, internal SCICLK, // Disable RX ERR, SLEEP, TXWAKE SciaRegs.SCICTL2.all =0x0003; SciaRegs.SCICTL2.bit.TXINTENA =1; SciaRegs.SCICTL2.bit.RXBKINTENA =1; SciaRegs.SCIHBAUD =scihbaud; // 9600 baud @LSPCLK = 37.5MHz. SciaRegs.SCILBAUD =scilbaud; // SciaRegs.SCICCR.bit.LOOPBKENA =1; // Enable loop back SciaRegs.SCICTL1.all =0x0023; // Relinquish SCI from Reset }
剩下的函数基本都是TI库函数自带的了。
1.3、运行结果
使用了STC公司的串口调试助手进行测试,也可以用别的串口调试助手,调试步骤如下:
- 先打开STC的串口调试助手,并打开串口
- 通过CCS下载程序到DSP28335上(RAM或Flash),进入调试阶段
- 通过串口调试助手收发数据,注意只有发送8个数据后才会有结果返回,因为我们设置的是8个深度的接收中断。
以上就是程序运行结果了;可以看到DSP28335的串口中断已经成功运行了。
二、与simulink进行串口通讯并收发double类型数据
simulink具有强大的数据处理功能,如果我们想通过simulink与TI的DSP28335进行通信,可按如下步骤来。需要注意的是,一般的UART通信只能以ASCII码的形式发送,也就是一次发送1个字节;要想发送double类型数据需要进行一定的修改。
2.1 matlab中的模块
simulink中的串口通讯模块有Serial configuration(进行串口配置),serial send(发送数据),serial receive(接收数据)。
每个模块配置如下:
Serial Receive中的Data Size表示的是接收数据个数,这里只接收一个double类型数据,所以是1,如果接收两个,那么此处写为[1 2],可以使用一个1输入,2输出的mux模块,第一条线就会输出第一个收到的数,第二条线就会输出第二个收到的数。
2.2 DSP28335程序
首线明确一点,matlab中的double类型数据是64位的;CCS编译器中的数据最低是16位的,最高的long double类型数据是64位的,串口通信每次发送8位数据(串口发送先发送低位,再发送高位)。
本程序发送一个double数据给单片机,单片机对该数据+1后再通过串口返回。
参考https://blog.csdn.net/humanking7/article/details/80851223
定义并声明一个联合体
1
2
3
4
5
6
7typedef union { char buff[4];//用于发送和接收,注意4个char长度和一个long double长度相等 long double number;//用于解码 }Un_sendData;//定义double联合体数据 Un_sendData trdata;
接收数据中断改进
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30__interrupt void sciaRxFifoIsr(void) { Uint16 i; for(i=0;i<8;i++) { if(i%2==0) {trdata.buff[i/2]=SciaRegs.SCIRXBUF.all;} else {trdata.buff[i/2]|=(SciaRegs.SCIRXBUF.all<<8);}//由于SCIRXBUF是16位寄存器,对接受到的8bit数据进行移位操作,填充未补满的char高8位 // Read data } trdata.number+=1;//加1后输出验证 for(i=0; i<8; i++) { if(i%2==0) {SciaRegs.SCITXBUF=(trdata.buff[i/2]&0x00FF);} // Send data else {SciaRegs.SCITXBUF=(trdata.buff[i/2]>>8);} } SciaRegs.SCIFFRX.bit.RXFFOVRCLR=1; // Clear Overflow flag SciaRegs.SCIFFRX.bit.RXFFINTCLR=1; // Clear Interrupt flag PieCtrlRegs.PIEACK.all|=0x100; // Issue PIE ack }
2.3、运行结果
看到虽然运行比较慢,但结果是正确的。
2.4、错误提示
- 错误1
原因是在单片机连好之前打开了matlab。把matlab关掉,连好单片机,然后打开matlab就可以了
- 错误2
我个人理解由于单片机只能处理离散数据,所以需要对matlab进行相应设置,使simulink处理离散数据。
解决方法:
总结
第一次发博客,写了这么多字,点个赞吧。可以留言交流。
最后
以上就是现实自行车最近收集整理的关于DSP28335与simulink进行串口中断模式通信并收发double类型数据一、DSP28335串口中断模式通信二、与simulink进行串口通讯并收发double类型数据的全部内容,更多相关DSP28335与simulink进行串口中断模式通信并收发double类型数据一、DSP28335串口中断模式通信二、与simulink进行串口通讯并收发double类型数据内容请搜索靠谱客的其他文章。
发表评论 取消回复