]> Cypherpunks repositories - gostls13.git/commitdiff
os: only add file descriptors which are set to non-blocking mode to the netpoller
authorYuval Pavel Zholkover <paulzhol@gmail.com>
Sat, 30 Jul 2022 17:41:58 +0000 (20:41 +0300)
committerGopher Robot <gobot@golang.org>
Thu, 18 Aug 2022 03:12:27 +0000 (03:12 +0000)
Either ones where kind == kindNonBlock or those we've successfully called syscall.SetNonblock() on.
Restore blocking behavior if we detect an error registering with the netpoller and our flow was
successful in setting the inital syscall.SetNonblock().

Update #54100

Change-Id: I08934e4107c7fb36c15a7ca23ac880490b4df235
Reviewed-on: https://go-review.googlesource.com/c/go/+/420334
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Dmitri Goutnik <dgoutnik@gmail.com>
Reviewed-by: Ian Lance Taylor <iant@google.com>
Run-TryBot: Yuval Pavel Zholkover <paulzhol@gmail.com>
Reviewed-by: Than McIntosh <thanm@google.com>
Auto-Submit: Ian Lance Taylor <iant@golang.org>

src/os/file_unix.go

index c30a6890de0f3895341f49273035f28762e90e20..1833c26531602b2256e0fa7ad44c1875a5525330 100644 (file)
@@ -168,18 +168,28 @@ func newFile(fd uintptr, name string, kind newFileKind) *File {
                }
        }
 
-       if err := f.pfd.Init("file", pollable); err != nil {
-               // An error here indicates a failure to register
-               // with the netpoll system. That can happen for
-               // a file descriptor that is not supported by
-               // epoll/kqueue; for example, disk files on
-               // Linux systems. We assume that any real error
-               // will show up in later I/O.
-       } else if pollable {
-               // We successfully registered with netpoll, so put
-               // the file into nonblocking mode.
-               if err := syscall.SetNonblock(fdi, true); err == nil {
+       clearNonBlock := false
+       if pollable {
+               if kind == kindNonBlock {
                        f.nonblock = true
+               } else if err := syscall.SetNonblock(fdi, true); err == nil {
+                       f.nonblock = true
+                       clearNonBlock = true
+               } else {
+                       pollable = false
+               }
+       }
+
+       // An error here indicates a failure to register
+       // with the netpoll system. That can happen for
+       // a file descriptor that is not supported by
+       // epoll/kqueue; for example, disk files on
+       // Linux systems. We assume that any real error
+       // will show up in later I/O.
+       // We do restore the blocking behavior if it was set by us.
+       if pollErr := f.pfd.Init("file", pollable); pollErr != nil && clearNonBlock {
+               if err := syscall.SetNonblock(fdi, false); err == nil {
+                       f.nonblock = false
                }
        }