轉:都江堰idea6410開發人員筆記色1

來源:互聯網
上載者:User

第一回:

應深圳友堅科技之邀,這幾天要把djyos移植到他們的idea6410上。

    現在發布的是si版本,是以單片機模式啟動並執行,S3C6410這樣強勁的cpu,運行si版本,就作為高速單片機用了,所有地址都是按照物理地址一一對應映射。cpu的狀態也沒有區分核心態和使用者態。

1、中斷引擎最初的部分代碼在IRQ態(還沒決定是否使用FIQ)。

2、中斷引擎的大部分以及使用者ISR運行在SVC態。

3、所有其他代碼運行在SYS態。

    移植碰到的第一個問題就是燒錄代碼到flash的問題,由於廉價的jtag燒錄器不支援arm11,我們不能要求使用者必須擁有昂貴的模擬燒錄工具才能夠在idea6410上使用djyos,這樣不利於使用者使用。

    我的第一個目標,就是弄清楚怎麼下載程式的問題,也就是把一個最簡單的閃燈程式運行起來,寫了幾行代碼,如下:

    ldr     r0,=0x7f008820

    ldr     r1,=0x1111

    str     r1,[r0]

    ldr     r0,=0x7f008824

    ldr     r1,[r0]

    bic     r2,r1,#3

    orr     r2,r2,#0xc

    bic     r3,r1,#0xc

    orr     r3,r3,#3

nn:

    str     r2,[r0]

    ldr     r4,=5000000

delay1:

    sub     r4,r4,#1

    cmp     r4,#0

    bne     delay1

    str     r3,[r0]

    ldr     r4,=5000000

delay2:

    sub     r4,r4,#1

    cmp     r4,#0

    bne     delay2

    b       nn

   
6410的手冊上說,可以從nandflash、onenand、SD卡啟動,沒有專用的燒錄工具的情況下,只有SD卡啟動是可以考慮的。手冊上看
到,SD卡啟動,實際上是先執行片內IROM中的一段程式,該程式從SD卡中讀取代碼,寫到stepping stone中,stepping
stone是位於0x0c000000、size為8K的片內記憶體,代碼寫入stepping
stone後,跳到0x0c000000處繼續執行程式。那麼,要實現從SD卡啟動,就必須弄清楚:

1、8K的代碼儲存在SD卡的什麼位置。

2、代碼以什麼格式儲存。

    為弄清楚上述問題,依例google

一番,沒找到有用的資料,上三星的網站,6410的資料沒有公開,申請了一下,第二天得到了批准,也沒有關於怎樣從SD卡啟動的資料。找三星代理,似乎不太愛搭理我,也是,我勢單力薄一個人,他們怎看得上眼。難道就沒有辦法了?

    山窮水盡疑無路,柳暗花明又一村,2450不是也可以從SD卡啟動嗎?找找2450的資料看有沒有,謝天謝地,從網上找到一篇文檔:

896554S3C2450_IROM_ApplicationNote_Rev003.pdf

我如獲至寶,細細讀之,雖然寫得不太細,比如代碼校正演算法等都沒有講,總是可以試一下了。

    依葫蘆畫瓢,把編譯好的代碼寫入到最後晶片末尾位移-9216位元組處,插入SD卡座,把開關撥到SD0卡啟動的位置,上電,哈哈,成功了,幾個藍色的LED歡快地閃爍起來。試了兩個SD卡,16M的可以,2G的不行,不知何故,暫且放一邊吧。

    首戰告捷,該歇歇了,待續。

第二回:

上篇說道,用16M的SD卡啟動可以,但用2G的卡卻不行,反覆試過,實在不知道怎麼回事,也沒有IROM中的載入程式的進一步資料,問題也就無從查起了,暫且先放一邊,把後續的移植工作做完再說吧。

移植作業系統,跟開發裸奔程式是不一樣的,裸奔程式可以從main開始寫程式,在執行main之前,編譯器產生了大量的代碼用於初始化cpu、記憶體清零、初始化堆和棧、直到建立main的執行環境。而作業系統往往有自己的運行環境要求,C編譯器完成的這些環境往往不能符合要求,需要自己寫初始設定檔案,即initcpu.s檔案。

初始設定檔案主要完成以下工作:

1、從複位地址跳轉到啟動地址。

2、設定cpu為特權模式,禁止看門狗和中斷,禁止cache。

3、設定時鐘,有些cpu的時鐘設定很複雜的,尤其是高速cpu,因為涉及到核心和外設匹配的問題,設定起來比較麻煩。

4、設定記憶體匯流排,設定記憶體訪問速度,要跟上一步的時鐘設計配合,使cpu能正確讀寫記憶體和記憶體映射的外設。

5、配置cache和mmu,然後使能cache和mmu。

6、初始化棧,跳轉到C代碼。

