mirror of
https://github.com/lgandx/Responder.git
synced 2024-10-17 20:50:25 -07:00
119 lines
4.7 KiB
Python
Executable File
119 lines
4.7 KiB
Python
Executable File
#!/usr/bin/env python
|
|
# This file is part of Responder, a network take-over set of tools
|
|
# created and maintained by Laurent Gaffie.
|
|
# email: laurent.gaffie@gmail.com
|
|
# This program is free software: you can redistribute it and/or modify
|
|
# it under the terms of the GNU General Public License as published by
|
|
# the Free Software Foundation, either version 3 of the License, or
|
|
# (at your option) any later version.
|
|
#
|
|
# This program is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU General Public License
|
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
import sys
|
|
import os
|
|
import _thread
|
|
|
|
BASEDIR = os.path.realpath(os.path.join(os.path.dirname(__file__), '..'))
|
|
sys.path.insert(0, BASEDIR)
|
|
|
|
from servers.Browser import WorkstationFingerPrint, RequestType, RAPThisDomain, RapFinger
|
|
from socketserver import UDPServer, ThreadingMixIn, BaseRequestHandler
|
|
from threading import Lock
|
|
from utils import *
|
|
|
|
def ParseRoles(data):
|
|
if len(data) != 4:
|
|
return ''
|
|
|
|
AllRoles = {
|
|
'Workstation': (ord(data[0]) >> 0) & 1,
|
|
'Server': (ord(data[0]) >> 1) & 1,
|
|
'SQL': (ord(data[0]) >> 2) & 1,
|
|
'Domain Controller': (ord(data[0]) >> 3) & 1,
|
|
'Backup Controller': (ord(data[0]) >> 4) & 1,
|
|
'Time Source': (ord(data[0]) >> 5) & 1,
|
|
'Apple': (ord(data[0]) >> 6) & 1,
|
|
'Novell': (ord(data[0]) >> 7) & 1,
|
|
'Member': (ord(data[1]) >> 0) & 1,
|
|
'Print': (ord(data[1]) >> 1) & 1,
|
|
'Dialin': (ord(data[1]) >> 2) & 1,
|
|
'Xenix': (ord(data[1]) >> 3) & 1,
|
|
'NT Workstation': (ord(data[1]) >> 4) & 1,
|
|
'WfW': (ord(data[1]) >> 5) & 1,
|
|
'Unused': (ord(data[1]) >> 6) & 1,
|
|
'NT Server': (ord(data[1]) >> 7) & 1,
|
|
'Potential Browser': (ord(data[2]) >> 0) & 1,
|
|
'Backup Browser': (ord(data[2]) >> 1) & 1,
|
|
'Master Browser': (ord(data[2]) >> 2) & 1,
|
|
'Domain Master Browser': (ord(data[2]) >> 3) & 1,
|
|
'OSF': (ord(data[2]) >> 4) & 1,
|
|
'VMS': (ord(data[2]) >> 5) & 1,
|
|
'Windows 95+': (ord(data[2]) >> 6) & 1,
|
|
'DFS': (ord(data[2]) >> 7) & 1,
|
|
'Local': (ord(data[3]) >> 6) & 1,
|
|
'Domain Enum': (ord(data[3]) >> 7) & 1,
|
|
}
|
|
|
|
return ', '.join(k for k,v in list(AllRoles.items()) if v == 1)
|
|
|
|
|
|
class BrowserListener(BaseRequestHandler):
|
|
def handle(self):
|
|
data, socket = self.request
|
|
|
|
lock = Lock()
|
|
lock.acquire()
|
|
|
|
DataOffset = struct.unpack('<H',data[139:141])[0]
|
|
BrowserPacket = data[82+DataOffset:]
|
|
ReqType = RequestType(BrowserPacket[0])
|
|
|
|
Domain = Decode_Name(data[49:81])
|
|
Name = Decode_Name(data[15:47])
|
|
Role1 = NBT_NS_Role(data[45:48])
|
|
Role2 = NBT_NS_Role(data[79:82])
|
|
Fprint = WorkstationFingerPrint(data[190:192])
|
|
Roles = ParseRoles(data[192:196])
|
|
|
|
print(text("[BROWSER] Request Type : %s" % ReqType))
|
|
print(text("[BROWSER] Address : %s" % self.client_address[0]))
|
|
print(text("[BROWSER] Domain : %s" % Domain))
|
|
print(text("[BROWSER] Name : %s" % Name))
|
|
print(text("[BROWSER] Main Role : %s" % Role1))
|
|
print(text("[BROWSER] 2nd Role : %s" % Role2))
|
|
print(text("[BROWSER] Fingerprint : %s" % Fprint))
|
|
print(text("[BROWSER] Role List : %s" % Roles))
|
|
|
|
RAPThisDomain(self.client_address[0], Domain)
|
|
|
|
lock.release()
|
|
|
|
|
|
class ThreadingUDPServer(ThreadingMixIn, UDPServer):
|
|
def server_bind(self):
|
|
self.allow_reuse_address = 1
|
|
UDPServer.server_bind(self)
|
|
|
|
def serve_thread_udp_broadcast(host, port, handler):
|
|
try:
|
|
server = ThreadingUDPServer(('', port), handler)
|
|
server.serve_forever()
|
|
except:
|
|
print("Error starting UDP server on port " + str(port) + ", check permissions or other servers running.")
|
|
|
|
if __name__ == "__main__":
|
|
try:
|
|
print("Listening for BROWSER datagrams...")
|
|
_thread.start_new(serve_thread_udp_broadcast,('', 138, BrowserListener))
|
|
|
|
while True:
|
|
time.sleep(1)
|
|
|
|
except KeyboardInterrupt:
|
|
sys.exit("\r Exiting...")
|