Resources

People often ask me "How did you learn how to hack?" The answer: by reading. This page is a collection of the blog posts and other articles that I have accumulated over the years of my journey. Enjoy!

RCE via LDAP truncation on hg.mozilla.org- 1317

joernchen     Reference →Posted 2 Years Ago
  • The author got code access from a friend to some of the Mozilla infrastructure. They use SCM for version control, which is where the bug is at.
  • pash appears to be a small shell that was used for handling SCM operations for hg.mozilla.org. One function allows users to clone private repos of a given user.
  • The user controls some input being read via SSH. In particular, the user is completely user controlled. When checking to see if the user exists via ldap, the author thought they had LDAP injection at first. However, characters necessary for this were being filtered out. So, what can we do?
  • When doing the processing, the filtration can be bypassed by injecting in nullbytes. The interpretation of the nullbyte will stop the processing within the filtering calls. It should be noted that the nullbyte is encoded and escaped for the LDAP syntax. However, when being used in the LDAP query, it's interpreted like normal. What does this mean?
  • The filtering of the bad characters in the LDAP query can be bypassed to get LDAP injection. With the LDAP injection, we can trick the query to return true with our user but contain other malicious information. In particular, command injection can be done within the rest of this script, which assumed that no user could have malicious characters.
  • To me, the filtering on the command should have been done no matter. You can't rely on valid users, as issues like this one may occur. I asked the author how they thought of this issue. The author said he was reading LDAP specifications, saw you can encode arbitrary bytes then just tried it on their local environment. To me, the takeaway is just trying lots of things and seeing the results of this with a good test env.

What is HTML Over the Wire? A brief history of web app tech.- 1316

bountyplz    Reference →Posted 2 Years Ago
  • Back in the day, websites were truly static, with only HTML and CSS being returned. Over time, responsive web design became a thing with AJAX/XHR requests being made in the background to get the information for the page. The Single Page Application (SPA) is extremely common to see now-a-days and that uses this pattern.
  • SPAs are snappy and react quickly. However, collecting data from the server takes time after all of the parsing things to be done. The frameworks for this are quite heavy as well. So, something new has gained popularity: HTML Over the Wire (FROW).
  • FROW is an architecture that attempts to combine to pre-rendering of HTML and the quickness of SPAs. It tries to render the HTML for the initial page on the backend but contains the ability to alter the page in an SPA-style fashion for dynamic portions. Hotwire Turbo, Unpoly, HTMLX and many other libraries take this approach.
  • Clicking links is kind of weird with this architecture. Should it reload the page like an old webpage or act like an SPA? Most of the libraries fire off a fetch() in the background then update the UI without reloading the page. This overwrites the default functionality of just making a GET request.
  • In order to support this, the FROW libraries add custom HTML attributes in order to allow for changing and editing of the fetch() request being made. For instance, you can change the method being used, the headers and more. The functionality is only intercepted from the browser if the origin of the path is the same as an internal meta tag.
  • To top this off, CSRF tokens are added into a header of the request automatically for most of these FROW apps. So, here's the idea: can we trick the application to send a user CSRF tokens on the request by poisoning the allowed domains?
  • On Turbo Drive, the turbo-root is can be set in a meta tag. According to the author, they've seen cases where it's possible for control this location as an attacker. Since the application thinks this is a trusted link, it will send the CSRF token alongside it.
  • On HTMX, the same thing can happen. If the link of the request can be set and the csrf token is supposed to be in the body, then it will blindly send it. Overall, an interesting post on the integration of technology causing weird issues. I'm not sure how exploitable this really is, since many things have to come together though.

SSRF Tricks- 1315