根據拿來主義的原則,寫cpu初始化代碼千萬不能自己從0開始寫,而是要找一個現成的來參考,因為各個系統的cpu初始化工作是大同小異的。而且,許多 cpu廠商都會出example,會帶一個檔案名稱類似startup.s的檔案,參考該檔案來寫即可。但是,三星不知從何年何月開始不公開其cpu的文檔了,甚至連datasheet都要申請才給。當我千辛萬苦找到三星提供的"6410_Test_Rev01"原始碼包時,心都涼了,該程式碼封裝中雖然有 start.s檔案,但檔案中只有幾條指令,初始化過程都在"__rt_entry"函數中,而該函數在庫中。對晶片應用資料的保密工作做得如此周密,不知三星所謀何事。

沒辦法,繼續找,實在不行再自己一行行寫。好在天無絕人之路,終於在友堅提供的wince的eboot代碼中,找到了eboot的start.s檔案,開啟一看,果然是一個詳細的開機檔案,心中不禁狂喜!

接下來的工作,就是對照datasheet,看懂這個start.s,然後改造成適合djyos的。別看說的輕巧,這裡面工作量還是很大的,6410的 datasheet有1300多頁,光時鐘和匯流排配置相關的部分就有100多頁,E文的,暈死。而且第一次用arm11,其mmu和cache配置和 arm9有多大差別,還不可知。今天先寫到這裡,下回分解吧。

第三回:

接續上回,開始啃start.s,跟所有的開機檔案一樣,開始部分是關閉cache、禁止中斷等,沒什麼問題。這裡稍稍解釋一下為什麼要做這些工作,禁止中斷大家應該沒什麼異議,關鍵是為什麼一定要禁止 cache,原來,我們不知道程式為什麼要重新啟動,也不知道重新啟動前cpu和cache處於什麼狀態,cache可能包含錯誤的資訊,cpu可能會從中取得錯誤的指令,從而不能正常啟動系統。eboot的start.s遺漏了一個很重要的過程,就是要重新把cpu設定成svc狀態,因為就像我們不瞭解重啟動前cache狀態一樣,cpu的狀態也是未知的,須加上這幾句確保cpu處於svc態:
mrs r0,cpsr @取CPSR
bic r0,r0,#MODEMASK @清模式位
orr r1,r0,#SVCMODE|NOINT @設定為管理態,並禁止中斷
msr cpsr_cxsf,r1 @切換到管理態,可防止意外返回0地址時出錯.
實際上,這幾句仍然不夠保險,因為如果程式是從user態直接跳轉到0地址的話,mrs和msr指令是無效的。保險的做法是用swi指令強制修改,既然是個簡易的bootloader程式,暫且偷懶一下。
依慣例,接下來是各種時鐘初始化,S3C6410的時鐘結構比較複雜,共有3個pll要設定,而且分頻控制也較為複雜,雖然start.s有得抄,但還是要自己弄清楚,因為接下來的編程用得上。6410的時鐘部分之所以如此複雜,完全是為了適應其內部豐富的外設,不同的外設需要不同的時鐘。設定時鐘,不外乎就是定義幾個常用的主頻,然後分別為這些主頻定義鎖相環(pll)的分頻係數,再把這些分頻係數填充到相應的寄存器中去,細節就不再贅述了,看代碼吧。
初始化完時鐘後,就輪到初始化記憶體匯流排了。依據用什麼初始化什麼的原則,這裡只初始化了srom0和dram兩個地區,這部分代碼是用C語言實現的,參見memcfg.c檔案,代碼比較簡單,不過是按照datasheet的要求,依次設定寄存器而已。
接下來,你一定會想到,該初始化mmu了,初始化mmu本來是一項複雜的工作,但si版本是為單片機準備的,即使6410再強勁,也只能委屈一下,當高速單片機了。mmu在這裡並沒有用來做地址變換,而是把4G記憶體空間全部映射到其物理地址上了。這種映射效果跟禁止mmu是一樣的,但是arm的mmu和cache是綁定在一起的,禁止mmu的同時也就禁止了cache,故只能開啟mmu。頁表的地址在0x50000000,佔用16Kbytes,故應用程式的起始地址是0x50004000。
又可以偷懶了,6410的核是arm11jzf-s的,2440的核是arm920T的,arm11jzf-s的mmu功能比arm920t的強很多,但都是arm公司的,做最簡易對應的話,能否相容呢?懶得讀arm11的手冊了,先試一下把2440版本的mmu初始化部分直接copy看行不行。事實證明是可行的,但我在這裡繞了一個大大的圈子,浪費了許多時間。加入初始化mmu部分代碼後,試了一下,發現燈不閃了,而把該段程式放到初始化頁表的代碼之前,則可以。仔細檢查,發現是因為dram沒有初始化,加上dram初始化後,先把閃燈程式放在dram初始化後面,發現可以了。這時候,不幸發生了,移動閃燈程式時,只copy了一半的代碼,當然不閃了,可我沒仔細檢查代碼,就懷疑是2440的mmu初始化代碼不能用於6410的造成的(偷懶了,心虛),於是找來arm11jzf-s的手冊猛啃,幾百頁的英文資料啊,費了好幾天功夫,最後證明了一件事:原來的mmu初始化是正確的!!
到這裡,基本硬體的初始化就算完成了,接下來要搞norflash和uart的driver了。待續......

