blob: 95334fa7afbfbcf9d93941d8052d8412b1c6c817 [file] [log] [blame]
Jon Hall05b2b432014-10-08 19:53:25 -04001#!/usr/bin/env python
andrewonlabe8e56fd2014-10-09 17:12:44 -04002
kelvin8ec71442015-01-15 16:57:00 -08003"""
4This driver interacts with ONOS bench, the OSGi platform
5that configures the ONOS nodes. ( aka ONOS-next )
andrewonlabe8e56fd2014-10-09 17:12:44 -04006
kelvin8ec71442015-01-15 16:57:00 -08007Please follow the coding style demonstrated by existing
andrewonlabe8e56fd2014-10-09 17:12:44 -04008functions and document properly.
9
10If you are a contributor to the driver, please
11list your email here for future contact:
12
13jhall@onlab.us
14andrew@onlab.us
15
16OCT 9 2014
17
kelvin8ec71442015-01-15 16:57:00 -080018"""
andrewonlab7735d852014-10-09 13:02:47 -040019import sys
Jon Hall05b2b432014-10-08 19:53:25 -040020import time
21import pexpect
kelvin-onlaba4074292015-07-09 15:19:49 -070022import os
andrewonlab7735d852014-10-09 13:02:47 -040023import os.path
pingping-lin6d23d9e2015-02-02 16:54:24 -080024from requests.models import Response
kelvin8ec71442015-01-15 16:57:00 -080025sys.path.append( "../" )
Jon Hall05b2b432014-10-08 19:53:25 -040026from drivers.common.clidriver import CLI
27
Jon Hall05b2b432014-10-08 19:53:25 -040028
kelvin8ec71442015-01-15 16:57:00 -080029class OnosDriver( CLI ):
Jon Hall05b2b432014-10-08 19:53:25 -040030
kelvin8ec71442015-01-15 16:57:00 -080031 def __init__( self ):
32 """
33 Initialize client
34 """
Jon Hallefbd9792015-03-05 16:11:36 -080035 self.name = None
36 self.home = None
37 self.handle = None
kelvin8ec71442015-01-15 16:57:00 -080038 super( CLI, self ).__init__()
39
40 def connect( self, **connectargs ):
41 """
Jon Hall05b2b432014-10-08 19:53:25 -040042 Creates ssh handle for ONOS "bench".
kelvin-onlaba4074292015-07-09 15:19:49 -070043 NOTE:
44 The ip_address would come from the topo file using the host tag, the
45 value can be an environment variable as well as a "localhost" to get
46 the ip address needed to ssh to the "bench"
kelvin8ec71442015-01-15 16:57:00 -080047 """
Jon Hall05b2b432014-10-08 19:53:25 -040048 try:
49 for key in connectargs:
kelvin8ec71442015-01-15 16:57:00 -080050 vars( self )[ key ] = connectargs[ key ]
andrew@onlab.us3b087132015-03-11 15:00:08 -070051 self.home = "~/onos"
Jon Hall05b2b432014-10-08 19:53:25 -040052 for key in self.options:
53 if key == "home":
kelvin8ec71442015-01-15 16:57:00 -080054 self.home = self.options[ 'home' ]
Jon Hall05b2b432014-10-08 19:53:25 -040055 break
Jon Hall274b6642015-02-17 11:57:17 -080056 if self.home is None or self.home == "":
Jon Halle94919c2015-03-23 11:42:57 -070057 self.home = "~/onos"
Jon Hall21270ac2015-02-16 17:59:55 -080058
kelvin8ec71442015-01-15 16:57:00 -080059 self.name = self.options[ 'name' ]
kelvin-onlaba4074292015-07-09 15:19:49 -070060
kelvin-onlabc2b79102015-07-14 11:41:20 -070061 # The 'nodes' tag is optional and it is not required in .topo file
kelvin-onlaba4074292015-07-09 15:19:49 -070062 for key in self.options:
63 if key == "nodes":
kelvin-onlabc2b79102015-07-14 11:41:20 -070064 # Maximum number of ONOS nodes to run, if there is any
kelvin-onlaba4074292015-07-09 15:19:49 -070065 self.maxNodes = int( self.options[ 'nodes' ] )
66 break
67 self.maxNodes = None
68
kelvin-onlabc2b79102015-07-14 11:41:20 -070069 if self.maxNodes == None or self.maxNodes == "":
70 self.maxNodes = 100
kelvin-onlaba4074292015-07-09 15:19:49 -070071
kelvin-onlabc2b79102015-07-14 11:41:20 -070072
73 # Grabs all OC environment variables based on max number of nodes
kelvin-onlaba4074292015-07-09 15:19:49 -070074 self.onosIps = {} # Dictionary of all possible ONOS ip
75
76 try:
77 if self.maxNodes:
kelvin-onlaba4074292015-07-09 15:19:49 -070078 for i in range( self.maxNodes ):
79 envString = "OC" + str( i + 1 )
kelvin-onlabc2b79102015-07-14 11:41:20 -070080 # If there is no more OC# then break the loop
81 if os.getenv( envString ):
82 self.onosIps[ envString ] = os.getenv( envString )
83 else:
84 self.maxNodes = len( self.onosIps )
85 main.log.info( self.name +
86 ": Created cluster data with " +
87 str( self.maxNodes ) +
88 " maximum number" +
89 " of nodes" )
90 break
kelvin-onlaba4074292015-07-09 15:19:49 -070091
92 if not self.onosIps:
93 main.log.info( "Could not read any environment variable"
94 + " please load a cell file with all" +
95 " onos IP" )
96 else:
97 main.log.info( self.name + ": Found " +
98 str( self.onosIps.values() ) +
99 " ONOS IPs" )
kelvin-onlaba4074292015-07-09 15:19:49 -0700100 except KeyError:
101 main.log.info( "Invalid environment variable" )
102 except Exception as inst:
103 main.log.error( "Uncaught exception: " + str( inst ) )
104
105 try:
106 if os.getenv( str( self.ip_address ) ) != None:
107 self.ip_address = os.getenv( str( self.ip_address ) )
108 else:
109 main.log.info( self.name +
110 ": Trying to connect to " +
111 self.ip_address )
kelvin-onlaba4074292015-07-09 15:19:49 -0700112 except KeyError:
113 main.log.info( "Invalid host name," +
114 " connecting to local host instead" )
115 self.ip_address = 'localhost'
116 except Exception as inst:
117 main.log.error( "Uncaught exception: " + str( inst ) )
118
kelvin8ec71442015-01-15 16:57:00 -0800119 self.handle = super( OnosDriver, self ).connect(
120 user_name=self.user_name,
kelvin-onlab08679eb2015-01-21 16:11:48 -0800121 ip_address=self.ip_address,
kelvin-onlabd3b64892015-01-20 13:26:24 -0800122 port=self.port,
123 pwd=self.pwd,
124 home=self.home )
Jon Hall05b2b432014-10-08 19:53:25 -0400125
Jon Hall05b2b432014-10-08 19:53:25 -0400126 if self.handle:
Jon Hall0fc0d452015-07-14 09:49:58 -0700127 self.handle.sendline( "cd " + self.home )
128 self.handle.expect( "\$" )
Jon Hall05b2b432014-10-08 19:53:25 -0400129 return self.handle
kelvin8ec71442015-01-15 16:57:00 -0800130 else:
Jon Hall0fc0d452015-07-14 09:49:58 -0700131 main.log.info( "Failed to create ONOS handle" )
Jon Hall05b2b432014-10-08 19:53:25 -0400132 return main.FALSE
133 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800134 main.log.error( self.name + ": EOF exception found" )
135 main.log.error( self.name + ": " + self.handle.before )
Jon Hall05b2b432014-10-08 19:53:25 -0400136 main.cleanup()
137 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800138 except Exception:
139 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall05b2b432014-10-08 19:53:25 -0400140 main.cleanup()
141 main.exit()
142
kelvin8ec71442015-01-15 16:57:00 -0800143 def disconnect( self ):
144 """
Jon Hall05b2b432014-10-08 19:53:25 -0400145 Called when Test is complete to disconnect the ONOS handle.
kelvin8ec71442015-01-15 16:57:00 -0800146 """
Jon Halld61331b2015-02-17 16:35:47 -0800147 response = main.TRUE
Jon Hall05b2b432014-10-08 19:53:25 -0400148 try:
Jon Hall61282e32015-03-19 11:34:11 -0700149 if self.handle:
150 self.handle.sendline( "" )
151 self.handle.expect( "\$" )
152 self.handle.sendline( "exit" )
153 self.handle.expect( "closed" )
Jon Hall05b2b432014-10-08 19:53:25 -0400154 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800155 main.log.error( self.name + ": EOF exception found" )
156 main.log.error( self.name + ": " + self.handle.before )
Jon Hall61282e32015-03-19 11:34:11 -0700157 except ValueError:
Jon Hall1a77a1e2015-04-06 10:41:13 -0700158 main.log.exception( "Exception in disconnect of " + self.name )
Jon Hall61282e32015-03-19 11:34:11 -0700159 response = main.TRUE
Jon Hallfebb1c72015-03-05 13:30:09 -0800160 except Exception:
161 main.log.exception( self.name + ": Connection failed to the host" )
Jon Hall05b2b432014-10-08 19:53:25 -0400162 response = main.FALSE
163 return response
andrew@onlab.us9e2cd0f2014-10-08 20:32:32 -0400164
andrew@onlab.usaee415a2015-06-05 14:38:58 -0400165 def getEpochMs( self ):
166 """
167 Returns milliseconds since epoch
168
169 When checking multiple nodes in a for loop,
170 around a hundred milliseconds of difference (ascending) is
171 generally acceptable due to calltime of the function.
172 Few seconds, however, is not and it means clocks
173 are off sync.
174 """
175 try:
176 self.handle.sendline( 'date +%s.%N' )
177 self.handle.expect( 'date \+\%s\.\%N' )
178 self.handle.expect( '\$' )
179 epochMs = self.handle.before
180 return epochMs
181 except Exception:
182 main.log.exception( 'Uncaught exception getting epoch time' )
183 main.cleanup()
184 main.exit()
185
pingping-lin57a56ce2015-05-20 16:43:48 -0700186 def onosPackage( self, opTimeout=30 ):
kelvin8ec71442015-01-15 16:57:00 -0800187 """
andrew@onlab.us9e2cd0f2014-10-08 20:32:32 -0400188 Produce a self-contained tar.gz file that can be deployed
kelvin8ec71442015-01-15 16:57:00 -0800189 and executed on any platform with Java 7 JRE.
190 """
andrew@onlab.us9e2cd0f2014-10-08 20:32:32 -0400191 try:
kelvin8ec71442015-01-15 16:57:00 -0800192 self.handle.sendline( "onos-package" )
193 self.handle.expect( "onos-package" )
pingping-lin57a56ce2015-05-20 16:43:48 -0700194 self.handle.expect( "tar.gz", opTimeout )
kelvin8ec71442015-01-15 16:57:00 -0800195 handle = str( self.handle.before )
196 main.log.info( "onos-package command returned: " +
197 handle )
198 # As long as the sendline does not time out,
199 # return true. However, be careful to interpret
200 # the results of the onos-package command return
andrewonlab0748d2a2014-10-09 13:24:17 -0400201 return main.TRUE
andrew@onlab.us9e2cd0f2014-10-08 20:32:32 -0400202
andrewonlab7735d852014-10-09 13:02:47 -0400203 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800204 main.log.error( self.name + ": EOF exception found" )
205 main.log.error( self.name + ": " + self.handle.before )
Jon Hallfebb1c72015-03-05 13:30:09 -0800206 except Exception:
207 main.log.exception( "Failed to package ONOS" )
andrew@onlab.us9e2cd0f2014-10-08 20:32:32 -0400208 main.cleanup()
209 main.exit()
210
kelvin-onlabd3b64892015-01-20 13:26:24 -0800211 def onosBuild( self ):
kelvin8ec71442015-01-15 16:57:00 -0800212 """
andrewonlab8790abb2014-11-06 13:51:54 -0500213 Use the pre defined script to build onos via mvn
kelvin8ec71442015-01-15 16:57:00 -0800214 """
andrewonlab8790abb2014-11-06 13:51:54 -0500215 try:
kelvin8ec71442015-01-15 16:57:00 -0800216 self.handle.sendline( "onos-build" )
217 self.handle.expect( "onos-build" )
218 i = self.handle.expect( [
kelvin-onlabd3b64892015-01-20 13:26:24 -0800219 "BUILD SUCCESS",
220 "ERROR",
221 "BUILD FAILED" ],
222 timeout=120 )
kelvin8ec71442015-01-15 16:57:00 -0800223 handle = str( self.handle.before )
andrewonlab8790abb2014-11-06 13:51:54 -0500224
kelvin8ec71442015-01-15 16:57:00 -0800225 main.log.info( "onos-build command returned: " +
226 handle )
andrewonlab8790abb2014-11-06 13:51:54 -0500227
228 if i == 0:
229 return main.TRUE
230 else:
231 return handle
232
233 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800234 main.log.error( self.name + ": EOF exception found" )
235 main.log.error( self.name + ": " + self.handle.before )
Jon Hallfebb1c72015-03-05 13:30:09 -0800236 except Exception:
237 main.log.exception( "Failed to build ONOS" )
andrewonlab8790abb2014-11-06 13:51:54 -0500238 main.cleanup()
239 main.exit()
240
shahshreya9f531fe2015-06-10 12:03:51 -0700241 def cleanInstall( self, skipTest=False, mciTimeout=600 ):
kelvin8ec71442015-01-15 16:57:00 -0800242 """
243 Runs mvn clean install in the root of the ONOS directory.
244 This will clean all ONOS artifacts then compile each module
shahshreya9f531fe2015-06-10 12:03:51 -0700245 Optional:
246 skipTest - Does "-DskipTests -Dcheckstyle.skip -U -T 1C" which
247 skip the test. This will make the building faster.
248 Disregarding the credibility of the build
kelvin8ec71442015-01-15 16:57:00 -0800249 Returns: main.TRUE on success
Jon Hallde9d9aa2014-10-08 20:36:02 -0400250 On Failure, exits the test
kelvin8ec71442015-01-15 16:57:00 -0800251 """
Jon Hallde9d9aa2014-10-08 20:36:02 -0400252 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800253 main.log.info( "Running 'mvn clean install' on " +
254 str( self.name ) +
kelvin8ec71442015-01-15 16:57:00 -0800255 ". This may take some time." )
256 self.handle.sendline( "cd " + self.home )
257 self.handle.expect( "\$" )
Jon Hallea7818b2014-10-09 14:30:59 -0400258
kelvin8ec71442015-01-15 16:57:00 -0800259 self.handle.sendline( "" )
260 self.handle.expect( "\$" )
shahshreya9f531fe2015-06-10 12:03:51 -0700261
262 if not skipTest:
263 self.handle.sendline( "mvn clean install" )
264 self.handle.expect( "mvn clean install" )
265 else:
266 self.handle.sendline( "mvn clean install -DskipTests" +
267 " -Dcheckstyle.skip -U -T 1C" )
268 self.handle.expect( "mvn clean install -DskipTests" +
269 " -Dcheckstyle.skip -U -T 1C" )
kelvin8ec71442015-01-15 16:57:00 -0800270 while True:
271 i = self.handle.expect( [
Jon Hall274b6642015-02-17 11:57:17 -0800272 'There\sis\sinsufficient\smemory\sfor\sthe\sJava\s' +
Jon Hallefbd9792015-03-05 16:11:36 -0800273 'Runtime\sEnvironment\sto\scontinue',
Jon Hallde9d9aa2014-10-08 20:36:02 -0400274 'BUILD\sFAILURE',
275 'BUILD\sSUCCESS',
Jon Halle94919c2015-03-23 11:42:57 -0700276 'onos\$', #TODO: fix this to be more generic?
Jon Hallde9d9aa2014-10-08 20:36:02 -0400277 'ONOS\$',
pingping-lin57a56ce2015-05-20 16:43:48 -0700278 pexpect.TIMEOUT ], mciTimeout )
Jon Hallde9d9aa2014-10-08 20:36:02 -0400279 if i == 0:
kelvin8ec71442015-01-15 16:57:00 -0800280 main.log.error( self.name + ":There is insufficient memory \
281 for the Java Runtime Environment to continue." )
282 # return main.FALSE
Jon Hallde9d9aa2014-10-08 20:36:02 -0400283 main.cleanup()
284 main.exit()
285 if i == 1:
kelvin8ec71442015-01-15 16:57:00 -0800286 main.log.error( self.name + ": Build failure!" )
287 # return main.FALSE
Jon Hallde9d9aa2014-10-08 20:36:02 -0400288 main.cleanup()
289 main.exit()
290 elif i == 2:
kelvin8ec71442015-01-15 16:57:00 -0800291 main.log.info( self.name + ": Build success!" )
Jon Halle94919c2015-03-23 11:42:57 -0700292 elif i == 3 or i == 4:
kelvin8ec71442015-01-15 16:57:00 -0800293 main.log.info( self.name + ": Build complete" )
294 # Print the build time
Jon Hallf8ef52c2014-10-09 19:37:33 -0400295 for line in self.handle.before.splitlines():
296 if "Total time:" in line:
kelvin8ec71442015-01-15 16:57:00 -0800297 main.log.info( line )
298 self.handle.sendline( "" )
299 self.handle.expect( "\$", timeout=60 )
Jon Hallde9d9aa2014-10-08 20:36:02 -0400300 return main.TRUE
Jon Halle94919c2015-03-23 11:42:57 -0700301 elif i == 5:
kelvin8ec71442015-01-15 16:57:00 -0800302 main.log.error(
303 self.name +
304 ": mvn clean install TIMEOUT!" )
305 # return main.FALSE
Jon Hallde9d9aa2014-10-08 20:36:02 -0400306 main.cleanup()
307 main.exit()
308 else:
Jon Hall274b6642015-02-17 11:57:17 -0800309 main.log.error( self.name + ": unexpected response from " +
Jon Hallefbd9792015-03-05 16:11:36 -0800310 "mvn clean install" )
kelvin8ec71442015-01-15 16:57:00 -0800311 # return main.FALSE
Jon Hallde9d9aa2014-10-08 20:36:02 -0400312 main.cleanup()
313 main.exit()
314 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800315 main.log.error( self.name + ": EOF exception found" )
316 main.log.error( self.name + ": " + self.handle.before )
Jon Hallde9d9aa2014-10-08 20:36:02 -0400317 main.cleanup()
318 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800319 except Exception:
320 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hallde9d9aa2014-10-08 20:36:02 -0400321 main.cleanup()
322 main.exit()
Jon Hallacabffd2014-10-09 12:36:53 -0400323
Jon Hall61282e32015-03-19 11:34:11 -0700324 def gitPull( self, comp1="", fastForward=True ):
kelvin8ec71442015-01-15 16:57:00 -0800325 """
Jon Hallacabffd2014-10-09 12:36:53 -0400326 Assumes that "git pull" works without login
Jon Hall47a93fb2015-01-06 16:46:06 -0800327
Jon Hall61282e32015-03-19 11:34:11 -0700328 If the fastForward boolean is set to true, only git pulls that can
329 be fast forwarded will be performed. IE if you have not local commits
330 in your branch.
331
Jon Hallacabffd2014-10-09 12:36:53 -0400332 This function will perform a git pull on the ONOS instance.
kelvin-onlabd3b64892015-01-20 13:26:24 -0800333 If used as gitPull( "NODE" ) it will do git pull + NODE. This is
Jon Hallacabffd2014-10-09 12:36:53 -0400334 for the purpose of pulling from other nodes if necessary.
335
Jon Hall47a93fb2015-01-06 16:46:06 -0800336 Otherwise, this function will perform a git pull in the
Jon Hallacabffd2014-10-09 12:36:53 -0400337 ONOS repository. If it has any problems, it will return main.ERROR
kelvin-onlabd3b64892015-01-20 13:26:24 -0800338 If it successfully does a gitPull, it will return a 1 ( main.TRUE )
Shreya Shahee15f6c2014-10-28 18:12:30 -0400339 If it has no updates, it will return 3.
Jon Hallacabffd2014-10-09 12:36:53 -0400340
kelvin8ec71442015-01-15 16:57:00 -0800341 """
Jon Hallacabffd2014-10-09 12:36:53 -0400342 try:
kelvin8ec71442015-01-15 16:57:00 -0800343 # main.log.info( self.name + ": Stopping ONOS" )
344 # self.stop()
345 self.handle.sendline( "cd " + self.home )
kelvin-onlaba1484582015-02-02 15:46:20 -0800346 self.handle.expect( self.home + "\$" )
Jon Hall61282e32015-03-19 11:34:11 -0700347 cmd = "git pull"
348 if comp1 != "":
349 cmd += ' ' + comp1
350 if fastForward:
351 cmd += ' ' + " --ff-only"
352 self.handle.sendline( cmd )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800353 i = self.handle.expect(
354 [
355 'fatal',
356 'Username\sfor\s(.*):\s',
357 '\sfile(s*) changed,\s',
358 'Already up-to-date',
359 'Aborting',
360 'You\sare\snot\scurrently\son\sa\sbranch',
Jon Hall274b6642015-02-17 11:57:17 -0800361 'You asked me to pull without telling me which branch you',
362 'Pull is not possible because you have unmerged files',
Jon Hall61282e32015-03-19 11:34:11 -0700363 'Please enter a commit message to explain why this merge',
364 'Found a swap file by the name',
365 'Please, commit your changes before you can merge.',
kelvin-onlabd3b64892015-01-20 13:26:24 -0800366 pexpect.TIMEOUT ],
367 timeout=300 )
kelvin8ec71442015-01-15 16:57:00 -0800368 # debug
kelvin-onlabd3b64892015-01-20 13:26:24 -0800369 # main.log.report( self.name +": DEBUG: \n"+
370 # "git pull response: " +
371 # str( self.handle.before ) + str( self.handle.after ) )
kelvin8ec71442015-01-15 16:57:00 -0800372 if i == 0:
Jon Hall61282e32015-03-19 11:34:11 -0700373 main.log.error( self.name + ": Git pull had some issue" )
374 output = self.handle.after
375 self.handle.expect( '\$' )
376 output += self.handle.before
377 main.log.warn( output )
Jon Hallacabffd2014-10-09 12:36:53 -0400378 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800379 elif i == 1:
380 main.log.error(
381 self.name +
382 ": Git Pull Asking for username. " )
Jon Hallacabffd2014-10-09 12:36:53 -0400383 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800384 elif i == 2:
385 main.log.info(
386 self.name +
387 ": Git Pull - pulling repository now" )
kelvin-onlaba1484582015-02-02 15:46:20 -0800388 self.handle.expect( self.home + "\$", 120 )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800389 # So that only when git pull is done, we do mvn clean compile
390 return main.TRUE
kelvin8ec71442015-01-15 16:57:00 -0800391 elif i == 3:
392 main.log.info( self.name + ": Git Pull - Already up to date" )
Jon Hall47a93fb2015-01-06 16:46:06 -0800393 return i
kelvin8ec71442015-01-15 16:57:00 -0800394 elif i == 4:
395 main.log.info(
396 self.name +
Jon Hall274b6642015-02-17 11:57:17 -0800397 ": Git Pull - Aborting..." +
398 "Are there conflicting git files?" )
Jon Hallacabffd2014-10-09 12:36:53 -0400399 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800400 elif i == 5:
401 main.log.info(
402 self.name +
Jon Hall274b6642015-02-17 11:57:17 -0800403 ": Git Pull - You are not currently " +
404 "on a branch so git pull failed!" )
Jon Hallacabffd2014-10-09 12:36:53 -0400405 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800406 elif i == 6:
407 main.log.info(
408 self.name +
Jon Hall274b6642015-02-17 11:57:17 -0800409 ": Git Pull - You have not configured an upstream " +
410 "branch to pull from. Git pull failed!" )
Jon Hallacabffd2014-10-09 12:36:53 -0400411 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800412 elif i == 7:
413 main.log.info(
414 self.name +
Jon Hall274b6642015-02-17 11:57:17 -0800415 ": Git Pull - Pull is not possible because " +
416 "you have unmerged files." )
Jon Hallacabffd2014-10-09 12:36:53 -0400417 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800418 elif i == 8:
Jon Hall61282e32015-03-19 11:34:11 -0700419 # NOTE: abandoning test since we can't reliably handle this
420 # there could be different default text editors and we
421 # also don't know if we actually want to make the commit
422 main.log.error( "Git pull resulted in a merge commit message" +
423 ". Exiting test!" )
424 main.cleanup()
425 main.exit()
426 elif i == 9: # Merge commit message but swap file exists
427 main.log.error( "Git pull resulted in a merge commit message" +
428 " but a swap file exists." )
429 try:
430 self.handle.send( 'A' ) # Abort
431 self.handle.expect( "\$" )
432 return main.ERROR
433 except Exception:
434 main.log.exception( "Couldn't exit editor prompt!")
435 main.cleanup()
436 main.exit()
437 elif i == 10: # In the middle of a merge commit
438 main.log.error( "Git branch is in the middle of a merge. " )
439 main.log.warn( self.handle.before + self.handle.after )
440 return main.ERROR
441 elif i == 11:
kelvin8ec71442015-01-15 16:57:00 -0800442 main.log.error( self.name + ": Git Pull - TIMEOUT" )
443 main.log.error(
444 self.name + " Response was: " + str(
445 self.handle.before ) )
Jon Hallacabffd2014-10-09 12:36:53 -0400446 return main.ERROR
447 else:
kelvin8ec71442015-01-15 16:57:00 -0800448 main.log.error(
449 self.name +
450 ": Git Pull - Unexpected response, check for pull errors" )
Jon Hallacabffd2014-10-09 12:36:53 -0400451 return main.ERROR
452 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800453 main.log.error( self.name + ": EOF exception found" )
454 main.log.error( self.name + ": " + self.handle.before )
Jon Hallacabffd2014-10-09 12:36:53 -0400455 main.cleanup()
456 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800457 except Exception:
458 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hallacabffd2014-10-09 12:36:53 -0400459 main.cleanup()
460 main.exit()
461
kelvin-onlabd3b64892015-01-20 13:26:24 -0800462 def gitCheckout( self, branch="master" ):
kelvin8ec71442015-01-15 16:57:00 -0800463 """
Jon Hallacabffd2014-10-09 12:36:53 -0400464 Assumes that "git pull" works without login
kelvin8ec71442015-01-15 16:57:00 -0800465
Jon Hallacabffd2014-10-09 12:36:53 -0400466 This function will perform a git git checkout on the ONOS instance.
kelvin-onlabd3b64892015-01-20 13:26:24 -0800467 If used as gitCheckout( "branch" ) it will do git checkout
468 of the "branch".
Jon Hallacabffd2014-10-09 12:36:53 -0400469
470 Otherwise, this function will perform a git checkout of the master
kelvin8ec71442015-01-15 16:57:00 -0800471 branch of the ONOS repository. If it has any problems, it will return
472 main.ERROR.
473 If the branch was already the specified branch, or the git checkout was
Jon Hallacabffd2014-10-09 12:36:53 -0400474 successful then the function will return main.TRUE.
475
kelvin8ec71442015-01-15 16:57:00 -0800476 """
Jon Hallacabffd2014-10-09 12:36:53 -0400477 try:
kelvin8ec71442015-01-15 16:57:00 -0800478 self.handle.sendline( "cd " + self.home )
kelvin-onlaba1484582015-02-02 15:46:20 -0800479 self.handle.expect( self.home + "\$" )
Jon Hall274b6642015-02-17 11:57:17 -0800480 main.log.info( self.name +
481 ": Checking out git branch/ref: " + branch + "..." )
kelvin8ec71442015-01-15 16:57:00 -0800482 cmd = "git checkout " + branch
483 self.handle.sendline( cmd )
484 self.handle.expect( cmd )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800485 i = self.handle.expect(
Jon Hall274b6642015-02-17 11:57:17 -0800486 [ 'fatal',
Jon Hall61282e32015-03-19 11:34:11 -0700487 'Username for (.*): ',
488 'Already on \'',
Jon Hall7a8354f2015-06-10 15:37:00 -0700489 'Switched to (a new )?branch \'' + str( branch ),
Jon Hall274b6642015-02-17 11:57:17 -0800490 pexpect.TIMEOUT,
491 'error: Your local changes to the following files' +
Jon Hallefbd9792015-03-05 16:11:36 -0800492 'would be overwritten by checkout:',
Jon Hall274b6642015-02-17 11:57:17 -0800493 'error: you need to resolve your current index first',
494 "You are in 'detached HEAD' state.",
495 "HEAD is now at " ],
kelvin-onlabd3b64892015-01-20 13:26:24 -0800496 timeout=60 )
kelvin8ec71442015-01-15 16:57:00 -0800497 if i == 0:
498 main.log.error(
499 self.name +
500 ": Git checkout had some issue..." )
501 main.log.error( self.name + ": " + self.handle.before )
Jon Hallacabffd2014-10-09 12:36:53 -0400502 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800503 elif i == 1:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800504 main.log.error(
505 self.name +
506 ": Git checkout asking for username." +
507 " Please configure your local git repository to be able " +
508 "to access your remote repository passwordlessly" )
Jon Hall274b6642015-02-17 11:57:17 -0800509 # TODO add support for authenticating
Jon Hallacabffd2014-10-09 12:36:53 -0400510 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800511 elif i == 2:
512 main.log.info(
513 self.name +
Jon Hall274b6642015-02-17 11:57:17 -0800514 ": Git Checkout %s : Already on this branch" % branch )
kelvin-onlaba1484582015-02-02 15:46:20 -0800515 self.handle.expect( self.home + "\$" )
kelvin8ec71442015-01-15 16:57:00 -0800516 # main.log.info( "DEBUG: after checkout cmd = "+
517 # self.handle.before )
Jon Hallacabffd2014-10-09 12:36:53 -0400518 return main.TRUE
kelvin8ec71442015-01-15 16:57:00 -0800519 elif i == 3:
520 main.log.info(
521 self.name +
Jon Hall274b6642015-02-17 11:57:17 -0800522 ": Git checkout %s - Switched to this branch" % branch )
kelvin-onlaba1484582015-02-02 15:46:20 -0800523 self.handle.expect( self.home + "\$" )
kelvin8ec71442015-01-15 16:57:00 -0800524 # main.log.info( "DEBUG: after checkout cmd = "+
525 # self.handle.before )
Jon Hallacabffd2014-10-09 12:36:53 -0400526 return main.TRUE
kelvin8ec71442015-01-15 16:57:00 -0800527 elif i == 4:
528 main.log.error( self.name + ": Git Checkout- TIMEOUT" )
529 main.log.error(
Jon Hall274b6642015-02-17 11:57:17 -0800530 self.name + " Response was: " + str( self.handle.before ) )
Jon Hallacabffd2014-10-09 12:36:53 -0400531 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800532 elif i == 5:
533 self.handle.expect( "Aborting" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800534 main.log.error(
535 self.name +
536 ": Git checkout error: \n" +
Jon Hall274b6642015-02-17 11:57:17 -0800537 "Your local changes to the following files would" +
538 " be overwritten by checkout:" +
539 str( self.handle.before ) )
kelvin-onlaba1484582015-02-02 15:46:20 -0800540 self.handle.expect( self.home + "\$" )
Jon Hall81e29af2014-11-04 20:41:23 -0500541 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -0800542 elif i == 6:
Jon Hall274b6642015-02-17 11:57:17 -0800543 main.log.error(
544 self.name +
545 ": Git checkout error: \n" +
546 "You need to resolve your current index first:" +
547 str( self.handle.before ) )
kelvin-onlaba1484582015-02-02 15:46:20 -0800548 self.handle.expect( self.home + "\$" )
Jon Hall81e29af2014-11-04 20:41:23 -0500549 return main.ERROR
Jon Hall274b6642015-02-17 11:57:17 -0800550 elif i == 7:
551 main.log.info(
552 self.name +
553 ": Git checkout " + str( branch ) +
554 " - You are in 'detached HEAD' state. HEAD is now at " +
555 str( branch ) )
556 self.handle.expect( self.home + "\$" )
557 return main.TRUE
558 elif i == 8: # Already in detached HEAD on the specified commit
559 main.log.info(
560 self.name +
561 ": Git Checkout %s : Already on commit" % branch )
562 self.handle.expect( self.home + "\$" )
563 return main.TRUE
Jon Hallacabffd2014-10-09 12:36:53 -0400564 else:
kelvin8ec71442015-01-15 16:57:00 -0800565 main.log.error(
566 self.name +
Jon Hall274b6642015-02-17 11:57:17 -0800567 ": Git Checkout - Unexpected response, " +
568 "check for pull errors" )
kelvin8ec71442015-01-15 16:57:00 -0800569 main.log.error( self.name + ": " + self.handle.before )
Jon Hallacabffd2014-10-09 12:36:53 -0400570 return main.ERROR
571
572 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800573 main.log.error( self.name + ": EOF exception found" )
574 main.log.error( self.name + ": " + self.handle.before )
Jon Hallacabffd2014-10-09 12:36:53 -0400575 main.cleanup()
576 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800577 except Exception:
578 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hallacabffd2014-10-09 12:36:53 -0400579 main.cleanup()
580 main.exit()
andrewonlab95ca1462014-10-09 14:04:24 -0400581
pingping-lin6d23d9e2015-02-02 16:54:24 -0800582 def getBranchName( self ):
pingping-linf30cf272015-05-29 15:54:07 -0700583 main.log.info( "self.home = " )
584 main.log.info( self.home )
pingping-lin6d23d9e2015-02-02 16:54:24 -0800585 self.handle.sendline( "cd " + self.home )
pingping-lin9bf3d8f2015-05-29 16:05:28 -0700586 self.handle.expect( self.home + "\$" )
pingping-lin6d23d9e2015-02-02 16:54:24 -0800587 self.handle.sendline( "git name-rev --name-only HEAD" )
588 self.handle.expect( "git name-rev --name-only HEAD" )
589 self.handle.expect( "\$" )
590
591 lines = self.handle.before.splitlines()
592 if lines[1] == "master":
593 return "master"
594 elif lines[1] == "onos-1.0":
595 return "onos-1.0"
596 else:
597 main.log.info( lines[1] )
598 return "unexpected ONOS branch for SDN-IP test"
599
kelvin-onlabd3b64892015-01-20 13:26:24 -0800600 def getVersion( self, report=False ):
kelvin8ec71442015-01-15 16:57:00 -0800601 """
Jon Hall274b6642015-02-17 11:57:17 -0800602 Writes the COMMIT number to the report to be parsed
Jon Hallefbd9792015-03-05 16:11:36 -0800603 by Jenkins data collector.
kelvin8ec71442015-01-15 16:57:00 -0800604 """
Jon Hall45ec0922014-10-10 19:33:49 -0400605 try:
kelvin8ec71442015-01-15 16:57:00 -0800606 self.handle.sendline( "" )
607 self.handle.expect( "\$" )
608 self.handle.sendline(
609 "cd " +
610 self.home +
Jon Hall274b6642015-02-17 11:57:17 -0800611 "; git log -1 --pretty=fuller --decorate=short | grep -A 6 " +
612 " \"commit\" --color=never" )
kelvin8ec71442015-01-15 16:57:00 -0800613 # NOTE: for some reason there are backspaces inserted in this
614 # phrase when run from Jenkins on some tests
615 self.handle.expect( "never" )
616 self.handle.expect( "\$" )
617 response = ( self.name + ": \n" + str(
618 self.handle.before + self.handle.after ) )
619 self.handle.sendline( "cd " + self.home )
620 self.handle.expect( "\$" )
621 lines = response.splitlines()
Jon Hall45ec0922014-10-10 19:33:49 -0400622 for line in lines:
Jon Hallfd191202014-11-07 18:36:09 -0500623 print line
624 if report:
pingping-lin763ee042015-05-20 17:45:30 -0700625 main.log.wiki( "<blockquote>" )
kelvin8ec71442015-01-15 16:57:00 -0800626 for line in lines[ 2:-1 ]:
627 # Bracket replacement is for Wiki-compliant
628 # formatting. '<' or '>' are interpreted
629 # as xml specific tags that cause errors
630 line = line.replace( "<", "[" )
631 line = line.replace( ">", "]" )
pingping-lin763ee042015-05-20 17:45:30 -0700632 #main.log.wiki( "\t" + line )
633 main.log.wiki( line + "<br /> " )
634 main.log.summary( line )
635 main.log.wiki( "</blockquote>" )
636 main.log.summary("\n")
kelvin8ec71442015-01-15 16:57:00 -0800637 return lines[ 2 ]
Jon Hall45ec0922014-10-10 19:33:49 -0400638 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800639 main.log.error( self.name + ": EOF exception found" )
640 main.log.error( self.name + ": " + self.handle.before )
Jon Hall45ec0922014-10-10 19:33:49 -0400641 main.cleanup()
642 main.exit()
Jon Hall368769f2014-11-19 15:43:35 -0800643 except pexpect.TIMEOUT:
kelvin8ec71442015-01-15 16:57:00 -0800644 main.log.error( self.name + ": TIMEOUT exception found" )
645 main.log.error( self.name + ": " + self.handle.before )
Jon Hall368769f2014-11-19 15:43:35 -0800646 main.cleanup()
647 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800648 except Exception:
649 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall45ec0922014-10-10 19:33:49 -0400650 main.cleanup()
651 main.exit()
652
kelvin-onlabd3b64892015-01-20 13:26:24 -0800653 def createCellFile( self, benchIp, fileName, mnIpAddrs,
kelvin-onlaba4074292015-07-09 15:19:49 -0700654 appString, onosIpAddrs ):
kelvin8ec71442015-01-15 16:57:00 -0800655 """
andrewonlab94282092014-10-10 13:00:11 -0400656 Creates a cell file based on arguments
657 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800658 * Bench IP address ( benchIp )
andrewonlab94282092014-10-10 13:00:11 -0400659 - Needed to copy the cell file over
kelvin-onlabd3b64892015-01-20 13:26:24 -0800660 * File name of the cell file ( fileName )
661 * Mininet IP address ( mnIpAddrs )
kelvin8ec71442015-01-15 16:57:00 -0800662 - Note that only 1 ip address is
andrewonlab94282092014-10-10 13:00:11 -0400663 supported currently
kelvin-onlabd3b64892015-01-20 13:26:24 -0800664 * ONOS IP addresses ( onosIpAddrs )
andrewonlab94282092014-10-10 13:00:11 -0400665 - Must be passed in as last arguments
kelvin8ec71442015-01-15 16:57:00 -0800666
andrewonlab94282092014-10-10 13:00:11 -0400667 NOTE: Assumes cells are located at:
668 ~/<self.home>/tools/test/cells/
kelvin8ec71442015-01-15 16:57:00 -0800669 """
670 # Variable initialization
Jon Hallf57a5ef2015-07-07 17:56:16 -0700671 cellDirectory = os.environ["ONOS_ROOT"] + "/tools/test/cells/"
kelvin8ec71442015-01-15 16:57:00 -0800672 # We want to create the cell file in the dependencies directory
673 # of TestON first, then copy over to ONOS bench
kelvin-onlabd3b64892015-01-20 13:26:24 -0800674 tempDirectory = "/tmp/"
kelvin8ec71442015-01-15 16:57:00 -0800675 # Create the cell file in the directory for writing ( w+ )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800676 cellFile = open( tempDirectory + fileName, 'w+' )
kelvin8ec71442015-01-15 16:57:00 -0800677
cameron@onlab.us75900962015-03-30 13:22:49 -0700678 # App string is hardcoded environment variables
kelvin8ec71442015-01-15 16:57:00 -0800679 # That you may wish to use by default on startup.
cameron@onlab.us75900962015-03-30 13:22:49 -0700680 # Note that you may not want certain apps listed
kelvin8ec71442015-01-15 16:57:00 -0800681 # on here.
cameron@onlab.us75900962015-03-30 13:22:49 -0700682 appString = "export ONOS_APPS=" + appString
kelvin-onlabd3b64892015-01-20 13:26:24 -0800683 mnString = "export OCN="
kelvin-onlabf70fd542015-05-07 18:41:40 -0700684 if mnIpAddrs == "":
685 mnString = ""
kelvin-onlabd3b64892015-01-20 13:26:24 -0800686 onosString = "export OC"
687 tempCount = 1
kelvin8ec71442015-01-15 16:57:00 -0800688
kelvin-onlabd3b64892015-01-20 13:26:24 -0800689 # Create ONOSNIC ip address prefix
kelvin-onlaba4074292015-07-09 15:19:49 -0700690 tempOnosIp = str( onosIpAddrs[ 0 ] )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800691 tempList = []
692 tempList = tempOnosIp.split( "." )
kelvin8ec71442015-01-15 16:57:00 -0800693 # Omit last element of list to format for NIC
kelvin-onlabd3b64892015-01-20 13:26:24 -0800694 tempList = tempList[ :-1 ]
kelvin8ec71442015-01-15 16:57:00 -0800695 # Structure the nic string ip
kelvin-onlabd3b64892015-01-20 13:26:24 -0800696 nicAddr = ".".join( tempList ) + ".*"
697 onosNicString = "export ONOS_NIC=" + nicAddr
andrewonlab94282092014-10-10 13:00:11 -0400698
699 try:
kelvin8ec71442015-01-15 16:57:00 -0800700 # Start writing to file
kelvin-onlabd3b64892015-01-20 13:26:24 -0800701 cellFile.write( onosNicString + "\n" )
andrewonlab94282092014-10-10 13:00:11 -0400702
kelvin-onlabd3b64892015-01-20 13:26:24 -0800703 for arg in onosIpAddrs:
704 # For each argument in onosIpAddrs, write to file
kelvin8ec71442015-01-15 16:57:00 -0800705 # Output should look like the following:
andrewonlabd4940492014-10-24 12:21:27 -0400706 # export OC1="10.128.20.11"
707 # export OC2="10.128.20.12"
kelvin-onlabd3b64892015-01-20 13:26:24 -0800708 cellFile.write( onosString + str( tempCount ) +
709 "=" + "\"" + arg + "\"" + "\n" )
710 tempCount = tempCount + 1
kelvin8ec71442015-01-15 16:57:00 -0800711
kelvin-onlabd3b64892015-01-20 13:26:24 -0800712 cellFile.write( mnString + "\"" + mnIpAddrs + "\"" + "\n" )
cameron@onlab.us75900962015-03-30 13:22:49 -0700713 cellFile.write( appString + "\n" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800714 cellFile.close()
andrewonlab94282092014-10-10 13:00:11 -0400715
kelvin8ec71442015-01-15 16:57:00 -0800716 # We use os.system to send the command to TestON cluster
717 # to account for the case in which TestON is not located
718 # on the same cluster as the ONOS bench
719 # Note that even if TestON is located on the same cluster
720 # as ONOS bench, you must setup passwordless ssh
721 # between TestON and ONOS bench in order to automate the test.
kelvin-onlabc2b79102015-07-14 11:41:20 -0700722 os.system( "scp " + tempDirectory + fileName + " " +
723 self.user_name + "@" + self.ip_address + ":" + cellDirectory )
andrewonlab94282092014-10-10 13:00:11 -0400724
andrewonlab2a6c9342014-10-16 13:40:15 -0400725 return main.TRUE
726
andrewonlab94282092014-10-10 13:00:11 -0400727 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800728 main.log.error( self.name + ": EOF exception found" )
729 main.log.error( self.name + ": " + self.handle.before )
andrewonlab94282092014-10-10 13:00:11 -0400730 main.cleanup()
731 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800732 except Exception:
733 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab94282092014-10-10 13:00:11 -0400734 main.cleanup()
735 main.exit()
736
kelvin-onlabd3b64892015-01-20 13:26:24 -0800737 def setCell( self, cellname ):
kelvin8ec71442015-01-15 16:57:00 -0800738 """
andrewonlab95ca1462014-10-09 14:04:24 -0400739 Calls 'cell <name>' to set the environment variables on ONOSbench
kelvin8ec71442015-01-15 16:57:00 -0800740 """
Hari Krishna03f530e2015-07-10 17:28:27 -0700741 import re
andrewonlab95ca1462014-10-09 14:04:24 -0400742 try:
743 if not cellname:
kelvin8ec71442015-01-15 16:57:00 -0800744 main.log.error( "Must define cellname" )
andrewonlab95ca1462014-10-09 14:04:24 -0400745 main.cleanup()
746 main.exit()
747 else:
kelvin8ec71442015-01-15 16:57:00 -0800748 self.handle.sendline( "cell " + str( cellname ) )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800749 # Expect the cellname in the ONOSCELL variable.
kelvin8ec71442015-01-15 16:57:00 -0800750 # Note that this variable name is subject to change
andrewonlab95ca1462014-10-09 14:04:24 -0400751 # and that this driver will have to change accordingly
Cameron Franke9c94fb02015-01-21 10:20:20 -0800752 self.handle.expect(str(cellname))
kelvin-onlabd3b64892015-01-20 13:26:24 -0800753 handleBefore = self.handle.before
754 handleAfter = self.handle.after
kelvin8ec71442015-01-15 16:57:00 -0800755 # Get the rest of the handle
Cameron Franke9c94fb02015-01-21 10:20:20 -0800756 self.handle.sendline("")
757 self.handle.expect("\$")
kelvin-onlabd3b64892015-01-20 13:26:24 -0800758 handleMore = self.handle.before
andrewonlab95ca1462014-10-09 14:04:24 -0400759
Hari Krishna03f530e2015-07-10 17:28:27 -0700760 cell_result = handleBefore + handleAfter + handleMore
761 print cell_result
762 if( re.search( "No such cell", cell_result ) ):
763 main.log.error( "Cell call returned: " + handleBefore +
kelvin-onlabd3b64892015-01-20 13:26:24 -0800764 handleAfter + handleMore )
Hari Krishna03f530e2015-07-10 17:28:27 -0700765 main.cleanup()
766 main.exit()
andrewonlab95ca1462014-10-09 14:04:24 -0400767 return main.TRUE
768
769 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800770 main.log.error( self.name + ": EOF exception found" )
771 main.log.error( self.name + ": " + self.handle.before )
andrewonlab95ca1462014-10-09 14:04:24 -0400772 main.cleanup()
773 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800774 except Exception:
775 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab95ca1462014-10-09 14:04:24 -0400776 main.cleanup()
777 main.exit()
778
kelvin-onlabd3b64892015-01-20 13:26:24 -0800779 def verifyCell( self ):
kelvin8ec71442015-01-15 16:57:00 -0800780 """
andrewonlabc03bf6c2014-10-09 14:56:18 -0400781 Calls 'onos-verify-cell' to check for cell installation
kelvin8ec71442015-01-15 16:57:00 -0800782 """
783 # TODO: Add meaningful expect value
andrewonlab8d0d7d72014-10-09 16:33:15 -0400784
andrewonlabc03bf6c2014-10-09 14:56:18 -0400785 try:
kelvin8ec71442015-01-15 16:57:00 -0800786 # Clean handle by sending empty and expecting $
787 self.handle.sendline( "" )
788 self.handle.expect( "\$" )
789 self.handle.sendline( "onos-verify-cell" )
790 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800791 handleBefore = self.handle.before
792 handleAfter = self.handle.after
kelvin8ec71442015-01-15 16:57:00 -0800793 # Get the rest of the handle
794 self.handle.sendline( "" )
795 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800796 handleMore = self.handle.before
andrewonlabc03bf6c2014-10-09 14:56:18 -0400797
kelvin-onlabd3b64892015-01-20 13:26:24 -0800798 main.log.info( "Verify cell returned: " + handleBefore +
799 handleAfter + handleMore )
andrewonlabc03bf6c2014-10-09 14:56:18 -0400800
801 return main.TRUE
Jon Halla5cb6172015-02-23 09:28:28 -0800802 except pexpect.ExceptionPexpect as e:
803 main.log.error( self.name + ": Pexpect exception found of type " +
804 str( type( e ) ) )
805 main.log.error ( e.get_trace() )
kelvin8ec71442015-01-15 16:57:00 -0800806 main.log.error( self.name + ": " + self.handle.before )
Jon Hall7993bfc2014-10-09 16:30:14 -0400807 main.cleanup()
808 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800809 except Exception:
810 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall7993bfc2014-10-09 16:30:14 -0400811 main.cleanup()
812 main.exit()
813
jenkins1e99e7b2015-04-02 18:15:39 -0700814 def onosCfgSet( self, ONOSIp, configName, configParam ):
815 """
816 Uses 'onos <node-ip> cfg set' to change a parameter value of an
817 application.
818
819 ex)
820 onos 10.0.0.1 cfg set org.onosproject.myapp appSetting 1
jenkins1e99e7b2015-04-02 18:15:39 -0700821 ONOSIp = '10.0.0.1'
822 configName = 'org.onosproject.myapp'
823 configParam = 'appSetting 1'
jenkins1e99e7b2015-04-02 18:15:39 -0700824 """
cameron@onlab.us78b89652015-07-08 15:21:03 -0700825 for i in range(5):
826 try:
827 cfgStr = ( "onos "+str(ONOSIp)+" cfg set "+
828 str(configName) + " " +
829 str(configParam)
830 )
jenkins1e99e7b2015-04-02 18:15:39 -0700831
cameron@onlab.us78b89652015-07-08 15:21:03 -0700832 self.handle.sendline( "" )
833 self.handle.expect( ":~" )
834 self.handle.sendline( cfgStr )
835 self.handle.expect("cfg set")
836 self.handle.expect( ":~" )
jenkins1e99e7b2015-04-02 18:15:39 -0700837
cameron@onlab.us78b89652015-07-08 15:21:03 -0700838 paramValue = configParam.split(" ")[1]
839 paramName = configParam.split(" ")[0]
840
841 checkStr = ( "onos " + str(ONOSIp) + """ cfg get " """ + str(configName) + " " + paramName + """ " """)
jenkins1e99e7b2015-04-02 18:15:39 -0700842
cameron@onlab.us78b89652015-07-08 15:21:03 -0700843 self.handle.sendline( checkStr )
844 self.handle.expect( ":~" )
jenkins1e99e7b2015-04-02 18:15:39 -0700845
cameron@onlab.us78b89652015-07-08 15:21:03 -0700846 if "value=" + paramValue + "," in self.handle.before:
847 main.log.info("cfg " + configName + " successfully set to " + configParam)
848 return main.TRUE
849
850 except pexpect.ExceptionPexpect as e:
851 main.log.error( self.name + ": Pexpect exception found of type " +
852 str( type( e ) ) )
853 main.log.error ( e.get_trace() )
854 main.log.error( self.name + ": " + self.handle.before )
855 main.cleanup()
856 main.exit()
857 except Exception:
858 main.log.exception( self.name + ": Uncaught exception!" )
859 main.cleanup()
860 main.exit()
861
862 time.sleep(5)
863
864 main.log.error("CFG SET FAILURE: " + configName + " " + configParam )
865 main.ONOSbench.handle.sendline("onos $OC1 cfg get")
866 main.ONOSbench.handle.expect("\$")
867 print main.ONOSbench.handle.before
868 main.ONOSbench.logReport( ONOSIp, ["ERROR","WARN","EXCEPT"], "d")
869 return main.FALSE
870
871
kelvin-onlabd3b64892015-01-20 13:26:24 -0800872 def onosCli( self, ONOSIp, cmdstr ):
kelvin8ec71442015-01-15 16:57:00 -0800873 """
andrewonlab05e362f2014-10-10 00:40:57 -0400874 Uses 'onos' command to send various ONOS CLI arguments.
875 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800876 * ONOSIp: specify the ip of the cell machine
andrewonlab94282092014-10-10 13:00:11 -0400877 * cmdstr: specify the command string to send
kelvin8ec71442015-01-15 16:57:00 -0800878
879 This function is intended to expose the entire karaf
andrewonlab6e20c342014-10-10 18:08:48 -0400880 CLI commands for ONOS. Try to use this function first
881 before attempting to write a ONOS CLI specific driver
kelvin8ec71442015-01-15 16:57:00 -0800882 function.
883 You can see a list of available 'cmdstr' arguments
andrewonlab6e20c342014-10-10 18:08:48 -0400884 by starting onos, and typing in 'onos' to enter the
885 onos> CLI. Then, type 'help' to see the list of
kelvin8ec71442015-01-15 16:57:00 -0800886 available commands.
887 """
andrewonlab05e362f2014-10-10 00:40:57 -0400888 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800889 if not ONOSIp:
kelvin8ec71442015-01-15 16:57:00 -0800890 main.log.error( "You must specify the IP address" )
andrewonlab05e362f2014-10-10 00:40:57 -0400891 return main.FALSE
892 if not cmdstr:
kelvin8ec71442015-01-15 16:57:00 -0800893 main.log.error( "You must specify the command string" )
andrewonlab05e362f2014-10-10 00:40:57 -0400894 return main.FALSE
895
kelvin8ec71442015-01-15 16:57:00 -0800896 cmdstr = str( cmdstr )
897 self.handle.sendline( "" )
898 self.handle.expect( "\$" )
andrewonlab05e362f2014-10-10 00:40:57 -0400899
kelvin-onlabd3b64892015-01-20 13:26:24 -0800900 self.handle.sendline( "onos -w " + ONOSIp + " " + cmdstr )
kelvin8ec71442015-01-15 16:57:00 -0800901 self.handle.expect( "\$" )
andrewonlab05e362f2014-10-10 00:40:57 -0400902
kelvin-onlabd3b64892015-01-20 13:26:24 -0800903 handleBefore = self.handle.before
Shreya Shaha73aaad2014-10-27 18:03:09 -0400904 print "handle_before = ", self.handle.before
kelvin-onlabd3b64892015-01-20 13:26:24 -0800905 # handleAfter = str( self.handle.after )
Jon Hall47a93fb2015-01-06 16:46:06 -0800906
kelvin8ec71442015-01-15 16:57:00 -0800907 # self.handle.sendline( "" )
908 # self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800909 # handleMore = str( self.handle.before )
andrewonlab05e362f2014-10-10 00:40:57 -0400910
kelvin8ec71442015-01-15 16:57:00 -0800911 main.log.info( "Command sent successfully" )
andrewonlab05e362f2014-10-10 00:40:57 -0400912
kelvin8ec71442015-01-15 16:57:00 -0800913 # Obtain return handle that consists of result from
914 # the onos command. The string may need to be
915 # configured further.
kelvin-onlabd3b64892015-01-20 13:26:24 -0800916 # returnString = handleBefore + handleAfter
917 returnString = handleBefore
918 print "return_string = ", returnString
919 return returnString
andrewonlab05e362f2014-10-10 00:40:57 -0400920
921 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800922 main.log.error( self.name + ": EOF exception found" )
923 main.log.error( self.name + ": " + self.handle.before )
andrewonlab05e362f2014-10-10 00:40:57 -0400924 main.cleanup()
925 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800926 except Exception:
927 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab05e362f2014-10-10 00:40:57 -0400928 main.cleanup()
929 main.exit()
Jon Hall7993bfc2014-10-09 16:30:14 -0400930
kelvin-onlabd3b64892015-01-20 13:26:24 -0800931 def onosInstall( self, options="-f", node="" ):
kelvin8ec71442015-01-15 16:57:00 -0800932 """
Jon Hall7993bfc2014-10-09 16:30:14 -0400933 Installs ONOS bits on the designated cell machine.
kelvin8ec71442015-01-15 16:57:00 -0800934 If -f option is provided, it also forces an uninstall.
935 Presently, install also includes onos-push-bits and
Jon Hall7993bfc2014-10-09 16:30:14 -0400936 onos-config within.
kelvin8ec71442015-01-15 16:57:00 -0800937 The node option allows you to selectively only push the jar
Jon Hall7993bfc2014-10-09 16:30:14 -0400938 files to certain onos nodes
939
940 Returns: main.TRUE on success and main.FALSE on failure
kelvin8ec71442015-01-15 16:57:00 -0800941 """
Jon Hall7993bfc2014-10-09 16:30:14 -0400942 try:
andrewonlab114768a2014-11-14 12:44:44 -0500943 if options:
kelvin8ec71442015-01-15 16:57:00 -0800944 self.handle.sendline( "onos-install " + options + " " + node )
andrewonlab114768a2014-11-14 12:44:44 -0500945 else:
kelvin8ec71442015-01-15 16:57:00 -0800946 self.handle.sendline( "onos-install " + node )
947 self.handle.expect( "onos-install " )
948 # NOTE: this timeout may need to change depending on the network
949 # and size of ONOS
950 i = self.handle.expect( [ "Network\sis\sunreachable",
kelvin-onlabd3b64892015-01-20 13:26:24 -0800951 "onos\sstart/running,\sprocess",
kelvin8ec71442015-01-15 16:57:00 -0800952 "ONOS\sis\salready\sinstalled",
953 pexpect.TIMEOUT ], timeout=60 )
Jon Hall7993bfc2014-10-09 16:30:14 -0400954
Jon Hall7993bfc2014-10-09 16:30:14 -0400955 if i == 0:
kelvin8ec71442015-01-15 16:57:00 -0800956 main.log.warn( "Network is unreachable" )
Jon Hall7993bfc2014-10-09 16:30:14 -0400957 return main.FALSE
958 elif i == 1:
kelvin8ec71442015-01-15 16:57:00 -0800959 main.log.info(
960 "ONOS was installed on " +
961 node +
962 " and started" )
Jon Hall7993bfc2014-10-09 16:30:14 -0400963 return main.TRUE
andrewonlabd9a73a72014-11-14 17:28:21 -0500964 elif i == 2:
kelvin8ec71442015-01-15 16:57:00 -0800965 main.log.info( "ONOS is already installed on " + node )
andrewonlabd9a73a72014-11-14 17:28:21 -0500966 return main.TRUE
kelvin8ec71442015-01-15 16:57:00 -0800967 elif i == 3:
968 main.log.info(
969 "Installation of ONOS on " +
970 node +
971 " timed out" )
Jon Hall7993bfc2014-10-09 16:30:14 -0400972 return main.FALSE
andrewonlabc03bf6c2014-10-09 14:56:18 -0400973
974 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800975 main.log.error( self.name + ": EOF exception found" )
976 main.log.error( self.name + ": " + self.handle.before )
andrewonlabc03bf6c2014-10-09 14:56:18 -0400977 main.cleanup()
978 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800979 except Exception:
980 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabc03bf6c2014-10-09 14:56:18 -0400981 main.cleanup()
982 main.exit()
andrewonlab95ca1462014-10-09 14:04:24 -0400983
kelvin-onlabd3b64892015-01-20 13:26:24 -0800984 def onosStart( self, nodeIp ):
kelvin8ec71442015-01-15 16:57:00 -0800985 """
andrewonlab8d0d7d72014-10-09 16:33:15 -0400986 Calls onos command: 'onos-service [<node-ip>] start'
andrewonlabe8e56fd2014-10-09 17:12:44 -0400987 This command is a remote management of the ONOS upstart daemon
kelvin8ec71442015-01-15 16:57:00 -0800988 """
andrewonlab8d0d7d72014-10-09 16:33:15 -0400989 try:
kelvin8ec71442015-01-15 16:57:00 -0800990 self.handle.sendline( "" )
991 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800992 self.handle.sendline( "onos-service " + str( nodeIp ) +
kelvin8ec71442015-01-15 16:57:00 -0800993 " start" )
994 i = self.handle.expect( [
andrewonlab8d0d7d72014-10-09 16:33:15 -0400995 "Job\sis\salready\srunning",
996 "start/running",
997 "Unknown\sinstance",
kelvin8ec71442015-01-15 16:57:00 -0800998 pexpect.TIMEOUT ], timeout=120 )
andrewonlab8d0d7d72014-10-09 16:33:15 -0400999
1000 if i == 0:
kelvin8ec71442015-01-15 16:57:00 -08001001 main.log.info( "Service is already running" )
andrewonlab8d0d7d72014-10-09 16:33:15 -04001002 return main.TRUE
1003 elif i == 1:
kelvin8ec71442015-01-15 16:57:00 -08001004 main.log.info( "ONOS service started" )
andrewonlab8d0d7d72014-10-09 16:33:15 -04001005 return main.TRUE
1006 else:
kelvin8ec71442015-01-15 16:57:00 -08001007 main.log.error( "ONOS service failed to start" )
andrewonlab8d0d7d72014-10-09 16:33:15 -04001008 main.cleanup()
1009 main.exit()
andrewonlab8d0d7d72014-10-09 16:33:15 -04001010 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001011 main.log.error( self.name + ": EOF exception found" )
1012 main.log.error( self.name + ": " + self.handle.before )
andrewonlab8d0d7d72014-10-09 16:33:15 -04001013 main.cleanup()
1014 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001015 except Exception:
1016 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab8d0d7d72014-10-09 16:33:15 -04001017 main.cleanup()
1018 main.exit()
1019
kelvin-onlabd3b64892015-01-20 13:26:24 -08001020 def onosStop( self, nodeIp ):
kelvin8ec71442015-01-15 16:57:00 -08001021 """
andrewonlab2b30bd32014-10-09 16:48:55 -04001022 Calls onos command: 'onos-service [<node-ip>] stop'
andrewonlabe8e56fd2014-10-09 17:12:44 -04001023 This command is a remote management of the ONOS upstart daemon
kelvin8ec71442015-01-15 16:57:00 -08001024 """
andrewonlab2b30bd32014-10-09 16:48:55 -04001025 try:
kelvin8ec71442015-01-15 16:57:00 -08001026 self.handle.sendline( "" )
1027 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001028 self.handle.sendline( "onos-service " + str( nodeIp ) +
kelvin8ec71442015-01-15 16:57:00 -08001029 " stop" )
1030 i = self.handle.expect( [
andrewonlab2b30bd32014-10-09 16:48:55 -04001031 "stop/waiting",
Jon Hall61282e32015-03-19 11:34:11 -07001032 "Could not resolve hostname",
andrewonlab2b30bd32014-10-09 16:48:55 -04001033 "Unknown\sinstance",
kelvin8ec71442015-01-15 16:57:00 -08001034 pexpect.TIMEOUT ], timeout=60 )
andrewonlab2b30bd32014-10-09 16:48:55 -04001035
1036 if i == 0:
kelvin8ec71442015-01-15 16:57:00 -08001037 main.log.info( "ONOS service stopped" )
andrewonlab2b30bd32014-10-09 16:48:55 -04001038 return main.TRUE
1039 elif i == 1:
Jon Hall65844a32015-03-09 19:09:37 -07001040 main.log.info( "onosStop() Unknown ONOS instance specified: " +
kelvin-onlabd3b64892015-01-20 13:26:24 -08001041 str( nodeIp ) )
andrewonlab2b30bd32014-10-09 16:48:55 -04001042 return main.FALSE
Jon Hall61282e32015-03-19 11:34:11 -07001043 elif i == 2:
1044 main.log.warn( "ONOS wasn't running" )
1045 return main.TRUE
andrewonlab2b30bd32014-10-09 16:48:55 -04001046 else:
kelvin8ec71442015-01-15 16:57:00 -08001047 main.log.error( "ONOS service failed to stop" )
andrewonlab2b30bd32014-10-09 16:48:55 -04001048 return main.FALSE
1049
1050 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001051 main.log.error( self.name + ": EOF exception found" )
1052 main.log.error( self.name + ": " + self.handle.before )
andrewonlab2b30bd32014-10-09 16:48:55 -04001053 main.cleanup()
1054 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001055 except Exception:
1056 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab2b30bd32014-10-09 16:48:55 -04001057 main.cleanup()
1058 main.exit()
kelvin8ec71442015-01-15 16:57:00 -08001059
kelvin-onlabd3b64892015-01-20 13:26:24 -08001060 def onosUninstall( self, nodeIp="" ):
kelvin8ec71442015-01-15 16:57:00 -08001061 """
andrewonlabc8d47972014-10-09 16:52:36 -04001062 Calls the command: 'onos-uninstall'
kelvin8ec71442015-01-15 16:57:00 -08001063 Uninstalls ONOS from the designated cell machine, stopping
andrewonlabe8e56fd2014-10-09 17:12:44 -04001064 if needed
kelvin8ec71442015-01-15 16:57:00 -08001065 """
andrewonlabc8d47972014-10-09 16:52:36 -04001066 try:
kelvin8ec71442015-01-15 16:57:00 -08001067 self.handle.sendline( "" )
pingping-lin763ee042015-05-20 17:45:30 -07001068 self.handle.expect( "\$", timeout=60 )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001069 self.handle.sendline( "onos-uninstall " + str( nodeIp ) )
kelvin8ec71442015-01-15 16:57:00 -08001070 self.handle.expect( "\$" )
andrewonlabc8d47972014-10-09 16:52:36 -04001071
kelvin-onlabd3b64892015-01-20 13:26:24 -08001072 main.log.info( "ONOS " + nodeIp + " was uninstalled" )
andrewonlab9dfd2082014-11-13 17:44:03 -05001073
kelvin8ec71442015-01-15 16:57:00 -08001074 # onos-uninstall command does not return any text
andrewonlabc8d47972014-10-09 16:52:36 -04001075 return main.TRUE
1076
pingping-lin763ee042015-05-20 17:45:30 -07001077 except pexpect.TIMEOUT:
1078 main.log.exception( self.name + ": Timeout in onosUninstall" )
1079 return main.FALSE
andrewonlabc8d47972014-10-09 16:52:36 -04001080 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001081 main.log.error( self.name + ": EOF exception found" )
1082 main.log.error( self.name + ": " + self.handle.before )
andrewonlabc8d47972014-10-09 16:52:36 -04001083 main.cleanup()
1084 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001085 except Exception:
1086 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabc8d47972014-10-09 16:52:36 -04001087 main.cleanup()
1088 main.exit()
andrewonlab2b30bd32014-10-09 16:48:55 -04001089
kelvin-onlabd3b64892015-01-20 13:26:24 -08001090 def onosDie( self, nodeIp ):
kelvin8ec71442015-01-15 16:57:00 -08001091 """
andrewonlabaedc8332014-12-04 12:43:03 -05001092 Issues the command 'onos-die <node-ip>'
1093 This command calls onos-kill and also stops the node
kelvin8ec71442015-01-15 16:57:00 -08001094 """
andrewonlabaedc8332014-12-04 12:43:03 -05001095 try:
kelvin8ec71442015-01-15 16:57:00 -08001096 self.handle.sendline( "" )
1097 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001098 cmdStr = "onos-kill " + str( nodeIp )
1099 self.handle.sendline( cmdStr )
kelvin8ec71442015-01-15 16:57:00 -08001100 i = self.handle.expect( [
andrewonlabaedc8332014-12-04 12:43:03 -05001101 "Killing\sONOS",
1102 "ONOS\sprocess\sis\snot\srunning",
kelvin8ec71442015-01-15 16:57:00 -08001103 pexpect.TIMEOUT ], timeout=20 )
andrewonlabaedc8332014-12-04 12:43:03 -05001104 if i == 0:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001105 main.log.info( "ONOS instance " + str( nodeIp ) +
kelvin8ec71442015-01-15 16:57:00 -08001106 " was killed and stopped" )
andrewonlabaedc8332014-12-04 12:43:03 -05001107 return main.TRUE
1108 elif i == 1:
kelvin8ec71442015-01-15 16:57:00 -08001109 main.log.info( "ONOS process was not running" )
andrewonlabaedc8332014-12-04 12:43:03 -05001110 return main.FALSE
1111 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001112 main.log.error( self.name + ": EOF exception found" )
1113 main.log.error( self.name + ": " + self.handle.before )
andrewonlabaedc8332014-12-04 12:43:03 -05001114 main.cleanup()
1115 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001116 except Exception:
1117 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabaedc8332014-12-04 12:43:03 -05001118 main.cleanup()
1119 main.exit()
1120
kelvin-onlabd3b64892015-01-20 13:26:24 -08001121 def onosKill( self, nodeIp ):
kelvin8ec71442015-01-15 16:57:00 -08001122 """
andrewonlabe8e56fd2014-10-09 17:12:44 -04001123 Calls the command: 'onos-kill [<node-ip>]'
1124 "Remotely, and unceremoniously kills the ONOS instance running on
1125 the specified cell machine" - Tom V
kelvin8ec71442015-01-15 16:57:00 -08001126 """
andrewonlabe8e56fd2014-10-09 17:12:44 -04001127 try:
kelvin8ec71442015-01-15 16:57:00 -08001128 self.handle.sendline( "" )
1129 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001130 self.handle.sendline( "onos-kill " + str( nodeIp ) )
kelvin8ec71442015-01-15 16:57:00 -08001131 i = self.handle.expect( [
andrewonlabe8e56fd2014-10-09 17:12:44 -04001132 "\$",
1133 "No\sroute\sto\shost",
1134 "password:",
kelvin8ec71442015-01-15 16:57:00 -08001135 pexpect.TIMEOUT ], timeout=20 )
1136
andrewonlabe8e56fd2014-10-09 17:12:44 -04001137 if i == 0:
kelvin8ec71442015-01-15 16:57:00 -08001138 main.log.info(
1139 "ONOS instance " + str(
kelvin-onlabd3b64892015-01-20 13:26:24 -08001140 nodeIp ) + " was killed" )
andrewonlabe8e56fd2014-10-09 17:12:44 -04001141 return main.TRUE
1142 elif i == 1:
kelvin8ec71442015-01-15 16:57:00 -08001143 main.log.info( "No route to host" )
andrewonlabe8e56fd2014-10-09 17:12:44 -04001144 return main.FALSE
1145 elif i == 2:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001146 main.log.info(
1147 "Passwordless login for host: " +
1148 str( nodeIp ) +
1149 " not configured" )
andrewonlabe8e56fd2014-10-09 17:12:44 -04001150 return main.FALSE
1151 else:
Jon Hallefbd9792015-03-05 16:11:36 -08001152 main.log.info( "ONOS instance was not killed" )
andrewonlabe8e56fd2014-10-09 17:12:44 -04001153 return main.FALSE
kelvin8ec71442015-01-15 16:57:00 -08001154
andrewonlabe8e56fd2014-10-09 17:12:44 -04001155 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001156 main.log.error( self.name + ": EOF exception found" )
1157 main.log.error( self.name + ": " + self.handle.before )
andrewonlabe8e56fd2014-10-09 17:12:44 -04001158 main.cleanup()
1159 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001160 except Exception:
1161 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabe8e56fd2014-10-09 17:12:44 -04001162 main.cleanup()
1163 main.exit()
1164
kelvin-onlabd3b64892015-01-20 13:26:24 -08001165 def onosRemoveRaftLogs( self ):
kelvin8ec71442015-01-15 16:57:00 -08001166 """
andrewonlab19fbdca2014-11-14 12:55:59 -05001167 Removes Raft / Copy cat files from ONOS to ensure
Jon Hallfcc88622014-11-25 13:09:54 -05001168 a cleaner environment.
1169
andrewonlab19fbdca2014-11-14 12:55:59 -05001170 Description:
Jon Hallfcc88622014-11-25 13:09:54 -05001171 Stops all ONOS defined in the cell,
andrewonlab19fbdca2014-11-14 12:55:59 -05001172 wipes the raft / copycat log files
kelvin8ec71442015-01-15 16:57:00 -08001173 """
andrewonlab19fbdca2014-11-14 12:55:59 -05001174 try:
kelvin8ec71442015-01-15 16:57:00 -08001175 self.handle.sendline( "" )
1176 self.handle.expect( "\$" )
1177 self.handle.sendline( "onos-remove-raft-logs" )
1178 # Sometimes this command hangs
1179 i = self.handle.expect( [ "\$", pexpect.TIMEOUT ],
1180 timeout=120 )
Jon Hallfcc88622014-11-25 13:09:54 -05001181 if i == 1:
kelvin8ec71442015-01-15 16:57:00 -08001182 i = self.handle.expect( [ "\$", pexpect.TIMEOUT ],
1183 timeout=120 )
Jon Hallfcc88622014-11-25 13:09:54 -05001184 if i == 1:
1185 return main.FALSE
shahshreya957feaa2015-03-23 16:08:29 -07001186 #self.handle.sendline( "" )
1187 #self.handle.expect( "\$" )
andrewonlab19fbdca2014-11-14 12:55:59 -05001188 return main.TRUE
1189
1190 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001191 main.log.error( self.name + ": EOF exception found" )
1192 main.log.error( self.name + ": " + self.handle.before )
andrewonlab19fbdca2014-11-14 12:55:59 -05001193 main.cleanup()
1194 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001195 except Exception:
1196 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab19fbdca2014-11-14 12:55:59 -05001197 main.cleanup()
1198 main.exit()
Jon Hallfcc88622014-11-25 13:09:54 -05001199
kelvin-onlabd3b64892015-01-20 13:26:24 -08001200 def onosStartNetwork( self, mntopo ):
kelvin8ec71442015-01-15 16:57:00 -08001201 """
1202 Calls the command 'onos-start-network [ <mininet-topo> ]
1203 "remotely starts the specified topology on the cell's
andrewonlab94282092014-10-10 13:00:11 -04001204 mininet machine against all controllers configured in the
kelvin8ec71442015-01-15 16:57:00 -08001205 cell."
andrewonlab94282092014-10-10 13:00:11 -04001206 * Specify mininet topology file name for mntopo
1207 * Topo files should be placed at:
1208 ~/<your-onos-directory>/tools/test/topos
kelvin8ec71442015-01-15 16:57:00 -08001209
andrewonlab94282092014-10-10 13:00:11 -04001210 NOTE: This function will take you to the mininet prompt
kelvin8ec71442015-01-15 16:57:00 -08001211 """
andrewonlab94282092014-10-10 13:00:11 -04001212 try:
1213 if not mntopo:
kelvin8ec71442015-01-15 16:57:00 -08001214 main.log.error( "You must specify a topo file to execute" )
andrewonlab94282092014-10-10 13:00:11 -04001215 return main.FALSE
andrewonlab94282092014-10-10 13:00:11 -04001216
kelvin8ec71442015-01-15 16:57:00 -08001217 mntopo = str( mntopo )
1218 self.handle.sendline( "" )
1219 self.handle.expect( "\$" )
andrewonlab94282092014-10-10 13:00:11 -04001220
kelvin8ec71442015-01-15 16:57:00 -08001221 self.handle.sendline( "onos-start-network " + mntopo )
1222 self.handle.expect( "mininet>" )
1223 main.log.info( "Network started, entered mininet prompt" )
1224
1225 # TODO: Think about whether return is necessary or not
andrewonlab94282092014-10-10 13:00:11 -04001226
1227 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001228 main.log.error( self.name + ": EOF exception found" )
1229 main.log.error( self.name + ": " + self.handle.before )
andrewonlab94282092014-10-10 13:00:11 -04001230 main.cleanup()
1231 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001232 except Exception:
1233 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab94282092014-10-10 13:00:11 -04001234 main.cleanup()
1235 main.exit()
1236
Cameron Franke9c94fb02015-01-21 10:20:20 -08001237 def isup(self, node = "", timeout = 120):
kelvin8ec71442015-01-15 16:57:00 -08001238 """
1239 Run's onos-wait-for-start which only returns once ONOS is at run
Cameron Franke9c94fb02015-01-21 10:20:20 -08001240 level 100(ready for use)
andrewonlab8d0d7d72014-10-09 16:33:15 -04001241
Jon Hall7993bfc2014-10-09 16:30:14 -04001242 Returns: main.TRUE if ONOS is running and main.FALSE on timeout
kelvin8ec71442015-01-15 16:57:00 -08001243 """
Jon Hall7993bfc2014-10-09 16:30:14 -04001244 try:
Cameron Franke9c94fb02015-01-21 10:20:20 -08001245 self.handle.sendline("onos-wait-for-start " + node )
1246 self.handle.expect("onos-wait-for-start")
kelvin8ec71442015-01-15 16:57:00 -08001247 # NOTE: this timeout is arbitrary"
Cameron Franke9c94fb02015-01-21 10:20:20 -08001248 i = self.handle.expect(["\$", pexpect.TIMEOUT], timeout)
Jon Hall7993bfc2014-10-09 16:30:14 -04001249 if i == 0:
kelvin8ec71442015-01-15 16:57:00 -08001250 main.log.info( self.name + ": " + node + " is up" )
Jon Hall7993bfc2014-10-09 16:30:14 -04001251 return main.TRUE
1252 elif i == 1:
kelvin8ec71442015-01-15 16:57:00 -08001253 # NOTE: since this function won't return until ONOS is ready,
Jon Hall7993bfc2014-10-09 16:30:14 -04001254 # we will kill it on timeout
kelvin8ec71442015-01-15 16:57:00 -08001255 main.log.error( "ONOS has not started yet" )
1256 self.handle.send( "\x03" ) # Control-C
1257 self.handle.expect( "\$" )
Jon Hall7993bfc2014-10-09 16:30:14 -04001258 return main.FALSE
1259 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001260 main.log.error( self.name + ": EOF exception found" )
1261 main.log.error( self.name + ": " + self.handle.before )
Jon Hall7993bfc2014-10-09 16:30:14 -04001262 main.cleanup()
1263 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001264 except Exception:
1265 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall7993bfc2014-10-09 16:30:14 -04001266 main.cleanup()
1267 main.exit()
andrewonlab05e362f2014-10-10 00:40:57 -04001268
kelvin-onlabd3b64892015-01-20 13:26:24 -08001269 def pushTestIntentsShell(
1270 self,
1271 dpidSrc,
1272 dpidDst,
1273 numIntents,
1274 dirFile,
1275 onosIp,
1276 numMult="",
1277 appId="",
1278 report=True,
1279 options="" ):
kelvin8ec71442015-01-15 16:57:00 -08001280 """
andrewonlabb66dfa12014-12-02 15:51:10 -05001281 Description:
kelvin8ec71442015-01-15 16:57:00 -08001282 Use the linux prompt to push test intents to
andrewonlabb66dfa12014-12-02 15:51:10 -05001283 better parallelize the results than the CLI
1284 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001285 * dpidSrc: specify source dpid
1286 * dpidDst: specify destination dpid
1287 * numIntents: specify number of intents to push
1288 * dirFile: specify directory and file name to save
andrewonlabb66dfa12014-12-02 15:51:10 -05001289 results
kelvin-onlabd3b64892015-01-20 13:26:24 -08001290 * onosIp: specify the IP of ONOS to install on
kelvin8ec71442015-01-15 16:57:00 -08001291 NOTE:
andrewonlabb66dfa12014-12-02 15:51:10 -05001292 You must invoke this command at linux shell prompt
kelvin8ec71442015-01-15 16:57:00 -08001293 """
1294 try:
1295 # Create the string to sendline
andrewonlabaedc8332014-12-04 12:43:03 -05001296 if options:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001297 baseCmd = "onos " + str( onosIp ) + " push-test-intents " +\
kelvin8ec71442015-01-15 16:57:00 -08001298 options + " "
andrewonlabaedc8332014-12-04 12:43:03 -05001299 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001300 baseCmd = "onos " + str( onosIp ) + " push-test-intents "
kelvin8ec71442015-01-15 16:57:00 -08001301
kelvin-onlabd3b64892015-01-20 13:26:24 -08001302 addDpid = baseCmd + str( dpidSrc ) + " " + str( dpidDst )
1303 if not numMult:
1304 addIntents = addDpid + " " + str( numIntents )
1305 elif numMult:
1306 addIntents = addDpid + " " + str( numIntents ) + " " +\
1307 str( numMult )
1308 if appId:
1309 addApp = addIntents + " " + str( appId )
andrewonlabb66dfa12014-12-02 15:51:10 -05001310 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001311 addApp = addIntents
andrewonlabb66dfa12014-12-02 15:51:10 -05001312
andrewonlabaedc8332014-12-04 12:43:03 -05001313 if report:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001314 sendCmd = addApp + " > " + str( dirFile ) + " &"
andrewonlabaedc8332014-12-04 12:43:03 -05001315 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001316 sendCmd = addApp + " &"
1317 main.log.info( "Send cmd: " + sendCmd )
andrewonlabb66dfa12014-12-02 15:51:10 -05001318
kelvin-onlabd3b64892015-01-20 13:26:24 -08001319 self.handle.sendline( sendCmd )
andrewonlabb66dfa12014-12-02 15:51:10 -05001320
1321 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001322 main.log.error( self.name + ": EOF exception found" )
1323 main.log.error( self.name + ": " + self.handle.before )
andrewonlabb66dfa12014-12-02 15:51:10 -05001324 main.cleanup()
1325 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001326 except Exception:
1327 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabb66dfa12014-12-02 15:51:10 -05001328 main.cleanup()
kelvin8ec71442015-01-15 16:57:00 -08001329 main.exit()
andrewonlab05e362f2014-10-10 00:40:57 -04001330
kelvin-onlabd3b64892015-01-20 13:26:24 -08001331 def getTopology( self, topologyOutput ):
kelvin8ec71442015-01-15 16:57:00 -08001332 """
Hari Krishnaef1bd4e2015-03-12 16:55:30 -07001333 Definition:
1334 Loads a json topology output
1335 Return:
1336 topology = current ONOS topology
kelvin8ec71442015-01-15 16:57:00 -08001337 """
Hari Krishnaef1bd4e2015-03-12 16:55:30 -07001338 import json
Jon Hall77f53ce2014-10-13 18:02:06 -04001339 try:
Hari Krishnaef1bd4e2015-03-12 16:55:30 -07001340 # either onos:topology or 'topology' will work in CLI
1341 topology = json.loads(topologyOutput)
1342 print topology
Jon Hall77f53ce2014-10-13 18:02:06 -04001343 return topology
1344 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001345 main.log.error( self.name + ": EOF exception found" )
1346 main.log.error( self.name + ": " + self.handle.before )
Jon Hall77f53ce2014-10-13 18:02:06 -04001347 main.cleanup()
1348 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001349 except Exception:
1350 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall77f53ce2014-10-13 18:02:06 -04001351 main.cleanup()
1352 main.exit()
1353
kelvin-onlabd3b64892015-01-20 13:26:24 -08001354 def checkStatus(
1355 self,
1356 topologyResult,
1357 numoswitch,
1358 numolink,
1359 logLevel="info" ):
kelvin8ec71442015-01-15 16:57:00 -08001360 """
Jon Hallefbd9792015-03-05 16:11:36 -08001361 Checks the number of switches & links that ONOS sees against the
kelvin8ec71442015-01-15 16:57:00 -08001362 supplied values. By default this will report to main.log, but the
Jon Hallefbd9792015-03-05 16:11:36 -08001363 log level can be specific.
kelvin8ec71442015-01-15 16:57:00 -08001364
Jon Hall77f53ce2014-10-13 18:02:06 -04001365 Params: ip = ip used for the onos cli
1366 numoswitch = expected number of switches
Jon Hallefbd9792015-03-05 16:11:36 -08001367 numolink = expected number of links
kelvin-onlabd3b64892015-01-20 13:26:24 -08001368 logLevel = level to log to.
1369 Currently accepts 'info', 'warn' and 'report'
Jon Hall77f53ce2014-10-13 18:02:06 -04001370
1371
kelvin-onlabd3b64892015-01-20 13:26:24 -08001372 logLevel can
Jon Hall77f53ce2014-10-13 18:02:06 -04001373
Jon Hallefbd9792015-03-05 16:11:36 -08001374 Returns: main.TRUE if the number of switches and links are correct,
1375 main.FALSE if the number of switches and links is incorrect,
Jon Hall77f53ce2014-10-13 18:02:06 -04001376 and main.ERROR otherwise
kelvin8ec71442015-01-15 16:57:00 -08001377 """
Jon Hall77f53ce2014-10-13 18:02:06 -04001378 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001379 topology = self.getTopology( topologyResult )
Jon Hall77f53ce2014-10-13 18:02:06 -04001380 if topology == {}:
1381 return main.ERROR
1382 output = ""
kelvin8ec71442015-01-15 16:57:00 -08001383 # Is the number of switches is what we expected
shahshreya234a1682015-05-27 15:41:56 -07001384 devices = topology.get( 'devices', False )
1385 links = topology.get( 'links', False )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001386 if not devices or not links:
Jon Hall77f53ce2014-10-13 18:02:06 -04001387 return main.ERROR
kelvin-onlabd3b64892015-01-20 13:26:24 -08001388 switchCheck = ( int( devices ) == int( numoswitch ) )
kelvin8ec71442015-01-15 16:57:00 -08001389 # Is the number of links is what we expected
kelvin-onlabd3b64892015-01-20 13:26:24 -08001390 linkCheck = ( int( links ) == int( numolink ) )
Jon Hallefbd9792015-03-05 16:11:36 -08001391 if switchCheck and linkCheck:
kelvin8ec71442015-01-15 16:57:00 -08001392 # We expected the correct numbers
Jon Hall77f53ce2014-10-13 18:02:06 -04001393 output = output + "The number of links and switches match "\
kelvin8ec71442015-01-15 16:57:00 -08001394 + "what was expected"
Jon Hall77f53ce2014-10-13 18:02:06 -04001395 result = main.TRUE
1396 else:
1397 output = output + \
Jon Hall274b6642015-02-17 11:57:17 -08001398 "The number of links and switches does not match " + \
1399 "what was expected"
Jon Hall77f53ce2014-10-13 18:02:06 -04001400 result = main.FALSE
Jon Hallefbd9792015-03-05 16:11:36 -08001401 output = output + "\n ONOS sees %i devices" % int( devices )
1402 output = output + " (%i expected) " % int( numoswitch )
Jon Hall274b6642015-02-17 11:57:17 -08001403 output = output + "and %i links " % int( links )
1404 output = output + "(%i expected)" % int( numolink )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001405 if logLevel == "report":
kelvin8ec71442015-01-15 16:57:00 -08001406 main.log.report( output )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001407 elif logLevel == "warn":
kelvin8ec71442015-01-15 16:57:00 -08001408 main.log.warn( output )
Jon Hall77f53ce2014-10-13 18:02:06 -04001409 else:
kelvin8ec71442015-01-15 16:57:00 -08001410 main.log.info( output )
1411 return result
Jon Hall77f53ce2014-10-13 18:02:06 -04001412 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001413 main.log.error( self.name + ": EOF exception found" )
1414 main.log.error( self.name + ": " + self.handle.before )
Jon Hall77f53ce2014-10-13 18:02:06 -04001415 main.cleanup()
1416 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001417 except Exception:
1418 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall77f53ce2014-10-13 18:02:06 -04001419 main.cleanup()
1420 main.exit()
andrewonlabba44bcf2014-10-16 16:54:41 -04001421
kelvin-onlabd3b64892015-01-20 13:26:24 -08001422 def tsharkPcap( self, interface, dirFile ):
kelvin8ec71442015-01-15 16:57:00 -08001423 """
andrewonlab970399c2014-11-07 13:09:32 -05001424 Capture all packet activity and store in specified
1425 directory/file
1426
1427 Required:
1428 * interface: interface to capture
1429 * dir: directory/filename to store pcap
kelvin8ec71442015-01-15 16:57:00 -08001430 """
Jon Hallfebb1c72015-03-05 13:30:09 -08001431 try:
1432 self.handle.sendline( "" )
1433 self.handle.expect( "\$" )
andrewonlab970399c2014-11-07 13:09:32 -05001434
Jon Hallfebb1c72015-03-05 13:30:09 -08001435 self.handle.sendline( "tshark -i " + str( interface ) +
1436 " -t e -w " + str( dirFile ) + " &" )
1437 self.handle.sendline( "\r" )
1438 self.handle.expect( "Capturing on" )
1439 self.handle.sendline( "\r" )
1440 self.handle.expect( "\$" )
andrewonlab970399c2014-11-07 13:09:32 -05001441
Jon Hallfebb1c72015-03-05 13:30:09 -08001442 main.log.info( "Tshark started capturing files on " +
1443 str( interface ) + " and saving to directory: " +
1444 str( dirFile ) )
1445 except pexpect.EOF:
1446 main.log.error( self.name + ": EOF exception found" )
1447 main.log.error( self.name + ": " + self.handle.before )
1448 main.cleanup()
1449 main.exit()
1450 except Exception:
1451 main.log.exception( self.name + ": Uncaught exception!" )
1452 main.cleanup()
1453 main.exit()
Shreya Shaha73aaad2014-10-27 18:03:09 -04001454
kelvin-onlabd3b64892015-01-20 13:26:24 -08001455 def runOnosTopoCfg( self, instanceName, jsonFile ):
kelvin8ec71442015-01-15 16:57:00 -08001456 """
kelvin-onlabd3b64892015-01-20 13:26:24 -08001457 On ONOS bench, run this command:
Jon Halle94919c2015-03-23 11:42:57 -07001458 {ONOS_HOME}/tools/test/bin/onos-topo-cfg $OC1 filename
kelvin-onlabd3b64892015-01-20 13:26:24 -08001459 which starts the rest and copies
1460 the json file to the onos instance
kelvin8ec71442015-01-15 16:57:00 -08001461 """
shahshreyae6c7cf42014-11-26 16:39:01 -08001462 try:
kelvin8ec71442015-01-15 16:57:00 -08001463 self.handle.sendline( "" )
1464 self.handle.expect( "\$" )
Jon Halle94919c2015-03-23 11:42:57 -07001465 self.handle.sendline( "cd " + self.home + "/tools/test/bin" )
kelvin8ec71442015-01-15 16:57:00 -08001466 self.handle.expect( "/bin$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001467 cmd = "./onos-topo-cfg " + instanceName + " " + jsonFile
shahshreyae6c7cf42014-11-26 16:39:01 -08001468 print "cmd = ", cmd
kelvin8ec71442015-01-15 16:57:00 -08001469 self.handle.sendline( cmd )
1470 self.handle.expect( "\$" )
1471 self.handle.sendline( "cd ~" )
1472 self.handle.expect( "\$" )
shahshreyae6c7cf42014-11-26 16:39:01 -08001473 return main.TRUE
Jon Hallfebb1c72015-03-05 13:30:09 -08001474 except pexpect.EOF:
1475 main.log.error( self.name + ": EOF exception found" )
1476 main.log.error( self.name + ": " + self.handle.before )
1477 main.cleanup()
1478 main.exit()
1479 except Exception:
1480 main.log.exception( self.name + ": Uncaught exception!" )
1481 main.cleanup()
1482 main.exit()
kelvin8ec71442015-01-15 16:57:00 -08001483
jenkins1e99e7b2015-04-02 18:15:39 -07001484 def tsharkGrep( self, grep, directory, interface='eth0', grepOptions='' ):
kelvin8ec71442015-01-15 16:57:00 -08001485 """
andrewonlabba44bcf2014-10-16 16:54:41 -04001486 Required:
kelvin8ec71442015-01-15 16:57:00 -08001487 * grep string
andrewonlabba44bcf2014-10-16 16:54:41 -04001488 * directory to store results
1489 Optional:
1490 * interface - default: eth0
jenkins1e99e7b2015-04-02 18:15:39 -07001491 * grepOptions - options for grep
andrewonlabba44bcf2014-10-16 16:54:41 -04001492 Description:
1493 Uses tshark command to grep specific group of packets
1494 and stores the results to specified directory.
kelvin8ec71442015-01-15 16:57:00 -08001495 The timestamp is hardcoded to be in epoch
1496 """
Jon Hallfebb1c72015-03-05 13:30:09 -08001497 try:
1498 self.handle.sendline( "" )
1499 self.handle.expect( "\$" )
1500 self.handle.sendline( "" )
jenkins1e99e7b2015-04-02 18:15:39 -07001501 if grepOptions:
1502 grepStr = "grep "+str(grepOptions)
1503 else:
1504 grepStr = "grep"
1505
Jon Hallfebb1c72015-03-05 13:30:09 -08001506 self.handle.sendline(
1507 "tshark -i " +
1508 str( interface ) +
jenkins1e99e7b2015-04-02 18:15:39 -07001509 " -t e | " +
1510 grepStr + " --line-buffered \"" +
Jon Hallfebb1c72015-03-05 13:30:09 -08001511 str(grep) +
1512 "\" >" +
1513 directory +
1514 " &" )
1515 self.handle.sendline( "\r" )
1516 self.handle.expect( "Capturing on" )
1517 self.handle.sendline( "\r" )
1518 self.handle.expect( "\$" )
1519 except pexpect.EOF:
1520 main.log.error( self.name + ": EOF exception found" )
1521 main.log.error( self.name + ": " + self.handle.before )
1522 main.cleanup()
1523 main.exit()
1524 except Exception:
1525 main.log.exception( self.name + ": Uncaught exception!" )
1526 main.cleanup()
1527 main.exit()
1528
kelvin-onlabd3b64892015-01-20 13:26:24 -08001529 def tsharkStop( self ):
kelvin8ec71442015-01-15 16:57:00 -08001530 """
andrewonlabba44bcf2014-10-16 16:54:41 -04001531 Removes wireshark files from /tmp and kills all tshark processes
kelvin8ec71442015-01-15 16:57:00 -08001532 """
1533 # Remove all pcap from previous captures
Jon Hallfebb1c72015-03-05 13:30:09 -08001534 try:
1535 self.execute( cmd="sudo rm /tmp/wireshark*" )
1536 self.handle.sendline( "" )
Jon Hallefbd9792015-03-05 16:11:36 -08001537 self.handle.sendline( "sudo kill -9 `ps -ef | grep \"tshark -i\"" +
1538 " | grep -v grep | awk '{print $2}'`" )
Jon Hallfebb1c72015-03-05 13:30:09 -08001539 self.handle.sendline( "" )
1540 main.log.info( "Tshark stopped" )
1541 except pexpect.EOF:
1542 main.log.error( self.name + ": EOF exception found" )
1543 main.log.error( self.name + ": " + self.handle.before )
1544 main.cleanup()
1545 main.exit()
1546 except Exception:
1547 main.log.exception( self.name + ": Uncaught exception!" )
1548 main.cleanup()
1549 main.exit()
1550
kelvin8ec71442015-01-15 16:57:00 -08001551 def ptpd( self, args ):
1552 """
andrewonlab0c38a4a2014-10-28 18:35:35 -04001553 Initiate ptp with user-specified args.
1554 Required:
1555 * args: specify string of args after command
1556 'sudo ptpd'
kelvin8ec71442015-01-15 16:57:00 -08001557 """
andrewonlab0c38a4a2014-10-28 18:35:35 -04001558 try:
kelvin8ec71442015-01-15 16:57:00 -08001559 self.handle.sendline( "sudo ptpd " + str( args ) )
1560 i = self.handle.expect( [
andrewonlab0c38a4a2014-10-28 18:35:35 -04001561 "Multiple",
1562 "Error",
kelvin8ec71442015-01-15 16:57:00 -08001563 "\$" ] )
1564 self.handle.expect( "\$" )
andrewonlabba44bcf2014-10-16 16:54:41 -04001565
andrewonlab0c38a4a2014-10-28 18:35:35 -04001566 if i == 0:
1567 handle = self.handle.before
kelvin8ec71442015-01-15 16:57:00 -08001568 main.log.info( "ptpd returned an error: " +
1569 str( handle ) )
andrewonlab0c38a4a2014-10-28 18:35:35 -04001570 return handle
1571 elif i == 1:
1572 handle = self.handle.before
kelvin8ec71442015-01-15 16:57:00 -08001573 main.log.error( "ptpd returned an error: " +
1574 str( handle ) )
andrewonlab0c38a4a2014-10-28 18:35:35 -04001575 return handle
1576 else:
1577 return main.TRUE
kelvin8ec71442015-01-15 16:57:00 -08001578
andrewonlab0c38a4a2014-10-28 18:35:35 -04001579 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001580 main.log.error( self.name + ": EOF exception found" )
1581 main.log.error( self.name + ": " + self.handle.before )
andrewonlab0c38a4a2014-10-28 18:35:35 -04001582 main.cleanup()
1583 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001584 except Exception:
1585 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab0c38a4a2014-10-28 18:35:35 -04001586 main.cleanup()
1587 main.exit()
andrewonlabba44bcf2014-10-16 16:54:41 -04001588
kelvin-onlabd3b64892015-01-20 13:26:24 -08001589 def cpLogsToDir( self, logToCopy,
Jon Hallefbd9792015-03-05 16:11:36 -08001590 destDir, copyFileName="" ):
kelvin8ec71442015-01-15 16:57:00 -08001591 """
1592 Copies logs to a desired directory.
andrewonlab5d7a8f32014-11-10 13:07:56 -05001593 Current implementation of ONOS deletes its karaf
1594 logs on every iteration. For debugging purposes,
kelvin8ec71442015-01-15 16:57:00 -08001595 you may want to use this function to capture
1596 certain karaf logs. ( or any other logs if needed )
andrewonlab5d7a8f32014-11-10 13:07:56 -05001597 Localtime will be attached to the filename
1598
1599 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001600 * logToCopy: specify directory and log name to
andrewonlab5d7a8f32014-11-10 13:07:56 -05001601 copy.
kelvin8ec71442015-01-15 16:57:00 -08001602 ex ) /opt/onos/log/karaf.log.1
kelvin-onlabd3b64892015-01-20 13:26:24 -08001603 For copying multiple files, leave copyFileName
1604 empty and only specify destDir -
kelvin8ec71442015-01-15 16:57:00 -08001605 ex ) /opt/onos/log/karaf*
kelvin-onlabd3b64892015-01-20 13:26:24 -08001606 * destDir: specify directory to copy to.
kelvin8ec71442015-01-15 16:57:00 -08001607 ex ) /tmp/
1608 Optional:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001609 * copyFileName: If you want to rename the log
1610 file, specify copyFileName. This will not work
andrewonlab5d7a8f32014-11-10 13:07:56 -05001611 with multiple file copying
kelvin8ec71442015-01-15 16:57:00 -08001612 """
andrewonlab5d7a8f32014-11-10 13:07:56 -05001613 try:
kelvin8ec71442015-01-15 16:57:00 -08001614 localtime = time.strftime( '%x %X' )
1615 localtime = localtime.replace( "/", "" )
1616 localtime = localtime.replace( " ", "_" )
1617 localtime = localtime.replace( ":", "" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001618 if destDir[ -1: ] != "/":
1619 destDir += "/"
andrewonlab5d7a8f32014-11-10 13:07:56 -05001620
kelvin-onlabd3b64892015-01-20 13:26:24 -08001621 if copyFileName:
Jon Hallfebb1c72015-03-05 13:30:09 -08001622 self.handle.sendline( "cp " + str( logToCopy ) + " " +
1623 str( destDir ) + str( copyFileName ) +
1624 localtime )
kelvin8ec71442015-01-15 16:57:00 -08001625 self.handle.expect( "cp" )
1626 self.handle.expect( "\$" )
andrewonlab5d7a8f32014-11-10 13:07:56 -05001627 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001628 self.handle.sendline( "cp " + str( logToCopy ) +
1629 " " + str( destDir ) )
kelvin8ec71442015-01-15 16:57:00 -08001630 self.handle.expect( "cp" )
1631 self.handle.expect( "\$" )
andrewonlab5d7a8f32014-11-10 13:07:56 -05001632
kelvin8ec71442015-01-15 16:57:00 -08001633 return self.handle.before
1634
1635 except pexpect.EOF:
1636 main.log.error( "Copying files failed" )
1637 main.log.error( self.name + ": EOF exception found" )
1638 main.log.error( self.name + ": " + self.handle.before )
Jon Hallfebb1c72015-03-05 13:30:09 -08001639 except Exception:
1640 main.log.exception( "Copying files failed" )
1641
Jon Hall16b72c42015-05-20 10:23:36 -07001642 def checkLogs( self, onosIp, restart=False):
kelvin8ec71442015-01-15 16:57:00 -08001643 """
Jon Hall94fd0472014-12-08 11:52:42 -08001644 runs onos-check-logs on the given onos node
Jon Hall80daded2015-05-27 16:07:00 -07001645 If restart is True, use the old version of onos-check-logs which
1646 does not print the full stacktrace, but shows the entire log file,
1647 including across restarts
Jon Hall94fd0472014-12-08 11:52:42 -08001648 returns the response
kelvin8ec71442015-01-15 16:57:00 -08001649 """
Jon Hall94fd0472014-12-08 11:52:42 -08001650 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001651 cmd = "onos-check-logs " + str( onosIp )
Jon Hall16b72c42015-05-20 10:23:36 -07001652 if restart:
1653 cmd += " old"
kelvin8ec71442015-01-15 16:57:00 -08001654 self.handle.sendline( cmd )
1655 self.handle.expect( cmd )
1656 self.handle.expect( "\$" )
Jon Hall94fd0472014-12-08 11:52:42 -08001657 response = self.handle.before
1658 return response
1659 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001660 main.log.error( "Lost ssh connection" )
1661 main.log.error( self.name + ": EOF exception found" )
1662 main.log.error( self.name + ": " + self.handle.before )
Jon Hallfebb1c72015-03-05 13:30:09 -08001663 except Exception:
1664 main.log.exception( self.name + ": Uncaught exception!" )
1665 main.cleanup()
1666 main.exit()
Jon Hall94fd0472014-12-08 11:52:42 -08001667
kelvin-onlabd3b64892015-01-20 13:26:24 -08001668 def onosStatus( self, node="" ):
kelvin8ec71442015-01-15 16:57:00 -08001669 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001670 Calls onos command: 'onos-service [<node-ip>] status'
kelvin8ec71442015-01-15 16:57:00 -08001671 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001672 try:
kelvin8ec71442015-01-15 16:57:00 -08001673 self.handle.sendline( "" )
1674 self.handle.expect( "\$" )
1675 self.handle.sendline( "onos-service " + str( node ) +
1676 " status" )
1677 i = self.handle.expect( [
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001678 "start/running",
1679 "stop/waiting",
kelvin8ec71442015-01-15 16:57:00 -08001680 pexpect.TIMEOUT ], timeout=120 )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001681
1682 if i == 0:
kelvin8ec71442015-01-15 16:57:00 -08001683 main.log.info( "ONOS is running" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001684 return main.TRUE
1685 elif i == 1:
kelvin8ec71442015-01-15 16:57:00 -08001686 main.log.info( "ONOS is stopped" )
kelvin8ec71442015-01-15 16:57:00 -08001687 main.log.error( "ONOS service failed to check the status" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001688 main.cleanup()
1689 main.exit()
1690 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001691 main.log.error( self.name + ": EOF exception found" )
1692 main.log.error( self.name + ": " + self.handle.before )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001693 main.cleanup()
1694 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001695 except Exception:
1696 main.log.exception( self.name + ": Uncaught exception!" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08001697 main.cleanup()
1698 main.exit()
Jon Hall21270ac2015-02-16 17:59:55 -08001699
Jon Hall63604932015-02-26 17:09:50 -08001700 def setIpTables( self, ip, port='', action='add', packet_type='',
1701 direction='INPUT', rule='DROP', states=True ):
Jon Hallefbd9792015-03-05 16:11:36 -08001702 """
Jon Hall21270ac2015-02-16 17:59:55 -08001703 Description:
1704 add or remove iptables rule to DROP (default) packets from
1705 specific IP and PORT
1706 Usage:
1707 * specify action ('add' or 'remove')
1708 when removing, pass in the same argument as you would add. It will
1709 delete that specific rule.
1710 * specify the ip to block
1711 * specify the destination port to block (defaults to all ports)
1712 * optional packet type to block (default tcp)
1713 * optional iptables rule (default DROP)
1714 * optional direction to block (default 'INPUT')
Jon Hall63604932015-02-26 17:09:50 -08001715 * States boolean toggles adding all supported tcp states to the
1716 firewall rule
Jon Hall21270ac2015-02-16 17:59:55 -08001717 Returns:
1718 main.TRUE on success or
1719 main.FALSE if given invalid input or
1720 main.ERROR if there is an error in response from iptables
1721 WARNING:
1722 * This function uses root privilege iptables command which may result
1723 in unwanted network errors. USE WITH CAUTION
Jon Hallefbd9792015-03-05 16:11:36 -08001724 """
Jon Hall21270ac2015-02-16 17:59:55 -08001725 import time
1726
1727 # NOTE*********
1728 # The strict checking methods of this driver function is intentional
1729 # to discourage any misuse or error of iptables, which can cause
1730 # severe network errors
1731 # *************
1732
1733 # NOTE: Sleep needed to give some time for rule to be added and
1734 # registered to the instance. If you are calling this function
1735 # multiple times this sleep will prevent any errors.
1736 # DO NOT REMOVE
Jon Hall63604932015-02-26 17:09:50 -08001737 # time.sleep( 5 )
Jon Hall21270ac2015-02-16 17:59:55 -08001738 try:
1739 # input validation
1740 action_type = action.lower()
1741 rule = rule.upper()
1742 direction = direction.upper()
1743 if action_type != 'add' and action_type != 'remove':
1744 main.log.error( "Invalid action type. Use 'add' or "
1745 "'remove' table rule" )
1746 if rule != 'DROP' and rule != 'ACCEPT' and rule != 'LOG':
1747 # NOTE Currently only supports rules DROP, ACCEPT, and LOG
1748 main.log.error( "Invalid rule. Valid rules are 'DROP' or "
1749 "'ACCEPT' or 'LOG' only." )
1750 if direction != 'INPUT' and direction != 'OUTPUT':
1751 # NOTE currently only supports rules INPUT and OUPTUT
1752 main.log.error( "Invalid rule. Valid directions are"
1753 " 'OUTPUT' or 'INPUT'" )
1754 return main.FALSE
1755 return main.FALSE
1756 return main.FALSE
1757 if action_type == 'add':
1758 # -A is the 'append' action of iptables
1759 actionFlag = '-A'
1760 elif action_type == 'remove':
1761 # -D is the 'delete' rule of iptables
1762 actionFlag = '-D'
1763 self.handle.sendline( "" )
1764 self.handle.expect( "\$" )
1765 cmd = "sudo iptables " + actionFlag + " " +\
1766 direction +\
Jon Hall21270ac2015-02-16 17:59:55 -08001767 " -s " + str( ip )
Jon Hall63604932015-02-26 17:09:50 -08001768 # " -p " + str( packet_type ) +\
1769 if packet_type:
1770 cmd += " -p " + str( packet_type )
Jon Hall21270ac2015-02-16 17:59:55 -08001771 if port:
1772 cmd += " --dport " + str( port )
Jon Hall63604932015-02-26 17:09:50 -08001773 if states:
1774 cmd += " -m state --state="
1775 #FIXME- Allow user to configure which states to block
1776 cmd += "INVALID,ESTABLISHED,NEW,RELATED,UNTRACKED"
Jon Hall21270ac2015-02-16 17:59:55 -08001777 cmd += " -j " + str( rule )
1778
1779 self.handle.sendline( cmd )
1780 self.handle.expect( "\$" )
1781 main.log.warn( self.handle.before )
1782
1783 info_string = "On " + str( self.name )
1784 info_string += " " + str( action_type )
1785 info_string += " iptable rule [ "
1786 info_string += " IP: " + str( ip )
1787 info_string += " Port: " + str( port )
1788 info_string += " Rule: " + str( rule )
1789 info_string += " Direction: " + str( direction ) + " ]"
1790 main.log.info( info_string )
1791 return main.TRUE
1792 except pexpect.TIMEOUT:
1793 main.log.exception( self.name + ": Timeout exception in "
1794 "setIpTables function" )
1795 return main.ERROR
1796 except pexpect.EOF:
1797 main.log.error( self.name + ": EOF exception found" )
1798 main.log.error( self.name + ": " + self.handle.before )
1799 main.cleanup()
1800 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001801 except Exception:
1802 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall21270ac2015-02-16 17:59:55 -08001803 main.cleanup()
1804 main.exit()
1805
Jon Hall0468b042015-02-19 19:08:21 -08001806 def detailed_status(self, log_filename):
Jon Hallefbd9792015-03-05 16:11:36 -08001807 """
Jon Hall0468b042015-02-19 19:08:21 -08001808 This method is used by STS to check the status of the controller
1809 Reports RUNNING, STARTING, STOPPED, FROZEN, ERROR (and reason)
Jon Hallefbd9792015-03-05 16:11:36 -08001810 """
Jon Hall0468b042015-02-19 19:08:21 -08001811 import re
1812 try:
1813 self.handle.sendline( "" )
1814 self.handle.expect( "\$" )
1815 self.handle.sendline( "cd " + self.home )
1816 self.handle.expect( "\$" )
1817 self.handle.sendline( "service onos status" )
1818 self.handle.expect( "\$" )
1819 response = self.handle.before
1820 if re.search( "onos start/running", response ):
1821 # onos start/running, process 10457
1822 return 'RUNNING'
1823 # FIXME: Implement this case
1824 # elif re.search( pattern, response ):
1825 # return 'STARTING'
1826 elif re.search( "onos stop/", response ):
1827 # onos stop/waiting
1828 # FIXME handle this differently?: onos stop/pre-stop
1829 return 'STOPPED'
1830 # FIXME: Implement this case
1831 # elif re.search( pattern, response ):
1832 # return 'FROZEN'
1833 else:
1834 main.log.warn( self.name +
Jon Hallefbd9792015-03-05 16:11:36 -08001835 " WARNING: status received unknown response" )
Jon Hall0468b042015-02-19 19:08:21 -08001836 main.log.warn( response )
1837 return 'ERROR', "Unknown response: %s" % response
1838 except pexpect.TIMEOUT:
1839 main.log.exception( self.name + ": Timeout exception in "
1840 "setIpTables function" )
1841 return 'ERROR', "Pexpect Timeout"
1842 except pexpect.EOF:
1843 main.log.error( self.name + ": EOF exception found" )
1844 main.log.error( self.name + ": " + self.handle.before )
1845 main.cleanup()
1846 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001847 except Exception:
1848 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall0468b042015-02-19 19:08:21 -08001849 main.cleanup()
1850 main.exit()
1851
andrew@onlab.us3b087132015-03-11 15:00:08 -07001852 def createLinkGraphFile( self, benchIp, ONOSIpList, deviceCount):
1853 '''
1854 Create/formats the LinkGraph.cfg file based on arguments
1855 -only creates a linear topology and connects islands
1856 -evenly distributes devices
1857 -must be called by ONOSbench
1858
1859 ONOSIpList - list of all of the node IPs to be used
1860
1861 deviceCount - number of switches to be assigned
1862 '''
1863 main.log.step("Creating link graph configuration file." )
1864 linkGraphPath = self.home + "/tools/package/etc/linkGraph.cfg"
1865 tempFile = "/tmp/linkGraph.cfg"
1866
1867 linkGraph = open(tempFile, 'w+')
1868 linkGraph.write("# NullLinkProvider topology description (config file).\n")
1869 linkGraph.write("# The NodeId is only added if the destination is another node's device.\n")
1870 linkGraph.write("# Bugs: Comments cannot be appended to a line to be read.\n")
1871
1872 clusterCount = len(ONOSIpList)
1873
1874 if type(deviceCount) is int or type(deviceCount) is str:
1875 deviceCount = int(deviceCount)
1876 switchList = [0]*(clusterCount+1)
1877 baselineSwitchCount = deviceCount/clusterCount
1878
1879 for node in range(1, clusterCount + 1):
1880 switchList[node] = baselineSwitchCount
1881
1882 for node in range(1, (deviceCount%clusterCount)+1):
1883 switchList[node] += 1
1884
1885 if type(deviceCount) is list:
1886 main.log.info("Using provided device distribution")
1887 switchList = [0]
1888 for i in deviceCount:
1889 switchList.append(int(i))
1890
1891 tempList = ['0']
1892 tempList.extend(ONOSIpList)
1893 ONOSIpList = tempList
1894
1895 myPort = 6
1896 lastSwitch = 0
1897 for node in range(1, clusterCount+1):
1898 if switchList[node] == 0:
1899 continue
1900
1901 linkGraph.write("graph " + ONOSIpList[node] + " {\n")
1902
1903 if node > 1:
1904 #connect to last device on previous node
1905 line = ("\t0:5 -> " + str(lastSwitch) + ":6:" + lastIp + "\n") #ONOSIpList[node-1]
1906 linkGraph.write(line)
1907
1908 lastSwitch = 0
1909 for switch in range (0, switchList[node]-1):
1910 line = ""
1911 line = ("\t" + str(switch) + ":" + str(myPort))
1912 line += " -- "
1913 line += (str(switch+1) + ":" + str(myPort-1) + "\n")
1914 linkGraph.write(line)
1915 lastSwitch = switch+1
1916 lastIp = ONOSIpList[node]
1917
1918 #lastSwitch += 1
1919 if node < (clusterCount):
1920 #connect to first device on the next node
1921 line = ("\t" + str(lastSwitch) + ":6 -> 0:5:" + ONOSIpList[node+1] + "\n")
1922 linkGraph.write(line)
1923
1924 linkGraph.write("}\n")
1925 linkGraph.close()
1926
1927 #SCP
kelvin-onlabc2b79102015-07-14 11:41:20 -07001928 os.system( "scp " + tempFile + " " + self.user_name + "@" + benchIp + ":" + linkGraphPath)
andrew@onlab.us3b087132015-03-11 15:00:08 -07001929 main.log.info("linkGraph.cfg creation complete")
1930
cameron@onlab.us75900962015-03-30 13:22:49 -07001931 def configNullDev( self, ONOSIpList, deviceCount, numPorts=10):
andrew@onlab.us3b087132015-03-11 15:00:08 -07001932
1933 '''
andrew@onlab.us3b087132015-03-11 15:00:08 -07001934 ONOSIpList = list of Ip addresses of nodes switches will be devided amongst
cameron@onlab.us75900962015-03-30 13:22:49 -07001935 deviceCount = number of switches to distribute, or list of values to use as custom distribution
1936 numPorts = number of ports per device. Defaults to 10 both in this function and in ONOS. Optional arg
andrew@onlab.us3b087132015-03-11 15:00:08 -07001937 '''
1938
cameron@onlab.us75900962015-03-30 13:22:49 -07001939 main.log.step("Configuring Null Device Provider" )
andrew@onlab.us3b087132015-03-11 15:00:08 -07001940 clusterCount = len(ONOSIpList)
1941
cameron@onlab.us75900962015-03-30 13:22:49 -07001942 try:
1943
1944 if type(deviceCount) is int or type(deviceCount) is str:
1945 main.log.step("Creating device distribution")
1946 deviceCount = int(deviceCount)
1947 switchList = [0]*(clusterCount+1)
1948 baselineSwitchCount = deviceCount/clusterCount
andrew@onlab.us3b087132015-03-11 15:00:08 -07001949
cameron@onlab.us75900962015-03-30 13:22:49 -07001950 for node in range(1, clusterCount + 1):
1951 switchList[node] = baselineSwitchCount
andrew@onlab.us3b087132015-03-11 15:00:08 -07001952
cameron@onlab.us75900962015-03-30 13:22:49 -07001953 for node in range(1, (deviceCount%clusterCount)+1):
1954 switchList[node] += 1
1955
1956 if type(deviceCount) is list:
1957 main.log.info("Using provided device distribution")
1958
1959 if len(deviceCount) == clusterCount:
1960 switchList = ['0']
1961 switchList.extend(deviceCount)
1962
1963 if len(deviceCount) == (clusterCount + 1):
1964 if deviceCount[0] == '0' or deviceCount[0] == 0:
1965 switchList = deviceCount
andrew@onlab.us3b087132015-03-11 15:00:08 -07001966
cameron@onlab.us75900962015-03-30 13:22:49 -07001967 assert len(switchList) == (clusterCount + 1)
1968
1969 except AssertionError:
1970 main.log.error( "Bad device/Ip list match")
1971 except TypeError:
1972 main.log.exception( self.name + ": Object not as expected" )
1973 return None
Jon Hall77ba41c2015-04-06 10:25:40 -07001974 except Exception:
cameron@onlab.us75900962015-03-30 13:22:49 -07001975 main.log.exception( self.name + ": Uncaught exception!" )
1976 main.cleanup()
1977 main.exit()
1978
andrew@onlab.us3b087132015-03-11 15:00:08 -07001979
1980 ONOSIp = [0]
1981 ONOSIp.extend(ONOSIpList)
1982
1983 devicesString = "devConfigs = "
1984 for node in range(1, len(ONOSIp)):
1985 devicesString += (ONOSIp[node] + ":" + str(switchList[node] ))
1986 if node < clusterCount:
1987 devicesString += (",")
cameron@onlab.us75900962015-03-30 13:22:49 -07001988
1989 try:
1990 self.handle.sendline("onos $OC1 cfg set org.onosproject.provider.nil.device.impl.NullDeviceProvider devConfigs " + devicesString )
1991 self.handle.expect(":~")
1992 self.handle.sendline("onos $OC1 cfg set org.onosproject.provider.nil.device.impl.NullDeviceProvider numPorts " + str(numPorts) )
1993 self.handle.expect(":~")
andrew@onlab.us3b087132015-03-11 15:00:08 -07001994
cameron@onlab.us75900962015-03-30 13:22:49 -07001995 for i in range(10):
1996 self.handle.sendline("onos $OC1 cfg get org.onosproject.provider.nil.device.impl.NullDeviceProvider")
1997 self.handle.expect(":~")
1998 verification = self.handle.before
1999 if (" value=" + str(numPorts)) in verification and (" value=" + devicesString) in verification:
2000 break
2001 else:
2002 time.sleep(1)
andrew@onlab.us3b087132015-03-11 15:00:08 -07002003
cameron@onlab.us2cc8bf12015-04-02 14:12:30 -07002004 assert ("value=" + str(numPorts)) in verification and (" value=" + devicesString) in verification
cameron@onlab.us75900962015-03-30 13:22:49 -07002005
2006 except AssertionError:
2007 main.log.error("Incorrect Config settings: " + verification)
Jon Hall77ba41c2015-04-06 10:25:40 -07002008 except Exception:
cameron@onlab.us75900962015-03-30 13:22:49 -07002009 main.log.exception( self.name + ": Uncaught exception!" )
2010 main.cleanup()
2011 main.exit()
2012
cameron@onlab.usc80a8c82015-04-15 14:57:37 -07002013 def configNullLink( self,fileName="/opt/onos/apache-karaf-3.0.3/etc/linkGraph.cfg", eventRate=0):
andrew@onlab.us3b087132015-03-11 15:00:08 -07002014 '''
cameron@onlab.us75900962015-03-30 13:22:49 -07002015 fileName default is currently the same as the default on ONOS, specify alternate file if
2016 you want to use a different topology file than linkGraph.cfg
andrew@onlab.us3b087132015-03-11 15:00:08 -07002017 '''
2018
andrew@onlab.us3b087132015-03-11 15:00:08 -07002019
cameron@onlab.us75900962015-03-30 13:22:49 -07002020 try:
2021 self.handle.sendline("onos $OC1 cfg set org.onosproject.provider.nil.link.impl.NullLinkProvider eventRate " + str(eventRate))
2022 self.handle.expect(":~")
2023 self.handle.sendline("onos $OC1 cfg set org.onosproject.provider.nil.link.impl.NullLinkProvider cfgFile " + fileName )
2024 self.handle.expect(":~")
2025
2026 for i in range(10):
2027 self.handle.sendline("onos $OC1 cfg get org.onosproject.provider.nil.link.impl.NullLinkProvider")
2028 self.handle.expect(":~")
2029 verification = self.handle.before
2030 if (" value=" + str(eventRate)) in verification and (" value=" + fileName) in verification:
2031 break
2032 else:
2033 time.sleep(1)
2034
2035 assert ("value=" + str(eventRate)) in verification and (" value=" + fileName) in verification
2036
2037 except pexpect.EOF:
2038 main.log.error( self.name + ": EOF exception found" )
2039 main.log.error( self.name + ": " + self.handle.before )
2040 main.cleanup()
2041 main.exit()
cameron@onlab.us75900962015-03-30 13:22:49 -07002042 except AssertionError:
2043 main.log.info("Settings did not post to ONOS")
2044 main.log.error(varification)
Jon Hall77ba41c2015-04-06 10:25:40 -07002045 except Exception:
cameron@onlab.us75900962015-03-30 13:22:49 -07002046 main.log.exception( self.name + ": Uncaught exception!" )
2047 main.log.error(varification)
2048 main.cleanup()
2049 main.exit()
andrew@onlab.us3b087132015-03-11 15:00:08 -07002050
kelvin-onlaba4074292015-07-09 15:19:49 -07002051 def getOnosIps( self ):
2052 """
2053 Get all onos IPs stored in
2054 """
cameron@onlab.us59d29d92015-05-11 14:31:54 -07002055
kelvin-onlaba4074292015-07-09 15:19:49 -07002056 return sorted( self.onosIps.values() )
cameron@onlab.us59d29d92015-05-11 14:31:54 -07002057
kelvin-onlaba4074292015-07-09 15:19:49 -07002058 def logReport( self, nodeIp, searchTerms, outputMode="s" ):
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002059 '''
2060 - accepts either a list or a string for "searchTerms" these
2061 terms will be searched for in the log and have their
2062 instances counted
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002063
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002064 - nodeIp is the ip of the node whos log is to be scanned
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002065
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002066 - output modes:
2067 "s" - Simple. Quiet output mode that just prints
cameron@onlab.us2e166212015-05-19 14:28:25 -07002068 the occurences of each search term
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002069
cameron@onlab.us2e166212015-05-19 14:28:25 -07002070 "d" - Detailed. Prints number of occurences as well as the entire
2071 line for each of the last 5 occurences
2072
2073 - returns total of the number of instances of all search terms
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002074 '''
2075 main.log.info("========================== Log Report ===========================\n")
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002076
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002077 if type(searchTerms) is str:
2078 searchTerms = [searchTerms]
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002079
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002080 logLines = [ [" "] for i in range(len(searchTerms)) ]
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002081
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002082 for term in range(len(searchTerms)):
2083 logLines[term][0] = searchTerms[term]
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002084
cameron@onlab.us2e166212015-05-19 14:28:25 -07002085 totalHits = 0
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002086 for term in range(len(searchTerms)):
2087 cmd = "onos-ssh " + nodeIp + " cat /opt/onos/log/karaf.log | grep " + searchTerms[term]
2088 self.handle.sendline(cmd)
2089 self.handle.expect(":~")
2090 before = (self.handle.before).splitlines()
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002091
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002092 count = [searchTerms[term],0]
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002093
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002094 for line in before:
2095 if searchTerms[term] in line and "grep" not in line:
2096 count[1] += 1
2097 if before.index(line) > ( len(before) - 7 ):
2098 logLines[term].append(line)
cameron@onlab.us70dd8c62015-05-14 11:19:39 -07002099
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002100 main.log.info( str(count[0]) + ": " + str(count[1]) )
2101 if term == len(searchTerms)-1:
2102 print("\n")
cameron@onlab.us2e166212015-05-19 14:28:25 -07002103 totalHits += int(count[1])
2104
cameron@onlab.us966d1be2015-05-15 14:54:09 -07002105 if outputMode != "s" and outputMode != "S":
2106 outputString = ""
2107 for i in logLines:
2108 outputString = i[0] + ": \n"
2109 for x in range(1,len(i)):
2110 outputString += ( i[x] + "\n" )
2111
2112 if outputString != (i[0] + ": \n"):
2113 main.log.info(outputString)
2114
2115 main.log.info("================================================================\n")
cameron@onlab.us2e166212015-05-19 14:28:25 -07002116 return totalHits
pingping-lin763ee042015-05-20 17:45:30 -07002117
Hari Krishnaade11a72015-07-01 17:06:46 -07002118 def getOnosIPfromCell(self):
2119 '''
2120 Returns the ONOS node names and their IP addresses as defined in the cell and applied to shell environment
Hari Krishnaa25104c2015-07-09 22:34:01 -07002121 Example output return: ['10.128.40.41','10.128.40.42','10.128.40.43']. This will work even if the Mininet is
2122 not part of the cell definition and also if there are multiple mininets, just by using static hostname
2123 in TOPO file.
2124 '''
Hari Krishnaade11a72015-07-01 17:06:46 -07002125 import re
2126 try:
2127 # Clean handle by sending empty and expecting $
2128 self.handle.sendline( "" )
2129 self.handle.expect( "\$" )
2130 self.handle.sendline( "cell" )
2131 self.handle.expect( "\$" )
2132 handleBefore = self.handle.before
2133 handleAfter = self.handle.after
2134 # Get the rest of the handle
2135 self.handle.sendline( "" )
2136 self.handle.expect( "\$" )
2137 handleMore = self.handle.before
2138 ipList = []
2139 cellOutput = handleBefore + handleAfter + handleMore
2140 cellOutput = cellOutput.replace("\r\r","")
2141 cellOutput = cellOutput.splitlines()
2142 for i in range( len(cellOutput) ):
2143 if( re.match( "OC", cellOutput[i] ) ):
2144 if( re.match( "OCI", cellOutput[i] ) or re.match( "OCN", cellOutput[i] ) ):
2145 continue
2146 else:
2147 onosIP = cellOutput[i].split("=")
Hari Krishnac195f3b2015-07-08 20:02:24 -07002148 ipList.append(onosIP[1])
Hari Krishnaade11a72015-07-01 17:06:46 -07002149 return ipList
2150 except pexpect.ExceptionPexpect as e:
2151 main.log.error( self.name + ": Pexpect exception found of type " +
2152 str( type( e ) ) )
2153 main.log.error ( e.get_trace() )
2154 main.log.error( self.name + ": " + self.handle.before )
2155 main.cleanup()
2156 main.exit()
2157 except Exception:
2158 main.log.exception( self.name + ": Uncaught exception!" )
2159 main.cleanup()
2160 main.exit()
kelvin-onlab7a719bb2015-07-08 11:09:51 -07002161
2162 def copyMininetFile( self, fileName, localPath, userName, ip,
2163 mnPath='~/mininet/custom/', timeout = 60 ):
2164 """
2165 Description:
2166 Copy mininet topology file from dependency folder in the test folder
2167 and paste it to the mininet machine's mininet/custom folder
2168 Required:
2169 fileName - Name of the topology file to copy
2170 localPath - File path of the mininet topology file
2171 userName - User name of the mininet machine to send the file to
2172 ip - Ip address of the mininet machine
2173 Optional:
2174 mnPath - of the mininet directory to send the file to
2175 Return:
2176 Return main.TRUE if successfully copied the file otherwise
2177 return main.FALSE
2178 """
2179
2180 try:
2181 cmd = "scp " + localPath + fileName + " " + userName + "@" + \
2182 str( ip ) + ":" + mnPath + fileName
2183
2184 self.handle.sendline( "" )
2185 self.handle.expect( "\$" )
2186
2187 main.log.info( self.name + ": Execute: " + cmd )
2188
2189 self.handle.sendline( cmd )
2190
2191 i = self.handle.expect( [ 'No such file',
2192 "100%",
2193 pexpect.TIMEOUT ] )
2194
2195 if i == 0:
2196 main.log.error( self.name + ": File " + fileName +
2197 " does not exist!" )
2198 return main.FALSE
2199
2200 if i == 1:
2201 main.log.info( self.name + ": File " + fileName +
2202 " has been copied!" )
2203 self.handle.sendline( "" )
2204 self.handle.expect( "\$" )
2205 return main.TRUE
2206
2207 except pexpect.EOF:
2208 main.log.error( self.name + ": EOF exception found" )
2209 main.log.error( self.name + ": " + self.handle.before )
2210 main.cleanup()
2211 main.exit()
2212 except pexpect.TIMEOUT:
2213 main.log.error( self.name + ": TIMEOUT exception found" )
2214 main.log.error( self.name + ": " + self.handle.before )
2215 main.cleanup()
2216 main.exit()
cameron@onlab.us78b89652015-07-08 15:21:03 -07002217
2218 def jvmSet(self, memory=8):
2219
2220 import os
2221
2222 homeDir = os.path.expanduser('~')
2223 filename = "/onos/tools/package/bin/onos-service"
2224
2225 serviceConfig = open(homeDir + filename, 'w+')
2226 serviceConfig.write("#!/bin/bash\n ")
2227 serviceConfig.write("#------------------------------------- \n ")
2228 serviceConfig.write("# Starts ONOS Apache Karaf container\n ")
2229 serviceConfig.write("#------------------------------------- \n ")
2230 serviceConfig.write("#export JAVA_HOME=${JAVA_HOME:-/usr/lib/jvm/java-7-openjdk-amd64/}\n ")
2231 serviceConfig.write("""export JAVA_OPTS="${JAVA_OPTS:--Xms""" + str(memory) + "G -Xmx" + str(memory) + """G}" \n """)
2232 serviceConfig.write("[ -d $ONOS_HOME ] && cd $ONOS_HOME || ONOS_HOME=$(dirname $0)/..\n")
2233 serviceConfig.write("""${ONOS_HOME}/apache-karaf-$KARAF_VERSION/bin/karaf "$@" \n """)
2234 serviceConfig.close()
2235
2236 def createDBFile(self, testData):
2237
2238 filename = main.TEST + "DB"
2239 DBString = ""
2240
2241 for item in testData:
2242 if type(item) is string:
2243 item = "'" + item + "'"
2244 if testData.index(item) < len(testData-1):
2245 item += ","
2246 DBString += str(item)
2247
2248 DBFile = open(filename, "a")
2249 DBFile.write(DBString)
2250 DBFile.close()
2251
2252 def verifySummary(self, ONOSIp,*deviceCount):
2253
2254 self.handle.sendline("onos " + ONOSIp + " summary")
2255 self.handle.expect(":~")
2256
2257 summaryStr = self.handle.before
2258 print "\nSummary\n==============\n" + summaryStr + "\n\n"
2259
2260 #passed = "SCC(s)=1" in summaryStr
2261 #if deviceCount:
2262 # passed = "devices=" + str(deviceCount) + "," not in summaryStr
2263
2264
2265 if "SCC(s)=1," in summaryStr:
2266 passed = True
2267 print("Summary is verifed")
2268 else:
2269 print("Summary failed")
2270
2271 if deviceCount:
2272 print" ============================="
2273 checkStr = "devices=" + str(deviceCount[0]) + ","
2274 print "Checkstr: " + checkStr
2275 if checkStr not in summaryStr:
2276 passed = False
2277 print("Device count failed")
2278 else:
2279 print "device count verified"
2280
2281 return passed