author | alanb |
Sat, 24 Mar 2018 08:49:55 +0000 | |
changeset 49417 | 1d3139252c1c |
parent 49248 | 15a0e60c8b97 |
child 49493 | 814bd31f8da0 |
permissions | -rw-r--r-- |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
1 |
/* |
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
2 |
* Copyright (c) 2012, 2018, Oracle and/or its affiliates. All rights reserved. |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
3 |
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
4 |
* |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
5 |
* This code is free software; you can redistribute it and/or modify it |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
6 |
* under the terms of the GNU General Public License version 2 only, as |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
7 |
* published by the Free Software Foundation. Oracle designates this |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
8 |
* particular file as subject to the "Classpath" exception as provided |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
9 |
* by Oracle in the LICENSE file that accompanied this code. |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
10 |
* |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
11 |
* This code is distributed in the hope that it will be useful, but WITHOUT |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
12 |
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
13 |
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
14 |
* version 2 for more details (a copy is included in the LICENSE file that |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
15 |
* accompanied this code). |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
16 |
* |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
17 |
* You should have received a copy of the GNU General Public License version |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
18 |
* 2 along with this work; if not, write to the Free Software Foundation, |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
19 |
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
20 |
* |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
21 |
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
22 |
* or visit www.oracle.com if you need additional information or have any |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
23 |
* questions. |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
24 |
*/ |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
25 |
|
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
26 |
package sun.nio.ch; |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
27 |
|
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
28 |
import java.io.IOException; |
49417 | 29 |
import java.nio.channels.ClosedSelectorException; |
30 |
import java.nio.channels.SelectableChannel; |
|
31 |
import java.nio.channels.SelectionKey; |
|
32 |
import java.nio.channels.Selector; |
|
33 |
import java.nio.channels.spi.SelectorProvider; |
|
34 |
import java.util.ArrayDeque; |
|
35 |
import java.util.Deque; |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
36 |
import java.util.HashMap; |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
37 |
import java.util.Iterator; |
49417 | 38 |
import java.util.Map; |
39 |
import java.util.concurrent.TimeUnit; |
|
40 |
import jdk.internal.misc.Unsafe; |
|
41 |
||
42 |
import static sun.nio.ch.SolarisEventPort.PORT_SOURCE_FD; |
|
43 |
import static sun.nio.ch.SolarisEventPort.PORT_SOURCE_USER; |
|
44 |
import static sun.nio.ch.SolarisEventPort.SIZEOF_PORT_EVENT; |
|
45 |
import static sun.nio.ch.SolarisEventPort.OFFSETOF_EVENTS; |
|
46 |
import static sun.nio.ch.SolarisEventPort.OFFSETOF_SOURCE; |
|
47 |
import static sun.nio.ch.SolarisEventPort.OFFSETOF_OBJECT; |
|
48 |
import static sun.nio.ch.SolarisEventPort.port_create; |
|
49 |
import static sun.nio.ch.SolarisEventPort.port_close; |
|
50 |
import static sun.nio.ch.SolarisEventPort.port_associate; |
|
51 |
import static sun.nio.ch.SolarisEventPort.port_dissociate; |
|
52 |
import static sun.nio.ch.SolarisEventPort.port_getn; |
|
53 |
import static sun.nio.ch.SolarisEventPort.port_send; |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
54 |
|
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
55 |
/** |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
56 |
* Selector implementation based on the Solaris event port mechanism. |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
57 |
*/ |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
58 |
|
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
59 |
class EventPortSelectorImpl |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
60 |
extends SelectorImpl |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
61 |
{ |
49417 | 62 |
// maximum number of events to retrive in one call to port_getn |
63 |
static final int MAX_EVENTS = Math.min(IOUtil.fdLimit()-1, 1024); |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
64 |
|
49417 | 65 |
// port file descriptor |
66 |
private final int pfd; |
|
67 |
||
68 |
// the poll array (populated by port_getn) |
|
69 |
private final long pollArrayAddress; |
|
70 |
private final AllocatedNativeObject pollArray; |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
71 |
|
49417 | 72 |
// a registration of a file descriptor with a selector |
73 |
private static class RegEntry { |
|
74 |
final SelectionKeyImpl ski; |
|
75 |
int registeredOps; |
|
76 |
int lastUpdate; |
|
77 |
RegEntry(SelectionKeyImpl ski) { |
|
78 |
this.ski = ski; |
|
79 |
} |
|
80 |
} |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
81 |
|
49417 | 82 |
// maps a file descriptor to registration entry, synchronize on selector |
83 |
private final Map<Integer, RegEntry> fdToRegEntry = new HashMap<>(); |
|
84 |
||
85 |
// the last update operation, incremented by processUpdateQueue |
|
86 |
private int lastUpdate; |
|
87 |
||
88 |
// pending new registrations/updates, queued by implRegister, putEventOps, |
|
89 |
// and updateSelectedKeys |
|
90 |
private final Object updateLock = new Object(); |
|
91 |
private final Deque<SelectionKeyImpl> newKeys = new ArrayDeque<>(); |
|
92 |
private final Deque<SelectionKeyImpl> updateKeys = new ArrayDeque<>(); |
|
93 |
private final Deque<Integer> updateOps = new ArrayDeque<>(); |
|
94 |
||
95 |
// interrupt triggering and clearing |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
96 |
private final Object interruptLock = new Object(); |
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
97 |
private boolean interruptTriggered; |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
98 |
|
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
99 |
EventPortSelectorImpl(SelectorProvider sp) throws IOException { |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
100 |
super(sp); |
49417 | 101 |
|
102 |
this.pfd = port_create(); |
|
103 |
||
104 |
int allocationSize = MAX_EVENTS * SIZEOF_PORT_EVENT; |
|
105 |
this.pollArray = new AllocatedNativeObject(allocationSize, false); |
|
106 |
this.pollArrayAddress = pollArray.address(); |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
107 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
108 |
|
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
109 |
private void ensureOpen() { |
49417 | 110 |
if (!isOpen()) |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
111 |
throw new ClosedSelectorException(); |
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
112 |
} |
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
113 |
|
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
114 |
@Override |
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
115 |
protected int doSelect(long timeout) throws IOException { |
49417 | 116 |
assert Thread.holdsLock(this); |
117 |
||
118 |
int numEvents; |
|
119 |
processUpdateQueue(); |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
120 |
processDeregisterQueue(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
121 |
try { |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
122 |
begin(); |
49417 | 123 |
|
124 |
long to = timeout; |
|
125 |
boolean timedPoll = (to > 0); |
|
126 |
do { |
|
127 |
long startTime = timedPoll ? System.nanoTime() : 0; |
|
128 |
numEvents = port_getn(pfd, pollArrayAddress, MAX_EVENTS, to); |
|
129 |
if (numEvents == IOStatus.INTERRUPTED && timedPoll) { |
|
130 |
// timed poll interrupted so need to adjust timeout |
|
131 |
long adjust = System.nanoTime() - startTime; |
|
132 |
to -= TimeUnit.MILLISECONDS.convert(adjust, TimeUnit.NANOSECONDS); |
|
133 |
if (to <= 0) { |
|
134 |
// timeout also expired so no retry |
|
135 |
numEvents = 0; |
|
136 |
} |
|
137 |
} |
|
138 |
} while (numEvents == IOStatus.INTERRUPTED); |
|
139 |
assert IOStatus.check(numEvents); |
|
140 |
||
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
141 |
} finally { |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
142 |
end(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
143 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
144 |
processDeregisterQueue(); |
49417 | 145 |
return processPortEvents(numEvents); |
146 |
} |
|
147 |
||
148 |
/** |
|
149 |
* Process new registrations and changes to the interest ops. |
|
150 |
*/ |
|
151 |
private void processUpdateQueue() throws IOException { |
|
152 |
assert Thread.holdsLock(this); |
|
153 |
||
154 |
// bump lastUpdate to ensure that the interest ops are changed at most |
|
155 |
// once per bulk update |
|
156 |
lastUpdate++; |
|
157 |
||
158 |
synchronized (updateLock) { |
|
159 |
SelectionKeyImpl ski; |
|
160 |
||
161 |
// new registrations |
|
162 |
while ((ski = newKeys.pollFirst()) != null) { |
|
163 |
if (ski.isValid()) { |
|
164 |
SelChImpl ch = ski.channel; |
|
165 |
int fd = ch.getFDVal(); |
|
166 |
RegEntry previous = fdToRegEntry.put(fd, new RegEntry(ski)); |
|
167 |
assert previous == null; |
|
168 |
} |
|
169 |
} |
|
170 |
||
171 |
// changes to interest ops |
|
172 |
assert updateKeys.size() == updateOps.size(); |
|
173 |
while ((ski = updateKeys.pollFirst()) != null) { |
|
174 |
int ops = updateOps.pollFirst(); |
|
175 |
int fd = ski.channel.getFDVal(); |
|
176 |
RegEntry e = fdToRegEntry.get(fd); |
|
177 |
if (ski.isValid() && (e != null) && (e.lastUpdate != lastUpdate)) { |
|
178 |
assert e.ski == ski; |
|
179 |
if ((ops != e.registeredOps)) { |
|
180 |
if (ops == 0) { |
|
181 |
port_dissociate(pfd, PORT_SOURCE_FD, fd); |
|
182 |
} else { |
|
183 |
port_associate(pfd, PORT_SOURCE_FD, fd, ops); |
|
184 |
} |
|
185 |
e.registeredOps = ops; |
|
186 |
} |
|
187 |
e.lastUpdate = lastUpdate; |
|
188 |
} |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
189 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
190 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
191 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
192 |
|
49417 | 193 |
/** |
194 |
* Process the port events. This method updates the keys of file descriptors |
|
195 |
* that were polled. It also re-queues the key so that the file descriptor |
|
196 |
* is re-associated at the next select operation. |
|
197 |
* |
|
198 |
* @return the number of selection keys updated. |
|
199 |
*/ |
|
200 |
private int processPortEvents(int numEvents) throws IOException { |
|
201 |
assert Thread.holdsLock(this); |
|
202 |
assert Thread.holdsLock(nioSelectedKeys()); |
|
203 |
||
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
204 |
int numKeysUpdated = 0; |
49417 | 205 |
boolean interrupted = false; |
206 |
||
207 |
synchronized (updateLock) { |
|
208 |
for (int i = 0; i < numEvents; i++) { |
|
209 |
short source = getSource(i); |
|
210 |
if (source == PORT_SOURCE_FD) { |
|
211 |
int fd = getDescriptor(i); |
|
212 |
RegEntry e = fdToRegEntry.get(fd); |
|
213 |
if (e != null) { |
|
214 |
SelectionKeyImpl ski = e.ski; |
|
215 |
int rOps = getEventOps(i); |
|
216 |
if (selectedKeys.contains(ski)) { |
|
217 |
if (ski.channel.translateAndSetReadyOps(rOps, ski)) { |
|
218 |
numKeysUpdated++; |
|
219 |
} |
|
220 |
} else { |
|
221 |
ski.channel.translateAndSetReadyOps(rOps, ski); |
|
222 |
if ((ski.nioReadyOps() & ski.nioInterestOps()) != 0) { |
|
223 |
selectedKeys.add(ski); |
|
224 |
numKeysUpdated++; |
|
225 |
} |
|
226 |
} |
|
227 |
||
228 |
// queue selection key so that it is re-associated at |
|
229 |
// next select. Push to end of deque so that changes to |
|
230 |
// the interest ops are processed first |
|
231 |
updateKeys.addLast(ski); |
|
232 |
updateOps.addLast(e.registeredOps); |
|
233 |
e.registeredOps = 0; |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
234 |
} |
49417 | 235 |
} else if (source == PORT_SOURCE_USER) { |
236 |
interrupted = true; |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
237 |
} else { |
49417 | 238 |
assert false; |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
239 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
240 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
241 |
} |
49417 | 242 |
|
243 |
if (interrupted) { |
|
244 |
clearInterrupt(); |
|
245 |
} |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
246 |
return numKeysUpdated; |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
247 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
248 |
|
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
249 |
@Override |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
250 |
protected void implClose() throws IOException { |
49417 | 251 |
assert !isOpen(); |
252 |
assert Thread.holdsLock(this); |
|
253 |
assert Thread.holdsLock(nioKeys()); |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
254 |
|
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
255 |
// prevent further wakeup |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
256 |
synchronized (interruptLock) { |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
257 |
interruptTriggered = true; |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
258 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
259 |
|
49417 | 260 |
port_close(pfd); |
261 |
pollArray.free(); |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
262 |
|
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
263 |
// Deregister channels |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
264 |
Iterator<SelectionKey> i = keys.iterator(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
265 |
while (i.hasNext()) { |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
266 |
SelectionKeyImpl ski = (SelectionKeyImpl)i.next(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
267 |
deregister(ski); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
268 |
SelectableChannel selch = ski.channel(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
269 |
if (!selch.isOpen() && !selch.isRegistered()) |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
270 |
((SelChImpl)selch).kill(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
271 |
i.remove(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
272 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
273 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
274 |
|
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
275 |
@Override |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
276 |
protected void implRegister(SelectionKeyImpl ski) { |
49417 | 277 |
assert Thread.holdsLock(nioKeys()); |
278 |
ensureOpen(); |
|
279 |
synchronized (updateLock) { |
|
280 |
newKeys.addLast(ski); |
|
281 |
} |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
282 |
keys.add(ski); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
283 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
284 |
|
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
285 |
@Override |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
286 |
protected void implDereg(SelectionKeyImpl ski) throws IOException { |
49417 | 287 |
assert !ski.isValid(); |
288 |
assert Thread.holdsLock(this); |
|
289 |
assert Thread.holdsLock(nioKeys()); |
|
290 |
assert Thread.holdsLock(nioSelectedKeys()); |
|
291 |
||
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
292 |
int fd = ski.channel.getFDVal(); |
49417 | 293 |
RegEntry e = fdToRegEntry.remove(fd); |
294 |
if (e != null && e.registeredOps != 0) { |
|
295 |
port_dissociate(pfd, PORT_SOURCE_FD, fd); |
|
296 |
} |
|
297 |
||
298 |
selectedKeys.remove(ski); |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
299 |
keys.remove(ski); |
49417 | 300 |
|
301 |
// remove from channel's key set |
|
302 |
deregister(ski); |
|
303 |
||
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
304 |
SelectableChannel selch = ski.channel(); |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
305 |
if (!selch.isOpen() && !selch.isRegistered()) |
49417 | 306 |
((SelChImpl) selch).kill(); |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
307 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
308 |
|
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
309 |
@Override |
49417 | 310 |
public void putEventOps(SelectionKeyImpl ski, int ops) { |
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
311 |
ensureOpen(); |
49417 | 312 |
synchronized (updateLock) { |
313 |
// push to front of deque so that it processed before other |
|
314 |
// updates for the same key. |
|
315 |
updateOps.addFirst(ops); |
|
316 |
updateKeys.addFirst(ski); |
|
317 |
} |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
318 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
319 |
|
49248
15a0e60c8b97
8199611: (se) Minor selector implementation clean-up
alanb
parents:
47216
diff
changeset
|
320 |
@Override |
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
321 |
public Selector wakeup() { |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
322 |
synchronized (interruptLock) { |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
323 |
if (!interruptTriggered) { |
49417 | 324 |
try { |
325 |
port_send(pfd, 0); |
|
326 |
} catch (IOException ioe) { |
|
327 |
throw new InternalError(ioe); |
|
328 |
} |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
329 |
interruptTriggered = true; |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
330 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
331 |
} |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
332 |
return this; |
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
333 |
} |
49417 | 334 |
|
335 |
private void clearInterrupt() throws IOException { |
|
336 |
synchronized (interruptLock) { |
|
337 |
interruptTriggered = false; |
|
338 |
} |
|
339 |
} |
|
340 |
||
341 |
private short getSource(int i) { |
|
342 |
int offset = SIZEOF_PORT_EVENT * i + OFFSETOF_SOURCE; |
|
343 |
return pollArray.getShort(offset); |
|
344 |
} |
|
345 |
||
346 |
private int getEventOps(int i) { |
|
347 |
int offset = SIZEOF_PORT_EVENT * i + OFFSETOF_EVENTS; |
|
348 |
return pollArray.getInt(offset); |
|
349 |
} |
|
350 |
||
351 |
private int getDescriptor(int i) { |
|
352 |
//assert Unsafe.getUnsafe().addressSize() == 8; |
|
353 |
int offset = SIZEOF_PORT_EVENT * i + OFFSETOF_OBJECT; |
|
354 |
return (int) pollArray.getLong(offset); |
|
355 |
} |
|
12872
16fa902b1469
7172826: (se) Selector based on the Solaris event port mechanism
alanb
parents:
diff
changeset
|
356 |
} |