S3C2440裸機編譯不支援浮點運算問題記錄

2021-09-24 09:58:15 字數 2999 閱讀 1068

軟體版本:練習程式

例程路徑:f:\code\004

硬體平台:jz2440(s3c2440)

知識普及:

(1)硬浮點(hard-float)

編譯器將**直接編譯成硬體浮點協處理器(浮點運算單元fpu)能識別的指令,這些指令在執行的時候arm核直接把它轉給協處理器執行。fpu 通常有一套額外的暫存器來完成浮點引數傳遞和運算。使用實際的硬體浮點運算單元(fpu)會帶來效能的提公升。

(2)軟浮點(soft-float)

編譯器把浮點運算轉成浮點運算的函式呼叫和庫函式呼叫,沒有fpu的指令呼叫,也沒有浮點暫存器的引數傳遞。浮點引數的傳遞也是通過arm暫存器或者堆疊完成。現在的linux系統預設編譯選擇使用hard-float,如果系統沒有任何浮點處理器單元,這就會產生非法指令和異常。因而一般的系統映象都採用軟浮點以相容沒有vfp的處理器。

用一句話總結,軟浮點是通過浮點庫去實現浮點運算的,效率低;硬浮點是通過浮點運算單元(fpu)來完成的,效率高。

編寫jz2440(s3c2440)uart驅動程式,初始化函式參考ti的dsp驅動寫法,配置波特率暫存器使用了浮點運算

ureg->ulcon=(0<<6)|(uartlink->parity<<3)|(uartlink->stopbit<<2)|(uartlink->databit<<0);

ureg->ucon=(0<<10)|(1<<2)|(1<<0);//pclk;tx/rx interrupt type:interrupt request or polling mode

ureg->ufcon=(0<<0);//disable fifo

ureg->umcon=(0<<4);

ureg->ubrdiv=(unsigned int)(clock_mhz*1000000.f/(uartlink->baudrate*16)-1);

上述**最後一行使用了浮點運算自行根據外設時鐘pclk計算波特率設定暫存器引數,編譯時出現錯誤如下:

arm-linux-ld -tlink.lds init.o uart.o start.o -o test.elf

uart.o(.text+0x1d8): in function `$a':

: undefined reference to `__mulsf3'

uart.o(.text+0x200): in function `$a':

: undefined reference to `__floatsisf'

uart.o(.text+0x224): in function `$a':

: undefined reference to `__floatsisf'

uart.o(.text+0x234): in function `$a':

: undefined reference to `__addsf3'

uart.o(.text+0x248): in function `$a':

: undefined reference to `__divsf3'

uart.o(.text+0x258): in function `$a':

: undefined reference to `__subsf3'

uart.o(.text+0x264): in function `$a':

: undefined reference to `__fixunssfsi'

makefile:26: recipe for target 'test' failed

make: *** [test] error 1

將ureg->ubrdiv=(unsigned int)(clock_mhz*1000000.f/(uartlink->baudrate*16)-1);改為

ureg->ubrdiv=26;則編譯通過沒有問題,查詢資料發現是s3c2440沒有浮點運算單元,只能使用軟浮點,即由編譯器的庫檔案支援,我使用的編譯器沒有浮點庫,需要自己新增浮點庫,並在編譯器選項上新增庫路徑。

cflags := -static -werror -iinclude -msoft -float -l/usr/local/arm/../libgcc.a

目前問題沒有解決,留待以後完善

echo $path檢視環境變數,得到編譯器路徑/usr/local/arm/gcc-3.4.5-glibc-2.3.6/bin,回到上層目錄/usr/local/arm/gcc-3.4.5-glibc-2.3.6,使用 grep "__floatsisf" * -nr查詢目錄下含有__floatsisf標示的檔案,得到:

binary file arm-linux/lib/libm.a matches

binary file arm-linux/lib/libm-2.3.6.so matches

binary file arm-linux/lib/libc.a matches

binary file arm-linux/lib/libgcc_s.so.1 matches

binary file arm-linux/lib/libc-2.3.6.so matches

binary file include/c++/3.4.5/arm-linux/bits/stdc++.h.gch/o0g matches

binary file include/c++/3.4.5/arm-linux/bits/stdc++.h.gch/o2g matches

info/gccint.info:555: -- runtime function: float __floatsisf (int i)

binary file info/gccint.info matches

binary file lib/gcc/arm-linux/3.4.5/libgcc.a matches

將靜態庫拷貝到**目錄下,修改鏈結器命令:$(ld) -tlink.lds $^ libgcc.a -o [email protected],測試發現libgcc.a庫包含浮點庫函式,可以正常編譯。

$(ld) -tlink.lds $^ -l$(libpath) -llibgcc -o [email protected]這個命令卻不能找到庫,只能拷貝到**目錄下鏈結

s3c2440裸機串列埠UART

串列埠收發資料 115200,8n1。每一位的時間是t 1 115200。傳輸乙個位元組需要10位 包括起始位1位,資料位8位,停止位1位,需要的時間是t 10 115200。每秒傳輸的的位元組數 1 t 115200 10 11520byte。回環模式 一發出資料就立刻收到,用於測試。main.c...

S3C2440裸機 時鐘

目錄 1.s3c2440的時鐘體系 1.1.s3c2440結構框圖 1.2 s3c2440時鐘樹 1.3 s3c2440上電順序 2.暫存器配置 2.1clkdivn暫存器 2.2mpllcon暫存器 2.3設定cpu為非同步模式 3.程式設計 4.實驗 從上面的結構圖可以看出,s3c2440主要分...

s3c2440裸機 ADC程式設計

模數轉換器即a d轉換器,或簡稱adc,通常是指乙個將模擬訊號轉變為數碼訊號的電子元件。如圖,是把可變電阻上的電壓值變換的模擬訊號通過adc轉換,輸出數碼訊號。對於數碼訊號我們需要得到它的2個屬性 1.轉換精度 用多少位來儲存這個資料 假如是10 bit 那麼最大值0b111111111對應3.3v...