...
In this noncompliant example, a diagnostic is required because an object of type float is incremented through a pointer to int, ip.:
| Code Block | ||||
|---|---|---|---|---|
| ||||
void f(void) {
if (sizeof(int) == sizeof(float)) {
float f = 0.0f;
int *ip = (int *)&f;
printf("float is %f\n", f);
(*ip)++; // diagnostic required
printf("float is %f\n", f);
}
}
|
...
In this compliant solution, the pointer to int, ip has been replaced by a pointer to float, fp.:
| Code Block | ||||
|---|---|---|---|---|
| ||||
void f(void) {
if (sizeof(int) == sizeof(float)) {
float f = 0.0f;
float *fp = &f;
printf("float is %f\n", f);
(*fp)++;
printf("float is %f\n", f);
}
}
|
...
The programmer in this noncompliant code example is attempting to read from a different union member than the one most recently written to; this is known as type-punning.:
| Code Block | ||||
|---|---|---|---|---|
| ||||
union a_union {
int i;
double d;
};
int f() {
a_union t;
int *ip;
t.d = 3.0;
ip = &t.i;
return *ip;
}
|
...
In this noncompliant code example, access by taking the address, casting the resulting pointer, and dereferencing the result has undefined behavior, even if the cast uses a union type.:
| Code Block | ||||
|---|---|---|---|---|
| ||||
union a_union {
int i;
double d;
};
int f() {
double d = 3.0;
return ((union a_union *) &d)->i;
}
|
...
Type-punning is allowed provided the memory is accessed through the union type. This compliant solution returns the expected value.:
| Code Block | ||||
|---|---|---|---|---|
| ||||
union a_union {
int i;
double d;
};
int f() {
a_union t;
t.d = 3.0;
return t.i;
}
|
...
This compliant solution uses a union type that includes a type compatible with the effective type of the object.:
| Code Block | ||||
|---|---|---|---|---|
| ||||
union {
short a[2];
int i;
} u;
u.a[0]=0x1111;
u.a[1]=0x1111;
u.i = 0x22222222;
printf("%x %x\n", u.a[0], u.a[1]);
|
...
Tool | Version | Checker | Description | ||||||
|---|---|---|---|---|---|---|---|---|---|
| PRQA QA-C |
| 0310 | Partially implemented |
Related Guidelines
| ISO/IEC TS 17961 (Draft) | Accessing an object through a pointer to an incompatible type [ptrcomp] |
Bibliography
| [Acton 2006] | "Understanding Strict Aliasing" |
| GCC Known Bugs | "C Bugs, Aliasing Issues while Casting to Incompatible Types" |
| GCC Manual | |
| [ISO/IEC 9899:2011] | Section 6.5, "Expressions" |
| [Walfridsson 2003] | Aliasing, Pointer Casts and GCC 3.3 |
...