View Javadoc
1   /*
2    * Copyright 2014 The Netty Project
3    *
4    * The Netty Project licenses this file to you under the Apache License,
5    * version 2.0 (the "License"); you may not use this file except in compliance
6    * with the License. You may obtain a copy of the License at:
7    *
8    *   http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12   * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13   * License for the specific language governing permissions and limitations
14   * under the License.
15   */
16  package io.netty.channel.epoll;
17  
18  import io.netty.buffer.ByteBufAllocator;
19  import io.netty.channel.ChannelOption;
20  import io.netty.channel.MessageSizeEstimator;
21  import io.netty.channel.RecvByteBufAllocator;
22  import io.netty.channel.socket.SocketChannelConfig;
23  import io.netty.util.internal.PlatformDependent;
24  
25  import java.util.Map;
26  
27  import static io.netty.channel.ChannelOption.*;
28  
29  public final class EpollSocketChannelConfig extends EpollChannelConfig implements SocketChannelConfig {
30  
31      private final EpollSocketChannel channel;
32      private volatile boolean allowHalfClosure;
33  
34      /**
35       * Creates a new instance.
36       */
37      EpollSocketChannelConfig(EpollSocketChannel channel) {
38          super(channel);
39  
40          this.channel = channel;
41          if (PlatformDependent.canEnableTcpNoDelayByDefault()) {
42              setTcpNoDelay(true);
43          }
44      }
45  
46      @Override
47      public Map<ChannelOption<?>, Object> getOptions() {
48          return getOptions(
49                  super.getOptions(),
50                  SO_RCVBUF, SO_SNDBUF, TCP_NODELAY, SO_KEEPALIVE, SO_REUSEADDR, SO_LINGER, IP_TOS,
51                  ALLOW_HALF_CLOSURE, EpollChannelOption.TCP_CORK, EpollChannelOption.TCP_KEEPCNT,
52                  EpollChannelOption.TCP_KEEPIDLE, EpollChannelOption.TCP_KEEPINTVL);
53      }
54  
55      @SuppressWarnings("unchecked")
56      @Override
57      public <T> T getOption(ChannelOption<T> option) {
58          if (option == SO_RCVBUF) {
59              return (T) Integer.valueOf(getReceiveBufferSize());
60          }
61          if (option == SO_SNDBUF) {
62              return (T) Integer.valueOf(getSendBufferSize());
63          }
64          if (option == TCP_NODELAY) {
65              return (T) Boolean.valueOf(isTcpNoDelay());
66          }
67          if (option == SO_KEEPALIVE) {
68              return (T) Boolean.valueOf(isKeepAlive());
69          }
70          if (option == SO_REUSEADDR) {
71              return (T) Boolean.valueOf(isReuseAddress());
72          }
73          if (option == SO_LINGER) {
74              return (T) Integer.valueOf(getSoLinger());
75          }
76          if (option == IP_TOS) {
77              return (T) Integer.valueOf(getTrafficClass());
78          }
79          if (option == ALLOW_HALF_CLOSURE) {
80              return (T) Boolean.valueOf(isAllowHalfClosure());
81          }
82          if (option == EpollChannelOption.TCP_CORK) {
83              return (T) Boolean.valueOf(isTcpCork());
84          }
85          if (option == EpollChannelOption.TCP_KEEPIDLE) {
86              return (T) Integer.valueOf(getTcpKeepIdle());
87          }
88          if (option == EpollChannelOption.TCP_KEEPINTVL) {
89              return (T) Integer.valueOf(getTcpKeepIntvl());
90          }
91          if (option == EpollChannelOption.TCP_KEEPCNT) {
92              return (T) Integer.valueOf(getTcpKeepCnt());
93          }
94          return super.getOption(option);
95      }
96  
97      @Override
98      public <T> boolean setOption(ChannelOption<T> option, T value) {
99          validate(option, value);
100 
101         if (option == SO_RCVBUF) {
102             setReceiveBufferSize((Integer) value);
103         } else if (option == SO_SNDBUF) {
104             setSendBufferSize((Integer) value);
105         } else if (option == TCP_NODELAY) {
106             setTcpNoDelay((Boolean) value);
107         } else if (option == SO_KEEPALIVE) {
108             setKeepAlive((Boolean) value);
109         } else if (option == SO_REUSEADDR) {
110             setReuseAddress((Boolean) value);
111         } else if (option == SO_LINGER) {
112             setSoLinger((Integer) value);
113         } else if (option == IP_TOS) {
114             setTrafficClass((Integer) value);
115         } else if (option == ALLOW_HALF_CLOSURE) {
116             setAllowHalfClosure((Boolean) value);
117         } else if (option == EpollChannelOption.TCP_CORK) {
118             setTcpCork((Boolean) value);
119         } else if (option == EpollChannelOption.TCP_KEEPIDLE) {
120             setTcpKeepIdle((Integer) value);
121         } else if (option == EpollChannelOption.TCP_KEEPCNT) {
122             setTcpKeepCntl((Integer) value);
123         } else if (option == EpollChannelOption.TCP_KEEPINTVL) {
124             setTcpKeepIntvl((Integer) value);
125         } else {
126             return super.setOption(option, value);
127         }
128 
129         return true;
130     }
131 
132     @Override
133     public int getReceiveBufferSize() {
134         return Native.getReceiveBufferSize(channel.fd().intValue());
135     }
136 
137     @Override
138     public int getSendBufferSize() {
139         return Native.getSendBufferSize(channel.fd().intValue());
140     }
141 
142     @Override
143     public int getSoLinger() {
144         return Native.getSoLinger(channel.fd().intValue());
145     }
146 
147     @Override
148     public int getTrafficClass() {
149         return Native.getTrafficClass(channel.fd().intValue());
150     }
151 
152     @Override
153     public boolean isKeepAlive() {
154         return Native.isKeepAlive(channel.fd().intValue()) == 1;
155     }
156 
157     @Override
158     public boolean isReuseAddress() {
159         return Native.isReuseAddress(channel.fd().intValue()) == 1;
160     }
161 
162     @Override
163     public boolean isTcpNoDelay() {
164         return Native.isTcpNoDelay(channel.fd().intValue()) == 1;
165     }
166 
167     /**
168      * Get the {@code TCP_CORK} option on the socket. See {@code man 7 tcp} for more details.
169      */
170     public boolean isTcpCork() {
171         return Native.isTcpCork(channel.fd().intValue()) == 1;
172     }
173 
174     /**
175      * Get the {@code TCP_KEEPIDLE} option on the socket. See {@code man 7 tcp} for more details.
176      */
177     public int getTcpKeepIdle() {
178         return Native.getTcpKeepIdle(channel.fd().intValue());
179     }
180 
181     /**
182      * Get the {@code TCP_KEEPINTVL} option on the socket. See {@code man 7 tcp} for more details.
183      */
184     public int getTcpKeepIntvl() {
185         return Native.getTcpKeepIntvl(channel.fd().intValue());
186     }
187 
188     /**
189      * Get the {@code TCP_KEEPCNT} option on the socket. See {@code man 7 tcp} for more details.
190      */
191     public int getTcpKeepCnt() {
192         return Native.getTcpKeepCnt(channel.fd().intValue());
193     }
194 
195     @Override
196     public EpollSocketChannelConfig setKeepAlive(boolean keepAlive) {
197         Native.setKeepAlive(channel.fd().intValue(), keepAlive ? 1 : 0);
198         return this;
199     }
200 
201     @Override
202     public EpollSocketChannelConfig setPerformancePreferences(
203             int connectionTime, int latency, int bandwidth) {
204         return this;
205     }
206 
207     @Override
208     public EpollSocketChannelConfig setReceiveBufferSize(int receiveBufferSize) {
209         Native.setReceiveBufferSize(channel.fd().intValue(), receiveBufferSize);
210         return this;
211     }
212 
213     @Override
214     public EpollSocketChannelConfig setReuseAddress(boolean reuseAddress) {
215         Native.setReuseAddress(channel.fd().intValue(), reuseAddress ? 1 : 0);
216         return this;
217     }
218 
219     @Override
220     public EpollSocketChannelConfig setSendBufferSize(int sendBufferSize) {
221         Native.setSendBufferSize(channel.fd().intValue(), sendBufferSize);
222         return this;
223     }
224 
225     @Override
226     public EpollSocketChannelConfig setSoLinger(int soLinger) {
227         Native.setSoLinger(channel.fd().intValue(), soLinger);
228         return this;
229     }
230 
231     @Override
232     public EpollSocketChannelConfig setTcpNoDelay(boolean tcpNoDelay) {
233         Native.setTcpNoDelay(channel.fd().intValue(), tcpNoDelay ? 1 : 0);
234         return this;
235     }
236 
237     /**
238      * Set the {@code TCP_CORK} option on the socket. See {@code man 7 tcp} for more details.
239      */
240     public EpollSocketChannelConfig setTcpCork(boolean tcpCork) {
241         Native.setTcpCork(channel.fd().intValue(), tcpCork ? 1 : 0);
242         return this;
243     }
244 
245     @Override
246     public EpollSocketChannelConfig setTrafficClass(int trafficClass) {
247         Native.setTrafficClass(channel.fd().intValue(), trafficClass);
248         return this;
249     }
250 
251     /**
252      * Set the {@code TCP_KEEPIDLE} option on the socket. See {@code man 7 tcp} for more details.
253      */
254     public EpollSocketChannelConfig setTcpKeepIdle(int seconds) {
255         Native.setTcpKeepIdle(channel.fd().intValue(), seconds);
256         return this;
257     }
258 
259     /**
260      * Set the {@code TCP_KEEPINTVL} option on the socket. See {@code man 7 tcp} for more details.
261      */
262     public EpollSocketChannelConfig setTcpKeepIntvl(int seconds) {
263         Native.setTcpKeepIntvl(channel.fd().intValue(), seconds);
264         return this;
265     }
266 
267     /**
268      * Set the {@code TCP_KEEPCNT} option on the socket. See {@code man 7 tcp} for more details.
269      */
270     public EpollSocketChannelConfig setTcpKeepCntl(int probes) {
271         Native.setTcpKeepCnt(channel.fd().intValue(), probes);
272         return this;
273     }
274 
275     @Override
276     public boolean isAllowHalfClosure() {
277         return allowHalfClosure;
278     }
279 
280     @Override
281     public EpollSocketChannelConfig setAllowHalfClosure(boolean allowHalfClosure) {
282         this.allowHalfClosure = allowHalfClosure;
283         return this;
284     }
285 
286     @Override
287     public EpollSocketChannelConfig setConnectTimeoutMillis(int connectTimeoutMillis) {
288         super.setConnectTimeoutMillis(connectTimeoutMillis);
289         return this;
290     }
291 
292     @Override
293     public EpollSocketChannelConfig setMaxMessagesPerRead(int maxMessagesPerRead) {
294         super.setMaxMessagesPerRead(maxMessagesPerRead);
295         return this;
296     }
297 
298     @Override
299     public EpollSocketChannelConfig setWriteSpinCount(int writeSpinCount) {
300         super.setWriteSpinCount(writeSpinCount);
301         return this;
302     }
303 
304     @Override
305     public EpollSocketChannelConfig setAllocator(ByteBufAllocator allocator) {
306         super.setAllocator(allocator);
307         return this;
308     }
309 
310     @Override
311     public EpollSocketChannelConfig setRecvByteBufAllocator(RecvByteBufAllocator allocator) {
312         super.setRecvByteBufAllocator(allocator);
313         return this;
314     }
315 
316     @Override
317     public EpollSocketChannelConfig setAutoRead(boolean autoRead) {
318         super.setAutoRead(autoRead);
319         return this;
320     }
321 
322     @Override
323     public EpollSocketChannelConfig setWriteBufferHighWaterMark(int writeBufferHighWaterMark) {
324         super.setWriteBufferHighWaterMark(writeBufferHighWaterMark);
325         return this;
326     }
327 
328     @Override
329     public EpollSocketChannelConfig setWriteBufferLowWaterMark(int writeBufferLowWaterMark) {
330         super.setWriteBufferLowWaterMark(writeBufferLowWaterMark);
331         return this;
332     }
333 
334     @Override
335     public EpollSocketChannelConfig setMessageSizeEstimator(MessageSizeEstimator estimator) {
336         super.setMessageSizeEstimator(estimator);
337         return this;
338     }
339 
340     @Override
341     public EpollSocketChannelConfig setEpollMode(EpollMode mode) {
342         super.setEpollMode(mode);
343         return this;
344     }
345 }