예제 #1
0
파일: list.cs 프로젝트: sdmaclea/SharpDebug
            /// <summary>
            /// Verifies if the specified code type is correct for this class.
            /// </summary>
            /// <param name="codeType">The code type.</param>
            /// <returns>Extracted data object or <c>null</c> if fails.</returns>
            internal static object VerifyCodeType(CodeType codeType)
            {
                // We want to have this kind of hierarchy
                // __end_
                // | __next_
                // | __prev_
                // | __value_ (exists in list node type)
                // __size_alloc_
                // | __value_
                CodeType __end_, __next_, __prev_, __size_alloc_, __value_;

                if (!codeType.GetFieldTypes().TryGetValue("__end_", out __end_))
                {
                    return(null);
                }
                if (!__end_.GetFieldTypes().TryGetValue("__next_", out __next_) || !__end_.GetFieldTypes().TryGetValue("__prev_", out __prev_))
                {
                    return(null);
                }
                if (!codeType.GetFieldTypes().TryGetValue("__size_alloc_", out __size_alloc_))
                {
                    return(null);
                }
                if (!__size_alloc_.GetFieldTypes().TryGetValue("__value_", out __value_))
                {
                    return(null);
                }

                CodeType listNodeType, __value_2;

                try
                {
                    CodeType     listNodeBaseType      = codeType.GetFieldType("__end_");
                    const string listNodeBaseNameStart = "std::__1::__list_node_base<";
                    const string listNodeNameStart     = "std::__1::__list_node<";
                    listNodeType = CodeType.Create(listNodeNameStart + listNodeBaseType.Name.Substring(listNodeBaseNameStart.Length), listNodeBaseType.Module);
                }
                catch
                {
                    return(null);
                }

                if (!listNodeType.GetFieldTypes().TryGetValue("__value_", out __value_2))
                {
                    return(null);
                }

                return(new ExtractedData
                {
                    ReadLength = codeType.Module.Process.GetReadInt(codeType, "__size_alloc_.__value_"),
                    HeadOffset = codeType.GetFieldOffset("__end_") + __end_.GetFieldOffset("__next_"),
                    HeadHasValue = true,
                    ItemNextOffset = listNodeType.GetFieldOffset("__next_"),
                    ItemPreviousOffset = listNodeType.GetFieldOffset("__prev_"),
                    ItemValueOffset = listNodeType.GetFieldOffset("__value_"),
                    ItemValueCodeType = __value_2,
                    CodeType = codeType,
                    Process = codeType.Module.Process,
                });
            }
예제 #2
0
        /// <summary>
        /// Reinterpret Cast, changes underlaying code type.
        /// </summary>
        /// <remarks>
        /// Requested Type must be a primitive (int, short etc).
        /// </remarks>
        /// <typeparam name="T">Primitive type to cast variable to.</typeparam>
        /// <param name="variable">The variable.</param>
        /// <returns>Return CodePointer to Variable pointer address.</returns>
        public static CodePointer <T> ReinterpretPointerCast <T>(this Variable variable)
            where T : struct
        {
            // Get CodeType from the generic argument.
            //
            string codeTypeName;

            if (typeof(T) == typeof(int))
            {
                codeTypeName = "int";
            }
            else if (typeof(T) == typeof(short))
            {
                codeTypeName = "short";
            }
            else if (typeof(T) == typeof(uint))
            {
                codeTypeName = "unsigned int";
            }
            else if (typeof(T) == typeof(ushort))
            {
                codeTypeName = "unsigned short";
            }
            else
            {
                throw new NotSupportedException("Requested type is not supported.");
            }

            // Return CodePointer<T>
            //
            return(new CodePointer <T>(
                       Variable.CreatePointer(
                           CodeType.Create(codeTypeName, variable.GetCodeType().Module).PointerToType,
                           variable.GetPointerAddress())));
        }
