Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

Comparing a function pointer to a value that is not a null function pointer of the same type shall will be diagnosed because this it typically indicates programmer error and can result in unexpected behavior. Implicit comparisons shall will be diagnosed, as well.

Noncompliant Code Example

In this noncompliant code example, the function pointers addresses of the POSIX functions getuid and geteuid are compared for equality to 0. Because no function address shall be null, the first subexpression will always evaluate to false (0), and the second subexpression always to true (nonzero). Consequently, the entire expression will always evaluate to true, leading to a potential security vulnerability.

Code Block
bgColor#FFcccc
langc

/* First the options that are allowed only allowed for root */ 
if (getuid == 0 || geteuid != 0) { 
  /* ... */ 
} 

Noncompliant Code Example

In this noncompliant code example, the function pointers getuid and geteuid are compared to 0. This noncompliant code example is from an actual vulnerability (VU#837857) discovered in some versions of the X Window System server. The vulnerability exists because the programmer neglected to provide the open and close parentheses following the geteuid() function identifier. As a result, the geteuid token returns the address of the function, which is never equal to zero0. As a resultConsequently, the or condition of this if statement is always true, and access is provided to the protected block for all users. Many compilers issue a warning noting such pointless expressions. Therefore, this coding error is normally detected by adherence to MSC00-C. Compile cleanly at high warning levels.

Code Block
bgColor#FFcccc
langc

/* First the options that are allowed only allowed for root */
if (getuid() == 0 || geteuid != 0) {
  /* ... */
}

Implementation-Specific Details

This error can often be detected through the analysis of compiler warnings. For example, when this code is compiled with some versions of the GCC compiler,

Code Block

#include <unistd.h>
#include <stdlib.h>

int main(void) {
  geteuid ? exit(0) : exit(1);
}

the following warning will be generated:

Code Block

example.c: In function 'main':
example.c:6: warning: the address of 'geteuid', will always
  evaluate as 'true'

Compliant Solution

The solution is to provide the open and close parentheses following the geteuid token so that the function is properly invoked.:

Code Block
bgColor#ccccff
langc

/* First the options that are allowed only allowed for root */
if (getuid() == 0 || geteuid() != 0) {
  /* ... */
}

Compliant

...

Solution

A function pointer can be compared to a null function pointer of the same type.:

Code Block
bgColor#ccccff
langc

/* First the options that are allowed only allowed for root */ 
if (getuid == (uid_t(*)(void))0 || geteuid != (uid_t(*)(void))0) { 
  /* ... */ 
} 

This code should not be diagnosed by an analyzer.

Noncompliant Code Example

In this noncompliant code example, the function pointer do_xyz is implicitly compared unequal to 0. :

Code Block
bgColor#FFcccc
langc

int do_xyz(void); 
 
int f(void) {
/* ... */
  if (do_xyz) { 
    return -1; /* handle errorIndicate failure */ 
  }
/* ... */
  return 0;
} 

Compliant Solution

In this compliant solution, the function do_xyz() is invoked and the return value is compared to 0. :

Code Block
bgColor#ccccff
langc

int do_xyz(void); 
 
int f(void) {
/* ... */ 
  if (do_xyz()) { 
    return -1; /* Indicate failure * handle error/
  }
/* ... */
  return 0;  
} 

Risk Assessment

Errors of omission can result in unintended program flow.

Recommendation

Severity

Likelihood

Remediation Cost

Priority

Level

MSC02

EXP16-C

low

Low

likely

Likely

medium

Medium

P6

L2

Automated Detection

...

Tool

Version

Checker

Description

Astrée
Include Page
Astrée_V
Astrée_V
function-name-constant-comparison
Partially checked

Coverity

Include Page
Coverity_V
Coverity_V

BAD_COMPARE

Can detect the specific instance where the address of a function is compared against 0, such as in the case of geteuid versus getuid() in the

...

implementation-specific details

GCC
Include Page
GCC_V
GCC_V

Can

The LDRA tool suite Version 7.6.0 can detect violations of this recommendation???

...

detect violations of this recommendation when the -Wall flag is used

...

Helix QAC

Include Page
Helix QAC_V
Helix QAC_V

C0428, C3004, C3344
Klocwork
Include Page
Klocwork_V
Klocwork_V

CWARN.NULLCHECK.FUNCNAME
CWARN.FUNCADDR


LDRA tool suite
Include Page
LDRA_V
LDRA_V
99 SPartially implemented
Parasoft C/C++test
Include Page
Parasoft_V
Parasoft_V
CERT_C-EXP16-a
Function address should not be compared to zero
PC-lint Plus

Include Page
PC-lint Plus_V
PC-lint Plus_V

2440, 2441

Partially supported: reports address of function, array, or variable directly or indirectly compared to null

PVS-Studio

Include Page
PVS-Studio_V
PVS-Studio_V

V516, V1058
RuleChecker

Include Page
RuleChecker_V
RuleChecker_V

function-name-constant-comparison
Partially checked

...

Related Vulnerabilities

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

Other Languages

...

Related Guidelines

...

...

...

conversions using void pointers
ISO/IEC TR 24772:2013Likely incorrect expressions [KOA]
ISO/IEC TS 17961Comparing function addresses to zero [funcaddr]
MITRE CWECWE-480, Use of incorrect operator
CWE-482, Comparing instead of assigning

Bibliography

[Hatton 1995]Section 2.7.2, "Errors of Omission and Addition"


...

Image Added Image Added Image Added

References

Wiki Markup\[[Hatton 95|AA. C References#Hatton 95]\] Section 2.7.2, "Errors of omission and addition" \[[ISO/IEC PDTR 24772|AA. C References#ISO/IEC PDTR 24772]\] "KOA Likely Incorrect Expressions" \[[MITRE 07|AA. C References#MITRE 07]\] [CWE ID 482|http://cwe.mitre.org/data/definitions/482.html], "Comparing instead of Assigning," [CWE ID 480|http://cwe.mitre.org/data/definitions/480.html], "Use of Incorrect Operator"