2014-02-21 2 views
0

У меня есть связующая ошибка, которую я думаю, что не должно быть: (.. Я изменил только пробельные, так что можно прочитать более легко я также сделал некоторые anonimization с большой осторожностью)C++ ссылки ошибка

koala.o: 
    In function `ns1::utils::io::protocol::InputSequenceFile 
    < 
     ns1::utils::io::protocol::TargetSequenceProtocol< 
     ns1::utils::io::FooIndexTarget 
     > 
     , false 
    >::InputSequenceFile(ns1::utils::io::DataFileDescriptor const&) [clone .constprop.1291]': 
koala.cpp:(.text+0x332a): 
    undefined reference to 
    `ns1::utils::io::DataFileFactory::createIndexedInputFile 
    (
     ns1::utils::io::DataFileDescriptor const&, ns1::utils::io::IndexMode::Enum, bool 
    )' 

Тогда я использовал nm чтобы открыть дело о символах:

nm other.o: 
0000000000008f20 t _ZN4ns15utils2io15DataFileFactory22createIndexedInputFileERKNS1_18DataFileDescriptorENS1_9IndexMode4EnumEb.constprop.1677 

nm koala.o: 
       U _ZN4ns15utils2io15DataFileFactory22createIndexedInputFileERKNS1_18DataFileDescriptorENS1_9IndexMode4EnumEb 

(grepped выходы)

Они одинаковы, не считая constprop.1677 (что я не знаю, что это такое). Этот метод является статическим методом класса. Мне нужна помощь, чтобы понять основную причину проблемы.

+0

Вы забыли связать с файлом библиотеки/объекта? –

+0

Не думаю. 'man nm':" t ": Символ находится в разделе текста (кода). 'man nm':" U "Символ не определен. Поэтому у меня есть 't' для того, что требуется' U', за исключением 'constprop.1677', которая не является чем-то, что я когда-либо писал. – Notinlist

+0

Какова ваша командная строка? – mockinterface

ответ

2

Коммутатор -O3 для gcc включает -fipa-cp-clone по умолчанию, добавьте -fno-ipa-cp-clone в командную строку для отключения.

Коммутатор обеспечивает соответствующую оптимизацию в управлении и анализ потока потока в компиляторе, который вводит свернутые клонированные версии функций, которые могут быть показаны как имеющие постоянное значение, а в скомпилированных объектах эти клоны могут быть идентифицированы с помощью .constprop суффикс.


фон

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

Wegman, Mark N; Zadeck Ф. Кеннет (апрель 1991), "постоянная распространения условных переходов", ACM Сделки по языкам программирования и систем 13 (2): 181-210

Вот конкретный пример:

int foo (int x, int y) { 
    if (y == 0) return 0; 
    return foo (x, --y) % 2; 
} 

int main() { 
    int z = 0; 
    for (int i = 0; i < 6; i++) {  
     z = z + foo (1, i); 
    } 
} 

// g++-4.8 -c -O2 -fipa-cp-clone main.cpp && nm main.o 
0000000000000030 T _Z3fooii 
0000000000000000 t _Z3fooii.constprop.0 
0000000000000000 T main 

Вы можете заметить, что с помощью -fipa-cp-clone компилятор идентифицирует, что существует постоянная, передаваемая внешнему виду foo(), и подготавливает для оптимизации путем клонирования функции.

(See live here)

+1

Так что «-fno-ipa-cp-clone» в командной строке сборки исправляет проблему, но почему это происходит в первую очередь? Почему GCC не может связать свой собственный результат в этом случае? –

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