blob: c565ae0fb69a7ed64fe5a9887760857698730ccd [file] [log] [blame]
timlindbergef8d55d2013-09-27 12:50:13 -07001#!/usr/bin/env python
2
3import time
4import pexpect
kelvin-onlabbbe46482015-01-16 10:44:28 -08005import struct
6import fcntl
7import os
8import sys
9import signal
timlindbergef8d55d2013-09-27 12:50:13 -070010import sys
11import re
12import json
kelvin-onlabbbe46482015-01-16 10:44:28 -080013sys.path.append( "../" )
timlindbergef8d55d2013-09-27 12:50:13 -070014from drivers.common.clidriver import CLI
15
timlindbergef8d55d2013-09-27 12:50:13 -070016
kelvin-onlabbbe46482015-01-16 10:44:28 -080017class QuaggaCliDriver( CLI ):
18
19 def __init__( self ):
20 super( CLI, self ).__init__()
timlindbergef8d55d2013-09-27 12:50:13 -070021
pingping-linc6b86fa2014-12-01 16:18:10 -080022 # TODO: simplify this method
kelvin-onlabbbe46482015-01-16 10:44:28 -080023 def connect( self, **connectargs ):
timlindbergef8d55d2013-09-27 12:50:13 -070024 for key in connectargs:
kelvin-onlabbbe46482015-01-16 10:44:28 -080025 vars( self )[ key ] = connectargs[ key ]
Srikanth Vavilapalli68a1a2b2015-02-27 10:29:14 -080026 self.name = self.options[ 'name' ]
27 self.handle = super( QuaggaCliDriver, self ).connect(
28 user_name=self.user_name,
29 ip_address="127.0.0.1",
30 port=self.port,
31 pwd=self.pwd )
32 if self.handle:
33 return self.handle
34 else:
35 main.log.info( "NO HANDLE" )
36 return main.FALSE
37
pingping-linc6b86fa2014-12-01 16:18:10 -080038
Srikanth Vavilapalli68a1a2b2015-02-27 10:29:14 -080039 def connectQuagga( self ):
kelvin-onlabbbe46482015-01-16 10:44:28 -080040 self.name = self.options[ 'name' ]
41 # self.handle = super( QuaggaCliDriver,self ).connect(
kelvin-onlab08679eb2015-01-21 16:11:48 -080042 # user_name=self.user_name, ip_address=self.ip_address,port=self.port,
kelvin-onlabbbe46482015-01-16 10:44:28 -080043 # pwd=self.pwd )
kelvin-onlab2c4342a2015-01-28 15:59:53 -080044 self.handle = super( QuaggaCliDriver, self ).connect(
kelvin-onlab08679eb2015-01-21 16:11:48 -080045 user_name=self.user_name,
kelvin-onlab2c4342a2015-01-28 15:59:53 -080046 ip_address="1.1.1.1",
47 port=self.port,
48 pwd=self.pwd )
49 main.log.info( "connect parameters:" + str( self.user_name ) + ";"
50 + str( self.ip_address ) + ";" + str( self.port )
51 + ";" + str(self.pwd ) )
timlindbergef8d55d2013-09-27 12:50:13 -070052
pingping-linc6b86fa2014-12-01 16:18:10 -080053 if self.handle:
kelvin-onlabbbe46482015-01-16 10:44:28 -080054 # self.handle.expect( "",timeout=10 )
55 # self.handle.expect( "\$",timeout=10 )
56 self.handle.sendline( "telnet localhost 2605" )
57 # self.handle.expect( "Password:", timeout=5 )
58 self.handle.expect( "Password:" )
59 self.handle.sendline( "hello" )
60 # self.handle.expect( "bgpd", timeout=5 )
61 self.handle.expect( "bgpd" )
62 self.handle.sendline( "enable" )
63 # self.handle.expect( "bgpd#", timeout=5 )
64 self.handle.expect( "bgpd#" )
timlindbergef8d55d2013-09-27 12:50:13 -070065 return self.handle
kelvin-onlabbbe46482015-01-16 10:44:28 -080066 else:
67 main.log.info( "NO HANDLE" )
timlindbergef8d55d2013-09-27 12:50:13 -070068 return main.FALSE
69
kelvin-onlab08679eb2015-01-21 16:11:48 -080070 def loginQuagga( self, ip_address ):
kelvin-onlabbbe46482015-01-16 10:44:28 -080071 self.name = self.options[ 'name' ]
72 self.handle = super( QuaggaCliDriver, self ).connect(
kelvin-onlab08679eb2015-01-21 16:11:48 -080073 user_name=self.user_name, ip_address=ip_address,
kelvin-onlabbbe46482015-01-16 10:44:28 -080074 port=self.port, pwd=self.pwd )
kelvin-onlab2c4342a2015-01-28 15:59:53 -080075 main.log.info( "connect parameters:" + str( self.user_name ) + ";"
76 + str( self.ip_address ) + ";" + str( self.port )
77 + ";" + str( self.pwd ) )
pingping-lin8b306ac2014-11-17 18:13:51 -080078
79 if self.handle:
kelvin-onlabbbe46482015-01-16 10:44:28 -080080 # self.handle.expect( "" )
81 # self.handle.expect( "\$" )
82 self.handle.sendline( "telnet localhost 2605" )
83 # self.handle.expect( "Password:", timeout=5 )
84 self.handle.expect( "Password:" )
85 self.handle.sendline( "hello" )
86 # self.handle.expect( "bgpd", timeout=5 )
87 self.handle.expect( "bgpd" )
88 self.handle.sendline( "enable" )
89 # self.handle.expect( "bgpd#", timeout=5 )
90 self.handle.expect( "bgpd#" )
kelvin-onlab2c4342a2015-01-28 15:59:53 -080091 main.log.info( "I am in quagga on host " + str( ip_address ) )
pingping-lin8b306ac2014-11-17 18:13:51 -080092
93 return self.handle
94 else:
kelvin-onlabbbe46482015-01-16 10:44:28 -080095 main.log.info( "NO HANDLE" )
pingping-lin8b306ac2014-11-17 18:13:51 -080096 return main.FALSE
97
kelvin-onlabd3b64892015-01-20 13:26:24 -080098 def enterConfig( self, asn ):
kelvin-onlabbbe46482015-01-16 10:44:28 -080099 main.log.info( "I am in enter_config method!" )
timlindbergef8d55d2013-09-27 12:50:13 -0700100 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800101 self.handle.sendline( "" )
102 self.handle.expect( "bgpd#" )
timlindbergef8d55d2013-09-27 12:50:13 -0700103 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800104 main.log.warn( "Probably not currently in enable mode!" )
timlindbergef8d55d2013-09-27 12:50:13 -0700105 self.disconnect()
106 return main.FALSE
kelvin-onlabbbe46482015-01-16 10:44:28 -0800107 self.handle.sendline( "configure terminal" )
108 self.handle.expect( "config", timeout=5 )
109 routerAS = "router bgp " + str( asn )
timlindbergef8d55d2013-09-27 12:50:13 -0700110 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800111 self.handle.sendline( routerAS )
112 self.handle.expect( "config-router", timeout=5 )
timlindbergef8d55d2013-09-27 12:50:13 -0700113 return main.TRUE
114 except:
115 return main.FALSE
pingping-lin8b306ac2014-11-17 18:13:51 -0800116
kelvin-onlabd3b64892015-01-20 13:26:24 -0800117 def generatePrefixes( self, net, numRoutes ):
kelvin-onlabbbe46482015-01-16 10:44:28 -0800118 main.log.info( "I am in generate_prefixes method!" )
pingping-lin6f6332e2014-11-19 19:13:58 -0800119
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800120 # each IP prefix is composed by "net" + "." + m + "." + n + "." + x
pingping-lin8b306ac2014-11-17 18:13:51 -0800121 # the length of each IP prefix is 24
122 routes = []
kelvin-onlabd3b64892015-01-20 13:26:24 -0800123 routesGen = 0
pingping-lin8b306ac2014-11-17 18:13:51 -0800124 m = numRoutes / 256
125 n = numRoutes % 256
126
kelvin-onlabbbe46482015-01-16 10:44:28 -0800127 for i in range( 0, m ):
128 for j in range( 0, 256 ):
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800129 network = str( net ) + "." + str( i ) + "." + str( j ) \
130 + ".0/24"
kelvin-onlabbbe46482015-01-16 10:44:28 -0800131 routes.append( network )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800132 routesGen = routesGen + 1
pingping-lin8b306ac2014-11-17 18:13:51 -0800133
kelvin-onlabbbe46482015-01-16 10:44:28 -0800134 for j in range( 0, n ):
135 network = str( net ) + "." + str( m ) + "." + str( j ) + ".0/24"
136 routes.append( network )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800137 routesGen = routesGen + 1
pingping-lin8b306ac2014-11-17 18:13:51 -0800138
kelvin-onlabd3b64892015-01-20 13:26:24 -0800139 if routesGen == numRoutes:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800140 main.log.info( "Successfully generated " + str( numRoutes )
141 + " prefixes!" )
pingping-lin8b306ac2014-11-17 18:13:51 -0800142 return routes
143 return main.FALSE
pingping-lin6f6332e2014-11-19 19:13:58 -0800144
kelvin-onlabbbe46482015-01-16 10:44:28 -0800145 # This method generates a multiple to single point intent(
146 # MultiPointToSinglePointIntent ) for a given route
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800147 def generateExpectedSingleRouteIntent( self, prefix, nextHop, nextHopMac,
148 sdnipData ):
pingping-lin6f6332e2014-11-19 19:13:58 -0800149
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800150 ingresses = []
pingping-lin6f6332e2014-11-19 19:13:58 -0800151 egress = ""
kelvin-onlabd3b64892015-01-20 13:26:24 -0800152 for peer in sdnipData[ 'bgpPeers' ]:
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800153 if peer[ 'ipAddress' ] == nextHop:
154 egress = "of:" + str(
155 peer[ 'attachmentDpid' ] ).replace( ":", "" ) + ":" \
156 + str( peer[ 'attachmentPort' ] )
157 for peer in sdnipData[ 'bgpPeers' ]:
158 if not peer[ 'ipAddress' ] == nextHop:
159 ingress = "of:" + str(
160 peer[ 'attachmentDpid' ] ).replace( ":", "" ) + ":" \
161 + str( peer[ 'attachmentPort' ] )
162 if not ingress == egress and ingress not in ingresses:
163 ingresses.append( ingress )
164 # ingresses.append( "of:" + str( peer[ 'attachmentDpid' ]
165 # ).replace( ":", "" ) + ":" + str( peer[ 'attachmentPort'
166 # ] ) )
pingping-lin6f6332e2014-11-19 19:13:58 -0800167
pingping-linc6b86fa2014-12-01 16:18:10 -0800168 selector = "ETH_TYPE{ethType=800},IPV4_DST{ip=" + prefix + "}"
kelvin-onlabbbe46482015-01-16 10:44:28 -0800169 treatment = "[ETH_DST{mac=" + str( nextHopMac ) + "}]"
pingping-lin6f6332e2014-11-19 19:13:58 -0800170
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800171 intent = egress + "/" + str( sorted( ingresses ) ) + "/" + \
172 selector + "/" + treatment
pingping-lin6f6332e2014-11-19 19:13:58 -0800173 return intent
174
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800175 def generateExpectedOnePeerRouteIntents( self, prefixes, nextHop,
176 nextHopMac, sdnipJsonFilePath ):
pingping-lin6f6332e2014-11-19 19:13:58 -0800177 intents = []
kelvin-onlabd3b64892015-01-20 13:26:24 -0800178 sdnipJsonFile = open( sdnipJsonFilePath ).read()
pingping-lin6f6332e2014-11-19 19:13:58 -0800179
kelvin-onlabd3b64892015-01-20 13:26:24 -0800180 sdnipData = json.loads( sdnipJsonFile )
pingping-lin6f6332e2014-11-19 19:13:58 -0800181
182 for prefix in prefixes:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800183 intents.append(
kelvin-onlabd3b64892015-01-20 13:26:24 -0800184 self.generateExpectedSingleRouteIntent(
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800185 prefix, nextHop, nextHopMac, sdnipData ) )
kelvin-onlabbbe46482015-01-16 10:44:28 -0800186 return sorted( intents )
pingping-lin6f6332e2014-11-19 19:13:58 -0800187
188 # TODO
189 # This method generates all expected route intents for all BGP peers
kelvin-onlabd3b64892015-01-20 13:26:24 -0800190 def generateExpectedRouteIntents( self ):
pingping-lin6f6332e2014-11-19 19:13:58 -0800191 intents = []
192 return intents
193
194 # This method extracts all actual routes from ONOS CLI
kelvin-onlabd3b64892015-01-20 13:26:24 -0800195 def extractActualRoutes( self, getRoutesResult ):
196 routesJsonObj = json.loads( getRoutesResult )
pingping-lin6f6332e2014-11-19 19:13:58 -0800197
kelvin-onlabd3b64892015-01-20 13:26:24 -0800198 allRoutesActual = []
Srikanth Vavilapalli68a1a2b2015-02-27 10:29:14 -0800199 for route in routesJsonObj['routes4']:
200 if 'prefix' in route:
201 if route[ 'prefix' ] == '172.16.10.0/24':
202 continue
203 allRoutesActual.append(
204 route[ 'prefix' ] + "/" + route[ 'nextHop' ] )
pingping-lin6f6332e2014-11-19 19:13:58 -0800205
kelvin-onlabd3b64892015-01-20 13:26:24 -0800206 return sorted( allRoutesActual )
pingping-lin6f6332e2014-11-19 19:13:58 -0800207
208 # This method extracts all actual route intents from ONOS CLI
kelvin-onlabd3b64892015-01-20 13:26:24 -0800209 def extractActualRouteIntents( self, getIntentsResult ):
pingping-lin6f6332e2014-11-19 19:13:58 -0800210 intents = []
211 # TODO: delete the line below when change to Mininet demo script
kelvin-onlabd3b64892015-01-20 13:26:24 -0800212 # getIntentsResult=open( "../tests/SdnIpTest/intents.json" ).read()
213 intentsJsonObj = json.loads( getIntentsResult )
pingping-lin6f6332e2014-11-19 19:13:58 -0800214
kelvin-onlabd3b64892015-01-20 13:26:24 -0800215 for intent in intentsJsonObj:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800216 if intent[ 'appId' ] != "org.onosproject.sdnip":
pingping-lin6f6332e2014-11-19 19:13:58 -0800217 continue
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800218 if intent[ 'type' ] == "MultiPointToSinglePointIntent" \
219 and intent[ 'state' ] == 'INSTALLED':
220 egress = str( intent[ 'egress' ][ 'device' ] ) + ":" \
221 + str( intent[ 'egress' ][ 'port' ] )
pingping-lin6f6332e2014-11-19 19:13:58 -0800222 ingress = []
kelvin-onlabbbe46482015-01-16 10:44:28 -0800223 for attachmentPoint in intent[ 'ingress' ]:
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800224 ingress.append(
225 str( attachmentPoint[ 'device' ] ) + ":"
226 + str( attachmentPoint[ 'port' ] ) )
pingping-linc6b86fa2014-12-01 16:18:10 -0800227
kelvin-onlabbbe46482015-01-16 10:44:28 -0800228 selector = intent[ 'selector' ].replace(
229 "[", "" ).replace( "]", "" ).replace( " ", "" )
230 if str( selector ).startswith( "IPV4" ):
231 str1, str2 = str( selector ).split( "," )
pingping-linc6b86fa2014-12-01 16:18:10 -0800232 selector = str2 + "," + str1
233
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800234 intent = egress + "/" + str( sorted( ingress ) ) + "/" + \
kelvin-onlabd3b64892015-01-20 13:26:24 -0800235 selector + "/" + intent[ 'treatment' ]
kelvin-onlabbbe46482015-01-16 10:44:28 -0800236 intents.append( intent )
237 return sorted( intents )
pingping-lin6f6332e2014-11-19 19:13:58 -0800238
239 # This method extracts all actual BGP intents from ONOS CLI
kelvin-onlabd3b64892015-01-20 13:26:24 -0800240 def extractActualBgpIntents( self, getIntentsResult ):
pingping-lin6f6332e2014-11-19 19:13:58 -0800241 intents = []
242 # TODO: delete the line below when change to Mininet demo script
kelvin-onlabd3b64892015-01-20 13:26:24 -0800243 # getIntentsResult=open( "../tests/SdnIpTest/intents.json" ).read()
244 intentsJsonObj = json.loads( getIntentsResult )
pingping-lin6f6332e2014-11-19 19:13:58 -0800245
kelvin-onlabd3b64892015-01-20 13:26:24 -0800246 for intent in intentsJsonObj:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800247 if intent[ 'appId' ] != "org.onosproject.sdnip":
pingping-lin6f6332e2014-11-19 19:13:58 -0800248 continue
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800249 if intent[ 'type' ] == "PointToPointIntent" \
250 and "protocol=6" in str( intent[ 'selector' ] ):
251 ingress = str( intent[ 'ingress' ][ 'device' ] ) + ":" \
252 + str( intent[ 'ingress' ][ 'port' ] )
253 egress = str( intent[ 'egress' ][ 'device' ] ) + ":" + \
254 str( intent[ 'egress' ][ 'port' ] )
255 selector = str( intent[ 'selector' ] ).replace( " ", "" )\
256 .replace( "[", "" ).replace( "]", "" ).split( "," )
257 intent = ingress + "/" + egress + "/" + \
258 str( sorted( selector ) )
kelvin-onlabbbe46482015-01-16 10:44:28 -0800259 intents.append( intent )
pingping-lin6f6332e2014-11-19 19:13:58 -0800260
kelvin-onlabbbe46482015-01-16 10:44:28 -0800261 return sorted( intents )
pingping-lin6f6332e2014-11-19 19:13:58 -0800262
kelvin-onlabbbe46482015-01-16 10:44:28 -0800263 # This method generates a single point to single point intent(
264 # PointToPointIntent ) for BGP path
kelvin-onlabd3b64892015-01-20 13:26:24 -0800265 def generateExpectedBgpIntents( self, sdnipJsonFilePath ):
pingping-lin6f6332e2014-11-19 19:13:58 -0800266 from operator import eq
267
kelvin-onlabd3b64892015-01-20 13:26:24 -0800268 sdnipJsonFile = open( sdnipJsonFilePath ).read()
269 sdnipData = json.loads( sdnipJsonFile )
pingping-lin6f6332e2014-11-19 19:13:58 -0800270
271 intents = []
pingping-linc6b86fa2014-12-01 16:18:10 -0800272 bgpPeerAttachmentPoint = ""
kelvin-onlabbbe46482015-01-16 10:44:28 -0800273 bgpSpeakerAttachmentPoint = "of:" + str(
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800274 sdnipData[ 'bgpSpeakers' ][ 0 ][ 'attachmentDpid' ] )\
275 .replace( ":", "" ) + ":" \
276 + str( sdnipData[ 'bgpSpeakers' ][ 0 ][ 'attachmentPort' ] )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800277 for peer in sdnipData[ 'bgpPeers' ]:
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800278 bgpPeerAttachmentPoint = "of:" \
279 + str( peer[ 'attachmentDpid' ] ).replace( ":", "" ) \
280 + ":" + str( peer[ 'attachmentPort' ] )
pingping-lin6f6332e2014-11-19 19:13:58 -0800281 # find out the BGP speaker IP address for this BGP peer
pingping-linc6b86fa2014-12-01 16:18:10 -0800282 bgpSpeakerIpAddress = ""
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800283 for interfaceAddress in \
284 sdnipData[ 'bgpSpeakers' ][ 0 ][ 'interfaceAddresses' ]:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800285 # if eq( interfaceAddress[ 'interfaceDpid' ],sdnipData[
kelvin-onlabbbe46482015-01-16 10:44:28 -0800286 # 'bgpSpeakers' ][ 0 ][ 'attachmentDpid' ] ) and eq(
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800287 # interfaceAddress[ 'interfacePort' ], sdnipData[ 'bgpSpeakers'
288 # ][ 0 ][ 'attachmentPort' ] ):
289 if eq( interfaceAddress[ 'interfaceDpid' ],
290 peer[ 'attachmentDpid' ] ) \
291 and eq( interfaceAddress[ 'interfacePort' ],
kelvin-onlabd3b64892015-01-20 13:26:24 -0800292 peer[ 'attachmentPort' ] ):
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800293 bgpSpeakerIpAddress = interfaceAddress[ 'ipAddress' ]
pingping-lin6f6332e2014-11-19 19:13:58 -0800294 break
295 else:
296 continue
297
kelvin-onlabbbe46482015-01-16 10:44:28 -0800298 # from bgpSpeakerAttachmentPoint to bgpPeerAttachmentPoint
299 # direction
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800300 selectorStr = "IPV4_SRC{ip=" + bgpSpeakerIpAddress + "/32}," \
301 + "IPV4_DST{ip=" + peer[ 'ipAddress' ] + "/32}," \
302 + "IP_PROTO{protocol=6}, ETH_TYPE{ethType=800}, \
303 TCP_DST{tcpPort=179}"
304 selector = selectorStr.replace( " ", "" ).replace("[", "" )\
305 .replace( "]", "" ).split( "," )
kelvin-onlabbbe46482015-01-16 10:44:28 -0800306 intent = bgpSpeakerAttachmentPoint + "/" + \
307 bgpPeerAttachmentPoint + "/" + str( sorted( selector ) )
308 intents.append( intent )
pingping-lin6f6332e2014-11-19 19:13:58 -0800309
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800310 selectorStr = "IPV4_SRC{ip=" + bgpSpeakerIpAddress + "/32}," \
311 + "IPV4_DST{ip=" + peer[ 'ipAddress' ] + "/32}," \
312 + "IP_PROTO{protocol=6}, ETH_TYPE{ethType=800}, \
313 TCP_SRC{tcpPort=179}"
314 selector = selectorStr.replace( " ", "" ).replace("[", "" )\
315 .replace( "]", "" ).split( "," )
316 intent = bgpSpeakerAttachmentPoint + "/" \
317 + bgpPeerAttachmentPoint + "/" + str( sorted( selector ) )
kelvin-onlabbbe46482015-01-16 10:44:28 -0800318 intents.append( intent )
pingping-lin6f6332e2014-11-19 19:13:58 -0800319
kelvin-onlabbbe46482015-01-16 10:44:28 -0800320 # from bgpPeerAttachmentPoint to bgpSpeakerAttachmentPoint
321 # direction
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800322 selectorStr = "IPV4_SRC{ip=" + peer[ 'ipAddress' ] + "/32}," \
323 + "IPV4_DST{ip=" + bgpSpeakerIpAddress + "/32}," \
324 + "IP_PROTO{protocol=6}, ETH_TYPE{ethType=800}, \
325 TCP_DST{tcpPort=179}"
326 selector = selectorStr.replace( " ", "" ).replace("[", "" )\
327 .replace( "]", "" ).split( "," )
328 intent = bgpPeerAttachmentPoint + "/" \
329 + bgpSpeakerAttachmentPoint + "/" + str( sorted( selector ) )
kelvin-onlabbbe46482015-01-16 10:44:28 -0800330 intents.append( intent )
pingping-lin6f6332e2014-11-19 19:13:58 -0800331
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800332 selectorStr = "IPV4_SRC{ip=" + peer[ 'ipAddress' ] + "/32}," \
333 + "IPV4_DST{ip=" + bgpSpeakerIpAddress + "/32}," \
334 + "IP_PROTO{protocol=6}, ETH_TYPE{ethType=800}, \
335 TCP_SRC{tcpPort=179}"
336 selector = selectorStr.replace( " ", "" ).replace( "[", "" )\
337 .replace( "]", "" ).split( "," )
338 intent = bgpPeerAttachmentPoint + "/" \
339 + bgpSpeakerAttachmentPoint + "/" + str( sorted( selector ) )
kelvin-onlabbbe46482015-01-16 10:44:28 -0800340 intents.append( intent )
pingping-lin6f6332e2014-11-19 19:13:58 -0800341
kelvin-onlabbbe46482015-01-16 10:44:28 -0800342 return sorted( intents )
pingping-linc6b86fa2014-12-01 16:18:10 -0800343
kelvin-onlabd3b64892015-01-20 13:26:24 -0800344 def addRoutes( self, routes, routeRate ):
kelvin-onlabbbe46482015-01-16 10:44:28 -0800345 main.log.info( "I am in add_routes method!" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800346
kelvin-onlabd3b64892015-01-20 13:26:24 -0800347 routesAdded = 0
pingping-lin8b306ac2014-11-17 18:13:51 -0800348 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800349 self.handle.sendline( "" )
350 # self.handle.expect( "config-router" )
351 self.handle.expect( "config-router", timeout=5 )
pingping-lin8b306ac2014-11-17 18:13:51 -0800352 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800353 main.log.warn( "Probably not in config-router mode!" )
pingping-lin8b306ac2014-11-17 18:13:51 -0800354 self.disconnect()
kelvin-onlabbbe46482015-01-16 10:44:28 -0800355 main.log.info( "Start to add routes" )
pingping-lin8b306ac2014-11-17 18:13:51 -0800356
sanghoshin70502002015-03-11 10:21:14 -0700357 chunk_size = 20
358
359 if len(routes) > chunk_size:
360 num_iter = (int) (len(routes) / chunk_size)
361 else:
362 num_iter = 1;
363
364 total = 0
365 for n in range( 0, num_iter + 1):
366 routeCmd = ""
367 if (len( routes ) - (n * chunk_size)) >= chunk_size:
368 m = (n + 1) * chunk_size
369 else:
370 m = len( routes )
371 for i in range( n * chunk_size, m ):
372 routeCmd = routeCmd + "network " + routes[ i ] + "\n"
373 total = total + 1
374
375 main.log.info(routeCmd)
pingping-lin8b306ac2014-11-17 18:13:51 -0800376 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800377 self.handle.sendline( routeCmd )
378 self.handle.expect( "bgpd", timeout=5 )
pingping-lin8b306ac2014-11-17 18:13:51 -0800379 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800380 main.log.warn( "Failed to add route" )
pingping-lin8b306ac2014-11-17 18:13:51 -0800381 self.disconnect()
sanghoshin70502002015-03-11 10:21:14 -0700382
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800383 # waitTimer = 1.00 / routeRate
sanghoshin70502002015-03-11 10:21:14 -0700384 main.log.info("Total routes so far " + ((str) (total)) + " wait for 0 sec")
385 #time.sleep( 1 )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800386 if routesAdded == len( routes ):
kelvin-onlabbbe46482015-01-16 10:44:28 -0800387 main.log.info( "Finished adding routes" )
pingping-lin8b306ac2014-11-17 18:13:51 -0800388 return main.TRUE
389 return main.FALSE
pingping-linc6b86fa2014-12-01 16:18:10 -0800390
kelvin-onlabd3b64892015-01-20 13:26:24 -0800391 def deleteRoutes( self, routes, routeRate ):
kelvin-onlabbbe46482015-01-16 10:44:28 -0800392 main.log.info( "I am in delete_routes method!" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800393
kelvin-onlabd3b64892015-01-20 13:26:24 -0800394 routesAdded = 0
pingping-linc6b86fa2014-12-01 16:18:10 -0800395 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800396 self.handle.sendline( "" )
397 # self.handle.expect( "config-router" )
398 self.handle.expect( "config-router", timeout=5 )
pingping-linc6b86fa2014-12-01 16:18:10 -0800399 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800400 main.log.warn( "Probably not in config-router mode!" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800401 self.disconnect()
kelvin-onlabbbe46482015-01-16 10:44:28 -0800402 main.log.info( "Start to delete routes" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800403
kelvin-onlabbbe46482015-01-16 10:44:28 -0800404 for i in range( 0, len( routes ) ):
405 routeCmd = "no network " + routes[ i ]
pingping-linc6b86fa2014-12-01 16:18:10 -0800406 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800407 self.handle.sendline( routeCmd )
408 self.handle.expect( "bgpd", timeout=5 )
pingping-linc6b86fa2014-12-01 16:18:10 -0800409 except:
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800410 main.log.warn( "Failed to delete route" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800411 self.disconnect()
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800412 # waitTimer = 1.00 / routeRate
413 # time.sleep( waitTimer )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800414 if routesAdded == len( routes ):
kelvin-onlabbbe46482015-01-16 10:44:28 -0800415 main.log.info( "Finished deleting routes" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800416 return main.TRUE
417 return main.FALSE
418
kelvin-onlab08679eb2015-01-21 16:11:48 -0800419 def pingTest( self, ip_address, pingTestFile, pingTestResultFile ):
420 main.log.info( "Start the ping test on host:" + str( ip_address ) )
pingping-linc6b86fa2014-12-01 16:18:10 -0800421
kelvin-onlabbbe46482015-01-16 10:44:28 -0800422 self.name = self.options[ 'name' ]
423 self.handle = super( QuaggaCliDriver, self ).connect(
kelvin-onlab08679eb2015-01-21 16:11:48 -0800424 user_name=self.user_name, ip_address=ip_address,
kelvin-onlabbbe46482015-01-16 10:44:28 -0800425 port=self.port, pwd=self.pwd )
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800426 main.log.info( "connect parameters:" + str( self.user_name ) + ";"
427 + str( self.ip_address ) + ";" + str( self.port )
428 + ";" + str( self.pwd ) )
pingping-linc6b86fa2014-12-01 16:18:10 -0800429
430 if self.handle:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800431 # self.handle.expect( "" )
432 # self.handle.expect( "\$" )
kelvin-onlab08679eb2015-01-21 16:11:48 -0800433 main.log.info( "I in host " + str( ip_address ) )
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800434 main.log.info( pingTestFile + " > " + pingTestResultFile + " &" )
kelvin-onlabbbe46482015-01-16 10:44:28 -0800435 self.handle.sendline(
kelvin-onlabd3b64892015-01-20 13:26:24 -0800436 pingTestFile +
kelvin-onlabbbe46482015-01-16 10:44:28 -0800437 " > " +
kelvin-onlabd3b64892015-01-20 13:26:24 -0800438 pingTestResultFile +
kelvin-onlabbbe46482015-01-16 10:44:28 -0800439 " &" )
440 self.handle.expect( "\$", timeout=60 )
pingping-linc6b86fa2014-12-01 16:18:10 -0800441 handle = self.handle.before
442
443 return handle
444 else:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800445 main.log.info( "NO HANDLE" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800446 return main.FALSE
447
sanghoshin29e6a472015-02-27 12:55:06 -0800448
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800449 # Please use the generateRoutes plus addRoutes instead of this one!
kelvin-onlabd3b64892015-01-20 13:26:24 -0800450 def addRoute( self, net, numRoutes, routeRate ):
timlindbergef8d55d2013-09-27 12:50:13 -0700451 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800452 self.handle.sendline( "" )
453 self.handle.expect( "config-router" )
timlindbergef8d55d2013-09-27 12:50:13 -0700454 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800455 main.log.warn( "Probably not in config-router mode!" )
timlindbergef8d55d2013-09-27 12:50:13 -0700456 self.disconnect()
kelvin-onlabbbe46482015-01-16 10:44:28 -0800457 main.log.info( "Adding Routes" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800458 j = 0
459 k = 0
timlindbergef8d55d2013-09-27 12:50:13 -0700460 while numRoutes > 255:
461 numRoutes = numRoutes - 255
462 j = j + 1
463 k = numRoutes % 254
kelvin-onlabd3b64892015-01-20 13:26:24 -0800464 routesAdded = 0
timlindbergef8d55d2013-09-27 12:50:13 -0700465 if numRoutes > 255:
466 numRoutes = 255
kelvin-onlabbbe46482015-01-16 10:44:28 -0800467 for m in range( 1, j + 1 ):
468 for n in range( 1, numRoutes + 1 ):
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800469 network = str( net ) + "." + str( m ) + "." + str( n ) \
470 + ".0/24"
timlindbergef8d55d2013-09-27 12:50:13 -0700471 routeCmd = "network " + network
472 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800473 self.handle.sendline( routeCmd )
474 self.handle.expect( "bgpd" )
timlindbergef8d55d2013-09-27 12:50:13 -0700475 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800476 main.log.warn( "failed to add route" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800477 self.disconnect()
478 waitTimer = 1.00 / routeRate
kelvin-onlabbbe46482015-01-16 10:44:28 -0800479 time.sleep( waitTimer )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800480 routesAdded = routesAdded + 1
kelvin-onlabbbe46482015-01-16 10:44:28 -0800481 for d in range( j + 1, j + 2 ):
482 for e in range( 1, k + 1 ):
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800483 network = str( net ) + "." + str( d ) + "." + str( e ) \
484 + ".0/24"
timlindbergef8d55d2013-09-27 12:50:13 -0700485 routeCmd = "network " + network
486 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800487 self.handle.sendline( routeCmd )
488 self.handle.expect( "bgpd" )
timlindbergef8d55d2013-09-27 12:50:13 -0700489 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800490 main.log.warn( "failed to add route" )
timlindbergef8d55d2013-09-27 12:50:13 -0700491 self.disconnect
pingping-linc6b86fa2014-12-01 16:18:10 -0800492 waitTimer = 1.00 / routeRate
kelvin-onlabbbe46482015-01-16 10:44:28 -0800493 time.sleep( waitTimer )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800494 routesAdded = routesAdded + 1
495 if routesAdded == numRoutes:
timlindbergef8d55d2013-09-27 12:50:13 -0700496 return main.TRUE
497 return main.FALSE
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800498
499 # Please use deleteRoutes method instead of this one!
kelvin-onlabd3b64892015-01-20 13:26:24 -0800500 def delRoute( self, net, numRoutes, routeRate ):
timlindbergef8d55d2013-09-27 12:50:13 -0700501 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800502 self.handle.sendline( "" )
503 self.handle.expect( "config-router" )
timlindbergef8d55d2013-09-27 12:50:13 -0700504 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800505 main.log.warn( "Probably not in config-router mode!" )
timlindbergef8d55d2013-09-27 12:50:13 -0700506 self.disconnect()
kelvin-onlabbbe46482015-01-16 10:44:28 -0800507 main.log.info( "Deleting Routes" )
pingping-linc6b86fa2014-12-01 16:18:10 -0800508 j = 0
509 k = 0
timlindbergef8d55d2013-09-27 12:50:13 -0700510 while numRoutes > 255:
511 numRoutes = numRoutes - 255
512 j = j + 1
513 k = numRoutes % 254
kelvin-onlabd3b64892015-01-20 13:26:24 -0800514 routesDeleted = 0
timlindbergef8d55d2013-09-27 12:50:13 -0700515 if numRoutes > 255:
516 numRoutes = 255
kelvin-onlabbbe46482015-01-16 10:44:28 -0800517 for m in range( 1, j + 1 ):
518 for n in range( 1, numRoutes + 1 ):
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800519 network = str( net ) + "." + str( m ) + "." + str( n ) \
520 + ".0/24"
timlindbergef8d55d2013-09-27 12:50:13 -0700521 routeCmd = "no network " + network
522 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800523 self.handle.sendline( routeCmd )
524 self.handle.expect( "bgpd" )
timlindbergef8d55d2013-09-27 12:50:13 -0700525 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800526 main.log.warn( "Failed to delete route" )
timlindbergef8d55d2013-09-27 12:50:13 -0700527 self.disconnect()
pingping-linc6b86fa2014-12-01 16:18:10 -0800528 waitTimer = 1.00 / routeRate
kelvin-onlabbbe46482015-01-16 10:44:28 -0800529 time.sleep( waitTimer )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800530 routesDeleted = routesDeleted + 1
kelvin-onlabbbe46482015-01-16 10:44:28 -0800531 for d in range( j + 1, j + 2 ):
532 for e in range( 1, k + 1 ):
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800533 network = str( net ) + "." + str( d ) + "." + str( e ) \
534 + ".0/24"
timlindbergef8d55d2013-09-27 12:50:13 -0700535 routeCmd = "no network " + network
536 try:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800537 self.handle.sendline( routeCmd )
538 self.handle.expect( "bgpd" )
timlindbergef8d55d2013-09-27 12:50:13 -0700539 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800540 main.log.warn( "Failed to delete route" )
timlindbergef8d55d2013-09-27 12:50:13 -0700541 self.disconnect()
pingping-linc6b86fa2014-12-01 16:18:10 -0800542 waitTimer = 1.00 / routeRate
kelvin-onlabbbe46482015-01-16 10:44:28 -0800543 time.sleep( waitTimer )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800544 routesDeleted = routesDeleted + 1
545 if routesDeleted == numRoutes:
timlindbergef8d55d2013-09-27 12:50:13 -0700546 return main.TRUE
547 return main.FALSE
pingping-linc6b86fa2014-12-01 16:18:10 -0800548
kelvin-onlabd3b64892015-01-20 13:26:24 -0800549 def checkRoutes( self, brand, ip, user, pw ):
kelvin-onlabbbe46482015-01-16 10:44:28 -0800550 def pronto( ip, user, passwd ):
timlindbergef8d55d2013-09-27 12:50:13 -0700551 print "Connecting to Pronto switch"
kelvin-onlabbbe46482015-01-16 10:44:28 -0800552 child = pexpect.spawn( "telnet " + ip )
553 i = child.expect( [ "login:", "CLI#", pexpect.TIMEOUT ] )
timlindbergef8d55d2013-09-27 12:50:13 -0700554 if i == 0:
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800555 print "user_name and password required. Passing login info."
kelvin-onlabbbe46482015-01-16 10:44:28 -0800556 child.sendline( user )
557 child.expect( "Password:" )
558 child.sendline( passwd )
559 child.expect( "CLI#" )
timlindbergef8d55d2013-09-27 12:50:13 -0700560 print "Logged in, getting flowtable."
kelvin-onlabbbe46482015-01-16 10:44:28 -0800561 child.sendline( "flowtable brief" )
562 for t in range( 9 ):
timlindbergef8d55d2013-09-27 12:50:13 -0700563 t2 = 9 - t
kelvin-onlabbbe46482015-01-16 10:44:28 -0800564 print "\r" + str( t2 )
565 sys.stdout.write( "\033[F" )
566 time.sleep( 1 )
timlindbergef8d55d2013-09-27 12:50:13 -0700567 print "Scanning flowtable"
kelvin-onlabbbe46482015-01-16 10:44:28 -0800568 child.expect( "Flow table show" )
timlindbergef8d55d2013-09-27 12:50:13 -0700569 count = 0
kelvin-onlabbbe46482015-01-16 10:44:28 -0800570 while True:
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800571 i = child.expect( [ '17\d\.\d{1,3}\.\d{1,3}\.\d{1,3}',
572 'CLI#', pexpect.TIMEOUT ] )
timlindbergef8d55d2013-09-27 12:50:13 -0700573 if i == 0:
574 count = count + 1
575 elif i == 1:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800576 print "Pronto flows: " + str( count ) + "\nDone\n"
timlindbergef8d55d2013-09-27 12:50:13 -0700577 break
578 else:
579 break
kelvin-onlabbbe46482015-01-16 10:44:28 -0800580
581 def cisco( ip, user, passwd ):
timlindbergef8d55d2013-09-27 12:50:13 -0700582 print "Establishing Cisco switch connection"
kelvin-onlabbbe46482015-01-16 10:44:28 -0800583 child = pexpect.spawn( "ssh " + user + "@" + ip )
584 i = child.expect( [ "Password:", "CLI#", pexpect.TIMEOUT ] )
timlindbergef8d55d2013-09-27 12:50:13 -0700585 if i == 0:
586 print "Password required. Passing now."
kelvin-onlabbbe46482015-01-16 10:44:28 -0800587 child.sendline( passwd )
588 child.expect( "#" )
timlindbergef8d55d2013-09-27 12:50:13 -0700589 print "Logged in. Retrieving flow table then counting flows."
kelvin-onlabbbe46482015-01-16 10:44:28 -0800590 child.sendline( "show openflow switch all flows all" )
591 child.expect( "Logical Openflow Switch" )
timlindbergef8d55d2013-09-27 12:50:13 -0700592 print "Flow table retrieved. Counting flows"
593 count = 0
kelvin-onlabbbe46482015-01-16 10:44:28 -0800594 while True:
595 i = child.expect( [ "nw_src=17", "#", pexpect.TIMEOUT ] )
timlindbergef8d55d2013-09-27 12:50:13 -0700596 if i == 0:
597 count = count + 1
598 elif i == 1:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800599 print "Cisco flows: " + str( count ) + "\nDone\n"
timlindbergef8d55d2013-09-27 12:50:13 -0700600 break
601 else:
602 break
603 if brand == "pronto" or brand == "PRONTO":
kelvin-onlabbbe46482015-01-16 10:44:28 -0800604 pronto( ip, user, passwd )
pingping-linc6b86fa2014-12-01 16:18:10 -0800605 # elif brand == "cisco" or brand == "CISCO":
kelvin-onlabbbe46482015-01-16 10:44:28 -0800606 # cisco( ip,user,passwd )
607
Srikanth Vavilapalli68a1a2b2015-02-27 10:29:14 -0800608 def disable_bgp_peer( self, peer, peer_as ):
609 main.log.info( "I am in disconnect_peer_session method!" )
610
611 try:
612 self.handle.sendline( "" )
613 # self.handle.expect( "config-router" )
614 self.handle.expect( "config-router", timeout=5 )
615 except:
616 main.log.warn( "Probably not in config-router mode!" )
617 self.disconnect()
618 main.log.info( "Start to disable peer" )
619
620 cmd = "no neighbor " + peer + " remote-as " + peer_as
621 try:
622 self.handle.sendline( cmd )
623 self.handle.expect( "bgpd", timeout=5 )
624 except:
625 main.log.warn( "Failed to disable peer" )
626 self.disconnect()
627
Srikanth Vavilapalli43f3a1d2015-03-04 11:09:44 -0800628 def enable_bgp_peer( self, peer, peer_as ):
629 main.log.info( "I am in enable_bgp_peer method!" )
630
631 try:
632 self.handle.sendline( "" )
633 # self.handle.expect( "config-router" )
634 self.handle.expect( "config-router", timeout=5 )
635 except:
636 main.log.warn( "Probably not in config-router mode!" )
637 self.disconnect()
638 main.log.info( "Start to disable peer" )
639
640 cmd = "neighbor " + peer + " remote-as " + peer_as
641 try:
642 self.handle.sendline( cmd )
643 self.handle.expect( "bgpd", timeout=5 )
644 except:
645 main.log.warn( "Failed to enable peer" )
646 self.disconnect()
647
kelvin-onlabbbe46482015-01-16 10:44:28 -0800648 def disconnect( self ):
649 """
650 Called when Test is complete to disconnect the Quagga handle.
651 """
timlindbergef8d55d2013-09-27 12:50:13 -0700652 response = ''
653 try:
654 self.handle.close()
655 except:
kelvin-onlabbbe46482015-01-16 10:44:28 -0800656 main.log.error( "Connection failed to the host" )
timlindbergef8d55d2013-09-27 12:50:13 -0700657 response = main.FALSE
658 return response
kelvin-onlab2c4342a2015-01-28 15:59:53 -0800659