1. Assume whatever can go wrong will.
Example: Never use gets().
2. Assume any input is going to be malformed or not what you expect.
Example: Check validity of input parameters.
3. Do not make a security decision based on untrusted inputs.
Example: Avoid Double-Free vulnerabilities.
4. Check parameters to ensure that all arguments are of the correct type and will not overflow any arrays.
Example: Improperly bounded string copies.
5. Use data abstraction to enable the compiler to perform rigorous type checking and to enforce constraints on values and lengths.
Example: Implicit type
6. Understand the context in which the program will execute.
Example: Deadlock in a multi-threaded program.
7. Validate your input stream to ensure that the commands invoked are expected and no other commands are injected.
Example: Avoid race condition while writing to a file using shell script.
8. When performing input validation take into account how programs invoked with those arguments could interpret them.
Example: Improper use of sizeof() function in strncpy() causes overflow.
9. Avoid hard-coded passwords and secrets in your program.
Example: Storing passwords in plaintext .
10. Use well known and accepted cryptographic algorithms and implementations of those algorithms.
Don't use obsolete or deprecated cryptographic algorithms or create your own algorithms.
Example: Use of broken or risky cryptographic algorithms.
11. Use well known and accepted cryptographic random number generation.Don't use obsolete or deprecated cryptographic algorithms or create your own
algorithms.
Example: Cryptographically weak pseudo-random number generator.
12. There are many tools to help you create a secure program, please take advantage of them. Example: SPC Clinic
A. If you have no reason to trust it, don't trust it.Take greater care with any input you have not generated.
Example: Check the validity of input parameters.
B. If it cannot happen, check for it. Someone may modify the program in such a way that it can happen... or you may be wrong.
Example: Avoid race conditions when doing file operations by using the file descriptor.
C. Do not use input or constructor string functions that do not perform any bound checking.
Example: Using gets( ) causes buffer overflow. Use fgets( ) instead.
D. Do not use input or constructor functions that cannot check the length of the input. Example: Using gets( ) causes buffer overflow. Use fgets( ) instead.
E. C and C++ compilers generally do not check types rigorously. A developer can increase this level of checking by turning or compiler warnings, which will often
catch more type errors than if they are not used. Some examples are given below:
(b) Use format specifiers to print output values.
F. Avoid calls to malloc( ) with parameter (number of bytes to be allocated)set to 0. Either the function returns NULL, or it returns a pointer to space that cannot
be used without overwriting unallocated memory.
Example: Avoid calling malloc(size_t size) with value of size parameter as 0.
G. Control the input values when possible by limiting them to a finite set. Some examples are given below.
(a) Example 1.
(b) Example 2.
H. Calling functions with null parameters for input should be checked and defended against.
Example: Avoid calling malloc(size_t size) with value of size parameter as 0.
I. Type conversion issues especially for cases that may result in integer wrap-around and overflows.
Example: Non-compliant comparisons.
J. Rules for pointer arithmetic as vulnerabilities can arise when addition or size checks involve two pointer types.
Example: Arithmetic involves two pointer types.
K. When performing input validation make sure that any validated path does not allow escaping from a restricted directory.
Example: Canonicalize path names originating from untrusted sources.
L. Before creating a directory or file, make sure you have set the correct default permission specification.
Example: Create files with appropriate access permissions.
M. Be wary of off-by-one errors. Some examples are given below.
(a) Check size or range of integer values to avoid numeric overflows.
(b) Wrong use of size_t parameter of strncpy() causes off-by-one error.
(c) Incorrect initiation and continuation condition causes off-by-one error.
N. When using format string functions, make sure that the format string can be authenticated/trusted. Some examples are given below.
(a) Never let the user input format string/s.
(b) Buffer Overflow.
i. Hide details that users don't need to know about. Some examples are given below.
(a) Information exposure through an error message.
(b) Intentional information exposure.
(c) Information exposure through discrepancy.
ii. Avoid side effects in arguments to unsafe macros. If developer is using a macro that uses its arguments more than once, then the developer must avoid passing any
arguments with side effects to that macro.
Example: Using unsafe macros.
iii. Use parentheses around macro replacement lists. Otherwise operator precedence may cause the expression to be computed in unexpected ways.
Example: Use parenthesis around macro replacement lists.
iv. Minimise the scope of variables and functions, This prevents many unexpected changes to the variables due to programming error.
Example: Minimise the scope of variables and functions.
v. When the memory a pointer points to is freed, the pointer should be reset to NULL. Otherwise, these dangling pointers could cause writing to freed memory, and cause
a double free.
Example: Avoid double-free vulnerabilities