問:如何指定代碼、常數(shù)或變量到某個(gè)特定的地址?
答:使用“#pragma psect”偽指令來把代碼、常數(shù)或變量放到你定制的psect。于是你就可以使用鏈接器選項(xiàng)來把這個(gè)定制的psect放到你想要的地址。Pragma psect的語法是:
#pragma psect original_psect=new_psect
這里的“original_psect”是標(biāo)準(zhǔn)的code、constant或變量原來位于的psect名稱,這個(gè)orignal psect名稱可以從map文件的symbol table里找到。 一個(gè)symbol table的示例:
__Lstrings strings 0008 __Lstringtable stringtable 0008
__Lstruct struct 0020 __Ltemp temp 0070
__Ltext text 0190 __Lvectors vectors 000B
__S0 (abs) 0800 __S1 (abs) 0190
_exit init 0004 _main text0 07FD
_serial const1 0009 intlevel0 intentry 0004
_serial const1 0009 ; 這個(gè)變量是這樣聲明的“const int serial = 5621;”
_serial是變量名加前下劃線,const1是psect名稱
這里在“const”后面有一個(gè)數(shù)字,也即“const1”,這個(gè)數(shù)字可以是任何數(shù)字,也就是說,它不一定是1。你可以使用“%%u”來代替這個(gè)數(shù)字,對(duì)于大部分的后面帶有數(shù)字的psect都可以這樣,除了rbss_x和rdata_x。因?yàn)閞bss_x和rdata_x是每個(gè)bank的RAM變量,rbss_0代表bank 0,rbss_1代表bank 1,依此類推……
“new_psect”是你要定制的psect的名稱,可以使任意名稱,但是不能和標(biāo)準(zhǔn)psect同名。
示例,聲明把“serial”放到一個(gè)新的psect里去是這樣做的:
#pragma psect const%%u=fixed_serial
const int serial = 5621;
每一個(gè)“#pragma psect”偽指令應(yīng)該是在一個(gè)獨(dú)立的文件中被聲明,也就是說,所有的在“#pragma psect”下面聲明的變量都會(huì)被放到新的定制psect中去。
// --File serial.c
#pragma psect const%%u=fixed_serial
const int serial = 5621;
// --End file
// --File serial.h
extern int serial;
// --End file
具體放置這個(gè)新的定制psect,你將需要加入一些額外的命令行選項(xiàng)。
-L-Pcustom_psect=addressh
這里'-L'是傳遞選項(xiàng)給鏈接器,'-P'是定位一個(gè)psect到特定的地址,'custom_psect'是你想要定位的psect的名稱,'addressh'是你想要定位到的16進(jìn)制地址。例如:
PICC -16f877 main.c serial.c -L-Pfixed_serial=50h
對(duì)于'text' psect有一些特殊問題。一個(gè)類似于'#pragma psect text%%u=myPsect'的偽指令會(huì)把所有的text psect放置到單個(gè)用戶定制的psect里。而優(yōu)化器一直認(rèn)為每個(gè)psect只包含一個(gè)函數(shù)。這將會(huì)產(chǎn)生bank切換的錯(cuò)誤。
要避免這個(gè)問題,可以對(duì)用戶定制psect名稱也使用'%%u'后綴,例如:
#pragma psect text%%u=myPsect%%u
這樣多個(gè)用戶定制的psect將被產(chǎn)生。
例如:
//file test.c
#pragma psect text%%u=myPsect%%u
void func()
{
}
void func2()
{
}
void main()
{
}
//end file
你可以從列表文件和map文件中看到下面這些信息。
'func()' is in psect 'myPsect0'
'func1()' is in psect 'myPsect1'
'main()' is in psect 'myPsect2'
你于是就可以用'-L-P'選項(xiàng)給每一個(gè)psect清楚地分配地址。
所以,要把這些函數(shù)放到500h地址,你可以使用下面的編譯選項(xiàng):
-L-PmyPsect0=500h,myPsect1,myPsect2
請(qǐng)注意-L-P 選項(xiàng)是沒有ROM頁邊界的檢查,你需要自己確保這個(gè)函數(shù)(psect)是不會(huì)超越頁邊界的,(譯者注:PICC要求每個(gè)函數(shù)都必須是在同一個(gè)ROM頁里的)。請(qǐng)查看使用說明書來得到更多關(guān)于'#pragma psect'的信息。
-
編碼器
+關(guān)注
關(guān)注
45文章
3647瀏覽量
134701 -
代碼
+關(guān)注
關(guān)注
30文章
4796瀏覽量
68706
發(fā)布評(píng)論請(qǐng)先 登錄
相關(guān)推薦
評(píng)論