Skip to content

Commit 6647b17

Browse files
committed
Support unprivileged (non-root) usage
1 parent 8f5e65f commit 6647b17

File tree

1 file changed

+23
-10
lines changed

1 file changed

+23
-10
lines changed

pinger/ping.py

Lines changed: 23 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -17,11 +17,16 @@ def checksum(data): # Calc ICMP checksum as in RFC 1071
1717
# pure python parallel pinger
1818
def pppping(iplist,cnt=5,interval=1,deadline=0,source=None,verbose=False):
1919
if not deadline: deadline=cnt*interval+2
20-
#sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.getprotobyname("icmp"))
21-
sock = socket.socket(socket.AF_INET, socket.SOCK_RAW, socket.getprotobyname("icmp"))
20+
try:
21+
sock = socket.socket(socket.AF_INET, socket.SOCK_RAW, socket.getprotobyname("icmp"))
22+
offset=20
23+
except PermissionError:
24+
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.getprotobyname("icmp"))
25+
offset=0
2226
if source: sock.bind((source, 0))
2327

2428
p_id=os.getpid()&0x7FFF
29+
p_id2=None
2530
p_seq=1
2631
# payload=bytes(1400)
2732
payload=bytes([0xAA,0x55]*700)
@@ -50,17 +55,25 @@ def pppping(iplist,cnt=5,interval=1,deadline=0,source=None,verbose=False):
5055
# print(source, packet[:64].hex(' '))
5156
t=time.time()
5257
ip=source[0]
53-
resp=struct.unpack("!BBHHH", packet[20:28]) # msg_type, msg_code, checksum, id, seq (0, 0, 48513, 17021, 1)
54-
csum=checksum(packet[20:])
58+
resp=struct.unpack("!BBHHH", packet[offset:offset+8]) # msg_type, msg_code, checksum, id, seq (0, 0, 48513, 17021, 1)
59+
# Unknown reply: (0, 0, 15807, 2, 1)
60+
csum=checksum(packet[offset:])
5561
# print(source, len(packet), resp, csum) # ('193.224.177.1', 0) 1428 (0, 0, 38736, 26798, 1) 0
56-
key=(ip,resp[3],resp[4])
5762
if csum==0:
58-
if resp[0]==0 and key in sent:
59-
if verbose: print("Received ping from %s time %5.3f ms"%(ip,1000.0*(t-sent[key])))
60-
result[ip]+=1
61-
del sent[key]
63+
if resp[0]==0:
64+
key=(ip,resp[3],resp[4])
65+
if not key in sent: # ID mismatch, OK for non-root users...
66+
key=(ip,p_id,resp[4])
67+
if key in sent:
68+
if p_id2==None: p_id2=resp[3] # learn new ID (IP & seq matched)
69+
elif p_id2!=resp[3] and verbose: print("ID mismatch! %d != %d (sent %d)"%(p_id2,resp[3],p_id))
70+
if key in sent:
71+
p_id2=resp[3]
72+
if verbose: print("Received ping from %s time %5.3f ms"%(ip,1000.0*(t-sent[key])))
73+
result[ip]+=1
74+
del sent[key]
75+
elif verbose: print("BAD reply:",key, sent.keys())
6276
elif verbose: print("Unknown reply:",resp)
63-
# else: print("Unknown reply:",resp)
6477
elif verbose: print("Bad checksum!", resp)
6578
if p_seq>cnt and len(sent)==0:
6679
if verbose: print("All OK!!!")

0 commit comments

Comments
 (0)