Corben Leo    Reference →Posted 2 Years Ago
  • The author of this Tweet has made over 500K in SSRF bugs. In this thread, they go through their best tricks. The first trick, is using other URL schemes like file:// and many others. This can lead to RCE or arbitrary file reads.
  • If you can't hit internal parts, try using alternative encodings. For instance, octal, hex, binary and others. They recommend the tool IPFuscator for doing this. Different representations of localhost like 127.0.0.1, 0.0.0.0 can make it possible to bypass these.
  • This is probably my favorite trick: if you can't hit the AWS instance 169.254.169.254 then use instance-data to resolve to this IP instead. That's pretty fire and clutch that this works on EC2 instances. On top of this, they mention knowing your technologies. Different techs have different internal endpoints to hit.
  • If you can't supply a full URL, there are still many ways to get SSRF. The @, ?, # and ; all have a sticky history with URL parsing. The SSRF bible is a good resource for thinking outside the box on this. The URL has 9 parts: protocol, user, password, subdomain, domain, top level domain, port, path, query and fragment.
  • Directory traversal can be very powerful with a relative path as well. This could allow hitting unintended endpoints on the application. Justin Gardner has even more tricks.
  • Different layers of URL encoding can cause issues. Justin mentions using 3 layers of URL encoding in an exploit. Another common issue is using a literal . within a regex. Although this seems fine, the . within a regex is actually a single character wildcard.
  • DNS rebinding attacks. If there is a TOCTOU bug then go to a public IP to begin with then a private one after the first check has been done. On the same type of thing, the When TLS Hacks You technique works good as well.

Achieving Remote Code Execution in Steam: a journey into the Remote Play protocol- 1314

Thalium    Reference →Posted 2 Years Ago
  • Steam remote play is a peer-to-peer system for playing video. The author of this video reverse engineered the protocol to understand how it worked, build a fuzzer and find fun vulnerabilities in it.
  • The remote play protocol was mostly using protobufs. Luckily for the author, many of this information was kept in a Github repo. There are various ways to perform networking, from webRTC to UDP but the author choose to use UDP because of its simplicity. For more details on how the protocol works, with headers, authentication, channels and things, read the post.
  • To interact with the project, the author built their own client and server implementation. An initial issue they ran into was that the session info for the session would have already been derived. They used a x32dbg script to automatically inject the key into the running process then use it on their client. Another issue they had was forcing the client to use the UDP connections. By changing advertising parameters to ONLY include this, the server would always choose UDP.
  • With a client and fuzzer built, the author setup a fuzzer. Since this uses protobuf, the fuzzer had to be grammer aware, which they created their own engine for. For strings, they added in weird things like paths, URLs, XML and more. For integers, they added in interesting sizes like powers of 2, negative numbers and more. They even randomly dropped random optional fields.
  • Some of the connection types were stateless while others were stateful. Because of this, they built a replay system and logging system to see what was going on. Additionally, a scenario system to test various stateful actions to interact with the system or reproduce bugs. One issue I've had with stateful fuzzing in the past is reproducing issues. It would require saving all previous inputs in order to be confident that we had the information to reproduce the issues.
  • With all of this built, they found a bunch of vulns! With fuzzing, crashes are nice and expected. However, looking for side effects is equally important for finding bugs; not all bugs are binary issues that lead to a crash. The first bug was a simple directory traversal, found by the fuzzer, that could be used to overwrite a Steam DLL to get code execution.
  • From there, they found a ton of format string issues but without %n available. Crazily enough, these were in parts of the system, like logging, that made it possible to use this as a leak. So, an attacker could steal arbitrary data from the heap and/or break ASLR on the system.
  • When calling CRemotePlayTogetherGroupUpdateMsg, there was an SSRF issue if JSON was not returned. By specifying a URL with a GET request, arbitrary data on the network could be leaked. Besides this, a few OOB reads and writes were found in player structs, audio encoding. One of the leaks allowed them to remotely read all heap data from the process, which is super cool.
  • Good read! The bugs are fun but the setup of the fuzzer and thought put into making the system testable was the most valuable thing to me. The SSRF issue which only leaked data if the data wasn't JSON was a good instance of fuzzing for bugs without memory corruption being the only goal. This requires you to be more active but will pay off in complicated systems like this one.

Levana Exploit Postmortem- 1313

Levana    Reference →Posted 2 Years Ago
  • Osmosis is a very popular blockchain in the Cosmos ecosystem. Levana in a perpetual swap built on Cosmos (CosmWasm?). On December 26th, a large chain congestion occurred via a bad set of configurations. This timing was enough for a hacker to profit though.
  • Levana uses the Pyth oracle to keep prices and things up to date. Usually, this occur on a per block basis but some leeway is allowed depending on the previous price. The market contract allow for a 120 second lag. If the market was highly volatile, this is plenty of attack to exploit the difference in price.
  • This difference in price comes down to a price delta attack. In this, the attacker waits for the difference between the actual price and the marked price to be large enough that an attacker could profit solely from the trade. If the price is up, open a long. If it's short, then a low. Once the update goes through from Pyth, sell to get the profit with no risk.
  • The system had many mitigations in place to prevent hits. First, the updates being so spread apart is just unlikely; normal trading would update the price. Second, there were maintainers with bots who were pushing these updates regularly from Pyth info.
  • Now, the delta attack is simply a limitation of the design. However, the circumstances of the market are what led to this being viable. In particular, Osmosis was experiencing large congestions from insufficient fee errors. This came from the newly added fee mark mechanism. Apparently, at the same time, a DDoS attack was occurring on the Levana platform as well.
  • During this timeframe, the authors launched a bot that was always updating the chain prices. Even with the bot and high gas prices, it was still not high enough to push it through. They also paused all markets. How do we actively mitigate this though?
  • The team assumed that that they could land all on-chain price updates, which ended up not being the case in the high congestion times. So, they've decided to decouple these where there will be placing and execution in separate calls. By doing this, the Python update MUST occur within a given timeframe, or the call will timeout. This prevents the exploit above.
  • Developers make assumptions about how a system runs. In these difficult times, it's important to think of worst case scenarios and extreme edge cases to ensure that the product is completely unhackable. Good read!

msg.data Hashing is bad- 1312

ddimtrov22    Reference →Posted 2 Years Ago
  • In Solidity, msg.data is the incoming data in the request as defined by the ABI. Using a hash of this for some cryptographic operation is a real bad idea. But why?
  • The original issue with this existed in the V1 ABI encoder. When encoding information, all data bytes are 32 bytes when sent in the unpacked format. However, some of the bits may be dropped with datatypes, such as uint8s first 31 bytes.
  • Since the truncation occurs with unused bytes, it does not affect any of the actual values but changes the hash. According to Solidity Github issue this only works on the V1 ABI encoder and not the V2 version, which is the default in Solidity 8.0.0+.
  • Regardless of this, there are other ways to abuse this. For instance, you can append arbitrary data to the end of the msg.data that will simply be ignored to change the hash. Additionally, some things, like dynamic data types, have infinite ways they can be encoded.
  • Overall, interesting Solidity quirk that many people may not consider. Thanks for calling this out.

IBC Rate Limits: Introduction and State of the Art (1/3)- 1311

Andres Monty    Reference →Posted 2 Years Ago
  • Bridges are an important piece of the blockchain ecosystem. Being able to move assets from one chain to another is a necessary requirement in the modern web3 space. However, doing bridges securely is difficult to do. In Cosmos, interblockchain communication (IBC) allows for Cosmos blockchains to talk together in a standardized format. In this article, the authors discuss bridge security and how to make IBC more secure.
  • Most security is put into the pre deployment of applications, such as pentests, code review and more. However, equal importance needs to be on the post-deployment protections. The authors mention four different mechanisms for on-chain post-deployment: circuit breakers, rate limits, settlement delayers and redundancy.
  • Circuit breakers simply pause a system when certain conditions occur or manually. This acts as a kill switch to be able to stop functionality when something bad is happening. The Cosmos SDK circuit module is a good example of this but it must be manually done and it's per message.
  • Rate limits disable functionality once a threshold has been passed. This can be a value rate limit such as a dollar amount or a volume rate limit. The second one is similar to API rate limits. This helps to limit the damage of attacks but doesn't prevent them entirely.
  • Delayers impose a delay window between certain transactions. This allows for incident response a time window to revert things if they are malicious. For instance, a 1hr delay may be imposed on a transaction of $1M or more. This is common on governance proposals but can be used in other places as well.
  • Bridge Redundancy Protocols are a consist relay of message over several bridge protocols. If one is effected by a bug, that doesn't matter! To me, having diversity in software is good, like how JumpCrypto is making an alternative validator for Solana.
  • The focus of the article was how the Osmosis blockchain implemented rate limiting on IBC. They have a rate limit on the amount of token assets that can be moved into the ecosystem. This is done with by static periods and net flow of assets moving. This rate limiting is implemented in a CosmWasm smart contract that interacts with the IBC middleware package as a wrapper around ICS20.
  • To be more specific on the Cosmos side, the rate limits are implemented on a given channel and denom. This allows for a standard transfer to occur between two blockchains, without interfering with others. These rate limits measure the inflow and outflow of tokens on a given channel. These are setup in different intervals but appear to be configurable.
  • There are other examples of rate limiting. On the Stride Cosmos SDK blockchain, they do IBC rate limiting based upon the amount of tokens transferred on a channel for a 24 hour window. The Wormhole governor, after a large hack in 2022, implemented functionality as well. They have two types of transactions: small and large. A large transaction has a finality delay of 24 hours while both transaction types of a daily quoted of funds that can be sent.
  • Overall, good post on different on chain protections can be done to reduce the risk.

Sonos Era 100 Secure Boot Bypass Through Unchecked setenv() call- 1310

Alex Plaskett - NCC Group    Reference →Posted 2 Years Ago
  • The Sonos Era 100 speakers uses UBoot for the basic boot process. UBoot is a common microcontroller boot framework that has a lot of existing functionality but can be crafted for whatever you need. The Sonos team created a custom sonosboot command that loads the kernel image, does the signature check then passes execution over to the bootm command.
  • bootm command uses environment variables from UBoot for various configurations. In order to ensure that only trusted parameters are used, the implementation calls setenv(). However, the error message is NOT checked for this call. Can we abuse this?
  • By interacting with the UBoot console or modifying the eMMC memory directly, we can control these variables. Normally, these would be overwritten. UBoot allows for the setting of environment variables as read only though. This can be done with bootargs=something then setting the flags with .flags=bootargs:sr. Now, going forward, any future writes to bootargs will fail.
  • Now, as an attacker, we can set any of the ENV variables we want then make them read only to ensure that the setenv() call fails. The authors set the initrd variable to control the initramfs image that was loaded, hijacking the boot process.
  • I really enjoy vulnerabilities that result in things failing in weird ways like this. Not handling errors can have devastating consequences even when it seems impossible that something would fail. Good article!

Cookie Bugs - Smuggling & Injection- 1309

Ankur Sundara    Reference →Posted 2 Years Ago
  • Cookies are a core part of browser mechanics. Understanding how they work is important when escalating existing issues. In this article, the author dives into quirks of various frameworks and browsers on cookies.
  • First, when are cookies sent? This depends on the domain attribute of a cookie. If the domain is set for example.com, then all subdomains will send this as well. If the cookie is set from a subdomain onto the parent, it will be sent with the parent as well. It's interesting that this is allowed to be set.
  • Cookies are ordered on Chrome and Firefox by first the path length then the last updated time. So, if you have a vulnerability that allows you to set a cookie, you can get yours parsed first by setting it with a longer path.
  • Browsers allow for cookies with an empty name. For instance, =test value; is a valid cookie that can be set. When rendered, this will break the parsing of the cookies by most web servers. So, we can set arbitrary cookies that are not secure or host cookies.
  • A new attack vector presented in this post is cookie smuggling. The idea is to break the parsing of cookies when you have control over some of them. If you can add a double quote (") to a cookie, then some items will follow the RFC2616 standard while others will follow RFC2965. Why does this matter? The double quote changes the meaning of the cookies being parsed. Using this HTTPOnly cookies could be smuggled or some cookies could be outright set.
  • Going deeper into the parsing issues, we need to ensure that everything parses cookies the same. In Java Undertow, they found that that parsing for a cookie begins right after a double quote. So, if we have a cookie with double quotes, it will then parse the rest of the data as our cookie, smuggling in our cookie!
  • Python stdlib http.cookie.SimpleCookie and http.cookie.BaseCookie suffer from a same issue. If a space is found in the cookie, then it will start parsing this as a new cookie, using it as a delimiter. Since the Python library has this issue, all frameworks using it are vulnerable as well. Cookie injection is bad where cookie based CSRF protections are used, spoofing secure or host cookies and authorization bypasses where things check for specific cookies.
  • Although they contacted many of the projects, only Jetty actually responded. So, many of these issues will exist going forwards! Overall, good article on cookie quirks that I had no idea about!

IppSec Search Engine- 1308

IppSec    Reference →Posted 2 Years Ago
  • IppSec is a YouTuber with great hacking videos. This is a search engine for timestamps in their videos. So, if you need a video example of a bug class, this is a great resource.