信息收集通常可以分为被动信息收集和 ** 主动信息收集,** 被动信息收集是指不与目标主机进行直接交互,通常根据搜索引擎或者社交等方式间接获取目标主机的信息;主动信息收集是指与目标主机进行直接交互,从而获取所需要的目标信息

攻击者比较关注目标主机的所有信息,比如:子域名、IP 地址、旁站、C 段查询、用户邮箱 CMS 类型、敏感目录、端口信息、服务器版本以及中间件等

被动信息收集主要是通过一些收集引擎例如 fofa、鹰图等等进行收集、或者通过一些社交方式来获得一些信息。该方法是不与目标机子产生交互的,可以不接触目标的情况下挖掘目标信息。主要方法包括:DNS 解析、子域名挖掘、邮件爬取等等

DNS 解析

DNS 是一种分布式网络目录服务,主要用于域名与 ip 地址的相互转换,能够使用户更方便地访问互联网,TCP/IP 中的 IP 地址是由四段以 "." 分开地数字组成,记起来总是不如名字那么方便,所以采用了域名系统来管理名字和 IP 地对应关系

IP 查询

IP 查询是通过当前所获取到的 URL 去查询对应 IP 地址的过程。可以应用 Socket 库函数中的 gethostbyname () 获取域名所对应的 IP 值

例:查询域名 www.baidu.com 所对应的 IP 值

1
2
3
import socket
ip = socket.gethostbyname('www.baidu.com')
print(ip)

输出结果:

1
112.80.248.75

Whois 查询

Whois 是用来查询域名的 IP 以及所有者信息的传输协议。简单地说,Whois 就是一个数据库,用来查询域名是否已经被注册,以及注册域名的详细信息(如域 - 名所有人、域名注册商等)。Python 中的 python-whois 模块可以用于 Whois 的查询

先通过 pip 安装 python-whois 模块:

1
pip install python-whois·

通过自带的 whois 模块查询域名 www.baidu.com
的注册信息

1
2
3
from whois import whois
data = whois('www.baidu.com')
print(data)

输出结果:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
{
  "domain_name": [
    "BAIDU.COM",
    "baidu.com"
  ],
  "registrar": "MarkMonitor, Inc.",
  "whois_server": "whois.markmonitor.com",
  "referral_url": null,
  "updated_date": [
    "2022-09-01 03:54:43",
    "2022-09-01 03:29:31"
  ],
  "creation_date": "1999-10-11 11:05:17",
  "expiration_date": [
    "2026-10-11 11:05:17",
    "2026-10-11 07:00:00"
  ],
  "name_servers": [
    "NS1.BAIDU.COM",
    "NS2.BAIDU.COM",
    "NS3.BAIDU.COM",
    "NS4.BAIDU.COM",
    "NS7.BAIDU.COM",
    "ns7.baidu.com",
    "ns4.baidu.com",
    "ns1.baidu.com",
    "ns2.baidu.com",
    "ns3.baidu.com"
  ],
  "status": [
    "clientDeleteProhibited https://icann.org/epp#clientDeleteProhibited",
    "clientTransferProhibited https://icann.org/epp#clientTransferProhibited",
    "clientUpdateProhibited https://icann.org/epp#clientUpdateProhibited",
    "serverDeleteProhibited https://icann.org/epp#serverDeleteProhibited",
    "serverTransferProhibited https://icann.org/epp#serverTransferProhibited",
    "serverUpdateProhibited https://icann.org/epp#serverUpdateProhibited",
    "clientUpdateProhibited (https://www.icann.org/epp#clientUpdateProhibited)",
    "clientTransferProhibited (https://www.icann.org/epp#clientTransferProhibited)",
    "clientDeleteProhibited (https://www.icann.org/epp#clientDeleteProhibited)",
    "serverUpdateProhibited (https://www.icann.org/epp#serverUpdateProhibited)",
    "serverTransferProhibited (https://www.icann.org/epp#serverTransferProhibited)",
    "serverDeleteProhibited (https://www.icann.org/epp#serverDeleteProhibited)"
  ],
  "emails": [
    "abusecomplaints@markmonitor.com",
    "whoisrequest@markmonitor.com"
  ],
  "dnssec": "unsigned",
  "name": null,
  "org": "Beijing Baidu Netcom Science Technology Co., Ltd.",
  "address": null,
  "city": null,
  "state": "Beijing",
  "registrant_postal_code": null,
  "country": "CN"
}

子域名挖掘

