Port-Forward для всех IP на интерфейсе

Я использую веб-сервер на основе Java как непривилегированный пользователь. Поэтому он прослушивает порты 8080 и 8443 вместо 80 и 443.

Прямо сейчас я использую следующее pf правила для внутренней переадресации портов:

rdr pass on $ext_if proto tcp from any to $ext_ip port 80 -> $ext_ip port 8080
rdr pass on $ext_if proto tcp from any to $ext_ip port 443 -> $ext_ip port 8443

(с макросами, определенными для $ext_if а также $ext_ipочевидно)

Теперь я хочу добавить больше IP-адресов в интерфейс (для SSL vHosts) - как лучше всего это сделать? Нужно ли повторять эти правила для каждого добавленного IP? Или я могу как-то сделать правило для "каждого IP на этом интерфейсе"?

РЕДАКТИРОВАТЬ: К сожалению, IP-адреса не из одной подсети. Я попытался перечислить их в $ext_ip макрос, но я все еще предпочел бы решение, где мне не нужно явно добавлять каждый IP.

Спасибо!

3 ответа

Мои исследования показывают, что нет pf.conf пункт, который даст вам этот уровень однозначного расширения правил.

Я надеялся, что вы могли бы сделать это с макросами, которые в вашем случае были бы что-то вроде:

vhost_ips = "{ 198.51.100.4, 198.51.100.5 }"
rdr pass on $ext_if proto tcp from any to $vhost_ips port 80  -> $ext_ip port 8080
rdr pass on $ext_if proto tcp from any to $vhost_ips port 443 -> $ext_ip port 8443

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

rdr pass on int0 proto tcp from any to 198.51.100.4 port 80  -> { 198.51.100.4, 198.51.100.5 } port 8080 round-robin
rdr pass on int0 proto tcp from any to 198.51.100.5 port 443 -> { 198.51.100.4, 198.51.100.5 } port 8443 round-robin

... что я уверен, что это не то, что вы хотели.:-) Таблицы также, кажется, отсутствуют. Страница руководства прямо говорит:

"Таблицы могут также использоваться для адреса перенаправления правил nat и rdr и в параметрах маршрутизации правил фильтрации, но только для циклических пулов".

Так что, к сожалению, похоже, что ваш единственный вариант - вручную поддерживать список или создать его в виде отдельного файла и включить его.

Также, к сожалению, include пункт не упоминается в pf.conf man-страницы в моих системах 7.4, 8.2 или 9.0-RC2, поэтому, если вы работаете со стандартной PF, поставляемой с FreeBSD, я считаю, что они работают с PF, импортированным из OpenBSD 4.5, которая, похоже, не поддерживает include... но на всякий случай вот способ сгенерировать include:

$ cat vhost.list
198.51.100.4
198.51.100.5

$ cat gen-vhosts-pf.sh
#!/bin/sh
for ip in `egrep -v ^# /etc/vhost.list`; do
        echo "rdr pass on \$ext_if proto tcp from any to $ip port 80  -> $ip port 8080"
        echo "rdr pass on \$ext_if proto tcp from any to $ip port 443 -> $ip port 8443"
done

$ ./gen-vhosts-pf.sh | sudo tee /etc/pf.conf.vhosts
rdr pass on $ext_if proto tcp from any to 198.51.100.4 port 80  -> 198.51.100.4 port 8080
rdr pass on $ext_if proto tcp from any to 198.51.100.4 port 443 -> 198.51.100.4 port 8443
rdr pass on $ext_if proto tcp from any to 198.51.100.5 port 80  -> 198.51.100.5 port 8080
rdr pass on $ext_if proto tcp from any to 198.51.100.5 port 443 -> 198.51.100.5 port 8443

... который будет импортирован в pf.conf с:

include "/etc/pf.conf.vhosts"

Если вы не используете PF с поддержкой включений, это будет немного сложнее, но вы поняли идею.

Извините за немного разбросанные исследования; Я также не смог найти канонический способ запросить у PF информацию о его версии, поэтому мне пришлось немного повозиться.

РЕДАКТИРОВАТЬ: Вы можете сделать в том числе с load anchor пункт, хотя, похоже, вам придется повторить $ext_if макрос внутри якоря.

Я не думаю, что вам нужно делать что-то особенное, поскольку псевдонимы не настроены как отдельные сетевые устройства. Это в отличие от Linux, где у вас есть eth0, eth0:1, eth0:2 которые рассматриваются как дискретные интерфейсы. Следовательно, правила pf должны быть расширены для применения ко всем IP-адресам, присутствующим на этом интерфейсе:

# ifconfig sis2 192.168.4.1 netmask 255.255.255.0 alias
# ifconfig sis2
sis2: flags=8843<UP,BROADCAST,RUNNING,SIMPLEX,MULTICAST> mtu 1500
        lladdr 00:00:24:c6:4d:ee
        priority: 0
        media: Ethernet autoselect (100baseTX full-duplex)
        status: active
        inet 192.168.1.1 netmask 0xffffff00 broadcast 192.168.1.255
        inet6 fe80::200:24ff:fec6:4dee%sis2 prefixlen 64 scopeid 0x3
        inet 192.168.4.1 netmask 0xffffff00 broadcast 192.168.4.255

Используя следующие правила pf...

# allow untrusted -> trusted ssh & http traffic
untrust="sis2"
pass in log on $untrust inet proto tcp from $untrust:network to $trust:network port 22
pass in log on $untrust inet proto tcp from $untrust:network to $trust:network port 80

И это распространяется на следующее...

@32 pass in log on sis2 inet proto tcp from 192.168.1.0/24 to 192.168.0.0/24 port = ssh flags S/SA
@33 pass in log on sis2 inet proto tcp from 192.168.1.0/24 to 192.168.0.0/24 port = www flags S/SA
@34 pass in log on sis2 inet proto tcp from 192.168.4.0/24 to 192.168.0.0/24 port = ssh flags S/SA
@35 pass in log on sis2 inet proto tcp from 192.168.4.0/24 to 192.168.0.0/24 port = www flags S/SA
@36 pass in log on sis1 inet proto tcp from 192.168.0.0/24 to 192.168.0.1 port = ssh flags S/SA

Вам нужно будет повторно применить ваши правила pf, используя pfctl но это все, что вам нужно сделать, чтобы учесть псевдонимы IP-адресов, если ваши макросы и правила верны.

Кроме того, вы можете игнорировать все псевдонимы интерфейса в pf, перечислив его interface:0,

Предполагая, что все IP-адреса находятся в одной подсети, вы можете использовать агрегацию

$ext_net = "192.168.1.0/24"
Другие вопросы по тегам