я нашел это strncpy_s()
определяется под VS2013 как
errno_t __cdecl strncpy_s(_Out_writes_z_(_SizeInBytes) char * _Dst, _In_ rsize_t _SizeInBytes, _In_reads_or_z_(_MaxCount) const char * _Src, _In_ rsize_t _MaxCount);
rsize_t
является:
typedef size_t rsize_t;
Я думаю, что это трюк Visual Studio. Тем не менее, я обнаружил, что эта функция определяется следующим образом страница
errno_t strncpy_s(char *restrict dest, rsize_t destsz,
const char *restrict src, rsize_t count);
Почему rsize_t
определяется здесь? Что, если size_t
был использован здесь? Любые особые случаи, чтобы использовать это rsize_t
?
Вы встречали это в стандартной библиотеке Microsoft C ++, но на самом деле она происходит от C. C 11, если быть точным, то есть технически она не является частью C ++.
Стандарт С 11, Приложение К ввел все _s
функции и соответствующие определения типов, в том числе rsize_t
, Существует также макрос «максимальное значение» RSIZE_MAX
который достаточно велик для типичных приложений, но меньше реального максимального значения типа. Безопасные функции ничего не делают и сообщают об ошибке, когда значение типа rsize_t
превышает RSIZE_MAX
,
Идея состоит в том, чтобы избежать сбоев при переполнении буфера и подобных ошибок, вызванных недопустимыми размерами, обычно в результате использования отрицательного значения для размера. В представлении значения со знаком дополнения 2 (самое распространенное) отрицательное число соответствует очень большое количество, когда рассматривается как без знака. RSIZE_MAX
должен поймать такое неправильное использование.
Цитирую «обоснование» части С11 (N1570), К.3.2:
3 Чрезвычайно большие размеры объекта часто являются признаком того, что размер объекта был рассчитан
неправильно. Например, отрицательные числа появляются как очень большие положительные числа, когда
преобразован в неподписанный тип, какsize_t
, Кроме того, некоторые реализации не поддерживают
объекты размером до максимального значения, которое может быть представлено типомsize_t
,4 По этим причинам иногда выгодно ограничивать диапазон размеров объектов для обнаружения.
ошибки программирования. Для реализаций, ориентированных на машины с большими адресными пространствами,
рекомендуетсяRSIZE_MAX
определяется как меньший из размеров самого большого
объект поддерживается или(SIZE_MAX >> 1)
даже если этот предел меньше размера
некоторые законные, но очень большие объекты. Реализации, ориентированные на машины с небольшим
адресные пространства, возможно, пожелают определитьRSIZE_MAX
какSIZE_MAX
, что означает, что нет размера объекта, который считается нарушением ограничения времени выполнения.
Стоит отметить, что Приложение K имеет очень мало реализаций, и есть предложение (N1967) осудить и / или удалить его из стандарта.
Эти typedefs имеют семантическое значение. Очевидно, вы можете использовать size_t
здесь (так как это то же самое), но rsize_t
более многословно:
Тип size_t обычно охватывает все адресное пространство. ИСО / МЭК TR 24731-1-2007 вводит новый тип rsize_t, определенный как size_t, но явно используемый для хранения размера одного объекта. [1]
Это та же ситуация, что и при использовании size_t
вместо unsigned int
, Это в основном то же самое, но названо по-другому, так что вам легко понять, с чем вы работаете (size_t
= «размер чего-либо», что подразумевает целое число без знака).
Стоит отметить (как предлагается в комментариях), что rsize_t
определяется в спецификации C, но не в спецификации C ++.