diff --git a/README.md b/README.md index 3aaa01c..99ecdff 100644 --- a/README.md +++ b/README.md @@ -254,28 +254,6 @@ This indirection is part of what allows programs to work without necessarily knowing where all of their symbols are ahead of time. -#### Partial RELRO -![](memes/boromir_got.png) - -Updating the GOT at runtime means that the memory page containing the -GOT must always be writable. This isn't ideal from a security -perspective. An attacker who can inject a malicious payload into the -program may be able to overwrite values in the GOT, giving them some -control over how the program behaves. To prevent this, GCC introduced an -option called [Relocation Read-only][sidhpurwala] or "RELRO". - -RELRO comes in two flavors: Full and Partial. Partial RELRO tells the -dynamic linker to do the following: - -* Resolve GOT entries for all `extern` variables -* Mark these entries read-only by calling [`mprotect(2)`][mprotect] -* Call the program's `main` function - -Partial RELRO helps protect the integrity of the GOT by marking is -read-only as soon as all legitimate modifications are done. We'll talk -about [Full RELRO](#full-relro) in the next section. - - ### Procedure Linkage Table The Procedure Linking Table (PLT) uses the GOT to help programs to @@ -379,19 +357,26 @@ compiler will create a "stub" function in the Procedure Linkage Table (PLT). -#### Full RELRO -Part of the original purpose of the PLT was to enable *lazy-binding*: -delaying the lookup of dynamic symbols until the first time they're -needed. However, this means that the GOT needs to remain writable until -all symbols have been resolved. If a program does not take all code -paths that use dynamic symbols, its GOT will remain writable the entire -time it is running. -Full RELRO tells the dynamic linker to resolve all symbols before a -program begins executing, and then mark the GOT read-only by calling -[`mprotect(2)`][mprotect]. This prevents the GOT from being modified by -an attacker, but it also makes program startup slower because every -dynamic symbol must be resolved before the `main` function can begin. +### RELRO +![](memes/boromir_got.png) + +Updating the GOT at runtime means that the memory page containing the +GOT must always be writable. This isn't ideal from a security +perspective. An attacker who can inject a malicious payload into the +program may be able to overwrite values in the GOT, giving them some +control over how the program behaves. To prevent this, GCC introduced an +option called [Relocation Read-only][sidhpurwala] or "RELRO". + +RELRO comes in two flavors: Full and Partial. Partial RELRO tells the +dynamic linker to do the following: + +* Resolve GOT entries for all `extern` variables +* Mark these entries read-only by calling [`mprotect(2)`][mprotect] +* Call the program's `main` function + +Full RELRO tells the dynamic linker to resolve *all* symbols before a +program begins executing, even functions. You can check what (if any) degree of RELRO is enabled by running [checksec(1)][checksec]. For example, we can inspect the @@ -406,6 +391,7 @@ Partial RELRO No canary found NX enabled No PIE No RPATH No RU + ## What is GNU IFUNC *supposed* do? It allows you to determine, at runtime, which version of some function you'd like to use. It does this by giving you to an opportunity to run