Python - 带套接字的多线程给出随机结果
Python - multithreading with sockets gives random results
我现在对我的问题真的很困惑。我想通过主机(或子网)列表发现一个开放端口。
所以首先让我们展示一下我到目前为止所做的事情..
from multiprocessing.dummy import Pool as ThreadPool
from netaddr import IPNetwork as getAddrList
import socket, sys
this = sys.modules[__name__]
def threading(ip):
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
sock.settimeout(this.timeout)
failCode = 0
try:
if sock.connect_ex((str(ip), this.port)) == 0:
#port open
this.count += 1
else:
#port closed/filtered
failCode = 1
pass
except Exception:
#host unreachable
failCode = 2
pass
finally:
sock.close()
#set thread num
threads = 64
#set socket timeout
this.timeout = 1
#set ip list
ipList = getAddrList('8.8.8.0/24')
#set port
this.port = 53
#set count
this.count = 0
#threading
Pool = ThreadPool(threads)
Pool.map_async(threading, ipList).get(9999999)
Pool.close()
Pool.join()
#result
print str(this.count)
脚本运行良好,没有任何错误。但是我正在为它打印出来的内容而苦苦挣扎..
因此,如果我想扫描子网 8.8.8.0/24
并发现端口 53
。我知道唯一具有开放 dns 端口的服务器是 8.8.8.8
(google-dns).
但是当我 运行 我的脚本几次时 print str(this.count)
将随机(在我看来..) return 0
或 1
.
我还知道:
- 仅扫描
8.8.8.8
始终打印 1
- 仅使用 1 个线程用于
/24
打印总是 1
- 使用 256 个线程进行
/24
随机打印 0
和 1
- 更改超时没有帮助
所以它似乎与导致我的计算机延迟的线程选项有关。但请注意,我的 CPU 使用率 <10%,网络使用率 <50%!
但是还有一点我不明白..
如果 print str(this.count)
returns 0
我通常会认为这是因为线程相互冲突并且套接字没有连接..但事实并非如此,因为如果 this.count
等于 0
,则 failCode
设置为 1
(在 8.8.8.8
上)!这意味着端口已关闭..但这一定也是我脚本的错误。我不认为这是由服务器延迟引起的..它是 google 没有延迟..
所以我们还知道:
- 输出
0
是因为服务器响应端口关闭
- 并且我们确定端口肯定是打开的
所以我也在想,如果我有很多线程同时 运行 if sock.connect_ex((str(ip), this.port)) == 0:
可能主机 8.8.8.8
查找错误的答案值。也许它挣扎并查看 8.8.8.7
的响应。 ..希望你明白我的意思。
**max_socket_connections 在我的 linux 发行版中设置为 512
任何人都对套接字线程有经验,可以向我解释情况或给我一个如何防止这种情况的答案?
已解决:
..看答案..
第一个错误是:
But note that my CPU usage is <10% and the
network usage is <50%!
实际上是 400% 的网络使用率。我期望位而不是字节。
好尴尬..
第二个错误是:
and we are sure the port is definitely open
Google 确实在短时间内尝试 ~5 次后实际上阻塞了端口。他们会在几秒或几分钟后解除限制。
我现在对我的问题真的很困惑。我想通过主机(或子网)列表发现一个开放端口。
所以首先让我们展示一下我到目前为止所做的事情..
from multiprocessing.dummy import Pool as ThreadPool
from netaddr import IPNetwork as getAddrList
import socket, sys
this = sys.modules[__name__]
def threading(ip):
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
sock.settimeout(this.timeout)
failCode = 0
try:
if sock.connect_ex((str(ip), this.port)) == 0:
#port open
this.count += 1
else:
#port closed/filtered
failCode = 1
pass
except Exception:
#host unreachable
failCode = 2
pass
finally:
sock.close()
#set thread num
threads = 64
#set socket timeout
this.timeout = 1
#set ip list
ipList = getAddrList('8.8.8.0/24')
#set port
this.port = 53
#set count
this.count = 0
#threading
Pool = ThreadPool(threads)
Pool.map_async(threading, ipList).get(9999999)
Pool.close()
Pool.join()
#result
print str(this.count)
脚本运行良好,没有任何错误。但是我正在为它打印出来的内容而苦苦挣扎..
因此,如果我想扫描子网 8.8.8.0/24
并发现端口 53
。我知道唯一具有开放 dns 端口的服务器是 8.8.8.8
(google-dns).
但是当我 运行 我的脚本几次时 print str(this.count)
将随机(在我看来..) return 0
或 1
.
我还知道:
- 仅扫描
8.8.8.8
始终打印1
- 仅使用 1 个线程用于
/24
打印总是1
- 使用 256 个线程进行
/24
随机打印0
和1
- 更改超时没有帮助
所以它似乎与导致我的计算机延迟的线程选项有关。但请注意,我的 CPU 使用率 <10%,网络使用率 <50%!
但是还有一点我不明白..
如果 print str(this.count)
returns 0
我通常会认为这是因为线程相互冲突并且套接字没有连接..但事实并非如此,因为如果 this.count
等于 0
,则 failCode
设置为 1
(在 8.8.8.8
上)!这意味着端口已关闭..但这一定也是我脚本的错误。我不认为这是由服务器延迟引起的..它是 google 没有延迟..
所以我们还知道:
- 输出
0
是因为服务器响应端口关闭 - 并且我们确定端口肯定是打开的
所以我也在想,如果我有很多线程同时 运行 if sock.connect_ex((str(ip), this.port)) == 0:
可能主机 8.8.8.8
查找错误的答案值。也许它挣扎并查看 8.8.8.7
的响应。 ..希望你明白我的意思。
**max_socket_connections 在我的 linux 发行版中设置为 512
任何人都对套接字线程有经验,可以向我解释情况或给我一个如何防止这种情况的答案?
已解决:
..看答案..
第一个错误是:
But note that my CPU usage is <10% and the network usage is <50%!
实际上是 400% 的网络使用率。我期望位而不是字节。
好尴尬..
第二个错误是:
and we are sure the port is definitely open
Google 确实在短时间内尝试 ~5 次后实际上阻塞了端口。他们会在几秒或几分钟后解除限制。