/// <summary>
        /// Get the variable assignment expression as a string. Returns null if the value is
        /// constant or invalid.
        /// </summary>
        public static string GetVariableAssignExpression(this RemoteValue remoteValue)
        {
            var valueType = remoteValue.GetValueType();

            if (valueType == ValueType.Invalid)
            {
                return(null);
            }

            if (valueType == ValueType.Register)
            {
                return($"${remoteValue.GetName()}");
            }

            TypeFlags?typeFlags = remoteValue.GetTypeInfo()?.GetTypeFlags();

            if (typeFlags.HasValue && typeFlags.Value.HasFlag(TypeFlags.IS_ARRAY))
            {
                return(null);
            }

            string variableExpression = remoteValue.GetFullName();

            if (variableExpression == null)
            {
                variableExpression = remoteValue.GetMemoryAddressAssignExpression();
            }
            return(variableExpression);
        }
        /// <summary>
        /// Returns the address to be used as memory context. This is used to get an address
        /// from an expression entered into Visual Studio's memory view's address text box.
        /// </summary>
        public static ulong?GetMemoryContextAddress(this RemoteValue remoteValue)
        {
            if (!IsValidValue(remoteValue))
            {
                return(null);
            }

            TypeFlags GetTypeFlags(RemoteValue value) =>
            remoteValue.GetTypeInfo().GetCanonicalType().GetTypeFlags();

            // If the value is an array, try to obtain its address.
            TypeFlags flags = GetTypeFlags(remoteValue);

            if (flags.HasFlag(TypeFlags.IS_ARRAY))
            {
                remoteValue = remoteValue.AddressOf();
                if (!IsValidValue(remoteValue))
                {
                    return(null);
                }
                flags = GetTypeFlags(remoteValue);
            }

            // Only interpret pointers, references and integers as addresses.
            if (!flags.HasFlag(TypeFlags.IS_REFERENCE) && !flags.HasFlag(TypeFlags.IS_POINTER) &&
                !flags.HasFlag(TypeFlags.IS_INTEGER))
            {
                return(null);
            }

            return(remoteValue.GetValueAsUnsigned());
        }
        static IEnumerable <RemoteValue> GetPointerChildren(RemoteValue value, int offset, int count)
        {
            var    result      = new List <RemoteValue>();
            SbType pointeeType = value.GetTypeInfo()?.GetPointeeType();

            if (pointeeType == null)
            {
                // If we cannot get the pointee type, just return the empty list.
                return(result);
            }
            ulong byteSize    = pointeeType.GetByteSize();
            ulong baseAddress = value.GetValueAsUnsigned() + (ulong)offset * byteSize;

            for (int n = 0; n < count; ++n)
            {
                ulong       address    = baseAddress + (ulong)n * byteSize;
                RemoteValue childValue =
                    value.CreateValueFromAddress($"[{offset + n}]", address, pointeeType);
                if (childValue != null)
                {
                    result.Add(childValue);
                }
            }
            return(result);
        }
示例#4
0
        private GrpcValueInfo CreateValueInfoAndUpdateStores(RemoteValue remoteValue)
        {
            if (remoteValue == null)
            {
                return(null);
            }

            string expressionPath;
            var    hasExpressionPath = remoteValue.GetExpressionPath(out expressionPath);
            var    valueInfo         = new GrpcValueInfo
            {
                ExpressionPath    = expressionPath ?? "",
                HasExpressionPath = hasExpressionPath,
                NumChildren       = remoteValue.GetNumChildren(),
                Summary           = remoteValue.GetSummary() ?? "",
                TypeName          = remoteValue.GetTypeName() ?? "",
                Value             = remoteValue.GetValue() ?? "",
                ValueType         = EnumUtil.ConvertTo <Debugger.Common.ValueType>(
                    remoteValue.GetValueType()),
                IsPointerType = remoteValue.TypeIsPointerType(),
                ByteSize      = remoteValue.GetByteSize(),
            };
            var typeInfo = remoteValue.GetTypeInfo();

            if (typeInfo != null)
            {
                valueInfo.Type = GrpcFactoryUtils.CreateType(
                    typeInfo, typeStore.AddObject(typeInfo));
            }
            return(valueInfo);
        }
 public virtual string FormatExpressionForAssignment(
     RemoteValue remoteValue, string expression)
 {
     if (remoteValue.GetTypeInfo().GetTypeFlags().HasFlag(TypeFlags.IS_FLOAT))
     {
         return(FloatRadixConversionHelper.TryConvertToFloatFromNumberString(
                    expression, new System.Lazy <int>(() => (int)remoteValue.GetByteSize())));
     }
     return(expression);
 }
        public virtual string FormatValueAsAddress(RemoteValue remoteValue)
        {
            TypeFlags flags = remoteValue?.GetTypeInfo()?.GetTypeFlags() ?? 0;

            if (flags.HasFlag(TypeFlags.IS_REFERENCE) || flags.HasFlag(TypeFlags.IS_POINTER))
            {
                return($"0x{remoteValue.GetValueAsUnsigned():x16}");
            }
            return(string.Empty);
        }
