CWE Rule 665
Description
Rule Description
The product does not initialize or incorrectly initializes a resource, which might leave the resource in an unexpected state when it is accessed or used.
Polyspace Implementation
The rule checker checks for these issues:
Call to memset family with unintended value
Improper array initialization
Overlapping assignment
Use of memset with size argument zero
Examples
Call to memset family with unintended value
This issue occurs when Polyspace®
Bug Finder™ detects a use of the memset
or
wmemset
function with possibly incorrect arguments.
void *memset (void *ptr, int value, size_t num)
fills the first
num
bytes of the memory block that ptr
points
to with the specified value
. If the argument value
is incorrect, the memory block is initialized with an unintended value.
The unintended initialization can occur in the following cases.
Issue | Risk | Possible Fix |
---|---|---|
The second argument is '0' instead of
0 or '\0' . | The ASCII value of character '0' is
48 (decimal), 0x30
(hexadecimal), 069 (octal) but not
0 (or
'\0' ). | If you want to initialize with '0' , use one of
the ASCII values. Otherwise, use 0 or
'\0' . |
The second and third arguments are probably reversed. For instance, the third argument is a literal and the second argument is not a literal. | If the order is reversed, a memory block of unintended size is initialized with incorrect arguments. | Reverse the order of the arguments. |
The second argument cannot be represented in a byte. | If the second argument cannot be represented in a byte, and you expect each byte of a memory block to be filled with that argument, the initialization does not occur as intended. | Apply a bit mask to the argument to produce a wrapped or truncated result that can be represented in a byte. When you apply a bit mask, make sure that it produces an expected result. For instance, replace |
The fix depends on the root cause of the defect. See fixes in the table above and code examples with fixes below.
If you do not want to fix the issue, add comments to your result or code to avoid another review. See:
Address Results in Polyspace User Interface Through Bug Fixes or Justifications if you review results in the Polyspace user interface.
Address Results in Polyspace Access Through Bug Fixes or Justifications (Polyspace Access) if you review results in a web browser.
Annotate Code and Hide Known or Acceptable Results if you review results in an IDE.
#include <string.h> #define SIZE 32 void func(void) { char buf[SIZE]; int c = -2; memset(buf, (char)c, sizeof(buf)); //Noncompliant }
In this example, (char)c
cannot be represented
in a byte.
One possible correction is to apply a cast so that the result can be represented in a
byte. Check that the result of the cast is an acceptable initialization value. In this
correction, Polyspace does not raise this defect. The cast from signed int
to
unsigned char
is contrary to best practices and Polyspace raises the defect Sign change integer
conversion overflow
.
#include <string.h> #define SIZE 32 void func(void) { char buf[SIZE ]; int c = -2; memset(buf, (unsigned char)c, sizeof(buf));// Might Overflow }
memset
One possible correction is to reserve the use of memset
only for
setting or clearing all bits in a buffer. For instance, in this code,
memset
is called to clear the bits of the character array
buf
.
#include <string.h> #define SIZE 32 void func(void) { char buf[SIZE ]; int c = -2; memset(buf, 0, sizeof(buf));//Compliant /* After clearing buf, use it in operations*/ }
Improper array initialization
This issue occurs when Polyspace Bug Finder considers that an array initialization using initializers is incorrect.
This defect applies to normal and designated initializers. In
C99, with designated initializers, you can place the elements of an
array initializer in any order and implicitly
initialize some array elements. The designated initializers use the
array index to establish correspondence between an array element and
an array initializer element. For instance, the statement int
arr[6] = { [4] = 29, [2] = 15 }
is equivalent to int
arr[6] = { 0, 0, 15, 0, 29, 0 }
.
You can use initializers incorrectly in one of the following ways.
Issue | Risk | Possible Fix |
---|---|---|
In your initializer for a one-dimensional array, you have more elements than the array size. | Unused array initializer elements indicate a possible coding error. | Increase the array size or remove excess elements. |
You place the braces enclosing initializer values incorrectly. | Because of the incorrect placement of braces, some array initializer elements are not used. Unused array initializer elements indicate a possible coding error. | Place braces correctly. |
In your designated initializer, you do not initialize the first element of the array explicitly. | The implicit initialization of the first array element indicates a possible coding error. You possibly overlooked the fact that array indexing starts from 0. | Initialize all elements explicitly. |
In your designated initializer, you initialize an element twice. | The first initialization is overridden. The redundant first initialization indicates a possible coding error. | Remove the redundant initialization. |
You use designated and nondesignated initializers in the same initialization. | You or another reviewer of your code cannot determine the size of the array by inspection. | Use either designated or nondesignated initializers. |
The fix depends on the root cause of the defect. See fixes in the table above and code examples with fixes below.
If you do not want to fix the issue, add comments to your result or code to avoid another review. See:
Address Results in Polyspace User Interface Through Bug Fixes or Justifications if you review results in the Polyspace user interface.
Address Results in Polyspace Access Through Bug Fixes or Justifications (Polyspace Access) if you review results in a web browser.
Annotate Code and Hide Known or Acceptable Results if you review results in an IDE.
int arr[2][3] = {{1, 2}, {3, 4}, {5, 6} //Noncompliant };
In this example, the array arr
is initialized
as {1,2,0,3,4,0}
. Because the initializer contains {5,6}
,
you might expect the array to be initialized {1,2,3,4,5,6}
.
One possible correction is to place the braces correctly so that all elements are explicitly initialized.
int a1[2][3] = {{1, 2, 3}, {4, 5, 6} };
int arr[5] = { [1] = 2, [2] = 3, [3] = 4, [4] = 5 }; //Noncompliant
In this example, arr[0]
is not explicitly
initialized. It is possible that the programmer did not consider that
the array indexing starts from 0.
One possible correction is to initialize all elements explicitly.
int arr[5] = { [0] = 1, [1] = 2, [2] = 3, [3] = 4, [4] = 5 };
int arr[5] = { [0] = 1, [1] = 2, [2] = 3, [2] = 4, //Noncompliant [4] = 5 };
In this example, arr[2]
is initialized twice.
The first initialization is overridden. In this case, because arr[3]
was
not explicitly initialized, it is possible that the programmer intended
to initialize arr[3]
when arr[2]
was
initialized a second time.
One possible correction is to eliminate the redundant initialization.
int arr[5] = { [0] = 1, [1] = 2, [2] = 3, [3] = 4, [4] = 5 };
int arr[] = { [0] = 1, [3] = 3, 4, [5] = 5, 6 }; //Noncompliant
In this example, because a mix of designated and nondesignated
initializers are used, it is difficult to determine the size of arr
by
inspection.
One possible correction is to use only designated initializers for array initialization.
int arr[] = { [0] = 1, [3] = 3, [4] = 4, [5] = 5, [6] = 6 };
Overlapping assignment
This issue occurs when there is a memory overlap between the left and right sides of an assignment. For instance, a variable is assigned to itself or one member of a union is assigned to another.
If the left and right sides of an assignment have memory overlap, the behavior is either redundant or undefined. For instance:
Self-assignment such as
x=(int)(long)x;
is redundant unlessx
isvolatile
-qualified.Assignment of one union member to another causes undefined behavior.
For instance, in the following code:
The result of the assignment
u1.a = u1.b
is undefined becauseu1.b
is not initialized.The result of the assignment
u2.b = u2.a
depends on the alignment and endianness of the implementation. It is not defined by C standards.
union { char a; int b; }u1={'a'}, u2={'a'}; //'u1.a' and 'u2.a' are initialized u1.a = u1.b; u2.b = u2.a;
Avoid assignment between two variables that have overlapping memory.
#include <string.h> union Data { int i; float f; }; int main( ) { union Data data; data.i = 0; data.f = data.i; //Noncompliant return 0; }
In this example, the variables data.i
and data.f
are
part of the same union
and are stored in the same
location. Therefore, part of their memory storage overlaps.
Use of memset with size argument zero
This issue occurs
when you call a function in the memset
family with
size argument zero. Functions include memset
, wmemset
, bzero
, SecureZeroMemory
, RtlSecureZeroMemory
,
and so on.
void *memset (void *ptr, int value, size_t num)
fills
the first num
bytes of the memory block that ptr
points
to with the specified value
. A zero value of num
renders
the call to memset
redundant. The memory that ptr
points
to:
Remains uninitialized, if not previously initialized.
Is not cleared and can contain sensitive data, if previously initialized.
Determine if the zero size argument occurs because of a previous error in your code. Fix the error.
#include <stdio.h> #include <string.h> void func (unsigned int size) { char str[] = "Buffer to be filled."; memset (str,'-',size); //Noncompliant puts (str); } void calling_func(void) { unsigned int buf_size=0; func(buf_size); }
In this example, the argument size
of memset
is
zero.
Check Information
Category: Others |
Version History
Introduced in R2024a
See Also
External Websites
MATLAB Command
You clicked a link that corresponds to this MATLAB command:
Run the command by entering it in the MATLAB Command Window. Web browsers do not support MATLAB commands.
Select a Web Site
Choose a web site to get translated content where available and see local events and offers. Based on your location, we recommend that you select: .
You can also select a web site from the following list
How to Get Best Site Performance
Select the China site (in Chinese or English) for best site performance. Other MathWorks country sites are not optimized for visits from your location.
Americas
- América Latina (Español)
- Canada (English)
- United States (English)
Europe
- Belgium (English)
- Denmark (English)
- Deutschland (Deutsch)
- España (Español)
- Finland (English)
- France (Français)
- Ireland (English)
- Italia (Italiano)
- Luxembourg (English)
- Netherlands (English)
- Norway (English)
- Österreich (Deutsch)
- Portugal (English)
- Sweden (English)
- Switzerland
- United Kingdom (English)
Asia Pacific
- Australia (English)
- India (English)
- New Zealand (English)
- 中国
- 日本Japanese (日本語)
- 한국Korean (한국어)