发 帖  
原厂入驻New
[问答] 在PIC18LF45K22微控制器上将USART和SPI结合在一起
93 微控制器 USART
分享
大家好,这是我第一次使用microchip论坛。所以请原谅,如果这不是在论坛上发布的正确方式。我正在进入项目中,我必须从SPI从机获取数据,并将数据从USART发送到PC。我使用的控制器是PIC18LF45K22。作为SPI主板和从板,通信是完美的。类似地,当我将一个PIC配置为USART Tx&Rx时,无论我发送什么,我都会看到数据显示在PC终端上,并且我也接收我发送给PC的数据。但是,当我将两个外围设备组合在一起时,问题就出现了。呃,我有一个主SPI设备,不是PIC18LF45K22,但它是一个MSP432控制器和一个PIC18LF45K22设备,作为SPI从设备。每当SPI从设备接收到MSP432发送的东西,它立即需要把它发送到PC终端。在第一个SPI缓冲区接收之后,PIC18不发送任何东西。这个逻辑似乎是正确的,就像我之前使用CC1310无线板作为从SPI时使用的逻辑一样。不确定我可能做错了什么。我在这种情况下使用中断概念。e代码,如果有人能看到我做错了什么,并指导我采取正确的方法,我将不胜感激。不知道如何附加整个代码。谢谢你Vikram
inter._manager.txt(2.55KB)-下载73次main.txt(2.24KB)-下载56次pin_manager.txt(2.66KB)-下载59次spi.txt(5.01KB)-下载86次
0
2020-4-6 17:05:40   评论 分享淘帖 邀请回答

相关问题

12个回答
非常赞同Susan(关于MCC的过度复杂性),但是建议的替代方案只有在Master发送SPI数据的速度比USART能够重新发送的速度慢时才能起作用。否则,您需要在两者之间使用一个FIFO缓冲区,以及一对状态机来处理“SPI接收”和“US”。艺术发送,或某种方式保持主人关闭之前的字符已经发送。
2020-4-6 17:24:38 评论

举报

另外,我不能使while循环一直等待BF标志检查的另一个原因是,它将消耗CPU功率,尤其是我的应用程序正在电池上运行,我将不能在while循环中这样做。总是运行的是无线电TX RX概念,如果另一个无线电台发送了任何命令,它会监视它吗?所以我不能使用while循环,必须使用中断概念。
2020-4-6 17:43:21 评论

举报

我很理解为什么要使用中断和(大概)睡眠模式来节省电能。但是我建议您首先使用基本功能,然后添加其他层。例如,步骤1是确保一次可以可靠地传递一个字符从SPI到UART。第2步是在缓冲区中添加(如果需要的话,我不知道你的全部要求)。步骤3可能是在返回数据的处理中添加,步骤4是添加剩余的功能。第五步是在使用休眠(或空闲)模式时使其全部工作,因为这可能会改变各个部分的定时,但至少你知道它们基本上按预期工作。根据您所说的,如果您希望通过此设备将命令从PC传递到SPI主机,*和*您希望使用低功率(空闲或休眠)模式,那么我假设SPI主机启动的交换足够快,以便它能够接收为你的申请及时提供命令。不要忘记SPI是一个交换过程,当交换发生时,主管负责。如果你不小心,这会干扰你对低功率睡眠/空闲模式的要求。苏珊
2020-4-6 17:56:31 评论

举报

