У меня странный. Я работаю над встроенной системой, используя файлы заголовков поставщиков. Я компилирую файлы, используя GCC 4.6.3. Я хочу использовать C ++ для своего кода, у меня есть ошибка, которую я не могу понять. Я запускаю пример программы поставщика, и все, что я сделал, это изменил имя файла main.c на main.cpp. В результате, я предполагаю, что заголовочные файлы интерпретируются компилятором C ++. Одна из них содержит следующие строки:
__attribute__((naked)) static return_type signature \
{ \
__asm( \
"svc %0\n" \
"bx r14" : : "I" (number) : "r0" \
); \
}
Файлы компилируются должным образом, если имя файла main.c, я предполагаю, что это потому, что файл обрабатывается компилятором C. Я получаю ошибку, если использую C ++,
error: impossible constraint in 'asm'
Но опять же, у меня нет проблем с компилятором C. Мне нужно вызвать функции, которые используют это определение в файлах C ++. Я рассмотрел написание функций-оболочек, которые остаются на стороне c, и ссылки на них, но это было бы настоящей болью и менее эффективным. Какие-либо предложения?
svc
также известен как swi
это ARM / Thumb программное прерывание инструкция. Требуются только константы, но они отличаются от других констант регистров. То есть, mov r0, #4096
, Вам нужно использовать препроцессор и вставку токена, если вы хотите указать немедленное. number
не может быть переменная или же регистр.
#define syscall(number) __attribute__((naked)) static return_type signature \
{ \
__asm( \
"svc " #number "\n" \
"bx r14" : : : "r0" \
); \
}
буду работать. Замечания: #
это ‘C’ препроцессоры преобразуются. Также обратите внимание, что неэффективно смотреть на SVC
номер, как это в I-CACHE
и проверка требует D-CACHE
, Как правило, это всегда constant
и функция номер передается в регистр для более быстрых системных вызовов.
Руководство GCC говорит,
‘Я’— Целое число, допустимое в качестве непосредственного операнда в данных
инструкция по обработке. То есть целое число в диапазоне 0
до 255 повернуты кратно 2
Это типично для Операнды обработки данных — немедленные, раздел A5.1.3 ARM ARM. SVC
операнды либо фиксированные 8-битные в режиме большого пальца, либо фиксированные 24-битные в режиме ARM. Это может быть возможно с некоторым другим ограничением, о котором я не знаю, но, по крайней мере, строковое преобразование препроцессора будет работать, пока числовая константа передается макросу.
Я думаю, повезло, что это сработало gcc
и не повезло, что g++
не. Вы можете получить дальнейшее понимание, используя -S
и просматривая (и публикуя) вывод, используя оба инструмента.
Редактировать: Ваш код, кажется, работает с gcc-4.7.2
, но number
это const int
местный в моем случае, использование number
возможно проблема. Возможно, у него есть тонкое семантическое изменение с «C» на «C ++».
Проверить Руководство GCC (встроенный ассемблер) для точного значения ограничений для вашей машины. Старые версии GCC были заведомо неаккуратными в проверке ограничений, возможно, вас это укусило. Странно что gcc
а также g++
(та же версия?) обрабатывать код по-разному, это просто может быть быть ошибкой компилятора, но я бы посчитал это только после того, как все остальные объяснения были исчерпаны.