diff --git a/docs/CHANGELOG.rst b/docs/CHANGELOG.rst index f4c301e4..496a65e5 100644 --- a/docs/CHANGELOG.rst +++ b/docs/CHANGELOG.rst @@ -1,6 +1,7 @@ * 2019-03-07 Output of `ssh -V` now configurable in cowrie.cfg with ssh_version setting * 2019-03-07 Multiple timezone support in cowrie.cfg timezone directive. Default timezone is now UTC for both cowrie.log and cowrie.json +* 2019-03-12 Handle multiple password prompt. Option to enable or disable keyboard interactive prompt. Release 1.5.3 ============= @@ -10,7 +11,7 @@ Release 1.5.3 * 2019-01-09 Documentation converted to ReStructuredText * 2018-12-04 Fixes for VT outut plugin to only submit new files -Release 1.5.2 +Release 1.5.2 ============= * 2018-11-19 Fix tftp exception and tftp test diff --git a/etc/cowrie.cfg.dist b/etc/cowrie.cfg.dist index 54431bb1..b9a9fb0e 100644 --- a/etc/cowrie.cfg.dist +++ b/etc/cowrie.cfg.dist @@ -190,6 +190,9 @@ auth_class = UserDB # (default: false) #auth_none_enabled = false +# Configure keyboard-interactive login +auth_keyboard_interactive_enabled = false + # ============================================================================ # Historical SSH Specific Options diff --git a/src/cowrie/ssh/userauth.py b/src/cowrie/ssh/userauth.py index 713c643b..49b95365 100644 --- a/src/cowrie/ssh/userauth.py +++ b/src/cowrie/ssh/userauth.py @@ -30,7 +30,12 @@ class HoneyPotSSHUserAuthServer(userauth.SSHUserAuthServer): def serviceStarted(self): self.interfaceToMethod[credentials.IUsername] = b'none' self.interfaceToMethod[credentials.IUsernamePasswordIP] = b'password' - self.interfaceToMethod[credentials.IPluggableAuthenticationModulesIP] = b'keyboard-interactive' + keyboard = CONFIG.getboolean('ssh', 'auth_keyboard_interactive_enabled', fallback=False) + + if keyboard is True: + self.interfaceToMethod[credentials. + IPluggableAuthenticationModulesIP] = ( + b'keyboard-interactive') self.bannerSent = False self._pamDeferred = None userauth.SSHUserAuthServer.serviceStarted(self) @@ -44,7 +49,8 @@ class HoneyPotSSHUserAuthServer(userauth.SSHUserAuthServer): return self.bannerSent = True try: - issuefile = CONFIG.get('honeypot', 'contents_path') + "/etc/issue.net" + issuefile = CONFIG.get( + 'honeypot', 'contents_path') + "/etc/issue.net" data = open(issuefile).read() except IOError: return @@ -59,12 +65,14 @@ class HoneyPotSSHUserAuthServer(userauth.SSHUserAuthServer): # def auth_publickey(self, packet): # """ - # We subclass to intercept non-dsa/rsa keys, or Conch will crash on ecdsa.. + # We subclass to intercept non-dsa/rsa keys, + # or Conch will crash on ecdsa.. # UPDATE: conch no longer crashes. comment this out # """ # algName, blob, rest = getNS(packet[1:], 2) # if algName not in (b'ssh-rsa', b'ssh-dsa'): - # log.msg("Attempted public key authentication with {} algorithm".format(algName)) + # log.msg("Attempted public key authentication\ + # with {} algorithm".format(algName)) # return defer.fail(error.ConchError("Incorrect signature")) # return userauth.SSHUserAuthServer.auth_publickey(self, packet) @@ -83,7 +91,8 @@ class HoneyPotSSHUserAuthServer(userauth.SSHUserAuthServer): password = getNS(packet[1:])[0] srcIp = self.transport.transport.getPeer().host c = credentials.UsernamePasswordIP(self.user, password, srcIp) - return self.portal.login(c, srcIp, IConchUser).addErrback(self._ebPassword) + return self.portal.login(c, srcIp, + IConchUser).addErrback(self._ebPassword) def auth_keyboard_interactive(self, packet): """ @@ -91,14 +100,19 @@ class HoneyPotSSHUserAuthServer(userauth.SSHUserAuthServer): PluggableAuthenticationModules credential and authenticate with our portal. - Overridden to pass src_ip to credentials.PluggableAuthenticationModulesIP + Overridden to pass src_ip to + credentials.PluggableAuthenticationModulesIP """ if self._pamDeferred is not None: - self.transport.sendDisconnect(DISCONNECT_PROTOCOL_ERROR, "only one keyboard interactive attempt at a time") + self.transport.sendDisconnect( + DISCONNECT_PROTOCOL_ERROR, + "only one keyboard interactive attempt at a time") return defer.fail(error.IgnoreAuthentication()) src_ip = self.transport.transport.getPeer().host - c = credentials.PluggableAuthenticationModulesIP(self.user, self._pamConv, src_ip) - return self.portal.login(c, src_ip, IConchUser).addErrback(self._ebPassword) + c = credentials.PluggableAuthenticationModulesIP( + self.user, self._pamConv, src_ip) + return self.portal.login(c, src_ip, + IConchUser).addErrback(self._ebPassword) def _pamConv(self, items): """