USART、SPI、I2C实训

来源:互联网 发布:mac版office多少钱 编辑:程序博客网 时间:2024/05/19 08:02

经常移植,协议熟悉了,开始动手自己写代码,主要是熟悉工作流程及初始化配置流程。

一,Usart 1)自发自收(rxd与txd在电路板上短接)2),与超级终端通信 3),Usart中断方式接收发送 4),Usart的DMA方式
二,SPI
三,I2C

一,Usart

1)自发自收(rxdtxd在电路板上短接)

1,我觉得我的初始化配置没什么问题,但是调试来调试去都不对。

  后来我仔细看IAR中的寄存器,发现其中的值不会变化。于是拿用了正常的debug口调试,发现寄存器内容也不会变。天哪!这样的话,给我调试带来了麻烦。于是想到调用已经有的配置函数。结果还是不正确。

2,只能拿个实例来跑跑。看看和我的有什么区别。于是还真找到了。能正常跑起来,接着我就用它的配置初始化配置,结果还是有问题。在发送或接受函数中死循环了。接着把发送和接收函数改了,另外,在最后增加了发送和接收使能函数。ok了。

3,最后对比的初始化配置函数,才发现原来没什么大问题。主要跑不起来的原因是发送和接收函数写的不对。于是配置函数都用我之前的,只是发送接收函数调用已有的。结果ok

 

小结:

1,配置初始化过程中,最好使能发送和使能接收放在最后,并且配置的第一行代码,是先reset rxtx,并且disable他们。

2USART 循环方式的发送接收与寄存器相关的流程如下:

参看图如下:

USART、SPI、I2C实训 - ARM爱好者 - ARM爱好者的博客

 

1,发送的数据放在US_THR中,然后就自动输入到TXEMPTY移位寄存器中,然后就自动从pin口输出。

   重点:TXEMPTY的状态就直接反应pin口是否把数据都输出。

   0: There are characters in either US_THR or the Transmit Shift Register, or the   transmitter is disabled.

   1: There are no characters in US_THR, nor in the Transmit Shift Register.

   所以,串口写函数可以如下:

   while ((AT91C_BASE_US1->US_CSR & AT91C_US_TXEMPTY) == 0);

   AT91C_BASE_US1->US_THR=c;

2,接收的数据放在US_RHR中。

   重点:接收的话由RXRDY状态决定。

   0: A character is in the US_THR waiting to be transferred to the Transmit Shift   Register, or an STTBRK command has been

requested, or the transmitter is disabled. As soon as the transmitter is enabled, TXRDY becomes 1.

1: There is no character in the US_THR.

   所以,串口接收函数可以如下:

   while ((AT91C_BASE_US1->US_CSR & AT91C_US_RXRDY) == 0);

 return AT91C_BASE_US1->US_RHR;

 

2),与超级终端通信

1,主要是把之前的发送函数给注销掉,只留个接收函数。就ok了。

2,但是出现了一个问题,US_BRGR,即波特率配置用,Baud Rate =Selected Clock/(16*CD),则没问题,当然SYNC = 0OVER = 0。然而我设置OVER = 1,应该用Baud Rate =Selected Clock/(8*CD)公式,但是接收的数据有问题。没搞明白,over难道不能设置为1

 

3),Usart中断方式接收发送

spi配置中断方式一样。在初始化的最后添加配置中断函数指针,添加USART口使能中断。另外,还要设置寄存器,确定使能中断的具体寄存器。代码我看下就算了,不动手了。

  IRQ_ConfigureIT(BOARD_ID_USART, 0, USART1_IrqHandler);

IRQ_EnableIT(BOARD_ID_USART);

 

BOARD_USART_BASE->US_IER = AT91C_US_RXBUFF;

只要注意,在中断函数中,最后要把AT91C_US_RXBUFF中断给disable掉,否则出不来了。

4),UsartDMA方式

 

另外,参考代码中使用了PDC通道。DMA的原理也很简单,从理论上讲,主要是DMAC中要配置存储器地址和字节长度。内存与外设传输一个字节后,DMAC会自动控制地址加1,字节长度减去1.我也没去查PDC这一章节的寄存器,看了Usart的系统框图,它连接了2PDC,基本看了下代码,就知道了,DMA方式的配置和理论几乎一致。估计不止Usart,只要是连接PDC的接口,应该都是这样配置的。所以这段代码作为备忘。

unsigned char USART_ReadBuffer(AT91S_USART *usart,

                                      void *buffer,

                                      unsigned int size)

{

    // Check if the first PDC bank is free

    if ((usart->US_RCR == 0) && (usart->US_RNCR == 0)) {

 

        usart->US_RPR = (unsigned int) buffer;

        usart->US_RCR = size;

        usart->US_PTCR = AT91C_PDC_RXTEN;

 

        return 1;

    }

    // Check if the second PDC bank is free

    else if (usart->US_RNCR == 0) {

 

        usart->US_RNPR = (unsigned int) buffer;

        usart->US_RNCR = size;

 

        return 1;

    }

    else {

 

        return 0;

    }

}

 