예제 #3
0
        /// <summary>
        /// Gets the runtime code type and offset to original code type.
        /// </summary>
        /// <param name="vtableAddress">The vtable address.</param>
        public Tuple <CodeType, int> GetRuntimeCodeTypeAndOffset(uint vtableAddress)
        {
            using (ProcessSwitcher switcher = new ProcessSwitcher(DbgEngDll.StateCache, Module.Process))
            {
                uint          nameSize;
                ulong         displacement;
                StringBuilder sb = new StringBuilder(Constants.MaxSymbolName);

                DbgEngDll.Symbols.GetNameByOffset(vtableAddress + Module.Address, sb, (uint)sb.Capacity, out nameSize, out displacement);

                // Fully undecorated name should be in form: "DerivedClass::`vftable'"
                string       fullyUndecoratedName = sb.ToString();
                const string vftableString        = "::`vftable'";

                if (string.IsNullOrEmpty(fullyUndecoratedName) || !fullyUndecoratedName.EndsWith(vftableString))
                {
                    // Pointer is not vtable.
                    return(null);
                }

                string   codeTypeName = fullyUndecoratedName.Substring(0, fullyUndecoratedName.Length - vftableString.Length);
                CodeType codeType     = CodeType.Create(Module.Process, codeTypeName);

                // TODO: We need to be able to get partially undecorated name in order to find offset (See DiaModule.cs for more info)
                return(Tuple.Create(codeType, 0));
            }
        }
예제 #4
0
 /// <summary>
 /// Initializes a new instance of the <see cref="GenericsElementCaster{T}"/> class.
 /// </summary>
 /// <param name="parentCodeType">CodeType of the generics class that will be using this helper class.</param>
 /// <param name="argumentNumber">The argument number in original user type.</param>
 public GenericsElementCaster(CodeType parentCodeType, int argumentNumber)
 {
     try
     {
         elementCodeType = CodeType.Create(parentCodeType.TemplateArgumentsStrings[argumentNumber], parentCodeType.Module);
     }
     catch (Exception)
     {
     }
 }
예제 #5
0
            /// <summary>
            /// Initializes a new instance of the <see cref="LibStdCpp6_NoAbi"/> class.
            /// </summary>
            /// <param name="variable">The variable.</param>
            public LibStdCpp6_NoAbi(Variable variable)
            {
                CodeType codeType = variable.GetCodeType();
                CodeType _Rep     = CodeType.Create($"{codeType.Name}::_Rep", codeType.Module);

                header   = UserMember.Create(() => text.Value.AdjustPointer(-(int)_Rep.Size).CastAs(_Rep));
                length   = UserMember.Create(() => (int)header.Value.GetField("_M_length"));
                text     = UserMember.Create(() => variable.GetField("_M_dataplus").GetField("_M_p"));
                capacity = UserMember.Create(() => (int)header.Value.GetField("_M_capacity"));
            }
예제 #6
0
            /// <summary>
            /// Verifies if the specified code type is correct for this class.
            /// </summary>
            /// <param name="codeType">The code type.</param>
            /// <returns>Extracted data object or <c>null</c> if fails.</returns>
            internal static object VerifyCodeType(CodeType codeType)
            {
                // We want to have this kind of hierarchy
                // _M_dataplus
                // | _M_p
                // basic_string<>::_Rep type
                // _M_length
                // _M_capacity
                // _M_refcount
                CodeType _M_dataplus, _M_p, _Rep, _M_length, _M_capacity, _M_refcount;

                try
                {
                    _Rep = CodeType.Create($"{codeType.Name}::_Rep", codeType.Module);
                }
                catch
                {
                    return(null);
                }

                if (!codeType.GetFieldTypes().TryGetValue("_M_dataplus", out _M_dataplus))
                {
                    return(null);
                }
                if (!_M_dataplus.GetFieldTypes().TryGetValue("_M_p", out _M_p))
                {
                    return(null);
                }
                if (!_Rep.GetFieldTypes().TryGetValue("_M_length", out _M_length))
                {
                    return(null);
                }
                if (!_Rep.GetFieldTypes().TryGetValue("_M_capacity", out _M_capacity))
                {
                    return(null);
                }
                if (!_Rep.GetFieldTypes().TryGetValue("_M_refcount", out _M_refcount))
                {
                    return(null);
                }
                int repOffset = -(int)_Rep.Size;

                return(new ExtractedData
                {
                    ReadLength = codeType.Module.Process.GetReadInt(_Rep, "_M_length", repOffset),
                    ReadCapacity = codeType.Module.Process.GetReadInt(_Rep, "_M_capacity", repOffset),
                    CharSize = (int)_M_p.ElementType.Size,
                    PointerOffset = codeType.GetFieldOffset("_M_dataplus") + _M_dataplus.GetFieldOffset("_M_p"),
                    CodeType = codeType,
                    Process = codeType.Module.Process,
                });
            }
