public void GetItems(DkmVisualizedExpression visualizedExpression, DkmEvaluationResultEnumContext enumContext, int startIndex, int count, out DkmChildVisualizedExpression[] items) { if (count == 0) { items = new DkmChildVisualizedExpression[0]; return; } var rawContextData = enumContext.GetDataItem <RawEnumContextData>(); var rawContext = rawContextData != null ? rawContextData.RawContext : enumContext; var result = new List <DkmChildVisualizedExpression>(count); if (rawContextData != null && rawContextData.PythonView != null) { if (startIndex == 0) { result.Add(rawContextData.PythonView); --count; } else { --startIndex; } } DkmEvaluationResult[] rawItems; visualizedExpression.GetItemsCallback(rawContext, startIndex, count, out rawItems); for (int i = 0; i < rawItems.Length; ++i) { var rawItem = rawItems[i]; var rawSuccessItem = rawItem as DkmSuccessEvaluationResult; DkmExpressionValueHome home = null; if (rawSuccessItem != null && rawSuccessItem.Address != null) { home = DkmPointerValueHome.Create(rawSuccessItem.Address.Value); } else { home = DkmFakeValueHome.Create(0); } var item = DkmChildVisualizedExpression.Create( visualizedExpression.InspectionContext, visualizedExpression.VisualizerId, visualizedExpression.SourceId, visualizedExpression.StackFrame, home, rawItem, visualizedExpression, (uint)(startIndex + i), rawItem.GetDataItem <RawEvaluationResultHolder>()); result.Add(item); } items = result.ToArray(); }
public override void GetChildItems(DkmEvaluationResultEnumContext enumContext, int start, int count, out DkmChildVisualizedExpression[] items) { var props = GetAllProperties(); int total_num_props = props.Length; int end_idx = Math.Min(start + count, total_num_props); int num_to_return = end_idx - start; items = new DkmChildVisualizedExpression[num_to_return]; for (int idx = start, out_idx = 0; idx < end_idx; ++idx, ++out_idx) { // We want to construct our own visualized expression from the eval. var eval = props[idx] as DkmSuccessEvaluationResult; // @TODO: Perhaps allow for failed evaluations and display anyway with unknown value?? Debug.Assert(eval != null); DkmExpressionValueHome home; if (eval.Address != null) { home = DkmPointerValueHome.Create(eval.Address.Value); } else { home = DkmFakeValueHome.Create(0); } var expr = DkmChildVisualizedExpression.Create( expression_.InspectionContext, // @TODO: This is weird... seems to affect whether we get callback. // Obviously the properties can be of any type, UObject or not. // Perhaps best to put back the guid for PropertyValue, even though we don't really need to use it. Guids.Visualizer.PropertyValue, //Guids.Visualizer.UObject,//Guids.Visualizer.PropertyList, // Seems that in order for these to be passed back to the EE for default expansion, they need to be given // the SourceId from the originally received root expression. PropListExpression.Parent.SourceId, expression_.StackFrame, home, eval, expression_, (uint)idx, null // Don't associate any data with the expression. If the EE calls back to us to expand it, we'll just tell it to use default expansion. ); items[out_idx] = expr; } }
public void EvaluateChildren(DkmChildVisualizedExpression[] output, int startIndex, out int numWritten) { DkmEvaluationResult evalResult = evaluator_(name_, startIndex); EvaluationDataItem originalDataItem = evalResult.GetDataItem <EvaluationDataItem>(); DkmChildVisualizedExpression childExpr = DkmChildVisualizedExpression.Create( expression_.InspectionContext, expression_.VisualizerId, expression_.SourceId, expression_.StackFrame, DkmFakeValueHome.Create(0), evalResult, expression_, (uint)startIndex, originalDataItem); output[startIndex] = childExpr; numWritten = 1; }
public void EvaluateChildren(DkmChildVisualizedExpression[] output, int startIndex, out int numWritten) { numWritten = 0; if (mode_ == ChildDisplayMode.Inline) { CreateDefaultEnumContext(); int count = ChildCount; DkmEvaluationResult[] results = new DkmEvaluationResult[count]; expression_.GetItemsCallback(defEnumContext_, 0, count, out results); for (int i = 0; i < count; ++i) { DkmSuccessEvaluationResult successResult = results[i] as DkmSuccessEvaluationResult; DkmExpressionValueHome home = null; if (successResult != null && successResult.Address != null) { home = DkmPointerValueHome.Create(successResult.Address.Value); } else { home = DkmFakeValueHome.Create(0); } output[startIndex + i] = DkmChildVisualizedExpression.Create( defEnumContext_.InspectionContext, Guids.CustomVisualizer.ForceDefault, expression_.SourceId, defEnumContext_.StackFrame, home, results[i], expression_, (uint)startIndex, null); EvaluationDataItem originalDataItem = results[i].GetDataItem <EvaluationDataItem>(); } numWritten = count; } else { numWritten = 1; } }
/* public override DkmChildVisualizedExpression GetMostDerived() * { * foreach (var child in MemberExpressions) * { * var eval = child.Value.EvaluationResult as DkmSuccessEvaluationResult; * if (eval != null && eval.Category == DkmEvaluationResultCategory.MostDerivedClass) * { * return child.Value; * } * } * * return null; * } */ private DkmChildVisualizedExpression CreateNewExpression(string expr_str) { DkmSuccessEvaluationResult result_eval = null; try { result_eval = DefaultEE.DefaultEval(expr_str, callback_expr_, true) as DkmSuccessEvaluationResult; } catch (Exception e) { } if (result_eval == null) { return(null); } DkmExpressionValueHome home; if (result_eval.Address != null) { home = DkmPointerValueHome.Create(result_eval.Address.Value); } else { home = DkmFakeValueHome.Create(0); } // @TODO: This is weird. Can I perhaps construct a DkmRootVisualizedExpression instead?? // Not sure about a couple of the parameters needed to do so, Module especially... return(DkmChildVisualizedExpression.Create( result_eval.InspectionContext, expr_.VisualizerId, expr_.SourceId, result_eval.StackFrame, home, result_eval, callback_expr_, //expr_, 0, // ?? null )); }
/* public override DkmChildVisualizedExpression GetMostDerived() * { * foreach (var child in MemberExpressions) * { * var eval = child.Value.EvaluationResult as DkmSuccessEvaluationResult; * if (eval != null && eval.Category == DkmEvaluationResultCategory.MostDerivedClass) * { * return child.Value; * } * } * * return null; * } */ private void EvaluateChildren() { MemberExpressions = new Dictionary <string, DkmChildVisualizedExpression>(); // @TODO: Am assuming that if expr_ is a child expression, it would be more // efficient to use its EvaluationResult property instead of invoking the default // evaluator again. However, doing this results in using child UObject expressions which // have been generated using the custom visualization (since ! specifier is not recursive). // We really don't want this since we just want the default expansion so we can navigate // through the members and bases of the class. // Problem is, don't know how to communicate to the 'UseDefaultEvaluationBehavior' // implementation to use a default expansion in this particular case. Setting the data // item on expr_ before calling GetItemsCallback doesn't work, since the expression that // gets passed through is not actually expr_, but a root visualized expression that was // created by the EE when visualizing the parent, which we don't have access to. // As it is, now that we inline the default expansion alongside the addition of the // 'UE4 Properties' child, this does seem to work. However, not obvious there is any // performance improvement, also not 100% sure it's safe to use the stored evaluation. DkmEvaluationResult uobj_eval = null; if (expr_.TagValue == DkmVisualizedExpression.Tag.ChildVisualizedExpression) { uobj_eval = ((DkmChildVisualizedExpression)expr_).EvaluationResult; } else { uobj_eval = DefaultEE.DefaultEval(callback_expr_, true); } eval_ = (DkmSuccessEvaluationResult)uobj_eval; DkmEvaluationResult[] children; DkmEvaluationResultEnumContext enum_context; try { callback_expr_.GetChildrenCallback(uobj_eval, 0, callback_expr_.InspectionContext, out children, out enum_context); // @NOTE: Assuming count will not be large here!! callback_expr_.GetItemsCallback(enum_context, 0, enum_context.Count, out children); } catch { return; } uint idx = 0; foreach (var child_eval in children) { if (child_eval.TagValue == DkmEvaluationResult.Tag.SuccessResult) { var success_eval = child_eval as DkmSuccessEvaluationResult; Debug.Assert(success_eval != null); DkmExpressionValueHome home; if (success_eval.Address != null) { home = DkmPointerValueHome.Create(success_eval.Address.Value); } else { home = DkmFakeValueHome.Create(0); } DkmChildVisualizedExpression child = DkmChildVisualizedExpression.Create( child_eval.InspectionContext, callback_expr_.VisualizerId, callback_expr_.SourceId, child_eval.StackFrame, home, child_eval, expr_, idx, null ); MemberExpressions[child_eval.Name] = child; } ++idx; } }
public override void GetChildItems(DkmEvaluationResultEnumContext enumContext, int start, int count, out DkmChildVisualizedExpression[] items) { // Cap the requested number to the total remaining from startIndex count = Math.Min(count, enumContext.Count - start); items = new DkmChildVisualizedExpression[count]; uint idx = 0; // Retrieve the default expansion enum context var default_data = enumContext.GetDataItem <DefaultEnumContextDataItem>(); if (start < default_data.Context.Count) { // Requesting default children int default_count = Math.Min(count, default_data.Context.Count - start); DkmEvaluationResult[] default_evals; expression_.GetItemsCallback(default_data.Context, start, default_count, out default_evals); for (int dft_idx = 0; dft_idx < default_count; ++dft_idx, ++idx) { DkmSuccessEvaluationResult success_eval = default_evals[dft_idx] as DkmSuccessEvaluationResult; DkmExpressionValueHome home = null; if (success_eval != null && success_eval.Address != null) { home = DkmPointerValueHome.Create(success_eval.Address.Value); } else { home = DkmFakeValueHome.Create(0); } items[idx] = DkmChildVisualizedExpression.Create( enumContext.InspectionContext, expression_.VisualizerId, // @TODO: Check this is what we want. Will we get callbacks for it, regardless of its type? expression_.SourceId, enumContext.StackFrame, home, default_evals[dft_idx], expression_, (uint)start, null ); } } if (start + count > default_data.Context.Count) { // Requesting custom children // @NOTE: Currently just assuming only 1 custom child (prop list) and hard coding as such. // DkmSuccessEvaluationResult.ExtractFromProperty(IDebugProperty3!!!!!!!) ............................................... // @NOTE: Had thought could just create an expression with a null evaluation // inside it, and by giving it a visualizer guid, the system would call back // to us to evaluate the expression. Seems not to work though, I guess because the // visualizer guid identifies the visualizer but not the containing component, // and since the expression itself doesn't have a type, it can't know that it // should call our component. DkmEvaluationResult eval = DkmSuccessEvaluationResult.Create( enumContext.InspectionContext, enumContext.StackFrame, Resources.UE4PropVis.IDS_DISP_BLUEPRINTPROPERTIES, Resources.UE4PropVis.IDS_DISP_BLUEPRINTPROPERTIES, DkmEvaluationResultFlags.ReadOnly | DkmEvaluationResultFlags.Expandable, "", // @TODO: something like "[<count> properties]" null, "", // Type column DkmEvaluationResultCategory.Other, DkmEvaluationResultAccessType.None, DkmEvaluationResultStorageType.None, DkmEvaluationResultTypeModifierFlags.None, null, null, null, null ); // This child is just for organization and does not correspond to anything in memory. DkmExpressionValueHome valueHome = DkmFakeValueHome.Create(0); var prop_list_expr = DkmChildVisualizedExpression.Create( enumContext.InspectionContext, Guids.Visualizer.PropertyList, // Associate the expression with ourselves, since we created it Guids.Component.VisualizerComponent, enumContext.StackFrame, valueHome, eval, expression_, idx, null ); // Create a visualizer for the property list, and attach it to the expression. var prop_list_visualizer = new PropertyListVisualizer(prop_list_expr, access_ctx_); prop_list_expr.SetDataItem(DkmDataCreationDisposition.CreateAlways, new ExpressionDataItem(prop_list_visualizer)); items[idx] = prop_list_expr; } }