rapid7 / metasploit-framework

Metasploit Framework
https://www.metasploit.com/
Other
33.78k stars 13.9k forks source link

ssh login windows gather proof does not work #14351

Closed adfoster-r7 closed 3 years ago

adfoster-r7 commented 3 years ago

Steps to reproduce

Run ssh_login against a windows target.

Expected behavior

Proof if gathered successfully

Current behavior

Running against the hackthebox room fails:

use ssh login
run rhosts=10.10.10.184 username=nadine password=L1k3B1gBut7s@W0rk
> run rhosts=10.10.10.184 username=nadine password=L1k3B1gBut7s@W0rk

[+] 10.10.10.184:22 - Success: 'nadine:L1k3B1gBut7s@W0rk' ''id' is not recognized as an internal or external command,  operable program or batch file.  '
[*] Command shell session 6 opened (10.10.14.37:55940 -> 10.10.10.184:22) at 2020-11-05 01:43:52 +0000
[-] 10.10.10.184:22 - While a session may have opened, it may be bugged.  If you experience issues with it, re-run this module with 'set gatherproof false'.  Also consider submitting an issue at github.com/rapid7/metasploit-framework with device details so it can be handled in the future.
[*] Scanned 1 of 1 hosts (100% complete)
[*] Auxiliary module execution completed

Additional Information

Module/Datastore

The following global/module datastore, and database setup was configured before the issue occurred:

Collapse ``` [framework/core] loglevel=3 [framework/database] default_db=local-https-data-service [framework/database/local-https-data-service] url=[Filtered] cert=[Filtered] skip_verify=[Filtered] api_token=[Filtered] [framework/features] wrapped_tables=true RHOST_HTTP_URL=true [framework/ui/console] ActiveModule=auxiliary/scanner/ssh/ssh_login [scanner/ssh/ssh_login] VERBOSE=false WORKSPACE= USERNAME= PASSWORD= USER_FILE= PASS_FILE= USERPASS_FILE= BRUTEFORCE_SPEED=5 BLANK_PASSWORDS=false USER_AS_PASS=false DB_ALL_CREDS=false DB_ALL_USERS=false DB_ALL_PASS=false STOP_ON_SUCCESS=false REMOVE_USER_FILE=false REMOVE_PASS_FILE=false REMOVE_USERPASS_FILE=false TRANSITION_DELAY=0 MaxGuessesPerService=0 MaxMinutesPerService=0 MaxGuessesPerUser=0 CreateSession=true InitialAutoRunScript= AutoRunScript= CommandShellCleanupCommand= RHOSTS= THREADS=1 ShowProgress=true ShowProgressPercent=10 RPORT=22 SSH_IDENT=SSH-2.0-OpenSSH_7.6p1 Ubuntu-4ubuntu0.3 SSH_TIMEOUT=30 SSH_DEBUG=false Proxies= GatherProof=true ```

History

The following commands were ran during the session and before this issue occurred:

Collapse ``` 12576 use ssh login 12585 run rhosts=10.10.10.184 username=nadine password=L1k3B1gBut7s@W0rk 12586 debug ```

Version/Install

The versions and install method of your Metasploit setup:

Collapse ``` Framework: 6.0.15-dev-9293e32f98 Ruby: ruby 2.7.2p137 (2020-10-01 revision 5445e04352) [x86_64-darwin19] Install Root: /Users/adfoster/Documents/code/metasploit-framework Session Type: Connected to remote_data_service: (https://localhost:5443). Connection type: http. Install Method: Git Clone ```
adfoster-r7 commented 3 years ago

I was having issues storing the creds successfully too, but it was fixed after an msfconsole restart - so unable to replicate and provide exact steps.

Here's the stack traces just incase it can be worked out later:

Writing PID to /Users/adfoster/.msf4/msf-ws.pid
Thin web server (v1.7.2 codename Bachmanity)
Maximum connections set to 1024
Listening on localhost:5443, CTRL+C to stop
#<Thread:0x00007ff9c070afc8@/Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:18 run> terminated with exception (report_on_exception is true):
/Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:24:in `rescue in block (2 levels) in start_processor_thread': undefined method `print_error' for #<JobProcessor:0x00007ff9c070b090> (NoMethodError)
    from /Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:21:in `block (2 levels) in start_processor_thread'
    from /Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:19:in `loop'
    from /Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:19:in `block in start_processor_thread'
/Users/adfoster/.rvm/rubies/ruby-2.6.6/lib/ruby/2.6.0/base64.rb:74:in `unpack1': invalid base64 (ArgumentError)
    from /Users/adfoster/.rvm/rubies/ruby-2.6.6/lib/ruby/2.6.0/base64.rb:74:in `strict_decode64'
    from /Users/adfoster/.rvm/rubies/ruby-2.6.6/lib/ruby/2.6.0/base64.rb:105:in `urlsafe_decode64'
    from /Users/adfoster/Documents/code/metasploit-framework/lib/metasploit/framework/data_service/remote/http/response_data_helper.rb:76:in `process_file'
    from /Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/servlet/loot_servlet.rb:46:in `block (2 levels) in report_loot'
    from /Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:22:in `block (2 levels) in start_processor_thread'
    from /Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:19:in `loop'
    from /Users/adfoster/Documents/code/metasploit-framework/lib/msf/core/web_services/job_processor.rb:19:in `block in start_processor_thread'
Exiting!

Code link: https://github.com/rapid7/metasploit-framework/blob/6f75fc77e64a200b67b1c0afc16a23edd6399483/lib/msf/core/web_services/job_processor.rb#L24

Additionally the creds were not persisting due to validation errors on the workspace field when attached to the remote dataservice

h00die commented 3 years ago

This line should have hit: https://github.com/rapid7/metasploit-framework/blob/9e51507e71322274b405ba239875ee62af31e8f2/lib/metasploit/framework/login_scanner/ssh.rb#L161

Which would then make https://github.com/rapid7/metasploit-framework/blob/9e51507e71322274b405ba239875ee62af31e8f2/lib/metasploit/framework/login_scanner/ssh.rb#L162 kick off. I suspect that syntax may have changed. can you provide the output of systeminfo?

adfoster-r7 commented 3 years ago

Thanks for the pointers :+1:

Looks like it goes into the windows block successfully:

From: /Users/adfoster/Documents/code/metasploit-framework/lib/metasploit/framework/login_scanner/ssh.rb:120 Metasploit::Framework::LoginScanner::SSH#gather_proof:

    115:         def gather_proof
    116:           proof = ''
    117:           begin
    118:           proof = ssh_socket.exec!("id\n").to_s
    119:           require 'pry'; binding.pry
 => 120:            if (proof =~ /id=/)
    121:                 proof << ssh_socket.exec!("uname -a\n").to_s
    122:                 if (proof =~ /JUNOS /)
    123:                   # We're in the SSH shell for a Juniper JunOS, we can pull the version from the cli
    124:                   # line 2 is hostname, 3 is model, 4 is the Base OS version
    125:                   proof = ssh_socket.exec!("cli show version\n").split("\n")[2..4].join(", ").to_s

[1] pry(#<Metasploit::Framework::LoginScanner::SSH>)> proof
=> "'id' is not recognized as an internal or external command,\r\noperable program or batch file.\r\n"

Then executing ssh_socket.exec!("systeminfo\n").to_s gives ERROR: Access denied:

From: /Users/adfoster/Documents/code/metasploit-framework/lib/metasploit/framework/login_scanner/ssh.rb:165 Metasploit::Framework::LoginScanner::SSH#gather_proof:

    160:                 # Windows
    161:                 elsif proof =~ /is not recognized as an internal or external command/
    162:                   proof = ssh_socket.exec!("systeminfo\n").to_s
    163:                   /OS Name:\s+(?<os_name>.+)$/ =~ proof
    164:                   /OS Version:\s+(?<os_num>.+)$/ =~ proof
 => 165:                   if os_name && os_num
    166:                     proof = "#{os_name.chomp} #{os_num.chomp}"
    167:                   end
    168:                 # mikrotik
    169:                 elsif proof =~ /bad command name id \(line 1 column 1\)/
    170:                   proof = ssh_socket.exec!("/ system resource print\n").to_s

[6] pry(#<Metasploit::Framework::LoginScanner::SSH>)> proof
=> "ERROR: Access denied\r\r\n"

I'm not a windows expert, I'm not sure what permissions are required for sysinfo, wmic doesn't work either:

[1] pry(#<Metasploit::Framework::LoginScanner::SSH>)> ssh_socket.exec!("wmic os get Caption,Version /value\n").to_s
=> "ERROR:\r\r\nDescription = Access denied\r\r\n"

Maybe ver or whoami would be a good fallback? Let me know your thoughts :+1:

[2] pry(#<Metasploit::Framework::LoginScanner::SSH>)> ssh_socket.exec!("whoami\n").to_s
=> "servmon\\nadine\r\n"
[3] pry(#<Metasploit::Framework::LoginScanner::SSH>)> ssh_socket.exec!("ver\n").to_s
=> "\r\nMicrosoft Windows [Version 10.0.18363.752]\r\n"
h00die commented 3 years ago

i'd favor ver as a fallback since we're just trying to determine OS. Even if its too tough to parse out the version string there (between windows 10, 8, 8.1, 7, 2003, 2008, etc), even just confirming "Microsoft Windows" was in there would be enough (in theory) to confirm what we need. Then maybe try an advance parse of the version number

adfoster-r7 commented 3 years ago

@h00die Thanks! Will get that added :+1: