OWASP Testing Guide
  • Foreword by Eoin Keary
  • Frontispiece
  • Introduction
  • The OWASP Testing Framework
    • The Web Security Testing Framework
    • Penetration Testing Methodologies
  • Web Application Security Testing
    • Introduction and Objectives
    • Information Gathering
      • Conduct Search Engine Discovery Reconnaissance for Information Leakage (WSTG-INFO-01)
      • Fingerprint Web Server (WSTG-INFO-02)
      • Review Webserver Metafiles for Information Leakage (WSTG-INFO-03)
      • Enumerate Applications on Webserver (WSTG-INFO-04)
      • Review Webpage Content for Information Leakage (WSTG-INFO-05)
      • Identify Application Entry Points (WSTG-INFO-06)
      • Map Execution Paths Through Application (WSTG-INFO-07)
      • Fingerprint Web Application Framework (WSTG-INFO-08)
      • Fingerprint Web Application (WSTG-INFO-09)
      • Map Application Architecture (WSTG-INFO-10)
    • Configuration and Deployment Management Testing
      • Test Network Infrastructure Configuration (WSTG-CONF-01)
      • Test Application Platform Configuration (WSTG-CONF-02)
      • Test File Extensions Handling for Sensitive Information (WSTG-CONF-03)
      • Review Old Backup and Unreferenced Files for Sensitive Information (WSTG-CONF-04)
      • Enumerate Infrastructure and Application Admin Interfaces (WSTG-CONF-05)
      • Test HTTP Methods (WSTG-CONF-06)
      • Test HTTP Strict Transport Security (WSTG-CONF-07)
      • Test RIA Cross Domain Policy (WSTG-CONF-08)
      • Test File Permission (WSTG-CONF-09)
      • Test for Subdomain Takeover (WSTG-CONF-10)
      • Test Cloud Storage (WSTG-CONF-11)
      • Testing for Content Security Policy (WSTG-CONF-12)
    • Identity Management Testing
      • Test Role Definitions (WSTG-IDNT-01)
      • Test User Registration Process (WSTG-IDNT-02)
      • Test Account Provisioning Process (WSTG-IDNT-03)
      • Testing for Account Enumeration and Guessable User Account (WSTG-IDNT-04)
      • Testing for Weak or Unenforced Username Policy (WSTG-IDNT-05)
    • Authentication Testing
      • Testing for Credentials Transported over an Encrypted Channel (WSTG-ATHN-01)
      • Testing for Default Credentials (WSTG-ATHN-02)
      • Testing for Weak Lock Out Mechanism (WSTG-ATHN-03)
      • Testing for Bypassing Authentication Schema (WSTG-ATHN-04)
      • Testing for Vulnerable Remember Password (WSTG-ATHN-05)
      • Testing for Browser Cache Weaknesses (WSTG-ATHN-06)
      • Testing for Weak Password Policy (WSTG-ATHN-07)
      • Testing for Weak Security Question Answer (WSTG-ATHN-08)
      • Testing for Weak Password Change or Reset Functionalities (WSTG-ATHN-09)
      • Testing for Weaker Authentication in Alternative Channel (WSTG-ATHN-10)
      • Testing Multi-Factor Authentication (MFA) (WSTG-AUTH-11)
    • Authorization Testing
      • Testing Directory Traversal File Include (WSTG-ATHZ-01)
      • Testing for Bypassing Authorization Schema (WSTG-ATHZ-02)
      • Testing for Privilege Escalation (WSTG-ATHZ-03)
      • Testing for Insecure Direct Object References (WSTG-ATHZ-04)
      • Testing for OAuth Authorization Server Weaknesses
      • Testing for OAuth Client Weaknesses
      • Testing for OAuth Weaknesses (WSTG-ATHZ-05)
    • Session Management Testing
      • Testing for Session Management Schema (WSTG-SESS-01)
      • Testing for Cookies Attributes (WSTG-SESS-02)
      • Testing for Session Fixation (WSTG-SESS-03)
      • Testing for Exposed Session Variables (WSTG-SESS-04)
      • Testing for Cross Site Request Forgery (WSTG-SESS-05)
      • Testing for Logout Functionality (WSTG-SESS-06)
      • Testing Session Timeout (WSTG-SESS-07)
      • Testing for Session Puzzling (WSTG-SESS-08)
      • Testing for Session Hijacking (WSTG-SESS-09)
      • Testing JSON Web Tokens (WSTG-SESS-10)
    • Input Validation Testing
      • Testing for Reflected Cross Site Scripting (WSTG-INPV-01)
      • Testing for Stored Cross Site Scripting (WSTG-INPV-02)
      • Testing for HTTP Verb Tampering (WSTG-INPV-03)
      • Testing for HTTP Parameter Pollution (WSTG-INPV-04)
      • Testing for Oracle
      • Testing for MySQL
      • Testing for SQL Server
      • Testing PostgreSQL
      • Testing for MS Access
      • Testing for NoSQL Injection
      • Testing for ORM Injection
      • Testing for Client-side
      • Testing for SQL Injection (WSTG-INPV-05)
      • Testing for LDAP Injection (WSTG-INPV-06)
      • Testing for XML Injection (WSTG-INPV-07)
      • Testing for SSI Injection (WSTG-INPV-08)
      • Testing for XPath Injection (WSTG-INPV-09)
      • Testing for IMAP SMTP Injection (WSTG-INPV-10)
      • Testing for File Inclusion
      • Testing for Code Injection (WSTG-INPV-11)
      • Testing for Command Injection (WSTG-INPV-12)
      • Testing for Buffer Overflow (WSTG-INPV-13)
      • Testing for Format String Injection (WSTG-INPV-13)
      • Testing for Incubated Vulnerability (WSTG-INPV-14)
      • Testing for HTTP Splitting Smuggling (WSTG-INPV-15)
      • Testing for HTTP Incoming Requests (WSTG-INPV-16)
      • Testing for Host Header Injection (WSTG-INPV-17)
      • Testing for Server-side Template Injection (WSTG-INPV-18)
      • Testing for Server-Side Request Forgery (WSTG-INPV-19)
      • Testing for Mass Assignment (WSTG-INPV-20)
    • Testing for Error Handling
      • Testing for Improper Error Handling (WSTG-ERRH-01)
      • Testing for Stack Traces (WSTG-ERRH-02)
    • Testing for Weak Cryptography
      • Testing for Weak Transport Layer Security (WSTG-CRYP-01)
      • Testing for Padding Oracle (WSTG-CRYP-02)
      • Testing for Sensitive Information Sent via Unencrypted Channels (WSTG-CRYP-03)
      • Testing for Weak Encryption (WSTG-CRYP-04)
    • Business Logic Testing
      • Introduction to Business Logic
      • Test Business Logic Data Validation (WSTG-BUSL-01)
      • Test Ability to Forge Requests (WSTG-BUSL-02)
      • Test Integrity Checks (WSTG-BUSL-03)
      • Test for Process Timing (WSTG-BUSL-04)
      • Test Number of Times a Function Can Be Used Limits (WSTG-BUSL-05)
      • Testing for the Circumvention of Work Flows (WSTG-BUSL-06)
      • Test Defenses Against Application Misuse (WSTG-BUSL-07)
      • Test Upload of Unexpected File Types (WSTG-BUSL-08)
      • Test Upload of Malicious Files (WSTG-BUSL-09)
      • Test Payment Functionality (WSTG-BUSL-10)
    • Client-Side Testing
      • Testing for Self DOM Based Cross-Site Scripting
      • Testing for DOM-Based Cross Site Scripting (WSTG-CLNT-01)
      • Testing for JavaScript Execution (WSTG-CLNT-02)
      • Testing for HTML Injection (WSTG-CLNT-03)
      • Testing for Client-side URL Redirect (WSTG-CLNT-04)
      • Testing for CSS Injection (WSTG-CLNT-05)
      • Testing for Client-side Resource Manipulation (WSTG-CLNT-06)
      • Testing Cross Origin Resource Sharing (WSTG-CLNT-07)
      • Testing for Cross Site Flashing (WSTG-CLNT-08)
      • Testing for Clickjacking (WSTG-CLNT-09)
      • Testing WebSockets (WSTG-CLNT-10)
      • Testing Web Messaging (WSTG-CLNT-11)
      • Testing Browser Storage (WSTG-CLNT-12)
      • Testing for Cross Site Script Inclusion (WSTG-CLNT-13)
      • Testing for Reverse Tabnabbing (WSTG-CLNT-14)
    • API Testing
      • Testing GraphQL (WSTG-APIT-01)
  • Reporting
    • Reporting
    • Vulnerability Naming Schemes
  • Appendix
    • Testing Tools Resource
    • Suggested Reading
    • Fuzz Vectors
    • Encoded Injection
    • History
    • Leveraging Dev Tools
  • Testing Checklist
  • Table of Contents
  • REST Assessment Cheat Sheet
  • API Testing
