You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 24 Next »

An object has a storage duration that determines its lifetime. There are three storage durations: static, automatic, and allocated.

According to [[ISO/IEC 9899-1999]]:

The lifetime of an object is the portion of program execution during which storage is guaranteed to be reserved for it. An object exists, has a constant address, and retains its last-stored value throughout its lifetime. If an object is referred to outside of its lifetime, the behavior is undefined. The value of a pointer becomes indeterminate when the object it points to reaches the end of its lifetime.

Attempting to access an object outside of its lifetime could result in exploitable vulnerabilities.

Non-Compliant Code Example 1

This non-compliant code example declares the variable p as a pointer to a constant char with file scope. The value of str is assigned to p within the dont_do_this() function. However, str has automatic storage duration so the lifetime of str ends when the dont_do_this() function exits.

char const *p;
void dont_do_this() {
    char const str[] = "This will change";
    p = str; /* dangerous */
    /* ... */
}

void innocuous() {
    char const str[] = "Surprise, surprise";
}
/* ... */
dont_do_this();
innocuous();
/* now, it is likely that p is pointing to "Surprise, surprise" */

As a result of this undefined behavior, it is likely that p will refer to the string literal "Surprise, surprise" after the call to the innocuous() function.

Compliant Solution 1

In this compliant solution, the pointer to the constant char p is moved within the this_is_OK() to prevent this variable from being accessed outside of the function.

void this_is_OK() {
    char const str[] = "Everything OK";
    char const *p = str;
    /* ... */
}
/* pointer p is now inaccessible outside the scope of string str */

Non-Compliant Code Example 2

In this example, the function func() incorrectly returns a pointer to a local stack variable.

char *func() {
   char a[10] ;
   /* Operate on a */
   return &a[0];
}

Compiling with appropriate warning levels should generate a warning when a local stack variable is returned from a function.

Compliant Solution 2

Correcting this example depends on the intent of the programmer. If the intent is to modify the value of a and have that modification persist outside of the scope of func(), then the desired behavior can be achieved by declaring a elsewhere and passing it as a parameter to func().

void func(char a[]) {
   /* Operate on a */
   return;
}

Risk Assessment

Referencing an object outside of its lifetime could result in an attacker being able to run arbitrary code.

Rule

Severity

Likelihood

Remediation Cost

Priority

Level

DCL30-C

3 (high)

2 (probable)

1 (high)

P6

L2

Related Vulnerabilities

Search for vulnerabilities resulting from the violation of this rule on the CERT website.

Automated Detection

The Coverity Prevent RETURN_LOCAL checker finds many instances where a function will return a pointer to a local stack variable.

References

[[ISO/IEC 9899-1999]] Section 6.2.4, "Storage durations of objects," and Section 7.20.3, "Memory management functions"

  • No labels