예제 #1
0
        /// <summary>
        /// Initializes a new instance of the <see cref="Process"/> class.
        /// </summary>
        /// <param name="id">The identifier.</param>
        internal Process(uint id)
        {
            Id                     = id;
            systemId               = SimpleCache.Create(() => Context.Debugger.GetProcessSystemId(this));
            upTime                 = SimpleCache.Create(() => Context.Debugger.GetProcessUpTime(this));
            pebAddress             = SimpleCache.Create(() => Context.Debugger.GetProcessEnvironmentBlockAddress(this));
            executableName         = SimpleCache.Create(() => Context.Debugger.GetProcessExecutableName(this));
            dumpFileName           = SimpleCache.Create(() => Context.Debugger.GetProcessDumpFileName(this));
            actualProcessorType    = SimpleCache.Create(() => Context.Debugger.GetProcessActualProcessorType(this));
            effectiveProcessorType = SimpleCache.Create(() => Context.Debugger.GetProcessEffectiveProcessorType(this));
            threads                = SimpleCache.Create(() => Context.Debugger.GetProcessThreads(this));
            modules                = SimpleCache.Create(() => Context.Debugger.GetProcessModules(this));
            userTypes              = SimpleCache.Create(GetUserTypes);
            clrDataTarget          = SimpleCache.Create(() =>
            {
                var dataTarget = Microsoft.Diagnostics.Runtime.DataTarget.CreateFromDataReader(new CsDebugScript.CLR.DataReader(this));

                dataTarget.SymbolLocator.SymbolPath += ";http://symweb";
                return(dataTarget);
            });
            clrRuntimes = SimpleCache.Create(() =>
            {
                try
                {
                    return(ClrDataTarget.ClrVersions.Select(clrInfo => new Runtime(this, clrInfo.CreateRuntime())).ToArray());
                }
                catch
                {
                    return(new Runtime[0]);
                }
            });
            currentAppDomain        = SimpleCache.Create(() => ClrRuntimes.SelectMany(r => r.AppDomains).FirstOrDefault());
            ModulesByName           = new DictionaryCache <string, Module>(GetModuleByName);
            ModulesById             = new DictionaryCache <ulong, Module>(GetModuleByAddress);
            Variables               = new DictionaryCache <Tuple <CodeType, ulong, string, string>, Variable>((tuple) => new Variable(tuple.Item1, tuple.Item2, tuple.Item3, tuple.Item4));
            UserTypeCastedVariables = new DictionaryCache <Variable, Variable>((variable) => Variable.CastVariableToUserType(variable));
            GlobalCache.UserTypeCastedVariables.Add(UserTypeCastedVariables);
            ClrModuleCache = new DictionaryCache <Microsoft.Diagnostics.Runtime.ClrModule, Module>((clrModule) =>
            {
                // TODO: This needs to change when ClrModule starts to be child of Module
                Module module = ModulesById[clrModule.ImageBase];

                module.ClrModule = clrModule;
                module.ImageName = clrModule.Name;
                if (clrModule.Pdb != null && !string.IsNullOrEmpty(clrModule.Pdb.FileName))
                {
                    try
                    {
                        if (!module.SymbolFileName.ToLowerInvariant().EndsWith(".pdb"))
                        {
                            module.SymbolFileName = clrModule.Pdb.FileName;
                        }
                    }
                    catch
                    {
                        module.SymbolFileName = clrModule.Pdb.FileName;
                    }
                }
                module.Name            = Path.GetFileNameWithoutExtension(clrModule.Name);
                module.LoadedImageName = clrModule.Name;
                module.Size            = clrModule.Size;
                return(module);
            });
            dumpFileMemoryReader = SimpleCache.Create(() =>
            {
                try
                {
                    return(string.IsNullOrEmpty(DumpFileName) ? null : new DumpFileMemoryReader(DumpFileName));
                }
                catch (Exception)
                {
                    return(null);
                }
            });
            memoryRegions = SimpleCache.Create(() =>
            {
                if (DumpFileMemoryReader != null)
                {
                    return(DumpFileMemoryReader.GetMemoryRanges());
                }
                else
                {
                    return(Context.Debugger.GetMemoryRegions(this));
                }
            });
            memoryRegionFinder        = SimpleCache.Create(() => new MemoryRegionFinder(MemoryRegions));
            TypeToUserTypeDescription = new DictionaryCache <Type, UserTypeDescription[]>(GetUserTypeDescription);
            ansiStringCache           = new DictionaryCache <Tuple <ulong, int>, string>(DoReadAnsiString);
            unicodeStringCache        = new DictionaryCache <Tuple <ulong, int>, string>(DoReadUnicodeString);
        }
