使用windbg排查一个内存溢出的问题

发现有一个服务占用大量的内存

image

奇怪的是服务一开始的时候只占用100M左右内存,随着时间推移越来越大,最后导致服务器内存吃紧。这可以算是一种内存泄漏的问题,之所以标题不说是内存泄漏,最后就会知道,并不是因为什么东西没回收导致内存泄漏。

于是dump了一下进程,使用windbg打开后先看看托管堆情况:

 

0:000> !eeheap -gc
Number of GC Heaps: 1
generation 0 starts at 0x00000000f2f76a70
generation 1 starts at 0x00000000f2f03400
generation 2 starts at 0x0000000002aa1000
ephemeral segment allocation context: none
         segment            begin         allocated             size
00000000001a0b80 0000064274e17588  0000064274e4d910 0x0000000000036388(222088)
00000000001a0990 0000064276928088  0000064276952e58 0x000000000002add0(175568)
0000000000163cd0 00000642787c3188  0000064278804c38 0x0000000000041ab0(268976)
0000000002aa0000 0000000002aa1000  0000000012a9fd70 0x000000000fffed70(268430704)
000000001e280000 000000001e281000  000000002e26ec58 0x000000000ffedc58(268360792)
000000003b0c0000 000000003b0c1000  000000004b0ac0f0 0x000000000ffeb0f0(268349680)
000000007fff0000 000000007fff1000  000000008ffeffb8 0x000000000fffefb8(268431288)
000000008fff0000 000000008fff1000  000000009ffea648 0x000000000fff9648(268408392)
00000000bfff0000 00000000bfff1000  00000000cffeffd8 0x000000000fffefd8(268431320)
00000000cfff0000 00000000cfff1000  00000000dffeffd8 0x000000000fffefd8(268431320)
00000000dfff0000 00000000dfff1000  00000000effeffb8 0x000000000fffefb8(268431288)
00000000efff0000 00000000efff1000  00000000f31fecf0 0x000000000320dcf0(52485360)
Large object heap starts at 0x0000000012aa1000
         segment            begin         allocated             size
0000000012aa0000 0000000012aa1000  000000001aa9b4f0 0x0000000007ffa4f0(134194416)
000000002fca0000 000000002fca1000  0000000037c92c88 0x0000000007ff1c88(134159496)
000000004b0c0000 000000004b0c1000  00000000530a2368 0x0000000007fe1368(134091624)
00000000530c0000 00000000530c1000  000000005b0bb3f0 0x0000000007ffa3f0(134194160)
0000000068140000 0000000068141000  00000000701236b8 0x0000000007fe26b8(134096568)
000000009fff0000 000000009fff1000  00000000a7fd37b0 0x0000000007fe27b0(134096816)
00000000a7ff0000 00000000a7ff1000  00000000af362700 0x0000000007371700(121050880)
00000000b7ff0000 00000000b7ff1000  00000000bc1a1260 0x00000000041b0260(68878944)
000000005b0c0000 000000005b0c1000  000000005f2c1048 0x0000000004200048(69206088)
00000000ffff0000 00000000ffff1000  0000000107ff1020 0x0000000008000020(134217760)
000000010bff0000 000000010bff1000  00000001101f1048 0x0000000004200048(69206088)
0000000113ff0000 0000000113ff1000  000000011bff1020 0x0000000008000020(134217760)
000000011fff0000 000000011fff1000  00000001241f1048 0x0000000004200048(69206088)
0000000127ff0000 0000000127ff1000  000000012fff1020 0x0000000008000020(134217760)
0000000133ff0000 0000000133ff1000  000000013d1f1080 0x0000000009200080(153092224)
000000013fff0000 000000013fff1000  0000000148229330 0x0000000008238330(136545072)
Total Size        0xf4163e98(4095098520)
------------------------------
GC Heap Size        0xf4163e98(4095098520)

 

4G内存占用,然后看看哪些对象最占用内存:

 

0:000> !dumpheap –stat

