Merge lp:~niemeyer/tomb/err-dying into lp:tomb
Proposed by
Gustavo Niemeyer
Status: | Merged |
---|---|
Merged at revision: | 14 |
Proposed branch: | lp:~niemeyer/tomb/err-dying |
Merge into: | lp:tomb |
Diff against target: |
176 lines (+63/-16) 3 files modified
.lbox (+1/-0) tomb.go (+26/-7) tomb_test.go (+36/-9) |
To merge this branch: | bzr merge lp:~niemeyer/tomb/err-dying |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Gustavo Niemeyer | Pending | ||
Review via email: mp+100662@code.launchpad.net |
Description of the change
Added ErrDying. Renamed ErrStillRunning to ErrStillAlive.
To post a comment you must log in.
Reviewers: mp+100662_ code.launchpad. net,
Message:
Please take a look.
Description:
Added ErrDying. Renamed ErrStillRunning to ErrStillAlive.
https:/ /code.launchpad .net/~niemeyer/ tomb/err- dying/+ merge/100662
(do not edit description out of merge proposal)
Please review this at https:/ /codereview. appspot. com/5981052/
Affected files:
A .lbox
A [revision details]
M tomb.go
M tomb_test.go
Index: .lbox
=== added file '.lbox'
--- .lbox 1970-01-01 00:00:00 +0000
+++ .lbox 2012-04-03 17:55:15 +0000
@@ -0,0 +1,1 @@
+propose -cr -for=lp:tomb
Index: [revision details]
=== added file '[revision details]'
--- [revision details] 2012-01-01 00:00:00 +0000
+++ [revision details] 2012-01-01 00:00:00 +0000
@@ -0,0 +1,2 @@
+Old revision: <email address hidden>
+New revision: <email address hidden>
Index: tomb.go blog.labix. org/2011/ 10/09/death- of-goroutines- under-control
=== modified file 'tomb.go'
--- tomb.go 2012-03-06 17:16:14 +0000
+++ tomb.go 2012-04-03 17:53:18 +0000
@@ -52,6 +52,12 @@
// explicit blocking until the state changes, and also to selectively
// unblock select statements accordingly.
//
+// When the tomb state changes to dying and there's still logic going
+// on within the goroutine, nested functions and methos may choose to
+// return ErrDying as their error value, as this error won't alter the
+// tomb state if provied to the Kill method. This is a convenient way to
+// follow standard Go practices in the context of a dying tomb.
+//
// For background and a detailed example, see the following blog post:
//
// http://
@@ -63,14 +69,17 @@
reason error
}
-var ErrStillRunning = errors.New("tomb: goroutine is still running")
+var (
+ ErrStillAlive = errors.New("tomb: still alive")
+ ErrDying = errors.New("tomb: dying")
+)
func (t *Tomb) init() {
t.m.Lock()
if t.dead == nil {
t.dead = make(chan struct{})
t.dying = make(chan struct{})
- t.reason = ErrStillRunning
+ t.reason = ErrStillAlive
}
t.m.Unlock()
}
@@ -108,12 +117,24 @@
}
// Kill flags the goroutine as dying for the given reason.
-// Kill may be called multiple times, but only the first non-nil error is
-// recorded as the reason for termination.
+// Kill may be called multiple times, but only the first
+// non-nil error is recorded as the reason for termination.
+//
+// If reason is ErrDying, the previous reason isn't replaced
+// even if it is nil. It's a runtime error to call Kill with
+// ErrDying if t is not in a dying state.
func (t *Tomb) Kill(reason error) {
t.init()
t.m.Lock()
- if t.reason == nil || t.reason == ErrStillRunning {
+ if reason == ErrDying {
+ alive := t.reason == ErrStillAlive
+ t.m.Unlock()
+ if alive {
+ panic("tomb: Kill with ErrDying while still alive")
+ }
+ return
+ }
+ if t.reason == nil || t.reason == ErrStillAlive {
t.reason = reason
}
// If the receive on t.dying succeeds, then
@@ -136,7 +157,7 @@
}
// Err returns the reason for the goroutine death provided via Kill
-// or Killf, or ErrStillRunning when the goroutine is still alive.
+// or Killf, or ErrStillAlive when the goroutine is still al...