2013-02-25 3 views
4

Я компилирую проект под VS2012 и GCC (CodeBlocks) для Windows. На VS2012 все работает отлично. Под НКУ я получить следующее сообщение об ошибке компиляции:GCC- Недопустимое использование регистра

C:\Users\Piotrek\AppData\Local\Temp\ccfdl0Ye.s|164|Error: invalid use of register| 
C:\Users\Piotrek\AppData\Local\Temp\ccfdl0Ye.s|166|Error: invalid use of register| 
C:\Users\Piotrek\AppData\Local\Temp\ccfdl0Ye.s|221|Error: invalid use of register| 
||=== Build finished: 3 errors, 14 warnings (0 minutes, 0 seconds) ===| 

Я с помощью опции компилятора -fpermissive - Он не должен иметь ничего общего с ошибкой.

Я просто не понимаю, почему он указывает на временный файл в папке Local Temp и говорит, что я использую неправильный регистр?

Есть ли у кого-нибудь идеи о том, что происходит?

+0

GCC на самом деле не одна программа, это набор программ, которые запускаются один за другим.Сначала есть препроцессор, тогда есть реальный компилятор, компилятор генерирует ассемблерный код, который подается на ассемблер, который генерирует объектные файлы, используемые компоновщиком для создания окончательного исполняемого файла. Файл, упомянутый в сообщении об ошибке, является сгенерированным файлом ассемблера. Хотя это не сильно помогает вашей проблеме, я надеюсь, что это объясняет, почему у вас есть эти временные файлы. –

+0

@JoachimPileborg: Выглядит больше как ошибка компилятора для меня. Предупреждения указывают * потенциальные * семантические ошибки, но если ошибка генерируется ассемблером, это, вероятно, указывает на недостаток в компиляторе. –

+4

Моя вторая лучшая ставка заключается в том, что есть несоответствие в флагах, предоставляемых ассемблеру и компилятору - это один код генерации, например. для SSE, и каждый ожидает устаревший набор инструкций x86. Лучше всего, чтобы код содержал asm-директиву, которая является VS2012 в синтаксисе Intel, а gcc ожидает AT & T. asm-директивы передаются как «как». –

ответ

4

Похоже, вы столкнулись с ошибкой в ​​компиляторе. Сообщения об ошибках (судя по имени файла источника) от ассемблера. Единственный раз, когда ассемблер должен генерировать сообщение об ошибке , - это когда в ассемблере есть что-то незаконное, а компилятор C++ должен никогда сгенерировать незаконный ассемблер; если он не может генерировать законный ассемблер, он должен вывести сообщение об ошибке и сбой.

Настоящая проблема, когда вы получаете этот вид сообщения, находится в , выяснить, что в вашем коде запускает его. g ++ имеет параметр , который сообщает ему, чтобы он не удалял ни один из промежуточных файлов . Используйте это, а затем попытайтесь посмотреть, что происходит в файлах сообщества в этих строках. (Когда вы запрашиваете g ++ для вывода ассемблера , он добавляет приятные комментарии, чтобы помочь найти нужный источник .Я не знаю, будет ли это делать, когда генерирует ассемблер в качестве промежуточного файла.) И затем попробуйте режущий код (если хуже ухудшается, используя двоичный поиск) , пока вы не получите ошибку для программы из одной или двух строк. Попытайтесь угадать, что особенного в них, и измените их, чтобы сделать то же самое, по-другому.

И не забудьте сообщить об ошибке в g ++.

+1

Правильно, если только не используется какая-то фанковая встроенная сборка (там программист может написать любой ненужный мусор). – vonbrand

+0

James Kanze, вот и все, я решил это, используя вашу рекомендацию. Я отправлю решение ASAP – filipehd

+0

James Kanze, пожалуйста, взгляните на мой ответ, возможно, вы знаете ответ на второй вопрос. благодаря – filipehd

0

Благодаря рекомендации Джеймса Канзе я решил рассказать компилятору не удалять временные файлы. Это делается с помощью флага:

-save-temps

Как сказал Джеймс, ассемблер генерирует некоторые хорошие комментарии, которые сообщают, какие именно линии на нашем коде C++ бросает ошибку. В моем случае, похоже, что он не принимает такую ​​инструкцию:

asm 
(
    ".intel_syntax noprefix\n" 
    "lock dec [DWORD PTR eax]\n" 
    ".att_syntax \n" 
    : 
    : "a" (data) 
    : 
); 

Я не знаю, почему он больше не принимает Intel синтаксис, так как он работал с предыдущей версией GCC, и теперь, когда я обновил его это уже не так.

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

О проблеме синтаксиса INTEL, любая идея, почему она больше не работает?