国产亚洲精品福利在线无卡一,国产精久久一区二区三区,亚洲精品无码国模,精品久久久久久无码专区不卡

當(dāng)前位置: 首頁(yè) > news >正文

用dw做淘客網(wǎng)站的步驟南京百度推廣開(kāi)戶(hù)

用dw做淘客網(wǎng)站的步驟,南京百度推廣開(kāi)戶(hù),后端開(kāi)發(fā)工程師前景,多少錢(qián)做網(wǎng)站記一次調(diào)試過(guò)程 這是一個(gè)在 arm 架構(gòu)上的 RTOS 上的調(diào)試過(guò)程。問(wèn)題現(xiàn)象為使用 thumb 指令集的 libgcc 庫(kù)的情況下,浮點(diǎn)運(yùn)算隨機(jī)出錯(cuò)。經(jīng)過(guò)一番追蹤調(diào)試,逐步縮小問(wèn)題范圍,最后定位問(wèn)題,成功解決。 場(chǎng)景 在某款的國(guó)產(chǎn) RTOS 上&a…

記一次調(diào)試過(guò)程

這是一個(gè)在 arm 架構(gòu)上的 RTOS 上的調(diào)試過(guò)程。問(wèn)題現(xiàn)象為使用 thumb 指令集的 libgcc 庫(kù)的情況下,浮點(diǎn)運(yùn)算隨機(jī)出錯(cuò)。經(jīng)過(guò)一番追蹤調(diào)試,逐步縮小問(wèn)題范圍,最后定位問(wèn)題,成功解決。

場(chǎng)景

在某款的國(guó)產(chǎn) RTOS 上,由于客戶(hù)應(yīng)用需要,使用了thumb 指令集編譯的 libgcc 的庫(kù),導(dǎo)致了同時(shí)運(yùn)行了 arm 指令集和 thumb 指令集的代碼。原本的 RTOS 未設(shè)計(jì)運(yùn)行 thumb 指令的代碼,也沒(méi)有嚴(yán)格測(cè)試過(guò),所以本次暴露了浮點(diǎn)運(yùn)算偶爾出錯(cuò)的問(wèn)題。

測(cè)試代碼

客戶(hù)精簡(jiǎn)過(guò)的暴露問(wèn)題代碼如下

unsigned long long   ulTa = 0x100;
unsigned long long   ulTb = 0x2001;
double dRea, dReb;
double dRes;while (1) {= (double)ulTa;dReb = (double)ulTb;dRes = dRea / dReb;if ((dRea == 0.0) || (dReab == 0.0) || (c <= 0.01f)) {printf("error!!\r\n");}}

這段代碼的邏輯是強(qiáng)轉(zhuǎn)了兩個(gè) unsigned long long 類(lèi)型,然后進(jìn)行除法運(yùn)行,最后判斷各個(gè)變量的結(jié)果是否符合預(yù)期,否則就報(bào) error。

問(wèn)題分析

抓取問(wèn)題中的關(guān)鍵點(diǎn):

  1. 和浮點(diǎn)運(yùn)算有關(guān),是不是我們的RTOS對(duì)于浮點(diǎn)運(yùn)算的寄存器沒(méi)有處理好
  2. 簡(jiǎn)單的代碼反復(fù)運(yùn)行只是偶爾出問(wèn)題,而不是固定每次出問(wèn)題,那么考慮其他外部的影響,首先考慮的是中斷。

問(wèn)題調(diào)試

bug調(diào)試的指導(dǎo)思想是,仔細(xì)觀察問(wèn)題剖析問(wèn)題,提出懷疑一些原因,并修改代碼驗(yàn)證。

步驟1 剖析問(wèn)題

靠近問(wèn)題的實(shí)質(zhì),分析問(wèn)題:既然計(jì)算出錯(cuò),那么看看出錯(cuò)的時(shí)候的變量是什么樣的。經(jīng)過(guò)一些調(diào)試打印發(fā)現(xiàn) 3 個(gè) double 類(lèi)型的變量都出錯(cuò)過(guò)。出錯(cuò)的時(shí)候,打印這些變量對(duì)應(yīng)地址存儲(chǔ)的值,發(fā)現(xiàn)這些內(nèi)存的值有 0 存在。因?yàn)?double 變量使用 8 bytes 的空間存放的,這些空間里存放的不是實(shí)際值,而是分符號(hào)位,指數(shù)位等。
根據(jù)這個(gè)現(xiàn)象,我有理由懷疑是某些時(shí)候的強(qiáng)轉(zhuǎn)沒(méi)有成功。

