Nmap Development mailing list archives
Re: [NSE] ventrilo-info Ventrilo server version detection and info
From: Marin Maržić <marzic () gmail com>
Date: Fri, 07 Jun 2013 23:59:38 +0200
Hey, these replies (2 emails at the bottom of this) slipped past me.
Just came across them now half a year later when I was looking to post
some updates to those probes. Never too late?
The updated scripts keep the kind of portrules you seemed to like to use
(less likely to run). Also added some version probes that can be
controlled by rarity and act as a sort of "softmatch" for activating the
scripts. Should help some when the services run on arbitrary ports and
the scripts have such restrictive portrules set.
- murmur-version.nse
Now only sends and receives 1 packet when scanning the same port number
on the same host in both TCP and UDP (used to repeat for each protocol).
The "softmatch" probe:
Probe UDP Murmur q|\0\0\0\0abcdefgh|
rarity 9
ports 64738
match murmur m|^\0.{3}abcdefgh.{12}$|s p/Murmur/ v/1.2.X/
- ventrilo-info.nse
Now only sends and receives 1 packet when scanning the same port number
on the same host in both TCP and UDP (used to repeat for each protocol).
Various code improvements, bug fixes.
The "softmatch" probe follows. This one is encrypted and the
match can't really be matched on anything except that it should be at
least 111 bytes (conservative guess, should catch all).
Probe UDP Ventrilo
q|\x01\xe7\xe5\x75\x31\xa3\x17\x0b\x21\xcf\xbf\x2b\x99\x4e\xdd\x19\xac\xde\x08\x5f\x8b\x24\x0a\x11\x19\xb6\x73\x6f\xad\x28\x13\xd2\x0a\xb9\x12\x75|
rarity 9
ports 3784
match ventrilo m|^.{111}|s p/Ventrilo/ v/2.1.2+/
The UDP payload follows. It is a general status request with a 1 packet
reply:
# Ventrilo 2.1.2+
# UDP general status request (encrypted).
# See http://aluigi.altervista.org/papers.htm#ventrilo
udp 3784
"\x01\xe7\xe5\x75\x31\xa3\x17\x0b\x21\xcf\xbf\x2b\x99\x4e\xdd\x19\xac\xde\x08\x5f\x8b\x24\x0a\x11\x19\xb6\x73\x6f\xad\x28\x13\xd2\x0a\xb9\x12\x75"
- teamspeak2-version.nse
You mentioned that this could have been done with a version probe and a
couple match lines (and you were right!), but I have since found where
the precise version numbers are hidden in the binary blob response.
There is some information on the protocol at
http://wiki.wireshark.org/TeamSpeak2 but they haven't found the version
offsets. A normal login request is used.
The "softmatch" probe:
Probe UDP TeamSpeak2
q|\xf4\xbe\x03\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\x00\x00\x00\x32\x78\xba\x85\x09\x54\x65\x61\x6d\x53\x70\x65\x61\x6b\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x0a\x57\x69\x6e\x64\x6f\x77\x73\x20\x58\x50\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x00\x00\x20\x00\x3c\x00\x00\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x08\x6e\x69\x63\x6b\x6e\x61\x6d\x65\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00|
rarity 9
ports 8767
match ts2
m|^\xf4\xbe\x04\x00\x00\x00\x00\x00.............([^\0]+)[^\w\s]+([^\0]+)\0+[^\0].{355}$|s
p/TeamSpeak 2/ o/$2/ i/name: $1; no password/
match ts2 m|^\xf4\xbe\x04\x00\x00\x00\x00\x00............\0{60}.{356}$|s
p/TeamSpeak 2/ i|name: n/a; has password or version < 2.0.19.16 (very
unlikely)|
Examples of output:
PORT STATE SERVICE VERSION
8767/udp open ts2 TeamSpeak 2 (name: COWCLANS; no password)
Service Info: OS: Win32
PORT STATE SERVICE VERSION
8767/udp open ts2 TeamSpeak 2 (name: TeamSpeak Server; no password)
Service Info: OS: Linux
- TeamSpeak 2 nmap-payloads
The payload sent is the one used in the above script. It is a normal
login request and is not encrypted. Some information fields sent are in
ASCII, but it's in hex here because it was convenient to copy it like
that off the wire. I guess the description could be something like:
# TeamSpeak 2
# UDP login request
# See http://wiki.wireshark.org/TeamSpeak2
- TeamSpeak 2 TCP port service detection (the "TCPQuery" interface):
Here are 2 examples you asked for of what output looks like for the
suggested "ver" command:
2.0.23.19 Win32 Freeware
OK
2.0.24.1 Linux Freeware
OK
- TeamSpeak 2 TCP port service detection (the http web admin interface):
When I comment it out, the specific line matches. When I leave it
functional below or above the specific lines, it overrides. Weird?
- TeamSpeak 3 UDP probe and nmap-payloads
This is an encrypted login request packet copied off the wire. Think
there is no documentation on it. There seem to be some fields that echo
back what is sent, and some that are static when sent this exact
payload, so I match on them. Length varies. I guess the description
could be something like:
# TeamSpeak 3
# UDP login request (encrypted)
- TeamSpeak 3 TCP port service detection (the "ServerQuery" interface):
2 examples of what output looks like for the suggested "version" command:
version=3.0.6.1 build=1340956745 platform=Windows
error id=0 msg=ok
version=3.0.7.2 build=1368605352 platform=Linux
error id=0 msg=ok
- On another note, when I tried to make version scripts run for any as
of yet unidentified port (like normal probes would with --version-all),
it wasn't that straightforward. I came across this bit in
http://nmap.org/book/nse-api.html#nse-api-arguments:
"port.service
Contains a string representation of the service running on
port.number as detected by the Nmap service detection. If the
port.version field is nil, Nmap has guessed the service based on the
port number. Otherwise version detection was able to determine the
listening service and this field is equal to port.version.name."
Thought that maybe the mentioned fields could help determine if it was a
guess or not, but this came up when testing (debug output at the start
of a portrule) the 4 possible combinations:
- port without an nmap-services entry, and no regex rule match:
NSE: port.service=nil
NSE: port.version=not nil
NSE: port.version.name=nil
NSE: port.version.name_confidence=3
PORT STATE SERVICE REASON VERSION
62314/udp open|filtered unknown no-response
- port without an nmap-services entry, and there is a regex rule match:
NSE: port.service=murmur
NSE: port.version=not nil
NSE: port.version.name=murmur
NSE: port.version.name_confidence=10
PORT STATE SERVICE REASON VERSION
62314/udp open murmur udp-response Murmur 1.2.X
- port (80) with a nmap-services entry (http), and no regex rule match:
NSE: port.service=http
NSE: port.version=not nil
NSE: port.version.name=http
NSE: port.version.name_confidence=3
PORT STATE SERVICE REASON VERSION
80/udp open|filtered http no-response
- port (80) with a nmap-service entry (http), and there is a regex rule
match:
NSE: port.service=murmur
NSE: port.version=not nil
NSE: port.version.name=murmur
NSE: port.version.name_confidence=10
PORT STATE SERVICE REASON VERSION
80/udp open murmur udp-response Murmur 1.2.X
Some conclusions from this:
- port.version is never nil (guess or not)
- port.service and port.version.name are always equal (guess or not)
- port.version.name_confidence is never nil; it is 3 when a guess was
made and it is 3 even when no guess can be made, it is 10 on a match
- if a port number has an entry in nmap-services, port.service and
port.version.name will be set to it. This is why, for example, the Skype
version script can never work against port 80 (it's set to "http"), or
against any other port with an entry in nmap-services that isn't
"unknown" or "".
Then it seems that the following type of port rule would best emulate a
normal probe that runs on any open or open|filtered, and as of yet
unidentified port (udp in this case):
portrule = function(host, port)
return port.version.name_confidence ~= 10
and not shortport.port_is_excluded(port.number, "udp")
end
Guess I would have to add such a rule to all scripts if I wanted "true"
--version-all functionality (full Nmap version detecting power).
Marin
On 16.1.2013. 1:30, David Fifield wrote:> On Tue, Dec 18, 2012 at
03:30:19AM +0100, Marin Maržić wrote:
here's a service detection and info script for the Ventrilo voice communication server service. If used as a normal script it prints out a lot of the server status details. More info in the .nse.Thank you, this is now committed in r30505 and following. I made some changes to the documentation, and changed the port rule to make it less likely to run. We don't yet have a good way to control the running of version scripts like this, which target services that can be run against arbitrary ports, but which we don't want to run for every open|filtered port by default. In version probes we use the rarity, but there is no equivalent notion for NSE scripts. David Fifield
On 23.12.2012. 2:14, David Fifield wrote:> On Wed, Dec 19, 2012 at 07:59:51PM +0100, Marin Maržić wrote:
been working on improving TeamSpeak 2 and 3 server service detection and here's what I came up with. TeamSpeak 2 (2 TCP and 1 UDP port): TCP port service detection (the "TCPQuery" interface): - replaced match line (for the NULL probe): match telnet m|^\[TS\]\r\n$| p/Teamspeak VoIP Information telnetd/ - with: softmatch ts2-TCPQuery m|^\[TS\]\r\n$| - and added probe: Probe TCP verLine q|ver\r\n| rarity 9 ports 51234 match ts2-TCPQuery m|^\[TS\]\r\n(\S+) (\S+) (\S+)\r\nOK\r\n$| p/TeamSpeak 2 server TCPQuery interface (telnetd)/ v/$1/ i/$3/ o/$2/ - This improves the detection of the specific TS2 telnetd (they call it the TCPQuery function) with additional information (more precise name, specific version, some extra info and OS). Rarity 9 works great because of the softmatch in the NULL probe so it doesn't slow down searches.I applied the part to make a more specific match for the TCPQuery port. Can you send some examples of verbatim responses sent in response to the "ver" command? I want to see what kind of things are going in the info field, and how the OS names are formatted. If there are multiple OS strings, we usually like to break them into multiple match lines in order to have different CPE.TCP port service detection (the "ServerQuery" interface): - replaced match lines (for the NULL probe): match teamspeak m|^TS3\n\r$| p/TeamSpeak voice communication/ v/3/ match teamspeak m|^TS3\n\rWelcome to the TeamSpeak 3 ServerQuery interface, type \"help\" for a list of commands and \"help <command>\" for information on a specific command\.\n\r$| p/TeamSpeak voice communication/ v/3/ - with: softmatch ts3-ServerQuery m|^TS3\n\r$| softmatch ts3-ServerQuery m|^TS3\n\rWelcome to the TeamSpeak 3 ServerQuery interface, type \"help\" for a list of commands and \"help <command>\" for information on a specific command\.\n\r$| - and added probe: Probe TCP versionLine q|version\r\n| rarity 9 ports 10011 match ts3-ServerQuery m|^TS3\n\r.*?version=(\S+) build=(\S+) platform=(\S+)\n\rerror id=0 msg=ok\n\r$|s p/TeamSpeak 3 server ServerQuery interface (telnetd)/ v/$1/ i/build: $2/ o/$3/Same here, I applied the more specific matches, but please show some example ooutput of the "version" command.TCP port service detection (the http web admin interface): - This one seemed to exist already in nmap-service-probes in the form of 2 match lines (for the NULL probe): match http m|^HTTP/1\.1 \d\d\d .*\r\nConnection: keep-alive\r\nContent-Type: text/HTML\r\nContent-Length: \d+\r\nServer: Indy/([\d.]+)\r\nSet-Cookie: .*\r\n\r\n<!-- header\.html -->.*TeamSpeak|s p/TeamSpeak admin httpd/ v/1.X/ i/Indy httpd $1/ match http m|^HTTP/1\.1 \d\d\d .*\r\nConnection: keep-alive\r\nContent-Type: text/HTML\r\nContent-Length: \d+\r\nServer: Indy/([\d.]+)\r\nSet-Cookie: .*<title>TeamSpeak 2 - Server-Administration</title>|s p/TeamSpeak admin httpd/ v/2.X/ i/Indy httpd $1/ - Unfortunately they never match because they are overriden by this line: match http m|^HTTP/1\.1 200 OK\r\n.*Server: Indy/([\w._-]+)\r\n|s p/Indy/ v/$1/ - not sure how this kind of stuff is usually fixedThis doesn't seem to be the case anymore in the current version of the file. The Indy/TeamSpeak lines appear (in the GetRequest probe) above any more generic Indy lines. Is it possible that the server output is slightly different and now doesn't match the regular expressions?- payload (nmap-payloads): # TeamSpeak 2 udp 8767
"\xf4\xbe\x03\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\x00\x00\x00\x32\x78\xba\x85\x09\x54\x65\x61\x6d\x53\x70\x65\x61\x6b\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x0a\x57\x69\x6e\x64\x6f\x77\x73\x20\x58\x50\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x00\x00\x20\x00\x3c\x00\x00\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x08\x6e\x69\x63\x6b\x6e\x61\x6d\x65\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
UDP port service detection (the voice/login/session port): Probe UDP TeamSpeak3
q|\x05\xca\x7f\x16\x9c\x11\xf9\x89\x00\x00\x00\x00\x02\x9d\x74\x8b\x45\xaa\x7b\xef\xb9\x9e\xfe\xad\x08\x19\xba\xcf\x41\xe0\x16\xa2\x32\x6c\xf3\xcf\xf4\x8e\x3c\x44\x83\xc8\x8d\x51\x45\x6f\x90\x95\x23\x3e\x00\x97\x2b\x1c\x71\xb2\x4e\xc0\x61\xf1\xd7\x6f\xc5\x7e\xf6\x48\x52\xbf\x82\x6a\xa2\x3b\x65\xaa\x18\x7a\x17\x38\xc3\x81\x27\xc3\x47\xfc\xa7\x35\xba\xfc\x0f\x9d\x9d\x72\x24\x9d\xfc\x02\x17\x6d\x6b\xb1\x2d\x72\xc6\xe3\x17\x1c\x95\xd9\x69\x99\x57\xce\xdd\xdf\x05\xdc\x03\x94\x56\x04\x3a\x14\xe5\xad\x9a\x2b\x14\x30\x3a\x23\xa3\x25\xad\xe8\xe6\x39\x8a\x85\x2a\xc6\xdf\xe5\x5d\x2d\xa0\x2f\x5d\x9c\xd7\x2b\x24\xfb\xb0\x9c\xc2\xba\x89\xb4\x1b\x17\xa2\xb6|
rarity 9 ports 9987 match ts3
m|^.{8}\x00\x00\x02\x97\x76\x8b\x54\xad\x79\xe3\xaf\x87\xeb\xaa\x1a\x19\xba\xcf\x41\xe0\x16\xa2\x32\x6c\xf3\xcf\xf4\x8e\x3c\x44\x83\xc8\x8d\x51\x45\x6f\x90\x95\x23\x33\x08\x86\x2d\x40|s
p/TeamSpeak 3 server/ - not sure about the rarity here, won't get picked up on a default scan with 9 - payload (nmap-payloads): # TeamSpeak 3 udp 9987
"\x05\xca\x7f\x16\x9c\x11\xf9\x89\x00\x00\x00\x00\x02\x9d\x74\x8b\x45\xaa\x7b\xef\xb9\x9e\xfe\xad\x08\x19\xba\xcf\x41\xe0\x16\xa2\x32\x6c\xf3\xcf\xf4\x8e\x3c\x44\x83\xc8\x8d\x51\x45\x6f\x90\x95\x23\x3e\x00\x97\x2b\x1c\x71\xb2\x4e\xc0\x61\xf1\xd7\x6f\xc5\x7e\xf6\x48\x52\xbf\x82\x6a\xa2\x3b\x65\xaa\x18\x7a\x17\x38\xc3\x81\x27\xc3\x47\xfc\xa7\x35\xba\xfc\x0f\x9d\x9d\x72\x24\x9d\xfc\x02\x17\x6d\x6b\xb1\x2d\x72\xc6\xe3\x17\x1c\x95\xd9\x69\x99\x57\xce\xdd\xdf\x05\xdc\x03\x94\x56\x04\x3a\x14\xe5\xad\x9a\x2b\x14\x30\x3a\x23\xa3\x25\xad\xe8\xe6\x39\x8a\x85\x2a\xc6\xdf\xe5\x5d\x2d\xa0\x2f\x5d\x9c\xd7\x2b\x24\xfb\xb0\x9c\xc2\xba\x89\xb4\x1b\x17\xa2\xb6"
For all these, we need some more information. We don't like having undocumented binary blobs in the database. Do you have a link to protocol documentation? What do these probes do? Where do they come from? Check the comments above each payload in nmap-payloads; that's the kind of information we need.UDP port service detection (the voice/login/session port): - Attached an NSE script for this one. More info in the .nse.It looks like what this script does can be done with a version probe. It just sends a static payload and then does a pattern match on the returned value. A blank name, for example, would be handled with two match lines. My above comments on documentation apply equally here; please show some example output if possible. David Fifield
Attachment:
murmur-version.nse
Description:
Attachment:
teamspeak2-version.nse
Description:
Attachment:
ventrilo-info.nse
Description:
_______________________________________________ Sent through the dev mailing list http://nmap.org/mailman/listinfo/dev Archived at http://seclists.org/nmap-dev/
Current thread:
- Re: [NSE] ventrilo-info Ventrilo server version detection and info Marin Maržić (Jun 07)
