diff options
| author | Kees Cook <kees@kernel.org> | 2026-03-23 01:27:25 +0000 |
|---|---|---|
| committer | Kees Cook <kees@kernel.org> | 2026-06-18 16:39:31 -0700 |
| commit | 079a028d6327e68cfa5d38b36123637b321c19a7 (patch) | |
| tree | d6bed2ef9b0f5969d1105f010d8b4a8804a13f61 /Documentation/process | |
| parent | 58c4ce8cd6cd1fbf1bca2e1d1f42f9e2899fa934 (diff) | |
string: Remove strncpy() from the kernel
strncpy() has been a persistent source of bugs due to its ambiguous
intended usage and frequently counter-intuitive semantics: it may not
NUL-terminate the destination, and it unconditionally zero-pads to the
full length, which isn't always needed. All former callers have been
migrated[1] to:
- strscpy() for NUL-terminated destinations
- strscpy_pad() for NUL-terminated destinations needing zero-padding
- strtomem_pad() for non-NUL-terminated fixed-width fields
- memcpy_and_pad() for bounded copies with explicit padding
- memcpy() for known-length copies
Remove the generic implementation, its declaration, the FORTIFY_SOURCE
wrapper, and associated tests.
Link: https://github.com/KSPP/linux/issues/90 [1]
Signed-off-by: Kees Cook <kees@kernel.org>
Diffstat (limited to 'Documentation/process')
| -rw-r--r-- | Documentation/process/deprecated.rst | 47 |
1 files changed, 26 insertions, 21 deletions
diff --git a/Documentation/process/deprecated.rst b/Documentation/process/deprecated.rst index 03de71f654c7..22a5e62c92ea 100644 --- a/Documentation/process/deprecated.rst +++ b/Documentation/process/deprecated.rst @@ -131,27 +131,32 @@ value of strcpy() was used, since strscpy() does not return a pointer to the destination, but rather a count of non-NUL bytes copied (or negative errno when it truncates). -strncpy() on NUL-terminated strings ------------------------------------ -Use of strncpy() does not guarantee that the destination buffer will -be NUL terminated. This can lead to various linear read overflows and -other misbehavior due to the missing termination. It also NUL-pads -the destination buffer if the source contents are shorter than the -destination buffer size, which may be a needless performance penalty -for callers using only NUL-terminated strings. - -When the destination is required to be NUL-terminated, the replacement is -strscpy(), though care must be given to any cases where the return value -of strncpy() was used, since strscpy() does not return a pointer to the -destination, but rather a count of non-NUL bytes copied (or negative -errno when it truncates). Any cases still needing NUL-padding should -instead use strscpy_pad(). - -If a caller is using non-NUL-terminated strings, strtomem() should be -used, and the destinations should be marked with the `__nonstring -<https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html>`_ -attribute to avoid future compiler warnings. For cases still needing -NUL-padding, strtomem_pad() can be used. +strncpy() +--------- +strncpy() has been removed from the kernel. All former callers have +been migrated to safer alternatives. + +strncpy() did not guarantee NUL-termination of the destination buffer, +leading to linear read overflows and other misbehavior. It also +unconditionally NUL-padded the destination, which was a needless +performance penalty for callers using only NUL-terminated strings. Due +to its various behaviors, it was an ambiguous API for determining what +an author's true intent was for the copy. + +The replacements for strncpy() are: + +- strscpy() when the destination must be NUL-terminated. +- strscpy_pad() when the destination must be NUL-terminated and + zero-padded (e.g., structs crossing privilege boundaries). +- memtostr() for NUL-terminated destinations from non-NUL-terminated + fixed-width sources (with the `__nonstring` attribute on the source). +- memtostr_pad() for the same, but with zero-padding. +- strtomem() for non-NUL-terminated fixed-width destinations, with + the `__nonstring` attribute on the destination. +- strtomem_pad() for non-NUL-terminated destinations that also need + zero-padding. +- memcpy_and_pad() for bounded copies from potentially unterminated + sources where the destination size is a runtime value. strlcpy() --------- |