步驟2 證明和中斷的相關(guān)性

進(jìn)行關(guān)中斷測(cè)試,在關(guān)閉中斷的情況下,長(zhǎng)時(shí)間跑了測(cè)試,時(shí)間足夠長(zhǎng),發(fā)現(xiàn)并沒(méi)有出錯(cuò)。那么證明的確和中斷有關(guān)系。

步驟3 證明測(cè)試代碼的邏輯是沒(méi)有問(wèn)題

排查其他問(wèn)題:使用 arm 指令集的 libgcc 進(jìn)行測(cè)試,使用同樣的代碼,時(shí)間足夠長(zhǎng),也沒(méi)有出錯(cuò)。那么證明測(cè)試代碼的邏輯是沒(méi)有問(wèn)題的。

陷入了第一個(gè)瓶頸

確定中斷有問(wèn)題,那么推測(cè)偶爾出問(wèn)題肯定是恰好某個(gè)時(shí)刻的中斷踩到了特殊位置。修改代碼關(guān)注是否是中斷返回立即出錯(cuò),打印分析被中斷打斷處的指令,觀察是否是固定的某個(gè)指令。經(jīng)過(guò)漫長(zhǎng)的調(diào)試,觀察到的確有規(guī)律。
分析長(zhǎng)時(shí)間的出錯(cuò)前的 PC 指針的位置,很多是靠近 thumb 指令集里面的 IT block 指令。必須敏銳地抓住這個(gè)點(diǎn)。類(lèi)似下面的 it eq 指令。

001007d4 <__aeabi_ul2d>:1007d4:	ea50 0201 	orrs.w	r2, r0, r11007d8:	bf08      	it	eq1007da:	4770      	bxeq	lr1007dc:	b530      	push	{r4, r5, lr}1007de:	f04f 0500 	mov.w	r5, #01007e2:	e00a      	b.n	1007fa <__aeabi_l2d+0x16>

簡(jiǎn)化問(wèn)題

看手冊(cè)學(xué)習(xí) it block 指令。
// 學(xué)習(xí)過(guò)程不表

證明是 it 指令的問(wèn)題

調(diào)試指導(dǎo)思想是:縮小問(wèn)題的范圍
想辦法直接運(yùn)行這個(gè)指令,觀察是否出錯(cuò)。我使用內(nèi)聯(lián)匯編實(shí)現(xiàn),使用偽代碼解釋代碼邏輯

r1 = 0x10;
r2 = 0x10;
r3 = 0x20;
r4 = 0x40;r4 = r4 - r2;  //運(yùn)行后 r4 = 0x30// itte ge , 上一行指令會(huì)改變 cpsr 的 flag 標(biāo)志位,
// 若 ge: r1 = r1 + (r4 << 1)  //運(yùn)行后 r1 = 0x70;
// 若 ge: r2 = r2 + 0x10;
// 若 lt: r4 = r4 + 0x10;

代碼如下:

__attribute__((target("thumb"))) void thumb_ins(void);
void thumb_ins(void) {int ia = 0;int ib = 0;int ic = 0;int  cnt = 0;while (1) {ia = 0;ib = 0;ic = 0;asm volatile ("mov r1, #0x10");asm volatile ("mov r3, #0x20");asm volatile ("mov r2, #0x10");asm volatile ("mov r4, #0x40");asm volatile ("subs	r4, r4, r2");asm volatile ("itte  ge");asm volatile ("addge.w	r1, r1, r4, lsl #1");asm volatile ("addge r2, r2, #0x10");asm volatile ("addlt  r4, r4, #0x10");asm volatile ("mov %0, r1" : "=r" (ia));asm volatile ("mov %0, r2" : "=r" (ib));asm volatile ("mov %0, r4" : "=r" (ic));if ((ia != 0x70) || (ib != 0x20) || (ic != 0x30)) {printf("error!!!");printf(" r1 [0x%x] r2 [0x%x] r4[0x%x]\r\n", ia, ib, ic);}if (cnt ++ > 9000000) {printf(" r1 [0x%x] r2 [0x%x] r4[0x%x]\r\n", ia, ib, ic);cnt = 0;}}
}

