Metasploit凭证入库

  • 6 分钟阅读
  • 标签: 
  • metasploit

前言

  • 在进入目标主机进行信息收集时会收集到各种密码凭证,Metasploit提供了管理从目标主机上收集到的凭证的接口。前提是需要开启msfdb服务。
  • 所以需要初始化postgres数据库,初始化数据库在metasploit官方的issues上已经是一个经久不衰的话题,非常多人遇到了问题,下面来填了数据库初始化这个坑。

初始化数据库

  • 安装postgresql,各个系统的安装方式不一样,有些系统会在安装完成后执行钩子程序添加postgres用户,有些系统就没有,请自行添加。
  • 先添加postgres用户密码passwd postgres输入两遍密码,su - postgres -c "initdb --locale en_US.UTF-8 -D '/var/lib/postgres/data'",输入之前设置的postgres密码。
  • 先别急着初始化msfdb,数据库默认使用/var/run/postgres作为套接字的目录,普通用户没有权限访问。
  • 取消/usr/share/postgresql/postgresql.conf.sample文件里面的unix_socket_directories = '/tmp' # comma-separated list of directories注释。
  • 重新打开终端执行初始化命令,执行export PGHOST=/tmp设置环境变量,重启postgres数据库服务sudo systemctl restart postgresql.service
  • 执行./msfdb reinit初始化msfdb数据库服务,没什么意外的话,应该会出现下面的界面。

image-20200903153206140.png

开发模板

def report_store_config(config)
    service_data = {
        address: config[:hostname], # 就是服务的IP地址
        port: config[:port], # 服务开放的端口
        service_name: 'smb', # 服务的名称
        protocol: 'tcp', # 服务连接的协议
        workspace_id: myworkspace_id # 这个不用改(默认)
        }

    credential_data = {
        origin_type: :session, # 来源类型,cong目标session得到的就是当前session的实例化对象
        session_id: session_db_id, # session的id
        post_reference_name: refname, # 当前执行的模块名称,就是你用哪一个模块获取的信息
        private_type: :password, # 密码类型,是明文密码还是,hash密文
        private_data: config[:password], # 密码,字符串,一定要UTF-8编码,不然进数据库会报错
        username: config[:username] # 用户名
        }.merge(service_data)

    credential_core = create_credential(credential_data)

    login_data = {
        core: credential_core,
        status: Metasploit::Model::Login::Status::UNTRIED # 密码登录的状态,下面详细说明
        }.merge(service_data)

    create_credential_login(login_data)
end

metasploit凭证ER图

  • 如果只看凭证这块的话可以从metasploit_credential_logins这个表看起,上面代码service_data就是创建services表的,如凭证中的服务没有会自动创建服务,credential_data则是创建凭证需要用到的。

image-20201130105524896.png

service_data

属性描述
address获取到的服务IP地址
port服务对应的端口
service_name大概就这些:ssh,http,https,ftp,mssql,postgres,smb,jboss…,Nmap扫出什么就写什么
protocoltcp,udp
workspace_id默认
  • 凭证的来源

image-20201130110158304.png

credential_data

属性描述
origin_type数据来源的类型::sessiom(是在目标session获取的),:import(从文件导入的),:services(auxiliary模块扫描得到的),:manuals(手工添加的),还有爆破出来等等
session_id如果origin_type是在session获取就要填,session的id
post_reference_name通过哪一个post模块得到的,编写后渗透模块选这个
module_fullname编写auxiliary模块,选这个
filename密码是通过从文件导入的,选这个
private_type密码的类型::password(明文密码),:ssh_key(ssh_密钥),:ntlm_hash(NTLM_HASH),:postgres_md5(postgres数据库 MD5),:nonreplayable_hash(不可重放hash),:(空白)
private_data比较重要的数据,有帐号和密码
public_data不那么重要的数据,普通用户可以通过API查看,只能看到用户名
realm_keyMetasploit::Model::Realm::Key::XXX,realm_type (domain db2db sid pgdb rsync wildcard)
realm_value对应realm_key的值
username用户名
jtr_format如果通过hashcat或者John the ripper这些密码恢复工具得到的就需要填写
  • 帐号密码都是分表存储的,为什么要这样呢?,为了方便auxiliary模块从数据库中获取用户名和密码进行爆破服务,简单来说一个表就是一个字典。

image-20201130111105864.png

login_data

属性描述
status没有测试过不知道密码的:Metasploit::Model::Login::Status::UNTRIED通过爆破登录成功的:Metasploit::Model::Login::Status::SUCCESSFUL密码不正确的:Metasploit::Model::Login::Status::INCORRECT无法连接的:Metasploit::Model::Login::Status::UNABLE_TO_CONNECT被锁定了的:Metasploit::Model::Login::Status::LOCKED_OUT被禁用了的:Metasploit::Model::Login::Status::DISABLED

使用示例

  • 下面是hashdump和kiwi密码hash入库代码片段,通过将收集到的信息导进库里面,在控制台输入creds命令可查看全部凭证,并且可以通过搜索指定的IP或者IP段显示密码凭证,也可以筛选制定服务类型或者密码类型的凭证。在也不用往上找之前收集的密码了。
def report_creds(user_data)
    user = user_data.user_name
    pass = "#{user_data.lanman}:#{user_data.ntlm}"
    return if (user.empty? || pass.include?('aad3b435b51404eeaad3b435b51404ee'))

    # Assemble data about the credential objects we will be creating
    credential_data = {
        origin_type: :session,
        post_reference_name: 'hashdump',
        private_data: pass,
        private_type: :ntlm_hash,
        session_id: client.db_record.id,
        username: user,
        workspace_id: shell.framework.db.workspace.id
        }

    credential_core = shell.framework.db.create_credential(credential_data)

    # Assemble the options hash for creating the Metasploit::Credential::Login object
    login_data = {
        core: credential_core,
        status: Metasploit::Model::Login::Status::UNTRIED,
        address: ::Rex::Socket.getaddress(client.sock.peerhost, true),
        port: 445,
        service_name: 'smb',
        protocol: 'tcp',
        workspace_id: shell.framework.db.workspace.id
        }

    shell.framework.db.create_credential_login(login_data)
end

image-20201130113243014.png

image-20201130113243014

image-20201130113349878.png

  • 开启Metasploit的数据库服务可以保存你的操作记录,就算把控制台退出了或者session掉线了。之前的操作过命令和输出都会保存在数据库里。
  • 如果你在收集信息的时候无法将密文解密,可以先保存到数据库,只要你还知道算法,在入库的时候提交jtr_format,后面可以调用hashcat和John the ripper进行自动化的字典攻击。

image-20200905153833548.png

image-20200905153833548

  • 重要的是Metasplot还提供API接口,这使得自动化和其他工具联动成为了可能。

参考

https://github.com/rapid7/metasploit-framework/pull/14432

https://github.com/rapid7/metasploit-framework/blob/master/documentation/api/v1/credential_api_doc.rb