子域名爆破

Preface

  Github传送地址: findSubDomains

  这个脚本源自lijiejie/subDomainsBrute, 用来探测子域名,我删除了很多代码,也添加了不少注释,使得代码变得更简练和清晰。

  你可以在这看到找到这个项目: https://github.com/lijiejie/subDomainsBrute

Dependencies

pip install dnspython gevent

Usage

python findSubDomains.py [your target domain]

Example

?  subDomainsBrute git:(master) ? python findSubDomains.py baidu.com
[*] Validate DNS servers ...
[+] Check DNS Server 223.6.6.6        < OK >   Found 4
[*] Found 4 available DNS Servers in total
[+] Load sub names ...
[+] Load sub names ...
[*] Exploiting sub domains of  baidu.com
[+] There are 15372 subs waiting for trying ...
--------------------------------------
[*] Initializing 100 threads
123.baidu.com   115.239.210.27, 115.239.211.112
0.baidu.com     180.149.144.203
1.baidu.com     61.135.186.115
11.baidu.com    220.181.57.55
12.baidu.com    220.181.57.166
100.baidu.com   180.149.131.33
1111.baidu.com  180.97.93.38
2013.baidu.com  180.149.131.33
2014.baidu.com  115.239.210.174, 180.97.33.136
365.baidu.com   180.149.131.33
3g.baidu.com    115.239.217.67, 115.239.217.68
7.baidu.com     61.135.185.212

代码

链接

#!/usr/bin/env python
# -*- encoding: utf-8 -*-
"""
    @version : subDomainsBrute 1.0.6
    @author : lijiejie
    description : A simple and fast sub domains brute tool for pentesters
    @contact : my[at]lijiejie.com (http://www.lijiejie.com)
    Modified by : starnight_cyber
    @contact : [email protected]
    blog : http://www.cnblogs.com/Hi-blog/
    Time : 2017.09.23
"""

"""
    program description : subDomainsBrute is for finding sub domains of a target domain
    a very simple way turns to be brute force, simple and effective
    ~ and the idea is simple too, find the target sub domains using dictionary (important)
    ~ using the found sub domains for further brute force
    ~ before that, you have to know how the DNS works, please refer to concerned materials
"""

import gevent
from gevent import monkey
monkey.patch_all()
from gevent.pool import Pool
from gevent.queue import PriorityQueue
import sys
import re
import dns.resolver
import time
import optparse
import os
from lib.consle_width import getTerminalSize
from multiprocessing import cpu_count