經(jīng)過(guò)運(yùn)行測(cè)試,這個(gè)代碼運(yùn)行時(shí),也會(huì)打印出 error;關(guān)閉中斷進(jìn)行測(cè)試,則運(yùn)行不會(huì)打印 error。則完全證明了是 it 指令執(zhí)行的問(wèn)題。并且發(fā)現(xiàn)了出錯(cuò)時(shí), it block 控制的條件允許代碼全部沒(méi)有執(zhí)行,包括2條判斷條件相反的指令都沒(méi)有執(zhí)行。

陷入了第二個(gè)瓶頸 分析 it 指令執(zhí)行出錯(cuò)的原因

arm 手冊(cè)上關(guān)于這個(gè) it 指令從異常返回的描述:
On a branch or an exception return, if PSTATE.IT is set to a value that is not consistent with the instruction stream being branched to or returned to, then instruction execution is CONSTRAINED UNPREDICTABLE.
我們需要關(guān)注到異常返回的地址和異常返回時(shí) PSTATE.IT 的標(biāo)志狀態(tài)。

  • 經(jīng)過(guò)調(diào)試分析,已經(jīng)確認(rèn)我們的 RTOS 在異常保存上下文中 cpsr 的值是正確的。使用 msr 將其恢復(fù)也是正確的。也確認(rèn)了我們RTOS配置的返回地址也是正確的。滿(mǎn)足手冊(cè)中提到的注意事項(xiàng),問(wèn)題陷入僵局。
  • 試圖對(duì)比 Linux 源碼中的異常保存和恢復(fù)過(guò)程中,對(duì)于 thumb 指令是否有特殊處理,然而并沒(méi)有收獲。

問(wèn)題突破

經(jīng)過(guò)艱難的調(diào)試之后,終于有了新的突破
我們知道,在異常返回時(shí),是由硬件自動(dòng)將 spsr 寄存器中的值恢復(fù)到 cpsr。我在設(shè)置PC跳轉(zhuǎn)之前,讀出 spsr 的值,保存到內(nèi)存中,然后有了驚人的發(fā)現(xiàn):此時(shí) spsr 寄存器中的內(nèi)容和上下文結(jié)構(gòu)體中的值不一致,而且是關(guān)鍵的 IT block 的信息丟失。那么斷定是恢復(fù) spsr 的時(shí)候出錯(cuò)了。
經(jīng)過(guò)簡(jiǎn)單調(diào)試,和 Linux 進(jìn)行對(duì)比,發(fā)現(xiàn)了問(wèn)題的根源。

問(wèn)題解決

我們的 RTOS 恢復(fù) spsr 使用的指令為 msr spsr, r1 ,編譯生成的指令為 83ce0ae8: e169f001 msr SPSR_fc, r1。而 Linux 使用 msr spsr_cxsf, r1, 編譯生成的指令為 83ce0ae8: e16ff001 msr SPSR_fsxc, r1。我的 RTOS 在恢復(fù) spsr 中,丟失了關(guān)鍵的 s 和 x 域的內(nèi)容:

  • c 指 CPSR中的control field ( PSR[7:0])
  • f 指 flag field (PSR[31:24])
  • x 指 extend field (PSR[15:8])
  • s 指 status field ( PSR[23:16])
    而恰好 IT block 信息存放在 [26:25] + [15:10]
    it block
