mirror of
https://github.com/netbirdio/gvisor.git
synced 2026-05-22 17:12:49 -07:00
gvisor/hostnet: restart epoll_wait after epoll_ctl
Otherwise changes of epoll_ctl will not have affect. PiperOrigin-RevId: 247964961 Change-Id: I9fbb35c44766421af45d9ed53760e0c324d80d99
This commit is contained in:
@@ -40,6 +40,10 @@ type notifier struct {
|
||||
// notifications.
|
||||
epFD int
|
||||
|
||||
// eventFD is used to restart epoll_wait in waitAndNotify after
|
||||
// reconfiguring epFD.
|
||||
eventFD int
|
||||
|
||||
// mu protects fdMap.
|
||||
mu sync.Mutex
|
||||
|
||||
@@ -55,9 +59,20 @@ func newNotifier() (*notifier, error) {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
eventFD, err := eventFDCreate()
|
||||
if err != nil {
|
||||
syscall.Close(epfd)
|
||||
return nil, err
|
||||
}
|
||||
|
||||
w := ¬ifier{
|
||||
epFD: epfd,
|
||||
fdMap: make(map[int32]*fdInfo),
|
||||
epFD: epfd,
|
||||
eventFD: eventFD,
|
||||
fdMap: make(map[int32]*fdInfo),
|
||||
}
|
||||
|
||||
if err := w.waitFD(int32(w.eventFD), &fdInfo{}, waiter.EventIn); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
go w.waitAndNotify() // S/R-SAFE: no waiter exists during save / load.
|
||||
@@ -91,6 +106,11 @@ func (n *notifier) waitFD(fd int32, fi *fdInfo, mask waiter.EventMask) error {
|
||||
}
|
||||
}
|
||||
|
||||
// Restart epoll_wait in waitAndNotify.
|
||||
if err := eventFDWrite(n.eventFD, 1); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -156,6 +176,12 @@ func (n *notifier) waitAndNotify() error {
|
||||
|
||||
n.mu.Lock()
|
||||
for i := 0; i < v; i++ {
|
||||
if e[i].Fd == int32(n.eventFD) {
|
||||
if _, err := eventFDRead(n.eventFD); err != nil {
|
||||
return err
|
||||
}
|
||||
continue
|
||||
}
|
||||
if fi, ok := n.fdMap[e[i].Fd]; ok {
|
||||
fi.queue.Notify(waiter.EventMaskFromLinux(e[i].Events))
|
||||
}
|
||||
|
||||
@@ -74,3 +74,28 @@ func epollWait(epfd int, events []syscall.EpollEvent, msec int) (int, error) {
|
||||
}
|
||||
return int(r), nil
|
||||
}
|
||||
|
||||
func eventFDCreate() (int, error) {
|
||||
eventFD, _, err := syscall.RawSyscall(syscall.SYS_EVENTFD2, 0, 0, 0)
|
||||
if err != 0 {
|
||||
return -1, err
|
||||
}
|
||||
return int(eventFD), nil
|
||||
}
|
||||
|
||||
func eventFDWrite(eventFD int, v uint64) error {
|
||||
if _, _, err := syscall.RawSyscall(syscall.SYS_WRITE, uintptr(eventFD), uintptr(unsafe.Pointer(&v)), 8); err != 0 {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func eventFDRead(eventFD int) (uint64, error) {
|
||||
var v uint64
|
||||
if _, _, err := syscall.RawSyscall(syscall.SYS_READ, uintptr(eventFD), uintptr(unsafe.Pointer(&v)), 8); err != 0 {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
return v, nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user