예제 #7
0
        public void TestGetTypeByName()
        {
            Module types = Process.Current.Modules.Where(m => m.Name == "Types").Single();

            Assert.IsNotNull(CodeType.Create("Foo", types));
            try
            {
                CodeType.Create("Foo2", types);
                Assert.Fail();
            }
            catch (Exception ex)
            {
                Assert.AreEqual("Type 'Foo2' wasn't found", ex.Message);
            }
        }
예제 #8
0
        public void FieldNameAndValueTests()
        {
            IClrHeap heap        = Process.Current.ClrRuntimes.Single().Heap;
            Module   typesModule = Module.All.Single(m => m.Name == "Types");
            CodeType fooType     = CodeType.Create("Foo", typesModule);
            Variable s_foo       = typesModule.GetVariable("Types.s_foo");

            Assert.Equal(fooType, s_foo.GetCodeType());
            Assert.Equal(42, (int)s_foo.GetField("i"));
            Assert.Equal("string", new ClrString(s_foo.GetField("s")).Text);
            Assert.True((bool)s_foo.GetField("b"));
            Assert.Equal(4.2f, (float)s_foo.GetField("f"));
            Assert.Equal(8.4, (double)s_foo.GetField("d"));
            Assert.Contains(s_foo, heap.EnumerateObjects());
        }
예제 #9
0
        public void TestGetTypeByName()
        {
            Module types = Process.Current.Modules.Where(m => m.Name == "Types").Single();

            Assert.NotNull(CodeType.Create("Foo", types));
            try
            {
                CodeType.Create("Foo2", types);
                throw new Exception("This should never happen");
            }
            catch (Exception ex)
            {
                Assert.Equal("Type 'Foo2' wasn't found", ex.Message);
            }
        }
예제 #10
0
파일: list.cs 프로젝트: sdmaclea/SharpDebug
            /// <summary>
            /// Finds _List_node code type for the specified list code type.
            /// </summary>
            /// <param name="codeType">std::list code type</param>
            private static CodeType GetListNodeCodeType(CodeType codeType)
            {
                string elementTypeName = codeType.TemplateArgumentsStrings[0];
                string listNodeCodeTypeName;

                if (elementTypeName.EndsWith(">"))
                {
                    listNodeCodeTypeName = $"std::_List_node<{elementTypeName} >";
                }
                else
                {
                    listNodeCodeTypeName = $"std::_List_node<{elementTypeName}>";
                }
                return(CodeType.Create(listNodeCodeTypeName, codeType.Module));
            }
예제 #11
0
        public void TestGetTypeByName()
        {
            var    modules = Process.Current.Modules;
            Module types   = modules.Where(m => m.Name == "Types").Single();

            Exception ex = Assert.Throws <Exception>(() => CodeType.Create("Foo", types));

            Assert.Equal("Type 'Foo' wasn't found", ex.Message);

            Module sharedLibrary = modules.Where(m => m.Name == "SharedLibrary").Single();

            Assert.NotNull(CodeType.Create("Foo", sharedLibrary));
            ex = Assert.Throws <Exception>(() => CodeType.Create("Foo2", sharedLibrary));
            Assert.Equal("Type 'Foo2' wasn't found", ex.Message);
        }
