Last active
February 2, 2017 11:09
-
-
Save bjornjohansen/d8eaa6793ea05b8d957e7be724b23666 to your computer and use it in GitHub Desktop.
Test a bunch of permutations of the password when logging into WordPress.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/** | |
* Test a bunch of permutations of the password when logging into WordPress. | |
* | |
* Drop this file in your mu-plugins directory. | |
* Inspired by Facebook: https://twitter.com/gcpascutto/status/821755332984717314/photo/1 | |
* Works with any properly coded hashing pluggables, like Roots’ WP Password bcrypt. | |
* | |
* @author bjornjohansen | |
* @version 0.1.4 | |
* @license https://www.gnu.org/licenses/old-licenses/gpl-2.0.html GNU General Public License version 2 (GPLv2) | |
* @package Test_Password_Permutations | |
*/ | |
add_filter( 'check_password', 'test_password_permutations', 20, 4 ); | |
/** | |
* Try permutations of the password if the login failed. | |
* | |
* @param bool $check Whether the passwords match. | |
* @param string $password The plaintext password. | |
* @param string $hash The hashed password. | |
* @param string|int $user_id User ID. Can be empty. | |
* @return bool False, if none of the $password permutations match the hashed password. | |
*/ | |
function test_password_permutations( $check, $password, $hash, $user_id ) { | |
// Don’t run this filter recursively (it is applied in wp_check_password() ). | |
if ( ! apply_filters( 'enable_password_fixer_filter', true ) ) { | |
return $check; | |
} | |
if ( ! has_filter( 'enable_password_fixer_filter' ) ) { | |
add_filter( 'enable_password_fixer_filter', '__return_false' ); | |
} | |
if ( $check ) { | |
// Password was correct. No need for us to try permutations. | |
return $check; | |
} | |
// Accept password if a user inadverntently has caps lock enabled. | |
if ( ! $check ) { | |
// Flip case. | |
$test_password = ''; | |
for ( $i = 0, $c = mb_strlen( $password ); $i < $c; $i++ ) { | |
$char = mb_substr( $password, $i, 1 ); | |
if ( mb_strtoupper( $char ) === $char ) { | |
$test_password .= mb_strtolower( $char ); | |
} else { | |
$test_password .= mb_strtoupper( $char ); | |
} | |
} | |
$check = wp_check_password( $test_password, $hash ); | |
} | |
// Accept password if their mobile device automatically capitalized the first character of the password. | |
if ( ! $check ) { | |
$test_password = mb_strtolower( mb_substr( $password, 0, 1 ) ) . mb_substr( $password, 1 ); | |
// Only test if the permutation actually changed the password. | |
if ( $test_password !== $password ) { | |
$check = wp_check_password( $test_password, $hash ); | |
} | |
} | |
// Accept password if an extra character is added to the end of the password. | |
if ( ! $check ) { | |
$test_password = mb_substr( $password, 0, mb_strlen( $password ) -1 ); | |
// Only test if the permutation actually changed the password. | |
if ( $test_password !== $password ) { | |
$check = wp_check_password( $test_password, $hash ); | |
} | |
} | |
// Trim whitespaces from both ends of the password. | |
if ( ! $check ) { | |
$test_password = trim( $password ); | |
// Only test if the permutation actually changed the password. | |
if ( $test_password !== $password ) { | |
$check = wp_check_password( $test_password, $hash ); | |
} | |
} | |
return $check; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I have written a post on the subject that explains this more, and with some password security math: https://bjornjohansen.no/wordpress-assisted-password-check