luckfox-pico-sdk/project/app/wifi_app/hisi_tools/securec/memmove_s.c
2023-08-08 20:36:47 +08:00

114 lines
3.2 KiB
C

/*
* Copyright (c) Huawei Technologies Co., Ltd. 2014-2018. All rights reserved.
* Description: memmove_s function
* Author: lishunda
* Create: 2014-02-25
*/
/*
* [Standardize-exceptions] Use unsafe function: Portability
* [reason] Use unsafe function to implement security function to maintain
* platform compatibility. And sufficient input validation is performed before
* calling
*/
#include "securecutil.h"
#ifdef SECUREC_NOT_CALL_LIBC_CORE_API
/*
* Implementing memory data movement
*/
SECUREC_INLINE void SecUtilMemmove(void *dst, const void *src, size_t count) {
unsigned char *pDest = (unsigned char *)dst;
const unsigned char *pSrc = (const unsigned char *)src;
size_t maxCount = count;
if (dst <= src || pDest >= (pSrc + maxCount)) {
/*
* Non-Overlapping Buffers
* Copy from lower addresses to higher addresses
*/
while (maxCount--) {
*pDest = *pSrc;
++pDest;
++pSrc;
}
} else {
/*
* Overlapping Buffers
* Copy from higher addresses to lower addresses
*/
pDest = pDest + maxCount - 1;
pSrc = pSrc + maxCount - 1;
while (maxCount--) {
*pDest = *pSrc;
--pDest;
--pSrc;
}
}
}
#endif
/*
* <FUNCTION DESCRIPTION>
* The memmove_s function copies count bytes of characters from src to dest.
* This function can be assigned correctly when memory overlaps.
* <INPUT PARAMETERS>
* dest Destination object.
* destMax Size of the destination buffer.
* src Source object.
* count Number of characters to copy.
*
* <OUTPUT PARAMETERS>
* dest buffer is uptdated.
*
* <RETURN VALUE>
* EOK Success
* EINVAL dest is NULL and destMax != 0 and destMax <=
* SECUREC_MEM_MAX_LEN EINVAL_AND_RESET dest != NULL and src is NULLL and
* destMax != 0 and destMax <= SECUREC_MEM_MAX_LEN ERANGE destMax >
* SECUREC_MEM_MAX_LEN or destMax is 0 ERANGE_AND_RESET count > destMax
* and dest != NULL and src != NULL and destMax != 0 and destMax <=
* SECUREC_MEM_MAX_LEN
*
* If an error occured, dest will be filled with 0 when dest and destMax
* valid. If some regions of the source area and the destination overlap,
* memmove_s ensures that the original source bytes in the overlapping region
* are copied before being overwritten.
*/
errno_t memmove_s(void *dest, size_t destMax, const void *src, size_t count) {
if (destMax == 0 || destMax > SECUREC_MEM_MAX_LEN) {
SECUREC_ERROR_INVALID_RANGE("memmove_s");
return ERANGE;
}
if (dest == NULL || src == NULL) {
SECUREC_ERROR_INVALID_PARAMTER("memmove_s");
if (dest != NULL) {
(void)memset(dest, 0, destMax);
return EINVAL_AND_RESET;
}
return EINVAL;
}
if (count > destMax) {
(void)memset(dest, 0, destMax);
SECUREC_ERROR_INVALID_RANGE("memmove_s");
return ERANGE_AND_RESET;
}
if (dest == src) {
return EOK;
}
if (count > 0) {
#ifdef SECUREC_NOT_CALL_LIBC_CORE_API
SecUtilMemmove(dest, src, count);
#else
/* Use underlying memmove for performance consideration */
(void)memmove(dest, src, count);
#endif
}
return EOK;
}
#if SECUREC_IN_KERNEL
EXPORT_SYMBOL(memmove_s);
#endif