域名可以分为顶级域名、一级域名、二级域名。子域名是顶级域名(一级域名或父域名)的下一级,例如 mail.example.com 和 calendar.example.com 是 example.com 的两个子域而 example.com 则是顶级域.com 的子域。在测试过程中,测试目标主站时如果未发现任何相关漏洞,此时通常会考虑挖掘目标系统的子域名。子域名的挖掘方式有很多种,例如:搜索引擎、子域名破解、字典查询等等

这里用 python 写一个子域名的挖掘工具(通过 Bing 搜索引擎进行子域名搜集):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
#! /usr/bin/env python
# _*_ coding:utf-8_*_
import requests
from bs4 import BeautifulSoup
from urllib.parse import urlparse
import sys

def bing_search(site,pages):
    Sudbomain = []
    headers = {
        'User-Agent':'Mozilla/5.0 (X11; Linux x86_64; rv:68.0)Gecko/20100101 Firefox/68.0'
        'Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
        'Referer':"https://cn.bing.com",
        'Cookie':"MUID=3B16E5B***********782&t=6" #填写相应的Cookie值
    }
    for i in range(1,int(pages)+1):
        url = "https://cn.bing.com/search?q=site%3a"+site+"&go=Search&ds&first="+ str((int(i)-1)*10) +"&FROM=PERE"
        html = requests.get(url,headers=headers)
        soup = BeautifulSoup(html.content,'html.parser')
        job_bt = soup.findAll('h2')
        for i in job_bt:
            link = i.a.get('href')
            domain = str(urlparse(link).scheme + "://" + urlparse(link).netloc)
            if domain in Subdomain:
                pass
            else:
                Subdomain.append(domain)
                print(domain)
if __name__ == '_main_':
    if len(sys.argv) == 3:
        site = sys.argv[1]
        page = sys.argv[2]
    else:
        print("usage: %s baidu.com 10"% sys.argv[0]) #输出帮助信息
        sys.exit(-1)
    Subdomain = bing_search(site,page)

邮件爬取

在针对目标系统进行渗透的过程中,如果目标服务器安全性很高,通过服务器很难获取目标权限时,通常会采用社工的方式对目标服务进行进一步的攻击。邮件钓鱼攻击是常见的攻击方式之一。在进行钓鱼之前,需要针对目标相关人员的邮件信息进行全面采集。
此处邮件采集工具主要通过国内常见的搜索引擎(百度、Bing 等进行搜集)。针对搜索界面的相关邮件信息进行爬取、处理等操作之后。利用获得的邮箱账号批量发送钓鱼邮件,等待目标用户或者管理员点击之后执行,进而获得目标的权限
邮件采集工具所用到的库如下所示

1
2
3
4
5
import sys
import getopt
import request
from bs4 import BeautifulSoup
import re

在程序的起始部分,在执行过程中没有发生异常时,则执行定义的 start () 函数。通过 sys.argv [] 实现外部指令的接受。其中,sys.argv [0] 表示代码本身的文件路径,sys.argv [1:] 表示从第一个命令行参数到输入的最后一个命令行参数,存储形式为 list 类型:

1
2
3
4
5
6
if __name__ == '__main__'
    #定义异常
    try:
        start(sys.argv[1:])
    except KeyboardInterrupt:
        print("interrupted by user, killing all threads...")

编写命令行参数处理功能。此处主要应用 getopt.getopt () 函数处理命令行参数,该函数目前有短选项和长选项两种格式。短选项格式为 "-" 加上单个字母选项;长选项格式为 "--" 加上一个单词选项。opts 为一个两元组列表,每个元素形式为 "(选项串,附加参数)"。当没有附加参数时,则为空串。之后通过 for 语句循环输出 opts 列表中的数值并赋值给自定义变量:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
def start(argv):
    url = " "
    pages = " "
    if len(sys.argv) < 2:
        print("-h 帮助信息 ;\n")
        sys.exit()
    #定义异常处理
    try:
        bannner()
        opts,args = getopt.getopt(argv,"-u;-p;-h")
    except getopt.GetoptError:
        print('Error an argument!')
        sys.exit()
    for opt,arg in opts:
        if opt == "-u":
            url = args
        elif opt == "-p":
            pages = arg
        elif opt == "-h":
            print(usage())
    launcher(url,pages)

输出帮助信息,增加代码工具的可读性和易用性。为了使输出信息更加美观简洁,可以通过转译字符设置输出字体颜色,从而实现需要的效果,开头部分包含三个参数:显示方式、前景色、背景色。这三个参数是可选的,可以只写其中的某一参数。结尾部分可以省略,但是为了书写规范,建议以 "\033 [0m" 结尾