예제 #2
0
        /// <summary>
        /// Initializes a new instance of the <see cref="Process"/> class.
        /// </summary>
        /// <param name="id">The identifier.</param>
        internal Process(uint id)
        {
            Id               = id;
            systemId         = SimpleCache.Create(() => Context.Debugger.GetProcessSystemId(this));
            upTime           = SimpleCache.Create(() => Context.Debugger.GetProcessUpTime(this));
            pebAddress       = SimpleCache.Create(() => Context.Debugger.GetProcessEnvironmentBlockAddress(this));
            executableName   = SimpleCache.Create(() => Context.Debugger.GetProcessExecutableName(this));
            dumpFileName     = SimpleCache.Create(() => Context.Debugger.GetProcessDumpFileName(this));
            architectureType = SimpleCache.Create(() => Context.Debugger.GetProcessArchitectureType(this));
            threads          = SimpleCache.Create(() => Context.Debugger.GetProcessThreads(this));
            modules          = SimpleCache.Create(() => Context.Debugger.GetProcessModules(this));
            userTypes        = SimpleCache.Create(GetUserTypes);
            clrRuntimes      = SimpleCache.Create(() =>
            {
                try
                {
                    if (Context.ClrProvider != null)
                    {
                        return(Context.ClrProvider.GetClrRuntimes(this));
                    }
                }
                catch
                {
                }
                return(new IClrRuntime[0]);
            });
            currentAppDomain        = SimpleCache.Create(() => ClrRuntimes.SelectMany(r => r.AppDomains).FirstOrDefault());
            ModulesByName           = new DictionaryCache <string, Module>(GetModuleByName);
            ModulesById             = new DictionaryCache <ulong, Module>(GetModuleByAddress);
            Variables               = new DictionaryCache <Tuple <CodeType, ulong, string, string>, Variable>((tuple) => new Variable(tuple.Item1, tuple.Item2, tuple.Item3, tuple.Item4));
            UserTypeCastedVariables = new DictionaryCache <Variable, Variable>((variable) => Variable.CastVariableToUserType(variable));
            GlobalCache.UserTypeCastedVariables.Add(UserTypeCastedVariables);
            ClrModuleCache = new DictionaryCache <IClrModule, Module>((clrModule) =>
            {
                // TODO: This needs to change when ClrModule starts to be child of Module
                Module module = ModulesById[clrModule.ImageBase];

                module.ClrModule = clrModule;
                module.ImageName = clrModule.Name;
                if (!string.IsNullOrEmpty(clrModule.PdbFileName))
                {
                    try
                    {
                        if (!module.SymbolFileName.ToLowerInvariant().EndsWith(".pdb"))
                        {
                            module.SymbolFileName = clrModule.PdbFileName;
                        }
                    }
                    catch
                    {
                        module.SymbolFileName = clrModule.PdbFileName;
                    }
                }
                module.Name            = Path.GetFileNameWithoutExtension(clrModule.Name);
                module.LoadedImageName = clrModule.Name;
                module.Size            = clrModule.Size;
                return(module);
            });
            dumpFileMemoryReader = SimpleCache.Create(() =>
            {
                try
                {
                    return(Context.Debugger.GetDumpFileMemoryReader(this));
                }
                catch (Exception)
                {
                    return(null);
                }
            });
            memoryRegions = SimpleCache.Create(() =>
            {
                if (DumpFileMemoryReader != null)
                {
                    return(DumpFileMemoryReader.GetMemoryRanges());
                }
                else
                {
                    return(Context.Debugger.GetMemoryRegions(this));
                }
            });
            memoryRegionFinder        = SimpleCache.Create(() => new MemoryRegionFinder(MemoryRegions));
            TypeToUserTypeDescription = new DictionaryCache <Type, UserTypeDescription[]>(GetUserTypeDescription);
            ansiStringCache           = new DictionaryCache <Tuple <ulong, int>, string>(DoReadAnsiString);
            unicodeStringCache        = new DictionaryCache <Tuple <ulong, int>, string>(DoReadUnicodeString);
            wideUnicodeStringCache    = new DictionaryCache <Tuple <ulong, int>, string>(DoReadWideUnicodeString);
        }
예제 #3
0
            /// <summary>
            /// Gets the thread stack trace.
            /// </summary>
            /// <param name="threadIndex">Index of the thread.</param>
            /// <param name="dumpFileMemoryReader">The dump file memory reader.</param>
            /// <param name="process">Process being debugged.</param>
            /// <param name="symbolProvider">The symbol provider.</param>
            /// <returns>Array of tuples of instruction offset, stack offset and frame offset.</returns>
            public Tuple <ulong, ulong, ulong>[] GetThreadStackTrace(int threadIndex, DumpFileMemoryReader dumpFileMemoryReader, Process process, DwarfSymbolProvider symbolProvider)
            {
                const int    pointerSize = 8;
                elf_prstatus prstatus    = threads[threadIndex];
                ulong        bp          = prstatus.pr_reg[X64RegisterIndex.RBP];
                ulong        ip          = prstatus.pr_reg[X64RegisterIndex.RIP];
                List <Tuple <ulong, ulong, ulong> > result = new List <Tuple <ulong, ulong, ulong> >();
                ulong segmentStartAddress, segmentSize;

                dumpFileMemoryReader.GetMemoryRange(bp, out segmentStartAddress, out segmentSize);
                while (bp >= segmentStartAddress && bp < segmentStartAddress + segmentSize)
                {
                    result.Add(Tuple.Create(ip, bp, bp));

                    ulong  savedLocationForRegisters = bp;
                    Module module = process.GetModuleByInnerAddress(ip);

                    if (module != null)
                    {
                        DwarfSymbolProviderModule symbolProviderModule = symbolProvider.GetSymbolProviderModule(module) as DwarfSymbolProviderModule;

                        if (symbolProviderModule != null)
                        {
                            ThreadContext frameContext          = new ThreadContext(ip, bp, bp, null);
                            ulong         canonicalFrameAddress = symbolProviderModule.GetFunctionCanonicalFrameAddress(process, ip, frameContext);

                            if (canonicalFrameAddress != 0)
                            {
                                savedLocationForRegisters = canonicalFrameAddress - pointerSize * 2;
                            }
                        }
                    }

                    MemoryBuffer buffer = dumpFileMemoryReader.ReadMemory(savedLocationForRegisters, pointerSize * 2);
                    bp = UserType.ReadPointer(buffer, 0, pointerSize);
                    ip = UserType.ReadPointer(buffer, pointerSize, pointerSize);
                }
                return(result.ToArray());
            }