cpu的初始化已經完成,下一步的工作便是初始化uart,使之能夠跟PC串連上。
    初始化6410的uart,有兩個時鐘必須區分清楚,即uartclk和baudclk,前者由系統


控制寄存器CLK_SRC和CLK_DIV2控制,手冊並沒有說明這個時鐘的用途,我猜測是用於uart模組本身啟動並執行;另一個時鐘是baudclk,用來控制baud,產生串列移位時鐘的,在uart模組的控制寄存器UCON中設定


,然後用UBRDIV和UDIVSLOT0兩個寄存器設定baud。uart的工作方式為:
baud=115200
接收和發送fifo:開
中斷:關閉,以查詢方式收發。
    接下來是norflash的驅動程式,也就是編寫擦除和寫入程式,根據am29lv160db的手冊寫就是了,沒什麼好說的。除了一些低級錯誤外,測試也幾乎一次成功。
    至此,該輪到xmodem協議收發程式了,xmodem是一個簡單的串口收發檔案


協議


,它把檔案分成128位元組的一個個小包傳送,最後一包資料



果不滿128位元組,則以0x1a填充。該協議是有缺陷的,用來傳送文字檔沒問題,因為文字檔不會出現0x1a,但傳送2進位檔案的話,就不行了,因為
接收方無法分辨最後的0x1a是檔案本身的內容,還是填充物。不過沒關係,作為代碼,最後多一些垃圾並不礙事,無非就是多佔幾個位元組而已。
    xmodem本來是有差錯控制的,通過逐幀應答和校正和(或者CRC)來確保傳輸正確,不過這裡偷了下懶,所有這些都省略了,傳錯了就再傳一次。
    至此,移植


到S3C6410的第一步,sdbootloader就製作完成了,接下來就是移植整個作業系統


了,sdbootloader的代碼在這裡下載:
   http://www.djyos.com/download/sdboot6410.zip


sdbootloader說明:
1、用winhex工具把boot_rom.bin寫入SD卡,地址:SD卡末地址-9216。
2、把開發板的撥碼開關撥到從SD卡啟動,上電即可。
2、開啟超級終端,用xmodem協議下載程式,儲存到dram中。
3、把下載的代碼寫入到norflash。
4、把開發板的撥碼開關撥到從norflash啟動,複位或重新上電即可。
5、省去了xmodem框架格式檢查、校正和檢查。

    但凡開發作業系統


,無論是PC、伺服器


,還是嵌入式作業系統,第一個要解決


的就是啟動檔案


的儲存問題。無論什麼cpu,上電或者複位後,都會從指定的儲存位置讀取第一條指令予以執行,我們把這個地址成為啟動向量,有些cpu可以通過跳線設定


不同的啟動向量地址。我們熟悉的PC,就是把bios燒錄到啟動向量處,再由bios逐步引導啟動更進階的作業系統,比如windows


linux


等。
   
在嵌入式行業,以linux為例,linux映像可以通過網口或者其他通訊口下載,但你拿到裸機的時候,必須先想辦法把uboot或者vivi或者其他
bootloader燒錄到flash中。djyos也不例外,不同的是,現在發布的si版本的djyos,是沒有單獨的bootloader的,而是把
bootloader的角色整合在可執行影像中了,所以,需要像燒錄uboot那樣,燒錄整個djyos影像。
   
在s3c6410之前,djyos發布了arm7(44b0)和arm9(2410和2440)兩個版本,得益於廉價的arm7和arm9模擬燒錄器,比
如hjtag,arm這兩個版本是通過hjtag或者jlink或其他工具直接燒錄到norflash上的。但s3c6410是arm11的核,這些廉價
工具不支援arm11,支援arm11的燒錄工具都在數千元以上,這樣勢必影響大家使用djyos。要讓6410執行djyos,必須解決在沒有專用燒錄
工具的情況下,把djyos燒錄到啟動裝置上的問題。
    6410一共支援4種啟動裝置:norflash、nandflash、SD卡、modem,其中norflash和nandflash必須使用專用燒錄工具,modem則需要瞭解其通訊協議


,編寫相應的PC端應用



序,相比之下,SD卡最為簡單,可以用普通的讀卡機+winhex工具就可以完成寫入。但有一個限制,就是6410啟動時只從SD卡中讀取8K代碼到內部
ram中(6410手冊第二章說4K,第八章說8K,實測是8K)。讀入代碼後,程式就跳轉到內部ram中執行,這8K程式,只能做一個簡易
bootloader,用這個bootloader去載入整個作業系統,這時候,就有兩種選擇:
1、把程式寫到SD卡的其他地方,   但這種方法不現實。SD卡是用nandflash做的, 必然要做ECC校正,那麼把代碼寫入SD卡時,要麼用檔案系統,但8K代碼根本做不了檔案系統;要麼在PC端用支援ECC的專用寫卡工具,可惜沒有找到。
2、用串口下載,這是傳統方法,PC端的工具很多,最通用的是超級終端了。
    我們選擇了超級終端,xmodem協議下載。
    代碼比較簡單,說明見“s3c6410移植日誌


之x”系列,下載原始碼:http://www.djyos.com/download/sdboot6410.zip

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.