Максимальный размер макроса объекта - PullRequest
0 голосов
/ 04 апреля 2019

Я пытался написать следующее:

#include <stdint.h>
#include <stdlib.h>

void *ptr = malloc(SIZE_MAX);

Но компилятор дал мне следующее предупреждение:

warning: argument 1 value ‘18446744073709551615’ exceeds maximum object 
size 9223372036854775807 [-Walloc-size-larger-than=]

Звучит разумно.Но в любом случае я хотел бы выделить объект максимально возможного размера в текущей реализации / арке.Существует макрос RSIZE_MAX, определенный в Annex.B(19):

__STDC_WANT_LIB_EXT1__
RSIZE_MAX

Итак, я попробовал следующий пример :

#define __STDC_WANT_LIB_EXT1__
#include <stdint.h>
#include <stdlib.h>

int main(){
    void *ptr = malloc(RSIZE_MAX);
}

Но безрезультатно,RSIZE_MAX не определен.Как использовать этот макрос или любой другой способ проверить максимальный размер объекта во время компиляции?

Ответы [ 2 ]

3 голосов
/ 04 апреля 2019

Определение SIZE_MAX определяет максимальное значение типа данных size_t. Тип данных size_t способен хранить размер любого объекта. Максимальный размер зависит от шины с 32 или 64 бит.

Если вы попытаетесь выделить в памяти максимально исчисляемый размер памяти, произойдет сбой, поскольку это заблокирует все ваше адресное пространство. Компилятор предупреждает вас, что вызов malloc всегда будет неудачным. Запрошенный размер просто не имеет смысла.

Кстати: 9223372036854775807 - это 0x7FFFFFFFFFFFFFFF

1 голос
/ 04 апреля 2019

RSIZE_MAX определено в Приложении К С11, которое является факультативным. Реализация, которая его поддерживает, заранее определит макрос __STDC_LIB_EXT1__. Например, реализация gcc / glibc, которую я использую в своей системе Ubuntu, не поддерживает ее и поэтому не определяет RSIZE_MAX.

В любом случае, нет гарантии, что malloc(RSIZE_MAX) будет успешным, и в стандарте нет никакого значения, что RSIZE_MAX, даже если он определен, является максимальным размером выделения, поддерживаемым malloc. Оценка malloc(RSIZE_MAX+1) даже не является нарушением ограничения времени выполнения ; malloc() по-прежнему принимает аргумент типа size_t, а не rsize_t. malloc сообщает об ошибке, возвращая нулевой указатель.

См. N1570 K.3.4:

Макрос

RSIZE_MAX

, которое расширяется до значения типа size_t. Функции, которые имеют параметры типа rsize_t считают это нарушением ограничения времени выполнения, если значения этих параметров больше RSIZE_MAX.

Обратите внимание, что в некоторых системах (в частности, в системах на основе Linux) malloc() может показаться успешным, возвращая ненулевой результат, даже если для выделения недостаточно памяти. Смотрите "overcommit" и "OOM killer".

...