summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorZhaozhong Ni <nzz@google.com>2018-07-12 13:48:18 -0700
committerShentubot <shentubot@google.com>2018-07-12 13:49:21 -0700
commit45c50eb12436bcc477a0fbc2616bfd664a07c43f (patch)
treefa16d5c6eb35e3843ed6bf6772545220d26b9782
parentcc34a90fb46348fd4588d4191ddba0a1d27c1132 (diff)
netstack: save tcp endpoint accepted channel directly.
PiperOrigin-RevId: 204356873 Change-Id: I5e2f885f58678e693aae1a69e8bf8084a685af28
-rw-r--r--pkg/tcpip/transport/tcp/endpoint.go6
-rw-r--r--pkg/tcpip/transport/tcp/endpoint_state.go46
2 files changed, 26 insertions, 26 deletions
diff --git a/pkg/tcpip/transport/tcp/endpoint.go b/pkg/tcpip/transport/tcp/endpoint.go
index 8b9a81f6a..5b8a1e20f 100644
--- a/pkg/tcpip/transport/tcp/endpoint.go
+++ b/pkg/tcpip/transport/tcp/endpoint.go
@@ -206,11 +206,7 @@ type endpoint struct {
// acceptedChan is used by a listening endpoint protocol goroutine to
// send newly accepted connections to the endpoint so that they can be
// read by Accept() calls.
- acceptedChan chan *endpoint `state:"manual"`
-
- // acceptedEndpoints is only used to save / restore the channel buffer.
- // FIXME
- acceptedEndpoints []*endpoint
+ acceptedChan chan *endpoint `state:".([]*endpoint)"`
// The following are only used from the protocol goroutine, and
// therefore don't need locks to protect them.
diff --git a/pkg/tcpip/transport/tcp/endpoint_state.go b/pkg/tcpip/transport/tcp/endpoint_state.go
index ad20407fa..9c2e8878f 100644
--- a/pkg/tcpip/transport/tcp/endpoint_state.go
+++ b/pkg/tcpip/transport/tcp/endpoint_state.go
@@ -88,17 +88,32 @@ func (e *endpoint) beforeSave() {
if !((e.state == stateBound || e.state == stateListen) == e.isPortReserved) {
panic("endpoint port must and must only be reserved in bound or listen state")
}
+}
- if e.acceptedChan != nil {
- close(e.acceptedChan)
- e.acceptedEndpoints = make([]*endpoint, len(e.acceptedChan), cap(e.acceptedChan))
- i := 0
- for ep := range e.acceptedChan {
- e.acceptedEndpoints[i] = ep
- i++
- }
- if i != len(e.acceptedEndpoints) {
- panic("endpoint acceptedChan buffer got consumed by background context")
+// saveAcceptedChan is invoked by stateify.
+func (e *endpoint) saveAcceptedChan() []*endpoint {
+ if e.acceptedChan == nil {
+ return nil
+ }
+ close(e.acceptedChan)
+ acceptedEndpoints := make([]*endpoint, len(e.acceptedChan), cap(e.acceptedChan))
+ i := 0
+ for ep := range e.acceptedChan {
+ acceptedEndpoints[i] = ep
+ i++
+ }
+ if i != len(acceptedEndpoints) {
+ panic("endpoint acceptedChan buffer got consumed by background context")
+ }
+ return acceptedEndpoints
+}
+
+// loadAcceptedChan is invoked by stateify.
+func (e *endpoint) loadAcceptedChan(acceptedEndpoints []*endpoint) {
+ if cap(acceptedEndpoints) > 0 {
+ e.acceptedChan = make(chan *endpoint, cap(acceptedEndpoints))
+ for _, ep := range acceptedEndpoints {
+ e.acceptedChan <- ep
}
}
}
@@ -134,17 +149,6 @@ func (e *endpoint) loadState(state endpointState) {
// afterLoad is invoked by stateify.
func (e *endpoint) afterLoad() {
- // We load acceptedChan buffer indirectly here. Note that closed
- // endpoints might not need to allocate the channel.
- // FIXME
- if cap(e.acceptedEndpoints) > 0 {
- e.acceptedChan = make(chan *endpoint, cap(e.acceptedEndpoints))
- for _, ep := range e.acceptedEndpoints {
- e.acceptedChan <- ep
- }
- e.acceptedEndpoints = nil
- }
-
e.stack = stack.StackFromEnv
e.segmentQueue.setLimit(2 * e.rcvBufSize)
e.workMu.Init()