1/*
2 * Copyright (c) 2008, 2013, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.  Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26package sun.nio.ch;
27
28import java.io.IOException;
29import jdk.internal.misc.Unsafe;
30
31/**
32 * Provides access to the Linux epoll facility.
33 */
34
35class EPoll {
36    private EPoll() { }
37
38    private static final Unsafe unsafe = Unsafe.getUnsafe();
39
40    /**
41     * typedef union epoll_data {
42     *     void *ptr;
43     *     int fd;
44     *     __uint32_t u32;
45     *     __uint64_t u64;
46     *  } epoll_data_t;
47     *
48     * struct epoll_event {
49     *     __uint32_t events;
50     *     epoll_data_t data;
51     * }
52     */
53    private static final int SIZEOF_EPOLLEVENT   = eventSize();
54    private static final int OFFSETOF_EVENTS     = eventsOffset();
55    private static final int OFFSETOF_FD         = dataOffset();
56
57    // opcodes
58    static final int EPOLL_CTL_ADD  = 1;
59    static final int EPOLL_CTL_DEL  = 2;
60    static final int EPOLL_CTL_MOD  = 3;
61
62    // flags
63    static final int EPOLLONESHOT   = (1 << 30);
64
65    /**
66     * Allocates a poll array to handle up to {@code count} events.
67     */
68    static long allocatePollArray(int count) {
69        return unsafe.allocateMemory(count * SIZEOF_EPOLLEVENT);
70    }
71
72    /**
73     * Free a poll array
74     */
75    static void freePollArray(long address) {
76        unsafe.freeMemory(address);
77    }
78
79    /**
80     * Returns event[i];
81     */
82    static long getEvent(long address, int i) {
83        return address + (SIZEOF_EPOLLEVENT*i);
84    }
85
86    /**
87     * Returns event->data.fd
88     */
89    static int getDescriptor(long eventAddress) {
90        return unsafe.getInt(eventAddress + OFFSETOF_FD);
91    }
92
93    /**
94     * Returns event->events
95     */
96    static int getEvents(long eventAddress) {
97        return unsafe.getInt(eventAddress + OFFSETOF_EVENTS);
98    }
99
100    // -- Native methods --
101
102    private static native int eventSize();
103
104    private static native int eventsOffset();
105
106    private static native int dataOffset();
107
108    static native int epollCreate() throws IOException;
109
110    static native int epollCtl(int epfd, int opcode, int fd, int events);
111
112    static native int epollWait(int epfd, long pollAddress, int numfds)
113        throws IOException;
114
115    static {
116        IOUtil.load();
117    }
118}
119