Причина различий в выводе на 1 бит между выводом скомпилированного кода C Linux-gcc и скомпилированным выводом MS-VS2008? - PullRequest
0 голосов
/ 09 февраля 2010

У меня есть библиотека видеодекодера Theora и приложение, скомпилированное с использованием VS-2008 для Windows (архитектура Intel x86). Я использую эту настройку для декодирования потоков битов theora (файлы *. Ogg). Исходный код для этой библиотеки декодера используется из исходного пакета FFMPEG v0.5 с некоторыми изменениями, чтобы он компилировался в комбинации windows-VS-2008.

Теперь, когда я декодирую тот же поток битов theora с помощью приложения ffmpeg (V0.5) на linux (архитектура Intel x86), который я создал с помощью gcc, и получаю некоторый декодированный выходной файл yuv, этот выходной файл имеет 1-битные различия с вывод получен из установки windows-VS2008, и это тоже для нескольких байтов выходного файла, а не для всех. Я ожидал, что 2 выхода будут соответствовать битам.

Я сомневаюсь в следующих факторах:

a.) Некоторое несоответствие типов данных между двумя компиляторами gcc и MS-VS2008?

b.) Я убедился, что в коде не используются никакие математические функции библиотеки времени выполнения, такие как log, pow, exp, cos и т. Д., Но все же в моем коде есть некоторые операции, такие как (a + b + c) / 3. Может ли это быть проблемой?

Реализация этого «деления на три» или любого другого числа может отличаться в двух установках.

в.) Какие-то эффекты округления / усечения происходят по-другому?

d.) Могу ли я пропустить какой-либо макрос, присутствующий в Linux как параметр makefile / configure, которого нет в настройке Windows?

Но я не могу сузить проблему и исправить ее.

1.) Являются ли мои сомнения выше обоснованными, или могут быть какие-либо другие проблемы, которые могут вызвать эти 1-битные различия в выходных данных, создаваемых этими двумя различными установками.

2.) Как мне отладить и исправить это?

Полагаю, этот сценарий различий в выходных данных между установкой linux-gcc и компиляторами Windows MS может быть верным даже для любого универсального кода (не обязательно характерного для моего случая с приложением видеодекодера)

Любые указатели были бы полезны в этом отношении.

спасибо,

-AD

Ответы [ 3 ]

1 голос
/ 10 февраля 2010

Я думаю, такое поведение может исходить из математики x87 / sse2. Какую версию GCC вы используете? Вы используете float (32-битный) или двойной (64-битный)? Математика на x87 имеет больше внутренних битов точности (82), чем может храниться в памяти

Попробуйте флаги для gcc -ffloat-store; -msse2 -mfpmath = sse

Флаги для msvc /fp:fast /arch:SSE2

0 голосов
/ 09 февраля 2010

Относительно б), целочисленное деление и деление числа с плавающей запятой полностью определены в C99. C99 определяет округление к нулю для целых чисел (более ранние стандарты оставляли определение направления округления определенным для реализации) и IEEE 754 для плавающей запятой.

Услышав, что VS2008 не претендует на реализацию C99, это не очень помогает. По крайней мере, определение реализации означает, что вы можете написать несколько тестовых примеров и убедиться, какое решение было принято в вашем компиляторе.

Если вы действительно заботитесь об этом, как насчет инструментов для вывода подробных трасс в отдельный файл и проверки трасс на первое различие? Эй, возможно, трассировка уже есть для отладки!

0 голосов
/ 09 февраля 2010

1, возможно, другая оптимизация некоторой плавающей запятой lib

2, это проблема?

редактирование:
Посмотрите на параметр "/ fprecise" на VS (http://msdn.microsoft.com/en-us/library/e7s85ffb.aspx) или "-fprecise-math" на gcc.

...