diff --git a/process.cc b/process.cc index aec16b2..8436e79 100644 --- a/process.cc +++ b/process.cc @@ -22,7 +22,17 @@ #include #include - +#if defined(__amd64__) +#define BP(regs) (regs.rbp) +#define SP(regs) (regs.rsp) +#define IP(regs) (regs.rip) +#elif defined(__i386__) +#define BP(regs) regs.ebp +#define SP(regs) regs.esp +#define IP(regs) (regs.eip) +#elif defined(__aarch64__) +#define IP(regs) (regs.pc) +#endif /* * convert a gregset_t to an Elf::CoreRegs @@ -933,30 +943,17 @@ ThreadStack::unwind(Process &p, Elf::CoreRegisters ®s, unsigned maxFrames) // For ARM, the concept is the same, but we look at the link // register rather than a pushd return address -#if defined(__amd64__) -#define BP(regs) (regs.rbp) -#define SP(regs) (regs.rsp) -#define IP(regs) (regs.rip) -#elif defined(__i386__) -#define BP(regs) regs.ebp -#define SP(regs) regs.esp -#define IP(regs) (regs.eip) -#elif defined(__aarch64__) -#define IP(regs) (regs.pc) -#endif - - auto newRegs = prev.regs; // start with a copy of prev frames regs. if (stack.size() == 1 || stack[stack.size() - 2].isSignalTrampoline) { - Dwarf::ProcessLocation prevlocation = prev.scopeIP(p); - Dwarf::ProcessLocation location(p, IP(newRegs)); - if (!prevlocation.valid() || (location.valid() && (location.codeloc->phdr_->p_flags & PF_X) == 0)) { + Dwarf::ProcessLocation badip = { p, IP(prev.regs) }; + if (!badip.valid() || (badip.codeloc->phdr_->p_flags & PF_X) == 0) { #if defined(__amd64__) || defined(__i386__) // get stack pointer in the current frame, and read content of TOS auto sp = SP(prev.regs); Elf::Addr ip; auto in = p.io->read(sp, sizeof ip, (char *)&ip); + auto newRegs = prev.regs; // start with a copy of prev frames regs. if (in == sizeof ip) { SP(newRegs) = sp + sizeof ip; IP(newRegs) = ip; // .. insn pointer. @@ -983,6 +980,7 @@ ThreadStack::unwind(Process &p, Elf::CoreRegisters ®s, unsigned maxFrames) ucontext_t uc; }; auto sigframe = p.io->readObj(prev.regs.sp); + Elf::CoreRegs newRegs; for (int i = 0; i < 31; ++i) newRegs.regs[i] = sigframe.uc.uc_mcontext.regs[i]; newRegs.sp = sigframe.uc.uc_mcontext.sp; @@ -1041,6 +1039,7 @@ ThreadStack::unwind(Process &p, Elf::CoreRegisters ®s, unsigned maxFrames) p.io->readObj(oldBp + ELF_BYTES, &newIp); p.io->readObj(oldBp, &newBp); if (newBp > oldBp && newIp > 4096) { + Elf::CoreRegisters newRegs = prev.regs; SP(newRegs) = oldBp + ELF_BYTES * 2; BP(newRegs) = newBp; IP(newRegs) = newIp;