Go to main content
Oracle® Developer Studio 12.6: Debugging a Program with dbx

Exit Print View

Updated: June 2017
 
 

Using Access Checking

Access checking checks whether your program accesses memory correctly by monitoring each read, write, allocate, and free operation.

Programs might incorrectly read or write memory in a variety of ways, which are called memory access errors. For example, the program might reference a block of memory that has been deallocated through a free()call for a heap block. Or a function might return a pointer to a local variable and when that pointer is accessed, an error would result. Access errors might result in wild pointers in the program and can cause incorrect program behavior, including wrong outputs and segmentation violations. Some kinds of memory access errors can be very hard to find.

Runtime checking maintains a table that tracks the state of each block of memory being used by the program. Runtime checking checks each memory operation against the state of the block of memory it involves and then determines whether the operation is valid. The possible memory states are:

  • Unallocated, initial state. Memory has not been allocated. It is illegal to read, write, or free this memory because it is not owned by the program.

  • Allocated, but uninitialized. Memory has been allocated to the program but not initialized. It is legal to write to or free this memory, but is illegal to read it because it is uninitialized. For example, upon entering a function, stack memory for local variables is allocated, but uninitialized.

  • Read-only. It is legal to read, but not write or free, read-only memory.

  • Allocated and initialized. It is legal to read, write, or free allocated and initialized memory.

Using runtime checking to find memory access errors is not unlike using a compiler to find syntax errors in your program. In both cases, a list of errors is produced, with each error message giving the cause of the error and the location in the program where the error occurred. In both cases, you should fix the errors in your program starting at the top of the error list and working your way down. One error can cause other errors in a chain reaction. The first error in the chain is, therefore, the “first cause” and fixing that error might also fix some subsequent errors.

For example, a read from an uninitialized section of memory can create an incorrect pointer, which when dereferenced can cause another invalid read or write, which can in turn lead to yet another error.

Understanding the Memory Access Error Report

Runtime checking provides the following information for memory access errors:

type

Type of error.

access

Type of access attempted (read or write).

size

Size of attempted access.

address

Address of attempted access.

size

Size of leaked block.

detail

More detailed information about address. For example, if the address is in the vicinity of the stack, then its position relative to the current stack pointer is given. If the address is in the heap, then the address, size, and relative position of the nearest heap block is given.

stack

Call stack at time of error (with batch mode).

allocation

If the address is in the heap, then the allocation trace of the nearest heap block is given.

location

Where the error occurred. If line number information is available, this information includes line number and function. If line numbers are not available, runtime checking provides function and address.

The following example shows a typical access error.

Read from uninitialized (rui):
Attempting to read 4 bytes at address 0xefffee50
    which is 96 bytes above the current stack pointer
Variable is ”j’
Current function is rui
   12           i = j;

Memory Access Errors

If debuggee is discover-instrumented, RTC reports the following errors:

UAR

Reading from unallocated memory

UAW

Writing to unallocated memory

OLP

Overlapping source and destination

AZS

Allocating zero size memory block (warning)

NAR

Non-annotated read (warning)

NAW

Non-annotated write (warning)

FMR

Reading from freed memory

FMW

Writing to freed memory

UMR

Accessing uninitialized data

PIR

Accessing partially initialized data

ABR

Reading memory beyond array bounds

ABW

Writing to memory beyond array bounds

DFM

Double free memory

BFM

Freeing wrong memory block

BRP

Bad address parameter for realloc

SBR

Read is beyond current stack bounds

SBW

Write is beyond current stack bounds

IMR

Read from invalid memory address

IMW

Write to invalid memory address

FRP

Freed pointer passed to realloc

CGB

Corrupted guard block