00000642788e5b38     5168    213551344 System.Int32[]
00000642b78659d0     2294    277543696 System.Data.RBTree`1+Node[[System.Int32, mscorlib]][]
00000642b7820d60     2338    346840112 System.Data.RBTree`1+Node[[System.Data.DataRow, System.Data]][]
0000000000165b40     4000    378238288      Free
00000642788d4758     4131    675366800 System.Object[]
00000642b77fe7c0  8667392    832069632 System.Data.DataRow
000006427881aaf8 18056660   1220045624 System.String

 

其中字符串占用1220MB,DataRow占用832MB,object数组占用675MB,就这三位大哥加起来差不多3G了,从什么红黑树结构和DataRow能初步判断,程序中用到了DataTable,866万行数据在内存中,再来算下一个字符串大概也就占用67字节,不是很大,这很可能属于一个DataRow的列数据。随便选一个DataRow开刀:

 

0:000> !dumpheap -mt 00000642b77fe7c0
         Address               MT     Size
0000000002aa2a68 00000642b77fe7c0       96    
0000000002aa9870 00000642b77fe7c0       96    
0000000002aae0c8 00000642b77fe7c0       96    
0000000002aae1b0 00000642b77fe7c0       96    
0000000002aae290 00000642b77fe7c0       96    
0000000002aae380 00000642b77fe7c0       96    
0000000002aae468 00000642b77fe7c0       96    
0000000002aae550 00000642b77fe7c0       96    
0000000002aae648 00000642b77fe7c0       96    
0000000002aae730 00000642b77fe7c0       96    

 

0:000> !do 0000000002aa2a68
Name: System.Data.DataRow
MethodTable: 00000642b77fe7c0
EEClass: 00000642b781e250
Size: 96(0x60) bytes
(C:\WINDOWS\assembly\GAC_64\System.Data\2.0.0.0__b77a5c561934e089\System.Data.dll)
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
00000642b77fcfb0  40006ad        8 ...em.Data.DataTable  0 instance 0000000002ab2590 _table
00000642b77ff198  40006ae       10 ...aColumnCollection  0 instance 0000000002aad950 _columns
0000064278827060  40006af       30         System.Int32  0 instance            31163 oldRecord
0000064278827060  40006b0       34         System.Int32  0 instance            31163 newRecord
0000064278827060  40006b1       38         System.Int32  0 instance               -1 tempRecord
0000064278827060  40006b2       3c         System.Int32  0 instance            31164 _rowID
00000642b7838d00  40006b3       40         System.Int32  0 instance                0 _action
0000064278821048  40006b4       50       System.Boolean  0 instance                0 inChangingEvent
0000064278821048  40006b5       51       System.Boolean  0 instance                0 inDeletingEvent
0000064278821048  40006b6       52       System.Boolean  0 instance                0 inCascade
00000642b77fe2f0  40006b7       18 ...m.Data.DataColumn  0 instance 0000000000000000 _lastChangedColumn
0000064278827060  40006b8       44         System.Int32  0 instance                0 _countColumnChange
00000642b78372f8  40006b9       20 ...em.Data.DataError  0 instance 0000000000000000 error
0000064278818fb0  40006ba       28        System.Object  0 instance 0000000000000000 _element
0000064278827060  40006bb       48         System.Int32  0 instance          3604796 _rbTreeNodeId
0000064278827060  40006bd       4c         System.Int32  0 instance           123463 ObjectID
0000064278827060  40006bc      4e8         System.Int32  0   static          8670024 _objectTypeCount

 

这是一个DataRow,那么我们来看看这个DataTable的情况:

