Определите другой конец соединения сокета домена unix

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

lsof предоставляет мне следующую информацию:

dbus-daem  4175  mvg   10u  unix 0xffff8803e256d9c0      0t0  12828 @/tmp/dbus-LyGToFzlcG

Итак, я знаю какой-то адрес («адрес ядра»?), я знаю какой-то номер сокета и я знаю путь. Я могу найти ту же информацию в других местах:

$ netstat -n | grep 12828
unix  3      [ ]         STREAM     CONNECTED     12828    @/tmp/dbus-LyGToFzlcG
$ grep -E '12828|ffff8803e256d9c0' /proc/net/unix
ffff8803e256d9c0: 00000003 00000000 00000000 0001 03 12828 @/tmp/dbus-LyGToFzlcG
$ ls -l /proc/*/fd/* 2>/dev/null | grep 12828
lrwx------ 1 mvg users 64 10. Aug 09:08 /proc/4175/fd/10 -> socket:[12828]

Однако ничто из этого не говорит мне, каков другой конец моего подключения к сокету. Как я могу определить, какой процесс держит другой конец?


person MvG    schedule 10.08.2012    source источник
comment
Вы можете задать этот вопрос на Unix и Linux Stack Exchange.   -  person derobert    schedule 10.08.2012


Ответы (2)


Обновление: уже некоторое время это можно сделать с помощью реальных интерфейсов. Начиная с Linux 3.3, функция UNIX_DIAG предоставляет API на основе netlink для этой информации, а lsof 4.89 и более поздние версии поддерживают ее. См. https://unix.stackexchange.com/a/190606/1820 для получения дополнительной информации.

person SamB    schedule 27.10.2016

Подобные вопросы задавались при сбое сервера и Unix и Linux. Принятый ответ заключается в том, что эта информация недоступна для пользовательского пространства в Linux.

Распространенным предложением является просмотр соседних номеров сокетов, но ls -l /proc/*/fd/* 2>/dev/null | grep 1282[79] здесь ничего не дало. Возможно, можно использовать соседние строки в выводе netstat. Похоже, что существовал шаблон соединений с соответствующим именем сокета и без него. Но хотелось бы какой-то определенности, а не только догадок.

Один ответ предлагает инструмент, который, по-видимому, может решить эту проблему, копаясь в структурах ядра. Использование этой опции требует отладочной информации для ядра, сгенерированной опцией CONFIG_DEBUG_INFO и предоставленной в виде отдельного пакета некоторыми дистрибутивами. Основываясь на этом ответе, используя адрес, предоставленный lsof, у меня сработало следующее решение:

# gdb /usr/src/linux/vmlinux /proc/kcore
(gdb) p ((struct unix_sock*)0xffff8803e256d9c0)->peer

Это напечатает адрес другого конца соединения. Grepping lsof -U для этого номера предоставит такие подробности, как идентификатор процесса и номер дескриптора файла.

Если отладочная информация недоступна, может получить доступ к требуемой информации, зная смещение равноправного члена в структуре unix_sock. В моем случае в Linux 3.5.0 для x86_64 следующий код можно использовать для вычисления того же адреса, не полагаясь на символы отладки:

(gdb) p ((void**)0xffff8803e256d9c0)[0x52]

Я не буду давать никаких гарантий относительно портативности этого решения.

person MvG    schedule 10.08.2012
comment
Возможно, это решение может быть преобразовано в модуль ядра (или инструмент), компилируемый с помощью заголовков или исходных кодов ядра, соответствующих загруженному ядру... - person imz -- Ivan Zakharyaschev; 16.08.2012
comment
Что ж, для Linux были отправлены исправления, раскрывающие эту информацию, но они не были объединены... -- reddit.com/r/linux/comments/ikizs/ - person imz -- Ivan Zakharyaschev; 16.08.2012