Skip to content

Commit

Permalink
context: reduce init-time allocations
Browse files Browse the repository at this point in the history
Small cleanup to remove a couple of needless global variables.
Instead of relying on two instances of emptyCtx having different
addresses, we use different types.

For #26775

Change-Id: I0bc4813e94226f7b3f52bf4b1b3c3a3bbbebcc9e
Reviewed-on: https://go-review.googlesource.com/c/go/+/455455
Reviewed-by: Damien Neil <[email protected]>
TryBot-Result: Gopher Robot <[email protected]>
Run-TryBot: Ian Lance Taylor <[email protected]>
Reviewed-by: Sameer Ajmani <[email protected]>
  • Loading branch information
CAFxX authored and neild committed Feb 10, 2023
1 parent f7b32f5 commit 6e5c260
Showing 1 changed file with 19 additions and 22 deletions.
41 changes: 19 additions & 22 deletions src/context/context.go
Original file line number Diff line number Diff line change
Expand Up @@ -172,55 +172,52 @@ func (deadlineExceededError) Error() string { return "context deadline exceede
func (deadlineExceededError) Timeout() bool { return true }
func (deadlineExceededError) Temporary() bool { return true }

// An emptyCtx is never canceled, has no values, and has no deadline. It is not
// struct{}, since vars of this type must have distinct addresses.
type emptyCtx int
// An emptyCtx is never canceled, has no values, and has no deadline.
// It is the common base of backgroundCtx and todoCtx.
type emptyCtx struct{}

func (*emptyCtx) Deadline() (deadline time.Time, ok bool) {
func (emptyCtx) Deadline() (deadline time.Time, ok bool) {
return
}

func (*emptyCtx) Done() <-chan struct{} {
func (emptyCtx) Done() <-chan struct{} {
return nil
}

func (*emptyCtx) Err() error {
func (emptyCtx) Err() error {
return nil
}

func (*emptyCtx) Value(key any) any {
func (emptyCtx) Value(key any) any {
return nil
}

func (e *emptyCtx) String() string {
switch e {
case background:
return "context.Background"
case todo:
return "context.TODO"
}
return "unknown empty Context"
type backgroundCtx struct{ emptyCtx }

func (backgroundCtx) String() string {
return "context.Background"
}

var (
background = new(emptyCtx)
todo = new(emptyCtx)
)
type todoCtx struct{ emptyCtx }

func (todoCtx) String() string {
return "context.TODO"
}

// Background returns a non-nil, empty Context. It is never canceled, has no
// values, and has no deadline. It is typically used by the main function,
// initialization, and tests, and as the top-level Context for incoming
// requests.
func Background() Context {
return background
return backgroundCtx{}
}

// TODO returns a non-nil, empty Context. Code should use context.TODO when
// it's unclear which Context to use or it is not yet available (because the
// surrounding function has not yet been extended to accept a Context
// parameter).
func TODO() Context {
return todo
return todoCtx{}
}

// A CancelFunc tells an operation to abandon its work.
Expand Down Expand Up @@ -653,7 +650,7 @@ func value(c Context, key any) any {
return &ctx.cancelCtx
}
c = ctx.Context
case *emptyCtx:
case backgroundCtx, todoCtx:
return nil
default:
return c.Value(key)
Expand Down

0 comments on commit 6e5c260

Please sign in to comment.