嗨,苏珊,你打算用DMA吗?由于我使用的是PIC18LF45K22,所以它没有DMA概念,并且我已经通过相同的数据表进行了验证。我已经修改了下面的代码,以便我可以将更多的数据传递给从机端的Tx缓冲区,从而在Rx.include<xc.h>include<string.h>include”中获得更多的数据。mcc_._files/mcc.h"definitionMY_BUFFER_SIZE 2uint8_t数据;uint8_t spi[2];易失性无符号字符r;//从ISRvoid USART_putc(无符号字符c)立即接收的字节;//字节逐字节USART写函数void USART_put(无符号字符*s);//字节串USART写函数uint8_t myTransMITBuff[2 ] = {0xAA,0xBB};空UsARTHARTPC(无符号char C){同时(!)!//等待直到传输移位寄存器为空TXREG2=c;//向TXREG写入字符并开始传输}void USART_put(无符号字符*s){.(*s){USART_putc(*s);//发送由s++指向的字符;//增加指向下一个字符的指针位置}void main(void main)}void main{uint8_t spi计数器=0; //初始化设备SYSTEM_初始化();设备SYSTEM_初始化();USART_put("Hi这是测试程序\\\\\\\\\\\\\\\\\\\\\n n n n n_n”);USART_USART_put设置()USA设备SYSTEM设备SYSTEM设备SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM SYSTEM系统系统系统系统系统初始化_系统系统系统SYSTEM_初始化_初始化(SYSTEM_初始化_初始化_初始化_初始化(spi计数器=0;对于(数据=0;数据&lt MY_BUFFER_SIZE;数据+++){USART_putc(spi[数据]]);LED_RED_Togg();_延迟(50000);_延迟(50000);}SSP1BUF=0x延迟(50000);}SSP1BUF=0x延迟(50000);}SSP1BUF=0xBBBB;._TXRX_DONE_DONE_DONE_Set低();}板_TXXXXXXXXXXXXXXXXXXXXXXXXXXXXDONE_DONE_Set低((Set低低低低低低();}}无符号字符SPI_I_Read(void){//Wait数据传输/接收完成,(!)SSP1STATbits.BF; ._TXRX_DONE_Set.();.(SSP1BUF);}无符号spiDataReady()//检查数据是否准备好读取{如果(SSP1STATbits.BF)返回1;否则返回0;}._TXRX_Done_Set.()和Set.()为主机发送下一个数据字节提供了延迟机制。这是错误的,请建议。
2020-4-6 18:32:31 评论

举报

好的,我在这里完成了。你显然不想学怎么做。
2020-4-6 18:37:59 评论

举报

如果我不想知道为什么我要问这么多问题。最令人困惑的是如何制作FIFO缓冲区。因为当我阅读其他PIC的数据表时,它们有单独的Tx和Rx缓冲区,例如PIC24,这与我正在使用的PIC18单片机不同。现在我不能更改PIC,因为硬件已经完成生产。并且当您提到数据到达的速度快于我能够发送的速度时,我并不担心暂时发回Master的数据,因为可以忽略这些数据,但是从Master接收的数据更加重要为了减慢速度,我使用了SPI传输之间上下拉动的GPIO线。如果我正确地理解了FIFO,就如同在调用从端SPI_Read之前创建具有虚拟字节的缓冲区一样,以便当Masters拉动时E时钟线发送数据,从TX已经响应于从主SPI发送的数据排队。
2020-4-6 18:57:00 评论

举报

正如其他人所说,这可能是因为你没有足够快地处理字符,或者你没有使用“SS”信号,并且SCK线上有噪声导致从机响应不正确。另外,我并不是建议你只测试一个字符。让奴隶先可靠地交换大量字符,然后从那里继续移动。对于PIC来说,情况并非如此。看看图15-1,你会看到缓冲区有不同的读写路径。在这个设备的数据表中(至少在我的快速阅读中),它并没有真正清楚地表明这意味着(实际上)存在两个具有相同名称的寄存器。当写入缓冲区以不覆盖最后接收的值时,并且也不会在下一个交换机上自动发送最后接收的值。只要在适当的时间执行访问,就可以将它们视为单独的读和写缓冲区(参见第152.1节的底部邻接缓冲区,当您写入时,它不会开始双缓冲。苏珊
2020-4-6 19:33:39 评论

举报

谢谢大家的建议。我试图在代码中实现FIFO概念,但是它仍然不能工作。即使逻辑分析器中MOSI行的数据显示出正确的值,我仍然在缓冲区中得到垃圾值,并将其存储。但是MISO行的值是不同的。从某种意义上说,它没有显示我发送的内容,而是显示我在MOSI线路上收到的内容,并且也显示每个备用字符。例如,从主SPI中,我发送ascii字符0-9,然后是A-Z,然后是a-z,我在MOSI线路上正确地看到这一点,但是在MISO线路上,每个字符替换字符被某个固定值替换,有时是0x8A,有时是0xE6,有时是0xE6。例如,我进入MISO行:'138'、's'、'138'、'u'、'138'、'w'、'138'、'y'、'138'……所以如果您看到序列之间的字符被某个常量字符替换。我也提供了足够的延迟。在将CS线拉高之前在主SPI上设置GPIO线,以便从机不会遗漏任何字符。此外,我还尝试在主机和从机之间设置GPIO线,该GPIO线在从机侧输出并在主侧输入。因此,一旦接收到字符,我就把线拉高,以便通知主控不要发送下一个数据缓冲区,并且只有当数据被传输到USART时,我才把线拉低。这甚至不起作用。下面是我试图实现FIFO概念的地方:if(inptr==outptr){USART_put("Buffer="{r\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\n n n n n”””));}}}spi spi spi spi SP spi spi spi spi spi spi sn_n n}\\\\_if((inptr+1)==MY_BUFFER_SIZE){inptr=0;}USART_putc(spi[outptr++]);._TXRX_DONE_Set.();_.(50000);GREEN_LED_Toggle();if(outptr==MY_BUFFER_SIZE){outptr=0;}甚至尝试了“Gort2015”建议的概念,但是甚至没有实现。有了SPI数据,我们可以在SPI_read中运行4次循环,因为它将总是上传到SSP1BUF中的新值。但是,当我们一次写入4个字节到SSP1BUF时,SSP1BUF就会被覆盖,因为从节点不能启动传输,而当主节点启动传输时,SSP1BUF就会被覆盖。任务它得到字节,并在同一个SSP1BUF上加载一些值,我们必须读取它以使其空。它将如何工作?最后,FIFO概念只有在我必须获取一个字节并立即将该字节转发到USART来显示时才有用。但是我正在尝试的应用程序是这样的,主SPI一次发送240字节的数据,该数据应该由从spi读取并通过美国广播电台总共有130块240字节的SPI主机要发送,同时每个块必须在SPI从机接收到另一个块之前发送到USART。不确定FIFO概念将如何解决这个问题。谢谢Vikram
2020-4-6 19:57:37 评论

