81 lines
2.7 KiB
Python
Executable File
81 lines
2.7 KiB
Python
Executable File
#!/usr/bin/env python3
|
|
"""Wait for the stick's telnet to cycle after a reboot, then run #ONT CLI reads to verify.
|
|
Usage: gpon_verify.py [--wait S] [--idle S] [--cap S] 'cmd1' 'cmd2' ..."""
|
|
import socket, sys, time, re
|
|
from gpon_env import HOST, PORT, USER, PASS
|
|
args=sys.argv[1:]; idle=5.0; cap=25.0; wait=140.0; cmds=[]
|
|
while args:
|
|
a=args.pop(0)
|
|
if a=='--idle': idle=float(args.pop(0))
|
|
elif a=='--cap': cap=float(args.pop(0))
|
|
elif a=='--wait': wait=float(args.pop(0))
|
|
else: cmds.append(a)
|
|
|
|
def strip_iac(data,outbuf):
|
|
res=bytearray(); i=0
|
|
while i<len(data):
|
|
b=data[i]
|
|
if b==0xFF and i+1<len(data):
|
|
c=data[i+1]
|
|
if c in (251,252,253,254) and i+2<len(data):
|
|
o=data[i+2]
|
|
if c==253: outbuf.append(bytes([255,252,o]))
|
|
elif c==251: outbuf.append(bytes([255,254,o]))
|
|
i+=3; continue
|
|
elif c==250:
|
|
j=data.find(b'\xff\xf0',i+2); i=len(data) if j<0 else j+2; continue
|
|
else: i+=2; continue
|
|
res.append(b); i+=1
|
|
return bytes(res)
|
|
|
|
def port_open():
|
|
try:
|
|
c=socket.create_connection((HOST,PORT),timeout=3); c.close(); return True
|
|
except (OSError,) : return False
|
|
|
|
t0=time.time()
|
|
# 1) give the reboot a moment to take the stick down
|
|
time.sleep(5)
|
|
# 2) wait for it to go DOWN (confirms the reboot began)
|
|
went_down=False
|
|
while time.time()-t0 < 30:
|
|
if not port_open(): went_down=True; break
|
|
time.sleep(2)
|
|
print("stick went DOWN: %s (t=%ds)"%(went_down, time.time()-t0))
|
|
# 3) wait for it to come back UP
|
|
came_up=False
|
|
while time.time()-t0 < wait:
|
|
if port_open(): came_up=True; break
|
|
time.sleep(3)
|
|
if not came_up:
|
|
print("STICK DID NOT COME BACK within %ds -- check MikroTik sfp1 / re-seat"%wait); sys.exit(1)
|
|
print("stick back UP (t=%ds); giving telnetd a few s to settle"%(time.time()-t0))
|
|
time.sleep(4)
|
|
|
|
s=socket.create_connection((HOST,PORT),timeout=8)
|
|
def rx(idle,cap,stop=None):
|
|
s.settimeout(0.5); buf=bytearray(); last=time.time(); start=time.time()
|
|
while True:
|
|
try:
|
|
d=s.recv(16384)
|
|
if not d: break
|
|
ob=[]; buf.extend(strip_iac(d,ob))
|
|
for o in ob: s.sendall(o)
|
|
last=time.time()
|
|
if stop and stop(buf): break
|
|
except socket.timeout:
|
|
if time.time()-last>idle: break
|
|
if time.time()-start>cap: break
|
|
return buf.decode('latin-1','replace')
|
|
def send(x): s.sendall(x.encode()+b'\r\n')
|
|
|
|
o=rx(3,10)
|
|
if re.search(r'(ogin|sername)',o): send(USER); o+=rx(2,6)
|
|
if re.search(r'assword',o,re.I): send(PASS); o+=rx(3,8)
|
|
promptend=lambda b: b.rstrip().endswith(b'>')
|
|
for c in cmds:
|
|
send(c); out=rx(idle,cap,stop=promptend)
|
|
print("\n>>> %s\n%s"%(c,out))
|
|
try: s.close()
|
|
except Exception: pass
|