Skip to content
Snippets Groups Projects
Commit 9701b08c authored by Pavel Valach's avatar Pavel Valach
Browse files

cowrie/wardenfiler: Store credentials for both successful and unsuccessful attempts

First implementation, which uses the aggregation ID (AID) "src_ip,dst_ip" to watch all credentials used during the time window.

If the login fails, the credentials are stored under the AID.
The credentials are flushed from the AID cache either when the aggregation window expires, or when the login is successful - the unsuccessful credentials from the cache are then sent with the successful ones appended.
parent 6158c8ba
No related branches found
No related tags found
1 merge request!10cowrie/wardenfiler: Store credentials for both successful and unsuccessful attempts
...@@ -87,6 +87,8 @@ class Output(cowrie.core.output.Output): ...@@ -87,6 +87,8 @@ class Output(cowrie.core.output.Output):
drop_malware = True drop_malware = True
win_start = None win_start = None
attackers = {} attackers = {}
# aggregated credentials from failed attempts per IP
attackers_creds = {}
sessions = {} sessions = {}
port_xlat = {} port_xlat = {}
...@@ -175,7 +177,7 @@ class Output(cowrie.core.output.Output): ...@@ -175,7 +177,7 @@ class Output(cowrie.core.output.Output):
if entry.get("dst_port") and self.reported_ssh_port: if entry.get("dst_port") and self.reported_ssh_port:
entry["dst_port"] = self.reported_ssh_port entry["dst_port"] = self.reported_ssh_port
if entry["eventid"] == 'cowrie.session.connect': if entry["eventid"] == 'cowrie.session.connect':
# Do not track a session for a source # Do not track a session for a source
# which is not globally routable # which is not globally routable
if not ip_address(entry["src_ip"]).is_global: if not ip_address(entry["src_ip"]).is_global:
...@@ -203,6 +205,10 @@ class Output(cowrie.core.output.Output): ...@@ -203,6 +205,10 @@ class Output(cowrie.core.output.Output):
self.sessions[entry["session"]] = entry self.sessions[entry["session"]] = entry
ws = self.win_start or time() ws = self.win_start or time()
cnt = self.attackers.get(aid, 0) cnt = self.attackers.get(aid, 0)
# aggregated credentials from attempts
if not self.attackers_creds.get(aid):
self.attackers_creds[aid] = []
creds = self.attackers_creds[aid]
if (time() - ws < self.aggr_win): if (time() - ws < self.aggr_win):
self.attackers[aid] = cnt + 1 self.attackers[aid] = cnt + 1
...@@ -222,10 +228,13 @@ class Output(cowrie.core.output.Output): ...@@ -222,10 +228,13 @@ class Output(cowrie.core.output.Output):
event["Target"] = [{"Proto": ["tcp", "ssh"], a_af: [a_dst_ip]}] event["Target"] = [{"Proto": ["tcp", "ssh"], a_af: [a_dst_ip]}]
if (self.anon_mask_4 < 32 and a_af == "IP4") or (self.anon_mask_6 < 128): if (self.anon_mask_4 < 32 and a_af == "IP4") or (self.anon_mask_6 < 128):
event["Target"][0]["Anonymised"] = True event["Target"][0]["Anonymised"] = True
if creds:
event["Credentials"] = creds
self.save_event(event) self.save_event(event)
self.attackers = {} self.attackers = {}
ws = time() ws = time()
self.attackers[aid] = 1 self.attackers[aid] = 1
self.attackers_creds[aid] = []
self.win_start = ws self.win_start = ws
elif entry["session"] not in self.sessions: elif entry["session"] not in self.sessions:
...@@ -235,10 +244,22 @@ class Output(cowrie.core.output.Output): ...@@ -235,10 +244,22 @@ class Output(cowrie.core.output.Output):
return() return()
elif entry["eventid"] == 'cowrie.login.success': elif entry["eventid"] == 'cowrie.login.success':
u, p = entry["username"], entry["password"]
s = entry["session"] s = entry["session"]
if s in self.sessions: if s in self.sessions:
aid = self.sessions[s]["aid"]
self.sessions[s]["credentials"] = self.attackers_creds.get(aid, [])
self.sessions[s]["credentials"].append({"Username": u, "Password": p, "Accepted": True})
self.sessions[s]["input"] = [] self.sessions[s]["input"] = []
self.sessions[s]["loggedin"] = True self.sessions[s]["loggedin"] = True
self.attackers_creds[aid] = []
elif entry["eventid"] == "cowrie.login.failed":
u, p = entry["username"], entry["password"]
s = entry["session"]
if s in self.sessions:
aid = self.sessions[s]["aid"]
self.attackers_creds[aid].append({"Username": u, "Password": p})
elif entry["eventid"] == 'cowrie.command.input': elif entry["eventid"] == 'cowrie.command.input':
s = entry["session"] s = entry["session"]
...@@ -381,5 +402,7 @@ class Output(cowrie.core.output.Output): ...@@ -381,5 +402,7 @@ class Output(cowrie.core.output.Output):
if not plain: if not plain:
attach["ContentEncoding"] = "base64" attach["ContentEncoding"] = "base64"
event["Attach"] = [attach] event["Attach"] = [attach]
if self.sessions[s]["credentials"]:
event["Credentials"] = self.sessions[s]["credentials"]
self.save_event(event) self.save_event(event)
self.sessions.pop(s, None) self.sessions.pop(s, None)
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment