Don't like this style? Click here to change it! blue.css

Welcome .... Click here to logout

Thinking in ROP

So the conversation in the last class got me thinking about the wide-open nature of hacking in a ROP context. That context is:

Context of ROP:

In class I used the analogy of learning to make meals given a supermarket. You now have a TON of freedom compared to having parents prepare your meals.

I was asked the question, what are the basics of ROP. The truth is that the basics are maybe too abstract to help, but here goes an attempt:

Universal Basics of ROP

That's maybe not that helpful to a young practitioner.

In my feeding yourself analogy that's like saying, all meals involve eating food.

You need to know how to make a meal for yourself, and the truth is there are a LOT of ways to do that. We have whole cooking networks and reality shows and recipe books and subcultures of etiquitte. None of which are prerequisites to you eating.

So now the question is, how do I guide you through some interesting ways to use this skill?

Typical Requirements for a ROP Shell

Let's tackle these one at a time

Address Randomization

We know that there are essentially 3 (soon to be 4) valuable memory segments that are randomized every time a program executes:

Our analogy for these has been a fleet of battleship pieces. If you can identify any address in any of the ships you can do some simple addition/subtraction to find anything else in that segment.

Things in each of the key segments:


This segment can be unrandomized by the -no-pie flag.

This segment contains:


The stack sets up a "stack frame" for each function called which has room for:

These frames are setup recursively so they can make a clean frame in the middle of a function call and restore the previous stack frame after a ret.

We've talked endlessly about it, but worth noting: there are always interesting little treasures (e.g. identifyable addresses from one of these key segments) to be found on the stack, so if you can scan the stack then that's good.

GLIBC segments

Inside of the glibc segments are almost anything you could ever want. I call them multiple segments because there is so much stuff that it's typically 4+ segments in a row some with R-X and some with RW-

Here are some key targets in glibc:

Possible Strategies for Randomization

OK so one of the things we need to assess is UNDER WHAT CONDITIONS can you undo randomization?

When we get to the heap we'll show more sophisticated ways to generate leaks that don't feel as toy-like.

Loading "/bin/sh" into system

So if you're in the wilderness you need to find a copy of "/bin/sh" somewhere

You can either write it to an address you can predict or find it in the binary or leak a glibc address.

But even given the address where "/bin/sh" lives how do you get it INTO the call of system?

Advanced Strategies

I'd like to highlight my auto-pwn ROP chain presuming NO PIE and partial RELRO.

This is a sophisticated ROP chain that is doing the following:

Here's the 64-bit version:

Here's the 32-bit version of the same concept:

Picking interesting targets

So my favorite recipe is system("/bin/sh") so I'm hunting for any method I can to do that.

But sometimes the challenge forces you to do unusual tricks so this section might be "alternatives" to the standard system("/bin/sh") strat.

With the supermarket strategy this section is sort of a world cuisine tour, there are MANY WAYS to win and you can expand your horizons with more practice, CTFing, experimenting with new methods.

You don't have to master them all, but the more you know the better you get.