예제 #12
0
파일: any.cs 프로젝트: sdmaclea/SharpDebug
            /// <summary>
            /// Initializes a new instance of the <see cref="ClangLibCpp"/> class.
            /// </summary>
            /// <param name="variable">The variable.</param>
            /// <param name="savedData">Data returned from VerifyCodeType function.</param>
            public ClangLibCpp(Variable variable, object savedData)
            {
                data    = (ExtractedData)savedData;
                address = variable.GetPointerAddress();
                ulong managerAddress = data.Process.ReadPointer(address + (uint)data.ManagerPointerOffset);

                if (managerAddress != 0)
                {
                    Tuple <string, ulong> nameAndOffset = Context.SymbolProvider.GetSymbolNameByAddress(data.Process, managerAddress);

                    if (nameAndOffset != null)
                    {
                        managerName = nameAndOffset.Item1;
                    }
                }
                if (HasValue)
                {
                    string codeTypeName;
                    string handlerCodeTypeName;

                    if (IsSmall)
                    {
                        string moduleName = managerName.Substring(0, managerName.IndexOf('!') + 1);

                        codeTypeName        = moduleName + managerName.Substring(moduleName.Length + SmallHandlerNameStart.Length, managerName.Length - moduleName.Length - SmallHandlerNameStart.Length - SmallHandlerNameEnd.Length);
                        handlerCodeTypeName = $"{moduleName}std::__1::__any_imp::_SmallHandler<{codeTypeName.Substring(moduleName.Length)}>";
                    }
                    else if (IsLarge)
                    {
                        string moduleName = managerName.Substring(0, managerName.IndexOf('!') + 1);

                        codeTypeName        = moduleName + managerName.Substring(moduleName.Length + LargeHandlerNameStart.Length, managerName.Length - moduleName.Length - LargeHandlerNameStart.Length - LargeHandlerNameEnd.Length);
                        handlerCodeTypeName = $"{moduleName}std::__1::__any_imp::_LargeHandler<{codeTypeName.Substring(moduleName.Length)}>";
                    }
                    else
                    {
                        throw new NotImplementedException();
                    }

                    CodeType handlerCodeType = CodeType.Create(handlerCodeTypeName);

                    valueCodeType = handlerCodeType.TemplateArguments[0] as CodeType ?? CodeType.Create(codeTypeName.Trim());
                }
            }
예제 #13
0
        /// <summary>
        /// Gets the runtime code type and offset to original code type.
        /// </summary>
        /// <param name="vtableAddress">The vtable address within the module.</param>
        public Tuple <CodeType, int> GetRuntimeCodeTypeAndOffset(uint vtableAddress)
        {
            IDiaSymbol symbol;
            int        displacement;
            string     fullyUndecoratedName, partiallyUndecoratedName;

            session.findSymbolByRVAEx(vtableAddress, SymTagEnum.PublicSymbol, out symbol, out displacement);
            fullyUndecoratedName     = symbol.get_undecoratedNameEx(UndecoratedNameOptions.NameOnly | UndecoratedNameOptions.NoEscu) ?? symbol.name;
            partiallyUndecoratedName = symbol.get_undecoratedNameEx(UndecoratedNameOptions.NoEscu) ?? symbol.name;

            // Fully undecorated name should be in form: "DerivedClass::`vftable'" or  "DerivedClass::`vbtable'"
            const string vftableString = "::`vftable'";
            const string vbtableString = "::`vbtable'";
            string       vtableString  = vftableString;

            if (string.IsNullOrEmpty(fullyUndecoratedName) || !fullyUndecoratedName.EndsWith(vftableString))
            {
                vtableString = vbtableString;
                if (string.IsNullOrEmpty(fullyUndecoratedName) || !fullyUndecoratedName.EndsWith(vbtableString))
                {
                    // Pointer is not vtable.
                    return(null);
                }
            }

            string   codeTypeName = fullyUndecoratedName.Substring(0, fullyUndecoratedName.Length - vtableString.Length);
            CodeType codeType     = CodeType.Create(codeTypeName, Module);

            // Partially undecorated name should be in form: "const DerivedClass::`vftable'{for `BaseClass'}"
            string partiallyUndecoratedNameStart = string.Format("const {0}{1}{{for `", codeTypeName, vtableString);

            if (!partiallyUndecoratedName.StartsWith(partiallyUndecoratedNameStart))
            {
                // Single Inheritace
                return(Tuple.Create(codeType, 0));
            }

            string innerCodeTypeName = partiallyUndecoratedName.Substring(partiallyUndecoratedNameStart.Length, partiallyUndecoratedName.Length - 2 - partiallyUndecoratedNameStart.Length);

            var baseClassWithVTable = codeType.BaseClasses[innerCodeTypeName];

            return(Tuple.Create(codeType, baseClassWithVTable.Item2));
        }
