Table of Contents
Fetching ...

How to Secure Existing C and C++ Software without Memory Safety

Úlfar Erlingsson

TL;DR

The paper addresses the persistent risk of memory-corruption in C/C++ programs by proposing a pragmatic, scalable defense that does not require memory safety. It advocates combining four existing mechanisms—stack integrity, control-flow integrity, heap data integrity, and pointer integrity/unforgeability—to dramatically reduce remote code execution without rewriting software in memory-safe languages. Each mechanism is positioned as already deployable in current toolchains and hardware, with Apple’s long-running deployment serving as evidence of real-world benefit. The work argues that, through integration into development lifecycles and standards, these defenses can deliver substantial security improvements at scale in unmodified C/C++ software, while acknowledging potential gaps and the need for ongoing refinement. This approach offers a practical pathway to greatly strengthen software security in the near term while broader memory-safety transitions continue over longer timescales.

Abstract

The most important security benefit of software memory safety is easy to state: for C and C++ software, attackers can exploit most bugs and vulnerabilities to gain full, unfettered control of software behavior, whereas this is not true for most bugs in memory-safe software. Fortunately, this security benefit -- most bugs don't give attackers full control -- can be had for unmodified C/C++ software, without per-application effort. This doesn't require trying to establish memory safety; instead, it is sufficient to eliminate most of the combinatorial ways in which software with corrupted memory can execute. To eliminate these interleavings, there already exist practical compiler and runtime mechanisms that incur little overhead and need no special hardware or platform support. Each of the mechanisms described here is already in production use, at scale, on one or more platforms. By supporting their combined use in development toolchains, the security of all C and C++ software against remote code execution attacks can be rapidly, and dramatically, improved.

How to Secure Existing C and C++ Software without Memory Safety

TL;DR

The paper addresses the persistent risk of memory-corruption in C/C++ programs by proposing a pragmatic, scalable defense that does not require memory safety. It advocates combining four existing mechanisms—stack integrity, control-flow integrity, heap data integrity, and pointer integrity/unforgeability—to dramatically reduce remote code execution without rewriting software in memory-safe languages. Each mechanism is positioned as already deployable in current toolchains and hardware, with Apple’s long-running deployment serving as evidence of real-world benefit. The work argues that, through integration into development lifecycles and standards, these defenses can deliver substantial security improvements at scale in unmodified C/C++ software, while acknowledging potential gaps and the need for ongoing refinement. This approach offers a practical pathway to greatly strengthen software security in the near term while broader memory-safety transitions continue over longer timescales.

Abstract

The most important security benefit of software memory safety is easy to state: for C and C++ software, attackers can exploit most bugs and vulnerabilities to gain full, unfettered control of software behavior, whereas this is not true for most bugs in memory-safe software. Fortunately, this security benefit -- most bugs don't give attackers full control -- can be had for unmodified C/C++ software, without per-application effort. This doesn't require trying to establish memory safety; instead, it is sufficient to eliminate most of the combinatorial ways in which software with corrupted memory can execute. To eliminate these interleavings, there already exist practical compiler and runtime mechanisms that incur little overhead and need no special hardware or platform support. Each of the mechanisms described here is already in production use, at scale, on one or more platforms. By supporting their combined use in development toolchains, the security of all C and C++ software against remote code execution attacks can be rapidly, and dramatically, improved.

Paper Structure

This paper contains 9 sections.