class SubNameBrute:
    """
        receive commandline args and do some initialization work
    """
    def __init__(self, target, options):
        self.start_time = time.time()
        self.target = target.strip()
        self.options = options
        self.scan_count = self.found_count = 0
        self.console_width = getTerminalSize()[0] - 2

        # create dns resolver pool ~ workers
        self.resolvers = [dns.resolver.Resolver(configure=False) for _ in range(options.threads)]
        for resolver in self.resolvers:
            resolver.lifetime = resolver.timeout = 10.0

        self.print_count = 0
        self.STOP_ME = False

        # load dns servers and check whether these dns servers works fine ?
        self._load_dns_servers()

        # load sub names
        self.subs = []                          # subs in file
        self.goodsubs = []                      # checks ok for further exploitation
        self._load_subname(‘dict/subnames.txt‘, self.subs)

        # load sub.sub names
        self.subsubs = []
        self._load_subname(‘dict/next_sub.txt‘, self.subsubs)

        # results will be save to target.txt
        self.outfile = open(target + ‘.txt‘, ‘a‘)

        self.ip_dict = set()                            #
        self.found_sub = set()

        # task queue
        self.queue = PriorityQueue()
        for sub in self.subs:
            self.queue.put(sub)

    """
        Load DNS Servers(ip saved in file), and check whether the DNS servers works fine
    """
    def _load_dns_servers(self):

        print ‘[*] Validate DNS servers ...‘
        self.dns_servers = []

        # create a process pool for checking DNS servers, the number is your processors(cores) * 4, just change it!
        processors = cpu_count() * 4
        pool = Pool(processors)

        # read dns ips and check one by one
        for server in open(‘dict/dns_servers.txt‘).xreadlines():
            server = server.strip()
            if server:
                pool.apply_async(self._test_server, (server, ))

        pool.join()                                     # waiting for process finish
        self.dns_count = len(self.dns_servers)

        sys.stdout.write(‘\n‘)
        print ‘[*] Found %s available DNS Servers in total‘ % self.dns_count
        if self.dns_count == 0:
            print ‘[ERROR] No DNS Servers available.‘
            sys.exit(-1)

    """
        test these dns servers whether works fine
    """
    def _test_server(self, server):

        # create a dns resolver and set timeout
        resolver = dns.resolver.Resolver()
        resolver.lifetime = resolver.timeout = 10.0

        try:
            resolver.nameservers = [server]

            # test : resolving a known domain, and check whether can get the right result
            answers = resolver.query(‘public-dns-a.baidu.com‘)
            if answers[0].address != ‘180.76.76.76‘:
                raise Exception(‘incorrect DNS response‘)
            self.dns_servers.append(server)
        except:
            self._print_msg(‘[-] Check DNS Server %s <Fail>   Found %s‘ % (server.ljust(16), len(self.dns_servers)))

        self._print_msg(‘[+] Check DNS Server %s < OK >   Found %s‘ % (server.ljust(16), len(self.dns_servers)))

    """
        load sub names in dict/*.txt, one function would be enough
        file for read, subname_list for saving sub names
    """
    def _load_subname(self, file, subname_list):
        self._print_msg(‘[+] Load sub names ...‘)

        with open(file) as f:
            for line in f:
                sub = line.strip()
                if sub and sub not in subname_list:
                    tmp_set = {sub}

                    """
                        in case of the sub names which contains the following expression
                        and replace them {alphnum}, {alpha}, {num} with character and num
                    """
                    while len(tmp_set) > 0:
                        item = tmp_set.pop()
                        if item.find(‘{alphnum}‘) >= 0:
                            for _letter in ‘abcdefghijklmnopqrstuvwxyz0123456789‘:
                                tmp_set.add(item.replace(‘{alphnum}‘, _letter, 1))
                        elif item.find(‘{alpha}‘) >= 0:
                            for _letter in ‘abcdefghijklmnopqrstuvwxyz‘:
                                tmp_set.add(item.replace(‘{alpha}‘, _letter, 1))
                        elif item.find(‘{num}‘) >= 0:
                            for _letter in ‘0123456789‘:
                                tmp_set.add(item.replace(‘{num}‘, _letter, 1))
                        elif item not in subname_list:
                            subname_list.append(item)

    """
        for better presentation of brute force results, not really matters ...
    """
    def _print_msg(self, _msg=None, _found_msg=False):
        if _msg is None:
            self.print_count += 1
            if self.print_count < 100:
                return
            self.print_count = 0
            msg = ‘%s Found| %s Groups| %s scanned in %.1f seconds‘ % (
                self.found_count, self.queue.qsize(), self.scan_count, time.time() - self.start_time)
            sys.stdout.write(‘\r‘ + ‘ ‘ * (self.console_width - len(msg)) + msg)
        elif _msg.startswith(‘[+] Check DNS Server‘):
            sys.stdout.write(‘\r‘ + _msg + ‘ ‘ * (self.console_width - len(_msg)))
        else:
            sys.stdout.write(‘\r‘ + _msg + ‘ ‘ * (self.console_width - len(_msg)) + ‘\n‘)
            if _found_msg:
                msg = ‘%s Found| %s Groups| %s scanned in %.1f seconds‘ % (
                    self.found_count, self.queue.qsize(), self.scan_count, time.time() - self.start_time)
                sys.stdout.write(‘\r‘ + ‘ ‘ * (self.console_width - len(msg)) + msg)
        sys.stdout.flush()

    """
        important : assign task to resolvers
    """
    def _scan(self, j):
        self.resolvers[j].nameservers = [self.dns_servers[j % self.dns_count]]
        while not self.queue.empty():
            sub = self.queue.get(timeout=1.0)

            # print cur_sub_domain
            try:
                cur_sub_domain = sub + ‘.‘ + self.target
                answers = self.resolvers[j].query(cur_sub_domain)
            except:
                continue

            if answers:
                ips = ‘, ‘.join(sorted([answer.address for answer in answers]))

                # exclude : intranet or kept addresses
                if ips in [‘1.1.1.1‘, ‘127.0.0.1‘, ‘0.0.0.0‘]:
                    continue
                if SubNameBrute.is_intranet(answers[0].address):
                    continue

                self.found_sub.add(cur_sub_domain)
                for answer in answers:
                    self.ip_dict.add(answer.address)

                if sub not in self.goodsubs:
                    self.goodsubs.append(sub)

                print cur_sub_domain, ‘\t‘, ips
                self.outfile.write(cur_sub_domain + ‘\t‘ + ips + ‘\n‘)

    @staticmethod
    def is_intranet(ip):
        ret = ip.split(‘.‘)
        if len(ret) != 4:
            return True
        if ret[0] == ‘10‘:
            return True
        if ret[0] == ‘172‘ and 16 <= int(ret[1]) <= 32:
            return True
        if ret[0] == ‘192‘ and ret[1] == ‘168‘:
            return True
        return False

    """
        assign task to threads ...
    """
    def run(self):
        threads = [gevent.spawn(self._scan, i) for i in range(self.options.threads)]

        print ‘[*] Initializing %d threads‘ % self.options.threads

        try:
            gevent.joinall(threads)
        except KeyboardInterrupt, e:
            msg = ‘[WARNING] User aborted.‘
            sys.stdout.write(‘\r‘ + msg + ‘ ‘ * (self.console_width - len(msg)) + ‘\n\r‘)
            sys.stdout.flush()

