手写netcat教程(详细)
1.1什么是 Socket?
Socket又称"套接字",应用程序通常通过"套接字"向网络发出请求或者应答网络请求,使主机间或者一台计算机上的进程间可以通讯。
socket的使用:
socket()
socket.socket([family[, type[, proto]]])
family: 套接字家族可以是 AF_UNIX 或者 AF_INET
type: 套接字类型可以根据是面向连接的还是非连接分为SOCK_STREAM或SOCK_DGRAM
proto: 一般不填默认为0.
常用方法
s.bind()
绑定地址(host,port)到套接字, 在AF_INET下,以元组(host,port)的形式表示地址。
s.listen()
开始TCP监听。backlog指定在拒绝连接之前,操作系统可以挂起的最大连接数量。该值至少为1,大部分应用程序设为5就可以了。
s.recv()
接收TCP数据,数据以字符串形式返回,bufsize指定要接收的最大数据量。flag提供有关消息的其他信息,通常可以忽略。
s.send()
发送TCP数据,将string中的数据发送到连接的套接字。返回值是要发送的字节数量,该数量可能小于string的字节大小。
s.close()
关闭套接字
1.2什么是tcp?
传输控制协议(TCP,Transmission Control Protocol)是一种面向连接的、可靠的、基于字节流的传输层通信协议。
1.3什么是udp?
“UDP 是User Datagram Protocol的简称, 参考模型中一种无连接的传输层协议,提供面向事务的简单不可靠信息传送服务
1.4tcp和udp有什么区别?
简单来说udp是一个无连接协议,具体体现在python代码上,我们的udp是无需先发送连接
代码对比:
1.定义socket对象
tcp socket.SOCK_STREAM
udp socket.SOCK_DGRAM2.是否需要连接客户端?
TCP client.connect((host,port))
udp 否3.发送请求
tcp send()
udp tosend()
1.4什么是多线程
举个通俗易懂的例子哈!
要考试了你和你同桌作弊,它抄前一部分,你抄一部分,最后你们顺利的通过考试。这里有个细节,就是无论你们谁先抄完都要等对方,不等就交卷两个都凉了。
两只手同时画圆和正方形,你会发现怎么画都基本上难同时画出来,除非训练得很多,大脑响应得快,(cpu交替运行得快)
当然了有的怪胎是天生就可以,经典的双核CPU。
1.5说一说python的多线程
python的多线程我感觉不咋地,为什么有这种感觉,学过go,c就。。。。。不过对于写点工具要得是生产力,不要管那些运行速度了。
线程的分类:
内核线程:由操作系统内核创建和撤销。
用户线程:不需要内核支持而在用户程序中实现的线程。(用的多)
Python3 线程中常用的两个模块为:
_thread
threading(推荐使用)
thread 模块已被废弃。用户可以使用 threading 模块代替。所以,在 Python3 中不能再使用"thread" 模块。为了兼容性,Python3 将 thread 重命名为 "_thread"。
Thread类提供了以下方法:
run(): 用以表示线程活动的方法。
start():启动线程活动。
join([time]): 等待至线程中止。这阻塞调用线程直至线程的join() 方法被调用中止-正常退出或者抛出未处理的异常-或者是可选的超时发生。
isAlive(): 返回线程是否活动的。
getName(): 返回线程名。
setName(): 设置线程名。
1.6编写一个netcat(实战)
难度:⭐⭐(5⭐标准)
难点:面向对象,网络编程基础
重点:应用网络编程基础,掌握工具开发基本结构
为什么要写netcat?
用过netcat的小伙伴有没有这样的经历?打开杀毒软件,咱才下载的netcat就被杀了。。。。为什么会这样呢?
精明的网络管理员总是会把系统里面netcat移除,防止被黑客利用。。。。。不过大部分服务器却会安装python,用python搓一个netcat是相对容易的。同时也是一次很好的编程练习。当然了,我们要使用内置包这里是个细节。
补充一下,为什么大部分服务器会装python?
第一,Python是一门后端语言,可以用来web编程,例如:django flask fastapi 等web框架。部署python应用,肯定要安装python环境;
第二,python是一门脚本语言,很多运维工程师在产品上线的时候,不是用shell就是用python批量配置环境。而且产品时不时更新啥的,为了方便直接安装后就不卸载python环境。
写这个项目有什么好处?
1.实践socket编程,socket面试会问的。。。。
2.其它好处不在这里说了,哈哈
知识点:
1.命令行工具设计
2.认识使用到的内置库
argparse
当一个项目的输入参数较多,且要进行修改和调试时,经常涉及到参数的格式和路径问题。
如果一行一行去进行修改代码,会非常繁琐且错误率很高。
shlex
subprocess
shlex 模块最常用的是 split() 函数,用来分割字符串,通常与 subprocess 结合使用
sys是Python提供的程序与解释器交互的标准库
textwrap库:Python格式化文本段落
3.面向对象程序设计
在netcat项目中我们使用了面向对象的思想,设计了netcat对象,并且根据需求对对象增加的方法。
项目的结构分析
我们只是开发简单的工具,所以以简洁为主。程序都写在了一个文件中方便使用,项目中,可以分为4个部分:
1.包
2.命令执行函数
3.netcat对象
4.主函数入口+help
项目详细讲解过程
1)导入
大家好,本节课我们将使用python3来写一个netcat。什么是netcat呢?netcat的中文翻译就是“瑞士军刀”(出示瑞士军刀图片)。netcat是一个功能丰富的网络工具,它经常会被黑客使用。精明的管理员会把它移除,不过我们可以用python快速编写,因为管理员不会随便把python卸载。接下来就和我一起来实战吧!
我们打开pycharm,无需创建虚拟环境,无需下载内置包。新建一个netcat.py文件,文件头导入一下包:
import argparse
import socket
import shlex
import subprocess
import sys
import textwrap
import threading
我们编写一个命令执行函数,输入 => exe函数接受命令并执行 =>输出
def execute(cmd):
cmd=cmd.strip() #@1
if not cmd:
return
output=subprocess.check_output(shlex.split(cmd),stderr=subprocess.STDOUT)#@2
return output.decode()
@1整理开头和结尾的字符串
@2这个函数是在 Python 2.7 中引入的。我们可以使用它在命令提示符下运行带有 Python 参数的命令。
subprocess.check_output() 函数将以字节形式返回给定命令的输出。如果函数返回非零代码,则会引发 CalledProcessError 对象。
CalledProcessError 对象有两个属性。这些是 returncode 和 output 属性。
我们为项目编写入口:
if name == 'main':
parser=argparse.ArgumentParser(
# 工具描述信息
description='jiang net tool',
#工具命令
formatter_class=argparse.RawDescriptionHelpFormatter,
epilog=textwrap.dedent(
'''example:
netcat.py -t host -p port -l -c # command shell
netcat.py -t host -p port -l -u=text.txt #upload to file
netcat.py -t host -p port -l -e=\"cat/etc/password\"#execute command
echo 'abc' | ./netcat.py -t host -p 135 # echo text to server port 135
netcat.py -t host -p port #connect server
'''
))
#注册命令
parser.add_argument('-c','--command',action='store_true',help='command shell')
parser.add_argument('-e','--execute',help='execute specified command ')
parser.add_argument('-l','--listen',action='store_true',help='listen')
parser.add_argument('-p','--port',type=int,help='specified port',default=5555)
parser.add_argument('-t','--target',default='192.168.1.203',help='specified ip')
parser.add_argument('-u','--upload',help='upload file')
最后实现netcat对象
对象初始化
class NetCat:
def init(self,args,buffer= None) :
self.args=args
self.buffer=buffer
self.socket=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
self.socket.setsockopt(socket.SOL_SOCKET,socket.SO_REUSEADDR,1)
run方法
def run(self):
if self.args.listen:
self.listen()
else:
self.send()
send 方法
def send(self):
self.socket.connect((self.args.target,self.args.port))
if self.buffer:
self.socket.send(self.buffer)
try:
while True:
recv_len=1
response=''
while recv_len:
data=self.socket.recv(4096)
recv_len=len(data)
response+=data.decode
if recv_len<4096:
break
if response:
print(response)
buffer=input('>')
buffer+='\n'
self.socket.send(buffer.encode)
except KeyboardInterrupt:
print('user terminated')
self.socket.close()
sys.exit()
listen 方法
def listen(self):
self.socket.bind((self.args.target,self.args.port))
self.socket.listen(5)
while True:
client_socket,_=self.socket.accept()
client_thread=threading.Thread(
target=self.handle,args=(client_socket,)
)
client_thread.start()
handle 方法
def handle(self,client_socket):
if self.args.execute:
output=execute(self.args.execute)
client_socket.send(output.encode)
elif self.args.upload:
file_buffer='b'
while True:
data=client_socket.recv(4096)
if data:
file_buffer+=data
else:
break
with open(self.args.upload,'wb') as f:
f.write(file_buffer)
message=f'Save file {self.args.upload}'
client_socket.send(message.encode)
elif self.args.command:
cmd_buffer='b'
while True:
try:
client_socket.send(b'BHP: #>')
while '\n'not in cmd_buffer.decode():
cmd_buffer+=client_socket.recv(64)
response=execute(cmd_buffer.decode())
if response:
client_socket.send(response.encode())
cmd_buffer='b'
except Exception as e:
print(f'server killed{e}')
self.socket.close()
sys.exit()
实战netcat总结
1.开发工具的选取。尽量使用pycharm,效率高,vscode插件装多难免会有bug。vim系列也不是不可以,前提你得配置好。
2.实战不要只会抄代码,要想一下为什么要这么写,遇到不会的马上补充知识点。学习模式就是:从知识走进实战,在实战中学习经验。
3.面向对象是一种编程思想,划分一下就是内功修炼,得慢慢来。
4.肯定有你不会的,肯定有bug。很喜欢某人说过的一句话:你从来没得过芒果确实悲哀,但回回是你得到,更悲哀!
1.7开发一个tcp代理
用途:
主机流量转发
检测网络软件
无法使用抓包的时候开代理
项目结构:
1.本地设备和远程设备通信过程显示
2.本地设备或远程设备入口
3.控制本地设备和远程设备的流量方向
4.监听socket......

浙公网安备 33010602011771号