Microsoft MVP성태의 닷넷 이야기
글쓴 사람
정성태 (techsharer at outlook.com)
홈페이지
첨부 파일
 
(연관된 글이 2개 있습니다.)
(시리즈 글이 5개 있습니다.)
디버깅 기술: 112. windbg - 닷넷 메모리 덤프에서 전역 객체의 내용을 조사하는 방법
; https://www.sysnet.pe.kr/2/0/11460

디버깅 기술: 115. windbg - 닷넷 메모리 덤프에서 정적(static) 필드 값을 조사하는 방법
; https://www.sysnet.pe.kr/2/0/11487

.NET Framework: 957. C# - static 필드의 정보가 GC Heap에 저장될까요?
; https://www.sysnet.pe.kr/2/0/12387

디버깅 기술: 182. windbg - 닷넷 메모리 덤프에서 AppDomain에 걸친 정적(static) 필드 값을 조사하는 방법
; https://www.sysnet.pe.kr/2/0/13004

디버깅 기술: 193. Windbg - ThreadStatic 필드 값을 조사하는 방법
; https://www.sysnet.pe.kr/2/0/13414




windbg - 닷넷 메모리 덤프에서 정적(static) 필드 값을 조사하는 방법

지난번에, singleton을 비롯해 인스턴스화된 객체 값을 조사하는 방법을 설명했는데요.

windbg - 닷넷 메모리 덤프에서 전역 객체의 내용을 조사하는 방법
; https://www.sysnet.pe.kr/2/0/11460

간단하게 다음과 같은 예제 코드를 이용해 테스트할 수 있습니다.

using System;

namespace ConsoleApp1
{
    class Program
    {
        static void Main(string[] args)
        {
            InstanceClass inst = new InstanceClass();
            inst.Count++;
            Console.WriteLine(inst.Count);

            Console.ReadLine(); // 이 시점에 메모리 덤프
        }
    }

    public class InstanceClass
    {
        public int Count;
    }
}

덤프 파일을 windbg에서 열고 지난번 글에서 설명한 대로 InstanceClass 타입의 Count 값을 이렇게 확인하게 됩니다.

0:000> !dumpheap -type ConsoleApp1.InstanceClass
         Address               MT     Size
0000013d93f26ce8 00007ffde3015ab8       24     

Statistics:
              MT    Count    TotalSize Class Name
00007ffde3015ab8        1           24 ConsoleApp1.InstanceClass
Total 1 objects

0:000> !DumpObj /d 0000013d93f26ce8
Name:        ConsoleApp1.InstanceClass
MethodTable: 00007ffde3015ab8
EEClass:     00007ffde3161020
Size:        24(0x18) bytes
File:        E:\ConsoleApp1\ConsoleApp1\bin\Debug\ConsoleApp1.exe
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
00007ffe3df69500  4000002        8         System.Int32  1 instance                1 Count

그럼, 이제 위의 예제 코드에 static 필드를 가진 타입을 추가해 보겠습니다.

using System;

namespace ConsoleApp1
{
    class Program
    {
        static void Main(string[] args)
        {
            StaticClass.Count++;
            Console.WriteLine(StaticClass.Count);

            InstanceClass inst = new InstanceClass();
            inst.Count++;
            Console.WriteLine(inst.Count);

            Console.ReadLine();
        }
    }

    public class StaticClass
    {
        public static int Count;
    }

    public class InstanceClass
    {
        public int Count;
    }
}

당연하겠지만, StaticClass 클래스의 Count 값은 dumpheap으로는 알 수 없습니다. 심지어, 위의 경우에는 인스턴스화 한 적도 없기 때문에 dumpheap으로는 기록조차 찾을 수 없습니다.

0:000> !dumpheap -type ConsoleApp1.StaticClass
         Address               MT     Size

Statistics:
              MT    Count    TotalSize Class Name
Total 0 objects

new를 했어야 Managed Heap에 기록이 남기 때문에 위의 결과는 지극히 정상적인 것입니다. 대신, static 필드의 값은 클래스 정보를 통해 알아낼 수 있습니다. 이를 위해 다음과 같이 클래스의 식별자를 알아내고,

0:000> !name2ee ConsoleApp1.exe!ConsoleApp1.StaticClass
Module:      00007ffde3014110
Assembly:    ConsoleApp1.exe
Token:       0000000002000003
MethodTable: 00007ffde3015b68
EEClass:     00007ffde3161098
Name:        ConsoleApp1.StaticClass

그에 대해 DumpClass 명령을 내리면 됩니다.

0:000> !DumpClass /d 00007ffde3161098
Class Name:      ConsoleApp1.StaticClass
mdToken:         0000000002000003
File:            E:\ConsoleApp1\ConsoleApp1\bin\Debug\ConsoleApp1.exe
Parent Class:    00007ffe3d8d1968
Module:          00007ffde3014110
Method Table:    00007ffde3015b68
Vtable Slots:    4
Total Method Slots:  5
Class Attributes:    100001  
Transparency:        Critical
NumInstanceFields:   0
NumStaticFields:     1
              MT    Field   Offset                 Type VT     Attr            Value Name
00007ffe3df69500  4000001       3c         System.Int32  1   static                1 Count




참고로, 타입 이름을 기준으로 하는 "!dumpheap -type ConsoleApp1.InstanceClass" 명령어로 관리 힙을 검색하는 것은 경우에 따라 불편함이 있습니다. 왜냐하면, 검색어로 준 "ConsoleApp1.InstanceClass" 이름과 정확히 일치하는 것이 아니라 그것을 포함하고 있어도 검색이 되기 때문입니다.