0:000> !do 0000000002ab2590
Name: System.Data.DataTable
MethodTable: 00000642b77fcfb0
EEClass: 00000642b781d3b0
Size: 512(0x200) bytes
(C:\WINDOWS\assembly\GAC_64\System.Data\2.0.0.0__b77a5c561934e089\System.Data.dll)
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
0000064274e54480  400099c        8 ...ponentModel.ISite  0 instance 0000000000000000 site
0000064274e4f1d8  400099d       10 ....EventHandlerList  0 instance 0000000000000000 events
0000064278818fb0  400099b      3d0        System.Object  0   static 0000000000000000 EventDisposed
0000000000000000  4000732       18  System.Data.DataSet  0 instance 0000000000000000 dataSet
00000642b77feb30  4000733       20 System.Data.DataView  0 instance 0000000000000000 defaultView
0000064278827060  4000734      1a0         System.Int32  0 instance          8575118 nextRowID
00000642b781ec10  4000735       28 ...DataRowCollection  0 instance 0000000002aada90 rowCollection
00000642b77ff198  4000736       30 ...aColumnCollection  0 instance 0000000002aad950 columnCollection
00000642b781e9d0  4000737       38 ...straintCollection  0 instance 0000000002aada30 constraintCollection
0000064278827060  4000738      1a4         System.Int32  0 instance                8 elementColumnCount
00000642b7800278  4000739       40 ...elationCollection  0 instance 0000000000000000 parentRelationsCollection
00000642b7800278  400073a       48 ...elationCollection  0 instance 0000000000000000 childRelationsCollection
00000642b77ff080  400073b       50 ...ata.RecordManager  0 instance 0000000002aad7f0 recordManager
0000000000000000  400073c       58                       0 instance 0000000002aae060 indexes
0000000000000000  400073d       60                       0 instance 0000000000000000 shadowIndexes
0000064278827060  400073e      1a8         System.Int32  0 instance                0 shadowCount
00000642b783bce8  400073f       68 ...ropertyCollection  0 instance 0000000000000000 extendedProperties
000006427881aaf8  4000740       70        System.String  0 instance 0000000002aa4f68 tableName
000006427881aaf8  4000741       78        System.String  0 instance 0000000000000000 tableNamespace

 

想通过!objsize看看这个DataTable的大小,是不是我们找的那个大家伙,可惜等了一个小时也没出来结果,只能放弃那么有没有办法看到行列数呢?

 

