- Critical Thinking - Bug Bounty Podcast
- Posts
- [HackerNotes Ep.92] SAML XPath Confusion, Chinese DNS Poisoning, and AI-Powered 403 Bypasser
[HackerNotes Ep.92] SAML XPath Confusion, Chinese DNS Poisoning, and AI-Powered 403 Bypasser
This weeks HackerNotes has dropped covering a bunch of new research. We've got SAML XPath confusion, some AssetNote research,WAF bypasses and a whole lot more. Check it out below!
Hacker TLDR;
Vulns caused by the Great Firewall of China: It turns out everything that passes through China’s infrastructure gets a little tampered with, who would have guessed? The key here is that researchers at Assetnote and Todayisnew found out that everything that used Chinese infrastructure was being checked for blacklisted keywords and then resolved to random IP addresses (that did not always exist) if something prohibited was found.
During the research, they found it possible to perform a kind of takeover because some of these seemingly random points pointed to Fastly. So it was just a matter of testing stuff until something popped up.
They also identified it was possible to trigger an XSS when one of the IPs was running a vulnerable version of cPanel.
Ruby-SAML / GitLab Authentication Bypass (CVE-2024-45409): ProjectDiscovery once again with a cool writeup from a CVE originally discovered by a researcher named
ahacker
. SAML is a protocol for secure authentication between identity providers and service providers, they found out that theXPath
selection was too broad and allowed attackers to inject a fake value earlier in the document to bypass authentication:encoded_digest_value = REXML::XPath.first( ref, "//ds:DigestValue", { "ds" => DSIG } )
The
//
in the XPath made it vulnerable to exploitation via thesamlp:extensions
element, because//
enables selection from anywhere in the document, including nested nodes.Exploiting CVE-2024-20017 in 4 Different Ways: @hyprdude introduces a case study exploring multiple exploit strategies for a stack buffer overflow vulnerability (CVE-2024-20017) caused by a copy operation using an attacker-controlled length value without any form of bounds checking.
The article aims to demonstrate various ways to exploit this single vulnerability under different conditions and mitigations.
The article also covers four different exploits for the bug, ranging from a basic version with minimal mitigations to a more complex exploit targeting the Netgear WAX206 device. These exploits demonstrate progression from x86-64 to arm64 architecture + security measures. In order to get a good understanding of how everything works, checking the full writeup is highly recommended, as it’s very technical.
Achieving RCE In A LLaMA.cpp RPC Server: A vulnerability in LLaMA.cpp allowed attackers to exploit chatbots hosted on servers or personal machines. The flaw leaked memory addresses and enabled arbitrary read/write capabilities.
The issue originated from the user’s ability to directly set the
data
pointer in therpc_tensor
structure. By analyzing the code and developer comments, researchers achieved arbitrary read/write access and RCE.
The White House has recently banned the use of Kaspersky products across the United States, citing concerns over potential data access risks and allegations of incorporating "backdoors" in their software.
Learn More About the ThreatLocker® Cyber Health Report Here
Researchers at Assetnote uncovered an intriguing DNS behaviour while processing millions of queries for their clients. They spotted an unusual pattern with a China-based client: numerous subdomains were resolving to seemingly random IP addresses.
Initially assumed to be a one-off DNS misconfig, the issue proved far more widespread. After encountering similar problems with other customers, the team realised they’d stumbled onto China’s DNS query tampering.
The scope of this issue is massive. In 2022, Chinese domains reached a whopping 33.8 million, not counting other TLDs routing through Chinese infrastructure. Estimates suggest tens of millions of zones could be vulnerable to these attack vectors.
To broaden their investigation, the researchers collaborated with Eric (todayisnew) an independent expert who’d also identified this issue. I’m sure you know who he is: https://hackerone.com/todayisnew?type=user (:
Unreliable DNS Resolvers
During their investigation, they encountered inconsistent DNS responses. At first, they suspected server-side load balancing or other technical issues. But further analysis revealed a pattern: all domains under the .cn TLD were affected by this vuln. Regardless of it’s TLD, any domain using nameservers located in China was subject to this DNS poisoning, confirming the widespread nature of the problem and its potential impact on global internet traffic passing through Chinese infrastructure.
While investigating a DNS inconsistency issue, they traced the problem to nameservers on alibabadns.com and observed unstable IP address resolutions for certain domains, which helped pinpoint the source of the issue.
Through further testing, Assetnote discovered that queries containing specific keywords, such as "webproxy.id", triggered this behaviour and even non-existent domains with these keywords would return unexpected responses. Similar behaviour could be seen even with Cloudflare’s DNS.
Weaponising via Fastly
Taking this a step further, Assetnote discovered a way to exploit China’s DNS poisoning using Fastly’s CDN. They found that some poisoned IP addresses pointed to Fastly, which allowed them to manipulate subdomains not already claimed on Fastly.
The researchers exploited this by:
Registering a Fastly account and creating a CDN profile
Adding *.domain.tld to the configuration
Pointing the Fastly CDN profile to their server
Using client-side code to generate random subdomains
Loading images from these subdomains until finding a poisoned one
This method allowed Assetnote to serve content for any subdomain of the target domain through Fastly, effectively exploiting the DNS poisoning vulnerability.
Weaponising via cPanel XSS
Another method exploits the Chinese DNS poisoning issue through a cross-site scripting (XSS) vulnerability in cPanel. This approach, shared by researcher Eric, proved more versatile than their Fastly proof-of-concept. However, it had a slightly lower impact as it couldn’t capture HTTPOnly cookies.
In the main article you’ll find Eric’s POC code which exploits the fact that one of the IPs returned through the poisoning will likely run a vulnerable version of cPanel, leading to XSS. It generates and tests subdomains until the XSS is triggered
The Impact
This vulnerability essentially functions as a subdomain takeover, so the impact is similar. The researchers identified two distinct exploitation vectors, each with slightly different impacts.
The Fastly takeover technique allows attackers to intercept all traffic routed to their origin. This method is more impactful than a standard XSS vulnerability as it enables the theft of HTTPOnly cookies, which are typically inaccessible to JavaScript. However, this attack requires that the domain isn’t already claimed on Fastly, potentially limiting its effectiveness against high-profile domains.
The cPanel XSS vector, on the other hand, is more universal and affects any domain impacted by China’s DNS poisoning. While it can’t steal HTTPOnly cookies, it works on a broader range of targets.
Theories & Mitigation
Assetnote’s leading theory is that this behaviour results from China’s censorship mechanism. The Great Firewall of China could be manipulating DNS responses based on blacklisted or blocked keywords, primarily targeting VPN software, proxies, adult sites, and file-sharing services.
The researchers noted that the keyword filtering appears to be greedy, triggering when a keyword is embedded anywhere in the domain. This explains why they were able to poison DNS responses for non-existent domains.
Mitigating this risk is challenging, especially for organisations operating in China, because businesses require a valid Chinese Internet Content Provider (ICP) licence to host in China, which comes with specific requirements including using China-based servers and registrars.
The researchers suggested hosting nameservers outside of China as a potential solution, though this could impact speed and reliability for Chinese users. They also emphasised the importance of implementing basic web security hygiene, such as using "Secure" and "HTTPOnly" flags on cookies.
Links:
ProjectDiscovery just dropped some serious stuff about a vulnerability they reverse in Ruby-SAML, and we’re talking about a full-on authentication bypass. This was originally found by a researcher named by ahacker
and later reversed (and written up) by the team over at PD.
Let’s break it down.
SAML 101
First things first, let’s check SAML. This protocol is used for exchanging auth data between identity providers (IdPs) and service providers (SPs) to make sure everything is legit.
How SAML Signatures Work
In a SAML response, we got this thing called an Assertion element. It’s where all the details about an authenticated user lives. To keep it safe from tampering, it gets digitally signed. Here’s how it works:
The Assertion element gets hashed (that’s the digest).
This digest gets tucked into the SignedInfo block of the signature element.
The whole SignedInfo block gets signed with the IdP’s private key.
The Ruby-SAML Vulnerability
Now, here’s the most important part and where it gets interesting. The Ruby-SAML library had this flaw in how it was using XPath to grab elements during validation. Specifically, when it was pulling the DigestValue, it was using this XPath expression:
encoded_digest_value = REXML::XPath.first(
ref,
"//ds:DigestValue",
{ "ds" => DSIG }
)
The problem lies in the //
. It means "grab the first DigestValue you see, anywhere in the document". An attacker could exploit this by sneaking in their own DigestValue earlier in the document, inside the samlp:extensions
element.
Exploitation
Here’s how an attacker could bypass the signature validation:
Slip a DigestValue of a modified assertion into the
samlp:extensions
element.The XPath selector grabs this fake
DigestValue
instead of the real one in the SignedInfo block.The
SignedInfo
block itself isn’t touched, so it still passes the signature check.
Here’s a snippet of what the exploit code might look like:
hash = digest_algorithm.digest(canon_hashed_element)
encoded_digest_value = REXML::XPath.first(
ref,
"//ds:DigestValue",
{ "ds" => DSIG }
)
digest_value = Base64.decode64(OneLogin::RubySaml::Utils.element_text(encoded_digest_value))
unless digests_match?(hash, digest_value)
return append_error("Digest mismatch", soft)
end
unless cert.public_key.verify(signature_algorithm.new, signature, canon_string)
return append_error("Key validation error", soft)
end
The Takeaway
This CVE-2024-45409 vulnerability is a prime example of how a tiny flaw in signature verification can lead to a massive security hole. It’s a wake-up call for developers to be extra careful when implementing security protocols like SAML.
If you’re using Ruby-SAML or OmniAuth-SAML for authentication, make sure you’ve updated to the latest version ASAP.
Mad props to ProjectDiscovery.
Links:
The bug was found using a network fuzzer called fuzzotron, which helps fuzz network services by generating test cases with tools like radamsa.
The bug stems from a lack of bounds checking in the function IAPP_RcvHandlerSSB(). It uses an attacker-controlled value without proper validation, causing a stack buffer overflow when copying data into a smaller structure, leading to a potential security vulnerability.
We’ll talk about some of the exploits briefly because they’re quite complex, but if you want to dig deep into how everything works, we’ll link the write-up at the bottom of this section.
Exploit 1: RIP Hijack Via Corrupted Return Address, ROP to system()
We start with the simplest code execution method, assuming minimal exploit mitigations (except non-executable stack). This allows for predictable addresses without leaks.
This exploit uses a classic RIP hijack via stack overflow to corrupt the return address. The process: overflow the stack, align to corrupt the return address, and wait for function return. We use this to jump to an ROP gadget that loads a command string into registers and calls system()
. Without ASLR, we assume known addresses for system()
and our payload on the stack.
Exploit 2: Arbitrary Write Via Pointer Corruption, GOT Overwrite
With stack canaries and ASLR enabled, the focus shifts from corrupting the return address to corrupting local variables before the stack canary in the function IAPP_RcvHandlerSSB()
. Among these variables, pointers like OidReq
and BufLen
can be corrupted, allowing an arbitrary 4-byte write.
In the function, the corrupted OidReq->Len = BufLen - sizeof(OID_REQ)
enables the write-what-where primitive. The exploit iteratively writes a shell command into the GOT (Global Offset Table), which is writable since partial RELRO is enabled and no PIE (Position Independent Executable) is in place.
To achieve code execution, the exploit:
Writes the shell command to a known address (GOT).
Manipulates the corrupted
OidReq
pointer to adjust the target address.Uses the 4-byte write primitive to overwrite the GOT entry of
read()
with a ROP gadget.This ROP chain prepares the environment by loading the shell command’s address into the
rdi
register (required forsystem()
on x86_64 architecture).Redirects execution to the
system()
function by jumping to asystem()
call in theIAPP_PID_Kill()
function.
A key aspect of this exploit is that is happens asynchronously from the payload that caused corruption. The execution redirection occurs separately from the corrupting payload, triggered only when a final TCP request activates the compromised GOT entry for read()
. This means the controlled data isn’t on the stack top, and the TCP packet’s content is never read, as read()
is overwritten.
If you want to dive into the full writeup, have fun! This research by @hyprdude really is packed with content.
Links:
@Tur24Tur released a new plugin for Caido that you can use to manage your custom wordlists and the ones from the SecLists repository on GitHub
Links:
This plugin strikes an excellent balance between automation and manual exploitation. We can customize how it attempts to bypass 403 errors, tailoring it to our specific needs. Once we’ve configured it to our liking, we can fire it and check how things are going.
It’s such an elegant implementation of AI that offers great value, especially for those of us accustomed to doing things manually most of the time.
One more thing, if we want the sec community to grow it’s incredibly important that we motivate the people who help build the community through their initiatives. So if you like someone’s work, consider supporting them financially, especially if their work helps you make money too!
Here’s the link to @Bebiks’ plugin:
Here’s another very useful tool made by @renniepak, this tool helps us (you guessed it) bypass CSP and exploit XSS on sites where injections are blocked by CSPs.
You can access the tool in the link below and don’t forget to contribute with your findings too on GitHub.
Links:
This one is kinda funny, imagine hosting a chatbot on your server or maybe even your machine just to get pwned. There was a vuln in LLaMA.cpp that leaked the memory addresses where it was allocating data.
It all happened because part of the rpc_tensor
structure that holds a pointer to the memory (the data
pointer) could be directly set by the user. By analysing the code and reading comments made by the devs, it was possible to get arbitrary read, arbitrary write and then finally pop a shell.
As always another proof that it’s incredibly important to read the documentation, we can find a lot of gems there even (especially) in huge projects like this. You’ll find all the links below and @0x_shaq walks us through every step of the process. It really is interesting to see, as people who usually just test web stuff, how other stuff that we are not familiar work. Watching @0x_shaq’s thought process on this really made it look a lot easier than it probably was.
Great stuff, and the video is funny too, go check it out!
Links:
We’ve all been through the process of finding something interesting in the code that was potentially vulnerable to XSS but has been blocked by a WAF. So @Edra went on a quest to build a payload that worked at least in most cases to the most common WAFs.
The key thing here is that he analysed what was being blocked and tried to work around it. Like when he noticed that onerror
was being blocked but aonerror
wasn’t, he came out with the idea of adding a quoted string right before the event with an entity alias. So his aonerror
became x="""onerror
.
So clever! And as discussed in a lot of previous episodes, it’s all about leveraging how different technologies see stuff and tricking them into doing what they want you to do.
Links:
We’re wrapping up for the week.
As always, keep hacking!