Revision 50cebe67 mininet/util.py

View differences:

mininet/util.py
1 1
"Utility functions for Mininet."
2 2

  
3
from mininet.log import output, info, error
4

  
3 5
from time import sleep
4 6
from resource import setrlimit, RLIMIT_NPROC, RLIMIT_NOFILE
5 7
from select import poll, POLLIN
6 8
from subprocess import call, check_call, Popen, PIPE, STDOUT
7
from mininet.log import output, info, error
8 9
import re
10
from fcntl import fcntl, F_GETFL, F_SETFL
11
from os import O_NONBLOCK
9 12

  
10 13
# Command execution support
11 14

  
......
300 303
    else:
301 304
        return s
302 305

  
306
# Popen support
307

  
308
def pmonitor(popens, timeoutms=500, readline=True,
309
             readmax=1024 ):
310
    """Monitor dict of hosts to popen objects
311
       a line at a time
312
       timeoutms: timeout for poll()
313
       readline: return single line of output
314
       yields: host, line/output (if any)
315
       terminates: when all EOFs received"""
316
    poller = poll()
317
    fdToHost = {}
318
    for host, popen in popens.iteritems():
319
        fd = popen.stdout.fileno()
320
        fdToHost[ fd ] = host
321
        poller.register( fd, POLLIN )
322
        if not readline:
323
            # Use non-blocking reads
324
            flags = fcntl( fd, F_GETFL )
325
            fcntl( fd, F_SETFL, flags | O_NONBLOCK )
326
    while True:
327
        fds = poller.poll( timeoutms )
328
        if fds:
329
            for fd, _event in fds:
330
                host = fdToHost[ fd ]
331
                popen = popens[ host ]
332
                if readline:
333
                    # Attempt to read a line of output
334
                    # This blocks until we receive a newline!
335
                    line = popen.stdout.readline()
336
                else:
337
                    line = popen.stdout.read( readmax )
338
                yield host, line
339
                # Check for EOF
340
                if not line:
341
                    popen.poll()
342
                    if popen.returncode is not None:
343
                        poller.unregister( fd )
344
                        del popens[ host ]
345
                        if not popens:
346
                            return
347
        else:
348
            yield None, ''
303 349

  
304 350
# Other stuff we use
305 351

  

Also available in: Unified diff