Какие существуют методы для безопасной обработки 32-битных и 64-битных указателей без условного макроса? - PullRequest
0 голосов
/ 08 октября 2009

Я обновляю некоторый код в библиотеке, потому что я обнаружил, что мой исходный код предполагал 32-битные указатели. У меня есть свои собственные мысли о том, как это исправить, но для полноты я хочу спросить, какие методы вы бы использовали, чтобы этот код работал как для 32-битных, так и для 64-битных без макроса?

char *argList = (char *)malloc(sizeof(id *) * argumentsCount);

sizeof (id *) - 4 на 32 бита, 8 на 64 бита. Я использую char * argList для создания массива указателей на объекты, затем использую метод getObjects NSArray:

[myNSArray getObjects:(id *)argList];

работает в 32-битном, вылетает в 64-битном (по понятным причинам)

Ответы [ 2 ]

2 голосов
/ 08 октября 2009

Хотя у меня нет всего контекста, я подозреваю, что это на самом деле не проблема 32/64 бит. Что вы, вероятно, хотите, это что-то вроде:

id *argList = malloc(sizeof(id) * argumentsCount);

В зависимости от ситуации, мне иногда нравится выделять блоки памяти таким образом, когда распределение уже обнулено:

id *argList = calloc(1UL, sizeof(id) * argumentsCount);

Оба из них выделяют кусок памяти, способный содержать argumentsCount количество указателей на объекты. Вы можете получить доступ к отдельным указателям, например, так:

argList[0] = [[NSString alloc] initWithUTF8String:argv[0]];
argList[1] = [[NSString alloc] initWithUTF8String:argv[1]];
NSLog(@"Argument 0 is: %@", argList[0]);

Когда вы объявляете argList как указатель на тип char, как вы делали в своем примере, индексируя отдельные элементы (т. Е. argList[0], argList[1]), получите доступ к отдельным байтам памяти, выделенной для argList, а не отдельные указатели, как вы, вероятно, ожидаете. Когда вы объявляете argList как id, как я делал выше, индексация отдельных элементов проходит через память, выделенную для argList на sizeof(id) байт. Компилятор автоматически компенсирует правильный размер указателя для целевой архитектуры.

Предполагая, что указатель, возвращаемый malloc(), равен 0x1000, вот таблица адресов, которые будут рассчитаны для 32- и 64-битного режима для объявлений char * и id *:

    32-bit: char *  id *     64-bit: char *  id *
argList[0]: 0x1000  0x1000           0x1000  0x1000
argList[1]: 0x1001  0x1004           0x1001  0x1008

Понятия не имею, почему это работало для вас в 32-битном режиме.

0 голосов
/ 08 октября 2009

Почему вы храните идентификаторы в массиве C вместо одного из классов коллекций, доступных в Foundation?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...