上一篇文章寫的是linux下通過(guò)gcc完成程序源文件的編譯執(zhí)行的過(guò)程。以及makefile文件的編寫,最后在終端平臺(tái)輸出myhello word!
有了這個(gè)基礎(chǔ),這次學(xué)習(xí)的就是通過(guò)linux編譯生成的代碼在ARM上完成硬件實(shí)現(xiàn)。因?yàn)檫€不涉及到系統(tǒng)移植,所以還是裸板程序開(kāi)發(fā)。
1.源代碼編寫
ARM裸板程序需要代碼原料主要包括:匯編文件,C文件,makefile文件。每個(gè)文件都有各自功能。
(1)匯編文件
完成關(guān)看門狗;配置時(shí)鐘;初始化sdram;設(shè)置棧;以及跳轉(zhuǎn)到C函數(shù)執(zhí)行入口(相當(dāng)于main函數(shù)),代碼如下(該例程不需要配置時(shí)鐘和sdram)。
@******************************************************************************
@ File:crt0.S
@ 功能:通過(guò)它轉(zhuǎn)入C程序
@******************************************************************************
@注:正常匯編程序還需要初始化時(shí)鐘,SDRAM功能,但對(duì)于點(diǎn)亮LED不需要。直接使用12Mhz
.text
.global _start
_start: @程序代碼段開(kāi)始處,各段在鏈接腳本定義
ldr r0,=0x53000000 @看門狗控制寄存器地址(32位地址賦值語(yǔ)句,r0地址為0x53000000)
@ ldr和mov區(qū)別就是,ldr傳輸32位數(shù)據(jù),而mov只能傳8位數(shù)
mov r1, #0x0 @立即數(shù)賦值給r1寄存器
str r1, [r0] @把r1寄存器內(nèi)的數(shù)據(jù)0x0給r0地址
@以上三條語(yǔ)句為看門狗控制寄存器賦值為0
ldr sp,= 4*1024 @設(shè)置堆在大小為4K(NAND FLASH前4k)
bl main @跳轉(zhuǎn) 到main函數(shù),同時(shí)保存了下一條指令地址
haltloop:
(2)C文件
匯編的代碼量相對(duì)較少,只執(zhí)行一些必要的初始化功能,真正功能部分在C文件里。C文件主要執(zhí)行:寄存器地址宏定義;外設(shè)初始化;功能實(shí)現(xiàn)等。
本例點(diǎn)亮的led引腳是GPF4,因此需要查詢2440的參考手冊(cè),查看GPF的相關(guān)寄存器地址,主要配置的寄存器是GPFCON(控制寄存器)和GPFDAT(數(shù)據(jù)寄存器)。GPFCON主要控制引腳的工作模式(模式有:輸入,輸出,復(fù)用),其中每?jī)晌豢刂埔粋€(gè)引腳的狀態(tài),從下圖可以看出:
引腳的高低電平由GPFDAT控制,每一位控制一個(gè)引腳,如圖:
所以學(xué)會(huì)看芯片手冊(cè)還是很重要的,明白各個(gè)寄存器并進(jìn)行編程,同時(shí)應(yīng)該掌握移位操作,在寄存器編程比較常用。該部分代碼如下:
#define GPFCON (*(volatile unsigned long*)0x56000050)
#define GPFDAT (*(volatile unsigned long*)0x56000054)
#define GPFUP (*(volatile unsigned long*)0x56000058)
#define GPIO_Pin_0 ((volatile unsigned char)0x00)
#define GPIO_Pin_1 ((volatile unsigned char)0x01)
#define GPIO_Pin_2 ((volatile unsigned char)0x02)
#define GPIO_Pin_3 ((volatile unsigned char)0x03)
#define GPIO_Pin_4 ((volatile unsigned char)0x04)
int main()
{
GPFCON = 0X01<<(GPIO_Pin_4*2); //GPF_4輸出模式
GPFDAT = ~(0X01 << (GPIO_Pin_4)); //GPF_4輸出0
return 0;
}
(3)makefile文件
編寫編譯規(guī)則,和上篇文章原理一樣。linux有專門針對(duì)ARM的編譯工具,主要用到的有這個(gè)3個(gè):
arm-linux-gcc:主要在文件編譯時(shí),由(.C/.S)文件編程成.o目標(biāo)文件時(shí)使用。
arm-linux-ls:主要對(duì)所有.o目標(biāo)文件鏈接生成一個(gè)可執(zhí)行文件
arm-linux-objcopy:主要對(duì)可執(zhí)行文件進(jìn)行二進(jìn)制轉(zhuǎn)換成.bin可以燒錄用的文件
文件代碼如下:
led_on.bin : crt0.S led_lighton.c
arm-linux-gcc -g -c -o crt0.o crt0.S
arm-linux-gcc -g -c -o led_lighton.o led_lighton.c
arm-linux-ld -Ttext 0x0000000 -g -o led_on_elf crt0.o led_lighton.o
arm-linux-objcopy -O binary -S led_on_elf led_on.bin
clean:
rm -f led_on.bin led_on_elf *.o
上述的3個(gè)文件分別為:crt0.S,led_lighton.c,Makefile。這是最簡(jiǎn)單的例程文件了,合適入門。代碼文件下載地址鏈接:
http://download.csdn.net/download/ludaoyi88/10151739
1.文件編譯鏈接
匯編文件和C文件需要編譯鏈接后生成可執(zhí)行文件,可執(zhí)行文件再轉(zhuǎn)換成.bin二進(jìn)制文件,才能燒錄到開(kāi)發(fā)板上執(zhí)行。而這些編譯鏈接與轉(zhuǎn)換都在makefile里寫好,只需在linux終端輸入make命令執(zhí)行即可。
通過(guò)secureCRE遠(yuǎn)程登錄到linux主機(jī)(這里用虛擬機(jī)),F(xiàn)TP文件傳輸工具連接到linux主機(jī),在Windows下編寫上述3個(gè)代碼文件,整個(gè)過(guò)程和上篇文章一樣,不再贅述。
將3個(gè)代碼文件上傳上linux主機(jī)的相關(guān)文件路徑下,在終端鍵入make命令,執(zhí)行makefile文件,執(zhí)行結(jié)果如下圖:
上述可以看到生成了led_on.bin的二進(jìn)制文件,將此文件燒錄到開(kāi)發(fā)板,燒錄方法可以用:oflash,dnw,tftpd,nfs等方法下載,前3種方法之前文章有講解使用方法。這里使用Windows下由dnw下載程序,先將二進(jìn)制文件傳入window再下載(開(kāi)發(fā)板應(yīng)撥碼至nand)。如圖:
下載成功后,復(fù)位開(kāi)發(fā)板,可以看到一個(gè)led燈變亮。效果如圖(成功咯O(∩_∩)O哈哈~)。這僅僅是裸板開(kāi)發(fā)的入門,如果有其他外設(shè)話就復(fù)雜了,同志仍需努力!
更多關(guān)于云服務(wù)器,域名注冊(cè),虛擬主機(jī)的問(wèn)題,請(qǐng)?jiān)L問(wèn)西部數(shù)碼官網(wǎng):m.ps-sw.cn