2017-04-17 146 views
1

編譯使用多個定製C++庫的小型Java程序時遇到了問題。所有庫都針對armeabi-v7a,並且使用硬浮點支持(mfloat-abi = hard -mfpu = neon -mhard-float -D_NDK_MATH_NO_SOFTFP = 1)進行編譯。我有幾個其他的cpp文件,它們是Java/Android項目的一部分;這些也編譯與上述設置和我鏈接反對libm_hard.a(而不是libm.a)Android NDK:libC++支持硬浮點數

當我運行該程序,我得到奇怪的行爲從cpp文件(不自定義庫),類似的浮動到arm cortex a9 cross compiling strange floating point behaviour。合法的浮點值(在代碼中,通過調試器檢查)將作爲極小值(例如1.47895e-309)輸出到stdout或fstream。

std::ofstream os; 
    os.open(filename, std::ios::out); 

    double x = 0.34343; 
    double y = log(0.1); 

    os << x << "\t" << y << endl; 

    os.close(); 

看來會發生這種情況,因爲libC++庫沒有編譯爲硬浮點;我嘗試了libC++的靜態和共享版本,並獲得相同的行爲。我也通過readelf檢查過它們,看起來它們沒有被編譯爲硬浮點(沒有提到VPF寄存器)。我無法找到爲NDK中的hard-float編譯的libC++(靜態或共享)版本。

  • Android SDK中:21(試圖與23以及)
  • NDK:14.1.3816874
  • Android Studio中:2.3.1

我不能(容易地)改變上游從hard-float到softfp的庫;有些專注於重載矩陣處理,並針對硬浮點進行了優化。而且,據我所知,我不能混用softfp和hard ...

除了重新編譯libC++ for hard-float之外,還有其他選項嗎? (我的理解前陣子谷歌下跌了硬ABI,必須有相應的libC++庫支持)

編輯:添加示例代碼

+1

發佈您用來輸出浮點值的代碼。如果是'libC++'庫就是問題所在,可能有辦法將'float'值轉換爲可以輸出的字符串。也許C風格的'printf()'或類似的工作。 –

+0

謝謝,我會嘗試,但我認爲這可能是相同的問題,只是推遲到libc而不是libC++。另外,可能會有其他地方(我無法控制的地方)在第三方庫中導致問題發生的libC++依賴關係。 –

+0

@AndrewHenle你的建議工作(至少處理文本io和浮動),再次感謝。我仍然很好奇其他人與使用硬浮標誌編譯的libC++鏈接的經驗。 –

回答

1

從NDK在R12去除硬浮動ABI支持:https://android.googlesource.com/platform/ndk/+/master/docs/HardFloatAbi.md

停止使用libm_hard,你應該沒問題(沒有刪除這是一個在r15中修復的疏忽,對於混淆抱歉!)。

非常重要的是要注意非硬性浮點ABI仍然使用浮點指令。唯一的區別是傳遞ABI的函數參數。

+0

謝謝。只是爲了確保我理解你的建議:我不應該鏈接libm_hard,並且還應該在編譯我的應用程序時刪除所有與hard-float相關的編譯器標誌,是否正確?當我這樣做時,我開始遇到問題(一些雙打的NaN值)與第三方庫,其中一個硬編譯支持編譯。我可以嘗試更多地瞭解爲什麼會發生這種情況,但要確保我瞭解您的建議,即我應該仍然能夠鏈接與硬浮標誌建立的庫? –

+1

你取決於應標註與'__attribute __頭硬浮動庫((PCS(「AAPCS-VFP」)))',如果它們的功能使用硬浮調用約定。你不需要刪除'-mfpu = neon'標誌,只需要'-mfloat-abi = hard'和'-mhard-float'(這是冗餘的,順便說一下)。 –