/// <summary> /// Gets a string field from the object. Note that the type must match exactly, as this method /// will not do type coercion. This method will throw an ArgumentException if no field matches /// the given name. It will throw an InvalidOperationException if the field is not /// of the correct type. Lastly, it will throw a MemoryReadException if there was an error reading /// the value of this field out of the data target. /// </summary> /// <param name="fieldName">The name of the field to get the value for.</param> /// <returns>The value of the given field or null if this object points to a null value.</returns> public string GetStringOrNull(string fieldName) { if (IsNull) { return(null); } ulong address = GetFieldAddress(fieldName, ClrElementType.String, "string"); ulong str; RuntimeBase runtime = (RuntimeBase)_type.Heap.Runtime; if (!runtime.ReadPointer(address, out str)) { throw new MemoryReadException(address); } string result; if (!runtime.ReadString(str, out result)) { throw new MemoryReadException(str); } return(result); }
internal HeapSegment(RuntimeBase clr, ISegmentData segment, SubHeap subHeap, bool large, HeapBase heap) { _clr = clr; _large = large; _segment = segment; _heap = heap; _subHeap = subHeap; }
public CorDebugValue(RuntimeBase runtime, ICorDebug.ICorDebugValue value) : base(runtime) { _value = value; ICorDebug.CorElementType el; value.GetType(out el); _elementType = (ClrElementType)el; }
internal static int GetTlsSlotForThread(RuntimeBase runtime, ulong teb) { const int maxTlsSlot = 64; const int tlsSlotOffset = 0x1480; // Same on x86 and amd64 const int tlsExpansionSlotsOffset = 0x1780; uint ptrSize = (uint)runtime.PointerSize; ulong lowerTlsSlots = teb + tlsSlotOffset; uint clrTlsSlot = runtime.GetTlsSlot(); if (clrTlsSlot == uint.MaxValue) { return(0); } ulong tlsSlot = 0; if (clrTlsSlot < maxTlsSlot) { tlsSlot = lowerTlsSlots + ptrSize * clrTlsSlot; } else { if (!runtime.ReadPointer(teb + tlsExpansionSlotsOffset, out tlsSlot) || tlsSlot == 0) { return(0); } tlsSlot += ptrSize * (clrTlsSlot - maxTlsSlot); } ulong clrTls = 0; if (!runtime.ReadPointer(tlsSlot, out clrTls)) { return(0); } // Get thread data; uint tlsThreadTypeIndex = runtime.GetThreadTypeIndex(); if (tlsThreadTypeIndex == uint.MaxValue) { return(0); } ulong threadType = 0; if (!runtime.ReadPointer(clrTls + ptrSize * tlsThreadTypeIndex, out threadType)) { return(0); } return((int)threadType); }
public HeapBase(RuntimeBase runtime) { _canWalkHeap = runtime.CanWalkHeap; if (runtime.DataReader.CanReadAsync) { MemoryReader = new AsyncMemoryReader(runtime.DataReader, 0x10000); } else { MemoryReader = new MemoryReader(runtime.DataReader, 0x10000); } _pointerSize = runtime.PointerSize; }
protected void InitSegments(RuntimeBase runtime) { // Populate segments SubHeap[] heaps; if (runtime.GetHeaps(out heaps)) { var segments = new List <HeapSegment>(); foreach (var heap in heaps) { if (heap != null) { ISegmentData seg = runtime.GetSegmentData(heap.FirstLargeSegment); while (seg != null) { var segment = new HeapSegment(runtime, seg, heap, true, this); segments.Add(segment); UpdateSegmentData(segment); seg = runtime.GetSegmentData(seg.Next); } seg = runtime.GetSegmentData(heap.FirstSegment); while (seg != null) { var segment = new HeapSegment(runtime, seg, heap, false, this); segments.Add(segment); UpdateSegmentData(segment); seg = runtime.GetSegmentData(seg.Next); } } } UpdateSegments(segments.ToArray()); } else { _segments = new ClrSegment[0]; } }
private int _lastSegmentIdx; // The last segment we looked at. public HeapBase(RuntimeBase runtime) { CanWalkHeap = runtime.CanWalkHeap; MemoryReader = new MemoryReader(runtime.DataReader, 0x10000); PointerSize = runtime.PointerSize; }
internal ClrValue(RuntimeBase runtime) { _runtime = runtime; }
internal ClrValue(ClrRuntime runtime) { _runtime = (RuntimeBase)runtime; }