2013-12-24 5 views
6

Я немного запутался в указателях и количестве байтов, которые они занимают. В моем учебнике сначала говорится, что указатели на 16-битных системах занимают 2 байта, 32-битные системы - 4 байта, 64-битные системы - 8 байтов и так далее. Затем 10 строк, говорится, что указатели занимают столько байтов, которые необходимы для хранения адресов. Вот мои вопросы:Сколько байтов занимает указатели?

  1. Значит ли это, что если мы скажем, что на 64-битной системе, адрес должен быть не более 8 байт?
  2. Если мы находимся на 16-битной системе и указатели занимают 2 байта, а адресу нужно больше 2 байтов, которые нужно разместить, то что происходит?
+0

Дубликат http://stackoverflow.com/questions/1473935/can-the-size-of-pointers-vary-depending-on-whats-pointed-to – Daniel

+0

@alk Я предполагаю, что это опечатка, и он означает 64 бит в # 1 – Leeor

+0

@alk @ Leeor Да, я 64 бит. – GovernmentFX

ответ

5

Не существует фиксированного ответа; он полностью зависит от архитектуры, реализации компилятора и даже от типа самого указателя. У указателей на разные типы не гарантируется одинаковый размер и/или представление.

Например, предположим, что архитектура с адресатом, где наименьшая адресуемая единица хранения составляет 16 бит в ширину (или шире). Каждое слово может содержать несколько значений char; все остальные типы занимают полное слово или больше. В такой архитектуре char * и void * потребуются дополнительные биты для смещения в слово по сравнению с другими типами указателей.

Обратите внимание, что тип указателя может быть шире, чем количество бит, фактически необходимых для хранения адреса. Оригинальный Macintosh работал на процессоре Motorola 68000, который имел размер 32-битного слова, но только 24 бит на адресной шине. Типы указателей были 32 бит в ширину, оставляя верхние 8 бит неиспользованными. Предприимчивые программисты MacOS воспользовались этим, чтобы хранить некоторые данные в самом верхнем байте типа указателя, используя большую часть этого драгоценного 128 КБ ОЗУ. Конечно, Motorola в конце концов выпустила процессор с 32 адресными строками (68020), что означает, что весь этот код пришлось переписать.

На современном товарном настольном и серверном оборудовании (читайте: x86) можно с уверенностью предположить, что все типы указателей имеют такой же размер, как размер родного слова (32- или 64-разрядный), и что все типы указателей имеют одинаковый размер и представление. Просто имейте в виду, что это не имеют значение, чтобы быть правдой.

10

Короткий ответ заключается в том, что это зависит. Когда мы говорим, что система 32-битная, это может означать, что нативное целое составляет 32 бита в ширину, что собственный адрес (то есть размер указателя) имеет ширину 32 бит или и то, и другое.

Кроме того, не каждая архитектура использует flat memory model (например, см. x86 memory segmentation). Это еще больше осложняет ситуацию.

Лучше всего обрабатывать размер указателя как непрозрачный.

C99 предоставляет инструменты в виде intptr_t and uintptr_t типов, которые являются целыми числами, которые гарантированно будут достаточно широкими, чтобы удерживать указатель.

1

Это сообщит вам, сколько байтов требуется для представления указателя на вашу систему.

#include <stdio.h> 
    int main() { 
     printf("%ld bytes per pointer\n", sizeof(void *)); 
    } 

Вот флаг компилятора вы можете играть с это на тему:

$ gcc -m32 -o prog32 prog.c 
$ gcc -m64 -o prog64 prog.c 

Первая строка создает двоичный файл для 32-разрядной среде, что дает вам 4 байта указателей. Вторая строка генерирует двоичный код для 64-разрядной среды, предоставляя вам 8-байтовые указатели. Вы можете подтвердить это, выполнив вышеуказанную программу.

Успение, вы находитесь на 64-битной системе с GCC. Надеюсь, это немного прояснит ситуацию.

+0

Указатели содержат адреса, и они сами имеют адреса, поэтому не совсем то же самое. Кроме того, 16-разрядные системы могут иметь более 64 КБ памяти, поэтому ваш второй оператор является ложным. –

+0

@MarkTolonen, да, хороший пункт. Мое намерение состояло в том, чтобы направить @GovernmentFX от понятия, что * «указатели берут 2 байта, а адрес требует больше двух байтов». * Это то, что я имел в виду, «указатели ** - это ** адреса, и все. " Например, чтобы указать на 'int', требуется только указатель. * Это * адрес. Спасибо, однако, потому что OP также должен понимать, что у вас могут быть адреса с адресом на адрес и т. Д. –

+0

@MarkTolonen, да, вы можете выйти за пределы возможностей языка C и использовать библиотеки или другие методы для решения любого объема памяти на 16-разрядная система. Тем не менее, я рассматриваю контекст этого вопроса как чистый вопрос C и указателей, так как это то, что он помечен. Я согласен с моим утверждением, что с 16-разрядным адресом можно адресовать 2^16 байт памяти * в C *. Это слишком близко к Рождеству, так что я уступлю, и я отредактировал свой ответ, чтобы упростить для OP, надеюсь, узнать немного больше о том, как указываются указатели и как он может это проверить, практический. Приветствия. :-) –

4

Размер указателя в основном зависит от архитектуры системы, в которой она реализована. Например, размер указателя в 32-битном формате составляет 4 байта (32 бит) и 8 байтов (64 бит) в 64-разрядных машинах. Типы бит в машине - это только адрес памяти, который он может удерживать. 32-разрядные машины могут содержать 2^32, а 64-разрядные машины могут содержать 2^64 адресные пространства. Поэтому указатель (переменная, указывающая на ячейку памяти) должен указывать на любой из адресов памяти (2^32 for 32 bit and 2^64 for 64 bit), которые хранятся в машинах.

По этой причине мы видим, что размер указателя составляет 4 байта в 32-битной машине и 8 байтов на 64-битной машине.

Ответил в Is the sizeof(some pointer) always equal to four?

1

Указатели используются для хранения адреса ширины variable.The адреса памяти/местоположение зависит от компьютера architecture.If компьютерной архитектуры является 16-битным, то это означает, что он может имеют 2^16 расположения памяти. Поэтому для того, чтобы указатель мог хранить любую ячейку памяти на этом компьютере, она должна быть 16 бит в ширину, то есть 2 байта (8 бит = 1 байт). Аналогично для 32-битной и 64-битной архитектуры нам нужны указатели размером 4 байта (32-разрядная ширина) и 8 байтов (64-разрядная ширина) соответственно.
Также, если система является 16-разрядной, то она не может иметь адресное местоположение размером более 16 бит.

Смежные вопросы