дамп ядра Python libsvm

У меня есть код Python, который отлично работает в моей среде разработки (Ubuntu 12.04), но сбрасывает ядро ​​​​в моей производственной среде (Linode под управлением CentOS).

*** glibc detected *** python2.7: double free or corruption (out): 0x090cba60 ***
======= Backtrace: =========
/lib/i686/nosegneg/libc.so.6(+0x717b1)[0xb763d7b1]
/lib/i686/nosegneg/libc.so.6(+0x73f01)[0xb763ff01]
/home/michael/libsvm-3.16/python/../libsvm.so.2(svm_free_model_content+0xe2)[0xb6e0c6b2]
/home/michael/libsvm-3.16/python/../libsvm.so.2(svm_free_and_destroy_model+0x2c)[0xb6e0c70c]
/home/michael/lib/python2.7/lib-dynload/_ctypes.so(ffi_call_SYSV+0x17)[0xb71e375f]
/home/michael/lib/python2.7/lib-dynload/_ctypes.so(ffi_call+0x5b)[0xb71e35ab]
/home/michael/lib/python2.7/lib-dynload/_ctypes.so(_ctypes_callproc+0x32d)[0xb71d82ad]
/home/michael/lib/python2.7/lib-dynload/_ctypes.so(+0x703e)[0xb71d003e]
python2.7(PyObject_Call+0x4a)[0x805d90a]
python2.7(PyEval_EvalFrameEx+0x3c0a)[0x80e04ba]
python2.7(PyEval_EvalCodeEx+0x7bb)[0x80e2c1b]
python2.7[0x813ee2a]
python2.7(PyObject_Call+0x4a)[0x805d90a]
python2.7[0x80657f1]
python2.7(PyObject_Call+0x4a)[0x805d90a]
python2.7(PyEval_CallObjectWithKeywords+0x42)[0x80db852]
python2.7[0x80af616]
python2.7[0x80a928e]
python2.7[0x808e024]
python2.7[0x8067c5b]
python2.7[0x808c079]
python2.7(PyDict_SetItem+0x87)[0x808cfa7]
python2.7(_PyModule_Clear+0x123)[0x8090693]
python2.7(PyImport_Cleanup+0x175)[0x80f2ca5]
python2.7(Py_Finalize+0x10c)[0x80ffacc]
python2.7(Py_Main+0x53d)[0x8058c1d]
python2.7(main+0x1b)[0x805839b]
/lib/i686/nosegneg/libc.so.6(__libc_start_main+0xe6)[0xb75e2ce6]
python2.7[0x80582e1]
======= Memory map: ========
08048000-0817d000 r-xp 00000000 ca:00 430104     /home/michael/bin/python2.7
0817d000-081ab000 rw-p 00134000 ca:00 430104     /home/michael/bin/python2.7
081ab000-081b4000 rw-p 00000000 00:00 0
...

Бывает часто, но не постоянно. Кроме того, если я удаляю файлы *.pyc в подкаталоге libsvm, то, похоже, он работает без сбоев, но после регенерации файлов *.pyc (после первого запуска) он имеет тенденцию снова сбрасывать ядро.

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

Некоторая информация, которая может иметь значение:

  • Это начало происходить только тогда, когда я установил Python 2.7. Этого не было с Python 2.6.
  • Python2.7 установлен в мой домашний каталог (из исходного кода, так как для CentOS нет пакетов python2.7)

Как мне подойти к этой проблеме? Где скорее всего проблема? Это в исходнике libsvm или в оболочке Python? Я почти уверен, что этого нет в моем исходном коде Python, так как я не смогу так сломать интерпретатор.

ИЗМЕНИТЬ

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

Заголовок diff первая модель:

4,7c4,7
< total_sv 8858
< rho -0.500251 -0.215012 2.99972 -0.00159202 0.000223509 1.00003
< label 3 2 1 0
< nr_sv 549 6095 587 1627
---
> total_sv 8782
> rho -2.99981 0.000329574 -1.00015 -0.335094 -0.999424 -0.66958
> label 0 3 2 1
> nr_sv 1586 535 6083 578
-bash-4.1$ diff model.svm model2.svm | head -n 20
4,7c4,7
< total_sv 8858
< rho -0.500251 -0.215012 2.99972 -0.00159202 0.000223509 1.00003
< label 3 2 1 0
< nr_sv 549 6095 587 1627

Заголовок diff вторая модель:

4,7c4,7
< total_sv 116
< rho 2.30068 -0.145028 0.169511 -1.09344 0.723723 -0.865381
< label 3 0 2 1
< nr_sv 18 32 34 32
---
> total_sv 132
> rho 0.72381 -2.00473 -0.220492 -0.962109 0.998243 -0.14499
> label 0 1 3 2
> nr_sv 43 35 18 36