示例#7
0
        public IEnumerable <string> GetAllInheritedTypes()
        {
            SbType typeInfo = _remoteValue.GetTypeInfo();

            if (typeInfo == null)
            {
                yield break;
            }

            TypeFlags typeFlags = typeInfo.GetTypeFlags();

            if (typeFlags.HasFlag(TypeFlags.IS_POINTER) ||
                typeFlags.HasFlag(TypeFlags.IS_REFERENCE))
            {
                typeInfo = typeInfo.GetPointeeType();
                if (typeInfo == null)
                {
                    yield break;
                }
            }

            var typeQueue = new Queue <SbType>();

            typeQueue.Enqueue(typeInfo);

            while (typeQueue.Count > 0)
            {
                SbType curType = typeQueue.Dequeue();
                yield return(curType.GetName());

                uint numDirectBaseClasses = curType.GetNumberOfDirectBaseClasses();
                for (uint i = 0; i < numDirectBaseClasses; i++)
                {
                    typeQueue.Enqueue(curType.GetDirectBaseClassAtIndex(i).GetTypeInfo());
                }
            }
        }
        public override string FormatValueAsAddress(RemoteValue remoteValue)
        {
            TypeFlags flags = remoteValue?.GetTypeInfo()?.GetTypeFlags() ?? 0;

            if (flags.HasFlag(TypeFlags.IS_REFERENCE) || flags.HasFlag(TypeFlags.IS_POINTER))
            {
                if (ValueFormat == ValueFormat.HexUppercase)
                {
                    return($"{remoteValue.GetValueAsUnsigned():X16}");
                }
                else
                {
                    return($"{remoteValue.GetValueAsUnsigned():x16}");
                }
            }
            return(string.Empty);
        }
        /// <summary>
        /// Returns a casted raw address expression that can be used to build a value assign
        /// expression.
        ///
        /// Can return null.
        /// </summary>
        public static string GetMemoryAddressAssignExpression(this RemoteValue remoteValue)
        {
            if (!IsValidValue(remoteValue))
            {
                return(null);
            }
            var flags = remoteValue.GetTypeInfo().GetTypeFlags();

            if (flags.HasFlag(TypeFlags.IS_REFERENCE))
            {
                // NOTE: This works for references implemented as a pointer. It is not known how
                // this will work for other implementations.
                var typeName = remoteValue.GetTypeName();
                typeName = typeName.Replace("&", "");
                return($"(*(({typeName}*){remoteValue.GetDefaultValue()}))");
            }

            RemoteValue addressOfValue;

            if (!TryGetAddressOf(remoteValue, out addressOfValue))
            {
                return(null);
            }

            if (flags.HasFlag(TypeFlags.IS_POINTER))
            {
                return($"(({remoteValue.GetTypeName()}){remoteValue.GetDefaultValue()})");
            }

            if (flags.HasFlag(TypeFlags.IS_ARRAY))
            {
                return(null);
            }

            return($"(*(({remoteValue.GetTypeName()}*){addressOfValue.GetDefaultValue()}))");
        }
 /// <summary>
 /// Determines if a RemoteValue is a valid value. i.e. has correct type information and
 /// isn't an error.
 /// </summary>
 /// <param name="remoteValue"></param>
 /// <returns></returns>
 private static bool IsValidValue(RemoteValue remoteValue)
 {
     return(remoteValue != null && remoteValue.GetTypeInfo() != null &&
            !remoteValue.GetError().Fail());
 }
 public virtual SbType GetTypeInfo()
 {
     return(value.GetTypeInfo());
 }