举报

每次M进行写操作时,将S应答设置为忙或不忙。当S从M读取数据时,S加载spi为忙,如果M尝试WR,S重新加载SPI为忙。这给了你在世界上所有时间来使用UART。他们交换的含义数据从S总是一个COM。过时了。你试过你的主人的回环吗?测试奴隶也是如此。一个命令结构只是处理S SPI COM的方法。缓冲区是可选的。再试一次。你可以让S做比UART更多的事情,那个芯片可以控制液晶,键盘,midi,甚至像双核微处理器一样为你编码。你也可以使用S RAM。我还有UART在另一个芯片上,但不是在同一个板上。我使用M SPI通过2.4GHz无线电发送命令。S执行它必须执行的操作,但是它让M知道它正在通过交换机忙碌。M在发出命令时总是检查返回结果,以确保S已经准备好。不管它是否花费1微秒或1小时。S芯片使用uart,做其他事情,并且是2米远。我经历过两堵墙。永远不要错过,如果你按照我的建议去做,你也会得到同样的结果。
2020-4-6 20:04:57 评论

举报

这是spi设备的一个典型命令。->command:read->address->sendcount接下来读取4个字节,再读取就返回status_ok。设置为16位模式以访问S内存。
2020-4-6 20:21:51 评论

举报

即使我说读了(帖子_18),交换仍然会发生。双方都必须检查他们的回报是否繁忙/信息。如果S忙(数据>uart),那么M必须等待轮到它了。可能发生错误,如UART向下,检查返回值。
2020-4-6 20:33:32 评论

举报

从编程的中断和硬盘崩溃的事实来看。该死的希捷)太多的时间编码对YA来说是不好的,你开始梦想为什么代码不工作。
2020-4-6 20:43:14 评论

举报

只有小组成员才能发言,加入小组>>

108个成员聚集在这个小组

加入小组

创建小组步骤

关闭

站长推荐 上一条 /7 下一条

快速回复 返回顶部 返回列表