예제 #14
0
        public void ArrayTests()
        {
            Module   typesModule = Module.All.Single(m => m.Name == "Types");
            CodeType fooType     = CodeType.Create("Types", typesModule);
            Variable s_array     = fooType.GetStaticField("s_array");
            Variable s_one       = fooType.GetStaticField("s_one");
            Variable s_two       = fooType.GetStaticField("s_two");
            Variable s_three     = fooType.GetStaticField("s_three");

            CodeArray <Variable> codeArray = new CodeArray <Variable>(s_array);

            Variable[] expected = new Variable[] { s_one, s_two, s_three };

            Assert.Equal(expected.Length, codeArray.Length);
            for (int i = 0; i < expected.Length; i++)
            {
                Assert.Equal(expected[i], codeArray[i]);
            }
        }
예제 #15
0
        public void TestBuiltinTypes()
        {
            CodeType codeType = CodeType.Create("BuiltinTypesTest", DefaultModule);

            VerifyFieldBuiltinType(codeType, "b", BuiltinType.Bool);
            VerifyFieldBuiltinType(codeType, "c1", BuiltinType.Char8, BuiltinType.Int8);
            VerifyFieldBuiltinType(codeType, "c2", BuiltinType.Char16, BuiltinType.Char32);
            VerifyFieldBuiltinType(codeType, "i8", BuiltinType.Int8, BuiltinType.Char8);
            VerifyFieldBuiltinType(codeType, "i16", BuiltinType.Int16);
            VerifyFieldBuiltinType(codeType, "i32", BuiltinType.Int32);
            VerifyFieldBuiltinType(codeType, "i64", BuiltinType.Int64);
            VerifyFieldBuiltinType(codeType, "u8", BuiltinType.UInt8);
            VerifyFieldBuiltinType(codeType, "u16", BuiltinType.UInt16);
            VerifyFieldBuiltinType(codeType, "u32", BuiltinType.UInt32);
            VerifyFieldBuiltinType(codeType, "u64", BuiltinType.UInt64);
            VerifyFieldBuiltinType(codeType, "f32", BuiltinType.Float32);
            VerifyFieldBuiltinType(codeType, "f64", BuiltinType.Float64);
            VerifyFieldBuiltinType(codeType, "f80", BuiltinType.Float80, BuiltinType.Float64);
        }
