In the past week there has been a lot of concern about a vulnerability released affecting WordPress core and the password reset functionality. This post is aimed to help every WordPress user better understand the issue at hand, and provide some guidance on how (if it’s needed) the issue can be addressed.

Summary:

There is functionality in WordPress core which emails a URL which can be utilized to reset that user account’s password. Commonly known as a “forgot password?” functionality. Under three specific conditions the “forgot password?” functionality can be manipulated into sending the URL to reset a WordPress user’s password to an email address controlled by a malicious party.

The three specific conditions, which ALL must be met, are each owned under entirely separate entities; one is the WordPress core software, one is the web server configuration, and the third is with the email service provider. They are described below in detail. Generally speaking, it is unlikely and uncommon for them all to be met. Pagely specifically is not vulnerable to this attack (more details here: Security Haiku: ExploitBox’s CVE-2017-8295)

When all three of the conditions for exploit can be met, the attack works as follows.

The attacker makes their request to the “forgot password?” function. In the request, they set the “Host” http header to a domain they control. (let’s call it evil.org) The WordPress software generates an email with the secret link that will reset a user’s password. It looks up who it should send the email as (e.g.. the “From” field) by looking at the value in PHP of $_SERVER[‘SERVER_NAME’] which just so happens to be set by the “Host” http header field. Normally this would be your site’s domain, but in event of this attack the email “From” field will be wordpress@evil.org. The email with secret key is queued for delivery to the WordPress user’s email address. Somehow (be it a bad email address, full inbox, or maybe even an away from office message that includes the original email) the email gets a response which includes the original message and is delivered to the listed “From” field. The reply is delivered to the attacker’s inbox, they are then able to use the secret link and log in to the WordPress user’s account.

Conditions for exploit:

The three key components that, again, ALL must be met in order for this exploit to work are:

The site’s WordPress software must be running a vulnerable version. At the time of writing there has not yet been a patch released to address this bug, it affects all versions of WordPress up to and including 4.7.4. The web server software configuration must be configuration in way where it does not require a valid Host header field which matches the site being requested, and passes the Host value provided by the browser to the PHP process.

This is how a default Apache web server installation would be configured, however it is not a common practice to leave Apache set up in this manner and is especially uncommon for environments where more than one website or domain is hosted at the same IP address. The email delivery method must be obstructed in some manner. Resulting in the email being returned or bounced back to the listed “From” field address in the email, the “From” field is what is controlled by the attackers.

This component of the exploit is would be the most difficult for attackers to be able to replicate reliably. However it is not inconceivable.

In events where all of the conditions the attack are NOT met. The attack will only cause unwanted network traffic or recipients will receive password reset emails they did not request.

Q&A

Is there a patch?

Not in WordPress core, we have some recommended work arounds below. WordPress versions after 4.2 up to and including 4.7.4 are vulnerable to the first component of this attack.

Where can I watch for a patch?

See the trac bug post here: #25239

Who released this exploit?

The exploit was released by ExploitBox.io.

Am I affected?

Pagely customers are not affected. Other hosting providers, including self-hosted and shared hosting are possibly affected but as mentioned above it is uncommon.

How do I check if I am affected?

Here are two methods to quickly check if you’re possibly affected without attempting the exploit:

Using the methods below are known not to be full proof detection. The information is provided for general informational only, you should be contacting your hosting provider for assistance.

Basic:

1. Request your site by it’s IP address directly. If you do not get your website when you put the IP address in the browser’s URL field, then your site’s server is likely not configured in a way to allow this attack.

Advanced:

2. Create a script on your site with the following PHP code:

<?php echo $_SERVER['SERVER_NAME']; ?>

Then request that file and set the Host field to another value. This can be done on the command line using

curl -H "Host: you_are_vulnerable" http://yoursite.com/test_server_name.php

If the response is the value of Host (e.g.. if it says “you_are_vulnerable” using the example above) then you are vulnerable. If the response is your site’s actual domain name, then you are not vulnerable.

How can I make certain I’m not vulnerable, in lieu of a patch from WordPress core?

Like this content? Meet Pagely.

Here are a few work arounds users may be able to utilize to ensure their site is secure against this vulnerability:

1. Create or use a plugin to monkey-patch the function that sets the from field for these emails. It can be done as simply as using the following code:

add_filter( 'wp_mail_from', function( $from_email ) { return 'insert@your_email.here'; } );

(of course change the ‘insert@your_email.here’ to the email address you want to set the email From field to)

2. Add UserCanonicalName On in your server configuration (or .htaccess if it is allowed)

3. Use a redirect to force requests to the domain name of your site if the Host field in the header does not match your domain name, this can be done in the server configuration or via .htaccess

RewriteEngine On RewriteCond %{HTTP_HOST} . RewriteCond %{HTTP_HOST} !^www\.example\.com RewriteRule (.*) http://www.example.com/$1 [R=301,L]

4. Lock down wp-login.php. Attackers can not attack what they can not see, either move this file’s functionality to another URL or more ideally lock down access based on IP address. (as an alternative, you could also disable the forgot password feature on your site, however this will mean your site administrators will have a lot more work to do if someone forgets a password)

Closing thoughts:

It’s my hope the information presented in this post is helpful to those who have concerns about this exploit. Ideally you will not need to use the temporary fixes presented, but if it provides any sense of comfort please feel free to use the information in this post and share it with your friends.

> Learn more about Pagely’s approach to secure WordPress hosting.