Пишу, по большей части, про историю, свою жизнь и немного про программирование.

Век живи, век учись, от нехватки памяти умрёшь

Наступил недавно на отличные питонячьи грабли. Хорошие такие, массивные, со специальными шипами на рукоятке.

Есть модуль, внутри него происходит fork — внутри потомка изолируется libmapi, у которой нещадно течёт память. Модуль используется внутри программы, которая перехватывает все exceptions (!). Знаю, что это неправильно, но она это делает в режиме отладки, для отладки и используется.

Загвоздка в том, что процесс-потомок выходил при помощи sys.exit. Если вы уже знаете в чём проблема, можете начинать хохотать. Я не знал и убил тестовую машину — кончилась память. Ваня Сагалаев тоже не знал.

sys.exit пораждает иключение и выходит с его помощью. Если где-то это исключение блокируется, то потомок, натурально, не может умереть. Решение простое — выходить надо по os._exit.

4 комментария
gaius-julius.livejournal.com 2009

Хохотал. Я тоже использовал такой способ отладки — «хватай все эксепшены, а там разберёмся». На том и погорел.

Евгений Степанищев (bolknote.ru) 2009

Комментарий для gaius-julius.livejournal.com:

А я-то гадал — кто положил машину, возмущался :)

isagalaev (softwaremaniacs.org/about/) 2009

Вообще, «используется для отладки» -​-​ это не оправдание для съедающего «except Exception:». Правильное поведение при этом -​-​ слогить exception и *прокинуть его дальше* с помощью «raise».

Евгений Степанищев (bolknote.ru) 2009

Комментарий для softwaremaniacs.org/about/:

Да бог с этим всем уже :) Главное, что мы все получили экспов. Лично я это люблю. :) А то я так бы и не поглядел никогда что за зверь _exit и не знал бы, что выходить из чайлдов при помощи sys.exit — неправильно.