二,SPI

     三周前,自己搞了个arm 926的自发自收程序。是通过设置中断方式,流程基本和Usart配置中断方式类似。其中有片选配置要注意,它有固定位置4个片选和不固定位置16个片选。这些是通过模式寄存器配置的。

spi配置为主机的时候,模式基本要设置3个,片选配置也要配置。 
spi配置为从机的时候,模式设置为SLAVE,片选配置就不用配置了,或者都配置为0。

spi配置为接收中断。当收到数据则产生中断。cortex-m3中配置中断调用的函数和arm 926是不同的。因为cortex-m3有一个NVIC中断寄存器。但是arm 926中是通过aic接口来控制的。nvic与aic的区别不太清楚。
cortex-m3的中断配置是调用如下些函数,放在spi配置初始化前面。
    NVIC_DisableIRQ( SPI_IRQn ) ;
    NVIC_ClearPendingIRQ( SPI_IRQn ) ;
    NVIC_SetPriority( SPI_IRQn, 0 ) ;
    NVIC_EnableIRQ( SPI_IRQn ) ;  
然后调用传输函数的最后,设置一个中断使用spi->SPI_IER =AT91C_SPI_RDRF;接着遇到AT91C_SPI_RDRF中断,则会跳到SPI0_IrqHandler函数中。而SPI0_IrqHandler函数可以在board_cstartup_iar.c中断向量表中找到。

看了网上的资料。原来这么赞美cortex内核。
“NVIC淘汰基于ARM7和ARM9的元件中的进阶中断控制器(AIC),NVIC具有各类型优势,比如中断延迟更短,没有疑似岔断(Spurious Interrupt)这类棘手的问题等。 此外,該向量表在記憶體中的位置現在可變化,即不再固定在地址0x00000000,而是可位於位址空間的任何地方。此外,该向量表在记忆体中的位置现在可变化,即不再固定在地址0x00000000,而是可位于位址空间的任何地方。 因此,不再須透過把SRAM重新鏡射到位址鏡射的開始以完成對異常表的寫入存取,從而也就毋須重新配置指令。因此,不再须透过把SRAM重新镜射到位址镜射的开始以完成对异常表的写入存取,从而也就毋须重新配置指令。

而且,處理器模式也被簡化,隨之影響到硬體堆疊的數目和其初始化。而且,处理器模式也被简化,随之影响到硬体堆叠的数目和其初始化。 ARM7TDMI支援七個工作模式(USR、FIQ、IRQ、SVC、ABT、SYS、UND),這顯示該核心最初是針對具有多工處理和分頁等功能的成熟作業系統而設計。 ARM7TDMI支援七个工作模式(USR、FIQ、IRQ、SVC、ABT、SYS、UND),这显示该核心最初是针对具有多工处理和分页等功能的成熟作业系统而设计。 相反,Cortex-M3是針對微控制器應用從頭開始量身定做,有兩種模式就足夠。相反,Cortex-M3是针对微控制器应用从头开始量身定做,有两种模式就足够。 正常的程式執行採用執行緒模式,中斷則採用處理模式。正常的程式执行采用执行绪模式,中断则采用处理模式。 實際上,ARM7TDMI程式內通常設置有兩個或三個堆疊,一個用於應用程式,一般運行在管理模式(SVC)下;一個用於中斷(IRQ);另一個用於快速中斷(FIQ)。实际上,ARM7TDMI程式内通常设置有两个或三个堆叠,一个用于应用程式,一般运行在管理模式(SVC)下;一个用于中断(IRQ);另一个用于快速中断(??FIQ)。 其餘的處理器模式一般對微控制器應用無用武之地。其余的处理器模式一般对微控制器应用无用武之地。 此外,Cortex-M3設計包含一個(主要)或兩個(主要和進程)堆疊。此外,Cortex-M3设计包含一个(主要)或两个(主要和进程)堆叠。”

三,I2C

  i2c模式寄存器设置的时候,有主机模式和从机模式。从机模式寄存器设置完成后,还要设置从机地址。从理论角度讲,主机和从机的接受方式是一致的。发送的话,主要需要先寻址,找到想要通信的从机,所以从机模式需要为自己设置地址。

现在使用并总结了Usartspii2c。觉得初始化流程都差不多。主要要用的就是配置控制寄存器,模式寄存器,中断使能寄存器。当然在这之前要开启这些接口的clock及开启这些接口的中断使能(如果不用中断方式,则可以不用),在使用这些接口的过程中,主要还会用到,读取接受寄存器的数据,和写入发送寄存器数据。通过读取状态寄存器来设置确定工作状态等。

 

over了,这些东东,真的在使用中应该无需你写的。

0 0
原创粉丝点击