person mpenkov    schedule 14.03.2013    source источник
comment
Это действительно странный сбой, потому что, если вы посмотрите на функцию svm_free_model_content в libsvm, вы увидите, что у нее есть два охранника: if(model_ptr->free_sv && model_ptr->l > 0 && model_ptr->SV != NULL) и if(model_ptr->sv_coef), что наводит меня на мысль, что на самом деле у вас есть несогласованный svm_model, который передается этой функции, что не NULL, потому что svm_free_and_destroy_model проверяет такие вещи. Получаете ли вы ожидаемые прогнозы до крушения или, может быть, крушения в другом месте?   -  person Mihai Todor    schedule 14.03.2013
comment
Кроме того, происходит ли этот сбой при обучении моделей или при попытке вычислить прогнозы?   -  person Mihai Todor    schedule 14.03.2013
comment
Спасибо за ваши Коментарии. Чтобы ответить на ваши вопросы: это происходит только тогда, когда я вычисляю прогнозы. Я получаю ожидаемые прогнозы до крушения.   -  person mpenkov    schedule 14.03.2013
comment
В таком случае, не могли бы вы поделиться образцом файла модели?   -  person Mihai Todor    schedule 14.03.2013
comment
Я думаю, что нашел проблему. У меня установлена ​​libsvm 3.1 на моей машине разработки, а libsvm 3.16 установлена ​​в производственной среде. Я использовал модели, обученные в среде разработки. Если я переобучу модели в производственной среде, сбой больше не произойдет. Спасибо за ваши предложения (упоминание непоследовательной svm_model поставило меня на правильный путь).   -  person mpenkov    schedule 14.03.2013
comment
О, ну, это имеет смысл. Должно быть, они что-то изменили в формате файла модели. Я рад, что помог вам решить эту проблему :)   -  person Mihai Todor    schedule 15.03.2013
comment
Кстати, не могли бы вы сравнить заголовки файла модели, созданного libsvm 3.1, и файла, созданного libsvm 3.16 для вашей конкретной установки, и опубликовать его в качестве ответа? Кому-то это может пригодиться :)   -  person Mihai Todor    schedule 15.03.2013
comment
Готово. Хотя особой разницы не вижу...   -  person mpenkov    schedule 16.03.2013
comment
Это происходит снова. Я воспроизвел его в своей среде разработки, установив libsvm 3.16. Я запустил отладочную сборку. Вы все еще заинтересованы в изучении этого? Я могу поделиться моделями и оскорбительным кодом Python.   -  person mpenkov    schedule 17.03.2013


Ответы (1)


Причиной ошибки является неинициализированный указатель в svm_load_model и непроверенный вызов free. Вот патч:

misha@misha-diginnos:~$ diff libsvm-3.16/svm.cpp.original libsvm-3.16/svm.cpp -p
*** libsvm-3.16/svm.cpp.original        2013-03-17 17:34:00.235661297 +0900
--- libsvm-3.16/svm.cpp 2013-03-17 17:39:29.677294903 +0900
*************** svm_model *svm_load_model(const char *mo
*** 2747,2752 ****
--- 2747,2753 ----
        model->probB = NULL;
        model->label = NULL;
        model->nSV = NULL;
+     model->sv_indices = NULL;

        char cmd[81];
        while(1)
*************** void svm_free_model_content(svm_model* m
*** 2973,2980 ****
        free(model_ptr->probB);
        model_ptr->probB= NULL;

!       free(model_ptr->sv_indices);
!       model_ptr->sv_indices = NULL;

        free(model_ptr->nSV);
        model_ptr->nSV = NULL;
--- 2974,2984 ----
        free(model_ptr->probB);
        model_ptr->probB= NULL;

!     if (model_ptr->sv_indices)
!     {
!         free(model_ptr->sv_indices);
!         model_ptr->sv_indices = NULL;
!     }

        free(model_ptr->nSV);
        model_ptr->nSV = NULL;

Я уведомил авторов. Они знают о проблеме и решат ее в следующей версии.

person mpenkov    schedule 17.03.2013
comment
Что ж, я рад, что авторам библиотеки удалось вам помочь. Прошла целая вечность, когда я попросил их о помощи. К сожалению, libsvm поддерживается исследователями, у которых мало опыта работы с производственным кодом. - person Mihai Todor; 17.03.2013
comment
Они делают относительно хорошую работу, на мой взгляд. Мое единственное желание состоит в том, чтобы они могли быть еще более открытыми со своим исходным кодом, например, делиться им в виде репозитория git на github.com. Если бы они поделились своей веткой разработки, подобные проблемы не причиняли бы столько боли. - person mpenkov; 17.03.2013