Достъп до памет, по-голяма от UINT_MAX*4 размер в C?

Да предположим, че имам масив с размер 78719476736 байта. имайте предвид, че този масив е динамично разпределен с помощта на malloc в моя C код. Да приемем, че malloc връща валиден указател след разпределяне на толкова много памет. Размерът на този масив е повече от UINT_MAX(4294967295), т.е. максималното ограничение на unsigned int(32 бита)

Да приемем, че кодът ми изглежда като нещо по-долу, напр.

int *buf;
buf = (int*)malloc(78719476736);

Тук 78719476736 е по-голямо от 4 * UINT_MAX.

Сега, ако трябва да се позова на всички елементи на buf, тогава, тъй като buf е int*, той ще бъде 32 бита, така че няма да може да адресира всички елементи на паметта, които съм разпределил с помощта на malloc(78719476736 байта).

Въпросът ми е не трябва ли кодът по-горе да бъде променен, за да направи buf толкова дълъг (64-битова променлива), тъй като само дълга дълга променлива ще може да адресира голямата памет, която съм разпределил.

Променен код напр.

unsigned long long int buf;
buf = (unsigned long long int*)malloc(78719476736);

Всъщност мисля, че променливата buf вече не трябва да бъде указател, тъй като всеки указател ще бъде 32-битов широк и следователно няма да има достъп до 78719476736 байта.

Така че трябва да е обикновен unsigned long long int и ще трябва да прехвърля стойността на указателя за връщане на malloc към unsigned long long int, както е показано в променения код по-горе, и да използвам buf за достъп до всички разпределени елементи.

Прав ли съм в предположенията си по-горе?

or

Бъркам/пропускам ли нещо?

РЕДАКТИРАНЕ: Ако помага,

Работя на настолен компютър с WinXP на Intel Core 2 Duo (64-битов процесор). Така че по отношение на процесора не би трябвало да има проблем с достъпа до повече от 4 GB адресно пространство. Кои други компоненти трябва да бъдат активирани за 64-битова поддръжка, т.е.

а.) Как да активирам поддръжка на компилатор за 64 бита, докато компилирам (използвам Visual Studio 2005 Professional edition)

b.) Поддръжка на ОС за 64 бита - използвам Windows XP Professional.

Благодаря ти.

-AD.


person goldenmean    schedule 16.06.2009    source източник
comment
Моля, кажете ми какво, по дяволите, пишете, така че никога да не ви накарам по невнимание да локализирате 73 GB на моя сървър...   -  person Eric    schedule 16.06.2009


Отговори (6)


  1. Трябва ви 64 битова ОС
  2. malloc получава size_t като параметър, който е 64 бита на 64 битови платформи
  3. И най-важното: Вероятно трябва да си помислите: Трябва ли да отделя повече от 4G памет?
person Artyom    schedule 16.06.2009

Мисля, че сте дълбоко объркан какво е указател. Поне в обикновените системи размерът на указателя (броят различни стойности, т.е. броят различни адреси) не зависи от типа!

int *a;
short *b;
double *c;

a, b и c са указатели към различни типове, но всички те имат еднакъв размер (4 байта на 32-битова система, например). Точно това е смисълът на 64-битовата система в сравнение с 32-битовата: да можете да адресирате повече от 2**32 местоположения от указател.

Също така, 32-битов процесор не може да адресира повече от 4 Gb в хардуера [1] и съответното виртуално адресно пространство също обикновено е ограничено до 32 бита. Така че злоупотребата с 8 Gb памет е малко вероятно да работи така или иначе.

[1] това не е съвсем вярно - процесорът на Intel например има разширения, така че 32-битовият процесор може да използва „разширени“ адреси.

person David Cournapeau    schedule 16.06.2009

int* е тип указател. Ако сте на система, която може да разпредели 78719476736 байта, тя вероятно има поне 64-битови адреси, т.е. sizeof(int*) >= 8. Размерът на показалеца няма нищо общо с това, което е sizeof(int).

person laalto    schedule 16.06.2009

За да адресирате повече от 4 GB памет, ви е необходим някакъв механизъм за избор на тази памет. Следователно трябва да компилирате вашето приложение да бъде 64-битово и тогава всичките ви указатели ще бъдат с ширина 64 бита.

Единственият друг начин за достъп до повече от 4 GB памет би бил да използвате допълнителен механизъм за избор на адрес/памет, подобно на този, който сте имали със сегмента, и да компенсирате бъркотията обратно в дните на реалния режим на DOS. Това разбира се зависи от архитектурата на вашия процесор.

person Daemin    schedule 16.06.2009

Ако стартирате софтуера си на 64-битова операционна система и използвате 64-битови настройки на компилатора, всичките ви указатели ще бъдат 64-битови. Няма нужда от специална декларация.

person joelr    schedule 16.06.2009

Не е възможно, вашият компилатор и операционна система не поддържат това, точка.

За Windows можете да видите документацията на _HEAP_MAXREQ.

Прочетете някои опции,

64-битови големи malloc

person RandomNickName42    schedule 14.07.2009