新聞中心

EEPW首頁 > 嵌入式系統(tǒng) > 設(shè)計應(yīng)用 > 關(guān)于LPC2200啟動程序分散加載描述文件的敘述

關(guān)于LPC2200啟動程序分散加載描述文件的敘述

作者: 時間:2016-11-09 來源:網(wǎng)絡(luò) 收藏
在ADS LPC2200的啟動模板中有一個scf文件夾,其中有mem_a.scf、mem_b.scf、mem_c.scf這3個文件,這3個文件是ADS的分散加載機(jī)制,其目的是將代碼段和數(shù)據(jù)段分別定位到制定地址上??梢栽贏rm Linker中選擇加載路徑。

分散裝在技術(shù)概述:

本文引用地址:http://m.butianyuan.cn/article/201611/317887.htm

分散裝在技術(shù)可以把用戶的應(yīng)用程序分割成多個RO(只讀)運行域和RW(可讀寫)運行域(關(guān)于域的概念大家可以在網(wǎng)上查查),并且給它們制定不同的地址。一個嵌入式系統(tǒng)中,F(xiàn)lash、16位RAM、32位RAM都可以存在于系統(tǒng)中,所以,將不同功能的代碼定位在特定的位置會大大地提高系統(tǒng)的運行效率。下面是最為常用的2種情況:
一、32位的RAM運行速度很快,因此就把中斷服務(wù)程序作為一個單獨的運行域,放在32位的RAM,使它的響應(yīng)時間達(dá)到最快。

二、程序在RAM中運行,其效率要遠(yuǎn)遠(yuǎn)高于在ROM中運行,所以將啟動代碼(Boot loader)以外的所有代碼都在RAM中運行,可以提高運行效率。

分散裝在技術(shù)主要完成了2個基本的功能:

如何分散。就是如何將輸入段組成輸出段和域。

如何裝載。就是確定裝載域和滅個運行域在存儲空間里的地址是多少。

域可以分為裝載域和運行域

裝載域描述運行前輸出段和域在ROM/RAM里的分布狀態(tài),運行域描述了運行時輸出段和域在ROM/RAM里的分布狀態(tài)。大多數(shù)情況下,映像文件哎執(zhí)行前把它裝載到ROM里,而當(dāng)運行時,域里的有些輸出段(比如RW類型的輸出段)必須到RAM里,程序才能正常運行,所以,在裝載和運行時,RW類的輸出段處在不同的位置(地址空間)。

Scatterfile分散加載文件:

在scatterfile中可以為每一個代碼或數(shù)據(jù)區(qū)在裝載和執(zhí)行時指定不同的存儲區(qū)域地址,Scatlertoading的存儲區(qū)塊可以分成二種類型:
裝載區(qū):當(dāng)系統(tǒng)啟動或加載時應(yīng)用程序的存放區(qū)。
執(zhí)行區(qū):系統(tǒng)啟動后,應(yīng)用程序進(jìn)行執(zhí)行和數(shù)據(jù)訪問的存儲器區(qū)域,系統(tǒng)在實時運行時可以有一個或多個執(zhí)行塊。
映像中所有的代碼和數(shù)據(jù)都有一個裝載地址和運行地址(二者可能相同也可能不同,視具體情況而定)。

scatter文件語法
scatter文件是一個簡單的文本文件,包含一些簡單的語法。
My Region 0x0000 0x1000
{
;the context of region
}
標(biāo)題
每個塊由一個頭標(biāo)題開始定義,頭中至少包含塊的名字和起始地址,如(0x0000),另外還有最大長度等其他一些屬性選項(注:這些屬性是可選的,如0x1000)。
內(nèi)容
塊定義的內(nèi)容包括在緊接的一對花括號內(nèi),依賴于具體的系統(tǒng)情況。
一個加載塊必須至少含有一個執(zhí)行塊;實踐中通常有多個執(zhí)行塊。
一個執(zhí)行塊必須至少含有一個代碼或數(shù)據(jù)段;這些通常來自源文件或庫函數(shù)等的目標(biāo)文件;通配符號*可以匹配指定屬性項中所有沒有在文件中定義的余下部分。

有以下幾種屬性:

RO:只讀的代碼段和常量

RW:可以讀寫的全局變量和靜態(tài)變量

ZI:RW段中要被初始化為零的變量。

Scatterfile中的定義要按照系統(tǒng)沖定向后的存儲器分布情況進(jìn)行,在引導(dǎo)程序完成初始化任務(wù)后,應(yīng)該把主程序轉(zhuǎn)移到RAM中運行以加快系統(tǒng)的運行速度。

LPC2200分散加載文件分析:

ROM_LOAD 0x80000000 (1)

{

ROM_EXEC 0x80000000 (2)

{

Startup.o (vectors, +First) (3)

* (+RO) (4)

}

IRAM 0x40000000 (5)

{

Startup.o (MyStacks) (6)

}

STACKS_BOTTOM +0 UNINIT (7)

{

Startup.o (StackBottom) (8)

}

STACKS 0x40004000 UNINIT (9)

{

Startup.o (Stacks) (10)

}

ERAM 0x80040000 (11)

{

* (+RW,+ZI) (12)

}

HEAP +0 UNINIT (13)

{

Startup.o (Heap) (14)

}

HEAP_BOTTOM 0x80080000 UNINIT (15)

{

Startup.o (HeapTop) (16)

}

}

FLASH_LOAD 0x81000000 0x1000 (17)

{

FLASH_EXEC 0x81000000 (18)

{

main.o (+RO) (19)

}

}

(1)加載時域描述,名稱位ROM_LODA 它的地址為0x80000000;0x80000000為LPC片外RAM地址,即將以下的加載的段和域都在RAM中。

(2)第一個運行時域描述。ROM_EXEC描述了執(zhí)行區(qū)的地址,放在第一塊定義,其起始地址、空間大小域加載區(qū)起始地址、空間大小要一樣。

(2)-(4)從起始地址開始放置向量表。Startup.o是Startup.s的目標(biāo)文件。Vectors為中斷向量表。模塊Startup位于該加載域的開頭(+First),vectors作為入口點,包含全部的RO代碼。ARM在芯片復(fù)位之后,系統(tǒng)進(jìn)入管理模式、ARM狀態(tài),PC(R15)寄存器的值為0x00000000,所以必須保證用戶的向量表代碼定位在0x00000000處,或者映射到0x00000000處(例如向量表代碼在0x80000000處,通過存儲器映射,訪問0x0000000就是訪問0x80000000)。

(5)-(6)第二運行時域描述。將MyStacks堆棧段裝載到片內(nèi)靜態(tài)RAM中。

(7)-(8)將棧底放入堆棧的后面(+0)不進(jìn)行初始化(UNINIT), 棧底為Startup中的StackBottom。

(9)-(10) 將棧放入地址為0x40004000 并且不進(jìn)行初始化(UNINIT)。

(11)-(12將所有的RW和ZI段放入外部存儲器中以0x80040000為開頭的地址中。并且全部清零(+ZI)外部RAM中指定的區(qū)域。

(13)-(14)在RW ZI段后放入堆底(Startup.o(Heap))并且不進(jìn)行初始化。

(15)-(16)將堆定放入外部RAM中(0x80080000)。

(17)-(19)自己添加的加載代碼,把main.c的目標(biāo)文件加載到片外Flash中并且占用了0x1000的大小。



評論


技術(shù)專區(qū)

關(guān)閉