友善mini2440裸机开发源码
源码+开发工具
开发工具:minitools、gcc-4.4.3、vim等
**我们需要先设置cpu工作模式+关闭看门狗+关闭中断后再执行我们自己的代码,因为本文是将代码下载到内存中运行,所以不具备跳转绝对地址的能力,也就不能处理中断。
1. led
mini2440有4个可供用户编程的led,分别是nled_1、nled_2、nled_3、nled_4:
他们分别连向GPB5、6、7、8,由于这里的led接入了上拉电阻,我们的cpu引脚应输出0而使led发光,输出1led熄灭。
接下来,我们先查看s3c2440的用户手册,找到GPB组的寄存器组:
这里就是我们需要编程的寄存器。第一个是GPB组IO的控制寄存器,用于选择配置引脚工作模式,第二个是数据寄存器,如果引脚被配置为输入口或其他功能口,我们将从这个寄存器中读出对应的数据。如果作为输出口,我们就从这个寄存器中写入需要输出的数据。最后是上拉寄存器。s3c2440每个GPIO的引脚都内部配置了上拉功能,不需要的时候写1关闭即可。
代码链接:https://download.csdn.net/download/weixin_38716790/12085350
2. 串口
mini2440有3个可编程串口,分别是串口0、1、2,其中串口0已经接了RS232接口出来,之前我调试串口1的时候自己用的ttl转232模块,上面用了max3232芯片,然后我用板子5V电源给它供电,一直有乱码,一查好几天才查到原因,囧。。。
串口0的编程设计GPIO+UART两个模块。所以我们需要配置两个模块的寄存器,首先是GPIO:
由图可知,我们需要配置GPH2、3
所以我们应该配置(*(volatile unsigned long )]0x56000070) | = 0x50;
取消上拉:((volatile unsigned long *)0x56000074) &= ~(0x3 << 2);
接下来设置UART,我们先看一下UART的工作原理:
假设现在我们要发送数据到串口,我们需要将数据先写入发送缓存寄存器,然后由控制单元控制发送移位发送数据到TXD脚上。发送移位和接收移位的时钟由波特率生成器提供。而波特率生成器的时钟源来源于PCLK、FCLK/n、UEXTCLK。
如果cpu写入发送缓存寄存器的速度比波特率要高,那么可能会导致数据丢失。所以我们在控制好写入的速度,或者在写入前检测串口发送移位寄存器是否为空。
对于接收数据的情况,也是相同的,外部数据会先接收到接收缓存寄存器中,然后等待控制单元的读取。如果接收的数据过多,也就是对方发送数据的速度大于波特率,那么数据也可能丢失。所以接收缓冲寄存器中的内容我们要及时读走,或者使用流控来控制通信双方数据的发送和接收。
数据通信的时序:在给定波特率下,发送端发送一个帧数据,先拉低TXD,作为起始位,然后发送5-8位数据,然后发送校验位,最后发送1-2位结束位,然后数据线拉高。接收方检测到数据低电平,开始接收数据,校验位,结束位,数据线被拉高。
s3c2440的串口支持DMA和中断的操作,但是我们这里没有使用,我们使用的是轮询的方式进行数据的接收发送。看看串口使用的寄存器:
行控制器ULCON:用于设置数据格式,我们使用的是8n1,即(*(volatile unsigned long )0x50000000) = 0x03;
UCON:通道控制寄存器,配置通道的工作模式,我们配置发送接收模式为polling mode,不使用send break signal、loopback mode、不使用中断、时钟源选择PCLK。所以,((volatile unsigned long )0x50000004) = 0x05;
最后,设置我们的波特率,s3c2440波特率的设置:
写入波特率分频寄存器的值 = (int)(PCLK/(baudrate * 16)) - 1;
我这里设置的buadrate=115200,PCLK经过分频之后是50MHZ,所以((volatile unsigned long *)0x50000028) = 0x1A;
到这里,我们的初始化需要操作的寄存器就结束了。下面是我们在处理数据的发送和接收的时候。需要访问的寄存器:
代码链接:https://download.csdn.net/download/weixin_38716790/12085359
3.nandflash
s3c2440含有一个nandflash控制器。我们利用它来实现nandflash的简单读写擦除操作。
简介关于nandflash启动的说明可以看看手册。
我们直接看nandflash控制器原理和寄存器。
由图可知,nandflash控制器接到了AHB总线上,所以使用的是HCLK时钟作为时钟源(时钟部分请看手册,12M晶振经过MPS提升之后生成FCLK、PCLK、HCLK,PCLK作为APB总线时钟使用,HCLK作为AHB总线时钟使用,我代码使用的是400MHZFCLK、时钟比率F:H:P为1:4:8)。APB总线操作SFR寄存器对nandflash控制器进行操作、ECC校验等。
往下看
这四个引脚用于配置nand的信息,硬件已经设置好。我们使用的是k9f2g08u0c,5个地址周期,8位线宽,1page=2k。nandflash控制器上电后会自动检测这4个引脚的值,然后设置相应寄存器的位
上图是当TACLS、TWRPH、TWRPH1 = 1,0,0时,写命令/地址时HCLK、CLE/ALE和WE的关系,以及读写数据时HCLK和WE/RE的关系。
当我们要写入地址或者命令时,要先进行锁存使能,然后才能拉低WE信号线,然后将地址或命令写入nandflash。最后要先释放WE然后才能释放ALE、CLE。
当我们要写入或读取数据时,开启WE/RE后,写入数据即可。
我们选择TACLS>=1(要求TACLS=Tcls-Twp =Tals-Twp >= 0,而Tcls和Twp的最小值都是12ns,TACLS可取任意给定值) TWRPH>=2(查看nandflash的数据手册,可知芯片要求WE持续的时间最小是12ns,我们的HCLK是100MHz,也就是一周期10ns。所以需要两个周期以上的时间),TWRPH=0,也就是一个HCLK周期;
RnB检测:检测nandflash是否忙信号。
寄存器设置这里不细讲,具体看代码即可。这里举例讲一下读数据的编程顺序:
首先,对nandflash操作之前需要将nandflash复位,然后使能片选,接下来才写入命令、地址、数据等。
nandflash读操作:
打开片选;
使能RnB;
NFCMMD = 0x00;
NFADDR = coladdr0-8;
NFADDR = coladdr9-15;
NFADDR = rowaddr0-8;
NFADDR = rowaddr9-15;
NFADDR = rowaddr16-23;
NFCMMD = 0x30;
while(等待不忙);
for(i=0;i<2048;i++)
{
ch[i] = NFDATA; //读出数据
}
关闭片选;
如果看手册时序图有延迟的地方我们也得延迟一下哈。要不读到的数据可能出错
写操作和擦除等操作不再叙述。
代码链接:https://download.csdn.net/download/weixin_38716790/12085356
关于ADC的代码、pwm、中断的代码、我打包上传了,具体的原理不是很复杂,中断需要将代码下到nandflash运行。我的板子中断貌似是有问题,网上别人运行成功的带代码+我自己的代码在我的板子上都运行不全。各位可以在自己的板子上跑跑看。
代码链接:https://download.csdn.net/download/weixin_38716790/12090952
来源:CSDN
作者:weixin_38716790
链接:https://blog.csdn.net/weixin_38716790/article/details/103867079