Powered by GitBook
On this page
  • Summary
  • Test Objectives
  • How to Test
  • Types of MFA
  • Check for MFA Bypasses
  • Check MFA Management
  • Check MFA Recovery Options
  • One-Time Passwords
  • Mobile Apps and Push Notifications
  • IP Address and Location Filtering
  • Certificates and Smartcards
  • Related Test Cases
  • Remediation
  • References
  1. Web Application Security Testing
  2. Authentication Testing

Testing Multi-Factor Authentication (MFA) (WSTG-AUTH-11)

PreviousTesting for Weaker Authentication in Alternative Channel (WSTG-ATHN-10)NextAuthorization Testing

Last updated 2 years ago

ID

WSTG-AUTH-11

Summary

Many applications implement Multi-Factor Authentication (MFA) as an additional layer of security to protect the login process. This is also known as two-factor authentication (2FA) or two-step verification (2SV) - although these are not strictly the same thing. MFA means asking the user to provide at least two different when logging in.

MFA adds additional complexity to both the authentication functionality, and also to other security-related areas (such as credential management and password recovery), meaning that it is critical for it to be implemented in a correct and robust manner.

Test Objectives

  • Identify the type of MFA used by the application.

  • Determine whether the MFA implementation is robust and secure.

  • Attempt to bypass the MFA.

