Запуск dnsmasq в качестве прокси DHCP из контейнера

Я пытаюсь настроить dnsmasq для работы в режиме DHCP-прокси, предоставляя клиентам информацию о загрузке сети PXE, в то время как мой маршрутизатор продолжает действовать как DHCP-сервер.

В идеале я бы хотел запустить dnsmasq в контейнере Docker.

Сначала я попытался настроить его на виртуальной машине VMware под управлением Linux, например:

# Verbose DHCP logging
log-dhcp

# Disable DNS
port=0

# Enable TFTP
enable-tftp
tftp-root=/tftproot

# Answer DHCP discovery requests coming in over the virtual machine
dhcp-range=172.0.0.0,proxy,255.0.0.0

dhcp-vendorclass=set:bios,PXEClient:Arch:00000
pxe-service=tag:bios,x86PC,"Netboot",netboot.xyz.kpxe,172.16.80.2

Я запустил другую виртуальную машину VMware и настроил ее на загрузку из сети. После долгого ожидания он начинает настройку через DHCP и успешно загружается. Это результат работы dnsmasq:

dnsmasq-dhcp: 705858459 available DHCP subnet: 172.0.0.0/255.0.0.0
dnsmasq-dhcp: 705858459 vendor class: PXEClient:Arch:00000:UNDI:002001
dnsmasq-dhcp: 705858459 PXE(ens33) 00:0c:29:12:8b:9b proxy
dnsmasq-dhcp: 705858459 tags: bios, ens33
dnsmasq-dhcp: 705858459 broadcast response
dnsmasq-dhcp: 705858459 sent size:  1 option: 53 message-type  2
dnsmasq-dhcp: 705858459 sent size:  4 option: 54 server-identifier  172.16.80.2
dnsmasq-dhcp: 705858459 sent size:  9 option: 60 vendor-class  50:58:45:43:6c:69:65:6e:74
dnsmasq-dhcp: 705858459 sent size: 17 option: 97 client-machine-id  00:56:4d:e4:12:5a:70:00:5b:07:fb:d3:7b:cc...
dnsmasq-dhcp: 705858459 sent size: 31 option: 43 vendor-encap  06:01:03:0a:04:00:50:58:45:08:07:80:00:01...
dnsmasq-dhcp: 705858459 available DHCP subnet: 172.0.0.0/255.0.0.0
dnsmasq-dhcp: 705858459 vendor class: PXEClient:Arch:00000:UNDI:002001
dnsmasq-dhcp: 705858459 available DHCP subnet: 172.0.0.0/255.0.0.0
dnsmasq-dhcp: 705858459 vendor class: PXEClient:Arch:00000:UNDI:002001
dnsmasq-dhcp: 705858459 PXE(ens33) 172.16.80.3 00:0c:29:12:8b:9b netboot.xyz.kpxe
dnsmasq-dhcp: 705858459 tags: bios, ens33
dnsmasq-dhcp: 705858459 bootfile name: netboot.xyz.kpxe
dnsmasq-dhcp: 705858459 next server: 172.16.80.2
dnsmasq-dhcp: 705858459 sent size:  1 option: 53 message-type  5
dnsmasq-dhcp: 705858459 sent size:  4 option: 54 server-identifier  172.16.80.2
dnsmasq-dhcp: 705858459 sent size:  9 option: 60 vendor-class  50:58:45:43:6c:69:65:6e:74
dnsmasq-dhcp: 705858459 sent size: 17 option: 97 client-machine-id  00:56:4d:e4:12:5a:70:00:5b:07:fb:d3:7b:cc...
dnsmasq-dhcp: 705858459 sent size:  7 option: 43 vendor-encap  47:04:80:00:00:00:ff
dnsmasq-tftp: error 0 TFTP Aborted received from 172.16.80.3
dnsmasq-tftp: failed sending /tftproot/netboot.xyz.kpxe to 172.16.80.3
dnsmasq-tftp: sent /tftproot/netboot.xyz.kpxe to 172.16.80.3

Теперь я запускаю то же самое внутри контейнера Docker:

docker run --rm -it \
    --cap-add NET_ADMIN \
    -v /tftproot:/tftproot:ro \
    -v $(pwd)/dnsmasq.conf:/etc/dnsmasq.conf:ro \
    -p 67:67/udp \
    -p 69:69/udp \
    -p 4011:4011/udp \
    andyshinn/dnsmasq:2.81 --no-daemon

Контейнер обнаруживает клиента, выполняющего DHCPDISCOVER , и пытается ответить:

dnsmasq-dhcp: 705858459 available DHCP subnet: 172.0.0.0/255.0.0.0
dnsmasq-dhcp: 705858459 vendor class: PXEClient:Arch:00000:UNDI:002001
dnsmasq-dhcp: 705858459 PXE(eth0) 00:0c:29:12:8b:9b proxy
dnsmasq-dhcp: 705858459 tags: bios, eth0
dnsmasq-dhcp: 705858459 broadcast response
dnsmasq-dhcp: 705858459 sent size:  1 option: 53 message-type  2
dnsmasq-dhcp: 705858459 sent size:  4 option: 54 server-identifier  172.17.0.2
dnsmasq-dhcp: 705858459 sent size:  9 option: 60 vendor-class  50:58:45:43:6c:69:65:6e:74
dnsmasq-dhcp: 705858459 sent size: 17 option: 97 client-machine-id  00:56:4d:e4:12:5a:70:00:5b:07:fb:d3:7b:cc...
dnsmasq-dhcp: 705858459 sent size: 31 option: 43 vendor-encap  06:01:03:0a:04:00:50:58:45:08:07:80:00:01...
[above repeats a few times]

Клиент не подтверждает загрузочную информацию по сети, когда dnsmasq запускается с идентичной конфигурацией внутри Контейнер Docker.

У меня есть две теории:

  1. Пакеты, отправленные клиенту, никогда не попадают туда из-за некоторых особенностей сети Docker.

  2. идентификатор сервера отправляется обратно из dnsmasq имеет IP-адрес интерфейса контейнера Docker, который не является сетевым IP-адресом хоста, на котором запущен контейнер (который должен быть 172.16.80.2).

0
задан 3 October 2020 в 20:13
1 ответ

dnsmasq отвечает клиенту, используя широковещательный пакет UDP на порту 68, который не выходит за пределы сети Docker с мостом, если только не используется --net=host.

Одним из обходных путей является добавление прослушивателя socat в сеть Docker, который перенаправляет на хост:

socat:
  image: alpine/socat
  command: >
    UDP4-LISTEN:68,reuseaddr,fork
    TCP4:172.18.0.1:24000

а затем прослушивает хост и ретранслирует в сеть:

socat \
  TCP4-LISTEN:24000,bind=172.18.0.1,reuseaddr,fork \
  UDP-DATAGRAM:255.255.255.255:68,broadcast

Это даст ответ клиенту, но может быть еще много работы.

0
ответ дан 3 October 2020 в 17:55

Теги

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