if __name__ == ‘__main__‘:
    parser = optparse.OptionParser(‘usage: %prog [options] target.com‘, version="%prog 1.0.6")
    parser.add_option(‘-f‘, dest=‘file‘, default=‘subnames.txt‘,
                      help=‘File contains new line delimited subs, default is subnames.txt.‘)
    parser.add_option(‘--full‘, dest=‘full_scan‘, default=False, action=‘store_true‘,
                      help=‘Full scan, NAMES FILE subnames_full.txt will be used to brute‘)
    parser.add_option(‘-t‘, ‘--threads‘, dest=‘threads‘, default=100, type=int,
                      help=‘Num of scan threads, 100 by default‘)

    (options, args) = parser.parse_args()
    if len(args) < 1:
        parser.print_help()
        sys.exit(0)

    # initialization ...
    d = SubNameBrute(target=args[0], options=options)

    print ‘[*] Exploiting sub domains of ‘, args[0]
    print ‘[+] There are %d subs waiting for trying ...‘ % len(d.queue)
    print ‘--------------------------------------‘
    d.run()
    print ‘--------------------------------------‘
    print ‘%d subnames found‘ % len(d.found_sub)
    print ‘[*] Program running %.1f seconds ‘ % (time.time() - d.start_time)

    print ‘[*] It is usually not recommended to exploit second-level sub domains,because needs to try %d times‘           % (len(d.subsubs) * len(d.goodsubs))
    go_on = raw_input(‘[-] Are you consist? YES/NO : ‘)
    if go_on == ‘YES‘ or go_on == ‘y‘ or go_on == ‘Y‘ or go_on == ‘yes‘:
        print ‘[*]Exploiting second level sub names ...‘

        d.queue = PriorityQueue()
        for subsub in d.subsubs:
            for sub in d.goodsubs:
                subname = subsub + ‘.‘ + sub
                d.queue.put(subname)

        print ‘There are %d subs waiting for trying ...‘ % len(d.queue)
        d.run()
    else:
        pass

    print ‘%d subnames found in total‘ % len(d.found_sub)
    print ‘[*]Results are saved to threes files starts with %s‘ % args

    """
        save ips and domains to files
    """
    with open(args[0]+‘-ip.txt‘, ‘w‘) as f:
        for ip in d.ip_dict:
            f.write(ip + ‘\n‘)

    with open(args[0] + ‘-subdomain.txt‘, ‘w‘) as f:
        for domain in d.found_sub:
            f.write(domain + ‘\n‘)

    print ‘[*] Program running %.1f seconds ‘ % (time.time() - d.start_time)

    d.outfile.flush()
    d.outfile.close()

需要提供两个子域名字典,就不提供百度云下载链接了,具体请参看Github findSubDomains

不断完善中,希望能收到您的意见 ~ RFC。

时间: 2024-10-16 02:26:33

子域名爆破的相关文章

ubuntu进行子域名爆破

好记性不如烂笔头,此处记录一下,ubuntu进行子域名的爆破. 先记录一个在线的子域名爆破网址,无意中发现,很不错的网址,界面很干净,作者也很用心,很感谢. https://phpinfo.me/domain/ 介绍一下,我在ubuntu上面安装的Sublist3r. 先放GitHub地址,感谢作者. https://github.com/aboul3la/Sublist3r 安装过程,首先git下来. git clone https://github.com/aboul3la/Sublist3