How to Test

Types of MFA

MFA means that at least two of the following factors are required to authentication:

Factor
Examples

Something You Know

Passwords, PINs and security questions.

Something You Have

Hardware or software tokens, certificates, email*, SMS, and phone calls.

Something You Are

Fingerprints, facial recognition, iris scans, handprint scans and behavioural factors.

Location

Source IP ranges, and geolocation.

* Email only really constitutes "something you have" if the email account itself is protected with MFA. As such, it should be considered weaker than other alternatives such as certificates or TOTP, and may not be accepted as MFA under some definitions.

Note that requiring multiple examples of a single factor (such as needing both a password and a PIN) does not constitute MFA, although it may provide some security benefits over a simple password, and may be considered two-step verification (2SV).

Due to the complexity of implementing biometrics in a browser-based environment, "Something You Are" is rarely used for web applications, although it is starting to be adopted using standards such as WebAuthn. The most common second factor is "Something You Have".

Check for MFA Bypasses

The first step for testing MFA is to identify all of the authentication functionality in the application, which may include:

  • The main login page.

  • Security critical functionality (such as disabling MFA or changing a password).

  • Federated login providers.

  • API endpoints (from both the main web interface and mobile apps).

  • Alternative (non-HTTP) protocols.

  • Test or debug functionality.

All of the different login methods should be reviewed, to ensure that MFA is enforced consistently. If some methods do not require MFA, then these can provide a simple method to bypass them.

If the authentication is done in multiple steps then it may be possible to bypass it by completing the first step of the authentication process (entering the username and password), and then force-browsing to the application or making direct API requests without completing the second stage (entering the MFA code).

In some cases, there may also be intentional MFA bypasses implemented, such as not requiring MFA:

  • From specific IP addresses (which may be spoofable using the X-Forwarded-For HTTP header).

  • When a specific HTTP header is set (such as a non-standard header like X-Debug).

  • For a specific hard-coded account (such as a "root" or "breakglass" account).

Where an application supports both local and federated logins, it may be possible to bypass the MFA if there is no strong separation between these two types of accounts. For example, if a user registers a local account and configures MFA for it, but does not have MFA configured on their account on the federated login provider, it may be possible for an attacker to re-register (or link) a federated account on the target application with the same email address by compromising the user's account on the federated login provider.

Check MFA Management

The functionality used to manage MFA from inside the user's account should be tested for vulnerabilities, including:

  • Is the user required to re-authenticate to remove or change MFA settings?

Check MFA Recovery Options

Many applications will provide users with a way to regain access to their account if they are unable to authenticate with their second factor (for example if they have lost their phone). These mechanisms can often represent a significant weakness in the application, as they effectively allow the second authentication factor to be bypassed.