예제 #16
0
            /// <summary>
            /// Verifies if the specified code type is correct for this class.
            /// </summary>
            /// <param name="codeType">The code type.</param>
            internal static bool VerifyCodeType(CodeType codeType)
            {
                // We want to have this kind of hierarchy
                // _M_dataplus
                // | _M_p
                // basic_string<>::_Rep type
                // _M_length
                // _M_capacity
                // _M_refcount
                CodeType _M_dataplus, _M_p, _Rep, _M_length, _M_capacity, _M_refcount;

                try
                {
                    _Rep = CodeType.Create($"{codeType.Name}::_Rep", codeType.Module);
                }
                catch
                {
                    return(false);
                }

                if (!codeType.GetFieldTypes().TryGetValue("_M_dataplus", out _M_dataplus))
                {
                    return(false);
                }
                if (!_M_dataplus.GetFieldTypes().TryGetValue("_M_p", out _M_p))
                {
                    return(false);
                }
                if (!_Rep.GetFieldTypes().TryGetValue("_M_length", out _M_length))
                {
                    return(false);
                }
                if (!_Rep.GetFieldTypes().TryGetValue("_M_capacity", out _M_capacity))
                {
                    return(false);
                }
                if (!_Rep.GetFieldTypes().TryGetValue("_M_refcount", out _M_refcount))
                {
                    return(false);
                }
                return(true);
            }
        /// <summary>
        /// Resolves code type by the specified name.
        /// </summary>
        /// <param name="process">The process where type is defined.</param>
        /// <param name="module">The module where type is defined.</param>
        /// <param name="codeTypeName">The code type name.</param>
        /// <returns>Resolved code type.</returns>
        internal static CodeType ResolveCodeType(Process process, Module module, string codeTypeName)
        {
            CodeType codeType;
            int      pointer = 0;

            FixCodeTypeSearchName(ref codeTypeName);
            while (codeTypeName.EndsWith("*"))
            {
                pointer++;
                codeTypeName = codeTypeName.Substring(0, codeTypeName.Length - 1).TrimEnd();
                FixCodeTypeSearchName(ref codeTypeName);
            }

            FixCodeTypeSearchName(ref codeTypeName);
            codeType = CodeType.Create(process, codeTypeName, module);
            for (int i = 0; i < pointer; i++)
            {
                codeType = codeType.PointerToType;
            }
            return(codeType);
        }
예제 #18
0
파일: any.cs 프로젝트: sdmaclea/SharpDebug
            /// <summary>
            /// Initializes a new instance of the <see cref="VisualStudio"/> class.
            /// </summary>
            /// <param name="variable">The variable.</param>
            /// <param name="savedData">Data returned from VerifyCodeType function.</param>
            public VisualStudio(Variable variable, object savedData)
            {
                data     = (ExtractedData)savedData;
                address  = variable.GetPointerAddress();
                typeData = data.Process.ReadPointer(address + (uint)data.TypeDataOffset);
                if (HasValue)
                {
                    Tuple <string, ulong> nameAndOffset = Context.SymbolProvider.GetSymbolNameByAddress(data.Process, TypeInfoAddress);

                    if (nameAndOffset != null)
                    {
                        string name = nameAndOffset.Item1;

                        if (name.EndsWith(rttiSignature))
                        {
                            name          = name.Substring(0, name.Length - rttiSignature.Length);
                            valueCodeType = CodeType.Create(name);
                        }
                    }
                }
            }
예제 #19
0
파일: any.cs 프로젝트: sdmaclea/SharpDebug
            /// <summary>
            /// Initializes a new instance of the <see cref="LibStdCpp7"/> class.
            /// </summary>
            /// <param name="variable">The variable.</param>
            /// <param name="savedData">Data returned from VerifyCodeType function.</param>
            public LibStdCpp7(Variable variable, object savedData)
            {
                data    = (ExtractedData)savedData;
                address = variable.GetPointerAddress();
                ulong managerAddress = data.Process.ReadPointer(address + (uint)data.ManagerPointerOffset);

                if (managerAddress != 0)
                {
                    Tuple <string, ulong> nameAndOffset = Context.SymbolProvider.GetSymbolNameByAddress(data.Process, managerAddress);

                    if (nameAndOffset != null)
                    {
                        managerName = nameAndOffset.Item1;
                    }
                }
                if (HasValue)
                {
                    string codeTypeName;

                    if (IsInternal)
                    {
                        string moduleName = managerName.Substring(0, managerName.IndexOf('!') + 1);

                        codeTypeName = moduleName + managerName.Substring(moduleName.Length + InternalManagerNameStart.Length, managerName.Length - moduleName.Length - InternalManagerNameStart.Length - InternalManagerNameEnd.Length);
                    }
                    else if (IsExternal)
                    {
                        string moduleName = managerName.Substring(0, managerName.IndexOf('!') + 1);

                        codeTypeName = moduleName + managerName.Substring(moduleName.Length + ExternalManagerNameStart.Length, managerName.Length - moduleName.Length - ExternalManagerNameStart.Length - ExternalManagerNameEnd.Length);
                    }
                    else
                    {
                        throw new NotImplementedException();
                    }
                    valueCodeType = CodeType.Create(codeTypeName.Trim());
                }
            }
