public unsafe bool TryRegister(int fileDescriptor, SocketAsyncEvents current, SocketAsyncEvents events, GCHandle handle, out Interop.Error error)
        {
            Debug.Assert(current != events);

            int op = Interop.libc.EPOLL_CTL_MOD;

            if (current == SocketAsyncEvents.None)
            {
                // This context was not listening for events, add it
                op = Interop.libc.EPOLL_CTL_ADD;
            }
            else if (events == SocketAsyncEvents.None)
            {
                // This context will no longer be listening for events, remove it
                op = Interop.libc.EPOLL_CTL_DEL;
            }

            // Register events
            var evt = new Interop.libc.epoll_event {
                events = GetEPollEvents(events) | Interop.libc.EPOLLET, data = (IntPtr)handle
            };
            int err = Interop.libc.epoll_ctl(_epollFd, op, fileDescriptor, &evt);

            if (err == 0)
            {
                error = Interop.Error.SUCCESS;
                return(true);
            }

            error = Interop.Sys.GetLastError();
            return(false);
        }
예제 #2
0
 public bool TryRegister(int fileDescriptor, SocketAsyncEvents current, SocketAsyncEvents events, GCHandle handle, out Interop.Error error)
 {
     if (current == events)
     {
         error = Interop.Error.SUCCESS;
         return true;
     }
     return _backend.TryRegister(fileDescriptor, current, events, handle, out error);
 }
 private static uint GetEPollEvents(SocketAsyncEvents events)
 {
     return
         (((events & SocketAsyncEvents.Read) != 0) ? Interop.libc.EPOLLIN : 0) |
         (((events & SocketAsyncEvents.Write) != 0) ? Interop.libc.EPOLLOUT : 0) |
         (((events & SocketAsyncEvents.ReadClose) != 0) ? Interop.libc.EPOLLRDHUP : 0) |
         (((events & SocketAsyncEvents.Close) != 0) ? Interop.libc.EPOLLHUP : 0) |
         (((events & SocketAsyncEvents.Error) != 0) ? Interop.libc.EPOLLERR : 0);
 }