Recovery Codes

Some applications will provide the user with a list of recovery or backup codes when they enable MFA, which can be used to login. These should be checked to ensure:

  • They are sufficiently long and complex to protect against brute-force attacks.

  • They are securely generated.

  • They can only be used once.

  • Brute-force protection is in place (such as account lockout).

  • The user is notified (via email, SMS, etc) when a code is used.

MFA Reset Process

Alternative Authentication

One-Time Passwords

The most common form of MFA is the one of One-Time Passwords (OTPs), which are typically six-digit numeric codes (although they can be longer or shorter). These can either be generated by both the server and the user (for example, with an authenticator app), or can be generated on the server and sent to the user. There are various ways that this OTP can be provided to the user, including:

Type
Description

HMAC One-Time Password (HOPT)

Generates a code based on the HMAC of a secret and a shared counter.

Time-based One-Time Password (TOTP)

Generates a code based on HMAC of a secret and the current time.

Email

Sends a code via email.

SMS

Sends a code via SMS.

Phone

Sends a code via a voice call to a phone number.

The OTP is typically entered after the user has provided their username and password. There are various checks that should be performed, including:

  • Is the account locked out after multiple failed MFA attempts?

  • Is the user's IP address blocked after multiple failed MFA attempts across different accounts?

  • Are failed MFA attempts logged?

Depending on the type of OTPs used, there are also some other specific checks that should be performed:

  • How are OTPs sent to user (email, SMS, phone, etc)

    • Is there rate limiting to prevent SMS/phone spam costing money?

  • How strong are OTPs (length and keyspace)?

  • How long are OTPs valid for?

  • Are multiple OTPs valid at once?

  • Can the OTPs be used more than once?

  • Are the OTPs tied to the correct user account or is it possible to authenticate with them on other accounts?

HOTP and TOTP

HOTP and TOTP codes are both based on a secret that is shared between the server and the user. For TOTP codes, this is usually provided to the user in the form of a QR code that they scan with an authenticator app (although it can also be provided as a text secret for them to manually enter).

Where the secret can be provided by the user, an appropriate minimum length should be enforced, and the input should be checked for the usual injection attacks.

Valid Codes
Success rate after 1 hour
Success rate after 4 hours
Success rate after 12 hours
Success rate after 24 hours

1

4%

13%

35%

58%

3

10%

35%

72%

92%

5

16%

51%

88%

99%

7

22%

63%

95%

99%

Email, SMS, and Phone

Where codes are generated by the server and sent to the client, the following areas should be considered:

  • Is the transport mechanism (email, SMS, or voice) secure enough for the application?

  • Are the codes sufficiently long and complex?

  • How long are the codes valid for?

  • Are multiple codes valid at once, or does generating a new code invalidate the previous one?

    • Could this be used to block access to an account by repeatedly requesting codes?

  • Is there sufficient rate-limiting to prevent an attacker requesting large numbers of codes?

    • Large numbers of emailed code may get the server blocked for sending spam.

    • Large numbers of SMS or voice calls may cost money, or be used to harass a user.

Mobile Apps and Push Notifications

An alternative approach to OTP codes is to send a push notification to the user's mobile phone, which they can either approve or deny. This method is less common, as it requires the user to install an application-specific authenticator.

Properly evaluating the security of this requires the scope of testing to be expanded to cover both the mobile app, and any supporting APIs or services used by it; meaning that it would often be outside of the scope of a traditional web application test. However, there are a couple of simple checks that can be performed without testing the mobile app, including:

  • Does the notification provide sufficient context (IP addresses, location, etc) for the user to make an informed decision about whether to approve or deny it?

  • Is there any kind of challenge and response mechanism (such as providing a code on the website that the user needs to enter into the app - often called "number matching" or "number challenge")?

  • Is there any rate limiting or mechanisms to prevent the user from being spammed with notifications in the hope that they will just blindly accept one?

IP Address and Location Filtering

One of the factors that is sometimes used with MFA is location ("somewhere you are"), although whether this constitutes a proper authentication factor is debatable. In the context of a web application, this typically means restricting access to specific IP addresses, or not prompting the user for a second factor as long as they are connecting from a specific trusted IP address. A common scenario for this would be to authenticate users with just their password when connecting from the office IP ranges, but requiring an OTP code when they connect from elsewhere.