예제 #20
0
        /// <summary>
        /// Gets the runtime code type and offset to original code type.
        /// </summary>
        /// <param name="process">The process.</param>
        /// <param name="vtableAddress">The vtable address.</param>
        /// <param name="distance">The distance within the module.</param>
        public Tuple <CodeType, int> GetRuntimeCodeTypeAndOffset(Process process, ulong vtableAddress, uint distance)
        {
            IDiaSymbol symbol;
            int        displacement;
            string     fullyUndecoratedName, partiallyUndecoratedName;

            session.findSymbolByRVAEx(distance, SymTagEnum.SymTagNull, out symbol, out displacement);
            symbol.get_undecoratedNameEx(0 | 0x8000 | 0x1000, out fullyUndecoratedName);
            symbol.get_undecoratedNameEx(0 | 0x8000, out partiallyUndecoratedName);

            // Fully undecorated name should be in form: "DerivedClass::`vftable'"
            const string vftableString = "::`vftable'";

            if (string.IsNullOrEmpty(fullyUndecoratedName) || !fullyUndecoratedName.EndsWith(vftableString))
            {
                // Pointer is not vtable.
                return(null);
            }

            string   codeTypeName = fullyUndecoratedName.Substring(0, fullyUndecoratedName.Length - vftableString.Length);
            CodeType codeType     = CodeType.Create(codeTypeName, Module);

            // Partially undecorated name should be in form: "const DerivedClass::`vftable'{for `BaseClass'}"
            string partiallyUndecoratedNameStart = string.Format("const {0}{1}{{for `", codeTypeName, vftableString);

            if (!partiallyUndecoratedName.StartsWith(partiallyUndecoratedNameStart))
            {
                // Single Inheritace
                return(Tuple.Create(codeType, 0));
            }

            string innerCodeTypeName = partiallyUndecoratedName.Substring(partiallyUndecoratedNameStart.Length, partiallyUndecoratedName.Length - 2 - partiallyUndecoratedNameStart.Length);

            var baseClassWithVTable = codeType.BaseClasses[innerCodeTypeName];

            return(Tuple.Create(codeType, baseClassWithVTable.Item2));
        }
예제 #21
0
파일: Heap.cs 프로젝트: sdmaclea/SharpDebug
 /// <summary>
 /// Gets the code type for Heap for the specified process.
 /// </summary>
 /// <param name="process">The process.</param>
 public static CodeType GetCodeType(Process process)
 {
     return(CodeType.Create(process, "ntdll!_HEAP", "nt!_HEAP", "wow64!_HEAP"));
 }
예제 #22
0
 /// <summary>
 /// Gets the pointer code type for the specified process.
 /// </summary>
 /// <param name="process">The process.</param>
 private static CodeType GetPointerCodeType(Process process)
 {
     return(CodeType.Create(CodeType.NakedPointerCodeTypeName, process.Modules[0]));
 }
