2016-12-18 8 views
0

Я пытаюсь написать программу на C++, которая выполняется на кластере машин, и все машины разговаривают друг с другом через сокеты TCP. Программа случайно срабатывает на одной из машин. Я сделал анализ core-dump с gdb. Ниже приведены результаты:Отладка C++: завершена с помощью SIGABRT

$ gdb executable dump 

    Core was generated by `/home/user/experiments/files/executable 2 /home/user/'. 
    Program terminated with signal SIGABRT, Aborted. 
    0 0x00007fb76a084c37 in __GI_raise ([email protected]=6) at ../nptl/sysdeps/unix/sysv/linux/raise.c:56 
    56 ../nptl/sysdeps/unix/sysv/linux/raise.c: No such file or directory. 

    (gdb) backtrace 
    0 0x00007fb76a084c37 in __GI_raise ([email protected]=6) at ../nptl/sysdeps/unix/sysv/linux/raise.c:56 
    1 0x00007fb76a088028 in __GI_abort() at abort.c:89 
    2 0x00007fb76a0c12a4 in __libc_message ([email protected]=2, [email protected]=0x7fb76a1cd113 "*** %s ***: %s terminated\n") at ../sysdeps/posix/libc_fatal.c:175 
    3 0x00007fb76a158bbc in __GI___fortify_fail (msg=<optimized out>, [email protected]=0x7fb76a1cd0aa "buffer overflow detected") at fortify_fail.c:38 
    4 0x00007fb76a157a90 in __GI___chk_fail() at chk_fail.c:28 
    5 0x00007fb76a158b07 in __fdelt_chk (d=<optimized out>) at fdelt_chk.c:25 
    6 0x000000000040a918 in LocalSenderPort::run()() 
    7 0x000000000040ae70 in LocalSenderPort::LocalSenderPort(unsigned int, std::string, std::vector<std::string, std::allocator<std::string> >, char*)() 
    8 0x00000000004033d5 in main() 

Любые предложения по поводу того, что я должен смотреть? Как мне продолжить? Любая помощь действительно ценится.

Я не использую код прямо сейчас, так как его большой код распространяется через файлы. Но я могу поделиться, если потребуется.

+0

Предполагая, что вы используете G ++/Clang, передайте параметр '-g' компилятору. Это будет генерировать информацию об отладочной информации и должно позволить вам видеть строки кода, в которых произошел сбой из-за gdb. – tambre

+0

@tambre Я добавил -g во время компиляции. И это показывает следующее: # 0 0x00007fb76a084c37 в __GI_raise (sig = sig @ entry = 6) at ../nptl/sysdeps/unix/sysv/linux/raise.c:56 – PHcoDer

+1

Даже не пытайтесь опубликовать трассировку стека в комментарии. Вместо этого отредактируйте новую (и полезную) трассировку стека в вопросе. Хотя трассировка стека, указывающая местоположение в вашем собственном коде, обычно должна быть достаточной для самостоятельного отладки остальных. – tambre

ответ

2

Эта ошибка: __fdelt_chk (d=<optimized out>) at fdelt_chk.c:25 что ваша программа нарушает предварительные условия одного из макросов FD_*.

Источник fdelt_chk довольно прост, и есть только два условия, при которых он терпит неудачу: вы передаете отрицательный дескриптор файла, или передать в файле дескриптора больше, чем 1023.

В этот день и возраст , используя select и/или FD_SET в любой программе, которая может иметь более 1024 одновременных подключений (что легко разрешает Linux) может только закончиться слезами. Вместо этого используйте epoll.

+0

Спасибо за ответ. Проблема была в том же духе. Но это не с выбором. function socket возвращает -1, когда уже вернул 1023 сокета. И все они еще живы. Как я могу увеличить допустимое количество всех живых гнезд за раз? – PHcoDer

+0

Если 'socket' возвращает ошибку, это вероятно, потому что вы используете лимит на общее количество файловых дескрипторов (' man setrlimit' или 'man ulimit'). ** Примечание: ** если вы увеличиваете этот предел * и * используете макросы 'select' или' FD_ * ', вы сразу же столкнетесь с проблемой в моем ответе. –

+0

Спасибо. Да, это правильно, теперь я в проблеме, упомянутой в вашем ответе. Пойдем с epoll сейчас. – PHcoDer