亚洲视频二区_亚洲欧洲日本天天堂在线观看_日韩一区二区在线观看_中文字幕不卡一区

公告:魔扣目錄網(wǎng)為廣大站長(zhǎng)提供免費(fèi)收錄網(wǎng)站服務(wù),提交前請(qǐng)做好本站友鏈:【 網(wǎng)站目錄:http://www.430618.com 】, 免友鏈快審服務(wù)(50元/站),

點(diǎn)擊這里在線咨詢客服
新站提交
  • 網(wǎng)站:51998
  • 待審:31
  • 小程序:12
  • 文章:1030137
  • 會(huì)員:747

一:背景

1. 講故事

前段時(shí)間收到了一個(gè)朋友的求助,說(shuō)他的ERP網(wǎng)站系統(tǒng)會(huì)出現(xiàn)偶發(fā)性崩潰,找了好久也沒(méi)找到是什么原因,讓我?guī)兔聪拢鋵?shí)崩潰好說(shuō),用 procdump 自動(dòng)抓一個(gè)就好,拿到 dump 之后,接下來(lái)就是一頓分析了。

二:WinDbg 分析

1. 是什么導(dǎo)致的崩潰

windbg 有一個(gè)自動(dòng)化的分析命令 !analyze -v 可以幫我們提前預(yù)診一下,就好像進(jìn)醫(yī)院先在問(wèn)詢臺(tái)那里過(guò)一下。

0:019> !analyze -v
CONTEXT:  (.ecxr)
eax=14c9cd00 ebx=00000000 ecx=00000000 edx=00000000 esi=00000000 edi=14c9d664
eip=682a024a esp=14c9cfd4 ebp=14c9d018 iopl=0         nv up ei pl nz ac po nc
cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00000212
msvcr90!fprintf+0x34:
682a024a 83c414          add     esp,14h
Resetting default scope

EXCEPTION_RECORD:  (.exr -1)
ExceptionAddress: 682a024a (msvcr90!fprintf+0x00000034)
   ExceptionCode: c0000417
  ExceptionFlags: 00000001
NumberParameters: 0

PROCESS_NAME:  w3wp.exe

ERROR_CODE: (NTSTATUS) 0xc0000417 -    C

EXCEPTION_CODE_STR:  c0000417

STACK_TEXT:  
14c9d018 1766013b     00000000 176d9c60 17def1a8 msvcr90!fprintf+0x34
WARNING: Stack unwind information not available. Following frames may be wrong.
14c9d664 454c5153     75636578 203a6574 5332347b satrda!Writer_Write+0x4bb
000000c8 75636578     203a6574 5332347b 207d3230 0x454c5153
000000c8 17673623     17d538e8 17ded730 00000001 crypt32!profapi_NULL_THUNK_DATA_DLA <PERF> (crypt32+0x126578)
00000009 176604b6     14c9d74c 17ded730 17dae9c8 satrda!SATRDA_Proto_UnitTest+0x6c93
ffffffff 17654012     17dae9c8 17d538e8 17ded730 satrda!Writer_Write+0x836
17dae9c8 665fe072     14c9d74c 00000001 1765405b satrda!ConfigDSN+0xd0c2
...
160a0000 00000000     00000000 00000000 00000000 0x7071e31

FAULTING_SOURCE_LINE:  f:ddvctoolscrt_bldself_x86crtsrcfprintf.c

FAULTING_SOURCE_FILE:  f:ddvctoolscrt_bldself_x86crtsrcfprintf.c

FAULTING_SOURCE_LINE_NUMBER:  55

FAULTING_SOURCE_CODE:  
No source found for 'f:ddvctoolscrt_bldself_x86crtsrcfprintf.c'


SYMBOL_NAME:  msvcr90!fprintf+34

MODULE_NAME: msvcr90

IMAGE_NAME:  msvcr90.dll

STACK_COMMAND:  ~19s; .ecxr ; kb

FAILURE_BUCKET_ID:  INVALID_CRUNTIME_PARAMETER_c0000417_msvcr90.dll!fprintf

從錯(cuò)誤信息看,問(wèn)題是出在 satrda.dll 這個(gè)第三方庫(kù),趕緊網(wǎng)上搜一下是這是何方神圣。

 

圖片

 

