-
Notifications
You must be signed in to change notification settings - Fork 14
/
Copy pathwemo-info.nse
144 lines (125 loc) · 5.84 KB
/
wemo-info.nse
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
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
local nmap = require "nmap"
local http = require "http"
local stdnse = require "stdnse"
local string = require "string"
local shortport = require "shortport"
description = [[
The Belkin Wemo Switch is a network enabled power outlet. This scripts obtains
information from Belkin Wemo Switch including nearby wireless networks and the
current switch state (ON/OFF).
There is a separate NSE script that may be used for changing the switch state.
No authentication is required.
Valid on Belkin Wemo Switch version WeMo_WW_2.00.10966.PVT-OWRT-SNS on 6/24/17
References:
* http://websec.ca/blog/view/Belkin-Wemo-Switch-NMap-Scripts
* https://www.tripwire.com/state-of-security/featured/my-sector-story-root-shell-on-the-belkin-wemo-switch/
* https://www.exploitee.rs/index.php/Belkin_Wemo
]]
---
-- @usage nmap -p49152,49153,49154 --script wemo-info.nse <target>
--
-- @output
-- | wemo-info:
-- | friendlyName: : Wemo Switch
-- | deviceType: urn:Belkin:device:controllee:1
-- | manufacturer: Belkin International Inc.
-- | manufacturerURL: http://www.belkin.com
-- | modelDescription: Belkin Plugin Socket 1.0
-- | modelName: Socket
-- | modelNumber: 1.0
-- | modelURL: http://www.belkin.com/plugin/
-- | serialNumber: 220333K0203A4E
-- | UDN: uuid:Socket-1_0-220333K0203A4E
-- | UPC: 123456789
-- | macAddress: EC1A59EE48E3
-- | firmwareVersion: WeMo_WW_2.00.10966.PVT-OWRT-SNS
-- | iconVersion: 0|49154
-- | binaryState: 1
-- | Switch is currently turned: ON
-- | Nearby wireless networks: Page:1/1/4$
-- | Visita Cozumel FTW|5|0|OPEN/NONE,
-- | PVGP-2|6|0|WPA1PSKWPA2PSK/TKIPAES,
-- | INFINITUM|8|65|WPA2PSK/AES,
-- |_INFINITUM|11|0|WPA1PSKWPA2PSK/TKIPAES,
--
-- @xmloutput
-- <elem key="deviceType">urn:Belkin:device:controllee:1</elem>
-- <elem key="manufacturer">Belkin International Inc.</elem>
-- <elem key="manufacturerURL">http://www.belkin.com</elem>
-- <elem key="modelDescription">Belkin Plugin Socket 1.0</elem>
-- <elem key="modelName">Socket</elem>
-- <elem key="modelNumber">1.0</elem>
-- <elem key="modelURL">http://www.belkin.com/plugin/</elem>
-- <elem key="serialNumber">220333K0203A4E</elem>
-- <elem key="UDN">uuid:Socket-1_0-220333K0203A4E</elem>
-- <elem key="UPC">123456789</elem>
-- <elem key="macAddress">EC1A59ED59C4</elem>
-- <elem key="firmwareVersion">WeMo_WW_2.00.10966.PVT-OWRT-SNS</elem>
-- <elem key="iconVersion">0|49153</elem>
-- <elem key="binaryState">1</elem>
-- <elem key="Switch is currently turned">ON</elem>
-- <elem key="Nearby wireless networks">Page:1/1/4$
Visita Cozumel FTW|5|0|OPEN/NONE,
PVGP-2|6|0|WPA1PSKWPA2PSK/TKIPAES,
INFINITUM|8|65|WPA2PSK/AES,
INFINITUM|11|0|WPA1PSKWPA2PSK/TKIPAES,
</elem>
---
author = "Pedro Joaquin <pjoaquin()websec.mx>"
license = "Same as Nmap--See https://nmap.org/book/man-legal.html"
categories = {"discover", "version", "safe"}
portrule = shortport.portnumber({49152,49153,49154})
local function GetInformation(host, port)
local uri = '/setup.xml'
local response = http.get(host, port, uri)
if response['status-line'] and response['status-line']:match("200 OK") then
--Verify parsing of XML from /setup.xml
local deviceType = response['body']:match("<deviceType>([^<]*)</deviceType>")
if not deviceType then
stdnse.debug1("Problem with XML parsing")
return nil,"Problem with XML parsing"
end
--Parse information from /setup.xml
local output = stdnse.output_table()
local keylist = {"friendlyName","deviceType","manufacturer","manufacturerURL","modelDescription", "modelName","modelName","modelNumber","modelURL","serialNumber","UDN","UPC","macAddress","firmwareVersion","iconVersion","binaryState"}
for _,key in ipairs(keylist) do
stdnse.debug1("Looking for : "..key)
output[key] = response['body']:match("<"..key..">([^<]*)</"..key..">")
end
--Identify current Switch state
local bstate="Switch is currently turned"
if output["binaryState"] == "1" then
output[bstate] = "ON"
else
output[bstate] = "OFF"
end
--Post request to obtain nearby wireless network information
local req = '<?xml ?><s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/" s:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"><s:Body><u:GetApList xmlns:u="urn:Belkin:service:WiFiSetup1:1"></u:GetApList></s:Body></s:Envelope>'
local path = "/upnp/control/WiFiSetup1"
local options = {header={["SOAPACTION"]='"urn:Belkin:service:WiFiSetup1:1#GetApList"', ["Content-Type"]="text/xml"}}
local result = http.post( host, port, path, options, nil, req)
stdnse.debug1("Status-a : %s", result['status-line'] or "No Response")
if result['status-line'] and result['status-line']:match("200 OK") then
output["Nearby wireless networks"] = result['body']:match("<ApList>([^<]*)</ApList>")
else
stdnse.debug1("Status-b : %s", result['status-line'] or "No Response")
return false, "Couldn't download file: " .. path
end
-- set the port version
port.version.name = "http"
port.version.name_confidence = 10
port.version.product = output["modelDescription"] or nil
port.version.version = output["firmwareVersion"] or nil
port.version.devicetype = output["deviceType"] or nil
table.insert(port.version.cpe, "cpe:/h:".. output["manufacturer"] .. ":" .. output["modelDescription"])
nmap.set_port_version(host, port, "hardmatched")
return output
else
stdnse.debug1("Could not open '%s'", uri)
return false, "Could not open "..uri
end
end
action = function(host,port)
-- Identify servers that answer 200 to invalid HTTP requests and exit as these would invalidate the tests
local status_404, result_404, _ = http.identify_404(host,port)
if ( status_404 and result_404 == 200 ) then
stdnse.debug1("Exiting due to ambiguous response from web server on %s:%s. All URIs return status 200.", host.ip, port.number)
return nil
end
return GetInformation(host, port)
end