...
- otherwise, if E is an integer identifier, then T is the derived type of the expression last used to store a value in E;
...
- otherwise, the derived type is an unspecified character type compatible with any of char, signed char, and unsigned char.
...
_ _Example:
Effective size of a pointer is the size of the object to which it points.
...
Effective type of an object is defined as either its declared type or (in case its type hasn't been declared) the effective type of the value assigned to it. In the examples below, we have used terms like 'effective type of pointer p' which implies that if the type of 'p' has been declared (eg: char *p) then that type (in this case char) is the effective type of the pointer. If the type is not declared (eg: void *p) and then the pointer is assigned a value (p = obj), then
Example: char *p
The effective type of pointer p in this case is char.
Example: void *p
p = obj
In this case, pointer p's type is not declared but it is later assigned 'obj'. So the effective type of 'p' is equal to the effective type of 'obj'.
...
In the noncompliant code example below, the effective type of *p is float while the derived type of the expression 'n' is int. This has been calculated using the first rule from the definition of derived types in the definitions section above. Since 'n' here is a sizeof expression, its derived type is equal to the type of the operand, which is int.
Code Block | ||
---|---|---|
| ||
void f2() { const size_t ARR_SIZE = 4; float a[ARR_SIZE]; const size_t n= sizeof(int) * ARR_SIZE; void *p = a; memset(p, 0, n); /* More program code */ } |
...
In this compliant solution, the derived type of 'n' is also float (since it is a sizeof expression and therefore the derived is equal to the type of the operand, which is float; see derived type above).
Code Block | ||
---|---|---|
| ||
void f2() { const size_t ARR_SIZE = 4; float a[ARR_SIZE]; const size_t n = sizeof(float) * ARR_SIZE; void *p = a; memset(p, 0, n); /* More program code */ } |
...
In this noncompliant code example, the value of 'n' is greater than the size of 'T' i.e. sizeof (wchar_t). But, the derived type of expression 'n' (wchar_t *) is not same as the type of 'T' because its derived type (from the definition above; see derived type) will be equal to the type of 'p', which is wchar_t *. The derived type of 'n' has been calculated using the first rule from the definition of derived types in the definitions section above. Since 'n' here is a sizeof expression, its derived type is equal to the type of the operand (p), which is wchar_t *.
Code Block | ||
---|---|---|
| ||
wchar_t *f7() { const wchar_t *p = L"Hello, World!"; const size_t n = sizeof(p) * (wcslen(p) + 1); wchar_t *q = (wchar_t *)malloc(n); return q; } |
...
This compliant solution makes sure that the derived type of 'n' (wchar_t) is same as the type of 'T' (wchar_t). Also, the value of 'n' is not less than the size of 'T'.
Code Block | ||
---|---|---|
| ||
wchar_t *f7() { const wchar_t *p = L"Hello, World!"; const size_t n = sizeof(wchar_t) * (wcslen(p) + 1); wchar_t *q = (wchar_t *)malloc(n); return q; } |
...