За да излезе еден порт надвор од VPN, потребно е рутирање по политика
NAT правило ги препишува адресите, но не избира излезна врска. Еве го правилото, табелата и ознаката што навистина држат еден TCP порт надвор од тунелот.
Барањето е секогаш варијанта на истата реченица: задржи го VPN за прелистување, но дозволи SSH или задача за резервна копија да ја користи нормалната врска. Советот што кружи за ова, префрлање на портот со iptables NAT правила, не го прави тоа. NAT правилото препишува адреси и портови внатре во текот; никогаш не избира низ кој интерфејс пакетот излегува. Таа одлука и припаѓа на пребарувањето на рута, а пребарувањето на рута бара помош за да види порт.
Зошто обична рута не може да се совпадне со порт
Linux избира рута со пребарување на одредишната адреса во табела, откако кандидат-табелите се филтрирани со правила на политика. Тие правила можат да се совпаднат со ознака на огнен ѕид, изворна адреса, влезен интерфејс или UID. Самиот запис за рута нема поле за порт, бидејќи рутата се избира пред транспортниот заглавје да има значење.
Современите iproute2 и јадра го прошируваат избирачот на правилото: ipproto, sport и dport се прифаќаат, па ip rule add ipproto tcp dport 22 table 100 ја изразува намерата во еден ред. Извршете ip rule add help на вистинскиот домаќин за да видите дали вашата градба наведува dport. Ако наведува, завршивте со една команда; ако не, патеката преку ознака подолу е еквивалентот.
Како и да е, правилото е само показател. Табелата 100 сè уште бара рута, и токму тој дел луѓето го забораваат.
Три дела, или еден
Современата форма е единственото правило погоре плус рута во алтернативната табела. Класичната форма додава netfilter во средината: означете го пакетот, потоа совпаѓајте ја ознаката во правило. Двете завршуваат на истото пребарување; се разликуваат по тоа каде се чита портот.
Пристапот со ознака постои затоа што netfilter го гледа транспортниот заглавје, а рутирачкиот код историски не го гледал. Тоа е целиот механизам и објаснува зошто резервната варијанта се три соработувачки дела, а не една лукава команда.
Трите дела по ред
Прво, означете ги тековите што сакате да ги пренасочите, во синџир што се извршува доволно рано за ознаката да постои пред одлуката за рута:
nft add table inet vpnexempt
nft 'add chain inet vpnexempt out { type route hook output priority mangle; }'
nft add rule inet vpnexempt out tcp dport 22 meta mark set 0x1Второ, пратете ги означените пакети во посебна табела:
ip rule add fwmark 0x1/0x1 table 100Трето, дајте и на таа табела стандардна рута преку физичката врска. Адресите се илустративни; ставете ги вашите:
ip route add default via 192.168.1.1 dev wlan0 table 100Прескокнете го третиот чекор и означениот пакет нема да најде рута во табелата 100, па ќе пропадне. Симптомот изгледа како правилото да го расипало мрежето, а всушност ја отстранило единствената патека што му останала на пакетот.
Што го одржува во работа по првиот пакет
Ознаките важат за излезни пакети. Одговорот пристигнува на физичкиот интерфејс со адресата што ја доделила таа врска, а главната табела може сè уште да го претпочита тунелот за тоа одредиште. Два механизми го држат патот на одговорот конзистентен: правило засновано на извор за адресата на врската и следење на врските што ја сочувува одлуката за целиот животен век на текот. Зачувувањето на ознаката во conntrack и нејзино враќање при одговорот е вообичаениот начин да се направи исклучок со состојба стабилен.
Филтрирањето на обратниот пат е другиот тивок убиец. Ако јадрото строго го проверува повратниот пат и одговорот пристигне на интерфејс што главната табела не би го избрала, пакетот се отфрла без порака. rp_filter стандардните вредности се разликуваат по дистрибуција и по тоа дали интерфејсот се препраќа, затоа прочитајте ја ефективната вредност наместо да претпоставите дека е исклучена.
Не означувајте го сопствениот транспорт на тунелот. Тунел WireGuard или UDP OpenVPN не е TCP 22, затоа рецептот погоре е безбеден, но исклучок напишан како сè освен одредиштето на тунелот може да ги фати шифрираните пакети и да го скрши тунелот на начин што изгледа како рутирачка јамка.
Проверете наместо да претпоставувате
Прашајте го јадрото кој пат би го избрало, за одредиштето и за портот, потоа извршете го вистинскиот пренос:
ip route get 203.0.113.10
ip rule show
nft list rulesetАко ознаката постои но бројачите никогаш не се движат, правилото не се совпаѓа. Бројачите се разликата помеѓу конфигурацијата што ја напишавте и политиката што јадрото ја применува.
Кога ова е погрешна алатка
Исклучоците засновани на порт се кревки по природа. Услугите ги менуваат портовите, HTTP/3 доаѓа како UDP 443, а една апликација може да отвори неколку текови од различен вид. Ако вистинското барање е оваа програма да ја користи нормалната врска, рутирачкиот слој е погрешно место; мрежен именски простор или прокси за секоја апликација подобро одговараат.
Ако барањето е оваа подмрежа да ја користи нормалната врска, целосно прескокнете ги ознаките и додајте поконкретна рута. Тоа е поедноставно, видливо е во една табела, и следната личност може да го ревидира без да чита множество правила.
Запишете кое од трите барања навистина го имате пред да го допрете огнениот ѕид. Механизмот погоре е прецизен, а прецизноста применета на погрешен слој е само подолг прекин.