Crack your mac password

Thomas Deegan
2 min readMay 15, 2023

--

In the rare case that you have access to your Mac but forgot your password you can use this script to brute force some close combinations of the password using some heuristic character dropping and replacement using nearest keys on the keyboard.

This came in handy for me when I setup up a new Macbook but realized I mistyped my password when I created the account but was already logged in.

import getpass
import os
import subprocess
import sys


def check_password(password):
print(f'checking: {password}')
result = subprocess.run(['sudo', '-k', '-S', 'true'],
input=password.encode(), stderr=subprocess.PIPE)
if result.returncode == 0:
print("Password is correct.")
return True
else:
print("Password is incorrect.")
return False

def replace_char(original_string, index, char):
if index < len(original_string):
modified_string = original_string[:index] + char + original_string[index + 1:]
return modified_string
else:
return "Index out of range"

def get_keys_around(key):
key = key.lower()
print(f'finding nearby keys {key}')
lines = '~1234567890-=', 'qwertyuiop', 'asdfghjkl;', 'zxcvbnm,./'
line_index, index = [(i, l.find(key)) for i, l in enumerate(lines) if key in l][0]
lines = lines[line_index-1: line_index+2] if line_index else lines[0: 2]
return [
line[index + i] for line in lines for i in [-1, 0, 1]
if len(line) > index + i and line[index + i] != key and index + i >= 0]

if __name__ == "__main__":
# Replace 'username' with the actual username
basepass = getpass.getpass("Enter your best guess for the password: ")
guess_num = 0

if check_password(basepass):
sys.exit(0)
while True:
print(guess_num)
if guess_num < len(basepass):
idx = guess_num
guess_pass = basepass[:guess_num] + basepass[guess_num+1:]
if check_password(guess_pass):
break

char_to_replace = basepass[guess_num]
char_to_replace = char_to_replace.capitalize () if char_to_replace.islower() else char_to_replace.lower()
guess_pass = replace_char(basepass, idx, char_to_replace)
if not guess_pass == basepass:
if check_password(guess_pass):
break

keyz = get_keys_around(basepass[idx])
print(f'{basepass[idx]} -> {keyz}')
for k in keyz:
guess_pass = replace_char(basepass, idx, k)
if check_password(guess_pass):
sys.exit(0)

else:
break
guess_num += 1

The public github gist is here: https://gist.github.com/tadeegan/bbe5ee581ac656b8a279b7fcf8a4dd3b

--

--