따라서, 해당 타입에 대해 정확히 일치하는 것만 검색하고 싶다면 name2ee 명령을 통해 우선 그 타입의 MethodTable을 얻는 것이 좋습니다.

0:017> !name2ee *!ConsoleApp1.InstanceClass
Module: 02d32010 (teslib.dll)
Token: 0x02000154
MethodTable: 043117dc
EEClass: 02db3280
Name: ConsoleApp1.InstanceClass

이렇게 알아낸 MethodTable로 dumpheap 검색을 하면 됩니다.

0:017> !DumpHeap -mt  043117dc




[이 글에 대해서 여러분들과 의견을 공유하고 싶습니다. 틀리거나 미흡한 부분 또는 의문 사항이 있으시면 언제든 댓글 남겨주십시오.]

[연관 글]






[최초 등록일: ]
[최종 수정일: 4/17/2025]

Creative Commons License
이 저작물은 크리에이티브 커먼즈 코리아 저작자표시-비영리-변경금지 2.0 대한민국 라이센스에 따라 이용하실 수 있습니다.
by SeongTae Jeong, mailto:techsharer at outlook.com

비밀번호

댓글 작성자
 




... 76  77  78  79  80  81  82  83  84  85  86  87  [88]  89  90  ...
NoWriterDateCnt.TitleFile(s)
11736정성태10/12/201818384오류 유형: 492. Visual Studio 로딩 시 오류 - The 'Scc Display Information' package did not load correctly.
11735정성태10/12/201824146VS.NET IDE: 129. Visual Studio - 특정 문자(열)를 개행 문자로 바꾸는 방법
11734정성태10/10/201818525Linux: 4. Synology NAS(DS216+II)에 FTDI 장치 연결 후 C#(.NET Core)으로 DTR 제어파일 다운로드1
11733정성태10/10/201821263Linux: 3. Synology NAS(DS216+II)에서 FTDI 장치를 C/C++로 제어
11732정성태10/10/201820980디버깅 기술: 119. windbg 분석 사례 - 종료자(Finalizer)에서 예외가 발생한 경우 비정상 종료(Crash) 발생파일 다운로드1
11731정성태10/9/201820515개발 환경 구성: 409. C# - REST API를 이용해 Azure Kudu 서비스 이용 - 웹 앱 확장 처리파일 다운로드1
11730정성태10/9/201819619개발 환경 구성: 408. C# - REST API를 이용해 Azure Kudu 서비스 이용 - 파일 처리파일 다운로드1
11729정성태10/9/201822229Windows: 150. 윈도우에서 ARP Cache 목록 확인 및 삭제하는 방법
11728정성태10/9/201820023사물인터넷: 50. Audio Jack 커넥터의 IR 적외선 송신기 [1]
11727정성태10/8/201821276오류 유형: 491. Visual Studio의 리눅스 SSH 원격 연결 - "Connectivity Failure. Please make sure host name and port number are correct."
11726정성태10/7/201823941사물인터넷: 49. 라즈베리 파이를 이용해 원격 컴퓨터의 전원 스위치 제어파일 다운로드1
11724정성태10/5/201823610개발 환경 구성: 407. 유니코드와 한글 - "Hangul Compatibility Jamo"파일 다운로드1
11723정성태10/4/201817506개발 환경 구성: 406. "Docker for Windows" 컨테이너 내의 .NET Core 응용 프로그램에서 직렬 포트(Serial Port, COM Port) 사용 방법
11722정성태10/4/201821188.NET Framework: 798. C# - Hyper-V 가상 머신의 직렬 포트와 연결된 Named Pipe 간의 통신파일 다운로드1
11721정성태10/4/201821487.NET Framework: 797. Linux 환경의 .NET Core 응용 프로그램에서 직렬 포트(Serial Port, COM Port) 사용 방법파일 다운로드1
11720정성태10/4/201823043개발 환경 구성: 405. Hyper-V 가상 머신에서 직렬 포트(Serial Port, COM Port) 사용
11719정성태10/4/201823660.NET Framework: 796. C# - 인증서를 윈도우에 설치하는 방법
11718정성태10/4/201818850개발 환경 구성: 404. (opkg가 설치된) Synology NAS(DS216+II)에 cmake 설치
11717정성태10/3/201821444사물인터넷: 48. 넷두이노의 C# 네트워크 프로그램 [1]
11716정성태10/3/201821994사물인터넷: 47. Raspberry PI Zero (W)에 FTDI 장치 연결 후 C/C++로 DTR 제어파일 다운로드1
11715정성태10/3/201820788사물인터넷: 46. Raspberry PI Zero (W)에 docker 설치
11714정성태10/2/201820026사물인터넷: 45. Raspberry PI에 ping을 hostname으로 하는 방법
11713정성태10/2/201822445개발 환경 구성: 403. Synology NAS(DS216+II)에 docker 설치 후 .NET Core 2.1 응용 프로그램 실행하는 방법
11712정성태10/2/201827629.NET Framework: 795. C# - 폰트 목록을 한글이 아닌 영문으로 구하는 방법 [3]
11711정성태10/2/201823087오류 유형: 490. 윈도우 라이선스 키 입력 오류 0xc004f050, 0xc004e028
11710정성태10/2/201822041.NET Framework: 794. C# - 같은 모양, 다른 값의 한글 자음을 비교하는 호환 분해 [5]
... 76  77  78  79  80  81  82  83  84  85  86  87  [88]  89  90  ...