예제 #4
0
 public bool TryRegister(int fileDescriptor, SocketAsyncEvents current, SocketAsyncEvents events, GCHandle handle, out Interop.Error error)
 {
     if (current == events)
     {
         error = Interop.Error.SUCCESS;
         return(true);
     }
     return(_backend.TryRegister(fileDescriptor, current, events, handle, out error));
 }
 private static uint GetEPollEvents(SocketAsyncEvents events)
 {
     return
         ((((events & SocketAsyncEvents.Read) != 0) ? Interop.libc.EPOLLIN : 0) |
          (((events & SocketAsyncEvents.Write) != 0) ? Interop.libc.EPOLLOUT : 0) |
          (((events & SocketAsyncEvents.ReadClose) != 0) ? Interop.libc.EPOLLRDHUP : 0) |
          (((events & SocketAsyncEvents.Close) != 0) ? Interop.libc.EPOLLHUP : 0) |
          (((events & SocketAsyncEvents.Error) != 0) ? Interop.libc.EPOLLERR : 0));
 }
        public unsafe bool TryRegister(int fileDescriptor, SocketAsyncEvents current, SocketAsyncEvents events, GCHandle handle, out Interop.Error error)
        {
            const ushort AddFlags    = Interop.libc.EV_ADD | Interop.libc.EV_CLEAR | Interop.libc.EV_RECEIPT;
            const ushort RemoveFlags = Interop.libc.EV_DELETE | Interop.libc.EV_RECEIPT;

            Debug.Assert(current != events);

            SocketAsyncEvents changed = current ^ events;
            bool readChanged          = (changed & SocketAsyncEvents.Read) != 0;
            bool writeChanged         = (changed & SocketAsyncEvents.Write) != 0;

            int evtCount = (readChanged ? 1 : 0) + (writeChanged ? 1 : 0);
            var kevents  = stackalloc Interop.libc.kevent64_s[evtCount];

            int i = 0;

            if (readChanged)
            {
                kevents[0].ident  = unchecked ((ulong)fileDescriptor);
                kevents[0].filter = Interop.libc.EVFILT_READ;
                kevents[0].flags  = (events & SocketAsyncEvents.Read) == 0 ? RemoveFlags : AddFlags;
                kevents[0].fflags = 0;
                kevents[0].data   = 0;
                kevents[0].udata  = (ulong)(IntPtr)handle;
                i = 1;
            }
            if (writeChanged)
            {
                kevents[i].ident  = unchecked ((ulong)fileDescriptor);
                kevents[i].filter = Interop.libc.EVFILT_WRITE;
                kevents[i].flags  = (events & SocketAsyncEvents.Write) == 0 ? RemoveFlags : AddFlags;
                kevents[i].fflags = 0;
                kevents[i].data   = 0;
                kevents[i].udata  = (ulong)(IntPtr)handle;
            }

            int err = Interop.libc.kevent64(_kqueueFd, kevents, evtCount, null, 0, 0, null);

            if (err == 0)
            {
                error = Interop.Error.SUCCESS;
                return(true);
            }

            error = Interop.Sys.GetLastError();
            return(false);
        }
        public unsafe bool TryRegister(int fileDescriptor, SocketAsyncEvents current, SocketAsyncEvents events, GCHandle handle, out Interop.Error error)
        {
            Debug.Assert(current != events);

            int op = Interop.libc.EPOLL_CTL_MOD;
            if (current == SocketAsyncEvents.None)
            {
                // This context was not listening for events, add it
                op = Interop.libc.EPOLL_CTL_ADD;
            }
            else if (events == SocketAsyncEvents.None)
            {
                // This context will no longer be listening for events, remove it
                op = Interop.libc.EPOLL_CTL_DEL;
            }

            // Register events
            var evt = new Interop.libc.epoll_event { events = GetEPollEvents(events) | Interop.libc.EPOLLET, data = (IntPtr)handle };
            int err = Interop.libc.epoll_ctl(_epollFd, op, fileDescriptor, &evt);
            if (err == 0)
            {
                error = Interop.Error.SUCCESS;
                return true;
            }

            error = Interop.Sys.GetLastError();
            return false;
        }
        public unsafe bool TryRegister(int fileDescriptor, SocketAsyncEvents current, SocketAsyncEvents events, GCHandle handle, out Interop.Error error)
        {
            const ushort AddFlags = Interop.libc.EV_ADD | Interop.libc.EV_CLEAR | Interop.libc.EV_RECEIPT;
            const ushort RemoveFlags = Interop.libc.EV_DELETE | Interop.libc.EV_RECEIPT;

            Debug.Assert(current != events);

            SocketAsyncEvents changed = current ^ events;
            bool readChanged = (changed & SocketAsyncEvents.Read) != 0;
            bool writeChanged = (changed & SocketAsyncEvents.Write) != 0;

            int evtCount = (readChanged ? 1 : 0) + (writeChanged ? 1 : 0);
            var kevents = stackalloc Interop.libc.kevent64_s[evtCount];

            int i = 0;
            if (readChanged)
            {
                kevents[0].ident = unchecked((ulong)fileDescriptor);
                kevents[0].filter = Interop.libc.EVFILT_READ;
                kevents[0].flags = (events & SocketAsyncEvents.Read) == 0 ? RemoveFlags : AddFlags;
                kevents[0].fflags = 0;
                kevents[0].data = 0;
                kevents[0].udata = (ulong)(IntPtr)handle;
                i = 1;
            }
            if (writeChanged)
            {
                kevents[i].ident = unchecked((ulong)fileDescriptor);
                kevents[i].filter = Interop.libc.EVFILT_WRITE;
                kevents[i].flags = (events & SocketAsyncEvents.Write) == 0 ? RemoveFlags : AddFlags;
                kevents[i].fflags = 0;
                kevents[i].data = 0;
                kevents[i].udata = (ulong)(IntPtr)handle;
            }

            int err = Interop.libc.kevent64(_kqueueFd, kevents, evtCount, null, 0, 0, null);
            if (err == 0)
            {
                error = Interop.Error.SUCCESS;
                return true;
            }

            error = Interop.Sys.GetLastError();
            return false;
        }