IP Address interpretation bugs (CVE-2021-29921) and AWS EC2 IMDsv2
A quick post to talk about the recently discovered IP address interpretation bug - CVE-2021-29921 and it's impact, if any, on the protection offered by IMDSv2 on AWS.
Background
A recently announced vulnerability (CVE-2021-29921) in the way Python's ipaddress library handles leading zeroes in IPv4 addresses triggered an internal discussion at Kloudle around AWS EC2 IMDSv2 and the protection it offers around SSRF.
What is the bug?
The ipaddress library between Python v3.8.0 and v3.10 does improper input validation of IP addresses that have a leading zero in the octets.
IP addresses can be denoted in many forms, the most common of which we know is the Dotted Decimal Notation. Examples of these would be 8.8.8.8, 127.0.0.1, 61.34.56.1 etc. Each byte separated by a dot goes from 0 and 255. A IPv4 Dotted Decimal IP address (127.0.0.1) can also be written in binary (01111111.00000000.00000000.0000000), hexadecimal (7f.00.00.01, 0x7f000001) and octal (0177.0000.0000.0001, 017700000001) formats.
The bug occurs as the Python library left strips any zeros from an IP address where the octet starts with a zero denoting an Octal notation and string length of 3 characters. An IP address like 010.8.8.8, which is octal for 8.8.8.8 gets converted to 10.8.8.8 by Python's ipaddress library, which is a completely different server! Octal IP addresses like 0116.0116.0014.0014 are not affected.
Understanding the bug in context with SSRF and AWS
Server Side Request Forgery is a common vulnerability that can occur in systems that trust user input and make a server side request on the user's behalf. This request could be a raw network request at the TCP/UDP layers or an application specific request like HTTP. As long as the server trusts the user input and makes the request to a user controlled destination, regardless of technology or communication channel, it is vulnerable to SSRF.
All cloud compute instances could become vulnerable to SSRF if there is code running that makes server side requests to user provided destinations. A well known dangerous outcome of this is that cloud compute instances can allow access to the instance metadata endpoints allowing the attacker to extract information about the instance or in some cases extract temporary credentials attached to the compute instance.
There are multiple ways of fixing an SSRF or from restricting what an attacker can do even if they do exploit the bug. Input sanitisation, using an allow list and dropping everything else, using a deny list of sensitive IP addresses that should never be accessed etc. are all valid solutions from the application point of view.
To ensure even more defense in depth, IMDSv2 can be enabled on AWS EC2 instances that would require the presence of a header which would thwart most attempts at the SSRF from accessing the instance metadata endpoint.
To put it plainly, if a SSRF vulnerable application is hosted on an EC2 instance with IMDSv1 then the following attacker input would work, resulting in IAM role temporary credentials to be generated.
https://169.254.169.254/latest/meta-data/iam/security-credentials/<role-name>/credentials
However, the same attack payload will not work if the EC2 instance is configured to use IMDSv2 as the instance metadata endpoint expects a token passed via a `x-aws-ec2-metadata-token` header which is in turn generated using a PUT request with a `x-aws-ec2-metadata-token-ttl-seconds` header.
So, now the question that we were trying to answer was, would an AWS EC2 instance with IMDSv2 become vulnerable if it is running a vanilla SSRF vulnerable Python application with the vulnerable ipaddress module being used to make server side requests while the application filters sensitive IPs like 169.254.169.254?
Verdict?
The instance would not be vulnerable.
There are multiple things at play here. The usage of IMDSv2 definitely creates a condition that cannot be bypassed with a simple SSRF where the attacker can only control the destination address and has no control over the method of the server side request (PUT, POST etc.), headers in the server side request or the body of the server side request. Regardless of what IP address notation we use, what hostname bypass we attempt, what DNS manipulation you do, IMDSv2 cannot be bypassed unless you can control the things mentioned above.
If the application was filtering sensitive destination addresses like 169.254.169.254, we could still achieve a non exploitable SSRF with the octal notation 0251.0376.0251.0376 or 0251.254.169.254 or 169.254.169.0376 or 169.0376.169.0376 (all of which are valid representations of 169.254.169.254). This IP itself is not impacted by the Python bug as the octet string length is 4 characters including the zero. So the Python bug is harmless when attempting to access the instance metadata endpoint.
Try this at home
To quickly check and verify this weird behavior, run the following commands in your terminal after starting Python3 interpreter
>>> import ipaddress
>>> harmless_ip = '010.0.0.1' >>> print(ipaddress.ip_network(harmless_ip, strict=True)) 10.0.0.1/32 >>> harmless_ip = '169.254.169.254' >>> print(ipaddress.ip_network(harmless_ip, strict=True)) 169.254.169.254/32 >>> harmless_ip = '0251.254.169.254' >>> print(ipaddress.ip_network(harmless_ip, strict=True)) Traceback (most recent call last): File "<stdin>", line 1, in <module> File "/usr/lib/python3.8/ipaddress.py", line 83, in ip_network raise ValueError('%r does not appear to be an IPv4 or IPv6 network' % ValueError: '0251.254.169.254' does not appear to be an IPv4 or IPv6 network
Conclusion
The CVE-2021-29921 bug in Python's ipaddress module does not change the way the instance metadata IP address is interpreted owing to the Octal notation of the IP 169.254.169.254 has 4 characters including the zero required for Octal interpretation. Developers still need to ensure proper sanitisation is achieved to ensure the application makes a request to the intended resource and does not give rise to an indeterminate SSRF bug. AWS administrators can (need to) enable IMDSv2 on their instances to employ a defense in depth approach to protect the instance metadata from vanilla SSRF issues.
Associate Consultant at Tata Consultancy Services | Ex-Accenture| | CISM | ECSA | RedHat | Web Application Security & Scanning | Vulnerability Management | Product Security | Application Security
3 å¹´Helpful! This will