0:000> !do 0000000002aad950
Name: System.Data.DataColumnCollection
MethodTable: 00000642b77ff198
EEClass: 00000642b788d078
Size: 96(0x60) bytes
(C:\WINDOWS\assembly\GAC_64\System.Data\2.0.0.0__b77a5c561934e089\System.Data.dll)
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
0000064274e6d8c8  400061f      220 ...onChangeEventArgs  0   static 0000000000000000 RefreshEventArgs
00000642b77fcfb0  4000675        8 ...em.Data.DataTable  0 instance 0000000002ab2590 table
000006427883e400  4000676       10 ...ections.ArrayList  0 instance 0000000002aad9b0 _list
0000064278827060  4000677       48         System.Int32  0 instance                1 defaultNameIndex
00000642788d4758  4000678       18      System.Object[]  0 instance 0000000000000000 delayedAddRangeColumns
00000642788405d8  4000679       20 ...ections.Hashtable  0 instance 0000000002aad9d8 columnFromName
0000064274e67628  400067a       28 ...hangeEventHandler  0 instance 0000000000000000 onCollectionChangedDelegate
0000064274e67628  400067b       30 ...hangeEventHandler  0 instance 0000000000000000 onCollectionChangingDelegate
0000064274e67628  400067c       38 ...hangeEventHandler  0 instance 0000000000000000 onColumnPropertyChangedDelegate
0000064278821048  400067d       54       System.Boolean  0 instance                0 fInClear
00000642788d4758  400067e       40      System.Object[]  0 instance 0000000002ab27a8 columnsImplementingIChangeTracking
0000064278827060  400067f       4c         System.Int32  0 instance                0 nColumnsImplementingIChangeTracking
0000064278827060  4000680       50         System.Int32  0 instance                0 nColumnsImplementingIRevertibleChangeTracking
0:000> !do 0000000002aad9b0
Name: System.Collections.ArrayList
MethodTable: 000006427883e400
EEClass: 0000064278955b38
Size: 40(0x28) bytes
(C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
00000642788d4758  4000911        8      System.Object[]  0 instance 0000000002b72888 _items
0000064278827060  4000912       18         System.Int32  0 instance                8 _size
0000064278827060  4000913       1c         System.Int32  0 instance                8 _version
0000064278818fb0  4000914       10        System.Object  0 instance 0000000000000000 _syncRoot
00000642788d4758  4000915      360      System.Object[]  0   shared           static emptyArray
                                 >> Domain:Value  0000000000160080:0000000002aa1e80 <<
0:000> !do 0000000002b72888
Name: System.Object[]
MethodTable: 00000642788d4758
EEClass: 00000642789d2f80
Size: 96(0x60) bytes
Array: Rank 1, Number of elements 8, Type CLASS
Element Type: System.Object
Fields:
None

 

这里看到了列数为8,我们选其中一列看看:

 

0:000> !do 0000000002b72640
Name: System.Data.DataColumn
MethodTable: 00000642b77fe2f0
EEClass: 00000642b781e198
Size: 232(0xe8) bytes
(C:\WINDOWS\assembly\GAC_64\System.Data\2.0.0.0__b77a5c561934e089\System.Data.dll)
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
0000064274e54480  400099c        8 ...ponentModel.ISite  0 instance 0000000000000000 site
0000064274e4f1d8  400099d       10 ....EventHandlerList  0 instance 0000000000000000 events
0000064278818fb0  400099b      3d0        System.Object  0   static 0000000000000000 EventDisposed
0000064278821048  400064c       d4       System.Boolean  0 instance                1 allowNull
0000064278821048  400064d       d5       System.Boolean  0 instance                0 autoIncrement
00000642788272d0  400064e       a0         System.Int64  0 instance 1 autoIncrementStep
00000642788272d0  400064f       a8         System.Int64  0 instance 0 autoIncrementSeed
000006427881aaf8  4000650       18        System.String  0 instance 0000000000000000 caption
000006427881aaf8  4000651       20        System.String  0 instance 0000000002b62fd0 _columnName
000006427882a650  4000652       28          System.Type  0 instance 0000000002ab6fe0 dataType
0000064278818fb0  4000653       30        System.Object  0 instance 0000000002ad8ac0 defaultValue
00000642b7839b30  4000654       b8         System.Int32  0 instance                3 _dateTimeMode
00000642b7800ab0  4000655       38 ...ta.DataExpression  0 instance 0000000000000000 expression
0000064278827060  4000656       bc         System.Int32  0 instance               32 maxLength
0000064278827060  4000657       c0         System.Int32  0 instance                3 _ordinal
0000064278821048  4000658       d6       System.Boolean  0 instance                0 readOnly
00000642b77ff4a0  4000659       40    System.Data.Index  0 instance 0000000000000000 sortIndex
00000642b77fcfb0  400065a       48 ...em.Data.DataTable  0 instance 0000000002ab2590 table
0000064278821048  400065b       d7       System.Boolean  0 instance                0 unique
00000642b783b5e0  400065c       c4         System.Int32  0 instance                1 columnMapping
0000064278827060  400065d       c8         System.Int32  0 instance                0 _hashCode
0000064278827060  400065e       cc         System.Int32  0 instance                0 errors
0000064278821048  400065f       d8       System.Boolean  0 instance                0 isSqlType
0000064278821048  4000660       d9       System.Boolean  0 instance                0 implementsINullable
0000064278821048  4000661       da       System.Boolean  0 instance                0 implementsIChangeTracking
0000064278821048  4000662       db       System.Boolean  0 instance                0 implementsIRevertibleChangeTracking
0000064278821048  4000663       dc       System.Boolean  0 instance                0 implementsIXMLSerializable
0000064278821048  4000664       dd       System.Boolean  0 instance                1 defaultValueIsNull
0000000000000000  4000665       50                       0 instance 0000000000000000 dependentColumns
00000642b783bce8  4000666       58 ...ropertyCollection  0 instance 0000000000000000 extendedProperties
0000064274e862f8  4000667       60 ...angedEventHandler  0 instance 0000000000000000 onPropertyChangingDelegate
00000642b77f7070  4000668       68 ...ommon.DataStorage  0 instance 0000000002b735f8 _storage
00000642788272d0  4000669       b0         System.Int64  0 instance 0 autoIncrementCurrent
000006427881aaf8  400066a       70        System.String  0 instance 0000000000000000 _columnUri
000006427881aaf8  400066b       78        System.String  0 instance 0000000002aa4f68 _columnPrefix
000006427881aaf8  400066c       80        System.String  0 instance 0000000000000000 encodedColumnName
000006427881aaf8  400066d       88        System.String  0 instance 0000000002aa4f68 description
000006427881aaf8  400066e       90        System.String  0 instance 0000000002aa4f68 dttype
00000642b77ffaa0  400066f       98 ...m.Data.SimpleType  0 instance 0000000002b72728 simpleType
0000064278827060  4000671       d0         System.Int32  0 instance               35 _objectID
0000064278827060  4000670      4d0         System.Int32  0   static            10254 _objectTypeCount
0:000> !do 0000000002b62fd0
Name: System.String
MethodTable: 000006427881aaf8
EEClass: 000006427892f7d8
Size: 36(0x24) bytes
(C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
String: mapid
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
0000064278827060  4000096        8         System.Int32  0 instance                6 m_arrayLength
0000064278827060  4000097        c         System.Int32  0 instance                5 m_stringLength
00000642788216d8  4000098       10          System.Char  0 instance               6d m_firstChar
000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<

 

看到了,这列叫mapid,有多少行?

 

0:000> !do 0000000002b735f8
Name: System.Data.Common.StringStorage
MethodTable: 00000642b781f218
EEClass: 00000642b788db20
Size: 80(0x50) bytes
(C:\WINDOWS\assembly\GAC_64\System.Data\2.0.0.0__b77a5c561934e089\System.Data.dll)
Fields:
              MT    Field   Offset                 Type VT     Attr            Value Name
00000642b77fe2f0  4000aab        8 ...m.Data.DataColumn  0 instance 0000000002b72640 Column
00000642b77fcfb0  4000aac       10 ...em.Data.DataTable  0 instance 0000000002ab2590 Table
000006427882a650  4000aad       18          System.Type  0 instance 0000000002ab6fe0 DataType
00000642b783f6a8  4000aae       38         System.Int32  0 instance               18 StorageTypeCode
000006427883f8d8  4000aaf       20 ...lections.BitArray  0 instance 0000000000000000 dbNullBits
0000064278818fb0  4000ab0       28        System.Object  0 instance 00000642787c36e0 DefaultValue
0000064278818fb0  4000ab1       30        System.Object  0 instance 0000000002ad8ac0 NullValue
0000064278821048  4000ab2       3c       System.Boolean  0 instance                0 IsCloneable
0000064278821048  4000ab3       3d       System.Boolean  0 instance                0 IsCustomDefinedType
0000064278821048  4000ab4       3e       System.Boolean  0 instance                1 IsStringType
0000064278821048  4000ab5       3f       System.Boolean  0 instance                0 IsValueType
00000642788d4758  4000aaa      330      System.Object[]  0   static 0000000002b64da0 StorageClassType
00000642788d4758  4000c26       40      System.Object[]  0 instance 0000000113ff1000 values
0:000> !do 0000000113ff1000
Name: System.Object[]
MethodTable: 00000642788d4758
EEClass: 00000642789d2f80
Size: 134217760(0x8000020) bytes
Array: Rank 1, Number of elements 16777216, Type CLASS
Element Type: System.String
Fields:
None

 

天哪,1600多万行,64位机器指针8字节,光指针占用134MB,别说里面的字符串了。那么基本可以确定这就是罪魁祸首了。现在问题就是想看看里面的数据,那么随便输出几个:

 

0:000> !dumparray -length 10 -details 0000000113ff1000
Name: System.String[]
MethodTable: 00000642788d4758
EEClass: 00000642789d2f80
Size: 134217760(0x8000020) bytes
Array: Rank 1, Number of elements 16777216, Type CLASS
Element Methodtable: 000006427881aaf8
[0] 0000000002b731c0
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     e51ff7d827024ea1981f7c3a754d6b80   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               65 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[1] 0000000002b73890
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     e5296215c29c4c2e97079b4d33357f1d   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               65 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[2] 0000000002b73978
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     7afb5e8ccefd4b5fb0a251efaec1356a   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               37 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[3] 0000000002b73a58
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     844faa0f6f5e407cae6d9f5dc7cead4f   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               38 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[4] 0000000002b73b38
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     35c966ae4fd445c2b1bae15d6ae4b940   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               33 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[5] 0000000002b73c18
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     cc09aef8fb314933b557758bc7d29f98   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               63 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[6] 0000000002b73cf8
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     dd60b243d07f4cffa8e61cccb668fe9e   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               64 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[7] 0000000002b73de0
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     eab4d9ebf4d54e1e9bc020fc36700745   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               65 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[8] 0000000002b73fc8
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     71117207efb3410298384554834dc389   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               37 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<
[9] 0000000002b740b0
    Name: System.String
    MethodTable: 000006427881aaf8
    EEClass: 000006427892f7d8
    Size: 90(0x5a) bytes
     (C:\WINDOWS\assembly\GAC_64\mscorlib\2.0.0.0__b77a5c561934e089\mscorlib.dll)
    String:     3c54a40a97ab4d4aa5fdaaeeefa903c1   
    Fields:
                  MT    Field   Offset                 Type VT     Attr            Value Name
    0000064278827060  4000096        8         System.Int32  0 instance               33 m_arrayLength
    0000064278827060  4000097        c         System.Int32  0 instance               32 m_stringLength
    00000642788216d8  4000098       10          System.Char  0 instance               33 m_firstChar
    000006427881aaf8  4000099       20        System.String  0   shared           static Empty
                                 >> Domain:Value  0000000000160080:00000642787c36e0 <<
    00000642788db830  400009a       28        System.Char[]  0   shared           static WhitespaceChars
                                 >> Domain:Value  0000000000160080:0000000002aa14e8 <<

 

好像都是一些md5后的字符串,现在的工作就是到代码中找DataTable了,看到:

 

SqlDataReader sqlDataReader = db.GetReader("select * from typetable");
            ddd.Load(sqlDataReader);

 

这个ddd的DataTable很可疑,因为对照数据库中的表看到这个表有8列:

 

image

并且其中也有一个mapid,那么看看mapid的数据:

image

差不多是这个,那么就是它了,但一看数据量:

image

才2万多,怎么内存里有千万数据??

之后通过探查其它列的数据发现这里面数据都是重复的,说明有重复加载,查找所有和ddd相关的代码:

image

只有3个地方往里面加数据,首先怀疑ddd.Rows.Add,但是后来查看发现只有在数据行不存在的情况下才会加,难道是Load方法?第一Load方法是在程序启动的时候一次性加载的,而第二个是在业务逻辑中做的,查看了一下MSDN傻眼了,由于ddd是静态变量,Load方法每一次都会根据主键检查行是否存在,如果不存在的话作为新行,因此ddd就不断重复加2万多行,导致。。。。

做一个实验:

using (SqlConnection conn = new SqlConnection(""))
            {
                conn.Open();
                using (SqlCommand cmd = new SqlCommand("select * from typetable", conn))
                {
                    using (SqlDataReader reader = cmd.ExecuteReader())
                    {
                        typetable.Load(reader);
                    }
                }
            }

            MessageBox.Show(typetable.Rows.Count.ToString());

 

 

第一次运行,程序很愉快的输出了:

image

再按一次按钮:

image 

果然这样,那么尝试把第一列设置为主键试试:

if (typetable.Columns.Count > 0)
{
    typetable.PrimaryKey = new DataColumn[] { typetable.Columns[0] };
}

经过试验,问题得到解决。好了,程序中问题找到了,解决办法也有了,接下去就是修改验证的过程了。

感觉这应该不算内存泄漏的问题,而是作者没有意识到DataTable的Load方法在没指明主键的时候作为新行来处理:

 

Load 方法的此版本尝试保留每行中的当前值,使原始值保持不变。(如果要更精细地控制传入数据的行为,请参见 DataTable.Load 方法。)如果现有的行和传入的行包含对应的主键值,将使用其当前行状态值来处理行,否则将该行视为新行。

posted @ 2010-06-18 13:50  lovecindywang  阅读(8873)  评论(22编辑  收藏  举报