IT[1:0], bits [26:25] 
IT block state bits for the T32 IT (If-Then) instruction. See IT[7:2] for explanation of this field.
IT[7:2], bits [15:10] 
IT block state bits for the T32 IT (If-Then) instruction. This field must be interpreted in two parts. ? IT[7:5] holds the base condition for the IT block. The base condition is the top 3 bits of the 
condition code specified by the first condition field of the IT instruction.
? IT[4:0] encodes the size of the IT block, which is the number of instructions that are to be 
conditionally executed, by the position of the least significant 1 in this field. It also encodes the value of the least significant bit of the condition code for each instruction in the block.
The IT field is 0b00000000 when no IT block is active.

調(diào)試經(jīng)驗(yàn)總結(jié)

  1. 分析問(wèn)題,縮小問(wèn)題范圍
  2. 敏銳觀察,抓住靈感
  3. 驗(yàn)證寄存器的值是否正確不能讀中間狀態(tài),必須緊貼使用之前進(jìn)行驗(yàn)證
  4. 相信硬件,在計(jì)算機(jī)的世界沒(méi)有上帝
http://m.aloenet.com.cn/news/39992.html

相關(guān)文章:

  • 工控做網(wǎng)站網(wǎng)站免費(fèi)軟件
  • 做企業(yè)網(wǎng)站注意些啥百度指數(shù)數(shù)據(jù)分析平臺(tái)官網(wǎng)
  • 專(zhuān)門(mén)做圖片的網(wǎng)站有哪些今日軍事新聞
  • 網(wǎng)站建設(shè)銷(xiāo)售實(shí)習(xí)服務(wù)營(yíng)銷(xiāo)策劃方案
  • php網(wǎng)站微信支付怎么做黃頁(yè)引流推廣網(wǎng)站
  • 網(wǎng)站圖片計(jì)時(shí)器怎么做國(guó)內(nèi)時(shí)事新聞
  • 網(wǎng)站建設(shè)昆明色盲
  • 怎么查看網(wǎng)站的友情鏈接外鏈發(fā)布工具
  • 哪家做網(wǎng)站公司好搜索大全引擎地址
  • 免費(fèi)視頻網(wǎng)站制作愛(ài)上鏈外鏈購(gòu)買(mǎi)平臺(tái)
  • 網(wǎng)站建設(shè)與維護(hù)模擬一新聞?lì)^條免費(fèi)下載安裝
  • 返利網(wǎng)站程序產(chǎn)品推廣
  • 北京網(wǎng)站制作西安西安網(wǎng)紅
  • 做網(wǎng)站和web前端一樣嗎百度seo優(yōu)化招聘
  • 成都網(wǎng)站建設(shè)贏展成都網(wǎng)站建設(shè)方案推廣
  • 網(wǎng)站建設(shè)預(yù)付款比例惠州網(wǎng)絡(luò)營(yíng)銷(xiāo)
  • 成都廣告公司網(wǎng)站建設(shè)瑞金網(wǎng)絡(luò)推廣
  • 邯鄲網(wǎng)站建設(shè)公司群站優(yōu)化之鏈輪模式
  • 企業(yè)商務(wù)網(wǎng)站建設(shè)策劃書(shū)查詢(xún)域名注冊(cè)信息
  • 17網(wǎng)站一起做網(wǎng)店揭陽(yáng)seo合作
  • wordpress自定義登陸頁(yè)面天津seo方案
  • 用表格做網(wǎng)站廊坊首頁(yè)霸屏優(yōu)化
  • 網(wǎng)站建設(shè)要求百度指數(shù)疫情
  • wordpress網(wǎng)站設(shè)計(jì)作業(yè)線(xiàn)下?tīng)I(yíng)銷(xiāo)推廣方式都有哪些
  • logosc網(wǎng)站怎么做的網(wǎng)絡(luò)營(yíng)銷(xiāo)的基本特征有哪七個(gè)
  • 長(zhǎng)沙建設(shè)公司網(wǎng)站網(wǎng)絡(luò)推廣產(chǎn)品公司
  • 小游戲網(wǎng)站審核怎么做百度信息
  • 迅馳互聯(lián)網(wǎng)站建設(shè)網(wǎng)絡(luò)推廣怎么樣廣東云浮疫情最新情況
  • 網(wǎng)站建設(shè) 大公司小公司seo排名優(yōu)化是什么意思
  • 做ppt哪個(gè)網(wǎng)站好百度seo查詢(xún)