blob: be18a95c53d39e76810447b2b7ce7071726be1a2 [file] [log] [blame]
Jian Li4df75b12018-06-07 22:11:04 +09001/*
2 * Copyright 2018-present Open Networking Foundation
3 *
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.openstacktelemetry.util;
17
18import com.google.common.base.Strings;
Jian Lida8867f2019-01-31 01:17:36 +090019import com.google.common.collect.Sets;
boyoung2a8549d22018-11-23 20:42:37 +090020import org.onlab.packet.IPv4;
Jian Li6c92b3c2018-08-03 11:26:55 +090021import org.onosproject.cfg.ConfigProperty;
Jian Lida8867f2019-01-31 01:17:36 +090022import org.onosproject.openstacktelemetry.api.DefaultLinkInfo;
23import org.onosproject.openstacktelemetry.api.DefaultLinkStatsInfo;
24import org.onosproject.openstacktelemetry.api.FlowInfo;
25import org.onosproject.openstacktelemetry.api.LinkInfo;
26import org.onosproject.openstacktelemetry.api.LinkStatsInfo;
Jian Li4df75b12018-06-07 22:11:04 +090027
Jian Li667c6eb2019-01-07 23:01:12 +090028import java.io.IOException;
29import java.net.InetSocketAddress;
30import java.net.Socket;
31import java.net.SocketAddress;
Jian Li4df75b12018-06-07 22:11:04 +090032import java.util.Dictionary;
Jian Li6c92b3c2018-08-03 11:26:55 +090033import java.util.Optional;
34import java.util.Set;
Jian Li4df75b12018-06-07 22:11:04 +090035
Jian Lida8867f2019-01-31 01:17:36 +090036import static org.onlab.packet.IPv4.PROTOCOL_ICMP;
37import static org.onlab.packet.IPv4.PROTOCOL_TCP;
38import static org.onlab.packet.IPv4.PROTOCOL_UDP;
Jian Li4df75b12018-06-07 22:11:04 +090039import static org.onlab.util.Tools.get;
40
41/**
42 * An utility that used in openstack telemetry app.
43 */
44public final class OpenstackTelemetryUtil {
45
boyoung2a8549d22018-11-23 20:42:37 +090046 private static final String PROTOCOL_NAME_TCP = "tcp";
47 private static final String PROTOCOL_NAME_UDP = "udp";
Jian Lida8867f2019-01-31 01:17:36 +090048 private static final String PROTOCOL_NAME_ICMP = "icmp";
boyoung2a8549d22018-11-23 20:42:37 +090049 private static final String PROTOCOL_NAME_ANY = "any";
50 private static final int ARBITRARY_PROTOCOL = 0x0;
Jian Li667c6eb2019-01-07 23:01:12 +090051 private static final int TIMEOUT = 2000;
boyoung2a8549d22018-11-23 20:42:37 +090052
Jian Lida8867f2019-01-31 01:17:36 +090053 private static final String ALL_IP_ADDRESSES = "0.0.0.0";
54 private static final String LINK_ID_DELIMITER = "_";
55
Jian Li4df75b12018-06-07 22:11:04 +090056 /**
57 * Prevents object instantiation from external.
58 */
59 private OpenstackTelemetryUtil() {
60 }
61
62 /**
63 * Gets Boolean property from the propertyName
64 * Return null if propertyName is not found.
65 *
66 * @param properties properties to be looked up
67 * @param propertyName the name of the property to look up
68 * @return value when the propertyName is defined or return null
69 */
70 public static Boolean getBooleanProperty(Dictionary<?, ?> properties,
71 String propertyName) {
72 Boolean value;
73 try {
74 String s = get(properties, propertyName);
75 value = Strings.isNullOrEmpty(s) ? null : Boolean.valueOf(s);
76 } catch (ClassCastException e) {
77 value = null;
78 }
79 return value;
80 }
Jian Li6c92b3c2018-08-03 11:26:55 +090081
82 /**
83 * Obtains the property value with specified property key name.
84 *
85 * @param properties a collection of properties
86 * @param name key name
87 * @return mapping value
88 */
89 public static boolean getPropertyValueAsBoolean(Set<ConfigProperty> properties, String name) {
90 Optional<ConfigProperty> property =
91 properties.stream().filter(p -> p.name().equals(name)).findFirst();
92
93 return property.map(ConfigProperty::asBoolean).orElse(false);
94 }
Jian Li3ed7f302018-08-27 17:16:27 +090095
96 /**
boyoung2a8549d22018-11-23 20:42:37 +090097 * Obtains transport protocol type from the given string.
98 *
99 * @param str transport protocol name
100 * @return transport protocol type
101 */
102 public static byte getProtocolTypeFromString(String str) {
103 switch (str.toLowerCase()) {
104 case PROTOCOL_NAME_TCP:
105 return IPv4.PROTOCOL_TCP;
106 case PROTOCOL_NAME_UDP:
107 return IPv4.PROTOCOL_UDP;
Jian Lib2a58882019-02-20 17:39:41 +0900108 case PROTOCOL_NAME_ANY:
boyoung2a8549d22018-11-23 20:42:37 +0900109 default:
110 return ARBITRARY_PROTOCOL;
111 }
112 }
113
114 /**
115 * Obtains protocol name from the protocol type.
116 *
117 * @param type transport protocol type
118 * @return transport protocol name
119 */
120 public static String getProtocolNameFromType(byte type) {
121 switch (type) {
122 case IPv4.PROTOCOL_TCP:
123 return PROTOCOL_NAME_TCP;
124 case IPv4.PROTOCOL_UDP:
125 return PROTOCOL_NAME_UDP;
126 case ARBITRARY_PROTOCOL:
boyoung2a8549d22018-11-23 20:42:37 +0900127 default:
128 return PROTOCOL_NAME_ANY;
129 }
130 }
Jian Li667c6eb2019-01-07 23:01:12 +0900131
132 /**
133 * Tests the connectivity with the given address and port.
134 *
135 * @param address address
136 * @param port port number
137 * @return true if the given address and port is accessible, false otherwise
138 */
139 public static boolean testConnectivity(String address, int port) {
140
141 boolean isConnected = false;
142 SocketAddress socketAddress = new InetSocketAddress(address, port);
143 Socket socket = new Socket();
144 try {
145 socket.connect(socketAddress, TIMEOUT);
146 socket.close();
147 isConnected = true;
148 } catch (IOException ignored) {
149 }
150
151 return isConnected;
152 }
Jian Lida8867f2019-01-31 01:17:36 +0900153
154 /**
155 * Converts flow info to link info.
156 *
157 * @param flowInfos a set of flow infos
158 * @return converted link infos
159 */
160 public static Set<LinkInfo> flowsToLinks(Set<FlowInfo> flowInfos) {
161
162 Set<LinkInfo> linkInfos = Sets.newConcurrentHashSet();
163
164 for (FlowInfo flowInfo : flowInfos) {
165 if (!ALL_IP_ADDRESSES.equals(flowInfo.srcIp().address().toString()) &&
166 ALL_IP_ADDRESSES.equals(flowInfo.dstIp().address().toString())) {
167 FlowInfo dstFlowInfo = flowInfos.stream()
168 .filter(f -> f.dstIp().address().toString()
169 .equals(flowInfo.srcIp().address().toString()))
170 .findFirst().orElse(null);
171
172 if (dstFlowInfo == null) {
173 continue;
174 }
175
176 String linkId = flowInfo.deviceId().toString() +
177 LINK_ID_DELIMITER + flowInfo.inputInterfaceId();
178 String srcIp = flowInfo.srcIp().address().toString();
179 String dstIp = flowInfo.dstIp().address().toString();
180 int srcPort = flowInfo.srcPort() == null ? 0 : flowInfo.srcPort().toInt();
181 int dstPort = flowInfo.dstPort() == null ? 0 : flowInfo.dstPort().toInt();
182 String protocol = protocolByteToString(flowInfo.protocol());
183
184 long txPacket = flowInfo.statsInfo().currAccPkts();
185 long txByte = flowInfo.statsInfo().currAccBytes();
186 long txDrop = flowInfo.statsInfo().dropPkts();
187
188 long rxPacket = dstFlowInfo.statsInfo().currAccPkts();
189 long rxByte = dstFlowInfo.statsInfo().currAccBytes();
190 long rxDrop = dstFlowInfo.statsInfo().dropPkts();
191
192 LinkStatsInfo statsInfo = DefaultLinkStatsInfo.builder()
193 .withTxPacket(txPacket)
194 .withRxPacket(rxPacket)
195 .withTxByte(txByte)
196 .withRxByte(rxByte)
197 .withTxDrop(txDrop)
198 .withRxDrop(rxDrop)
199 .withTimestamp(System.currentTimeMillis())
200 .build();
201
202 LinkInfo linkInfo = DefaultLinkInfo.builder()
203 .withLinkId(linkId)
204 .withSrcIp(srcIp)
205 .withDstIp(dstIp)
206 .withSrcPort(srcPort)
207 .withDstPort(dstPort)
208 .withProtocol(protocol)
209 .withLinkStats(statsInfo)
210 .build();
211
212 linkInfos.add(linkInfo);
213 }
214 }
215
216 return linkInfos;
217 }
218
219 /**
220 * Converts byte formatted protocol to string type.
221 *
222 * @param protocol byte formatted protocol
223 * @return string formatted protocol
224 */
225 public static String protocolByteToString(byte protocol) {
226 switch (protocol) {
227 case PROTOCOL_TCP:
228 return PROTOCOL_NAME_TCP;
229 case PROTOCOL_UDP:
230 return PROTOCOL_NAME_UDP;
231 case PROTOCOL_ICMP:
232 return PROTOCOL_NAME_ICMP;
233 default:
234 return "";
235 }
236 }
Jian Li4df75b12018-06-07 22:11:04 +0900237}