memset, memset_explicit, memset_s
|
Определено в заголовке
<string.h>
|
||
|
void
*
memset
(
void
*
dest,
int
ch,
size_t
count
)
;
|
(1) | |
|
void
*
memset_explicit
(
void
*
dest,
int
ch,
size_t
count
)
;
|
(2) | (начиная с C23) |
|
errno_t memset_s
(
void
*
dest, rsize_t destsz,
int
ch, rsize_t count
)
;
|
(3) | (начиная с C11) |
count
символов объекта, на который указывает
dest
.
dest
является нулевым указателем.
ch
в каждой позиции диапазона назначения
[
dest, dest
+
destsz
)
, если
dest
и
destsz
сами являются допустимыми:
-
-
destявляется нулевым указателем -
destszилиcountбольше RSIZE_MAX -
countбольшеdestsz(произойдет переполнение буфера)
-
dest
<
count
<=
destsz
; другими словами, ошибочное значение
destsz
не выявляет надвигающееся переполнение буфера.
-
Как и все функции с проверкой границ,
memset_sгарантированно доступна только если __STDC_LIB_EXT1__ определено реализацией и если пользователь определяет __STDC_WANT_LIB_EXT1__ как целочисленную константу 1 до включения <string.h> .
Содержание |
Параметры
| dest | - | указатель на заполняемый объект |
| ch | - | байт для заполнения |
| count | - | количество байт для заполнения |
| destsz | - | размер целевого массива |
Возвращаемое значение
dest
dest
не является нулевым указателем и
destsz
допустим, записывает
destsz
заполняющих байтов
ch
в целевой массив.
Примечания
memset
может быть оптимизирован (в соответствии с правилами
as-if
), если объект, изменяемый этой функцией, больше не используется до конца своего времени жизни (например,
gcc bug 8537
). По этой причине данная функция не может использоваться для очистки памяти (например, для заполнения нулями массива, в котором хранился пароль).
Эта оптимизация запрещена для
memset_explicit
и
memset_s
: они гарантированно выполняют запись в память.
Сторонние решения для этого включают FreeBSD
explicit_bzero
или Microsoft
SecureZeroMemory
.
Пример
#define __STDC_WANT_LIB_EXT1__ 1 #include <stdio.h> #include <string.h> #include <stdlib.h> int main(void) { char str[] = "ghghghghghghghghghghgh"; puts(str); memset(str,'a',5); puts(str); #ifdef __STDC_LIB_EXT1__ set_constraint_handler_s(ignore_handler_s); int r = memset_s(str, sizeof str, 'b', 5); printf("str = \"%s\", r = %d\n", str, r); r = memset_s(str, 5, 'c', 10); // count is greater than destsz printf("str = \"%s\", r = %d\n", str, r); #endif }
Возможный вывод:
ghghghghghghghghghghgh aaaaahghghghghghghghgh str = "bbbbbhghghghghghghghgh", r = 0 str = "ccccchghghghghghghghgh", r = 22
Ссылки
- Стандарт C17 (ISO/IEC 9899:2018):
-
- 7.24.6.1 Функция memset (стр: 270)
-
- K.3.7.4.1 Функция memset_s (стр: 451)
- Стандарт C11 (ISO/IEC 9899:2011):
-
- 7.24.6.1 Функция memset (стр. 371)
-
- K.3.7.4.1 Функция memset_s (стр. 621-622)
- Стандарт C99 (ISO/IEC 9899:1999):
-
- 7.21.6.1 Функция memset (стр: 333)
- Стандарт C89/C90 (ISO/IEC 9899:1990):
-
- 4.11.6.1 Функция memset
Смотрите также
|
(C11)
|
копирует один буфер в другой
(функция) |
|
(C95)
|
копирует заданный широкий символ в каждую позицию массива широких символов
(функция) |
|
C++ documentation
для
memset
|
|