看樣子是一個(gè)連接數(shù)據(jù)庫(kù)的商業(yè)組件,接下來(lái)看下 FAILURE_BUCKET_ID: INVALID_CRUNTIME_PARAMETER_c0000417_msvcr90.dll!fprintf 信息,可以發(fā)現(xiàn)因?yàn)樵谡{(diào)用 fprintf 函數(shù)時(shí)出現(xiàn)了參數(shù)錯(cuò)誤,到這里我們將包圍圈極大的收縮了。

2. 為什么會(huì)出現(xiàn)參數(shù)錯(cuò)誤

熟悉 C 語(yǔ)言 fprintf 函數(shù)的朋友都知道,它是用來(lái)向 文件 寫入數(shù)據(jù)的,類似 C# 的 WriteFile,既然報(bào)了參數(shù)異常,那就說(shuō)明肯定在參數(shù)上出了問(wèn)題,接下來(lái)看下它的簽名。

int fprintf(
   FILE *stream,
   const char *format [,
   argument ]...
);

有了這些基礎(chǔ)之后切到 19 號(hào)線程觀察下它的調(diào)用棧。

0:019> ~19s; .ecxr ; kb 10
eax=14c9cd00 ebx=00000000 ecx=00000000 edx=00000000 esi=00000000 edi=14c9d664
eip=682a024a esp=14c9cfd4 ebp=14c9d018 iopl=0         nv up ei pl nz ac po nc
cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00000212
msvcr90!fprintf+0x34:
682a024a 83c414          add     esp,14h
 # ChildEBP RetAddr      Args to Child              
00 14c9d018 1766013b     00000000 176d9c60 17def1a8 msvcr90!fprintf+0x34 [f:ddvctoolscrt_bldself_x86crtsrcfprintf.c @ 55] 
WARNING: Stack unwind information not available. Following frames may be wrong.
01 14c9d664 454c5153     75636578 203a6574 5332347b satrda!Writer_Write+0x4bb
02 000000c8 75636578     203a6574 5332347b 207d3230 0x454c5153
03 000000c8 17673623     17d538e8 17ded730 00000001 crypt32!profapi_NULL_THUNK_DATA_DLA <PERF> (crypt32+0x126578)
04 00000009 176604b6     14c9d74c 17ded730 17dae9c8 satrda!SATRDA_Proto_UnitTest+0x6c93
05 ffffffff 17654012     17dae9c8 17d538e8 17ded730 satrda!Writer_Write+0x836
06 17dae9c8 665fe072     14c9d74c 00000001 1765405b satrda!ConfigDSN+0xd0c2
07 17ded730 63207463     2c44492e 6f532e63 632c7472 clr!CompressDebugInfo::CompressBoundariesAndVars+0x2d0
08 656c6573 2c44492e     6f532e63 632c7472 7261502e 0x63207463
09 656c6573 6f532e63     632c7472 7261502e 49746e65 0x2c44492e
0a 656c6573 69482e63     6e656464 4c2e632c 6c657665 Microsoft_Build_Tasks_v4_0_ni+0x2f2e63
0b 2c687461 6e656464     4c2e632c 6c657665 64646948 System_ServiceModel_Web_ni+0xf2e63
0c 69482e63 4c2e632c     6c657665 64646948 632c6e65 System_Runtime_Serialization_ni+0x226464
0d 6e656464 6c657665     64646948 632c6e65 6d6f432e 0x4c2e632c
0e 6e656464 64646948     632c6e65 6d6f432e 656e6f70 System_ServiceModel_ni+0x537665
0f 6c657665 632c6e65     6d6f432e 656e6f70 632c746e 0x64646948

從線程棧來(lái)看 msvcr90!fprintf 函數(shù)的第一個(gè)參數(shù)居然是 00000000 ,也就是說(shuō) *stream 這個(gè)參數(shù)為 NULL,難怪說(shuō)參數(shù)異常!

3. 為什么 stream 為空

熟悉 C 的朋友應(yīng)該知道 *stream 參數(shù)是通過(guò) fopen 函數(shù)得到的,可能有些朋友有點(diǎn)混,這里就寫個(gè)簡(jiǎn)單的模型吧。

int main()
{
 FILE* pFile;
 int n;
 char name[100];

 pFile = fopen("D:\dumps\myfile2.txt", "w");

 gets_s(name, 100);

 fprintf(pFile, "%s", name);

 fclose(pFile);

 return 0;
}

接下來(lái)我們到 dump 中尋找一下 fopen 函數(shù),這個(gè)在線程棧上是沒(méi)有了,先提取出 msvcr90!fprintf+0x34 中的 RetAddr=1766013b 返回值地址到匯編窗口查找,截圖如下:

 

圖片

 

從圖中可以看到,esi 是 eax 給的,而 eax 是 call 返回值給的,不出意外 176D727Ch 中存的就是 fopen 函數(shù),輸出如下:

0:019> u poi(176D727Ch)
msvcr90!fopen [f:ddvctoolscrt_bldself_x86crtsrcfopen.c @ 123]:
682a01a2 8bff            mov     edi,edi
682a01a4 55              push    ebp
682a01a5 8bec            mov     ebp,esp
682a01a7 6a40            push    40h
682a01a9 ff750c          push    dword ptr [ebp+0Ch]
682a01ac ff7508          push    dword ptr [ebp+8]
682a01af e825ffffff      call    msvcr90!_fsopen (682a00d9)
682a01b4 83c40c          add     esp,0Ch

接下來(lái)我們需要提取 fopen 中的兩個(gè)參數(shù),截圖如下:

 

圖片

 

第二個(gè)參數(shù)很好獲取就是 176D9C60h 的 ascii 表示,第一個(gè)參數(shù)獲取起來(lái)就麻煩了,我們需要詳細(xì)的如圖那樣推測(cè)當(dāng)時(shí)的 esp 指向的位置。

 

0:019> da 14c9d074
14c9d074  "0810"
0:019> da 176D9C64h
176d9c64  "at++"

 

還原成 C 代碼大概就是:

FILE*  pFile = fopen("0810", "at++");

代碼大概是恢復(fù)出來(lái)了,那為什么會(huì)拋異常呢?windbg 有一個(gè) !gle 命令可以查看當(dāng)時(shí)發(fā)生了什么錯(cuò)誤。

0:019> !gle
LastErrorValue: (NTSTATUS) 0 (0) - STATUS_SUCCESS
LastStatusValue: (NTSTATUS) 0xc000003a - {            }       %hs

接下來(lái)到微軟的官方文檔:https://learn.microsoft.com/en-us/openspecs/windows_protocols/ms-erref/596a1078-e883-4972-9bbc-49e60bebca55 找一下這個(gè) 3a 到底表示啥意思,截圖如下:

 

圖片

 

從圖中看,原來(lái)是路徑不存在的錯(cuò)誤,應(yīng)該就是沒(méi)找到 0810 這個(gè)文件。

到這里就基本弄清楚了來(lái)龍去脈,應(yīng)該是朋友的服務(wù)器有意或者無(wú)意清理了由 satrda 生成的 0810 文件,引發(fā) satrda.dll 找不到文件路徑導(dǎo)致的程序崩潰,將這些信息提供給朋友之后,讓朋友去找 satrda 官網(wǎng)去了解下詳情,畢竟官方才是最清楚的。

三:總結(jié)

這次事故是由于 satrda 層面找不到文件路徑導(dǎo)致的程序崩潰,據(jù)朋友說(shuō)在 C# 層面沒(méi)收到這種C++異常,確實(shí)當(dāng) C# 和 C++ 產(chǎn)生交互時(shí)經(jīng)常會(huì)有各種奇怪的問(wèn)題,我無(wú)意刪除你的,你無(wú)意干擾我的,大家都好自為之吧

分享到:
標(biāo)簽:NET
用戶無(wú)頭像

網(wǎng)友整理

注冊(cè)時(shí)間:

網(wǎng)站:5 個(gè)   小程序:0 個(gè)  文章:12 篇

  • 51998

    網(wǎng)站

  • 12

    小程序

  • 1030137

    文章

  • 747

    會(huì)員

趕快注冊(cè)賬號(hào),推廣您的網(wǎng)站吧!
最新入駐小程序

數(shù)獨(dú)大挑戰(zhàn)2018-06-03

數(shù)獨(dú)一種數(shù)學(xué)游戲,玩家需要根據(jù)9

答題星2018-06-03

您可以通過(guò)答題星輕松地創(chuàng)建試卷

全階人生考試2018-06-03

各種考試題,題庫(kù),初中,高中,大學(xué)四六

運(yùn)動(dòng)步數(shù)有氧達(dá)人2018-06-03

記錄運(yùn)動(dòng)步數(shù),積累氧氣值。還可偷

每日養(yǎng)生app2018-06-03

每日養(yǎng)生,天天健康

體育訓(xùn)練成績(jī)?cè)u(píng)定2018-06-03

通用課目體育訓(xùn)練成績(jī)?cè)u(píng)定