Depending on the implementation, it may be possible for a user to spoof a trusted IP address by setting the X-Forwarded-For header, which could allow them to bypass this check. Note that if the application does not correctly sanitize the contents of this header, it may also be possible to carry out attack such as SQL injection here. If the application supports IPv6, then this should also be checked to ensure that appropriate restrictions are applied to those connections.

Additionally, the trusted IP addresses should be reviewed to ensure that they do not present any weaknesses, such as if they include:

  • IP addresses that could be accessible by untrusted users (such as the guest wireless networks in an office).

  • Dynamically assigned IP address that could change.

  • Public network ranges where an attacker could host their own system (such as Azure or AWS).

Certificates and Smartcards

Transport Layer Security (TLS) is commonly used to encrypt traffic between the client and the server, and to provide a mechanism for the client to confirm the identity of the server (by comparing Common Name (CN) or Subject Alternative Name (SAN) on the certificate to the requested domain). However, it can also provide a mechanism for the server to confirm the identity of the client, known as client certificate authentication or mutual TLS (mTLS). A full discussion of client certificate authentication is outside of the scope of this guide, but the key principle is that the user presents a digital certificate (stored either on their machine or on a smartcard), which is validated by the server.

The first step when testing is to determine whether the target application restricts the Certificate Authorities (CAs) that are trusted to issue certificates. This information can be obtained using various tools, or by manually examining the TLS handshake. The simplest way is to use OpenSSL's s_client:

$ openssl s_client -connect example:443
[...]
Acceptable client certificate CA names
C = US, ST = Example, L = Example, O = Example Org, CN = Example Org Root Certificate Authority
Client Certificate Types: RSA sign, DSA sign, ECDSA sign

If there are no restrictions, then it may be possible to authenticate using a certificate from a different CA. If there are restrictions but they are badly implemented, it may be possible to create a local CA with the correct name ("Example Org Root Certificate Authority" in the example above), and to use this new CA to sign client certificates.

If a valid certificate can be obtained, then it should also be verified that the certificate can only be used for the user that it is issued for (i.e, that you can't use a certificate issued to Alice to authenticate on Bob's account). Additionally, certificates should be checked to ensure that they have neither expired nor been revoked.

Related Test Cases

Remediation

Ensure that:

  • MFA is implemented for all relevant accounts and functionality on the applications.

  • The support MFA methods are appropriate for the application.

  • The mechanisms used to implement MFA are appropriately secured and protected against brute-force attacks.

  • There is appropriate auditing and logging for all MFA-related activity.

References

Finally, if the MFA is implemented on a different system to the main application (such as on a reverse proxy, in order to protect a legacy application that does not natively support MFA), then it may be possible to bypass it by connecting directly to the backend application server, as discussed in the guide on how to .

Is the MFA management functionality vulnerable to ?

Can other users' MFA setting be modified through ?

See the for further details.

If the application implements an MFA reset process, this should be tested in the same way that the is tested. It is important that this process is at least as strong as the MFA implementation for the application.

Some applications will allow the user to prove their identity through other means, such as the use of . This usually represents a significant weakness, as security questions provide a far lower level of security than MFA.

Is the form vulnerable to injection attacks, including ?

Where the secret is generated on the server, it should be checked to ensure that it is sufficiently long and complex ( recommends at least 160 bits), and that it is generated using a .

TOTP codes are typically valid for 30 seconds, but some applications choose to accept multiple codes (such as the previous, current, and next codes) in order to deal with differences between the system time on the server and on the user's device. Some applications may allow multiple codes on either side of the current one, which may make it easier for an attacker to guess or brute-force the code. The table below shows the chance of successfully brute-forcing an OTP code based on an attacker being able to make 10 requests a second, for applications that accept either only the current code, or multiple codes (see for the calculations behind the table).

Are the codes generated using a ?

See the for further recommendations.

cross-site request forgery
IDOR vulnerabilities
"Backup Codes" section in the Forgotten Password Cheat Sheet
password reset process
security questions
RFC 4226
secure random function
this article
secure random function
Testing for Weak Lock Out Mechanism
Testing for Weak Password Change or Reset Functionalities
OWASP Multi-Factor Authentication Cheat Sheet
OWASP Multi-Factor Authentication Cheat Sheet
authentication factors
map the application architecture
SQL wildcard injection