private string PrintArray(int indentLevel, CorArrayValue av, int expandDepth, bool canDoFunceval) { Debug.Assert(expandDepth >= 0); StringBuilder txt = new StringBuilder(); txt.Append("array ["); int[] dims = av.GetDimensions(); Debug.Assert(dims != null); for (int i = 0; i < dims.Length; ++i) { if (i != 0) { txt.Append(","); } txt.Append(dims[i]); } txt.Append("]"); if (expandDepth > 0 && av.Rank == 1 && av.ElementType != CorElementType.ELEMENT_TYPE_VOID) { for (int i = 0; i < dims[0]; i++) { MDbgValue v = new MDbgValue(Process, av.GetElementAtPosition(i)); txt.Append("\n").Append(IndentedString(indentLevel + 1, "[" + i + "] = ")). Append(IndentedBlock(indentLevel + 2, v.GetStringValue(expandDepth - 1, canDoFunceval))); } } return(txt.ToString()); }
/// <summary> /// Gets the Array Item for the specified indexes /// </summary> /// <param name="indexes">Which indexes to get the Array Item for.</param> /// <returns>The Value for the given indexes.</returns> public MDbgValue GetArrayItem(params int[] indexes) { if (!IsArrayType) { throw new MDbgValueException("Type is not array type"); } CorValue value = Dereference(CorValue, null); CorArrayValue av = value.CastToArrayValue(); Debug.Assert(av != null); if (av.Rank != indexes.Length) { throw new MDbgValueException("Invalid number of dimensions."); } StringBuilder sb = new StringBuilder("["); for (int i = 0; i < indexes.Length; ++i) { if (i != 0) { sb.Append(","); } sb.Append(indexes[i]); } sb.Append("]"); MDbgValue v = new MDbgValue(Process, sb.ToString(), av.GetElement(indexes)); return(v); }
/// <summary> Returns an element of an array (treats the array as zero-based and single dimensional) </summary> public Value GetElementAtPosition(int index) { try { return(new Value(this.AppDomain, CorArrayValue.GetElementAtPosition((uint)index))); } catch (ArgumentException) { throw new GetValueException("Invalid array index"); } }
/// <summary> Returns an element of an array </summary> public Value GetArrayElement(uint[] indices) { try { return(new Value(this.AppDomain, CorArrayValue.GetElement(indices))); } catch (ArgumentException) { throw new GetValueException("Invalid array index"); } }
public object GetElement(int[] indices) { return(new CorValRef(delegate { // If we have a zombie state array, reload it. if (!obj.IsValid) { obj.Reload(); array = CorObjectAdaptor.GetRealObject(ctx, obj) as CorArrayValue; } return array != null ? array.GetElement(indices) : null; })); }
// May be called later ICorDebugValue GetCorValueOfArrayElement(int[] indices) { if (indices.Length != ArrayRank) { throw new GetValueException("Given indicies do not have the same dimension as array."); } if (!this.ArrayDimensions.IsIndexValid(indices)) { throw new GetValueException("Given indices are out of range of the array"); } return(CorArrayValue.GetElement(indices)); }
public int[] GetDimensions() { CorArrayValue array = CorObjectAdaptor.GetRealObject(ctx, obj) as CorArrayValue; if (array != null) { return(array.GetDimensions()); } else { return(new int[0]); } }
public ObjectValue CreateElementValue(ArrayElementGroup grp, ObjectPath path, int[] indices) { CorArrayValue array = CorObjectAdaptor.GetRealObject(ctx, obj) as CorArrayValue; if (array != null) { CorValRef elem = (CorValRef)GetElement(indices); return(ctx.Adapter.CreateObjectValue(ctx, grp, path, elem, ObjectValueFlags.ArrayElement)); } else { return(ObjectValue.CreateUnknown("?")); } }
public object GetElement(int[] indices) { return(new CorValRef(delegate { CorArrayValue array = CorObjectAdaptor.GetRealObject(ctx, obj) as CorArrayValue; if (array != null) { return array.GetElement(indices); } else { return null; } })); }
CorValRef Box(CorEvaluationContext ctx, CorValRef val) { CorValRef arr = new CorValRef(delegate { return(ctx.Session.NewArray(ctx, (CorType)GetValueType(ctx, val), 1)); }); CorArrayValue array = CorObjectAdaptor.GetRealObject(ctx, arr) as CorArrayValue; ArrayAdaptor realArr = new ArrayAdaptor(ctx, arr, array); realArr.SetElement(new int[] { 0 }, val); CorType at = (CorType)GetType(ctx, "System.Array"); object[] argTypes = new object[] { GetType(ctx, "System.Int32") }; return((CorValRef)RuntimeInvoke(ctx, at, arr, "GetValue", argTypes, new object[] { CreateValue(ctx, 0) })); }
// May be called later ICorDebugValue GetCorValueOfArrayElement(uint[] indices) { if (!IsArray) { throw new CannotGetValueException("The value is not an array"); } if (indices.Length != ArrayRank) { throw new CannotGetValueException("Given indicies do not have the same dimension as array."); } for (int i = 0; i < indices.Length; i++) { if (indices[i] > ArrayDimensions[i]) { throw new CannotGetValueException("Given indices are out of range of the array"); } } return(CorArrayValue.GetElement(indices)); }
public override object TargetObjectToObject(EvaluationContext ctx, object objr) { CorValue obj = GetRealObject(ctx, objr); if ((obj is CorReferenceValue) && ((CorReferenceValue)obj).IsNull) { return(new EvaluationResult("(null)")); } CorStringValue stringVal = obj as CorStringValue; if (stringVal != null) { return(stringVal.String); } CorArrayValue arr = obj as CorArrayValue; if (arr != null) { return(base.TargetObjectToObject(ctx, objr)); } CorEvaluationContext cctx = (CorEvaluationContext)ctx; CorObjectValue co = obj as CorObjectValue; if (co != null) { return(base.TargetObjectToObject(ctx, objr)); } CorGenericValue genVal = obj as CorGenericValue; if (genVal != null) { return(genVal.GetValue()); } return(base.TargetObjectToObject(ctx, objr)); }
/// <summary> /// Gets Array Items. This function can be called only on one dimensional arrays. /// </summary> /// <returns>An array of the values for the Array Items.</returns> public MDbgValue[] GetArrayItems() { if (!IsArrayType) { throw new MDbgValueException("Type is not array type"); } CorValue value = Dereference(CorValue, null); CorArrayValue av = value.CastToArrayValue(); int[] dims = av.GetDimensions(); Debug.Assert(dims != null); ArrayList al = new ArrayList(); Debug.Assert(av.Rank == 1); for (int i = 0; i < dims[0]; i++) { MDbgValue v = new MDbgValue(Process, "[" + i + "]", av.GetElementAtPosition(i)); al.Add(v); } return((MDbgValue[])al.ToArray(typeof(MDbgValue))); }
public ArrayAdaptor(EvaluationContext ctx, CorValRef obj, CorArrayValue array) { this.ctx = (CorEvaluationContext)ctx; this.array = array; this.obj = obj; }
public static CorValue GetRealObject(EvaluationContext ctx, CorValue obj) { CorEvaluationContext cctx = (CorEvaluationContext)ctx; if (obj == null) { return(null); } try { if (obj is CorStringValue) { return(obj); } if (obj is CorGenericValue) { return(obj); } if (obj is CorGenericValue) { return(obj); } if (obj is CorArrayValue) { return(obj); } CorArrayValue arrayVal = obj.CastToArrayValue(); if (arrayVal != null) { return(arrayVal); } CorReferenceValue refVal = obj.CastToReferenceValue(); if (refVal != null) { if (refVal.IsNull) { return(refVal); } else { cctx.Session.WaitUntilStopped(); return(GetRealObject(cctx, refVal.Dereference())); } } cctx.Session.WaitUntilStopped(); CorBoxValue boxVal = obj.CastToBoxValue(); if (boxVal != null) { return(Unbox(ctx, boxVal)); } if (obj.ExactType.Type == CorElementType.ELEMENT_TYPE_STRING) { return(obj.CastToStringValue()); } if (CorMetadataImport.CoreTypes.ContainsKey(obj.Type)) { CorGenericValue genVal = obj.CastToGenericValue(); if (genVal != null) { return(genVal); } } if (!(obj is CorObjectValue)) { return(obj.CastToObjectValue()); } } catch { // Ignore throw; } return(obj); }
public override string CallToString(EvaluationContext ctx, object objr) { CorValue obj = GetRealObject(ctx, objr); if ((obj is CorReferenceValue) && ((CorReferenceValue)obj).IsNull) { return(string.Empty); } CorStringValue stringVal = obj as CorStringValue; if (stringVal != null) { return(stringVal.String); } CorArrayValue arr = obj as CorArrayValue; if (arr != null) { StringBuilder tn = new StringBuilder(GetDisplayTypeName(ctx, arr.ExactType.FirstTypeParameter)); tn.Append("["); int[] dims = arr.GetDimensions(); for (int n = 0; n < dims.Length; n++) { if (n > 0) { tn.Append(','); } tn.Append(dims[n]); } tn.Append("]"); return(tn.ToString()); } CorEvaluationContext cctx = (CorEvaluationContext)ctx; CorObjectValue co = obj as CorObjectValue; if (co != null) { if (IsEnum(ctx, co.ExactType)) { MetadataType rt = co.ExactType.GetTypeInfo(cctx.Session) as MetadataType; bool isFlags = rt != null && rt.ReallyIsFlagsEnum; string enumName = GetTypeName(ctx, co.ExactType); ValueReference val = GetMember(ctx, null, objr, "value__"); ulong nval = (ulong)System.Convert.ChangeType(val.ObjectValue, typeof(ulong)); ulong remainingFlags = nval; string flags = null; foreach (ValueReference evals in GetMembers(ctx, co.ExactType, null, BindingFlags.Public | BindingFlags.Static)) { ulong nev = (ulong)System.Convert.ChangeType(evals.ObjectValue, typeof(ulong)); if (nval == nev) { return(evals.Name); } if (isFlags && nev != 0 && (nval & nev) == nev) { if (flags == null) { flags = enumName + "." + evals.Name; } else { flags += " | " + enumName + "." + evals.Name; } remainingFlags &= ~nev; } } if (isFlags) { if (remainingFlags == nval) { return(nval.ToString()); } if (remainingFlags != 0) { flags += " | " + remainingFlags; } return(flags); } else { return(nval.ToString()); } } CorType targetType = (CorType)GetValueType(ctx, objr); MethodInfo met = OverloadResolve(cctx, "ToString", targetType, new CorType[0], BindingFlags.Public | BindingFlags.Instance, false); if (met != null && met.DeclaringType.FullName != "System.Object") { object[] args = new object[0]; object ores = RuntimeInvoke(ctx, targetType, objr, "ToString", args, args); CorStringValue res = GetRealObject(ctx, ores) as CorStringValue; if (res != null) { return(res.String); } } return(GetDisplayTypeName(ctx, targetType)); } CorGenericValue genVal = obj as CorGenericValue; if (genVal != null) { return(genVal.GetValue().ToString()); } return(base.CallToString(ctx, obj)); }
private string PrintArray(int indentLevel, CorArrayValue av, int expandDepth, bool canDoFunceval, string variableName, Dictionary <string, int> variablesToLog) { Debug.Assert(expandDepth >= 0); if (variablesToLog == null) { } else if (variablesToLog.Any(variable => variable.Key.StartsWith($@"{variableName}."))) { variablesToLog = variablesToLog .Where(variable => variable.Key.StartsWith($@"{variableName}.")) .ToDictionary(variable => variable.Key, variable => variable.Value); expandDepth = 1; } else if (variablesToLog.Any(variable => variable.Key == variableName)) { var thisVariable = variablesToLog.First(variable => variable.Key == variableName); expandDepth = thisVariable.Value; variablesToLog = null; } else { return("[SKIP]"); } StringBuilder txt = new StringBuilder(); txt.Append("array ["); int[] dims = av.GetDimensions(); Debug.Assert(dims != null); for (int i = 0; i < dims.Length; ++i) { if (i != 0) { txt.Append(","); } txt.Append(dims[i]); } txt.Append("]"); if (expandDepth > 0 && av.Rank == 1 && av.ElementType != CorElementType.ELEMENT_TYPE_VOID) { for (int i = 0; i < dims[0]; i++) { MDbgValue v = new MDbgValue(Process, av.GetElementAtPosition(i)); var newVariableName = $"{variableName}.[{i}]"; var newVariablesToLog = variablesToLog == null ? null : variablesToLog .ToDictionary( variable => $"{newVariableName}{variable.Key.Remove(0, variableName.Length)}", variable => variable.Value); txt .Append("\n") .Append(IndentedString(indentLevel + 1, "[" + i + "] = ")) .Append(IndentedBlock(indentLevel + 2, v.GetStringValue(expandDepth - 1, canDoFunceval, $"{variableName}.[{i}]", newVariablesToLog))); } } return(txt.ToString()); }
private string InternalGetValue(int indentLevel, int expandDepth, bool canDoFunceval) { Debug.Assert(expandDepth >= 0); CorValue value = this.CorValue; if (value == null) { return("<N/A>"); } // Record the memory addresses if displaying them is enabled string prefix = String.Empty; StringBuilder ptrStrBuilder = null; if (m_process.m_engine.Options.ShowAddresses) { ptrStrBuilder = new StringBuilder(); } try { value = Dereference(value, ptrStrBuilder); } catch (COMException ce) { if (ce.ErrorCode == (int)HResult.CORDBG_E_BAD_REFERENCE_VALUE) { return(MakePrefixFromPtrStringBuilder(ptrStrBuilder) + "<invalid reference value>"); } throw; } prefix = MakePrefixFromPtrStringBuilder(ptrStrBuilder); if (value == null) { return(prefix + "<null>"); } Unbox(ref value); switch (value.Type) { case CorElementType.ELEMENT_TYPE_BOOLEAN: case CorElementType.ELEMENT_TYPE_I1: case CorElementType.ELEMENT_TYPE_U1: case CorElementType.ELEMENT_TYPE_I2: case CorElementType.ELEMENT_TYPE_U2: case CorElementType.ELEMENT_TYPE_I4: case CorElementType.ELEMENT_TYPE_U4: case CorElementType.ELEMENT_TYPE_I: case CorElementType.ELEMENT_TYPE_U: case CorElementType.ELEMENT_TYPE_I8: case CorElementType.ELEMENT_TYPE_U8: case CorElementType.ELEMENT_TYPE_R4: case CorElementType.ELEMENT_TYPE_R8: case CorElementType.ELEMENT_TYPE_CHAR: { object v = value.CastToGenericValue().GetValue(); string result; IFormattable vFormattable = v as IFormattable; if (vFormattable != null) { result = vFormattable.ToString(null, System.Globalization.CultureInfo.CurrentUICulture); } else { result = v.ToString(); } // let's put quotes around char values if (value.Type == CorElementType.ELEMENT_TYPE_CHAR) { result = "'" + result + "'"; } return(prefix + result); } case CorElementType.ELEMENT_TYPE_CLASS: case CorElementType.ELEMENT_TYPE_VALUETYPE: CorObjectValue ov = value.CastToObjectValue(); return(prefix + PrintObject(indentLevel, ov, expandDepth, canDoFunceval)); case CorElementType.ELEMENT_TYPE_STRING: CorStringValue sv = value.CastToStringValue(); return(prefix + '"' + sv.String + '"'); case CorElementType.ELEMENT_TYPE_SZARRAY: case CorElementType.ELEMENT_TYPE_ARRAY: CorArrayValue av = value.CastToArrayValue(); return(prefix + PrintArray(indentLevel, av, expandDepth, canDoFunceval)); case CorElementType.ELEMENT_TYPE_PTR: return(prefix + "<non-null pointer>"); case CorElementType.ELEMENT_TYPE_FNPTR: return(prefix + "0x" + value.CastToReferenceValue().Value.ToString("X")); case CorElementType.ELEMENT_TYPE_BYREF: case CorElementType.ELEMENT_TYPE_TYPEDBYREF: case CorElementType.ELEMENT_TYPE_OBJECT: default: return(prefix + "<printing value of type: " + value.Type + " not implemented>"); } }
private string InternalGetValue(int indentLevel, int expandDepth, bool canDoFunceval, string variableName, Dictionary <string, int> variablesToLog) { Debug.Assert(expandDepth >= 0); CorValue value = this.CorValue; if (value == null) { return("<N/A>"); } // Record the memory addresses if displaying them is enabled string prefix = String.Empty; StringBuilder ptrStrBuilder = null; if (m_process.m_engine.Options.ShowAddresses) { ptrStrBuilder = new StringBuilder(); } try { value = Dereference(value, ptrStrBuilder); } catch (COMException ce) { if (ce.ErrorCode == (int)HResult.CORDBG_E_BAD_REFERENCE_VALUE) { return(MakePrefixFromPtrStringBuilder(ptrStrBuilder) + "<invalid reference value>"); } throw; } prefix = MakePrefixFromPtrStringBuilder(ptrStrBuilder); if (value == null) { return(prefix + "<null>"); } Unbox(ref value); switch (value.Type) { case CorElementType.ELEMENT_TYPE_BOOLEAN: case CorElementType.ELEMENT_TYPE_I1: case CorElementType.ELEMENT_TYPE_U1: case CorElementType.ELEMENT_TYPE_I2: case CorElementType.ELEMENT_TYPE_U2: case CorElementType.ELEMENT_TYPE_I4: case CorElementType.ELEMENT_TYPE_U4: case CorElementType.ELEMENT_TYPE_I: case CorElementType.ELEMENT_TYPE_U: case CorElementType.ELEMENT_TYPE_I8: case CorElementType.ELEMENT_TYPE_U8: case CorElementType.ELEMENT_TYPE_R4: case CorElementType.ELEMENT_TYPE_R8: case CorElementType.ELEMENT_TYPE_CHAR: { if (variablesToLog == null) { } else if (!variablesToLog.Any(variable => variable.Key == variableName)) { return("[SKIP]"); } object v = value.CastToGenericValue().GetValue(); string result; IFormattable vFormattable = v as IFormattable; if (vFormattable != null) { result = vFormattable.ToString(null, System.Globalization.CultureInfo.CurrentUICulture); } else { result = v.ToString(); } // let's put quotes around char values if (value.Type == CorElementType.ELEMENT_TYPE_CHAR) { result = "'" + result + "'"; } return(Loger.WriteThisToLog(variableName, prefix + result)); } case CorElementType.ELEMENT_TYPE_CLASS: case CorElementType.ELEMENT_TYPE_VALUETYPE: CorObjectValue ov = value.CastToObjectValue(); var objectString = PrintObject(indentLevel, ov, expandDepth, canDoFunceval, variableName, variablesToLog); string objectPrint; if (objectString == "[SKIP]") { objectPrint = "[SKIP]"; } else { objectPrint = prefix + objectString; Loger.WriteThisToLog(variableName, objectPrint.Substring(0, objectPrint.IndexOf('\n') > -1 ? objectPrint.IndexOf('\n') : objectPrint.Length)); } return(objectPrint); case CorElementType.ELEMENT_TYPE_STRING: if (variablesToLog == null) { } else if (!variablesToLog.Any(variable => variable.Key == variableName)) { return("[SKIP]"); } CorStringValue sv = value.CastToStringValue(); return(Loger.WriteThisToLog(variableName, $"{prefix}\"{sv.String}\"")); case CorElementType.ELEMENT_TYPE_SZARRAY: case CorElementType.ELEMENT_TYPE_ARRAY: CorArrayValue av = value.CastToArrayValue(); var arrayString = PrintArray(indentLevel, av, expandDepth, canDoFunceval, variableName, variablesToLog); string arrayPrint; if (arrayString == "[SKIP]") { arrayPrint = "[SKIP]"; } else { arrayPrint = prefix + arrayString; Loger.WriteThisToLog(variableName, arrayPrint.Substring(0, arrayPrint.IndexOf('\n') > -1 ? arrayPrint.IndexOf('\n') : arrayPrint.Length)); } return(arrayPrint); case CorElementType.ELEMENT_TYPE_PTR: return(Loger.WriteThisToLog(variableName, prefix + "<non-null pointer>"));; case CorElementType.ELEMENT_TYPE_FNPTR: return(Loger.WriteThisToLog(variableName, prefix + "0x" + value.CastToReferenceValue().Value.ToString("X"))); case CorElementType.ELEMENT_TYPE_BYREF: case CorElementType.ELEMENT_TYPE_TYPEDBYREF: case CorElementType.ELEMENT_TYPE_OBJECT: default: return(Loger.WriteThisToLog(variableName, prefix + "<printing value of type: " + value.Type + " not implemented>")); } }