예제 #23
0
            /// <summary>
            /// Verifies if the specified code type is correct for this class.
            /// </summary>
            /// <param name="codeType">The code type.</param>
            /// <returns>Extracted data object or <c>null</c> if fails.</returns>
            internal static object VerifyCodeType(CodeType codeType)
            {
                // We want to have this kind of hierarchy
                // __tree_
                // | __begin_node_
                //   | __left_
                //     | __is_black_
                //     | __left_
                //     | __parent_
                //     | __right_
                // | __pair1_
                //   | __value_ (same type as __begin_node_)
                //     | __left_
                //       | __is_black_
                //       | __left_
                //       | __parent_
                //       | __right_
                // | __pair3_
                //   | __value_
                CodeType __tree_, __begin_node_, __left_, __is_black_, __left_2, __parent_, __right_, __pair1_, __value_, __pair3_, __value_2;

                if (!codeType.GetFieldTypes().TryGetValue("__tree_", out __tree_))
                {
                    return(null);
                }
                if (!__tree_.GetFieldTypes().TryGetValue("__begin_node_", out __begin_node_) || !__tree_.GetFieldTypes().TryGetValue("__pair1_", out __pair1_) || !__tree_.GetFieldTypes().TryGetValue("__pair3_", out __pair3_))
                {
                    return(null);
                }
                if (!__begin_node_.GetFieldTypes().TryGetValue("__left_", out __left_))
                {
                    return(null);
                }
                if (!__left_.GetFieldTypes().TryGetValue("__is_black_", out __is_black_) || !__left_.GetFieldTypes().TryGetValue("__left_", out __left_2) || !__left_.GetFieldTypes().TryGetValue("__parent_", out __parent_) || !__left_.GetFieldTypes().TryGetValue("__right_", out __right_))
                {
                    return(null);
                }
                if (!__pair1_.GetFieldTypes().TryGetValue("__value_", out __value_) || __value_ != __begin_node_.ElementType)
                {
                    return(null);
                }
                if (!__pair3_.GetFieldTypes().TryGetValue("__value_", out __value_2))
                {
                    return(null);
                }

                CodeType pairCodeType, treeNodeCodeType;
                string   pairFieldName;

                try
                {
                    CodeType valueCodeType = (CodeType)__tree_.TemplateArguments[0];
                    pairFieldName = valueCodeType.GetFieldTypes().ContainsKey("__nc") ? "__nc" : "__cc";
                    pairCodeType  = valueCodeType.GetFieldType(pairFieldName);
                    CodeType     treeNodeBaseCodeType  = __left_.ElementType;
                    const string treeNodeBaseNameStart = "std::__1::__tree_node_base<";
                    const string treeNodeNameStart     = "std::__1::__tree_node<";
                    string       treeNodeName          = treeNodeNameStart + valueCodeType.Name + ", " + treeNodeBaseCodeType.Name.Substring(treeNodeBaseNameStart.Length);
                    treeNodeCodeType = CodeType.Create(treeNodeName, valueCodeType.Module);
                }
                catch
                {
                    return(null);
                }

                if (!pair <TKey, TValue> .VerifyCodeType(pairCodeType))
                {
                    return(null);
                }

                return(new ExtractedData
                {
                    ReadSize = codeType.Module.Process.GetReadInt(codeType, "__tree_.__pair3_.__value_"),
                    HeadIsPointer = true,
                    HeadIsAtParent = false,
                    HeadOffset = codeType.GetFieldOffset("__tree_") + __tree_.GetFieldOffset("__pair1_") + __pair1_.GetFieldOffset("__value_") + __value_.GetFieldOffset("__left_"),
                    ItemLeftOffset = treeNodeCodeType.GetFieldOffset("__left_"),
                    ItemParentOffset = treeNodeCodeType.GetFieldOffset("__parent_"),
                    ItemRightOffset = treeNodeCodeType.GetFieldOffset("__right_"),
                    ItemValueOffset = treeNodeCodeType.GetFieldOffset("__value_") + treeNodeCodeType.GetFieldType("__value_").GetFieldOffset(pairFieldName),
                    ItemValueCodeType = pairCodeType,
                    ReadItemIsNil = null,
                    CodeType = codeType,
                    Process = codeType.Module.Process,
                });
            }