D -Шина в Ubuntu внутри контейнера Docker

/proc/[pid]/memпозволяет получить доступ к виртуальной памяти процесса.

Смещения в этом файле соответствуют виртуальным адресам. /proc/[pid]/mapsговорит вам, какие диапазоны адресов поддерживаются фактической памятью (и где сама память поддерживается файлами ).

Все это задокументировано на странице proc (5 ).

Процесс может обращаться к памяти только тех процессов, которые запущены под тем же пользователем, что и он сам, и которые не имеют setgid/uid. Раньше было так, что вам нужно было ptrace()процесса, чтобы получить доступ к его памяти через /proc/[pid]/mem, но это НЕ ВЕРНО уже довольно давно (more именно, поскольку этот коммит от января 2012 года (v3.2+ ), целью которого было исправление ошибки безопасности, также отредактированный в статье lwn ).

Практический пример

В окне терминала:

% echo $$ # show our pid
6744
% read -sp 'secret pasword: '; echo
secret pasword:
%

Затем в другом окне терминала:

% grep heap /proc/6744/maps
01bb7000-01c3e000 rw-p 00000000 00:00 0                                  [heap]
% dd if=/proc/6744/mem bs=1 skip=$((0x01bb7000)) count=$((0x01c3e000-0x01bb7000)) status=none |
    strings | less
...
% dd if=/proc/6744/mem bs=1 skip=$((0x01bb7000)) count=$((0x01c3e000-0x01bb7000)) status=none |
    strings | grep qwerty
qwertyuiop # here is the "secret password"

Люди обычно используют отладчик, подобный gdb, чтобы заглянуть в память запущенного процесса вместо элементарных способов, подобных этому (отладчик знает формат структур, используемых процессом, может отслеживать указатели, списки и т. д. ), но принцип в основном тот же.

Последние ядра Linux также имеют более приятный интерфейс вместо /proc/[pid]/mem, напримерprocess_vm_readv. Так же, как с /proc/[pid]/memили PTRACE_PEEKи т. д., вам нужен root -как привилегии (CAP_SYS_PTRACE), чтобы прочитать память процесса, которым вы не владеете.

0
27.04.2021, 10:26
1 ответ

Я сам нашел решение:

В моем Dockerfile я устанавливаю пакет dbus, но ничего не связанного с X11. Я также устанавливаю все зависимости своего программного обеспечения, в том числе те, которые относятся к скрипту Python, которым я поделился в вопросе.

В моем Dockerfile есть следующие строки:

COPY start.sh /usr/local/bin
RUN chmod +x /usr/local/bin/start.sh
ENTRYPOINT ["/bin/bash", "/usr/local/bin/start.sh"]

Содержимое файла start.sh таково:

#!/usr/bin/env bash

export DBUS_SESSION_BUS_ADDRESS=`dbus-daemon --fork --config-file=/usr/share/dbus-1/session.conf --print-address`

exec bash

Таким образом, запуск контейнера дает мне оболочку с правильно установленным DBUS _SESSION _BUS _ADDRESS. Я могу запустить фон тестового сценария и сказать

dbus-send --print-reply --session --dest=com.testservice /testservice com.testservice.Exit

убить его.

1
29.04.2021, 07:26

Теги

Похожие вопросы