blob: 127dee5f3e7d77a2dcd456199bf011132e55c29a [file] [log] [blame]
Vidyashree Rama7bd3d782015-11-23 08:46:33 +05301/*
Brian O'Connor5ab426f2016-04-09 01:19:45 -07002 * Copyright 2015-present Open Networking Laboratory
Vidyashree Rama7bd3d782015-11-23 08:46:33 +05303 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * 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,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16package org.onosproject.bgp;
17
18import org.jboss.netty.buffer.ChannelBuffer;
19import org.jboss.netty.channel.Channel;
20import org.jboss.netty.channel.ChannelHandlerContext;
21import org.jboss.netty.handler.codec.frame.FrameDecoder;
22import org.slf4j.Logger;
23import org.slf4j.LoggerFactory;
24import java.util.concurrent.CountDownLatch;
25
26/**
27 * Class to decode the message received.
28 */
29public class BgpPeerFrameDecoderTest extends FrameDecoder {
30 static final byte OPEN_MSG_TYPE = 0x1;
31 static final byte KEEPALIVE_MSG_TYPE = 0x4;
32 static final byte UPDATE_MSG_TYPE = 0x2;
33 static final byte NOTIFICATION_MSG_TYPE = 0x3;
34 static final int MINIMUM_COMMON_HEADER_LENGTH = 19;
35 static final int MINIMUM_OPEN_MSG_LENGTH = 29;
36 static final int MINIMUM_HEADER_MARKER_LENGTH = 16;
37 static final int HEADER_AND_MSG_LEN = 18;
38
39 protected static final Logger log = LoggerFactory
40 .getLogger(BgpPeerFrameDecoderTest.class);
41 final CountDownLatch receivedOpenMessageLatch = new CountDownLatch(1);
42 final CountDownLatch receivedKeepaliveMessageLatch = new CountDownLatch(1);
43 final CountDownLatch receivedNotificationMessageLatch = new CountDownLatch(1);
44
45 @Override
46 protected Object decode(ChannelHandlerContext ctx,
47 Channel channel,
48 ChannelBuffer cb) throws Exception {
49
50 if (cb.readableBytes() < MINIMUM_COMMON_HEADER_LENGTH) {
51 log.debug("Error: Packet length is less then minimum length");
52 return null;
53 }
54
55 byte[] marker = new byte[MINIMUM_HEADER_MARKER_LENGTH];
56 cb.readBytes(marker);
57 for (int i = 0; i < marker.length; i++) {
58 if (marker[i] != (byte) 0xff) {
59 log.debug("Error: Marker must be set all ones");
60 ctx.getChannel().close();
61 return null;
62 }
63 }
64
65 short length = cb.readShort();
66 if (length < MINIMUM_COMMON_HEADER_LENGTH) {
67 log.debug("Error: Bad message length");
68 ctx.getChannel().close();
69 return null;
70 }
71
72 if (length != (cb.readableBytes() + HEADER_AND_MSG_LEN)) {
73 log.debug("Error: Bad message length");
74 ctx.getChannel().close();
75 return null;
76 }
77
78 byte type = cb.readByte();
79 int len = length - MINIMUM_COMMON_HEADER_LENGTH;
80
81 ChannelBuffer message = cb.readBytes(len);
82
83 switch (type) {
84 case OPEN_MSG_TYPE:
85 processBgpOpen(ctx, message);
86 break;
87 case UPDATE_MSG_TYPE:
88 break;
89 case NOTIFICATION_MSG_TYPE:
90 processBgpNotification(ctx, message);
91 break;
92 case KEEPALIVE_MSG_TYPE:
93 processBgpKeepalive(ctx, message);
94 break;
95 default:
96 ctx.getChannel().close();
97 return null;
98 }
99
100 return null;
101 }
102
103 /**
104 * Processes BGP open message.
105 *
106 * @param ctx Channel handler context
107 * @param message open message
108 */
109 private void processBgpOpen(ChannelHandlerContext ctx,
110 ChannelBuffer message) {
111 int minLength =
112 MINIMUM_OPEN_MSG_LENGTH - MINIMUM_COMMON_HEADER_LENGTH;
113 if (message.readableBytes() < minLength) {
114 log.debug("Error: Bad message length");
115 ctx.getChannel().close();
116 return;
117 }
118
119 message.readByte(); // read version
120 message.readShort(); // read AS number
121 message.readShort(); // read Hold timer
122 message.readInt(); // read BGP Identifier
123 // Optional Parameters
124 int optParamLen = message.readUnsignedByte();
125 if (message.readableBytes() < optParamLen) {
126 log.debug("Error: Bad message length");
127 ctx.getChannel().close();
128 return;
129 }
130 message.readBytes(optParamLen);
131
132 // Open message received
133 receivedOpenMessageLatch.countDown();
134 }
135
136 /**
137 * Processes BGP keepalive message.
138 *
139 * @param ctx Channel handler context
140 * @param message keepalive message
141 */
142 private void processBgpKeepalive(ChannelHandlerContext ctx,
143 ChannelBuffer message) {
144
145 // Keepalive message received
146 receivedKeepaliveMessageLatch.countDown();
147 }
148
149 /**
150 * Processes BGP notification message.
151 *
152 * @param ctx Channel handler context
153 * @param message notification message
154 */
155 private void processBgpNotification(ChannelHandlerContext ctx,
156 ChannelBuffer message) {
157 byte[] data;
158 message.readByte(); //read error code
159 message.readByte(); // read error sub code
160 if (message.readableBytes() > 0) {
161 data = new byte[message.readableBytes()];
162 message.readBytes(data, 0, message.readableBytes());
163 }
164
165 // Notification message received
166 receivedNotificationMessageLatch.countDown();
167 }
168}