Automating MFA in Amazon EC2 instance adds a critical security layer to protect your infrastructure. By configuring MFA for SSH access, you’re ensuring that access requires more than just a private key or password. Users must also present a time-based one-time password (TOTP) generated by an MFA device, such as Google Authenticator or Authy. This means that even if an attacker manages to obtain an SSH key, they cannot access the instance without the MFA token. Implementing MFA on EC2, especially Amazon Linux, helps safeguard your system from unauthorized access and significantly reduces the risk of remote attacks.
In addition to MFA, you may have SELinux (Security-Enhanced Linux) enabled on your Amazon Linux instance. SELinux is a security mechanism that provides an additional layer of protection for the system by enforcing security policies that govern how processes interact with each other and the system’s files. But, automating MFA in Amazon EC2 instance with SELinux enabled requires ensuring that the necessary security contexts and policies are properly configured to allow the MFA process to work alongside SELinux’s protections.

In this guide, we will walk through the following steps:
- Setting up MFA on the EC2 instance for SSH login.
- Ensure SELinux is properly configured to not interfere with the MFA process.
- Testing the MFA-enabled SSH login to ensure that access is secure and compliant with both MFA and SELinux policies.
Key Components for This Setup:
- Amazon EC2 Instance running Amazon Linux (or compatible version) with SELinux enabled.
- Virtual MFA device (such as Google Authenticator or Authy).
- SSH access is configured for the EC2 instance.
- Sudo privileges on the EC2 instance to modify configurations.
- The system has SELinux enabled and configured to permit the necessary changes required for implementing MFA.
Why You Need SELinux and MFA?
- MFA: Protects against unauthorized access by requiring users to provide not only their SSH key but also a time-sensitive code from a registered MFA device.
- SELinux: SELinux adds an additional security layer by actively controlling processes and access to files through strict security policies. To enable MFA on your EC2 instance, you must configure SELinux to allow the necessary modifications and ensure it doesn’t block authentication-related operations.
By the end of this guide, you’ll have successfully automate MFA in Amazon EC2 for SSH access to your Amazon Linux instance, with SELinux configured to support the changes without breaking the system’s security context. This will significantly enhance your instance’s overall security, making unauthorized access much more difficult.
Step 1: Installing Google Authenticator on the EC2 Instance
First, SSH into your EC2 instance. Once connected, switch to the root user (or use sudo
for administrative tasks) and install the necessary software packages.
- Install Google Authenticator and QRencode: Run the following commands to install the Google Authenticator PAM module and
qrencode
(for generating QR codes):sudo dnf install google-authenticator qrencode -y
- Initialize Google Authenticator: Run the
google-authenticator
command for the user for whom you want to enable MFA (e.g.,ec2-user
). This command will generate a secret key and provide a QR code to scan with the Google Authenticator app.google-authenticator -s ~/.ssh/google_authenticator
When you set up Google Authenticator on your EC2 instance, the system prompts you with several configuration questions to customize how MFA (Multi-Factor Authentication) operates. These prompts allow you to fine-tune the behavior of the authentication process—helping you strike the right balance between strong security and user convenience. Below is a detailed breakdown of each option and what it means:
Do you want authentication tokens to be time-based?
Prompt:Do you want authentication tokens to be time-based? (y/n)
- Google Authenticator and most MFA apps use time-based tokens by default. These tokens expire after a short period, usually 30 seconds, and then generate a new token for the next time window. This time-based approach ensures that even if someone intercepts a token, they cannot reuse it later. Therefore, choosing Yes (y) to enable time-based tokens is recommended because it provides stronger security. Regular rotation of tokens reduces the risk of reuse or interception.
The system displays a QR code for you to scan or lets you manually enter the secret key into your authentication app. You add your account name and enable the time-based option. You must securely store the secret key, verification codes, and scratch codes generated during this process in case you lose access to the app. Remember that you can use each scratch code only once. Instead of entering the key manually, you will scan the QR code.
Next, You’ll be prompted with several questions to configure MFA:
a. Do you want me to update your “/home/ec2-user/.ssh/.google_authenticator” file? (y/n)
When you configure Google Authenticator for Multi-Factor Authentication (MFA) on your EC2 instance, one of the prompts you will encounter is:Do you want me to update your "/home/ec2-user/.ssh/.google_authenticator" file (y/n)?
The .google_authenticator file stores your secret key, OTP settings, and scratch codes crucial for MFA setup and recovery.
b . Do you want to disallow multiple uses of the same authentication token?
Prompt:Do you want to disallow multiple uses of the same authentication token? (y/n)
- If you choose Yes (
y
), each authentication token will only be valid for a single login attempt. This ensures that once you use a token to log in successfully, it becomes invalid and cannot be reused—even if someone tries to enter the same token again. Disallowing multiple uses of the same token provides an additional layer of security. In case a malicious actor intercepts a token during transmission, they won’t be able to reuse it for another login attempt, even if they manage to access the server or your session. Recommendation: Yes (y
) is recommended because it prevents the token from being reused by attackers, which is a useful security measure. It forces attackers to generate a new token for each login attempt, reducing the chances of successful brute-force attacks.
c . Do you want to increase the time window for valid tokens (default is 1:30 min)?
Prompt:Do you want to increase the time window for valid tokens (default is 1:30 min)? (y/n)
- This option allows you to extend the time window in which a generated authentication token is valid. By default, Google Authenticator tokens are valid for 30 seconds (the “1:30 min” refers to the 1 minute 30 seconds time window, which includes the current 30-second token and the previous and next 30-second tokens to accommodate any time skew between the client and server). Increasing the time window (e.g., to 4 minutes) could be helpful if you’re experiencing issues with time synchronization between the client (your phone or device) and the server, especially if you are in a region with unstable or variable network conditions. However, the downside is that extending the window makes it easier for attackers to guess the token, as they have more time to try to authenticate.
- Recommendation: Choosing No (n) is generally the best option. The default 1 minute and 30-second window typically offers a solid balance between security and usability. You should only consider extending this time window if you’re experiencing issues with clock drift or synchronization delays between your MFA device and the server.
d . Do you want to enable rate-limiting for login attempts?
Prompt:Do you want to enable rate-limiting for login attempts? (y/n)
- Rate-limiting helps prevent brute-force attacks by limiting the number of login attempts a user can make within a specific time frame. If enabled, the system will allow only a certain number of authentication attempts (e.g., 3 attempts) within a defined period (e.g., 30 seconds). After this limit is reached, further attempts will be blocked temporarily. Recommendation: Yes (
y
) is the recommended option. Enabling rate-limiting is a simple but effective way to reduce the chances of a successful brute-force attack. If an attacker tries to guess the token by repeatedly entering incorrect values, the system will block them after a few failed attempts, making it much harder for them to break into the system.
- Restore the SELinux context for the new configuration: Since we have SELinux enabled, we need to restore the proper security context for the
.google_authenticator
file:restorecon -Rv ~/.ssh/
Step 2: Configure PAM (Pluggable Authentication Module) for automating MFA in Amazon EC2
The next step is to modify the PAM configuration to enable Google Authenticator for SSH logins. We’ll update the PAM configuration file (/etc/pam.d/sshd
) to require Google Authenticator’s second-factor authentication.
- Edit the PAM configuration file: Open the PAM configuration file for SSH (
/etc/pam.d/sshd
) with a text editor:sudo nano /etc/pam.d/sshd
Add the following line at the bottom of the file to enable Google Authenticator for MFA:auth required pam_google_authenticator.so secret=/home/${USER}/.ssh/google_authenticator auth required pam_permit.so
(This is a single line command)
Alternatively, if you want to allow some users to bypass MFA, you can add thenullok
option to the end of the line:auth required pam_google_authenticator.so secret=/home/${USER}/.ssh/google_authenticator nullok auth required pam_permit.so
(This is a single line command)
Note:nullok
will allow users who haven’t set up MFA to log in without a second-factor prompt. - Comment out the password authentication line: In the same file (
/etc/pam.d/sshd
), find the line that referencespassword-auth
and comment it out to ensure only SSH key-based authentication and MFA are required:#auth substack password-auth
You may also like: Full AWS CodeDeploy tutorial with Tomcat Server Deployment with Code
Step 3: Update SSH Configuration to Require MFA
Next, we need to update the SSH server configuration (/etc/ssh/sshd_config
) to require both an SSH key and a verification code.
- Edit the SSH configuration file: Open the SSH configuration file with a text editor:
sudo nano /etc/ssh/sshd_config
- Make the following changes:
- Disable the interactive keyboard authentication: Comment out the line:
#KbdInteractiveAuthentication yes KbdInteractiveAuthentication yes
- Enable Challenge-Response Authentication: Uncomment or add the following line:
ChallengeResponseAuthentication yes
- Enable the Authentication Methods: Add this line at the bottom of the file:
AuthenticationMethods publickey,keyboard-interactive
- Disable the interactive keyboard authentication: Comment out the line:
- Restart the SSH service: After saving the changes, restart the SSH service for the changes to take effect:
sudo systemctl restart sshd.service
Step 4: Test the Automating MFA in Amazon EC2 Instance
To confirm MFA is working correctly, open a new terminal and attempt to SSH into your EC2 instance. After entering your SSH key passphrase (if required), the system prompts you to provide a verification code from your Google Authenticator app. When you enter the correct code, the system grants access, confirming that MFA is properly set up.
Example prompt:
Verification code:
Enter the code shown in your Google Authenticator app. If the code is correct, the system logs you in successfully.If you fail to authenticate, check that your system time syncs accurately, because Google Authenticator uses time-based one-time passwords (TOTP), and even small time differences cause login problems.
Step 5: Force Users to Set Up Google Authenticator on First Login
Create a script to prompt users to set up Google Authenticator if they haven’t configured MFA during first login. This will be our final step in automating MFA in Amazon EC2 instance.
- Create a script to enforce MFA setup: Create a new file in the
/etc/profile.d/
directory:sudo nano /etc/profile.d/mfa.sh
Paste the following script into the file:if [ ! -e ~/.ssh/google_authenticator ] && [ "$USER" != "root" ];
then google-authenticator -s ~/.ssh/google_authenticator
restorecon -Rv ~/.ssh/
echo "Save the generated emergency scratch codes and use the secret key or scan the QR code to register your device for multifactor authentication."
echo "Login again using your ssh key pair and the generated One-Time Password on your registered device."
echo "logout"
fi
- Set the correct permissions for the script: Set the script file’s permissions to make it readable for all users:
sudo chmod o+r /etc/profile.d/mfa.sh
- Update PAM configuration: Update the PAM configuration for SSH (
/etc/pam.d/sshd
) to run the MFA setup script on user login:auth required pam_google_authenticator.so secret=/home/${USER}/.ssh/google_authenticator nullok
(This is a single line command)
Remove nullok
After MFA Setup
Once all users have configured MFA, you can remove the nullok
option from the PAM configuration file to ensure that users must use MFA for all future logins.
- Edit the PAM configuration again:
sudo nano /etc/pam.d/sshd
- Remove
nullok
from the line that includespam_google_[authenticator.so](<http://authenticator.so/>)
:auth required pam_google_authenticator.so secret=/home/${USER}/.ssh/google_authenticator
- Save and exit.
Conclusion
By following these steps, you’ve successfully automated Multi-Factor Authentication (MFA) on your Amazon EC2 instance running Amazon Linux 2023. This setup enhances security by requiring users to authenticate with both an SSH key and a time-based OTP generated by the Google Authenticator app.
Additionally, by configuring SELinux properly, you maintain strict security policies without interfering with MFA functionality. Enforcing MFA setup on a user’s first login ensures that every individual accessing your EC2 instance is protected with an extra layer of authentication, further strengthening your instance’s overall security posture.
If you like scripts or any other automation tasks, feel free to reach out to us at guidekorner@gmail.com. Don’t forget to subscribe to our newsletter for more updates and helpful tips!