1*1767006bSBryan Cantrill /* 2*1767006bSBryan Cantrill * This file and its contents are supplied under the terms of the 3*1767006bSBryan Cantrill * Common Development and Distribution License ("CDDL"), version 1.0. 4*1767006bSBryan Cantrill * You may only use this file in accordance with the terms of version 5*1767006bSBryan Cantrill * 1.0 of the CDDL. 6*1767006bSBryan Cantrill * 7*1767006bSBryan Cantrill * A full copy of the text of the CDDL should have accompanied this 8*1767006bSBryan Cantrill * source. A copy of the CDDL is also available via the Internet at 9*1767006bSBryan Cantrill * http://www.illumos.org/license/CDDL. 10*1767006bSBryan Cantrill */ 11*1767006bSBryan Cantrill 12*1767006bSBryan Cantrill /* 13*1767006bSBryan Cantrill * Copyright (c) 2015, Joyent, Inc. All rights reserved. 14*1767006bSBryan Cantrill */ 15*1767006bSBryan Cantrill 16*1767006bSBryan Cantrill #include <sys/eventfd.h> 17*1767006bSBryan Cantrill #include <sys/stat.h> 18*1767006bSBryan Cantrill #include <unistd.h> 19*1767006bSBryan Cantrill #include <errno.h> 20*1767006bSBryan Cantrill #include <fcntl.h> 21*1767006bSBryan Cantrill 22*1767006bSBryan Cantrill int 23*1767006bSBryan Cantrill eventfd(unsigned int initval, int flags) 24*1767006bSBryan Cantrill { 25*1767006bSBryan Cantrill int oflags = O_RDWR; 26*1767006bSBryan Cantrill uint64_t val = initval; 27*1767006bSBryan Cantrill int fd; 28*1767006bSBryan Cantrill 29*1767006bSBryan Cantrill if (flags & ~(EFD_NONBLOCK | EFD_CLOEXEC | EFD_SEMAPHORE)) { 30*1767006bSBryan Cantrill errno = EINVAL; 31*1767006bSBryan Cantrill return (-1); 32*1767006bSBryan Cantrill } 33*1767006bSBryan Cantrill 34*1767006bSBryan Cantrill if (flags & EFD_NONBLOCK) 35*1767006bSBryan Cantrill oflags |= O_NONBLOCK; 36*1767006bSBryan Cantrill 37*1767006bSBryan Cantrill if (flags & EFD_CLOEXEC) 38*1767006bSBryan Cantrill oflags |= O_CLOEXEC; 39*1767006bSBryan Cantrill 40*1767006bSBryan Cantrill if ((fd = open("/dev/eventfd", oflags)) < 0) 41*1767006bSBryan Cantrill return (-1); 42*1767006bSBryan Cantrill 43*1767006bSBryan Cantrill if ((flags & EFD_SEMAPHORE) && 44*1767006bSBryan Cantrill ioctl(fd, EVENTFDIOC_SEMAPHORE, 0) != 0) { 45*1767006bSBryan Cantrill (void) close(fd); 46*1767006bSBryan Cantrill return (-1); 47*1767006bSBryan Cantrill } 48*1767006bSBryan Cantrill 49*1767006bSBryan Cantrill if (write(fd, &val, sizeof (val)) < sizeof (val)) { 50*1767006bSBryan Cantrill (void) close(fd); 51*1767006bSBryan Cantrill return (-1); 52*1767006bSBryan Cantrill } 53*1767006bSBryan Cantrill 54*1767006bSBryan Cantrill return (fd); 55*1767006bSBryan Cantrill } 56*1767006bSBryan Cantrill 57*1767006bSBryan Cantrill int 58*1767006bSBryan Cantrill eventfd_read(int fd, eventfd_t *valp) 59*1767006bSBryan Cantrill { 60*1767006bSBryan Cantrill return (read(fd, valp, sizeof (*valp)) < sizeof (*valp) ? -1 : 0); 61*1767006bSBryan Cantrill } 62*1767006bSBryan Cantrill 63*1767006bSBryan Cantrill int 64*1767006bSBryan Cantrill eventfd_write(int fd, eventfd_t val) 65*1767006bSBryan Cantrill { 66*1767006bSBryan Cantrill return (write(fd, &val, sizeof (val)) < sizeof (val) ? -1 : 0); 67*1767006bSBryan Cantrill } 68