summaryrefslogtreecommitdiff
path: root/src/inc
diff options
context:
space:
mode:
authorJiyoung Yun <jy910.yun@samsung.com>2016-11-23 10:09:09 (GMT)
committerJiyoung Yun <jy910.yun@samsung.com>2016-11-23 10:09:09 (GMT)
commit4b4aad7217d3292650e77eec2cf4c198ea9c3b4b (patch)
tree98110734c91668dfdbb126fcc0e15ddbd93738ca /src/inc
parentfa45f57ed55137c75ac870356a1b8f76c84b229c (diff)
downloadcoreclr-4b4aad7217d3292650e77eec2cf4c198ea9c3b4b.zip
coreclr-4b4aad7217d3292650e77eec2cf4c198ea9c3b4b.tar.gz
coreclr-4b4aad7217d3292650e77eec2cf4c198ea9c3b4b.tar.bz2
Imported Upstream version 1.1.0upstream/1.1.0
Diffstat (limited to 'src/inc')
-rw-r--r--src/inc/.gitmirrorall1
-rw-r--r--src/inc/1031/CORPerfMonSymbols.ini576
-rw-r--r--src/inc/1031/_DataPerfCounters.inibin0 -> 4664 bytes
-rw-r--r--src/inc/1031/_NetworkingPerfCounters.inibin0 -> 5246 bytes
-rw-r--r--src/inc/1031/aspnet_perf.ini415
-rw-r--r--src/inc/1031/aspnet_perf2.ini416
-rw-r--r--src/inc/1041/CORPerfMonSymbols.ini577
-rw-r--r--src/inc/1041/_DataPerfCounters.inibin0 -> 4364 bytes
-rw-r--r--src/inc/1041/_NetworkingPerfCounters.inibin0 -> 4204 bytes
-rw-r--r--src/inc/1041/aspnet_perf.ini414
-rw-r--r--src/inc/1041/aspnet_perf2.ini411
-rw-r--r--src/inc/CMakeLists.txt87
-rw-r--r--src/inc/CrstTypeTool.cs990
-rw-r--r--src/inc/CrstTypes.def781
-rw-r--r--src/inc/MSCOREE.IDL2438
-rw-r--r--src/inc/OpCodeGen.pl501
-rw-r--r--src/inc/UacAsInvoker.manifest11
-rw-r--r--src/inc/allocacheck.h84
-rw-r--r--src/inc/apithreadstress.cpp171
-rw-r--r--src/inc/apithreadstress.h90
-rw-r--r--src/inc/appxutil.h145
-rw-r--r--src/inc/arraylist.h305
-rw-r--r--src/inc/assemblyfilehash.h92
-rw-r--r--src/inc/assemblyusagelog.idl51
-rw-r--r--src/inc/assemblyusagelogmanager.h53
-rw-r--r--src/inc/bbsweep.h425
-rw-r--r--src/inc/binderngen.idl255
-rw-r--r--src/inc/bitmask.h103
-rw-r--r--src/inc/bitmask.inl292
-rw-r--r--src/inc/bitposition.h55
-rw-r--r--src/inc/bitvector.h462
-rw-r--r--src/inc/blobfetcher.h174
-rw-r--r--src/inc/cahlpr.h41
-rw-r--r--src/inc/caparser.h377
-rw-r--r--src/inc/ceefilegenwriter.h245
-rw-r--r--src/inc/ceegen.h440
-rw-r--r--src/inc/ceegentokenmapper.h142
-rw-r--r--src/inc/ceesectionstring.h55
-rw-r--r--src/inc/cfi.h33
-rw-r--r--src/inc/check.h734
-rw-r--r--src/inc/check.inl367
-rw-r--r--src/inc/circularlog.h38
-rw-r--r--src/inc/clr/fs.h16
-rw-r--r--src/inc/clr/fs/dir.h129
-rw-r--r--src/inc/clr/fs/file.h40
-rw-r--r--src/inc/clr/fs/path.h141
-rw-r--r--src/inc/clr/stack.h99
-rw-r--r--src/inc/clr/str.h28
-rw-r--r--src/inc/clr/win32.h38
-rw-r--r--src/inc/clr_std/algorithm119
-rw-r--r--src/inc/clr_std/string414
-rw-r--r--src/inc/clr_std/type_traits549
-rw-r--r--src/inc/clr_std/utility254
-rw-r--r--src/inc/clr_std/vector431
-rw-r--r--src/inc/clrconfig.h259
-rw-r--r--src/inc/clrconfigvalues.h1186
-rw-r--r--src/inc/clrdata.idl313
-rw-r--r--src/inc/clrhost.h625
-rw-r--r--src/inc/clrinternal.idl491
-rw-r--r--src/inc/clrnt.h998
-rw-r--r--src/inc/clrprivappxhosting.idl66
-rw-r--r--src/inc/clrprivbinderutil.h872
-rw-r--r--src/inc/clrprivbinding.idl324
-rw-r--r--src/inc/clrprivhosting.idl92
-rw-r--r--src/inc/clrprivruntimebinders.idl39
-rw-r--r--src/inc/clrtypes.h422
-rw-r--r--src/inc/compatibilityflags.h17
-rw-r--r--src/inc/compatibilityflagsdef.h48
-rw-r--r--src/inc/complex.h80
-rw-r--r--src/inc/configuration.h57
-rw-r--r--src/inc/contract.h2598
-rw-r--r--src/inc/contract.inl748
-rw-r--r--src/inc/contxt.h3472
-rw-r--r--src/inc/cor.h2523
-rw-r--r--src/inc/corbbtprof.h589
-rw-r--r--src/inc/corcompile.h1939
-rw-r--r--src/inc/cordbpriv.h68
-rw-r--r--src/inc/cordebug.idl7292
-rw-r--r--src/inc/cordebug_mktlb.rc11
-rw-r--r--src/inc/cordebuginfo.h323
-rw-r--r--src/inc/coredistools.h142
-rw-r--r--src/inc/coregen.h22
-rw-r--r--src/inc/corerror.xml6993
-rw-r--r--src/inc/corexcep.h42
-rw-r--r--src/inc/corguids.nativeproj438
-rw-r--r--src/inc/corguids.targets53
-rw-r--r--src/inc/corhdr.h1930
-rw-r--r--src/inc/corhlpr.cpp307
-rw-r--r--src/inc/corhlpr.h694
-rw-r--r--src/inc/corhlprpriv.cpp313
-rw-r--r--src/inc/corhlprpriv.h773
-rw-r--r--src/inc/corhost.h1188
-rw-r--r--src/inc/corimage.h67
-rw-r--r--src/inc/corinfo.h3139
-rw-r--r--src/inc/corjit.h575
-rw-r--r--src/inc/corjithost.h48
-rw-r--r--src/inc/corperm.h205
-rw-r--r--src/inc/corperme.h56
-rw-r--r--src/inc/corpermp.h57
-rw-r--r--src/inc/corpolicy.h129
-rw-r--r--src/inc/corpriv.h731
-rw-r--r--src/inc/corprof.idl3857
-rw-r--r--src/inc/corpub.idl265
-rw-r--r--src/inc/corsym.idl1785
-rw-r--r--src/inc/cortpoolhdr.h50
-rw-r--r--src/inc/cortypeinfo.h49
-rw-r--r--src/inc/crosscomp.h363
-rw-r--r--src/inc/crsttypes.h559
-rw-r--r--src/inc/crtwrap.h30
-rw-r--r--src/inc/cvconst.h3728
-rw-r--r--src/inc/cvinfo.h4989
-rw-r--r--src/inc/cycletimer.h56
-rw-r--r--src/inc/daccess.h2463
-rw-r--r--src/inc/dacprivate.h1010
-rw-r--r--src/inc/dacvars.h339
-rw-r--r--src/inc/dbgconfigstrings.h23
-rw-r--r--src/inc/dbgenginemetrics.h30
-rw-r--r--src/inc/dbgmeta.h38
-rw-r--r--src/inc/dbgportable.h141
-rw-r--r--src/inc/debugmacros.h270
-rw-r--r--src/inc/debugmacrosext.h46
-rw-r--r--src/inc/debugreturn.h127
-rw-r--r--src/inc/declsec.h255
-rw-r--r--src/inc/defaultallocator.h49
-rw-r--r--src/inc/delayloadhelpers.h113
-rw-r--r--src/inc/dlwrap.h205
-rw-r--r--src/inc/downlevel.h239
-rw-r--r--src/inc/eetwain.h725
-rw-r--r--src/inc/eexcp.h156
-rw-r--r--src/inc/entrypoints.h60
-rw-r--r--src/inc/eventtrace.h346
-rw-r--r--src/inc/eventtracebase.h1082
-rw-r--r--src/inc/ex.h1519
-rw-r--r--src/inc/expandarray.h210
-rw-r--r--src/inc/factory.h49
-rw-r--r--src/inc/factory.inl32
-rw-r--r--src/inc/fixedsizestring.h188
-rw-r--r--src/inc/fixuppointer.h597
-rw-r--r--src/inc/formattype.cpp1574
-rw-r--r--src/inc/formattype.h181
-rw-r--r--src/inc/fstream.h50
-rw-r--r--src/inc/fstring.h42
-rw-r--r--src/inc/fusion.idl530
-rw-r--r--src/inc/fusionbind.h316
-rw-r--r--src/inc/fusionpriv.idl970
-rw-r--r--src/inc/fusionsetup.h63
-rw-r--r--src/inc/fusionsink.h129
-rw-r--r--src/inc/fxretarget.h340
-rw-r--r--src/inc/gcdecoder.cpp589
-rw-r--r--src/inc/gcdump.h102
-rw-r--r--src/inc/gchost.idl144
-rw-r--r--src/inc/gcinfo.h82
-rw-r--r--src/inc/gcinfoarraylist.h114
-rw-r--r--src/inc/gcinfodecoder.h661
-rw-r--r--src/inc/gcinfodumper.h117
-rw-r--r--src/inc/gcinfoencoder.h552
-rw-r--r--src/inc/gcinfotypes.h832
-rw-r--r--src/inc/gcrefmap.h247
-rw-r--r--src/inc/genericstackprobe.h610
-rw-r--r--src/inc/genericstackprobe.inl15
-rw-r--r--src/inc/genheaders.cs222
-rw-r--r--src/inc/genrops.pl91
-rw-r--r--src/inc/getproductversionnumber.h77
-rw-r--r--src/inc/guidfromname.h19
-rw-r--r--src/inc/holder.h1515
-rw-r--r--src/inc/holderinst.h33
-rw-r--r--src/inc/iallocator.h77
-rw-r--r--src/inc/iappdomainsetup.h612
-rw-r--r--src/inc/iceefilegen.h245
-rw-r--r--src/inc/iilfingerprint.h128
-rw-r--r--src/inc/il_kywd.h303
-rw-r--r--src/inc/ildbsymlib.h21
-rw-r--r--src/inc/ilformatter.h76
-rw-r--r--src/inc/internalunknownimpl.h494
-rw-r--r--src/inc/intrinsic.h25
-rw-r--r--src/inc/ipcfunccall.h117
-rw-r--r--src/inc/ipcmanagerinterface.h204
-rw-r--r--src/inc/isolation.h2577
-rw-r--r--src/inc/isolationpriv.h18263
-rw-r--r--src/inc/iterator.h639
-rw-r--r--src/inc/ivalidator.idl116
-rw-r--r--src/inc/ivehandler.idl72
-rw-r--r--src/inc/jithelpers.h396
-rw-r--r--src/inc/jithost.h28
-rw-r--r--src/inc/jitperf.h97
-rw-r--r--src/inc/lazycow.h99
-rw-r--r--src/inc/legacyactivationshim.h1382
-rw-r--r--src/inc/legacyactivationshimdelayload.h13
-rw-r--r--src/inc/legacyactivationshimutil.h1116
-rw-r--r--src/inc/livedatatarget.h105
-rw-r--r--src/inc/llvm/Dwarf.def393
-rw-r--r--src/inc/llvm/Dwarf.h711
-rw-r--r--src/inc/llvm/ELF.h1273
-rw-r--r--src/inc/loaderheap.h1085
-rw-r--r--src/inc/log.h99
-rw-r--r--src/inc/loglf.h42
-rw-r--r--src/inc/longfilepathwrappers.h271
-rw-r--r--src/inc/marvin32.h85
-rw-r--r--src/inc/md5.h134
-rw-r--r--src/inc/mdcommon.h54
-rw-r--r--src/inc/memorypool.h143
-rw-r--r--src/inc/memoryrange.h98
-rw-r--r--src/inc/metadata.h1557
-rw-r--r--src/inc/metadataexports.h57
-rw-r--r--src/inc/metadatatracker.h367
-rw-r--r--src/inc/metahost.idl1097
-rw-r--r--src/inc/metahost_mktlb.rc11
-rw-r--r--src/inc/metahostpriv.idl212
-rw-r--r--src/inc/metamodelpub.h1672
-rw-r--r--src/inc/mpl/type_list76
-rw-r--r--src/inc/mscorcfg.h34
-rw-r--r--src/inc/mscoree_mktlb.rc12
-rw-r--r--src/inc/mscoree_tlb.idl15
-rw-r--r--src/inc/mscoreepriv.h21
-rw-r--r--src/inc/mscorpesxswrapper.h125
-rw-r--r--src/inc/mscorsvc.idl683
-rw-r--r--src/inc/mscoruef.idl117
-rw-r--r--src/inc/msodw.h585
-rw-r--r--src/inc/msodwwrap.h11
-rw-r--r--src/inc/nativevaraccessors.h48
-rw-r--r--src/inc/new.hpp27
-rw-r--r--src/inc/newapis.h352
-rw-r--r--src/inc/ngen.h153
-rw-r--r--src/inc/ngenparser.inl1087
-rw-r--r--src/inc/nibblemapmacros.h56
-rw-r--r--src/inc/nibblestream.h300
-rw-r--r--src/inc/nsutilpriv.h266
-rw-r--r--src/inc/obj/i386/dummy1
-rw-r--r--src/inc/opcode.def359
-rw-r--r--src/inc/openum.h51
-rw-r--r--src/inc/opinfo.h83
-rw-r--r--src/inc/optdefault.h12
-rw-r--r--src/inc/optsmallperfcritical.h21
-rw-r--r--src/inc/ostype.h176
-rw-r--r--src/inc/outstring.h157
-rw-r--r--src/inc/palclr.h624
-rw-r--r--src/inc/palclr_win.h206
-rw-r--r--src/inc/pedecoder.h478
-rw-r--r--src/inc/pedecoder.inl1429
-rw-r--r--src/inc/peinformation.h75
-rw-r--r--src/inc/perfcounterdefs.h495
-rw-r--r--src/inc/perfcounterdefs.inl89
-rw-r--r--src/inc/perfcounters.h124
-rw-r--r--src/inc/perflog.h142
-rw-r--r--src/inc/pesectionman.h213
-rw-r--r--src/inc/posterror.h50
-rw-r--r--src/inc/predeftlsslot.h84
-rw-r--r--src/inc/prettyprintsig.h91
-rw-r--r--src/inc/profilepriv.h156
-rw-r--r--src/inc/profilepriv.inl826
-rw-r--r--src/inc/quirksapi.h37
-rw-r--r--src/inc/random.h279
-rw-r--r--src/inc/rangetree.h141
-rw-r--r--src/inc/readytorun.h333
-rw-r--r--src/inc/readytorunhelpers.h113
-rw-r--r--src/inc/regdisp.h584
-rw-r--r--src/inc/regex_base.h973
-rw-r--r--src/inc/regex_util.h209
-rw-r--r--src/inc/registrywrapper.h48
-rw-r--r--src/inc/safemath.h872
-rw-r--r--src/inc/safewrap.h171
-rw-r--r--src/inc/sarray.h229
-rw-r--r--src/inc/sarray.inl377
-rw-r--r--src/inc/sbuffer.h575
-rw-r--r--src/inc/sbuffer.inl1711
-rw-r--r--src/inc/securityutil.h53
-rw-r--r--src/inc/securitywrapper.h111
-rw-r--r--src/inc/shash.h1105
-rw-r--r--src/inc/shash.inl935
-rw-r--r--src/inc/shim/locationinfo.h42
-rw-r--r--src/inc/shim/runtimeselector.h55
-rw-r--r--src/inc/shim/runtimeselector.inl105
-rw-r--r--src/inc/shim/shimselector.h55
-rw-r--r--src/inc/shim/shimselector.inl104
-rw-r--r--src/inc/shim/versionandlocationinfo.h36
-rw-r--r--src/inc/shim/versionandlocationinfo.inl35
-rw-r--r--src/inc/shim/versioninfo.h46
-rw-r--r--src/inc/shim/versioninfo.inl170
-rw-r--r--src/inc/shimload.h38
-rw-r--r--src/inc/sigbuilder.h79
-rw-r--r--src/inc/sigparser.h985
-rw-r--r--src/inc/simplerhash.h423
-rw-r--r--src/inc/simplerhash.inl350
-rw-r--r--src/inc/slist.h387
-rw-r--r--src/inc/sortversioning.h207
-rw-r--r--src/inc/sospriv.idl359
-rw-r--r--src/inc/sstring.h1084
-rw-r--r--src/inc/sstring.inl2279
-rw-r--r--src/inc/stack.h87
-rw-r--r--src/inc/stackframe.h130
-rw-r--r--src/inc/stacktrace.h91
-rw-r--r--src/inc/static_assert.h28
-rw-r--r--src/inc/staticcontract.h408
-rw-r--r--src/inc/stdmacros.h356
-rw-r--r--src/inc/stgpool.h1515
-rw-r--r--src/inc/stgpooli.h256
-rw-r--r--src/inc/stresslog.h841
-rw-r--r--src/inc/stringarraylist.h31
-rw-r--r--src/inc/stringarraylist.inl76
-rw-r--r--src/inc/strongname.h9
-rw-r--r--src/inc/switches.h268
-rw-r--r--src/inc/sxshelpers.h141
-rw-r--r--src/inc/sxshelpers.inl76
-rw-r--r--src/inc/testhook.h159
-rw-r--r--src/inc/tlbimpexp.idl72
-rw-r--r--src/inc/tlbutils.h52
-rw-r--r--src/inc/tls.h78
-rw-r--r--src/inc/unsafe.h102
-rw-r--r--src/inc/utilcode.h5753
-rw-r--r--src/inc/utsem.h63
-rw-r--r--src/inc/vererror.h137
-rw-r--r--src/inc/volatile.h514
-rw-r--r--src/inc/vptr_list.h156
-rw-r--r--src/inc/warningcontrol.h86
-rw-r--r--src/inc/win64unwind.h117
-rw-r--r--src/inc/winrt/ntassert.h210
-rw-r--r--src/inc/winrt/paraminstanceapi.h1749
-rw-r--r--src/inc/winrt/windowsruntime.h65
-rw-r--r--src/inc/winrt/windowsstring.h774
-rw-r--r--src/inc/winrtprojectedtypes.h271
-rw-r--r--src/inc/winsqmevents.h84
-rw-r--r--src/inc/winwrap.h1038
-rw-r--r--src/inc/xclrdata.idl2538
-rw-r--r--src/inc/xcordebug.idl85
-rw-r--r--src/inc/xmlparser.h1385
-rw-r--r--src/inc/xmlparser_i.c86
-rw-r--r--src/inc/zapper.h581
327 files changed, 177358 insertions, 0 deletions
diff --git a/src/inc/.gitmirrorall b/src/inc/.gitmirrorall
new file mode 100644
index 0000000..9ee5c57
--- /dev/null
+++ b/src/inc/.gitmirrorall
@@ -0,0 +1 @@
+This folder will be mirrored by the Git-TFS Mirror recursively. \ No newline at end of file
diff --git a/src/inc/1031/CORPerfMonSymbols.ini b/src/inc/1031/CORPerfMonSymbols.ini
new file mode 100644
index 0000000..3c656ef
--- /dev/null
+++ b/src/inc/1031/CORPerfMonSymbols.ini
@@ -0,0 +1,576 @@
+; Licensed to the .NET Foundation under one or more agreements.
+; The .NET Foundation licenses this file to you under the MIT license.
+; See the LICENSE file in the project root for more information.
+
+//------------------------------------------------------------------------
+// WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
+//
+// AUTO GENERATED FILE. DO NOT EDIT. USE $/com99/src/profile/perfmonhelp
+//
+// WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
+//------------------------------------------------------------------------
+
+// CORPerfMonSymbols.ini file
+[info]
+drivername=.NETFramework
+symbolfile=CORPerfMonSymbols.h
+
+[languages]
+009=English
+; 001=Arabic
+; 004=Chinese
+ 007=German
+; 00D=Hebrew
+; 011=Japanese
+; 012=Korean
+; 00A=Spanish
+; 00C=French
+; 010=Italian
+
+[objects]
+DotNetCLR_Memory_OBJECT_009_NAME=.NET CLR Memory
+DotNetCLR_Loading_OBJECT_009_NAME=.NET CLR Loading
+DotNetCLR_Jit_OBJECT_009_NAME=.NET CLR Jit
+DotNetCLR_Interop_OBJECT_009_NAME=.NET CLR Interop
+DotNetCLR_LocksAndThreads_OBJECT_009_NAME=.NET CLR LocksAndThreads
+DotNetCLR_Security_OBJECT_009_NAME=.NET CLR Security
+DotNetCLR_Remoting_OBJECT_009_NAME=.NET CLR Remoting
+DotNetCLR_Excep_OBJECT_009_NAME=.NET CLR Exceptions
+DotNetCLR_Memory_OBJECT_007_NAME=.NET CLR-Speicher
+DotNetCLR_Loading_OBJECT_007_NAME=.NET CLR-Ladevorgang
+DotNetCLR_Jit_OBJECT_007_NAME=.NET CLR-Jit
+DotNetCLR_Interop_OBJECT_007_NAME=.NET CLR-Interop
+DotNetCLR_LocksAndThreads_OBJECT_007_NAME=.NET CLR-Sperren und Threads
+DotNetCLR_Security_OBJECT_007_NAME=.NET CLR-Sicherheit
+DotNetCLR_Remoting_OBJECT_007_NAME=.NET CLR-Remote
+DotNetCLR_Excep_OBJECT_007_NAME=.NET CLR-Ausnahmen
+
+[text]
+DotNetCLR_Memory_OBJECT_009_NAME=.NET CLR Memory
+DotNetCLR_Memory_OBJECT_009_HELP=Counters for CLR Garbage Collected heap.
+
+GEN0_COLLECTIONS_COUNTER_009_NAME=# Gen 0 Collections
+GEN0_COLLECTIONS_COUNTER_009_HELP=This counter displays the number of times the generation 0 objects (youngest; most recently allocated) are garbage collected (Gen 0 GC) since the start of the application. Gen 0 GC occurs when the available memory in generation 0 is not sufficient to satisfy an allocation request. This counter is incremented at the end of a Gen 0 GC. Higher generation GCs include all lower generation GCs. This counter is explicitly incremented when a higher generation (Gen 1 or Gen 2) GC occurs. _Global_ counter value is not accurate and should be ignored. This counter displays the last observed value.
+
+GEN1_COLLECTIONS_COUNTER_009_NAME=# Gen 1 Collections
+GEN1_COLLECTIONS_COUNTER_009_HELP=This counter displays the number of times the generation 1 objects are garbage collected since the start of the application. The counter is incremented at the end of a Gen 1 GC. Higher generation GCs include all lower generation GCs. This counter is explicitly incremented when a higher generation (Gen 2) GC occurs. _Global_ counter value is not accurate and should be ignored. This counter displays the last observed value.
+
+GEN2_COLLECTIONS_COUNTER_009_NAME=# Gen 2 Collections
+GEN2_COLLECTIONS_COUNTER_009_HELP=This counter displays the number of times the generation 2 objects (older) are garbage collected since the start of the application. The counter is incremented at the end of a Gen 2 GC (also called full GC). _Global_ counter value is not accurate and should be ignored. This counter displays the last observed value.
+
+GEN0_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Memory from Gen 0
+GEN0_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that survive garbage collection (GC) and are promoted from generation 0 to generation 1; objects that are promoted just because they are waiting to be finalized are not included in this counter. This counter displays the value observed at the end of the last GC; its not a cumulative counter.
+
+GEN1_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Memory from Gen 1
+GEN1_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that survive garbage collection (GC) and are promoted from generation 1 to generation 2; objects that are promoted just because they are waiting to be finalized are not included in this counter. This counter displays the value observed at the end of the last GC; its not a cumulative counter. This counter is reset to 0 if the last GC was a Gen 0 GC only.
+
+GEN0_PROMOTION_RATE_009_NAME=Gen 0 Promoted Bytes/Sec
+GEN0_PROMOTION_RATE_009_HELP=This counter displays the bytes per second that are promoted from generation 0 (youngest) to generation 1; objects that are promoted just because they are waiting to be finalized are not included in this counter. Memory is promoted when it survives a garbage collection. This counter was designed as an indicator of relatively long-lived objects being created per sec. This counter displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+GEN1_PROMOTION_RATE_009_NAME=Gen 1 Promoted Bytes/Sec
+GEN1_PROMOTION_RATE_009_HELP=This counter displays the bytes per second that are promoted from generation 1 to generation 2 (oldest); objects that are promoted just because they are waiting to be finalized are not included in this counter. Memory is promoted when it survives a garbage collection. Nothing is promoted from generation 2 since it is the oldest. This counter was designed as an indicator of very long-lived objects being created per sec. This counter displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Finalization-Memory from Gen 0
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that are promoted from generation 0 to generation 1 just because they are waiting to be finalized. This counter displays the value observed at the end of the last GC; its not a cumulative counter.
+
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Finalization-Memory from Gen 1
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that are promoted from generation 1 to generation 2 just because they are waiting to be finalized. This counter displays the value observed at the end of the last GC; its not a cumulative counter. This counter is reset to 0 if the last GC was a Gen 0 GC only.
+
+GEN0_HEAP_SIZE_COUNTER_009_NAME=Gen 0 heap size
+GEN0_HEAP_SIZE_COUNTER_009_HELP=This counter displays the maximum bytes that can be allocated in generation 0 (Gen 0); its does not indicate the current number of bytes allocated in Gen 0. A Gen 0 GC is triggered when the allocations since the last GC exceed this size. The Gen 0 size is tuned by the Garbage Collector and can change during the execution of the application. At the end of a Gen 0 collection the size of the Gen 0 heap is infact 0 bytes; this counter displays the size (in bytes) of allocations that would trigger the next Gen 0 GC. This counter is updated at the end of a GC; its not updated on every allocation.
+
+GEN1_HEAP_SIZE_COUNTER_009_NAME=Gen 1 heap size
+GEN1_HEAP_SIZE_COUNTER_009_HELP=This counter displays the current number of bytes in generation 1 (Gen 1); this counter does not display the maximum size of Gen 1. Objects are not directly allocated in this generation; they are promoted from previous Gen 0 GCs. This counter is updated at the end of a GC; its not updated on every allocation.
+
+GEN2_HEAP_SIZE_COUNTER_009_NAME=Gen 2 heap size
+GEN2_HEAP_SIZE_COUNTER_009_HELP=This counter displays the current number of bytes in generation 2 (Gen 2). Objects are not directly allocated in this generation; they are promoted from Gen 1 during previous Gen 1 GCs. This counter is updated at the end of a GC; its not updated on every allocation.
+
+LARGE_OBJECT_SIZE_COUNTER_009_NAME=Large Object Heap size
+LARGE_OBJECT_SIZE_COUNTER_009_HELP=This counter displays the current size of the Large Object Heap in bytes. Objects greater than 20 KBytes are treated as large objects by the Garbage Collector and are directly allocated in a special heap; they are not promoted through the generations. This counter is updated at the end of a GC; its not updated on every allocation.
+
+SURVIVE_FINALIZE_COUNTER_009_NAME=Finalization Survivors
+SURVIVE_FINALIZE_COUNTER_009_HELP=This counter displays the number of garbage collected objects that survive a collection because they are waiting to be finalized. If these objects hold references to other objects then those objects also survive but are not counted by this counter; the "Promoted Finalization-Memory from Gen 0" and "Promoted Finalization-Memory from Gen 1" counters represent all the memory that survived due to finalization. This counter is not a cumulative counter; its updated at the end of every GC with count of the survivors during that particular GC only. This counter was designed to indicate the extra overhead that the application might incur because of finalization.
+
+NUM_HANDLES_COUNTER_009_NAME=# GC Handles
+NUM_HANDLES_COUNTER_009_HELP=This counter displays the current number of GC Handles in use. GCHandles are handles to resources external to the CLR and the managed environment. Handles occupy small amounts of memory in the GCHeap but potentially expensive unmanaged resources.
+
+ALLOCATION_RATE_COUNTER_009_NAME=Allocated Bytes/sec
+ALLOCATION_RATE_COUNTER_009_HELP=This counter displays the rate of bytes per second allocated on the GC Heap. This counter is updated at the end of every GC; not at each allocation. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+INDUCED_GC_COUNTER_009_NAME=# Induced GC
+INDUCED_GC_COUNTER_009_HELP=This counter displays the peak number of times a garbage collection was performed because of an explicit call to GC.Collect. Its a good practice to let the GC tune the frequency of its collections.
+
+PER_TIME_IN_GC_COUNTER_009_NAME=% Time in GC
+PER_TIME_IN_GC_COUNTER_009_HELP=% Time in GC is the percentage of elapsed time that was spent in performing a garbage collection (GC) since the last GC cycle. This counter is usually an indicator of the work done by the Garbage Collector on behalf of the application to collect and compact memory. This counter is updated only at the end of every GC and the counter value reflects the last observed value; its not an average.
+
+PER_TIME_IN_GC_COUNTER_BASE_009_NAME=Not Displayed
+PER_TIME_IN_GC_COUNTER_BASE_009_HELP=Not Displayed.
+
+TOTAL_HEAP_SIZE_COUNTER_009_NAME=# Bytes in all Heaps
+TOTAL_HEAP_SIZE_COUNTER_009_HELP=This counter is the sum of four other counters; Gen 0 Heap Size; Gen 1 Heap Size; Gen 2 Heap Size and the Large Object Heap Size. This counter indicates the current memory allocated in bytes on the GC Heaps.
+
+TOTAL_COMMITTED_MEM_COUNTER_009_NAME=# Total committed Bytes
+TOTAL_COMMITTED_MEM_COUNTER_009_HELP=This counter displays the amount of virtual memory (in bytes) currently committed by the Garbage Collector. (Committed memory is the physical memory for which space has been reserved on the disk paging file).
+
+TOTAL_RESERVED_MEM_COUNTER_009_NAME=# Total reserved Bytes
+TOTAL_RESERVED_MEM_COUNTER_009_HELP=This counter displays the amount of virtual memory (in bytes) currently reserved by the Garbage Collector. (Reserved memory is the virtual memory space reserved for the application but no disk or main memory pages have been used.)
+
+GC_PINNED_OBJECTS_009_NAME=# of Pinned Objects
+GC_PINNED_OBJECTS_009_HELP=This counter displays the number of pinned objects encountered in the last GC. This counter tracks the pinned objects only in the heaps that were garbage collected e.g. a Gen 0 GC would cause enumeration of pinned objects in the generation 0 heap only. A pinned object is one that the Garbage Collector cannot move in memory.
+
+GC_SINKBLOCKS_009_NAME=# of Sink Blocks in use
+GC_SINKBLOCKS_009_HELP=This counter displays the current number of sync blocks in use. Sync blocks are per-object data structures allocated for storing synchronization information. Sync blocks hold weak references to managed objects and need to be scanned by the Garbage Collector. Sync blocks are not limited to storing synchronization information and can also store COM interop metadata. This counter was designed to indicate performance problems with heavy use of synchronization primitives.
+
+DotNetCLR_Loading_OBJECT_009_NAME=.NET CLR Loading
+DotNetCLR_Loading_OBJECT_009_HELP=Statistics for CLR Class Loader.
+
+LOADING_CLASSES_TOTAL_009_NAME=Total Classes Loaded
+LOADING_CLASSES_TOTAL_009_HELP=This counter displays the cumulative number of classes loaded in all Assemblies since the start of this application.
+
+LOADING_TIME_009_NAME=% Time Loading
+LOADING_TIME_009_HELP=Reserved for future use.
+
+LOADING_ASMSEARCHLEN_009_NAME=Assembly Search Length
+LOADING_ASMSEARCHLEN_009_HELP=Reserved for future use.
+
+LOADING_LOADFAILURES_TOTAL_009_NAME=Total # of Load Failures
+LOADING_LOADFAILURES_TOTAL_009_HELP=This counter displays the peak number of classes that have failed to load since the start of the application. These load failures could be due to many reasons like inadequate security or illegal format. Full details can be found in the profiling services help.
+
+LOADING_LOADFAILURES_INST_009_NAME=Rate of Load Failures
+LOADING_LOADFAILURES_INST_009_HELP=This counter displays the number of classes that failed to load per second. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval. These load failures could be due to many reasons like inadequate security or illegal format. Full details can be found in the profiling services help.
+
+LOADING_HEAPSIZE_009_NAME=Bytes in Loader Heap
+LOADING_HEAPSIZE_009_HELP=This counter displays the current size (in bytes) of the memory committed by the class loader across all AppDomains. (Committed memory is the physical memory for which space has been reserved on the disk paging file.)
+
+LOADING_APPDOMAINS_UNLOADED_TOTAL_009_NAME=Total appdomains unloaded
+LOADING_APPDOMAINS_UNLOADED_TOTAL_009_HELP=This counter displays the total number of AppDomains unloaded since the start of the application. If an AppDomain is loaded and unloaded multiple times this counter would count each of those unloads as separate.
+
+LOADING_APPDOMAINS_UNLOADED_INST_009_NAME=Rate of appdomains unloaded
+LOADING_APPDOMAINS_UNLOADED_INST_009_HELP=This counter displays the number of AppDomains unloaded per second. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+LOADING_CLASSES_CUR_009_NAME=Current Classes Loaded
+LOADING_CLASSES_CUR_009_HELP=This counter displays the current number of classes loaded in all Assemblies.
+
+LOADING_CLASSES_INST_009_NAME=Rate of Classes Loaded
+LOADING_CLASSES_INST_009_HELP=This counter displays the number of classes loaded per second in all Assemblies. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+LOADING_APPDOMAINS_CUR_009_NAME=Current appdomains
+LOADING_APPDOMAINS_CUR_009_HELP=This counter displays the current number of AppDomains loaded in this application. AppDomains (application domains) provide a secure and versatile unit of processing that the CLR can use to provide isolation between applications running in the same process.
+
+LOADING_APPDOMAINS_TOTAL_009_NAME=Total Appdomains
+LOADING_APPDOMAINS_TOTAL_009_HELP=This counter displays the peak number of AppDomains loaded since the start of this application. AppDomains (application domains) provide a secure and versatile unit of processing that the CLR can use to provide isolation between applications running in the same process.
+
+LOADING_APPDOMAINS_INST_009_NAME=Rate of appdomains
+LOADING_APPDOMAINS_INST_009_HELP=This counter displays the number of AppDomains loaded per second. AppDomains (application domains) provide a secure and versatile unit of processing that the CLR can use to provide isolation between applications running in the same process. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+LOADING_ASSEMBLIES_CUR_009_NAME=Current Assemblies
+LOADING_ASSEMBLIES_CUR_009_HELP=This counter displays the current number of Assemblies loaded across all AppDomains in this application. If the Assembly is loaded as domain-neutral from multiple AppDomains then this counter is incremented once only. Assemblies can be loaded as domain-neutral when their code can be shared by all AppDomains or they can be loaded as domain-specific when their code is private to the AppDomain.
+
+LOADING_ASSEMBLIES_TOTAL_009_NAME=Total Assemblies
+LOADING_ASSEMBLIES_TOTAL_009_HELP=This counter displays the total number of Assemblies loaded since the start of this application. If the Assembly is loaded as domain-neutral from multiple AppDomains then this counter is incremented once only. Assemblies can be loaded as domain-neutral when their code can be shared by all AppDomains or they can be loaded as domain-specific when their code is private to the AppDomain.
+
+LOADING_ASSEMBLIES_INST_009_NAME=Rate of Assemblies
+LOADING_ASSEMBLIES_INST_009_HELP=This counter displays the number of Assemblies loaded across all AppDomains per second. If the Assembly is loaded as domain-neutral from multiple AppDomains then this counter is incremented once only. Assemblies can be loaded as domain-neutral when their code can be shared by all AppDomains or they can be loaded as domain-specific when their code is private to the AppDomain. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+DotNetCLR_Jit_OBJECT_009_NAME=.NET CLR Jit
+DotNetCLR_Jit_OBJECT_009_HELP=Stats for CLR Jit.
+
+TOTAL_METHODS_JITTED_009_NAME=# of Methods Jitted
+TOTAL_METHODS_JITTED_009_HELP=This counter displays the total number of methods compiled Just-In-Time (JIT) by the CLR JIT compiler since the start of the application. This counter does not include the pre-jitted methods.
+
+JITTED_IL_CUR_009_NAME=# of IL Bytes Jitted
+JITTED_IL_CUR_009_HELP=This counter displays the total IL bytes jitted since the start of the application. This counter is exactly equivalent to the "Total # of IL Bytes Jitted" counter.
+
+JITTED_IL_TOTAL_009_NAME=Total # of IL Bytes Jitted
+JITTED_IL_TOTAL_009_HELP=This counter displays the total IL bytes jitted since the start of the application. This counter is exactly equivalent to the "# of IL Bytes Jitted" counter.
+
+JITTED_IL_INST_009_NAME=IL Bytes Jitted / sec
+JITTED_IL_INST_009_HELP=This counter displays the rate at which IL bytes are jitted per second. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+JIT_FAILURES_009_NAME=Standard Jit Failures
+JIT_FAILURES_009_HELP=This counter displays the peak number of methods the JIT compiler has failed to JIT since the start of the application. This failure can occur if the IL cannot be verified or if there was an internal error in the JIT compiler.
+
+TIME_IN_JIT_009_NAME=% Time in Jit
+TIME_IN_JIT_009_HELP=This counter displays the percentage of elapsed time spent in JIT compilation since the last JIT compilation phase. This counter is updated at the end of every JIT compilation phase. A JIT compilation phase is the phase when a method and its dependencies are being compiled.
+
+TIME_IN_JIT_BASE_009_NAME=Not Displayed
+TIME_IN_JIT_BASE_009_HELP=Not Displayed.
+
+DotNetCLR_Interop_OBJECT_009_NAME=.NET CLR Interop
+DotNetCLR_Interop_OBJECT_009_HELP=Stats for CLR interop.
+
+CURRENT_CCW_009_NAME=# of CCWs
+CURRENT_CCW_009_HELP=This counter displays the current number of Com-Callable-Wrappers (CCWs). A CCW is a proxy for the .NET managed object being referenced from unmanaged COM client(s). This counter was designed to indicate the number of managed objects being referenced by unmanaged COM code.
+
+CURRENT_STUBS_009_NAME=# of Stubs
+CURRENT_STUBS_009_HELP=This counter displays the current number of stubs created by the CLR. Stubs are responsible for marshalling arguments and return values from managed to unmanaged code and vice versa; during a COM Interop call or PInvoke call.
+
+NUM_MARSHALLING_009_NAME=# of marshalling
+NUM_MARSHALLING_009_HELP=This counter displays the total number of times arguments and return values have been marshaled from managed to unmanaged code and vice versa since the start of the application. This counter is not incremented if the stubs are inlined. (Stubs are responsible for marshalling arguments and return values). Stubs usually get inlined if the marshalling overhead is small.
+
+TOTAL_TLB_IMPORTS_009_NAME=# of TLB imports / sec
+TOTAL_TLB_IMPORTS_009_HELP=Reserved for future use.
+
+TOTAL_TLB_EXPORTS_009_NAME=# of TLB exports / sec
+TOTAL_TLB_EXPORTS_009_HELP=Reserved for future use.
+
+DotNetCLR_LocksAndThreads_OBJECT_009_NAME=.NET CLR LocksAndThreads
+DotNetCLR_LocksAndThreads_OBJECT_009_HELP=Stats for CLR Locks and Threads.
+
+CONTENTION_TOTAL_009_NAME=Total # of Contentions
+CONTENTION_TOTAL_009_HELP=This counter displays the total number of times threads in the CLR have attempted to acquire a managed lock unsuccessfully. Managed locks can be acquired in many ways; by the "lock" statement in C# or by calling System.Monitor.Enter or by using MethodImplOptions.Synchronized custom attribute.
+
+CONTENTION_INST_009_NAME=Contention Rate / sec
+CONTENTION_INST_009_HELP=Rate at which threads in the runtime attempt to acquire a managed lock unsuccessfully. Managed locks can be acquired in many ways; by the "lock" statement in C# or by calling System.Monitor.Enter or by using MethodImplOptions.Synchronized custom attribute.
+
+QUEUE_LENGTH_CUR_009_NAME=Current Queue Length
+QUEUE_LENGTH_CUR_009_HELP=This counter displays the total number of threads currently waiting to acquire some managed lock in the application. This counter is not an average over time; it displays the last observed value.
+
+QUEUE_LENGTH_TOTAL_009_NAME=Queue Length Peak
+QUEUE_LENGTH_TOTAL_009_HELP=This counter displays the total number of threads that waited to acquire some managed lock since the start of the application.
+
+QUEUE_LENGTH_INST_009_NAME=Queue Length / sec
+QUEUE_LENGTH_INST_009_HELP=This counter displays the number of threads per second waiting to acquire some lock in the application. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+CURRENT_LOGICAL_THREADS_009_NAME=# of current logical Threads
+CURRENT_LOGICAL_THREADS_009_HELP=This counter displays the number of current .NET thread objects in the application. A .NET thread object is created either by new System.Threading.Thread or when an unmanaged thread enters the managed environment. This counters maintains the count of both running and stopped threads. This counter is not an average over time; it just displays the last observed value.
+
+CURRENT_PHYSICAL_THREADS_009_NAME=# of current physical Threads
+CURRENT_PHYSICAL_THREADS_009_HELP=This counter displays the number of native OS threads created and owned by the CLR to act as underlying threads for .NET thread objects. This counters value does not include the threads used by the CLR in its internal operations; it is a subset of the threads in the OS process.
+
+RECOGNIZED_THREADS_CUR_009_NAME=# of current recognized threads
+RECOGNIZED_THREADS_CUR_009_HELP=This counter displays the number of threads that are currently recognized by the CLR; they have a corresponding .NET thread object associated with them. These threads are not created by the CLR; they are created outside the CLR but have since run inside the CLR at least once. Only unique threads are tracked; threads with same thread ID re-entering the CLR or recreated after thread exit are not counted twice.
+
+RECOGNIZED_THREADS_TOTAL_009_NAME=# of total recognized threads
+RECOGNIZED_THREADS_TOTAL_009_HELP=This counter displays the total number of threads that have been recognized by the CLR since the start of this application; these threads have a corresponding .NET thread object associated with them. These threads are not created by the CLR; they are created outside the CLR but have since run inside the CLR at least once. Only unique threads are tracked; threads with same thread ID re-entering the CLR or recreated after thread exit are not counted twice.
+
+RECOGNIZED_THREADS_INST_009_NAME=rate of recognized threads / sec
+RECOGNIZED_THREADS_INST_009_HELP=This counter displays the number of threads per second that have been recognized by the CLR; these threads have a corresponding .NET thread object associated with them. These threads are not created by the CLR; they are created outside the CLR but have since run inside the CLR at least once. Only unique threads are tracked; threads with same thread ID re-entering the CLR or recreated after thread exit are not counted twice. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+DotNetCLR_Security_OBJECT_009_NAME=.NET CLR Security
+DotNetCLR_Security_OBJECT_009_HELP=Stats for CLR Security.
+
+SECURITY_TOTALRTCHECKS_009_NAME=Total Runtime Checks
+SECURITY_TOTALRTCHECKS_009_HELP=This counter displays the total number of runtime Code Access Security (CAS) checks performed since the start of the application. Runtime CAS checks are performed when a caller makes a call to a callee demanding a particular permission; the runtime check is made on every call by the caller; the check is done by examining the current thread stack of the caller. This counter used together with "Stack Walk Depth" is indicative of performance penalty for security checks.
+
+SECURITY_TIMEAUTHORIZE_009_NAME=% Time Sig. Authenticating
+SECURITY_TIMEAUTHORIZE_009_HELP=Reserved for future use.
+
+SECURITY_LINKCHECKS_009_NAME=# Link Time Checks
+SECURITY_LINKCHECKS_009_HELP=This counter displays the total number of linktime Code Access Security (CAS) checks since the start of the application. Linktime CAS checks are performed when a caller makes a call to a callee demanding a particular permission at JIT compile time; linktime check is performed once per caller. This count is not indicative of serious performance issues; its indicative of the security system activity.
+
+SECURITY_TIMERTCHECKS_009_NAME=% Time in RT checks
+SECURITY_TIMERTCHECKS_009_HELP=This counter displays the percentage of elapsed time spent in performing runtime Code Access Security (CAS) checks since the last such check. CAS allows code to be trusted to varying degrees and enforces these varying levels of trust depending on code identity. This counter is updated at the end of a runtime security check; it represents the last observed value; its not an average.
+
+SECURITY_TIMERTCHECKS_BASE_009_NAME=Not Displayed
+SECURITY_TIMERTCHECKS_BASE_009_HELP=Not Displayed.
+
+SECURITY_DEPTHSECURITY_009_NAME=Stack Walk Depth
+SECURITY_DEPTHSECURITY_009_HELP=This counter displays the depth of the stack during that last runtime Code Access Security check. Runtime Code Access Security check is performed by crawling the stack. This counter is not an average; it just displays the last observed value.
+
+DotNetCLR_Remoting_OBJECT_009_NAME=.NET CLR Remoting
+DotNetCLR_Remoting_OBJECT_009_HELP=Stats for CLR Remoting.
+
+CONTEXT_REMOTECALLS_INST_009_NAME=Remote Calls/sec
+CONTEXT_REMOTECALLS_INST_009_HELP=This counter displays the number of remote procedure calls invoked per second. A remote procedure call is a call on any object outside the caller;s AppDomain. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+CONTEXT_CHANNELS_009_NAME=Channels
+CONTEXT_CHANNELS_009_HELP=This counter displays the total number of remoting channels registered across all AppDomains since the start of the application. Channels are used to transport messages to and from remote objects.
+
+CONTEXT_PROXIES_009_NAME=Context Proxies
+CONTEXT_PROXIES_009_HELP=This counter displays the total number of remoting proxy objects created in this process since the start of the process. Proxy object acts as a representative of the remote objects and ensures that all calls made on the proxy are forwarded to the correct remote object instance.
+
+CONTEXT_CLASSES_009_NAME=Context-Bound Classes Loaded
+CONTEXT_CLASSES_009_HELP=This counter displays the current number of context-bound classes loaded. Classes that can be bound to a context are called context-bound classes; context-bound classes are marked with Context Attributes which provide usage rules for synchronization; thread affinity; transactions etc.
+
+CONTEXT_OBJALLOC_009_NAME=Context-Bound Objects Alloc / sec
+CONTEXT_OBJALLOC_009_HELP=This counter displays the number of context-bound objects allocated per second. Instances of classes that can be bound to a context are called context-bound objects; context-bound classes are marked with Context Attributes which provide usage rules for synchronization; thread affinity; transactions etc. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+CONTEXT_CONTEXTS_009_NAME=Contexts
+CONTEXT_CONTEXTS_009_HELP=This counter displays the current number of remoting contexts in the application. A context is a boundary containing a collection of objects with the same usage rules like synchronization; thread affinity; transactions etc.
+
+CONTEXT_REMOTECALLS_TOTAL_009_NAME=Total Remote Calls
+CONTEXT_REMOTECALLS_TOTAL_009_HELP=This counter displays the total number of remote procedure calls invoked since the start of this application. A remote procedure call is a call on any object outside the caller;s AppDomain.
+
+DotNetCLR_Excep_OBJECT_009_NAME=.NET CLR Exceptions
+DotNetCLR_Excep_OBJECT_009_HELP=Runtime statistics on CLR exception handling.
+
+EXCEP_THROWN_TOTAL_009_NAME=# of Exceps Thrown
+EXCEP_THROWN_TOTAL_009_HELP=This counter displays the total number of exceptions thrown since the start of the application. These include both .NET exceptions and unmanaged exceptions that get converted into .NET exceptions e.g. null pointer reference exception in unmanaged code would get re-thrown in managed code as a .NET System.NullReferenceException; this counter includes both handled and unhandled exceptions. Exceptions that are re-thrown would get counted again. Exceptions should only occur in rare situations and not in the normal control flow of the program.
+
+EXCEP_THROWN_INST_009_NAME=# of Exceps Thrown / sec
+EXCEP_THROWN_INST_009_HELP=This counter displays the number of exceptions thrown per second. These include both .NET exceptions and unmanaged exceptions that get converted into .NET exceptions e.g. null pointer reference exception in unmanaged code would get re-thrown in managed code as a .NET System.NullReferenceException; this counter includes both handled and unhandled exceptions. Exceptions should only occur in rare situations and not in the normal control flow of the program; this counter was designed as an indicator of potential performance problems due to large (>100s) rate of exceptions thrown. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+TOTAL_EXCEP_FILTERS_RUN_009_NAME=# of Filters / sec
+TOTAL_EXCEP_FILTERS_RUN_009_HELP=This counter displays the number of .NET exception filters executed per second. An exception filter evaluates whether an exception should be handled or not. This counter tracks the rate of exception filters evaluated; irrespective of whether the exception was handled or not. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+TOTAL_EXCEP_FINALLYS_RUN_009_NAME=# of Finallys / sec
+TOTAL_EXCEP_FINALLYS_RUN_009_HELP=This counter displays the number of finally blocks executed per second. A finally block is guaranteed to be executed regardless of how the try block was exited. Only the finally blocks that are executed for an exception are counted; finally blocks on normal code paths are not counted by this counter. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+EXCEPT_STACK_DEPTH_009_NAME=Throw To Catch Depth / sec
+EXCEPT_STACK_DEPTH_009_HELP=This counter displays the number of stack frames traversed from the frame that threw the .NET exception to the frame that handled the exception per second. This counter resets to 0 when an exception handler is entered; so nested exceptions would show the handler to handler stack depth. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+DotNetCLR_Memory_OBJECT_007_NAME=.NET CLR-Speicher
+DotNetCLR_Memory_OBJECT_007_HELP=Zhler fr CLR Garbage Collection Heap.
+
+GEN0_COLLECTIONS_COUNTER_007_NAME=Auflistungsanzahl der Generation 0
+GEN0_COLLECTIONS_COUNTER_007_HELP=Dieser Zhler zeigt an, wie oft die Objekte der Generation 0 (die zuletzt zugeordneten Objekte) seit dem Anwendungsstart in die Garbage collection (Gen 0 GC) aufgenommen wurden. Gen 0 GC tritt auf, wenn in Generation 0 nicht gengend Speicher verfgbar ist, um eine Zuordnungsanforderung auszufhren. Der Zhler wird am Ende einer Gen 0 GC erhht. Die hheren GCs enthalten alle niedrigeren GCs. Der Zhler wird explizit erhht, wenn eine hhere Generation (Gen 1 oder Gen 2) GC auftritt. Der Zhlerwert _Global_ ist falsch und sollte ignoriert werden. Der Zhler zeigt den letzten Wert an.
+
+GEN1_COLLECTIONS_COUNTER_007_NAME=Auflistungsanzahl der Generation 1
+GEN1_COLLECTIONS_COUNTER_007_HELP=Dieser Zhler zeigt an, wie oft die Objekte der Generation 1 seit dem Anwendungsstart in die Garbage collection (Gen 0 GC) aufgenommen wurden. Der Zhler wird am Ende einer Gen 1 GC erhht. Die hheren GCs enthalten alle niedrigeren GCs. Der Zhler wird explizit erhht, wenn eine hhere Generation (Gen 2) GC auftritt. Der Zhlerwert _Global_ ist falsch und sollte ignoriert werden. Der Zhler zeigt den letzten Wert an.
+
+GEN2_COLLECTIONS_COUNTER_007_NAME=Auflistungsanzahl der Generation 2
+GEN2_COLLECTIONS_COUNTER_007_HELP=Dieser Zhler zeigt an, wie oft die Objekte der Generation 2 (lter) seit dem Anwendungsstart in die Garbage collection (Gen 0 GC) aufgenommen wurden. Der Zhler wird am Ende einer Gen 2 GC (Vollstndige GC) erhht. Der Zhlerwert _Global_ ist falsch und sollte ignoriert werden. Der Zhler zeigt den letzten Wert an.
+
+GEN0_BYTES_PROMOTED_COUNTER_007_NAME=Von Generation 0 avancierter Speicher
+GEN0_BYTES_PROMOTED_COUNTER_007_HELP=Dieser Zhler zeigt die Gre des Arbeitsspeichers in Bytes an, der nicht in die Garbage collection (GC) aufgenommen und von Generation 0 zu Generation 1 heraufgestuft wurde. Objekte, die nur heraufgestuft werden, da sie auf die Beendigung warten, sind nicht in diesem Zhler enthalten. Der Zhler zeigt den Wert am Ende der letzten GC an. Der Zhler ist nicht kumulativ.
+
+GEN1_BYTES_PROMOTED_COUNTER_007_NAME=Von Generation 1 avancierter Speicher
+GEN1_BYTES_PROMOTED_COUNTER_007_HELP=Dieser Zhler zeigt die Gre des Arbeitsspeichers in Bytes an, der nicht in die Garbage Collection (GC) aufgenommen und von Generation 1 zu Generation 2 heraufgestuft wurde. Objekte, die nur heraufgestuft werden, da sie auf die Beendigung warten, sind nicht in diesem Zhler enthalten. Der Zhler zeigt den Wert am Ende der letzten GC an. Der Zhler ist nicht kumulativ. Der Zhler wird auf 0 zurckgesetzt, wenn die letzte GC nur eine Gen 0 GC war.
+
+GEN0_PROMOTION_RATE_007_NAME=Von Generation 0 avancierte Bytes/Sek.
+GEN0_PROMOTION_RATE_007_HELP=Dieser Zhler zeigt die Bytes pro Sekunde an, die von Generation 0 (neueste) zu Generation 1 heraufgestuft werden. Objekte, die nur heraufgestuft werden, da sie auf die Beendigung warten, sind nicht in diesem Zhler enthalten. Der Speicher wird heraufgestuft, wenn er nicht in eine Garbage Collection aufgenommen wurde. Der Zhler wurde als Indikator von relativ langlebigen Objekten entworfen, die pro Sekunde erstellt werden. Der Zhlen zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+GEN1_PROMOTION_RATE_007_NAME=Von Generation 1 avancierte Bytes/Sek.
+GEN1_PROMOTION_RATE_007_HELP=Dieser Zhler zeigt die Bytes pro Sekunde an, die von Generation 1 zu Generation 2 (lteste) heraufgestuft werden. Objekte, die nur heraufgestuft werden, da sie auf die Beendigung warten, sind nicht in diesem Zhler enthalten. Der Speicher wird heraufgestuft, wenn er nicht in eine Garbage Collection aufgenommen wurde. Von Generation 2 werden keine Objekte heraufgestuft, da sie die lteste Generation ist. Der Zhler wurde als Indikator von sehr langlebigen Objekten entworfen, die pro Sekunde erstellt werden. Der Zhlen zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_007_NAME=Von Gen 0 heraufgestufter Finalization-Speicher
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_007_HELP=Dieser Zhler zeigt die Gre des Arbeitsspeichers in Bytes an, von Generation 0 zu Generation 1 heraufgestuft wurde, da er auf die Beendigung wartet. Der Zhler zeigt den Wert am Ende der letzten GC an. Der Zhler ist nicht kumulativ.
+
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_007_NAME=Von Gen 1 heraufgestufter Finalization-Speicher
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_007_HELP=Dieser Zhler zeigt die Gre des Arbeitsspeichers in Bytes an, von Generation 1 zu Generation 2 heraufgestuft wurde, da er auf die Beendigung wartet. Der Zhler zeigt den Wert am Ende der letzten GC an. Der Zhler ist nicht kumulativ. Der Zhler wird auf 0 zurckgesetzt, wenn die letzte GC nur eine Gen 0 GC war.
+
+GEN0_HEAP_SIZE_COUNTER_007_NAME=Heapgre der Generation 0
+GEN0_HEAP_SIZE_COUNTER_007_HELP=Dieser Zhler zeigt die maximale Anzahl der Bytes an, die in Generation 0 (Gen 0) zugeordnet werden knnen. Die aktuelle Anzahl der in Gen 0 zugeordneten Bytes wird nicht angezeigt. Eine Gen 0 GC wird ausgelst, wenn die Zuordnung seit der letzten GC diesen Wert berschreitet size. Die Gre von Gen 0 wird vom Garbage Collector festgelegt und kann sich whrend dem Ausfhren der Anwendung ndern. Am Ende einer Gen 0-Collection betrgt die Gre des Gen 0-Heaps 0 Bytes. Der Zhler zeigt die Gre (in Bytes) von Zuordnungen an, die die nchste Gen 0 GC auslsen. Der Zhler wird am Ende einer GC aktualisiert; nicht bei jeder Zuordnung.
+
+GEN1_HEAP_SIZE_COUNTER_007_NAME=Heapgre der Generation 1
+GEN1_HEAP_SIZE_COUNTER_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der Bytes in Generation 1 (Gen 1) an. Die maximale Gre von Gen 1 wird nicht angezeigt. Objekte werden in dieser Generation nicht direkt zugeordnet, sondern von vorherigen Gen 0 GCs heraufgestuft. Der Zhler wird am Ende einer GC aktualisiert; nicht bei jeder Zuordnung.
+
+GEN2_HEAP_SIZE_COUNTER_007_NAME=Heapgre der Generation 2
+GEN2_HEAP_SIZE_COUNTER_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der Bytes in Generation 2 (Gen 2) an. Objekte werden in dieser Generation nicht direkt zugeordnet, sondern von Gen 1 whrend vorherigenen Gen 1 GCs heraufgestuft. Der Zhler wird am Ende einer GC aktualisiert; nicht bei jeder Zuordnung.
+
+LARGE_OBJECT_SIZE_COUNTER_007_NAME=Objektheapgre
+LARGE_OBJECT_SIZE_COUNTER_007_HELP=Dieser Zhler zeigt die aktuelle Gre des groen Objektheaps in Bytes an. Objekte, die grer als 20 KB sind, werden vom Garbage Collector als groe Objekte behandelt und direkt in einem speziellen Heap zugeordnet. Sie werden nicht ber Generationen heraufgestuft. Der Zhler wird am Ende einer GC aktualisiert; nicht bei jeder Zuordnung.
+
+SURVIVE_FINALIZE_COUNTER_007_NAME=Finalization Survivors
+SURVIVE_FINALIZE_COUNTER_007_HELP=Dieser Zhler zeigt die Anzahl der Objekt in der Garbage Collection an, die beibehalten werden, da sie auf die Beendigung warten. Wenn die Objekte Verweise auf andere Objekte enthalten, werden diese ebenfalls beibehalten, aber nicht gezhlt. Die Zhler "Von Gen 0 heraufgestufter Finalization-Speicher" und "Von Gen 1 heraufgestufter Finalization-Speicher" stellen den gesamten Speicher dar, der beibehalten wurde. Der Zhler ist nicht kumulativ. Er wird am Ende einer GC mit den beibehaltenen Objekten aktualisiert. Der Zhler zeigt die zustzlichen Objekte an, die die Anwendung aufgrund der Beendigung mglicherweise bernimmt.
+
+NUM_HANDLES_COUNTER_007_NAME=Anzahl der GC-Handle
+NUM_HANDLES_COUNTER_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der verwendeten G-Handles an. GCHandles sind Handles fr externe CLR-Ressourecen und der verwalteten Umgebung. Die Handles belegeben nur wenig Arbeitsspeicher im GCHeap, aber wertvolle nicht verwaltete Ressourcen.
+
+ALLOCATION_RATE_COUNTER_007_NAME=Zugewiesene Bytes/Sek.
+ALLOCATION_RATE_COUNTER_007_HELP=Dieser Zhle zeigt die Rate der Bytes pro Sekunde an, die im GC-Heap zugeordnet werden. Der Zhler wird am Ende der GC aktualisiert, nicht bei jeder Zuordnung. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+INDUCED_GC_COUNTER_007_NAME=Anzahl der ausgelsten GC
+INDUCED_GC_COUNTER_007_HELP=Dieser Zhler zeigt an, wie oft die Garbage Collection aufgrund eines expliziten Aufrufs an GC.Collect maximal ausgefhrt wurde. Die GC sollte die Frequenz ihrer Collections selbst festlegen.
+
+PER_TIME_IN_GC_COUNTER_007_NAME=GC-Zeitdauer in Prozent
+PER_TIME_IN_GC_COUNTER_007_HELP=Die GC-Zeitdauer in Prozent gibt die verstrichene Zeitdauer fr eine Garbage Collection (GC) an, die seit dem letzten GC-Zyklus ausgefhrt wurde. Der Zhler zeigt gewhnlich an, wieviel Speicher vom Garbage Collector fr die Anwendung gesammelt und komprimiert wurde. Der Zhler wird nur am Ende einer GC aktualisiert. Der Zhlerwert reflektiert den letzten Wert; er gibt keinen Durchschnitt an.
+
+PER_TIME_IN_GC_COUNTER_BASE_007_NAME=Nicht angezeigt
+PER_TIME_IN_GC_COUNTER_BASE_007_HELP=Nicht angezeigt.
+
+TOTAL_HEAP_SIZE_COUNTER_007_NAME=Anzahl der Bytes in den Heaps
+TOTAL_HEAP_SIZE_COUNTER_007_HELP=Dieser Zhler stellt die Summe aus den vier anderen Zhlern dar: Gen 0-Heapgre, Gen 1-Heapgre, Gen 2-Heapgre und die Large Object-Heapgre. Dieser Zhler zeigt den in den GC-Heaps zugeordneten Speicher in Bytes an.
+
+TOTAL_COMMITTED_MEM_COUNTER_007_NAME=Festgelegte Bytes insgesamt
+TOTAL_COMMITTED_MEM_COUNTER_007_HELP=Dieser Zhler zeigt den virtuellen Speicher in Bytes an, der vom Garbage Collector reserviert wurde. (Reservierter Arbeitsspeicher ist der physikalische Speicher, der in der Auslagerungsdatei des Datentrgers reserviert wird).
+
+TOTAL_RESERVED_MEM_COUNTER_007_NAME=Gesamtanzahl der reservierten Bytes
+TOTAL_RESERVED_MEM_COUNTER_007_HELP=Dieser Zhler zeigt den virtuellen Speicher in Bytes an, der vom Garbage Collector reserviert wird. (Reservierter Speicher ist der virtuelle Arbeitsspeicher, der fr die Anwendung reserviert wird.)
+
+GC_PINNED_OBJECTS_007_NAME=Anzahl der fixierten Objekte
+GC_PINNED_OBJECTS_007_HELP=Dieser Zhler zeigt die Anzahl der fixierten Objekte in der letzten GC an. Der Zhler verfolgt die fixierten Objekte nur in den Heaps in der Garbage Collection. Eine Gen 0 GC verursacht z.B. die Enumeration der fixierten Objekte nur im Generation 0-Heap. Ein fixiertes Objekt kann nicht vom Garbage Collector in den Speicher verschoben werden.
+
+GC_SINKBLOCKS_007_NAME=Anzahl der verwendeten Sinkblcke
+GC_SINKBLOCKS_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der verwendeten Synchronisierungsblcke an. Synchronisierungsblcke sind die Datenstrukturen pro Objekt, die zum Speichern der Synchronisierungsinformationen zugeordnet werden. Synchronisierungsblcke enthalten Weak-Verweise auf verwaltete Objekte und mssen vom Garbage Collector berprft werden. In Synchronisierungsblcken knnen auch COM-Interop-Metadaten gespeichert werden. Der Zhler zeigt Leistungsprobleme an, die auftreten, wenn die Synchronisierungsprimitiven zu oft verwendet werden.
+
+DotNetCLR_Loading_OBJECT_007_NAME=.NET CLR-Ladevorgang
+DotNetCLR_Loading_OBJECT_007_HELP=Statistiken fr das CLR-Klassenladeprogramm.
+
+LOADING_CLASSES_TOTAL_007_NAME=Gesamtanzahl der geladenen Klassen
+LOADING_CLASSES_TOTAL_007_HELP=Dieser Zhler zeigt die kumulative Anzahl der Klassen an, die in allen Assemblys seit dem Start der Anwendung geladen wurden.
+
+LOADING_TIME_007_NAME=Ladezeit in Prozent
+LOADING_TIME_007_HELP=Fr die zuknftige Verwendung reserviert.
+
+LOADING_ASMSEARCHLEN_007_NAME=Assemblysuchlnge
+LOADING_ASMSEARCHLEN_007_HELP=Fr die zuknftige Verwendung reserviert.
+
+LOADING_LOADFAILURES_TOTAL_007_NAME=Gesamtanzahl der Ladefehler
+LOADING_LOADFAILURES_TOTAL_007_HELP=Dieser Zhler zeigt die Hchstanzahl der Klassen an, die seit dem Start der Anwendung nicht geladen werden konnten. Mglicherweise ist die Sicherheit unangemessen oder das Format ist ungltig. Weitere Informationen finden Sie in der Hilfe.
+
+LOADING_LOADFAILURES_INST_007_NAME=Rate der Ladefehler
+LOADING_LOADFAILURES_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Klassen pro Sekunde an, die nicht geladen werden konnten. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an. Die Ladefehler knnen mehrere Ursachen haben; z.B. unzureichende Sicherheit oder ein ungltiges Format. Weitere Informationen finden Sie in der Hilfe.
+
+LOADING_HEAPSIZE_007_NAME=Bytes im Lademodulheap
+LOADING_HEAPSIZE_007_HELP=Dieser Zhler zeigt die aktuelle Gre (in Bytes) des Arbeitsspeichers an, der vom Klassenladeprogramm in allen Anwendungsdomnen reserviert wurde. (Reservierter Arbeitsspeicher ist der physikalische Speicher, der in der Auslagerungsdatei des Datentrgers reserviert wird.)
+
+LOADING_APPDOMAINS_UNLOADED_TOTAL_007_NAME=Gesamtanzahl der entladenen Anwendungsdomnen
+LOADING_APPDOMAINS_UNLOADED_TOTAL_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Anwendungsdomnen an, die seit dem Anwendungsstart entladen wurden. Wenn eine Anwendungsdomne mehrmals geladen und entladen wird, werden die Entladevorgnge einzeln gezhlt.
+
+LOADING_APPDOMAINS_UNLOADED_INST_007_NAME=Rate der entladenen Anwendungsdomnen
+LOADING_APPDOMAINS_UNLOADED_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Anwendungsdomnen an, die pro Sekunde entladen werden. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+LOADING_CLASSES_CUR_007_NAME=Aktuelle geladene Klassen
+LOADING_CLASSES_CUR_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der in allen Assemblys geladenen Klassen an.
+
+LOADING_CLASSES_INST_007_NAME=Rate der geladenen Klassen
+LOADING_CLASSES_INST_007_HELP=Dieser Zhler zeigt die Anzahl der pro Sekunden in allen Assemblys geladenen Klassen an. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+LOADING_APPDOMAINS_CUR_007_NAME=Aktuelle Anwendungsdomnen
+LOADING_APPDOMAINS_CUR_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der Anwendungsdomnen an, die in der Anwendung geladen sind. Anwendungsdomnen stellen eine sichere und vielseitige Verarbeitungseinheit bereit, mit der die CLR Anwendungen isolieren kann, die im gleichen Prozess ausgefhrt werden.
+
+LOADING_APPDOMAINS_TOTAL_007_NAME=Anwendungsdomnen insgesamt
+LOADING_APPDOMAINS_TOTAL_007_HELP=Dieser Zhler zeigt die Hchstanzahl der Anwendungsdomnen an, die seit dem Starten Anwendung geladen wurden. Anwendungsdomnen stellen eine sichere und vielseitige Verarbeitungseinheit bereit, mit der die CLR Anwendungen isolieren kann, die im gleichen Prozess ausgefhrt werden.
+
+LOADING_APPDOMAINS_INST_007_NAME=Rate der Anwendungsdomnen
+LOADING_APPDOMAINS_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Anwendungsdomnen an, die pro Sekunde geladen werden. Anwendungsdomnen stellen eine sichere und vielseitige Verarbeitungseinheit bereit, mit der die CLR Anwendungen isolieren kann, die im gleichen Prozess ausgefhrt werden. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+LOADING_ASSEMBLIES_CUR_007_NAME=Aktuelle Assemblys
+LOADING_ASSEMBLIES_CUR_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der Assemblys an, die in dieser Anwendung in allen Anwendungsdomnen geladen werden. Wenn die Assembly von mehreren Anwendungsdomnen als domnenneutral geladen wird, wird der Zhler nur einmal erhht. Assemblys knnen als domnenneutral geladen werden, wenn ihr Code von allen Anwendungsdomnen gemeinsam genutzt werden kann. Assemblys knnen domnenspezifisch geladen werden, wenn ihr Code in der Anwendungsdomne privat ist.
+
+LOADING_ASSEMBLIES_TOTAL_007_NAME=Assemblys insgesamt
+LOADING_ASSEMBLIES_TOTAL_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Assemblys an, die seit dem Start der Anwendung geladen wurden. Wenn die Assembly von mehreren Anwendungsdomnen als domnenneutral geladen wird, wird der Zhler nur einmal erhht. Assemblys knnen als domnenneutral geladen werden, wenn ihr Code von allen Anwendungsdomnen gemeinsam genutzt werden kann. Assemblys knnen domnenspezifisch geladen werden, wenn ihr Code in der Anwendungsdomne privat ist.
+
+LOADING_ASSEMBLIES_INST_007_NAME=Assemblyrate
+LOADING_ASSEMBLIES_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Assemblys an, die pro Sekunden in allen Anwendungsdomnen geladen werden. Wenn die Assembly von mehreren Anwendungsdomnen als domnenneutral geladen wird, wird der Zhler nur einmal erhht. Assemblys knnen als domnenneutral geladen werden, wenn ihr Code von allen Anwendungsdomnen gemeinsam genutzt werden kann. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+DotNetCLR_Jit_OBJECT_007_NAME=.NET CLR-Jit
+DotNetCLR_Jit_OBJECT_007_HELP=Statistik fr CLR-Jit.
+
+TOTAL_METHODS_JITTED_007_NAME=Anzahl der mit JIT kompilierten Methoden
+TOTAL_METHODS_JITTED_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Methoden an, die vom CLR JIT-Compiler seit dem Start der Anwendung kompiliert wurden. Die nicht JIT-Methoden sind in diesem Zhler nicht enthalten.
+
+JITTED_IL_CUR_007_NAME=Anzahl der mit JIT kompilierten IL-Bytes
+JITTED_IL_CUR_007_HELP=Dieser Zeiger zeigt die Gesamtanzahl der mit JIT kompilierten IL-Bytes seit dem Start der Anwendung an. Dieser Zhler ist mit dem Zhler "Gesamtanzahl der mit JIT kompilierten IL-Bytes" identisch.
+
+JITTED_IL_TOTAL_007_NAME=Gesamtanzahl der mit JIT kompilierten IL-Bytes
+JITTED_IL_TOTAL_007_HELP=Dieser Zeiger zeigt die Gesamtanzahl der mit JIT kompilierten IL-Bytes seit dem Start der Anwendung an. Dieser Zhler ist mit dem Zhler "Anzahl der mit JIT kompilierten IL-Bytes" identisch.
+
+JITTED_IL_INST_007_NAME=Mit JIT kompilierte IL-Bytes/Sek.
+JITTED_IL_INST_007_HELP=Dieser Zhler zeigt die JIT-Rate pro Sekunde fr IL-Bytes an. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+JIT_FAILURES_007_NAME=JIT-Standardfehler
+JIT_FAILURES_007_HELP=Dieser Zhler zeigt die Hchstanzahl der Methoden an, die seit dem Start der Anwendung nicht mit dem JIT-Compiler kompiliert werden konnten. Dieses Problem kann auftreten, wenn die IL nicht berprft werden kann, oder wenn ein interner Fehler im JIT-Compiler aufgetreten ist.
+
+TIME_IN_JIT_007_NAME=JIT-Zeitdauer in Prozent
+TIME_IN_JIT_007_HELP=Dieser Zhler zeigt die verstrichene Zeit fr die JIT-Kompilierung seit der letzten Kompilierungsphase in Prozent an. Der Zhler wird am Ende jeder JIT-Kompilierungsphase aktualisiert. Whrend einer JIT-Kompilierungsphase werden eine Methode und ihre Abhngigkeiten kompiliert.
+
+TIME_IN_JIT_BASE_007_NAME=Nicht angezeigt
+TIME_IN_JIT_BASE_007_HELP=Nicht angezeigt.
+
+DotNetCLR_Interop_OBJECT_007_NAME=.NET CLR-Interop
+DotNetCLR_Interop_OBJECT_007_HELP=Statistik fr CLR-Interop.
+
+CURRENT_CCW_007_NAME=Anzahl der CCWs
+CURRENT_CCW_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der CCWs (Com-Callable-Wrappers) an. Ein CCW ist ein Proxy fr das verwaltete .NET-Objekt, auf das von nicht verwalteten COM-Client verwiesen wird. Der Zhler zeigt die Anzahl der verwalteten Objekte an, auf die von nicht verwaltetem COM-Code verwiesen wird.
+
+CURRENT_STUBS_007_NAME=Anzahl der Stubs
+CURRENT_STUBS_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der Stubs an, die von der CLR erstellt wurden. Stubs sind fr das Marshallen von Argumenten und Rckgabewerten zwischen verwaltetem und nicht verwaltetem Code whrend einem COM-Interopaufruf oder PInvoke-Aufruf verantwortlich.
+
+NUM_MARSHALLING_007_NAME=Anzahl der Marshallvorgnge
+NUM_MARSHALLING_007_HELP=Dieser Zhler zeigt an, wie oft Argumente und Rckgabewerte zwischen verwaltetem und nicht verwaltetem Code seit dem Start der Anwendung gemarshallt wurden. Der Zhler wird nicht erhht, wenn die Stubs intern sind. (Stubs sind fr das Marshallen von Argumenten und Rckgabewerten verantwortlich).
+
+TOTAL_TLB_IMPORTS_007_NAME=Anzahl der TLB-Importe/Sek.
+TOTAL_TLB_IMPORTS_007_HELP=Fr die zuknftige Verwendung reserviert.
+
+TOTAL_TLB_EXPORTS_007_NAME=Anzahl der TLB-Exporte/Sek.
+TOTAL_TLB_EXPORTS_007_HELP=Fr die zuknftige Verwendung reserviert.
+
+DotNetCLR_LocksAndThreads_OBJECT_007_NAME=.NET CLR-Sperren und Threads
+DotNetCLR_LocksAndThreads_OBJECT_007_HELP=Statistik fr CLR-Sperren und Threads.
+
+CONTENTION_TOTAL_007_NAME=Gesamtanzahl der Konflikte
+CONTENTION_TOTAL_007_HELP=Dieser Zhler zeigt an, wie oft die Threads in der CLR versucht haben, erfolglos eine verwaltete Sperre abzurufen. Verwaltete Sperren knnen mit mehreren Methoden abgerufen werden. Durch die Anweisung "lock" in C#, durch Aufrufen von System.Monitor.Enter oder mit dem benutzerdefinierten Attribut MethodImplOptions.Synchronized.
+
+CONTENTION_INST_007_NAME=Konfliktrate/Sek.
+CONTENTION_INST_007_HELP=Rate mit der die Threads in der Runtime versuchen, erfolglos eine verwaltete Sperre abzurufen. Verwaltete Sperren knnen mit mehreren Methoden abgerufen werden. Durch die Anweisung "lock" in C#, durch Aufrufen von System.Monitor.Enter oder mit dem benutzerdefinierten Attribut MethodImplOptions.Synchronized.
+
+QUEUE_LENGTH_CUR_007_NAME=Aktuelle Warteschlangenlnge
+QUEUE_LENGTH_CUR_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Threads an, die auf eine verwaltete Sperrung in der Anwendung warten. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den letzten Wert an.
+
+QUEUE_LENGTH_TOTAL_007_NAME=Maximale Warteschlangenlnge
+QUEUE_LENGTH_TOTAL_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Threads an, die seit dem Start der Anwendung auf eine verwaltete Sperrung warten.
+
+QUEUE_LENGTH_INST_007_NAME=Warteschlangenlnge/Sek.
+QUEUE_LENGTH_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Threads pro Sekunde an, die auf eine Sperrung der Anwendung warten. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+CURRENT_LOGICAL_THREADS_007_NAME=Anzahl der aktuellen logischen Threads
+CURRENT_LOGICAL_THREADS_007_HELP=Dieser Zhler zeigt die Anzahl der aktuellen .NET-Threadobjekte in der Anwendung an. Ein .NET-Threadobjekt wird von System.Threading.Thread erstellt, oder wenn ein nicht verwalteter Thread in die verwaltete Umgebung aufgenommen wird. Der Zhler verwaltet die Anzahl der ausgefhrten und beendeten Threads. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den letzten Wert an.
+
+CURRENT_PHYSICAL_THREADS_007_NAME=Anzahl der aktuellen physikalischen Threads
+CURRENT_PHYSICAL_THREADS_007_HELP=Dieser Zhler zeigt die Anzahl der systemeigenen Betriebssystemthreads an, die von der CLR als untergeordnete .NET-Threadobjekte erstellt werden. Dieser Zhlerwert enthlt die Threads nicht, die von der CLR fr interne Vorgnge verwendet werden. Er ist eine Teilmenge der Threads im Betriebssystemprozess.
+
+RECOGNIZED_THREADS_CUR_007_NAME=Anzahl der aktuellen erkannten Threads
+RECOGNIZED_THREADS_CUR_007_HELP=Dieser Zhler zeigt die Anzahl der Threads an, die von der CLR erkannt werden. Diesen Threads ist ein entsprechendes .NET-Threadobjekt zugewiesen. Die Threads werden auerhalb der CLR erstellt, aber wurden mindestens einmal in der CLR ausgefhrt. Nur eindeutige Threads werden verfolgt. Threads mit der gleichen Thread-ID, die erneut in die CLR aufgenommen oder nach dem Beenden erstellt werden, werden nicht zweimal gezhlt.
+
+RECOGNIZED_THREADS_TOTAL_007_NAME=Gesamtanzahl der erkannten Threads
+RECOGNIZED_THREADS_TOTAL_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Threads an, die von der CLR seit dem Start der Anwendung erkannt wurden. Diesen Threads ist ein entsprechendes .NET-Threadobjekt zugewiesen. Die Threads werden auerhalb der CLR erstellt, aber wurden mindestens einmal in der CLR ausgefhrt. Nur eindeutige Threads werden verfolgt. Threads mit der gleichen Thread-ID, die erneut in die CLR aufgenommen oder nach dem Beenden erstellt werden, werden nicht zweimal gezhlt.
+
+RECOGNIZED_THREADS_INST_007_NAME=Erkannte Threadrate/Sek.
+RECOGNIZED_THREADS_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Threads pro Sekunde an, die von der CLR erkannt wurden. Diesen Threads ist ein entsprechendes .NET-Threadobjekt zugeordnet. Die Threads werden nicht von der CLR, sondern auerhalb der CLR erstellt, aber mindestens einmal in der CLR ausgefhrt. Nur eindeutige Threads werden nachverfolgt; Threads mit der gleichen Thread-ID, die in der CLR wiederholt oder erneut erstellt werden, werden nicht zweimal gezhlt. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+DotNetCLR_Security_OBJECT_007_NAME=.NET CLR-Sicherheit
+DotNetCLR_Security_OBJECT_007_HELP=Statistik fr die CLR-Sicherheit.
+
+SECURITY_TOTALRTCHECKS_007_NAME=Laufzeitberprfungen insgesamt
+SECURITY_TOTALRTCHECKS_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der CAS-Laufzeitberprfungen (Code Access Security) seit dem Start der Anwendung an. CAS-Laufzeitberprfungen werden ausgefhrt wenn beim einem Aufruf eine bestimmte Berechtigung angefordert wird. Die Laufzeitberprfung wird fr jeden Aufruf ausgefhrt, indem der aktuelle Threadstapel des Aufrufers berprft wird. Dieser Zhler gibt zusammen mit "Stapeltiefe" die Leistungseinbuen fr Sicherheitsberprfungen an.
+
+SECURITY_TIMEAUTHORIZE_007_NAME=Zeit fr die Signaturauthentifizierung in Prozent
+SECURITY_TIMEAUTHORIZE_007_HELP=Fr die zuknftige Verwendung reserviert.
+
+SECURITY_LINKCHECKS_007_NAME=Anzahl der Verbindungszeitberprfungen
+SECURITY_LINKCHECKS_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der CAS-berprfungen (Code Access Security) seit dem Anwendungsstart an. CAS-Linktimeberprfen werden ausgefhrt, wenn eine bestimmte Berechtigung whrend der JIT-Kompilierung aufgerufen wird. Eine Linktimeberprfung wird nur einmal pro Aufrufer ausgefhrt. Dieser Wert zeigt keine Leistungsprobleme an, nur die Sicherheitssystemaktivitten.
+
+SECURITY_TIMERTCHECKS_007_NAME=Zeit fr die RT-berprfungen in Prozent
+SECURITY_TIMERTCHECKS_007_HELP=Dieser Zhler zeigt den Zeitraum an, der seit der letzten CAS-berprfung (Code Access Security) verstrichen ist. CAS ermglicht unterschiedliche Vertrauensebenen fr den Code und erzwingt die Ebenen abhngig von der Codeidentitt. Der Zhler wird am Ende einer Sicherheitsberprfung aktualisiert. Er zeigt keinen Durchschnittswert, sondern den letzten Wert an.
+
+SECURITY_TIMERTCHECKS_BASE_007_NAME=Nicht angezeigt
+SECURITY_TIMERTCHECKS_BASE_007_HELP=Nicht angezeigt.
+
+SECURITY_DEPTHSECURITY_007_NAME=Stapeltiefe
+SECURITY_DEPTHSECURITY_007_HELP=Dieser Zhler zeigt die Stapeltiefe whrend der letzten berprfung der Codezugriffssicherheit zur Laufzeit an. Beim berprfen Codezugriffssicherheit zur Laufzeit wird der Stapel durchsucht. Der Zhler gibt keinen Durchnittswert, sondern nur den letzten Wert an.
+
+DotNetCLR_Remoting_OBJECT_007_NAME=.NET CLR-Remote
+DotNetCLR_Remoting_OBJECT_007_HELP=Statistik fr CLR-Remote.
+
+CONTEXT_REMOTECALLS_INST_007_NAME=Remoteaufrufe/Sek.
+CONTEXT_REMOTECALLS_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Remoteprozeduraufrufe pro Sekunde an. Ein Remoteprozeduraufruf ist ein Aufruf eines Objekts auerhalb der Anwendungsdomne des Aufrufers. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+CONTEXT_CHANNELS_007_NAME=Channel
+CONTEXT_CHANNELS_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Remotechannel in den Anwendungsdomnen an, die seit dem Start der Anwendung registriert wurden. Channel werden zum bertragen von Nachrichten zwischen Remoteobjekten verwendet.
+
+CONTEXT_PROXIES_007_NAME=Kontextproxys
+CONTEXT_PROXIES_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Remoteproxyobjekte an, die in diesem Prozess seit dem Start der Anwendung erstellt wurden. Proxyobjekte stellen die Remoteobjekte dar und stellen sicher, dass alle Proxyaufrufe an die entsprechende Remoteobjektinstanz weitergeleitet werden.
+
+CONTEXT_CLASSES_007_NAME=Geladene kontextgebundene Klassen
+CONTEXT_CLASSES_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der kontextgebundenen geladenen Klassen an. Klassen, die an einen Kontext gebunden werden knnen, sind kontextgebundene Klassen. Kontextgebundene Klassen werden mit Kontextattributen fr die Synchronisierung, Threadaffinitt, Transaktionen, usw. markiert.
+
+CONTEXT_OBJALLOC_007_NAME=Kontextgebundene Objektzuordnung/Sek.
+CONTEXT_OBJALLOC_007_HELP=Dieser Zhler zeigt die Anzahl der kontextgebundenen Objekte an, die pro Sekunde zugeordnet werden. Instanzen von Klassen, die an einen Kontext gebunden werden knnen, sind kontextgebundene Objekte. Kontextgebundene Klassen werden mit Kontextattributen fr die Synchronisation, Threadaffinitt, Transaktionen, usw. markiert. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+CONTEXT_CONTEXTS_007_NAME=Kontext
+CONTEXT_CONTEXTS_007_HELP=Dieser Zhler zeigt die aktuelle Anzahl der Remotekontexte in der Anwendung an. Ein Kontext enthlt eine Auflistung der Objekte mit den gleichen Syntaxregeln; z.B. Synchronisierung, Threadaffinitt, Transaktionen, usw.
+
+CONTEXT_REMOTECALLS_TOTAL_007_NAME=Remoteaufrufe insgesamt
+CONTEXT_REMOTECALLS_TOTAL_007_HELP=Dieser Zhle zeigt die Gesamtanzahl der Remoteprozeduraufrufe an, die seit dem Start der Anwendung initialisiert wurden. Ein Remoteprozeduraufruf ist der Aufruf eines Objekts auerhalb der Anwendungsdomne des Aufrufers.
+
+DotNetCLR_Excep_OBJECT_007_NAME=.NET CLR-Ausnahmen
+DotNetCLR_Excep_OBJECT_007_HELP=Laufzeitstatistik fr die CLR-Ausnahmebehandlung.
+
+EXCEP_THROWN_TOTAL_007_NAME=Anzahl der ausgelsten Ausnahmen
+EXCEP_THROWN_TOTAL_007_HELP=Dieser Zhler zeigt die Gesamtanzahl der Ausnahmen an, die seit dem Start der Anwendung ausgelst wurden. TDiese schlieen .NET-Ausnahmen und nicht verwaltete Ausnahmen ein, die in .NET-Ausnahmen konvertiert werden; z.B. wird eine Nullzeigerverweis-Ausnahme in nicht verwaltetem Code in eine .NET System.NullReferenceException in verwaltetem Code konvertiert. Dieser Zhler enthlt behandelte und unbehandelte Ausnahmen. Erneut ausgelste Ausnahmen, werden wieder gezhlt. Ausnahmen sollten nur selten und nicht im normalen Programmablauf auftreten.
+
+EXCEP_THROWN_INST_007_NAME=Anzahl der ausgelsten Ausnahmen/Sek.
+EXCEP_THROWN_INST_007_HELP=Dieser Zhler zeigt die Anzahl der Ausnahmen pro Sekunde an. Diese schlieen .NET-Ausnahmen und nicht verwaltete Ausnahmen ein, die in .NET-Ausnahmen konvertiert werden; z.B. wird eine Nullzeigerverweis-Ausnahme in nicht verwaltetem Code in eine .NET System.NullReferenceException in verwaltetem Code konvertiert. Dieser Zhler enthlt behandelte und unbehandelte Ausnahmen. Ausnahmen sollten nur selten und nicht im normalen Programmablauf auftreten. Der Zhler zeigt potentielle Leistungsprobleme an, die aufgrund einer groen Ausnahmerate auftreten. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+TOTAL_EXCEP_FILTERS_RUN_007_NAME=Anzahl der Filter/Sek.
+TOTAL_EXCEP_FILTERS_RUN_007_HELP=Dieser Zhler zeigt die Anzahl der .NET-Ausnahmefilter an, die pro Sekunde ausgefhrt werden. Ein Ausnahmefilter wertet aus, ob eine Ausnahme behandelt werden soll. Der Zhler verfolgt die Rate der ausgewerteten Ausnahmefilter; ungeachtet davon, ob die Ausnahme behandelt wurde oder nicht. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+TOTAL_EXCEP_FINALLYS_RUN_007_NAME=Finallyanzahl/Sek.
+TOTAL_EXCEP_FINALLYS_RUN_007_HELP=Dieser Zhler zeigt die Anzahl der finally-Blcke an, die pro Sekunde ausgefhrt werden. Ein finally-Block wird ausgefhrt, unabhngig davon, wie der try-Block beendet wurde. Nur die finally-Blcke, die fr eine Ausnahme ausgefhrt werden, werden gezhlt. finally-Blcke in normalen Codepfaden werden nicht gezhlt. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
+EXCEPT_STACK_DEPTH_007_NAME=Throw To Catch Depth / sec
+EXCEPT_STACK_DEPTH_007_HELP=Dieser Zhler zeigt die Anzahl der Stapelrahmen an, die vom Rahmen durchlaufen werden, der die .NET-Ausnahme ausgelst hat. Der Zhler wird auf 0 zurckgesetzt, wenn ein Ausnahmehandler eingegeben wird. Der Zhler bildet nicht den Mittelwert aus der Zeit, sondern zeigt den Unterschied zwischen den Werten in den letzten zwei Beispielen geteilt durch das Beispielintervall an.
+
diff --git a/src/inc/1031/_DataPerfCounters.ini b/src/inc/1031/_DataPerfCounters.ini
new file mode 100644
index 0000000..ecb7a30
--- /dev/null
+++ b/src/inc/1031/_DataPerfCounters.ini
Binary files differ
diff --git a/src/inc/1031/_NetworkingPerfCounters.ini b/src/inc/1031/_NetworkingPerfCounters.ini
new file mode 100644
index 0000000..1586788
--- /dev/null
+++ b/src/inc/1031/_NetworkingPerfCounters.ini
Binary files differ
diff --git a/src/inc/1031/aspnet_perf.ini b/src/inc/1031/aspnet_perf.ini
new file mode 100644
index 0000000..a6f386f
--- /dev/null
+++ b/src/inc/1031/aspnet_perf.ini
@@ -0,0 +1,415 @@
+[info]
+drivername=ASP.NET_1.0.3620.0
+symbolfile=aspnet_perf.h
+
+[languages]
+007=German
+009=English
+
+[objects]
+OBJECT_1_009_NAME=ASP.NET v1.0.3620.0
+OBJECT_2_009_NAME=ASP.NET Apps v1.0.3620.0
+
+[text]
+OBJECT_1_009_NAME=ASP.NET v1.0.3620.0
+OBJECT_1_009_HELP=ASP.NET v1.0.3620.0 global performance counters
+OBJECT_2_009_NAME=ASP.NET Apps v1.0.3620.0
+OBJECT_2_009_HELP=ASP.NET v1.0.3620.0 application performance counters
+
+;;
+;; ASP.NET System Counters
+;;
+
+ASPNET_APPLICATION_RESTARTS_009_NAME=Application Restarts
+ASPNET_APPLICATION_RESTARTS_009_HELP=Number of times the application has been restarted during the web server's lifetime.
+
+ASPNET_APPLICATIONS_RUNNING_009_NAME=Applications Running
+ASPNET_APPLICATIONS_RUNNING_009_HELP=Number of currently running web applications.
+
+ASPNET_REQUESTS_DISCONNECTED_009_NAME=Requests Disconnected
+ASPNET_REQUESTS_DISCONNECTED_009_HELP=The number of requests disconnected due to communication errors or user terminated.
+
+ASPNET_REQUEST_EXECUTION_TIME_009_NAME=Request Execution Time
+ASPNET_REQUEST_EXECUTION_TIME_009_HELP=The number of milliseconds that it took to execute the most recent request.
+
+ASPNET_REQUESTS_REJECTED_009_NAME=Requests Rejected
+ASPNET_REQUESTS_REJECTED_009_HELP=The number of requests rejected because the request queue was full.
+
+ASPNET_REQUESTS_QUEUED_009_NAME=Requests Queued
+ASPNET_REQUESTS_QUEUED_009_HELP=The number of requests waiting to be processed.
+
+ASPNET_WPS_RUNNING_009_NAME=Worker Processes Running
+ASPNET_WPS_RUNNING_009_HELP=Number of worker processes running on the machine.
+
+ASPNET_WPS_RESTARTS_009_NAME=Worker Process Restarts
+ASPNET_WPS_RESTARTS_009_HELP=Number of times a worker process has restarted on the machine.
+
+ASPNET_REQUEST_WAIT_TIME_009_NAME=Request Wait Time
+ASPNET_REQUEST_WAIT_TIME_009_HELP=The number of milliseconds the most recent request was waiting in the queue.
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_NAME=State Server Sessions Active
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_NAME=State Server Sessions Abandoned
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_NAME=State Server Sessions Timed Out
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_NAME=State Server Sessions Total
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_HELP=The number of sessions total.
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_009_NAME=Anonymous Requests
+ASPNET_ANONYMOUS_REQUESTS_009_HELP=Number of requests utilizing anonymous authentication.
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_NAME=Anonymous Requests/Sec
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_HELP=Number of Authentication Anonymous Requests/Sec
+
+ASPNET_TOTAL_CACHE_ENTRIES_009_NAME=Cache Total Entries
+ASPNET_TOTAL_CACHE_ENTRIES_009_HELP=Total number of entries within the cache (both internal and user added)
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_NAME=Cache Total Turnover Rate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the total cache per second.
+
+ASPNET_TOTAL_CACHE_HITS_009_NAME=Cache Total Hits
+ASPNET_TOTAL_CACHE_HITS_009_HELP=Total number of hits from the cache.
+
+ASPNET_TOTAL_CACHE_MISSES_009_NAME=Cache Total Misses
+ASPNET_TOTAL_CACHE_MISSES_009_HELP=Total number of cache misses.
+
+ASPNET_TOTAL_CACHE_RATIO_009_NAME=Cache Total Hit Ratio
+ASPNET_TOTAL_CACHE_RATIO_009_HELP=Ratio of hits from all cache calls.
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_NAME=Cache Total Hit Ratio Base
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_HELP=Cache Total Hit Ratio Base
+
+ASPNET_API_CACHE_ENTRIES_009_NAME=Cache API Entries
+ASPNET_API_CACHE_ENTRIES_009_HELP=Total number of entries within the cache added by the user.
+
+ASPNET_API_CACHE_TURNOVER_RATE_009_NAME=Cache API Turnover Rate
+ASPNET_API_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the API cache per second.
+
+ASPNET_API_CACHE_HITS_009_NAME=Cache API Hits
+ASPNET_API_CACHE_HITS_009_HELP=Number of cache hits from user code.
+
+ASPNET_API_CACHE_MISSES_009_NAME=Cache API Misses
+ASPNET_API_CACHE_MISSES_009_HELP=Number of cache misses called from user code.
+
+ASPNET_API_CACHE_RATIO_009_NAME=Cache API Hit Ratio
+ASPNET_API_CACHE_RATIO_009_HELP=Ratio of hits called from user code.
+
+ASPNET_API_CACHE_RATIO_BASE_009_NAME=Cache API Hit Ratio Base
+ASPNET_API_CACHE_RATIO_BASE_009_HELP=Cache API Hit Ratio Base
+
+ASPNET_OUTPUT_CACHE_ENTRIES_009_NAME=Output Cache Entries
+ASPNET_OUTPUT_CACHE_ENTRIES_009_HELP=Current number of entries in the output cache.
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_NAME=Output Cache Turnover Rate
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the output cache per second.
+
+ASPNET_OUTPUT_CACHE_HITS_009_NAME=Output Cache Hits
+ASPNET_OUTPUT_CACHE_HITS_009_HELP=Total number of ouput cacheable requests served from the output cache.
+
+ASPNET_OUTPUT_CACHE_MISSES_009_NAME=Output Cache Misses
+ASPNET_OUTPUT_CACHE_MISSES_009_HELP=Total number of ouput cacheable requests not served from the output cache.
+
+ASPNET_OUTPUT_CACHE_RATIO_009_NAME=Output Cache Hit Ratio
+ASPNET_OUTPUT_CACHE_RATIO_009_HELP=Ratio of hits to requests for output cacheable requests.
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_NAME=Output Cache Hit Ratio Base
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_HELP=Output Cache Hit Ratio Base
+
+ASPNET_COMPILATIONS_009_NAME=Compilations Total
+ASPNET_COMPILATIONS_009_HELP=Number of .asax, .ascx, .ashx, .asmx, or .aspx source files dynamically compiled.
+
+ASPNET_DEBUGGING_REQUESTS_009_NAME=Debugging Requests
+ASPNET_DEBUGGING_REQUESTS_009_HELP=Number of debugging requests processed.
+
+ASPNET_ERRORS_PRE_PROCESSING_009_NAME=Errors During Preprocessing
+ASPNET_ERRORS_PRE_PROCESSING_009_HELP=Number of errors that have occurred during parsing and configuration.
+
+ASPNET_ERRORS_COMPILING_009_NAME=Errors During Compilation
+ASPNET_ERRORS_COMPILING_009_HELP=Number of errors that have occurred during compilation.
+
+ASPNET_ERRORS_DURING_REQUEST_009_NAME=Errors During Execution
+ASPNET_ERRORS_DURING_REQUEST_009_HELP=Number of errors that have occurred during the processing of a request.
+
+ASPNET_ERRORS_UNHANDLED_009_NAME=Errors Unhandled During Execution
+ASPNET_ERRORS_UNHANDLED_009_HELP=Number of errors not handled by user code, but by the default error handler.
+
+ASPNET_ERRORS_UNHANDLED_RATE_009_NAME=Errors Unhandled During Execution/Sec
+ASPNET_ERRORS_UNHANDLED_RATE_009_HELP=Rate of unhandled errors.
+
+ASPNET_ERRORS_TOTAL_009_NAME=Errors Total
+ASPNET_ERRORS_TOTAL_009_HELP=Total number of errors occurred.
+
+ASPNET_ERRORS_TOTAL_RATE_009_NAME=Errors Total/Sec
+ASPNET_ERRORS_TOTAL_RATE_009_HELP=Rate of errors occurred.
+
+ASPNET_PIPELINES_009_NAME=Pipeline Instance Count
+ASPNET_PIPELINES_009_HELP=Number of active pipeline instances.
+
+ASPNET_REQUEST_BYTES_IN_009_NAME=Request Bytes In Total
+ASPNET_REQUEST_BYTES_IN_009_HELP=The total size, in bytes, of all requests.
+
+ASPNET_REQUEST_BYTES_OUT_009_NAME=Request Bytes Out Total
+ASPNET_REQUEST_BYTES_OUT_009_HELP=The total size, in bytes, of responses sent to a client. This does not include standard HTTP response headers.
+
+ASPNET_REQUESTS_EXECUTING_009_NAME=Requests Executing
+ASPNET_REQUESTS_EXECUTING_009_HELP=The number of requests currently executing.
+
+ASPNET_REQUESTS_FAILED_009_NAME=Requests Failed
+ASPNET_REQUESTS_FAILED_009_HELP=Total number of failed requests.
+
+ASPNET_REQUESTS_NOT_FOUND_009_NAME=Requests Not Found
+ASPNET_REQUESTS_NOT_FOUND_009_HELP=The number of requests for resources that were not found.
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_NAME=Requests Not Authorized
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_HELP=Number of requests failed due to unauthorized access.
+
+ASPNET_REQUESTS_TIMED_OUT_009_NAME=Requests Timed Out
+ASPNET_REQUESTS_TIMED_OUT_009_HELP=The number of requests that timed out.
+
+ASPNET_REQUESTS_SUCCEDED_009_NAME=Requests Succeeded
+ASPNET_REQUESTS_SUCCEDED_009_HELP=The number of requests that executed successfully.
+
+ASPNET_REQUESTS_TOTAL_009_NAME=Requests Total
+ASPNET_REQUESTS_TOTAL_009_HELP=The total number of requests since the application was started.
+
+ASPNET_REQUESTS_TOTAL_RATE_009_NAME=Requests/Sec
+ASPNET_REQUESTS_TOTAL_RATE_009_HELP=The number of requests executed per second.
+
+ASPNET_SESSIONS_ACTIVE_009_NAME=Sessions Active
+ASPNET_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_SESSIONS_ABANDONED_009_NAME=Sessions Abandoned
+ASPNET_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_SESSIONS_TIMED_OUT_009_NAME=Sessions Timed Out
+ASPNET_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_SESSIONS_TOTAL_009_NAME=Sessions Total
+ASPNET_SESSIONS_TOTAL_009_HELP=Total number of sessions since the application was started.
+
+ASPNET_TRANSACTIONS_ABORTED_009_NAME=Transactions Aborted
+ASPNET_TRANSACTIONS_ABORTED_009_HELP=The number of transactions aborted.
+
+ASPNET_TRANSACTIONS_COMMITTED_009_NAME=Transactions Committed
+ASPNET_TRANSACTIONS_COMMITTED_009_HELP=The number of transactions committed.
+
+ASPNET_TRANSACTIONS_PENDING_009_NAME=Transactions Pending
+ASPNET_TRANSACTIONS_PENDING_009_HELP=Number of transactions in progress.
+
+ASPNET_TRANSACTIONS_TOTAL_009_NAME=Transactions Total
+ASPNET_TRANSACTIONS_TOTAL_009_HELP=The total number of transactions since the application was started.
+
+ASPNET_TRANSACTIONS_RATE_009_NAME=Transactions/Sec
+ASPNET_TRANSACTIONS_RATE_009_HELP=Transactions started per second.
+
+;;
+;;
+;;
+
+OBJECT_1_007_NAME=ASP.NET v1.0.3620.0
+OBJECT_1_007_HELP=Globale Leistungsindikatoren fr ASP.NET v1.0.3620.0
+OBJECT_2_007_NAME=ASP.NET Apps v1.0.3620.0
+OBJECT_2_007_HELP=Programmleistungsindikatoren fr ASP.NET v1.0.3620.0
+
+;;
+;; ASP.NET System Counters
+;;
+
+ASPNET_APPLICATION_RESTARTS_007_NAME=Anwendungsneustarts
+ASPNET_APPLICATION_RESTARTS_007_HELP=Gibt an, wie oft die Anwendung whrend der Gltigkeitsdauer des Webservers neu gestartet wurde.
+
+ASPNET_APPLICATIONS_RUNNING_007_NAME=Ausgefhrte Anwendungen
+ASPNET_APPLICATIONS_RUNNING_007_HELP=Die Anzahl der Webanwendungen, die momentan ausgefhrt werden.
+
+ASPNET_REQUESTS_DISCONNECTED_007_NAME=Getrennte Anforderungen
+ASPNET_REQUESTS_DISCONNECTED_007_HELP=Die Anzahl der Anforderungen, die aufgrund von Kommunikationsfehlern oder vom Benutzer getrennt wurden.
+
+ASPNET_REQUEST_EXECUTION_TIME_007_NAME=Ausfhrungszeit der Anforderung
+ASPNET_REQUEST_EXECUTION_TIME_007_HELP=Die Zeitdauer zum Ausfhren der letzten Anforderung in Millisekunden.
+
+ASPNET_REQUESTS_REJECTED_007_NAME=Anforderungen wurden abgelehnt
+ASPNET_REQUESTS_REJECTED_007_HELP=Die Anzahl der abgelehnten Anforderungen, da die Anforderungsschlange voll war.
+
+ASPNET_REQUESTS_QUEUED_007_NAME=Anforderungen in Warteschlange
+ASPNET_REQUESTS_QUEUED_007_HELP=Die Anzahl der Anforderungen, die auf die Verarbeitung warten.
+
+ASPNET_WPS_RUNNING_007_NAME=Ausgefhrte Workerprozesse
+ASPNET_WPS_RUNNING_007_HELP=Die Anzahl der Workerprozesse, die auf dem Computer ausgefhrt werden.
+
+ASPNET_WPS_RESTARTS_007_NAME=Workerprozess-Neustarts
+ASPNET_WPS_RESTARTS_007_HELP=Gibt an, wie oft ein Workerprozess auf dem Computer neu gestartet wurde.
+
+ASPNET_REQUEST_WAIT_TIME_007_NAME=Wartezeit der Anforderung
+ASPNET_REQUEST_WAIT_TIME_007_HELP=Die Anzahl der Millisekunden, die die letzte Anforderung in der Warteschlange wartete.
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_007_NAME=Aktive Statusserversitzungen
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_007_HELP=Die Anzahl der Sitzungen, die momentan aktive sind.
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_007_NAME=Abgebrochene Statusserversitzungen
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_007_HELP=Die Anzahl der Sitzungen, die explizit abgebrochen wurden.
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_007_NAME=Abgelaufene Statusserversitzungen
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_007_HELP=Anzahl der Sitzungen mit Zeitberschreitung
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_007_NAME=Statusserversitzungen insgesamt
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_007_HELP=Gesamtanzahl der Sitzungen.
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_007_NAME=Anonyme Anforderungen
+ASPNET_ANONYMOUS_REQUESTS_007_HELP=Die Anzahl der Anforderungen, die anonyme Authentifizierung verwenden.
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_007_NAME=Anonyme Anforderungen/Sek.
+ASPNET_ANONYMOUS_REQUESTS_RATE_007_HELP=Die Anzahl der Anforderungen mit anonymer Authentifizierung pro Sekunde.
+
+ASPNET_TOTAL_CACHE_ENTRIES_007_NAME=Cacheeintrge gesamt
+ASPNET_TOTAL_CACHE_ENTRIES_007_HELP=Die Gesamtzahl der Cacheeintrge (intern und von Benutzer hinzugefgt).
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_007_NAME=Gesamte Cacheturnoverrate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_007_HELP=Anzahl der Hinzufge- und Lschvorgnge im gesamten Cache pro Sekunde.
+
+ASPNET_TOTAL_CACHE_HITS_007_NAME=Cachetreffer gesamt
+ASPNET_TOTAL_CACHE_HITS_007_HELP=Die Gesamtzahl der Cachetreffer.
+
+ASPNET_TOTAL_CACHE_MISSES_007_NAME=Fehlgeschlagene Cachezugriffe gesamt
+ASPNET_TOTAL_CACHE_MISSES_007_HELP=Die Gesamtzahl der fehlgeschlagenen Cachezugriffe.
+
+ASPNET_TOTAL_CACHE_RATIO_007_NAME=Cache-Trefferrate gesamt
+ASPNET_TOTAL_CACHE_RATIO_007_HELP=Die Trefferrate aller Cacheaufrufe.
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_007_NAME=Cache-Trefferrate gesamt (Basis)
+ASPNET_TOTAL_CACHE_RATIO_BASE_007_HELP=Cache-Trefferrate gesamt (Basis)
+
+ASPNET_API_CACHE_ENTRIES_007_NAME=Cache-API-Eintrge
+ASPNET_API_CACHE_ENTRIES_007_HELP=Die Gesamtzahl der Cacheeintrge, die vom Benutzer hinzugefgt wurden.
+
+ASPNET_API_CACHE_TURNOVER_RATE_007_NAME=Turnoverrate fr Cache-API
+ASPNET_API_CACHE_TURNOVER_RATE_007_HELP=Anzahl der Hinzufge- und Lschvorgnge im API-Cache pro Sekunde.
+
+ASPNET_API_CACHE_HITS_007_NAME=Cache-API-Treffer
+ASPNET_API_CACHE_HITS_007_HELP=Die Anzahl der Cachetreffer vom Benutzercode aus.
+
+ASPNET_API_CACHE_MISSES_007_NAME=Fehlgeschlagene Cache-API-Zugriffe
+ASPNET_API_CACHE_MISSES_007_HELP=Die Anzahl der fehlgeschlagenen Cachezugriffe, die vom Benutzercode aus aufgerufen wurden.
+
+ASPNET_API_CACHE_RATIO_007_NAME=Cache-API-Trefferrate
+ASPNET_API_CACHE_RATIO_007_HELP=Die Trefferrate der Benutzercodeaufrufe.
+
+ASPNET_API_CACHE_RATIO_BASE_007_NAME=API-Cache-Trefferrate (Basis)
+ASPNET_API_CACHE_RATIO_BASE_007_HELP=API-Cache-Trefferrate (Basis)
+
+ASPNET_OUTPUT_CACHE_ENTRIES_007_NAME=Ausgabecacheeintrge
+ASPNET_OUTPUT_CACHE_ENTRIES_007_HELP=Die aktuelle Anzahl der Eintrge im Ausgabecache.
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_007_NAME=Turnoverrate fr den Ausgabecache
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_007_HELP=Anzahl der Hinzufge- und Lschvorgnge im Ausgabecache pro Sekunde.
+
+ASPNET_OUTPUT_CACHE_HITS_007_NAME=Ausgabecachetreffer
+ASPNET_OUTPUT_CACHE_HITS_007_HELP=Die Gesamtanzahl der zwischenspeicherbaren Anforderungen, die vom Ausgabecache beantwortet werden.
+
+ASPNET_OUTPUT_CACHE_MISSES_007_NAME=Fehlgeschlagene Ausgabecache-Zugriffe
+ASPNET_OUTPUT_CACHE_MISSES_007_HELP=Die Gesamtanzahl der zwischenspeicherbaren Anforderungen, die nicht vom Ausgabecache beantwortet werden.
+
+ASPNET_OUTPUT_CACHE_RATIO_007_NAME=Ausgabecache-Trefferrate
+ASPNET_OUTPUT_CACHE_RATIO_007_HELP=Trefferrate der zwischenspeicherbaren Ausgabeanforderungen.
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_007_NAME=Ausgabecache-Trefferrate
+ASPNET_OUTPUT_CACHE_RATIO_BASE_007_HELP=Ausgabecache-Trefferrate
+
+ASPNET_COMPILATIONS_007_NAME=Kompilierungen insgesamt
+ASPNET_COMPILATIONS_007_HELP=Die Anzahl der dynamisch kompilierten Quelldateien .asax, .ascx, .ashx, .asmx oder .aspx.
+
+ASPNET_DEBUGGING_REQUESTS_007_NAME=Debug-Anforderungen
+ASPNET_DEBUGGING_REQUESTS_007_HELP=Die Anzahl der Debug-Anforderungen, die verarbeitet wurden.
+
+ASPNET_ERRORS_PRE_PROCESSING_007_NAME=Fehler bei der Vorverarbeitung
+ASPNET_ERRORS_PRE_PROCESSING_007_HELP=Die Anzahl der Fehler, die beim Analysieren und Konfigurieren aufgetreten sind.
+
+ASPNET_ERRORS_COMPILING_007_NAME=Fehler bei der Kompilierung
+ASPNET_ERRORS_COMPILING_007_HELP=Die Anzahl der Fehler, die beim Kompilieren aufgetreten sind.
+
+ASPNET_ERRORS_DURING_REQUEST_007_NAME=Fehler beim Ausfhren
+ASPNET_ERRORS_DURING_REQUEST_007_HELP=Die Anzahl der Fehler, die beim Verarbeiten einer Anforderung aufgetreten sind.
+
+ASPNET_ERRORS_UNHANDLED_007_NAME=Unbehandelte Fehler beim Ausfhren
+ASPNET_ERRORS_UNHANDLED_007_HELP=Die Anzahl der Fehler, die nicht vom Benutzercode verarbeitet wurden, sondern vom Standardfehlerhandler.
+
+ASPNET_ERRORS_UNHANDLED_RATE_007_NAME=Unbehandelte Fehler whrend der Ausfhrung pro Sekunde
+ASPNET_ERRORS_UNHANDLED_RATE_007_HELP=Rate der unbehandelten Fehler.
+
+ASPNET_ERRORS_TOTAL_007_NAME=Fehler gesamt
+ASPNET_ERRORS_TOTAL_007_HELP=Anzahl der aufgetretenen Fehler.
+
+ASPNET_ERRORS_TOTAL_RATE_007_NAME=Fehler gesamt/Sek.
+ASPNET_ERRORS_TOTAL_RATE_007_HELP=Rate der aufgetretenen Fehler.
+
+ASPNET_PIPELINES_007_NAME=Pipeline-Instanzenzahl
+ASPNET_PIPELINES_007_HELP=Die Anzahl der aktiven Pipelineinstanzen.
+
+ASPNET_REQUEST_BYTES_IN_007_NAME=Anforderungsbytes gesamt (einschliel.)
+ASPNET_REQUEST_BYTES_IN_007_HELP=Die Gesamtgre aller Anforderungen in Bytes.
+
+ASPNET_REQUEST_BYTES_OUT_007_NAME=Anforderungsbytes gesamt (ausschliel.)
+ASPNET_REQUEST_BYTES_OUT_007_HELP=Die Gesamtgre aller Antworten in Bytes, die an einen Client gesendet wurden, wobei standardmige HTTP-Antwortheader ausgeschlossen werden.
+
+ASPNET_REQUESTS_EXECUTING_007_NAME=Ausgefhrte Anforderungen
+ASPNET_REQUESTS_EXECUTING_007_HELP=Die Anzahl der Anforderungen, die momentan ausgefhrt werden.
+
+ASPNET_REQUESTS_FAILED_007_NAME=Fehlgeschlagene Anforderungen
+ASPNET_REQUESTS_FAILED_007_HELP=Die Gesamtszahl der fehlgeschlagenen Anforderungen.
+
+ASPNET_REQUESTS_NOT_FOUND_007_NAME=Nicht gefundene Anforderungen
+ASPNET_REQUESTS_NOT_FOUND_007_HELP=Die Anzahl der Anforderungen fr Ressourcen, die nicht gefunden wurden.
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_007_NAME=Nicht berechtigte Anforderungen
+ASPNET_REQUESTS_NOT_AUTHORIZED_007_HELP=Die Anzahl der Anforderungen, die wegen mangelnder Zugriffsberechtigung fehlgeschlagen sind.
+
+ASPNET_REQUESTS_TIMED_OUT_007_NAME=Anforderungen mit Zeitberschreitung
+ASPNET_REQUESTS_TIMED_OUT_007_HELP=Die Anzahl der Anforderungen, deren mit Zeitlimit berschritten wurde.
+
+ASPNET_REQUESTS_SUCCEDED_007_NAME=Erfolgreiche Anforderungen
+ASPNET_REQUESTS_SUCCEDED_007_HELP=Die Anzahl der Anforderungen, die erfolgreich ausgefhrt wurden.
+
+ASPNET_REQUESTS_TOTAL_007_NAME=Anforderungen gesamt
+ASPNET_REQUESTS_TOTAL_007_HELP=Die Gesamtszahl der Anforderungen seit die Anwendung gestartet wurde.
+
+ASPNET_REQUESTS_TOTAL_RATE_007_NAME=Anforderungen/Sek.
+ASPNET_REQUESTS_TOTAL_RATE_007_HELP=Die Anzahl der Anforderungen, die pro Sekunde ausgefhrt werden.
+
+ASPNET_SESSIONS_ACTIVE_007_NAME=Aktive Sitzungen
+ASPNET_SESSIONS_ACTIVE_007_HELP=Die Anzahl der Sitzungen, die momentan aktive sind.
+
+ASPNET_SESSIONS_ABANDONED_007_NAME=Abgebrochene Sitzungen
+ASPNET_SESSIONS_ABANDONED_007_HELP=Die Anzahl der Sitzungen, die explizit abgebrochen wurden.
+
+ASPNET_SESSIONS_TIMED_OUT_007_NAME=Sitzungen mit Zeitberschreitung
+ASPNET_SESSIONS_TIMED_OUT_007_HELP=Anzahl der Sitzungen mit Zeitberschreitung
+
+ASPNET_SESSIONS_TOTAL_007_NAME=Sitzungen gesamt
+ASPNET_SESSIONS_TOTAL_007_HELP=Gesamtanzahl der Sitzungen seit die Anwendung gestartet wurde.
+
+ASPNET_TRANSACTIONS_ABORTED_007_NAME=Abgebrochene Transaktionen
+ASPNET_TRANSACTIONS_ABORTED_007_HELP=Die Anzahl der abgebrochenen Transaktionen.
+
+ASPNET_TRANSACTIONS_COMMITTED_007_NAME=bermittelte Transaktionen
+ASPNET_TRANSACTIONS_COMMITTED_007_HELP=Die Anzahl der Transaktionen, fr die ein Commit ausgefhrt wurde.
+
+ASPNET_TRANSACTIONS_PENDING_007_NAME=Ausstehende Transaktionen
+ASPNET_TRANSACTIONS_PENDING_007_HELP=Die Anzahl der Transaktionen, die sich Bearbeitung befinden.
+
+ASPNET_TRANSACTIONS_TOTAL_007_NAME=Transaktionen gesamt
+ASPNET_TRANSACTIONS_TOTAL_007_HELP=Die Gesamtanzahl der Transaktionen seit die Anwendung gestartet wurde.
+
+ASPNET_TRANSACTIONS_RATE_007_NAME=Transaktionen/Sek
+ASPNET_TRANSACTIONS_RATE_007_HELP=Die Anzahl der Transaktionen, die pro Sekunde gestartet werden.
+
diff --git a/src/inc/1031/aspnet_perf2.ini b/src/inc/1031/aspnet_perf2.ini
new file mode 100644
index 0000000..2e82d22
--- /dev/null
+++ b/src/inc/1031/aspnet_perf2.ini
@@ -0,0 +1,416 @@
+[info]
+drivername=ASP.NET
+symbolfile=aspnet_perf.h
+
+[languages]
+007=German
+009=English
+
+[objects]
+OBJECT_1_009_NAME=ASP.NET
+OBJECT_2_009_NAME=ASP.NET Applications
+
+[text]
+OBJECT_1_009_NAME=ASP.NET
+OBJECT_1_009_HELP=ASP.NET global performance counters
+OBJECT_2_009_NAME=ASP.NET Applications
+OBJECT_2_009_HELP=ASP.NET Application performance counters
+
+;;
+;; ASP.NET System Counters
+;;
+
+ASPNET_APPLICATION_RESTARTS_009_NAME=Application Restarts
+ASPNET_APPLICATION_RESTARTS_009_HELP=Number of times the application has been restarted during the web server's lifetime.
+
+ASPNET_APPLICATIONS_RUNNING_009_NAME=Applications Running
+ASPNET_APPLICATIONS_RUNNING_009_HELP=Number of currently running web applications.
+
+ASPNET_REQUESTS_DISCONNECTED_009_NAME=Requests Disconnected
+ASPNET_REQUESTS_DISCONNECTED_009_HELP=The number of requests disconnected due to communication errors or user terminated.
+
+ASPNET_REQUEST_EXECUTION_TIME_009_NAME=Request Execution Time
+ASPNET_REQUEST_EXECUTION_TIME_009_HELP=The number of milliseconds that it took to execute the most recent request.
+
+ASPNET_REQUESTS_REJECTED_009_NAME=Requests Rejected
+ASPNET_REQUESTS_REJECTED_009_HELP=The number of requests rejected because the request queue was full.
+
+ASPNET_REQUESTS_QUEUED_009_NAME=Requests Queued
+ASPNET_REQUESTS_QUEUED_009_HELP=The number of requests waiting to be processed.
+
+ASPNET_WPS_RUNNING_009_NAME=Worker Processes Running
+ASPNET_WPS_RUNNING_009_HELP=Number of worker processes running on the machine.
+
+ASPNET_WPS_RESTARTS_009_NAME=Worker Process Restarts
+ASPNET_WPS_RESTARTS_009_HELP=Number of times a worker process has restarted on the machine.
+
+ASPNET_REQUEST_WAIT_TIME_009_NAME=Request Wait Time
+ASPNET_REQUEST_WAIT_TIME_009_HELP=The number of milliseconds the most recent request was waiting in the queue.
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_NAME=State Server Sessions Active
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_NAME=State Server Sessions Abandoned
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_NAME=State Server Sessions Timed Out
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_NAME=State Server Sessions Total
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_HELP=The number of sessions total.
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_009_NAME=Anonymous Requests
+ASPNET_ANONYMOUS_REQUESTS_009_HELP=Number of requests utilizing anonymous authentication.
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_NAME=Anonymous Requests/Sec
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_HELP=Number of Authentication Anonymous Requests/Sec
+
+ASPNET_TOTAL_CACHE_ENTRIES_009_NAME=Cache Total Entries
+ASPNET_TOTAL_CACHE_ENTRIES_009_HELP=Total number of entries within the cache (both internal and user added)
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_NAME=Cache Total Turnover Rate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the total cache per second.
+
+ASPNET_TOTAL_CACHE_HITS_009_NAME=Cache Total Hits
+ASPNET_TOTAL_CACHE_HITS_009_HELP=Total number of hits from the cache.
+
+ASPNET_TOTAL_CACHE_MISSES_009_NAME=Cache Total Misses
+ASPNET_TOTAL_CACHE_MISSES_009_HELP=Total number of cache misses.
+
+ASPNET_TOTAL_CACHE_RATIO_009_NAME=Cache Total Hit Ratio
+ASPNET_TOTAL_CACHE_RATIO_009_HELP=Ratio of hits from all cache calls.
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_NAME=Cache Total Hit Ratio Base
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_HELP=Cache Total Hit Ratio Base
+
+ASPNET_API_CACHE_ENTRIES_009_NAME=Cache API Entries
+ASPNET_API_CACHE_ENTRIES_009_HELP=Total number of entries within the cache added by the user.
+
+ASPNET_API_CACHE_TURNOVER_RATE_009_NAME=Cache API Turnover Rate
+ASPNET_API_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the API cache per second.
+
+ASPNET_API_CACHE_HITS_009_NAME=Cache API Hits
+ASPNET_API_CACHE_HITS_009_HELP=Number of cache hits from user code.
+
+ASPNET_API_CACHE_MISSES_009_NAME=Cache API Misses
+ASPNET_API_CACHE_MISSES_009_HELP=Number of cache misses called from user code.
+
+ASPNET_API_CACHE_RATIO_009_NAME=Cache API Hit Ratio
+ASPNET_API_CACHE_RATIO_009_HELP=Ratio of hits called from user code.
+
+ASPNET_API_CACHE_RATIO_BASE_009_NAME=Cache API Hit Ratio Base
+ASPNET_API_CACHE_RATIO_BASE_009_HELP=Cache API Hit Ratio Base
+
+ASPNET_OUTPUT_CACHE_ENTRIES_009_NAME=Output Cache Entries
+ASPNET_OUTPUT_CACHE_ENTRIES_009_HELP=Current number of entries in the output cache.
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_NAME=Output Cache Turnover Rate
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the output cache per second.
+
+ASPNET_OUTPUT_CACHE_HITS_009_NAME=Output Cache Hits
+ASPNET_OUTPUT_CACHE_HITS_009_HELP=Total number of ouput cacheable requests served from the output cache.
+
+ASPNET_OUTPUT_CACHE_MISSES_009_NAME=Output Cache Misses
+ASPNET_OUTPUT_CACHE_MISSES_009_HELP=Total number of ouput cacheable requests not served from the output cache.
+
+ASPNET_OUTPUT_CACHE_RATIO_009_NAME=Output Cache Hit Ratio
+ASPNET_OUTPUT_CACHE_RATIO_009_HELP=Ratio of hits to requests for output cacheable requests.
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_NAME=Output Cache Hit Ratio Base
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_HELP=Output Cache Hit Ratio Base
+
+ASPNET_COMPILATIONS_009_NAME=Compilations Total
+ASPNET_COMPILATIONS_009_HELP=Number of .asax, .ascx, .ashx, .asmx, or .aspx source files dynamically compiled.
+
+ASPNET_DEBUGGING_REQUESTS_009_NAME=Debugging Requests
+ASPNET_DEBUGGING_REQUESTS_009_HELP=Number of debugging requests processed.
+
+ASPNET_ERRORS_PRE_PROCESSING_009_NAME=Errors During Preprocessing
+ASPNET_ERRORS_PRE_PROCESSING_009_HELP=Number of errors that have occurred during parsing and configuration.
+
+ASPNET_ERRORS_COMPILING_009_NAME=Errors During Compilation
+ASPNET_ERRORS_COMPILING_009_HELP=Number of errors that have occurred during compilation.
+
+ASPNET_ERRORS_DURING_REQUEST_009_NAME=Errors During Execution
+ASPNET_ERRORS_DURING_REQUEST_009_HELP=Number of errors that have occurred during the processing of a request.
+
+ASPNET_ERRORS_UNHANDLED_009_NAME=Errors Unhandled During Execution
+ASPNET_ERRORS_UNHANDLED_009_HELP=Number of errors not handled by user code, but by the default error handler.
+
+ASPNET_ERRORS_UNHANDLED_RATE_009_NAME=Errors Unhandled During Execution/Sec
+ASPNET_ERRORS_UNHANDLED_RATE_009_HELP=Rate of unhandled errors.
+
+ASPNET_ERRORS_TOTAL_009_NAME=Errors Total
+ASPNET_ERRORS_TOTAL_009_HELP=Total number of errors occurred.
+
+ASPNET_ERRORS_TOTAL_RATE_009_NAME=Errors Total/Sec
+ASPNET_ERRORS_TOTAL_RATE_009_HELP=Rate of errors occurred.
+
+ASPNET_PIPELINES_009_NAME=Pipeline Instance Count
+ASPNET_PIPELINES_009_HELP=Number of active pipeline instances.
+
+ASPNET_REQUEST_BYTES_IN_009_NAME=Request Bytes In Total
+ASPNET_REQUEST_BYTES_IN_009_HELP=The total size, in bytes, of all requests.
+
+ASPNET_REQUEST_BYTES_OUT_009_NAME=Request Bytes Out Total
+ASPNET_REQUEST_BYTES_OUT_009_HELP=The total size, in bytes, of responses sent to a client. This does not include standard HTTP response headers.
+
+ASPNET_REQUESTS_EXECUTING_009_NAME=Requests Executing
+ASPNET_REQUESTS_EXECUTING_009_HELP=The number of requests currently executing.
+
+ASPNET_REQUESTS_FAILED_009_NAME=Requests Failed
+ASPNET_REQUESTS_FAILED_009_HELP=Total number of failed requests.
+
+ASPNET_REQUESTS_NOT_FOUND_009_NAME=Requests Not Found
+ASPNET_REQUESTS_NOT_FOUND_009_HELP=The number of requests for resources that were not found.
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_NAME=Requests Not Authorized
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_HELP=Number of requests failed due to unauthorized access.
+
+ASPNET_REQUESTS_TIMED_OUT_009_NAME=Requests Timed Out
+ASPNET_REQUESTS_TIMED_OUT_009_HELP=The number of requests that timed out.
+
+ASPNET_REQUESTS_SUCCEDED_009_NAME=Requests Succeeded
+ASPNET_REQUESTS_SUCCEDED_009_HELP=The number of requests that executed successfully.
+
+ASPNET_REQUESTS_TOTAL_009_NAME=Requests Total
+ASPNET_REQUESTS_TOTAL_009_HELP=The total number of requests since the application was started.
+
+ASPNET_REQUESTS_TOTAL_RATE_009_NAME=Requests/Sec
+ASPNET_REQUESTS_TOTAL_RATE_009_HELP=The number of requests executed per second.
+
+ASPNET_SESSIONS_ACTIVE_009_NAME=Sessions Active
+ASPNET_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_SESSIONS_ABANDONED_009_NAME=Sessions Abandoned
+ASPNET_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_SESSIONS_TIMED_OUT_009_NAME=Sessions Timed Out
+ASPNET_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_SESSIONS_TOTAL_009_NAME=Sessions Total
+ASPNET_SESSIONS_TOTAL_009_HELP=Total number of sessions since the application was started.
+
+ASPNET_TRANSACTIONS_ABORTED_009_NAME=Transactions Aborted
+ASPNET_TRANSACTIONS_ABORTED_009_HELP=The number of transactions aborted.
+
+ASPNET_TRANSACTIONS_COMMITTED_009_NAME=Transactions Committed
+ASPNET_TRANSACTIONS_COMMITTED_009_HELP=The number of transactions committed.
+
+ASPNET_TRANSACTIONS_PENDING_009_NAME=Transactions Pending
+ASPNET_TRANSACTIONS_PENDING_009_HELP=Number of transactions in progress.
+
+ASPNET_TRANSACTIONS_TOTAL_009_NAME=Transactions Total
+ASPNET_TRANSACTIONS_TOTAL_009_HELP=The total number of transactions since the application was started.
+
+ASPNET_TRANSACTIONS_RATE_009_NAME=Transactions/Sec
+ASPNET_TRANSACTIONS_RATE_009_HELP=Transactions started per second.
+
+
+;;
+;;
+;;
+
+OBJECT_1_007_NAME=ASP.NET
+OBJECT_1_007_HELP=Globale ASP.NET-Leistungsindikatoren
+OBJECT_2_007_NAME=ASP.NET-Anwendungen
+OBJECT_2_007_HELP=Leistungsindikatoren fr ASP.NET-Anwendungen
+
+;;
+;; ASP.NET System Counters
+;;
+
+ASPNET_APPLICATION_RESTARTS_007_NAME=Anwendungsneustarts
+ASPNET_APPLICATION_RESTARTS_007_HELP=Gibt an, wie oft die Anwendung whrend der Gltigkeitsdauer des Webservers neu gestartet wurde.
+
+ASPNET_APPLICATIONS_RUNNING_007_NAME=Ausgefhrte Anwendungen
+ASPNET_APPLICATIONS_RUNNING_007_HELP=Die Anzahl der Webanwendungen, die momentan ausgefhrt werden.
+
+ASPNET_REQUESTS_DISCONNECTED_007_NAME=Getrennte Anforderungen
+ASPNET_REQUESTS_DISCONNECTED_007_HELP=Die Anzahl der Anforderungen, die aufgrund von Kommunikationsfehlern oder vom Benutzer getrennt wurden.
+
+ASPNET_REQUEST_EXECUTION_TIME_007_NAME=Ausfhrungszeit der Anforderung
+ASPNET_REQUEST_EXECUTION_TIME_007_HELP=Die Zeitdauer zum Ausfhren der letzten Anforderung in Millisekunden.
+
+ASPNET_REQUESTS_REJECTED_007_NAME=Anforderungen wurden abgelehnt
+ASPNET_REQUESTS_REJECTED_007_HELP=Die Anzahl der abgelehnten Anforderungen, da die Anforderungsschlange voll war.
+
+ASPNET_REQUESTS_QUEUED_007_NAME=Anforderungen in Warteschlange
+ASPNET_REQUESTS_QUEUED_007_HELP=Die Anzahl der Anforderungen, die auf die Verarbeitung warten.
+
+ASPNET_WPS_RUNNING_007_NAME=Ausgefhrte Workerprozesse
+ASPNET_WPS_RUNNING_007_HELP=Die Anzahl der Workerprozesse, die auf dem Computer ausgefhrt werden.
+
+ASPNET_WPS_RESTARTS_007_NAME=Workerprozess-Neustarts
+ASPNET_WPS_RESTARTS_007_HELP=Gibt an, wie oft ein Workerprozess auf dem Computer neu gestartet wurde.
+
+ASPNET_REQUEST_WAIT_TIME_007_NAME=Wartezeit der Anforderung
+ASPNET_REQUEST_WAIT_TIME_007_HELP=Die Anzahl der Millisekunden, die die letzte Anforderung in der Warteschlange wartete.
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_007_NAME=Aktive Statusserversitzungen
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_007_HELP=Die Anzahl der Sitzungen, die momentan aktive sind.
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_007_NAME=Abgebrochene Statusserversitzungen
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_007_HELP=Die Anzahl der Sitzungen, die explizit abgebrochen wurden.
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_007_NAME=Abgelaufene Statusserversitzungen
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_007_HELP=Anzahl der Sitzungen mit Zeitberschreitung
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_007_NAME=Statusserversitzungen insgesamt
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_007_HELP=Gesamtanzahl der Sitzungen.
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_007_NAME=Anonyme Anforderungen
+ASPNET_ANONYMOUS_REQUESTS_007_HELP=Die Anzahl der Anforderungen, die anonyme Authentifizierung verwenden.
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_007_NAME=Anonyme Anforderungen/Sek.
+ASPNET_ANONYMOUS_REQUESTS_RATE_007_HELP=Die Anzahl der Anforderungen mit anonymer Authentifizierung pro Sekunde.
+
+ASPNET_TOTAL_CACHE_ENTRIES_007_NAME=Cacheeintrge gesamt
+ASPNET_TOTAL_CACHE_ENTRIES_007_HELP=Die Gesamtzahl der Cacheeintrge (intern und von Benutzer hinzugefgt).
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_007_NAME=Gesamte Cacheturnoverrate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_007_HELP=Anzahl der Hinzufge- und Lschvorgnge im gesamten Cache pro Sekunde.
+
+ASPNET_TOTAL_CACHE_HITS_007_NAME=Cachetreffer gesamt
+ASPNET_TOTAL_CACHE_HITS_007_HELP=Die Gesamtzahl der Cachetreffer.
+
+ASPNET_TOTAL_CACHE_MISSES_007_NAME=Fehlgeschlagene Cachezugriffe gesamt
+ASPNET_TOTAL_CACHE_MISSES_007_HELP=Die Gesamtzahl der fehlgeschlagenen Cachezugriffe.
+
+ASPNET_TOTAL_CACHE_RATIO_007_NAME=Cache-Trefferrate gesamt
+ASPNET_TOTAL_CACHE_RATIO_007_HELP=Die Trefferrate aller Cacheaufrufe.
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_007_NAME=Cache-Trefferrate gesamt (Basis)
+ASPNET_TOTAL_CACHE_RATIO_BASE_007_HELP=Cache-Trefferrate gesamt (Basis)
+
+ASPNET_API_CACHE_ENTRIES_007_NAME=Cache-API-Eintrge
+ASPNET_API_CACHE_ENTRIES_007_HELP=Die Gesamtzahl der Cacheeintrge, die vom Benutzer hinzugefgt wurden.
+
+ASPNET_API_CACHE_TURNOVER_RATE_007_NAME=Turnoverrate fr Cache-API
+ASPNET_API_CACHE_TURNOVER_RATE_007_HELP=Anzahl der Hinzufge- und Lschvorgnge im API-Cache pro Sekunde.
+
+ASPNET_API_CACHE_HITS_007_NAME=Cache-API-Treffer
+ASPNET_API_CACHE_HITS_007_HELP=Die Anzahl der Cachetreffer vom Benutzercode aus.
+
+ASPNET_API_CACHE_MISSES_007_NAME=Fehlgeschlagene Cache-API-Zugriffe
+ASPNET_API_CACHE_MISSES_007_HELP=Die Anzahl der fehlgeschlagenen Cachezugriffe, die vom Benutzercode aus aufgerufen wurden.
+
+ASPNET_API_CACHE_RATIO_007_NAME=Cache-API-Trefferrate
+ASPNET_API_CACHE_RATIO_007_HELP=Die Trefferrate der Benutzercodeaufrufe.
+
+ASPNET_API_CACHE_RATIO_BASE_007_NAME=API-Cache-Trefferrate (Basis)
+ASPNET_API_CACHE_RATIO_BASE_007_HELP=API-Cache-Trefferrate (Basis)
+
+ASPNET_OUTPUT_CACHE_ENTRIES_007_NAME=Ausgabecacheeintrge
+ASPNET_OUTPUT_CACHE_ENTRIES_007_HELP=Die aktuelle Anzahl der Eintrge im Ausgabecache.
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_007_NAME=Turnoverrate fr den Ausgabecache
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_007_HELP=Anzahl der Hinzufge- und Lschvorgnge im Ausgabecache pro Sekunde.
+
+ASPNET_OUTPUT_CACHE_HITS_007_NAME=Ausgabecachetreffer
+ASPNET_OUTPUT_CACHE_HITS_007_HELP=Die Gesamtanzahl der zwischenspeicherbaren Anforderungen, die vom Ausgabecache beantwortet werden.
+
+ASPNET_OUTPUT_CACHE_MISSES_007_NAME=Fehlgeschlagene Ausgabecache-Zugriffe
+ASPNET_OUTPUT_CACHE_MISSES_007_HELP=Die Gesamtanzahl der zwischenspeicherbaren Anforderungen, die nicht vom Ausgabecache beantwortet werden.
+
+ASPNET_OUTPUT_CACHE_RATIO_007_NAME=Ausgabecache-Trefferrate
+ASPNET_OUTPUT_CACHE_RATIO_007_HELP=Trefferrate der zwischenspeicherbaren Ausgabeanforderungen.
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_007_NAME=Ausgabecache-Trefferrate
+ASPNET_OUTPUT_CACHE_RATIO_BASE_007_HELP=Ausgabecache-Trefferrate
+
+ASPNET_COMPILATIONS_007_NAME=Kompilierungen insgesamt
+ASPNET_COMPILATIONS_007_HELP=Die Anzahl der dynamisch kompilierten Quelldateien .asax, .ascx, .ashx, .asmx oder .aspx.
+
+ASPNET_DEBUGGING_REQUESTS_007_NAME=Debug-Anforderungen
+ASPNET_DEBUGGING_REQUESTS_007_HELP=Die Anzahl der Debug-Anforderungen, die verarbeitet wurden.
+
+ASPNET_ERRORS_PRE_PROCESSING_007_NAME=Fehler bei der Vorverarbeitung
+ASPNET_ERRORS_PRE_PROCESSING_007_HELP=Die Anzahl der Fehler, die beim Analysieren und Konfigurieren aufgetreten sind.
+
+ASPNET_ERRORS_COMPILING_007_NAME=Fehler bei der Kompilierung
+ASPNET_ERRORS_COMPILING_007_HELP=Die Anzahl der Fehler, die beim Kompilieren aufgetreten sind.
+
+ASPNET_ERRORS_DURING_REQUEST_007_NAME=Fehler beim Ausfhren
+ASPNET_ERRORS_DURING_REQUEST_007_HELP=Die Anzahl der Fehler, die beim Verarbeiten einer Anforderung aufgetreten sind.
+
+ASPNET_ERRORS_UNHANDLED_007_NAME=Unbehandelte Fehler beim Ausfhren
+ASPNET_ERRORS_UNHANDLED_007_HELP=Die Anzahl der Fehler, die nicht vom Benutzercode verarbeitet wurden, sondern vom Standardfehlerhandler.
+
+ASPNET_ERRORS_UNHANDLED_RATE_007_NAME=Unbehandelte Fehler whrend der Ausfhrung pro Sekunde
+ASPNET_ERRORS_UNHANDLED_RATE_007_HELP=Rate der unbehandelten Fehler.
+
+ASPNET_ERRORS_TOTAL_007_NAME=Fehler gesamt
+ASPNET_ERRORS_TOTAL_007_HELP=Anzahl der aufgetretenen Fehler.
+
+ASPNET_ERRORS_TOTAL_RATE_007_NAME=Fehler gesamt/Sek.
+ASPNET_ERRORS_TOTAL_RATE_007_HELP=Rate der aufgetretenen Fehler.
+
+ASPNET_PIPELINES_007_NAME=Pipeline-Instanzenzahl
+ASPNET_PIPELINES_007_HELP=Die Anzahl der aktiven Pipelineinstanzen.
+
+ASPNET_REQUEST_BYTES_IN_007_NAME=Anforderungsbytes gesamt (einschliel.)
+ASPNET_REQUEST_BYTES_IN_007_HELP=Die Gesamtgre aller Anforderungen in Bytes.
+
+ASPNET_REQUEST_BYTES_OUT_007_NAME=Anforderungsbytes gesamt (ausschliel.)
+ASPNET_REQUEST_BYTES_OUT_007_HELP=Die Gesamtgre aller Antworten in Bytes, die an einen Client gesendet wurden, wobei standardmige HTTP-Antwortheader ausgeschlossen werden.
+
+ASPNET_REQUESTS_EXECUTING_007_NAME=Ausgefhrte Anforderungen
+ASPNET_REQUESTS_EXECUTING_007_HELP=Die Anzahl der Anforderungen, die momentan ausgefhrt werden.
+
+ASPNET_REQUESTS_FAILED_007_NAME=Fehlgeschlagene Anforderungen
+ASPNET_REQUESTS_FAILED_007_HELP=Die Gesamtszahl der fehlgeschlagenen Anforderungen.
+
+ASPNET_REQUESTS_NOT_FOUND_007_NAME=Nicht gefundene Anforderungen
+ASPNET_REQUESTS_NOT_FOUND_007_HELP=Die Anzahl der Anforderungen fr Ressourcen, die nicht gefunden wurden.
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_007_NAME=Nicht berechtigte Anforderungen
+ASPNET_REQUESTS_NOT_AUTHORIZED_007_HELP=Die Anzahl der Anforderungen, die wegen mangelnder Zugriffsberechtigung fehlgeschlagen sind.
+
+ASPNET_REQUESTS_TIMED_OUT_007_NAME=Anforderungen mit Zeitberschreitung
+ASPNET_REQUESTS_TIMED_OUT_007_HELP=Die Anzahl der Anforderungen, deren mit Zeitlimit berschritten wurde.
+
+ASPNET_REQUESTS_SUCCEDED_007_NAME=Erfolgreiche Anforderungen
+ASPNET_REQUESTS_SUCCEDED_007_HELP=Die Anzahl der Anforderungen, die erfolgreich ausgefhrt wurden.
+
+ASPNET_REQUESTS_TOTAL_007_NAME=Anforderungen gesamt
+ASPNET_REQUESTS_TOTAL_007_HELP=Die Gesamtszahl der Anforderungen seit die Anwendung gestartet wurde.
+
+ASPNET_REQUESTS_TOTAL_RATE_007_NAME=Anforderungen/Sek.
+ASPNET_REQUESTS_TOTAL_RATE_007_HELP=Die Anzahl der Anforderungen, die pro Sekunde ausgefhrt werden.
+
+ASPNET_SESSIONS_ACTIVE_007_NAME=Aktive Sitzungen
+ASPNET_SESSIONS_ACTIVE_007_HELP=Die Anzahl der Sitzungen, die momentan aktive sind.
+
+ASPNET_SESSIONS_ABANDONED_007_NAME=Abgebrochene Sitzungen
+ASPNET_SESSIONS_ABANDONED_007_HELP=Die Anzahl der Sitzungen, die explizit abgebrochen wurden.
+
+ASPNET_SESSIONS_TIMED_OUT_007_NAME=Sitzungen mit Zeitberschreitung
+ASPNET_SESSIONS_TIMED_OUT_007_HELP=Anzahl der Sitzungen mit Zeitberschreitung
+
+ASPNET_SESSIONS_TOTAL_007_NAME=Sitzungen gesamt
+ASPNET_SESSIONS_TOTAL_007_HELP=Gesamtanzahl der Sitzungen seit die Anwendung gestartet wurde.
+
+ASPNET_TRANSACTIONS_ABORTED_007_NAME=Abgebrochene Transaktionen
+ASPNET_TRANSACTIONS_ABORTED_007_HELP=Die Anzahl der abgebrochenen Transaktionen.
+
+ASPNET_TRANSACTIONS_COMMITTED_007_NAME=bermittelte Transaktionen
+ASPNET_TRANSACTIONS_COMMITTED_007_HELP=Die Anzahl der Transaktionen, fr die ein Commit ausgefhrt wurde.
+
+ASPNET_TRANSACTIONS_PENDING_007_NAME=Ausstehende Transaktionen
+ASPNET_TRANSACTIONS_PENDING_007_HELP=Die Anzahl der Transaktionen, die sich Bearbeitung befinden.
+
+ASPNET_TRANSACTIONS_TOTAL_007_NAME=Transaktionen gesamt
+ASPNET_TRANSACTIONS_TOTAL_007_HELP=Die Gesamtanzahl der Transaktionen seit die Anwendung gestartet wurde.
+
+ASPNET_TRANSACTIONS_RATE_007_NAME=Transaktionen/Sek
+ASPNET_TRANSACTIONS_RATE_007_HELP=Die Anzahl der Transaktionen, die pro Sekunde gestartet werden.
+
diff --git a/src/inc/1041/CORPerfMonSymbols.ini b/src/inc/1041/CORPerfMonSymbols.ini
new file mode 100644
index 0000000..b982b2d
--- /dev/null
+++ b/src/inc/1041/CORPerfMonSymbols.ini
@@ -0,0 +1,577 @@
+; Licensed to the .NET Foundation under one or more agreements.
+; The .NET Foundation licenses this file to you under the MIT license.
+; See the LICENSE file in the project root for more information.
+
+//------------------------------------------------------------------------
+// WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
+//
+// AUTO GENERATED FILE. DO NOT EDIT. USE $/com99/src/profile/perfmonhelp
+//
+// WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
+//------------------------------------------------------------------------
+
+// CORPerfMonSymbols.ini file
+[info]
+drivername=.NETFramework
+symbolfile=CORPerfMonSymbols.h
+
+[languages]
+009=English
+011=Japanese
+; 001=Arabic
+; 004=Chinese
+; 007=German
+; 00D=Hebrew
+; 011=Japanese
+; 012=Korean
+; 00A=Spanish
+; 00C=French
+; 010=Italian
+
+[objects]
+DotNetCLR_Memory_OBJECT_009_NAME=.NET CLR Memory
+DotNetCLR_Loading_OBJECT_009_NAME=.NET CLR Loading
+DotNetCLR_Jit_OBJECT_009_NAME=.NET CLR Jit
+DotNetCLR_Interop_OBJECT_009_NAME=.NET CLR Interop
+DotNetCLR_LocksAndThreads_OBJECT_009_NAME=.NET CLR LocksAndThreads
+DotNetCLR_Security_OBJECT_009_NAME=.NET CLR Security
+DotNetCLR_Remoting_OBJECT_009_NAME=.NET CLR Remoting
+DotNetCLR_Excep_OBJECT_009_NAME=.NET CLR Exceptions
+DotNetCLR_Memory_OBJECT_011_NAME=.NET CLR Memory
+DotNetCLR_Loading_OBJECT_011_NAME=.NET CLR Loading
+DotNetCLR_Jit_OBJECT_011_NAME=.NET CLR Jit
+DotNetCLR_Interop_OBJECT_011_NAME=.NET CLR Interop
+DotNetCLR_LocksAndThreads_OBJECT_011_NAME=.NET CLR LocksAndThreads
+DotNetCLR_Security_OBJECT_011_NAME=.NET CLR Security
+DotNetCLR_Remoting_OBJECT_011_NAME=.NET CLR Remoting
+DotNetCLR_Excep_OBJECT_011_NAME=.NET CLR Exceptions
+
+[text]
+DotNetCLR_Memory_OBJECT_009_NAME=.NET CLR Memory
+DotNetCLR_Memory_OBJECT_009_HELP=Counters for CLR Garbage Collected heap.
+
+GEN0_COLLECTIONS_COUNTER_009_NAME=# Gen 0 Collections
+GEN0_COLLECTIONS_COUNTER_009_HELP=This counter displays the number of times the generation 0 objects (youngest; most recently allocated) are garbage collected (Gen 0 GC) since the start of the application. Gen 0 GC occurs when the available memory in generation 0 is not sufficient to satisfy an allocation request. This counter is incremented at the end of a Gen 0 GC. Higher generation GCs include all lower generation GCs. This counter is explicitly incremented when a higher generation (Gen 1 or Gen 2) GC occurs. _Global_ counter value is not accurate and should be ignored. This counter displays the last observed value.
+
+GEN1_COLLECTIONS_COUNTER_009_NAME=# Gen 1 Collections
+GEN1_COLLECTIONS_COUNTER_009_HELP=This counter displays the number of times the generation 1 objects are garbage collected since the start of the application. The counter is incremented at the end of a Gen 1 GC. Higher generation GCs include all lower generation GCs. This counter is explicitly incremented when a higher generation (Gen 2) GC occurs. _Global_ counter value is not accurate and should be ignored. This counter displays the last observed value.
+
+GEN2_COLLECTIONS_COUNTER_009_NAME=# Gen 2 Collections
+GEN2_COLLECTIONS_COUNTER_009_HELP=This counter displays the number of times the generation 2 objects (older) are garbage collected since the start of the application. The counter is incremented at the end of a Gen 2 GC (also called full GC). _Global_ counter value is not accurate and should be ignored. This counter displays the last observed value.
+
+GEN0_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Memory from Gen 0
+GEN0_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that survive garbage collection (GC) and are promoted from generation 0 to generation 1; objects that are promoted just because they are waiting to be finalized are not included in this counter. This counter displays the value observed at the end of the last GC; its not a cumulative counter.
+
+GEN1_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Memory from Gen 1
+GEN1_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that survive garbage collection (GC) and are promoted from generation 1 to generation 2; objects that are promoted just because they are waiting to be finalized are not included in this counter. This counter displays the value observed at the end of the last GC; its not a cumulative counter. This counter is reset to 0 if the last GC was a Gen 0 GC only.
+
+GEN0_PROMOTION_RATE_009_NAME=Gen 0 Promoted Bytes/Sec
+GEN0_PROMOTION_RATE_009_HELP=This counter displays the bytes per second that are promoted from generation 0 (youngest) to generation 1; objects that are promoted just because they are waiting to be finalized are not included in this counter. Memory is promoted when it survives a garbage collection. This counter was designed as an indicator of relatively long-lived objects being created per sec. This counter displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+GEN1_PROMOTION_RATE_009_NAME=Gen 1 Promoted Bytes/Sec
+GEN1_PROMOTION_RATE_009_HELP=This counter displays the bytes per second that are promoted from generation 1 to generation 2 (oldest); objects that are promoted just because they are waiting to be finalized are not included in this counter. Memory is promoted when it survives a garbage collection. Nothing is promoted from generation 2 since it is the oldest. This counter was designed as an indicator of very long-lived objects being created per sec. This counter displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Finalization-Memory from Gen 0
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that are promoted from generation 0 to generation 1 just because they are waiting to be finalized. This counter displays the value observed at the end of the last GC; its not a cumulative counter.
+
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_009_NAME=Promoted Finalization-Memory from Gen 1
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_009_HELP=This counter displays the bytes of memory that are promoted from generation 1 to generation 2 just because they are waiting to be finalized. This counter displays the value observed at the end of the last GC; its not a cumulative counter. This counter is reset to 0 if the last GC was a Gen 0 GC only.
+
+GEN0_HEAP_SIZE_COUNTER_009_NAME=Gen 0 heap size
+GEN0_HEAP_SIZE_COUNTER_009_HELP=This counter displays the maximum bytes that can be allocated in generation 0 (Gen 0); its does not indicate the current number of bytes allocated in Gen 0. A Gen 0 GC is triggered when the allocations since the last GC exceed this size. The Gen 0 size is tuned by the Garbage Collector and can change during the execution of the application. At the end of a Gen 0 collection the size of the Gen 0 heap is infact 0 bytes; this counter displays the size (in bytes) of allocations that would trigger the next Gen 0 GC. This counter is updated at the end of a GC; its not updated on every allocation.
+
+GEN1_HEAP_SIZE_COUNTER_009_NAME=Gen 1 heap size
+GEN1_HEAP_SIZE_COUNTER_009_HELP=This counter displays the current number of bytes in generation 1 (Gen 1); this counter does not display the maximum size of Gen 1. Objects are not directly allocated in this generation; they are promoted from previous Gen 0 GCs. This counter is updated at the end of a GC; its not updated on every allocation.
+
+GEN2_HEAP_SIZE_COUNTER_009_NAME=Gen 2 heap size
+GEN2_HEAP_SIZE_COUNTER_009_HELP=This counter displays the current number of bytes in generation 2 (Gen 2). Objects are not directly allocated in this generation; they are promoted from Gen 1 during previous Gen 1 GCs. This counter is updated at the end of a GC; its not updated on every allocation.
+
+LARGE_OBJECT_SIZE_COUNTER_009_NAME=Large Object Heap size
+LARGE_OBJECT_SIZE_COUNTER_009_HELP=This counter displays the current size of the Large Object Heap in bytes. Objects greater than 20 KBytes are treated as large objects by the Garbage Collector and are directly allocated in a special heap; they are not promoted through the generations. This counter is updated at the end of a GC; its not updated on every allocation.
+
+SURVIVE_FINALIZE_COUNTER_009_NAME=Finalization Survivors
+SURVIVE_FINALIZE_COUNTER_009_HELP=This counter displays the number of garbage collected objects that survive a collection because they are waiting to be finalized. If these objects hold references to other objects then those objects also survive but are not counted by this counter; the "Promoted Finalization-Memory from Gen 0" and "Promoted Finalization-Memory from Gen 1" counters represent all the memory that survived due to finalization. This counter is not a cumulative counter; its updated at the end of every GC with count of the survivors during that particular GC only. This counter was designed to indicate the extra overhead that the application might incur because of finalization.
+
+NUM_HANDLES_COUNTER_009_NAME=# GC Handles
+NUM_HANDLES_COUNTER_009_HELP=This counter displays the current number of GC Handles in use. GCHandles are handles to resources external to the CLR and the managed environment. Handles occupy small amounts of memory in the GCHeap but potentially expensive unmanaged resources.
+
+ALLOCATION_RATE_COUNTER_009_NAME=Allocated Bytes/sec
+ALLOCATION_RATE_COUNTER_009_HELP=This counter displays the rate of bytes per second allocated on the GC Heap. This counter is updated at the end of every GC; not at each allocation. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+INDUCED_GC_COUNTER_009_NAME=# Induced GC
+INDUCED_GC_COUNTER_009_HELP=This counter displays the peak number of times a garbage collection was performed because of an explicit call to GC.Collect. Its a good practice to let the GC tune the frequency of its collections.
+
+PER_TIME_IN_GC_COUNTER_009_NAME=% Time in GC
+PER_TIME_IN_GC_COUNTER_009_HELP=% Time in GC is the percentage of elapsed time that was spent in performing a garbage collection (GC) since the last GC cycle. This counter is usually an indicator of the work done by the Garbage Collector on behalf of the application to collect and compact memory. This counter is updated only at the end of every GC and the counter value reflects the last observed value; its not an average.
+
+PER_TIME_IN_GC_COUNTER_BASE_009_NAME=Not Displayed
+PER_TIME_IN_GC_COUNTER_BASE_009_HELP=Not Displayed.
+
+TOTAL_HEAP_SIZE_COUNTER_009_NAME=# Bytes in all Heaps
+TOTAL_HEAP_SIZE_COUNTER_009_HELP=This counter is the sum of four other counters; Gen 0 Heap Size; Gen 1 Heap Size; Gen 2 Heap Size and the Large Object Heap Size. This counter indicates the current memory allocated in bytes on the GC Heaps.
+
+TOTAL_COMMITTED_MEM_COUNTER_009_NAME=# Total committed Bytes
+TOTAL_COMMITTED_MEM_COUNTER_009_HELP=This counter displays the amount of virtual memory (in bytes) currently committed by the Garbage Collector. (Committed memory is the physical memory for which space has been reserved on the disk paging file).
+
+TOTAL_RESERVED_MEM_COUNTER_009_NAME=# Total reserved Bytes
+TOTAL_RESERVED_MEM_COUNTER_009_HELP=This counter displays the amount of virtual memory (in bytes) currently reserved by the Garbage Collector. (Reserved memory is the virtual memory space reserved for the application but no disk or main memory pages have been used.)
+
+GC_PINNED_OBJECTS_009_NAME=# of Pinned Objects
+GC_PINNED_OBJECTS_009_HELP=This counter displays the number of pinned objects encountered in the last GC. This counter tracks the pinned objects only in the heaps that were garbage collected e.g. a Gen 0 GC would cause enumeration of pinned objects in the generation 0 heap only. A pinned object is one that the Garbage Collector cannot move in memory.
+
+GC_SINKBLOCKS_009_NAME=# of Sink Blocks in use
+GC_SINKBLOCKS_009_HELP=This counter displays the current number of sync blocks in use. Sync blocks are per-object data structures allocated for storing synchronization information. Sync blocks hold weak references to managed objects and need to be scanned by the Garbage Collector. Sync blocks are not limited to storing synchronization information and can also store COM interop metadata. This counter was designed to indicate performance problems with heavy use of synchronization primitives.
+
+DotNetCLR_Loading_OBJECT_009_NAME=.NET CLR Loading
+DotNetCLR_Loading_OBJECT_009_HELP=Statistics for CLR Class Loader.
+
+LOADING_CLASSES_TOTAL_009_NAME=Total Classes Loaded
+LOADING_CLASSES_TOTAL_009_HELP=This counter displays the cumulative number of classes loaded in all Assemblies since the start of this application.
+
+LOADING_TIME_009_NAME=% Time Loading
+LOADING_TIME_009_HELP=Reserved for future use.
+
+LOADING_ASMSEARCHLEN_009_NAME=Assembly Search Length
+LOADING_ASMSEARCHLEN_009_HELP=Reserved for future use.
+
+LOADING_LOADFAILURES_TOTAL_009_NAME=Total # of Load Failures
+LOADING_LOADFAILURES_TOTAL_009_HELP=This counter displays the peak number of classes that have failed to load since the start of the application. These load failures could be due to many reasons like inadequate security or illegal format. Full details can be found in the profiling services help.
+
+LOADING_LOADFAILURES_INST_009_NAME=Rate of Load Failures
+LOADING_LOADFAILURES_INST_009_HELP=This counter displays the number of classes that failed to load per second. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval. These load failures could be due to many reasons like inadequate security or illegal format. Full details can be found in the profiling services help.
+
+LOADING_HEAPSIZE_009_NAME=Bytes in Loader Heap
+LOADING_HEAPSIZE_009_HELP=This counter displays the current size (in bytes) of the memory committed by the class loader across all AppDomains. (Committed memory is the physical memory for which space has been reserved on the disk paging file.)
+
+LOADING_APPDOMAINS_UNLOADED_TOTAL_009_NAME=Total appdomains unloaded
+LOADING_APPDOMAINS_UNLOADED_TOTAL_009_HELP=This counter displays the total number of AppDomains unloaded since the start of the application. If an AppDomain is loaded and unloaded multiple times this counter would count each of those unloads as separate.
+
+LOADING_APPDOMAINS_UNLOADED_INST_009_NAME=Rate of appdomains unloaded
+LOADING_APPDOMAINS_UNLOADED_INST_009_HELP=This counter displays the number of AppDomains unloaded per second. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+LOADING_CLASSES_CUR_009_NAME=Current Classes Loaded
+LOADING_CLASSES_CUR_009_HELP=This counter displays the current number of classes loaded in all Assemblies.
+
+LOADING_CLASSES_INST_009_NAME=Rate of Classes Loaded
+LOADING_CLASSES_INST_009_HELP=This counter displays the number of classes loaded per second in all Assemblies. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+LOADING_APPDOMAINS_CUR_009_NAME=Current appdomains
+LOADING_APPDOMAINS_CUR_009_HELP=This counter displays the current number of AppDomains loaded in this application. AppDomains (application domains) provide a secure and versatile unit of processing that the CLR can use to provide isolation between applications running in the same process.
+
+LOADING_APPDOMAINS_TOTAL_009_NAME=Total Appdomains
+LOADING_APPDOMAINS_TOTAL_009_HELP=This counter displays the peak number of AppDomains loaded since the start of this application. AppDomains (application domains) provide a secure and versatile unit of processing that the CLR can use to provide isolation between applications running in the same process.
+
+LOADING_APPDOMAINS_INST_009_NAME=Rate of appdomains
+LOADING_APPDOMAINS_INST_009_HELP=This counter displays the number of AppDomains loaded per second. AppDomains (application domains) provide a secure and versatile unit of processing that the CLR can use to provide isolation between applications running in the same process. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+LOADING_ASSEMBLIES_CUR_009_NAME=Current Assemblies
+LOADING_ASSEMBLIES_CUR_009_HELP=This counter displays the current number of Assemblies loaded across all AppDomains in this application. If the Assembly is loaded as domain-neutral from multiple AppDomains then this counter is incremented once only. Assemblies can be loaded as domain-neutral when their code can be shared by all AppDomains or they can be loaded as domain-specific when their code is private to the AppDomain.
+
+LOADING_ASSEMBLIES_TOTAL_009_NAME=Total Assemblies
+LOADING_ASSEMBLIES_TOTAL_009_HELP=This counter displays the total number of Assemblies loaded since the start of this application. If the Assembly is loaded as domain-neutral from multiple AppDomains then this counter is incremented once only. Assemblies can be loaded as domain-neutral when their code can be shared by all AppDomains or they can be loaded as domain-specific when their code is private to the AppDomain.
+
+LOADING_ASSEMBLIES_INST_009_NAME=Rate of Assemblies
+LOADING_ASSEMBLIES_INST_009_HELP=This counter displays the number of Assemblies loaded across all AppDomains per second. If the Assembly is loaded as domain-neutral from multiple AppDomains then this counter is incremented once only. Assemblies can be loaded as domain-neutral when their code can be shared by all AppDomains or they can be loaded as domain-specific when their code is private to the AppDomain. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+DotNetCLR_Jit_OBJECT_009_NAME=.NET CLR Jit
+DotNetCLR_Jit_OBJECT_009_HELP=Stats for CLR Jit.
+
+TOTAL_METHODS_JITTED_009_NAME=# of Methods Jitted
+TOTAL_METHODS_JITTED_009_HELP=This counter displays the total number of methods compiled Just-In-Time (JIT) by the CLR JIT compiler since the start of the application. This counter does not include the pre-jitted methods.
+
+JITTED_IL_CUR_009_NAME=# of IL Bytes Jitted
+JITTED_IL_CUR_009_HELP=This counter displays the total IL bytes jitted since the start of the application. This counter is exactly equivalent to the "Total # of IL Bytes Jitted" counter.
+
+JITTED_IL_TOTAL_009_NAME=Total # of IL Bytes Jitted
+JITTED_IL_TOTAL_009_HELP=This counter displays the total IL bytes jitted since the start of the application. This counter is exactly equivalent to the "# of IL Bytes Jitted" counter.
+
+JITTED_IL_INST_009_NAME=IL Bytes Jitted / sec
+JITTED_IL_INST_009_HELP=This counter displays the rate at which IL bytes are jitted per second. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+JIT_FAILURES_009_NAME=Standard Jit Failures
+JIT_FAILURES_009_HELP=This counter displays the peak number of methods the JIT compiler has failed to JIT since the start of the application. This failure can occur if the IL cannot be verified or if there was an internal error in the JIT compiler.
+
+TIME_IN_JIT_009_NAME=% Time in Jit
+TIME_IN_JIT_009_HELP=This counter displays the percentage of elapsed time spent in JIT compilation since the last JIT compilation phase. This counter is updated at the end of every JIT compilation phase. A JIT compilation phase is the phase when a method and its dependencies are being compiled.
+
+TIME_IN_JIT_BASE_009_NAME=Not Displayed
+TIME_IN_JIT_BASE_009_HELP=Not Displayed.
+
+DotNetCLR_Interop_OBJECT_009_NAME=.NET CLR Interop
+DotNetCLR_Interop_OBJECT_009_HELP=Stats for CLR interop.
+
+CURRENT_CCW_009_NAME=# of CCWs
+CURRENT_CCW_009_HELP=This counter displays the current number of Com-Callable-Wrappers (CCWs). A CCW is a proxy for the .NET managed object being referenced from unmanaged COM client(s). This counter was designed to indicate the number of managed objects being referenced by unmanaged COM code.
+
+CURRENT_STUBS_009_NAME=# of Stubs
+CURRENT_STUBS_009_HELP=This counter displays the current number of stubs created by the CLR. Stubs are responsible for marshalling arguments and return values from managed to unmanaged code and vice versa; during a COM Interop call or PInvoke call.
+
+NUM_MARSHALLING_009_NAME=# of marshalling
+NUM_MARSHALLING_009_HELP=This counter displays the total number of times arguments and return values have been marshaled from managed to unmanaged code and vice versa since the start of the application. This counter is not incremented if the stubs are inlined. (Stubs are responsible for marshalling arguments and return values). Stubs usually get inlined if the marshalling overhead is small.
+
+TOTAL_TLB_IMPORTS_009_NAME=# of TLB imports / sec
+TOTAL_TLB_IMPORTS_009_HELP=Reserved for future use.
+
+TOTAL_TLB_EXPORTS_009_NAME=# of TLB exports / sec
+TOTAL_TLB_EXPORTS_009_HELP=Reserved for future use.
+
+DotNetCLR_LocksAndThreads_OBJECT_009_NAME=.NET CLR LocksAndThreads
+DotNetCLR_LocksAndThreads_OBJECT_009_HELP=Stats for CLR Locks and Threads.
+
+CONTENTION_TOTAL_009_NAME=Total # of Contentions
+CONTENTION_TOTAL_009_HELP=This counter displays the total number of times threads in the CLR have attempted to acquire a managed lock unsuccessfully. Managed locks can be acquired in many ways; by the "lock" statement in C# or by calling System.Monitor.Enter or by using MethodImplOptions.Synchronized custom attribute.
+
+CONTENTION_INST_009_NAME=Contention Rate / sec
+CONTENTION_INST_009_HELP=Rate at which threads in the runtime attempt to acquire a managed lock unsuccessfully. Managed locks can be acquired in many ways; by the "lock" statement in C# or by calling System.Monitor.Enter or by using MethodImplOptions.Synchronized custom attribute.
+
+QUEUE_LENGTH_CUR_009_NAME=Current Queue Length
+QUEUE_LENGTH_CUR_009_HELP=This counter displays the total number of threads currently waiting to acquire some managed lock in the application. This counter is not an average over time; it displays the last observed value.
+
+QUEUE_LENGTH_TOTAL_009_NAME=Queue Length Peak
+QUEUE_LENGTH_TOTAL_009_HELP=This counter displays the total number of threads that waited to acquire some managed lock since the start of the application.
+
+QUEUE_LENGTH_INST_009_NAME=Queue Length / sec
+QUEUE_LENGTH_INST_009_HELP=This counter displays the number of threads per second waiting to acquire some lock in the application. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+CURRENT_LOGICAL_THREADS_009_NAME=# of current logical Threads
+CURRENT_LOGICAL_THREADS_009_HELP=This counter displays the number of current .NET thread objects in the application. A .NET thread object is created either by new System.Threading.Thread or when an unmanaged thread enters the managed environment. This counters maintains the count of both running and stopped threads. This counter is not an average over time; it just displays the last observed value.
+
+CURRENT_PHYSICAL_THREADS_009_NAME=# of current physical Threads
+CURRENT_PHYSICAL_THREADS_009_HELP=This counter displays the number of native OS threads created and owned by the CLR to act as underlying threads for .NET thread objects. This counters value does not include the threads used by the CLR in its internal operations; it is a subset of the threads in the OS process.
+
+RECOGNIZED_THREADS_CUR_009_NAME=# of current recognized threads
+RECOGNIZED_THREADS_CUR_009_HELP=This counter displays the number of threads that are currently recognized by the CLR; they have a corresponding .NET thread object associated with them. These threads are not created by the CLR; they are created outside the CLR but have since run inside the CLR at least once. Only unique threads are tracked; threads with same thread ID re-entering the CLR or recreated after thread exit are not counted twice.
+
+RECOGNIZED_THREADS_TOTAL_009_NAME=# of total recognized threads
+RECOGNIZED_THREADS_TOTAL_009_HELP=This counter displays the total number of threads that have been recognized by the CLR since the start of this application; these threads have a corresponding .NET thread object associated with them. These threads are not created by the CLR; they are created outside the CLR but have since run inside the CLR at least once. Only unique threads are tracked; threads with same thread ID re-entering the CLR or recreated after thread exit are not counted twice.
+
+RECOGNIZED_THREADS_INST_009_NAME=rate of recognized threads / sec
+RECOGNIZED_THREADS_INST_009_HELP=This counter displays the number of threads per second that have been recognized by the CLR; these threads have a corresponding .NET thread object associated with them. These threads are not created by the CLR; they are created outside the CLR but have since run inside the CLR at least once. Only unique threads are tracked; threads with same thread ID re-entering the CLR or recreated after thread exit are not counted twice. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+DotNetCLR_Security_OBJECT_009_NAME=.NET CLR Security
+DotNetCLR_Security_OBJECT_009_HELP=Stats for CLR Security.
+
+SECURITY_TOTALRTCHECKS_009_NAME=Total Runtime Checks
+SECURITY_TOTALRTCHECKS_009_HELP=This counter displays the total number of runtime Code Access Security (CAS) checks performed since the start of the application. Runtime CAS checks are performed when a caller makes a call to a callee demanding a particular permission; the runtime check is made on every call by the caller; the check is done by examining the current thread stack of the caller. This counter used together with "Stack Walk Depth" is indicative of performance penalty for security checks.
+
+SECURITY_TIMEAUTHORIZE_009_NAME=% Time Sig. Authenticating
+SECURITY_TIMEAUTHORIZE_009_HELP=Reserved for future use.
+
+SECURITY_LINKCHECKS_009_NAME=# Link Time Checks
+SECURITY_LINKCHECKS_009_HELP=This counter displays the total number of linktime Code Access Security (CAS) checks since the start of the application. Linktime CAS checks are performed when a caller makes a call to a callee demanding a particular permission at JIT compile time; linktime check is performed once per caller. This count is not indicative of serious performance issues; its indicative of the security system activity.
+
+SECURITY_TIMERTCHECKS_009_NAME=% Time in RT checks
+SECURITY_TIMERTCHECKS_009_HELP=This counter displays the percentage of elapsed time spent in performing runtime Code Access Security (CAS) checks since the last such check. CAS allows code to be trusted to varying degrees and enforces these varying levels of trust depending on code identity. This counter is updated at the end of a runtime security check; it represents the last observed value; its not an average.
+
+SECURITY_TIMERTCHECKS_BASE_009_NAME=Not Displayed
+SECURITY_TIMERTCHECKS_BASE_009_HELP=Not Displayed.
+
+SECURITY_DEPTHSECURITY_009_NAME=Stack Walk Depth
+SECURITY_DEPTHSECURITY_009_HELP=This counter displays the depth of the stack during that last runtime Code Access Security check. Runtime Code Access Security check is performed by crawling the stack. This counter is not an average; it just displays the last observed value.
+
+DotNetCLR_Remoting_OBJECT_009_NAME=.NET CLR Remoting
+DotNetCLR_Remoting_OBJECT_009_HELP=Stats for CLR Remoting.
+
+CONTEXT_REMOTECALLS_INST_009_NAME=Remote Calls/sec
+CONTEXT_REMOTECALLS_INST_009_HELP=This counter displays the number of remote procedure calls invoked per second. A remote procedure call is a call on any object outside the caller;s AppDomain. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+CONTEXT_CHANNELS_009_NAME=Channels
+CONTEXT_CHANNELS_009_HELP=This counter displays the total number of remoting channels registered across all AppDomains since the start of the application. Channels are used to transport messages to and from remote objects.
+
+CONTEXT_PROXIES_009_NAME=Context Proxies
+CONTEXT_PROXIES_009_HELP=This counter displays the total number of remoting proxy objects created in this process since the start of the process. Proxy object acts as a representative of the remote objects and ensures that all calls made on the proxy are forwarded to the correct remote object instance.
+
+CONTEXT_CLASSES_009_NAME=Context-Bound Classes Loaded
+CONTEXT_CLASSES_009_HELP=This counter displays the current number of context-bound classes loaded. Classes that can be bound to a context are called context-bound classes; context-bound classes are marked with Context Attributes which provide usage rules for synchronization; thread affinity; transactions etc.
+
+CONTEXT_OBJALLOC_009_NAME=Context-Bound Objects Alloc / sec
+CONTEXT_OBJALLOC_009_HELP=This counter displays the number of context-bound objects allocated per second. Instances of classes that can be bound to a context are called context-bound objects; context-bound classes are marked with Context Attributes which provide usage rules for synchronization; thread affinity; transactions etc. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+CONTEXT_CONTEXTS_009_NAME=Contexts
+CONTEXT_CONTEXTS_009_HELP=This counter displays the current number of remoting contexts in the application. A context is a boundary containing a collection of objects with the same usage rules like synchronization; thread affinity; transactions etc.
+
+CONTEXT_REMOTECALLS_TOTAL_009_NAME=Total Remote Calls
+CONTEXT_REMOTECALLS_TOTAL_009_HELP=This counter displays the total number of remote procedure calls invoked since the start of this application. A remote procedure call is a call on any object outside the caller;s AppDomain.
+
+DotNetCLR_Excep_OBJECT_009_NAME=.NET CLR Exceptions
+DotNetCLR_Excep_OBJECT_009_HELP=Runtime statistics on CLR exception handling.
+
+EXCEP_THROWN_TOTAL_009_NAME=# of Exceps Thrown
+EXCEP_THROWN_TOTAL_009_HELP=This counter displays the total number of exceptions thrown since the start of the application. These include both .NET exceptions and unmanaged exceptions that get converted into .NET exceptions e.g. null pointer reference exception in unmanaged code would get re-thrown in managed code as a .NET System.NullReferenceException; this counter includes both handled and unhandled exceptions. Exceptions that are re-thrown would get counted again. Exceptions should only occur in rare situations and not in the normal control flow of the program.
+
+EXCEP_THROWN_INST_009_NAME=# of Exceps Thrown / sec
+EXCEP_THROWN_INST_009_HELP=This counter displays the number of exceptions thrown per second. These include both .NET exceptions and unmanaged exceptions that get converted into .NET exceptions e.g. null pointer reference exception in unmanaged code would get re-thrown in managed code as a .NET System.NullReferenceException; this counter includes both handled and unhandled exceptions. Exceptions should only occur in rare situations and not in the normal control flow of the program; this counter was designed as an indicator of potential performance problems due to large (>100s) rate of exceptions thrown. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+TOTAL_EXCEP_FILTERS_RUN_009_NAME=# of Filters / sec
+TOTAL_EXCEP_FILTERS_RUN_009_HELP=This counter displays the number of .NET exception filters executed per second. An exception filter evaluates whether an exception should be handled or not. This counter tracks the rate of exception filters evaluated; irrespective of whether the exception was handled or not. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+TOTAL_EXCEP_FINALLYS_RUN_009_NAME=# of Finallys / sec
+TOTAL_EXCEP_FINALLYS_RUN_009_HELP=This counter displays the number of finally blocks executed per second. A finally block is guaranteed to be executed regardless of how the try block was exited. Only the finally blocks that are executed for an exception are counted; finally blocks on normal code paths are not counted by this counter. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+EXCEPT_STACK_DEPTH_009_NAME=Throw To Catch Depth / sec
+EXCEPT_STACK_DEPTH_009_HELP=This counter displays the number of stack frames traversed from the frame that threw the .NET exception to the frame that handled the exception per second. This counter resets to 0 when an exception handler is entered; so nested exceptions would show the handler to handler stack depth. This counter is not an average over time; it displays the difference between the values observed in the last two samples divided by the duration of the sample interval.
+
+DotNetCLR_Memory_OBJECT_011_NAME=.NET CLR Memory
+DotNetCLR_Memory_OBJECT_011_HELP=CLR Kx[W RNV q[ṽJE^łB
+
+GEN0_COLLECTIONS_COUNTER_011_NAME=# Gen 0 Collections
+GEN0_COLLECTIONS_COUNTER_011_HELP=̃JE^́AAvP[VJnĈȗA 0 IuWFNg (ŐV̊蓖ĂňԐV) AKx[W RNV (Gen 0 GC) ꂽ񐔂\܂BGen 0 GC ́A 0 ̗p”\ȃA蓖ėv\ȂƂɔ܂B̃JE^ Gen 0 GC ̍ŌɃCNg܂BV GC ͌ GC ׂĊ܂݂܂B̃JE^́AV (Gen 1 ܂ Gen 2) GC ƂɖIɃCNg܂B_Global_ counter ̒l͐mł͂Ȃ̂ŖׂłB̃JE^͍ŐV̒l\܂B
+
+GEN1_COLLECTIONS_COUNTER_011_NAME=# Gen 1 Collections
+GEN1_COLLECTIONS_COUNTER_011_HELP=̃JE^́AAvP[VJnĈȗA 1 IuWFNgAKx[W RNVꂽ񐔂\܂B̃JE^ Gen 1 GC ̍ŌɃCNg܂BV GC ͌Â GC ׂĊ܂݂܂B̃JE^́AV (Gen 2) GC ƂɖIɃCNg܂B_Global_ counter ̒l͐mł͂Ȃ̂ŖׂłB̃JE^͍ŐV̒l\܂B
+
+GEN2_COLLECTIONS_COUNTER_011_NAME=# Gen 2 Collections
+GEN2_COLLECTIONS_COUNTER_011_HELP=̃JE^́AAvP[VJnĈȗA 2 IuWFNg (Â) AKx[W RNVꂽ񐔂\܂B̃JE^ Gen 2 GC ̍ŌɃCNg܂ (t GC ƂĂ΂܂)B_Global_ counter ̒l͐mł͂Ȃ̂ŖׂłB̃JE^͍ŌɊώ@ꂽl\܂B
+
+GEN0_BYTES_PROMOTED_COUNTER_011_NAME=Promoted Memory from Gen 0
+GEN0_BYTES_PROMOTED_COUNTER_011_HELP=̃JE^́AKx[W RNV (GC) ςāA 0 琶 1 ɏʕϊ̃oCg\܂B̃JE^ɂ́APɊ̂҂‚߂ɏʕϊIuWFNg͊܂݂܂B̃JE^́AŌ GC ̍ŌɊώ@ꂽl\܂B͗ݐσJE^ł͂܂B
+
+GEN1_BYTES_PROMOTED_COUNTER_011_NAME=Promoted Memory from Gen 1
+GEN1_BYTES_PROMOTED_COUNTER_011_HELP=̃JE^́AKx[W RNV (GC) ςāA 1 琶 2 ɏʕϊ̃oCg\܂B̃JE^́APɊ̂҂‚߂ɏʕϊIuWFNg͊܂݂܂B̃JE^͍ŌɊώ@ꂽl\܂B͗ݐσJE^ł͂܂B̃JE^́AŌ GC Gen 0 GC ݂̂̏ꍇ́A0 ɃZbg܂B
+
+GEN0_PROMOTION_RATE_011_NAME=Gen 0 Promoted Bytes/Sec
+GEN0_PROMOTION_RATE_011_HELP=̃JE^́A 0 (ԐV) 琶 1 ɏʕϊ̖b̃oCg\܂B̃JE^́APɊ̂҂‚߂ɏʕϊIuWFNg͊܂݂܂B́AKx[W RNVςƏʕϊ܂B̃JE^́Ab쐬rIɒIuWFNgɊւCfBP[^ƂăfUC܂B̃JE^́ATv̎ԊԊuŕꂽAŌ 2 ̃TvԂŊώ@ꂽl̈Ⴂ\܂B
+
+GEN1_PROMOTION_RATE_011_NAME=Gen 1 Promoted Bytes/Sec
+GEN1_PROMOTION_RATE_011_HELP=̃JE^́A 1 琶 2 (ԌÂ) ɐi񂾃̖b̃oCg\܂B̃JE^́APɊ̂҂‚߂ɏʕϊIuWFNg͊܂݂܂B́AKx[W RNVςƏʕϊ܂B 2 ͈ԌÂ߁A̎͂܂B̃JE^́Ab쐬ɒIuWFNgɊւCfBP[^ƂăfUC܂B̃JE^́ATv̎ԊԊuŕꂽAŌ 2 ̃TvԂŊώ@ꂽl̈Ⴂ\܂B
+
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_011_NAME=Promoted Finalization-Memory from Gen 0
+GEN0_FINALIZATION_BYTES_PROMOTED_COUNTER_011_HELP=̃JE^́APɊ̂҂‚߂ɐ 0 琶 1 ɏʕϊ̖b̃oCg\܂B̃JE^́AŌ GC ̍ŌɊώ@ꂽl\܂B͗ݐσJE^ł͂܂B
+
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_011_NAME=Promoted Finalization-Memory from Gen 1
+GEN1_FINALIZATION_BYTES_PROMOTED_COUNTER_011_HELP=̃JE^́APɊ̂҂‚߂ɐ 1 琶 2 ɏʕϊ̖b̃oCg\܂B̃JE^́AŌ GC ̍ŌɊώ@ꂽl\܂B͗ݐσJE^ł͂܂B̃JE^́AŌ GC Gen 0 GC ݂̂̏ꍇ́A0 ɃZbg܂B
+
+GEN0_HEAP_SIZE_COUNTER_011_NAME=Gen 0 heap size
+GEN0_HEAP_SIZE_COUNTER_011_HELP=̃JE^́A 0 (Gen 0) Ɋ蓖Ăő̃oCg\܂B 0 Ɋ蓖Ăꂽ݂̃oCg͎܂BGen 0 GC ́AŌ GC ȗA蓖ẴTCY𒴂Ɣ܂BGen 0 TCY̓Kx[W RN^ɂĒAAvP[V̎sɕύX܂BGen 0 RNV̍Ō Gen 0 q[ṽTCY͎ۂ 0 oCgłB̃JE^́A Gen 0 GC 𔭐銄蓖ẴTCYoCgŕ\܂B̃JE^ GC ̍ŌɍXV܂B蓖ĂƂɂ͍XV܂B
+
+GEN1_HEAP_SIZE_COUNTER_011_NAME=Gen 1 heap size
+GEN1_HEAP_SIZE_COUNTER_011_HELP=̃JE^́A 1 (Gen 1) ݂̌̃oCg\܂B̃JE^ł Gen 1 ̍őTCY\܂BIuWFNg͂̐ł͒ڊ蓖Ă܂BIuWFNg͑O Gen 0 GC ʕϊ܂B̃JE^ GC ̍ŌɍXV܂B蓖ĂƂɂ͍XV܂B
+
+GEN2_HEAP_SIZE_COUNTER_011_NAME=Gen 2 heap size
+GEN2_HEAP_SIZE_COUNTER_011_HELP=̃JE^́A 2 (Gen 2) ݂̌̃oCg\܂BIuWFNg͂̐ł͒ڊ蓖Ă܂BIuWFNg͑O Gen 1 GC Gen 1 ʕϊ܂B̃JE^ GC ̍ŌɍXV܂B蓖ĂƂɂ͍XV܂B
+
+LARGE_OBJECT_SIZE_COUNTER_011_NAME=Large Object Heap size
+LARGE_OBJECT_SIZE_COUNTER_011_HELP=̃JE^́ALarge Object Heap ݂̌̃TCYoCgŕ\܂B20 KBytes 傫IuWFNg Garbage Collector ɂ large IuWFNgƂĈAʂȃq[vŒڊ蓖Ă܂B͐ɂďʕϊ܂B̃JE^ GC ̍ŌɍXV܂B蓖ĂƂɂ͍XV܂B
+
+SURVIVE_FINALIZE_COUNTER_011_NAME=Finalization Survivors
+SURVIVE_FINALIZE_COUNTER_011_HELP=̃JE^́Â҂‚߂ɁAKx[W RNgςăRNgꂽIuWFNg̐\܂B̃IuWFNg̃IuWFNgւ̎QƂĂȂ΁ÃIuWFNglɑς܂ÃJE^ł̓JEg܂B"Promoted Finalization-Memory from Gen 0" "Promoted Finalization-Memory from Gen 1" JE^́A邽߂ɑςʂׂă\܂B̃JE^͗ݐσJE^ł͂܂B̃JE^́A̓ GC ԂɐcJEgg GC ̍ŌɍXV܂B̃JE^́A邽߂ɃAvP[Vނlj̃I[o[wbh悤fUC܂B
+
+NUM_HANDLES_COUNTER_011_NAME=# GC Handles
+NUM_HANDLES_COUNTER_011_HELP=̃JE^͌ݎgpĂ GC nh̐\܂B GCHandles LR ̊Oƃ}l[W‹̃\[Xւ̃nhłBnh GCHeap ɏʂ̃ێ܂Ap̊|A}l[W \[XɂȂ”\܂B
+
+ALLOCATION_RATE_COUNTER_011_NAME=Allocated Bytes/sec
+ALLOCATION_RATE_COUNTER_011_HELP=̃JE^ GC q[vɊ蓖Ăꂽb̃oCg\܂B̃JE^͊蓖ĂƂł͂ȂAe GC ̏IƂɍXV܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+INDUCED_GC_COUNTER_011_NAME=# Induced GC
+INDUCED_GC_COUNTER_011_HELP=̃JE^ GC.Collect ւ̖IȌĂяô߂ɃKx[W RNVsꂽő̉񐔂\܂BGC ̎gKx[W RNVɍ킹Ă̂悢@łB
+
+PER_TIME_IN_GC_COUNTER_011_NAME=% Time in GC
+PER_TIME_IN_GC_COUNTER_011_HELP=GC % Time ́AŌ GC TCNȗAKx[W RNV (GC) s߂Ɍo߂Ԃ̃p[Ze[W\܂B̃JE^́AʏAKx[W RNVAAvP[V̑ɃWăRpNgsƂCWP[^łB̃JE^͖ GC ̍Ōɂ̂ݍXV܂BJE^̒l͕ϒlł͂ȂAŌɊώ@l𔽉f܂B
+
+PER_TIME_IN_GC_COUNTER_BASE_011_NAME=Not Displayed
+PER_TIME_IN_GC_COUNTER_BASE_011_HELP=\Ă܂B
+
+TOTAL_HEAP_SIZE_COUNTER_011_NAME=# Bytes in all Heaps
+TOTAL_HEAP_SIZE_COUNTER_011_HELP=̃JE^͎ 4 ‚̃JE^̍vłBGen 0 q[v TCYAGen 1 q[v TCYAGen 2 q[v TCY ё傫IuWFNg̃q[v TCYB̃JE^ GC q[vɊ蓖Ăꂽ݂̃oCg܂B
+
+TOTAL_COMMITTED_MEM_COUNTER_011_NAME=# Total committed Bytes
+TOTAL_COMMITTED_MEM_COUNTER_011_HELP=̃JE^́A݃Kx[W RN^ɂăR~bgĂ鉼zoCgŕ\܂B (R~bg ́AfBXÑy[WO t@CɃXy[X\񂳂Ă镨Iȃł)B
+
+TOTAL_RESERVED_MEM_COUNTER_011_NAME=# Total reserved Bytes
+TOTAL_RESERVED_MEM_COUNTER_011_HELP=̃JE^́A݃Kx[W RN^ɂăR~bgĂ鉼zoCgŕ\܂B(\񂳂ꂽ̓AvP[Vɗ\񂳂ꂽz Xy[XŁAfBXNA܂̓C y[W͉gpĂ܂)B
+
+GC_PINNED_OBJECTS_011_NAME=# of Pinned Objects
+GC_PINNED_OBJECTS_011_HELP=̃JE^͍Ō GC Ō‚s~߃IuWFNg̐\܂B̃JE^̓Kx[W RNgꂽq[v̒̃s~߃IuWFNg݂̏̂L^܂BƂ Gen 0 GC ́A 0 q[vł̂݃s~߃IuWFNg̗񋓂𐶂܂BKx[W RN^́As~߃IuWFNgňړ邱Ƃ͂ł܂B
+
+GC_SINKBLOCKS_011_NAME=# of Sink Blocks in use
+GC_SINKBLOCKS_011_HELP=̃JE^͌ݎgpĂ Sync ubN\܂BSync ubŃAXg[W̓ɂ߂Ɋ蓖ĂꂽIuWFNgƂ̃f[^\łBSync ubN̓}l[W IuWFNgɎアQƂێAKx[W RN^ɂăXLKv܂BSync ubN͓ۑ邾Ɍ炸ACOM ݉^p@\^f[^ۑł܂B̃JE^́Av~eBupɂɎgp邱ƂɂĐwE悤ɃfUC܂B
+
+DotNetCLR_Loading_OBJECT_011_NAME=.NET CLR Loading
+DotNetCLR_Loading_OBJECT_011_HELP=CLR NX [_[̓v
+
+LOADING_CLASSES_TOTAL_011_NAME=Total Classes Loaded
+LOADING_CLASSES_TOTAL_011_HELP=̃JE^́AAvP[VJnĈȗAׂẴAZuɓǂݍ܂ꂽNX̗ݐϐ\܂B
+
+LOADING_TIME_011_NAME=% Time Loading
+LOADING_TIME_011_HELP=p邽߂ɗ\񂳂Ă܂B
+
+LOADING_ASMSEARCHLEN_011_NAME=Assembly Search Length
+LOADING_ASMSEARCHLEN_011_HELP=p邽߂ɗ\񂳂Ă܂B
+
+LOADING_LOADFAILURES_TOTAL_011_NAME=Total # of Load Failures
+LOADING_LOADFAILURES_TOTAL_011_HELP=̃JE^́AAvP[VJnĈȗAǂݍ݂łȂNX̍ő吔\܂Bǂݍ݂ɎsŔA\ȃZLeBA܂͊ԈtH[}bgƂA낢l܂Bڍׂɂ‚ẮAvt@C T[rX̃wvŎQƂłĂB
+
+LOADING_LOADFAILURES_INST_011_NAME=Rate of Load Failures
+LOADING_LOADFAILURES_INST_011_HELP=̃JE^͓ǂݍ݂łȂNX̖b̐\܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂Bǂݍ݂ɎsŔA\ȃZLeBA܂͊ԈtH[}bgƂA낢l܂Bڍׂɂ‚ẮAvt@C T[rX̃wvŎQƂłĂB
+
+LOADING_HEAPSIZE_011_NAME=Bytes in Loader Heap
+LOADING_HEAPSIZE_011_HELP=̃JE^́A݁AׂĂ AppDomains ŃNX [_[ɂăR~bgĂ郁oCgŕ\܂B (R~bg ́AfBXÑy[WO t@CɃXy[X\񂳂Ă镨Iȃł)B
+
+LOADING_APPDOMAINS_UNLOADED_TOTAL_011_NAME=Total appdomains unloaded
+LOADING_APPDOMAINS_UNLOADED_TOTAL_011_HELP=̃JE^́AAvP[VJnĈȗAA[hꂽ AppDomains ̍v\܂B̃JE^́AAppDomain ǂݍ܂AĕA[hꂽꍇ́AeA[hʁXɃJEg܂B
+
+LOADING_APPDOMAINS_UNLOADED_INST_011_NAME=Rate of appdomains unloaded
+LOADING_APPDOMAINS_UNLOADED_INST_011_HELP=̃JE^́AA[hꂽ AppDomains ̖b̐\܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\ ܂B
+
+LOADING_CLASSES_CUR_011_NAME=Current Classes Loaded
+LOADING_CLASSES_CUR_011_HELP=̃JE^ׂ͂ẴAZuɓǂݍ܂ꂽ݂̃NX\܂B
+
+LOADING_CLASSES_INST_011_NAME=Rate of Classes Loaded
+LOADING_CLASSES_INST_011_HELP=̃JE^ׂ͂ẴAZuɓǂݍ܂ꂽNX̖b̐\܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+LOADING_APPDOMAINS_CUR_011_NAME=Current appdomains
+LOADING_APPDOMAINS_CUR_011_HELP=̃JE^͂̃AvP[Vɓǂݍ܂ꂽ݂ AppDomains \܂BAppDomains (AvP[V hC) ͈Sőpr̃vZX jbg񋟂܂BCLR ͂gpāAvZXŎsĂAvP[V̊Ԃ̕񋟂邱Ƃł܂B
+
+LOADING_APPDOMAINS_TOTAL_011_NAME=Total Appdomains
+LOADING_APPDOMAINS_TOTAL_011_HELP=̃JE^́AAvP[VJnĈȗAǂݍ܂ꂽő AppDomains \܂BAppDomains (AvP[V hC) ͈Sőpr̃vZX jbg񋟂܂BCLR ͂gpāAvZXŎsĂAvP[V̊Ԃ̕񋟂邱Ƃł܂B
+
+LOADING_APPDOMAINS_INST_011_NAME=Rate of appdomains
+LOADING_APPDOMAINS_INST_011_HELP=̃JE^ ǂݍ܂ꂽ AppDomains ̖b̐\܂BAppDomains (AvP[V hC) ͈Sőpr̃vZX jbg񋟂܂BCLR ͂gpāAvZXŎsĂAvP[V̊Ԃ̕񋟂邱Ƃł܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+LOADING_ASSEMBLIES_CUR_011_NAME=Current Assemblies
+LOADING_ASSEMBLIES_CUR_011_HELP=̃JE^͂̃AvP[Vׂ̂Ă AppDomains œǂݍ܂ꂽAZǔ݂̐\܂BAZu AppDomains hCœǂݍ܂ꂽꍇ́ÃJE^ 1 xCNg܂BAZúAR[hׂĂ AppDomains ŋLłꍇ́AhCœǂݍ܂܂B܂́AR[h AppDomain ɃvCx[głƂ́AhCŗLƂēǂݍ܂܂B
+
+LOADING_ASSEMBLIES_TOTAL_011_NAME=Total Assemblies
+LOADING_ASSEMBLIES_TOTAL_011_HELP=̃JE^́AAvP[VJnĈȗǂݍ܂ꂽṽAZu\܂BAZu AppDomains hCœǂݍ܂ꂽꍇ́ÃJE^ 1 xCNg܂BAZúAR[hׂĂ AppDomains ŋLłꍇ́AhCœǂݍ܂܂B܂́AR[h AppDomain ɃvCx[głƂ́AhCŗLƂēǂݍ܂܂B
+
+LOADING_ASSEMBLIES_INST_011_NAME=Rate of Assemblies
+LOADING_ASSEMBLIES_INST_011_HELP=̃JE^́AׂĂ AppDomains œǂݍ܂ꂽAZu̖b̐\܂BAZu AppDomains hCœǂݍ܂ꂽꍇ́ÃJE^ 1 xCNg܂BAZúAR[hׂĂ AppDomains ŋLłꍇ́AhCœǂݍ܂܂B܂́AR[h AppDomain ɃvCx[głƂ́AhCŗLƂēǂݍ܂܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+DotNetCLR_Jit_OBJECT_011_NAME=.NET CLR Jit
+DotNetCLR_Jit_OBJECT_011_HELP=CLR Jit ̓vłB
+
+TOTAL_METHODS_JITTED_011_NAME=# of Methods Jitted
+TOTAL_METHODS_JITTED_011_HELP=̃JE^́AAvP[VJnĈȗ CLR JIT RpCɂ Just-In-Time (JIT) ɃRpCꂽ\bh̍v\܂B
+
+JITTED_IL_CUR_011_NAME=# of IL Bytes Jitted
+JITTED_IL_CUR_011_HELP=̃JE^́AAvP[VJnĂgpꂽv IL oCg\܂B̃JE^́A "Total # of IL Bytes Jitted" JE^Ƃ܂lłB
+
+JITTED_IL_TOTAL_011_NAME=Total # of IL Bytes Jitted
+JITTED_IL_TOTAL_011_HELP=̃JE^́AAvP[VJnĂgpꂽv IL oCg\܂B̃JE^́A "# of IL Bytes Jitted" JE^ƊSɓlłB
+
+JITTED_IL_INST_011_NAME=IL Bytes Jitted / sec
+JITTED_IL_INST_011_HELP=̃JE^́Agpꂽ IL oCg̖b̊\܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+JIT_FAILURES_011_NAME=Standard Jit Failures
+JIT_FAILURES_011_HELP=̃JE^́AAvP[VJnĈȗ JIT RpC JIT Ɏső̃\bh\܂Bs IL ؂łȂꍇA܂ JIT RpCɓG[ꍇɔ܂B
+
+TIME_IN_JIT_011_NAME=% Time in Jit
+TIME_IN_JIT_011_HELP=̃JE^́AŌ JIT RpC̒iKȗA JIT RpCs߂Ɍo߂Ԃ̃p[Ze[W\܂B̃JE^́A JIT RpC̒iK̍ŌɍXV܂BJE^̒ĺAϒlł͂ȂAŌɊώ@l𔽉f܂BJIT RpC̒iḰA\bhт̈ˑ֌WRpCꂽiK\܂B
+
+TIME_IN_JIT_BASE_011_NAME=Not Displayed
+TIME_IN_JIT_BASE_011_HELP=\Ă܂B
+
+DotNetCLR_Interop_OBJECT_011_NAME=.NET CLR Interop
+DotNetCLR_Interop_OBJECT_011_HELP=CLR ݉^p@\̓vłB
+
+CURRENT_CCW_011_NAME=# of CCWs
+CURRENT_CCW_011_HELP=̃JE^́ACom Ăяo”\bp[ (CCWs) ݂̌̐\܂BCCW ́AA}l[W COM NCAgQƂĂ .NET }l[W IuWFNg̃vLVłB̃JE^́AA}l[W COM NCAgQƂĂ}l[W IuWFNg̐悤ɃfUC܂B
+
+CURRENT_STUBS_011_NAME=# of Stubs
+CURRENT_STUBS_011_HELP=̃JE^́ACLR ō쐬ꂽ݂̃X^bh\܂BX^bh͈і߂l}l[WA}l[W R[hցA܂̓A}l[W}l[W R[hփ}[VOڂĂ܂B COM ݉^p@\ĂяoA܂ PInvoke Ăяoɍs܂B
+
+NUM_MARSHALLING_011_NAME=# of marshalling
+NUM_MARSHALLING_011_HELP=̃JE^́AAvP[VJnĈȗAƖ߂l}l[WA}l[W R[hɁA܂A}l[W}l[W R[hɃ}[VOꂽv񐔂\܂B̃JEg̓X^bhCC̏ꍇ̓CNg܂B (X^bh͈і߂l}[VOڂĂ܂)BX^bh́A}[VÕI[o[wbhꍇ́AʏCCɂȂ܂B
+
+TOTAL_TLB_IMPORTS_011_NAME=# of TLB imports / sec
+TOTAL_TLB_IMPORTS_011_HELP=p邽߂ɗ\񂳂Ă܂B
+
+TOTAL_TLB_EXPORTS_011_NAME=# of TLB exports / sec
+TOTAL_TLB_EXPORTS_011_HELP=p邽߂ɗ\񂳂Ă܂B
+
+DotNetCLR_LocksAndThreads_OBJECT_011_NAME=.NET CLR LocksAndThreads
+DotNetCLR_LocksAndThreads_OBJECT_011_HELP=CLR bNуXbh̓vłB
+
+CONTENTION_TOTAL_011_NAME=Total # of Contentions
+CONTENTION_TOTAL_011_HELP=̃JE^́ACLR ̃Xbh}l[W bN擾悤ƂĎs񐔂̍v\܂B}l[W bN擾ɂ͂낢ȕ@܂BƂ΁AC# "lock" Xe[gggpASystem.Monitor.Enter ĂяoAMethodImplOptions.Synchronized custom gpAȂǁB
+
+CONTENTION_INST_011_NAME=Contention Rate / sec
+CONTENTION_INST_011_HELP=^C̃Xbh}l[W bN擾悤ƂĎsłB}l[W bN擾ɂ͎̂悤ȕ@܂BC# "lock" Xe[gggpASystem.Monitor.Enter ̌ĂяoA܂ MethodImplOptions.Synchronized JX^gpB
+
+QUEUE_LENGTH_CUR_011_NAME=Current Queue Length
+QUEUE_LENGTH_CUR_011_HELP=̃JE^͌݃AvP[VŃ}l[W bN擾悤Ƒ҂ĂXbh̍v\܂B̃JEg͑Ŝ̕ςł͂ȂAŌɊώ@ꂽl\܂B
+
+QUEUE_LENGTH_TOTAL_011_NAME=Queue Length Peak
+QUEUE_LENGTH_TOTAL_011_HELP=̃JE^́AAvP[VJnĂA}l[W bN̎擾҂ĂXbh̍v\܂B
+
+QUEUE_LENGTH_INST_011_NAME=Queue Length / sec
+QUEUE_LENGTH_INST_011_HELP=̃JE^́AAvP[VŃbN̎擾҂ĂXbh̖b̐\܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+CURRENT_LOGICAL_THREADS_011_NAME=# of current logical Threads
+CURRENT_LOGICAL_THREADS_011_HELP=̃JE^́AAvP[V .NET Xbh IuWFNǧ݂̐\܂B.NET Xbh IuWFNg͐V System.Threading.Thread ɂč쐬邩A܂̓A}l[W Xbh}l[W‹ɓƂɍ쐬܂B̃JE^́As̃Xbhђ~Xbh̗̃JEgێ܂BB̃JEg͑Ŝ̕ςł͂ȂAŌɊώ@ꂽl\܂B
+
+CURRENT_PHYSICAL_THREADS_011_NAME=# of current physical Threads
+CURRENT_PHYSICAL_THREADS_011_HELP=̃JE^́ACLR ɂč쐬ꏊLāA.NET Xbh IuWFNg̊ɂȂXbhƂē삷lCeBu OS Xbh̐\܂B̃JE^̒ĺA CLR ɂĎgpXbh܂݂܂BOS vZX̃Xbh̃TuZbgłB
+
+RECOGNIZED_THREADS_CUR_011_NAME=# of current recognized threads
+RECOGNIZED_THREADS_CUR_011_HELP=̃JE^́A CLR ɂĔFĂXbh\܂B̃Xbh́AXbhƊ֘Atꂽv .NET Xbh IuWFNgĂ܂B̃Xbh CLR ɂč쐬ꂸACLR ̊Oō쐬܂ACLR ŏȂƂ 1 x͎sĂ܂B񂪋L^͈̂ӂ̃Xbĥ݂łBXbh ID CLR ɍĂъ܂܂ꂽA܂Iɍč쐬ꂽXbh 2 xڂ̓JEg܂B
+
+RECOGNIZED_THREADS_TOTAL_011_NAME=# of total recognized threads
+RECOGNIZED_THREADS_TOTAL_011_HELP=̃JE^́AAvP[V̊Jnȗ CLR ɂĔFꂽXbhv\܂B̃Xbh́AXbhƊ֘Atꂽv .NET Xbh IuWFNgĂ܂B̃Xbh CLR ɂč쐬ꂸACLR ̊Oō쐬܂ACLR ŏȂƂ 1 x͎sĂ܂B񂪋L^͈̂ӂ̃Xbĥ݂łBXbh ID CLR ɍĂъ܂܂ꂽA܂Iɍč쐬ꂽXbh 2 xڂ̓JEg܂B
+
+RECOGNIZED_THREADS_INST_011_NAME=rate of recognized threads / sec
+RECOGNIZED_THREADS_INST_011_HELP=̃JE^́A CLR ɂĔFꂽXbh̖b̐\܂B̃Xbh́AXbhƊ֘Atꂽv .NET Xbh IuWFNgĂ܂B̃Xbh CLR ɂč쐬ꂸACLR ̊Oō쐬܂ACLR ŏȂƂ 1 x͎sĂ܂B񂪋L^͈̂ӂ̃Xbĥ݂łBXbh ID CLR ɍĂъ܂܂ꂽA܂Iɍč쐬ꂽXbh 2 xڂ̓JEg܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+DotNetCLR_Security_OBJECT_011_NAME=.NET CLR Security
+DotNetCLR_Security_OBJECT_011_HELP=CLR ZLeB̓vłB
+
+SECURITY_TOTALRTCHECKS_011_NAME=Total Runtime Checks
+SECURITY_TOTALRTCHECKS_011_HELP=̃JE^́AAvP[V̊JnȗAsꂽ^C Code Access Security (CAS) `FbN̍v\܂B^C Code Access Security (CAS) `FbŃAĂяoĂяoɓʂ̃ANZXvČĂяoƂɎs܂BĂяoĂяoƂɃ^C `FbNs܂B܂Ăяǒ݂̃Xbh X^bN𒲂ׂ邱Ƃɂă`FbNs܂B"Stack Walk Depth" ƋɎgp邱̃JE^́AZLeB `FbÑptH[}X yieB܂B
+
+SECURITY_TIMEAUTHORIZE_011_NAME=% Time Sig. Authenticating
+SECURITY_TIMEAUTHORIZE_011_HELP=p邽߂ɗ\񂳂Ă܂B
+
+SECURITY_LINKCHECKS_011_NAME=# Link Time Checks
+SECURITY_LINKCHECKS_011_HELP=̃JE^́AAvP[VJnĈȗ̃N^C Code Access Security (CAS) `FbN̍v\܂BN^C CAS `FbŃAJIT RpCɁAĂяoĂяoɓʂ̃ANZXvČĂяoƂɎs܂BN^C CAS `FbN͌ĂяoƂ 1 xs܂B̃JEg͏dȃptH[}X̂ł͂ȂAZLeB VXe̓̂łB
+
+SECURITY_TIMERTCHECKS_011_NAME=% Time in RT checks
+SECURITY_TIMERTCHECKS_011_HELP=̃JE^́AŌ̃`FbNȗA^C Code Access Security (CAS) `FbNs߂Ɍo߂Ԃ̃p[Ze[W\܂BCAS ̓R[hɈقȂ͈͂ł̐M^܂BR[h ID ɏ]Ă̈قȂMxKp܂B̃JE^̓^C̃ZLeB `FbN̍ŌɍXV܂BJE^̒l͕ϒlł͂ȂAŌɊώ@l𔽉f܂B
+
+SECURITY_TIMERTCHECKS_BASE_011_NAME=Not Displayed
+SECURITY_TIMERTCHECKS_BASE_011_HELP=\Ă܂B
+
+SECURITY_DEPTHSECURITY_011_NAME=Stack Walk Depth
+SECURITY_DEPTHSECURITY_011_HELP=̃JE^͍Ō̃^C Code Access Security `FbÑX^bN̐[\܂B^C Code Access Security `FbN̓X^bNN[Ďs܂B̃JEg͑Ŝ̕ςł͂ȂAŌɊώ@ꂽl\܂B
+
+DotNetCLR_Remoting_OBJECT_011_NAME=.NET CLR Remoting
+DotNetCLR_Remoting_OBJECT_011_HELP=CLR [g̓vłB
+
+CONTEXT_REMOTECALLS_INST_011_NAME=Remote Calls/sec
+CONTEXT_REMOTECALLS_INST_011_HELP=̃JE^́A[g vV[W̌ĂяoȂꂽb̉񐔂\܂B[g vV[W̌ĂяóAĂяo AppDomain ȊÕIuWFNgɂȂꂽĂяoׂĂ܂݂܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+CONTEXT_CHANNELS_011_NAME=Channels
+CONTEXT_CHANNELS_011_HELP=̃JE^́AAvP[VJnĈȗAׂĂ AppDomain œo^Ă郊[g `l̍v\܂B`l̓[g IuWFNgԂŃbZ[W𑗐M̂Ɏgp܂B
+
+CONTEXT_PROXIES_011_NAME=Context Proxies
+CONTEXT_PROXIES_011_HELP=̃JE^́AvZXJnĈȗÃvZXō쐬ꂽ[g vLV IuWFNg̍v\܂BvLV IuWFNg̓[g IuWFNg\ē삵AvLVɂ邷ׂĂ̌ĂяóA[g IuWFNg CX^Xɐmɓ]邱Ƃmɂ܂B
+
+CONTEXT_CLASSES_011_NAME=Context-Bound Classes Loaded
+CONTEXT_CLASSES_011_HELP=̃JE^́Aǂݍ܂ꂽ context-bound NX̌ݐ\܂BReLXgɍS邱Ƃ̂łNX context-bound NXƌĂ΂܂Bcontext-bound NX́AAXbhގAgUNVȂǂ̂߂̎gpK񋟂 Context Ń}[N܂B
+
+CONTEXT_OBJALLOC_011_NAME=Context-Bound Objects Alloc / sec
+CONTEXT_OBJALLOC_011_HELP=̃JE^́Acontext-bound IuWFNg蓖Ăꂽb̐\܂BReLXgɍS邱Ƃ̂łNX̃CX^X context-bound IuWFNgƌĂ΂܂Bcontext-bound NX́AAXbhގAgUNVȂǂ̂߂̎gpK񋟂 Context Ń}[N܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+CONTEXT_CONTEXTS_011_NAME=Contexts
+CONTEXT_CONTEXTS_011_HELP=̃JE^́AAvP[Ṽ[g ReLXǧ݂̐\܂BReLXǵAAXbhގAgUNVȂǂƓgpKƒIuWFNg̃RNV܂ł鋫EłB
+
+CONTEXT_REMOTECALLS_TOTAL_011_NAME=Total Remote Calls
+CONTEXT_REMOTECALLS_TOTAL_011_HELP=̃JE^́ÃAvP[VJnĈȗȂꂽ[g vV[W̌Ăяo̍v񐔂\܂B[g vV[W̌ĂяóAĂяo AppDomain ȊÕIuWFNgɂȂꂽĂяoׂĂ܂݂܂B
+
+DotNetCLR_Excep_OBJECT_011_NAME=.NET CLR Exceptions
+DotNetCLR_Excep_OBJECT_011_HELP=CLR Õ^CvłB
+
+EXCEP_THROWN_TOTAL_011_NAME=# of Exceps Thrown
+EXCEP_THROWN_TOTAL_011_HELP=̃JE^́AAvP[VJnĈȗAX[ꂽO̍v\܂Bɂ .NET OA .NET OɕϊꂽA}l[WO܂܂Ă܂BƂ΁AA}l[W R[h NULL |C^QƂ̗ÓA.NET System.NullReferenceException Ƃă}l[W R[hɍēxX[܂B̃JE^ɂ́AnhꂽOƃnhĂȂO̗܂݂܂BēxX[ꂽO͍ēxJEg܂BÔ͂܂ȏԂłAʏ̃vO̗̒ł͋Nׂł͂܂B
+
+EXCEP_THROWN_INST_011_NAME=# of Exceps Thrown / sec
+EXCEP_THROWN_INST_011_HELP=̃JE^͗OX[ꂽb̐\܂Bɂ .NET OA .NET OɕϊꂽA}l[WO܂܂Ă܂BƂ΁AA}l[W R[h NULL |C^QƂ̗ÓA.NET System.NullReferenceException Ƃă}l[W R[hɍēxX[܂B̃JE^ɂ́AnhꂽOƃnhĂȂO̗܂݂܂BēxX[ꂽO͍ēxJEg܂BÔ͂܂ȏԂłAʏ̃vO̗̒ł͋Nׂł͂܂B̃JE^́AX[O̐傫 (>100)AN”\̂ptH[}XwE悤ɃfUC܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+TOTAL_EXCEP_FILTERS_RUN_011_NAME=# of Filters / sec
+TOTAL_EXCEP_FILTERS_RUN_011_HELP=̃JE^́A.NET OtB^sꂽb̐\܂BOtB^͗Oׂǂ]܂B̃JE^́AOꂽǂɂ͊֌WȂAOtB^]ꂽL^܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+TOTAL_EXCEP_FINALLYS_RUN_011_NAME=# of Finallys / sec
+TOTAL_EXCEP_FINALLYS_RUN_011_HELP=̃JE^ finally ubNsꂽb̐\܂Bfinally ubŃAtry ubNǂ̂悤Ɏsꂽɂ͊֌WȂKs悤ɂȂĂ܂BOɎsꂽ finally ubNJEg܂Bʏ̃R[h pX finally ubN͂̃JE^ł̓JEg܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
+EXCEPT_STACK_DEPTH_011_NAME=Throw To Catch Depth / sec
+EXCEPT_STACK_DEPTH_011_HELP=̃JE^́A.NET OOt[ɃX[t[ڂꂽX^bN t[̖b̐\܂B̃JE^́AOnh͂ 0 ɃZbgAqɂȂO̓nhɃX^bN̐[\܂B̃JE^͑Ŝ̕ςł͂ȂATvԊǔpԂŊŌ 2 ‚̃Tv̊ԂŊώ@ꂽl̈Ⴂ\܂B
+
diff --git a/src/inc/1041/_DataPerfCounters.ini b/src/inc/1041/_DataPerfCounters.ini
new file mode 100644
index 0000000..53f94b8
--- /dev/null
+++ b/src/inc/1041/_DataPerfCounters.ini
Binary files differ
diff --git a/src/inc/1041/_NetworkingPerfCounters.ini b/src/inc/1041/_NetworkingPerfCounters.ini
new file mode 100644
index 0000000..d75180b
--- /dev/null
+++ b/src/inc/1041/_NetworkingPerfCounters.ini
Binary files differ
diff --git a/src/inc/1041/aspnet_perf.ini b/src/inc/1041/aspnet_perf.ini
new file mode 100644
index 0000000..9c09cc5
--- /dev/null
+++ b/src/inc/1041/aspnet_perf.ini
@@ -0,0 +1,414 @@
+[info]
+drivername=ASP.NET_1.0.3430.0
+symbolfile=aspnet_perf.h
+
+[languages]
+011=Japanese
+009=English
+
+[objects]
+OBJECT_1_009_NAME=ASP.NET v1.0.3430.0
+OBJECT_2_009_NAME=ASP.NET Apps v1.0.3430.0
+
+OBJECT_1_011_NAME=ASP.NET v1.0.3430.0
+OBJECT_2_011_NAME=ASP.NET Apps v1.0.3430.0
+
+[text]
+OBJECT_1_009_NAME=ASP.NET v1.0.3430.0
+OBJECT_1_009_HELP=ASP.NET v1.0.3430.0 global performance counters
+OBJECT_2_009_NAME=ASP.NET Apps v1.0.3430.0
+OBJECT_2_009_HELP=ASP.NET v1.0.3430.0 application performance counters
+
+OBJECT_1_011_NAME=ASP.NET v1.0.3430.0
+OBJECT_1_011_HELP=ASP.NET v1.0.3430.0 O[o p[tH[}X JE^
+OBJECT_2_011_NAME=ASP.NET Apps v1.0.3430.0
+OBJECT_2_011_HELP=ASP.NET v1.0.3430.0 AvP[V p[tH[}X JE^
+
+;;
+;; ASP.NET System Counters
+;;
+
+ASPNET_APPLICATION_RESTARTS_009_NAME=Application Restarts
+ASPNET_APPLICATION_RESTARTS_009_HELP=Number of times the application has been restarted during the web server's lifetime.
+
+ASPNET_APPLICATIONS_RUNNING_009_NAME=Applications Running
+ASPNET_APPLICATIONS_RUNNING_009_HELP=Number of currently running web applications.
+
+ASPNET_REQUESTS_DISCONNECTED_009_NAME=Requests Disconnected
+ASPNET_REQUESTS_DISCONNECTED_009_HELP=The number of requests disconnected due to communication errors or user terminated.
+
+ASPNET_REQUEST_EXECUTION_TIME_009_NAME=Request Execution Time
+ASPNET_REQUEST_EXECUTION_TIME_009_HELP=The number of milliseconds that it took to execute the most recent request.
+
+ASPNET_REQUESTS_REJECTED_009_NAME=Requests Rejected
+ASPNET_REQUESTS_REJECTED_009_HELP=The number of requests rejected because the request queue was full.
+
+ASPNET_REQUESTS_QUEUED_009_NAME=Requests Queued
+ASPNET_REQUESTS_QUEUED_009_HELP=The number of requests waiting to be processed.
+
+ASPNET_WPS_RUNNING_009_NAME=Worker Processes Running
+ASPNET_WPS_RUNNING_009_HELP=Number of worker processes running on the machine.
+
+ASPNET_WPS_RESTARTS_009_NAME=Worker Process Restarts
+ASPNET_WPS_RESTARTS_009_HELP=Number of times a worker process has restarted on the machine.
+
+ASPNET_REQUEST_WAIT_TIME_009_NAME=Request Wait Time
+ASPNET_REQUEST_WAIT_TIME_009_HELP=The number of milliseconds the most recent request was waiting in the queue.
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_NAME=State Server Sessions Active
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_NAME=State Server Sessions Abandoned
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_NAME=State Server Sessions Timed Out
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_NAME=State Server Sessions Total
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_HELP=The number of sessions total.
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_009_NAME=Anonymous Requests
+ASPNET_ANONYMOUS_REQUESTS_009_HELP=Number of requests utilizing anonymous authentication.
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_NAME=Anonymous Requests/Sec
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_HELP=Number of Authentication Anonymous Requests/Sec
+
+ASPNET_TOTAL_CACHE_ENTRIES_009_NAME=Cache Total Entries
+ASPNET_TOTAL_CACHE_ENTRIES_009_HELP=Total number of entries within the cache (both internal and user added)
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_NAME=Cache Total Turnover Rate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the total cache per second.
+
+ASPNET_TOTAL_CACHE_HITS_009_NAME=Cache Total Hits
+ASPNET_TOTAL_CACHE_HITS_009_HELP=Total number of hits from the cache.
+
+ASPNET_TOTAL_CACHE_MISSES_009_NAME=Cache Total Misses
+ASPNET_TOTAL_CACHE_MISSES_009_HELP=Total number of cache misses.
+
+ASPNET_TOTAL_CACHE_RATIO_009_NAME=Cache Total Hit Ratio
+ASPNET_TOTAL_CACHE_RATIO_009_HELP=Ratio of hits from all cache calls.
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_NAME=Cache Total Hit Ratio Base
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_HELP=Cache Total Hit Ratio Base
+
+ASPNET_API_CACHE_ENTRIES_009_NAME=Cache API Entries
+ASPNET_API_CACHE_ENTRIES_009_HELP=Total number of entries within the cache added by the user.
+
+ASPNET_API_CACHE_TURNOVER_RATE_009_NAME=Cache API Turnover Rate
+ASPNET_API_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the API cache per second.
+
+ASPNET_API_CACHE_HITS_009_NAME=Cache API Hits
+ASPNET_API_CACHE_HITS_009_HELP=Number of cache hits from user code.
+
+ASPNET_API_CACHE_MISSES_009_NAME=Cache API Misses
+ASPNET_API_CACHE_MISSES_009_HELP=Number of cache misses called from user code.
+
+ASPNET_API_CACHE_RATIO_009_NAME=Cache API Hit Ratio
+ASPNET_API_CACHE_RATIO_009_HELP=Ratio of hits called from user code.
+
+ASPNET_API_CACHE_RATIO_BASE_009_NAME=Cache API Hit Ratio Base
+ASPNET_API_CACHE_RATIO_BASE_009_HELP=Cache API Hit Ratio Base
+
+ASPNET_OUTPUT_CACHE_ENTRIES_009_NAME=Output Cache Entries
+ASPNET_OUTPUT_CACHE_ENTRIES_009_HELP=Current number of entries in the output cache.
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_NAME=Output Cache Turnover Rate
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the output cache per second.
+
+ASPNET_OUTPUT_CACHE_HITS_009_NAME=Output Cache Hits
+ASPNET_OUTPUT_CACHE_HITS_009_HELP=Total number of ouput cacheable requests served from the output cache.
+
+ASPNET_OUTPUT_CACHE_MISSES_009_NAME=Output Cache Misses
+ASPNET_OUTPUT_CACHE_MISSES_009_HELP=Total number of ouput cacheable requests not served from the output cache.
+
+ASPNET_OUTPUT_CACHE_RATIO_009_NAME=Output Cache Hit Ratio
+ASPNET_OUTPUT_CACHE_RATIO_009_HELP=Ratio of hits to requests for output cacheable requests.
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_NAME=Output Cache Hit Ratio Base
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_HELP=Output Cache Hit Ratio Base
+
+ASPNET_COMPILATIONS_009_NAME=Compilations Total
+ASPNET_COMPILATIONS_009_HELP=Number of .asax, .ascx, .ashx, .asmx, or .aspx source files dynamically compiled.
+
+ASPNET_DEBUGGING_REQUESTS_009_NAME=Debugging Requests
+ASPNET_DEBUGGING_REQUESTS_009_HELP=Number of debugging requests processed.
+
+ASPNET_ERRORS_PRE_PROCESSING_009_NAME=Errors During Preprocessing
+ASPNET_ERRORS_PRE_PROCESSING_009_HELP=Number of errors that have occurred during parsing and configuration.
+
+ASPNET_ERRORS_COMPILING_009_NAME=Errors During Compilation
+ASPNET_ERRORS_COMPILING_009_HELP=Number of errors that have occurred during compilation.
+
+ASPNET_ERRORS_DURING_REQUEST_009_NAME=Errors During Execution
+ASPNET_ERRORS_DURING_REQUEST_009_HELP=Number of errors that have occurred during the processing of a request.
+
+ASPNET_ERRORS_UNHANDLED_009_NAME=Errors Unhandled During Execution
+ASPNET_ERRORS_UNHANDLED_009_HELP=Number of errors not handled by user code, but by the default error handler.
+
+ASPNET_ERRORS_UNHANDLED_RATE_009_NAME=Errors Unhandled During Execution/Sec
+ASPNET_ERRORS_UNHANDLED_RATE_009_HELP=Rate of unhandled errors.
+
+ASPNET_ERRORS_TOTAL_009_NAME=Errors Total
+ASPNET_ERRORS_TOTAL_009_HELP=Total number of errors occurred.
+
+ASPNET_ERRORS_TOTAL_RATE_009_NAME=Errors Total/Sec
+ASPNET_ERRORS_TOTAL_RATE_009_HELP=Rate of errors occurred.
+
+ASPNET_PIPELINES_009_NAME=Pipeline Instance Count
+ASPNET_PIPELINES_009_HELP=Number of active pipeline instances.
+
+ASPNET_REQUEST_BYTES_IN_009_NAME=Request Bytes In Total
+ASPNET_REQUEST_BYTES_IN_009_HELP=The total size, in bytes, of all requests.
+
+ASPNET_REQUEST_BYTES_OUT_009_NAME=Request Bytes Out Total
+ASPNET_REQUEST_BYTES_OUT_009_HELP=The total size, in bytes, of responses sent to a client. This does not include standard HTTP response headers.
+
+ASPNET_REQUESTS_EXECUTING_009_NAME=Requests Executing
+ASPNET_REQUESTS_EXECUTING_009_HELP=The number of requests currently executing.
+
+ASPNET_REQUESTS_FAILED_009_NAME=Requests Failed
+ASPNET_REQUESTS_FAILED_009_HELP=Total number of failed requests.
+
+ASPNET_REQUESTS_NOT_FOUND_009_NAME=Requests Not Found
+ASPNET_REQUESTS_NOT_FOUND_009_HELP=The number of requests for resources that were not found.
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_NAME=Requests Not Authorized
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_HELP=Number of requests failed due to unauthorized access.
+
+ASPNET_REQUESTS_TIMED_OUT_009_NAME=Requests Timed Out
+ASPNET_REQUESTS_TIMED_OUT_009_HELP=The number of requests that timed out.
+
+ASPNET_REQUESTS_SUCCEDED_009_NAME=Requests Succeeded
+ASPNET_REQUESTS_SUCCEDED_009_HELP=The number of requests that executed successfully.
+
+ASPNET_REQUESTS_TOTAL_009_NAME=Requests Total
+ASPNET_REQUESTS_TOTAL_009_HELP=The total number of requests since the application was started.
+
+ASPNET_REQUESTS_TOTAL_RATE_009_NAME=Requests/Sec
+ASPNET_REQUESTS_TOTAL_RATE_009_HELP=The number of requests executed per second.
+
+ASPNET_SESSIONS_ACTIVE_009_NAME=Sessions Active
+ASPNET_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_SESSIONS_ABANDONED_009_NAME=Sessions Abandoned
+ASPNET_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_SESSIONS_TIMED_OUT_009_NAME=Sessions Timed Out
+ASPNET_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_SESSIONS_TOTAL_009_NAME=Sessions Total
+ASPNET_SESSIONS_TOTAL_009_HELP=Total number of sessions since the application was started.
+
+ASPNET_TRANSACTIONS_ABORTED_009_NAME=Transactions Aborted
+ASPNET_TRANSACTIONS_ABORTED_009_HELP=The number of transactions aborted.
+
+ASPNET_TRANSACTIONS_COMMITTED_009_NAME=Transactions Committed
+ASPNET_TRANSACTIONS_COMMITTED_009_HELP=The number of transactions committed.
+
+ASPNET_TRANSACTIONS_PENDING_009_NAME=Transactions Pending
+ASPNET_TRANSACTIONS_PENDING_009_HELP=Number of transactions in progress.
+
+ASPNET_TRANSACTIONS_TOTAL_009_NAME=Transactions Total
+ASPNET_TRANSACTIONS_TOTAL_009_HELP=The total number of transactions since the application was started.
+
+ASPNET_TRANSACTIONS_RATE_009_NAME=Transactions/Sec
+ASPNET_TRANSACTIONS_RATE_009_HELP=Transactions started per second.
+
+;;
+;; ASP.NET System Counters
+;;
+
+ASPNET_APPLICATION_RESTARTS_011_NAME=Application Restarts
+ASPNET_APPLICATION_RESTARTS_011_HELP=Web T[o[̗LԒɃAvP[VċNꂽ񐔂łB
+
+ASPNET_APPLICATIONS_RUNNING_011_NAME=Applications Running
+ASPNET_APPLICATIONS_RUNNING_011_HELP=ݎs Web AvP[V̐łB
+
+ASPNET_REQUESTS_DISCONNECTED_011_NAME=Requests Disconnected
+ASPNET_REQUESTS_DISCONNECTED_011_HELP=ʐMG[܂̓[U[ɂĐؒfꂽv̐łB
+
+ASPNET_REQUEST_EXECUTION_TIME_011_NAME=Request Execution Time
+ASPNET_REQUEST_EXECUTION_TIME_011_HELP=Ō̗vŝɔ₵~błB
+
+ASPNET_REQUESTS_REJECTED_011_NAME=Requests Rejected
+ASPNET_REQUESTS_REJECTED_011_HELP=vςɂȂ߂ɋۂꂽv̐łB
+
+ASPNET_REQUESTS_QUEUED_011_NAME=Requests Queued
+ASPNET_REQUESTS_QUEUED_011_HELP=҂̗v̐łB
+
+ASPNET_WPS_RUNNING_011_NAME=Worker Processes Running
+ASPNET_WPS_RUNNING_011_HELP=Rs[^Ŏs̃[J[ vZX̐łB
+
+ASPNET_WPS_RESTARTS_011_NAME=Worker Process Restarts
+ASPNET_WPS_RESTARTS_011_HELP=Rs[^Ń[J[ vZXċNꂽ񐔂łB
+
+ASPNET_REQUEST_WAIT_TIME_011_NAME=Request Wait Time
+ASPNET_REQUEST_WAIT_TIME_011_HELP=Ō̗vAL[ő҂Ă鎞 (~b) łB
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_011_NAME=State Server Sessions Active
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_011_HELP=݃ANeBuȃZbV̐łB
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_011_NAME=State Server Sessions Abandoned
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_011_HELP=IɔjꂽZbV̐łB
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_011_NAME=State Server Sessions Timed Out
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_011_HELP=^CAEgZbV̐łB
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_011_NAME=State Server Sessions Total
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_011_HELP=ZbV̍vłB
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_011_NAME=Anonymous Requests
+ASPNET_ANONYMOUS_REQUESTS_011_HELP=F؂gpv̐łB
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_011_NAME=Anonymous Requests/Sec
+ASPNET_ANONYMOUS_REQUESTS_RATE_011_HELP=Fؓv̐ (bP) łB
+
+ASPNET_TOTAL_CACHE_ENTRIES_011_NAME=Cache Total Entries
+ASPNET_TOTAL_CACHE_ENTRIES_011_HELP=LbṼGg̑ (у[U[lj)
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_011_NAME=Cache Total Turnover Rate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_011_HELP=lj/폜ꂽvLbV (bP) łB
+
+ASPNET_TOTAL_CACHE_HITS_011_NAME=Cache Total Hits
+ASPNET_TOTAL_CACHE_HITS_011_HELP=LbṼqbg̑łB
+
+ASPNET_TOTAL_CACHE_MISSES_011_NAME=Cache Total Misses
+ASPNET_TOTAL_CACHE_MISSES_011_HELP=LbV ~X̑łB
+
+ASPNET_TOTAL_CACHE_RATIO_011_NAME=Cache Total Hit Ratio
+ASPNET_TOTAL_CACHE_RATIO_011_HELP=ׂẴLbV̌Ăяõqbg̊łB
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_011_NAME=Cache Total Hit Ratio Base
+ASPNET_TOTAL_CACHE_RATIO_BASE_011_HELP=LbVvqbgx[XłB
+
+ASPNET_API_CACHE_ENTRIES_011_NAME=Cache API Entries
+ASPNET_API_CACHE_ENTRIES_011_HELP=[U[ljALbṼGg̑łB
+
+ASPNET_API_CACHE_TURNOVER_RATE_011_NAME=Cache API Turnover Rate
+ASPNET_API_CACHE_TURNOVER_RATE_011_HELP=lj/폜ꂽ API LbV (bP) łB
+
+ASPNET_API_CACHE_HITS_011_NAME=Cache API Hits
+ASPNET_API_CACHE_HITS_011_HELP=[U[ R[h̃LbV qbg̐łB
+
+ASPNET_API_CACHE_MISSES_011_NAME=Cache API Misses
+ASPNET_API_CACHE_MISSES_011_HELP=[U[ R[h̃LbV ~X̐łB
+
+ASPNET_API_CACHE_RATIO_011_NAME=Cache API Hit Ratio
+ASPNET_API_CACHE_RATIO_011_HELP=[U[ R[hĂяoAqbg̊łB
+
+ASPNET_API_CACHE_RATIO_BASE_011_NAME=Cache API Hit Ratio Base
+ASPNET_API_CACHE_RATIO_BASE_011_HELP=LbV API qbgx[XłB
+
+ASPNET_OUTPUT_CACHE_ENTRIES_011_NAME=Output Cache Entries
+ASPNET_OUTPUT_CACHE_ENTRIES_011_HELP=o̓LbV݂̌̃Gg̐łB
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_011_NAME=Output Cache Turnover Rate
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_011_HELP=lj/폜ꂽo̓LbV (bP) łB
+
+ASPNET_OUTPUT_CACHE_HITS_011_NAME=Output Cache Hits
+ASPNET_OUTPUT_CACHE_HITS_011_HELP=o̓LbV瑗Mꂽo̓LbV”\ȗv̍vłB
+
+ASPNET_OUTPUT_CACHE_MISSES_011_NAME=Output Cache Misses
+ASPNET_OUTPUT_CACHE_MISSES_011_HELP=o̓LbV瑗MȂo̓LbV”\ȗv̍vłB
+
+ASPNET_OUTPUT_CACHE_RATIO_011_NAME=Output Cache Hit Ratio
+ASPNET_OUTPUT_CACHE_RATIO_011_HELP=o͂̃LbV”\vɑ΂ṽqbgłB
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_011_NAME=Output Cache Hit Ratio Base
+ASPNET_OUTPUT_CACHE_RATIO_BASE_011_HELP=o̓LbV qbgx[XłB
+
+ASPNET_COMPILATIONS_011_NAME=Compilations Total
+ASPNET_COMPILATIONS_011_HELP=IɃRpCꂽ .asaxA.ascxA.ashxA.asmx ܂ .aspx \[X t@C̐łB
+
+ASPNET_DEBUGGING_REQUESTS_011_NAME=Debugging Requests
+ASPNET_DEBUGGING_REQUESTS_011_HELP=fobO NGXg̐łB
+
+ASPNET_ERRORS_PRE_PROCESSING_011_NAME=Errors During Preprocessing
+ASPNET_ERRORS_PRE_PROCESSING_011_HELP=͂ƍ\ɔG[̐łB
+
+ASPNET_ERRORS_COMPILING_011_NAME=Errors During Compilation
+ASPNET_ERRORS_COMPILING_011_HELP=RpCɔG[̐łB
+
+ASPNET_ERRORS_DURING_REQUEST_011_NAME=Errors During Execution
+ASPNET_ERRORS_DURING_REQUEST_011_HELP=v̏ɔG[̐łB
+
+ASPNET_ERRORS_UNHANDLED_011_NAME=Errors Unhandled During Execution
+ASPNET_ERRORS_UNHANDLED_011_HELP=[U[ R[hłȂÃG[ nhɂnhꂽG[̐łB
+
+ASPNET_ERRORS_UNHANDLED_RATE_011_NAME=Errors Unhandled During Execution/Sec
+ASPNET_ERRORS_UNHANDLED_RATE_011_HELP=̃G[̊łB
+
+ASPNET_ERRORS_TOTAL_011_NAME=Errors Total
+ASPNET_ERRORS_TOTAL_011_HELP=G[̑łB
+
+ASPNET_ERRORS_TOTAL_RATE_011_NAME=Errors Total/Sec
+ASPNET_ERRORS_TOTAL_RATE_011_HELP=G[̊łB
+
+ASPNET_PIPELINES_011_NAME=Pipeline Instance Count
+ASPNET_PIPELINES_011_HELP=ANeBu pCvC CX^X̐łB
+
+ASPNET_REQUEST_BYTES_IN_011_NAME=Request Bytes In Total
+ASPNET_REQUEST_BYTES_IN_011_HELP=ׂĂ̗v̑TCYł (oCg)B
+
+ASPNET_REQUEST_BYTES_OUT_011_NAME=Request Bytes Out Total
+ASPNET_REQUEST_BYTES_OUT_011_HELP=NCAgɑMꂽ̑TCYł (oCg)Bɂ́AHTTP wb_[͊܂܂Ă܂B
+
+ASPNET_REQUESTS_EXECUTING_011_NAME=Requests Executing
+ASPNET_REQUESTS_EXECUTING_011_HELP=ݎsĂv̐łB
+
+ASPNET_REQUESTS_FAILED_011_NAME=Requests Failed
+ASPNET_REQUESTS_FAILED_011_HELP=sv̑łB
+
+ASPNET_REQUESTS_NOT_FOUND_011_NAME=Requests Not Found
+ASPNET_REQUESTS_NOT_FOUND_011_HELP=‚Ȃ\[XvłB
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_011_NAME=Requests Not Authorized
+ASPNET_REQUESTS_NOT_AUTHORIZED_011_HELP=F؂̂ȂANZXs߁AvɎs܂B
+
+ASPNET_REQUESTS_TIMED_OUT_011_NAME=Requests Timed Out
+ASPNET_REQUESTS_TIMED_OUT_011_HELP=^CAEgv̐łB
+
+ASPNET_REQUESTS_SUCCEDED_011_NAME=Requests Succeeded
+ASPNET_REQUESTS_SUCCEDED_011_HELP=sɐv̐łB
+
+ASPNET_REQUESTS_TOTAL_011_NAME=Requests Total
+ASPNET_REQUESTS_TOTAL_011_HELP=AvP[VJn̗v̍vłB
+
+ASPNET_REQUESTS_TOTAL_RATE_011_NAME=Requests/Sec
+ASPNET_REQUESTS_TOTAL_RATE_011_HELP=1 bƂɎsv̐łB
+
+ASPNET_SESSIONS_ACTIVE_011_NAME=Sessions Active
+ASPNET_SESSIONS_ACTIVE_011_HELP=݃ANeBuȃZbV̐łB
+
+ASPNET_SESSIONS_ABANDONED_011_NAME=Sessions Abandoned
+ASPNET_SESSIONS_ABANDONED_011_HELP=IɔjꂽZbV̐łB
+
+ASPNET_SESSIONS_TIMED_OUT_011_NAME=Sessions Timed Out
+ASPNET_SESSIONS_TIMED_OUT_011_HELP=^CAEgZbV̐łB
+
+ASPNET_SESSIONS_TOTAL_011_NAME=Sessions Total
+ASPNET_SESSIONS_TOTAL_011_HELP=AvP[VJñZbV̍vłB
+
+ASPNET_TRANSACTIONS_ABORTED_011_NAME=Transactions Aborted
+ASPNET_TRANSACTIONS_ABORTED_011_HELP=~ꂽgUNV̐łB
+
+ASPNET_TRANSACTIONS_COMMITTED_011_NAME=Transactions Committed
+ASPNET_TRANSACTIONS_COMMITTED_011_HELP=R~bggUNV̐łB
+
+ASPNET_TRANSACTIONS_PENDING_011_NAME=Transactions Pending
+ASPNET_TRANSACTIONS_PENDING_011_HELP=̃gUNVłB
+
+ASPNET_TRANSACTIONS_TOTAL_011_NAME=Transactions Total
+ASPNET_TRANSACTIONS_TOTAL_011_HELP=AvP[VJñgUNV̍vłB
+
+ASPNET_TRANSACTIONS_RATE_011_NAME=Transactions/Sec
+ASPNET_TRANSACTIONS_RATE_011_HELP=1 bɊJngUNVłB
+
diff --git a/src/inc/1041/aspnet_perf2.ini b/src/inc/1041/aspnet_perf2.ini
new file mode 100644
index 0000000..d08121b
--- /dev/null
+++ b/src/inc/1041/aspnet_perf2.ini
@@ -0,0 +1,411 @@
+[info]
+drivername=ASP.NET
+symbolfile=aspnet_perf.h
+
+[languages]
+011=Japanese
+009=English
+
+[objects]
+OBJECT_1_009_NAME=ASP.NET
+OBJECT_2_009_NAME=ASP.NET Applications
+
+OBJECT_1_011_NAME=ASP.NET
+OBJECT_2_011_NAME=ASP.NET Applications
+
+[text]
+OBJECT_1_009_NAME=ASP.NET
+OBJECT_1_009_HELP=ASP.NET global performance counters
+OBJECT_2_009_NAME=ASP.NET Applications
+OBJECT_2_009_HELP=ASP.NET Application performance counters
+
+OBJECT_1_011_NAME=ASP.NET
+OBJECT_1_011_HELP=ASP.NET O[o p[tH[}X JE^
+OBJECT_2_011_NAME=ASP.NET Applications
+OBJECT_2_011_HELP=ASP.NET AvP[V p[tH[}X JE^
+
+;;
+;; ASP.NET System Counters
+;;
+
+ASPNET_APPLICATION_RESTARTS_009_NAME=Application Restarts
+ASPNET_APPLICATION_RESTARTS_009_HELP=Number of times the application has been restarted during the web server's lifetime.
+
+ASPNET_APPLICATIONS_RUNNING_009_NAME=Applications Running
+ASPNET_APPLICATIONS_RUNNING_009_HELP=Number of currently running web applications.
+
+ASPNET_REQUESTS_DISCONNECTED_009_NAME=Requests Disconnected
+ASPNET_REQUESTS_DISCONNECTED_009_HELP=The number of requests disconnected due to communication errors or user terminated.
+
+ASPNET_REQUEST_EXECUTION_TIME_009_NAME=Request Execution Time
+ASPNET_REQUEST_EXECUTION_TIME_009_HELP=The number of milliseconds that it took to execute the most recent request.
+
+ASPNET_REQUESTS_REJECTED_009_NAME=Requests Rejected
+ASPNET_REQUESTS_REJECTED_009_HELP=The number of requests rejected because the request queue was full.
+
+ASPNET_REQUESTS_QUEUED_009_NAME=Requests Queued
+ASPNET_REQUESTS_QUEUED_009_HELP=The number of requests waiting to be processed.
+
+ASPNET_WPS_RUNNING_009_NAME=Worker Processes Running
+ASPNET_WPS_RUNNING_009_HELP=Number of worker processes running on the machine.
+
+ASPNET_WPS_RESTARTS_009_NAME=Worker Process Restarts
+ASPNET_WPS_RESTARTS_009_HELP=Number of times a worker process has restarted on the machine.
+
+ASPNET_REQUEST_WAIT_TIME_009_NAME=Request Wait Time
+ASPNET_REQUEST_WAIT_TIME_009_HELP=The number of milliseconds the most recent request was waiting in the queue.
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_NAME=State Server Sessions Active
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_NAME=State Server Sessions Abandoned
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_NAME=State Server Sessions Timed Out
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_NAME=State Server Sessions Total
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_009_HELP=The number of sessions total.
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_009_NAME=Anonymous Requests
+ASPNET_ANONYMOUS_REQUESTS_009_HELP=Number of requests utilizing anonymous authentication.
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_NAME=Anonymous Requests/Sec
+ASPNET_ANONYMOUS_REQUESTS_RATE_009_HELP=Number of Authentication Anonymous Requests/Sec
+
+ASPNET_TOTAL_CACHE_ENTRIES_009_NAME=Cache Total Entries
+ASPNET_TOTAL_CACHE_ENTRIES_009_HELP=Total number of entries within the cache (both internal and user added)
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_NAME=Cache Total Turnover Rate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the total cache per second.
+
+ASPNET_TOTAL_CACHE_HITS_009_NAME=Cache Total Hits
+ASPNET_TOTAL_CACHE_HITS_009_HELP=Total number of hits from the cache.
+
+ASPNET_TOTAL_CACHE_MISSES_009_NAME=Cache Total Misses
+ASPNET_TOTAL_CACHE_MISSES_009_HELP=Total number of cache misses.
+
+ASPNET_TOTAL_CACHE_RATIO_009_NAME=Cache Total Hit Ratio
+ASPNET_TOTAL_CACHE_RATIO_009_HELP=Ratio of hits from all cache calls.
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_NAME=Cache Total Hit Ratio Base
+ASPNET_TOTAL_CACHE_RATIO_BASE_009_HELP=Cache Total Hit Ratio Base
+
+ASPNET_API_CACHE_ENTRIES_009_NAME=Cache API Entries
+ASPNET_API_CACHE_ENTRIES_009_HELP=Total number of entries within the cache added by the user.
+
+ASPNET_API_CACHE_TURNOVER_RATE_009_NAME=Cache API Turnover Rate
+ASPNET_API_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the API cache per second.
+
+ASPNET_API_CACHE_HITS_009_NAME=Cache API Hits
+ASPNET_API_CACHE_HITS_009_HELP=Number of cache hits from user code.
+
+ASPNET_API_CACHE_MISSES_009_NAME=Cache API Misses
+ASPNET_API_CACHE_MISSES_009_HELP=Number of cache misses called from user code.
+
+ASPNET_API_CACHE_RATIO_009_NAME=Cache API Hit Ratio
+ASPNET_API_CACHE_RATIO_009_HELP=Ratio of hits called from user code.
+
+ASPNET_API_CACHE_RATIO_BASE_009_NAME=Cache API Hit Ratio Base
+ASPNET_API_CACHE_RATIO_BASE_009_HELP=Cache API Hit Ratio Base
+
+ASPNET_OUTPUT_CACHE_ENTRIES_009_NAME=Output Cache Entries
+ASPNET_OUTPUT_CACHE_ENTRIES_009_HELP=Current number of entries in the output cache.
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_NAME=Output Cache Turnover Rate
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_009_HELP=Number of additions and removals to the output cache per second.
+
+ASPNET_OUTPUT_CACHE_HITS_009_NAME=Output Cache Hits
+ASPNET_OUTPUT_CACHE_HITS_009_HELP=Total number of ouput cacheable requests served from the output cache.
+
+ASPNET_OUTPUT_CACHE_MISSES_009_NAME=Output Cache Misses
+ASPNET_OUTPUT_CACHE_MISSES_009_HELP=Total number of ouput cacheable requests not served from the output cache.
+
+ASPNET_OUTPUT_CACHE_RATIO_009_NAME=Output Cache Hit Ratio
+ASPNET_OUTPUT_CACHE_RATIO_009_HELP=Ratio of hits to requests for output cacheable requests.
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_NAME=Output Cache Hit Ratio Base
+ASPNET_OUTPUT_CACHE_RATIO_BASE_009_HELP=Output Cache Hit Ratio Base
+
+ASPNET_COMPILATIONS_009_NAME=Compilations Total
+ASPNET_COMPILATIONS_009_HELP=Number of .asax, .ascx, .ashx, .asmx, or .aspx source files dynamically compiled.
+
+ASPNET_DEBUGGING_REQUESTS_009_NAME=Debugging Requests
+ASPNET_DEBUGGING_REQUESTS_009_HELP=Number of debugging requests processed.
+
+ASPNET_ERRORS_PRE_PROCESSING_009_NAME=Errors During Preprocessing
+ASPNET_ERRORS_PRE_PROCESSING_009_HELP=Number of errors that have occurred during parsing and configuration.
+
+ASPNET_ERRORS_COMPILING_009_NAME=Errors During Compilation
+ASPNET_ERRORS_COMPILING_009_HELP=Number of errors that have occurred during compilation.
+
+ASPNET_ERRORS_DURING_REQUEST_009_NAME=Errors During Execution
+ASPNET_ERRORS_DURING_REQUEST_009_HELP=Number of errors that have occurred during the processing of a request.
+
+ASPNET_ERRORS_UNHANDLED_009_NAME=Errors Unhandled During Execution
+ASPNET_ERRORS_UNHANDLED_009_HELP=Number of errors not handled by user code, but by the default error handler.
+
+ASPNET_ERRORS_UNHANDLED_RATE_009_NAME=Errors Unhandled During Execution/Sec
+ASPNET_ERRORS_UNHANDLED_RATE_009_HELP=Rate of unhandled errors.
+
+ASPNET_ERRORS_TOTAL_009_NAME=Errors Total
+ASPNET_ERRORS_TOTAL_009_HELP=Total number of errors occurred.
+
+ASPNET_ERRORS_TOTAL_RATE_009_NAME=Errors Total/Sec
+ASPNET_ERRORS_TOTAL_RATE_009_HELP=Rate of errors occurred.
+
+ASPNET_PIPELINES_009_NAME=Pipeline Instance Count
+ASPNET_PIPELINES_009_HELP=Number of active pipeline instances.
+
+ASPNET_REQUEST_BYTES_IN_009_NAME=Request Bytes In Total
+ASPNET_REQUEST_BYTES_IN_009_HELP=The total size, in bytes, of all requests.
+
+ASPNET_REQUEST_BYTES_OUT_009_NAME=Request Bytes Out Total
+ASPNET_REQUEST_BYTES_OUT_009_HELP=The total size, in bytes, of responses sent to a client. This does not include standard HTTP response headers.
+
+ASPNET_REQUESTS_EXECUTING_009_NAME=Requests Executing
+ASPNET_REQUESTS_EXECUTING_009_HELP=The number of requests currently executing.
+
+ASPNET_REQUESTS_FAILED_009_NAME=Requests Failed
+ASPNET_REQUESTS_FAILED_009_HELP=Total number of failed requests.
+
+ASPNET_REQUESTS_NOT_FOUND_009_NAME=Requests Not Found
+ASPNET_REQUESTS_NOT_FOUND_009_HELP=The number of requests for resources that were not found.
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_NAME=Requests Not Authorized
+ASPNET_REQUESTS_NOT_AUTHORIZED_009_HELP=Number of requests failed due to unauthorized access.
+
+ASPNET_REQUESTS_TIMED_OUT_009_NAME=Requests Timed Out
+ASPNET_REQUESTS_TIMED_OUT_009_HELP=The number of requests that timed out.
+
+ASPNET_REQUESTS_SUCCEDED_009_NAME=Requests Succeeded
+ASPNET_REQUESTS_SUCCEDED_009_HELP=The number of requests that executed successfully.
+
+ASPNET_REQUESTS_TOTAL_009_NAME=Requests Total
+ASPNET_REQUESTS_TOTAL_009_HELP=The total number of requests since the application was started.
+
+ASPNET_REQUESTS_TOTAL_RATE_009_NAME=Requests/Sec
+ASPNET_REQUESTS_TOTAL_RATE_009_HELP=The number of requests executed per second.
+
+ASPNET_SESSIONS_ACTIVE_009_NAME=Sessions Active
+ASPNET_SESSIONS_ACTIVE_009_HELP=The current number of sessions currently active.
+
+ASPNET_SESSIONS_ABANDONED_009_NAME=Sessions Abandoned
+ASPNET_SESSIONS_ABANDONED_009_HELP=The number of sessions that have been explicitly abandoned.
+
+ASPNET_SESSIONS_TIMED_OUT_009_NAME=Sessions Timed Out
+ASPNET_SESSIONS_TIMED_OUT_009_HELP=The number of sessions timed out.
+
+ASPNET_SESSIONS_TOTAL_009_NAME=Sessions Total
+ASPNET_SESSIONS_TOTAL_009_HELP=Total number of sessions since the application was started.
+
+ASPNET_TRANSACTIONS_ABORTED_009_NAME=Transactions Aborted
+ASPNET_TRANSACTIONS_ABORTED_009_HELP=The number of transactions aborted.
+
+ASPNET_TRANSACTIONS_COMMITTED_009_NAME=Transactions Committed
+ASPNET_TRANSACTIONS_COMMITTED_009_HELP=The number of transactions committed.
+
+ASPNET_TRANSACTIONS_PENDING_009_NAME=Transactions Pending
+ASPNET_TRANSACTIONS_PENDING_009_HELP=Number of transactions in progress.
+
+ASPNET_TRANSACTIONS_TOTAL_009_NAME=Transactions Total
+ASPNET_TRANSACTIONS_TOTAL_009_HELP=The total number of transactions since the application was started.
+
+ASPNET_TRANSACTIONS_RATE_009_NAME=Transactions/Sec
+ASPNET_TRANSACTIONS_RATE_009_HELP=Transactions started per second.
+
+
+ASPNET_APPLICATION_RESTARTS_011_NAME=Application Restarts
+ASPNET_APPLICATION_RESTARTS_011_HELP=Web T[o[̗LԒɃAvP[VċNꂽ񐔂łB
+
+ASPNET_APPLICATIONS_RUNNING_011_NAME=Applications Running
+ASPNET_APPLICATIONS_RUNNING_011_HELP=ݎs Web AvP[V̐łB
+
+ASPNET_REQUESTS_DISCONNECTED_011_NAME=Requests Disconnected
+ASPNET_REQUESTS_DISCONNECTED_011_HELP=ʐMG[܂̓[U[ɂĐؒfꂽv̐łB
+
+ASPNET_REQUEST_EXECUTION_TIME_011_NAME=Request Execution Time
+ASPNET_REQUEST_EXECUTION_TIME_011_HELP=Ō̗vŝɔ₵~błB
+
+ASPNET_REQUESTS_REJECTED_011_NAME=Requests Rejected
+ASPNET_REQUESTS_REJECTED_011_HELP=vςɂȂ߂ɋۂꂽv̐łB
+
+ASPNET_REQUESTS_QUEUED_011_NAME=Requests Queued
+ASPNET_REQUESTS_QUEUED_011_HELP=҂̗v̐łB
+
+ASPNET_WPS_RUNNING_011_NAME=Worker Processes Running
+ASPNET_WPS_RUNNING_011_HELP=Rs[^Ŏs̃[J[ vZX̐łB
+
+ASPNET_WPS_RESTARTS_011_NAME=Worker Process Restarts
+ASPNET_WPS_RESTARTS_011_HELP=Rs[^Ń[J[ vZXċNꂽ񐔂łB
+
+ASPNET_REQUEST_WAIT_TIME_011_NAME=Request Wait Time
+ASPNET_REQUEST_WAIT_TIME_011_HELP=Ō̗vAL[ő҂Ă鎞 (~b) łB
+
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_011_NAME=State Server Sessions Active
+ASPNET_STATE_SERVER_SESSIONS_ACTIVE_011_HELP=݃ANeBuȃZbV̐łB
+
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_011_NAME=State Server Sessions Abandoned
+ASPNET_STATE_SERVER_SESSIONS_ABANDONED_011_HELP=IɔjꂽZbV̐łB
+
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_011_NAME=State Server Sessions Timed Out
+ASPNET_STATE_SERVER_SESSIONS_TIMED_OUT_011_HELP=^CAEgZbV̐łB
+
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_011_NAME=State Server Sessions Total
+ASPNET_STATE_SERVER_SESSIONS_TOTAL_011_HELP=ZbV̍vłB
+
+;;
+;; ASP.NET Application Counters
+;;
+
+ASPNET_ANONYMOUS_REQUESTS_011_NAME=Anonymous Requests
+ASPNET_ANONYMOUS_REQUESTS_011_HELP=F؂gpv̐łB
+
+ASPNET_ANONYMOUS_REQUESTS_RATE_011_NAME=Anonymous Requests/Sec
+ASPNET_ANONYMOUS_REQUESTS_RATE_011_HELP=Fؓv̐ (bP) łB
+
+ASPNET_TOTAL_CACHE_ENTRIES_011_NAME=Cache Total Entries
+ASPNET_TOTAL_CACHE_ENTRIES_011_HELP=LbṼGg̑ (у[U[lj)
+
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_011_NAME=Cache Total Turnover Rate
+ASPNET_TOTAL_CACHE_TURNOVER_RATE_011_HELP=lj/폜ꂽvLbV (bP) łB
+
+ASPNET_TOTAL_CACHE_HITS_011_NAME=Cache Total Hits
+ASPNET_TOTAL_CACHE_HITS_011_HELP=LbṼqbg̑łB
+
+ASPNET_TOTAL_CACHE_MISSES_011_NAME=Cache Total Misses
+ASPNET_TOTAL_CACHE_MISSES_011_HELP=LbV ~X̑łB
+
+ASPNET_TOTAL_CACHE_RATIO_011_NAME=Cache Total Hit Ratio
+ASPNET_TOTAL_CACHE_RATIO_011_HELP=ׂẴLbV̌Ăяõqbg̊łB
+
+ASPNET_TOTAL_CACHE_RATIO_BASE_011_NAME=Cache Total Hit Ratio Base
+ASPNET_TOTAL_CACHE_RATIO_BASE_011_HELP=LbVvqbgx[XłB
+
+ASPNET_API_CACHE_ENTRIES_011_NAME=Cache API Entries
+ASPNET_API_CACHE_ENTRIES_011_HELP=[U[ljALbṼGg̑łB
+
+ASPNET_API_CACHE_TURNOVER_RATE_011_NAME=Cache API Turnover Rate
+ASPNET_API_CACHE_TURNOVER_RATE_011_HELP=lj/폜ꂽ API LbV (bP) łB
+
+ASPNET_API_CACHE_HITS_011_NAME=Cache API Hits
+ASPNET_API_CACHE_HITS_011_HELP=[U[ R[h̃LbV qbg̐łB
+
+ASPNET_API_CACHE_MISSES_011_NAME=Cache API Misses
+ASPNET_API_CACHE_MISSES_011_HELP=[U[ R[h̃LbV ~X̐łB
+
+ASPNET_API_CACHE_RATIO_011_NAME=Cache API Hit Ratio
+ASPNET_API_CACHE_RATIO_011_HELP=[U[ R[hĂяoAqbg̊łB
+
+ASPNET_API_CACHE_RATIO_BASE_011_NAME=Cache API Hit Ratio Base
+ASPNET_API_CACHE_RATIO_BASE_011_HELP=LbV API qbgx[XłB
+
+ASPNET_OUTPUT_CACHE_ENTRIES_011_NAME=Output Cache Entries
+ASPNET_OUTPUT_CACHE_ENTRIES_011_HELP=o̓LbV݂̌̃Gg̐łB
+
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_011_NAME=Output Cache Turnover Rate
+ASPNET_OUTPUT_CACHE_TURNOVER_RATE_011_HELP=lj/폜ꂽo̓LbV (bP) łB
+
+ASPNET_OUTPUT_CACHE_HITS_011_NAME=Output Cache Hits
+ASPNET_OUTPUT_CACHE_HITS_011_HELP=o̓LbV瑗Mꂽo̓LbV”\ȗv̍vłB
+
+ASPNET_OUTPUT_CACHE_MISSES_011_NAME=Output Cache Misses
+ASPNET_OUTPUT_CACHE_MISSES_011_HELP=o̓LbV瑗MȂo̓LbV”\ȗv̍vłB
+
+ASPNET_OUTPUT_CACHE_RATIO_011_NAME=Output Cache Hit Ratio
+ASPNET_OUTPUT_CACHE_RATIO_011_HELP=o͂̃LbV”\vɑ΂ṽqbgłB
+
+ASPNET_OUTPUT_CACHE_RATIO_BASE_011_NAME=Output Cache Hit Ratio Base
+ASPNET_OUTPUT_CACHE_RATIO_BASE_011_HELP=o̓LbV qbgx[XłB
+
+ASPNET_COMPILATIONS_011_NAME=Compilations Total
+ASPNET_COMPILATIONS_011_HELP=IɃRpCꂽ .asaxA.ascxA.ashxA.asmx ܂ .aspx \[X t@C̐łB
+
+ASPNET_DEBUGGING_REQUESTS_011_NAME=Debugging Requests
+ASPNET_DEBUGGING_REQUESTS_011_HELP=fobO NGXg̐łB
+
+ASPNET_ERRORS_PRE_PROCESSING_011_NAME=Errors During Preprocessing
+ASPNET_ERRORS_PRE_PROCESSING_011_HELP=͂ƍ\ɔG[̐łB
+
+ASPNET_ERRORS_COMPILING_011_NAME=Errors During Compilation
+ASPNET_ERRORS_COMPILING_011_HELP=RpCɔG[̐łB
+
+ASPNET_ERRORS_DURING_REQUEST_011_NAME=Errors During Execution
+ASPNET_ERRORS_DURING_REQUEST_011_HELP=v̏ɔG[̐łB
+
+ASPNET_ERRORS_UNHANDLED_011_NAME=Errors Unhandled During Execution
+ASPNET_ERRORS_UNHANDLED_011_HELP=[U[ R[hłȂÃG[ nhɂnhꂽG[̐łB
+
+ASPNET_ERRORS_UNHANDLED_RATE_011_NAME=Errors Unhandled During Execution/Sec
+ASPNET_ERRORS_UNHANDLED_RATE_011_HELP=̃G[̊łB
+
+ASPNET_ERRORS_TOTAL_011_NAME=Errors Total
+ASPNET_ERRORS_TOTAL_011_HELP=G[̑łB
+
+ASPNET_ERRORS_TOTAL_RATE_011_NAME=Errors Total/Sec
+ASPNET_ERRORS_TOTAL_RATE_011_HELP=G[̊łB
+
+ASPNET_PIPELINES_011_NAME=Pipeline Instance Count
+ASPNET_PIPELINES_011_HELP=ANeBu pCvC CX^X̐łB
+
+ASPNET_REQUEST_BYTES_IN_011_NAME=Request Bytes In Total
+ASPNET_REQUEST_BYTES_IN_011_HELP=ׂĂ̗v̑TCYł (oCg)B
+
+ASPNET_REQUEST_BYTES_OUT_011_NAME=Request Bytes Out Total
+ASPNET_REQUEST_BYTES_OUT_011_HELP=NCAgɑMꂽ̑TCYł (oCg)Bɂ́AHTTP wb_[͊܂܂Ă܂B
+
+ASPNET_REQUESTS_EXECUTING_011_NAME=Requests Executing
+ASPNET_REQUESTS_EXECUTING_011_HELP=ݎsĂv̐łB
+
+ASPNET_REQUESTS_FAILED_011_NAME=Requests Failed
+ASPNET_REQUESTS_FAILED_011_HELP=sv̑łB
+
+ASPNET_REQUESTS_NOT_FOUND_011_NAME=Requests Not Found
+ASPNET_REQUESTS_NOT_FOUND_011_HELP=‚Ȃ\[XvłB
+
+ASPNET_REQUESTS_NOT_AUTHORIZED_011_NAME=Requests Not Authorized
+ASPNET_REQUESTS_NOT_AUTHORIZED_011_HELP=F؂̂ȂANZXs߁AvɎs܂B
+
+ASPNET_REQUESTS_TIMED_OUT_011_NAME=Requests Timed Out
+ASPNET_REQUESTS_TIMED_OUT_011_HELP=^CAEgv̐łB
+
+ASPNET_REQUESTS_SUCCEDED_011_NAME=Requests Succeeded
+ASPNET_REQUESTS_SUCCEDED_011_HELP=sɐv̐łB
+
+ASPNET_REQUESTS_TOTAL_011_NAME=Requests Total
+ASPNET_REQUESTS_TOTAL_011_HELP=AvP[VJn̗v̍vłB
+
+ASPNET_REQUESTS_TOTAL_RATE_011_NAME=Requests/Sec
+ASPNET_REQUESTS_TOTAL_RATE_011_HELP=1 bƂɎsv̐łB
+
+ASPNET_SESSIONS_ACTIVE_011_NAME=Sessions Active
+ASPNET_SESSIONS_ACTIVE_011_HELP=݃ANeBuȃZbV̐łB
+
+ASPNET_SESSIONS_ABANDONED_011_NAME=Sessions Abandoned
+ASPNET_SESSIONS_ABANDONED_011_HELP=IɔjꂽZbV̐łB
+
+ASPNET_SESSIONS_TIMED_OUT_011_NAME=Sessions Timed Out
+ASPNET_SESSIONS_TIMED_OUT_011_HELP=^CAEgZbV̐łB
+
+ASPNET_SESSIONS_TOTAL_011_NAME=Sessions Total
+ASPNET_SESSIONS_TOTAL_011_HELP=AvP[VJñZbV̍vłB
+
+ASPNET_TRANSACTIONS_ABORTED_011_NAME=Transactions Aborted
+ASPNET_TRANSACTIONS_ABORTED_011_HELP=~ꂽgUNV̐łB
+
+ASPNET_TRANSACTIONS_COMMITTED_011_NAME=Transactions Committed
+ASPNET_TRANSACTIONS_COMMITTED_011_HELP=R~bggUNV̐łB
+
+ASPNET_TRANSACTIONS_PENDING_011_NAME=Transactions Pending
+ASPNET_TRANSACTIONS_PENDING_011_HELP=̃gUNVłB
+
+ASPNET_TRANSACTIONS_TOTAL_011_NAME=Transactions Total
+ASPNET_TRANSACTIONS_TOTAL_011_HELP=AvP[VJñgUNV̍vłB
+
+ASPNET_TRANSACTIONS_RATE_011_NAME=Transactions/Sec
+ASPNET_TRANSACTIONS_RATE_011_HELP=1 bɊJngUNVłB
+
diff --git a/src/inc/CMakeLists.txt b/src/inc/CMakeLists.txt
new file mode 100644
index 0000000..803ca3b
--- /dev/null
+++ b/src/inc/CMakeLists.txt
@@ -0,0 +1,87 @@
+set( CORGUIDS_IDL_SOURCES
+ cordebug.idl
+ xcordebug.idl
+ clrdata.idl
+ clrinternal.idl
+ xclrdata.idl
+ corprof.idl
+ corpub.idl
+ ivalidator.idl
+ ivehandler.idl
+ gchost.idl
+ fusionpriv.idl
+ mscorsvc.idl
+ tlbimpexp.idl
+ clrprivappxhosting.idl
+ clrprivbinding.idl
+ clrprivhosting.idl
+ clrprivruntimebinders.idl
+ corsym.idl
+ sospriv.idl
+)
+
+if(WIN32)
+#Build for corguids is done in two steps:
+#1. compile .idl to *_i.c : This is done using custom midl command
+#2. compile *_i.c to .lib
+
+# Get the current list of definitions to pass to midl
+get_compile_definitions(MIDL_DEFINITIONS)
+get_include_directories(MIDL_INCLUDE_DIRECTORIES)
+
+
+# Run custom midl command over each idl file
+FIND_PROGRAM( MIDL midl.exe )
+foreach(GENERATE_IDL IN LISTS CORGUIDS_IDL_SOURCES)
+ get_filename_component(IDLNAME ${GENERATE_IDL} NAME_WE)
+ set(OUT_NAME ${CMAKE_CURRENT_BINARY_DIR}/idls_out/${IDLNAME}_i.c)
+ list(APPEND CORGUIDS_SOURCES ${OUT_NAME})
+ add_custom_command(OUTPUT ${OUT_NAME}
+ COMMAND ${MIDL} ${MIDL_INCLUDE_DIRECTORIES} /h ${CMAKE_CURRENT_BINARY_DIR}/idls_out/${IDLNAME}.h ${MIDL_DEFINITIONS} /out ${CMAKE_CURRENT_BINARY_DIR}/idls_out ${CMAKE_CURRENT_SOURCE_DIR}/${GENERATE_IDL}
+ DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${GENERATE_IDL}
+ COMMENT "Compiling ${GENERATE_IDL}")
+endforeach(GENERATE_IDL)
+
+set_source_files_properties(${CORGUIDS_SOURCES}
+ PROPERTIES GENERATED TRUE)
+
+# Compile *_i.c as C files
+add_compile_options(/TC)
+
+else()
+
+#The MIDL tool exists for Windows only, so for other systems, we have the prebuilt xxx_i.c files checked in
+
+# The prebuilt files contain extra '!_MIDL_USE_GUIDDEF_' after the #endif, but not in the comment.
+# In order to not to have to modify these prebuilt files, we disable the extra tokens warning.
+add_compile_options(-Wno-extra-tokens)
+
+foreach(IDL_SOURCE IN LISTS CORGUIDS_IDL_SOURCES)
+ get_filename_component(IDLNAME ${IDL_SOURCE} NAME_WE)
+ set(C_SOURCE ../pal/prebuilt/idl/${IDLNAME}_i.c)
+ list(APPEND CORGUIDS_SOURCES ${C_SOURCE})
+endforeach(IDL_SOURCE)
+
+add_compile_options(-fPIC)
+
+endif(WIN32)
+
+# Compile *_i.c to lib
+_add_library(corguids ${CORGUIDS_SOURCES})
+
+# Binplace the inc files for packaging later.
+
+_install (FILES cfi.h
+ cor.h
+ cordebuginfo.h
+ coredistools.h
+ corhdr.h
+ corinfo.h
+ corjit.h
+ corjithost.h
+ opcode.def
+ openum.h
+ gcinfoencoder.h
+ gcinfotypes.h
+ DESTINATION inc)
+_install (TARGETS corguids DESTINATION lib)
diff --git a/src/inc/CrstTypeTool.cs b/src/inc/CrstTypeTool.cs
new file mode 100644
index 0000000..d6d90e4
--- /dev/null
+++ b/src/inc/CrstTypeTool.cs
@@ -0,0 +1,990 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+//
+// This tool exists to transform a high level description of Crst dependencies (i.e. which Crst type may be
+// acquired before or after other Crst types) into a header file that defines a enum to describe each Crst
+// type and tables that map type to numerical ranking and a string based name.
+//
+// To use the tool, run "csc.exe CrstTypeTool.cs" and run the resulting executable.
+//
+// The Crst type definition file is written in a very simple language. Comments begin with '//' and continue
+// to the end of the line. All remaining tokens after comment removal are simply sequences of non-whitespace
+// characters separated by whitespace. Keywords are case-insensitive and identifiers (which are always Crst
+// type names) are case sensitive. The language grammar is given below in EBNF-like form:
+//
+// TopLevel ::= CrstDefinition*
+//
+// CrstDefinition ::= 'Crst' <Crst type name> CrstDependency* 'End'
+//
+// CrstDependency ::= 'AcquiredBefore' <Crst type name>*
+// | 'AcquiredAfter' <Crst type name>*
+// | 'SameLevelAs' <Crst type name>*
+// | 'Unordered'
+//
+// Crst type names match the CrstType enums used in the source code minus the 'Crst' prefix. For example
+// CrstAppDomainCache is written as 'AppDomainCache' in the .def file.
+//
+// The dependency "A 'AcquiredBefore' B" indicates that CrstA may be legally held while CrstB is acquired.
+// Similarly "A 'AcquiredAfter' B" indicates that CrstA may be legally acquired while CrstB is held. "A
+// 'AcquiredBefore' B" is logically equivalent to "B 'AcquiredAfter' A" and authors may enter the dependency
+// is whichever seems to make the most sense to them (or add both rules if they so desire).
+//
+// 'Unordered' indicates that the Crst type does not participate in ranking (there should be very few Crsts
+// like this and those that are know how to avoid or deal with deadlocks manually).
+//
+// 'SameLevelAs' indicates the given Crst type may be acquired alongside any number of instances of the Crst
+// types indicated. "A 'SameLevel' B" automatically implies "B 'SameLevel' A" so it's not necessary to specify
+// the dependency both ways though authors can do so if they wish.
+//
+// Simple validation of the .def file (over and above syntax checking) is performed by this tool prior to
+// emitting the header file. This will catch logic errors such as referencing a Crst type that is not
+// defined or using the 'Unordered' attribute along with any other attribute within a single definition. It
+// will also catch cycles in the dependency graph (i.e. definitions that logically describe a system where the
+// Crst types can't be ranked).
+//
+
+using System;
+using System.Collections.Generic;
+using System.Text;
+using System.IO;
+using System.Text.RegularExpressions;
+
+// The main application class containing the program entry point.
+class CrstTypeTool
+{
+ // A hash containing every Crst type defined by the input .def file along with its attributes. Keyed by
+ // Crst type name (which is case sensitive and doesn't include the 'Crst' enum prefix).
+ Dictionary<string, CrstType> m_crsts = new Dictionary<string, CrstType>();
+
+ // The program entry point.
+ public static int Main()
+ {
+ try
+ {
+ // Calculate the filenames of the input and output files.
+ string inputFile = "CrstTypes.def";
+ string outputFile = "CrstTypes.h";
+
+ // A common error is to forget to check out the CrstTypes.h file first. Handle this case specially
+ // so we can give a good error message.
+ if (File.Exists(outputFile) && (File.GetAttributes(outputFile) & FileAttributes.ReadOnly) != 0)
+ {
+ Console.WriteLine(outputFile + " is read-only, you must check it out of TFS/SD first");
+ return 2;
+ }
+
+ // Create an instance of our application class to store state in (specifically the collection of
+ // Crst type definitions).
+ CrstTypeTool app = new CrstTypeTool();
+
+ // Create a parser for the CrstTypes.def file and run it over the input file (errors are signalled
+ // via exception, in common with all the following steps except validation).
+ new TypeFileParser().ParseFile(inputFile, app.m_crsts);
+
+ // Validate the collection of Crst type definitions we built up during parsing for common logic
+ // errors and the presence of dependency cycles. False is returned from ValidateCrsts if an error
+ // was detected (an error message will have already been output to the console at this point).
+ if (!app.ValidateCrsts())
+ return 3;
+
+ // Perform a topological sort to map each Crst type to a numeric ranking.
+ app.LevelCrsts();
+
+ // Emit the new header file containing Crst type definitions and ranking information.
+ app.WriteHeaderFile(outputFile);
+
+ // If we get here the transformation was successful; inform the user and we're done.
+ Console.WriteLine(outputFile + " successfully updated");
+ return 0;
+ }
+ catch (TypeFileParser.ParseError pe)
+ {
+ // Syntax errors specific to parsing the input file.
+ Console.WriteLine("ParseError: " + pe.Message);
+ return 4;
+ }
+ catch (Exception e)
+ {
+ // Any other general errors (file I/O problems, out of memory etc.).
+ Console.WriteLine("Unexpected exception:");
+ Console.WriteLine(e);
+ return 5;
+ }
+ }
+
+ // Emit the CrstTypes.h output file.
+ void WriteHeaderFile(string fileName)
+ {
+ FileStream stream = new FileStream(fileName, FileMode.Create, FileAccess.Write, FileShare.None);
+ StreamWriter writer = new StreamWriter(stream);
+
+ // Create a collection based on all the Crst types we've stored in the hash. We do this so we can sort
+ // the Crst types we emit (lexically, based on type name).
+ Dictionary<string, CrstType>.ValueCollection crstCollection = m_crsts.Values;
+ CrstType[] crsts = new CrstType[crstCollection.Count];
+ crstCollection.CopyTo(crsts, 0);
+ Array.Sort(crsts);
+
+ // Emit the header. Contains copyright information, the usual goop to avoid multiple inclusion and a
+ // header comment to discourage direct editing and point the user at the CrstTypes.def file instead
+ // (where all will be explained in greater detail).
+ writer.WriteLine("//");
+ writer.WriteLine("// Licensed to the .NET Foundation under one or more agreements.");
+ writer.WriteLine("// The .NET Foundation licenses this file to you under the MIT license.");
+ writer.WriteLine("// See the LICENSE file in the project root for more information.");
+ writer.WriteLine("//");
+ writer.WriteLine();
+ writer.WriteLine("#ifndef __CRST_TYPES_INCLUDED");
+ writer.WriteLine("#define __CRST_TYPES_INCLUDED");
+ writer.WriteLine();
+ writer.WriteLine("// **** THIS IS AN AUTOMATICALLY GENERATED HEADER FILE -- DO NOT EDIT!!! ****");
+ writer.WriteLine();
+ writer.WriteLine("// This file describes the range of Crst types available and their mapping to a numeric level (used by the");
+ writer.WriteLine("// runtime in debug mode to validate we're deadlock free). To modify these settings edit the");
+ writer.WriteLine("// file:CrstTypes.def file and run the clr\\bin\\CrstTypeTool utility to generate a new version of this file.");
+ writer.WriteLine();
+
+ // Emit the CrstType enum to define a value for each crst type (along with the kNumberOfCrstTypes
+ // constant).
+ writer.WriteLine("// Each Crst type is declared as a value in the following CrstType enum.");
+ writer.WriteLine("enum CrstType");
+ writer.WriteLine("{");
+ for (int i = 0; i < crsts.Length; i++)
+ writer.WriteLine(" Crst" + crsts[i].Name + " = " + i.ToString() + ",");
+ writer.WriteLine(" kNumberOfCrstTypes = " + crsts.Length.ToString());
+ writer.WriteLine("};");
+ writer.WriteLine();
+
+ // This is the end of the regular part of the header included by most files.
+ writer.WriteLine("#endif // __CRST_TYPES_INCLUDED");
+ writer.WriteLine();
+
+ // There is a second section of the header intended for inclusion only by vm\Crst.cpp. This contains
+ // some data tables used to map crst type to rank or name. We could instead define two separate
+ // headers, but on the whole it seems simpler to do it this way.
+ writer.WriteLine("// Define some debug data in one module only -- vm\\crst.cpp.");
+ writer.WriteLine("#if defined(__IN_CRST_CPP) && defined(_DEBUG)");
+ writer.WriteLine();
+
+ // Emit the crst type to rank mapping table.
+ writer.WriteLine("// An array mapping CrstType to level.");
+ writer.WriteLine("int g_rgCrstLevelMap[] =");
+ writer.WriteLine("{");
+ foreach (CrstType crst in crsts)
+ writer.WriteLine(" " + crst.Level + ",\t\t\t// Crst" + crst.Name);
+ writer.WriteLine("};");
+ writer.WriteLine();
+
+ // Emit the crst type to name mapping table.
+ writer.WriteLine("// An array mapping CrstType to a stringized name.");
+ writer.WriteLine("LPCSTR g_rgCrstNameMap[] =");
+ writer.WriteLine("{");
+ foreach (CrstType crst in crsts)
+ writer.WriteLine(" \"Crst" + crst.Name + "\",");
+ writer.WriteLine("};");
+ writer.WriteLine();
+
+ // Emit the constant Crst.cpp uses to record an unordered rank.
+ writer.WriteLine("// Define a special level constant for unordered locks.");
+ writer.WriteLine("#define CRSTUNORDERED (-1)");
+ writer.WriteLine();
+
+ // Emit a couple of inline helpers to map type to rank or name (and validate the type while they're at
+ // it).
+ writer.WriteLine("// Define inline helpers to map Crst types to names and levels.");
+ writer.WriteLine("inline static int GetCrstLevel(CrstType crstType)");
+ writer.WriteLine("{");
+ writer.WriteLine(" LIMITED_METHOD_CONTRACT;");
+ writer.WriteLine(" _ASSERTE(crstType >= 0 && crstType < kNumberOfCrstTypes);");
+ writer.WriteLine(" return g_rgCrstLevelMap[crstType];");
+ writer.WriteLine("}");
+ writer.WriteLine("inline static LPCSTR GetCrstName(CrstType crstType)");
+ writer.WriteLine("{");
+ writer.WriteLine(" LIMITED_METHOD_CONTRACT;");
+ writer.WriteLine(" _ASSERTE(crstType >= 0 && crstType < kNumberOfCrstTypes);");
+ writer.WriteLine(" return g_rgCrstNameMap[crstType];");
+ writer.WriteLine("}");
+ writer.WriteLine();
+
+ // And that's the end of the second section of the header file.
+ writer.WriteLine("#endif // defined(__IN_CRST_CPP) && defined(_DEBUG)");
+
+ writer.Close();
+ stream.Close();
+ }
+
+ // Peform checking of the Crst type definitions we've read just read. Various forms of logic error are
+ // scanned for including cycles in the dependency graph. Returns true if no errors are found. If false is
+ // returned a descriptive error message will have already been written to the console.
+ bool ValidateCrsts()
+ {
+ // Look at each Crst type definition in turn.
+ foreach (CrstType crst in m_crsts.Values)
+ {
+ // Catch Crst types that are referenced but never defined.
+ if (!crst.Defined)
+ {
+ Console.WriteLine(String.Format("Error: CrstType 'Crst{0}' is referenced without being defined",
+ crst.Name));
+ return false;
+ }
+
+ // Catch the use of the 'Unordered' attribute alongside the 'AcquiredBefore' attribute (which
+ // indicates an ordering).
+ if (crst.Level == CrstType.CrstUnordered && (crst.AcquiredBeforeList.Count > 0 ||
+ crst.Group != null))
+ {
+ Console.WriteLine(String.Format("Error: CrstType 'Crst{0}' is declared as both unordered and acquired before 'Crst{1}'",
+ crst.Name, crst.AcquiredBeforeList[0].Name));
+ return false;
+ }
+
+ // Catch the use of the 'Unordered' attribute alongside the 'SameLevelAs' attribute (which
+ // indicates an ordering).
+ if (crst.Level == CrstType.CrstUnordered && crst.Group != null)
+ {
+ Console.WriteLine(String.Format("Error: CrstType 'Crst{0}' is declared as both unordered and in the same level as another CrstType",
+ crst.Name));
+ return false;
+ }
+
+ // Catch the simple cycle where the Crst type depends on itself.
+ if (crst.AcquiredBeforeList.Contains(crst))
+ {
+ Console.WriteLine(String.Format("Error: CrstType 'Crst{0}' is declared as being acquired before itself",
+ crst.Name));
+ return false;
+ }
+
+ // Look for deeper cycles using a recursive algorithm in 'FindCycle()'.
+ List<CrstType> cycleList = new List<CrstType>();
+ if (FindCycle(crst, crst, cycleList))
+ {
+ Console.WriteLine(String.Format("Error: CrstType 'Crst{0}' is involved in a dependency cycle with the following CrstTypes:",
+ crst.Name));
+ foreach (CrstType cycleCrst in cycleList)
+ Console.WriteLine(String.Format(" Crst{0}", cycleCrst.Name));
+ return false;
+ }
+ }
+
+ // Perform normalization of each set of Crst types that are included in the same group (i.e. have a
+ // 'SameLevelAs' relationship). Normalization means that each Crst type in a group will have exactly
+ // the same set of dependency rules as all the others.
+ CrstTypeGroup.NormalizeAllRules();
+
+ // The normalization process could have introduced cycles in the dependency graph so run the cycle
+ // detection pass again. We do separate passes like this since normalizing can lead to less intuitive
+ // error messages if a cycle is found: so if the cycle exists before normalization takes place we want
+ // to generate an error message then.
+ foreach (CrstType crst in m_crsts.Values)
+ {
+ List<CrstType> cycleList = new List<CrstType>();
+ if (FindCycle(crst, crst, cycleList))
+ {
+ Console.WriteLine(String.Format("Error: CrstType 'Crst{0}' is involved in a dependency cycle with the following CrstTypes:",
+ crst.Name));
+ foreach (CrstType cycleCrst in cycleList)
+ Console.WriteLine(String.Format(" Crst{0}", cycleCrst));
+ Console.WriteLine("Note that the cycle was detected only after 'SameLevelAs' processing was performed so some CrstType dependencies are implied by peer CrstTypes");
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ // Recursively determine if a cycle exists in the Crst type dependency graph rooted at the 'rootCrst'
+ // type. The 'currCrst' indicates the next dependency to be examined (it will be the same as the
+ // 'rootCrst' when we're first called). The 'cycleList' argument contains a list of Crst types we've
+ // already examined in this branch of the algorithm and serves both to avoid checking the same node twice
+ // and to provide a list of the involved Crst types should a cycle be detected.
+ // Note that this algorithm is not designed to detect general cycles in the graph, only those that involve
+ // the 'rootCrst' directly. This is somewhat inefficient but gives us a simple way to generate clear error
+ // messages.
+ bool FindCycle(CrstType rootCrst, CrstType currCrst, List<CrstType> cycleList)
+ {
+ // Add the current Crst type to the list of those we've seen.
+ cycleList.Add(currCrst);
+
+ // Look through all the dependencies of the current Crst type.
+ foreach (CrstType childCrst in currCrst.AcquiredBeforeList)
+ {
+ // If we find a reference back to the root Crst type then we've found a cycle. Start backing out
+ // from the recursion (keeping the list of nodes we visited intact) by returning true.
+ if (childCrst == rootCrst)
+ return true;
+
+ // Otherwise iterate over the dependencies of the current node and for each one that we haven't
+ // already seen and recursively extend the search.
+ if (!cycleList.Contains(childCrst))
+ if (FindCycle(rootCrst, childCrst, cycleList))
+ return true;
+ }
+
+ // Didn't find any cycles involving the root and this node; remove this node from the potential cycle
+ // list and return up to our caller indicating such.
+ cycleList.RemoveAt(cycleList.Count - 1);
+
+ return false;
+ }
+
+ // Topologically sort all the Crsts so we can assign a total ordering to them (in the form of a numeric
+ // ranking). Ranks start from 0 (Crst types that may be acquired at any time) and increment from there
+ // (Crst types that may only be acquired if a lower type is not already held).
+ // **** NOTE: The leveling process is destructive in that we will lose all dependency information from the
+ // Crst type definitions during the course of the algorithm.
+ void LevelCrsts()
+ {
+ // Note that Crst type dependency rules have been normalized (by the input parser) so that all
+ // AcquiredBefore/AcquiredAfter relationships have been reduced to AcquiredBefore relationships (i.e.
+ // any rule of the form "A AcquiredAfter B" has been converted to "B AcquiredBefore A". Any
+ // normalization makes the algorithm easier to program, but a normaliztion to AcquiredBefore
+ // relationships was chosen since it makes it particularly easy to implement an algorithm that assigns
+ // ranks beginning with zero and moving up to an arbitrary level. Any type that doesn't have any
+ // AcquiredBefore dependencies can always be ranked at a lower level than any remaining unranked types
+ // by definition and from this we can derive a simple iterative process to rank all the crst types.
+
+ // Calculate how many Crst types we have left to rank (some are not included in this step because
+ // they've been marked as 'Unordered' in the input file).
+ int unsorted = 0;
+ foreach (CrstType crst in m_crsts.Values)
+ if (crst.Level == CrstType.CrstUnassigned)
+ unsorted++;
+
+ // The ranking level we're going to assign to Crst types on the next pass of the algorithm.
+ int currLevel = 0;
+
+ // Iterate while we still have Crst types left to rank. On each pass we'll assign a rank to those
+ // types that no longer have any dependencies forcing them to have a higher rank and then remove
+ // dependency rules involving those newly ranked types from the remaining types.
+ while (unsorted > 0)
+ {
+ // Record a flag indicating whether we manage to assign a rank to at least one Crst type on this
+ // pass. If we ever fail to do this we've hit a cycle (this is just paranoia, the Crst declaration
+ // validation performed in ValidateCrsts() should have detected such a cycle first).
+ bool madeProgress = false;
+
+ // If we spot any types that are in a group (SameLevelAs relationship) then we defer assigning a
+ // rank till we've dealt with any non-group types (we wish to always place type groups in their
+ // very own rank else the Crst rank violation detection code won't detect violations between
+ // members of the group and singleton types that happened to be assigned rank on the same pass).
+ List<CrstTypeGroup> deferredGroups = new List<CrstTypeGroup>();
+
+ // Scan through all the Crst types.
+ foreach (CrstType crst in m_crsts.Values)
+ {
+ // Skip those types that already have a rank assigned.
+ if (crst.Level != CrstType.CrstUnassigned)
+ continue;
+
+ // We're looking for Crst types that no longer have any types that can be acquired while they
+ // are already held. This indicates that it's safe to assign the current rank to them (since
+ // there are no remaining dependencies that need to be ranked first (i.e. with a lower rank
+ // value than this type).
+ if (crst.AcquiredBeforeList.Count == 0)
+ {
+ if (crst.Group == null)
+ {
+ // If this type is not part of the group we can go and assign the rank right away.
+ crst.Level = currLevel;
+ madeProgress = true;
+ unsorted--;
+ }
+ else if (!deferredGroups.Contains(crst.Group))
+ // Otherwise we'll defer ranking this group member until all the singletons are
+ // processed.
+ deferredGroups.Add(crst.Group);
+ }
+ }
+
+ // We've gone through the entire collection of Crst types and assigned the current rank level to
+ // any singleton Crst types that qualify. Now deal with any group members we detected (it's
+ // possible that more than one group qualifies for ranking at this level but we need to be careful
+ // to assign distinct rank values to each group to avoid hiding lock rank violations (since group
+ // members are always allowed to be acquired alongside any other type with the same rank value).
+ // Iterate over each distinct group that we found in this pass.
+ foreach (CrstTypeGroup group in deferredGroups)
+ {
+ // Look at our progress flag here. If it is false then we didn't have any singleton Crst types
+ // ranked at this level and we haven't processed any other groups at this level either. Thus
+ // we can rank this group at the current level. Otherwise at least one type was already ranked
+ // with this level so we need to increment to a new, distinct level to avoid ranking
+ // ambiguity.
+ if (madeProgress)
+ currLevel++;
+
+ // Iterate through each Crst type that is a member of this group assigning them the (same)
+ // current rank.
+ foreach (CrstType crst in group.Members)
+ {
+ // Double check that each member has the same dependencies (i.e. they should all be empty
+ // by now). There should be no way that this error should ever occur, it's just paranoia
+ // on my part.
+ if (crst.AcquiredBeforeList.Count != 0)
+ throw new Exception("Internal error: SameLevel CrstTypes with differing rulesets");
+
+ crst.Level = currLevel;
+ unsorted--;
+ }
+
+ // Once we've processed at least one group we've made progress this iteration.
+ madeProgress = true;
+ }
+
+ // If we didn't manage to assign rank to at least one Crst type then we're not going to do any
+ // better next iteration either (because no state was updated in this iteration). This should only
+ // occur in the presence of a dependency cycle and we shouldn't get that here after a successful
+ // call to ValidateCrsts(), so this check is pure paranoia.
+ if (!madeProgress)
+ {
+ Console.WriteLine(String.Format("{0} unsorted remain", unsorted));
+ throw new Exception("Cycle detected trying to assign level " + currLevel.ToString());
+ }
+
+ // Loop through all the unranked Crsts types and remove any AcquiredBefore relationships that
+ // involve types we've already leveled (since those types, by definition, have already been
+ // assigned a lower rank).
+ foreach (CrstType crst in m_crsts.Values)
+ {
+ if (crst.Level != CrstType.CrstUnassigned)
+ continue;
+ List<CrstType> prunedCrsts = crst.AcquiredBeforeList.FindAll(Unleveled);
+ crst.AcquiredBeforeList = prunedCrsts;
+ }
+
+ // Done with this rank level, move to the next.
+ currLevel++;
+ }
+ }
+
+ // Predicate method used with List<T>.FindAll() to locate Crst types that haven't had their rank assigned
+ // yet.
+ static bool Unleveled(CrstType crst)
+ {
+ return crst.Level == CrstType.CrstUnassigned;
+ }
+}
+
+// Class used to parse a CrstTypes.def file into a dictionary of Crst type definitions. It uses a simple lexer
+// that removes comments then forms tokens out of any consecutive non-whitespace characters. An equally simple
+// recursive descent parser forms Crst instances by parsing the token stream.
+class TypeFileParser
+{
+ // Remember the input file name and the dictionary we're meant to populate.
+ string m_typeFileName;
+ Dictionary<string, CrstType> m_crsts;
+
+ // Compile regular expressions for detecting comments and tokens in the parser input.
+ Regex m_commentRegex = new Regex(@"//.*");
+ Regex m_tokenRegex = new Regex(@"^(\s*(\S+)\s*)*");
+
+ // Input is lexed into an array of tokens. We record the index of the token being currently parsed.
+ Token[] m_tokens;
+ int m_currToken;
+
+ // Parse the given file into Crst type definitions and place these definitions in the dictionary provided.
+ // Syntax errors are signalled via ParseError derived exceptions.
+ public void ParseFile(string typeFileName, Dictionary<string, CrstType> crsts)
+ {
+ m_typeFileName = typeFileName;
+ m_crsts = crsts;
+
+ // Lex the file into tokens.
+ InitTokenStream();
+
+ // Parse the tokens according to the grammar set out at the top of this file.
+ // Loop until we have no further tokens to process.
+ while (!IsEof())
+ {
+ // Grab the next token.
+ Token token = NextToken();
+
+ // We're at the top level, so the token had better be 'Crst'.
+ if (token.Id != KeywordId.Crst)
+ throw new UnexpectedTokenError(token, KeywordId.Crst);
+
+ // OK, parse the rest of this single Crst type definition.
+ ParseCrst();
+ }
+ }
+
+ // Parse a single Crst type definition.
+ void ParseCrst()
+ {
+ // The next token had better be an identifier (the Crst type name).
+ Token token = NextToken();
+ if (token.Id != KeywordId.Id)
+ throw new UnexpectedTokenError(token, KeywordId.Id);
+
+ // The Crst instance might already exist in the dictionary (forward references to a Crst type cause
+ // these entries to auto-vivify). But in that case the entry better not be marked as 'Defined' which
+ // would indicate a double declaration.
+ CrstType crst;
+ if (m_crsts.ContainsKey(token.Text))
+ {
+ crst = m_crsts[token.Text];
+ if (crst.Defined)
+ throw new ParseError(String.Format("Duplicate definition for CrstType '{0}'", token.Text), token);
+ }
+ else
+ {
+ // Otherwise this Crst type hasn't been seen thus far so we allocate a new instance and add it to
+ // the dictionary.
+ crst = new CrstType(token.Text);
+ m_crsts.Add(crst.Name, crst);
+ }
+
+ // We're defining, not just referencing this type.
+ crst.Defined = true;
+
+ // Parse any attributes inside this definition (until we see an 'End' token).
+ bool parsingCrst = true;
+ while (parsingCrst)
+ {
+ // Get the next token. Either some attribute keyword or 'End'.
+ token = NextToken();
+ List<CrstType> list;
+
+ switch (token.Id)
+ {
+
+ case KeywordId.AcquiredBefore:
+ // Simply parse the following list of Crst types into the current type's AcquiredBefore list.
+ ParseList(crst.AcquiredBeforeList);
+ break;
+
+ case KeywordId.AcquiredAfter:
+ // AcquiredAfter is trickier. To make the ranking algorithm's life easier we actually
+ // normalize all rules to the AcquiredBefore form (see LevelCrsts() for the reasoning). So we
+ // capture the list of Crst types that follow the AcquiredAfter keyword and then append the
+ // current type to the AcquiredBefore list of each type found.
+ list = new List<CrstType>();
+ ParseList(list);
+ foreach (CrstType priorCrst in list)
+ priorCrst.AcquiredBeforeList.Add(crst);
+ break;
+
+ case KeywordId.SameLevelAs:
+ // Parse the following list of Crst types them let the CrstTypeGroup class handle the
+ // resulting updates to the type groups we're currently maintaining. See the comments for the
+ // CrstTypeGroup class for more details.
+ list = new List<CrstType>();
+ ParseList(list);
+ foreach (CrstType sameLevelCrst in list)
+ CrstTypeGroup.Join(crst, sameLevelCrst);
+ break;
+
+ case KeywordId.Unordered:
+ crst.Level = CrstType.CrstUnordered;
+ break;
+
+ case KeywordId.End:
+ parsingCrst = false;
+ break;
+
+ default:
+ throw new UnexpectedTokenError(token,
+ KeywordId.AcquiredBefore,
+ KeywordId.AcquiredAfter,
+ KeywordId.SameLevelAs,
+ KeywordId.Unordered);
+ }
+ }
+ }
+
+ // Parse a list of Crst type names. Any other token terminates the list (without error and without
+ // consuming that token from the stream). The list of tokens is returned as a list of corresponding
+ // CrstTypes (which are auto-vivified in the output dictionary if they haven't been declared yet).
+ void ParseList(List<CrstType> list)
+ {
+ // Parse tokens until we find a non-indentifier.
+ while (true)
+ {
+ Token token = NextToken();
+ if (token.Id != KeywordId.Id)
+ {
+ // We found the list terminator. Push the non-identifier token back into the stream for our
+ // caller to parse correctly.
+ UnwindToken();
+ return;
+ }
+
+ // Look up or add a new CrstType corresponding to this type name.
+ CrstType crst;
+ if (m_crsts.ContainsKey(token.Text))
+ crst = m_crsts[token.Text];
+ else
+ {
+ crst = new CrstType(token.Text);
+ m_crsts[crst.Name] = crst;
+ }
+
+ // Add the type to the output list we're building.
+ list.Add(crst);
+ }
+ }
+
+ // Lex the input file into an array of tokens.
+ void InitTokenStream()
+ {
+ StreamReader file = new StreamReader(m_typeFileName);
+ int lineNumber = 1;
+ List<Token> tokenList = new List<Token>();
+
+ // Read the file a line at a time.
+ string line;
+ while ((line = file.ReadLine()) != null)
+ {
+ // Remove comments from the current line.
+ line = m_commentRegex.Replace(line, "");
+
+ // Match all contiguous non-whitespace characters as individual tokens.
+ Match match = m_tokenRegex.Match(line);
+ if (match.Success)
+ {
+ // For each token captured build a token instance and record the token text and the file, line
+ // and column at which it was encountered (these latter in order to produce useful syntax
+ // error messages).
+ CaptureCollection cap = match.Groups[2].Captures;
+ for (int i = 0; i < cap.Count; i++)
+ tokenList.Add(new Token(m_typeFileName, cap[i].Value, lineNumber, cap[i].Index));
+ }
+
+ lineNumber++;
+ }
+
+ // Record the list of tokens we captured as an array and reset the index of the next token to be
+ // handled by the parser.
+ m_tokens = tokenList.ToArray();
+ m_currToken = 0;
+ }
+
+ // Have we run out of tokens to parse?
+ bool IsEof()
+ {
+ return m_currToken >= m_tokens.Length;
+ }
+
+ // Get the next token and throw an exception if we ran out.
+ Token NextToken()
+ {
+ if (m_currToken >= m_tokens.Length)
+ throw new UnexpectedEofError();
+ return m_tokens[m_currToken++];
+ }
+
+ // Push the last token parsed back into the stream.
+ void UnwindToken()
+ {
+ if (m_currToken <= 0)
+ throw new InvalidOperationException();
+ m_currToken--;
+ }
+
+ // The various keywords we can encounter (plus Id for identifiers, which are currently always Crst type
+ // names).
+ internal enum KeywordId
+ {
+ Id,
+ Crst,
+ End,
+ AcquiredBefore,
+ AcquiredAfter,
+ Unordered,
+ SameLevelAs,
+ }
+
+ // Class encapsulating a single token captured from the input file.
+ internal class Token
+ {
+ // Hash of keyword text to enum values.
+ static Dictionary<string, KeywordId> s_keywords;
+
+ // The characters comprising the text of the token from the input file.
+ string m_text;
+
+ // Where the token was found (for error messages).
+ string m_file;
+ int m_line;
+ int m_column;
+
+ // The ID of the keyword this token represents (or KeywordId.Id).
+ KeywordId m_id;
+
+ // Static class initialization.
+ static Token()
+ {
+ // Populate the keyword hash. No sense building complex finite state machines to improve the
+ // efficiency of keyword lexing here since the input file (and keyword set) is never going to be
+ // big enough to justify the extra work.
+ s_keywords = new Dictionary<string, KeywordId>();
+ s_keywords.Add("crst", KeywordId.Crst);
+ s_keywords.Add("end", KeywordId.End);
+ s_keywords.Add("acquiredbefore", KeywordId.AcquiredBefore);
+ s_keywords.Add("acquiredafter", KeywordId.AcquiredAfter);
+ s_keywords.Add("unordered", KeywordId.Unordered);
+ s_keywords.Add("samelevelas", KeywordId.SameLevelAs);
+ }
+
+ public Token(string file, string text, int line, int column)
+ {
+ m_file = file;
+ m_text = text;
+ m_line = line;
+ m_column = column;
+
+ // Map token text to keyword ID. True keywords (not identifiers) are case insensitive so normalize
+ // the text to lower case before performing the keyword hash lookup.
+ string canonName = m_text.ToLower();
+ if (s_keywords.ContainsKey(canonName))
+ m_id = s_keywords[canonName];
+ else
+ m_id = KeywordId.Id;
+ }
+
+ public string Text {get { return m_text; }}
+ public string Location {get { return String.Format("{0} line {1}, column {2}", m_file, m_line, m_column); }}
+ public KeywordId Id {get { return m_id; }}
+ }
+
+ // Base class for all syntax errors reported by the parser.
+ internal class ParseError : Exception
+ {
+ // A raw error message.
+ public ParseError(string message)
+ : base(message)
+ {}
+
+ // An error message tagged with a file, line and column (coming from an error token).
+ public ParseError(string message, Token errorToken)
+ : base(String.Format("{0}: {1}", errorToken.Location, message))
+ {}
+
+ // Produce a textual name for the given keyword type.
+ protected static string IdToName(KeywordId id)
+ {
+ if (id == KeywordId.Id)
+ return "a CrstType name";
+ return String.Format("'{0}'", id.ToString());
+ }
+ }
+
+ // Syntax error used when an unexpected token is encountered which further lists the valid tokens that
+ // would otherwise have been accepted.
+ internal class UnexpectedTokenError : ParseError
+ {
+ // Produce an unexpected token message with a file, line and column coming from an error token and
+ // optionally the names of zero or more tokens that would have been accepted.
+ public UnexpectedTokenError(Token errorToken, params KeywordId[] expected)
+ : base(FormatErrorMessage(errorToken, expected))
+ {}
+
+ static string FormatErrorMessage(Token errorToken, KeywordId[] expected)
+ {
+ StringBuilder message = new StringBuilder(String.Format("Unexpected token '{0}' at {1}",
+ errorToken.Text, errorToken.Location));
+ if (expected.Length == 0)
+ {
+ }
+ else if (expected.Length == 1)
+ {
+ message.Append(String.Format("; expected {0}", IdToName(expected[0])));
+ }
+ else
+ {
+ message.Append("; expected one of ");
+ for (int i = 0; i < expected.Length - 1; i++)
+ message.Append(String.Format("{0}, ", IdToName(expected[i])));
+ message.Append(IdToName(expected[expected.Length - 1]));
+
+ }
+
+ return message.ToString();
+ }
+ }
+
+ // Syntax error used when we unexpectedly ran out of tokens.
+ internal class UnexpectedEofError : ParseError
+ {
+ public UnexpectedEofError()
+ : base("Unexpected end of file")
+ {}
+ }
+}
+
+// This class represents an instance of a Crst type. These are unqiuely identified by case-sensitive name (the
+// same as the enum name used in vm code, minus the 'Crst' prefix).
+class CrstType : IComparable
+{
+ // Special level constants used to indicate unordered Crst types or those types we haven't gotten around
+ // to ranking yet.
+ public static readonly int CrstUnordered = -1;
+ public static readonly int CrstUnassigned = -2;
+
+ // Name of the type, e.g. "AppDomainCache" for the CrstAppDomainCache type.
+ string m_name;
+
+ // The numeric ranking assigned to this type. Starts as CrstUnassigned and then becomes either
+ // CrstUnordered (while parsing the input file) or a number >= 0 (during LevelCrsts()).
+ int m_level;
+
+ // List of Crst types that can be legally acquired while this one is held. (AcquiredAfter relationships
+ // are by switching the terms and adding to the second type's AcquiredBefore list).
+ List<CrstType> m_acquiredBeforeCrsts;
+
+ // Either null if this Crst type is not in (or has not yet been determined to be in) a SameLevelAs
+ // relationship or points to a CrstTypeGroup that records all the sibling types at the same level (that
+ // have been discovered thus far during parsing).
+ CrstTypeGroup m_group;
+
+ // Set once a definition for this type has been discovered. Used to detect double definitions and types
+ // referenced without definitions.
+ bool m_defined;
+
+ public CrstType(string name)
+ {
+ m_name = name;
+ m_level = CrstUnassigned;
+ m_acquiredBeforeCrsts = new List<CrstType>();
+ m_group = null;
+ m_defined = false;
+ }
+
+ public string Name {get { return m_name; }}
+ public int Level {get { return m_level; } set { m_level = value; }}
+ public List<CrstType> AcquiredBeforeList {get { return m_acquiredBeforeCrsts; } set { m_acquiredBeforeCrsts = value; }}
+ public CrstTypeGroup Group {get { return m_group; } set { m_group = value; }}
+ public bool Defined {get {return m_defined; } set { m_defined = value; }}
+
+ // Helper used to sort CrstTypes. The sort order is lexical based on the type name.
+ public int CompareTo(object other)
+ {
+ return m_name.CompareTo(((CrstType)other).m_name);
+ }
+}
+
+// Every time a SameLevelAs relationship is used we need to be careful to keep track of the transitive closure
+// of all types bound in the relationship. That's because such a relationship impacts the other dependency
+// rules (each member of a SameLevelAs group must behave as though it has exactly the same dependency rules as
+// all the others). Identifying all the members is tricky because "A SameLevelAs B" and "B SameLevelAs C"
+// implies "A SameLevelAs C". So we use a separate tracking structure, instances of the CrstTypeGroup type, to
+// do the bookkeeping for us. Each Crst type belongs to either zero or one CrstTypeGroups. As we find new
+// SameLevelAs relationships we create new groups, add types to existing groups or merge groups (as previous
+// distinct groups are merged by the discovery of a SameLevelAs relationship that links them). By the time
+// parsing has finished we are guaranteed to have discovered all the distinct, disjoint groups and to have
+// fully populated them with the transitive closure of all related types. We can them normalize all groups
+// members so they share the same AcquiredBefore relationships.
+class CrstTypeGroup
+{
+ // We record every group that has been formed so far. This makes normalizing all groups easier.
+ static List<CrstTypeGroup> s_groups = new List<CrstTypeGroup>();
+
+ // Crst types that are members of the current group. There are no duplicates in this list.
+ List<CrstType> m_members = new List<CrstType>();
+
+ // Declare a SameLevelAs relationship between the two Crst types given. Groups will be assigned, created
+ // or merged as required to maintain our guarantees (each CrstType is a member of at most one group and
+ // all CrstTypes involved in the same transitive closure of a SameLevelAs relationship are members of one
+ // group).
+ public static void Join(CrstType crst1, CrstType crst2)
+ {
+ CrstTypeGroup group;
+
+ if (crst1 == crst2)
+ {
+ // In this case the type refers to itself. Create a singleton group for this type if it doesn't
+ // already exist.
+ if (crst1.Group == null)
+ {
+ group = new CrstTypeGroup();
+ group.m_members.Add(crst1);
+
+ s_groups.Add(group);
+
+ crst1.Group = group;
+ }
+ }
+ else if (crst1.Group == null && crst2.Group == null)
+ {
+ // Neither types belong to a group already. So we can create a new one and add both types to it.
+ group = new CrstTypeGroup();
+ group.m_members.Add(crst1);
+ group.m_members.Add(crst2);
+
+ s_groups.Add(group);
+
+ crst1.Group = group;
+ crst2.Group = group;
+ }
+ else if (crst1.Group == null)
+ {
+ // The first type doesn't belong to a group yet but the second does. So we can simply add the
+ // first type to the second group.
+ group = crst2.Group;
+ group.m_members.Add(crst1);
+
+ crst1.Group = group;
+ }
+ else if (crst2.Group == null)
+ {
+ // As for the case above but the group/no-group positions are reversed.
+ group = crst1.Group;
+ group.m_members.Add(crst2);
+
+ crst2.Group = group;
+ }
+ else if (crst1.Group != crst2.Group)
+ {
+ // Both types belong to different groups so we'll have to merge them. Add the members of group 2
+ // to group 1 and throw away group 2.
+ group = crst1.Group;
+ CrstTypeGroup absorbGroup = crst2.Group;
+ foreach (CrstType crst in absorbGroup.m_members)
+ {
+ group.m_members.Add(crst);
+ crst.Group = group;
+ }
+
+ s_groups.Remove(absorbGroup);
+ }
+
+ // The only case left is when both types are already in the same group and there's no work needed in
+ // this case.
+ }
+
+ // Normalize all the groups we created during parsing. See below for the definition of normalization.
+ public static void NormalizeAllRules()
+ {
+ foreach (CrstTypeGroup group in s_groups)
+ group.NormalizeRules();
+ }
+
+ // Normalize this group. This involves adjusting the AcquiredBefore list of each member to be the union of
+ // all such rules within the group. This step allows us to detect cycles in the dependency graph that
+ // would otherwise remain hidden if we only examined the unnormalized AcquiredBefore rules.
+ void NormalizeRules()
+ {
+ // This local will contain the union of all AcquiredBefore rules.
+ List<CrstType> acquiredBeforeList = new List<CrstType>();
+
+ // Iterate through each member of the group.
+ foreach (CrstType crst in m_members)
+ {
+ // Add each AcquiredBefore rule we haven't already seen to the union.
+ foreach (CrstType afterCrst in crst.AcquiredBeforeList)
+ if (!acquiredBeforeList.Contains(afterCrst))
+ acquiredBeforeList.Add(afterCrst);
+ }
+
+ // Reset each member's AcquiredBefore list to a copy of the union we calculated. Note it's important
+ // to make a (shallow) copy because the ranking process modifies this list and so a shared copy would
+ // cause unexpected results.
+ foreach (CrstType crst in m_members)
+ crst.AcquiredBeforeList = acquiredBeforeList.GetRange(0, acquiredBeforeList.Count);
+ }
+
+ public List<CrstType> Members {get { return m_members; }}
+}
diff --git a/src/inc/CrstTypes.def b/src/inc/CrstTypes.def
new file mode 100644
index 0000000..bb6e710
--- /dev/null
+++ b/src/inc/CrstTypes.def
@@ -0,0 +1,781 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+//
+// This file is used to describe the different types of Crst and their dependencies on other Crst types (in
+// terms of which types may be legally held while others are acquired).
+//
+// The CrstTypeTool utility is used to parse this file, verify that there are no logical inconsistencies (such
+// as a cycle in the dependencies) and generate an enum value and numerical ranking for each type. This
+// ranking is used by the runtime (in checked builds) to verify that none of the rules described below are
+// violated (which could lead to a deadlock).
+//
+// When you add a new Crst type you need to be aware of which Crst types may be already held when your Crst is
+// acquired and which other types may be subsequently acquired. You can then add a Crst definition to this
+// file and annotate it with those dependencies. Running CrstTypeTool will check to see if this introduces a
+// potential deadlock problem and if everything checks out will generate a new version of
+// file:CrstTypes.h (be sure to check this file out from TFS/SD before running CrstTypeTool).
+//
+// The format of this file is a very simple language. Comments are introduced with '//' and continue to the
+// end of the line. Keywords are case insensitive (Crst type names, however, are case sensitive since they'll
+// be translated directly to C++ enum values). Crst type names are used without the 'Crst' prefix used in C++
+// code (e.g. CrstAppDomainCache is referred to as AppDomainCache). The following words are reserved keywords
+// and may not be used as the names of Crst types:
+// Crst
+// End
+// AcquiredBefore
+// AcquiredAfter
+// Unordered
+// SameLevelAs
+//
+// Each Crst type definition has the following format (where [] indicates optional and ... indicates zero or
+// more repetitions):
+// Crst <type name>
+// [AcquiredBefore <type name>...]
+// [AcquiredAfter <type name>...]
+// [SameLevelAs <type name>...]
+// [Unordered]
+// End
+//
+// For example:
+// Crst Foo
+// AcquiredBefore Bar
+// AcquiredAfter Zob Baz
+// SameLevelAs Foo
+// End
+//
+// This introduces a new Crst type Foo (CrstFoo inside the runtime). This type may be legally acquired when
+// the current thread holds Crst instances of type Zob, Bar or even other instances of Foo. While Foo is held
+// it is legal to acquire Crsts of type Bar. Assuming that this definition does not introduce any dependency
+// cycles, CrstTypeTool will assign a numeric rank to CrstFoo that maximizes the chance that any other Crst
+// type interaction you didn't explicitly specify (e.g. holding Foo while taking a Crst of type Wibble) will
+// generate a ranking violation assert in the checked build.
+//
+// Note that the following set of definitions:
+// Crst A AcquiredBefore B End
+// Crst B End
+//
+// Crst A End
+// Crst B AcquiredAfter A End
+//
+// Crst A AcquiredBefore B End
+// Crst B AcquiredAfter A End
+//
+// are all equivalent. You are free to use whichever variant seems clearest to you (CrstTypeTool will tell you
+// if you introduce conflicting rules). Similarly "A SameLevelAs B" implies "B SameLevelAs A". The initial
+// contents of this file uses AcquiredBefore in preference to AcquiredAfter purely because it was generated
+// automatically by a profiling mechanism (the initial rules were seeded from observations of Crst usage while
+// running our test suites). Feel free to add meaningful comments to existing rules if you feel they can
+// usefully clarify the reasons for particular dependencies.
+//
+// CrstTypeTool is a csScript file at file:..\..\bin\CrstTypeTool.csScript. Simply typing "CrstTypeTool" from a
+// clrenv command window prompt should rebuild file:CrstTypes.h from the current CrstTypes.def (again,
+// remember to check out CrstTypes.h first).
+// Note: If you cannot run the script from command line, because of this error:
+// Script language type is unsupported.
+// Use /? for more help on usage.
+// Or because .csscript extension is not associated with anything on your machine,
+// Then use "csc.exe CrstTypeTool.csscript" from ClrEnv environment and run the resulting executable.
+//
+// Each Crst type definition is currently in alphabetical order. Please maintain this convention.
+//
+
+Crst AllowedFiles
+ AcquiredBefore JumpStubCache UniqueStack
+End
+
+Crst AppDomainCache
+ AcquiredBefore FusionBindContext FusionLoadContext LoaderHeap UniqueStack UnresolvedClassLock
+End
+
+Crst AppDomainHandleTable
+ AcquiredBefore AvailableParamTypes HandleTable IbcProfile SyncBlockCache SystemDomainDelayedUnloadList
+ ThreadStore SystemDomain
+End
+
+Crst ArgBasedStubCache
+End
+
+Crst AssemblyIdentityCache
+End
+
+Crst AssemblyLoader
+ AcquiredBefore DeadlockDetection UniqueStack
+End
+
+Crst AvailableClass
+ AcquiredBefore LoaderHeap
+End
+
+Crst AssemblyDependencyGraph
+End
+
+Crst AvailableParamTypes
+ AcquiredBefore FusionBindContext FusionLoadContext IbcProfile LoaderHeap
+End
+
+Crst BaseDomain
+ AcquiredBefore LoaderHeap UniqueStack
+End
+
+Crst CCompRC
+ Unordered
+End
+
+Crst Cer
+ AcquiredBefore JumpStubCache UniqueStack
+End
+
+Crst ClassFactInfoHash
+ AcquiredBefore SyncBlockCache ThreadStore
+End
+
+Crst ClassInit
+ AcquiredBefore DeadlockDetection IbcProfile
+ SameLevelAs Jit
+End
+
+Crst ClrNotification
+ Unordered
+End
+
+Crst CrstCLRPrivBinderLocalWinMDPath
+End
+
+Crst CLRPrivBinderMaps
+End
+
+Crst CLRPrivBinderMapsAdd
+ AcquiredBefore CLRPrivBinderMaps
+End
+
+Crst COMWrapperCache
+ AcquiredBefore HandleTable UniqueStack
+End
+
+Crst ConnectionNameTable
+End
+
+Crst Contexts
+ AcquiredBefore AvailableParamTypes Cer ClassInit DeadlockDetection DomainLocalBlock FuncPtrStubs
+ GlobalStrLiteralMap Jit LoaderHeap ModuleLookupTable RWLock SigConvert SingleUseLock
+ StubUnwindInfoHeapSegments SyncBlockCache TypeIDMap UnresolvedClassLock FusionClosure
+End
+
+Crst CoreCLRBinderLog
+ Unordered
+End
+
+Crst CSPCache
+ AcquiredBefore JumpStubCache
+End
+
+Crst DeadlockDetection
+End
+
+Crst DebuggerController
+ // AcquiredBefore DebuggerHeapLock DebuggerJitInfo LoaderHeap
+
+ // See bug: 581892. This has a conflict with CrstInstMethodHashTableRanking.
+ // The controller logic will be moved to OOP in V3, and so this lock will no longer be necessary.
+ // Fixing this in-proc would be difficult, and it would all be throwaway as we go oop.
+ Unordered
+End
+
+// This is a leaf debugger lock.
+Crst DebuggerFavorLock
+ AcquiredAfter DebuggerJitInfo DebuggerMutex
+End
+
+// This is the lock used by the DebuggerHeapExecutableMemoryAllocator for allocating/freeing memory.
+Crst DebuggerHeapExecMemLock
+End
+
+// Debugger Heap lock is the smallest of the debugger locks.
+Crst DebuggerHeapLock
+ AcquiredAfter DebuggerFavorLock DebuggerJitInfo DebuggerMutex
+ // Disabled per bug 581892
+ // AcquiredAfter DebuggerController
+End
+
+Crst DebuggerJitInfo
+ AcquiredBefore DebuggerHeapLock
+End
+
+// This is the major debugger lock.
+// It's the largest of the debugger locks.
+Crst DebuggerMutex
+ AcquiredBefore AvailableParamTypes ConnectionNameTable
+ DynamicIL LoaderHeap ModuleLookupTable ThreadStore
+
+ // Disabled per bug 581892
+ // AcquiredBefore DebuggerController
+ AcquiredBefore DebuggerHeapLock DebuggerJitInfo
+
+End
+
+// This lock is used only for testing data consistency (see code:DataTest::TestDataSafety)
+// and is released before taking any other lock except for CrstDataTest2
+Crst DataTest1
+ AcquiredAfter DebuggerMutex
+End
+
+// This lock is used only for testing data consistency (see code:DataTest::TestDataSafety)
+// and is released before taking any other lockCrst DataTest2
+Crst DataTest2
+ AcquiredAfter DataTest1
+End
+
+
+Crst DbgTransport
+End
+
+Crst DelegateToFPtrHash
+End
+
+Crst DomainLocalBlock
+ AcquiredBefore AppDomainHandleTable IbcProfile LoaderHeap SystemDomainDelayedUnloadList UniqueStack
+End
+
+Crst DynamicIL
+End
+
+Crst DynamicMT
+ AcquiredBefore IbcProfile
+End
+
+Crst DynLinkZapItems
+ AcquiredBefore LoaderHeap
+End
+
+Crst EventStore
+End
+
+Crst Exception
+End
+
+Crst ExecuteManLock
+ AcquiredBefore UniqueStack
+End
+
+Crst ExecuteManRangeLock
+End
+
+Crst FCall
+ AcquiredBefore LoaderHeap
+End
+
+Crst RetThunkCache
+ AcquiredBefore LoaderHeap
+End
+
+Crst FriendAccessCache
+ AcquiredBefore JumpStubCache UniqueStack
+End
+
+Crst FuncPtrStubs
+ AcquiredBefore IbcProfile LoaderHeap UniqueStack CodeFragmentHeap JumpStubCache PatchEntryPoint
+End
+
+Crst FusionAppCtx
+ AcquiredBefore FusionPolicyConfigPool FusionSingleUse FusionAssemblyDownload
+End
+
+Crst FusionAssemblyDownload
+ AcquiredBefore FusionDownload UniqueStack
+End
+
+Crst FusionBindResult
+End
+
+Crst FusionClb
+End
+
+Crst FusionClosure
+ AcquiredBefore FusionBindContext FusionLoadContext FusionAppCtx FusionClosureGraph DomainLocalBlock ModuleFixup
+End
+
+Crst FusionClosureGraph
+ AcquiredBefore FusionAppCtx FusionBindContext FusionLoadContext
+End
+
+Crst FusionConfigSettings
+End
+
+Crst FusionDownload
+End
+
+Crst FusionLoadContext
+ AcquiredBefore PEImage
+End
+
+Crst FusionBindContext
+ AcquiredBefore PEImage
+End
+
+Crst FusionLog
+ AcquiredBefore IbcProfile UniqueStack
+End
+
+Crst FusionWarningLog
+ AcquiredBefore FusionBindContext FusionLoadContext FusionLog
+End
+
+Crst FusionNgenIndex
+ AcquiredBefore SystemDomainDelayedUnloadList
+End
+
+Crst FusionNgenIndexPool
+ AcquiredBefore SystemDomainDelayedUnloadList
+End
+
+Crst FusionPcyCache
+End
+
+Crst FusionPolicyConfigPool
+ AcquiredBefore UniqueStack
+End
+
+Crst FusionSingleUse
+ AcquiredBefore PEImage
+End
+
+Crst FusionIsoLibInit
+End
+
+Crst NativeBinderInit
+ Unordered
+End
+
+Crst NativeImageCache
+ Unordered
+End
+
+Crst GCMemoryPressure
+End
+
+Crst GlobalStrLiteralMap
+ AcquiredBefore HandleTable IbcProfile SyncBlockCache SystemDomainDelayedUnloadList ThreadStore UniqueStack
+End
+
+Crst HandleTable
+ SameLevelAs HandleTable
+End
+
+Crst HostAssemblyMap
+End
+
+Crst HostAssemblyMapAdd
+ AcquiredBefore HostAssemblyMap
+End
+
+Crst IbcProfile
+End
+
+Crst IJWFixupData
+ AcquiredBefore FuncPtrStubs IJWHash LoaderHeap
+End
+
+Crst IJWHash
+End
+
+Crst ILStubGen
+ AcquiredBefore DeadlockDetection UniqueStack
+End
+
+Crst InstMethodHashTable
+ AcquiredBefore FusionBindContext FusionLoadContext LoaderHeap UniqueStack JumpStubCache
+End
+
+Crst InterfaceVTableMap
+End
+
+Crst Interop
+ AcquiredBefore AppDomainHandleTable AvailableParamTypes Cer ClassInit DeadlockDetection DomainLocalBlock
+ HandleTable InstMethodHashTable InteropData JitGenericHandleCache LoaderHeap SigConvert
+ StubDispatchCache StubUnwindInfoHeapSegments SyncBlockCache TypeIDMap UnresolvedClassLock
+End
+
+Crst InteropData
+ AcquiredBefore LoaderHeap UniqueStack
+End
+
+Crst IOThreadpoolWorker
+ AcquiredBefore ThreadIdDispenser ThreadStore
+End
+
+Crst IsJMCMethod
+End
+
+Crst ISymUnmanagedReader
+ AcquiredBefore PEImagePDBStream UniqueStack JumpStubCache
+End
+
+Crst Jit
+ AcquiredBefore DeadlockDetection JumpStubCache
+ SameLevelAs ClassInit
+End
+
+Crst JitGenericHandleCache
+End
+
+Crst JitPerf
+ Unordered
+End
+
+Crst JumpStubCache
+ AcquiredBefore ExecuteManRangeLock LoaderHeap SingleUseLock
+ AcquiredAfter AppDomainCache ExecuteManLock FusionAssemblyDownload FusionNgenIndex FusionNgenIndexPool
+ ILStubGen SharedBaseDomain ThreadpoolTimerQueue ThreadpoolWaitThreads
+ TPMethodTable TypeIDMap BaseDomain AssemblyLoader
+End
+
+Crst ListLock
+ Unordered
+End
+
+// Leaflock leveling, used for crsts that explicitly want to be a leaf lock
+Crst LeafLock
+End
+
+Crst LoaderAllocator
+ AcquiredBefore AppDomainHandleTable HandleTable UniqueStack ThreadStore
+ AcquiredAfter DomainLocalBlock
+End
+
+Crst LoaderAllocatorReferences
+ AcquiredBefore LoaderAllocator
+ AcquiredAfter PendingTypeLoadEntry InstMethodHashTable
+End
+
+Crst AssemblyList
+ AcquiredAfter LoaderAllocatorReferences ThreadStore AssemblyLoader
+End
+
+Crst LoaderHeap
+End
+
+Crst Mda
+End
+
+Crst MetadataTracker
+ Unordered
+End
+
+Crst StubCache
+ AcquiredBefore LoaderHeap
+End
+
+Crst ModIntPairList
+End
+
+Crst Module
+ AcquiredBefore LoaderHeap UniqueStack
+End
+
+Crst ModuleFixup
+ AcquiredBefore AppDomainHandleTable GlobalStrLiteralMap IbcProfile SyncBlockCache
+End
+
+Crst ModuleLookupTable
+ AcquiredBefore LoaderHeap
+End
+
+Crst MUThunkHash
+End
+
+Crst Nls
+End
+
+Crst ObjectList
+ SameLevelAs ObjectList
+End
+
+Crst OnEventManager
+End
+
+Crst PatchEntryPoint
+End
+
+Crst PEFileSecurityManager
+End
+
+Crst PEImage
+ AcquiredBefore UniqueStack
+End
+
+Crst ILFingerprintCache
+ AcquiredBefore PEImage
+End
+
+Crst PEImagePDBStream
+End
+
+Crst PendingTypeLoadEntry
+ AcquiredBefore AppDomainCache AppDomainHandleTable AssemblyLoader AvailableClass AvailableParamTypes
+ BaseDomain ClassInit DeadlockDetection DebuggerController DebuggerJitInfo DebuggerMutex
+ DomainLocalBlock DynLinkZapItems Exception ExecuteManRangeLock FuncPtrStubs
+ FusionAppCtx FusionAssemblyDownload FusionBindResult FusionClosure FusionDownload
+ FusionBindContext FusionLoadContext FusionNgenIndex FusionNgenIndexPool FusionPcyCache
+ FusionPolicyConfigPool FusionSingleUse GlobalStrLiteralMap HandleTable IbcProfile
+ IJWFixupData IJWHash ISymUnmanagedReader Jit JumpStubCache LoaderHeap ModIntPairList
+ Module ModuleLookupTable PEImage SecurityStackwalkCache SharedAssemblyCreate
+ SharedBaseDomain SigConvert SingleUseLock StubDispatchCache StubUnwindInfoHeapSegments
+ SyncBlockCache SystemDomain ThreadIdDispenser ThreadStore TypeIDMap UnresolvedClassLock
+ SameLevelAs PendingTypeLoadEntry
+End
+
+Crst PinHandle
+End
+
+// ProfilerGCRefDataFreeList synchronizes access to the profiler API's list of
+// free, previously allocated structures that track moved references and
+// root references during a GC.
+Crst ProfilerGCRefDataFreeList
+End
+
+// ProfilingAPIStatus serializes attempts to transition the global status
+// from state to state, and access to the ProfilerDetachInfo structure
+// between the thread executing DetachProfiler(), and the DetachThread
+// carrying out the evacuation order.
+Crst ProfilingAPIStatus
+End
+
+Crst PublisherCertificate
+End
+
+Crst RCWCache
+ AcquiredBefore IbcProfile LoaderHeap RCWCleanupList
+End
+
+Crst RCWRefCache
+ AcquiredBefore HandleTable
+End
+
+Crst RCWCleanupList
+End
+
+Crst ReDacl
+End
+
+Crst Reflection
+ AcquiredBefore LoaderHeap UnresolvedClassLock
+End
+
+// Used to synchronize all rejit information stored in a given AppDomain. One of these
+// crsts exist per domain (except the SharedDomain--see below)
+Crst ReJITDomainTable
+ AcquiredBefore LoaderHeap SingleUseLock DeadlockDetection JumpStubCache DebuggerController
+ AcquiredAfter ReJITGlobalRequest ThreadStore GlobalStrLiteralMap SystemDomain DebuggerMutex
+End
+
+// Same as ReJITDomainTable, but this is for the SharedDomain's ReJitManager. Only
+// reason we have a special type for the SharedDomain's ReJitManager is so that we can
+// explicitly level this guy differently from ReJITDomainTable, so that both the
+// SharedDomain's ReJitManager table lock AND one non-SharedDomain's ReJitManager table
+// lock may be held simultaneously. This is useful during ETW rundown.
+Crst ReJITSharedDomainTable
+ AcquiredBefore ReJITDomainTable
+ AcquiredAfter ReJITGlobalRequest ThreadStore GlobalStrLiteralMap SystemDomain DebuggerMutex
+End
+
+// Used to synchronize all global requests (which may span multiple AppDomains) which add
+// new functions to rejit tables, or request Reverts on existing functions in the rejit
+// tables. One of these crsts exist per runtime.
+Crst ReJITGlobalRequest
+ AcquiredBefore ThreadStore ReJITSharedDomainTable ReJITDomainTable SystemDomain
+End
+
+// ETW infrastructure uses this crst to protect a hash table of TypeHandles which is
+// used to remember which types have been logged (to avoid duplicate logging of the
+// same type).
+Crst EtwTypeLogHash
+ AcquiredAfter ThreadStore AllowedFiles Cer TPMethodTable
+ AcquiredBefore AvailableParamTypes ConnectionNameTable DeadlockDetection DebuggerController
+ DebuggerHeapLock DebuggerJitInfo DynamicIL ExecuteManRangeLock HandleTable IbcProfile
+ JitGenericHandleCache JumpStubCache LoaderHeap ModuleLookupTable ProfilingAPIStatus
+ ProfilerGCRefDataFreeList RWLock SingleUseLock SyncBlockCache SystemDomainDelayedUnloadList
+ ThreadIdDispenser ThreadStaticDataHashTable
+End
+
+Crst Remoting
+ AcquiredBefore AppDomainHandleTable AvailableParamTypes Cer ClassInit DeadlockDetection DebuggerController
+ DebuggerHeapLock DebuggerJitInfo DebuggerMutex DomainLocalBlock ExecuteManRangeLock
+ FuncPtrStubs GlobalStrLiteralMap HandleTable InstMethodHashTable Jit JitGenericHandleCache
+ JumpStubCache LoaderHeap StubCache Module ModuleLookupTable SecurityStackwalkCache SigConvert
+ SingleUseLock StubUnwindInfoHeapSegments SyncBlockCache SystemDomainDelayedUnloadList
+ ThreadStore UnresolvedClassLock PendingTypeLoadEntry
+End
+
+Crst RWLock
+End
+
+Crst SavedExceptionInfo
+ AcquiredBefore DebuggerController
+End
+
+Crst SaveModuleProfileData
+End
+
+Crst SecurityPolicyCache
+End
+
+Crst SecurityPolicyInit
+ AcquiredBefore SecurityPolicyCache
+End
+
+Crst SecurityStackwalkCache
+End
+
+Crst SharedAssemblyCreate
+ AcquiredBefore DeadlockDetection UniqueStack
+End
+
+Crst SharedBaseDomain
+ AcquiredBefore UniqueStack
+End
+
+Crst SigConvert
+ AcquiredBefore LoaderHeap
+End
+
+Crst SingleUseLock
+ AcquiredBefore ExecuteManRangeLock LoaderHeap UniqueStack DebuggerJitInfo
+End
+
+Crst UnwindInfoTableLock
+ AcquiredAfter StubUnwindInfoHeapSegments SingleUseLock
+ AcquiredBefore StressLog
+End
+
+Crst SpecialStatics
+End
+
+Crst StressLog
+ Unordered
+End
+
+Crst StrongName
+End
+
+Crst CodeFragmentHeap
+ AcquiredBefore SingleUseLock
+End
+
+Crst StubDispatchCache
+End
+
+Crst StubUnwindInfoHeapSegments
+ AcquiredAfter StubCache
+End
+
+Crst SyncBlockCache
+ AcquiredBefore ThreadIdDispenser
+End
+
+Crst SyncHashLock
+End
+
+Crst SystemBaseDomain
+End
+
+Crst SystemDomain
+ AcquiredBefore DebuggerMutex HandleTable IbcProfile SaveModuleProfileData SecurityPolicyCache
+ ThreadIdDispenser ThreadStore
+End
+
+Crst SystemDomainDelayedUnloadList
+End
+
+Crst ThreadIdDispenser
+End
+
+Crst ThreadpoolEventCache
+End
+
+Crst ThreadpoolTimerQueue
+ AcquiredBefore UniqueStack
+End
+
+Crst ThreadpoolWaitThreads
+ AcquiredBefore UniqueStack
+End
+
+Crst ThreadpoolWorker
+ AcquiredBefore ThreadIdDispenser ThreadStore
+End
+
+Crst ThreadStaticDataHashTable
+ AcquiredBefore SyncBlockCache
+End
+
+Crst ThreadStore
+ AcquiredBefore AvailableParamTypes ConnectionNameTable DeadlockDetection DebuggerController
+ DebuggerHeapLock DebuggerJitInfo DynamicIL ExecuteManRangeLock HandleTable IbcProfile
+ JitGenericHandleCache JumpStubCache LoaderHeap ModuleLookupTable ProfilingAPIStatus
+ ProfilerGCRefDataFreeList RWLock SingleUseLock SyncBlockCache SystemDomainDelayedUnloadList
+ ThreadIdDispenser ThreadStaticDataHashTable
+End
+
+Crst TPMethodTable
+ AcquiredBefore DebuggerHeapLock LoaderHeap UniqueStack AvailableParamTypes
+End
+
+Crst TypeIDMap
+ AcquiredBefore UniqueStack
+End
+
+Crst TypeEquivalenceMap
+ AcquiredBefore LoaderHeap
+End
+
+Crst UMThunkHash
+End
+
+Crst UniqueStack
+ AcquiredBefore LoaderHeap
+End
+
+Crst UnresolvedClassLock
+ AcquiredBefore AvailableParamTypes DynLinkZapItems IbcProfile JumpStubCache
+End
+
+Crst WrapperTemplate
+ AcquiredBefore IbcProfile
+End
+
+Crst UMEntryThunkCache
+ AcquiredBefore LoaderHeap
+End
+
+Crst PinnedByrefValidation
+End
+
+Crst AssemblyUsageLog
+End
+
+Crst VSDIndirectionCellLock
+ AcquiredBefore LoaderHeap
+End
+
+Crst MulticoreJitHash
+End
+
+Crst MulticoreJitManager
+ AcquiredBefore MulticoreJitHash ThreadStore
+End
+
+Crst WinRTFactoryCache
+ AcquiredBefore HandleTable
+End
+
+Crst SqmManager
+End
+
+Crst StackSampler
+End
+
+Crst InlineTrackingMap
+ AcquiredBefore IbcProfile
+End \ No newline at end of file
diff --git a/src/inc/MSCOREE.IDL b/src/inc/MSCOREE.IDL
new file mode 100644
index 0000000..67605e2
--- /dev/null
+++ b/src/inc/MSCOREE.IDL
@@ -0,0 +1,2438 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+//
+/**************************************************************************************
+ ** **
+ ** Mscoree.idl - interface definitions for mscoree.dll **
+ ** **
+ **************************************************************************************/
+
+#ifdef FEATURE_CORECLR
+// API deprecation does not apply to CoreCLR
+cpp_quote("#define DECLARE_DEPRECATED ")
+cpp_quote("#define DEPRECATED_CLR_STDAPI STDAPI")
+#else // !FEATURE_CORECLR
+// API deprecation is only applicable to Desktop runtime.
+cpp_quote("#ifndef USE_DEPRECATED_CLR_API_WITHOUT_WARNING")
+cpp_quote("#define DEPRECATED_CLR_API_MESG \"This API has been deprecated. Refer to http://go.microsoft.com/fwlink/?LinkId=143720 for more details.\"")
+cpp_quote("#define DECLARE_DEPRECATED __declspec(deprecated(DEPRECATED_CLR_API_MESG))")
+cpp_quote("#define DEPRECATED_CLR_STDAPI EXTERN_C DECLARE_DEPRECATED HRESULT STDAPICALLTYPE")
+cpp_quote("#else // USE_DEPRECATED_CLR_API_WITHOUT_WARNING")
+cpp_quote("#define DECLARE_DEPRECATED ")
+cpp_quote("#define DEPRECATED_CLR_STDAPI STDAPI")
+cpp_quote("#endif // !USE_DEPRECATED_CLR_API_WITHOUT_WARNING")
+#endif // FEATURE_CORECLR
+cpp_quote("")
+
+//
+// Interface descriptions
+//
+import "unknwn.idl";
+#if defined(FEATURE_INCLUDE_ALL_INTERFACES) || defined(FEATURE_WINDOWSPHONE)
+import "gchost.idl";
+#endif
+import "ivalidator.idl";
+
+#include "product_version.h"
+
+#ifdef FEATURE_CORECLR
+cpp_quote("struct IActivationFactory;")
+interface IActivationFactory;
+#endif
+
+const char* CLR_MAJOR_VERSION = VER_MAJORVERSION;
+const char* CLR_MINOR_VERSION = VER_MINORVERSION;
+const char* CLR_BUILD_VERSION = VER_PRODUCTBUILD;
+
+const char* CLR_ASSEMBLY_MAJOR_VERSION = VER_ASSEMBLYMAJORVERSION;
+const char* CLR_ASSEMBLY_MINOR_VERSION = VER_ASSEMBLYMINORVERSION;
+const char* CLR_ASSEMBLY_BUILD_VERSION = VER_ASSEMBLYBUILD;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// LIBID mscoree
+cpp_quote("EXTERN_GUID(LIBID_mscoree, 0x5477469e,0x83b1,0x11d2,0x8b,0x49,0x00,0xa0,0xc9,0xb7,0xc9,0xc4);")
+
+// CLSID CorRuntimeHost : uuid(CB2F6723-AB3A-11d2-9C40-00C04FA30A3E)
+cpp_quote("EXTERN_GUID(CLSID_CorRuntimeHost, 0xcb2f6723, 0xab3a, 0x11d2, 0x9c, 0x40, 0x00, 0xc0, 0x4f, 0xa3, 0x0a, 0x3e);")
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+// CLSID TypeNameFactory : uuid{B81FF171-20F3-11d2-8DCC-00A0C9B00525}
+cpp_quote("EXTERN_GUID(CLSID_TypeNameFactory, 0xB81FF171, 0x20F3, 0x11d2, 0x8d, 0xcc, 0x00, 0xa0, 0xc9, 0xb0, 0x05, 0x25);")
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// CLSID CLRRuntimeHost : uuid(90F1A06E-7712-4762-86B5-7A5EBA6BDB02)
+cpp_quote("EXTERN_GUID(CLSID_CLRRuntimeHost, 0x90F1A06E, 0x7712, 0x4762, 0x86, 0xB5, 0x7A, 0x5E, 0xBA, 0x6B, 0xDB, 0x02);")
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+#ifdef FEATURE_COMINTEROP
+// CLSID ComCallUnmarshal
+cpp_quote("EXTERN_GUID(CLSID_ComCallUnmarshal, 0x3F281000,0xE95A,0x11d2,0x88,0x6B,0x00,0xC0,0x4F,0x86,0x9F,0x04);")
+
+// CLSID ComCallUnmarshal2
+cpp_quote("EXTERN_GUID(CLSID_ComCallUnmarshalV4, 0x45fb4600,0xe6e8,0x4928,0xb2,0x5e,0x50,0x47,0x6f,0xf7,0x94,0x25);")
+#endif // FEATURE_COMINTEROP
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// IID IObjectHandle : uuid(C460E2B4-E199-412a-8456-84DC3E4838C3)
+cpp_quote("EXTERN_GUID(IID_IObjectHandle, 0xc460e2b4, 0xe199, 0x412a, 0x84, 0x56, 0x84, 0xdc, 0x3e, 0x48, 0x38, 0xc3);")
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+#ifdef FEATURE_COMINTEROP
+// IID IManagedObject : uuid(C3FCC19E-A970-11d2-8B5A-00A0C9B7C9C4)
+cpp_quote("EXTERN_GUID(IID_IManagedObject, 0xc3fcc19e, 0xa970, 0x11d2, 0x8b, 0x5a, 0x00, 0xa0, 0xc9, 0xb7, 0xc9, 0xc4);")
+#endif // FEATURE_COMINTEROP
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// IID IApartmentCallback : uuid(178E5337-1528-4591-B1C9-1C6E484686D8)
+cpp_quote("EXTERN_GUID(IID_IApartmentCallback, 0x178e5337, 0x1528, 0x4591, 0xb1, 0xc9, 0x1c, 0x6e, 0x48, 0x46, 0x86, 0xd8);")
+
+// IID ICatalogServices : uuid(04C6BE1E-1DB1-4058-AB7A-700CCCFBF254)
+cpp_quote("EXTERN_GUID(IID_ICatalogServices, 0x04c6be1e, 0x1db1, 0x4058, 0xab, 0x7a, 0x70, 0x0c, 0xcc, 0xfb, 0xf2, 0x54);")
+
+// IID ICorRuntimeHost : uuid(CB2F6722-AB3A-11d2-9C40-00C04FA30A3E)
+cpp_quote("EXTERN_GUID(IID_ICorRuntimeHost, 0xcb2f6722, 0xab3a, 0x11d2, 0x9c, 0x40, 0x00, 0xc0, 0x4f, 0xa3, 0x0a, 0x3e);")
+
+// IID ICorThreadpool : uuid(84680D3A-B2C1-46e8-ACC2-DBC0A359159A)
+cpp_quote("EXTERN_GUID(IID_ICorThreadpool, 0x84680D3A, 0xB2C1, 0x46e8, 0xAC, 0xC2, 0xDB, 0xC0, 0xA3, 0x59, 0x15, 0x9A);")
+
+// IID_ICLRDebugManager : uuid(00DCAEC6-2AC0-43a9-ACF9-1E36C139B10D)
+cpp_quote("EXTERN_GUID(IID_ICLRDebugManager, 0xdcaec6, 0x2ac0, 0x43a9, 0xac, 0xf9, 0x1e, 0x36, 0xc1, 0x39, 0xb1, 0xd);")
+
+// IID IHostMemoryNeededCallback : uuid(47EB8E57-0846-4546-AF76-6F42FCFC2649)
+cpp_quote("EXTERN_GUID(IID_IHostMemoryNeededCallback, 0x47EB8E57, 0x0846, 0x4546, 0xAF, 0x76, 0x6F, 0x42, 0xFC, 0xFC, 0x26, 0x49);")
+
+// IID IHostMalloc : uuid(1831991C-CC53-4A31-B218-04E910446479)
+cpp_quote("EXTERN_GUID(IID_IHostMalloc, 0x1831991C, 0xCC53, 0x4A31, 0xB2, 0x18, 0x04, 0xE9, 0x10, 0x44, 0x64, 0x79);")
+
+// IID IHostMemoryManager : uuid(7BC698D1-F9E3-4460-9CDE-D04248E9FA25)
+cpp_quote("EXTERN_GUID(IID_IHostMemoryManager, 0x7BC698D1, 0xF9E3, 0x4460, 0x9C, 0xDE, 0xD0, 0x42, 0x48, 0xE9, 0xFA, 0x25);")
+
+// IID ICLRTask : uuid(28E66A4A-9906-4225-B231-9187C3EB8611)
+cpp_quote("EXTERN_GUID(IID_ICLRTask, 0x28E66A4A, 0x9906, 0x4225, 0xB2, 0x31, 0x91, 0x87, 0xc3, 0xeb, 0x86, 0x11);")
+
+// IID ICLRTask2 : uuid(28E66A4A-9906-4225-B231-9187C3EB8612)
+cpp_quote("EXTERN_GUID(IID_ICLRTask2, 0x28E66A4A, 0x9906, 0x4225, 0xB2, 0x31, 0x91, 0x87, 0xc3, 0xeb, 0x86, 0x12);")
+
+// IID IHostTask : uuid(C2275828-C4B1-4B55-82C9-92135F74DF1A)
+cpp_quote("EXTERN_GUID(IID_IHostTask, 0xC2275828, 0xC4B1, 0x4B55, 0x82, 0xC9, 0x92, 0x13, 0x5F, 0x74, 0xDF, 0x1A);")
+
+// IID ICLRTaskManager : uuid(4862efbe-3ae5-44f8-8feb-346190ee8a34)
+cpp_quote("EXTERN_GUID(IID_ICLRTaskManager, 0x4862efbe, 0x3ae5, 0x44f8, 0x8F, 0xEB, 0x34, 0x61, 0x90, 0xeE, 0x8A, 0x34);")
+
+// IID IHostTaskManager : uuid(997FF24C-43B7-4352-8667-0DC04FAFD354)
+cpp_quote("EXTERN_GUID(IID_IHostTaskManager, 0x997FF24C, 0x43B7, 0x4352, 0x86, 0x67, 0x0D, 0xC0, 0x4F, 0xAF, 0xD3, 0x54);")
+
+// IID IHostThreadpoolManager : uuid(983D50E2-CB15-466B-80FC-845DC6E8C5FD)
+cpp_quote("EXTERN_GUID(IID_IHostThreadpoolManager, 0x983D50E2, 0xCB15, 0x466B, 0x80, 0xFC, 0x84, 0x5D, 0xC6, 0xE8, 0xC5, 0xFD);")
+
+// IID_ICLRIOCompletionManager : uuid(2D74CE86-B8D6-4C84-B3A7-9768933B3C12)
+cpp_quote("EXTERN_GUID(IID_ICLRIoCompletionManager, 0x2D74CE86, 0xB8D6, 0x4C84, 0xB3, 0xA7, 0x97, 0x68, 0x93, 0x3B, 0x3C, 0x12);")
+
+// IID_IHostIOCompletionManager : uuid(8BDE9D80-EC06-41D6-83E6-22580EFFCC20)
+cpp_quote("EXTERN_GUID(IID_IHostIoCompletionManager, 0x8BDE9D80, 0xEC06, 0x41D6, 0x83, 0xE6, 0x22, 0x58, 0x0E, 0xFF, 0xCC, 0x20);")
+
+// IID IHostSyncManager : uuid(234330c7-5f10-4f20-9615-5122dab7a0ac)
+cpp_quote("EXTERN_GUID(IID_IHostSyncManager, 0x234330c7, 0x5f10, 0x4f20, 0x96, 0x15, 0x51, 0x22, 0xda, 0xb7, 0xa0, 0xac);")
+
+// IID IHostCrst : uuid(6DF710A6-26A4-4a65-8CD5-7237B8BDA8DC)
+cpp_quote("EXTERN_GUID(IID_IHostCrst, 0x6DF710A6, 0x26A4, 0x4a65, 0x8c, 0xd5, 0x72, 0x37, 0xb8, 0xbd, 0xa8, 0xdc);")
+
+// IID IHostAutoEvent : uuid(50B0CFCE-4063-4278-9673-E5CB4ED0BDB8)
+cpp_quote("EXTERN_GUID(IID_IHostAutoEvent, 0x50B0CFCE, 0x4063, 0x4278, 0x96, 0x73, 0xe5, 0xcb, 0x4e, 0xd0, 0xbd, 0xb8);")
+
+// IID IHostManualEvent : uuid(1BF4EC38-AFFE-4fb9-85A6-525268F15B54)
+cpp_quote("EXTERN_GUID(IID_IHostManualEvent, 0x1BF4EC38, 0xAFFE, 0x4fb9, 0x85, 0xa6, 0x52, 0x52, 0x68, 0xf1, 0x5b, 0x54);")
+
+// IID IHostSemaphore : uuid(855efd47-cc09-463a-a97d-16acab882661)
+cpp_quote("EXTERN_GUID(IID_IHostSemaphore, 0x855efd47, 0xcc09, 0x463a, 0xa9, 0x7d, 0x16, 0xac, 0xab, 0x88, 0x26, 0x61);")
+
+// IID ICLRSyncManager : uuid(55FF199D-AD21-48f9-A16C-F24EBBB8727D)
+cpp_quote("EXTERN_GUID(IID_ICLRSyncManager, 0x55FF199D, 0xAD21, 0x48f9, 0xa1, 0x6c, 0xf2, 0x4e, 0xbb, 0xb8, 0x72, 0x7d);")
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+#ifdef FEATURE_APPDOMAIN_RESOURCE_MONITORING
+// IID ICLRAppDomainResourceMonitor: uuid(C62DE18C-2E23-4AEA-8423-B40C1FC59EAE)
+cpp_quote("EXTERN_GUID(IID_ICLRAppDomainResourceMonitor, 0XC62DE18C, 0X2E23, 0X4AEA, 0X84, 0X23, 0XB4, 0X0C, 0X1F, 0XC5, 0X9E, 0XAE);")
+#endif //FEATURE_APPDOMAIN_RESOURCE_MONITORING
+
+// {7D290010-D781-45da-A6F8-AA5D711A730E}
+cpp_quote("EXTERN_GUID(IID_ICLRPolicyManager, 0x7D290010, 0xD781, 0x45da, 0xA6, 0xF8, 0xAA, 0x5D, 0x71, 0x1A, 0x73, 0x0E);")
+
+#if defined(FEATURE_INCLUDE_ALL_INTERFACES) || defined (FEATURE_WINDOWSPHONE)
+// IID_ICLRGCManager : uuid(54D9007E-A8E2-4885-B7BF-F998DEEE4F2A)
+cpp_quote("EXTERN_GUID(IID_ICLRGCManager, 0x54D9007E, 0xA8E2, 0x4885, 0xB7, 0xBF, 0xF9, 0x98, 0xDE, 0xEE, 0x4F, 0x2A);")
+// IID_ICLRGCManager2 : uuid(0603B793-A97A-4712-9CB4-0CD1C74C0F7C)
+cpp_quote("EXTERN_GUID(IID_ICLRGCManager2, 0x0603B793, 0xA97A, 0x4712, 0x9C, 0xB4, 0x0C, 0xD1, 0xC7, 0x4C, 0x0F, 0x7C);")
+// IID_ICLRErrorReportingManager : uuid(980D2F1A-BF79-4c08-812A-BB9778928F78)
+cpp_quote("EXTERN_GUID(IID_ICLRErrorReportingManager, 0x980d2f1a, 0xbf79, 0x4c08, 0x81, 0x2a, 0xbb, 0x97, 0x78, 0x92, 0x8f, 0x78);")
+#endif // FEATURE_INCLUDE_ALL_INTERFACES || FEATURE_WINDOWSPHONE
+
+#ifdef FEATURE_WINDOWSPHONE
+// IID_ICLRErrorReportingManager2 : uuid(C68F63B1-4D8B-4E0B-9564-9D2EFE2FA18C)
+cpp_quote("EXTERN_GUID(IID_ICLRErrorReportingManager2, 0xc68f63b1, 0x4d8b, 0x4e0b, 0x95, 0x64, 0x9d, 0x2e, 0xfe, 0x2f, 0xa1, 0x8c);")
+#endif // FEATURE_WINDOWSPHONE
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// {7AE49844-B1E3-4683-BA7C-1E8212EA3B79}
+cpp_quote("EXTERN_GUID(IID_IHostPolicyManager, 0x7AE49844, 0xB1E3, 0x4683, 0xBA, 0x7C, 0x1E, 0x82, 0x12, 0xEA, 0x3B, 0x79);")
+
+// IID IHostGCManager : uuid(5D4EC34E-F248-457B-B603-255FAABA0D21)
+cpp_quote("EXTERN_GUID(IID_IHostGCManager, 0x5D4EC34E, 0xF248, 0x457B, 0xB6, 0x03, 0x25, 0x5F, 0xAA, 0xBA, 0x0D, 0x21);")
+
+// {607BE24B-D91B-4E28-A242-61871CE56E35}
+cpp_quote("EXTERN_GUID(IID_IActionOnCLREvent, 0x607BE24B, 0xD91B, 0x4E28, 0xA2, 0x42, 0x61, 0x87, 0x1C, 0xE5, 0x6E, 0x35);")
+
+// {1D0E0132-E64F-493D-9260-025C0E32C175}
+cpp_quote("EXTERN_GUID(IID_ICLROnEventManager, 0x1D0E0132, 0xE64F, 0x493D, 0x92, 0x60, 0x02, 0x5C, 0x0E, 0x32, 0xC1, 0x75);")
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+// IID ICLRRuntimeHost: uuid(90F1A06C-7712-4762-86B5-7A5EBA6BDB02)
+cpp_quote("EXTERN_GUID(IID_ICLRRuntimeHost, 0x90F1A06C, 0x7712, 0x4762, 0x86, 0xB5, 0x7A, 0x5E, 0xBA, 0x6B, 0xDB, 0x02);")
+
+#ifdef FEATURE_CORECLR
+// IID ICLRRuntimeHost2: uuid(712AB73F-2C22-4807-AD7E-F501D7B72C2D)
+cpp_quote("EXTERN_GUID(IID_ICLRRuntimeHost2, 0x712AB73F, 0x2C22, 0x4807, 0xAD, 0x7E, 0xF5, 0x01, 0xD7, 0xb7, 0x2C, 0x2D);")
+
+// IID IID_ICLRExecutionManager: uuid(1000A3E7-B420-4620-AE30-FB19B587AD1D)
+cpp_quote("EXTERN_GUID(IID_ICLRExecutionManager, 0x1000A3E7, 0xB420, 0x4620, 0xAE, 0x30, 0xFB, 0x19, 0xB5, 0x87, 0xAD, 0x1D);")
+
+#endif // FEATURE_CORECLR
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// IID ICLRHostProtectionManager : uuid{89F25F5C-CEEF-43e1-9CFA-A68CE863AAAC}
+cpp_quote("EXTERN_GUID(IID_ICLRHostProtectionManager, 0x89f25f5c, 0xceef, 0x43e1, 0x9c, 0xfa, 0xa6, 0x8c, 0xe8, 0x63, 0xaa, 0xac);")
+
+// IID IHostAssemblyStore : uuid(7B102A88-3F7F-496D-8FA2-C35374E01AF3)
+cpp_quote("EXTERN_GUID(IID_IHostAssemblyStore, 0x7b102a88, 0x3f7f, 0x496d, 0x8f, 0xa2, 0xc3, 0x53, 0x74, 0xe0, 0x1a, 0xf3);")
+
+// IID IHostAssemblyManager : uuid(613dabd7-62b2-493e-9e65-c1e32a1e0c5e)
+cpp_quote("EXTERN_GUID(IID_IHostAssemblyManager, 0x613dabd7, 0x62b2, 0x493e, 0x9e, 0x65, 0xc1, 0xe3, 0x2a, 0x1e, 0x0c, 0x5e);")
+
+// IID IHostSecurityManager : uuid{75AD2468-A349-4D02-A764-76A68AEE0C4F}
+cpp_quote("EXTERN_GUID(IID_IHostSecurityManager, 0x75ad2468, 0xa349, 0x4d02, 0xa7, 0x64, 0x76, 0xa6, 0x8a, 0xee, 0x0c, 0x4f);")
+
+// IID IHostSecurityContext : uuid{7E573CE4-0343-4423-98D7-6318348A1D3C}
+cpp_quote("EXTERN_GUID(IID_IHostSecurityContext, 0x7e573ce4, 0x343, 0x4423, 0x98, 0xd7, 0x63, 0x18, 0x34, 0x8a, 0x1d, 0x3c);")
+
+// IID ICLRAssemblyIdentityManager: uuid(15f0a9da-3ff6-4393-9da9-fdfd284e6972)
+cpp_quote("EXTERN_GUID(IID_ICLRAssemblyIdentityManager, 0x15f0a9da, 0x3ff6, 0x4393, 0x9d, 0xa9, 0xfd, 0xfd, 0x28, 0x4e, 0x69, 0x72);")
+
+// IID ICLRDomainManager: uuid(270D00A2-8E15-4d0b-ADEB-37BC3E47DF77)
+cpp_quote("EXTERN_GUID(IID_ICLRDomainManager, 0x270d00a2, 0x8e15, 0x4d0b, 0xad, 0xeb, 0x37, 0xbc, 0x3e, 0x47, 0xdf, 0x77);")
+
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+// IID ITypeName : uuid{B81FF171-20F3-11d2-8DCC-00A0C9B00522}
+cpp_quote("EXTERN_GUID(IID_ITypeName, 0xB81FF171, 0x20F3, 0x11d2, 0x8d, 0xcc, 0x00, 0xa0, 0xc9, 0xb0, 0x05, 0x22);")
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// IID ICLRAssemblyReferenceList: uuid(1b2c9750-2e66-4bda-8b44-0a642c5cd733)
+cpp_quote("EXTERN_GUID(IID_ICLRAssemblyReferenceList, 0x1b2c9750, 0x2e66, 0x4bda, 0x8b, 0x44, 0x0a, 0x64, 0x2c, 0x5c, 0xd7, 0x33);")
+
+// IID ICLRReferenceAssemblyEnum: uuid(d509cb5d-cf32-4876-ae61-67770cf91973)
+cpp_quote("EXTERN_GUID(IID_ICLRReferenceAssemblyEnum, 0xd509cb5d, 0xcf32, 0x4876, 0xae, 0x61, 0x67, 0x77, 0x0c, 0xf9, 0x19, 0x73);")
+
+// IID ICLRProbingAssemblyEnum: uuid(d0c5fb1f-416b-4f97-81f4-7ac7dc24dd5d)
+cpp_quote("EXTERN_GUID(IID_ICLRProbingAssemblyEnum, 0xd0c5fb1f, 0x416b, 0x4f97, 0x81, 0xf4, 0x7a, 0xc7, 0xdc, 0x24, 0xdd, 0x5d);")
+
+// IID ICLRHostBindingPolicyManager: uuid(4b3545e7-1856-48c9-a8ba-24b21a753c09)
+cpp_quote("EXTERN_GUID(IID_ICLRHostBindingPolicyManager, 0x4b3545e7, 0x1856, 0x48c9, 0xa8, 0xba, 0x24, 0xb2, 0x1a, 0x75, 0x3c, 0x09);")
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+// IID ITypeNameBuilder : uuid{B81FF171-20F3-11d2-8DCC-00A0C9B00523}
+cpp_quote("EXTERN_GUID(IID_ITypeNameBuilder, 0xB81FF171, 0x20F3, 0x11d2, 0x8d, 0xcc, 0x00, 0xa0, 0xc9, 0xb0, 0x05, 0x23);")
+
+// IID ITypeNameFactory : uuid{B81FF171-20F3-11d2-8DCC-00A0C9B00521}
+cpp_quote("EXTERN_GUID(IID_ITypeNameFactory, 0xB81FF171, 0x20F3, 0x11d2, 0x8d, 0xcc, 0x00, 0xa0, 0xc9, 0xb0, 0x05, 0x21);")
+
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetCORSystemDirectory(_Out_writes_to_(cchBuffer, *dwLength) LPWSTR pbuffer, DWORD cchBuffer, DWORD* dwLength);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetCORVersion(_Out_writes_to_(cchBuffer, *dwLength) LPWSTR pbBuffer, DWORD cchBuffer, DWORD* dwLength);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetFileVersion(LPCWSTR szFilename, _Out_writes_to_opt_(cchBuffer, *dwLength) LPWSTR szBuffer, DWORD cchBuffer, DWORD* dwLength);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetCORRequiredVersion(_Out_writes_to_(cchBuffer, *dwLength) LPWSTR pbuffer, DWORD cchBuffer, DWORD* dwLength);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetRequestedRuntimeInfo(LPCWSTR pExe, LPCWSTR pwszVersion, LPCWSTR pConfigurationFile, DWORD startupFlags, DWORD runtimeInfoFlags, _Out_writes_opt_(dwDirectory) LPWSTR pDirectory, DWORD dwDirectory, _Out_opt_ DWORD *dwDirectoryLength, _Out_writes_opt_(cchBuffer) LPWSTR pVersion, DWORD cchBuffer, _Out_opt_ DWORD* dwlength);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetRequestedRuntimeVersion(_In_ LPWSTR pExe, _Out_writes_to_(cchBuffer, *dwLength) LPWSTR pVersion, DWORD cchBuffer, _Out_ DWORD* dwLength);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI CorBindToRuntimeHost(LPCWSTR pwszVersion, LPCWSTR pwszBuildFlavor, LPCWSTR pwszHostConfigFile, VOID* pReserved, DWORD startupFlags, REFCLSID rclsid, REFIID riid, LPVOID FAR *ppv);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI CorBindToRuntimeEx(LPCWSTR pwszVersion, LPCWSTR pwszBuildFlavor, DWORD startupFlags, REFCLSID rclsid, REFIID riid, LPVOID FAR *ppv);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI CorBindToRuntimeByCfg(IStream* pCfgStream, DWORD reserved, DWORD startupFlags, REFCLSID rclsid,REFIID riid, LPVOID FAR* ppv);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI CorBindToRuntime(LPCWSTR pwszVersion, LPCWSTR pwszBuildFlavor, REFCLSID rclsid, REFIID riid, LPVOID FAR *ppv);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI CorBindToCurrentRuntime(LPCWSTR pwszFileName, REFCLSID rclsid, REFIID riid, LPVOID FAR *ppv);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI ClrCreateManagedInstance(LPCWSTR pTypeName, REFIID riid, void **ppObject);")
+#pragma midl_echo("DECLARE_DEPRECATED void STDMETHODCALLTYPE CorMarkThreadInThreadPool();")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI RunDll32ShimW(HWND hwnd, HINSTANCE hinst, LPCWSTR lpszCmdLine, int nCmdShow);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI LoadLibraryShim(LPCWSTR szDllName, LPCWSTR szVersion, LPVOID pvReserved, HMODULE *phModDll);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI CallFunctionShim(LPCWSTR szDllName, LPCSTR szFunctionName, LPVOID lpvArgument1, LPVOID lpvArgument2, LPCWSTR szVersion, LPVOID pvReserved);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetRealProcAddress(LPCSTR pwszProcName, VOID** ppv);")
+#pragma midl_echo("DECLARE_DEPRECATED void STDMETHODCALLTYPE CorExitProcess(int exitCode);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI LoadStringRC(UINT iResouceID, _Out_writes_z_(iMax) LPWSTR szBuffer, int iMax, int bQuiet);")
+#ifdef FEATURE_USE_LCID
+#pragma midl_echo("DEPRECATED_CLR_STDAPI LoadStringRCEx(LCID lcid, UINT iResouceID, _Out_writes_z_(iMax) LPWSTR szBuffer, int iMax, int bQuiet, int *pcwchUsed);")
+#endif
+
+#ifndef FEATURE_CORECLR
+// Ideally we would like to make the function pointer definition below as DEPRECATED_CLR_STDAPI. However,
+// since it is referenced in the following definition of LockClrVersion, it will result in a build failure
+// in our own build (since we treat warnings as errors).
+//
+// However, there is no other usage of this pointer outside LockClrVersion. Thus, we will not mark
+// the pointer as legacy API. This will ensure we can build the runtime and if someone tries to use
+// it via LockClrVersion, they will have build warning since LockClrVersion is marked as legacy API.
+#pragma midl_echo("typedef HRESULT (__stdcall *FLockClrVersionCallback) ();")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI LockClrVersion(FLockClrVersionCallback hostCallback,FLockClrVersionCallback *pBeginHostSetup,FLockClrVersionCallback *pEndHostSetup);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI CreateDebuggingInterfaceFromVersion(int iDebuggerVersion, LPCWSTR szDebuggeeVersion, IUnknown ** ppCordb);")
+#pragma midl_echo("DEPRECATED_CLR_STDAPI GetVersionFromProcess(HANDLE hProcess, _Out_writes_to_(cchBuffer, *dwLength) LPWSTR pVersion, DWORD cchBuffer, _Out_ DWORD* dwLength);")
+#endif
+
+
+#ifdef FEATURE_CORECLR
+#pragma midl_echo("typedef HRESULT (STDAPICALLTYPE *FnGetCLRRuntimeHost)(REFIID riid, IUnknown **pUnk);")
+#endif
+
+typedef enum {
+ HOST_TYPE_DEFAULT = 0x0,
+ HOST_TYPE_APPLAUNCH = 0x1,
+ HOST_TYPE_CORFLAG = 0x2
+} HOST_TYPE;
+
+#pragma midl_echo("STDAPI CorLaunchApplication(HOST_TYPE dwClickOnceHost, LPCWSTR pwzAppFullName, DWORD dwManifestPaths, LPCWSTR* ppwzManifestPaths, DWORD dwActivationData, LPCWSTR* ppwzActivationData, LPPROCESS_INFORMATION lpProcessInformation);")
+
+typedef HRESULT (__stdcall *FExecuteInAppDomainCallback) (void* cookie);
+
+// By default GC is concurrent and only the base system library is loaded into the domain-neutral area.
+typedef enum {
+ STARTUP_CONCURRENT_GC = 0x1,
+
+ STARTUP_LOADER_OPTIMIZATION_MASK = 0x3<<1, // loader optimization mask
+ STARTUP_LOADER_OPTIMIZATION_SINGLE_DOMAIN = 0x1<<1, // no domain neutral loading
+ STARTUP_LOADER_OPTIMIZATION_MULTI_DOMAIN = 0x2<<1, // all domain neutral loading
+ STARTUP_LOADER_OPTIMIZATION_MULTI_DOMAIN_HOST = 0x3<<1, // strong name domain neutral loading
+
+
+ STARTUP_LOADER_SAFEMODE = 0x10, // Do not apply runtime version policy to the version passed in
+ STARTUP_LOADER_SETPREFERENCE = 0x100, // Set preferred runtime. Do not actally start it
+
+ STARTUP_SERVER_GC = 0x1000, // Use server GC
+ STARTUP_HOARD_GC_VM = 0x2000, // GC keeps virtual address used
+ STARTUP_SINGLE_VERSION_HOSTING_INTERFACE = 0x4000, // Disallow mixing hosting interface
+ STARTUP_LEGACY_IMPERSONATION = 0x10000, // Do not flow impersonation across async points by default
+ STARTUP_DISABLE_COMMITTHREADSTACK = 0x20000, // Don't eagerly commit thread stack
+ STARTUP_ALWAYSFLOW_IMPERSONATION = 0x40000, // Force flow impersonation across async points
+ // (impersonations achieved thru p/invoke and managed will flow.
+ // default is to flow only managed impersonation)
+ STARTUP_TRIM_GC_COMMIT = 0x80000, // GC uses less committed space when system memory low
+ STARTUP_ETW = 0x100000,
+ STARTUP_ARM = 0x400000, // Enable the ARM feature.
+#ifdef FEATURE_CORECLR
+ STARTUP_SINGLE_APPDOMAIN = 0x800000, // application runs in default domain, no more domains are created
+ STARTUP_APPX_APP_MODEL = 0x1000000, // jupiter app
+ STARTUP_DISABLE_RANDOMIZED_STRING_HASHING = 0x2000000 // Disable the randomized string hashing
+#endif
+} STARTUP_FLAGS;
+
+typedef enum {
+ CLSID_RESOLUTION_DEFAULT = 0x0, // Standard behavior that interop uses
+ CLSID_RESOLUTION_REGISTERED = 0x1, // Searches the registry and applies shim policy
+} CLSID_RESOLUTION_FLAGS;
+
+typedef enum
+{
+ RUNTIME_INFO_UPGRADE_VERSION = 0x001, // apply upgrades - i.e RTM->Everett
+ RUNTIME_INFO_REQUEST_IA64 = 0x002, // requesting a CLR for ia64
+ RUNTIME_INFO_REQUEST_AMD64 = 0x004, // requesting a CLR for amd64
+ RUNTIME_INFO_REQUEST_X86 = 0x008, // requesting a CLR for x86
+ RUNTIME_INFO_DONT_RETURN_DIRECTORY = 0x010, // don't return directory information
+ RUNTIME_INFO_DONT_RETURN_VERSION = 0x020, // don't return version information
+ RUNTIME_INFO_DONT_SHOW_ERROR_DIALOG = 0x040, // don't pop up an error dialog on failure
+ RUNTIME_INFO_IGNORE_ERROR_MODE = 0x1000,// ignore SEM_FAILCRITICALERRORS
+ // (by default the error dialog is not shown if SEM_FAILCRITICALERRORS is set)
+ // Reserved values here - see mscoreepriv.h
+} RUNTIME_INFO_FLAGS;
+
+
+typedef enum
+{
+ APPDOMAIN_SECURITY_DEFAULT =0x0,
+ APPDOMAIN_SECURITY_SANDBOXED = 0x1, // appdomain is sandboxed
+ APPDOMAIN_SECURITY_FORBID_CROSSAD_REVERSE_PINVOKE = 0x2, // no cross ad reverse pinvokes
+#ifdef FEATURE_CORECLR
+ APPDOMAIN_IGNORE_UNHANDLED_EXCEPTIONS = 0x4, //
+#endif //FEATURE_CORECLR
+ APPDOMAIN_FORCE_TRIVIAL_WAIT_OPERATIONS = 0x08, // do not pump messages during wait operations, do not call sync context
+#ifdef FEATURE_CORECLR
+ // When passed by the host, this flag will allow any assembly to perform PInvoke or COMInterop operations.
+ // Otherwise, by default, only platform assemblies can perform those operations.
+ APPDOMAIN_ENABLE_PINVOKE_AND_CLASSIC_COMINTEROP = 0x10,
+
+ APPDOMAIN_ENABLE_PLATFORM_SPECIFIC_APPS = 0x40,
+ APPDOMAIN_ENABLE_ASSEMBLY_LOADFILE = 0x80,
+
+ APPDOMAIN_DISABLE_TRANSPARENCY_ENFORCEMENT = 0x100,
+#endif //FEATURE_CORECLR
+} APPDOMAIN_SECURITY_FLAGS;
+
+#pragma midl_echo("STDAPI GetRequestedRuntimeVersionForCLSID(REFCLSID rclsid, _Out_writes_opt_(cchBuffer) LPWSTR pVersion, DWORD cchBuffer, _Out_opt_ DWORD* dwLength, CLSID_RESOLUTION_FLAGS dwResolutionFlags);")
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+//*****************************************************************************
+// Interface for Object Handles
+//*****************************************************************************
+[
+ object,
+ oleautomation,
+ uuid(C460E2B4-E199-412a-8456-84DC3E4838C3),
+ helpstring("Object Handle Interface"),
+ pointer_default(unique)
+]
+interface IObjectHandle : IUnknown
+{
+ HRESULT Unwrap([out, retval] VARIANT *ppv);
+};
+
+//*****************************************************************************
+// Interface for Setting runtime configuration
+//*****************************************************************************
+[
+ uuid(5C2B07A7-1E98-11d3-872F-00C04F79ED0D),
+ version(1.0),
+ helpstring("Application Domain call back"),
+ pointer_default(unique),
+ local
+]
+interface IAppDomainBinding : IUnknown
+{
+ // <TODO>TODO: this should return an AppDomain interface
+ // The event is invoked everytime a domain is created </TODO>
+ HRESULT OnAppDomain([in] IUnknown* pAppdomain);
+}
+
+
+//*****************************************************************************
+// Interface for participating in the scheduling of threads that would
+// otherwise be blocked for a GC
+//*****************************************************************************
+[
+ uuid(F31D1788-C397-4725-87A5-6AF3472C2791),
+ version(1.0),
+ helpstring("Control over threads blocked in GC"),
+ pointer_default(unique),
+ local
+]
+interface IGCThreadControl : IUnknown
+{
+ // Notification that the thread making the call is about to block, perhaps for
+ // a GC or other suspension. This gives the host an opportunity to re-schedule
+ // the thread for unmanaged tasks.
+ HRESULT ThreadIsBlockingForSuspension();
+
+ // Notification that the runtime is beginning a thread suspension for a GC or
+ // other suspension. Do not reschedule this thread!
+ HRESULT SuspensionStarting();
+
+ // Notification that the runtime is resuming threads after a GC or other
+ // suspension. Do not reschedule this thread!
+ HRESULT SuspensionEnding(DWORD Generation);
+}
+
+//*****************************************************************************
+// Interface for GC to request change in virtual memory limit
+//*****************************************************************************
+[
+ uuid(5513D564-8374-4cb9-AED9-0083F4160A1D),
+ version(1.1),
+ helpstring("Request change in virtual memory for GC"),
+ pointer_default(unique),
+ local
+]
+interface IGCHostControl : IUnknown
+{
+ // Request to increase the virtual memeory limit of the runtime (GC heap)
+ HRESULT RequestVirtualMemLimit([in] SIZE_T sztMaxVirtualMemMB,
+ [in, out] SIZE_T* psztNewMaxVirtualMemMB);
+}
+
+//*****************************************************************************
+// Interface for accessing threadpool
+//*****************************************************************************
+cpp_quote("#ifdef __midl")
+typedef VOID (__stdcall *WAITORTIMERCALLBACK)(PVOID, BOOL);
+cpp_quote("#endif // __midl")
+
+cpp_quote("#ifdef __midl")
+typedef DWORD (__stdcall *LPTHREAD_START_ROUTINE)(LPVOID lpThreadParameter);
+typedef VOID (*LPOVERLAPPED_COMPLETION_ROUTINE)(DWORD dwErrorCode,
+ DWORD dwNumberOfBytesTransfered,
+ LPVOID lpOverlapped);
+cpp_quote("#endif // __midl")
+
+// Callback function for cleaning up TLS
+typedef VOID (__stdcall *PTLS_CALLBACK_FUNCTION)(PVOID);
+
+[
+ uuid(84680D3A-B2C1-46e8-ACC2-DBC0A359159A),
+ version(1.0),
+ helpstring("Threadpool interface"),
+ pointer_default(unique),
+ local
+]
+interface ICorThreadpool : IUnknown
+{
+ HRESULT CorRegisterWaitForSingleObject([in] HANDLE* phNewWaitObject,
+ [in] HANDLE hWaitObject,
+ [in] WAITORTIMERCALLBACK Callback,
+ [in] PVOID Context,
+ [in] ULONG timeout,
+ [in] BOOL executeOnlyOnce,
+ [out] BOOL* result );
+
+ HRESULT CorUnregisterWait([in] HANDLE hWaitObject,[in] HANDLE CompletionEvent,[out] BOOL* result);
+
+ HRESULT CorQueueUserWorkItem([in] LPTHREAD_START_ROUTINE Function,
+ [in] PVOID Context,
+ [in] BOOL executeOnlyOnce,
+ [out] BOOL* result );
+
+
+ HRESULT CorCreateTimer([in] HANDLE* phNewTimer,
+ [in] WAITORTIMERCALLBACK Callback,
+ [in] PVOID Parameter,
+ [in] DWORD DueTime,
+ [in] DWORD Period,
+ [out] BOOL* result);
+
+ HRESULT CorChangeTimer([in] HANDLE Timer, [in] ULONG DueTime, [in] ULONG Period, [out] BOOL* result);
+
+ HRESULT CorDeleteTimer([in] HANDLE Timer, [in] HANDLE CompletionEvent, [out] BOOL* result);
+
+ HRESULT CorBindIoCompletionCallback([in] HANDLE fileHandle, [in] LPOVERLAPPED_COMPLETION_ROUTINE callback);
+
+ HRESULT CorCallOrQueueUserWorkItem([in] LPTHREAD_START_ROUTINE Function,
+ [in] PVOID Context,
+ [out] BOOL* result );
+ HRESULT CorSetMaxThreads([in] DWORD MaxWorkerThreads,
+ [in] DWORD MaxIOCompletionThreads);
+
+ HRESULT CorGetMaxThreads([out] DWORD *MaxWorkerThreads,
+ [out] DWORD *MaxIOCompletionThreads);
+
+ HRESULT CorGetAvailableThreads([out] DWORD *AvailableWorkerThreads,
+ [out] DWORD *AvailableIOCompletionThreads);
+
+
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+cpp_quote("EXTERN_GUID(IID_IDebuggerThreadControl, 0x23d86786, 0x0bb5, 0x4774, 0x8f, 0xb5, 0xe3, 0x52, 0x2a, 0xdd, 0x62, 0x46);")
+[
+ uuid(23D86786-0BB5-4774-8FB5-E3522ADD6246),
+ version(1.0),
+ helpstring("Control over threads blocked in debugging services"),
+ pointer_default(unique),
+ local
+]
+interface IDebuggerThreadControl : IUnknown
+{
+ // Notification that the thread making the call is about to
+ // block within the debugging services. This gives the host
+ // an opportunity to perform another action while the thread
+ // blocks. This will always be called on a Runtime thread.
+ HRESULT ThreadIsBlockingForDebugger();
+
+ // Notification that the debugging services is about to
+ // release all threads it has blocked. This will never be
+ // called on a Runtime thread. If the host has a Runtime
+ // thread blocked in ThreadIsBlockingForDebugger() then it
+ // should release it now.
+ HRESULT ReleaseAllRuntimeThreads();
+
+ // Notification that the debugging services are about to
+ // start blocking all threads. This could be called on a
+ // Runtime thread. This is the signal to the host to
+ // start blocking threads in ThreadIsBlockingForDebugger().
+ HRESULT StartBlockingForDebugger(DWORD dwUnused);
+}
+
+cpp_quote("EXTERN_GUID(IID_IDebuggerInfo, 0xbf24142d, 0xa47d, 0x4d24, 0xa6, 0x6d, 0x8c, 0x21, 0x41, 0x94, 0x4e, 0x44);")
+[
+ uuid(BF24142D-A47D-4d24-A66D-8C2141944E44),
+ version(1.0),
+ helpstring("Information on the state of the debugging services"),
+ pointer_default(unique),
+ local
+]
+interface IDebuggerInfo : IUnknown
+{
+ // Indicates whether or not a managed debugger is attached to this process.
+ HRESULT IsDebuggerAttached([out] BOOL *pbAttached);
+}
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+// {5C2B07A5-1E98-11d3-872F-00C04F79ED0D}
+cpp_quote("EXTERN_GUID(IID_ICorConfiguration, 0x5c2b07a5, 0x1e98, 0x11d3, 0x87, 0x2f, 0x00, 0xc0, 0x4f, 0x79, 0xed, 0x0d);")
+[
+ uuid(5C2B07A5-1E98-11d3-872F-00C04F79ED0D),
+ version(1.0),
+ helpstring("Common Language Runtime Configuration Interface"),
+ pointer_default(unique),
+ local
+]
+interface ICorConfiguration : IUnknown
+{
+ // Set the callback for scheduling threads for non-runtime tasks when they
+ // would otherwise be blocked for a GC.
+ HRESULT SetGCThreadControl([in] IGCThreadControl* pGCThreadControl);
+
+ // Set the callback for gc to request a change in virtual memmory limit
+ HRESULT SetGCHostControl([in] IGCHostControl* pGCHostControl);
+
+ // Set the callback interface that the debugging services will
+ // call as Runtime threads are blocked and un-blocked for
+ // debugging.
+ HRESULT SetDebuggerThreadControl([in] IDebuggerThreadControl* pDebuggerThreadControl);
+
+ // The host may indicate to the debugging services that a
+ // particular thread should be allowed to continue to execute
+ // while the debugger has an application stopped during
+ // managed/unmanaged debugging scenarios. The specified thread
+ // will not be allowed to run managed code, or to enter the
+ // Runtime in any way. An example of such a thread would be an
+ // in-process thread to support legacy script debuggers.
+ HRESULT AddDebuggerSpecialThread([in] DWORD dwSpecialThreadId);
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+//*****************************************************************************
+// Interface for hosting mscoree
+//*****************************************************************************
+typedef void* HDOMAINENUM;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ uuid(CB2F6722-AB3A-11d2-9C40-00C04FA30A3E),
+ version(1.0),
+ helpstring("Common Language Runtime Hosting Interface"),
+ pointer_default(unique),
+ local
+]
+interface ICorRuntimeHost : IUnknown
+{
+ HRESULT CreateLogicalThreadState();
+ HRESULT DeleteLogicalThreadState();
+ HRESULT SwitchInLogicalThreadState(
+ [in] DWORD *pFiberCookie); // [in] Cookie that indicates the fiber to use.
+
+ HRESULT SwitchOutLogicalThreadState(
+ [out] DWORD **pFiberCookie); // [out] Cookie that indicates the fiber being switched out.
+
+ HRESULT LocksHeldByLogicalThread( // Return code.
+ [out] DWORD *pCount // [out] Number of locks that the current thread holds.
+ );
+
+ HRESULT MapFile(
+ [in] HANDLE hFile, // [in] HANDLE for file
+ [out] HMODULE* hMapAddress); // [out] HINSTANCE for mapped file
+
+ //=================================================================
+ //
+ // New hosting methods
+ //
+ // Returns an object for configuring the runtime prior to
+ // it starting. If the runtime has been initialized this
+ // routine returns an error. See ICorConfiguration.
+ HRESULT GetConfiguration([out] ICorConfiguration** pConfiguration);
+
+ // Starts the runtime. This is equivalent to CoInitializeCor();
+ HRESULT Start();
+
+ // Terminates the runtime, This is equivalent CoUninitializeCor();
+ HRESULT Stop();
+
+ // Creates a domain in the runtime. The identity array is
+ // a pointer to an array TYPE containing IIdentity objects defining
+ // the security identity.
+ HRESULT CreateDomain([in] LPCWSTR pwzFriendlyName,
+ [in] IUnknown* pIdentityArray, // Optional
+ [out] IUnknown** pAppDomain);
+
+ // Returns the default domain.
+ HRESULT GetDefaultDomain([out] IUnknown** pAppDomain);
+
+
+ // Enumerate currently existing domains.
+ HRESULT EnumDomains([out] HDOMAINENUM *hEnum);
+
+ // Returns S_FALSE when there are no more domains. A domain
+ // is passed out only when S_OK is returned.
+ HRESULT NextDomain([in] HDOMAINENUM hEnum,
+ [out] IUnknown** pAppDomain);
+
+ // Close the enumeration, releasing resources
+ HRESULT CloseEnum([in] HDOMAINENUM hEnum);
+
+ HRESULT CreateDomainEx([in] LPCWSTR pwzFriendlyName, // Optional
+ [in] IUnknown* pSetup, // Optional
+ [in] IUnknown* pEvidence, // Optional
+ [out] IUnknown** pAppDomain);
+
+ HRESULT CreateDomainSetup([out] IUnknown** pAppDomainSetup);
+
+ HRESULT CreateEvidence([out] IUnknown** pEvidence);
+
+ HRESULT UnloadDomain([in] IUnknown* pAppDomain);
+
+ // Returns the thread's domain.
+ HRESULT CurrentDomain([out] IUnknown** pAppDomain);
+};
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+typedef enum
+{
+ eMemoryAvailableLow = 1,
+ eMemoryAvailableNeutral = 2,
+ eMemoryAvailableHigh = 3
+} EMemoryAvailable;
+
+typedef enum
+{
+ eTaskCritical = 0,
+ eAppDomainCritical = 1,
+ eProcessCritical = 2
+} EMemoryCriticalLevel;
+
+typedef enum {
+ WAIT_MSGPUMP = 0x1,
+ WAIT_ALERTABLE = 0x2,
+ WAIT_NOTINDEADLOCK = 0x4
+}WAIT_OPTION;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+cpp_quote("EXTERN_GUID(IID_ICLRMemoryNotificationCallback, 0x47EB8E57, 0x0846, 0x4546, 0xAF, 0x76, 0x6F, 0x42, 0xFC, 0xFC, 0x26, 0x49);")
+[
+ uuid(47EB8E57-0846-4546-AF76-6F42FCFC2649),
+ version(1.0),
+ helpstring("Callback by Host to notify runtime short of memory"),
+ pointer_default(unique),
+ local
+]
+interface ICLRMemoryNotificationCallback : IUnknown
+{
+ // Callback by Host on out of memory to request runtime to free memory.
+ // Runtime will do a GC and Wait for PendingFinalizer.
+ HRESULT OnMemoryNotification([in] EMemoryAvailable eMemoryAvailable);
+}
+
+[
+ uuid(1831991C-CC53-4A31-B218-04E910446479),
+ version(1.0),
+ helpstring("Host Malloc"),
+ pointer_default(unique),
+ local
+]
+interface IHostMalloc : IUnknown
+{
+ HRESULT Alloc([in] SIZE_T cbSize,
+ [in] EMemoryCriticalLevel eCriticalLevel,
+ [out] void** ppMem);
+
+ HRESULT DebugAlloc([in] SIZE_T cbSize,
+ [in] EMemoryCriticalLevel eCriticalLevel,
+ [in, annotation("_In_ ")] char* pszFileName,
+ [in] int iLineNo,
+ [out, annotation("_Outptr_result_maybenull_")] void** ppMem);
+
+ HRESULT Free([in] void* pMem);
+}
+
+typedef enum
+{
+ MALLOC_THREADSAFE = 0x1,
+ MALLOC_EXECUTABLE = 0x2,
+} MALLOC_TYPE;
+
+[
+ uuid(7BC698D1-F9E3-4460-9CDE-D04248E9FA25),
+ version(1.0),
+ helpstring("Host memory manager"),
+ pointer_default(unique),
+ local
+]
+interface IHostMemoryManager : IUnknown
+{
+ HRESULT CreateMalloc([in] DWORD dwMallocType,
+ [out] IHostMalloc **ppMalloc);
+
+ HRESULT VirtualAlloc([in] void* pAddress,
+ [in] SIZE_T dwSize,
+ [in] DWORD flAllocationType,
+ [in] DWORD flProtect,
+ [in] EMemoryCriticalLevel eCriticalLevel,
+ [out] void** ppMem);
+
+ HRESULT VirtualFree([in] LPVOID lpAddress,
+ [in] SIZE_T dwSize,
+ [in] DWORD dwFreeType);
+
+ HRESULT VirtualQuery([in] void * lpAddress,
+ [out] void* lpBuffer,
+ [in] SIZE_T dwLength,
+ [out] SIZE_T * pResult);
+
+ HRESULT VirtualProtect([in] void * lpAddress,
+ [in] SIZE_T dwSize,
+ [in] DWORD flNewProtect,
+ [out] DWORD * pflOldProtect);
+
+ HRESULT GetMemoryLoad([out] DWORD* pMemoryLoad,
+ [out] SIZE_T *pAvailableBytes);
+
+ HRESULT RegisterMemoryNotificationCallback([in] ICLRMemoryNotificationCallback * pCallback);
+
+ HRESULT NeedsVirtualAddressSpace(
+ [in] LPVOID startAddress,
+ [in] SIZE_T size
+ );
+
+ HRESULT AcquiredVirtualAddressSpace(
+ [in] LPVOID startAddress,
+ [in] SIZE_T size
+ );
+
+ HRESULT ReleasedVirtualAddressSpace(
+ [in] LPVOID startAddress
+ );
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+typedef UINT64 TASKID;
+typedef DWORD CONNID;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ uuid(28E66A4A-9906-4225-B231-9187C3EB8611),
+ version(1.0),
+ helpstring("Callback by Host to collaborate with CLR on HostTask"),
+ pointer_default(unique),
+ local
+]
+interface ICLRTask: IUnknown
+{
+ HRESULT SwitchIn([in] HANDLE threadHandle);
+ HRESULT SwitchOut();
+ HRESULT GetMemStats([out] COR_GC_THREAD_STATS *memUsage);
+ HRESULT Reset(BOOL fFull);
+ HRESULT ExitTask();
+ HRESULT Abort();
+ HRESULT RudeAbort();
+ HRESULT NeedsPriorityScheduling([out] BOOL * pbNeedsPriorityScheduling);
+ HRESULT YieldTask();
+ HRESULT LocksHeld([out] SIZE_T *pLockCount);
+ HRESULT SetTaskIdentifier([in] TASKID asked);
+}
+
+[
+ uuid(28E66A4A-9906-4225-B231-9187C3EB8612),
+ version(1.0),
+ helpstring("Callback by Host to collaborate with CLR on HostTask"),
+ pointer_default(unique),
+ local
+]
+interface ICLRTask2 : ICLRTask
+{
+ HRESULT BeginPreventAsyncAbort();
+ HRESULT EndPreventAsyncAbort();
+}
+
+
+[
+ uuid(C2275828-C4B1-4B55-82C9-92135F74DF1A),
+ version(1.0),
+ helpstring("Called by CLR to operate on a HostTask"),
+ pointer_default(unique),
+ local
+]
+interface IHostTask : IUnknown
+{
+ HRESULT Start();
+ HRESULT Alert();
+ HRESULT Join([in] DWORD dwMilliseconds,
+ [in] DWORD option);
+ HRESULT SetPriority([in] int newPriority);
+ HRESULT GetPriority([out] int *pPriority);
+ HRESULT SetCLRTask([in] ICLRTask *pCLRTask);
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+typedef enum ETaskType
+{
+ TT_DEBUGGERHELPER = 0x1,
+ TT_GC = 0x2,
+ TT_FINALIZER = 0x4,
+ TT_THREADPOOL_TIMER = 0x8,
+ TT_THREADPOOL_GATE = 0x10,
+ TT_THREADPOOL_WORKER = 0x20,
+ TT_THREADPOOL_IOCOMPLETION = 0x40,
+ TT_ADUNLOAD = 0x80,
+ TT_USER = 0x100,
+ TT_THREADPOOL_WAIT = 0x200,
+
+ TT_UNKNOWN = 0x80000000,
+} ETaskType;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ uuid(4862efbe-3ae5-44f8-8feb-346190ee8a34),
+ version(1.0),
+ helpstring("Functions provided by CLR to handle a CLRTask"),
+ pointer_default(unique),
+ local
+]
+interface ICLRTaskManager : IUnknown
+{
+ HRESULT CreateTask ([out] ICLRTask **pTask);
+ HRESULT GetCurrentTask ([out] ICLRTask **pTask);
+ HRESULT SetUILocale([in] LCID lcid);
+ HRESULT SetLocale([in] LCID lcid);
+
+ HRESULT GetCurrentTaskType([out] ETaskType *pTaskType);
+
+}
+
+[
+ uuid(997FF24C-43B7-4352-8667-0DC04FAFD354),
+ version(1.0),
+ helpstring("Functions provided by host to handle a HostTask"),
+ pointer_default(unique),
+ local
+]
+interface IHostTaskManager : IUnknown
+{
+ HRESULT GetCurrentTask ([out] IHostTask **pTask);
+ HRESULT CreateTask ([in] DWORD dwStackSize,
+ [in] LPTHREAD_START_ROUTINE pStartAddress,
+ [in] PVOID pParameter,
+ [out] IHostTask **ppTask);
+ HRESULT Sleep([in] DWORD dwMilliseconds,
+ [in] DWORD option);
+ HRESULT SwitchToTask([in] DWORD option);
+
+ HRESULT SetUILocale([in] LCID lcid);
+ HRESULT SetLocale([in] LCID lcid);
+
+ HRESULT CallNeedsHostHook([in] SIZE_T target,
+ [out] BOOL *pbCallNeedsHostHook);
+
+ HRESULT LeaveRuntime([in] SIZE_T target);
+ HRESULT EnterRuntime();
+
+ HRESULT ReverseLeaveRuntime();
+ HRESULT ReverseEnterRuntime();
+
+ HRESULT BeginDelayAbort();
+ HRESULT EndDelayAbort();
+ HRESULT BeginThreadAffinity();
+ HRESULT EndThreadAffinity();
+
+ HRESULT SetStackGuarantee([in] ULONG guarantee);
+ HRESULT GetStackGuarantee([out] ULONG *pGuarantee);
+
+ HRESULT SetCLRTaskManager([in] ICLRTaskManager *ppManager);
+
+}
+
+[
+ uuid(983D50E2-CB15-466B-80FC-845DC6E8C5FD),
+ version(1.0),
+ helpstring("Threadpool Functions provided by host"),
+ pointer_default(unique),
+ local
+]
+interface IHostThreadpoolManager : IUnknown
+{
+ HRESULT QueueUserWorkItem(
+ [in] LPTHREAD_START_ROUTINE Function,
+ [in] PVOID Context,
+ [in] ULONG Flags);
+ HRESULT SetMaxThreads(
+ [in] DWORD dwMaxWorkerThreads);
+ HRESULT GetMaxThreads(
+ [out] DWORD *pdwMaxWorkerThreads);
+ HRESULT GetAvailableThreads(
+ [out] DWORD *pdwAvailableWorkerThreads);
+ HRESULT SetMinThreads(
+ [in] DWORD dwMinIOCompletionThreads);
+ HRESULT GetMinThreads(
+ [out] DWORD *pdwMinIOCompletionThreads);
+}
+
+[
+ uuid(2d74ce86-b8d6-4c84-b3a7-9768933b3c12),
+ version(1.0),
+ helpstring("Asynchronous IO support callback"),
+ pointer_default(unique),
+ local
+]
+interface ICLRIoCompletionManager : IUnknown
+{
+ HRESULT OnComplete(
+ [in] DWORD dwErrorCode,
+ [in] DWORD NumberOfBytesTransferred,
+ [in] void* pvOverlapped);
+}
+
+[
+ uuid(8bde9d80-ec06-41d6-83e6-22580effcc20),
+ version(1.0),
+ helpstring("Asynchronous IO support provided by host"),
+ pointer_default(unique),
+ local
+]
+interface IHostIoCompletionManager : IUnknown
+{
+ HRESULT CreateIoCompletionPort(
+ [out] HANDLE *phPort);
+ HRESULT CloseIoCompletionPort(
+ [in] HANDLE hPort);
+ HRESULT SetMaxThreads(
+ [in] DWORD dwMaxIOCompletionThreads);
+ HRESULT GetMaxThreads(
+ [out] DWORD *pdwMaxIOCompletionThreads);
+ HRESULT GetAvailableThreads(
+ [out] DWORD *pdwAvailableIOCompletionThreads);
+ HRESULT GetHostOverlappedSize(
+ [out] DWORD * pcbSize);
+ HRESULT SetCLRIoCompletionManager(
+ [in] ICLRIoCompletionManager * pManager);
+ HRESULT InitializeHostOverlapped(
+ [in] void * pvOverlapped);
+ HRESULT Bind(
+ [in] HANDLE hPort,
+ [in] HANDLE hHandle);
+ HRESULT SetMinThreads(
+ [in] DWORD dwMinIOCompletionThreads);
+ HRESULT GetMinThreads(
+ [out] DWORD *pdwMinIOCompletionThreads);
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+typedef enum {
+ eSymbolReadingNever = 0, // Never read PDBs
+ eSymbolReadingAlways = 1, // Always read PDBs
+ eSymbolReadingFullTrustOnly = 2 // Only read PDBs that correspond to full-trust assemblies
+} ESymbolReadingPolicy;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ uuid(00DCAEC6-2AC0-43a9-ACF9-1E36C139B10D),
+ version(1.0),
+ helpstring("CLR debugger manager"),
+ pointer_default(unique),
+ local
+]
+interface ICLRDebugManager : IUnknown
+{
+ HRESULT BeginConnection(
+ [in] CONNID dwConnectionId,
+ [in, string, annotation("_In_")] wchar_t *szConnectionName);
+ HRESULT SetConnectionTasks(
+ [in] CONNID id,
+ [in] DWORD dwCount,
+ [in, size_is(dwCount)] ICLRTask **ppCLRTask);
+ HRESULT EndConnection(
+ [in] CONNID dwConnectionId);
+ // Set ACL on shared section, events, and process
+ HRESULT SetDacl([in] PACL pacl);
+
+ // Returning the current ACL that CLR is using
+ // The memory is allocated by runtime using CoTaskmemAlloc. Caller must
+ // free the memory pointed to by pacl using CoTaskMemFree.
+ HRESULT GetDacl([out] PACL *pacl);
+
+ // Indicates whether or not a managed debugger is attached to this process.
+ HRESULT IsDebuggerAttached([out] BOOL *pbAttached);
+
+ // Specify whether the symbol reader should be used. Affects whether file and line
+ // info can be included when the CLR captures a call stack.
+ HRESULT SetSymbolReadingPolicy([in] ESymbolReadingPolicy policy);
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+typedef enum {
+ // Default to minidump
+ DUMP_FLAVOR_Mini = 0,
+
+ // Include critical CLR state
+ DUMP_FLAVOR_CriticalCLRState = 1,
+
+ // Include critical CLR state and ngen images without including hosted heap
+ // It is host's responsibility to report hosted heap.
+ DUMP_FLAVOR_NonHeapCLRState = 2,
+
+ DUMP_FLAVOR_Default = DUMP_FLAVOR_Mini
+
+} ECustomDumpFlavor;
+
+// reserved for future extension
+typedef enum
+{
+ DUMP_ITEM_None = 0
+} ECustomDumpItemKind;
+
+//
+// The CustomDumpItem structure describes an item to be added to a dump.
+// It is defined for future expansion and is not presently used.
+//
+typedef struct
+{
+ ECustomDumpItemKind itemKind; //this affects how next fields are interpreted.
+ union
+ {
+ // Union to be expanded later if need be
+ UINT_PTR pReserved;
+ };
+} CustomDumpItem;
+
+const DWORD BucketParamsCount = 10;
+const DWORD BucketParamLength = 255;
+
+// used for indexing into BucketParameters::pszParams
+typedef enum
+{
+ Parameter1 = 0,
+ Parameter2,
+ Parameter3,
+ Parameter4,
+ Parameter5,
+ Parameter6,
+ Parameter7,
+ Parameter8,
+ Parameter9,
+ InvalidBucketParamIndex
+} BucketParameterIndex;
+
+typedef struct _BucketParameters
+{
+ BOOL fInited; // Set to TRUE if the rest of this structure is valid.
+ WCHAR pszEventTypeName[BucketParamLength]; // Name of the event type.
+ WCHAR pszParams[BucketParamsCount][BucketParamLength]; // Parameter strings.
+} BucketParameters;
+
+#if defined(FEATURE_INCLUDE_ALL_INTERFACES) || defined(FEATURE_WINDOWSPHONE)
+[
+ uuid(980D2F1A-BF79-4c08-812A-BB9778928F78),
+ version(1.0),
+ helpstring("CLR error reporting manager"),
+ pointer_default(unique),
+ local
+]
+interface ICLRErrorReportingManager : IUnknown
+{
+ // Get Watson bucket parameters for "current" exception (on calling thread).
+ HRESULT GetBucketParametersForCurrentException([out] BucketParameters *pParams);
+
+ // The BeginCustomDump function configures the custom dump support
+ HRESULT BeginCustomDump( [in] ECustomDumpFlavor dwFlavor,
+ [in] DWORD dwNumItems,
+ [in, size_is(dwNumItems), length_is(dwNumItems)] CustomDumpItem *items,
+ DWORD dwReserved);
+
+ // EndCustomDump clears the custom dump configuration
+ HRESULT EndCustomDump();
+}
+
+#ifdef FEATURE_WINDOWSPHONE
+typedef enum
+{
+ // indicates that the specified value is the Application ID
+ ApplicationID = 0x1,
+
+ // indicates that the specified value is the application's Instance ID
+ InstanceID = 0x2,
+
+ // additional values are reserved for future use
+} ApplicationDataKey;
+
+[
+ uuid(C68F63B1-4D8B-4E0B-9564-9D2EFE2FA18C),
+ version(1.0),
+ helpstring("CLR error reporting manager 2"),
+ pointer_default(unique),
+ local
+]
+interface ICLRErrorReportingManager2 : ICLRErrorReportingManager
+{
+ // This API will allow the host to specify key/value pairs of data to be consumed by the CLR.
+ //
+ // Parameters:
+ // [in] key - One of the values specified in the ApplicationDataKey enumerated type.
+ //
+ // [in] pValue - A NULL-terminated WCHAR string with a maximum length of MAX_PATH containing the corresponding
+ // value. Note that the CLR maintains its own copy of the data so this structure does not need
+ // to persist after the API call returns.
+ //
+ // Return values:
+ // S_OK upon success.
+ //
+ // Any other return value indicates that the API did not complete successfully and no value was set.
+ //
+ // Well-defined errors:
+ // E_INVALIDOPERATION if the CLR has already started.
+ // E_INVALIDARG for any of the following:
+ // key is not within the range of valid values for ApplicationDataKey
+ // pValue == NULL
+ // length of pValue is greater than MAX_PATH
+ HRESULT SetApplicationData([in] ApplicationDataKey key, [in] WCHAR const* pValue);
+
+ // This API will allow the host to specify pre-defined Watson bucket data in the event of an unhandled
+ // exception, allowing the host to override Watson bucket parameter data that is usually collected and
+ // populated by the CLR. It should be called before the CLR has started.
+ // The BucketParameters data structure must be properly initialized before calling this API by zeroing
+ // out all fields, setting pszParams entries as required, then setting fInited to TRUE.
+ // A NULL pszParams entry indicates that the bucket parameter should not be overridden, and if all pszParams
+ // entries are NULL then the API call will fail.
+ // To override a bucket parameter with an empty string specify a pszParams entry with a blank string (one or
+ // more whitespace characters).
+ //
+ // NOTE: The current implementation allows overriding of the first bucket parameter only (pszParams[0]).
+ // Any other non-NULL pszParams entries will be ignored. This is subject to change in future releases.
+ //
+ // Parameters:
+ // [in] pBucketParams - A pointer to an initialized BucketParameters structure which contains the data to be
+ // reported in the event of an unhandled exception. Note that the CLR maintains its own
+ // copy of the data so this structure does not need to persist after the API call returns.
+ //
+ // [out] pCountParams - A pointer to a DWORD indicating the number of bucket parameter values that have
+ // been overridden by the host. A count of 0 indicates that no parameters were
+ // overridden.
+ //
+ // Return values:
+ // S_OK upon success. In this case the value pointed to by pCountParams will be greater than 0.
+ //
+ // Any other return value indicates that the API did not complete successfully. In this case the value
+ // pointed to by pCountParams will be 0.
+ //
+ // Well-defined errors:
+ // E_INVALIDOPERATION if the CLR has already started.
+ // E_INVALIDARG for any of the following:
+ // pBucketParams or pCountParams is NULL
+ // pBucketParams->fInited != TRUE
+ // if all BucketParameters.pszParams are NULL
+ HRESULT SetBucketParametersForUnhandledException([in] BucketParameters const* pBucketParams, [out] DWORD* pCountParams);
+}
+#endif // FEATURE_WINDOWSPHONE
+
+#endif // defined(FEATURE_INCLUDE_ALL_INTERFACES) || defined(FEATURE_WINDOWSPHONE)
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ uuid(6DF710A6-26A4-4a65-8CD5-7237B8BDA8DC),
+ version(1.0),
+ helpstring("CriticalSection provided by host"),
+ pointer_default(unique),
+ local
+]
+interface IHostCrst : IUnknown
+{
+ HRESULT Enter([in] DWORD option);
+ HRESULT Leave();
+ HRESULT TryEnter([in] DWORD option,
+ [out] BOOL *pbSucceeded);
+ HRESULT SetSpinCount([in] DWORD dwSpinCount);
+}
+
+[
+ uuid(50B0CFCE-4063-4278-9673-E5CB4ED0BDB8),
+ version(1.0),
+ helpstring("AutoEvent provided by host"),
+ pointer_default(unique),
+ local
+]
+interface IHostAutoEvent : IUnknown
+{
+ HRESULT Wait([in] DWORD dwMilliseconds,
+ [in] DWORD option);
+ HRESULT Set();
+}
+
+[
+ uuid(1BF4EC38-AFFE-4fb9-85A6-525268F15B54),
+ version(1.0),
+ helpstring("ManualEvent provided by host"),
+ pointer_default(unique),
+ local
+]
+interface IHostManualEvent : IUnknown
+{
+ HRESULT Wait([in] DWORD dwMilliseconds,
+ [in] DWORD option);
+ HRESULT Reset();
+ HRESULT Set();
+}
+
+[
+ uuid(855efd47-cc09-463a-a97d-16acab882661),
+ version(1.0),
+ helpstring("Semaphore provided by host"),
+ pointer_default(unique),
+ local
+]
+interface IHostSemaphore : IUnknown
+{
+ HRESULT Wait([in] DWORD dwMilliseconds,
+ [in] DWORD option);
+ HRESULT ReleaseSemaphore([in] LONG lReleaseCount,
+ [out] LONG *lpPreviousCount);
+}
+
+[
+ uuid(55FF199D-AD21-48f9-A16C-F24EBBB8727D),
+ version(1.0),
+ helpstring("Functions provided by CLR to provide infomation on synchronization objects"),
+ pointer_default(unique),
+ local
+]
+interface ICLRSyncManager : IUnknown
+{
+ HRESULT GetMonitorOwner ([in] SIZE_T Cookie,
+ [out] IHostTask **ppOwnerHostTask);
+
+ HRESULT CreateRWLockOwnerIterator([in] SIZE_T Cookie, [out] SIZE_T *pIterator);
+ HRESULT GetRWLockOwnerNext([in] SIZE_T Iterator, [out] IHostTask **ppOwnerHostTask);
+ HRESULT DeleteRWLockOwnerIterator([in] SIZE_T Iterator);
+}
+
+[
+ uuid(234330c7-5f10-4f20-9615-5122dab7a0ac),
+ version(1.0),
+ helpstring("Functions provided by host to create synchronization objects"),
+ pointer_default(unique),
+ local
+]
+interface IHostSyncManager : IUnknown
+{
+ HRESULT SetCLRSyncManager([in] ICLRSyncManager *pManager);
+
+ HRESULT CreateCrst([out] IHostCrst** ppCrst);
+ HRESULT CreateCrstWithSpinCount ([in] DWORD dwSpinCount,
+ [out] IHostCrst** ppCrst);
+
+ HRESULT CreateAutoEvent([out] IHostAutoEvent **ppEvent);
+ HRESULT CreateManualEvent([in] BOOL bInitialState,
+ [out] IHostManualEvent **ppEvent);
+
+ HRESULT CreateMonitorEvent([in] SIZE_T Cookie,
+ [out] IHostAutoEvent **ppEvent);
+
+ HRESULT CreateRWLockWriterEvent([in] SIZE_T Cookie,
+ [out] IHostAutoEvent **ppEvent);
+ HRESULT CreateRWLockReaderEvent([in] BOOL bInitialState,
+ [in] SIZE_T Cookie,
+ [out] IHostManualEvent **ppEvent);
+
+ HRESULT CreateSemaphore([in] DWORD dwInitial,
+ [in] DWORD dwMax,
+ [out] IHostSemaphore ** ppSemaphore);
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+typedef enum
+{
+ OPR_ThreadAbort,
+ OPR_ThreadRudeAbortInNonCriticalRegion,
+ OPR_ThreadRudeAbortInCriticalRegion,
+ OPR_AppDomainUnload,
+ OPR_AppDomainRudeUnload,
+ OPR_ProcessExit,
+ OPR_FinalizerRun,
+ MaxClrOperation
+ // Do not add anything after this
+} EClrOperation;
+
+typedef enum
+{
+ FAIL_NonCriticalResource,
+ FAIL_CriticalResource,
+ FAIL_FatalRuntime,
+ FAIL_OrphanedLock,
+ FAIL_StackOverflow,
+ // In CoreCLR, we will treat AV specially, based upon the escalation policy.
+ // Currently only used in CoreCLR.
+ FAIL_AccessViolation,
+ FAIL_CodeContract,
+ MaxClrFailure
+ // Do not add anything after this
+} EClrFailure;
+
+typedef enum
+{
+ eRuntimeDeterminedPolicy, // default
+ eHostDeterminedPolicy, // revert back to Everett behavior, i.e. swallow all exception
+} EClrUnhandledException;
+
+typedef enum
+{
+ // !!! Please keep these ordered by severity
+ // !!! If you don't, you need to change EEPolicy::IsValidActionForOperation
+ // !!! and EEPolicy::IsValidActionForFailure
+ eNoAction,
+ eThrowException,
+ eAbortThread,
+ eRudeAbortThread,
+ eUnloadAppDomain,
+ eRudeUnloadAppDomain,
+ eExitProcess,
+ // Look at CorHost2::Stop. For eFastExitProcess, eRudeExitProcess, eDisableRuntime,
+ // Stop bypasses finalizer run.
+ eFastExitProcess,
+ eRudeExitProcess,
+ eDisableRuntime,
+ MaxPolicyAction
+} EPolicyAction;
+
+[
+ uuid(7D290010-D781-45da-A6F8-AA5D711A730E),
+ version(1.0),
+ helpstring("Allow host to specify policy for CLR to follow in abnormal condition"),
+ pointer_default(unique),
+ local
+]
+interface ICLRPolicyManager: IUnknown
+{
+ HRESULT SetDefaultAction(
+ [in] EClrOperation operation,
+ [in] EPolicyAction action);
+
+ HRESULT SetTimeout(
+ [in] EClrOperation operation,
+ [in] DWORD dwMilliseconds);
+
+ HRESULT SetActionOnTimeout(
+ [in] EClrOperation operation,
+ [in] EPolicyAction action);
+
+ HRESULT SetTimeoutAndAction(
+ [in] EClrOperation operation,
+ [in] DWORD dwMilliseconds,
+ [in] EPolicyAction action);
+
+ HRESULT SetActionOnFailure(
+ [in] EClrFailure failure,
+ [in] EPolicyAction action);
+
+ HRESULT SetUnhandledExceptionPolicy(
+ [in] EClrUnhandledException policy);
+}
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ uuid(7AE49844-B1E3-4683-BA7C-1E8212EA3B79),
+ version(1.0),
+ helpstring("Notify host about how CLR handles abnormal condition"),
+ pointer_default(unique),
+ local
+]
+interface IHostPolicyManager: IUnknown
+{
+ HRESULT OnDefaultAction(
+ [in] EClrOperation operation,
+ [in] EPolicyAction action);
+
+ HRESULT OnTimeout(
+ [in] EClrOperation operation,
+ [in] EPolicyAction action);
+
+ HRESULT OnFailure(
+ [in] EClrFailure failure,
+ [in] EPolicyAction action);
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+typedef enum
+{
+ Event_DomainUnload,
+ Event_ClrDisabled,
+ Event_MDAFired,
+ Event_StackOverflow,
+ MaxClrEvent
+ // Do not add anything after this
+} EClrEvent;
+
+// An MDAInfo is passed via OnEvent for Event_MDAFired events.
+typedef struct _MDAInfo
+{
+ LPCWSTR lpMDACaption;
+ LPCWSTR lpMDAMessage;
+ LPCWSTR lpStackTrace;
+} MDAInfo;
+
+// An StackOverflowInfo is passed via OnEvent for Event_StackOverflow events.
+typedef enum
+{
+ SO_Managed,
+ SO_ClrEngine,
+ SO_Other,
+} StackOverflowType;
+
+cpp_quote("typedef struct _StackOverflowInfo")
+cpp_quote("{")
+cpp_quote(" StackOverflowType soType;")
+cpp_quote(" EXCEPTION_POINTERS *pExceptionInfo;")
+cpp_quote("} StackOverflowInfo;")
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ uuid(607BE24B-D91B-4E28-A242-61871CE56E35),
+ version(1.0),
+ helpstring("Allow host to register action on domain unload"),
+ pointer_default(unique),
+ local
+]
+interface IActionOnCLREvent: IUnknown
+{
+ HRESULT OnEvent(
+ [in] EClrEvent event,
+ [in] PVOID data
+ );
+}
+
+[
+ uuid(1D0E0132-E64F-493D-9260-025C0E32C175),
+ version(1.0),
+ helpstring("Allow host to register action on event"),
+ pointer_default(unique),
+ local
+]
+interface ICLROnEventManager: IUnknown
+{
+ HRESULT RegisterActionOnEvent(
+ [in] EClrEvent event,
+ [in] IActionOnCLREvent *pAction
+ );
+ HRESULT UnregisterActionOnEvent(
+ [in] EClrEvent event,
+ [in] IActionOnCLREvent *pAction
+ );
+}
+
+[
+ uuid(5D4EC34E-F248-457B-B603-255FAABA0D21),
+ version(1.0),
+ helpstring("Control over threads blocked in GC"),
+ pointer_default(unique),
+ local
+]
+interface IHostGCManager : IUnknown
+{
+ // Notification that the thread making the call is about to block, perhaps for
+ // a GC or other suspension. This gives the host an opportunity to re-schedule
+ // the thread for unmanaged tasks.
+ HRESULT ThreadIsBlockingForSuspension();
+
+ // Notification that the runtime is beginning a thread suspension for a GC or
+ // other suspension. Do not reschedule this thread!
+ HRESULT SuspensionStarting();
+
+ // Notification that the runtime is resuming threads after a GC or other
+ // suspension. Do not reschedule this thread!
+ HRESULT SuspensionEnding(DWORD Generation);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// ICLRAssemblyReferenceList
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ object,
+ version(1.0),
+ uuid(1b2c9750-2e66-4bda-8b44-0a642c5cd733),
+ helpstring("Generic Assembly Reference List, created by CLR."),
+ pointer_default(unique),
+ local
+]
+interface ICLRAssemblyReferenceList : IUnknown
+{
+ HRESULT IsStringAssemblyReferenceInList(
+ [in] LPCWSTR pwzAssemblyName
+ );
+
+ HRESULT IsAssemblyReferenceInList(
+ [in] IUnknown *pName
+ );
+};
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// ICLRReferenceAssemblyEnum
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ object,
+ version(1.0),
+ uuid(d509cb5d-cf32-4876-ae61-67770cf91973),
+ helpstring("Reference Enum of an Assembly."),
+ pointer_default(unique),
+ local
+]
+interface ICLRReferenceAssemblyEnum : IUnknown
+{
+ HRESULT Get(
+ [in] DWORD dwIndex,
+ [out, size_is(*pcchBufferSize), annotation("_Out_writes_all_(*pcchBufferSize)")]
+ LPWSTR pwzBuffer,
+ [in, out] DWORD *pcchBufferSize
+ );
+};
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// ICLRProbingAssemblyEnum
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ object,
+ version(1.0),
+ uuid(d0c5fb1f-416b-4f97-81f4-7ac7dc24dd5d),
+ helpstring("The assemblies CLR will probe for given assembly"),
+ pointer_default(unique),
+ local
+]
+interface ICLRProbingAssemblyEnum:IUnknown
+{
+ HRESULT Get(
+ [in] DWORD dwIndex,
+ [out, size_is(*pcchBufferSize), annotation("_Out_writes_all_(*pcchBufferSize)")]
+ LPWSTR pwzBuffer,
+ [in, out] DWORD *pcchBufferSize
+ );
+};
+
+typedef enum _CLRAssemblyIdentityFlags
+{
+ CLR_ASSEMBLY_IDENTITY_FLAGS_DEFAULT = 0
+}ECLRAssemblyIdentityFlags;
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// ICLRAssemblyIdentityManager
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ object,
+ version(1.0),
+ uuid(15f0a9da-3ff6-4393-9da9-fdfd284e6972),
+ helpstring("CLR Assembly Identity Manager"),
+ pointer_default(unique),
+ local
+]
+interface ICLRAssemblyIdentityManager : IUnknown
+{
+ HRESULT GetCLRAssemblyReferenceList(
+ [in] LPCWSTR *ppwzAssemblyReferences,
+ [in] DWORD dwNumOfReferences,
+ [out] ICLRAssemblyReferenceList **ppReferenceList
+ );
+
+ HRESULT GetBindingIdentityFromFile(
+ [in] LPCWSTR pwzFilePath,
+ [in] DWORD dwFlags,
+ [out, size_is(*pcchBufferSize), annotation("_Out_writes_all_(*pcchBufferSize)")]
+ LPWSTR pwzBuffer,
+ [in, out] DWORD *pcchBufferSize
+ );
+
+ HRESULT GetBindingIdentityFromStream(
+ [in] IStream *pStream,
+ [in] DWORD dwFlags,
+ [out, size_is(*pcchBufferSize), annotation("_Out_writes_all_(*pcchBufferSize)")]
+ LPWSTR pwzBuffer,
+ [in, out] DWORD *pcchBufferSize
+ );
+
+ HRESULT GetReferencedAssembliesFromFile(
+ [in] LPCWSTR pwzFilePath,
+ [in] DWORD dwFlags,
+ [in] ICLRAssemblyReferenceList *pExcludeAssembliesList,
+ [out] ICLRReferenceAssemblyEnum **ppReferenceEnum
+ );
+
+ HRESULT GetReferencedAssembliesFromStream(
+ [in] IStream *pStream,
+ [in] DWORD dwFlags,
+ [in] ICLRAssemblyReferenceList *pExcludeAssembliesList,
+ [out] ICLRReferenceAssemblyEnum **ppReferenceEnum
+ );
+
+ HRESULT GetProbingAssembliesFromReference(
+ [in] DWORD dwMachineType,
+ [in] DWORD dwFlags,
+ [in] LPCWSTR pwzReferenceIdentity,
+ [out] ICLRProbingAssemblyEnum **ppProbingAssemblyEnum
+ );
+
+ HRESULT IsStronglyNamed(
+ [in] LPCWSTR pwzAssemblyIdentity,
+ [out] BOOL *pbIsStronglyNamed
+ );
+};
+
+typedef enum _hostBiningPolicyModifyFlags
+{
+ HOST_BINDING_POLICY_MODIFY_DEFAULT = 0,
+ HOST_BINDING_POLICY_MODIFY_CHAIN = 1,
+ HOST_BINDING_POLICY_MODIFY_REMOVE = 2,
+ HOST_BINDING_POLICY_MODIFY_MAX = 3
+}EHostBindingPolicyModifyFlags;
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// ICLRHostBindingPolicyManager
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ object,
+ version(1.0),
+ uuid(4b3545e7-1856-48c9-a8ba-24b21a753c09),
+ helpstring("CLR Host Binding Policy Manager, managing binding policy for host."),
+ pointer_default(unique),
+ local
+]
+interface ICLRHostBindingPolicyManager : IUnknown
+{
+ HRESULT ModifyApplicationPolicy(
+ [in] LPCWSTR pwzSourceAssemblyIdentity,
+ [in] LPCWSTR pwzTargetAssemblyIdentity,
+ [in] BYTE *pbApplicationPolicy,
+ [in] DWORD cbAppPolicySize,
+ [in] DWORD dwPolicyModifyFlags,
+ [out, size_is(*pcbNewAppPolicySize), annotation("_Out_writes_all_(*pcbNewAppPolicySize)")]
+ BYTE *pbNewApplicationPolicy,
+ [in, out] DWORD *pcbNewAppPolicySize
+ );
+
+ HRESULT EvaluatePolicy(
+ [in] LPCWSTR pwzReferenceIdentity,
+ [in] BYTE *pbApplicationPolicy,
+ [in] DWORD cbAppPolicySize,
+ [out, size_is(*pcchPostPolicyReferenceIdentity), annotation("_Out_writes_all_(*pcchPostPolicyReferenceIdentity)")]
+ LPWSTR pwzPostPolicyReferenceIdentity,
+ [in, out] DWORD *pcchPostPolicyReferenceIdentity,
+ [out] DWORD *pdwPoliciesApplied
+ );
+};
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+#if defined(FEATURE_INCLUDE_ALL_INTERFACES) || defined(FEATURE_WINDOWSPHONE)
+
+/*
+ * This interface is used to get information about the GC system and
+ * control some aspects of the GC. This interface is for expert usage
+ * only, and can severely impact the performance of an application if
+ * used improperly!!
+ */
+[
+ uuid(54D9007E-A8E2-4885-B7BF-F998DEEE4F2A),
+ version(1.0),
+ pointer_default(unique),
+ local
+]
+interface ICLRGCManager : IUnknown
+{
+ /*
+ * Forces a collection to occur for the given generation, regardless of
+ * current GC statistics. A value of -1 means collect all generations.
+ */
+ HRESULT Collect([in] LONG Generation);
+
+ /*
+ * Returns a set of current statistics about the state of the GC system.
+ * These values can then be used by a smart allocation system to help the
+ * GC run, by say adding more memory or forcing a collection.
+ */
+ HRESULT GetStats([in][out] COR_GC_STATS *pStats);
+
+ /*
+ * Sets the segment size and gen 0 maximum size. This value may only be
+ * specified once and will not change if called later.
+ */
+ HRESULT SetGCStartupLimits([in] DWORD SegmentSize, [in] DWORD MaxGen0Size);
+}
+
+/*
+ * This interface is added to allow users to specify 64-bit numbers on 64-bit OSs
+ * for the parameters to SetGCStartupLimits.
+ */
+[
+ uuid(0603B793-A97A-4712-9CB4-0CD1C74C0F7C),
+ version(2.0),
+ pointer_default(unique),
+ local
+]
+interface ICLRGCManager2 : ICLRGCManager
+{
+ /*
+ * Sets the segment size and gen 0 maximum size. This value may only be
+ * specified once and will not change if called later.
+ */
+ HRESULT SetGCStartupLimitsEx([in] SIZE_T SegmentSize, [in] SIZE_T MaxGen0Size);
+};
+
+
+#endif //FEATURE_INCLUDE_ALL_INTERFACES || FEATURE_WINDOWSPHONE
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// enum EBindPolicyLevels
+//
+///////////////////////////////////////////////////////////////////////////////
+typedef enum
+{
+ ePolicyLevelNone = 0x0,
+ ePolicyLevelRetargetable = 0x1,
+ ePolicyUnifiedToCLR = 0x2,
+ ePolicyLevelApp = 0x4,
+ ePolicyLevelPublisher = 0x8,
+ ePolicyLevelHost = 0x10,
+ ePolicyLevelAdmin = 0x20,
+ ePolicyPortability = 0x40,
+} EBindPolicyLevels;
+///////////////////////////////////////////////////////////////////////////////
+//
+// struct AssemblyBindInfo
+//
+///////////////////////////////////////////////////////////////////////////////
+typedef struct _AssemblyBindInfo
+{
+ DWORD dwAppDomainId;
+ LPCWSTR lpReferencedIdentity;
+ LPCWSTR lpPostPolicyIdentity;
+ DWORD ePolicyLevel;
+}AssemblyBindInfo;
+///////////////////////////////////////////////////////////////////////////////
+//
+// struct ModuleBindInfo
+//
+///////////////////////////////////////////////////////////////////////////////
+typedef struct _ModuleBindInfo
+{
+ DWORD dwAppDomainId;
+ LPCWSTR lpAssemblyIdentity;
+ LPCWSTR lpModuleName;
+} ModuleBindInfo;
+
+
+typedef enum _HostApplicationPolicy
+{
+ HOST_APPLICATION_BINDING_POLICY = 1
+}EHostApplicationPolicy;
+
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+///////////////////////////////////////////////////////////////////////////////
+//
+// IHostAssemblyStore
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ local,
+ object,
+ version(1.0),
+ uuid(7b102a88-3f7f-496d-8fa2-c35374e01af3),
+ helpstring("Assembly Store provided by host"),
+ pointer_default(unique)
+]
+interface IHostAssemblyStore: IUnknown
+{
+ HRESULT ProvideAssembly
+ (
+ [in] AssemblyBindInfo *pBindInfo,
+ [out] UINT64 *pAssemblyId,
+ [out] UINT64 *pContext,
+ [out] IStream **ppStmAssemblyImage,
+ [out] IStream **ppStmPDB);
+
+ HRESULT ProvideModule
+ (
+ [in] ModuleBindInfo *pBindInfo,
+ [out] DWORD *pdwModuleId,
+ [out] IStream **ppStmModuleImage,
+ [out] IStream **ppStmPDB);
+};
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// IHostAssemblyManager
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ local,
+ object,
+ version(1.0),
+ uuid(613dabd7-62b2-493e-9e65-c1e32a1e0c5e),
+ helpstring("Assembly Manager provided by host"),
+ pointer_default(unique)
+]
+interface IHostAssemblyManager: IUnknown
+{
+ HRESULT GetNonHostStoreAssemblies
+ (
+ [out] ICLRAssemblyReferenceList **ppReferenceList
+ );
+
+ HRESULT GetAssemblyStore
+ (
+ [out] IHostAssemblyStore **ppAssemblyStore
+ );
+};
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+// Implemented in mscorwks.dll, use mscoree!GetRealProcAddress to get
+// a function pointer of this API.
+#pragma midl_echo("STDAPI GetCLRIdentityManager(REFIID riid, IUnknown **ppManager);")
+
+// {02CA073D-7079-4860-880A-C2F7A449C991}
+cpp_quote("EXTERN_GUID(IID_IHostControl, 0x02CA073C, 0x7079, 0x4860, 0x88, 0x0A, 0xC2, 0xF7, 0xA4, 0x49, 0xC9, 0x91);")
+[
+ uuid(02CA073C-7079-4860-880A-C2F7A449C991),
+ version(1.0),
+ helpstring("Common Language Runtime Host Control Interface"),
+ pointer_default(unique),
+ local
+]
+interface IHostControl : IUnknown
+{
+ HRESULT GetHostManager(
+ [in] REFIID riid,
+ [out] void **ppObject);
+
+ /* Notify Host with IUnknown with the pointer to AppDomainManager */
+ HRESULT SetAppDomainManager(
+ [in] DWORD dwAppDomainID,
+ [in] IUnknown* pUnkAppDomainManager);
+}
+
+cpp_quote("EXTERN_GUID(IID_ICLRControl, 0x9065597E, 0xD1A1, 0x4fb2, 0xB6, 0xBA, 0x7E, 0x1F, 0xCE, 0x23, 0x0F, 0x61);")
+[
+ uuid(9065597E-D1A1-4fb2-B6BA-7E1FCE230F61),
+ version(1.0),
+ helpstring("Common Language Runtime Control Interface"),
+ pointer_default(unique),
+ local
+]
+interface ICLRControl : IUnknown
+{
+ HRESULT GetCLRManager(
+ [in] REFIID riid,
+ [out] void **ppObject);
+
+ HRESULT SetAppDomainManagerType(
+ [in] LPCWSTR pwzAppDomainManagerAssembly,
+ [in] LPCWSTR pwzAppDomainManagerType);
+}
+
+
+
+//*****************************************************************************
+// New interface for hosting mscoree
+//*****************************************************************************
+[
+ uuid(90F1A06C-7712-4762-86B5-7A5EBA6BDB02),
+ version(1.0),
+ helpstring("Common Language Runtime Hosting Interface"),
+ pointer_default(unique),
+ local
+]
+interface ICLRRuntimeHost : IUnknown
+{
+ // Starts the runtime. This is equivalent to CoInitializeCor().
+ HRESULT Start();
+
+ // Terminates the runtime, This is equivalent CoUninitializeCor();
+ HRESULT Stop();
+
+ // Returns an object for configuring runtime, e.g. threading, lock
+ // prior it starts. If the runtime has been initialized this
+ // routine returns an error. See IHostControl.
+ HRESULT SetHostControl([in] IHostControl* pHostControl);
+
+ HRESULT GetCLRControl([out] ICLRControl** pCLRControl);
+
+ HRESULT UnloadAppDomain([in] DWORD dwAppDomainId,
+ [in] BOOL fWaitUntilDone);
+
+ HRESULT ExecuteInAppDomain([in] DWORD dwAppDomainId,
+ [in] FExecuteInAppDomainCallback pCallback,
+ [in] void* cookie);
+
+ HRESULT GetCurrentAppDomainId([out] DWORD *pdwAppDomainId);
+
+ HRESULT ExecuteApplication([in] LPCWSTR pwzAppFullName,
+ [in] DWORD dwManifestPaths,
+ [in] LPCWSTR *ppwzManifestPaths, // optional
+ [in] DWORD dwActivationData,
+ [in] LPCWSTR *ppwzActivationData, // optional
+ [out] int *pReturnValue);
+
+ HRESULT ExecuteInDefaultAppDomain([in] LPCWSTR pwzAssemblyPath,
+ [in] LPCWSTR pwzTypeName,
+ [in] LPCWSTR pwzMethodName,
+ [in] LPCWSTR pwzArgument,
+ [out] DWORD *pReturnValue);
+};
+
+#ifdef FEATURE_CORECLR
+
+// Keys for ICLRRuntmeHost2::Authenticate. No longer required.
+cpp_quote("#define CORECLR_HOST_AUTHENTICATION_KEY 0x1C6CA6F94025800LL")
+cpp_quote("#define CORECLR_HOST_AUTHENTICATION_KEY_NONGEN 0x1C6CA6F94025801LL")
+
+//*****************************************************************************
+// New interface for hosting mscoree
+//*****************************************************************************
+[
+ object,
+ uuid(712AB73F-2C22-4807-AD7E-F501D7B72C2D),
+ version(2.0),
+ helpstring("Common Language Runtime Hosting Interface"),
+ pointer_default(unique),
+ local
+]
+interface ICLRRuntimeHost2 : ICLRRuntimeHost
+{
+ // Creates an app domain (sandboxed or not) with the given manager class and the given
+ // set of properties.
+ HRESULT CreateAppDomainWithManager([in] LPCWSTR wszFriendlyName,
+ [in] DWORD dwFlags,
+ [in] LPCWSTR wszAppDomainManagerAssemblyName,
+ [in] LPCWSTR wszAppDomainManagerTypeName,
+ [in] int nProperties,
+ [in] LPCWSTR* pPropertyNames,
+ [in] LPCWSTR* pPropertyValues,
+ [out] DWORD* pAppDomainID);
+
+ HRESULT CreateDelegate([in] DWORD appDomainID,
+ [in] LPCWSTR wszAssemblyName,
+ [in] LPCWSTR wszClassName,
+ [in] LPCWSTR wszMethodName,
+ [out] INT_PTR* fnPtr);
+
+ // Authenticates a host based upon a key value. No longer required.
+ HRESULT Authenticate([in] ULONGLONG authKey);
+
+ // Ensures CLR-set Mac (Mach) EH port is registered.
+ HRESULT RegisterMacEHPort();
+
+ HRESULT SetStartupFlags([in] STARTUP_FLAGS dwFlags);
+
+ HRESULT DllGetActivationFactory([in] DWORD appDomainID,
+ [in] LPCWSTR wszTypeName,
+ [out] IActivationFactory ** factory);
+
+ HRESULT ExecuteAssembly([in] DWORD dwAppDomainId,
+ [in] LPCWSTR pwzAssemblyPath,
+ [in] int argc,
+ [in] LPCWSTR* argv,
+ [out] DWORD *pReturnValue);
+
+};
+
+[
+ uuid(1000A3E7-B420-4620-AE30-FB19B587AD1D),
+ version(1.0),
+ helpstring("Pause and Resume Interface"),
+ pointer_default(unique),
+ local
+]
+interface ICLRExecutionManager : IUnknown
+{
+ // Pause all managed threads
+ // Parameters are ignored and reserved for future use.
+ HRESULT Pause([in] DWORD dwAppDomainId, [in] DWORD dwFlags);
+
+ // Resume managed threads
+ // Parameters are ignored and reserved for future use.
+ HRESULT Resume([in] DWORD dwAppDomainId);
+}
+
+#endif // FEATURE_CORECLR
+
+//*****************************************************************************
+// Interface to utilize HostProtection
+//*****************************************************************************
+typedef enum
+{
+ eNoChecks = 0,
+ //---------------------------------
+ eSynchronization = 0x1,
+ eSharedState = 0x2,
+ eExternalProcessMgmt = 0x4,
+ eSelfAffectingProcessMgmt = 0x8,
+ eExternalThreading = 0x10,
+ eSelfAffectingThreading = 0x20,
+ eSecurityInfrastructure = 0x40,
+ eUI = 0x80,
+ eMayLeakOnAbort = 0x100,
+ //----------------------------------
+ eAll = 0x1ff
+} EApiCategories;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ object,
+ uuid(89F25F5C-CEEF-43e1-9CFA-A68CE863AAAC),
+ helpstring("Host Protection Interface"),
+ pointer_default(unique)
+]
+interface ICLRHostProtectionManager : IUnknown
+{
+ // These allow the host to specify resources that could cause
+ // instability in order to guarantee protection from them.
+ HRESULT SetProtectedCategories([in] EApiCategories categories);
+
+ // Call once before starting the runtime to sacrifice a little
+ // assembly-loading-performance for a guarantee that a certain
+ // rare race condition that can result in a FatalEE error won't
+ // happen.
+ HRESULT SetEagerSerializeGrantSets();
+};
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+//
+// Interface for configuring the default AppDomain
+//
+
+typedef enum
+{
+ eInitializeNewDomainFlags_None = 0x0000,
+
+ // InitializeNewDomain will not make changes to the security state of the AppDomain
+ eInitializeNewDomainFlags_NoSecurityChanges = 0x0002
+}
+EInitializeNewDomainFlags;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+[
+ object,
+ uuid(270D00A2-8E15-4d0b-ADEB-37BC3E47DF77),
+ helpstring("Default AppDomain Configuration Interface"),
+ pointer_default(unique)
+]
+interface ICLRDomainManager : IUnknown
+{
+ HRESULT SetAppDomainManagerType([in] LPCWSTR wszAppDomainManagerAssembly,
+ [in] LPCWSTR wszAppDomainManagerType,
+ [in] EInitializeNewDomainFlags dwInitializeDomainFlags);
+
+ HRESULT SetPropertiesForDefaultAppDomain([in] DWORD nProperties,
+ [in] LPCWSTR *pwszPropertyNames,
+ [in] LPCWSTR *pwszPropertyValues);
+}
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+//*****************************************************************************
+// mscoree typelib definition
+//*****************************************************************************
+
+[
+ uuid(5477469e-83b1-11d2-8b49-00a0c9b7c9c4),
+ version(2.4),
+ helpstring("Common Language Runtime Execution Engine 2.4 Library")
+]
+library mscoree
+{
+ importlib("stdole32.tlb");
+
+#ifdef INCLUDE_SVC_IDL
+#define IN_MSCOREE
+#include "mscorsvc.idl"
+#endif
+
+ //*****************************************************************************
+ //
+ //*****************************************************************************
+ [
+ object,
+ oleautomation,
+ uuid(B81FF171-20F3-11d2-8DCC-00A0C9B00522),
+ helpstring("Type name parser"),
+ pointer_default(unique)
+ ]
+ interface ITypeName : IUnknown
+ {
+ HRESULT GetNameCount([out, retval] DWORD* pCount);
+ HRESULT GetNames([in] DWORD count, [out] BSTR* rgbszNames, [out, retval] DWORD* pCount);
+ HRESULT GetTypeArgumentCount([out, retval] DWORD* pCount);
+ HRESULT GetTypeArguments([in] DWORD count, [out] ITypeName** rgpArguments, [out, retval] DWORD* pCount);
+ HRESULT GetModifierLength([out, retval] DWORD* pCount);
+ HRESULT GetModifiers([in] DWORD count, [out] DWORD* rgModifiers, [out, retval] DWORD* pCount);
+ HRESULT GetAssemblyName([out, retval] BSTR* rgbszAssemblyNames);
+ };
+
+ //*****************************************************************************
+ //
+ //*****************************************************************************
+ [
+ object,
+ oleautomation,
+ uuid(B81FF171-20F3-11d2-8DCC-00A0C9B00523),
+ helpstring("Type name builder"),
+ pointer_default(unique)
+ ]
+ interface ITypeNameBuilder : IUnknown
+ {
+ HRESULT OpenGenericArguments();
+ HRESULT CloseGenericArguments();
+ HRESULT OpenGenericArgument();
+ HRESULT CloseGenericArgument();
+ HRESULT AddName([in] LPCWSTR szName);
+ HRESULT AddPointer();
+ HRESULT AddByRef();
+ HRESULT AddSzArray();
+ HRESULT AddArray([in] DWORD rank);
+ HRESULT AddAssemblySpec([in] LPCWSTR szAssemblySpec);
+ HRESULT ToString([out, retval] BSTR* pszStringRepresentation);
+ HRESULT Clear();
+ };
+
+ //*****************************************************************************
+ //
+ //*****************************************************************************
+ [
+ object,
+ oleautomation,
+ uuid(B81FF171-20F3-11d2-8DCC-00A0C9B00521),
+ helpstring("Type name builder and parser factory"),
+ pointer_default(unique)
+ ]
+ interface ITypeNameFactory : IUnknown
+ {
+ HRESULT ParseTypeName([in] LPCWSTR szName, [out] DWORD* pError, [out, retval] ITypeName** ppTypeName);
+ HRESULT GetTypeNameBuilder([out, retval] ITypeNameBuilder** ppTypeBuilder);
+ };
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+ //*****************************************************************************
+ // Interface for apartment callbacks.
+ //*****************************************************************************
+ [
+ object,
+ oleautomation,
+ uuid(178E5337-1528-4591-B1C9-1C6E484686D8),
+ helpstring("Apartment callback interface"),
+ pointer_default(unique)
+ ]
+ interface IApartmentCallback : IUnknown
+ {
+ HRESULT _stdcall DoCallback(
+ [in] SIZE_T pFunc,
+ [in] SIZE_T pData);
+ };
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+#ifdef _WIN64
+ #define CCW_PTR __int64 *
+ cpp_quote("#define CCW_PTR __int64 *")
+#else // WIN64
+ #define CCW_PTR int *
+ cpp_quote("#define CCW_PTR int *")
+#endif // WIN64
+
+#ifdef FEATURE_COMINTEROP
+ //*****************************************************************************
+ // Interface for controlling a managed object
+ //*****************************************************************************
+ [
+ object,
+ oleautomation,
+ uuid(C3FCC19E-A970-11d2-8B5A-00A0C9B7C9C4),
+ helpstring("Managed Object Interface"),
+ pointer_default(unique),
+ proxy
+ ]
+ interface IManagedObject : IUnknown
+ {
+ // helper to serialize the object and marshal it to the client
+ HRESULT GetSerializedBuffer( [out] BSTR *pBSTR);
+
+ // Object identity includes, process guid, appdomain id, ccw
+ HRESULT GetObjectIdentity([out] BSTR* pBSTRGUID, [out] int* AppDomainID, [out] CCW_PTR pCCW);
+ };
+#endif // FEATURE_COMINTEROP
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+ //*****************************************************************************
+ // Interface for controlling a managed object
+ //*****************************************************************************
+ [
+ object,
+ oleautomation,
+ uuid(04C6BE1E-1DB1-4058-AB7A-700CCCFBF254),
+ helpstring("ICatalogServices Interface"),
+ pointer_default(unique)
+ ]
+ interface ICatalogServices : IUnknown
+ {
+ HRESULT Autodone();
+
+ HRESULT NotAutodone();
+ };
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+#ifdef FEATURE_COMINTEROP
+ //*****************************************************************************
+ // IMarshal implementation for 1.0, 1.1, and 2.0 COM callable wrappers
+ //*****************************************************************************
+ [
+ uuid(3F281000-E95A-11d2-886B-00C04F869F04),
+ helpstring("Com Call Wrapper Unmarshalling Class")
+ ]
+ coclass ComCallUnmarshal
+ {
+ [default] interface IMarshal;
+ };
+
+ //*****************************************************************************
+ // IMarshal implementation for 4.0 COM callable wrappers
+ //*****************************************************************************
+ [
+ uuid(45FB4600-E6E8-4928-B25E-50476FF79425),
+ helpstring("Com Call Wrapper Unmarshalling Class 4.0")
+ ]
+ coclass ComCallUnmarshalV4
+ {
+ [default] interface IMarshal;
+ };
+#endif // FEATURE_COMINTEROP
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+ [
+ uuid(CB2F6723-AB3A-11d2-9C40-00C04FA30A3E),
+ helpstring("Cor Runtime Hosting Class")
+ ]
+ coclass CorRuntimeHost
+ {
+ [default] interface ICorRuntimeHost;
+ interface IGCHost;
+ interface ICorConfiguration;
+ interface IValidator;
+ interface IDebuggerInfo;
+ };
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+ [
+ uuid(90F1A06E-7712-4762-86B5-7A5EBA6BDB02),
+ helpstring("CLR Runtime Hosting Class V2")
+ ]
+ coclass CLRRuntimeHost
+ {
+ [default] interface ICLRRuntimeHost;
+ interface ICLRValidator;
+ };
+
+ [
+ uuid(B81FF171-20F3-11d2-8DCC-00A0C9B00525),
+ helpstring("TypeName parser and builder")
+ ]
+ coclass TypeNameFactory
+ {
+ [default] interface ITypeNameFactory;
+ };
+};
+
+typedef enum
+{
+ eCurrentContext=0x00,
+ eRestrictedContext=0x01
+} EContextType;
+
+#ifdef FEATURE_INCLUDE_ALL_INTERFACES
+///////////////////////////////////////////////////////////////////////////////
+//
+// IHostSecurityContext
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ object,
+ version(1.0),
+ uuid(7E573CE4-0343-4423-98D7-6318348A1D3C),
+ helpstring("Security Context provided by host"),
+ pointer_default(unique),
+ local
+]
+
+interface IHostSecurityContext : IUnknown
+{
+ HRESULT Capture([out] IHostSecurityContext** ppClonedContext);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// IHostSecurityManager
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ object,
+ version(1.0),
+ uuid(75ad2468-a349-4d02-a764-76a68aee0c4f),
+ helpstring("Security Manager provided by host"),
+ pointer_default(unique),
+ local
+]
+interface IHostSecurityManager: IUnknown
+{
+ // Impersonation APIs.
+ HRESULT ImpersonateLoggedOnUser(
+ [in] HANDLE hToken);
+
+ HRESULT RevertToSelf();
+
+ HRESULT OpenThreadToken(
+ [in] DWORD dwDesiredAccess,
+ [in] BOOL bOpenAsSelf,
+ [out] HANDLE *phThreadToken
+ );
+
+ HRESULT SetThreadToken(
+ [in] HANDLE hToken);
+
+ HRESULT GetSecurityContext([in] EContextType eContextType,
+ [out] IHostSecurityContext** ppSecurityContext);
+ // May return S_OK, E_FAIL (in what circumstances?)
+ HRESULT SetSecurityContext([in] EContextType eContextType,
+ [in] IHostSecurityContext* pSecurityContext);
+
+};
+#endif // FEATURE_INCLUDE_ALL_INTERFACES
+
+#ifdef FEATURE_APPDOMAIN_RESOURCE_MONITORING
+///////////////////////////////////////////////////////////////////////////////
+//
+// ICLRAppDomainResourceMonitor
+//
+///////////////////////////////////////////////////////////////////////////////
+[
+ version(1.0),
+ uuid(c62de18c-2e23-4aea-8423-b40c1fc59eae),
+ helpstring("ARM interface"),
+ pointer_default(unique),
+ local
+]
+interface ICLRAppDomainResourceMonitor: IUnknown
+{
+ HRESULT GetCurrentAllocated([in] DWORD dwAppDomainId,
+ [out] ULONGLONG* pBytesAllocated);
+
+ HRESULT GetCurrentSurvived([in] DWORD dwAppDomainId,
+ [out] ULONGLONG* pAppDomainBytesSurvived,
+ [out] ULONGLONG* pTotalBytesSurvived);
+
+ HRESULT GetCurrentCpuTime([in] DWORD dwAppDomainId,
+ [out] ULONGLONG* pMilliseconds);
+
+
+};
+#endif //FEATURE_APPDOMAIN_RESOURCE_MONITORING
+
+cpp_quote("#undef DEPRECATED_CLR_STDAPI")
+cpp_quote("#undef DECLARE_DEPRECATED")
+cpp_quote("#undef DEPRECATED_CLR_API_MESG")
diff --git a/src/inc/OpCodeGen.pl b/src/inc/OpCodeGen.pl
new file mode 100644
index 0000000..d929451
--- /dev/null
+++ b/src/inc/OpCodeGen.pl
@@ -0,0 +1,501 @@
+# Licensed to the .NET Foundation under one or more agreements.
+# The .NET Foundation licenses this file to you under the MIT license.
+# See the LICENSE file in the project root for more information.
+#
+# GENREFOPS.PL
+#
+# PERL script used to generate the numbering of the reference opcodes
+#
+#use strict 'vars';
+#use strict 'subs';
+#use strict 'refs';
+
+
+my $ret = 0;
+my %oneByte;
+my %twoByte;
+my %controlFlow;
+my @singleByteArg;
+my %stackbehav;
+my %opcodetype;
+my %operandtype;
+my %opcodes;
+my $popstate;
+my $pushstate;
+
+$ctrlflowcount = 0;
+
+$count = 0;
+
+my @lowercaseAlphabet = ('a'..'z','0'..'9');
+my %upcaseAlphabet = ();
+
+foreach $letter (@lowercaseAlphabet) {
+ $j = $letter;
+ $j=~tr/a-z/A-Z/;
+ $upcaseAlphabet{$letter}=$j;
+}
+
+open (OPCODE, "opcode.def") or die "Couldn't open opcode.def: $!\n";
+open (OUTPUT, ">OpCodes.cs") or die "Couldn't open OpCodes.cs: $!\n";
+open (FCOUTPUT, ">FlowControl.cs") or die "Couldn't open FlowControl.cs: $!\n";
+open (SOUTPUT, ">StackBehaviour.cs") or die "Couldn't open StackBehaviour.cs: $!\n";
+open (OCOUTPUT, ">OpCodeType.cs") or die "Couldn't open OpCodeType.cs: $!\n";
+open (OPOUTPUT, ">OperandType.cs") or die "Couldn't open OprandType.cs: $!\n";
+
+
+print OUTPUT "/*============================================================\n";
+print OUTPUT "**\n";
+print OUTPUT "**Class: OpCodes\n";
+print OUTPUT "**\n";
+print OUTPUT "**Purpose: Exposes all of the il instructions supported by the runtime.\n";
+print OUTPUT "**\n";
+print OUTPUT "**Licensed to the .NET Foundation under one or more agreements.\n";
+print OUTPUT "**The .NET Foundation licenses this file to you under the MIT license.\n";
+print OUTPUT "**See the LICENSE file in the project root for more information.\n";
+print OUTPUT "**\n";
+print OUTPUT "** THIS FILE IS AUTOMATICALLY GENERATED. DO NOT EDIT BY HAND!\n";
+print OUTPUT "** See clr\src\inc\opcodegen.pl for more information.**\n";
+print OUTPUT "============================================================*/\n";
+
+print OUTPUT "namespace System.Reflection.Emit {\n\n";
+print OUTPUT "using System;\n\n";;
+print OUTPUT "public class OpCodes {\n\n";;
+print OUTPUT "/// <summary>\n";
+print OUTPUT "/// <para>\n";
+print OUTPUT "/// The IL instruction opcodes supported by the\n";
+print OUTPUT "/// runtime. The IL Instruction Specification describes each\n";
+print OUTPUT "/// Opcode.\n";
+print OUTPUT "/// </para>\n";
+print OUTPUT "/// </summary>\n";
+print OUTPUT "/// <seealso topic='IL Instruction Set Specification'/>\n";
+print OUTPUT "\n";
+print OUTPUT "\tprivate OpCodes() { \n\t}\n\n";
+
+
+print FCOUTPUT "/*============================================================\n";
+print FCOUTPUT "**\n";
+print FCOUTPUT "**Class: FlowControl\n";
+print FCOUTPUT "**\n";
+print FCOUTPUT "**Purpose: Exposes FlowControl Attribute of IL .\n";
+print FCOUTPUT "**\n";
+print FCOUTPUT "**Licensed to the .NET Foundation under one or more agreements.\n";
+print FCOUTPUT "**The .NET Foundation licenses this file to you under the MIT license.\n";
+print FCOUTPUT "**See the LICENSE file in the project root for more information.\n";
+print FCOUTPUT "**\n";
+print FCOUTPUT "** THIS FILE IS AUTOMATICALLY GENERATED. DO NOT EDIT BY HAND!\n";
+print FCOUTPUT "** See clr\src\inc\opcodegen.pl for more information.**\n";
+print FCOUTPUT "============================================================*/\n";
+
+print FCOUTPUT "namespace System.Reflection.Emit {\n\n";
+print FCOUTPUT "using System;\n\n";
+print FCOUTPUT "public enum FlowControl\n{\n\n";
+
+print SOUTPUT "/*============================================================\n";
+print SOUTPUT "**\n";
+print SOUTPUT "**Class: StackBehaviour\n";
+print SOUTPUT "**\n";
+print SOUTPUT "**Purpose: Exposes StackBehaviour Attribute of IL .\n";
+print SOUTPUT "**\n";
+print SOUTPUT "**Licensed to the .NET Foundation under one or more agreements.\n";
+print SOUTPUT "**The .NET Foundation licenses this file to you under the MIT license.\n";
+print SOUTPUT "**See the LICENSE file in the project root for more information.\n";
+print SOUTPUT "**\n";
+print SOUTPUT "** THIS FILE IS AUTOMATICALLY GENERATED. DO NOT EDIT BY HAND!\n";
+print SOUTPUT "** See clr\src\inc\opcodegen.pl for more information.**\n";
+print SOUTPUT "============================================================*/\n";
+
+print SOUTPUT "namespace System.Reflection.Emit {\n\n";
+print SOUTPUT "using System;\n\n";
+print SOUTPUT "public enum StackBehaviour\n{\n\n";
+
+print OCOUTPUT "/*============================================================\n";
+print OCOUTPUT "**\n";
+print OCOUTPUT "**Class: OpCodeType\n";
+print OCOUTPUT "**\n";
+print OCOUTPUT "**Purpose: Exposes OpCodeType Attribute of IL .\n";
+print OCOUTPUT "**\n";
+print OCOUTPUT "**Licensed to the .NET Foundation under one or more agreements.\n";
+print OCOUTPUT "**The .NET Foundation licenses this file to you under the MIT license.\n";
+print OCOUTPUT "**See the LICENSE file in the project root for more information.\n";
+print OCOUTPUT "**\n";
+print OCOUTPUT "** THIS FILE IS AUTOMATICALLY GENERATED. DO NOT EDIT BY HAND!\n";
+print OCOUTPUT "** See clr\src\inc\opcodegen.pl for more information.**\n";
+print OCOUTPUT "============================================================*/\n";
+
+print OCOUTPUT "namespace System.Reflection.Emit {\n\n";
+print OCOUTPUT "using System;\n\n";
+print OCOUTPUT "public enum OpCodeType\n{\n\n";
+
+print OPOUTPUT "/*============================================================\n";
+print OPOUTPUT "**\n";
+print OPOUTPUT "**Class: OperandType\n";
+print OPOUTPUT "**\n";
+print OPOUTPUT "**Purpose: Exposes OperandType Attribute of IL .\n";
+print OPOUTPUT "**\n";
+print OPOUTPUT "**Licensed to the .NET Foundation under one or more agreements.\n";
+print OPOUTPUT "**The .NET Foundation licenses this file to you under the MIT license.\n";
+print OPOUTPUT "**See the LICENSE file in the project root for more information.\n";
+print OPOUTPUT "**\n";
+print OPOUTPUT "** THIS FILE IS AUTOMATICALLY GENERATED. DO NOT EDIT BY HAND!\n";
+print OPOUTPUT "** See clr\src\inc\opcodegen.pl for more information.**\n";
+print OPOUTPUT "============================================================*/\n";
+
+print OPOUTPUT "namespace System.Reflection.Emit {\n\n";
+print OPOUTPUT "using System;\n\n";
+print OPOUTPUT "public enum OperandType\n{\n\n";
+
+while (<OPCODE>)
+{
+ # Process only OPDEF(....) lines
+ if (/OPDEF\(\s*/)
+ {
+ chop; # Strip off trailing CR
+ s/^OPDEF\(\s*//; # Strip off "OP("
+ s/\)$//; # Strip off ")" at end
+ s/,\s*/,/g; # Remove whitespace
+
+ # Split the line up into its basic parts
+ ($enumname, $stringname, $pop, $push, $operand, $type, $size, $s1, $s2, $ctrl) = split(/,/);
+ $s1 =~ s/0x//;
+ $s1 = hex($s1);
+ $s2 =~ s/0x//;
+ $s2 = hex($s2);
+
+ if ($size == 0)
+ {
+ next;
+ }
+
+ next if ($enumname =~ /UNUSED/);
+
+ #Remove the prefix
+ $enumname=~s/CEE_//g;
+
+ #Convert name to our casing convention
+ $enumname=~tr/A-Z/a-z/;
+ $enumname=~s/^(.)/\u$1/g;
+ $enumname=~s/_(.)/_\u$1/g;
+
+
+ #Convert pop to our casing convention
+ $pop=~tr/A-Z/a-z/;
+ $pop=~s/^(.)/\u$1/g;
+ $pop=~s/_(.)/_\u$1/g;
+
+
+ #Convert push to our casing convention
+ $push=~tr/A-Z/a-z/;
+ $push=~s/^(.)/\u$1/g;
+ $push=~s/_(.)/_\u$1/g;
+
+
+ #Convert operand to our casing convention
+ #$operand=~tr/A-Z/a-z/;
+ #$operand=~s/^(.)/\u$1/g;
+ #$operand=~s/_(.)/_\u$1/g;
+
+ #Remove the I prefix on type
+ $type=~s/I//g;
+
+ #Convert Type to our casing convention
+ $type=~tr/A-Z/a-z/;
+ $type=~s/^(.)/\u$1/g;
+ $type=~s/_(.)/_\u$1/g;
+
+
+ #Convert ctrl to our casing convention
+ $ctrl=~tr/A-Z/a-z/;
+ $ctrl=~s/^(.)/\u$1/g;
+ $ctrl=~s/_(.)/_\u$1/g;
+
+
+
+
+ # Make a list of the flow Control type
+
+ # Make a list of the opcodes and there values
+ if ($opcodes{$enumname})
+ {
+
+ }
+ else
+ {
+ if ($size == 1)
+ {
+ $opcodes{$enumname} = $s2;
+ }
+ else
+ {
+ $opcodes{$enumname} = ($s2 + 256 * $s1);
+ }
+ }
+
+ #Make a list of the instructions which only take one-byte arguments
+ if ($enumname =~ /^.*_S$/) {
+ #but exclude the deprecated expressions (sometimes spelled "depricated")
+ if (!($enumname=~/^Depr.cated.*/)) {
+ my $caseStatement = sprintf("\t\tcase %-20s: \n", $enumname);
+ push(@singleByteArg, $caseStatement);
+ }
+ }
+
+ #make a list of the control Flow Types
+ if ($controlFlow{$ctrl})
+ {
+ #printf("DUPE Control Flow\n");
+ }
+ else
+ {
+ $controlFlow{$ctrl} = $ctrlflowcount;
+ $ctrlflowcount++;
+ }
+
+ $ctrlflowcount = 0;
+ #make a list of the control Flow Types
+ $pop=~s/\+/_/g;
+ if ($stackbehav{$pop})
+ {
+ #printf("DUPE Control Flow\n");
+ }
+ else
+ {
+ $stackbehav{$pop} = $ctrlflowcount;
+ $ctrlflowcount++;
+ }
+
+ #make a list of the control Flow Types
+ $push=~s/\+/_/g;
+ if ($stackbehav{$push})
+ {
+ #printf("DUPE Control Flow\n");
+ }
+ else
+ {
+ $stackbehav{$push} = $ctrlflowcount;
+ $ctrlflowcount++;
+ }
+ #make a list of operand types
+ if ($operandtype{$operand})
+ {
+ #printf("DUPE Control Flow\n");
+ }
+ else
+ {
+ $operandtype{$operand} = $ctrlflowcount;
+ $ctrlflowcount++;
+ }
+
+
+ #make a list of opcode types
+ if ($opcodetype{$type})
+ {
+ #printf("DUPE Control Flow\n");
+ }
+ else
+ {
+ $opcodetype{$type} = $ctrlflowcount;
+ $ctrlflowcount++;
+ }
+
+ print "$enumname\n";
+ print "$stringname\n";
+ if ($stringname eq "arglist")
+ {
+ print "This is arglist----------\n";
+ }
+ my $line = sprintf("\tpublic static readonly OpCode %-20s = ", $enumname);
+ if ($size == 1)
+ {
+ $line .= sprintf("new OpCode(%s, StackBehaviour.%s, StackBehaviour.%s, OperandType.%s, OpCodeType.%s, %u, (byte)0x%x, (byte)0x%x, FlowControl.%s, " , $stringname, $pop, $push, $operand, $type, $size, $s1, $s2, $ctrl);
+
+
+ if ($ctrl eq "Return" || $ctrl eq "Branch" || $ctrl eq "Throw" || $stringname eq "\"jmp\"" || $stringname eq "\"jmpi\"")
+ {
+ $line .= sprintf("true, ");
+
+ }
+ else
+ {
+ $line .= sprintf("false, ");
+ }
+
+ $popstate = 0;
+ if($pop eq "Pop0" || $pop eq "Varpop")
+ {
+ $popstate = 0;
+ }
+ elsif ($pop eq "Pop1" || $pop eq "Popi" || $pop eq "Popref")
+ {
+ $popstate = $popstate -1;
+ }
+ elsif ($pop eq "Pop1_pop1" || $pop eq "Popi_pop1" || $pop eq "Popi_popi" || $pop eq "Popi_popi8" || $pop eq "Popi_popr4" || $pop eq "Popi_popr8" || $pop eq "Popref_pop1" || $pop eq "Popref_popi")
+ {
+ $popstate = $popstate -2;
+ }
+ elsif ($pop eq "Popi_popi_popi" || $pop eq "Popref_popi_popi" || $pop eq "Popref_popi_popi8" || $pop eq "Popref_popi_popr4" || $pop eq "Popref_popi_popr8" || $pop eq "Popref_popi_popref")
+ {
+ $popstate = $popstate -3;
+ }
+
+ if ($push eq "Push1" || $push eq "Pushi" ||$push eq "Pushi8" ||$push eq "Pushr4" ||$push eq "Pushr8" ||$push eq "Pushref")
+ {
+ $popstate = $popstate + 1;
+ }
+ elsif($push eq "Push1_push1")
+ {
+ $popstate = $popstate + 2;
+ }
+
+
+ $line .= sprintf(" $popstate");
+ $line .= sprintf(");\n\n");
+ if ($oneByte{$s2})
+ {
+ printf("Error opcode 0x%x already defined!\n", $s2);
+ print " Old = $oneByte{$s2}";
+ print " New = $line";
+ $ret = -1;
+ }
+ $oneByte{$s2} = $line;
+ }
+ elsif ($size == 2)
+ {
+ if ($twoByte{$s2})
+ {
+ printf("Error opcode 0x%x%x already defined!\n", $s1, $s2);
+ print " Old = $oneByte{$s2}";
+ print " New = $line";
+ $ret = -1;
+ }
+ $line .= sprintf("new OpCode(%s, StackBehaviour.%s, StackBehaviour.%s, OperandType.%s, OpCodeType.%s, %u, (byte)0x%x, (byte)0x%x, FlowControl.%s, " , $stringname, $pop, $push, $operand, $type, $size, $s1, $s2, $ctrl);
+
+ if ($ctrl eq "Return" || $ctrl eq "Branch" || $ctrl eq "Throw" || $stringname eq "\"jmp\"" || $stringname eq "\"jmpi\"")
+ {
+ $line .= sprintf("true, ");
+
+ }
+ else
+ {
+ $line .= sprintf("false, ");
+ }
+
+ $popstate = 0;
+ if($pop eq "Pop0" || $pop eq "Varpop")
+ {
+ $popstate = 0;
+ }
+ elsif($pop eq "Pop1" || $pop eq "Popi" || $pop eq "Popref")
+ {
+ $popstate = $popstate -1;
+ }
+ elsif ($pop eq "Pop1_pop1" || $pop eq "Popi_pop1" || $pop eq "Popi_popi" || $pop eq "Popi_popi8" || $pop eq "Popi_popr4" || $pop eq "Popi_popr8" || $pop eq "Popref_pop1" || $pop eq "Popref_popi")
+ {
+ $popstate = $popstate -2;
+ }
+ elsif ($pop eq "Popi_popi_popi" || $pop eq "Popref_popi_popi" || $pop eq "Popref_popi_popi8" || $pop eq "Popref_popi_popr4" || $pop eq "Popref_popi_popr8" || $pop eq "Popref_popi_popref")
+ {
+ $popstate = $popstate -3;
+ }
+
+ if ($push eq "Push1" || $push eq "Pushi" ||$push eq "Pushi8" ||$push eq "Pushr4" ||$push eq "Pushr8" ||$push eq "Pushref")
+ {
+ $popstate = $popstate + 1;
+ }
+ elsif($push eq "Push1_push1")
+ {
+ $popstate = $popstate + 2;
+ }
+
+ $line .= sprintf(" $popstate");
+ $line .= sprintf(");\n\n");
+
+ $twoByte{$s2 + 256 * $s1} = $line;
+
+ }
+ else
+ {
+ $line .= "\n";
+ push(@deprecated, $line);
+ }
+ $count++;
+ }
+}
+
+#Write out the Flow Control class
+$ctrlflowcount = 0;
+foreach $key (sort {$a cmp $b} keys (%controlFlow))
+{
+ print FCOUTPUT "\t$key";
+ print FCOUTPUT "\t= $ctrlflowcount,\n";
+ $ctrlflowcount++;
+}
+
+#end the flowcontrol class
+print FCOUTPUT "}\n}";
+
+#Write out the StackBehaviour class
+$ctrlflowcount = 0;
+foreach $key (sort {$a cmp $b} keys (%stackbehav))
+{
+ print SOUTPUT "\t$key";
+ print SOUTPUT "\t= $ctrlflowcount,\n";
+ $ctrlflowcount++;
+}
+#end the StackBehaviour class
+print SOUTPUT "}\n}";
+
+$ctrlflowcount = 0;
+foreach $key (sort {$a cmp $b} keys (%opcodetype))
+{
+ print OCOUTPUT "\t$key";
+ print OCOUTPUT "\t= $ctrlflowcount,\n";
+ $ctrlflowcount++;
+}
+#end the OpCodeTYpe class
+print OCOUTPUT "}\n}";
+
+$ctrlflowcount = 0;
+foreach $key (sort {$a cmp $b} keys (%operandtype))
+{
+ print OPOUTPUT "\t$key";
+ print OPOUTPUT "\t= $ctrlflowcount,\n";
+ $ctrlflowcount++;
+}
+#end the OperandType class
+print OPOUTPUT "}\n}";
+
+
+my $opcode;
+my $lastOp = -1;
+foreach $opcode (sort {$a <=> $b} keys(%oneByte)) {
+ printf("***** GAP %d instrs ****\n", $opcode - $lastOp) if ($lastOp + 1 != $opcode && $lastOp > 0);
+ print OUTPUT $oneByte{$opcode};
+ $lastOp = $opcode;
+}
+
+$lastOp = -1;
+foreach $opcode (sort {$a <=> $b} keys(%twoByte)) {
+ printf("***** GAP %d instrs ****\n", $opcode - $lastOp) if ($lastOp + 1 != $opcode && $lastOp > 0);
+ print OUTPUT $twoByte{$opcode};
+ $lastOp = $opcode;
+}
+
+
+
+
+
+print OUTPUT "\n\n\tpublic static bool TakesSingleByteArgument(OpCode inst)\n\t{\n";
+print OUTPUT"\t\tswitch(inst.m_operand)\n\t\t{\n";
+print OUTPUT "\t\t\tcase OperandType.ShortInlineBrTarget :\n";
+print OUTPUT "\t\t\tcase OperandType.ShortInlineI :\n";
+print OUTPUT "\t\t\tcase OperandType.ShortInlineVar :\n";
+print OUTPUT "\t\t\treturn true;\n";
+print OUTPUT "\t\t};\n";
+print OUTPUT "\t\treturn false;\n";
+print OUTPUT "\t}\n";
+print OUTPUT "}\n}";
+exit($ret);
+
+
+
diff --git a/src/inc/UacAsInvoker.manifest b/src/inc/UacAsInvoker.manifest
new file mode 100644
index 0000000..80a5e05
--- /dev/null
+++ b/src/inc/UacAsInvoker.manifest
@@ -0,0 +1,11 @@
+<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
+ <ms_asmv3:trustInfo xmlns:ms_asmv3="urn:schemas-microsoft-com:asm.v3">
+ <ms_asmv3:security>
+ <ms_asmv3:requestedPrivileges>
+ <ms_asmv3:requestedExecutionLevel
+ level="asInvoker"
+ uiAccess="false"/>
+ </ms_asmv3:requestedPrivileges>
+ </ms_asmv3:security>
+ </ms_asmv3:trustInfo>
+</assembly>
diff --git a/src/inc/allocacheck.h b/src/inc/allocacheck.h
new file mode 100644
index 0000000..3ba2e4d
--- /dev/null
+++ b/src/inc/allocacheck.h
@@ -0,0 +1,84 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+/*********************************************************************/
+/* AllocaCheck */
+/*********************************************************************/
+
+/* check for alloca overruns (which otherwise are hard to track down
+ and often only repro on optimized builds).
+
+ USAGE:
+
+ void foo() {
+ ALLOCA_CHECK(); // Declare at function level scope
+
+ ....
+ void* mem = ALLOCA(size); // does an alloca,
+
+ } // destructor of ALLOCA_CHECK for buffer overruns.
+*/
+
+/* */
+/*********************************************************************/
+
+#ifndef AllocaCheck_h
+#define AllocaCheck_h
+#include <malloc.h> // for alloca itself
+
+#if defined(assert) && !defined(_ASSERTE)
+#define _ASSERTE assert
+#endif
+
+#if defined(_DEBUG) || defined(DEBUG)
+
+/*********************************************************************/
+class AllocaCheck {
+public:
+ enum { CheckBytes = 0xCCCDCECF,
+ };
+
+ struct AllocaSentinal {
+ int check;
+ AllocaSentinal* next;
+ };
+
+public:
+ /***************************************************/
+ AllocaCheck() {
+ sentinals = 0;
+ }
+
+ ~AllocaCheck() {
+ AllocaSentinal* ptr = sentinals;
+ while (ptr != 0) {
+ if (ptr->check != (int)CheckBytes)
+ _ASSERTE(!"alloca buffer overrun");
+ ptr = ptr->next;
+ }
+ }
+
+ void* add(void* allocaBuff, unsigned size) {
+ AllocaSentinal* newSentinal = (AllocaSentinal*) ((char*) allocaBuff + size);
+ newSentinal->check = CheckBytes;
+ newSentinal->next = sentinals;
+ sentinals = newSentinal;
+ memset(allocaBuff, 0xDD, size);
+ return allocaBuff;
+ }
+
+private:
+ AllocaSentinal* sentinals;
+};
+
+#define ALLOCA_CHECK() AllocaCheck __allocaChecker
+#define ALLOCA(size) __allocaChecker.add(_alloca(size+sizeof(AllocaCheck::AllocaSentinal)), size);
+
+#else
+
+#define ALLOCA_CHECK()
+#define ALLOCA(size) _alloca(size)
+
+#endif
+
+#endif
diff --git a/src/inc/apithreadstress.cpp b/src/inc/apithreadstress.cpp
new file mode 100644
index 0000000..0a802a2
--- /dev/null
+++ b/src/inc/apithreadstress.cpp
@@ -0,0 +1,171 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+// ---------------------------------------------------------------------------
+// APIThreadStress.cpp (API thread stresser)
+// ---------------------------------------------------------------------------
+
+#include "stdafx.h"
+
+#ifdef _DEBUG
+#define LOGGING 1
+#endif
+
+#include "apithreadstress.h"
+#include "clrhost.h"
+#include "ex.h"
+#include "log.h"
+
+
+
+// For now, thread stress is incompatible with hosting. We need a host CreateThread
+// to fix this.
+#undef SetEvent
+#undef ResetEvent
+
+int APIThreadStress::s_threadStressCount = 0;
+
+APIThreadStress::APIThreadStress()
+{
+ m_threadCount = 0;
+
+ // Don't "fork" stress threads
+ if (ClrFlsGetValue(TlsIdx_StressThread) == NULL)
+ m_threadCount = s_threadStressCount;
+
+ if (m_threadCount != 0)
+ {
+ m_setupOK = TRUE;
+
+ m_hThreadArray = new (nothrow) HANDLE [ m_threadCount ];
+ if (m_hThreadArray == NULL)
+ m_setupOK = FALSE;
+ else
+ {
+ HANDLE *p = m_hThreadArray;
+ HANDLE *pEnd = p + m_threadCount;
+
+ while (p < pEnd)
+ {
+ DWORD id;
+ *p = ::CreateThread(NULL, 0, StartThread, this, 0, &id);
+ if (*p == NULL)
+ m_setupOK = FALSE;
+ p++;
+ }
+ }
+
+ m_syncEvent = ClrCreateManualEvent(FALSE);
+ if (m_syncEvent == INVALID_HANDLE_VALUE)
+ m_setupOK = FALSE;
+ }
+}
+
+APIThreadStress::~APIThreadStress()
+{
+ if (m_threadCount > 0)
+ {
+ HANDLE *p = m_hThreadArray;
+ HANDLE *pEnd = p + m_threadCount;
+
+ if (p != NULL)
+ {
+ while (p < pEnd)
+ {
+ if (*p != NULL)
+ {
+ if (m_threadCount > 0 && m_setupOK)
+ WaitForSingleObjectEx(*p, INFINITE, FALSE);
+
+ ::CloseHandle(*p);
+ }
+ p++;
+ }
+ delete [] m_hThreadArray;
+ }
+
+ if (m_syncEvent != INVALID_HANDLE_VALUE)
+ CloseHandle(m_syncEvent);
+ }
+}
+
+void APIThreadStress::SetThreadStressCount(int threadCount)
+{
+ s_threadStressCount = threadCount;
+}
+
+
+DWORD WINAPI APIThreadStress::StartThread(void *arg)
+{
+ APIThreadStress *pThis = (APIThreadStress *) arg;
+
+ ClrFlsSetValue(TlsIdx_StressThread, pThis);
+
+ EX_TRY
+ {
+ // Perform initial synchronization
+ WaitForSingleObjectEx(pThis->m_syncEvent, INFINITE, FALSE);
+ InterlockedIncrement(&pThis->m_runCount);
+
+ LOG((LF_SYNC, LL_INFO100, "Stressing operation on thread %d\n", GetCurrentThreadId()));
+ ((APIThreadStress *)arg)->Invoke();
+ LOG((LF_SYNC, LL_INFO100, "End stress operation on thread %d\n", GetCurrentThreadId()));
+
+ if (InterlockedDecrement(&pThis->m_runCount) == 0)
+ ::SetEvent(pThis->m_syncEvent);
+ }
+ EX_CATCH
+ {
+ LOG((LF_SYNC, LL_ERROR, "Exception during stress operation on thread %d\n", GetCurrentThreadId()));
+ }
+ EX_END_CATCH(SwallowAllExceptions);
+
+ return 0;
+}
+
+BOOL APIThreadStress::DoThreadStress()
+{
+ if (m_threadCount > 0 && m_setupOK)
+ {
+ HANDLE *p = m_hThreadArray;
+ HANDLE *pEnd = p + m_threadCount;
+
+ while (p < pEnd)
+ {
+ ::ResumeThread(*p);
+ p++;
+ }
+
+ // Start the threads at the same time
+ ::SetEvent(m_syncEvent);
+
+ return TRUE;
+ }
+ else
+ {
+ SyncThreadStress();
+ return FALSE;
+ }
+}
+
+void APIThreadStress::SyncThreadStress()
+{
+ APIThreadStress *pThis = (APIThreadStress *) ClrFlsGetValue(TlsIdx_StressThread);
+
+ if (pThis != NULL)
+ {
+ LOG((LF_SYNC, LL_INFO1000, "Syncing stress operation on thread %d\n", GetCurrentThreadId()));
+
+ ::ResetEvent(pThis->m_syncEvent);
+
+ if (InterlockedDecrement(&pThis->m_runCount) == 0)
+ ::SetEvent(pThis->m_syncEvent);
+ else
+ WaitForSingleObjectEx(pThis->m_syncEvent, INFINITE, FALSE);
+ InterlockedIncrement(&pThis->m_runCount);
+
+ LOG((LF_SYNC, LL_INFO1000, "Resuming stress operation on thread %d\n", GetCurrentThreadId()));
+ }
+}
+
diff --git a/src/inc/apithreadstress.h b/src/inc/apithreadstress.h
new file mode 100644
index 0000000..fc18dcc
--- /dev/null
+++ b/src/inc/apithreadstress.h
@@ -0,0 +1,90 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+// ---------------------------------------------------------------------------
+// APIThreadStress.h (API thread stresser)
+// ---------------------------------------------------------------------------
+
+// ---------------------------------------------------------------------------
+// This class provides a simple base to wrap "thread stress" logic around an API,
+// which will (in thread stress mode) cause an API to "fork" onto many threads
+// executing the same operation simulatenously. This can help to expose race
+// conditions.
+//
+// Usage:
+//
+// First, subtype APIThreadStress and override Invoke to implement the operation.
+// You will likely need to add data members for the arguments.
+//
+// Next, inside the API, write code like this:
+//
+// void MyRoutine(int a1, void *a2)
+// {
+// class stress : APIThreadStress
+// {
+// int a1;
+// void *a2;
+// stress(int a1, void *a2) : a1(a1), a2(a2)
+// { DoThreadStress(); }
+// void Invoke() { MyRoutine(a1, a2); }
+// } ts (a1, a2);
+//
+// // implementation
+//
+// // perhaps we have a common sub-point in the routine where we want the threads to
+// // queue up and race again
+//
+// ts.SyncThreadStress();
+//
+// // more implementation
+// }
+// ---------------------------------------------------------------------------
+
+
+#ifndef _APITHREADSTRESS_H_
+#define _APITHREADSTRESS_H_
+
+#include "utilcode.h"
+
+#ifdef STRESS_THREAD
+
+class APIThreadStress
+{
+ public:
+ APIThreadStress();
+ ~APIThreadStress();
+
+ BOOL DoThreadStress();
+ static void SyncThreadStress();
+
+ static void SetThreadStressCount(int count);
+
+ protected:
+ virtual void Invoke() {LIMITED_METHOD_CONTRACT;};
+
+ private:
+ static DWORD WINAPI StartThread(void *arg);
+
+ static int s_threadStressCount;
+
+ int m_threadCount;
+ HANDLE *m_hThreadArray;
+ BOOL m_setupOK;
+ LONG m_runCount;
+ HANDLE m_syncEvent;
+
+};
+
+#else // STRESS_THREAD
+
+class APIThreadStress
+{
+ public:
+ BOOL DoThreadStress() { return FALSE; }
+ static void SyncThreadStress() { }
+ static void SetThreadStressCount(int count) { }
+};
+
+#endif // STRESS_THREAD
+
+#endif // _APITHREADSTRESS_H_
diff --git a/src/inc/appxutil.h b/src/inc/appxutil.h
new file mode 100644
index 0000000..2892ab7
--- /dev/null
+++ b/src/inc/appxutil.h
@@ -0,0 +1,145 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+
+#pragma once
+
+#ifdef FEATURE_APPX
+
+#include "clrtypes.h"
+#include "appmodel.h"
+#include "fusionsetup.h"
+
+#define PACKAGE_FILTER_CLR_DEFAULT (PACKAGE_FILTER_HEAD|PACKAGE_FILTER_DIRECT)
+
+
+typedef PACKAGE_INFO * PPACKAGE_INFO;
+typedef PACKAGE_INFO const * PCPACKAGE_INFO;
+
+//---------------------------------------------------------------------------------------------
+// Forward declarations
+template <typename T>
+class NewArrayHolder;
+BOOL WinRTSupported();
+
+#ifdef FEATURE_CORECLR
+
+namespace AppX
+{
+ // Returns true if process is immersive (or if running in mockup environment).
+ bool IsAppXProcess();
+
+ // On CoreCLR, the host is in charge of determining whether the process is AppX or not.
+ void SetIsAppXProcess(bool);
+
+ inline bool IsAppXNGen()
+ {
+ WRAPPER_NO_CONTRACT;
+ return false;
+ }
+
+#ifdef DACCESS_COMPILE
+ bool DacIsAppXProcess();
+#endif // DACCESS_COMPILE
+};
+
+#else // FEATURE_CORECLR
+
+struct AppXRTInfo;
+typedef DPTR(AppXRTInfo) PTR_AppXRTInfo;
+
+//---------------------------------------------------------------------------------------------
+namespace AppX
+{
+ // cleans up resources allocated in InitAppXRT()
+ void ShutDown();
+
+ // Returns true if process is immersive (or if running in mockup environment).
+ // NOTE: a return value of true doesn't necessarily indicate that the process is a
+ // real Metro app, e.g. it could be an ngen process compiling an AppX assembly.
+ bool IsAppXProcess();
+
+#ifdef DACCESS_COMPILE
+ bool DacIsAppXProcess();
+#endif // DACCESS_COMPILE
+
+ // Returns true if process is immersive (or if running in mockup environment).
+ // Use only in NOFAULT regions when you are 100% sure that code:IsAppXProcess has been already called.
+ // This function does not initialize (no faults).
+ bool IsAppXProcess_Initialized_NoFault();
+
+ // Returns true if process is NGen worker compiling an AppX assembly.
+ bool IsAppXNGen();
+
+ // Returns true if the host OS supports immersive apps.
+ inline bool IsAppXSupported()
+ { return WinRTSupported() != FALSE; }
+
+ LPCWSTR GetHeadPackageMoniker();
+
+ HRESULT GetCurrentPackageId(
+ __inout PUINT32 pBufferLength,
+ __out PBYTE pBuffer);
+
+ HRESULT GetCurrentPackageInfo(
+ __in UINT32 dwFlags,
+ __inout PUINT32 pcbBuffer,
+ __out PBYTE pbBuffer,
+ __out PUINT32 nCount);
+
+ bool IsAdaptiveApp();
+ HRESULT GetCurrentPackageRoot(_Inout_ UINT32* length, _Out_opt_ PWSTR packageRoot);
+ HRESULT GetWinMetadataDirForAdaptiveApps(_Out_ LPWSTR* winMetadDataDir);
+#ifdef FEATURE_APPX_BINDER
+ enum FindFindInPackageFlags
+ {
+ FindFindInPackageFlags_None = 0,
+ FindFindInPackageFlags_AllowLongFormatPath = 1,
+ FindFindInPackageFlags_SkipCurrentPackageGraph = 2, // Only search in alt path
+ };
+
+ // If the function succeeds, pcchPathName is set to the length of the string that is copied to the buffer,
+ // in characters, including the terminating null character, and the function returns S_OK. If the buffer
+ // is too small, pcchPathName is set to the length of the buffer required (in characters),
+ // including the terminating null character, and the function returns ERROR_INSUFFICIENT_BUFFER.
+ HRESULT FindFileInCurrentPackage(
+ __in PCWSTR pszFileName,
+ __inout PUINT32 pcchPathName,
+ __out PWSTR pszPathName,
+ __in UINT32 uiFlags = PACKAGE_FILTER_CLR_DEFAULT,
+ __in PCWSTR *rgwzAltPaths = NULL,
+ __in UINT32 cAltPaths = 0,
+ FindFindInPackageFlags findInCurrentPackageFlags = FindFindInPackageFlags_None);
+#endif // FEATURE_APPX_BINDER
+
+ // Attempts to retrieve the AppContainer SID for the specified process.
+ // For non-AppContainer processes the function will return S_FALSE and pAppContainerTokenInfo will be NULL.
+ // For AppContainer processes the function will return S_OK and pAppContainerTokenInfo will contain data.
+ // Note that there might be legitimate cases where this function fails (caller doesn't have permissions to
+ // OpenProcess() for example) so any callers must account for such failures.
+ // Use of NewArrayHolder permits method to reuse info for current process (dwPid == self) or to allocate
+ // memory (dwPid != self). Cast the result to PTOKEN_APPCONTAINER_INFORMATION;
+ HRESULT GetAppContainerTokenInfoForProcess(
+ DWORD dwPid,
+ NewArrayHolder<BYTE>& pbAppContainerTokenInfo, // Cast to PTOKEN_APPCONTAINER_INFORMATION on return.
+ DWORD* pcbAppContainerTokenInfo = nullptr);
+
+ // Called during NGen to pretend that we are in a certain package.
+ HRESULT SetCurrentPackageForNGen(__in PCWSTR pszPackageFullName);
+}
+
+#endif // FEATURE_CORECLR
+
+#else // FEATURE_APPX
+
+namespace AppX
+{
+ inline bool IsAppXProcess()
+ {
+ return false;
+ }
+}
+
+#endif // FEATURE_APPX
diff --git a/src/inc/arraylist.h b/src/inc/arraylist.h
new file mode 100644
index 0000000..f45085b
--- /dev/null
+++ b/src/inc/arraylist.h
@@ -0,0 +1,305 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+
+#ifndef ARRAYLIST_H_
+#define ARRAYLIST_H_
+
+#include <daccess.h>
+#include <contract.h>
+#include <stddef.h> // offsetof
+
+//
+// ArrayList is a simple class which is used to contain a growable
+// list of pointers, stored in chunks. Modification is by appending
+// only currently. Access is by index (efficient if the number of
+// elements stays small) and iteration (efficient in all cases).
+//
+// An important property of an ArrayList is that the list remains
+// coherent while it is being modified. This means that readers
+// never need to lock when accessing it.
+//
+
+#ifdef _MSC_VER
+#pragma warning(push)
+#pragma warning(disable : 4200) // Disable zero-sized array warning
+#endif
+
+class ArrayListBase
+{
+ public:
+
+ enum
+ {
+ ARRAY_BLOCK_SIZE_START = 5,
+ };
+
+ private:
+
+ struct ArrayListBlock
+ {
+ SPTR(ArrayListBlock) m_next;
+ DWORD m_blockSize;
+#ifdef _WIN64
+ DWORD m_padding;
+#endif
+ PTR_VOID m_array[0];
+
+#ifdef DACCESS_COMPILE
+ static ULONG32 DacSize(TADDR addr)
+ {
+ LIMITED_METHOD_CONTRACT;
+ return offsetof(ArrayListBlock, m_array) +
+ (*PTR_DWORD(addr + offsetof(ArrayListBlock, m_blockSize)) * sizeof(void*));
+ }
+#endif
+ };
+ typedef SPTR(ArrayListBlock) PTR_ArrayListBlock;
+
+ struct FirstArrayListBlock
+ {
+ PTR_ArrayListBlock m_next;
+ DWORD m_blockSize;
+#ifdef _WIN64
+ DWORD m_padding;
+#endif
+ void * m_array[ARRAY_BLOCK_SIZE_START];
+ };
+
+ typedef DPTR(FirstArrayListBlock) PTR_FirstArrayListBlock;
+
+ DWORD m_count;
+ FirstArrayListBlock m_firstBlock;
+
+ public:
+
+ PTR_VOID *GetPtr(DWORD index) const;
+ PTR_VOID Get(DWORD index) const
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ return *GetPtr(index);
+ }
+
+ void Set(DWORD index, PTR_VOID element)
+ {
+ WRAPPER_NO_CONTRACT;
+ STATIC_CONTRACT_SO_INTOLERANT;
+ *GetPtr(index) = element;
+ }
+
+ DWORD GetCount() const { LIMITED_METHOD_DAC_CONTRACT; return m_count; }
+
+ HRESULT Append(void *element);
+
+ enum { NOT_FOUND = -1 };
+ DWORD FindElement(DWORD start, PTR_VOID element) const;
+
+ void Clear();
+
+ void Init()
+ {
+ LIMITED_METHOD_CONTRACT;
+ STATIC_CONTRACT_SO_INTOLERANT;
+
+ m_count = 0;
+ m_firstBlock.m_next = NULL;
+ m_firstBlock.m_blockSize = ARRAY_BLOCK_SIZE_START;
+ }
+
+ void Destroy()
+ {
+ WRAPPER_NO_CONTRACT;
+ STATIC_CONTRACT_SO_INTOLERANT;
+ Clear();
+ }
+
+#ifdef DACCESS_COMPILE
+ void EnumMemoryRegions(CLRDataEnumMemoryFlags flags);
+#endif
+
+ class ConstIterator;
+
+ class Iterator
+ {
+ friend class ArrayListBase;
+ friend class ConstIterator;
+
+ public:
+ BOOL Next();
+
+ void SetEmpty()
+ {
+ LIMITED_METHOD_CONTRACT;
+
+ m_block = NULL;
+ m_index = (DWORD)-1;
+ m_remaining = 0;
+ m_total = 0;
+ }
+
+ PTR_VOID GetElement() {LIMITED_METHOD_DAC_CONTRACT; return m_block->m_array[m_index]; }
+ PTR_VOID * GetElementPtr() {LIMITED_METHOD_CONTRACT; return m_block->m_array + m_index; }
+ DWORD GetIndex() {LIMITED_METHOD_CONTRACT; return m_index + m_total; }
+ void *GetBlock() { return m_block; }
+
+ private:
+ ArrayListBlock* m_block;
+ DWORD m_index;
+ DWORD m_remaining;
+ DWORD m_total;
+ static Iterator Create(ArrayListBlock* block, DWORD remaining)
+ {
+ LIMITED_METHOD_DAC_CONTRACT;
+ STATIC_CONTRACT_SO_INTOLERANT;
+ Iterator i;
+ i.m_block = block;
+ i.m_index = (DWORD) -1;
+ i.m_remaining = remaining;
+ i.m_total = 0;
+ return i;
+ }
+ };
+
+ class ConstIterator
+ {
+ public:
+ ConstIterator(ArrayListBlock *pBlock, DWORD dwRemaining) : m_iterator(Iterator::Create(pBlock, dwRemaining))
+ {
+ }
+
+ BOOL Next()
+ {
+ WRAPPER_NO_CONTRACT;
+ return m_iterator.Next();
+ }
+
+ PTR_VOID GetElement()
+ {
+ WRAPPER_NO_CONTRACT;
+ return m_iterator.GetElement();
+ }
+
+ private:
+ Iterator m_iterator;
+ };
+
+ Iterator Iterate()
+ {
+ STATIC_CONTRACT_SO_INTOLERANT;
+ WRAPPER_NO_CONTRACT;
+ return Iterator::Create((ArrayListBlock*)&m_firstBlock, m_count);
+ }
+
+ ConstIterator Iterate() const
+ {
+ STATIC_CONTRACT_SO_INTOLERANT;
+
+ // Const cast is safe because ConstIterator does not expose any way to modify the block
+ ArrayListBlock *pFirstBlock = const_cast<ArrayListBlock *>(reinterpret_cast<const ArrayListBlock *>(&m_firstBlock));
+ return ConstIterator(pFirstBlock, m_count);
+ }
+
+ // BlockIterator is used for only memory walking, such as prejit save/fixup.
+ // It is not appropriate for other more typical ArrayList use.
+ class BlockIterator
+ {
+ private:
+
+ ArrayListBlock *m_block;
+ DWORD m_remaining;
+
+ friend class ArrayListBase;
+ BlockIterator(ArrayListBlock *block, DWORD remaining)
+ : m_block(block), m_remaining(remaining)
+ {
+ }
+
+ public:
+
+ BOOL Next()
+ {
+ if (m_block != NULL)
+ {
+ // Prevent m_remaining from underflowing - we can have completely empty block at the end.
+ if (m_remaining > m_block->m_blockSize)
+ m_remaining -= m_block->m_blockSize;
+ else
+ m_remaining = 0;
+
+ m_block = m_block->m_next;
+ }
+ return m_block != NULL;
+ }
+
+ void ClearUnusedMemory()
+ {
+ if (m_remaining < m_block->m_blockSize)
+ ZeroMemory(&(m_block->m_array[m_remaining]), (m_block->m_blockSize - m_remaining) * sizeof(void*));
+#ifdef _WIN64
+ m_block->m_padding = 0;
+#endif
+ }
+
+ void **GetNextPtr()
+ {
+ return (void **) &m_block->m_next;
+ }
+
+ void *GetBlock()
+ {
+ return m_block;
+ }
+
+ SIZE_T GetBlockSize()
+ {
+ return offsetof(ArrayListBlock, m_array) + (m_block->m_blockSize * sizeof(void*));
+ }
+ };
+
+ void **GetInitialNextPtr()
+ {
+ return (void **) &m_firstBlock.m_next;
+ }
+
+ BlockIterator IterateBlocks()
+ {
+ return BlockIterator((ArrayListBlock *) &m_firstBlock, m_count);
+ }
+
+};
+
+class ArrayList : public ArrayListBase
+{
+public:
+#ifndef DACCESS_COMPILE
+ ArrayList()
+ {
+ STATIC_CONTRACT_SO_INTOLERANT;
+ WRAPPER_NO_CONTRACT;
+ Init();
+ }
+
+ ~ArrayList()
+ {
+ STATIC_CONTRACT_SO_INTOLERANT;
+ WRAPPER_NO_CONTRACT;
+ Destroy();
+ }
+#endif
+};
+
+/* to be used as static variable - no constructor/destructor, assumes zero
+ initialized memory */
+class ArrayListStatic : public ArrayListBase
+{
+};
+
+typedef DPTR(ArrayListStatic) PTR_ArrayListStatic;
+#ifdef _MSC_VER
+#pragma warning(pop)
+#endif
+
+#endif
diff --git a/src/inc/assemblyfilehash.h b/src/inc/assemblyfilehash.h
new file mode 100644
index 0000000..5f6fb23
--- /dev/null
+++ b/src/inc/assemblyfilehash.h
@@ -0,0 +1,92 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+
+
+#ifndef __ASSEMBLYHASH_H__
+#define __ASSEMBLYHASH_H__
+
+#include "wincrypt.h"
+#include "ex.h"
+
+
+
+class AssemblyFileHash
+{
+protected:
+ BOOL m_bDataOwner;
+ PBYTE m_pbData;
+ DWORD m_cbData;
+ PBYTE m_pbHash;
+ DWORD m_cbHash;
+ HRESULT HashData(HCRYPTHASH);
+ HANDLE m_hFile;
+ BOOL m_NeedToReadData;
+
+ HRESULT ReadData();
+public:
+
+ HRESULT SetFileName(LPCWSTR wszFileName);
+ HRESULT ReleaseFileHandle()
+ {
+ WRAPPER_NO_CONTRACT;
+ return SetFileHandle(INVALID_HANDLE_VALUE);
+ };
+ HRESULT SetFileHandle(HANDLE hFile)
+ {
+ LIMITED_METHOD_CONTRACT;
+ m_hFile=hFile;
+ return S_OK;
+ };
+
+ HRESULT SetData(PBYTE pbData, DWORD cbData) // Owned by owners context. Will not be deleted
+ {
+ CONTRACTL
+ {
+ NOTHROW;
+ GC_NOTRIGGER;
+ }
+ CONTRACTL_END;
+
+ m_pbData = pbData;
+ m_cbData = cbData;
+ m_bDataOwner = FALSE;
+ m_NeedToReadData=FALSE;
+ return S_OK;
+ }
+
+ PBYTE GetHash() { LIMITED_METHOD_CONTRACT; _ASSERTE(!m_NeedToReadData);return m_pbHash; }
+ DWORD GetHashSize() { LIMITED_METHOD_CONTRACT;_ASSERTE(!m_NeedToReadData); return m_cbHash; }
+
+ HRESULT CalculateHash(DWORD algid);
+
+ AssemblyFileHash()
+ : m_pbData( NULL ),
+ m_cbData( 0 ),
+ m_pbHash( NULL ),
+ m_cbHash( 0 ),
+ m_hFile(INVALID_HANDLE_VALUE),
+ m_NeedToReadData(TRUE)
+ {
+ CONTRACTL
+ {
+ CONSTRUCTOR_CHECK;
+ NOTHROW;
+ GC_NOTRIGGER;
+ }
+ CONTRACTL_END;
+ }
+
+ ~AssemblyFileHash()
+ {
+ delete [] m_pbHash;
+ if (m_bDataOwner)
+ delete [] m_pbData;
+ if (m_hFile!=INVALID_HANDLE_VALUE)
+ CloseHandle(m_hFile);
+ m_hFile=INVALID_HANDLE_VALUE;
+ }
+};
+
+#endif
diff --git a/src/inc/assemblyusagelog.idl b/src/inc/assemblyusagelog.idl
new file mode 100644
index 0000000..b942d59
--- /dev/null
+++ b/src/inc/assemblyusagelog.idl
@@ -0,0 +1,51 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//+---------------------------------------------------------------------------
+//
+// File: assemblyusageloginterface.idl
+//
+// Contents: COM interface for assembly usage log.
+//
+// Classes:
+//
+// Functions:
+//
+//
+//----------------------------------------------------------------------------
+
+cpp_quote("")
+cpp_quote("#ifdef _MSC_VER")
+cpp_quote("#pragma comment(lib,\"uuid.lib\")")
+cpp_quote("#endif")
+cpp_quote("")
+cpp_quote("//---------------------------------------------------------------------------=")
+cpp_quote("// Assembly Usage Log Interfaces")
+cpp_quote("")
+
+import "objidl.idl";
+
+cpp_quote("#ifdef _MSC_VER")
+cpp_quote("#pragma once")
+cpp_quote("#endif")
+
+cpp_quote("// {ec2b5f70-d576-4d33-876f-6e3caeb0a7ba}")
+cpp_quote("EXTERN_GUID(IID_IAssemblyUsageLog, 0xec2b5f70, 0xd576, 0x4d33, 0x87, 0x6f, 0x6e, 0x3c, 0xae, 0xb0, 0xa7, 0xba);")
+
+typedef enum
+{
+ ASSEMBLY_USAGE_LOG_FLAGS_NI = 1,
+ ASSEMBLY_USAGE_LOG_FLAGS_IL = 2,
+} ASSEMBLY_USAGE_LOG_FLAGS;
+
+[
+ local,
+ object,
+ uuid(ec2b5f70-d576-4d33-876f-6e3caeb0a7ba),
+ pointer_default(unique)
+]
+interface IAssemblyUsageLog : IUnknown
+{
+ HRESULT LogFile(LPCWSTR pwszILFile, LPCWSTR pwszNIFile, ASSEMBLY_USAGE_LOG_FLAGS flags);
+};
+
diff --git a/src/inc/assemblyusagelogmanager.h b/src/inc/assemblyusagelogmanager.h
new file mode 100644
index 0000000..5fae606
--- /dev/null
+++ b/src/inc/assemblyusagelogmanager.h
@@ -0,0 +1,53 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+#ifndef ASSEMBLY_USAGE_LOG_MANAGER_H
+#define ASSEMBLY_USAGE_LOG_MANAGER_H
+
+#include "assemblyusagelog.h"
+#include "daccess.h"
+
+class AssemblyUsageLogManager
+{
+public:
+
+ class Config
+ {
+ public:
+ LPCWSTR wszLogDir;
+ unsigned int cLogBufferSize;
+#ifdef FEATURE_APPX
+ unsigned int uiLogRefreshInterval;
+#endif
+ };
+
+ enum GENERATE_LOG_FLAGS
+ {
+ GENERATE_LOG_FLAGS_NONE = 0,
+ };
+
+ // we depend on static PODs being initialized to 0 which is why ASSEMBLY_USAGE_LOG_FLAGS_NONE is 0
+ enum ASSEMBLY_USAGE_LOG_FLAGS : DWORD
+ {
+ ASSEMBLY_USAGE_LOG_FLAGS_NONE = 0,
+ ASSEMBLY_USAGE_LOG_FLAGS_INITTED = 1,
+ ASSEMBLY_USAGE_LOG_FLAGS_APPLOCALNGENDISABLED = 2,
+ };
+
+ static HRESULT Init(const Config *pConfig);
+ static HRESULT GenerateLog(GENERATE_LOG_FLAGS flags);
+ static HRESULT GetUsageLogForContext(LPCWSTR binder, LPCWSTR binderParameter, IAssemblyUsageLog **ppUsageLog);
+ static HRESULT RegisterBinderWithUsageLog(UINT_PTR binderId, IAssemblyUsageLog *pUsageLog);
+ static HRESULT UnRegisterBinderFromUsageLog(UINT_PTR binderId);
+ static IAssemblyUsageLog *GetUsageLogForBinder(UINT_PTR binderId);
+ static ASSEMBLY_USAGE_LOG_FLAGS GetUsageLogFlags();
+ static HRESULT SetUsageLogFlag(ASSEMBLY_USAGE_LOG_FLAGS flag, BOOL);
+
+private:
+ SVAL_DECL(ASSEMBLY_USAGE_LOG_FLAGS, s_UsageLogFlags);
+};
+
+#endif /* ASSEMBLY_USAGE_LOG_MANAGER_H */
+
diff --git a/src/inc/bbsweep.h b/src/inc/bbsweep.h
new file mode 100644
index 0000000..d5526d8
--- /dev/null
+++ b/src/inc/bbsweep.h
@@ -0,0 +1,425 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+/*****************************************************************************\
+* *
+* BBSweep.h - Classes for sweeping profile data to disk *
+* *
+* Version 1.0 *
+*******************************************************************************
+* *
+* THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY *
+* KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE *
+* IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR *
+* PURPOSE. *
+* *
+\*****************************************************************************/
+
+#ifndef _BBSWEEP_H_
+#define _BBSWEEP_H_
+
+#ifndef FEATURE_PAL
+#include <aclapi.h>
+#endif // !FEATURE_PAL
+
+// The CLR headers don't allow us to use methods like SetEvent directly (instead
+// we need to use the host APIs). However, this file is included both in the CLR
+// and in the BBSweep tool, and the host API is not available in the tool. Moreover,
+// BBSweep is not designed to work in an environment where the host controls
+// synchronization. For this reason, we work around the problem by undefining
+// these APIs (the CLR redefines them so that they will not be used).
+#pragma push_macro("SetEvent")
+#pragma push_macro("ResetEvent")
+#pragma push_macro("ReleaseSemaphore")
+#pragma push_macro("LocalFree")
+#undef SetEvent
+#undef ResetEvent
+#undef ReleaseSemaphore
+#undef LocalFree
+
+// MAX_COUNT is the maximal number of runtime processes that can run at a given time
+#define MAX_COUNT 20
+
+#define INVALID_PID -1
+
+/* CLRBBSweepCallback is implemented by the CLR which passes it as an argument to WatchForSweepEvents.
+ * It is used by BBSweep to tell the CLR to write the profile data to disk at the right time.
+ */
+
+class ICLRBBSweepCallback
+{
+public:
+ virtual HRESULT WriteProfileData() = NULL; // tells the runtime to write the profile data to disk
+};
+
+/* BBSweep is used by both the CLR and the BBSweep utility.
+ * BBSweep: calls the PerformSweep method which returns after all the CLR processes
+ * have written their profile data to disk.
+ * CLR: starts up a sweeper thread which calls WatchForSweepEvents and waits until the
+ * sweeper program is invoked. At that point, all the CLR processes will synchronize
+ * and write their profile data to disk one at a time. The sweeper threads will then
+ * wait for the next sweep event. The CLR also calls ShutdownBBSweepThread at
+ * shutdown which returns when the BBSweep thread has terminated.
+ */
+
+class BBSweep
+{
+public:
+ BBSweep()
+ {
+ // The BBSweep constructor could be called even the the object is not used, so
+ // don't do any work here.
+ bInitialized = false;
+ bTerminate = false;
+ hSweepMutex = NULL;
+ hProfDataWriterMutex = NULL;
+ hSweepEvent = NULL;
+ hTerminationEvent = NULL;
+ hProfWriterSemaphore = NULL;
+ hBBSweepThread = NULL;
+ }
+
+ ~BBSweep()
+ {
+ // When the destructor is called, everything should be cleaned up already.
+ }
+
+ // Called by the sweeper utility to tell all the CLR threads to write their profile
+ // data to disk.
+ // THIS FUNCTIONALITY IS ALSO DUPLICATED IN TOOLBOX\MPGO\BBSWEEP.CS
+ // IF YOU CHANGE THIS CODE, YOU MUST ALSO CHANGE THAT TO MATCH!
+ bool PerformSweep(DWORD processID = INVALID_PID)
+ {
+ bool success = true;
+
+ if (!Initialize(processID, FALSE)) return false;
+
+ ::WaitForSingleObject(hSweepMutex, INFINITE);
+ {
+ success = success && ::SetEvent(hSweepEvent);
+ {
+ for (int i=0; i<MAX_COUNT; i++)
+ {
+ ::WaitForSingleObject(hProfWriterSemaphore, INFINITE);
+ }
+
+ ::ReleaseSemaphore(hProfWriterSemaphore, MAX_COUNT, NULL);
+
+ }
+ success = success && ::ResetEvent(hSweepEvent);
+ }
+ ::ReleaseMutex(hSweepMutex);
+
+ return success;
+ }
+
+ // Called by the CLR sweeper thread to wait until a sweep event, at which point
+ // it calls back into the CLR via the clrCallback interface to write the profile
+ // data to disk.
+ bool WatchForSweepEvents(ICLRBBSweepCallback *clrCallback)
+ {
+ if (!Initialize()) return false;
+
+ bool success = true;
+
+ while (!bTerminate)
+ {
+ ::WaitForSingleObject(hSweepMutex, INFINITE);
+ {
+ ::WaitForSingleObject(hProfWriterSemaphore, INFINITE);
+ }
+ ::ReleaseMutex(hSweepMutex);
+
+ HANDLE hEvents[2];
+ hEvents[0] = hSweepEvent;
+ hEvents[1] = hTerminationEvent;
+ ::WaitForMultipleObjectsEx(2, hEvents, false, INFINITE, FALSE);
+
+ ::WaitForSingleObject(hProfDataWriterMutex, INFINITE);
+ {
+ if (!bTerminate && FAILED(clrCallback->WriteProfileData()))
+ success = false;
+ }
+ ::ReleaseMutex(hProfDataWriterMutex);
+
+ ::ReleaseSemaphore(hProfWriterSemaphore, 1, NULL);
+ }
+
+ return success;
+ }
+
+ void SetBBSweepThreadHandle(HANDLE threadHandle)
+ {
+ hBBSweepThread = threadHandle;
+ }
+
+ void ShutdownBBSweepThread()
+ {
+ // Set the termination event and wait for the BBSweep thread to terminate on its own.
+ // Note that this is called by the shutdown thread (and never called by the BBSweep thread).
+ if (hBBSweepThread && bInitialized)
+ {
+ bTerminate = true;
+ ::SetEvent(hTerminationEvent);
+ ::WaitForSingleObject(hBBSweepThread, INFINITE);
+ Cleanup();
+ }
+ }
+
+ void Cleanup()
+ {
+ if (hSweepMutex) { ::CloseHandle(hSweepMutex); hSweepMutex = NULL;}
+ if (hProfDataWriterMutex) { ::CloseHandle(hProfDataWriterMutex); hProfDataWriterMutex = NULL;}
+ if (hSweepEvent) { ::CloseHandle(hSweepEvent); hSweepEvent = NULL;}
+ if (hTerminationEvent) { ::CloseHandle(hTerminationEvent); hTerminationEvent = NULL;}
+ if (hProfWriterSemaphore) { ::CloseHandle(hProfWriterSemaphore); hProfWriterSemaphore = NULL;}
+ }
+
+private:
+
+ // THIS FUNCTIONALITY IS ALSO DUPLICATED IN TOOLBOX\MPGO\BBSWEEP.CS
+ // IF YOU CHANGE THIS CODE, YOU MUST ALSO CHANGE THAT TO MATCH!
+ bool Initialize(DWORD processID = INVALID_PID, BOOL fromRuntime = TRUE)
+ {
+ if (!bInitialized)
+ {
+ SECURITY_ATTRIBUTES * pSecurityAttributes = NULL;
+
+#ifndef FEATURE_CORESYSTEM // @CORESYSTEMTODO
+ PSECURITY_DESCRIPTOR pSD = NULL;
+ PSID pAdminSid = NULL;
+ HANDLE hToken = NULL;
+ PACL pACL = NULL;
+ LPVOID buffer = NULL;
+
+ if (!OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken))
+ goto cleanup;
+
+ // don't set pSecurityAttributes for Metro processes
+ if(!IsAppContainerProcess(hToken))
+ {
+ SECURITY_ATTRIBUTES securityAttributes;
+ PSID pUserSid = NULL;
+ SID_IDENTIFIER_AUTHORITY SIDAuthNT = SECURITY_NT_AUTHORITY;
+ DWORD retLength;
+
+#ifdef _PREFAST_
+#pragma warning(push)
+#pragma warning(disable:6211) // PREfast warning: Leaking memory 'pSD' due to an exception.
+#endif /*_PREFAST_ */
+ pSD = (PSECURITY_DESCRIPTOR) new char[SECURITY_DESCRIPTOR_MIN_LENGTH];
+ if (!pSD)
+ goto cleanup;
+
+ if (GetTokenInformation(hToken, TokenOwner, NULL, 0, &retLength))
+ goto cleanup;
+
+ buffer = (LPVOID) new char[retLength];
+ if (!buffer)
+ goto cleanup;
+#ifdef _PREFAST_
+#pragma warning(pop)
+#endif /*_PREFAST_*/
+
+ // Get the SID for the current user
+ if (!GetTokenInformation(hToken, TokenOwner, (LPVOID) buffer, retLength, &retLength))
+ goto cleanup;
+
+ pUserSid = ((TOKEN_OWNER *) buffer)->Owner;
+
+ // Get the SID for the admin group
+ // Create a SID for the BUILTIN\Administrators group.
+ if(! AllocateAndInitializeSid(&SIDAuthNT, 2,
+ SECURITY_BUILTIN_DOMAIN_RID,
+ DOMAIN_ALIAS_RID_ADMINS,
+ 0, 0, 0, 0, 0, 0,
+ &pAdminSid))
+ goto cleanup;
+
+ EXPLICIT_ACCESS ea[2];
+ ZeroMemory(ea, 2 * sizeof(EXPLICIT_ACCESS));
+
+ // Initialize an EXPLICIT_ACCESS structure for an ACE.
+ // The ACE will allow the current user full access
+ ea[0].grfAccessPermissions = STANDARD_RIGHTS_ALL | SPECIFIC_RIGHTS_ALL; // KEY_ALL_ACCESS;
+ ea[0].grfAccessMode = SET_ACCESS;
+ ea[0].grfInheritance= NO_INHERITANCE;
+ ea[0].Trustee.TrusteeForm = TRUSTEE_IS_SID;
+ ea[0].Trustee.TrusteeType = TRUSTEE_IS_USER;
+ ea[0].Trustee.ptstrName = (LPTSTR) pUserSid;
+
+ // Initialize an EXPLICIT_ACCESS structure for an ACE.
+ // The ACE will allow admins full access
+ ea[1].grfAccessPermissions = STANDARD_RIGHTS_ALL | SPECIFIC_RIGHTS_ALL; //KEY_ALL_ACCESS;
+ ea[1].grfAccessMode = SET_ACCESS;
+ ea[1].grfInheritance= NO_INHERITANCE;
+ ea[1].Trustee.TrusteeForm = TRUSTEE_IS_SID;
+ ea[1].Trustee.TrusteeType = TRUSTEE_IS_GROUP;
+ ea[1].Trustee.ptstrName = (LPTSTR) pAdminSid;
+
+ if (SetEntriesInAcl(2, ea, NULL, &pACL) != ERROR_SUCCESS)
+ goto cleanup;
+
+ if (!InitializeSecurityDescriptor(pSD, SECURITY_DESCRIPTOR_REVISION))
+ goto cleanup;
+
+ if (!SetSecurityDescriptorDacl(pSD, TRUE, pACL, FALSE))
+ goto cleanup;
+
+ memset((void *) &securityAttributes, 0, sizeof(SECURITY_ATTRIBUTES));
+ securityAttributes.nLength = sizeof(SECURITY_ATTRIBUTES);
+ securityAttributes.lpSecurityDescriptor = pSD;
+ securityAttributes.bInheritHandle = FALSE;
+
+ pSecurityAttributes = &securityAttributes;
+ }
+#endif // !FEATURE_CORESYSTEM
+
+ WCHAR objectName[MAX_LONGPATH] = {0};
+ WCHAR objectNamePrefix[MAX_LONGPATH] = {0};
+ GetObjectNamePrefix(processID, fromRuntime, objectNamePrefix);
+ // if there is a non-empty name prefix, append a '\'
+ if (objectNamePrefix[0] != '\0')
+ wcscat_s(objectNamePrefix, ARRAYSIZE(objectNamePrefix), W("\\"));
+ swprintf_s(objectName, MAX_LONGPATH, W("%sBBSweep_hSweepMutex"), objectNamePrefix);
+ hSweepMutex = ::WszCreateMutex(pSecurityAttributes, false, objectName);
+ swprintf_s(objectName, MAX_LONGPATH, W("%sBBSweep_hProfDataWriterMutex"), objectNamePrefix);
+ hProfDataWriterMutex = ::WszCreateMutex(pSecurityAttributes, false, objectName);
+ swprintf_s(objectName, MAX_LONGPATH, W("%sBBSweep_hSweepEvent"), objectNamePrefix);
+ hSweepEvent = ::WszCreateEvent(pSecurityAttributes, true, false, objectName);
+
+ // Note that hTerminateEvent is not a named event. That is because it is not
+ // shared amongst the CLR processes (each process terminates at a different time)
+ hTerminationEvent = ::WszCreateEvent(pSecurityAttributes, true, false, NULL);
+ swprintf_s(objectName, MAX_LONGPATH, W("%sBBSweep_hProfWriterSemaphore"), objectNamePrefix);
+ hProfWriterSemaphore = ::WszCreateSemaphore(pSecurityAttributes, MAX_COUNT, MAX_COUNT, objectName);
+
+#ifndef FEATURE_CORESYSTEM // @CORESYSTEMTODO
+cleanup:
+ if (pSD) delete [] ((char *) pSD);
+ if (pAdminSid) FreeSid(pAdminSid);
+ if (hToken) CloseHandle(hToken);
+ if (pACL) LocalFree(pACL);
+ if (buffer) delete [] ((char *) buffer);
+#endif
+ }
+
+ bInitialized = hSweepMutex &&
+ hProfDataWriterMutex &&
+ hSweepEvent &&
+ hTerminationEvent &&
+ hProfWriterSemaphore;
+
+ if (!bInitialized) Cleanup();
+ return bInitialized;
+ }
+
+#ifndef FEATURE_PAL
+ BOOL IsAppContainerProcess(HANDLE hToken)
+ {
+#ifndef TokenIsAppContainer
+#define TokenIsAppContainer ((TOKEN_INFORMATION_CLASS) 29)
+#endif
+ BOOL fIsAppContainerProcess;
+ DWORD dwReturnLength;
+ if (!GetTokenInformation(hToken, TokenIsAppContainer, &fIsAppContainerProcess, sizeof(BOOL), &dwReturnLength) ||
+ dwReturnLength != sizeof(BOOL))
+ {
+ fIsAppContainerProcess = FALSE;
+ }
+ return fIsAppContainerProcess;
+ }
+#endif // !FEATURE_PAL
+
+ // helper to get the correct object name prefix
+ void GetObjectNamePrefix(DWORD processID, BOOL fromRuntime, __inout_z WCHAR* objectNamePrefix)
+ {
+ // default prefix
+ swprintf_s(objectNamePrefix, MAX_LONGPATH, W("Global"));
+#ifndef FEATURE_PAL
+ //
+ // This method can be called:
+ // 1. From process init code
+ // 2. From bbsweepclr.exe
+ //
+ // When called from process init code, processID is always INVALID_PID.
+ // In case it is a Win8-Metro/WP8 process, we need to add the AppContainerNamedObjectPath to prefix.
+ // And if it is a non-Metro process, we will continue to use the default prefix (Global).
+ // We use IsAppContainerProcess(CurrentProcessId) to make this decision.
+ //
+ //
+ // When called from bbsweepclr, processID is valid when sweeping a Metro or WP8 process.
+ // We use this valid processID to determine if the process being swept is Metro/WP8 indeed and then
+ // add AppContainerNamedObjectPath to prefix. This is done by IsAppContainerProcess(processID).
+ //
+ // In case INVALID_PID is passed(non-Metro process), we have to use default prefix. To handle this
+ // case we use IsAppContainerProcess(CurrentProcessId) and since bbsweepclr is a non-Metro process,
+ // this check always returns false and we end up using the intended(default) prefix.
+ //
+ if(processID == INVALID_PID) {
+ // we reach here when:
+ // * called from process init code:
+ // * called from bbsweepclr.exe and no processID has been passed as argument, that is, when sweeping a non-Metro process
+ processID = GetCurrentProcessId();
+ }
+
+ HandleHolder hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, processID);
+ if (hProcess != INVALID_HANDLE_VALUE)
+ {
+ HandleHolder hToken = NULL;
+ // if in the process init code of a Metro app or if bbsweepclr is used to sweep a Metro app,
+ // construct the object name prefix using AppContainerNamedObjectPath
+ if (OpenProcessToken(hProcess, TOKEN_QUERY, &hToken) && IsAppContainerProcess(hToken))
+ {
+ WCHAR appxNamedObjPath[MAX_LONGPATH] = { 0 };
+ ULONG appxNamedObjPathBufLen = 0;
+
+ if (fromRuntime)
+ {
+ // for Metro apps, create the object in the "default" object path, i.e. do not provide any prefix
+ objectNamePrefix[0] = W('\0');
+ }
+ else
+ {
+#if defined (FEATURE_CORESYSTEM) && !defined(CROSSGEN_COMPILE) && !defined(DACCESS_COMPILE)
+#define MODULE_NAME W("api-ms-win-security-appcontainer-l1-1-0.dll")
+#else
+#define MODULE_NAME W("kernel32.dll")
+#endif
+ typedef BOOL(WINAPI *PFN_GetAppContainerNamedObjectPath)
+ (HANDLE Token, PSID AppContainerSid, ULONG ObjectPathLength, WCHAR * ObjectPath, PULONG ReturnLength);
+
+ PFN_GetAppContainerNamedObjectPath pfnGetAppContainerNamedObjectPath = (PFN_GetAppContainerNamedObjectPath)
+ GetProcAddress(WszGetModuleHandle(MODULE_NAME), "GetAppContainerNamedObjectPath");
+ if (pfnGetAppContainerNamedObjectPath)
+ {
+ // for bbsweepclr sweeping a Metro app, create the object specifying the AppContainer's path
+ DWORD sessionId = 0;
+ ProcessIdToSessionId(processID, &sessionId);
+ pfnGetAppContainerNamedObjectPath(hToken, NULL, sizeof (appxNamedObjPath) / sizeof (WCHAR), appxNamedObjPath, &appxNamedObjPathBufLen);
+ swprintf_s(objectNamePrefix, MAX_LONGPATH, W("Global\\Session\\%d\\%s"), sessionId, appxNamedObjPath);
+ }
+ }
+ }
+ }
+#endif // FEATURE_PAL
+ }
+private:
+
+ bool bInitialized; // true when the BBSweep object has initialized successfully
+ bool bTerminate; // set to true when the CLR wants us to terminate
+ HANDLE hSweepMutex; // prevents processing from incrementing the semaphore after the sweep has began
+ HANDLE hProfDataWriterMutex; // guarantees that profile data will be written by one process at a time
+ HANDLE hSweepEvent; // tells the CLR processes to sweep their profile data
+ HANDLE hTerminationEvent; // set when the CLR process is ready to terminate
+ HANDLE hProfWriterSemaphore; // helps determine when all the writers are finished
+ HANDLE hBBSweepThread; // a handle to the CLR sweeper thread (that calls watch for sweep events)
+};
+
+#pragma pop_macro("LocalFree")
+#pragma pop_macro("ReleaseSemaphore")
+#pragma pop_macro("ResetEvent")
+#pragma pop_macro("SetEvent")
+
+#endif //_BBSWEEP_H
diff --git a/src/inc/binderngen.idl b/src/inc/binderngen.idl
new file mode 100644
index 0000000..d20cf93
--- /dev/null
+++ b/src/inc/binderngen.idl
@@ -0,0 +1,255 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+//+---------------------------------------------------------------------------
+//
+// File: binderngen.idl
+//
+// Contents: Binder to Native Binder Interfaces
+//
+// Classes:
+//
+// Functions:
+//
+//
+//----------------------------------------------------------------------------
+
+cpp_quote("")
+cpp_quote("#ifdef _MSC_VER")
+cpp_quote("#pragma comment(lib,\"uuid.lib\")")
+cpp_quote("#endif")
+cpp_quote("")
+cpp_quote("//---------------------------------------------------------------------------=")
+cpp_quote("// Binder Interfaces")
+cpp_quote("interface INativeImageInstallInfo;")
+cpp_quote("interface IILFingerprint;")
+cpp_quote("interface IILFingerprintFactory;")
+
+import "objidl.idl";
+import "fusion.idl";
+import "fusionpriv.idl";
+
+cpp_quote("#ifdef _MSC_VER")
+cpp_quote("#pragma once")
+cpp_quote("#endif")
+
+// interface IAssemblyName defined in fusion.idl
+// interface IAssemblyEnum defined in fusion.idl
+// interface IFusionBindLog defined in fusionpriv.idl
+// interface ICorSvcLogger defined in mscorsvc.idl
+
+interface IAssemblyLocation;
+interface IBindResult;
+interface IBindContext;
+interface INativeImageInstallInfo;
+interface IILFingerprint;
+
+typedef enum
+{
+ PRE_BIND_NONE = 0x00,
+ PRE_BIND_APPLY_POLICY = 0x80
+} PRE_BIND_FLAGS;
+
+
+typedef enum
+{
+ ASSEMBLY_LOCATION_PATH = 0x01,
+ ASSEMBLY_LOCATION_GAC = 0x02,
+ ASSEMBLY_LOCATION_HAS = 0x04,
+ ASSEMBLY_LOCATION_BYTE_ARRAY = 0x08
+} ASSEMBLY_LOCATION_FLAGS;
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// IAssemblyLocation
+//
+///////////////////////////////////////////////////////////////////////////////
+
+cpp_quote("// {6970aad6-d5fb-469b-9098-a03ddc65a4bd}")
+cpp_quote("EXTERN_GUID(IID_IAssemblyLocation, 0x6970aad6, 0xd5fb, 0x469b, 0x90, 0x98, 0xa0, 0x3d, 0xdc, 0x65, 0xa4, 0xbd);")
+
+[
+ local,
+ object,
+ uuid(6970aad6-d5fb-469b-9098-a03ddc65a4bd),
+ pointer_default(unique)
+]
+interface IAssemblyLocation : IUnknown
+{
+ typedef [unique] IAssemblyLocation *LPASSEMBLYLOCATION;
+
+ HRESULT GetLocationType([in] DWORD *pdwLocationType);
+
+ HRESULT GetPath([in, annotation("__inout_ecount(*pdwccAssemblyPath)")] LPWSTR pwzAssemblyPath,
+ [in, annotation("__inout")] LPDWORD pdwccAssemblyPath);
+
+ HRESULT GetHostID(UINT64 *puiHostID);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// IBindResult
+//
+// IBindResult was added mid-Dev10 when the native binder was split off
+// from Fusion. It seeks to provide a unified view of filepath-based assemblies (IAssembly),
+// host assemblies (IHostAssembly), NI images (the now-defunct CNativeImageAssembly) and
+// other things such as byte array assemblies (currently not expressible in Fusion at all.)
+//
+// At this time, it has not yet been widely adopted outside the native binder.
+//
+// @todo: Is it necessary for IBindResult to be a separately allocated object?
+// Why not create a base interface for the existing IAssembly/IHostAssembly?
+//
+//
+// Changes from Dev10:
+// Removed a bunch of methods that were added as expediencies and would
+// be long term liabilities if IBindResult is adopted as a universal assembly interface.
+//
+// In particular, it is no longer permitted to create IBindResult's that wrap
+// nothing more than an assembly name.
+//
+///////////////////////////////////////////////////////////////////////////////
+cpp_quote("// {82cff42f-55c2-45d2-aa6b-ff96e4de889c}")
+cpp_quote("EXTERN_GUID(IID_IBindResult, 0x82cff42f, 0x55c2, 0x45d2, 0xaa, 0x6b, 0xff, 0x96, 0xe4, 0xde, 0x88, 0x9c);")
+
+[
+ local,
+ object,
+ uuid(82cff42f-55c2-45d2-aa6b-ff96e4de889c),
+ pointer_default(unique)
+]
+interface IBindResult : IUnknown
+{
+ typedef [unique] IBindResult *LPBINDRESULT;
+
+ //--------------------------------------------------------------------------------
+ // These methods are good candidates for a "universal" Assembly interface.
+ //--------------------------------------------------------------------------------
+ HRESULT GetAssemblyNameDef([out] IAssemblyName **ppIAssemblyNameDef);
+
+ HRESULT GetNextAssemblyModuleName([in] DWORD dwNIndex,
+ [in, out, annotation("__inout_ecount(*pdwCCModuleName)")] LPWSTR pwzModuleName,
+ [in, out, annotation("__inout")] LPDWORD pdwCCModuleName);
+
+ HRESULT GetAssemblyLocation([out] IAssemblyLocation **ppIAssemblyLocation);
+
+
+ //--------------------------------------------------------------------------------
+ // Native image binding.
+ //
+ // @todo: Do these need to be on IBindResult? I'd say it's cleaner for
+ // these to be exposed as methods on the load context as was done pre-split.
+ //--------------------------------------------------------------------------------
+ HRESULT GetNativeImage([out] IBindResult **ppINativeImage,
+ [out] BOOL *pfNativeImageProbed);
+
+ HRESULT SetNativeImage([in] IBindResult *pINativeImage,
+ [out] IBindResult **ppINativeImageFinal);
+
+
+ //--------------------------------------------------------------------------------
+ // This is needed because IBindResults in Dev10 are not "interned" objects
+ // so we can't do pointer comparison on them as is done with IAssembly.
+ //--------------------------------------------------------------------------------
+ HRESULT IsEqual([in] IUnknown *pIUnk);
+
+
+ //--------------------------------------------------------------------------------
+ // These are used by the closure code only. We may want to rework these further
+ // post Dev10-MQ.
+ //--------------------------------------------------------------------------------
+ HRESULT GetNextAssemblyNameRef([in] DWORD dwNIndex,
+ [out] IAssemblyName **ppIAssemblyNameRef);
+
+ HRESULT GetNextDependentAssembly([in] DWORD dwNIndex,
+ [out] IUnknown **ppIUnknownAssembly);
+
+ // Ad-hoc method that gives the closure code the info it needs without native IBindResults
+ // actually having to maintain a reference to its partnered IL IBindResult.
+ HRESULT GetAssemblyLocationOfILImage([out] IAssemblyLocation **ppAssemblyLocation);
+
+
+ //--------------------------------------------------------------------------------
+ // For use on IL's only: Obtain information about IL timestamps/MVIDs/SNHashes, etc.
+ // Note that the MVID/SNHashes may be speculative (as we avoid opening the IL
+ // for workset reasons.) However, everyone in the process will see the same MVID/SNHashs
+ // for a given IL file.
+ //--------------------------------------------------------------------------------
+ HRESULT GetILFingerprint([out] IILFingerprint **ppFingerprint);
+ HRESULT GetSourceILTimestamp([out] FILETIME* pFileTime);
+ HRESULT GetSourceILSize([out] DWORD* pSize);
+
+ //--------------------------------------------------------------------------------
+ // For use on NI's only: Obtain information about NI version and dependencies.
+ //--------------------------------------------------------------------------------
+ HRESULT GetNIInfo([out] INativeImageInstallInfo** pInfo);
+
+ enum
+ {
+ IBindResultFlag_Default = 0x00,
+ IBindResultFlag_AssemblyNameDefIncomplete = 0x01,
+ };
+
+ //--------------------------------------------------------------------------------
+ // Returns the set of flags, defined in IBindResultFlags, that apply to this
+ // IBindResult object.
+ //--------------------------------------------------------------------------------
+ HRESULT GetFlags(DWORD * pdwFlags);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+//
+// IBindContext
+//
+// IBindContext represents a Fusion load context. It is an interface
+// via which Fusion provides services to the native binder.
+//
+// Note: This should *not* be adopted as a general interface for Fusion
+// load contexts. The services exposed here are quite specific to the native
+// binder's needs and it would be a liability to make them widely available.
+//
+///////////////////////////////////////////////////////////////////////////////
+cpp_quote("// {88db0d1a-460e-4341-96d7-a7c9b68f4679}")
+cpp_quote("EXTERN_GUID(IID_IBindContext, 0x88db0d1a, 0x460e, 0x4341, 0x96, 0xd7, 0xa7, 0xc9, 0xb6, 0x8f, 0x46, 0x79);")
+
+[
+ local,
+ object,
+ uuid(88db0d1a-460e-4341-96d7-a7c9b68f4679),
+ pointer_default(unique)
+]
+interface IBindContext : IUnknown
+{
+ typedef [unique] IBindContext *LPBINDCONTEXT;
+
+ HRESULT PreBind([in] IAssemblyName *pIAssemblyName,
+ [in] DWORD dwPreBindFlags,
+ [out] IBindResult **ppIBindResult);
+
+ HRESULT IsDefaultContext();
+}
+
+
+
+#pragma midl_echo("STDAPI GetBindResultFromPath(LPCWSTR pwzFilePath, DWORD dwMetaDataImportFlags, DWORD dwAssemblyLocation, IBindContext *pBindContext, IBindResult **ppIBindResult, HANDLE hFile = INVALID_HANDLE_VALUE); ")
+//
+// Interface fraction implemented by ngen binder folks.
+//
+
+typedef struct
+{
+ WCHAR *pwzZapConfigString;
+ DWORD dwZapConfigMask;
+} NativeConfigData;
+
+#pragma midl_echo("interface ICorSvcLogger;")
+#pragma midl_echo("STDAPI InitializeNativeBinder(); ")
+#pragma midl_echo("STDAPI GetZapDir(__deref_out LPCWSTR *pszZapDir); ")
+#pragma midl_echo("STDAPI InstallNativeAssembly(LPCWSTR pwzAssemblyPath, HANDLE hFile, LPCWSTR pwzZapSet, IBindContext* pBindCtx, IAssemblyName **ppAssemblyName, IAssemblyLocation **ppAssemblyLocation);")
+#pragma midl_echo("STDAPI UninstallNativeAssembly(IAssemblyName *pIAssemblyName, ICorSvcLogger *pLogSink); ")
+#pragma midl_echo("STDAPI QueryNativeAssemblyInfo(IAssemblyName *pIAssemblyName, __out_ecount(*pdwSize) LPWSTR pwzFilePath, __inout LPDWORD pdwSize); ")
+#pragma midl_echo("STDAPI GetAssemblyNameFromNIPath(LPCWSTR wszNIPath, IAssemblyName ** ppAssemblyName); ")
+#pragma midl_echo("STDAPI CreateNativeAssemblyEnum(IAssemblyEnum **ppIAssemblyEnum, IAssemblyName *pIAssemblyName);")
+#pragma midl_echo("STDAPI BindToNativeAssembly(IBindResult *pGivenILAsm, const NativeConfigData *pNativeConfigData, IBindContext *pBindContext, IFusionBindLog *pFusionBindLog); ")
+#pragma midl_echo("struct IMDInternalImport;")
diff --git a/src/inc/bitmask.h b/src/inc/bitmask.h
new file mode 100644
index 0000000..a59d2e2
--- /dev/null
+++ b/src/inc/bitmask.h
@@ -0,0 +1,103 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+//
+
+// --------------------------------------------------------------------------------
+// BitMask.h
+// --------------------------------------------------------------------------------
+
+// --------------------------------------------------------------------------------
+// BitMask is an arbitrarily large sized bitfield which has optimal storage
+// for 32 bits or less.
+// Storage is proportional to the highest index which is set.
+// --------------------------------------------------------------------------------
+
+
+#include <clrtypes.h>
+
+#ifndef _BITMASK_H_
+#define _BITMASK_H_
+
+class BitMask
+{
+ public:
+
+ BitMask();
+ ~BitMask();
+
+ BOOL TestBit(int bit);
+ void SetBit(int bit);
+ void ClearBit(int bit);
+
+ // returns true if any bit is set
+ BOOL TestAnyBit();
+
+ void ClearAllBits();
+
+ // Allocation exposed for ngen save/fixup
+ size_t GetAllocatedBlockOffset();
+ void *GetAllocatedBlock();
+ COUNT_T GetAllocatedBlockSize();
+
+ private:
+
+ static const int BIT_SIZE_SHIFT = 5;
+ static const int BIT_SIZE = (1<<BIT_SIZE_SHIFT);
+ static const int BIT_SIZE_MASK = BIT_SIZE-1;
+
+ static const COUNT_T MIN_ARRAY_ALLOCATION = 3;
+
+ // The first bit is used to indicate whether we've got a flat mask or
+ // an array of mask elements
+ BOOL IsArray();
+
+ // Indexing computations
+ COUNT_T BitToIndex(int bit);
+ COUNT_T BitToShift(int bit);
+
+ // Generic mask array access. Works for either case (array or non-array).
+ COUNT_T *GetMaskArray();
+ COUNT_T GetMaskArraySize();
+
+ // Need more bits...
+ void GrowArray(COUNT_T newSize);
+
+ union
+ {
+ COUNT_T m_mask;
+ COUNT_T *m_maskArray; // first array element is size of rest of array
+ };
+};
+
+// provides a wrapper around the BitMask class providing synchronized reads/writes safe for multithreaded access.
+// I've only added the public methods that were required by Module which needs a thread-safe BitMask. add others as required.
+class SynchronizedBitMask
+{
+ public:
+ // Allow Module access so we can use Offsetof on this class's private members during native image creation (determinism)
+ friend class Module;
+ SynchronizedBitMask();
+ ~SynchronizedBitMask() {}
+
+ BOOL TestBit(int bit);
+ void SetBit(int bit);
+ void ClearBit(int bit);
+
+ BOOL TestAnyBit();
+
+ void ClearAllBits();
+
+ private:
+
+ BitMask m_bitMask;
+
+ // note that this lock (at present) doesn't support promotion from reader->writer so be very careful
+ // when taking this lock else you might deadlock your own thread!
+ SimpleRWLock m_bitMaskLock;
+};
+
+#include <bitmask.inl>
+
+#endif // _BITMASK_H_
diff --git a/src/inc/bitmask.inl b/src/inc/bitmask.inl
new file mode 100644
index 0000000..00bfe01
--- /dev/null
+++ b/src/inc/bitmask.inl
@@ -0,0 +1,292 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+//
+
+// --------------------------------------------------------------------------------
+// BitMask.inl
+// --------------------------------------------------------------------------------
+
+#include <bitmask.h>
+
+#ifndef _BITMASK_INL_
+#define _BITMASK_INL_
+
+inline BOOL BitMask::IsArray()
+{
+ LIMITED_METHOD_CONTRACT;
+ return (m_mask&1) == 0;
+}
+
+// Indexing computations
+inline COUNT_T BitMask::BitToIndex(int bit)
+{
+ LIMITED_METHOD_CONTRACT;
+ // First word has one less bit due to tag
+ return (bit+1) >> BIT_SIZE_SHIFT;
+}
+
+inline COUNT_T BitMask::BitToShift(int bit)
+{
+ LIMITED_METHOD_CONTRACT;
+ // First word has one less bit due to tag
+ return (bit+1) & BIT_SIZE_MASK;
+}
+
+// Array access. Note the first array element is the count of the
+// rest of the elements
+
+inline COUNT_T *BitMask::GetMaskArray()
+{
+ LIMITED_METHOD_CONTRACT;
+ if (IsArray())
+ {
+ CONSISTENCY_CHECK(CheckPointer(m_maskArray));
+ return m_maskArray+1;
+ }
+ else
+ return &m_mask;
+}
+
+inline COUNT_T BitMask::GetMaskArraySize()
+{
+ LIMITED_METHOD_CONTRACT;
+ if (IsArray())
+ return *m_maskArray;
+ else
+ return 1;
+}
+
+inline void BitMask::GrowArray(COUNT_T newSize)
+{
+ CONTRACTL
+ {
+ THROWS;
+ }
+ CONTRACTL_END;
+
+ // Ensure we don't grow too often
+
+ COUNT_T oldSize = GetMaskArraySize();
+ if (newSize <= oldSize)
+ return;
+
+ if (newSize < oldSize*2)
+ newSize = oldSize*2;
+ if (newSize < MIN_ARRAY_ALLOCATION)
+ newSize = MIN_ARRAY_ALLOCATION;
+
+ // Allocate new array
+
+ COUNT_T *newArray = new COUNT_T [newSize+1];
+ *newArray = newSize;
+
+ CopyMemory(newArray+1, GetMaskArray(), oldSize * sizeof(COUNT_T));
+ ZeroMemory(newArray+oldSize+1, (newSize - oldSize) * sizeof(COUNT_T));
+
+ if (IsArray())
+ delete [] m_maskArray;
+
+ m_maskArray = newArray;
+}
+
+inline BitMask::BitMask()
+ : m_mask(1)
+{
+ LIMITED_METHOD_CONTRACT;
+}
+
+inline BitMask::~BitMask()
+{
+ LIMITED_METHOD_CONTRACT;
+
+ if (IsArray())
+ delete [] m_maskArray;
+}
+
+inline BOOL BitMask::TestBit(int bit)
+{
+ LIMITED_METHOD_CONTRACT;
+
+ COUNT_T index = BitToIndex(bit);
+
+ if (index >= GetMaskArraySize())
+ return FALSE;
+
+ return ( GetMaskArray()[index] >> BitToShift(bit) ) & 1;
+}
+
+inline void BitMask::SetBit(int bit)
+{
+ CONTRACTL
+ {
+ THROWS;
+ }
+ CONTRACTL_END;
+
+ COUNT_T index = BitToIndex(bit);
+
+ if (index >= GetMaskArraySize())
+ GrowArray(index+1);
+
+ GetMaskArray()[index] |= (1 << BitToShift(bit));
+}
+
+inline void BitMask::ClearBit(int bit)
+{
+ LIMITED_METHOD_CONTRACT;
+
+ COUNT_T index = BitToIndex(bit);
+
+ if (index >= GetMaskArraySize())
+ return;
+
+ GetMaskArray()[index] &= ~(1 << BitToShift(bit));
+}
+
+inline BOOL BitMask::TestAnyBit()
+{
+ LIMITED_METHOD_CONTRACT;
+
+ if (IsArray())
+ {
+ COUNT_T *mask = m_maskArray+1;
+ COUNT_T *maskEnd = mask + m_maskArray[0];
+
+ while (mask < maskEnd)
+ {
+ if (*mask != 0)
+ return TRUE;
+ mask++;
+ }
+
+ return FALSE;
+ }
+ else
+ return m_mask != (COUNT_T) 1;
+}
+
+inline void BitMask::ClearAllBits()
+{
+ LIMITED_METHOD_CONTRACT;
+
+ if (IsArray())
+ delete [] m_maskArray;
+
+ m_mask = 1;
+}
+
+inline size_t BitMask::GetAllocatedBlockOffset()
+{
+ LIMITED_METHOD_CONTRACT;
+
+ return offsetof(BitMask, m_maskArray);
+}
+
+inline void *BitMask::GetAllocatedBlock()
+{
+ LIMITED_METHOD_CONTRACT;
+
+ if (IsArray())
+ return m_maskArray;
+ else
+ return NULL;
+}
+
+inline COUNT_T BitMask::GetAllocatedBlockSize()
+{
+ LIMITED_METHOD_CONTRACT;
+
+ if (IsArray())
+ return (GetMaskArraySize()+1) * sizeof(COUNT_T);
+ else
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////////
+/////////////////////////////////////////////////////////////////////////////////////////////
+
+inline SynchronizedBitMask::SynchronizedBitMask()
+ : m_bitMaskLock(PREEMPTIVE, LOCK_TYPE_DEFAULT)
+{
+ LIMITED_METHOD_CONTRACT;
+}
+
+inline BOOL SynchronizedBitMask::TestBit(int bit)
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ MODE_ANY;
+ CAN_TAKE_LOCK;
+ }
+ CONTRACTL_END;
+
+ SimpleReadLockHolder holder(&m_bitMaskLock);
+
+ return m_bitMask.TestBit(bit);
+}
+
+inline void SynchronizedBitMask::SetBit(int bit)
+{
+ CONTRACTL
+ {
+ THROWS;
+ MODE_ANY;
+ CAN_TAKE_LOCK;
+ }
+ CONTRACTL_END;
+
+ SimpleWriteLockHolder holder(&m_bitMaskLock);
+
+ m_bitMask.SetBit(bit);
+}
+
+inline void SynchronizedBitMask::ClearBit(int bit)
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ MODE_ANY;
+ CAN_TAKE_LOCK;
+ }
+ CONTRACTL_END;
+
+ SimpleWriteLockHolder holder(&m_bitMaskLock);
+
+ m_bitMask.ClearBit(bit);
+}
+
+inline BOOL SynchronizedBitMask::TestAnyBit()
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ MODE_ANY;
+ CAN_TAKE_LOCK;
+ }
+ CONTRACTL_END;
+
+ SimpleReadLockHolder holder(&m_bitMaskLock);
+
+ return m_bitMask.TestAnyBit();
+}
+
+inline void SynchronizedBitMask::ClearAllBits()
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ MODE_ANY;
+ CAN_TAKE_LOCK;
+ }
+ CONTRACTL_END;
+
+ SimpleWriteLockHolder holder(&m_bitMaskLock);
+
+ m_bitMask.ClearAllBits();
+}
+
+#endif // _BITMASK_INL_
+
diff --git a/src/inc/bitposition.h b/src/inc/bitposition.h
new file mode 100644
index 0000000..0f3831f
--- /dev/null
+++ b/src/inc/bitposition.h
@@ -0,0 +1,55 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+#ifndef _BITPOSITION_H_
+#define _BITPOSITION_H_
+
+//------------------------------------------------------------------------
+// BitPosition: Return the position of the single bit that is set in 'value'.
+//
+// Return Value:
+// The position (0 is LSB) of bit that is set in 'value'
+//
+// Notes:
+// 'value' must have exactly one bit set.
+// The algorithm is as follows:
+// - PRIME is a prime bigger than sizeof(unsigned int), which is not of the
+// form 2^n-1.
+// - Taking the modulo of 'value' with this will produce a unique hash for all
+// powers of 2 (which is what "value" is).
+// - Entries in hashTable[] which are -1 should never be used. There
+// should be PRIME-8*sizeof(value) entries which are -1 .
+//
+inline
+unsigned BitPosition(unsigned value)
+{
+ _ASSERTE((value != 0) && ((value & (value-1)) == 0));
+#ifndef _TARGET_AMD64_
+ const unsigned PRIME = 37;
+
+ static const char hashTable[PRIME] =
+ {
+ -1, 0, 1, 26, 2, 23, 27, -1, 3, 16,
+ 24, 30, 28, 11, -1, 13, 4, 7, 17, -1,
+ 25, 22, 31, 15, 29, 10, 12, 6, -1, 21,
+ 14, 9, 5, 20, 8, 19, 18
+ };
+
+ _ASSERTE(PRIME >= 8*sizeof(value));
+ _ASSERTE(sizeof(hashTable) == PRIME);
+
+
+ unsigned hash = value % PRIME;
+ unsigned index = hashTable[hash];
+ _ASSERTE(index != (unsigned char)-1);
+#else
+ // not enabled for x86 because BSF is extremely slow on Atom
+ // (15 clock cycles vs 1-3 on any other Intel CPU post-P4)
+ DWORD index;
+ BitScanForward(&index, value);
+#endif
+ return index;
+}
+
+#endif
diff --git a/src/inc/bitvector.h b/src/inc/bitvector.h
new file mode 100644
index 0000000..a4181db
--- /dev/null
+++ b/src/inc/bitvector.h
@@ -0,0 +1,462 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+
+/***************************************************************************/
+/* BitVector.h */
+/***************************************************************************/
+// Routines to support a growable bitvector
+/***************************************************************************/
+
+#ifndef BITVECTOR_H
+#define BITVECTOR_H 1
+
+
+#ifndef LIMITED_METHOD_CONTRACT
+#define LIMITED_METHOD_CONTRACT
+#define UNDEF_LIMITED_METHOD_CONTRACT
+#endif
+
+#ifndef WRAPPER_NO_CONTRACT
+#define WRAPPER_NO_CONTRACT
+#define UNDEF_WRAPPER_NO_CONTRACT
+#endif
+
+#ifndef SUPPORTS_DAC
+#define SUPPORTS_DAC
+#define UNDEF_SUPPORTS_DAC
+#endif
+
+#ifndef _ASSERTE
+#define _ASSERTE(x)
+#define UNDEF_ASSERTE
+#endif
+
+#define USE_BITVECTOR 1
+#if USE_BITVECTOR
+
+/* The bitvector class is meant to be a drop in replacement for an integer
+ (that is you use it like an integer), however it grows as needed.
+
+ Features:
+ plug compatible with normal integers;
+ grows as needed
+ Optimized for the small case when the vector fits in machine word
+ Uses one machine word if vector fits in machine word (minus a bit)
+
+ Some caveates:
+ You should use mutator operators &=, |= ... instead of the
+ non-mutators whenever possible to avoid creating a temps
+
+ Specifically did NOT supply automatic coersions to
+ and from short types so that the programmer is aware of
+ when code was being injected on his behalf. The upshot of this
+ is that you have to use the BitVector() toUnsigned() to convert
+*/
+
+/***************************************************************************/
+
+class BitVector {
+ // Set this to be unsigned char to do testing, should be UINT_PTR for real life
+
+ typedef UINT_PTR ChunkType; // The size of integer type that the machine can operate on directly
+// typedef BYTE ChunkType; // Use for testing
+
+ // Maximum number of bits in our bitvector
+#define MAX_PTRARG_OFS 1024
+
+ enum {
+ IS_BIG = 1, // The low bit is used to discrimate m_val and m_vals
+ CHUNK_BITS = sizeof(ChunkType)*8, // The number of bits that we can manipuate as a chunk
+ SMALL_BITS = CHUNK_BITS - 1, // The number of bits we can fit in the small representation
+// SMALL_BITS = 5, // TESTING ONLY: The number of bits we can fit in the small representation
+ VALS_COUNT = MAX_PTRARG_OFS / CHUNK_BITS, // The number of ChunkType elements in the Vals array
+ };
+
+public:
+ BitVector()
+ {
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ m_val = 0;
+ }
+
+ BOOL isBig() const
+ {
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ return ((m_val & IS_BIG) != 0);
+ }
+
+ void toBig()
+ {
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (!isBig())
+ {
+ doBigInit(smallBits());
+ }
+ }
+
+ explicit BitVector(ChunkType arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (arg > MaxVal)
+ {
+ doBigInit(arg);
+ }
+ else
+ {
+ m_val = ChunkType(arg << 1);
+ }
+ }
+
+ BitVector(ChunkType arg, UINT shift)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if ((arg > MaxVal) || (shift >= SMALL_BITS) || (arg > (MaxVal >> shift)))
+ {
+ doBigInit(arg);
+ doBigLeftShiftAssign(shift);
+ }
+ else
+ {
+ m_val = ChunkType(arg << (shift+1));
+ }
+ }
+
+#define CONSTRUCT_ptrArgTP(arg,shift) BitVector((arg), (shift))
+
+ BitVector(const BitVector& arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (arg.isBig())
+ {
+ doBigInit(arg);
+ }
+ else
+ {
+ m_val = arg.m_val;
+ }
+ }
+
+ void operator <<=(unsigned shift)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if ((m_val == 0) || (shift == 0)) // Zero is a special case, don't need to do anything
+ return;
+
+ if (isBig() || (shift >= SMALL_BITS) || (m_val > (MaxVal >> (shift-1))))
+ {
+ doBigLeftShiftAssign(shift);
+ }
+ else
+ {
+ m_val <<= shift;
+ }
+ }
+
+ void operator >>=(unsigned shift)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (isBig())
+ {
+ doBigRightShiftAssign(shift);
+ }
+ else
+ {
+ m_val >>= shift;
+ m_val &= ~IS_BIG; // clear the isBig bit if it got set
+ }
+ }
+
+ void operator |=(const BitVector& arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (((m_val | arg.m_val) & IS_BIG) != 0)
+ {
+ doBigOrAssign(arg);
+ }
+ else
+ {
+ m_val |= arg.m_val;
+ }
+ }
+
+ // Note that that is set difference, not subtration
+ void operator -=(const BitVector& arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (((m_val | arg.m_val) & IS_BIG) != 0)
+ {
+ doBigDiffAssign(arg);
+ }
+ else
+ {
+ m_val &= ~arg.m_val;
+ }
+ }
+
+ void operator &=(const BitVector& arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (((m_val | arg.m_val) & IS_BIG) != 0)
+ {
+ doBigAndAssign(arg);
+ }
+ else
+ {
+ m_val &= arg.m_val;
+ }
+ }
+
+ friend void setDiff(BitVector& target, const BitVector& arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ target -= arg;
+ }
+
+ friend BOOL intersect(const BitVector& arg1, const BitVector& arg2)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (((arg1.m_val | arg2.m_val) & IS_BIG) != 0)
+ {
+ return arg1.doBigIntersect(arg2);
+ }
+ else
+ {
+ return ((arg1.m_val & arg2.m_val) != 0);
+ }
+ }
+
+ BOOL operator ==(const BitVector& arg) const
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if ((m_val | arg.m_val) & IS_BIG)
+ {
+ return doBigEquals(arg);
+ }
+ else
+ {
+ return m_val == arg.m_val;
+ }
+ }
+
+ BOOL operator !=(const BitVector& arg) const
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ return !(*this == arg);
+ }
+
+ friend ChunkType toUnsigned(const BitVector& arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (arg.isBig())
+ {
+ return arg.m_vals.m_chunks[0]; // Note truncation
+ }
+ else
+ {
+ return arg.smallBits();
+ }
+ }
+
+ // Note that we require the invariant that zero is always stored in the
+ // small form so that this works bitvector is zero iff (m_val == 0)
+ friend BOOL isZero(const BitVector& arg)
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ return arg.m_val == 0;
+ }
+
+ /* currently only used in asserts */
+ BitVector operator &(const BitVector& arg) const
+ {
+ WRAPPER_NO_CONTRACT;
+ SUPPORTS_DAC;
+
+ BitVector ret = *this;
+ ret &= arg;
+ return ret;
+ }
+
+ int NumBits() const;
+
+private:
+
+ static const ChunkType MaxVal = ((ChunkType)1 << SMALL_BITS) - 1; // Maximum value that can be stored in m_val
+
+ // This is the structure that we use when the bit vector overflows.
+ // It is a simple vector.
+ struct Vals {
+ unsigned m_encodedLength; // An encoding of the current length of the 'm_chunks' array
+ ChunkType m_chunks[VALS_COUNT];
+
+ BOOL isBig() const
+ {
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ return ((m_encodedLength & IS_BIG) != 0);
+ }
+
+ unsigned GetLength() const
+ {
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ if (isBig())
+ {
+ unsigned length = (m_encodedLength >> 1);
+ _ASSERTE(length > 0);
+ return length;
+ }
+ else
+ {
+ return 0;
+ }
+ }
+
+ void SetLength(unsigned length)
+ {
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ _ASSERTE(length > 0);
+ _ASSERTE(length <= VALS_COUNT);
+
+ m_encodedLength = (ChunkType) (length << 1);
+ m_encodedLength |= (ChunkType) IS_BIG;
+ }
+ };
+
+ //
+ // This is the instance data for the bitvector
+ //
+ // We discrimininate on this
+ union {
+ ChunkType m_val; // if m_val bit 0 is false, then bits 1-N are the bit vector
+ Vals m_vals; // if m_val bit 1 is true, then use Vals
+ };
+
+
+ ChunkType smallBits() const
+ {
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ _ASSERTE(!isBig());
+ return (m_val >> 1);
+ }
+
+#ifdef STRIKE
+ void doBigInit(ChunkType arg) {}
+#else
+ void doBigInit(ChunkType arg);
+#endif
+ void doBigInit(const BitVector& arg);
+ void doBigLeftShiftAssign(unsigned arg);
+ void doBigRightShiftAssign(unsigned arg);
+ void doBigDiffAssign(const BitVector&);
+ void doBigAndAssign(const BitVector&);
+ void doBigOrAssign(const BitVector& arg);
+ BOOL doBigEquals(const BitVector&) const;
+ BOOL doBigIntersect(const BitVector&) const;
+};
+
+typedef BitVector ptrArgTP;
+
+#else // !USE_BITVECTOR
+
+typedef unsigned __int64 ptrArgTP;
+
+ // Maximum number of bits in our bitvector
+#define MAX_PTRARG_OFS (sizeof(ptrArgTP) * 8)
+
+#define CONSTRUCT_ptrArgTP(arg,shift) (((ptrArgTP) (arg)) << (shift))
+
+inline BOOL isZero(const ptrArgTP& arg)
+{
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+ return (arg == 0);
+}
+
+inline ptrArgTP toUnsigned(const ptrArgTP& arg)
+{
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+ return arg;
+}
+
+inline void setDiff(ptrArgTP& target, const ptrArgTP& arg)
+{
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ target &= ~arg;
+}
+
+inline BOOL intersect(const ptrArgTP arg1, const ptrArgTP arg2)
+{
+ LIMITED_METHOD_CONTRACT;
+ SUPPORTS_DAC;
+
+ return ((arg1 & arg2) != 0);
+}
+
+#endif // !USE_BITVECTOR
+
+#ifdef UNDEF_LIMITED_METHOD_CONTRACT
+#undef LIMITED_METHOD_CONTRACT
+#undef UNDEF_LIMITED_METHOD_CONTRACT
+#endif
+
+#ifdef UNDEF_WRAPPER_NO_CONTRACT
+#undef WRAPPER_NO_CONTRACT
+#undef UNDEF_WRAPPER_NO_CONTRACT
+#endif
+
+#ifdef UNDEF_SUPPORTS_DAC
+#undef SUPPORTS_DAC
+#undef UNDEF_SUPPORTS_DAC
+#endif
+
+#ifdef UNDEF_ASSERTE
+#undef _ASSERTE
+#undef UNDEF_ASSERTE
+#endif
+
+#endif // BITVECTOR_H
diff --git a/src/inc/blobfetcher.h b/src/inc/blobfetcher.h
new file mode 100644
index 0000000..0c640f0
--- /dev/null
+++ b/src/inc/blobfetcher.h
@@ -0,0 +1,174 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//*****************************************************************************
+// CBlobFetcher - it fetches binary chunks, similar to new, but more controlled
+//
+// Fast, dynamic, memory management which doesn't relocate blocks
+// m_pIndex has array of pillars, where each pillar starts off empty and has
+// just-in-time allocation. As each pillar fills up, we move to the next pillar
+// If the entire array of pillars fill up, we need to allocate a new array and
+// copy the pillars over. But the actual data returned from GetBlock() never
+// gets moved. So everyone's happy.
+//
+//*****************************************************************************
+
+
+#ifndef __BLOB_FETCHER_H_
+#define __BLOB_FETCHER_H_
+
+#include <windef.h>
+
+
+class CBlobFetcher
+{
+protected:
+
+ class CPillar {
+ public:
+ CPillar();
+ ~CPillar();
+
+ void SetAllocateSize(unsigned nSize);
+ unsigned GetAllocateSize() const;
+
+ char* MakeNewBlock(unsigned len, unsigned pad);
+ void StealDataFrom(CPillar & src);
+ unsigned GetDataLen() const;
+ char* GetRawDataStart();
+ BOOL Contains(__in char *ptr);
+ ULONG32 GetOffset(__in char *ptr);
+
+ protected:
+ unsigned m_nTargetSize; // when we allocate, make it this large
+
+ // Make these public so CBlobFetcher can do easy manipulation
+ public:
+ char* m_dataAlloc;
+ char* m_dataStart;
+ char* m_dataCur;
+ char* m_dataEnd;
+ };
+
+
+ CPillar * m_pIndex; // array of pillars
+
+ unsigned m_nIndexMax; // actual size of m_ppIndex
+ unsigned m_nIndexUsed; // current pillar, so start at 0
+
+ unsigned m_nDataLen; // sum of all pillars' lengths
+
+// Don't allow these because they'll mess up the ownership
+ CBlobFetcher(const CBlobFetcher & src);
+ CBlobFetcher& operator=(const CBlobFetcher & src);
+
+public:
+#if defined(_WIN64)
+ // needs to be 64 so that we can purposefully cache align code in ngen'd images
+ enum { maxAlign = 64 }; // maximum alignment we support
+#else
+ enum { maxAlign = 32 }; // maximum alignment we support
+#endif
+ CBlobFetcher();
+ ~CBlobFetcher();
+
+// get a block to write on (use instead of write to avoid copy)
+ char * MakeNewBlock(unsigned int nSize, unsigned align=1);
+
+// Index segment as if this were linear
+ char * ComputePointer(unsigned offset) const;
+
+// Determine if pointer came from this fetcher
+ BOOL ContainsPointer(__in char *ptr) const;
+
+// Find an offset as if this were linear
+ unsigned ComputeOffset(__in char *ptr) const;
+
+// Write out the section to the stream
+ HRESULT Write(HANDLE file);
+
+// Write out the section to memory
+ HRESULT WriteMem(void ** pMem);
+
+// Get the total length of all our data (sum of all the pillar's data length's)
+// cached value, so light weight & no computations
+ unsigned GetDataLen() const;
+
+ HRESULT Merge(CBlobFetcher *destination);
+
+// Set the blob fetcher to slow growth mode. This should be done before any allocations
+ void SetInitialGrowth(unsigned growth);
+};
+
+
+//*****************************************************************************
+// Inlines
+//*****************************************************************************
+
+// Set the size that the Pillar will allocate if we call getBlock()
+inline void CBlobFetcher::CPillar::SetAllocateSize(unsigned nSize)
+{
+ LIMITED_METHOD_CONTRACT;
+ m_nTargetSize = nSize;
+}
+
+// Get the size we will allocate so we can decide if we need to change it
+// This is not the same as the GetDataLen() and is only useful
+// before we do the allocation
+inline unsigned CBlobFetcher::CPillar::GetAllocateSize() const
+{
+ LIMITED_METHOD_CONTRACT;
+ return m_nTargetSize;
+}
+
+inline char* CBlobFetcher::CPillar::GetRawDataStart()
+{
+ LIMITED_METHOD_CONTRACT;
+ return m_dataStart;
+}
+
+inline BOOL CBlobFetcher::CPillar::Contains(__in char *ptr)
+{
+ LIMITED_METHOD_CONTRACT;
+
+ return ptr >= m_dataStart && ptr < m_dataCur;
+}
+
+inline ULONG32 CBlobFetcher::CPillar::GetOffset(__in char *ptr)
+{
+ LIMITED_METHOD_CONTRACT;
+ _ASSERTE(Contains(ptr));
+
+ return (ULONG32)(ptr - m_dataStart);
+}
+
+//-----------------------------------------------------------------------------
+// Calculate the length of data being used, (not the length allocated)
+//-----------------------------------------------------------------------------
+inline unsigned CBlobFetcher::CPillar::GetDataLen() const
+{
+ LIMITED_METHOD_CONTRACT;
+
+ _ASSERTE((m_dataCur >= m_dataStart) && (m_dataCur <= m_dataEnd));
+
+ return (unsigned)(m_dataCur - m_dataStart);
+}
+
+inline unsigned CBlobFetcher::GetDataLen() const
+{
+ LIMITED_METHOD_CONTRACT;
+
+ return m_nDataLen;
+}
+
+// Set the blob fetcher to slow growth mode. This should be done before any allocations
+inline void CBlobFetcher::SetInitialGrowth(unsigned growth)
+{
+ _ASSERTE(GetDataLen() == 0);
+ if (GetDataLen() == 0)
+ {
+ m_pIndex[0].SetAllocateSize(growth);
+ }
+}
+
+#endif // __BLOB_FETCHER_H_
diff --git a/src/inc/cahlpr.h b/src/inc/cahlpr.h
new file mode 100644
index 0000000..903d3ab
--- /dev/null
+++ b/src/inc/cahlpr.h
@@ -0,0 +1,41 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//*****************************************************************************
+// File: CAHLPR.H
+//
+//
+//
+//*****************************************************************************
+#ifndef __CAHLPR_H__
+#define __CAHLPR_H__
+
+#include "caparser.h"
+
+//*****************************************************************************
+// This class assists in the parsing of CustomAttribute blobs.
+//*****************************************************************************
+struct CaValue
+{
+ union
+ {
+ signed __int8 i1;
+ unsigned __int8 u1;
+ signed __int16 i2;
+ unsigned __int16 u2;
+ signed __int32 i4;
+ unsigned __int32 u4;
+ signed __int64 i8;
+ unsigned __int64 u8;
+ float r4;
+ double r8;
+ struct
+ {
+ LPCUTF8 pStr;
+ ULONG cbStr;
+ } str;
+ };
+ unsigned __int8 tag;
+};
+
+#endif // __CAHLPR_H__
diff --git a/src/inc/caparser.h b/src/inc/caparser.h
new file mode 100644
index 0000000..0dfbb91
--- /dev/null
+++ b/src/inc/caparser.h
@@ -0,0 +1,377 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+// File: caparser.h
+//
+
+
+//
+
+//
+// ============================================================================
+
+#ifndef __CAPARSER_H__
+#define __CAPARSER_H__
+
+#include "stgpooli.h"
+
+class CustomAttributeParser {
+public:
+ CustomAttributeParser( // Constructor for CustomAttributeParser.
+ const void *pvBlob, // Pointer to the CustomAttribute blob.
+ ULONG cbBlob) // Size of the CustomAttribute blob.
+ : m_pbCur(reinterpret_cast<const BYTE*>(pvBlob)),
+ m_pbBlob(reinterpret_cast<const BYTE*>(pvBlob)),
+ m_cbBlob(cbBlob)
+ {
+ LIMITED_METHOD_CONTRACT;
+ }
+
+private:
+ signed __int8 GetI1()
+ {
+ LIMITED_METHOD_CONTRACT;
+ signed __int8 tmp = *reinterpret_cast<const signed __int8*>(m_pbCur);
+ m_pbCur += sizeof(signed __int8);
+ return tmp;
+ }
+ unsigned __int8 GetU1()
+ {
+ LIMITED_METHOD_CONTRACT;
+ unsigned __int8 tmp = *reinterpret_cast<const unsigned __int8*>(m_pbCur);
+ m_pbCur += sizeof(unsigned __int8);
+ return tmp;
+ }
+
+ signed __int16 GetI2()
+ {
+ LIMITED_METHOD_CONTRACT;
+ signed __int16 tmp = GET_UNALIGNED_VAL16(m_pbCur);
+ m_pbCur += sizeof(signed __int16);
+ return tmp;
+ }
+ unsigned __int16 GetU2()
+ {
+ LIMITED_METHOD_CONTRACT;
+ unsigned __int16 tmp = GET_UNALIGNED_VAL16(m_pbCur);
+ m_pbCur += sizeof(unsigned __int16 );
+ return tmp;
+ }
+
+ signed __int32 GetI4()
+ {
+ LIMITED_METHOD_CONTRACT;
+ signed __int32 tmp = GET_UNALIGNED_VAL32(m_pbCur);
+ m_pbCur += sizeof(signed __int32 );
+ return tmp;
+ }
+ unsigned __int32 GetU4()
+ {
+ LIMITED_METHOD_CONTRACT;
+ unsigned __int32 tmp = GET_UNALIGNED_VAL32(m_pbCur);
+ m_pbCur += sizeof(unsigned __int32 );
+ return tmp;
+ }
+
+ signed __int64 GetI8()
+ {
+ LIMITED_METHOD_CONTRACT;
+ signed __int64 tmp = GET_UNALIGNED_VAL64(m_pbCur);
+ m_pbCur += sizeof(signed __int64 );
+ return tmp;
+ }
+ unsigned __int64 GetU8()
+ {
+ LIMITED_METHOD_CONTRACT;
+ unsigned __int64 tmp = GET_UNALIGNED_VAL64(m_pbCur);
+ m_pbCur += sizeof(unsigned __int64 );
+ return tmp;
+ }
+
+public:
+ float GetR4()
+ {
+ LIMITED_METHOD_CONTRACT;
+ __int32 tmp = GET_UNALIGNED_VAL32(m_pbCur);
+ _ASSERTE(sizeof(__int32) == sizeof(float));
+ m_pbCur += sizeof(float);
+ return (float &)tmp;
+ }
+
+ double GetR8()
+ {
+ LIMITED_METHOD_CONTRACT;
+ __int64 tmp = GET_UNALIGNED_VAL64(m_pbCur);
+ _ASSERTE(sizeof(__int64) == sizeof(double));
+ m_pbCur += sizeof(double);
+ return (double &)tmp;
+ }
+
+private:
+ unsigned __int16 GetProlog()
+ {
+ WRAPPER_NO_CONTRACT;
+ unsigned __int16 val;
+ VERIFY(SUCCEEDED(GetProlog(&val)));
+ return val;
+ }
+
+ LPCUTF8 GetString(ULONG *pcbString)
+ {
+ WRAPPER_NO_CONTRACT;
+ LPCUTF8 val;
+ VERIFY(SUCCEEDED(GetString(&val, pcbString)));
+ return val;
+ }
+
+public:
+ HRESULT GetI1(signed __int8 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(signed __int8))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetI1();
+ return S_OK;
+ }
+
+ HRESULT GetTag(CorSerializationType *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+ HRESULT hr;
+ signed __int8 tmp;
+ IfFailRet(GetI1(&tmp));
+ *pVal = (CorSerializationType)((unsigned __int8)tmp);
+ return hr;
+ }
+
+ HRESULT GetU1(unsigned __int8 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(unsigned __int8))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetU1();
+ return S_OK;
+ }
+
+ HRESULT GetI2(signed __int16 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(signed __int16))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetI2();
+ return S_OK;
+ }
+ HRESULT GetU2(unsigned __int16 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(unsigned __int16))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetU2();
+ return S_OK;
+ }
+
+ HRESULT GetI4(signed __int32 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(signed __int32))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetI4();
+ return S_OK;
+ }
+ HRESULT GetU4(unsigned __int32 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(unsigned __int32))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetU4();
+ return S_OK;
+ }
+
+ HRESULT GetI8(signed __int64 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(signed __int64))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetI8();
+ return S_OK;
+ }
+ HRESULT GetU8(unsigned __int64 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(unsigned __int64))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetU8();
+ return S_OK;
+ }
+
+ HRESULT GetR4(float *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(float))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetR4();
+ return S_OK;
+ }
+ HRESULT GetR8(double *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ if (BytesLeft() < (int) sizeof(double))
+ return META_E_CA_INVALID_BLOB;
+ *pVal = GetR8();
+ return S_OK;
+ }
+
+ HRESULT GetProlog(unsigned __int16 *pVal)
+ {
+ WRAPPER_NO_CONTRACT;
+
+ m_pbCur = m_pbBlob;
+
+ if (BytesLeft() < (int)(sizeof(BYTE) * 2))
+ return META_E_CA_INVALID_BLOB;
+
+ return GetU2(pVal);
+ }
+
+ // Added for compatibility with anyone that may emit
+ // blobs where the prolog is the only incorrect data.
+ HRESULT SkipProlog()
+ {
+ unsigned __int16 val;
+ return GetProlog(&val);
+ }
+
+ HRESULT ValidateProlog()
+ {
+ HRESULT hr;
+ unsigned __int16 val;
+ IfFailRet(GetProlog(&val));
+
+ if (val != 0x0001)
+ return META_E_CA_INVALID_BLOB;
+
+ return hr;
+ }
+
+ //
+ // IMPORTANT: the returned string is typically not null-terminated.
+ //
+ // This can return any of three distinct valid results:
+ // - NULL string, indicated by *pszString==NULL, *pcbString==0
+ // - empty string, indicated by *pszString!=NULL, *pcbString==0
+ // - non-empty string, indicated by *pdzString!=NULL, *pcbString!=0
+ // If you expect non-null or non-empty strings in your usage scenario,
+ // call the GetNonNullString and GetNonEmptyString helpers below.
+ //
+ HRESULT GetString(LPCUTF8 *pszString, ULONG *pcbString)
+ {
+ STATIC_CONTRACT_NOTHROW;
+ STATIC_CONTRACT_FORBID_FAULT;
+
+ HRESULT hr;
+
+ if (BytesLeft() == 0)
+ { // Need to check for NULL string sentinal (see below),
+ // so need to have at least one byte to read.
+ IfFailRet(META_E_CA_INVALID_BLOB);
+ }
+
+ if (*m_pbCur == 0xFF)
+ { // 0xFF indicates the NULL string, which is semantically
+ // different than the empty string.
+ *pszString = NULL;
+ *pcbString = 0;
+ m_pbCur++;
+ return S_OK;
+ }
+
+ // Get the length, pointer to data following the length.
+ return GetData((BYTE const **)pszString, pcbString);
+ }
+
+ //
+ // This can return any of two distinct valid results:
+ // - empty string, indicated by *pszString!=NULL, *pcbString==0
+ // - non-empty string, indicated by *pszString!=NULL, *pcbString!=0
+ // If you expect non-null or non-empty strings in your usage scenario,
+ // call the GetNonNullString and GetNonEmptyString helpers below.
+ //
+ HRESULT GetNonNullString(LPCUTF8 *pszString, ULONG *pcbString)
+ {
+ STATIC_CONTRACT_NOTHROW;
+ STATIC_CONTRACT_FORBID_FAULT;
+
+ HRESULT hr;
+
+ IfFailRet(GetString(pszString, pcbString));
+
+ if (*pszString == NULL)
+ {
+ return META_E_CA_INVALID_BLOB;
+ }
+
+ return S_OK;
+ }
+
+ //
+ // This function will only return success if the string is valid,
+ // non-NULL and non-empty; i.e., *pszString!=NULL, *pcbString!=0
+ //
+ HRESULT GetNonEmptyString(LPCUTF8 *pszString, ULONG *pcbString)
+ {
+ STATIC_CONTRACT_NOTHROW;
+ STATIC_CONTRACT_FORBID_FAULT;
+
+ HRESULT hr;
+
+ IfFailRet(GetNonNullString(pszString, pcbString));
+
+ if (*pcbString == 0)
+ {
+ return META_E_CA_INVALID_BLOB;
+ }
+
+ return S_OK;
+ }
+
+ // IMPORTANT: do not use with string fetching - use GetString instead.
+ HRESULT GetData(BYTE const **ppbData, ULONG *pcbData)
+ {
+ HRESULT hr;
+ IfFailRet(CPackedLen::SafeGetData(m_pbCur, m_pbBlob + m_cbBlob, pcbData, ppbData));
+ // Move past the data we just recovered
+ m_pbCur = *ppbData + *pcbData;
+
+ return S_OK;
+ }
+
+ // IMPORTANT: do not use with string fetching - use GetString instead.
+ HRESULT GetPackedValue(ULONG *pcbData)
+ {
+ return CPackedLen::SafeGetLength(m_pbCur, m_pbBlob + m_cbBlob, pcbData, &m_pbCur);
+ }
+
+ int BytesLeft()
+ {
+ LIMITED_METHOD_CONTRACT;
+ return (int)(m_cbBlob - (m_pbCur - m_pbBlob));
+ }
+
+private:
+ const BYTE *m_pbCur;
+ const BYTE *m_pbBlob;
+ ULONG m_cbBlob;
+};
+
+#endif // __CAPARSER_H__
diff --git a/src/inc/ceefilegenwriter.h b/src/inc/ceefilegenwriter.h
new file mode 100644
index 0000000..8bfea46
--- /dev/null
+++ b/src/inc/ceefilegenwriter.h
@@ -0,0 +1,245 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+// ===========================================================================
+// File: CeeFileGenWriter.h
+//
+// ===========================================================================
+
+#ifndef _CEEFILEGENWRITER_H_
+#define _CEEFILEGENWRITER_H_
+//
+
+// CeeFileGenWriter contains all the code necessary to actually write an exe
+// while CCeeGen contains everything else. This lets CeeGen.exe and the VM
+// share more code without forcing the VM to carry the extra code to write an
+// exe.
+#include <windef.h>
+#include "ceegen.h"
+#include "iceefilegen.h"
+
+class PEWriter;
+class CeeFileGenWriter;
+
+// default setting for PE file
+const UINT32 CEE_IMAGE_BASE_32 = 0x00400000;
+const UINT64 CEE_IMAGE_BASE_64 = UI64(0x0000000140000000);
+const int CEE_IMAGE_SUBSYSTEM_MAJOR_VERSION = 4;
+const int CEE_IMAGE_SUBSYSTEM_MINOR_VERSION = 0;
+
+class CeeFileGenWriter : public CCeeGen
+{
+ mdToken m_entryPoint; // token for entry point
+ DWORD m_comImageFlags;
+
+ LPWSTR m_outputFileName;
+ LPWSTR m_resourceFileName;
+ LPWSTR m_libraryName;
+ GUID m_libraryGuid;
+ bool m_dllSwitch;
+
+ ULONG m_iatOffset;
+ DWORD m_dwMacroDefinitionRVA;
+ DWORD m_dwMacroDefinitionSize;
+
+ DWORD m_dwManifestRVA;
+ DWORD m_dwManifestSize;
+
+ DWORD m_dwStrongNameRVA;
+ DWORD m_dwStrongNameSize;
+
+ DWORD m_dwVTableRVA;
+ DWORD m_dwVTableSize;
+
+ bool m_linked;
+ bool m_fixed;
+
+ HRESULT checkForErrors();
+
+ struct IDataDllInfo {
+ const char *m_name;
+ int m_numMethods;
+ const char **m_methodName;
+ int m_iltOffset;
+ int m_ibnOffset;
+ int m_iatOffset;
+ int m_nameOffset;
+ } *m_iDataDlls;
+ int m_dllCount;
+
+ CeeSection *m_iDataSectionIAT;
+ int m_iDataOffsetIAT;
+ char *m_iDataIAT;
+
+#ifdef EMIT_FIXUPS
+
+ CeeSection * m_sectionFixups;
+ IMAGE_DEBUG_DIRECTORY * m_pDebugDir;
+ bool m_fFixupsUpdated;
+ bool m_fEmitFixups;
+
+#endif
+
+ HRESULT allocateIAT();
+public:
+ // Create with one of these two methods, not operator new
+ static HRESULT CreateNewInstance(CCeeGen *pCeeFileGenFrom, CeeFileGenWriter* & pGenWriter,
+ DWORD createFlags = ICEE_CREATE_FILE_PURE_IL);
+ // See ICeeFileGen.h for the definition of the bits used in createFlags
+ static HRESULT CreateNewInstanceEx(CCeeGen *pCeeFileGenFrom, CeeFileGenWriter* & pGenWriter,
+ DWORD createFlags, LPCWSTR seedFileName = NULL);
+
+ virtual HRESULT Cleanup();
+
+ PEWriter &getPEWriter();
+
+ HRESULT link(); // Layout the sections and assign their starting addresses
+ HRESULT fixup(); // Apply relocations to any pointer data. Also generate PE base relocs
+ HRESULT generateImage(void **ppImage);
+
+ HRESULT setImageBase(size_t imageBase);
+ HRESULT setImageBase64(ULONGLONG imageBase);
+ HRESULT setFileAlignment(ULONG fileAlignment);
+ HRESULT setSubsystem(DWORD subsystem, DWORD major, DWORD minor);
+
+ HRESULT getMethodRVA(ULONG codeOffset, ULONG *codeRVA);
+
+ HRESULT setEntryPoint(mdMethodDef method);
+ mdMethodDef getEntryPoint();
+
+ HRESULT setComImageFlags(DWORD mask);
+ HRESULT clearComImageFlags(DWORD mask);
+ DWORD getComImageFlags();
+
+ HRESULT setOutputFileName(__in LPWSTR outputFileName);
+ LPWSTR getOutputFileName();
+
+ HRESULT setResourceFileName(__in LPWSTR resourceFileName);
+ LPWSTR getResourceFileName();
+
+ HRESULT setLibraryName(__in LPWSTR libraryName);
+ LPWSTR getLibraryName();
+
+ HRESULT setDirectoryEntry(CeeSection &section, ULONG entry, ULONG size, ULONG offset=0);
+ HRESULT computeSectionOffset(CeeSection &section, __in char *ptr,
+ unsigned *offset);
+ HRESULT computeOffset(__in char *ptr, CeeSection **pSection,
+ unsigned *offset);
+ HRESULT getCorHeader(IMAGE_COR20_HEADER **ppHeader);
+
+ HRESULT getFileTimeStamp(DWORD *pTimeStamp);
+
+//<TODO>@FUTURE: this entry point is only here so that down level clients of this interface
+// can import the method by name in the exports table using the original name.
+// These things really ought to be exported through a v-table so there is no
+// name mangling issues. It would make the export table much smaller as well.</TODO>
+ HRESULT emitLibraryName(IMetaDataEmit *emitter);
+ HRESULT setLibraryGuid(__in LPWSTR libraryGuid);
+
+ HRESULT setDllSwitch(bool dllSwitch);
+ bool getDllSwitch();
+ HRESULT setObjSwitch(bool objSwitch);
+ bool getObjSwitch();
+ HRESULT EmitMacroDefinitions(void *pData, DWORD cData);
+ HRESULT setManifestEntry(ULONG size, ULONG offset);
+ HRESULT setStrongNameEntry(ULONG size, ULONG offset);
+ HRESULT setEnCRvaBase(ULONG dataBase, ULONG rdataBase);
+ HRESULT setVTableEntry(ULONG size, ULONG offset);
+ HRESULT setVTableEntry64(ULONG size, void* ptr);
+
+protected:
+ CeeFileGenWriter(); // ctor is protected
+
+ HRESULT emitResourceSection();
+ HRESULT emitExeMain();
+
+ HRESULT setAddrReloc(UCHAR *instrAddr, DWORD value);
+ HRESULT addAddrReloc(CeeSection &thisSection, UCHAR *instrAddr, DWORD offset, CeeSection *targetSection);
+
+ HRESULT MapTokens(CeeGenTokenMapper *pMapper, IMetaDataImport *pImport);
+ HRESULT MapTokensForMethod(CeeGenTokenMapper *pMapper,BYTE *pCode, LPCWSTR szMethodName);
+
+#ifdef EMIT_FIXUPS
+
+ HRESULT InitFixupSection();
+ HRESULT UpdateFixups();
+ HRESULT setEmitFixups();
+
+#ifdef TEST_EMIT_FIXUPS
+ HRESULT TestEmitFixups();
+#endif
+
+public:
+ HRESULT addFixup(CeeSection& secFixups, unsigned offset, CeeSectionRelocType reloc, CeeSection * relativeTo = NULL, CeeSectionRelocExtra *extra = 0);
+#endif
+};
+
+
+inline PEWriter &CeeFileGenWriter::getPEWriter()
+{
+ return (PEWriter &) *m_peSectionMan;
+}
+
+inline LPWSTR CeeFileGenWriter::getOutputFileName() {
+ return m_outputFileName;
+}
+
+inline LPWSTR CeeFileGenWriter::getResourceFileName() {
+ return m_resourceFileName;
+}
+
+inline HRESULT CeeFileGenWriter::setDllSwitch(bool dllSwitch) {
+ if((m_dllSwitch = dllSwitch)) m_objSwitch = FALSE; return S_OK;
+}
+
+inline bool CeeFileGenWriter::getDllSwitch() {
+ return m_dllSwitch;
+}
+
+inline HRESULT CeeFileGenWriter::setObjSwitch(bool objSwitch) {
+ if((m_objSwitch = objSwitch)) m_dllSwitch = FALSE; return S_OK;
+}
+
+inline bool CeeFileGenWriter::getObjSwitch() {
+ return m_objSwitch;
+}
+
+inline LPWSTR CeeFileGenWriter::getLibraryName() {
+ return m_libraryName;
+}
+
+inline mdMethodDef CeeFileGenWriter::getEntryPoint() {
+ return m_entryPoint;
+}
+
+inline HRESULT CeeFileGenWriter::setEntryPoint(mdMethodDef method) {
+ m_entryPoint = method;
+ return S_OK;
+}
+
+inline HRESULT CeeFileGenWriter::setComImageFlags(DWORD mask) {
+ m_comImageFlags |= mask; return S_OK;
+}
+
+inline HRESULT CeeFileGenWriter::clearComImageFlags(DWORD mask) {
+ m_comImageFlags &= ~mask; return S_OK;
+}
+
+inline DWORD CeeFileGenWriter::getComImageFlags() {
+ return m_comImageFlags;
+}
+
+
+//
+#if defined(_IMAGE_FILE_4K_SECTION_ALIGNMENT_)
+#define IMAGE_NT_OPTIONAL_HDR_SECTION_ALIGNMENT 0x1000
+#else
+#define IMAGE_NT_OPTIONAL_HDR_SECTION_ALIGNMENT 0x2000
+#endif
+
+// The stub is always x86 so we always mark the image as x86
+#define IMAGE_FILE_MACHINE IMAGE_FILE_MACHINE_I386
+
+
+#endif // _CEEFILEGENWRITER_H_
+
diff --git a/src/inc/ceegen.h b/src/inc/ceegen.h
new file mode 100644
index 0000000..a2dfadf
--- /dev/null
+++ b/src/inc/ceegen.h
@@ -0,0 +1,440 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+// ===========================================================================
+// File: CEEGEN.H
+//
+// ===========================================================================
+
+#ifndef _CEEGEN_H_
+#define _CEEGEN_H_
+
+#include "cor.h"
+#include "iceefilegen.h"
+#include "ceegentokenmapper.h"
+
+class CeeSection;
+class CeeSectionString;
+class CCeeGen;
+class PESectionMan;
+class PESection;
+
+typedef DWORD StringRef;
+
+#if 0
+
+ This is a description of the current implementation of these types for generating
+ CLR modules.
+
+ ICeeGen - interface to generate in-memory CLR module.
+
+ CCeeGen - implementation of ICeeGen. Currently it uses both CeeSections
+ as well as PESections (inside PESectionMan), and maintains a
+ 1:1 relation between them. This is ugly.
+
+ CeeFileGenWriter - Provides functionality to write in-memory module to
+ PE format file. Uses PEWriter (m_pSectionMan) for
+ file-writing functionality
+
+ PEWriter - It can generate a PE format file. It also knows to apply
+ pointer relocs when it lays out the PESections.
+
+
+ ICeeFileGen - Interface used by compilers, ngen, etc, to generate
+ a CLR file.
+ Has a bunch of methods to emit signatures, tokens, methods,
+ etc which are not implemented. These are left over from before
+
+ CeeFileGenWriter, PEWriter and ICeeFileGen are implemented in mscorpe.dll.
+ The other types live in mscorwks.dll (src\md\CeeFileGen)
+
+ +----------------------------+
+ | ICeeGen |
+ | |
+ | COM-style version of |
+ | ICeeFileGen. HCEEFILE is |
+ | replaced with "this" |
+ +-------------------------+ | |
+ | CeeSectionImpl | +----------------------------+
+ +-------------------------+ |
+ | | |
+ | | v
+ | v +---------------------------+
+ | +------------+ | CCeeGen |
+ | | | +---------------------------+
+ | | CeeSection | contains | |
+ | | |<-------------| CeeSection* m_sections |
+ | +------------+ | |
+ | /| PESectionMan m_pSectionMan|
+ | / | |
+ | +-----------------+ / +---------------------------+
+ v | PESectionMan |<----+ |
+ +-----------+ | | contains |
+ | PESection | +-----------------+ |
+ | | contains | PESection * | v
+ | |<----------| sectStart, | +------------------------------+
+ +-----------+ | sectCur, | | CeeFileGenWriter |
+ | sectEnd | +------------------------------+
+ +-----------------+ | Does meta-data specific |
+ | | stuff and then dispatches to |
+ | | m_pSectionMan.PEWriter::***()|
+ | | |
+ v +------------------------------+
+ +------------------------+ ^
+ | PEWriter | |wraps
+ +------------------------+ |
+ | Low -level file writer | +----------------------------+
+ | Knows how to do | | ICeeFileGen |
+ | pointer relocs | | |
+ | | | C-style inteface. Deals |
+ +------------------------+ | with HCEEFILE, HCEESECTION |
+ | etc. It is mostly just a |
+ | thin wrapper for a |
+ | CeeFileGenWriter |
+ +----------------------------+
+
+#endif // 0
+
+// ***** CeeSection classes
+
+class CeeSectionImpl {
+ public:
+ virtual unsigned dataLen() = 0;
+ virtual char * getBlock(
+ unsigned len,
+ unsigned align = 1) = 0;
+ virtual HRESULT addSectReloc(
+ unsigned offset,
+ CeeSection & relativeTo,
+ CeeSectionRelocType reloc = srRelocAbsolute,
+ CeeSectionRelocExtra * extra = NULL) = 0;
+ virtual HRESULT addBaseReloc(
+ unsigned offset,
+ CeeSectionRelocType reloc = srRelocHighLow,
+ CeeSectionRelocExtra * extra = NULL) = 0;
+ virtual HRESULT directoryEntry(unsigned num) = 0;
+ virtual unsigned char * name() = 0;
+ virtual char * computePointer(unsigned offset) const = 0;
+ virtual BOOL containsPointer(__in char * ptr) const = 0;
+ virtual unsigned computeOffset(__in char * ptr) const = 0;
+ virtual unsigned getBaseRVA() = 0;
+ virtual void SetInitialGrowth(unsigned growth) = 0;
+};
+
+class CeeSection {
+ // m_ceeFile allows inter-section communication
+ CCeeGen &m_ceeFile;
+
+ // abstract away implementation to allow inheritance from CeeSection
+ CeeSectionImpl &m_impl;
+
+ public:
+ enum RelocFlags {
+ RELOC_NONE = 0,
+
+ // address should be fixed up to be a RVA not a normal address
+ RELOC_RVA = 1
+ };
+
+ CeeSection(CCeeGen &ceeFile, CeeSectionImpl &impl)
+ : m_ceeFile(ceeFile), m_impl(impl) { LIMITED_METHOD_CONTRACT; }
+
+ virtual ~CeeSection() {LIMITED_METHOD_CONTRACT; }
+
+ // bytes in this section at present
+ unsigned dataLen();
+
+ // section base, after linking
+ unsigned getBaseRVA();
+
+ // get a block to write on (use instead of write to avoid copy)
+ char* getBlock(unsigned len, unsigned align=1);
+
+ // Indicates that the DWORD at 'offset' in the current section should
+ // have the base of section 'relativeTo added to it
+ HRESULT addSectReloc(unsigned offset, CeeSection& relativeTo,
+ CeeSectionRelocType = srRelocAbsolute, CeeSectionRelocExtra *extra = 0);
+ // Add a base reloc for the given offset in the current section
+ virtual HRESULT addBaseReloc(unsigned offset, CeeSectionRelocType reloc = srRelocHighLow, CeeSectionRelocExtra *extra = 0);
+
+
+ // this section will be directory entry 'num'
+ HRESULT directoryEntry(unsigned num);
+
+ // return section name
+ unsigned char *name();
+
+ // simulate the base + offset with a more complex data storage
+ char * computePointer(unsigned offset) const;
+ BOOL containsPointer(__in char *ptr) const;
+ unsigned computeOffset(__in char *ptr) const;
+
+ CeeSectionImpl &getImpl();
+ CCeeGen &ceeFile();
+ void SetInitialGrowth(unsigned growth);
+};
+
+// ***** CCeeGen class
+// Only handles in memory stuff
+// Base class for CeeFileGenWriter (which actually generates PEFiles)
+
+class CCeeGen : public ICeeGen, ICeeGenInternal {
+ LONG m_cRefs;
+ BOOL m_encMode;
+ protected:
+ short m_textIdx; // m_sections[] index for the .text section
+ short m_metaIdx; // m_sections[] index for metadata (.text, or .cormeta for obj files)
+ short m_corHdrIdx; // m_sections[] index for the COM+ header (.text0)
+ short m_stringIdx; // m_sections[] index for strings (.text, or .rdata for EnC)
+ short m_ilIdx; // m_sections[] index for IL (.text)
+ bool m_objSwitch;
+
+ CeeGenTokenMapper *m_pTokenMap;
+ BOOLEAN m_fTokenMapSupported; // temporary to support both models
+ IMapToken *m_pRemapHandler;
+
+ CeeSection **m_sections;
+ short m_numSections;
+ short m_allocSections;
+
+ PESectionMan * m_peSectionMan;
+
+ IMAGE_COR20_HEADER *m_corHeader;
+ DWORD m_corHeaderOffset;
+
+ HRESULT allocateCorHeader();
+
+ HRESULT addSection(CeeSection *section, short *sectionIdx);
+
+ HRESULT setEnCMode();
+
+// Init process: Call static CreateNewInstance() , not operator new
+ protected:
+ HRESULT Init();
+ CCeeGen();
+
+ public:
+
+ virtual ~CCeeGen() {}
+
+ static HRESULT CreateNewInstance(CCeeGen* & pCeeFileGen); // call this to instantiate
+
+ virtual HRESULT Cleanup();
+
+ // ICeeGen interfaces
+
+ ULONG STDMETHODCALLTYPE AddRef();
+ ULONG STDMETHODCALLTYPE Release();
+ STDMETHODIMP QueryInterface(
+ REFIID riid,
+ void **ppInterface);
+
+ STDMETHODIMP EmitString (
+ __in LPWSTR lpString, // [IN] String to emit
+ ULONG *RVA);
+
+ STDMETHODIMP GetString (
+ ULONG RVA,
+ __inout LPWSTR *lpString);
+
+ STDMETHODIMP AllocateMethodBuffer (
+ ULONG cchBuffer, // [IN] Length of string to emit
+ UCHAR **lpBuffer, // [OUT] Returned buffer
+ ULONG *RVA);
+
+ STDMETHODIMP GetMethodBuffer (
+ ULONG RVA,
+ UCHAR **lpBuffer);
+
+ STDMETHODIMP GetIMapTokenIface (
+ IUnknown **pIMapToken);
+
+ STDMETHODIMP GenerateCeeFile ();
+
+ STDMETHODIMP GetIlSection (
+ HCEESECTION *section);
+
+ STDMETHODIMP GetStringSection (
+ HCEESECTION *section);
+
+ STDMETHODIMP AddSectionReloc (
+ HCEESECTION section,
+ ULONG offset,
+ HCEESECTION relativeTo,
+ CeeSectionRelocType relocType);
+
+ STDMETHODIMP GetSectionCreate (
+ const char *name,
+ DWORD flags,
+ HCEESECTION *section);
+
+ STDMETHODIMP GetSectionDataLen (
+ HCEESECTION section,
+ ULONG *dataLen);
+
+ STDMETHODIMP GetSectionBlock (
+ HCEESECTION section,
+ ULONG len,
+ ULONG align=1,
+ void **ppBytes=0);
+
+ STDMETHODIMP TruncateSection (
+ HCEESECTION section,
+ ULONG len);
+
+ STDMETHODIMP GenerateCeeMemoryImage (void **ppImage);
+
+ STDMETHODIMP ComputePointer (
+ HCEESECTION section,
+ ULONG RVA, // [IN] RVA for method to return
+ UCHAR **lpBuffer); // [OUT] Returned buffer
+
+
+ STDMETHODIMP AddNotificationHandler(IUnknown *pHandler);
+
+ // Write the metadata in "emitter" to the default metadata section is "section" is 0
+ // If 'section != 0, it will put the data in 'buffer'. This
+ // buffer is assumed to be in 'section' at 'offset' and of size 'buffLen'
+ // (should use GetSaveSize to insure that buffer is big enough
+ virtual HRESULT emitMetaData(IMetaDataEmit *emitter,
+ CeeSection* section=0, DWORD offset=0, BYTE* buffer=0, unsigned buffLen=0);
+ virtual HRESULT getMethodRVA(ULONG codeOffset, ULONG *codeRVA);
+
+ STDMETHODIMP SetInitialGrowth(DWORD growth);
+
+ CeeSection &getTextSection();
+ CeeSection &getMetaSection();
+ CeeSection &getCorHeaderSection();
+ CeeSectionString &getStringSection();
+ CeeSection &getIlSection();
+
+ virtual HRESULT getSectionCreate (const char *name, DWORD flags, CeeSection **section=NULL, short *sectionIdx = NULL);
+
+ PESectionMan* getPESectionMan() {
+ LIMITED_METHOD_CONTRACT;
+ return m_peSectionMan;
+ }
+
+ virtual HRESULT getMapTokenIface(IUnknown **pIMapToken, IMetaDataEmit *emitter=0);
+
+ CeeGenTokenMapper *getTokenMapper() {
+ LIMITED_METHOD_CONTRACT;
+ return m_pTokenMap;
+ }
+
+ virtual HRESULT addNotificationHandler(IUnknown *pHandler);
+
+ //Clone is actually a misnomer here. This method will copy all of the
+ //instance variables and then do a deep copy (as necessary) of the sections.
+ //Section data will be appended onto any information already in the section.
+ //This is done to support the DynamicIL -> PersistedIL transform.
+ virtual HRESULT cloneInstance(CCeeGen *destination);
+
+#ifdef EMIT_FIXUPS
+public:
+ virtual HRESULT addFixup(CeeSection& sectionSource, unsigned offset, CeeSectionRelocType reloc, CeeSection * sectionTarget = NULL, CeeSectionRelocExtra *extra = 0) {
+ LIMITED_METHOD_CONTRACT;
+
+ return(E_NOTIMPL);
+ }
+#endif
+};
+
+// ***** CeeSection inline methods
+
+inline unsigned CeeSection::dataLen() {
+ WRAPPER_NO_CONTRACT;
+ return m_impl.dataLen(); }
+
+inline unsigned CeeSection::getBaseRVA() {
+ WRAPPER_NO_CONTRACT;
+ return m_impl.getBaseRVA(); }
+
+inline char *CeeSection::getBlock(unsigned len, unsigned align) {
+ WRAPPER_NO_CONTRACT;
+ return m_impl.getBlock(len, align); }
+
+inline HRESULT CeeSection::addSectReloc(
+ unsigned offset, CeeSection& relativeTo, CeeSectionRelocType reloc, CeeSectionRelocExtra *extra) {
+ WRAPPER_NO_CONTRACT;
+ return(m_impl.addSectReloc(offset, relativeTo, reloc, extra));
+}
+
+inline HRESULT CeeSection::addBaseReloc(unsigned offset, CeeSectionRelocType reloc, CeeSectionRelocExtra *extra) {
+ WRAPPER_NO_CONTRACT;
+ return(m_impl.addBaseReloc(offset, reloc, extra));
+}
+
+
+inline HRESULT CeeSection::directoryEntry(unsigned num) {
+ WRAPPER_NO_CONTRACT;
+ TESTANDRETURN(num < IMAGE_NUMBEROF_DIRECTORY_ENTRIES, E_INVALIDARG);
+ m_impl.directoryEntry(num);
+ return S_OK;
+}
+
+inline CCeeGen &CeeSection::ceeFile() {
+ LIMITED_METHOD_CONTRACT;
+ return m_ceeFile; }
+
+inline CeeSectionImpl &CeeSection::getImpl() {
+ LIMITED_METHOD_CONTRACT;
+ return m_impl; }
+
+inline unsigned char *CeeSection::name() {
+ WRAPPER_NO_CONTRACT;
+ return m_impl.name();
+}
+
+inline char * CeeSection::computePointer(unsigned offset) const
+{
+ WRAPPER_NO_CONTRACT;
+ return m_impl.computePointer(offset);
+}
+
+inline BOOL CeeSection::containsPointer(__in char *ptr) const
+{
+ WRAPPER_NO_CONTRACT;
+ return m_impl.containsPointer(ptr);
+}
+
+inline unsigned CeeSection::computeOffset(__in char *ptr) const
+{
+ WRAPPER_NO_CONTRACT;
+ return m_impl.computeOffset(ptr);
+}
+
+inline void CeeSection::SetInitialGrowth(unsigned growth)
+{
+ WRAPPER_NO_CONTRACT;
+ m_impl.SetInitialGrowth(growth);
+}
+
+// ***** CCeeGen inline methods
+
+inline CeeSection &CCeeGen::getTextSection() {
+ LIMITED_METHOD_CONTRACT;
+
+ return *m_sections[m_textIdx]; }
+
+inline CeeSection &CCeeGen::getMetaSection() {
+ LIMITED_METHOD_CONTRACT;
+
+ return *m_sections[m_metaIdx]; }
+
+inline CeeSection &CCeeGen::getCorHeaderSection() {
+ LIMITED_METHOD_CONTRACT;
+ _ASSERTE(m_corHdrIdx >= 0);
+ return *m_sections[m_corHdrIdx]; }
+
+inline CeeSectionString &CCeeGen::getStringSection() {
+ LIMITED_METHOD_CONTRACT;
+
+ return *(CeeSectionString*)m_sections[m_stringIdx]; }
+
+inline CeeSection &CCeeGen::getIlSection() {
+ LIMITED_METHOD_CONTRACT;
+
+ return *m_sections[m_ilIdx]; }
+
+#endif
diff --git a/src/inc/ceegentokenmapper.h b/src/inc/ceegentokenmapper.h
new file mode 100644
index 0000000..a2312a0
--- /dev/null
+++ b/src/inc/ceegentokenmapper.h
@@ -0,0 +1,142 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//*****************************************************************************
+// CeeGenTokenMapper.h
+//
+// This helper class tracks mapped tokens from their old value to the new value
+// which can happen when the data is optimized on save.
+//
+//*****************************************************************************
+
+#ifndef __CeeGenTokenMapper_h__
+#define __CeeGenTokenMapper_h__
+
+#include "utilcode.h"
+
+typedef CDynArray<mdToken> TOKENMAP;
+
+#define INDEX_OF_TYPE(type) ((type) >> 24)
+//r#define INDEX_FROM_TYPE(type) case INDEX_OF_TYPE(mdt ## type): return (tkix ## type)
+
+// Define the list of CeeGen tracked tokens
+#define CEEGEN_TRACKED_TOKENS() \
+ CEEGEN_TRACKED_TOKEN(TypeDef) \
+ CEEGEN_TRACKED_TOKEN(InterfaceImpl) \
+ CEEGEN_TRACKED_TOKEN(MethodDef) \
+ CEEGEN_TRACKED_TOKEN(TypeRef) \
+ CEEGEN_TRACKED_TOKEN(MemberRef) \
+ CEEGEN_TRACKED_TOKEN(CustomAttribute) \
+ CEEGEN_TRACKED_TOKEN(FieldDef) \
+ CEEGEN_TRACKED_TOKEN(ParamDef) \
+ CEEGEN_TRACKED_TOKEN(File) \
+ CEEGEN_TRACKED_TOKEN(GenericParam) \
+
+class CCeeGen;
+
+#define CEEGEN_TRACKED_TOKEN(x) tkix ## x,
+
+class CeeGenTokenMapper : public IMapToken
+{
+friend class CCeeGen;
+friend class PESectionMan;
+public:
+ enum
+ {
+ CEEGEN_TRACKED_TOKENS()
+ MAX_TOKENMAP
+ };
+
+ static int IndexForType(mdToken tk);
+
+ CeeGenTokenMapper() : m_pIImport(0), m_cRefs(1), m_pIMapToken(NULL) { LIMITED_METHOD_CONTRACT; }
+ virtual ~CeeGenTokenMapper() {}
+
+//*****************************************************************************
+// IUnknown implementation.
+//*****************************************************************************
+ virtual ULONG __stdcall AddRef()
+ {LIMITED_METHOD_CONTRACT; return ++m_cRefs; }
+
+ virtual ULONG __stdcall Release()
+ {
+ STATIC_CONTRACT_NOTHROW;
+ STATIC_CONTRACT_FORBID_FAULT;
+ SUPPORTS_DAC_HOST_ONLY;
+
+ ULONG cRefs = --m_cRefs;
+ if (cRefs == 0)
+ {
+ if (m_pIMapToken)
+ {
+ m_pIMapToken->Release();
+ m_pIMapToken = NULL;
+ }
+
+ delete this;
+ }
+ return cRefs;
+ }
+
+ virtual HRESULT __stdcall QueryInterface(REFIID iid, PVOID *ppIUnk);
+
+//*****************************************************************************
+// Called by the meta data engine when a token is remapped to a new location.
+// This value is recorded in the m_rgMap array based on type and rid of the
+// from token value.
+//*****************************************************************************
+ virtual HRESULT __stdcall Map(mdToken tkImp, mdToken tkEmit);
+
+//*****************************************************************************
+// Check the given token to see if it has moved to a new location. If so,
+// return true and give back the new token.
+//*****************************************************************************
+ virtual int HasTokenMoved(mdToken tkFrom, mdToken &tkTo);
+
+ int GetMaxMapSize() const
+ { LIMITED_METHOD_CONTRACT; return (MAX_TOKENMAP); }
+
+ IUnknown *GetMapTokenIface() const
+ { LIMITED_METHOD_CONTRACT; return ((IUnknown *) this); }
+
+
+//*****************************************************************************
+// Hand out a copy of the meta data information.
+//*****************************************************************************
+ virtual HRESULT GetMetaData(IMetaDataImport **ppIImport);
+
+//*****************************************************************************
+// Add another token mapper.
+//*****************************************************************************
+ virtual HRESULT AddTokenMapper(IMapToken *pIMapToken)
+ {
+ STATIC_CONTRACT_NOTHROW;
+ STATIC_CONTRACT_FORBID_FAULT;
+
+ // Add the token mapper, if there isn't already one.
+ if (m_pIMapToken == NULL)
+ {
+ m_pIMapToken = pIMapToken;
+ m_pIMapToken->AddRef();
+ return S_OK;
+ }
+ else
+ {
+ _ASSERTE(!"Token mapper already set!");
+ return E_FAIL;
+ }
+ }
+
+protected:
+// m_rgMap is an array indexed by token type. For each type, an array of
+// tokens is kept, indexed by from rid. To see if a token has been moved,
+// do a lookup by type to get the right array, then use the from rid to
+// find the to rid.
+ TOKENMAP m_rgMap[MAX_TOKENMAP];
+ IMetaDataImport *m_pIImport;
+ ULONG m_cRefs; // Ref count.
+ IMapToken *m_pIMapToken;
+
+};
+
+#endif // __CeeGenTokenMapper_h__
diff --git a/src/inc/ceesectionstring.h b/src/inc/ceesectionstring.h
new file mode 100644
index 0000000..06a534a
--- /dev/null
+++ b/src/inc/ceesectionstring.h
@@ -0,0 +1,55 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+// ===========================================================================
+// File: CeeSectionString.h
+//
+// ===========================================================================
+
+#ifndef CeeSectionString_H
+#define CeeSectionString_H
+
+#include <ole2.h>
+#include "ceegen.h"
+
+// This class is responsible for managing all the strings that have
+// been emitted for the PE file.
+
+// This class manages the strings that are added to the .rdata section.
+// It keeps track of each string that has been added using a hashtable.
+// The hash table is effectively 2-dimensional. There is a large "virtual
+// hash space" that is used to get a wide hash code distribution. The
+// virtual hash space is mapped into a real hash table where each n
+// hash values in the virtual space fall into a given hash bucket for
+// real hash table size n. Within the bucket, elements are stored in a linked
+// list in-order. When an virtual hash entry corresponds to a given bucket,
+// that bucket is searched for the matching hash id. If not found, it is
+// inserted, otherwise, the value is returned. The idea is that for smaller
+// apps, there won't be a large number of strings, so that collisions are
+// minimal and the length of each bucket's chain is small. For larger
+// numbers of strings, having a large hash space also reduces numbers
+// of collisions, avoiding string compares unless the hash codes match.
+
+struct StringTableEntry;
+
+class CeeSectionString : public CeeSection {
+ enum { MaxRealEntries = 100, MaxVirtualEntries = 10000 };
+ StringTableEntry *stringTable[MaxRealEntries];
+
+ StringTableEntry *createEntry(__in_z LPWSTR target, ULONG hashId);
+ StringTableEntry *findStringInsert(
+ StringTableEntry *&entry, __in_z LPWSTR targetValue, ULONG hashId);
+ void deleteEntries(StringTableEntry *e);
+#ifdef RDATA_STATS
+ int dumpEntries(StringTableEntry *e);
+ void dumpTable();
+#endif
+
+ public:
+ ~CeeSectionString();
+ CeeSectionString(CCeeGen &ceeFile, CeeSectionImpl &impl);
+ virtual HRESULT getEmittedStringRef(__in_z LPWSTR targetValue, StringRef *ref);
+};
+
+#endif
+
diff --git a/src/inc/cfi.h b/src/inc/cfi.h
new file mode 100644
index 0000000..d5d7784
--- /dev/null
+++ b/src/inc/cfi.h
@@ -0,0 +1,33 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+#ifndef CFI_H_
+#define CFI_H_
+
+#define DWARF_REG_ILLEGAL -1
+enum CFI_OPCODE
+{
+ CFI_ADJUST_CFA_OFFSET, // Offset is adjusted relative to the current one.
+ CFI_DEF_CFA_REGISTER, // New register is used to compute CFA
+ CFI_REL_OFFSET // Register is saved at offset from the current CFA
+};
+
+struct CFI_CODE
+{
+ unsigned char CodeOffset;// Offset from the start of code the frame covers.
+ unsigned char CfiOpCode;
+ short DwarfReg; // Dwarf register number. 0~32 for x64.
+ int Offset;
+ CFI_CODE(unsigned char codeOffset, unsigned char cfiOpcode,
+ short dwarfReg, int offset)
+ : CodeOffset(codeOffset)
+ , CfiOpCode(cfiOpcode)
+ , DwarfReg(dwarfReg)
+ , Offset(offset)
+ {}
+};
+typedef CFI_CODE* PCFI_CODE;
+
+#endif // CFI_H
+
diff --git a/src/inc/check.h b/src/inc/check.h
new file mode 100644
index 0000000..b1fdba9
--- /dev/null
+++ b/src/inc/check.h
@@ -0,0 +1,734 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+// ---------------------------------------------------------------------------
+// Check.h
+//
+
+//
+// Assertion checking infrastructure
+// ---------------------------------------------------------------------------
+
+
+#ifndef CHECK_H_
+#define CHECK_H_
+
+#include "static_assert.h"
+#include "daccess.h"
+
+#ifdef _DEBUG
+
+#ifdef _MSC_VER
+// Make sure we can recurse deep enough for FORCEINLINE
+#pragma inline_recursion(on)
+#pragma inline_depth(16)
+#pragma warning(disable:4714)
+#endif // _MSC_VER
+
+#if !defined(DISABLE_CONTRACTS)
+#define CHECK_INVARIANTS 1
+#define VALIDATE_OBJECTS 1
+#endif
+
+#endif // _DEBUG
+
+#if defined(_DEBUG) && !defined(DACCESS_COMPILE)
+#define _DEBUG_IMPL 1
+#endif
+
+#ifdef _DEBUG
+#define DEBUG_ARG(x) , x
+#else
+#define DEBUG_ARG(x)
+#endif
+
+#define CHECK_STRESS 1
+
+//--------------------------------------------------------------------------------
+// A CHECK is an object which encapsulates a potential assertion
+// failure. It not only contains the result of the check, but if the check fails,
+// also records information about the condition and call site.
+//
+// CHECK also serves as a holder to prevent recursive CHECKS. These can be
+// particularly common when putting preconditions inside predicates, especially
+// routines called by an invariant.
+//
+// Note that using CHECK is perfectly efficient in a free build - the CHECK becomes
+// a simple string constant pointer (typically either NULL or (LPCSTR)1, although some
+// check failures may include messages)
+//
+// NOTE: you should NEVER use the CHECK class API directly - use the macros below.
+//--------------------------------------------------------------------------------
+
+class SString;
+
+class CHECK
+{
+protected:
+ // On retail, this is a pointer to a string literal, null or (LPCSTR)1.
+ // On debug, this is a pointer to dynamically allocated memory - that
+ // lets us have formatted strings in debug builds.
+ LPCSTR m_message;
+
+#ifdef _DEBUG
+ LPCSTR m_condition;
+ LPCSTR m_file;
+ INT m_line;
+ LONG *m_pCount;
+
+ // Keep leakage counters.
+ static size_t s_cLeakedBytes;
+ static size_t s_cNumFailures;
+#endif
+
+ static BOOL s_neverEnforceAsserts;
+
+public: // !!! NOTE: Called from macros only!!!
+
+ // If we are not in a check, return TRUE and PushCheck; otherwise return FALSE
+ BOOL EnterAssert();
+
+ // Pops check count
+ void LeaveAssert();
+
+ // Just return if we are in a check
+ BOOL IsInAssert();
+
+ // Should we skip enforcing asserts
+ static BOOL EnforceAssert();
+
+ static BOOL EnforceAssert_StaticCheckOnly();
+
+ static void ResetAssert();
+
+#ifdef _MSC_VER
+#pragma warning(push)
+#pragma warning(disable:4702) // Disable bogus unreachable code warning
+#endif // _MSC_VER
+ CHECK() : m_message(NULL)
+#ifdef _DEBUG
+ , m_condition (NULL)
+ , m_file(NULL)
+ , m_line(NULL)
+ , m_pCount(NULL)
+#endif
+ {}
+#ifdef _MSC_VER
+#pragma warning(pop)
+#endif // _MSC_VER
+
+ // Fail records the result of a condition check. Can take either a
+ // boolean value or another check result
+ BOOL Fail(BOOL condition);
+ BOOL Fail(const CHECK &check);
+
+ // Setup records context info after a failure.
+ void Setup(LPCSTR message DEBUG_ARG(LPCSTR condition) DEBUG_ARG(LPCSTR file) DEBUG_ARG(INT line));
+ static LPCSTR FormatMessage(LPCSTR messageFormat, ...);
+
+ // Trigger triggers the actual check failure. The trigger may provide a reason
+ // to include in the failure message.
+ void Trigger(LPCSTR reason);
+
+ // Finally, convert to a BOOL to allow just testing the result of a Check function
+ operator BOOL();
+
+ BOOL operator!();
+
+ CHECK &operator()() { return *this; }
+
+ static inline const CHECK OK() {
+ return CHECK();
+ }
+
+ static void SetAssertEnforcement(BOOL value);
+
+ static void ReleaseTls(void* pCountTLS);
+
+ private:
+ static LONG* InitTls();
+#ifdef _DEBUG
+ static LPCSTR AllocateDynamicMessage(const SString &s);
+#endif
+};
+
+
+//--------------------------------------------------------------------------------
+// These CHECK macros are the correct way to propagate an assertion. These
+// routines are designed for use inside "Check" routines. Such routines may
+// be Invariants, Validate routines, or any other assertional predicates.
+//
+// A Check routine should return a value of type CHECK.
+//
+// It should consist of multiple CHECK or CHECK_MSG statements (along with appropritate
+// control flow) and should end with CHECK_OK() if all other checks pass.
+//
+// It may contain a CONTRACT_CHECK contract, but this is only appropriate if the
+// check is used for non-assertional purposes (otherwise the contract will never execute).
+// Note that CONTRACT_CHECK contracts do not support postconditions.
+//
+// CHECK: Check the given condition, return a CHECK failure if FALSE
+// CHECK_MSG: Same, but include a message paramter if the check fails
+// CHECK_OK: Return a successful check value;
+//--------------------------------------------------------------------------------
+
+#ifdef _DEBUG
+#define DEBUG_ONLY_MESSAGE(msg) msg
+#else
+// On retail, we don't want to add a bunch of string literals to the image,
+// so we just use the same one everywhere.
+#define DEBUG_ONLY_MESSAGE(msg) ((LPCSTR)1)
+#endif
+
+#define CHECK_MSG_EX(_condition, _message, _RESULT) \
+do \
+{ \
+ CHECK _check; \
+ if (_check.Fail(_condition)) \
+ { \
+ ENTER_DEBUG_ONLY_CODE; \
+ _check.Setup(DEBUG_ONLY_MESSAGE(_message) \
+ DEBUG_ARG(#_condition) \
+ DEBUG_ARG(__FILE__) \
+ DEBUG_ARG(__LINE__)); \
+ _RESULT(_check); \
+ LEAVE_DEBUG_ONLY_CODE; \
+ } \
+} while (0)
+
+#define RETURN_RESULT(r) return r
+
+#define CHECK_MSG(_condition, _message) \
+ CHECK_MSG_EX(_condition, _message, RETURN_RESULT)
+
+#define CHECK(_condition) \
+ CHECK_MSG(_condition, "")
+
+#define CHECK_MSGF(_condition, _args) \
+ CHECK_MSG(_condition, CHECK::FormatMessage _args)
+
+#define CHECK_FAIL(_message) \
+ CHECK_MSG(FALSE, _message); UNREACHABLE()
+
+#define CHECK_FAILF(_args) \
+ CHECK_MSGF(FALSE, _args); UNREACHABLE()
+
+#define CHECK_OK \
+ return CHECK::OK()
+
+//--------------------------------------------------------------------------------
+// ASSERT_CHECK is the proper way to trigger a check result. If the CHECK
+// has failed, the diagnostic assertion routines will fire with appropriate
+// context information.
+//
+// Note that the condition may either be a raw boolean expression or a CHECK result
+// returned from a Check routine.
+//
+// Recursion note: ASSERT_CHECKs are only performed if there is no current check in
+// progress.
+//--------------------------------------------------------------------------------
+
+#ifndef ENTER_DEBUG_ONLY_CODE
+#define ENTER_DEBUG_ONLY_CODE
+#endif
+
+#ifndef LEAVE_DEBUG_ONLY_CODE
+#define LEAVE_DEBUG_ONLY_CODE
+#endif
+
+#define ASSERT_CHECK(_condition, _message, _reason) \
+do \
+{ \
+ CHECK _check; \
+ if (_check.EnterAssert()) \
+ { \
+ ENTER_DEBUG_ONLY_CODE; \
+ if (_check.Fail(_condition)) \
+ { \
+ _check.Setup(_message \
+ DEBUG_ARG(#_condition) \
+ DEBUG_ARG(__FILE__) \
+ DEBUG_ARG(__LINE__)); \
+ _check.Trigger(_reason); \
+ } \
+ LEAVE_DEBUG_ONLY_CODE; \
+ _check.LeaveAssert(); \
+ } \
+} while (0)
+
+// ex: ASSERT_CHECKF(1+2==4, "my reason", ("Woah %d", 1+3));
+// note that the double parenthesis, the 'args' param below will include one pair of parens.
+#define ASSERT_CHECKF(_condition, _reason, _args) \
+ ASSERT_CHECK(_condition, CHECK::FormatMessage _args, _reason)
+
+//--------------------------------------------------------------------------------
+// INVARIANTS are descriptions of conditions which are always true at well defined
+// points of execution. Invariants may be checked by the caller or callee at any
+// time as paranoia requires.
+//
+// There are really two flavors of invariant. The "public invariant" describes
+// to the caller invariant behavior about the abstraction which is visible from
+// the public API (and of course it should be expressible in that public API).
+//
+// The "internal invariant" (or representation invariant), on the other hand, is
+// a description of the private implementation of the abstraction, which may examine
+// internal state of the abstraction or use private entry points.
+//
+// Classes with invariants should introduce methods called
+// void Invariant();
+// and
+// void InternalInvariant();
+// to allow invariant checks.
+//--------------------------------------------------------------------------------
+
+#if CHECK_INVARIANTS
+
+template <typename TYPENAME>
+CHECK CheckInvariant(TYPENAME &obj)
+{
+ __if_exists(TYPENAME::Invariant)
+ {
+ CHECK(obj.Invariant());
+ }
+ __if_exists(TYPENAME::InternalInvariant)
+ {
+ CHECK(obj.InternalInvariant());
+ }
+
+ CHECK_OK;
+}
+
+#define CHECK_INVARIANT(o) \
+ ASSERT_CHECK(CheckInvariant(o), NULL, "Invariant failure")
+
+#else
+
+#define CHECK_INVARIANT(o) do { } while (0)
+
+#endif
+
+//--------------------------------------------------------------------------------
+// VALIDATE is a check to be made on an object type which identifies a pointer as
+// a valid instance of the object, by calling CheckPointer on it. Normally a null
+// pointer is treated as an error; VALIDATE_NULL (or CheckPointer(o, NULL_OK))
+// may be used when a null pointer is acceptible.
+//
+// In addition to the null/non-null check, a type may provide a specific Check method
+// for more sophisticated identification. In general, the Check method
+// should answer the question
+// "Is this a valid instance of its declared compile-time type?". For instance, if
+// runtype type identification were supported for the type, it should be invoked here.
+//
+// Note that CheckPointer will also check the invariant(s) if appropriate, so the
+// invariants should NOT be explicitly invoked from the Check method.
+//--------------------------------------------------------------------------------
+
+enum IsNullOK
+{
+ NULL_NOT_OK = 0,
+ NULL_OK = 1
+};
+
+#if CHECK_INVARIANTS
+template <typename TYPENAME>
+CHECK CheckPointer(TYPENAME *o, IsNullOK ok = NULL_NOT_OK)
+{
+ if (o == NULL)
+ {
+ CHECK_MSG(ok, "Illegal null pointer");
+ }
+ else
+ {
+ __if_exists(TYPENAME::Check)
+ {
+ CHECK(o->Check());
+ }
+ }
+
+ CHECK_OK;
+}
+
+template <typename TYPENAME>
+CHECK CheckValue(TYPENAME &val)
+{
+ __if_exists(TYPENAME::Check)
+ {
+ CHECK(val.Check());
+ }
+
+ CHECK(CheckInvariant(val));
+
+ CHECK_OK;
+}
+#else // CHECK_INVARIANTS
+
+#ifdef _DEBUG_IMPL
+// Don't defined these functions to be nops for the non-debug
+// build as it may hide important checks
+template <typename TYPENAME>
+CHECK CheckPointer(TYPENAME *o, IsNullOK ok = NULL_NOT_OK)
+{
+ if (o == NULL)
+ {
+ CHECK_MSG(ok, "Illegal null pointer");
+ }
+
+ CHECK_OK;
+}
+
+template <typename TYPENAME>
+CHECK CheckValue(TYPENAME &val)
+{
+ CHECK_OK;
+}
+#endif
+
+#endif // CHECK_INVARIANTS
+
+#if VALIDATE_OBJECTS
+
+#define VALIDATE(o) \
+ ASSERT_CHECK(CheckPointer(o), "Validation failure")
+#define VALIDATE_NULL(o) \
+ ASSERT_CHECK(CheckPointer(o, NULL_OK), "Validation failure")
+
+#else
+
+#define VALIDATE(o) do { } while (0)
+#define VALIDATE_NULL(o) do { } while (0)
+
+#endif
+
+//--------------------------------------------------------------------------------
+// CONSISTENCY_CHECKS are ad-hoc assertions about the expected state of the program
+// at a given time. A failure in one of these indicates a bug in the code.
+//
+// Note that the condition may either be a raw boolean expression or a CHECK result
+// returned from a Check routine.
+//--------------------------------------------------------------------------------
+
+#define CONSISTENCY_CHECK(_condition) \
+ CONSISTENCY_CHECK_MSG(_condition, "")
+
+#ifdef _DEBUG_IMPL
+
+#define CONSISTENCY_CHECK_MSG(_condition, _message) \
+ ASSERT_CHECK(_condition, _message, "Consistency check failed")
+
+#define CONSISTENCY_CHECK_MSGF(_condition, args) \
+ ASSERT_CHECKF(_condition, "Consistency check failed", args)
+
+#else
+
+#define CONSISTENCY_CHECK_MSG(_condition, _message) do { } while (0)
+#define CONSISTENCY_CHECK_MSGF(_condition, args) do { } while (0)
+
+#endif
+
+//--------------------------------------------------------------------------------
+// SIMPLIFYING_ASSUMPTIONS are workarounds which are placed in the code to allow progress
+// to be made in the case of difficult corner cases. These should NOT be left in the
+// code; they are really just markers of things which need to be fixed.
+//
+// Note that the condition may either be a raw boolean expression or a CHECK result
+// returned from a Check routine.
+//--------------------------------------------------------------------------------
+
+// Ex usage:
+// SIMPLIFYING_ASSUMPTION(SomeExpression());
+#define SIMPLIFYING_ASSUMPTION(_condition) \
+ SIMPLIFYING_ASSUMPTION_MSG(_condition, "")
+
+
+// Helper for HRs. Will provide formatted message showing the failure code.
+#define SIMPLIFYING_ASSUMPTION_SUCCEEDED(__hr) \
+ { \
+ HRESULT __hr2 = (__hr); \
+ (void)__hr2; \
+ SIMPLIFYING_ASSUMPTION_MSGF(SUCCEEDED(__hr2), ("HRESULT failed.\n Expected success.\n Actual=0x%x\n", __hr2)); \
+ }
+
+#ifdef _DEBUG_IMPL
+
+// Ex usage:
+// SIMPLIFYING_ASSUMPTION_MSG(SUCCEEDED(hr), "It failed!");
+#define SIMPLIFYING_ASSUMPTION_MSG(_condition, _message) \
+ ASSERT_CHECK(_condition, _message, "Unhandled special case detected")
+
+// use a formatted string. Ex usage:
+// SIMPLIFYING_ASSUMPTION_MSGF(SUCCEEDED(hr), ("Woah it failed! 0x%08x", hr));
+#define SIMPLIFYING_ASSUMPTION_MSGF(_condition, args) \
+ ASSERT_CHECKF(_condition, "Unhandled special case detected", args)
+
+#else // !_DEBUG_IMPL
+
+#define SIMPLIFYING_ASSUMPTION_MSG(_condition, _message) do { } while (0)
+#define SIMPLIFYING_ASSUMPTION_MSGF(_condition, args) do { } while (0)
+
+#endif // !_DEBUG_IMPL
+
+//--------------------------------------------------------------------------------
+// COMPILER_ASSUME_MSG is a statement that tells the compiler to assume the
+// condition is true. In a checked build these turn into asserts;
+// in a free build they are passed through to the compiler to use in optimization.
+//--------------------------------------------------------------------------------
+
+#if defined(_PREFAST_) || defined(_PREFIX_)
+#define COMPILER_ASSUME_MSG(_condition, _message) if (!(_condition)) __UNREACHABLE();
+#define COMPILER_ASSUME_MSGF(_condition, args) if (!(_condition)) __UNREACHABLE();
+#else
+
+#if defined(DACCESS_COMPILE)
+#define COMPILER_ASSUME_MSG(_condition, _message) do { } while (0)
+#define COMPILER_ASSUME_MSGF(_condition, args) do { } while (0)
+#else
+
+#if defined(_DEBUG)
+#define COMPILER_ASSUME_MSG(_condition, _message) \
+ ASSERT_CHECK(_condition, _message, "Compiler optimization assumption invalid")
+#define COMPILER_ASSUME_MSGF(_condition, args) \
+ ASSERT_CHECKF(_condition, "Compiler optimization assumption invalid", args)
+#else
+#define COMPILER_ASSUME_MSG(_condition, _message) __assume(_condition)
+#define COMPILER_ASSUME_MSGF(_condition, args) __assume(_condition)
+#endif // _DEBUG
+
+#endif // DACCESS_COMPILE
+
+#endif // _PREFAST_ || _PREFIX_
+
+
+#define COMPILER_ASSUME(_condition) \
+ COMPILER_ASSUME_MSG(_condition, "")
+
+
+//--------------------------------------------------------------------------------
+// PREFIX_ASSUME_MSG and PREFAST_ASSUME_MSG are just another name
+// for COMPILER_ASSUME_MSG
+// In a checked build these turn into asserts; in a free build
+// they are passed through to the compiler to use in optimization;
+// via an __assume(_condition) optimization hint.
+//--------------------------------------------------------------------------------
+
+#define PREFIX_ASSUME_MSG(_condition, _message) \
+ COMPILER_ASSUME_MSG(_condition, _message)
+
+#define PREFIX_ASSUME_MSGF(_condition, args) \
+ COMPILER_ASSUME_MSGF(_condition, args)
+
+#define PREFIX_ASSUME(_condition) \
+ COMPILER_ASSUME_MSG(_condition, "")
+
+#define PREFAST_ASSUME_MSG(_condition, _message) \
+ COMPILER_ASSUME_MSG(_condition, _message)
+
+#define PREFAST_ASSUME_MSGF(_condition, args) \
+ COMPILER_ASSUME_MSGF(_condition, args)
+
+#define PREFAST_ASSUME(_condition) \
+ COMPILER_ASSUME_MSG(_condition, "")
+
+//--------------------------------------------------------------------------------
+// UNREACHABLE points are locations in the code which should not be able to be
+// reached under any circumstances (e.g. a default in a switch which is supposed to
+// cover all cases.). This macro tells the compiler this, and also embeds a check
+// to make sure it is always true.
+//--------------------------------------------------------------------------------
+
+#define UNREACHABLE() \
+ UNREACHABLE_MSG("")
+
+#ifdef __llvm__
+
+// LLVM complains if a function does not return what it says.
+#define UNREACHABLE_RET() do { UNREACHABLE(); return 0; } while (0)
+#define UNREACHABLE_MSG_RET(_message) UNREACHABLE_MSG(_message); return 0;
+
+#else // __llvm__
+
+#define UNREACHABLE_RET() UNREACHABLE()
+#define UNREACHABLE_MSG_RET(_message) UNREACHABLE_MSG(_message)
+
+#endif // __llvm__ else
+
+#if defined(_MSC_VER) || defined(_PREFIX_)
+#if defined(_TARGET_AMD64_)
+// Empty methods that consist of UNREACHABLE() result in a zero-sized declspec(noreturn) method
+// which causes the pdb file to make the next method declspec(noreturn) as well, thus breaking BBT
+// Remove when we get a VC compiler that fixes VSW 449170
+# define __UNREACHABLE() DebugBreak(); __assume(0);
+#else
+# define __UNREACHABLE() __assume(0)
+#endif
+#else
+#define __UNREACHABLE() do { } while(true)
+#endif
+
+#ifdef _DEBUG_IMPL
+
+// Note that the "do { } while (0)" syntax trick here doesn't work, as the compiler
+// gives an error that the while(0) is unreachable code
+#define UNREACHABLE_MSG(_message) \
+{ \
+ CHECK _check; \
+ _check.Setup(_message, "<unreachable>", __FILE__, __LINE__); \
+ _check.Trigger("Reached the \"unreachable\""); \
+} __UNREACHABLE()
+
+#else
+
+#define UNREACHABLE_MSG(_message) __UNREACHABLE()
+
+#endif
+
+
+//--------------------------------------------------------------------------------
+// STRESS_CHECK represents a check which is included in a free build
+// @todo: behavior on trigger
+//
+// Note that the condition may either be a raw boolean expression or a CHECK result
+// returned from a Check routine.
+//
+// Since Retail builds don't allow formatted checks, there's no STRESS_CHECK_MSGF.
+//--------------------------------------------------------------------------------
+
+#if CHECK_STRESS
+
+#define STRESS_CHECK(_condition, _message) \
+ ASSERT_CHECK(_condition, _message, "Stress Assertion Failure")
+
+#else
+
+#define STRESS_CHECK(_condition, _message) do { } while (0)
+
+#endif
+
+//--------------------------------------------------------------------------------
+// CONTRACT_CHECK is used to put contracts on Check function. Note that it does
+// not support postconditions.
+//--------------------------------------------------------------------------------
+
+#define CONTRACT_CHECK CONTRACTL
+#define CONTRACT_CHECK_END CONTRACTL_END
+
+//--------------------------------------------------------------------------------
+// CCHECK is used for Check functions which may fail due to out of memory
+// or other transient failures. These failures should be ignored when doing
+// assertions, but they cannot be ignored when the Check function is used in
+// normal code.
+// @todo: really crufty to have 2 sets of CHECK macros
+//--------------------------------------------------------------------------------
+
+#ifdef _DEBUG
+
+#define CCHECK_START \
+ { \
+ BOOL ___exception = FALSE; \
+ BOOL ___transient = FALSE; \
+ CHECK ___result = CHECK::OK(); \
+ EX_TRY {
+
+#define CCHECK_END \
+ } EX_CATCH { \
+ if (___result.IsInAssert()) \
+ { \
+ ___exception = TRUE; \
+ ___transient = GET_EXCEPTION()->IsTransient(); \
+ } \
+ else \
+ EX_RETHROW; \
+ } EX_END_CATCH(RethrowTerminalExceptions); \
+ \
+ if (___exception) \
+ { \
+ if (___transient) \
+ CHECK_OK; \
+ else \
+ CHECK_FAIL("Nontransient exception occurred during check"); \
+ } \
+ CHECK(___result); \
+ }
+
+#define CRETURN_RESULT(r) ___result = r
+
+#define CCHECK_MSG(_condition, _message) \
+ CHECK_MSG_EX(_condition, _message, CRETURN_RESULT)
+
+#define CCHECK(_condition) \
+ CCHECK_MSG(_condition, "")
+
+#define CCHECK_MSGF(_condition, _args) \
+ CCHECK_MSG(_condition, CHECK::FormatMessage _args)
+
+#define CCHECK_FAIL(_message) \
+ CCHECK_MSG(FALSE, _message); UNREACHABLE()
+
+#define CCHECK_FAILF(_args) \
+ CCHECK_MSGF(FALSE, _args); UNREACHABLE()
+
+#else // _DEBUG
+
+#define CCHECK_START
+#define CCHECK_END
+
+#define CCHECK CHECK
+#define CCHECK_MSG CHECK_MSG
+#define CCHECK_MSGF CHECK_MSGF
+#define CCHECK_FAIL CHECK_FAIL
+#define CCHECK_FAILF CHECK_FAILF
+
+#endif
+
+
+
+//--------------------------------------------------------------------------------
+// Common base level checks
+//--------------------------------------------------------------------------------
+
+CHECK CheckAlignment(UINT alignment);
+
+CHECK CheckAligned(UINT value, UINT alignment);
+#if defined(_MSC_VER)
+CHECK CheckAligned(ULONG value, UINT alignment);
+#endif
+CHECK CheckAligned(UINT64 value, UINT alignment);
+CHECK CheckAligned(const void *address, UINT alignment);
+
+CHECK CheckOverflow(UINT value1, UINT value2);
+#if defined(_MSC_VER)
+CHECK CheckOverflow(ULONG value1, ULONG value2);
+#endif
+CHECK CheckOverflow(UINT64 value1, UINT64 value2);
+CHECK CheckOverflow(PTR_CVOID address, UINT offset);
+#if defined(_MSC_VER)
+CHECK CheckOverflow(const void *address, ULONG offset);
+#endif
+CHECK CheckOverflow(const void *address, UINT64 offset);
+
+CHECK CheckUnderflow(UINT value1, UINT value2);
+#if defined(_MSC_VER)
+CHECK CheckUnderflow(ULONG value1, ULONG value2);
+#endif
+CHECK CheckUnderflow(UINT64 value1, UINT64 value2);
+CHECK CheckUnderflow(const void *address, UINT offset);
+#if defined(_MSC_VER)
+CHECK CheckUnderflow(const void *address, ULONG offset);
+#endif
+CHECK CheckUnderflow(const void *address, UINT64 offset);
+CHECK CheckUnderflow(const void *address, void *address2);
+
+CHECK CheckZeroedMemory(const void *memory, SIZE_T size);
+
+// These include overflow checks
+CHECK CheckBounds(const void *rangeBase, UINT32 rangeSize, UINT32 offset);
+CHECK CheckBounds(const void *rangeBase, UINT32 rangeSize, UINT32 offset, UINT32 size);
+
+void WINAPI ReleaseCheckTls(LPVOID pTlsData);
+
+// ================================================================================
+// Inline definitions
+// ================================================================================
+
+#include "check.inl"
+
+#endif // CHECK_H_
diff --git a/src/inc/check.inl b/src/inc/check.inl
new file mode 100644
index 0000000..9a3597e
--- /dev/null
+++ b/src/inc/check.inl
@@ -0,0 +1,367 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+#ifndef CHECK_INL_
+#define CHECK_INL_
+
+#include "check.h"
+#include "clrhost.h"
+#include "debugmacros.h"
+#include "clrtypes.h"
+
+inline LONG *CHECK::InitTls()
+{
+#pragma push_macro("HeapAlloc")
+#pragma push_macro("GetProcessHeap")
+#undef HeapAlloc
+#undef GetProcessHeap
+
+ LONG *pCount = (LONG *)::HeapAlloc(GetProcessHeap(), 0, sizeof(LONG));
+ if (pCount)
+ *pCount = 0;
+
+#pragma pop_macro("HeapAlloc")
+#pragma pop_macro("GetProcessHeap")
+ ClrFlsSetValue(TlsIdx_Check, pCount);
+ ClrFlsAssociateCallback(TlsIdx_Check, ReleaseCheckTls);
+ return pCount;
+}
+
+inline void CHECK::ReleaseTls(void* pCountTLS)
+{
+#pragma push_macro("HeapFree")
+#pragma push_macro("GetProcessHeap")
+#undef HeapFree
+#undef GetProcessHeap
+ LONG* pCount = (LONG*) pCountTLS;
+ if (pCount)
+ ::HeapFree(GetProcessHeap(), 0, pCount);
+
+#pragma pop_macro("HeapFree")
+#pragma pop_macro("GetProcessHeap")
+}
+
+FORCEINLINE BOOL CHECK::EnterAssert()
+{
+ if (s_neverEnforceAsserts)
+ return FALSE;
+
+#ifdef _DEBUG_IMPL
+ m_pCount = (LONG *)ClrFlsGetValue(TlsIdx_Check);
+ if (!m_pCount)
+ {
+ m_pCount = InitTls();
+ if (!m_pCount)
+ return FALSE;
+ }
+
+ if (!*m_pCount)
+ {
+ *m_pCount = 1;
+ return TRUE;
+ }
+ else
+ return FALSE;
+#else
+ // Don't bother doing recursive checks on a free build, since checks should
+ // be extremely isolated
+ return TRUE;
+#endif
+}
+
+FORCEINLINE void CHECK::LeaveAssert()
+{
+#ifdef _DEBUG_IMPL
+ *m_pCount = 0;
+#endif
+}
+
+FORCEINLINE BOOL CHECK::IsInAssert()
+{
+#ifdef _DEBUG_IMPL
+ if (!m_pCount)
+ m_pCount = (LONG *)ClrFlsGetValue(TlsIdx_Check);
+
+ if (!m_pCount)
+ return FALSE;
+ else
+ return *m_pCount;
+#else
+ return FALSE;
+#endif
+}
+
+FORCEINLINE BOOL CHECK::EnforceAssert()
+{
+ if (s_neverEnforceAsserts)
+ return FALSE;
+ else
+ {
+ CHECK chk;
+ return !chk.IsInAssert();
+ }
+}
+
+FORCEINLINE void CHECK::ResetAssert()
+{
+ CHECK chk;
+ if (chk.IsInAssert())
+ chk.LeaveAssert();
+}
+
+inline void CHECK::SetAssertEnforcement(BOOL value)
+{
+ s_neverEnforceAsserts = !value;
+}
+
+// Fail records the result of a condition check. Can take either a
+// boolean value or another check result
+FORCEINLINE BOOL CHECK::Fail(BOOL condition)
+{
+#ifdef _DEBUG
+ if (!condition)
+ {
+ m_condition = NULL;
+ m_file = NULL;
+ m_line = 0;
+ }
+#endif
+ return !condition;
+}
+
+FORCEINLINE BOOL CHECK::Fail(const CHECK &check)
+{
+ m_message = check.m_message;
+#ifdef _DEBUG
+ if (m_message != NULL)
+ {
+ m_condition = check.m_condition;
+ m_file = check.m_file;
+ m_line = check.m_line;
+ }
+#endif
+ return m_message != NULL;
+}
+
+#ifndef _DEBUG
+FORCEINLINE void CHECK::Setup(LPCSTR message)
+{
+ m_message = message;
+}
+
+FORCEINLINE LPCSTR CHECK::FormatMessage(LPCSTR messageFormat, ...)
+{
+ return messageFormat;
+}
+#endif
+
+FORCEINLINE CHECK::operator BOOL ()
+{
+ return m_message == NULL;
+}
+
+FORCEINLINE BOOL CHECK::operator!()
+{
+ return m_message != NULL;
+}
+
+inline CHECK CheckAlignment(UINT alignment)
+{
+ STATIC_CONTRACT_WRAPPER;
+ CHECK((alignment & (alignment-1)) == 0);
+ CHECK_OK;
+}
+
+inline CHECK CheckAligned(UINT value, UINT alignment)
+{
+ STATIC_CONTRACT_WRAPPER;
+ CHECK(AlignmentTrim(value, alignment) == 0);
+ CHECK_OK;
+}
+
+#ifndef PLATFORM_UNIX
+// For Unix this and the previous function get the same types.
+// So, exclude this one.
+inline CHECK CheckAligned(ULONG value, UINT alignment)
+{
+ STATIC_CONTRACT_WRAPPER;
+ CHECK(AlignmentTrim(value, alignment) == 0);
+ CHECK_OK;
+}
+#endif // PLATFORM_UNIX
+
+inline CHECK CheckAligned(UINT64 value, UINT alignment)
+{
+ STATIC_CONTRACT_WRAPPER;
+ CHECK(AlignmentTrim(value, alignment) == 0);
+ CHECK_OK;
+}
+
+inline CHECK CheckAligned(const void *address, UINT alignment)
+{
+ STATIC_CONTRACT_WRAPPER;
+ CHECK(AlignmentTrim((SIZE_T)address, alignment) == 0);
+ CHECK_OK;
+}
+
+inline CHECK CheckOverflow(UINT value1, UINT value2)
+{
+ CHECK(value1 + value2 >= value1);
+ CHECK_OK;
+}
+
+#if defined(_MSC_VER)
+inline CHECK CheckOverflow(ULONG value1, ULONG value2)
+{
+ CHECK(value1 + value2 >= value1);
+ CHECK_OK;
+}
+#endif
+
+inline CHECK CheckOverflow(UINT64 value1, UINT64 value2)
+{
+ CHECK(value1 + value2 >= value1);
+ CHECK_OK;
+}
+
+inline CHECK CheckOverflow(PTR_CVOID address, UINT offset)
+{
+ TADDR targetAddr = dac_cast<TADDR>(address);
+#if POINTER_BITS == 32
+ CHECK((UINT) (SIZE_T)(targetAddr) + offset >= (UINT) (SIZE_T) (targetAddr));
+#else
+ CHECK((UINT64) targetAddr + offset >= (UINT64) targetAddr);
+#endif
+
+ CHECK_OK;
+}
+
+#if defined(_MSC_VER)
+inline CHECK CheckOverflow(const void *address, ULONG offset)
+{
+#if POINTER_BITS == 32
+ CHECK((ULONG) (SIZE_T) address + offset >= (ULONG) (SIZE_T) address);
+#else
+ CHECK((UINT64) address + offset >= (UINT64) address);
+#endif
+
+ CHECK_OK;
+}
+#endif
+
+inline CHECK CheckOverflow(const void *address, UINT64 offset)
+{
+#if POINTER_BITS == 32
+ CHECK(offset >> 32 == 0);
+ CHECK((UINT) (SIZE_T) address + (UINT) offset >= (UINT) (SIZE_T) address);
+#else
+ CHECK((UINT64) address + offset >= (UINT64) address);
+#endif
+
+ CHECK_OK;
+}
+
+
+inline CHECK CheckUnderflow(UINT value1, UINT value2)
+{
+ CHECK(value1 - value2 <= value1);
+
+ CHECK_OK;
+}
+
+#ifndef PLATFORM_UNIX
+// For Unix this and the previous function get the same types.
+// So, exclude this one.
+inline CHECK CheckUnderflow(ULONG value1, ULONG value2)
+{
+ CHECK(value1 - value2 <= value1);
+
+ CHECK_OK;
+}
+#endif // PLATFORM_UNIX
+
+inline CHECK CheckUnderflow(UINT64 value1, UINT64 value2)
+{
+ CHECK(value1 - value2 <= value1);
+
+ CHECK_OK;
+}
+
+inline CHECK CheckUnderflow(const void *address, UINT offset)
+{
+#if POINTER_BITS == 32
+ CHECK((UINT) (SIZE_T) address - offset <= (UINT) (SIZE_T) address);
+#else
+ CHECK((UINT64) address - offset <= (UINT64) address);
+#endif
+
+ CHECK_OK;
+}
+
+#if defined(_MSC_VER)
+inline CHECK CheckUnderflow(const void *address, ULONG offset)
+{
+#if POINTER_BITS == 32
+ CHECK((ULONG) (SIZE_T) address - offset <= (ULONG) (SIZE_T) address);
+#else
+ CHECK((UINT64) address - offset <= (UINT64) address);
+#endif
+
+ CHECK_OK;
+}
+#endif
+
+inline CHECK CheckUnderflow(const void *address, UINT64 offset)
+{
+#if POINTER_BITS == 32
+ CHECK(offset >> 32 == 0);
+ CHECK((UINT) (SIZE_T) address - (UINT) offset <= (UINT) (SIZE_T) address);
+#else
+ CHECK((UINT64) address - offset <= (UINT64) address);
+#endif
+
+ CHECK_OK;
+}
+
+inline CHECK CheckUnderflow(const void *address, void *address2)
+{
+#if POINTER_BITS == 32
+ CHECK((UINT) (SIZE_T) address - (UINT) (SIZE_T) address2 <= (UINT) (SIZE_T) address);
+#else
+ CHECK((UINT64) address - (UINT64) address2 <= (UINT64) address);
+#endif
+
+ CHECK_OK;
+}
+
+inline CHECK CheckZeroedMemory(const void *memory, SIZE_T size)
+{
+ CHECK(CheckOverflow(memory, size));
+
+ BYTE *p = (BYTE *) memory;
+ BYTE *pEnd = p + size;
+
+ while (p < pEnd)
+ CHECK(*p++ == 0);
+
+ CHECK_OK;
+}
+
+inline CHECK CheckBounds(const void *rangeBase, UINT32 rangeSize, UINT32 offset)
+{
+ CHECK(CheckOverflow(dac_cast<PTR_CVOID>(rangeBase), rangeSize));
+ CHECK(offset <= rangeSize);
+ CHECK_OK;
+}
+
+inline CHECK CheckBounds(const void *rangeBase, UINT32 rangeSize, UINT32 offset, UINT32 size)
+{
+ CHECK(CheckOverflow(dac_cast<PTR_CVOID>(rangeBase), rangeSize));
+ CHECK(CheckOverflow(offset, size));
+ CHECK(offset + size <= rangeSize);
+ CHECK_OK;
+}
+
+#endif // CHECK_INL_
+
diff --git a/src/inc/circularlog.h b/src/inc/circularlog.h
new file mode 100644
index 0000000..4ee8d2f
--- /dev/null
+++ b/src/inc/circularlog.h
@@ -0,0 +1,38 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+
+#ifndef _CIRCULARLOG_H__
+
+#define _CIRCULARLOG_H__
+
+#include "sstring.h"
+
+class CircularLog
+{
+public:
+ CircularLog();
+ ~CircularLog();
+
+ bool Init(const WCHAR* logname, const WCHAR* logHeader, DWORD maxSize = 1024*1024);
+ void Shutdown();
+ void Log(const WCHAR* string);
+
+protected:
+
+ void CheckForLogReset(BOOL fOverflow);
+ BOOL CheckLogHeader();
+ HANDLE OpenFile();
+ void CloseFile();
+
+ bool m_bInit;
+ SString m_LogFilename;
+ SString m_LogHeader;
+ SString m_OldLogFilename;
+ SString m_LockFilename;
+ DWORD m_MaxSize;
+ unsigned m_uLogCount;
+};
+
+#endif
diff --git a/src/inc/clr/fs.h b/src/inc/clr/fs.h
new file mode 100644
index 0000000..d6bcb75
--- /dev/null
+++ b/src/inc/clr/fs.h
@@ -0,0 +1,16 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+//
+// This header will include all headers relating to file system functionality.
+
+#ifndef _clr_fs_h_
+#define _clr_fs_h_
+
+#include "fs/path.h"
+#include "fs/file.h"
+#include "fs/dir.h"
+
+#endif // _clr_fs_h_
diff --git a/src/inc/clr/fs/dir.h b/src/inc/clr/fs/dir.h
new file mode 100644
index 0000000..2516151
--- /dev/null
+++ b/src/inc/clr/fs/dir.h
@@ -0,0 +1,129 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+//
+// This header provides general directory-related file system services.
+
+#ifndef _clr_fs_Dir_h_
+#define _clr_fs_Dir_h_
+
+#include "clrtypes.h"
+#include "clr/str.h"
+#include "strsafe.h"
+
+#ifndef countof
+ #define countof(x) (sizeof(x) / sizeof(x[0]))
+#endif // !countof
+
+namespace clr
+{
+ namespace fs
+ {
+ class Dir
+ {
+ public:
+ static inline bool Exists(
+ LPCWSTR wzDirPath)
+ {
+ DWORD attrs = WszGetFileAttributes(wzDirPath);
+ return (attrs != INVALID_FILE_ATTRIBUTES) && (attrs & FILE_ATTRIBUTE_DIRECTORY);
+ }
+
+ //-----------------------------------------------------------------------------------------
+ // Creates new directory indicated by wzDirPath.
+ //
+ // Returns:
+ // S_OK - on success directory creation
+ // S_FALSE - when directory previously existed
+ // HR(ERROR_PATH_NOT_FOUND) - when creation of dir fails.
+ static inline HRESULT Create(
+ LPCWSTR wzDirPath)
+ {
+ HRESULT hr = S_OK;
+
+ if (!WszCreateDirectory(wzDirPath, nullptr))
+ {
+ hr = HRESULT_FROM_GetLastError();
+ if (hr == HRESULT_FROM_WIN32(ERROR_ALREADY_EXISTS))
+ {
+ hr = S_FALSE;
+ }
+ }
+ return hr;
+ }
+
+ //-----------------------------------------------------------------------------------------
+ // Creates the specified directory and all required subdirectories. wzDirPath will be
+ // temporarily modified in the process.
+ //
+ // Returns:
+ // S_OK - on success directory creation
+ // S_FALSE - when directory previously existed
+ // HR(ERROR_PATH_NOT_FOUND) - when creation of any dir fails.
+ static inline HRESULT CreateRecursively(
+ __inout_z LPWSTR wzDirPath,
+ size_t cchDirPath = 0)
+ {
+ HRESULT hr = S_OK;
+
+ if (wzDirPath == nullptr)
+ {
+ return E_POINTER;
+ }
+
+ if (cchDirPath == 0)
+ {
+ cchDirPath = wcslen(wzDirPath);
+ }
+
+ // Try to create the path. If it fails, assume that's because the parent folder does
+ // not exist. Try to create the parent then re-attempt.
+ WCHAR chOrig = wzDirPath[cchDirPath];
+ hr = Create(wzDirPath);
+ if (hr == HRESULT_FROM_WIN32(ERROR_PATH_NOT_FOUND))
+ {
+ for (WCHAR* pCurCh = wzDirPath + cchDirPath - 1; pCurCh != wzDirPath; --pCurCh)
+ {
+ if (*pCurCh == W('\\') || *pCurCh == W('\0'))
+ {
+ WCHAR chOrig = *pCurCh;
+ *pCurCh = W('\0');
+ IfFailRet(CreateRecursively(wzDirPath, pCurCh - wzDirPath));
+ *pCurCh = chOrig;
+ break;
+ }
+ }
+ IfFailRet(Create(wzDirPath));
+ }
+
+ return hr;
+ }
+
+ //-----------------------------------------------------------------------------------------
+ // Creates the specified directory and all required subdirectories.
+ static inline HRESULT CreateRecursively(
+ LPCWSTR wzDirPath)
+ {
+ HRESULT hr = S_OK;
+
+ if (wzDirPath == nullptr)
+ {
+ return E_POINTER;
+ }
+
+ // Make a writable copy of wzDirPath
+ size_t cchDirPath = wcslen(wzDirPath);
+ CQuickWSTR wzBuffer;
+ IfFailRet(wzBuffer.ReSizeNoThrow(cchDirPath + 1));
+ wcscpy_s(wzBuffer.Ptr(), wzBuffer.Size(), wzDirPath);
+ IfFailRet(CreateRecursively(wzBuffer.Ptr(), cchDirPath));
+
+ return hr;
+ }
+ };
+ }
+}
+
+#endif // _clr_fs_Dir_h_
diff --git a/src/inc/clr/fs/file.h b/src/inc/clr/fs/file.h
new file mode 100644
index 0000000..70f22a2
--- /dev/null
+++ b/src/inc/clr/fs/file.h
@@ -0,0 +1,40 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+//
+// This header provides general filename-related file system services.
+
+#ifndef _clr_fs_File_h_
+#define _clr_fs_File_h_
+
+#include "clrtypes.h"
+#include "cor.h" // SELECTANY
+
+namespace clr
+{
+ namespace fs
+ {
+ // This list taken from ndp/clr/src/bcl/system/io/path.cs
+ SELECTANY WCHAR const g_rgInvalidFileNameChars[] =
+ { W('"'), W('<'), W('>'), W('|'), W('\0'), (WCHAR)1, (WCHAR)2, (WCHAR)3, (WCHAR)4, (WCHAR)5, (WCHAR)6,
+ (WCHAR)7, (WCHAR)8, (WCHAR)9, (WCHAR)10, (WCHAR)11, (WCHAR)12, (WCHAR)13, (WCHAR)14,
+ (WCHAR)15, (WCHAR)16, (WCHAR)17, (WCHAR)18, (WCHAR)19, (WCHAR)20, (WCHAR)21, (WCHAR)22,
+ (WCHAR)23, (WCHAR)24, (WCHAR)25, (WCHAR)26, (WCHAR)27, (WCHAR)28, (WCHAR)29, (WCHAR)30,
+ (WCHAR)31, W(':'), W('*'), W('?'), W('\\'), W('/') };
+
+ class File
+ {
+ public:
+ static inline bool Exists(
+ LPCWSTR wzFilePath)
+ {
+ DWORD attrs = WszGetFileAttributes(wzFilePath);
+ return (attrs != INVALID_FILE_ATTRIBUTES) && !(attrs & FILE_ATTRIBUTE_DIRECTORY);
+ }
+ };
+ }
+}
+
+#endif // _clr_fs_File_h_
diff --git a/src/inc/clr/fs/path.h b/src/inc/clr/fs/path.h
new file mode 100644
index 0000000..7c1995e
--- /dev/null
+++ b/src/inc/clr/fs/path.h
@@ -0,0 +1,141 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+//
+// This header provides general path-related file system services.
+
+#ifndef _clr_fs_Path_h_
+#define _clr_fs_Path_h_
+
+#include "clrtypes.h"
+#include "cor.h" // SELECTANY
+
+#include "strsafe.h"
+
+#include "clr/str.h"
+
+#ifndef LONG_FORMAT_PATH_PREFIX
+ #define LONG_FORMAT_PATH_PREFIX W("\\\\?\\")
+#endif
+
+namespace clr
+{
+ namespace fs
+ {
+ // This list taken from ndp/clr/src/bcl/system/io/path.cs
+ SELECTANY WCHAR const g_rgInvalidPathChars[] =
+ { W('"'), W('<'), W('>'), W('|'), W('\0'), (WCHAR)1, (WCHAR)2, (WCHAR)3, (WCHAR)4, (WCHAR)5, (WCHAR)6,
+ (WCHAR)7, (WCHAR)8, (WCHAR)9, (WCHAR)10, (WCHAR)11, (WCHAR)12, (WCHAR)13, (WCHAR)14,
+ (WCHAR)15, (WCHAR)16, (WCHAR)17, (WCHAR)18, (WCHAR)19, (WCHAR)20, (WCHAR)21, (WCHAR)22,
+ (WCHAR)23, (WCHAR)24, (WCHAR)25, (WCHAR)26, (WCHAR)27, (WCHAR)28, (WCHAR)29, (WCHAR)30,
+ (WCHAR)31 };
+
+ class Path
+ {
+ public:
+ //-----------------------------------------------------------------------------------------
+ static inline bool
+ Exists(
+ LPCWSTR wzPath)
+ {
+ DWORD attrs = WszGetFileAttributes(wzPath);
+ return (attrs != INVALID_FILE_ATTRIBUTES);
+ }
+
+ //-----------------------------------------------------------------------------------------
+ // Returns true if wzPath represents a long format path (i.e., prefixed with '\\?\').
+ static inline bool
+ HasLongFormatPrefix(LPCWSTR wzPath)
+ {
+ _ASSERTE(!clr::str::IsNullOrEmpty(wzPath)); // Must check this first.
+ return wcscmp(wzPath, LONG_FORMAT_PATH_PREFIX) == 0;
+ }
+
+ //-----------------------------------------------------------------------------------------
+ // Returns true if wzPath represents a relative path.
+ static inline bool
+ IsRelative(LPCWSTR wzPath)
+ {
+ _ASSERTE(wzPath != nullptr);
+
+ // Similar to System.IO.Path.IsRelative()
+#if PLATFORM_UNIX
+ if(wzPath[0] == VOLUME_SEPARATOR_CHAR_W)
+ {
+ return false;
+ }
+#else
+ // Check for a paths like "C:\..." or "\\...". Additional notes:
+ // - "\\?\..." - long format paths are considered as absolute paths due to the "\\" prefix
+ // - "\..." - these paths are relative, as they depend on the current drive
+ // - "C:..." and not "C:\..." - these paths are relative, as they depend on the current directory for drive C
+ if (wzPath[0] != W('\0') &&
+ wzPath[1] == VOLUME_SEPARATOR_CHAR_W &&
+ wzPath[2] == DIRECTORY_SEPARATOR_CHAR_W &&
+ (
+ (wzPath[0] >= W('A') && wzPath[0] <= W('Z')) ||
+ (wzPath[0] >= W('a') && wzPath[0] <= W('z'))
+ ))
+ {
+ return false;
+ }
+ if (wzPath[0] == DIRECTORY_SEPARATOR_CHAR_W && wzPath[1] == DIRECTORY_SEPARATOR_CHAR_W)
+ {
+ return false;
+ }
+#endif
+
+ return true;
+ }
+
+ //-----------------------------------------------------------------------------------------
+ // Combines two path parts. wzPathLeft must be a directory path and may be either absolute
+ // or relative. wzPathRight may be a directory or file path and must be relative. The
+ // result is placed in wzBuffer and the number of chars written is placed in pcchBuffer on
+ // success; otherwise an error HRESULT is returned.
+ static HRESULT
+ Combine(LPCWSTR wzPathLeft, LPCWSTR wzPathRight, __in DWORD *pcchBuffer, __out_ecount(*pcchBuffer) LPWSTR wzBuffer)
+ {
+ STATIC_CONTRACT_NOTHROW;
+
+ HRESULT hr = S_OK;
+
+ if (clr::str::IsNullOrEmpty(wzPathLeft) || clr::str::IsNullOrEmpty(wzPathRight) || pcchBuffer == nullptr)
+ return E_INVALIDARG;
+
+ LPWSTR wzBuf = wzBuffer;
+ size_t cchBuf = *pcchBuffer;
+
+ IfFailRet(StringCchCopyExW(wzBuf, cchBuf, wzPathLeft, &wzBuf, &cchBuf, STRSAFE_NULL_ON_FAILURE));
+ IfFailRet(StringCchCatExW(wzBuf, cchBuf, wzBuf[-1] == DIRECTORY_SEPARATOR_CHAR_W ? W("") : DIRECTORY_SEPARATOR_STR_W, &wzBuf, &cchBuf, STRSAFE_NULL_ON_FAILURE));
+ IfFailRet(StringCchCatExW(wzBuf, cchBuf, wzPathRight, &wzBuf, &cchBuf, STRSAFE_NULL_ON_FAILURE));
+
+ return S_OK;
+ }
+
+ //-----------------------------------------------------------------------------------------
+ // Checks if the path provided is valid within the specified constraints.
+ // ***NOTE: does not yet check for invalid path characters.
+ static bool
+ IsValid(LPCWSTR wzPath, DWORD cchPath, bool fAllowLongFormat)
+ {
+ if (clr::str::IsNullOrEmpty(wzPath))
+ return false;
+
+ bool fIsLongFormat = HasLongFormatPrefix(wzPath);
+
+ if (fIsLongFormat && !fAllowLongFormat)
+ return false;
+
+ if (!fIsLongFormat && cchPath > _MAX_PATH)
+ return false;
+
+ return true;
+ }
+ };
+ }
+}
+
+#endif // _clr_fs_Path_h_
diff --git a/src/inc/clr/stack.h b/src/inc/clr/stack.h
new file mode 100644
index 0000000..f9741b2
--- /dev/null
+++ b/src/inc/clr/stack.h
@@ -0,0 +1,99 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+//
+// This header provides a basic stack implementation
+
+#ifndef _clr_Stack_h_
+#define _clr_Stack_h_
+
+namespace clr
+{
+ //-------------------------------------------------------------------------------------------------
+ // A basic stack class.
+ //
+ template < typename T >
+ class Stack
+ {
+ private:
+ //---------------------------------------------------------------------------------------------
+ struct Link
+ {
+ template < typename A1 >
+ Link(A1 && a1, Link * next = nullptr)
+ : _value(std::forward<A1>(a1))
+ , _next(next)
+ {}
+
+ T _value;
+ Link * _next;
+ };
+
+ public:
+ //---------------------------------------------------------------------------------------------
+ // Empty stack constructor.
+ Stack()
+ : _top(nullptr)
+ , _size(0)
+ {}
+
+ //---------------------------------------------------------------------------------------------
+ // Move constructor.
+ Stack(Stack && stack)
+ : _top(nullptr)
+ , _size(0)
+ { *this = std::move(stack); }
+
+ //---------------------------------------------------------------------------------------------
+ ~Stack()
+ {
+ while (!empty())
+ {
+ pop();
+ }
+ }
+
+ //---------------------------------------------------------------------------------------------
+ // Move assignment.
+ Stack& operator=(Stack && stack)
+ { std::swap(_top, stack._top); std::swap(_size, stack._size); }
+
+ //---------------------------------------------------------------------------------------------
+ bool empty() const
+ { return _top == nullptr; }
+
+ //---------------------------------------------------------------------------------------------
+ size_t size() const
+ { return _size; }
+
+ //---------------------------------------------------------------------------------------------
+ T & top()
+ { return _top->_value; }
+
+ //---------------------------------------------------------------------------------------------
+ T const & top() const
+ { return _top->_value; }
+
+ //---------------------------------------------------------------------------------------------
+ template < typename A1 > inline
+ void push(A1 && value)
+ {
+ STATIC_CONTRACT_THROWS;
+ _top = new Link(std::forward<A1>(value), _top);
+ ++_size;
+ }
+
+ //---------------------------------------------------------------------------------------------
+ void pop()
+ { Link * del = _top; _top = _top->_next; --_size; delete del; }
+
+ private:
+ //---------------------------------------------------------------------------------------------
+ Link * _top;
+ size_t _size;
+ };
+} // namespace clr
+
+#endif // _clr_Stack_h_
diff --git a/src/inc/clr/str.h b/src/inc/clr/str.h
new file mode 100644
index 0000000..94c8ed4
--- /dev/null
+++ b/src/inc/clr/str.h
@@ -0,0 +1,28 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+
+//
+// This header provides general standard string services.
+//
+
+#ifndef _clr_str_h_
+#define _clr_str_h_
+
+namespace clr
+{
+ namespace str
+ {
+ //-----------------------------------------------------------------------------------------
+ // Returns true if the provided string is a null pointer or the empty string.
+ static inline bool
+ IsNullOrEmpty(LPCWSTR wzStr)
+ {
+ return wzStr == nullptr || *wzStr == W('\0');
+ }
+ }
+}
+
+#endif // _clr_str_h_
+
diff --git a/src/inc/clr/win32.h b/src/inc/clr/win32.h
new file mode 100644
index 0000000..a0e00c6
--- /dev/null
+++ b/src/inc/clr/win32.h
@@ -0,0 +1,38 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+//
+// clr/win32.h
+//
+// Provides Win32-specific utility functionality.
+//
+
+//
+
+#ifndef clr_win32_h
+#define clr_win32_h
+
+#include "winwrap.h"
+
+namespace clr
+{
+ namespace win32
+ {
+ // Prevents an HMODULE from being unloaded until process termination.
+ inline
+ HRESULT PreventModuleUnload(HMODULE hMod)
+ {
+ if (!WszGetModuleHandleEx(
+ GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | GET_MODULE_HANDLE_EX_FLAG_PIN,
+ reinterpret_cast<LPCTSTR>(hMod),
+ &hMod))
+ {
+ return HRESULT_FROM_GetLastError();
+ }
+
+ return S_OK;
+ }
+ } // namespace win
+} // namespace clr
+
+#endif // clr_win32_h
diff --git a/src/inc/clr_std/algorithm b/src/inc/clr_std/algorithm
new file mode 100644
index 0000000..92b4e8e
--- /dev/null
+++ b/src/inc/clr_std/algorithm
@@ -0,0 +1,119 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+//
+// clr_std/algorithm
+//
+// Copy of some key Standard Template Library functionality
+
+#ifdef _MSC_VER
+#pragma once
+#endif
+
+#ifdef USE_STL
+#include <algorithm>
+#else
+#ifndef __clr_std_algorithm_h__
+#define __clr_std_algorithm_h__
+
+namespace std
+{
+ template<class iter, class CompareFunc>
+ iter find_if ( iter first, iter last, CompareFunc comp )
+ {
+ for ( ; first!=last ; first++ )
+ if ( comp(*first) )
+ break;
+ return first;
+ }
+
+ template<class iter, class T>
+ iter find(iter first, iter last, const T& val)
+ {
+ for (;first != last; first++)
+ {
+ if (*first == val)
+ break;
+ }
+ return first;
+ }
+
+ template <class iter, class comp>
+ iter qsort_partition( iter first, iter last, iter pivot, comp compare )
+ {
+ iter lastMinusOne = last - 1;
+ swap(pivot, lastMinusOne);
+
+ // Pivot is at end
+ pivot = last - 1;
+
+ iter partitionLoc = first;
+
+ for (iter partitionWalk = first; partitionWalk != pivot; ++partitionWalk)
+ {
+ if (compare(*partitionWalk, *pivot))
+ {
+ swap(*partitionWalk, *partitionLoc);
+ partitionLoc++;
+ }
+ }
+ swap(*pivot, *partitionLoc);
+
+ return partitionL