The most effective way to prevent memory problems is to be disciplined in writing memory management code. The development team should adopt a standard approach and apply it consistently.
Dynamic memory management
C, UNIX, Win32
Attacker executes arbitrary code on machine with permissions of compromised process or changes the behavior of the program.
Standard C dynamic memory management functions such as malloc(), calloc(), realloc(), and free() [ISO/IEC 99] are prone to programmer mistakes that can lead to vulnerabilities resulting from buffer overflow in the heap, writing to already freed memory, and freeing the same memory multiple times (e.g., double-free vulnerabilities).
The most effective way to prevent memory problems is to be disciplined in writing memory management code. The development team should adopt a standard approach and apply it consistently. Some good practices include the following:
Use the same pattern for allocating and freeing memory. In C++, perform all memory allocation in constructors and all memory deallocation in destructors. In C, define create() and destroy() functions that perform an equivalent function.
Allocate and free memory in the same module, at the same level of abstraction. Freeing memory in subroutines leads to confusion about if, when, and where memory is freed.
Match allocations and deallocations. If there are multiple constructors, make sure the destructors can handle all possibilities.
Steadfast consistency is often the best way to avoid memory errors. MIT krb5 Security Advisory 2004-002 provides a good example of how inconsistent memory management practices can lead to software vulnerabilities.
In the MIT krb5 library, in all releases up to and including krb5-1.3.4, ASN.1 decoder functions and their callers do not use a consistent set of memory management conventions. The callers expect the decoders to allocate memory. The callers typically have error-handling code that frees memory allocated by the ASN.1 decoders if pointers to the allocated memory are non-null. Upon encountering error conditions, the ASN.1 decoders themselves free memory that they have allocated but do not null the corresponding pointers. When some library functions receive errors from the ASN.1 decoders, they attempt to pass the non-null pointer (which points to freed memory) to free(), causing a double-free.
This example also shows the value of setting dangling pointers to NULL.
ISO/IEC. ISO/IEC 9899 Second edition 1999-12-01 Programming languages — C. International Organization for Standardization, 1999.
This material is excerpted from Secure Coding in C and C++, by Robert C. Seacord, copyright © 2006 by Pearson Education, Inc., published as a CERT® book in the SEI Series in Software Engineering. All rights reserved. It is reprinted with permission and may not be further reproduced or distributed without the prior written consent of Pearson Education, Inc.