子域名爆破&amp;C段查询&amp;调用Bing查询同IP网站

在线子域名爆破 1 <?php 2 3 function domainfuzz($domain) { 4 $ip = gethostbyname($domain); 5 preg_match("/\d+\.\d+\.\d+\.\d+/",$ip,$arr); 6 return $arr; 7 } 8 9 function main() { 10 if(isset($_GET['q'])) { 11 $return = array(); 12 $domain = trim($_GE

子域名收集的一些姿势

测试dns域传送 测试方式如图: 当然,这种方式不一定都能成功,但也不失为一种获取二级域名的方式. 反查whois 工具:站长工具 1 查询whois http://whois.chinaz.com/baidu.com 2 反查whois http://whois.chinaz.com/reverse?host=domainmaster@baidu.com&ddlSearchMode=1 获得关联域名信息 通过搜索引擎 搜索推荐工具:https://github.com/laramies/the

小米范工具系列之九:小米范子域名收集工具

小米范子域名收集工具为一款收集子域名(二级域名.三级域名.四级域名)的工具. 工具的工作流程如下: // 1.获取常用记录类型.MX NS SOA// 2.测试每个dns服务器的区域传送.获取泛域名解析ip列表加入黑名单(也可手动输入黑名单ip).// 3.通过搜索引擎.获取其他接口查询二级域名(百度.必应.netcraft,可设置爬取线程也爬取条数)// 4.通过字典爆破二级域名(可自定义线程数即字典).// 5.获取上面几步收集的域名对应的ip地址列表.// 6.反查(爱站)上一步得到的ip

PJzhang:子域名发掘工具Sublist3r

猫宁!!! 参考链接:https://www.freebuf.com/sectool/90584.html 作者上一次更新是2018年10月16日了,sublist3r中融合有另外一个子域名爆破工具SubBrute. sublist3r github地址 https://github.com/aboul3la/Sublist3r subbrute github地址 https://github.com/TheRook/subbrute 操作在kali linux上进行 下载到本地,需要pip3

JSFinder:一个在js文件中提取URL和子域名的脚本

JSFinder介绍 JSFinder是一款用作快速在网站的js文件中提取URL,子域名的脚本工具. 支持用法 简单爬取 深度爬取 批量指定URL/指定JS 其他参数 以往我们子域名多数使用爆破或DNS中获得,这个脚本从JS文件中匹配出子域也算是添砖加瓦. 简单爬取示例 子域名清单 https://github.com/Threezh1/JSFinder 点个赞 (0) 原文地址:https://www.cnblogs.com/nul1/p/11140910.html

利用.htaccess绑定子域名到子目录(亲测万网可用)

http://www.xmgho.com/archives/783.html 利用.htaccess绑定域名到子目录,前提你的空间服务器必须支持apache的rewrite功能,只有这样才能使用.htaccess.如果你的空间是Linux服务器 一般默认都开启了的. 绑定域名 登陆域名管理台(如DNSPod) 把需要绑定的域名 解析到你的空间:登陆虚拟主机/空间管理台(如万网) 绑定域名到空间; 首先在本地建个txt文件,复制下面的代码修改替换你要绑的域名和目录,并传到网站主目录下再改成为.ht

子域名查找

利用SubDomainScanner_V0.8_Beta.exe工具进行查找,如图所示: SubDomainScanner_V0.8_Beta.exe是一个子域名查找工具,利用它可以查找到输入域名的所有子域名. 在”输入域名“栏里输入所要查找域名,在查询引擎里选择Baidu,点击”搜索“ 大概几分钟后就会出来结果. 结果会显示输入域名下的子域名还会给出相应的IP地址. 格式如上图中输出框中显示的内容. 想要保存搜索的结果可以直接”导出“,点击文件——导出选项,根据需要把结果导出,默认的导出路径是

Centos 子域名绑定子目录过程记录

加载重写模块 LoadModule rewrite_module modules/mod_rewrite.so 添加配置 RewriteEngine on RewriteMap lowercase int:tolower RewriteMap vhost txt:/opt/lampp/etc/vhost.map RewriteCond ${lowercase:%{SERVER_NAME}} ^(.+)$ RewriteCond ${vhost:%1} ^(/.*)$ RewriteRule ^(