Lack of space for ROP
Stack Pivoting is a technique we use when we lack space on the stack - for example, we have 16 bytes past RIP. In this scenario, we're not able to complete a full ROP chain.
During Stack Pivoting, we take control of the RSP register and "fake" the location of the stack. There are a few ways to do this.
Possibly the simplest, but also the least likely to exist. If there is one of these, you're quite lucky.
If you can find a
pop <reg>gadget, you can then use this
xchggadget to swap the values with the ones in RSP. Requires about 16 bytes of stack space after the saved return pointer:
pop <reg> <=== return pointer
xchg <rag>, rsp
This is a very interesting way of stack pivoting, and it only requires 8 bytes.
Every function (except
main) is ended with a
leaveis equivalent to
mov rsp, rbp
Note that the function ending therefore looks like
mov rsp, rbp
That means that when we overwrite RIP the 8 bytes before that overwrite RBP (you may have noticed this before). So, cool - we can overwrite
leave. How does that help us?
Well if we look at
leaveagain, we noticed the value in RBP gets moved to RSP! So if we call overwrite RBP then overwrite RIP with the address of
leave; retagain, the value in RBP gets moved to RSP. And, even better, we don't need any more stack space than just overwriting RIP, making it very compressed.