diff --git a/include/lib/libc/string.h b/include/lib/libc/string.h index 812940418..bba98167b 100644 --- a/include/lib/libc/string.h +++ b/include/lib/libc/string.h @@ -30,5 +30,7 @@ char *strrchr(const char *p, int ch); size_t strlcpy(char * dst, const char * src, size_t dsize); size_t strlcat(char * dst, const char * src, size_t dsize); char *strtok_r(char *s, const char *delim, char **last); +size_t strnlen_secure(const char *str, size_t maxlen); +int strcpy_secure(char *restrict dest, size_t dest_size, const char *restrict src); #endif /* STRING_H */ diff --git a/lib/libc/libc_common.mk b/lib/libc/libc_common.mk index 5f44bd517..3b8321606 100644 --- a/lib/libc/libc_common.mk +++ b/lib/libc/libc_common.mk @@ -21,9 +21,11 @@ LIBC_SRCS := $(addprefix lib/libc/, \ snprintf.c \ strchr.c \ strcmp.c \ + strcpy_secure.c \ strlcat.c \ strlcpy.c \ strlen.c \ + strnlen_secure.c \ strncmp.c \ strnlen.c \ strrchr.c \ diff --git a/lib/libc/strcpy_secure.c b/lib/libc/strcpy_secure.c new file mode 100644 index 000000000..6f8de2982 --- /dev/null +++ b/lib/libc/strcpy_secure.c @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2024-2025, Altera Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include +#include +#include +#include + +int strcpy_secure(char *restrict dest, size_t dest_size, const char *restrict src) +{ + /* Check for null pointers */ + if ((dest == NULL) || (src == NULL)) { + return -EINVAL; + } + + /* Check the destination size valid range */ + if (dest_size == 0) { + return -ERANGE; + } + + /* Calculate the length of the source string */ + size_t src_len = strnlen_secure(src, dest_size); + + /* Check if the source string fits in the destination buffer */ + if (src_len >= dest_size) { + /* Set destination to an empty string */ + dest[0] = '\0'; + return -ERANGE; + } + + /* Copy the source string to the destination */ + for (dest[src_len] = '\0'; src_len > 0; src_len--) { + dest[src_len - 1] = src[src_len - 1]; + } + + return 0; +} diff --git a/lib/libc/strnlen_secure.c b/lib/libc/strnlen_secure.c new file mode 100644 index 000000000..36b35712f --- /dev/null +++ b/lib/libc/strnlen_secure.c @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2024-2025, Altera Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include + +size_t strnlen_secure(const char *str, size_t maxlen) +{ + size_t len = 0; + + if (str == NULL) { + return 0; + } + + while ((len < maxlen) && (str[len] != '\0')) { + len++; + } + + return len; +}