OpenVPN's memory management strategies

This section describes several implementation details relating to OpenVPN's memory management strategies.

During operation, the OpenVPN process performs all kinds of operations on blocks of data. Receiving packets, encrypting content, prepending headers, etc. To make the programmer's job easier and to decrease the likelihood of memory-related bugs, OpenVPN uses its own memory buffer library and garbage collection facilities. These are described in brief here.

The buffer structure

The buffer structure is a wrapper around a block of dynamically allocated memory which keeps track of the block's capacity buffer.capacity and location in memory This structure supports efficient prepending and appending within the allocated memory through the use of offset buffer.offset and length buffer.len fields. See the buffer documentation for more details on the structure itself.

OpenVPN's buffer library, implemented in the buffer.h and buffer.c files, contains many utility functions for working with buffer structures. These functions facilitate common operations, such as allocating, freeing, reading and writing to buffer structures, and even offer several more advanced operations, such as string matching and creating sub-buffers.

Not only do these utility functions make working with buffer structures easy, they also perform extensive error checking. Each function, where necessary, checks whether enough space is available before performing its actions. This minimizes the chance of bugs leading to buffer overflows and other vulnerabilities.

The frame structure

The frame structure keeps track of the maximum allowed packet geometries of a network connection.

It is used, for example, to determine the size of buffer structures in which to store data channel packets. This is done by having each data channel processing module register the maximum amount of extra space it will need for header prepending and content expansion in the frame structure. Once these parameters are known, buffer structures can be allocated, based on the frame parameters, so that they are large enough to allow efficient prepending of headers and processing of content.

Garbage collection

OpenVPN has many sizable functions which perform various actions depending on their context. This makes it difficult to know in advance exactly how much memory must be allocated. The garbage collection facilities are used to keep track of dynamic allocations, thereby allowing easy collective freeing of the allocated memory.

The garbage collection system is implemented by the gc_arena and gc_entry structures. The arena represents a garbage collecting unit, and contains a linked list of entries. Each entry represents one block of dynamically allocated memory.

The garbage collection system also contains various utility functions for working with the garbage collection structures. These include functions for initializing new arenas, allocating memory of a given size and registering the allocation in an arena, and freeing all the allocated memory associated with an arena.