1
2
开头:\033[显示方式;前景色;背景色m]
结尾部分:\033[0m

示例代码:

1
2
print('\033[0;30;41m 你好 \033[0m')
print('\033[0;30;47m 你好 \033[0m')

输出显示:

先以图案形式输出脚本出自 MS08067 实验室,然后输出有关脚本使用的帮助信息,即可执行参数执行以及对应的功能简介

1
2
3
4
5
6
7
8
9
10
#banner信息
def banner():
print('\033[1;34m###############################################################################################\033[0m\n''\033[1;34m#############################################\033[1;32mMS08067实验室\033[1;34m#############################################\033[0m\n''\033[1;34m##########################################################################################################\033[0m\n')
#使用规则
def usage():
print('-h: --help 帮助;')
print('-u: --url 域名;')
print('-p: --pages 页数;')
print('eg:python -u "www.baidu.com" -p 100'+'\n')
sys.exit()

同时也可以根据自己的喜好设置输出不同类型的字体颜色或者图案
确定搜索邮件的关键字,并调用 bing_search () 和 baidu_search () 两个函数,返回 Bing 与百度两大搜索引擎的查询结果,由获取到的结果进行列表合并,去重之后循环输出

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#漏洞回调函数
def launcher(url,pages):
email_num = []
key_words = ['email','mail','mailbox','邮件','邮箱','postbox']
for page in range(1,int(pages)+1):
for key_word in key_words:
bing_emails = bing_search(url,page,key_word)
baidu_emails = baidu_search(url,page,key_word)
sum_emails = bing_emails + baidu_emails
for email in sum_emails:
if email in email_num:
pass
else:
print(email)
with open('data.txt','a+') as f:
f.write(email + '\n')
email_num.append(email)

用 Bing 搜索引擎进行邮件爬取。Bing 引擎具有反爬系统,会通过限定 referer、cookie 等信息来确定是否是网页爬取操作。可以通过指定 referer 与 request.session () 函数自动获取 cookie 信息,绕过 Bing 搜索引擎的防爬防护

1
2
3
4
5
6
7
8
def bing_search(url,page,key_word):
referer = "http://cn.bing.com/search?q=email+site%3abaidu.com&qs=n&sp=-1&pq=emailsite%3baidu.com&first=1&FROM=PERE1"
conn = requests.session()
bing_url = "http://cn.bing.com/search?q=" + key_word + "+site%3a" + url + "&qs=n&sp=-1&pq=" + key_word + "site%3a" + url + "&first=" +str((page-1)*10) + "&FROM=FEERE1"
conn.get('http://cn.bing.com',headers=headers(referer))
r = conn.get(bing_url,stream=True,headers=headers(referer),timeout=8)
emails = search_email(r.text)
return emails

用百度搜索引擎进行邮件爬取。同样的,百度搜索引擎也做了反爬防护,相对于 Bing 来说,百度不仅对 referer 和 cookie 进行校验,也同时在页面中通过 JavaScript 语句进行动态请求链接,从而导致不能动态获取页面中的信息。可以通过对链接的提取,再进行 request 请求,从而绕过百度搜索引擎的反爬设置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
def baidu_search(url,page,key_word):
email_list = []
emails = []
referer = "https://www.baidu.com/s?wd=email+site%3Abaidu.com&pn=1"
baidu_url = "https://www.baidu.com/s?wa="+key_word+"+site%3A"+url+"&pn="+str((page-1)*10)
conn = requests.session
conn.get(referer,headers=headers(referer))
r = conn.get(baidu_url,headers=headers(referer))
soup = BeautifulSoup(r.txt,'html')
tagh3 = soup.find_all('h3')
for h3 in tagh3:
href = h3.find('a').get('href')
try:
r = requests.get(href,headers=headers(referer),timeout=8)
emails = search_email(r.txt)
except Exception as e:
pass
for email in emails:
email_list.append(email)
return email_list

接下来通过正则表达式获取邮箱号码,此处也可换成目标企业邮箱的正则表达式:

1
2
3
4
5
6
7
8
9
10
11
def search_email(html):
emails = re.findall(r"[a-z0-9\.\-+_]+@[a-z0-9\.\-+_]+\.[a-z]+",html,re.I)
return emails
def headers(referer):
headers = {'User-Agent':'Mozilla/5.0(X11;Linux x86_64;rv:60.0) Gecko/20100101 Firefoc/60.0',
'Accept':'*/*'
'Accept-Language': 'en-US,en;q=0.5',
'Accept-Encoding': 'gzip,deflate',
'Referer':referer
}
return headers

用 python3 执行脚本,-u 参数指定域名,-p 参数指定搜索引擎的页数,如:

1
python3 ce.py -u "baidu.com" -p 1