private void EnsureInitialized([NotNull] ClrRuntime runtime) { if (initialized) { return; } try { ClrHeap heap = runtime.GetHeap(); enumeratedTypes = new List <ClrType>(); foreach (string typename in EnumeratedTypesNames) { if (string.IsNullOrEmpty(typename)) { continue; } ClrType tmp = heap.GetTypeByName(typename); if (tmp == null) { Trace.TraceWarning("{0} type was not found in runtime.", typename); continue; } enumeratedTypes.Add(tmp); } } finally { initialized = true; } }
public void ArrayReferenceEnumeration() { using (DataTarget dt = TestTargets.Types.LoadFullDump()) { ClrRuntime runtime = dt.ClrVersions.Single().CreateRuntime(); ClrHeap heap = runtime.Heap; ClrAppDomain domain = runtime.AppDomains.Single(); ClrModule typesModule = runtime.GetModule("types.exe"); ClrType type = heap.GetTypeByName("Types"); ulong s_array = (ulong)type.GetStaticFieldByName("s_array").GetValue(domain); ulong s_one = (ulong)type.GetStaticFieldByName("s_one").GetValue(domain); ulong s_two = (ulong)type.GetStaticFieldByName("s_two").GetValue(domain); ulong s_three = (ulong)type.GetStaticFieldByName("s_three").GetValue(domain); ClrType arrayType = heap.GetObjectType(s_array); List <ulong> objs = new List <ulong>(); arrayType.EnumerateRefsOfObject(s_array, (obj, offs) => objs.Add(obj)); // We do not guarantee the order in which these are enumerated. Assert.Equal(3, objs.Count); Assert.Contains(s_one, objs); Assert.Contains(s_two, objs); Assert.Contains(s_three, objs); } }
public void ArrayOffsetsTest() { using (DataTarget dt = TestTargets.Types.LoadFullDump()) { ClrRuntime runtime = dt.ClrVersions.Single().CreateRuntime(); ClrHeap heap = runtime.Heap; ClrAppDomain domain = runtime.AppDomains.Single(); ClrModule typesModule = runtime.GetModule("types.exe"); ClrType type = heap.GetTypeByName("Types"); ulong s_array = (ulong)type.GetStaticFieldByName("s_array").GetValue(domain); ulong s_one = (ulong)type.GetStaticFieldByName("s_one").GetValue(domain); ulong s_two = (ulong)type.GetStaticFieldByName("s_two").GetValue(domain); ulong s_three = (ulong)type.GetStaticFieldByName("s_three").GetValue(domain); ulong[] expected = new ulong[] { s_one, s_two, s_three }; ClrType arrayType = heap.GetObjectType(s_array); for (int i = 0; i < expected.Length; i++) { Assert.Equal(expected[i], (ulong)arrayType.GetArrayElementValue(s_array, i)); ulong address = arrayType.GetArrayElementAddress(s_array, i); ulong value = dt.DataReader.ReadPointerUnsafe(address); Assert.NotEqual(0ul, address); Assert.Equal(expected[i], value); } } }
private Dictionary <int, string> GetManagedThreadNames(ClrHeap heap) { var result = new Dictionary <int, string>(); if (!heap.CanWalkHeap) { return(result); } var threadObjects = from obj in heap.EnumerateObjectAddresses() let type = heap.GetObjectType(obj) where type != null && type.Name == "System.Threading.Thread" select obj; var threadType = heap.GetTypeByName("System.Threading.Thread"); var nameField = threadType.GetFieldByName("m_Name"); var managedIdField = threadType.GetFieldByName("m_ManagedThreadId"); foreach (var threadObject in threadObjects) { string name = (string)nameField.GetValue(threadObject); int id = (int)managedIdField.GetValue(threadObject); result.Add(id, name); } return(result); }
private DepPropertiesProvider(ulong objAddress, ClrHeap heap) { _targetObject = heap.GetInstance(objAddress); _effectiveValues = _targetObject.AsDynamic._effectiveValues; _depPropertyType = heap.GetTypeByName(DependencyPropertyTypeName); }
public StaticField(ClrRuntime runtime, string typee, string name) { Domain = runtime.AppDomains.First(); ClrHeap heap = runtime.GetHeap(); ClrType type = heap.GetTypeByName(typee); Field = type.GetStaticFieldByName(name); Heap = runtime.GetHeap(); }
private void InitSearchedType(ClrHeap heap) { this._searchedType = heap.GetTypeByName(this.searchedTypeName); Assert.Required(_searchedType, $"{searchedTypeName} was not found by name in the heap"); this._typeIndex = this._searchedType.MetadataToken; searchedTypeSet = true; }
private ClrObject FindFirstInstanceOfType(ClrHeap heap, string typeName) { var type = heap.GetTypeByName(typeName); if (type is null) { throw new InvalidOperationException($"Could not find {typeName} in {TestTarget.Source} source."); } return(new ClrObject(heap.GetObjectsOfType(typeName).First(), type)); }
public void ArrayLengthTest() { using (DataTarget dt = TestTargets.Types.LoadFullDump()) { ClrRuntime runtime = dt.ClrVersions.Single().CreateRuntime(); ClrHeap heap = runtime.Heap; ClrAppDomain domain = runtime.AppDomains.Single(); ClrModule typesModule = runtime.GetModule("types.exe"); ClrType type = heap.GetTypeByName("Types"); ulong s_array = (ulong)type.GetStaticFieldByName("s_array").GetValue(domain); ClrType arrayType = heap.GetObjectType(s_array); Assert.Equal(3, arrayType.GetArrayLength(s_array)); } }
/// <summary> /// Gets the static field value. /// <para> WARN - resolves value for single domain only.</para> /// </summary> /// <param name="runtime">The runtime.</param> /// <param name="typeName">Name of the type.</param> /// <param name="fieldName">Name of the field.</param> /// <returns></returns> /// <exception cref="ClrTypeNotFound"></exception> public static ClrObject GetStaticFldValue(this ClrRuntime runtime, [NotNull] string typeName, [NotNull] string fieldName) { Assert.ArgumentNotNullOrEmpty(typeName, "typeName"); Assert.ArgumentNotNullOrEmpty(fieldName, "fieldName"); ClrHeap heap = runtime.GetHeap(); Assert.ResultNotNull(heap, "Could not fetch heap from runtime"); ClrType type = heap.GetTypeByName(typeName); if (type == null) { throw new ClrTypeNotFound(typeName); } return(runtime.GetStaticFldValue(type, fieldName)); }
public ClrDriver(ClrRuntime runtime) { (this.runtime, heap, domain) = (runtime, runtime.Heap, runtime.AppDomains[0]); typeObject = heap.GetTypeByName("System.Object"); typeDelegate = heap.GetTypeByName("System.Delegate"); fieldDelegateTarget = typeDelegate.GetFieldByName("_target"); typeTask = heap.GetTypeByName("System.Threading.Tasks.Task"); if (typeTask.BaseType.Name == "System.Threading.Tasks.Task") { typeTask = typeTask.BaseType; } fieldTaskAction = typeTask.GetFieldByName("m_action"); fieldTaskScheduler = typeTask.GetFieldByName("m_taskScheduler"); fieldTaskContinuationObject = typeTask.GetFieldByName("m_continuationObject"); typeDelayPromise = heap.GetTypeByName("System.Threading.Tasks.Task+DelayPromise"); typeQueueUserWorkItemCallback = heap.GetTypeByName("System.Threading.QueueUserWorkItemCallback"); fieldCallback = typeQueueUserWorkItemCallback.GetFieldByName("callback"); typeWaitCallback = heap.GetTypeByName("System.Threading.WaitCallback"); }
public IEnumerable <ValuePointer> AllValuesOfType(params string[] typeNames) { return(AllValuesOfType(from tn in typeNames select Heap.GetTypeByName(tn))); }
private Dictionary<int, string> GetManagedThreadNames(ClrHeap heap) { var result = new Dictionary<int, string>(); if (!heap.CanWalkHeap) return result; var threadObjects = from obj in heap.EnumerateObjectAddresses() let type = heap.GetObjectType(obj) where type != null && type.Name == "System.Threading.Thread" select obj; var threadType = heap.GetTypeByName("System.Threading.Thread"); var nameField = threadType.GetFieldByName("m_Name"); var managedIdField = threadType.GetFieldByName("m_ManagedThreadId"); foreach (var threadObject in threadObjects) { string name = (string)nameField.GetValue(threadObject); int id = (int)managedIdField.GetValue(threadObject); result.Add(id, name); } return result; }
/// <summary> /// Looks up a type by name. /// </summary> /// <param name="name">The name of the type.</param> /// <returns> /// The ClrType matching 'name', null if the type was not found, and undefined if more than one /// type shares the same name. /// </returns> /// <inheritdoc /> public IClrType GetTypeByName(string name) => Converter.Convert(Heap.GetTypeByName(name));
// Sample based on https://github.com/Microsoft/dotnetsamples/blob/master/Microsoft.Diagnostics.Runtime/CLRMD/docs/MachineCode.md // All the common code was copied from the MemStats project "dotnetsamples-master\Microsoft.Diagnostics.Runtime\CLRMD\MemStats\Program.cs" static void Main(string[] args) { string dump, dac; if (!TryParseArgs(args, out dump, out dac)) { Usage(); Environment.Exit(1); } try { // Create a ClrRuntime instance from the dump and dac location. The ClrRuntime // object represents a version of CLR loaded in the process. It contains data // such as the managed threads in the process, the AppDomains in the process, // the managed heap, and so on. //ClrRuntime runtime = CreateRuntime(dump, dac); // 1. Get the ClrType object for the type the method is on // 2. Get the ClrMethod object for the method // 3. Get the offset of the native code // 4. Compute the end address by mapping the IL instruction to addresses // 5. Disassemble the native code contained in that range (not provided by CLRMD) using (DataTarget dt = DataTarget.LoadCrashDump(dump)) { // Boilerplate. //ClrRuntime runtime = dt.CreateRuntime(dt.ClrVersions.Single().TryDownloadDac()); var version = dt.ClrVersions.Single(); //{v4.0.30319.18444} //version.Version = new VersionInfo { Major = 4, Minor = 0, Patch = 30319, Revision = 18444 }; Console.WriteLine("CLR Version: {0} ({1}), Dac: {2}", version.Version, version.Flavor, version.DacInfo); var dacFileName = version.TryDownloadDac(); Console.WriteLine("DacFile: " + Path.GetFileName(dacFileName)); Console.WriteLine("DacPath: " + Path.GetDirectoryName(dacFileName)); ClrRuntime runtime = dt.CreateRuntime(dacFileName); ClrHeap heap = runtime.GetHeap(); PrintDiagnosticInfo(dt, runtime, heap); Console.WriteLine(); // Note heap.GetTypeByName doesn't always get you the type, even if it exists, due to // limitations in the dac private apis that ClrMD is written on. If you have the ClrType // already via other means (heap walking, stack walking, etc), then that's better than // using GetTypeByName: var classNameWithNamespace = "JITterOptimisations.Program"; ClrType @class = heap.GetTypeByName(classNameWithNamespace); // Get the method you are looking for. var signature = "JITterOptimisations.Program.Log(System.ConsoleColor, System.String)"; ClrMethod @method = @class.Methods.Single(m => m.GetFullSignature() == signature); // This is the first instruction of the JIT'ed (or NGEN'ed) machine code. ulong startAddress = @method.NativeCode; // Unfortunately there's not a great way to get the size of the code, or the end address. // This is partly due to the fact that we don't *have* to put all the JIT'ed code into one // contiguous chunk, though I think an implementation detail is that we actually do. // You are supposed to do code flow analysis like "uf" in windbg to find the size, but // in practice you can use the IL to native mapping: ulong endAddress = @method.ILOffsetMap.Select(entry => entry.EndAddress).Max(); var lines = File.ReadAllLines( @"C:\Users\warma11\Documents\Visual Studio 2013\Projects\JITterOptimisations\JITterOptimisations\Program.cs"); PrintILToNativeOffsetAlternative(method, lines); // This doesn't seem to work as expected, using alternative method (above) //PrintILToNativeOffsets(method, startAddress, lines); // So the assembly code for the function is is in the range [startAddress, endAddress] inclusive. var count = (int)endAddress + runtime.PointerSize - (int)startAddress; Console.WriteLine("\nCode startAddress 0x{0:X} -> endAddress 0x{1:X} (inclusive), will read {2} bytes", startAddress, endAddress, count); var bytes = new byte[count]; int bytesRead; runtime.ReadMemory(startAddress, bytes, count, out bytesRead); if (count != bytesRead) { Console.WriteLine("Expected to read {0} bytes, but only read {1}\n", count, bytesRead); } else { Console.WriteLine("Read read {0} bytes, as expected\n", bytesRead); } var fileName = string.Format("result-{0}bit.bin", runtime.PointerSize == 8 ? 64 : 32); if (File.Exists(fileName)) { File.Delete(fileName); } File.WriteAllBytes(fileName, bytes); var filename = @"C:\Users\warma11\Downloads\__GitHub__\dotnetsamples\Microsoft.Diagnostics.Runtime\CLRMD\MachineCode\nasm-2.11.05-win32\ndisasm.exe"; var currentFolder = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location); var arguments = "-b32 " + Path.Combine(currentFolder, fileName); // +" -o " + startAddress; var disassembly = Disassembler.GetDisassembly(filename, arguments, timeoutMsecs: 250); var assemblyData = Disassembler.ProcessDisassembly(disassembly); } } catch (Exception ex) { Console.WriteLine("Unhandled exception:"); Console.WriteLine(ex); } }