esp32平臺ulp程序無法啓動問題分析

1.現象

在ulp程序增加了一些邏輯之後,編譯報錯。編譯器打印故障信息(rel too far)如下:

 

上網搜索之後,發現是編譯器bug(編譯器會差label 到引用直接打的文件地址偏移, 如果隔太遠就會拋異常, 事實上這個機制並不合理)。官網給出的解決方案是將程序分成多文件,或者將引用的label聲明爲全局(global),或者直接註釋掉編譯器檢查偏移相關部分代碼(開源的好處,隨便讓你折騰)。

參考地址:

https://esp32.com/viewtopic.php?t=326

https://github.com/espressif/binutils-esp32ulp/issues/4

權衡之下決定使用分文件的方法。於是參考例程將邏輯分爲多個彙編文件進行編譯。順利完成編譯。開開心心的燒錄測試,發現ulp程序起不來了。

2.漫漫調試路

2.1瞎子過河

剛開始以爲是程序邏輯問題。於是一遍又一遍檢查代碼,分析邏輯(ulp下面運行彙編代碼,沒有打印,不拋異常,出了問題完全是盲調)。最終沒有結果。只能回滾代碼到可以運行版本,然後小心翼翼一點一點分邏輯。發現只要一分開就不能運行(程序邏輯沒有變動,BTW,這個時候有撞牆的衝動)。

2.2無心插柳

來來回回折騰了幾遍之後,手賤打印了程序符號表。發現無法運行的程序入口地址不爲零(零地址處是引用的label)。猜想可能是入口地址不爲零,或者跳轉地址爲零導致異常。

於是,打印可以運行的程序符號表進行對比,發現可以運行程序入口(entry)地址爲零。

 2.3柳暗花明

進一步研究發現,編譯器按照源文件編譯順序保存符號表。於是調整源文件編譯順序進行驗證。結果與預期一致,將程序入口所在文件順序調整到第一個進行編譯之後,程序入口地址爲零,同時程序恢復正常運行,反之,無法正常運行。

3.總結

爲避免不必要的問題。ulp下面程序入口函數一點要是對應文件的第一個函數。並且程序入口函數所在文件需要第一個編譯。

編程不易,且行且珍惜!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章