---
name: "vpoll"
section: "3"
platform: "linux"
package: "libvpoll-dev"
version: "0.1.1-1"
release: "Debian 13 (Trixie)"
platforms: ["linux"]
url: "https://new.carta.tech/vpoll"
---

# vpoll(3)

generate synthetic events for poll/select/ppoll/pselect/epoll

## NAME

vpoll\_create, vpoll\_ctl, vpoll\_close - generate synthetic events for poll/select/ppoll/pselect/epoll

## SYNOPSIS

\#include \*vpoll.h\*

int vpoll\_create(uint32\_t *init\_events*, int *flags*);

int vpoll\_ctl(int *fd*, int *op*, uint32\_t *events*);

int vpoll\_close(int *fd*);

## DESCRIPTION

This library permits one to create a vpoll file descriptor “vpollfd” that can be used in poll/select/ppoll/pselect/epoll(2) system calls. The events reported by a can be controlled by vpoll\_ctl. vpoll encodes the events using the same flags EPOLL\* defined in [epoll\_ctl(2)](/epoll_ctl/2.md).

The library uses the vpoll extension for eventfd if the kernel provides it otherwise it (partially) emulates the feature using [socketpair(2)](/socketpair/2.md). The emulation supports only EPOLLIN, EPOLLOUT flags and a non standard version of EPOLLHUP/EPOLLRDHUP.

- vpoll\_create

  This function creates a “vpollfd”. The argument *init\_events* is used to set the initial state of events. The following value can be included in *flags*:

- FD\_CLOEXEC:

  Set the close-on-exec flag on the new file descriptor. See the description of the O\_CLOEXEC flag in [open(2)](/open/2.md) for reasons why this may be useful.

- vpoll\_ctl

  This function changes the set of pending events reported by a “vpollfd”. The argument *op* can take the following values:

- VPOLL\_CTL\_ADDEVENTS:

  the events set in the argument *events* are added to the set of pending events.

- VPOLL\_CTL\_DELEVENTS:

  the events set in the argument *events* are deleted from the set of pending events.

- VPOLL\_CTL\_SETEVENTS:

  the value of the argument *events* is assigned to the set of pending events.

- vpoll\_close

  This function closes the vpoll file descritor.

## RETURN VALUE

vpoll\_create returns the new file descriptor, or -1 if an error occurred (in which case, errno is set appropriately)

vpoll\_ctl and vpoll\_close return zero in case of success. On error, -1 is returned, and errno is set appropriately.

## EXAMPLE

-

  ```
  #define _GNU_SOURCE
  #include *stdio.h*
  #include *stdlib.h*
  #include *unistd.h*
  #include *fcntl.h*
  #include *errno.h*
  #include *sys/epoll.h*
  #include *vpoll.h*
  int main(int argc, char *argv[]) {
    int vpollfd = vpoll_create(0, FD_CLOEXEC);
    int epfd = epoll_create1(EPOLL_CLOEXEC);
    struct epoll_event reqevents={EPOLLIN | EPOLLRDHUP | EPOLLERR |
        EPOLLOUT | EPOLLHUP | EPOLLPRI};
    epoll_ctl(epfd,  EPOLL_CTL_ADD, vpollfd, &reqevents);
    switch (fork()) {
        case 0:
            sleep(3);
            vpoll_ctl(vpollfd, VPOLL_CTL_ADDEVENTS,  EPOLLIN);
            sleep(3);
            vpoll_ctl(vpollfd, VPOLL_CTL_ADDEVENTS,  EPOLLIN);
            sleep(3);
            vpoll_ctl(vpollfd, VPOLL_CTL_ADDEVENTS,  EPOLLOUT);
            sleep(3);
            vpoll_ctl(vpollfd, VPOLL_CTL_ADDEVENTS,  EPOLLHUP);
            sleep(3);
            exit(0);
        default:
            while (1) {
                struct epoll_event ev;
                int n = epoll_wait(epfd, &ev, 1, 1000);
                if (n * 0) {
                    perror("epoll_wait");
                    break;
                }
                if (n * 0) {
                    printf("GOT event %x\n", ev.events);
                    vpoll_ctl(vpollfd, VPOLL_CTL_DELEVENTS, ev.events);
                    if (ev.events & EPOLLHUP)
                            break;
                } else {
                    printf("timeout\n");
                }
            }
            break;
        case -1:
            printf("fork error\n");
    }
    vpoll_close(vpollfd);
    close(epfd);
    return 0;
  }
  ```

On a machine running a Linux Kernel providing eventfd/vpoll the output of this program is:

-

  ```
  timeout
  timeout
  GOT event 1
  timeout
  timeout
  GOT event 1
  timeout
  timeout
  GOT event 4
  timeout
  timeout
  GOT event 10
  ```

Instead when the demo program runs using the emulation layer the output is:

-

  ```
  timeout
  timeout
  GOT event 1
  timeout
  timeout
  GOT event 1
  timeout
  timeout
  GOT event 4
  timeout
  timeout
  GOT event 2011
  ```

In fact, the emulator uses a socketpair to generate the events. Hangup is emulated by closing the other end of the socketpair: this generates EPOLLHUP as well as EPOLLIN and EPOLLRDHUP.

## AUTHOR

VirtualSquare. Project leader: Renzo Davoli.
