提交 3c8d4d52 编写于 作者: A aarzilli 提交者: Derek Parker

*: un-export unnecessarily public symbols

上级 1ee8d5c2
......@@ -53,7 +53,7 @@ func (fde *FrameDescriptionEntry) EstablishFrame(pc uint64) *FrameContext {
type FrameDescriptionEntries []*FrameDescriptionEntry
func NewFrameIndex() FrameDescriptionEntries {
func newFrameIndex() FrameDescriptionEntries {
return make(FrameDescriptionEntries, 0, 1000)
}
......
......@@ -13,7 +13,7 @@ func ptrSizeByRuntimeArch() int {
}
func TestFDEForPC(t *testing.T) {
frames := NewFrameIndex()
frames := newFrameIndex()
frames = append(frames,
&FrameDescriptionEntry{begin: 10, size: 40},
&FrameDescriptionEntry{begin: 50, size: 50},
......
......@@ -29,7 +29,7 @@ type parseContext struct {
func Parse(data []byte, order binary.ByteOrder, staticBase uint64, ptrSize int) FrameDescriptionEntries {
var (
buf = bytes.NewBuffer(data)
pctx = &parseContext{buf: buf, entries: NewFrameIndex(), staticBase: staticBase, ptrSize: ptrSize}
pctx = &parseContext{buf: buf, entries: newFrameIndex(), staticBase: staticBase, ptrSize: ptrSize}
)
for fn := parselength; buf.Len() != 0; {
......
......@@ -127,7 +127,7 @@ func executeCIEInstructions(cie *CommonInformationEntry) *FrameContext {
buf: bytes.NewBuffer(initialInstructions),
}
frame.ExecuteDwarfProgram()
frame.executeDwarfProgram()
return frame
}
......@@ -142,7 +142,7 @@ func executeDwarfProgramUntilPC(fde *FrameDescriptionEntry, pc uint64) *FrameCon
return frame
}
func (frame *FrameContext) ExecuteDwarfProgram() {
func (frame *FrameContext) executeDwarfProgram() {
for frame.buf.Len() > 0 {
executeDwarfInstruction(frame)
}
......
......@@ -9,7 +9,7 @@ import (
"github.com/go-delve/delve/pkg/proc"
)
// A SplicedMemory represents a memory space formed from multiple regions,
// A splicedMemory represents a memory space formed from multiple regions,
// each of which may override previously regions. For example, in the following
// core, the program text was loaded at 0x400000:
// Start End Page Offset
......@@ -22,7 +22,7 @@ import (
// 0x0000000000002000 0x0000000000002000 RW 1000
// This can be represented in a SplicedMemory by adding the original region,
// then putting the RW mapping on top of it.
type SplicedMemory struct {
type splicedMemory struct {
readers []readerEntry
}
......@@ -33,7 +33,7 @@ type readerEntry struct {
}
// Add adds a new region to the SplicedMemory, which may override existing regions.
func (r *SplicedMemory) Add(reader proc.MemoryReader, off, length uintptr) {
func (r *splicedMemory) Add(reader proc.MemoryReader, off, length uintptr) {
if length == 0 {
return
}
......@@ -93,7 +93,7 @@ func (r *SplicedMemory) Add(reader proc.MemoryReader, off, length uintptr) {
}
// ReadMemory implements MemoryReader.ReadMemory.
func (r *SplicedMemory) ReadMemory(buf []byte, addr uintptr) (n int, err error) {
func (r *splicedMemory) ReadMemory(buf []byte, addr uintptr) (n int, err error) {
started := false
for _, entry := range r.readers {
if entry.offset+entry.length < addr {
......@@ -132,40 +132,40 @@ func (r *SplicedMemory) ReadMemory(buf []byte, addr uintptr) (n int, err error)
return n, nil
}
// OffsetReaderAt wraps a ReaderAt into a MemoryReader, subtracting a fixed
// offsetReaderAt wraps a ReaderAt into a MemoryReader, subtracting a fixed
// offset from the address. This is useful to represent a mapping in an address
// space. For example, if program text is mapped in at 0x400000, an
// OffsetReaderAt with offset 0x400000 can be wrapped around file.Open(program)
// to return the results of a read in that part of the address space.
type OffsetReaderAt struct {
type offsetReaderAt struct {
reader io.ReaderAt
offset uintptr
}
// ReadMemory will read the memory at addr-offset.
func (r *OffsetReaderAt) ReadMemory(buf []byte, addr uintptr) (n int, err error) {
func (r *offsetReaderAt) ReadMemory(buf []byte, addr uintptr) (n int, err error) {
return r.reader.ReadAt(buf, int64(addr-r.offset))
}
// Process represents a core file.
type Process struct {
// process represents a core file.
type process struct {
mem proc.MemoryReader
Threads map[int]*Thread
Threads map[int]*thread
pid int
entryPoint uint64
bi *proc.BinaryInfo
breakpoints proc.BreakpointMap
currentThread *Thread
currentThread *thread
}
var _ proc.ProcessInternal = &Process{}
var _ proc.ProcessInternal = &process{}
// Thread represents a thread in the core file being debugged.
type Thread struct {
// thread represents a thread in the core file being debugged.
type thread struct {
th osThread
p *Process
p *process
common proc.CommonThread
}
......@@ -189,7 +189,7 @@ var (
ErrChangeRegisterCore = errors.New("can not change register values of core process")
)
type openFn func(string, string) (*Process, error)
type openFn func(string, string) (*process, error)
var openFns = []openFn{readLinuxCore, readAMD64Minidump}
......@@ -201,7 +201,7 @@ var ErrUnrecognizedFormat = errors.New("unrecognized core format")
// If the DWARF information cannot be found in the binary, Delve will look
// for external debug files in the directories passed in.
func OpenCore(corePath, exePath string, debugInfoDirs []string) (*proc.Target, error) {
var p *Process
var p *process
var err error
for _, openFn := range openFns {
p, err = openFn(corePath, exePath)
......@@ -222,49 +222,49 @@ func OpenCore(corePath, exePath string, debugInfoDirs []string) (*proc.Target, e
}
// BinInfo will return the binary info.
func (p *Process) BinInfo() *proc.BinaryInfo {
func (p *process) BinInfo() *proc.BinaryInfo {
return p.bi
}
// EntryPoint will return the entry point address for this core file.
func (p *Process) EntryPoint() (uint64, error) {
func (p *process) EntryPoint() (uint64, error) {
return p.entryPoint, nil
}
// writeBreakpoint is a noop function since you
// cannot write breakpoints into core files.
func (p *Process) writeBreakpoint(addr uint64) (file string, line int, fn *proc.Function, originalData []byte, err error) {
func (p *process) writeBreakpoint(addr uint64) (file string, line int, fn *proc.Function, originalData []byte, err error) {
return "", 0, nil, nil, errors.New("cannot write a breakpoint to a core file")
}
// Recorded returns whether this is a live or recorded process. Always returns true for core files.
func (p *Process) Recorded() (bool, string) { return true, "" }
func (p *process) Recorded() (bool, string) { return true, "" }
// Restart will only return an error for core files, as they are not executing.
func (p *Process) Restart(string) error { return ErrContinueCore }
func (p *process) Restart(string) error { return ErrContinueCore }
// ChangeDirection will only return an error as you cannot continue a core process.
func (p *Process) ChangeDirection(proc.Direction) error { return ErrContinueCore }
func (p *process) ChangeDirection(proc.Direction) error { return ErrContinueCore }
// GetDirection will always return forward.
func (p *Process) GetDirection() proc.Direction { return proc.Forward }
func (p *process) GetDirection() proc.Direction { return proc.Forward }
// When does not apply to core files, it is to support the Mozilla 'rr' backend.
func (p *Process) When() (string, error) { return "", nil }
func (p *process) When() (string, error) { return "", nil }
// Checkpoint for core files returns an error, there is no execution of a core file.
func (p *Process) Checkpoint(string) (int, error) { return -1, ErrContinueCore }
func (p *process) Checkpoint(string) (int, error) { return -1, ErrContinueCore }
// Checkpoints returns nil on core files, you cannot set checkpoints when debugging core files.
func (p *Process) Checkpoints() ([]proc.Checkpoint, error) { return nil, nil }
func (p *process) Checkpoints() ([]proc.Checkpoint, error) { return nil, nil }
// ClearCheckpoint clears a checkpoint, but will only return an error for core files.
func (p *Process) ClearCheckpoint(int) error { return errors.New("checkpoint not found") }
func (p *process) ClearCheckpoint(int) error { return errors.New("checkpoint not found") }
// ReadMemory will return memory from the core file at the specified location and put the
// read memory into `data`, returning the length read, and returning an error if
// the length read is shorter than the length of the `data` buffer.
func (t *Thread) ReadMemory(data []byte, addr uintptr) (n int, err error) {
func (t *thread) ReadMemory(data []byte, addr uintptr) (n int, err error) {
n, err = t.p.mem.ReadMemory(data, addr)
if err == nil && n != len(data) {
err = ErrShortRead
......@@ -274,13 +274,13 @@ func (t *Thread) ReadMemory(data []byte, addr uintptr) (n int, err error) {
// WriteMemory will only return an error for core files, you cannot write
// to the memory of a core process.
func (t *Thread) WriteMemory(addr uintptr, data []byte) (int, error) {
func (t *thread) WriteMemory(addr uintptr, data []byte) (int, error) {
return 0, ErrWriteCore
}
// Location returns the location of this thread based on
// the value of the instruction pointer register.
func (t *Thread) Location() (*proc.Location, error) {
func (t *thread) Location() (*proc.Location, error) {
regs, err := t.th.registers(false)
if err != nil {
return nil, err
......@@ -293,150 +293,150 @@ func (t *Thread) Location() (*proc.Location, error) {
// Breakpoint returns the current breakpoint this thread is stopped at.
// For core files this always returns an empty BreakpointState struct, as
// there are no breakpoints when debugging core files.
func (t *Thread) Breakpoint() *proc.BreakpointState {
func (t *thread) Breakpoint() *proc.BreakpointState {
return &proc.BreakpointState{}
}
// ThreadID returns the ID for this thread.
func (t *Thread) ThreadID() int {
func (t *thread) ThreadID() int {
return int(t.th.pid())
}
// Registers returns the current value of the registers for this thread.
func (t *Thread) Registers(floatingPoint bool) (proc.Registers, error) {
func (t *thread) Registers(floatingPoint bool) (proc.Registers, error) {
return t.th.registers(floatingPoint)
}
// RestoreRegisters will only return an error for core files,
// you cannot change register values for core files.
func (t *Thread) RestoreRegisters(proc.Registers) error {
func (t *thread) RestoreRegisters(proc.Registers) error {
return ErrChangeRegisterCore
}
// BinInfo returns information about the binary.
func (t *Thread) BinInfo() *proc.BinaryInfo {
func (t *thread) BinInfo() *proc.BinaryInfo {
return t.p.bi
}
// StepInstruction will only return an error for core files,
// you cannot execute a core file.
func (t *Thread) StepInstruction() error {
func (t *thread) StepInstruction() error {
return ErrContinueCore
}
// Blocked will return false always for core files as there is
// no execution.
func (t *Thread) Blocked() bool {
func (t *thread) Blocked() bool {
return false
}
// SetCurrentBreakpoint will always just return nil
// for core files, as there are no breakpoints in core files.
func (t *Thread) SetCurrentBreakpoint(adjustPC bool) error {
func (t *thread) SetCurrentBreakpoint(adjustPC bool) error {
return nil
}
// Common returns a struct containing common information
// across thread implementations.
func (t *Thread) Common() *proc.CommonThread {
func (t *thread) Common() *proc.CommonThread {
return &t.common
}
// SetPC will always return an error, you cannot
// change register values when debugging core files.
func (t *Thread) SetPC(uint64) error {
func (t *thread) SetPC(uint64) error {
return ErrChangeRegisterCore
}
// SetSP will always return an error, you cannot
// change register values when debugging core files.
func (t *Thread) SetSP(uint64) error {
func (t *thread) SetSP(uint64) error {
return ErrChangeRegisterCore
}
// SetDX will always return an error, you cannot
// change register values when debugging core files.
func (t *Thread) SetDX(uint64) error {
func (t *thread) SetDX(uint64) error {
return ErrChangeRegisterCore
}
// Breakpoints will return all breakpoints for the process.
func (p *Process) Breakpoints() *proc.BreakpointMap {
func (p *process) Breakpoints() *proc.BreakpointMap {
return &p.breakpoints
}
// ClearBreakpoint will always return an error as you cannot set or clear
// breakpoints on core files.
func (p *Process) ClearBreakpoint(addr uint64) (*proc.Breakpoint, error) {
func (p *process) ClearBreakpoint(addr uint64) (*proc.Breakpoint, error) {
return nil, proc.NoBreakpointError{Addr: addr}
}
// ClearInternalBreakpoints will always return nil and have no
// effect since you cannot set breakpoints on core files.
func (p *Process) ClearInternalBreakpoints() error {
func (p *process) ClearInternalBreakpoints() error {
return nil
}
// ContinueOnce will always return an error because you
// cannot control execution of a core file.
func (p *Process) ContinueOnce() (proc.Thread, proc.StopReason, error) {
func (p *process) ContinueOnce() (proc.Thread, proc.StopReason, error) {
return nil, proc.StopUnknown, ErrContinueCore
}
// StepInstruction will always return an error
// as you cannot control execution of a core file.
func (p *Process) StepInstruction() error {
func (p *process) StepInstruction() error {
return ErrContinueCore
}
// RequestManualStop will return nil and have no effect
// as you cannot control execution of a core file.
func (p *Process) RequestManualStop() error {
func (p *process) RequestManualStop() error {
return nil
}
// CheckAndClearManualStopRequest will always return false and
// have no effect since there are no manual stop requests as
// there is no controlling execution of a core file.
func (p *Process) CheckAndClearManualStopRequest() bool {
func (p *process) CheckAndClearManualStopRequest() bool {
return false
}
// CurrentThread returns the current active thread.
func (p *Process) CurrentThread() proc.Thread {
func (p *process) CurrentThread() proc.Thread {
return p.currentThread
}
// Detach will always return nil and have no
// effect as you cannot detach from a core file
// and have it continue execution or exit.
func (p *Process) Detach(bool) error {
func (p *process) Detach(bool) error {
return nil
}
// Valid returns whether the process is active. Always returns true
// for core files as it cannot exit or be otherwise detached from.
func (p *Process) Valid() (bool, error) {
func (p *process) Valid() (bool, error) {
return true, nil
}
// Pid returns the process ID of this process.
func (p *Process) Pid() int {
func (p *process) Pid() int {
return p.pid
}
// ResumeNotify is a no-op on core files as we cannot
// control execution.
func (p *Process) ResumeNotify(chan<- struct{}) {
func (p *process) ResumeNotify(chan<- struct{}) {
}
// SetBreakpoint will always return an error for core files as you cannot write memory or control execution.
func (p *Process) SetBreakpoint(addr uint64, kind proc.BreakpointKind, cond ast.Expr) (*proc.Breakpoint, error) {
func (p *process) SetBreakpoint(addr uint64, kind proc.BreakpointKind, cond ast.Expr) (*proc.Breakpoint, error) {
return nil, ErrWriteCore
}
// ThreadList will return a list of all threads currently in the process.
func (p *Process) ThreadList() []proc.Thread {
func (p *process) ThreadList() []proc.Thread {
r := make([]proc.Thread, 0, len(p.Threads))
for _, v := range p.Threads {
r = append(r, v)
......@@ -445,12 +445,12 @@ func (p *Process) ThreadList() []proc.Thread {
}
// FindThread will return the thread with the corresponding thread ID.
func (p *Process) FindThread(threadID int) (proc.Thread, bool) {
func (p *process) FindThread(threadID int) (proc.Thread, bool) {
t, ok := p.Threads[threadID]
return t, ok
}
// SetCurrentThread is used internally by proc.Target to change the current thread.
func (p *Process) SetCurrentThread(th proc.Thread) {
p.currentThread = th.(*Thread)
func (p *process) SetCurrentThread(th proc.Thread) {
p.currentThread = th.(*thread)
}
......@@ -134,10 +134,10 @@ func TestSplicedReader(t *testing.T) {
}
for _, test := range tests {
t.Run(test.name, func(t *testing.T) {
mem := &SplicedMemory{}
mem := &splicedMemory{}
for _, region := range test.regions {
r := bytes.NewReader(region.data)
mem.Add(&OffsetReaderAt{r, 0}, region.off, region.length)
mem.Add(&offsetReaderAt{r, 0}, region.off, region.length)
}
got := make([]byte, test.readLen)
n, err := mem.ReadMemory(got, test.readAddr)
......
......@@ -15,68 +15,68 @@ import (
// Copied from golang.org/x/sys/unix.Timeval since it's not available on all
// systems.
type LinuxCoreTimeval struct {
type linuxCoreTimeval struct {
Sec int64
Usec int64
}
// NT_FILE is file mapping information, e.g. program text mappings. Desc is a LinuxNTFile.
const NT_FILE elf.NType = 0x46494c45 // "FILE".
const _NT_FILE elf.NType = 0x46494c45 // "FILE".
// NT_X86_XSTATE is other registers, including AVX and such.
const NT_X86_XSTATE elf.NType = 0x202 // Note type for notes containing X86 XSAVE area.
const _NT_X86_XSTATE elf.NType = 0x202 // Note type for notes containing X86 XSAVE area.
// NT_AUXV is the note type for notes containing a copy of the Auxv array
const NT_AUXV elf.NType = 0x6
const _NT_AUXV elf.NType = 0x6
// NT_FPREGSET is the note type for floating point registers.
const NT_FPREGSET elf.NType = 0x2
const _NT_FPREGSET elf.NType = 0x2
// Fetch architecture using exeELF.Machine from core file
// Refer http://man7.org/linux/man-pages/man5/elf.5.html
const (
EM_AARCH64 = 183
EM_X86_64 = 62
_EM_AARCH64 = 183
_EM_X86_64 = 62
_ARM_FP_HEADER_START = 512
)
const elfErrorBadMagicNumber = "bad magic number"
func linuxThreadsFromNotes(p *Process, notes []*Note, machineType elf.Machine) {
func linuxThreadsFromNotes(p *process, notes []*note, machineType elf.Machine) {
var lastThreadAMD *linuxAMD64Thread
var lastThreadARM *linuxARM64Thread
for _, note := range notes {
switch note.Type {
case elf.NT_PRSTATUS:
if machineType == EM_X86_64 {
t := note.Desc.(*LinuxPrStatusAMD64)
if machineType == _EM_X86_64 {
t := note.Desc.(*linuxPrStatusAMD64)
lastThreadAMD = &linuxAMD64Thread{linutil.AMD64Registers{Regs: &t.Reg}, t}
p.Threads[int(t.Pid)] = &Thread{lastThreadAMD, p, proc.CommonThread{}}
p.Threads[int(t.Pid)] = &thread{lastThreadAMD, p, proc.CommonThread{}}
if p.currentThread == nil {
p.currentThread = p.Threads[int(t.Pid)]
}
} else if machineType == EM_AARCH64 {
t := note.Desc.(*LinuxPrStatusARM64)
} else if machineType == _EM_AARCH64 {
t := note.Desc.(*linuxPrStatusARM64)
lastThreadARM = &linuxARM64Thread{linutil.ARM64Registers{Regs: &t.Reg}, t}
p.Threads[int(t.Pid)] = &Thread{lastThreadARM, p, proc.CommonThread{}}
p.Threads[int(t.Pid)] = &thread{lastThreadARM, p, proc.CommonThread{}}
if p.currentThread == nil {
p.currentThread = p.Threads[int(t.Pid)]
}
}
case NT_FPREGSET:
if machineType == EM_AARCH64 {
case _NT_FPREGSET:
if machineType == _EM_AARCH64 {
if lastThreadARM != nil {
lastThreadARM.regs.Fpregs = note.Desc.(*linutil.ARM64PtraceFpRegs).Decode()
}
}
case NT_X86_XSTATE:
if machineType == EM_X86_64 {
case _NT_X86_XSTATE:
if machineType == _EM_X86_64 {
if lastThreadAMD != nil {
lastThreadAMD.regs.Fpregs = note.Desc.(*linutil.AMD64Xstate).Decode()
}
}
case elf.NT_PRPSINFO:
p.pid = int(note.Desc.(*LinuxPrPsInfo).Pid)
p.pid = int(note.Desc.(*linuxPrPsInfo).Pid)
}
}
}
......@@ -87,7 +87,7 @@ func linuxThreadsFromNotes(p *Process, notes []*Note, machineType elf.Machine) {
// http://uhlo.blogspot.fr/2012/05/brief-look-into-core-dumps.html,
// elf_core_dump in http://lxr.free-electrons.com/source/fs/binfmt_elf.c,
// and, if absolutely desperate, readelf.c from the binutils source.
func readLinuxCore(corePath, exePath string) (*Process, error) {
func readLinuxCore(corePath, exePath string) (*process, error) {
coreFile, err := elf.Open(corePath)
if err != nil {
if _, isfmterr := err.(*elf.FormatError); isfmterr && (strings.Contains(err.Error(), elfErrorBadMagicNumber) || strings.Contains(err.Error(), " at offset 0x0: too short")) {
......@@ -122,9 +122,9 @@ func readLinuxCore(corePath, exePath string) (*Process, error) {
// TODO support 386
var bi *proc.BinaryInfo
switch machineType {
case EM_X86_64:
case _EM_X86_64:
bi = proc.NewBinaryInfo("linux", "amd64")
case EM_AARCH64:
case _EM_AARCH64:
bi = proc.NewBinaryInfo("linux", "arm64")
default:
return nil, fmt.Errorf("unsupported machine type")
......@@ -132,9 +132,9 @@ func readLinuxCore(corePath, exePath string) (*Process, error) {
entryPoint := findEntryPoint(notes, bi.Arch.PtrSize())
p := &Process{
p := &process{
mem: memory,
Threads: map[int]*Thread{},
Threads: map[int]*thread{},
entryPoint: entryPoint,
bi: bi,
breakpoints: proc.NewBreakpointMap(),
......@@ -146,12 +146,12 @@ func readLinuxCore(corePath, exePath string) (*Process, error) {
type linuxAMD64Thread struct {
regs linutil.AMD64Registers
t *LinuxPrStatusAMD64
t *linuxPrStatusAMD64
}
type linuxARM64Thread struct {
regs linutil.ARM64Registers
t *LinuxPrStatusARM64
t *linuxPrStatusARM64
}
func (t *linuxAMD64Thread) registers(floatingPoint bool) (proc.Registers, error) {
......@@ -187,14 +187,14 @@ func (t *linuxARM64Thread) pid() int {
// - NT_PRSTATUS: Information about a thread, including base registers, state, etc. Desc is a LinuxPrStatus.
// - NT_FPREGSET (Not implemented): x87 floating point registers.
// - NT_X86_XSTATE: Other registers, including AVX and such.
type Note struct {
type note struct {
Type elf.NType
Name string
Desc interface{} // Decoded Desc from the
}
// readNotes reads all the notes from the notes prog in core.
func readNotes(core *elf.File, machineType elf.Machine) ([]*Note, error) {
func readNotes(core *elf.File, machineType elf.Machine) ([]*note, error) {
var notesProg *elf.Prog
for _, prog := range core.Progs {
if prog.Type == elf.PT_NOTE {
......@@ -204,7 +204,7 @@ func readNotes(core *elf.File, machineType elf.Machine) ([]*Note, error) {
}
r := notesProg.Open()
notes := []*Note{}
notes := []*note{}
for {
note, err := readNote(r, machineType)
if err == io.EOF {
......@@ -220,11 +220,11 @@ func readNotes(core *elf.File, machineType elf.Machine) ([]*Note, error) {
}
// readNote reads a single note from r, decoding the descriptor if possible.
func readNote(r io.ReadSeeker, machineType elf.Machine) (*Note, error) {
func readNote(r io.ReadSeeker, machineType elf.Machine) (*note, error) {
// Notes are laid out as described in the SysV ABI:
// http://www.sco.com/developers/gabi/latest/ch5.pheader.html#note_section
note := &Note{}
hdr := &ELFNotesHdr{}
note := &note{}
hdr := &elfNotesHdr{}
err := binary.Read(r, binary.LittleEndian, hdr)
if err != nil {
......@@ -247,10 +247,10 @@ func readNote(r io.ReadSeeker, machineType elf.Machine) (*Note, error) {
descReader := bytes.NewReader(desc)
switch note.Type {
case elf.NT_PRSTATUS:
if machineType == EM_X86_64 {
note.Desc = &LinuxPrStatusAMD64{}
} else if machineType == EM_AARCH64 {
note.Desc = &LinuxPrStatusARM64{}
if machineType == _EM_X86_64 {
note.Desc = &linuxPrStatusAMD64{}
} else if machineType == _EM_AARCH64 {
note.Desc = &linuxPrStatusARM64{}
} else {
return nil, fmt.Errorf("unsupported machine type")
}
......@@ -258,39 +258,39 @@ func readNote(r io.ReadSeeker, machineType elf.Machine) (*Note, error) {
return nil, fmt.Errorf("reading NT_PRSTATUS: %v", err)
}
case elf.NT_PRPSINFO:
note.Desc = &LinuxPrPsInfo{}
note.Desc = &linuxPrPsInfo{}
if err := binary.Read(descReader, binary.LittleEndian, note.Desc); err != nil {
return nil, fmt.Errorf("reading NT_PRPSINFO: %v", err)
}
case NT_FILE:
case _NT_FILE:
// No good documentation reference, but the structure is
// simply a header, including entry count, followed by that
// many entries, and then the file name of each entry,
// null-delimited. Not reading the names here.
data := &LinuxNTFile{}
if err := binary.Read(descReader, binary.LittleEndian, &data.LinuxNTFileHdr); err != nil {
data := &linuxNTFile{}
if err := binary.Read(descReader, binary.LittleEndian, &data.linuxNTFileHdr); err != nil {
return nil, fmt.Errorf("reading NT_FILE header: %v", err)
}
for i := 0; i < int(data.Count); i++ {
entry := &LinuxNTFileEntry{}
entry := &linuxNTFileEntry{}
if err := binary.Read(descReader, binary.LittleEndian, entry); err != nil {
return nil, fmt.Errorf("reading NT_FILE entry %v: %v", i, err)
}
data.entries = append(data.entries, entry)
}
note.Desc = data
case NT_X86_XSTATE:
if machineType == EM_X86_64 {
case _NT_X86_XSTATE:
if machineType == _EM_X86_64 {
var fpregs linutil.AMD64Xstate
if err := linutil.AMD64XstateRead(desc, true, &fpregs); err != nil {
return nil, err
}
note.Desc = &fpregs
}
case NT_AUXV:
case _NT_AUXV:
note.Desc = desc
case NT_FPREGSET:
if machineType == EM_AARCH64 {
case _NT_FPREGSET:
if machineType == _EM_AARCH64 {
fpregs := &linutil.ARM64PtraceFpRegs{}
rdr := bytes.NewReader(desc[:_ARM_FP_HEADER_START])
if err := binary.Read(rdr, binary.LittleEndian, fpregs.Byte()); err != nil {
......@@ -320,15 +320,15 @@ func skipPadding(r io.ReadSeeker, pad int64) error {
return nil
}
func buildMemory(core, exeELF *elf.File, exe io.ReaderAt, notes []*Note) proc.MemoryReader {
memory := &SplicedMemory{}
func buildMemory(core, exeELF *elf.File, exe io.ReaderAt, notes []*note) proc.MemoryReader {
memory := &splicedMemory{}
// For now, assume all file mappings are to the exe.
for _, note := range notes {
if note.Type == NT_FILE {
fileNote := note.Desc.(*LinuxNTFile)
if note.Type == _NT_FILE {
fileNote := note.Desc.(*linuxNTFile)
for _, entry := range fileNote.entries {
r := &OffsetReaderAt{
r := &offsetReaderAt{
reader: exe,
offset: uintptr(entry.Start - (entry.FileOfs * fileNote.PageSize)),
}
......@@ -346,7 +346,7 @@ func buildMemory(core, exeELF *elf.File, exe io.ReaderAt, notes []*Note) proc.Me
if prog.Filesz == 0 {
continue
}
r := &OffsetReaderAt{
r := &offsetReaderAt{
reader: prog.ReaderAt,
offset: uintptr(prog.Vaddr),
}
......@@ -357,9 +357,9 @@ func buildMemory(core, exeELF *elf.File, exe io.ReaderAt, notes []*Note) proc.Me
return memory
}
func findEntryPoint(notes []*Note, ptrSize int) uint64 {
func findEntryPoint(notes []*note, ptrSize int) uint64 {
for _, note := range notes {
if note.Type == NT_AUXV {
if note.Type == _NT_AUXV {
return linutil.EntryPointFromAuxv(note.Desc.([]byte), ptrSize)
}
}
......@@ -370,7 +370,7 @@ func findEntryPoint(notes []*Note, ptrSize int) uint64 {
// AMD64 specific primarily because of unix.PtraceRegs, but also
// because some of the fields are word sized.
// See http://lxr.free-electrons.com/source/include/uapi/linux/elfcore.h
type LinuxPrPsInfo struct {
type linuxPrPsInfo struct {
State uint8
Sname int8
Zomb uint8
......@@ -384,61 +384,61 @@ type LinuxPrPsInfo struct {
}
// LinuxPrStatusAMD64 is a copy of the prstatus kernel struct.
type LinuxPrStatusAMD64 struct {
Siginfo LinuxSiginfo
type linuxPrStatusAMD64 struct {
Siginfo linuxSiginfo
Cursig uint16
_ [2]uint8
Sigpend uint64
Sighold uint64
Pid, Ppid, Pgrp, Sid int32
Utime, Stime, CUtime, CStime LinuxCoreTimeval
Utime, Stime, CUtime, CStime linuxCoreTimeval
Reg linutil.AMD64PtraceRegs
Fpvalid int32
}
// LinuxPrStatusARM64 is a copy of the prstatus kernel struct.
type LinuxPrStatusARM64 struct {
Siginfo LinuxSiginfo
type linuxPrStatusARM64 struct {
Siginfo linuxSiginfo
Cursig uint16
_ [2]uint8
Sigpend uint64
Sighold uint64
Pid, Ppid, Pgrp, Sid int32
Utime, Stime, CUtime, CStime LinuxCoreTimeval
Utime, Stime, CUtime, CStime linuxCoreTimeval
Reg linutil.ARM64PtraceRegs
Fpvalid int32
}
// LinuxSiginfo is a copy of the
// siginfo kernel struct.
type LinuxSiginfo struct {
type linuxSiginfo struct {
Signo int32
Code int32
Errno int32
}
// LinuxNTFile contains information on mapped files.
type LinuxNTFile struct {
LinuxNTFileHdr
entries []*LinuxNTFileEntry
type linuxNTFile struct {
linuxNTFileHdr
entries []*linuxNTFileEntry
}
// LinuxNTFileHdr is a header struct for NTFile.
type LinuxNTFileHdr struct {
type linuxNTFileHdr struct {
Count uint64
PageSize uint64
}
// LinuxNTFileEntry is an entry of an NT_FILE note.
type LinuxNTFileEntry struct {
type linuxNTFileEntry struct {
Start uint64
End uint64
FileOfs uint64
}
// ELFNotesHdr is the ELF Notes header.
// elfNotesHdr is the ELF Notes header.
// Same size on 64 and 32-bit machines.
type ELFNotesHdr struct {
type elfNotesHdr struct {
Namesz uint32
Descsz uint32
Type uint32
......
......@@ -7,7 +7,7 @@ import (
"github.com/go-delve/delve/pkg/proc/winutil"
)
func readAMD64Minidump(minidumpPath, exePath string) (*Process, error) {
func readAMD64Minidump(minidumpPath, exePath string) (*process, error) {
var logfn func(string, ...interface{})
if logflags.Minidump() {
logfn = logflags.MinidumpLogger().Infof
......@@ -21,16 +21,16 @@ func readAMD64Minidump(minidumpPath, exePath string) (*Process, error) {
return nil, err
}
memory := &SplicedMemory{}
memory := &splicedMemory{}
for i := range mdmp.MemoryRanges {
m := &mdmp.MemoryRanges[i]
memory.Add(m, uintptr(m.Addr), uintptr(len(m.Data)))
}
p := &Process{
p := &process{
mem: memory,
Threads: map[int]*Thread{},
Threads: map[int]*thread{},
bi: proc.NewBinaryInfo("windows", "amd64"),
breakpoints: proc.NewBreakpointMap(),
pid: int(mdmp.Pid),
......@@ -38,7 +38,7 @@ func readAMD64Minidump(minidumpPath, exePath string) (*Process, error) {
for i := range mdmp.Threads {
th := &mdmp.Threads[i]
p.Threads[int(th.ID)] = &Thread{&windowsAMD64Thread{th}, p, proc.CommonThread{}}
p.Threads[int(th.ID)] = &thread{&windowsAMD64Thread{th}, p, proc.CommonThread{}}
if p.currentThread == nil {
p.currentThread = p.Threads[int(th.ID)]
}
......
此差异已折叠。
......@@ -545,7 +545,7 @@ func (conn *gdbConn) writeRegister(threadID string, regnum int, data []byte) err
// resume each thread. If a thread has sig == 0 the 'c' action will be used,
// otherwise the 'C' action will be used and the value of sig will be passed
// to it.
func (conn *gdbConn) resume(threads map[int]*Thread, tu *threadUpdater) (string, uint8, error) {
func (conn *gdbConn) resume(threads map[int]*gdbThread, tu *threadUpdater) (string, uint8, error) {
if conn.direction == proc.Forward {
conn.outbuf.Reset()
fmt.Fprintf(&conn.outbuf, "$vCont")
......
......@@ -104,7 +104,7 @@ func Replay(tracedir string, quiet, deleteOnDetach bool, debugInfoDirs []string)
return nil, init.err
}
p := New(rrcmd.Process)
p := newProcess(rrcmd.Process)
p.tracedir = tracedir
if deleteOnDetach {
p.onDetach = func() {
......
......@@ -21,15 +21,15 @@ func Attach(pid int, _ []string) (*proc.Target, error) {
return nil, ErrNativeBackendDisabled
}
// WaitStatus is a synonym for the platform-specific WaitStatus
type WaitStatus struct{}
// waitStatus is a synonym for the platform-specific WaitStatus
type waitStatus struct{}
// OSSpecificDetails holds information specific to the OSX/Darwin
// osSpecificDetails holds information specific to the OSX/Darwin
// operating system / kernel.
type OSSpecificDetails struct{}
type osSpecificDetails struct{}
// OSProcessDetails holds Darwin specific information.
type OSProcessDetails struct{}
// osProcessDetails holds Darwin specific information.
type osProcessDetails struct{}
func findExecutable(path string, pid int) string {
panic(ErrNativeBackendDisabled)
......@@ -39,94 +39,94 @@ func killProcess(pid int) error {
panic(ErrNativeBackendDisabled)
}
func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
func registers(thread *nativeThread, floatingPoint bool) (proc.Registers, error) {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) loadProcessInformation(wg *sync.WaitGroup) {
func (dbp *nativeProcess) loadProcessInformation(wg *sync.WaitGroup) {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) requestManualStop() (err error) {
func (dbp *nativeProcess) requestManualStop() (err error) {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) resume() error {
func (dbp *nativeProcess) resume() error {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) trapWait(pid int) (*Thread, error) {
func (dbp *nativeProcess) trapWait(pid int) (*nativeThread, error) {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) stop(trapthread *Thread) (err error) {
func (dbp *nativeProcess) stop(trapthread *nativeThread) (err error) {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) updateThreadList() error {
func (dbp *nativeProcess) updateThreadList() error {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) kill() (err error) {
func (dbp *nativeProcess) kill() (err error) {
panic(ErrNativeBackendDisabled)
}
func (dbp *Process) detach(kill bool) error {
func (dbp *nativeProcess) detach(kill bool) error {
panic(ErrNativeBackendDisabled)
}
// EntryPoint returns the entry point for the process,
// useful for PIEs.
func (dbp *Process) EntryPoint() (uint64, error) {
func (dbp *nativeProcess) EntryPoint() (uint64, error) {
panic(ErrNativeBackendDisabled)
}
// Blocked returns true if the thread is blocked
func (t *Thread) Blocked() bool {
func (t *nativeThread) Blocked() bool {
panic(ErrNativeBackendDisabled)
}
// SetPC sets the value of the PC register.
func (t *Thread) SetPC(pc uint64) error {
func (t *nativeThread) SetPC(pc uint64) error {
panic(ErrNativeBackendDisabled)
}
// SetSP sets the value of the SP register.
func (t *Thread) SetSP(sp uint64) error {
func (t *nativeThread) SetSP(sp uint64) error {
panic(ErrNativeBackendDisabled)
}
// SetDX sets the value of the DX register.
func (t *Thread) SetDX(dx uint64) error {
func (t *nativeThread) SetDX(dx uint64) error {
panic(ErrNativeBackendDisabled)
}
// ReadMemory reads len(buf) bytes at addr into buf.
func (t *Thread) ReadMemory(buf []byte, addr uintptr) (int, error) {
func (t *nativeThread) ReadMemory(buf []byte, addr uintptr) (int, error) {
panic(ErrNativeBackendDisabled)
}
// WriteMemory writes the contents of data at addr.
func (t *Thread) WriteMemory(addr uintptr, data []byte) (int, error) {
func (t *nativeThread) WriteMemory(addr uintptr, data []byte) (int, error) {
panic(ErrNativeBackendDisabled)
}
func (t *Thread) resume() error {
func (t *nativeThread) resume() error {
panic(ErrNativeBackendDisabled)
}
func (t *Thread) singleStep() error {
func (t *nativeThread) singleStep() error {
panic(ErrNativeBackendDisabled)
}
func (t *Thread) restoreRegisters(sr proc.Registers) error {
func (t *nativeThread) restoreRegisters(sr proc.Registers) error {
panic(ErrNativeBackendDisabled)
}
// Stopped returns whether the thread is stopped at
// the operating system level.
func (t *Thread) Stopped() bool {
func (t *nativeThread) Stopped() bool {
panic(ErrNativeBackendDisabled)
}
func initialize(dbp *Process) error { return nil }
func initialize(dbp *nativeProcess) error { return nil }
......@@ -10,7 +10,7 @@ import (
// Process represents all of the information the debugger
// is holding onto regarding the process we are debugging.
type Process struct {
type nativeProcess struct {
bi *proc.BinaryInfo
pid int // Process Pid
......@@ -20,12 +20,12 @@ type Process struct {
breakpoints proc.BreakpointMap
// List of threads mapped as such: pid -> *Thread
threads map[int]*Thread
threads map[int]*nativeThread
// Active thread
currentThread *Thread
currentThread *nativeThread
os *OSProcessDetails
os *osProcessDetails
firstStart bool
stopMu sync.Mutex
resumeChan chan<- struct{}
......@@ -37,19 +37,19 @@ type Process struct {
exited, detached bool
}
var _ proc.ProcessInternal = &Process{}
var _ proc.ProcessInternal = &nativeProcess{}
// New returns an initialized Process struct. Before returning,
// newProcess returns an initialized Process struct. Before returning,
// it will also launch a goroutine in order to handle ptrace(2)
// functions. For more information, see the documentation on
// `handlePtraceFuncs`.
func New(pid int) *Process {
dbp := &Process{
func newProcess(pid int) *nativeProcess {
dbp := &nativeProcess{
pid: pid,
threads: make(map[int]*Thread),
threads: make(map[int]*nativeThread),
breakpoints: proc.NewBreakpointMap(),
firstStart: true,
os: new(OSProcessDetails),
os: new(osProcessDetails),
ptraceChan: make(chan func()),
ptraceDoneChan: make(chan interface{}),
bi: proc.NewBinaryInfo(runtime.GOOS, runtime.GOARCH),
......@@ -59,20 +59,20 @@ func New(pid int) *Process {
}
// BinInfo will return the binary info struct associated with this process.
func (dbp *Process) BinInfo() *proc.BinaryInfo {
func (dbp *nativeProcess) BinInfo() *proc.BinaryInfo {
return dbp.bi
}
// Recorded always returns false for the native proc backend.
func (dbp *Process) Recorded() (bool, string) { return false, "" }
func (dbp *nativeProcess) Recorded() (bool, string) { return false, "" }
// Restart will always return an error in the native proc backend, only for
// recorded traces.
func (dbp *Process) Restart(string) error { return proc.ErrNotRecorded }
func (dbp *nativeProcess) Restart(string) error { return proc.ErrNotRecorded }
// ChangeDirection will always return an error in the native proc backend, only for
// recorded traces.
func (dbp *Process) ChangeDirection(dir proc.Direction) error {
func (dbp *nativeProcess) ChangeDirection(dir proc.Direction) error {
if dir != proc.Forward {
return proc.ErrNotRecorded
}
......@@ -80,25 +80,25 @@ func (dbp *Process) ChangeDirection(dir proc.Direction) error {
}
// GetDirection will always return Forward.
func (p *Process) GetDirection() proc.Direction { return proc.Forward }
func (p *nativeProcess) GetDirection() proc.Direction { return proc.Forward }
// When will always return an empty string and nil, not supported on native proc backend.
func (dbp *Process) When() (string, error) { return "", nil }
func (dbp *nativeProcess) When() (string, error) { return "", nil }
// Checkpoint will always return an error on the native proc backend,
// only supported for recorded traces.
func (dbp *Process) Checkpoint(string) (int, error) { return -1, proc.ErrNotRecorded }
func (dbp *nativeProcess) Checkpoint(string) (int, error) { return -1, proc.ErrNotRecorded }
// Checkpoints will always return an error on the native proc backend,
// only supported for recorded traces.
func (dbp *Process) Checkpoints() ([]proc.Checkpoint, error) { return nil, proc.ErrNotRecorded }
func (dbp *nativeProcess) Checkpoints() ([]proc.Checkpoint, error) { return nil, proc.ErrNotRecorded }
// ClearCheckpoint will always return an error on the native proc backend,
// only supported in recorded traces.
func (dbp *Process) ClearCheckpoint(int) error { return proc.ErrNotRecorded }
func (dbp *nativeProcess) ClearCheckpoint(int) error { return proc.ErrNotRecorded }
// Detach from the process being debugged, optionally killing it.
func (dbp *Process) Detach(kill bool) (err error) {
func (dbp *nativeProcess) Detach(kill bool) (err error) {
if dbp.exited {
return nil
}
......@@ -135,7 +135,7 @@ func (dbp *Process) Detach(kill bool) (err error) {
// Valid returns whether the process is still attached to and
// has not exited.
func (dbp *Process) Valid() (bool, error) {
func (dbp *nativeProcess) Valid() (bool, error) {
if dbp.detached {
return false, proc.ErrProcessDetached
}
......@@ -147,17 +147,17 @@ func (dbp *Process) Valid() (bool, error) {
// ResumeNotify specifies a channel that will be closed the next time
// ContinueOnce finishes resuming the target.
func (dbp *Process) ResumeNotify(ch chan<- struct{}) {
func (dbp *nativeProcess) ResumeNotify(ch chan<- struct{}) {
dbp.resumeChan = ch
}
// Pid returns the process ID.
func (dbp *Process) Pid() int {
func (dbp *nativeProcess) Pid() int {
return dbp.pid
}
// ThreadList returns a list of threads in the process.
func (dbp *Process) ThreadList() []proc.Thread {
func (dbp *nativeProcess) ThreadList() []proc.Thread {
r := make([]proc.Thread, 0, len(dbp.threads))
for _, v := range dbp.threads {
r = append(r, v)
......@@ -166,29 +166,29 @@ func (dbp *Process) ThreadList() []proc.Thread {
}
// FindThread attempts to find the thread with the specified ID.
func (dbp *Process) FindThread(threadID int) (proc.Thread, bool) {
func (dbp *nativeProcess) FindThread(threadID int) (proc.Thread, bool) {
th, ok := dbp.threads[threadID]
return th, ok
}
// CurrentThread returns the current selected, active thread.
func (dbp *Process) CurrentThread() proc.Thread {
func (dbp *nativeProcess) CurrentThread() proc.Thread {
return dbp.currentThread
}
// SetCurrentThread is used internally by proc.Target to change the current thread.
func (p *Process) SetCurrentThread(th proc.Thread) {
p.currentThread = th.(*Thread)
func (p *nativeProcess) SetCurrentThread(th proc.Thread) {
p.currentThread = th.(*nativeThread)
}
// Breakpoints returns a list of breakpoints currently set.
func (dbp *Process) Breakpoints() *proc.BreakpointMap {
func (dbp *nativeProcess) Breakpoints() *proc.BreakpointMap {
return &dbp.breakpoints
}
// RequestManualStop sets the `halt` flag and
// sends SIGSTOP to all threads.
func (dbp *Process) RequestManualStop() error {
func (dbp *nativeProcess) RequestManualStop() error {
if dbp.exited {
return &proc.ErrProcessExited{Pid: dbp.Pid()}
}
......@@ -200,7 +200,7 @@ func (dbp *Process) RequestManualStop() error {
// CheckAndClearManualStopRequest checks if a manual stop has
// been requested, and then clears that state.
func (dbp *Process) CheckAndClearManualStopRequest() bool {
func (dbp *nativeProcess) CheckAndClearManualStopRequest() bool {
dbp.stopMu.Lock()
defer dbp.stopMu.Unlock()
......@@ -210,7 +210,7 @@ func (dbp *Process) CheckAndClearManualStopRequest() bool {
return msr
}
func (dbp *Process) writeBreakpoint(addr uint64) (string, int, *proc.Function, []byte, error) {
func (dbp *nativeProcess) writeBreakpoint(addr uint64) (string, int, *proc.Function, []byte, error) {
f, l, fn := dbp.bi.PCToLine(uint64(addr))
originalData := make([]byte, dbp.bi.Arch.BreakpointSize())
......@@ -227,12 +227,12 @@ func (dbp *Process) writeBreakpoint(addr uint64) (string, int, *proc.Function, [
// SetBreakpoint sets a breakpoint at addr, and stores it in the process wide
// break point table.
func (dbp *Process) SetBreakpoint(addr uint64, kind proc.BreakpointKind, cond ast.Expr) (*proc.Breakpoint, error) {
func (dbp *nativeProcess) SetBreakpoint(addr uint64, kind proc.BreakpointKind, cond ast.Expr) (*proc.Breakpoint, error) {
return dbp.breakpoints.Set(addr, kind, cond, dbp.writeBreakpoint)
}
// ClearBreakpoint clears the breakpoint at addr.
func (dbp *Process) ClearBreakpoint(addr uint64) (*proc.Breakpoint, error) {
func (dbp *nativeProcess) ClearBreakpoint(addr uint64) (*proc.Breakpoint, error) {
if dbp.exited {
return nil, &proc.ErrProcessExited{Pid: dbp.Pid()}
}
......@@ -241,7 +241,7 @@ func (dbp *Process) ClearBreakpoint(addr uint64) (*proc.Breakpoint, error) {
// ContinueOnce will continue the target until it stops.
// This could be the result of a breakpoint or signal.
func (dbp *Process) ContinueOnce() (proc.Thread, proc.StopReason, error) {
func (dbp *nativeProcess) ContinueOnce() (proc.Thread, proc.StopReason, error) {
if dbp.exited {
return nil, proc.StopExited, &proc.ErrProcessExited{Pid: dbp.Pid()}
}
......@@ -270,7 +270,7 @@ func (dbp *Process) ContinueOnce() (proc.Thread, proc.StopReason, error) {
}
// FindBreakpoint finds the breakpoint for the given pc.
func (dbp *Process) FindBreakpoint(pc uint64, adjustPC bool) (*proc.Breakpoint, bool) {
func (dbp *nativeProcess) FindBreakpoint(pc uint64, adjustPC bool) (*proc.Breakpoint, bool) {
if adjustPC {
// Check to see if address is past the breakpoint, (i.e. breakpoint was hit).
if bp, ok := dbp.breakpoints.M[pc-uint64(dbp.bi.Arch.BreakpointSize())]; ok {
......@@ -286,7 +286,7 @@ func (dbp *Process) FindBreakpoint(pc uint64, adjustPC bool) (*proc.Breakpoint,
// initialize will ensure that all relevant information is loaded
// so the process is ready to be debugged.
func (dbp *Process) initialize(path string, debugInfoDirs []string) (*proc.Target, error) {
func (dbp *nativeProcess) initialize(path string, debugInfoDirs []string) (*proc.Target, error) {
if err := initialize(dbp); err != nil {
return nil, err
}
......@@ -307,7 +307,7 @@ func (dbp *Process) initialize(path string, debugInfoDirs []string) (*proc.Targe
// ClearInternalBreakpoints will clear all non-user set breakpoints. These
// breakpoints are set for internal operations such as 'next'.
func (dbp *Process) ClearInternalBreakpoints() error {
func (dbp *nativeProcess) ClearInternalBreakpoints() error {
return dbp.breakpoints.ClearInternalBreakpoints(func(bp *proc.Breakpoint) error {
if err := dbp.currentThread.ClearBreakpoint(bp); err != nil {
return err
......@@ -321,7 +321,7 @@ func (dbp *Process) ClearInternalBreakpoints() error {
})
}
func (dbp *Process) handlePtraceFuncs() {
func (dbp *nativeProcess) handlePtraceFuncs() {
// We must ensure here that we are running on the same thread during
// while invoking the ptrace(2) syscall. This is due to the fact that ptrace(2) expects
// all commands after PTRACE_ATTACH to come from the same thread.
......@@ -333,19 +333,19 @@ func (dbp *Process) handlePtraceFuncs() {
}
}
func (dbp *Process) execPtraceFunc(fn func()) {
func (dbp *nativeProcess) execPtraceFunc(fn func()) {
dbp.ptraceChan <- fn
<-dbp.ptraceDoneChan
}
func (dbp *Process) postExit() {
func (dbp *nativeProcess) postExit() {
dbp.exited = true
close(dbp.ptraceChan)
close(dbp.ptraceDoneChan)
dbp.bi.Close()
}
func (dbp *Process) writeSoftwareBreakpoint(thread *Thread, addr uint64) error {
func (dbp *nativeProcess) writeSoftwareBreakpoint(thread *nativeThread, addr uint64) error {
_, err := thread.WriteMemory(uintptr(addr), dbp.bi.Arch.BreakpointInstruction())
return err
}
......@@ -20,8 +20,8 @@ import (
"github.com/go-delve/delve/pkg/proc"
)
// OSProcessDetails holds Darwin specific information.
type OSProcessDetails struct {
// osProcessDetails holds Darwin specific information.
type osProcessDetails struct {
task C.task_t // mach task for the debugged process.
exceptionPort C.mach_port_t // mach port for receiving mach exceptions.
notificationPort C.mach_port_t // mach port for dead name notification (process exit).
......@@ -64,7 +64,7 @@ func Launch(cmd []string, wd string, foreground bool, _ []string) (*proc.Target,
// argv array must be null terminated.
argvSlice = append(argvSlice, nil)
dbp := New(0)
dbp := newProcess(0)
var pid int
dbp.execPtraceFunc(func() {
ret := C.fork_exec(argv0, &argvSlice[0], C.int(len(argvSlice)),
......@@ -129,7 +129,7 @@ func Launch(cmd []string, wd string, foreground bool, _ []string) (*proc.Target,
// Attach to an existing process with the given PID.
func Attach(pid int, _ []string) (*proc.Target, error) {
dbp := New(pid)
dbp := newProcess(pid)
kret := C.acquire_mach_task(C.int(pid),
&dbp.os.task, &dbp.os.portSet, &dbp.os.exceptionPort,
......@@ -142,7 +142,7 @@ func Attach(pid int, _ []string) (*proc.Target, error) {
dbp.os.initialized = true
var err error
dbp.execPtraceFunc(func() { err = PtraceAttach(dbp.pid) })
dbp.execPtraceFunc(func() { err = ptraceAttach(dbp.pid) })
if err != nil {
return nil, err
}
......@@ -160,7 +160,7 @@ func Attach(pid int, _ []string) (*proc.Target, error) {
}
// Kill kills the process.
func (dbp *Process) kill() (err error) {
func (dbp *nativeProcess) kill() (err error) {
if dbp.exited {
return nil
}
......@@ -184,7 +184,7 @@ func (dbp *Process) kill() (err error) {
return
}
func (dbp *Process) requestManualStop() (err error) {
func (dbp *nativeProcess) requestManualStop() (err error) {
var (
task = C.mach_port_t(dbp.os.task)
thread = C.mach_port_t(dbp.currentThread.os.threadAct)
......@@ -201,11 +201,11 @@ func (dbp *Process) requestManualStop() (err error) {
var couldNotGetThreadCount = errors.New("could not get thread count")
var couldNotGetThreadList = errors.New("could not get thread list")
func (dbp *Process) updateThreadList() error {
func (dbp *nativeProcess) updateThreadList() error {
return dbp.updateThreadListForTask(dbp.os.task)
}
func (dbp *Process) updateThreadListForTask(task C.task_t) error {
func (dbp *nativeProcess) updateThreadListForTask(task C.task_t) error {
var (
err error
kret C.kern_return_t
......@@ -255,14 +255,14 @@ func (dbp *Process) updateThreadListForTask(task C.task_t) error {
return nil
}
func (dbp *Process) addThread(port int, attach bool) (*Thread, error) {
func (dbp *nativeProcess) addThread(port int, attach bool) (*nativeThread, error) {
if thread, ok := dbp.threads[port]; ok {
return thread, nil
}
thread := &Thread{
thread := &nativeThread{
ID: port,
dbp: dbp,
os: new(OSSpecificDetails),
os: new(osSpecificDetails),
}
dbp.threads[port] = thread
thread.os.threadAct = C.thread_act_t(port)
......@@ -279,7 +279,7 @@ func findExecutable(path string, pid int) string {
return path
}
func (dbp *Process) trapWait(pid int) (*Thread, error) {
func (dbp *nativeProcess) trapWait(pid int) (*nativeThread, error) {
for {
task := dbp.os.task
port := C.mach_port_wait(dbp.os.portSet, &task, C.int(0))
......@@ -357,7 +357,7 @@ func (dbp *Process) trapWait(pid int) (*Thread, error) {
}
}
func (dbp *Process) waitForStop() ([]int, error) {
func (dbp *nativeProcess) waitForStop() ([]int, error) {
ports := make([]int, 0, len(dbp.threads))
count := 0
for {
......@@ -379,7 +379,7 @@ func (dbp *Process) waitForStop() ([]int, error) {
}
}
func (dbp *Process) wait(pid, options int) (int, *sys.WaitStatus, error) {
func (dbp *nativeProcess) wait(pid, options int) (int, *sys.WaitStatus, error) {
var status sys.WaitStatus
wpid, err := sys.Wait4(pid, &status, options, nil)
return wpid, &status, err
......@@ -389,7 +389,7 @@ func killProcess(pid int) error {
return sys.Kill(pid, sys.SIGINT)
}
func (dbp *Process) exitGuard(err error) error {
func (dbp *nativeProcess) exitGuard(err error) error {
if err != ErrContinueThread {
return err
}
......@@ -401,7 +401,7 @@ func (dbp *Process) exitGuard(err error) error {
return err
}
func (dbp *Process) resume() error {
func (dbp *nativeProcess) resume() error {
// all threads stopped over a breakpoint are made to step over it
for _, thread := range dbp.threads {
if thread.CurrentBreakpoint.Breakpoint != nil {
......@@ -421,7 +421,7 @@ func (dbp *Process) resume() error {
}
// stop stops all running threads and sets breakpoints
func (dbp *Process) stop(trapthread *Thread) (err error) {
func (dbp *nativeProcess) stop(trapthread *nativeThread) (err error) {
if dbp.exited {
return &proc.ErrProcessExited{Pid: dbp.Pid()}
}
......@@ -452,13 +452,13 @@ func (dbp *Process) stop(trapthread *Thread) (err error) {
return nil
}
func (dbp *Process) detach(kill bool) error {
return PtraceDetach(dbp.pid, 0)
func (dbp *nativeProcess) detach(kill bool) error {
return ptraceDetach(dbp.pid, 0)
}
func (dbp *Process) EntryPoint() (uint64, error) {
func (dbp *nativeProcess) EntryPoint() (uint64, error) {
//TODO(aarzilli): implement this
return 0, nil
}
func initialize(dbp *Process) error { return nil }
func initialize(dbp *nativeProcess) error { return nil }
......@@ -22,18 +22,18 @@ import (
// Process statuses
const (
StatusIdle = 1
StatusRunning = 2
StatusSleeping = 3
StatusStopped = 4
StatusZombie = 5
StatusWaiting = 6
StatusLocked = 7
statusIdle = 1
statusRunning = 2
statusSleeping = 3
statusStopped = 4
statusZombie = 5
statusWaiting = 6
statusLocked = 7
)
// OSProcessDetails contains FreeBSD specific
// osProcessDetails contains FreeBSD specific
// process details.
type OSProcessDetails struct {
type osProcessDetails struct {
comm string
tid int
}
......@@ -59,7 +59,7 @@ func Launch(cmd []string, wd string, foreground bool, debugInfoDirs []string) (*
foreground = false
}
dbp := New(0)
dbp := newProcess(0)
dbp.execPtraceFunc(func() {
process = exec.Command(cmd[0])
process.Args = cmd
......@@ -95,10 +95,10 @@ func Launch(cmd []string, wd string, foreground bool, debugInfoDirs []string) (*
// the DWARF information cannot be found in the binary, Delve will look
// for external debug files in the directories passed in.
func Attach(pid int, debugInfoDirs []string) (*proc.Target, error) {
dbp := New(pid)
dbp := newProcess(pid)
var err error
dbp.execPtraceFunc(func() { err = PtraceAttach(dbp.pid) })
dbp.execPtraceFunc(func() { err = ptraceAttach(dbp.pid) })
if err != nil {
return nil, err
}
......@@ -115,7 +115,7 @@ func Attach(pid int, debugInfoDirs []string) (*proc.Target, error) {
return tgt, nil
}
func initialize(dbp *Process) error {
func initialize(dbp *nativeProcess) error {
comm, _ := C.find_command_name(C.int(dbp.pid))
defer C.free(unsafe.Pointer(comm))
comm_str := C.GoString(comm)
......@@ -124,11 +124,11 @@ func initialize(dbp *Process) error {
}
// kill kills the target process.
func (dbp *Process) kill() (err error) {
func (dbp *nativeProcess) kill() (err error) {
if dbp.exited {
return nil
}
dbp.execPtraceFunc(func() { err = PtraceCont(dbp.pid, int(sys.SIGKILL)) })
dbp.execPtraceFunc(func() { err = ptraceCont(dbp.pid, int(sys.SIGKILL)) })
if err != nil {
return err
}
......@@ -140,13 +140,13 @@ func (dbp *Process) kill() (err error) {
}
// Used by RequestManualStop
func (dbp *Process) requestManualStop() (err error) {
func (dbp *nativeProcess) requestManualStop() (err error) {
return sys.Kill(dbp.pid, sys.SIGTRAP)
}
// Attach to a newly created thread, and store that thread in our list of
// known threads.
func (dbp *Process) addThread(tid int, attach bool) (*Thread, error) {
func (dbp *nativeProcess) addThread(tid int, attach bool) (*nativeThread, error) {
if thread, ok := dbp.threads[tid]; ok {
return thread, nil
}
......@@ -159,10 +159,10 @@ func (dbp *Process) addThread(tid int, attach bool) (*Thread, error) {
}
}
dbp.threads[tid] = &Thread{
dbp.threads[tid] = &nativeThread{
ID: tid,
dbp: dbp,
os: new(OSSpecificDetails),
os: new(osSpecificDetails),
}
if dbp.currentThread == nil {
......@@ -173,9 +173,9 @@ func (dbp *Process) addThread(tid int, attach bool) (*Thread, error) {
}
// Used by initialize
func (dbp *Process) updateThreadList() error {
func (dbp *nativeProcess) updateThreadList() error {
var tids []int32
dbp.execPtraceFunc(func() { tids = PtraceGetLwpList(dbp.pid) })
dbp.execPtraceFunc(func() { tids = ptraceGetLwpList(dbp.pid) })
for _, tid := range tids {
if _, err := dbp.addThread(int(tid), false); err != nil {
return err
......@@ -195,12 +195,12 @@ func findExecutable(path string, pid int) string {
return path
}
func (dbp *Process) trapWait(pid int) (*Thread, error) {
func (dbp *nativeProcess) trapWait(pid int) (*nativeThread, error) {
return dbp.trapWaitInternal(pid, false)
}
// Used by stop and trapWait
func (dbp *Process) trapWaitInternal(pid int, halt bool) (*Thread, error) {
func (dbp *nativeProcess) trapWaitInternal(pid int, halt bool) (*nativeThread, error) {
for {
wpid, status, err := dbp.wait(pid, 0)
if err != nil {
......@@ -225,13 +225,13 @@ func (dbp *Process) trapWaitInternal(pid int, halt bool) (*Thread, error) {
pl_flags := int(info.Flags)
th, ok := dbp.threads[tid]
if ok {
th.Status = (*WaitStatus)(status)
th.Status = (*waitStatus)(status)
}
if status.StopSignal() == sys.SIGTRAP {
if pl_flags&sys.PL_FLAG_EXITED != 0 {
delete(dbp.threads, tid)
dbp.execPtraceFunc(func() { err = PtraceCont(tid, 0) })
dbp.execPtraceFunc(func() { err = ptraceCont(tid, 0) })
if err != nil {
return nil, err
}
......@@ -287,25 +287,25 @@ func status(pid int) rune {
// Used by stop and singleStep
// waitFast is like wait but does not handle process-exit correctly
func (dbp *Process) waitFast(pid int) (int, *sys.WaitStatus, error) {
func (dbp *nativeProcess) waitFast(pid int) (int, *sys.WaitStatus, error) {
var s sys.WaitStatus
wpid, err := sys.Wait4(pid, &s, 0, nil)
return wpid, &s, err
}
// Only used in this file
func (dbp *Process) wait(pid, options int) (int, *sys.WaitStatus, error) {
func (dbp *nativeProcess) wait(pid, options int) (int, *sys.WaitStatus, error) {
var s sys.WaitStatus
wpid, err := sys.Wait4(pid, &s, options, nil)
return wpid, &s, err
}
// Only used in this file
func (dbp *Process) exitGuard(err error) error {
func (dbp *nativeProcess) exitGuard(err error) error {
if err != sys.ESRCH {
return err
}
if status(dbp.pid) == StatusZombie {
if status(dbp.pid) == statusZombie {
_, err := dbp.trapWaitInternal(-1, false)
return err
}
......@@ -314,7 +314,7 @@ func (dbp *Process) exitGuard(err error) error {
}
// Used by ContinueOnce
func (dbp *Process) resume() error {
func (dbp *nativeProcess) resume() error {
// all threads stopped over a breakpoint are made to step over it
for _, thread := range dbp.threads {
if thread.CurrentBreakpoint.Breakpoint != nil {
......@@ -326,13 +326,13 @@ func (dbp *Process) resume() error {
}
// all threads are resumed
var err error
dbp.execPtraceFunc(func() { err = PtraceCont(dbp.pid, 0) })
dbp.execPtraceFunc(func() { err = ptraceCont(dbp.pid, 0) })
return err
}
// Used by ContinueOnce
// stop stops all running threads and sets breakpoints
func (dbp *Process) stop(trapthread *Thread) (err error) {
func (dbp *nativeProcess) stop(trapthread *nativeThread) (err error) {
if dbp.exited {
return &proc.ErrProcessExited{Pid: dbp.Pid()}
}
......@@ -348,13 +348,13 @@ func (dbp *Process) stop(trapthread *Thread) (err error) {
}
// Used by Detach
func (dbp *Process) detach(kill bool) error {
return PtraceDetach(dbp.pid)
func (dbp *nativeProcess) detach(kill bool) error {
return ptraceDetach(dbp.pid)
}
// Used by PostInitializationSetup
// EntryPoint will return the process entry point address, useful for debugging PIEs.
func (dbp *Process) EntryPoint() (uint64, error) {
func (dbp *nativeProcess) EntryPoint() (uint64, error) {
ep, err := C.get_entry_point(C.int(dbp.pid))
return uint64(ep), err
}
......
......@@ -26,21 +26,21 @@ import (
// Process statuses
const (
StatusSleeping = 'S'
StatusRunning = 'R'
StatusTraceStop = 't'
StatusZombie = 'Z'
statusSleeping = 'S'
statusRunning = 'R'
statusTraceStop = 't'
statusZombie = 'Z'
// Kernel 2.6 has TraceStop as T
// TODO(derekparker) Since this means something different based on the
// version of the kernel ('T' is job control stop on modern 3.x+ kernels) we
// may want to differentiate at some point.
StatusTraceStopT = 'T'
statusTraceStopT = 'T'
)
// OSProcessDetails contains Linux specific
// osProcessDetails contains Linux specific
// process details.
type OSProcessDetails struct {
type osProcessDetails struct {
comm string
}
......@@ -65,7 +65,7 @@ func Launch(cmd []string, wd string, foreground bool, debugInfoDirs []string) (*
foreground = false
}
dbp := New(0)
dbp := newProcess(0)
dbp.execPtraceFunc(func() {
process = exec.Command(cmd[0])
process.Args = cmd
......@@ -101,10 +101,10 @@ func Launch(cmd []string, wd string, foreground bool, debugInfoDirs []string) (*
// the DWARF information cannot be found in the binary, Delve will look
// for external debug files in the directories passed in.
func Attach(pid int, debugInfoDirs []string) (*proc.Target, error) {
dbp := New(pid)
dbp := newProcess(pid)
var err error
dbp.execPtraceFunc(func() { err = PtraceAttach(dbp.pid) })
dbp.execPtraceFunc(func() { err = ptraceAttach(dbp.pid) })
if err != nil {
return nil, err
}
......@@ -128,7 +128,7 @@ func Attach(pid int, debugInfoDirs []string) (*proc.Target, error) {
return tgt, nil
}
func initialize(dbp *Process) error {
func initialize(dbp *nativeProcess) error {
comm, err := ioutil.ReadFile(fmt.Sprintf("/proc/%d/comm", dbp.pid))
if err == nil {
// removes newline character
......@@ -156,7 +156,7 @@ func initialize(dbp *Process) error {
}
// kill kills the target process.
func (dbp *Process) kill() (err error) {
func (dbp *nativeProcess) kill() (err error) {
if dbp.exited {
return nil
}
......@@ -173,13 +173,13 @@ func (dbp *Process) kill() (err error) {
return
}
func (dbp *Process) requestManualStop() (err error) {
func (dbp *nativeProcess) requestManualStop() (err error) {
return sys.Kill(dbp.pid, sys.SIGTRAP)
}
// Attach to a newly created thread, and store that thread in our list of
// known threads.
func (dbp *Process) addThread(tid int, attach bool) (*Thread, error) {
func (dbp *nativeProcess) addThread(tid int, attach bool) (*nativeThread, error) {
if thread, ok := dbp.threads[tid]; ok {
return thread, nil
}
......@@ -217,10 +217,10 @@ func (dbp *Process) addThread(tid int, attach bool) (*Thread, error) {
}
}
dbp.threads[tid] = &Thread{
dbp.threads[tid] = &nativeThread{
ID: tid,
dbp: dbp,
os: new(OSSpecificDetails),
os: new(osSpecificDetails),
}
if dbp.currentThread == nil {
dbp.currentThread = dbp.threads[tid]
......@@ -228,7 +228,7 @@ func (dbp *Process) addThread(tid int, attach bool) (*Thread, error) {
return dbp.threads[tid], nil
}
func (dbp *Process) updateThreadList() error {
func (dbp *nativeProcess) updateThreadList() error {
tids, _ := filepath.Glob(fmt.Sprintf("/proc/%d/task/*", dbp.pid))
for _, tidpath := range tids {
tidstr := filepath.Base(tidpath)
......@@ -250,7 +250,7 @@ func findExecutable(path string, pid int) string {
return path
}
func (dbp *Process) trapWait(pid int) (*Thread, error) {
func (dbp *nativeProcess) trapWait(pid int) (*nativeThread, error) {
return dbp.trapWaitInternal(pid, 0)
}
......@@ -261,7 +261,7 @@ const (
trapWaitNohang
)
func (dbp *Process) trapWaitInternal(pid int, options trapWaitOptions) (*Thread, error) {
func (dbp *nativeProcess) trapWaitInternal(pid int, options trapWaitOptions) (*nativeThread, error) {
halt := options&trapWaitHalt != 0
for {
wopt := 0
......@@ -280,7 +280,7 @@ func (dbp *Process) trapWaitInternal(pid int, options trapWaitOptions) (*Thread,
}
th, ok := dbp.threads[wpid]
if ok {
th.Status = (*WaitStatus)(status)
th.Status = (*waitStatus)(status)
}
if status.Exited() {
if wpid == dbp.pid {
......@@ -387,13 +387,13 @@ func status(pid int, comm string) rune {
}
// waitFast is like wait but does not handle process-exit correctly
func (dbp *Process) waitFast(pid int) (int, *sys.WaitStatus, error) {
func (dbp *nativeProcess) waitFast(pid int) (int, *sys.WaitStatus, error) {
var s sys.WaitStatus
wpid, err := sys.Wait4(pid, &s, sys.WALL, nil)
return wpid, &s, err
}
func (dbp *Process) wait(pid, options int) (int, *sys.WaitStatus, error) {
func (dbp *nativeProcess) wait(pid, options int) (int, *sys.WaitStatus, error) {
var s sys.WaitStatus
if (pid != dbp.pid) || (options != 0) {
wpid, err := sys.Wait4(pid, &s, sys.WALL|options, nil)
......@@ -418,18 +418,18 @@ func (dbp *Process) wait(pid, options int) (int, *sys.WaitStatus, error) {
if wpid != 0 {
return wpid, &s, err
}
if status(pid, dbp.os.comm) == StatusZombie {
if status(pid, dbp.os.comm) == statusZombie {
return pid, nil, nil
}
time.Sleep(200 * time.Millisecond)
}
}
func (dbp *Process) exitGuard(err error) error {
func (dbp *nativeProcess) exitGuard(err error) error {
if err != sys.ESRCH {
return err
}
if status(dbp.pid, dbp.os.comm) == StatusZombie {
if status(dbp.pid, dbp.os.comm) == statusZombie {
_, err := dbp.trapWaitInternal(-1, 0)
return err
}
......@@ -437,7 +437,7 @@ func (dbp *Process) exitGuard(err error) error {
return err
}
func (dbp *Process) resume() error {
func (dbp *nativeProcess) resume() error {
// all threads stopped over a breakpoint are made to step over it
for _, thread := range dbp.threads {
if thread.CurrentBreakpoint.Breakpoint != nil {
......@@ -457,7 +457,7 @@ func (dbp *Process) resume() error {
}
// stop stops all running threads and sets breakpoints
func (dbp *Process) stop(trapthread *Thread) (err error) {
func (dbp *nativeProcess) stop(trapthread *nativeThread) (err error) {
if dbp.exited {
return &proc.ErrProcessExited{Pid: dbp.Pid()}
}
......@@ -517,9 +517,9 @@ func (dbp *Process) stop(trapthread *Thread) (err error) {
return nil
}
func (dbp *Process) detach(kill bool) error {
func (dbp *nativeProcess) detach(kill bool) error {
for threadID := range dbp.threads {
err := PtraceDetach(threadID, 0)
err := ptraceDetach(threadID, 0)
if err != nil {
return err
}
......@@ -540,7 +540,7 @@ func (dbp *Process) detach(kill bool) error {
// EntryPoint will return the process entry point address, useful for
// debugging PIEs.
func (dbp *Process) EntryPoint() (uint64, error) {
func (dbp *nativeProcess) EntryPoint() (uint64, error) {
auxvbuf, err := ioutil.ReadFile(fmt.Sprintf("/proc/%d/auxv", dbp.pid))
if err != nil {
return 0, fmt.Errorf("could not read auxiliary vector: %v", err)
......
......@@ -15,8 +15,8 @@ import (
"github.com/go-delve/delve/pkg/proc"
)
// OSProcessDetails holds Windows specific information.
type OSProcessDetails struct {
// osProcessDetails holds Windows specific information.
type osProcessDetails struct {
hProcess syscall.Handle
breakThread int
entryPoint uint64
......@@ -58,7 +58,7 @@ func Launch(cmd []string, wd string, foreground bool, _ []string) (*proc.Target,
env := proc.DisableAsyncPreemptEnv()
var p *os.Process
dbp := New(0)
dbp := newProcess(0)
dbp.execPtraceFunc(func() {
attr := &os.ProcAttr{
Dir: wd,
......@@ -86,7 +86,7 @@ func Launch(cmd []string, wd string, foreground bool, _ []string) (*proc.Target,
return tgt, nil
}
func initialize(dbp *Process) error {
func initialize(dbp *nativeProcess) error {
// It should not actually be possible for the
// call to waitForDebugEvent to fail, since Windows
// will always fire a CREATE_PROCESS_DEBUG_EVENT event
......@@ -155,7 +155,7 @@ func findExePath(pid int) (string, error) {
// Attach to an existing process with the given PID.
func Attach(pid int, _ []string) (*proc.Target, error) {
dbp := New(pid)
dbp := newProcess(pid)
var err error
dbp.execPtraceFunc(func() {
// TODO: Probably should have SeDebugPrivilege before starting here.
......@@ -177,7 +177,7 @@ func Attach(pid int, _ []string) (*proc.Target, error) {
}
// kill kills the process.
func (dbp *Process) kill() error {
func (dbp *nativeProcess) kill() error {
if dbp.exited {
return nil
}
......@@ -203,24 +203,24 @@ func (dbp *Process) kill() error {
return nil
}
func (dbp *Process) requestManualStop() error {
func (dbp *nativeProcess) requestManualStop() error {
return _DebugBreakProcess(dbp.os.hProcess)
}
func (dbp *Process) updateThreadList() error {
func (dbp *nativeProcess) updateThreadList() error {
// We ignore this request since threads are being
// tracked as they are created/killed in waitForDebugEvent.
return nil
}
func (dbp *Process) addThread(hThread syscall.Handle, threadID int, attach, suspendNewThreads bool) (*Thread, error) {
func (dbp *nativeProcess) addThread(hThread syscall.Handle, threadID int, attach, suspendNewThreads bool) (*nativeThread, error) {
if thread, ok := dbp.threads[threadID]; ok {
return thread, nil
}
thread := &Thread{
thread := &nativeThread{
ID: threadID,
dbp: dbp,
os: new(OSSpecificDetails),
os: new(osSpecificDetails),
}
thread.os.hThread = hThread
dbp.threads[threadID] = thread
......@@ -250,7 +250,7 @@ const (
const _MS_VC_EXCEPTION = 0x406D1388 // part of VisualC protocol to set thread names
func (dbp *Process) waitForDebugEvent(flags waitForDebugEventFlags) (threadID, exitCode int, err error) {
func (dbp *nativeProcess) waitForDebugEvent(flags waitForDebugEventFlags) (threadID, exitCode int, err error) {
var debugEvent _DEBUG_EVENT
shouldExit := false
for {
......@@ -378,7 +378,7 @@ func (dbp *Process) waitForDebugEvent(flags waitForDebugEventFlags) (threadID, e
}
}
func (dbp *Process) trapWait(pid int) (*Thread, error) {
func (dbp *nativeProcess) trapWait(pid int) (*nativeThread, error) {
var err error
var tid, exitCode int
dbp.execPtraceFunc(func() {
......@@ -395,15 +395,15 @@ func (dbp *Process) trapWait(pid int) (*Thread, error) {
return th, nil
}
func (dbp *Process) wait(pid, options int) (int, *sys.WaitStatus, error) {
func (dbp *nativeProcess) wait(pid, options int) (int, *sys.WaitStatus, error) {
return 0, nil, fmt.Errorf("not implemented: wait")
}
func (dbp *Process) exitGuard(err error) error {
func (dbp *nativeProcess) exitGuard(err error) error {
return err
}
func (dbp *Process) resume() error {
func (dbp *nativeProcess) resume() error {
for _, thread := range dbp.threads {
if thread.CurrentBreakpoint.Breakpoint != nil {
if err := thread.StepInstruction(); err != nil {
......@@ -424,7 +424,7 @@ func (dbp *Process) resume() error {
}
// stop stops all running threads threads and sets breakpoints
func (dbp *Process) stop(trapthread *Thread) (err error) {
func (dbp *nativeProcess) stop(trapthread *nativeThread) (err error) {
if dbp.exited {
return &proc.ErrProcessExited{Pid: dbp.Pid()}
}
......@@ -475,7 +475,7 @@ func (dbp *Process) stop(trapthread *Thread) (err error) {
return nil
}
func (dbp *Process) detach(kill bool) error {
func (dbp *nativeProcess) detach(kill bool) error {
if !kill {
//TODO(aarzilli): when debug.Target exist Detach should be moved to
// debug.Target and the call to RestoreAsyncPreempt should be moved there.
......@@ -489,7 +489,7 @@ func (dbp *Process) detach(kill bool) error {
return _DebugActiveProcessStop(uint32(dbp.pid))
}
func (dbp *Process) EntryPoint() (uint64, error) {
func (dbp *nativeProcess) EntryPoint() (uint64, error) {
return dbp.os.entryPoint, nil
}
......
......@@ -4,23 +4,23 @@ package native
import sys "golang.org/x/sys/unix"
// PtraceAttach executes the sys.PtraceAttach call.
func PtraceAttach(pid int) error {
// ptraceAttach executes the sys.PtraceAttach call.
func ptraceAttach(pid int) error {
return sys.PtraceAttach(pid)
}
// PtraceDetach executes the PT_DETACH ptrace call.
func PtraceDetach(tid, sig int) error {
// ptraceDetach executes the PT_DETACH ptrace call.
func ptraceDetach(tid, sig int) error {
return ptrace(sys.PT_DETACH, tid, 1, uintptr(sig))
}
// PtraceCont executes the PTRACE_CONT ptrace call.
func PtraceCont(tid, sig int) error {
// ptraceCont executes the PTRACE_CONT ptrace call.
func ptraceCont(tid, sig int) error {
return ptrace(sys.PTRACE_CONT, tid, 1, 0)
}
// PtraceSingleStep returns PT_STEP ptrace call.
func PtraceSingleStep(tid int) error {
// ptraceSingleStep returns PT_STEP ptrace call.
func ptraceSingleStep(tid int) error {
return ptrace(sys.PT_STEP, tid, 1, 0)
}
......
......@@ -17,31 +17,31 @@ import (
"github.com/go-delve/delve/pkg/proc/fbsdutil"
)
// PtraceAttach executes the sys.PtraceAttach call.
// ptraceAttach executes the sys.PtraceAttach call.
// pid must be a PID, not a LWPID
func PtraceAttach(pid int) error {
func ptraceAttach(pid int) error {
return sys.PtraceAttach(pid)
}
// PtraceDetach calls ptrace(PTRACE_DETACH).
func PtraceDetach(pid int) error {
// ptraceDetach calls ptrace(PTRACE_DETACH).
func ptraceDetach(pid int) error {
return sys.PtraceDetach(pid)
}
// PtraceCont executes ptrace PTRACE_CONT
// ptraceCont executes ptrace PTRACE_CONT
// id may be a PID or an LWPID
func PtraceCont(id, sig int) error {
func ptraceCont(id, sig int) error {
return sys.PtraceCont(id, sig)
}
// PtraceSingleStep executes ptrace PTRACE_SINGLE_STEP.
// ptraceSingleStep executes ptrace PTRACE_SINGLE_STEP.
// id may be a PID or an LWPID
func PtraceSingleStep(id int) error {
func ptraceSingleStep(id int) error {
return sys.PtraceSingleStep(id)
}
// Get a list of the thread ids of a process
func PtraceGetLwpList(pid int) (tids []int32) {
func ptraceGetLwpList(pid int) (tids []int32) {
num_lwps, _ := C.ptrace_get_num_lwps(C.int(pid))
tids = make([]int32, num_lwps)
n, _ := C.ptrace_get_lwp_list(C.int(pid), (*C.int)(unsafe.Pointer(&tids[0])), C.size_t(num_lwps))
......@@ -54,7 +54,7 @@ func ptraceGetLwpInfo(wpid int) (info sys.PtraceLwpInfoStruct, err error) {
return info, err
}
func PtraceGetRegset(id int) (regset fbsdutil.AMD64Xstate, err error) {
func ptraceGetRegset(id int) (regset fbsdutil.AMD64Xstate, err error) {
_, _, err = syscall.Syscall6(syscall.SYS_PTRACE, sys.PTRACE_GETFPREGS, uintptr(id), uintptr(unsafe.Pointer(&regset.AMD64PtraceFpRegs)), 0, 0, 0)
if err == syscall.Errno(0) || err == syscall.ENODEV {
var xsave_len C.size_t
......
......@@ -2,18 +2,17 @@ package native
import (
"syscall"
"unsafe"
sys "golang.org/x/sys/unix"
)
// PtraceAttach executes the sys.PtraceAttach call.
func PtraceAttach(pid int) error {
// ptraceAttach executes the sys.PtraceAttach call.
func ptraceAttach(pid int) error {
return sys.PtraceAttach(pid)
}
// PtraceDetach calls ptrace(PTRACE_DETACH).
func PtraceDetach(tid, sig int) error {
// ptraceDetach calls ptrace(PTRACE_DETACH).
func ptraceDetach(tid, sig int) error {
_, _, err := sys.Syscall6(sys.SYS_PTRACE, sys.PTRACE_DETACH, uintptr(tid), 1, uintptr(sig), 0, 0)
if err != syscall.Errno(0) {
return err
......@@ -21,31 +20,7 @@ func PtraceDetach(tid, sig int) error {
return nil
}
// PtraceCont executes ptrace PTRACE_CONT
func PtraceCont(tid, sig int) error {
// ptraceCont executes ptrace PTRACE_CONT
func ptraceCont(tid, sig int) error {
return sys.PtraceCont(tid, sig)
}
// PtraceSingleStep executes ptrace PTRACE_SINGLE_STEP.
func PtraceSingleStep(tid int) error {
return sys.PtraceSingleStep(tid)
}
// PtracePokeUser execute ptrace PTRACE_POKE_USER.
func PtracePokeUser(tid int, off, addr uintptr) error {
_, _, err := sys.Syscall6(sys.SYS_PTRACE, sys.PTRACE_POKEUSR, uintptr(tid), uintptr(off), uintptr(addr), 0, 0)
if err != syscall.Errno(0) {
return err
}
return nil
}
// PtracePeekUser execute ptrace PTRACE_PEEK_USER.
func PtracePeekUser(tid int, off uintptr) (uintptr, error) {
var val uintptr
_, _, err := syscall.Syscall6(syscall.SYS_PTRACE, syscall.PTRACE_PEEKUSR, uintptr(tid), uintptr(off), uintptr(unsafe.Pointer(&val)), 0, 0)
if err != syscall.Errno(0) {
return 0, err
}
return val, nil
}
......@@ -12,12 +12,12 @@ import (
"github.com/go-delve/delve/pkg/proc/linutil"
)
// PtraceGetRegset returns floating point registers of the specified thread
// ptraceGetRegset returns floating point registers of the specified thread
// using PTRACE.
// See i386_linux_fetch_inferior_registers in gdb/i386-linux-nat.c.html
// and i386_supply_xsave in gdb/i386-tdep.c.html
// and Section 13.1 (and following) of Intel® 64 and IA-32 Architectures Software Developer’s Manual, Volume 1: Basic Architecture
func PtraceGetRegset(tid int) (regset linutil.I386Xstate, err error) {
func ptraceGetRegset(tid int) (regset linutil.I386Xstate, err error) {
_, _, err = syscall.Syscall6(syscall.SYS_PTRACE, sys.PTRACE_GETFPREGS, uintptr(tid), uintptr(0), uintptr(unsafe.Pointer(&regset.I386PtraceFpRegs)), 0, 0)
if err == syscall.Errno(0) || err == syscall.ENODEV {
// ignore ENODEV, it just means this CPU doesn't have X87 registers (??)
......@@ -43,7 +43,7 @@ func PtraceGetRegset(tid int) (regset linutil.I386Xstate, err error) {
return
}
// PtraceGetTls return the addr of tls by PTRACE_GET_THREAD_AREA for specify thread.
// ptraceGetTls return the addr of tls by PTRACE_GET_THREAD_AREA for specify thread.
// See http://man7.org/linux/man-pages/man2/ptrace.2.html for detail about PTRACE_GET_THREAD_AREA.
// struct user_desc at https://golang.org/src/runtime/sys_linux_386.s
// type UserDesc struct {
......@@ -52,7 +52,7 @@ func PtraceGetRegset(tid int) (regset linutil.I386Xstate, err error) {
// Limit uint32
// Flag uint32
// }
func PtraceGetTls(gs int32, tid int) (uint32, error) {
func ptraceGetTls(gs int32, tid int) (uint32, error) {
ud := [4]uint32{}
// Gs usually is 0x33
......@@ -64,8 +64,8 @@ func PtraceGetTls(gs int32, tid int) (uint32, error) {
return uint32(ud[1]), nil
}
// ProcessVmRead calls process_vm_readv
func ProcessVmRead(tid int, addr uintptr, data []byte) (int, error) {
// processVmRead calls process_vm_readv
func processVmRead(tid int, addr uintptr, data []byte) (int, error) {
len_iov := uint32(len(data))
local_iov := sys.Iovec{Base: &data[0], Len: len_iov}
remote_iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(addr)), Len: len_iov}
......@@ -78,8 +78,8 @@ func ProcessVmRead(tid int, addr uintptr, data []byte) (int, error) {
return int(n), nil
}
// ProcessVmWrite calls process_vm_writev
func ProcessVmWrite(tid int, addr uintptr, data []byte) (int, error) {
// processVmWrite calls process_vm_writev
func processVmWrite(tid int, addr uintptr, data []byte) (int, error) {
len_iov := uint32(len(data))
local_iov := sys.Iovec{Base: &data[0], Len: len_iov}
remote_iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(addr)), Len: len_iov}
......
......@@ -9,8 +9,8 @@ import (
sys "golang.org/x/sys/unix"
)
// ProcessVmRead calls process_vm_readv
func ProcessVmRead(tid int, addr uintptr, data []byte) (int, error) {
// processVmRead calls process_vm_readv
func processVmRead(tid int, addr uintptr, data []byte) (int, error) {
len_iov := uint64(len(data))
local_iov := sys.Iovec{Base: &data[0], Len: len_iov}
remote_iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(addr)), Len: len_iov}
......@@ -23,8 +23,8 @@ func ProcessVmRead(tid int, addr uintptr, data []byte) (int, error) {
return int(n), nil
}
// ProcessVmWrite calls process_vm_writev
func ProcessVmWrite(tid int, addr uintptr, data []byte) (int, error) {
// processVmWrite calls process_vm_writev
func processVmWrite(tid int, addr uintptr, data []byte) (int, error) {
len_iov := uint64(len(data))
local_iov := sys.Iovec{Base: &data[0], Len: len_iov}
remote_iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(addr)), Len: len_iov}
......
......@@ -9,12 +9,12 @@ import (
"github.com/go-delve/delve/pkg/proc/linutil"
)
// PtraceGetRegset returns floating point registers of the specified thread
// ptraceGetRegset returns floating point registers of the specified thread
// using PTRACE.
// See amd64_linux_fetch_inferior_registers in gdb/amd64-linux-nat.c.html
// and amd64_supply_xsave in gdb/amd64-tdep.c.html
// and Section 13.1 (and following) of Intel® 64 and IA-32 Architectures Software Developer’s Manual, Volume 1: Basic Architecture
func PtraceGetRegset(tid int) (regset linutil.AMD64Xstate, err error) {
func ptraceGetRegset(tid int) (regset linutil.AMD64Xstate, err error) {
_, _, err = syscall.Syscall6(syscall.SYS_PTRACE, sys.PTRACE_GETFPREGS, uintptr(tid), uintptr(0), uintptr(unsafe.Pointer(&regset.AMD64PtraceFpRegs)), 0, 0)
if err == syscall.Errno(0) || err == syscall.ENODEV {
// ignore ENODEV, it just means this CPU doesn't have X87 registers (??)
......@@ -38,4 +38,4 @@ func PtraceGetRegset(tid int) (regset linutil.AMD64Xstate, err error) {
regset.Xsave = xstateargs[:iov.Len]
err = linutil.AMD64XstateRead(regset.Xsave, false, &regset)
return
}
\ No newline at end of file
}
......@@ -10,7 +10,7 @@ import (
)
// SetPC sets EIP to the value specified by 'pc'.
func (thread *Thread) SetPC(pc uint64) error {
func (thread *nativeThread) SetPC(pc uint64) error {
ir, err := registers(thread, false)
if err != nil {
return err
......@@ -22,7 +22,7 @@ func (thread *Thread) SetPC(pc uint64) error {
}
// SetSP sets ESP to the value specified by 'sp'
func (thread *Thread) SetSP(sp uint64) (err error) {
func (thread *nativeThread) SetSP(sp uint64) (err error) {
var ir proc.Registers
ir, err = registers(thread, false)
if err != nil {
......@@ -34,7 +34,7 @@ func (thread *Thread) SetSP(sp uint64) (err error) {
return
}
func (thread *Thread) SetDX(dx uint64) (err error) {
func (thread *nativeThread) SetDX(dx uint64) (err error) {
var ir proc.Registers
ir, err = registers(thread, false)
if err != nil {
......@@ -46,7 +46,7 @@ func (thread *Thread) SetDX(dx uint64) (err error) {
return
}
func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
func registers(thread *nativeThread, floatingPoint bool) (proc.Registers, error) {
var (
regs linutil.I386PtraceRegs
err error
......@@ -65,7 +65,7 @@ func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
}
}
thread.dbp.execPtraceFunc(func() {
tls, _ := PtraceGetTls(regs.Xgs, thread.ThreadID())
tls, _ := ptraceGetTls(regs.Xgs, thread.ThreadID())
r.Tls = uint64(tls)
})
return r, nil
......@@ -81,8 +81,8 @@ const (
_XSAVE_SSE_REGION_LEN = 416
)
func (thread *Thread) fpRegisters() (regs []proc.Register, fpregs linutil.I386Xstate, err error) {
thread.dbp.execPtraceFunc(func() { fpregs, err = PtraceGetRegset(thread.ID) })
func (thread *nativeThread) fpRegisters() (regs []proc.Register, fpregs linutil.I386Xstate, err error) {
thread.dbp.execPtraceFunc(func() { fpregs, err = ptraceGetRegset(thread.ID) })
regs = fpregs.Decode()
if err != nil {
err = fmt.Errorf("could not get floating point registers: %v", err.Error())
......
......@@ -111,7 +111,7 @@ func (r *Regs) GAddr() (uint64, bool) {
}
// SetPC sets the RIP register to the value specified by `pc`.
func (thread *Thread) SetPC(pc uint64) error {
func (thread *nativeThread) SetPC(pc uint64) error {
kret := C.set_pc(thread.os.threadAct, C.uint64_t(pc))
if kret != C.KERN_SUCCESS {
return fmt.Errorf("could not set pc")
......@@ -120,11 +120,11 @@ func (thread *Thread) SetPC(pc uint64) error {
}
// SetSP sets the RSP register to the value specified by `pc`.
func (thread *Thread) SetSP(sp uint64) error {
func (thread *nativeThread) SetSP(sp uint64) error {
return errors.New("not implemented")
}
func (thread *Thread) SetDX(dx uint64) error {
func (thread *nativeThread) SetDX(dx uint64) error {
return errors.New("not implemented")
}
......@@ -285,7 +285,7 @@ func (r *Regs) Get(n int) (uint64, error) {
return 0, proc.ErrUnknownRegister
}
func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
func registers(thread *nativeThread, floatingPoint bool) (proc.Registers, error) {
var state C.x86_thread_state64_t
var identity C.thread_identifier_info_data_t
kret := C.get_registers(C.mach_port_name_t(thread.os.threadAct), &state)
......
......@@ -10,7 +10,7 @@ import (
)
// SetPC sets RIP to the value specified by 'pc'.
func (thread *Thread) SetPC(pc uint64) error {
func (thread *nativeThread) SetPC(pc uint64) error {
ir, err := registers(thread, false)
if err != nil {
return err
......@@ -22,7 +22,7 @@ func (thread *Thread) SetPC(pc uint64) error {
}
// SetSP sets RSP to the value specified by 'sp'
func (thread *Thread) SetSP(sp uint64) (err error) {
func (thread *nativeThread) SetSP(sp uint64) (err error) {
var ir proc.Registers
ir, err = registers(thread, false)
if err != nil {
......@@ -34,7 +34,7 @@ func (thread *Thread) SetSP(sp uint64) (err error) {
return
}
func (thread *Thread) SetDX(dx uint64) (err error) {
func (thread *nativeThread) SetDX(dx uint64) (err error) {
var ir proc.Registers
ir, err = registers(thread, false)
if err != nil {
......@@ -46,7 +46,7 @@ func (thread *Thread) SetDX(dx uint64) (err error) {
return
}
func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
func registers(thread *nativeThread, floatingPoint bool) (proc.Registers, error) {
var (
regs fbsdutil.AMD64PtraceRegs
err error
......@@ -82,8 +82,8 @@ const (
_XSAVE_SSE_REGION_LEN = 416
)
func (thread *Thread) fpRegisters() (regs []proc.Register, fpregs fbsdutil.AMD64Xstate, err error) {
thread.dbp.execPtraceFunc(func() { fpregs, err = PtraceGetRegset(thread.ID) })
func (thread *nativeThread) fpRegisters() (regs []proc.Register, fpregs fbsdutil.AMD64Xstate, err error) {
thread.dbp.execPtraceFunc(func() { fpregs, err = ptraceGetRegset(thread.ID) })
if err != nil {
err = fmt.Errorf("could not get floating point registers: %v", err.Error())
}
......
......@@ -10,7 +10,7 @@ import (
)
// SetPC sets RIP to the value specified by 'pc'.
func (thread *Thread) SetPC(pc uint64) error {
func (thread *nativeThread) SetPC(pc uint64) error {
ir, err := registers(thread, false)
if err != nil {
return err
......@@ -22,7 +22,7 @@ func (thread *Thread) SetPC(pc uint64) error {
}
// SetSP sets RSP to the value specified by 'sp'
func (thread *Thread) SetSP(sp uint64) (err error) {
func (thread *nativeThread) SetSP(sp uint64) (err error) {
var ir proc.Registers
ir, err = registers(thread, false)
if err != nil {
......@@ -34,7 +34,7 @@ func (thread *Thread) SetSP(sp uint64) (err error) {
return
}
func (thread *Thread) SetDX(dx uint64) (err error) {
func (thread *nativeThread) SetDX(dx uint64) (err error) {
var ir proc.Registers
ir, err = registers(thread, false)
if err != nil {
......@@ -46,7 +46,7 @@ func (thread *Thread) SetDX(dx uint64) (err error) {
return
}
func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
func registers(thread *nativeThread, floatingPoint bool) (proc.Registers, error) {
var (
regs linutil.AMD64PtraceRegs
err error
......@@ -77,8 +77,8 @@ const (
_XSAVE_SSE_REGION_LEN = 416
)
func (thread *Thread) fpRegisters() (regs []proc.Register, fpregs linutil.AMD64Xstate, err error) {
thread.dbp.execPtraceFunc(func() { fpregs, err = PtraceGetRegset(thread.ID) })
func (thread *nativeThread) fpRegisters() (regs []proc.Register, fpregs linutil.AMD64Xstate, err error) {
thread.dbp.execPtraceFunc(func() { fpregs, err = ptraceGetRegset(thread.ID) })
regs = fpregs.Decode()
if err != nil {
err = fmt.Errorf("could not get floating point registers: %v", err.Error())
......
......@@ -13,12 +13,12 @@ import (
)
const (
AARCH64_GREGS_SIZE = 34 * 8
AARCH64_FPREGS_SIZE = 32*16 + 8
_AARCH64_GREGS_SIZE = 34 * 8
_AARCH64_FPREGS_SIZE = 32*16 + 8
)
func ptraceGetGRegs(pid int, regs *linutil.ARM64PtraceRegs) (err error) {
iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(regs)), Len: AARCH64_GREGS_SIZE}
iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(regs)), Len: _AARCH64_GREGS_SIZE}
_, _, err = syscall.Syscall6(syscall.SYS_PTRACE, sys.PTRACE_GETREGSET, uintptr(pid), uintptr(elf.NT_PRSTATUS), uintptr(unsafe.Pointer(&iov)), 0, 0)
if err == syscall.Errno(0) {
err = nil
......@@ -27,7 +27,7 @@ func ptraceGetGRegs(pid int, regs *linutil.ARM64PtraceRegs) (err error) {
}
func ptraceSetGRegs(pid int, regs *linutil.ARM64PtraceRegs) (err error) {
iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(regs)), Len: AARCH64_GREGS_SIZE}
iov := sys.Iovec{Base: (*byte)(unsafe.Pointer(regs)), Len: _AARCH64_GREGS_SIZE}
_, _, err = syscall.Syscall6(syscall.SYS_PTRACE, sys.PTRACE_SETREGSET, uintptr(pid), uintptr(elf.NT_PRSTATUS), uintptr(unsafe.Pointer(&iov)), 0, 0)
if err == syscall.Errno(0) {
err = nil
......@@ -35,11 +35,11 @@ func ptraceSetGRegs(pid int, regs *linutil.ARM64PtraceRegs) (err error) {
return
}
// PtraceGetFpRegset returns floating point registers of the specified thread
// ptraceGetFpRegset returns floating point registers of the specified thread
// using PTRACE.
func PtraceGetFpRegset(tid int) (fpregset []byte, err error) {
var arm64_fpregs [AARCH64_FPREGS_SIZE]byte
iov := sys.Iovec{Base: &arm64_fpregs[0], Len: AARCH64_FPREGS_SIZE}
func ptraceGetFpRegset(tid int) (fpregset []byte, err error) {
var arm64_fpregs [_AARCH64_FPREGS_SIZE]byte
iov := sys.Iovec{Base: &arm64_fpregs[0], Len: _AARCH64_FPREGS_SIZE}
_, _, err = syscall.Syscall6(syscall.SYS_PTRACE, sys.PTRACE_GETREGSET, uintptr(tid), uintptr(elf.NT_FPREGSET), uintptr(unsafe.Pointer(&iov)), 0, 0)
if err != syscall.Errno(0) {
if err == syscall.ENODEV {
......@@ -55,7 +55,7 @@ func PtraceGetFpRegset(tid int) (fpregset []byte, err error) {
}
// SetPC sets PC to the value specified by 'pc'.
func (thread *Thread) SetPC(pc uint64) error {
func (thread *nativeThread) SetPC(pc uint64) error {
ir, err := registers(thread, false)
if err != nil {
return err
......@@ -67,7 +67,7 @@ func (thread *Thread) SetPC(pc uint64) error {
}
// SetSP sets RSP to the value specified by 'sp'
func (thread *Thread) SetSP(sp uint64) (err error) {
func (thread *nativeThread) SetSP(sp uint64) (err error) {
var ir proc.Registers
ir, err = registers(thread, false)
if err != nil {
......@@ -79,11 +79,11 @@ func (thread *Thread) SetSP(sp uint64) (err error) {
return
}
func (thread *Thread) SetDX(dx uint64) (err error) {
func (thread *nativeThread) SetDX(dx uint64) (err error) {
return fmt.Errorf("not supported")
}
func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
func registers(thread *nativeThread, floatingPoint bool) (proc.Registers, error) {
var (
regs linutil.ARM64PtraceRegs
err error
......
......@@ -9,7 +9,7 @@ import (
)
// SetPC sets the RIP register to the value specified by `pc`.
func (thread *Thread) SetPC(pc uint64) error {
func (thread *nativeThread) SetPC(pc uint64) error {
context := winutil.NewCONTEXT()
context.ContextFlags = _CONTEXT_ALL
......@@ -24,7 +24,7 @@ func (thread *Thread) SetPC(pc uint64) error {
}
// SetSP sets the RSP register to the value specified by `sp`.
func (thread *Thread) SetSP(sp uint64) error {
func (thread *nativeThread) SetSP(sp uint64) error {
context := winutil.NewCONTEXT()
context.ContextFlags = _CONTEXT_ALL
......@@ -38,7 +38,7 @@ func (thread *Thread) SetSP(sp uint64) error {
return _SetThreadContext(thread.os.hThread, context)
}
func (thread *Thread) SetDX(dx uint64) error {
func (thread *nativeThread) SetDX(dx uint64) error {
context := winutil.NewCONTEXT()
context.ContextFlags = _CONTEXT_ALL
......@@ -52,7 +52,7 @@ func (thread *Thread) SetDX(dx uint64) error {
return _SetThreadContext(thread.os.hThread, context)
}
func registers(thread *Thread, floatingPoint bool) (proc.Registers, error) {
func registers(thread *nativeThread, floatingPoint bool) (proc.Registers, error) {
context := winutil.NewCONTEXT()
context.ContextFlags = _CONTEXT_ALL
......
......@@ -11,14 +11,14 @@ import (
// Process struct that contains info on the process as
// a whole, and Status represents the last result of a `wait` call
// on this thread.
type Thread struct {
type nativeThread struct {
ID int // Thread ID or mach port
Status *WaitStatus // Status returned from last wait call
Status *waitStatus // Status returned from last wait call
CurrentBreakpoint proc.BreakpointState // Breakpoint thread is currently stopped at
dbp *Process
dbp *nativeProcess
singleStepping bool
os *OSSpecificDetails
os *osSpecificDetails
common proc.CommonThread
}
......@@ -27,7 +27,7 @@ type Thread struct {
// If we are currently at a breakpoint, we'll clear it
// first and then resume execution. Thread will continue until
// it hits a breakpoint or is signaled.
func (t *Thread) Continue() error {
func (t *nativeThread) Continue() error {
pc, err := t.PC()
if err != nil {
return err
......@@ -48,7 +48,7 @@ func (t *Thread) Continue() error {
// If the thread is at a breakpoint, we first clear it,
// execute the instruction, and then replace the breakpoint.
// Otherwise we simply execute the next instruction.
func (t *Thread) StepInstruction() (err error) {
func (t *nativeThread) StepInstruction() (err error) {
t.singleStepping = true
defer func() {
t.singleStepping = false
......@@ -85,7 +85,7 @@ func (t *Thread) StepInstruction() (err error) {
// Location returns the threads location, including the file:line
// of the corresponding source code, the function we're in
// and the current instruction address.
func (t *Thread) Location() (*proc.Location, error) {
func (t *nativeThread) Location() (*proc.Location, error) {
pc, err := t.PC()
if err != nil {
return nil, err
......@@ -95,19 +95,19 @@ func (t *Thread) Location() (*proc.Location, error) {
}
// BinInfo returns information on the binary.
func (t *Thread) BinInfo() *proc.BinaryInfo {
func (t *nativeThread) BinInfo() *proc.BinaryInfo {
return t.dbp.bi
}
// Common returns information common across Process
// implementations.
func (t *Thread) Common() *proc.CommonThread {
func (t *nativeThread) Common() *proc.CommonThread {
return &t.common
}
// SetCurrentBreakpoint sets the current breakpoint that this
// thread is stopped at as CurrentBreakpoint on the thread struct.
func (t *Thread) SetCurrentBreakpoint(adjustPC bool) error {
func (t *nativeThread) SetCurrentBreakpoint(adjustPC bool) error {
t.CurrentBreakpoint.Clear()
pc, err := t.PC()
if err != nil {
......@@ -139,17 +139,17 @@ func (t *Thread) SetCurrentBreakpoint(adjustPC bool) error {
// Breakpoint returns the current breakpoint that is active
// on this thread.
func (t *Thread) Breakpoint() *proc.BreakpointState {
func (t *nativeThread) Breakpoint() *proc.BreakpointState {
return &t.CurrentBreakpoint
}
// ThreadID returns the ID of this thread.
func (t *Thread) ThreadID() int {
func (t *nativeThread) ThreadID() int {
return t.ID
}
// ClearBreakpoint clears the specified breakpoint.
func (t *Thread) ClearBreakpoint(bp *proc.Breakpoint) error {
func (t *nativeThread) ClearBreakpoint(bp *proc.Breakpoint) error {
if _, err := t.WriteMemory(uintptr(bp.Addr), bp.OriginalData); err != nil {
return fmt.Errorf("could not clear breakpoint %s", err)
}
......@@ -157,18 +157,18 @@ func (t *Thread) ClearBreakpoint(bp *proc.Breakpoint) error {
}
// Registers obtains register values from the debugged process.
func (t *Thread) Registers(floatingPoint bool) (proc.Registers, error) {
func (t *nativeThread) Registers(floatingPoint bool) (proc.Registers, error) {
return registers(t, floatingPoint)
}
// RestoreRegisters will set the value of the CPU registers to those
// passed in via 'savedRegs'.
func (t *Thread) RestoreRegisters(savedRegs proc.Registers) error {
func (t *nativeThread) RestoreRegisters(savedRegs proc.Registers) error {
return t.restoreRegisters(savedRegs)
}
// PC returns the current program counter value for this thread.
func (t *Thread) PC() (uint64, error) {
func (t *nativeThread) PC() (uint64, error) {
regs, err := t.Registers(false)
if err != nil {
return 0, err
......
......@@ -15,12 +15,12 @@ import (
"github.com/go-delve/delve/pkg/proc"
)
// WaitStatus is a synonym for the platform-specific WaitStatus
type WaitStatus sys.WaitStatus
// waitStatus is a synonym for the platform-specific WaitStatus
type waitStatus sys.WaitStatus
// OSSpecificDetails holds information specific to the OSX/Darwin
// osSpecificDetails holds information specific to the OSX/Darwin
// operating system / kernel.
type OSSpecificDetails struct {
type osSpecificDetails struct {
threadAct C.thread_act_t
registers C.x86_thread_state64_t
exists bool
......@@ -30,7 +30,7 @@ type OSSpecificDetails struct {
// be continued.
var ErrContinueThread = fmt.Errorf("could not continue thread")
func (t *Thread) stop() (err error) {
func (t *nativeThread) stop() (err error) {
kret := C.thread_suspend(t.os.threadAct)
if kret != C.KERN_SUCCESS {
errStr := C.GoString(C.mach_error_string(C.mach_error_t(kret)))
......@@ -49,7 +49,7 @@ func (t *Thread) stop() (err error) {
return
}
func (t *Thread) singleStep() error {
func (t *nativeThread) singleStep() error {
kret := C.single_step(t.os.threadAct)
if kret != C.KERN_SUCCESS {
return fmt.Errorf("could not single step")
......@@ -71,10 +71,10 @@ func (t *Thread) singleStep() error {
return nil
}
func (t *Thread) resume() error {
func (t *nativeThread) resume() error {
// TODO(dp) set flag for ptrace stops
var err error
t.dbp.execPtraceFunc(func() { err = PtraceCont(t.dbp.pid, 0) })
t.dbp.execPtraceFunc(func() { err = ptraceCont(t.dbp.pid, 0) })
if err == nil {
return nil
}
......@@ -85,7 +85,7 @@ func (t *Thread) resume() error {
return nil
}
func (t *Thread) Blocked() bool {
func (t *nativeThread) Blocked() bool {
// TODO(dp) cache the func pc to remove this lookup
regs, err := t.Registers(false)
if err != nil {
......@@ -106,11 +106,11 @@ func (t *Thread) Blocked() bool {
// Stopped returns whether the thread is stopped at
// the operating system level.
func (t *Thread) Stopped() bool {
func (t *nativeThread) Stopped() bool {
return C.thread_blocked(t.os.threadAct) > C.int(0)
}
func (t *Thread) WriteMemory(addr uintptr, data []byte) (int, error) {
func (t *nativeThread) WriteMemory(addr uintptr, data []byte) (int, error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
......@@ -128,7 +128,7 @@ func (t *Thread) WriteMemory(addr uintptr, data []byte) (int, error) {
return len(data), nil
}
func (t *Thread) ReadMemory(buf []byte, addr uintptr) (int, error) {
func (t *nativeThread) ReadMemory(buf []byte, addr uintptr) (int, error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
......@@ -148,6 +148,6 @@ func (t *Thread) ReadMemory(buf []byte, addr uintptr) (int, error) {
return len(buf), nil
}
func (t *Thread) restoreRegisters(sr proc.Registers) error {
func (t *nativeThread) restoreRegisters(sr proc.Registers) error {
return errors.New("not implemented")
}
......@@ -13,14 +13,14 @@ import (
"github.com/go-delve/delve/pkg/proc"
)
type WaitStatus sys.WaitStatus
type waitStatus sys.WaitStatus
// OSSpecificDetails hold FreeBSD specific process details.
type OSSpecificDetails struct {
// osSpecificDetails hold FreeBSD specific process details.
type osSpecificDetails struct {
registers sys.Reg
}
func (t *Thread) stop() (err error) {
func (t *nativeThread) stop() (err error) {
_, err = C.thr_kill2(C.pid_t(t.dbp.pid), C.long(t.ID), C.int(sys.SIGSTOP))
if err != nil {
err = fmt.Errorf("stop err %s on thread %d", err, t.ID)
......@@ -28,7 +28,7 @@ func (t *Thread) stop() (err error) {
}
// If the process is stopped, we must continue it so it can receive the
// signal
t.dbp.execPtraceFunc(func() { err = PtraceCont(t.dbp.pid, 0) })
t.dbp.execPtraceFunc(func() { err = ptraceCont(t.dbp.pid, 0) })
if err != nil {
return err
}
......@@ -40,22 +40,22 @@ func (t *Thread) stop() (err error) {
return
}
func (t *Thread) Stopped() bool {
func (t *nativeThread) Stopped() bool {
state := status(t.dbp.pid)
return state == StatusStopped
return state == statusStopped
}
func (t *Thread) resume() error {
func (t *nativeThread) resume() error {
return t.resumeWithSig(0)
}
func (t *Thread) resumeWithSig(sig int) (err error) {
t.dbp.execPtraceFunc(func() { err = PtraceCont(t.ID, sig) })
func (t *nativeThread) resumeWithSig(sig int) (err error) {
t.dbp.execPtraceFunc(func() { err = ptraceCont(t.ID, sig) })
return
}
func (t *Thread) singleStep() (err error) {
t.dbp.execPtraceFunc(func() { err = PtraceSingleStep(t.ID) })
func (t *nativeThread) singleStep() (err error) {
t.dbp.execPtraceFunc(func() { err = ptraceSingleStep(t.ID) })
if err != nil {
return err
}
......@@ -67,7 +67,7 @@ func (t *Thread) singleStep() (err error) {
if th.ID == t.ID {
break
}
t.dbp.execPtraceFunc(func() { err = PtraceCont(th.ID, 0) })
t.dbp.execPtraceFunc(func() { err = ptraceCont(th.ID, 0) })
if err != nil {
return err
}
......@@ -75,7 +75,7 @@ func (t *Thread) singleStep() (err error) {
return nil
}
func (t *Thread) Blocked() bool {
func (t *nativeThread) Blocked() bool {
loc, err := t.Location()
if err != nil {
return false
......@@ -86,7 +86,7 @@ func (t *Thread) Blocked() bool {
return false
}
func (t *Thread) restoreRegisters(savedRegs proc.Registers) error {
func (t *nativeThread) restoreRegisters(savedRegs proc.Registers) error {
sr := savedRegs.(*fbsdutil.AMD64Registers)
var restoreRegistersErr error
......@@ -110,7 +110,7 @@ func (t *Thread) restoreRegisters(savedRegs proc.Registers) error {
return restoreRegistersErr
}
func (t *Thread) WriteMemory(addr uintptr, data []byte) (written int, err error) {
func (t *nativeThread) WriteMemory(addr uintptr, data []byte) (written int, err error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
......@@ -121,7 +121,7 @@ func (t *Thread) WriteMemory(addr uintptr, data []byte) (written int, err error)
return written, err
}
func (t *Thread) ReadMemory(data []byte, addr uintptr) (n int, err error) {
func (t *nativeThread) ReadMemory(data []byte, addr uintptr) (n int, err error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
......
......@@ -8,18 +8,18 @@ import (
"github.com/go-delve/delve/pkg/proc"
)
type WaitStatus sys.WaitStatus
type waitStatus sys.WaitStatus
// OSSpecificDetails hold Linux specific
// osSpecificDetails hold Linux specific
// process details.
type OSSpecificDetails struct {
type osSpecificDetails struct {
delayedSignal int
registers sys.PtraceRegs
running bool
setbp bool
}
func (t *Thread) stop() (err error) {
func (t *nativeThread) stop() (err error) {
err = sys.Tgkill(t.dbp.pid, t.ID, sys.SIGSTOP)
if err != nil {
err = fmt.Errorf("stop err %s on thread %d", err, t.ID)
......@@ -30,24 +30,24 @@ func (t *Thread) stop() (err error) {
// Stopped returns whether the thread is stopped at
// the operating system level.
func (t *Thread) Stopped() bool {
func (t *nativeThread) Stopped() bool {
state := status(t.ID, t.dbp.os.comm)
return state == StatusTraceStop || state == StatusTraceStopT
return state == statusTraceStop || state == statusTraceStopT
}
func (t *Thread) resume() error {
func (t *nativeThread) resume() error {
sig := t.os.delayedSignal
t.os.delayedSignal = 0
return t.resumeWithSig(sig)
}
func (t *Thread) resumeWithSig(sig int) (err error) {
func (t *nativeThread) resumeWithSig(sig int) (err error) {
t.os.running = true
t.dbp.execPtraceFunc(func() { err = PtraceCont(t.ID, sig) })
t.dbp.execPtraceFunc(func() { err = ptraceCont(t.ID, sig) })
return
}
func (t *Thread) singleStep() (err error) {
func (t *nativeThread) singleStep() (err error) {
for {
t.dbp.execPtraceFunc(func() { err = sys.PtraceSingleStep(t.ID) })
if err != nil {
......@@ -71,7 +71,7 @@ func (t *Thread) singleStep() (err error) {
}
}
func (t *Thread) Blocked() bool {
func (t *nativeThread) Blocked() bool {
regs, err := t.Registers(false)
if err != nil {
return false
......@@ -84,7 +84,7 @@ func (t *Thread) Blocked() bool {
return false
}
func (t *Thread) WriteMemory(addr uintptr, data []byte) (written int, err error) {
func (t *nativeThread) WriteMemory(addr uintptr, data []byte) (written int, err error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
......@@ -94,7 +94,7 @@ func (t *Thread) WriteMemory(addr uintptr, data []byte) (written int, err error)
// ProcessVmWrite can't poke read-only memory like ptrace, so don't
// even bother for small writes -- likely breakpoints and such.
if len(data) > sys.SizeofPtr {
written, _ = ProcessVmWrite(t.ID, addr, data)
written, _ = processVmWrite(t.ID, addr, data)
}
if written == 0 {
t.dbp.execPtraceFunc(func() { written, err = sys.PtracePokeData(t.ID, addr, data) })
......@@ -102,14 +102,14 @@ func (t *Thread) WriteMemory(addr uintptr, data []byte) (written int, err error)
return
}
func (t *Thread) ReadMemory(data []byte, addr uintptr) (n int, err error) {
func (t *nativeThread) ReadMemory(data []byte, addr uintptr) (n int, err error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
if len(data) == 0 {
return
}
n, _ = ProcessVmRead(t.ID, addr, data)
n, _ = processVmRead(t.ID, addr, data)
if n == 0 {
t.dbp.execPtraceFunc(func() { n, err = sys.PtracePeekData(t.ID, addr, data) })
}
......
......@@ -5,6 +5,6 @@ import (
"github.com/go-delve/delve/pkg/proc"
)
func (t *Thread) restoreRegisters(savedRegs proc.Registers) error {
func (t *nativeThread) restoreRegisters(savedRegs proc.Registers) error {
return fmt.Errorf("restore regs not supported on i386")
}
......@@ -10,7 +10,7 @@ import (
"github.com/go-delve/delve/pkg/proc/linutil"
)
func (t *Thread) restoreRegisters(savedRegs proc.Registers) error {
func (t *nativeThread) restoreRegisters(savedRegs proc.Registers) error {
sr := savedRegs.(*linutil.AMD64Registers)
var restoreRegistersErr error
......
......@@ -12,10 +12,10 @@ import (
"github.com/go-delve/delve/pkg/proc/linutil"
)
func (thread *Thread) fpRegisters() ([]proc.Register, []byte, error) {
func (thread *nativeThread) fpRegisters() ([]proc.Register, []byte, error) {
var err error
var arm_fpregs linutil.ARM64PtraceFpRegs
thread.dbp.execPtraceFunc(func() { arm_fpregs.Vregs, err = PtraceGetFpRegset(thread.ID) })
thread.dbp.execPtraceFunc(func() { arm_fpregs.Vregs, err = ptraceGetFpRegset(thread.ID) })
fpregs := arm_fpregs.Decode()
if err != nil {
err = fmt.Errorf("could not get floating point registers: %v", err.Error())
......@@ -23,7 +23,7 @@ func (thread *Thread) fpRegisters() ([]proc.Register, []byte, error) {
return fpregs, arm_fpregs.Vregs, err
}
func (t *Thread) restoreRegisters(savedRegs proc.Registers) error {
func (t *nativeThread) restoreRegisters(savedRegs proc.Registers) error {
sr := savedRegs.(*linutil.ARM64Registers)
var restoreRegistersErr error
......
......@@ -10,16 +10,16 @@ import (
"github.com/go-delve/delve/pkg/proc/winutil"
)
// WaitStatus is a synonym for the platform-specific WaitStatus
type WaitStatus sys.WaitStatus
// waitStatus is a synonym for the platform-specific WaitStatus
type waitStatus sys.WaitStatus
// OSSpecificDetails holds information specific to the Windows
// osSpecificDetails holds information specific to the Windows
// operating system / kernel.
type OSSpecificDetails struct {
type osSpecificDetails struct {
hThread syscall.Handle
}
func (t *Thread) singleStep() error {
func (t *nativeThread) singleStep() error {
context := winutil.NewCONTEXT()
context.ContextFlags = _CONTEXT_ALL
......@@ -101,7 +101,7 @@ func (t *Thread) singleStep() error {
return _SetThreadContext(t.os.hThread, context)
}
func (t *Thread) resume() error {
func (t *nativeThread) resume() error {
var err error
t.dbp.execPtraceFunc(func() {
//TODO: Note that we are ignoring the thread we were asked to continue and are continuing the
......@@ -111,7 +111,7 @@ func (t *Thread) resume() error {
return err
}
func (t *Thread) Blocked() bool {
func (t *nativeThread) Blocked() bool {
// TODO: Probably incorrect - what are the runtime functions that
// indicate blocking on Windows?
regs, err := t.Registers(false)
......@@ -133,11 +133,11 @@ func (t *Thread) Blocked() bool {
// Stopped returns whether the thread is stopped at the operating system
// level. On windows this always returns true.
func (t *Thread) Stopped() bool {
func (t *nativeThread) Stopped() bool {
return true
}
func (t *Thread) WriteMemory(addr uintptr, data []byte) (int, error) {
func (t *nativeThread) WriteMemory(addr uintptr, data []byte) (int, error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
......@@ -154,7 +154,7 @@ func (t *Thread) WriteMemory(addr uintptr, data []byte) (int, error) {
var ErrShortRead = errors.New("short read")
func (t *Thread) ReadMemory(buf []byte, addr uintptr) (int, error) {
func (t *nativeThread) ReadMemory(buf []byte, addr uintptr) (int, error) {
if t.dbp.exited {
return 0, proc.ErrProcessExited{Pid: t.dbp.pid}
}
......@@ -169,6 +169,6 @@ func (t *Thread) ReadMemory(buf []byte, addr uintptr) (int, error) {
return int(count), err
}
func (t *Thread) restoreRegisters(savedRegs proc.Registers) error {
func (t *nativeThread) restoreRegisters(savedRegs proc.Registers) error {
return _SetThreadContext(t.os.hThread, savedRegs.(*winutil.AMD64Registers).Context)
}
......@@ -239,12 +239,6 @@ func TestHalt(t *testing.T) {
withTestProcess("loopprog", t, func(p *proc.Target, fixture protest.Fixture) {
setFunctionBreakpoint(p, t, "main.loop")
assertNoError(p.Continue(), t, "Continue")
if p, ok := p.Process.(*native.Process); ok {
for _, th := range p.ThreadList() {
_, err := th.Registers(false)
assertNoError(err, t, "Registers")
}
}
resumeChan := make(chan struct{}, 1)
go func() {
<-resumeChan
......@@ -258,21 +252,6 @@ func TestHalt(t *testing.T) {
if err, ok := retVal.(error); ok && err != nil {
t.Fatal()
}
// Loop through threads and make sure they are all
// actually stopped, err will not be nil if the process
// is still running.
if p, ok := p.Process.(*native.Process); ok {
for _, th := range p.ThreadList() {
if th, ok := th.(*native.Thread); ok {
if !th.Stopped() {
t.Fatal("expected thread to be stopped, but was not")
}
}
_, err := th.Registers(false)
assertNoError(err, t, "Registers")
}
}
})
}
......
......@@ -35,13 +35,13 @@ type Fixture struct {
}
// FixtureKey holds the name and builds flags used for a test fixture.
type FixtureKey struct {
type fixtureKey struct {
Name string
Flags BuildFlags
}
// Fixtures is a map of fixtureKey{ Fixture.Name, buildFlags } to Fixture.
var Fixtures = make(map[FixtureKey]Fixture)
var fixtures = make(map[fixtureKey]Fixture)
// PathsToRemove is a list of files and directories to remove after running all the tests
var PathsToRemove []string
......@@ -84,8 +84,8 @@ func BuildFixture(name string, flags BuildFlags) Fixture {
if !runningWithFixtures {
panic("RunTestsWithFixtures not called")
}
fk := FixtureKey{name, flags}
if f, ok := Fixtures[fk]; ok {
fk := fixtureKey{name, flags}
if f, ok := fixtures[fk]; ok {
return f
}
......@@ -180,8 +180,8 @@ func BuildFixture(name string, flags BuildFlags) Fixture {
fixture := Fixture{Name: name, Path: tmpfile, Source: source, BuildDir: absdir}
Fixtures[fk] = fixture
return Fixtures[fk]
fixtures[fk] = fixture
return fixtures[fk]
}
// RunTestsWithFixtures will pre-compile test fixtures before running test
......@@ -194,7 +194,7 @@ func RunTestsWithFixtures(m *testing.M) int {
status := m.Run()
// Remove the fixtures.
for _, f := range Fixtures {
for _, f := range fixtures {
os.Remove(f.Path)
}
......
......@@ -85,23 +85,23 @@ type Commands struct {
}
var (
// LongLoadConfig loads more information:
// longLoadConfig loads more information:
// * Follows pointers
// * Loads more array values
// * Does not limit struct fields
LongLoadConfig = api.LoadConfig{FollowPointers: true, MaxVariableRecurse: 1, MaxStringLen: 64, MaxArrayValues: 64, MaxStructFields: -1}
longLoadConfig = api.LoadConfig{FollowPointers: true, MaxVariableRecurse: 1, MaxStringLen: 64, MaxArrayValues: 64, MaxStructFields: -1}
// ShortLoadConfig loads less information, not following pointers
// and limiting struct fields loaded to 3.
ShortLoadConfig = api.LoadConfig{MaxStringLen: 64, MaxStructFields: 3}
)
// ByFirstAlias will sort by the first
// byFirstAlias will sort by the first
// alias of a command.
type ByFirstAlias []command
type byFirstAlias []command
func (a ByFirstAlias) Len() int { return len(a) }
func (a ByFirstAlias) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
func (a ByFirstAlias) Less(i, j int) bool { return a[i].aliases[0] < a[j].aliases[0] }
func (a byFirstAlias) Len() int { return len(a) }
func (a byFirstAlias) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
func (a byFirstAlias) Less(i, j int) bool { return a[i].aliases[0] < a[j].aliases[0] }
// DebugCommands returns a Commands struct with default commands defined.
func DebugCommands(client service.Client) *Commands {
......@@ -443,7 +443,7 @@ Currently, only the rev step-instruction command is supported.`,
})
}
sort.Sort(ByFirstAlias(c.cmds))
sort.Sort(byFirstAlias(c.cmds))
return c
}
......@@ -592,7 +592,7 @@ func threads(t *Term, ctx callContext, args string) error {
}
if th.Function != nil {
fmt.Printf("%sThread %d at %#v %s:%d %s\n",
prefix, th.ID, th.PC, ShortenFilePath(th.File),
prefix, th.ID, th.PC, shortenFilePath(th.File),
th.Line, th.Function.Name())
} else {
fmt.Printf("%sThread %s\n", prefix, formatThread(th))
......@@ -825,7 +825,7 @@ func (c *Commands) frameCommand(t *Term, ctx callContext, argstr string, directi
}
printcontext(t, state)
th := stack[frame]
fmt.Printf("Frame %d: %s:%d (PC: %x)\n", frame, ShortenFilePath(th.File), th.Line, th.PC)
fmt.Printf("Frame %d: %s:%d (PC: %x)\n", frame, shortenFilePath(th.File), th.Line, th.PC)
printfile(t, th.File, th.Line, true)
return nil
}
......@@ -863,7 +863,7 @@ func formatThread(th *api.Thread) string {
if th == nil {
return "<nil>"
}
return fmt.Sprintf("%d at %s:%d", th.ID, ShortenFilePath(th.File), th.Line)
return fmt.Sprintf("%d at %s:%d", th.ID, shortenFilePath(th.File), th.Line)
}
type formatGoroutineLoc int
......@@ -876,7 +876,7 @@ const (
)
func formatLocation(loc api.Location) string {
return fmt.Sprintf("%s:%d %s (%#v)", ShortenFilePath(loc.File), loc.Line, loc.Function.Name(), loc.PC)
return fmt.Sprintf("%s:%d %s (%#v)", shortenFilePath(loc.File), loc.Line, loc.Function.Name(), loc.PC)
}
func formatGoroutine(g *api.Goroutine, fgl formatGoroutineLoc) string {
......@@ -1325,19 +1325,19 @@ func clearAll(t *Term, ctx callContext, args string) error {
return nil
}
// ByID sorts breakpoints by ID.
type ByID []*api.Breakpoint
// byID sorts breakpoints by ID.
type byID []*api.Breakpoint
func (a ByID) Len() int { return len(a) }
func (a ByID) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
func (a ByID) Less(i, j int) bool { return a[i].ID < a[j].ID }
func (a byID) Len() int { return len(a) }
func (a byID) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
func (a byID) Less(i, j int) bool { return a[i].ID < a[j].ID }
func breakpoints(t *Term, ctx callContext, args string) error {
breakPoints, err := t.client.ListBreakpoints()
if err != nil {
return err
}
sort.Sort(ByID(breakPoints))
sort.Sort(byID(breakPoints))
for _, bp := range breakPoints {
fmt.Printf("%s at %v (%d)\n", formatBreakpointName(bp, true), formatBreakpointLocation(bp), bp.TotalHitCount)
......@@ -1352,14 +1352,14 @@ func breakpoints(t *Term, ctx callContext, args string) error {
attrs = append(attrs, "\tgoroutine")
}
if bp.LoadArgs != nil {
if *(bp.LoadArgs) == LongLoadConfig {
if *(bp.LoadArgs) == longLoadConfig {
attrs = append(attrs, "\targs -v")
} else {
attrs = append(attrs, "\targs")
}
}
if bp.LoadLocals != nil {
if *(bp.LoadLocals) == LongLoadConfig {
if *(bp.LoadLocals) == longLoadConfig {
attrs = append(attrs, "\tlocals -v")
} else {
attrs = append(attrs, "\tlocals")
......@@ -1955,7 +1955,7 @@ func disassCommand(t *Term, ctx callContext, args string) error {
return disasmErr
}
DisasmPrint(disasm, os.Stdout)
disasmPrint(disasm, os.Stdout)
return nil
}
......@@ -2004,7 +2004,7 @@ func printStack(stack []api.Stackframe, ind string, offsets bool) {
continue
}
fmt.Printf(fmtstr, ind, i, stack[i].PC, stack[i].Function.Name())
fmt.Printf("%sat %s:%d\n", s, ShortenFilePath(stack[i].File), stack[i].Line)
fmt.Printf("%sat %s:%d\n", s, shortenFilePath(stack[i].File), stack[i].Line)
if offsets {
fmt.Printf("%sframe: %+#x frame pointer %+#x\n", s, stack[i].FrameOffset, stack[i].FramePointerOffset)
......@@ -2084,7 +2084,7 @@ func printcontext(t *Term, state *api.DebuggerState) {
}
func printcontextLocation(loc api.Location) {
fmt.Printf("> %s() %s:%d (PC: %#v)\n", loc.Function.Name(), ShortenFilePath(loc.File), loc.Line, loc.PC)
fmt.Printf("> %s() %s:%d (PC: %#v)\n", loc.Function.Name(), shortenFilePath(loc.File), loc.Line, loc.PC)
if loc.Function != nil && loc.Function.Optimized {
fmt.Println(optimizedFunctionWarning)
}
......@@ -2137,7 +2137,7 @@ func printcontextThread(t *Term, th *api.Thread) {
bpname,
fn.Name(),
args,
ShortenFilePath(th.File),
shortenFilePath(th.File),
th.Line,
th.GoroutineID,
hitCount,
......@@ -2148,7 +2148,7 @@ func printcontextThread(t *Term, th *api.Thread) {
bpname,
fn.Name(),
args,
ShortenFilePath(th.File),
shortenFilePath(th.File),
th.Line,
th.Breakpoint.TotalHitCount,
th.PC)
......@@ -2172,14 +2172,14 @@ func printcontextThread(t *Term, th *api.Thread) {
}
for _, v := range bpi.Locals {
if *bp.LoadLocals == LongLoadConfig {
if *bp.LoadLocals == longLoadConfig {
fmt.Printf("\t%s: %s\n", v.Name, v.MultilineString("\t"))
} else {
fmt.Printf("\t%s: %s\n", v.Name, v.SinglelineString())
}
}
if bp.LoadArgs != nil && *bp.LoadArgs == LongLoadConfig {
if bp.LoadArgs != nil && *bp.LoadArgs == longLoadConfig {
for _, v := range bpi.Arguments {
fmt.Printf("\t%s: %s\n", v.Name, v.MultilineString("\t"))
}
......@@ -2302,9 +2302,9 @@ func conditionCmd(t *Term, ctx callContext, argstr string) error {
return t.client.AmendBreakpoint(bp)
}
// ShortenFilePath take a full file path and attempts to shorten
// shortenFilePath take a full file path and attempts to shorten
// it by replacing the current directory to './'.
func ShortenFilePath(fullPath string) string {
func shortenFilePath(fullPath string) string {
workingDir, _ := os.Getwd()
return strings.Replace(fullPath, workingDir, ".", 1)
}
......@@ -2463,7 +2463,7 @@ func formatBreakpointLocation(bp *api.Breakpoint) string {
fmt.Fprintf(&out, "%#x", bp.Addr)
}
fmt.Fprintf(&out, " for ")
p := ShortenFilePath(bp.File)
p := shortenFilePath(bp.File)
if bp.FunctionName != "" {
fmt.Fprintf(&out, "%s() ", bp.FunctionName)
}
......
......@@ -10,7 +10,7 @@ import (
"github.com/go-delve/delve/service/api"
)
func DisasmPrint(dv api.AsmInstructions, out io.Writer) {
func disasmPrint(dv api.AsmInstructions, out io.Writer) {
bw := bufio.NewWriter(out)
defer bw.Flush()
if len(dv) > 0 && dv[0].Loc.Function != nil {
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册