Skip to content

Commit

Permalink
Remove timeoutWait due to improved scheduler handling
Browse files Browse the repository at this point in the history
  • Loading branch information
derekparker committed Nov 27, 2014
1 parent 16392ce commit afa3a9c
Show file tree
Hide file tree
Showing 3 changed files with 3 additions and 61 deletions.
58 changes: 1 addition & 57 deletions proctl/proctl_linux_amd64.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ import (
"os/exec"
"sync"
"syscall"
"time"

"github.com/derekparker/delve/dwarf/frame"
"github.com/derekparker/delve/vendor/elf"
Expand Down Expand Up @@ -319,11 +318,7 @@ func (dbp *DebuggedProcess) Continue() error {
for _, thread := range dbp.Threads {
err := thread.Continue()
if err != nil {
// TODO(dp): There are some coordination issues
// here that need to be resolved.
if _, ok := err.(TimeoutError); !ok && err != syscall.ESRCH {
return err
}
return err
}
}

Expand Down Expand Up @@ -558,57 +553,6 @@ type waitstats struct {
status *syscall.WaitStatus
}

type TimeoutError struct {
pid int
}

func (err TimeoutError) Error() string {
return fmt.Sprintf("timeout waiting for %d", err.pid)
}

// TODO(dp): this is a hacky, racy implementation. Ideally this method will
// become defunct and replaced by a non-blocking incremental sleeping wait.
// The purpose is to detect whether a thread is sleeping. However, this is
// tricky because a thread can be sleeping due to being a blocked M in the
// scheduler or sleeping due to a user calling sleep.
func timeoutWait(thread *ThreadContext, options int) (int, *syscall.WaitStatus, error) {
var (
statchan = make(chan *waitstats)
errchan = make(chan error)
)

ps, err := parseProcessStatus(thread.Id)
if err != nil {
return -1, nil, err
}

if ps.state == STATUS_SLEEPING {
return 0, nil, nil
}

go func(pid int, statchan chan *waitstats, errchan chan error) {
wpid, status, err := wait(pid, 0)
if err != nil {
errchan <- fmt.Errorf("wait err %s %d", err, pid)
}

statchan <- &waitstats{pid: wpid, status: status}
}(thread.Id, statchan, errchan)

select {
case s := <-statchan:
return s.pid, s.status, nil
case <-time.After(10 * time.Millisecond):
if err := syscall.Tgkill(thread.Process.Pid, thread.Id, syscall.SIGSTOP); err != nil {
return -1, nil, err
}
<-statchan
return 0, nil, TimeoutError{thread.Id}
case err := <-errchan:
return -1, nil, err
}
}

func wait(pid, options int) (int, *syscall.WaitStatus, error) {
var status syscall.WaitStatus
wpid, err := syscall.Wait4(pid, &status, syscall.WALL|options, nil)
Expand Down
4 changes: 1 addition & 3 deletions proctl/proctl_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -102,9 +102,7 @@ func TestBreakPoint(t *testing.T) {
}

err = p.Step()
if _, ok := err.(proctl.TimeoutError); !ok {
assertNoError(err, t, "Step()")
}
assertNoError(err, t, "Step()")

pc, err = p.CurrentPC()
if err != nil {
Expand Down
2 changes: 1 addition & 1 deletion proctl/threads_linux_amd64.go
Original file line number Diff line number Diff line change
Expand Up @@ -170,7 +170,7 @@ func (thread *ThreadContext) Step() (err error) {
return fmt.Errorf("step failed: %s", err.Error())
}

_, _, err = timeoutWait(thread, 0)
_, _, err = wait(thread.Id, 0)
if err != nil {
return err
}
Expand Down

0 comments on commit afa3a9c

Please sign in to comment.