2 * Copyright (c) 2013 Pantheon Technologies s.r.o. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
9 package org.opendaylight.openflowjava.protocol.impl.core;
11 import io.netty.channel.Channel;
12 import io.netty.channel.ChannelInitializer;
13 import io.netty.channel.group.DefaultChannelGroup;
14 import io.netty.channel.socket.SocketChannel;
15 import io.netty.handler.ssl.SslHandler;
17 import java.net.InetAddress;
18 import java.util.Iterator;
19 import java.util.concurrent.TimeUnit;
21 import javax.net.ssl.SSLEngine;
23 import org.opendaylight.openflowjava.protocol.api.connection.SwitchConnectionHandler;
24 import org.opendaylight.openflowjava.protocol.api.connection.TlsConfiguration;
25 import org.opendaylight.openflowjava.protocol.impl.connection.ConnectionAdapterFactory;
26 import org.opendaylight.openflowjava.protocol.impl.connection.ConnectionAdapterFactoryImpl;
27 import org.opendaylight.openflowjava.protocol.impl.connection.ConnectionFacade;
28 import org.opendaylight.openflowjava.protocol.impl.deserialization.DeserializationFactory;
29 import org.opendaylight.openflowjava.protocol.impl.serialization.SerializationFactory;
30 import org.slf4j.Logger;
31 import org.slf4j.LoggerFactory;
34 * Initializes the channel
35 * @author michal.polkorab
37 public class PublishingChannelInitializer extends ChannelInitializer<SocketChannel> {
40 * Enum used for storing names of used components (in pipeline).
42 public static enum COMPONENT_NAMES {
45 * Detects switch idle state
49 * Detects TLS connections
53 * Component for handling TLS frames
57 * Decodes incoming messages into message frames
61 * Detects version of incoming OpenFlow Protocol message
65 * Transforms OpenFlow Protocol byte messages into POJOs
69 * Transforms POJOs into OpenFlow Protocol byte messages
73 * Delegates translated POJOs into MessageConsumer
75 DELEGATING_INBOUND_HANDLER,
78 private static final Logger LOGGER = LoggerFactory
79 .getLogger(PublishingChannelInitializer.class);
80 private final DefaultChannelGroup allChannels;
81 private SwitchConnectionHandler switchConnectionHandler;
82 private long switchIdleTimeout;
83 private SerializationFactory serializationFactory;
84 private DeserializationFactory deserializationFactory;
85 private ConnectionAdapterFactory connectionAdapterFactory;
86 private TlsConfiguration tlsConfiguration ;
91 public PublishingChannelInitializer() {
92 this( new DefaultChannelGroup("netty-receiver", null), new ConnectionAdapterFactoryImpl() );
99 protected PublishingChannelInitializer( DefaultChannelGroup channelGroup, ConnectionAdapterFactory connAdaptorFactory ) {
100 allChannels = channelGroup ;
101 connectionAdapterFactory = connAdaptorFactory ;
105 protected void initChannel(final SocketChannel ch) {
106 InetAddress switchAddress = ch.remoteAddress().getAddress();
107 int port = ch.localAddress().getPort();
108 int remotePort = ch.remoteAddress().getPort();
109 LOGGER.info("Incoming connection from (remote address): " + switchAddress.toString()
110 + ":" + remotePort + " --> :" + port);
111 if (!switchConnectionHandler.accept(switchAddress)) {
113 LOGGER.info("Incoming connection rejected");
116 LOGGER.info("Incoming connection accepted - building pipeline");
118 ConnectionFacade connectionFacade = null;
119 connectionFacade = connectionAdapterFactory.createConnectionFacade(ch);
121 LOGGER.debug("calling plugin: " + switchConnectionHandler);
122 switchConnectionHandler.onSwitchConnected(connectionFacade);
123 connectionFacade.checkListeners();
124 ch.pipeline().addLast(COMPONENT_NAMES.IDLE_HANDLER.name(), new IdleHandler(switchIdleTimeout, TimeUnit.MILLISECONDS));
126 // If this channel is configured to support SSL it will only support SSL
127 if (tlsConfiguration != null) {
128 SslContextFactory sslFactory = new SslContextFactory(tlsConfiguration);
129 SSLEngine engine = sslFactory.getServerContext().createSSLEngine();
130 engine.setNeedClientAuth(true);
131 engine.setUseClientMode(false);
132 ch.pipeline().addLast(COMPONENT_NAMES.SSL_HANDLER.name(), new SslHandler(engine));
134 ch.pipeline().addLast(COMPONENT_NAMES.OF_FRAME_DECODER.name(), new OFFrameDecoder(connectionFacade));
135 ch.pipeline().addLast(COMPONENT_NAMES.OF_VERSION_DETECTOR.name(), new OFVersionDetector());
136 OFDecoder ofDecoder = new OFDecoder();
137 ofDecoder.setDeserializationFactory(deserializationFactory);
138 ch.pipeline().addLast(COMPONENT_NAMES.OF_DECODER.name(), ofDecoder);
139 OFEncoder ofEncoder = new OFEncoder();
140 ofEncoder.setSerializationFactory(serializationFactory);
141 ch.pipeline().addLast(COMPONENT_NAMES.OF_ENCODER.name(), ofEncoder);
142 ch.pipeline().addLast(COMPONENT_NAMES.DELEGATING_INBOUND_HANDLER.name(), new DelegatingInboundHandler(connectionFacade));
143 if (tlsConfiguration == null) {
144 connectionFacade.fireConnectionReadyNotification();
146 } catch (Exception e) {
147 LOGGER.error("Failed to initialize channel", e);
153 * @return iterator through active connections
155 public Iterator<Channel> getConnectionIterator() {
156 return allChannels.iterator();
160 * @return amount of active channels
163 return allChannels.size();
167 * @param switchConnectionHandler the switchConnectionHandler to set
169 public void setSwitchConnectionHandler(final SwitchConnectionHandler switchConnectionHandler) {
170 this.switchConnectionHandler = switchConnectionHandler;
174 * @param switchIdleTimeout the switchIdleTimeout to set
176 public void setSwitchIdleTimeout(final long switchIdleTimeout) {
177 this.switchIdleTimeout = switchIdleTimeout;
181 * @param serializationFactory
183 public void setSerializationFactory(final SerializationFactory serializationFactory) {
184 this.serializationFactory = serializationFactory;
188 * @param deserializationFactory
190 public void setDeserializationFactory(final DeserializationFactory deserializationFactory) {
191 this.deserializationFactory = deserializationFactory;
195 * @param tlsConfiguration
197 public void setTlsConfiguration(TlsConfiguration tlsConfiguration) {
198 this.tlsConfiguration = tlsConfiguration;