Safeguard
Application Security•

CWE-788 Access of Memory Location After End of Buffer

Reads and writes past the end of a buffer are the classic overflow. See how CWE-788 shows up in C and C++ and the checks that prevent it.

Safeguard Security Team
3 min read

CWE-788 is the general form of the buffer overflow and over-read: the program uses an index or pointer that refers to memory after the end of the buffer. It applies to C and C++ and other memory-unsafe code.

How it happens

MITRE says it typically occurs when a pointer or index is incremented past the buffer, or when pointer arithmetic lands beyond it.

The record lists several classic cases:

  • CVE-2009-2550: a stack-based buffer overflow in a media player, triggered by a long entry in a playlist.
  • CVE-2009-2403: a heap-based overflow in a media player, again from a long playlist entry.
  • CVE-2009-0689: a large precision value in a format string triggered an overflow.

A short example:

char name[16];
for (int i = 0; input[i] != '\0'; i++)
    name[i] = input[i];       /* no limit, input may exceed 16 */

Reads work the same way. A loop that scans for a delimiter and never finds one keeps reading until it leaves the buffer.

What an attacker gains

The record lists three effects. A read past the end may expose sensitive information. Out-of-bounds access can corrupt memory and crash the program. And if the attacker controls the memory involved, arbitrary code execution may be possible.

How to find it

MITRE lists fuzzing, static analysis and compile-time runtime checks as detection methods. In practice:

  • Fuzz every input parser, with long values and missing terminators.
  • Build with AddressSanitizer for test runs.
  • Review loops over buffers for an explicit end bound.
  • Keep dependencies current. Media and parsing libraries have a long record of this weakness, and the free dependency scan can show which of yours have known flaws.

How to fix it

char name[16];
size_t i;
for (i = 0; i + 1 < sizeof(name) && input[i] != '\0'; i++)
    name[i] = input[i];
name[i] = '\0';
  • Carry the length with the buffer and check it at every access.
  • Use bounded functions with correct sizes, and verify termination.
  • Prefer safer containers and string types.
  • Use compiler hardening as a second layer, not the fix.
  • For new code that parses untrusted data, choose a memory-safe language where you can.

Quick check

What does a read past the end of a buffer risk?

Disclosure of whatever sensitive data sits next to the buffer in memory, and sometimes a crash.

Sources

Never miss an update

Weekly insights on software supply chain security, delivered to your inbox.

Self-healing security runs on Safeguard.

Your first fix PR is minutes away.

No sales call required, even your agent can complete the purchase over MCP.