路由器
此文章是將一台電腦配置為一台網關/路由器的指南。為加強安全性,不應在此機器上運行對外服務。對於區域網(LAN),只運行特定的網關服務而不運行httpd、ftpd、samba、nfsd等屬於區域網伺服器的服務,因為這樣會帶來風險。
此文章不涉及如何設置兩台PC用交叉網線進行網絡連接共享。簡單網絡連接共享,參見Internet sharing。
硬體需求[編輯 | 編輯原始碼]
- 至少 1GB 硬碟空間。基本安裝約需 500MB 硬碟空間,如果使用web代理緩存還需額外預留緩存空間。
- 至少兩個實體網絡接口:網關要將兩個網絡彼此連通(實際上路由器可以用一個物理網絡接口實現兩個VLAN接口並連接到VLAN交換機,這稱為單臂路由/router-on-a-stick,但本文不討論這種情況)。需要將兩個網絡連接到同一台實體機器,其中一個網口連接到外部網絡,另一個連接內部網絡。其中一個接口必須連接到外部網絡,其他接口連接到內部網絡。
- 一個集線器、交換機或UTP線纜:將其他機器連接到網關。
網絡接口配置[編輯 | 編輯原始碼]
網絡接口名稱約定[編輯 | 編輯原始碼]
Systemd 會自動為網口選擇唯一接口名稱。命名是持續不變的,直到重啟。你可能希望更改接口名稱,以便標記不同的網絡接口。在以下的說明中,我們約定使用以下名稱:
- intern0:連接到區域網(LAN)的網絡接口。真實名稱可能是 enp2s0、enp1s1 等等。
- extern0:連接到外部網絡或廣域網的網絡接口。真實名字可能是 enp2s0、enp1s1 等等。
你可以通過Systemd-networkd#Renaming an interface中說明的方法使用Systemd-networkd的配置文件,或通過網絡配置#Change interface name中說明的方法使用udev規則重新分配設備名稱。由於本文是示例性質,使用以上約定名稱。
IP 配置[編輯 | 編輯原始碼]
首先需要配置網絡接口。配置網絡接口最好的方式是編輯 netctl 配置文件。下面需要創建兩個配置文件。
/etc/netctl/extern0-profile
Description='Public Interface.' Interface=extern0 Connection=ethernet IP='dhcp'
/etc/netctl/intern0-profile
Description='Private Interface' Interface=intern0 Connection=ethernet IP='static' Address=('10.0.0.1/24')
/27
是限定範圍在 10.0.0.1
至 10.0.0.30
。有很多在線CIDR計算器可用,例如sipcalc包。下一步是用 netctl 啟用網絡接口配置。
# netctl enable extern0-profile # netctl enable intern0-profile
ADSL連接/PPPoE[編輯 | 編輯原始碼]
可以用 rp-pppoe 將防火牆的 extern0
接口連接到ADSL modem並管理該連接。確認已將modem設置為橋接(或半橋接或RFC1483)模式,否則modem工作於路由器模式。安裝 rp-pppoe包 包。
需要注意的是:如果僅能通過PPPoE連接到網際網路(除了能連接modem之外沒有其它廣域網接口),則不必啟用 extern0-profile
,因為此時外網口使用名為 ppp0 的偽接口。
PPPoE配置[編輯 | 編輯原始碼]
可以使用 netctl 設置 pppoe 連接。首先,
# cp /etc/netctl/examples/pppoe /etc/netctl/
然後編輯它。選擇連接到modem的接口並配置。如果你僅僅通過PPPoE連接到網際網路,這就是 extern0
接口。其他欄位填入ISP的信息。詳情參閱 netctl.profile(5) 手冊。
DNS 和 DHCP[編輯 | 編輯原始碼]
可以使用專為小型站點設計的 dnsmasq 為區域網提供DNS和DHCP服務。安裝 dnsmasq包 包即可。
Dnsmasq 要配置為DHCP伺服器。編輯 /etc/dnsmasq.conf
:
/etc/dnsmasq.conf
interface=intern0 # 使dnsmasq只侦听来自内网口(intern0,即局域网)的请求 expand-hosts # 为 /etc/hosts 中的主机名添加一个域名 domain=foo.bar # 允许DHCP主机的完全限定域名(需要启用“expand-hosts”) dhcp-range=10.0.0.2,10.0.0.255,255.255.255.0,1h # 定义局域网中DHCP地址范围:从 10.0.0.2 至10.0.0.255,子网掩码为 255.255.255.0,DHCP 租期为 1 小时 (可按需修改)
下面將看到,只能添加靜態DHCP租約。例如,分配一個IP位址給區域網中某一台指定MAC地址的機器。這樣,無論這台機器何時請求DHCP,都獲得同一個IP位址。對於需要DNS記錄的網絡服務來說這非常有用。這也可以拒絕特定MAC的機器獲取IP位址。
現在 啟動 dnsmasq.service
服務。
連接共享[編輯 | 編輯原始碼]
現在可以連通兩個網絡接口。
Manual[編輯 | 編輯原始碼]
首先,需要允許數據包從一個網絡接口跳轉到另一個網絡接口。這樣需要通過內核中的 sysctl(8) 功能啟用包轉發功能。詳情參閱 Internet sharing#Enable packet forwarding。
假設 net.**forwarding
設置正確(即設置為 1
),數據包仍需要正確地發送和接收。因此,必須在外部網路和內部子網之間轉換IP位址。這種技術稱為「偽裝」(masquerading)。還需要兩個轉發規則保持連接,並使LAN能夠轉發到WAN。為此,我們可以使用iptables:
/etc/iptables/iptables.rules
*nat :PREROUTING ACCEPT [0:0] :INPUT ACCEPT [0:0] :OUTPUT ACCEPT [0:0] :POSTROUTING ACCEPT [0:0] -A POSTROUTING -o extern0 -j MASQUERADE COMMIT *filter :INPUT ACCEPT [0:0] :FORWARD ACCEPT [0:0] :OUTPUT ACCEPT [0:0] -A FORWARD -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT -A FORWARD -i intern0 -o extern0 -j ACCEPT COMMIT
如果通過PPPoE連接,還需要將 mss 鉗制到 pmtu,防止產生碎片:
/etc/iptables/iptables.rules
*mangle :PREROUTING ACCEPT [0:0] :INPUT ACCEPT [0:0] :FORWARD ACCEPT [0:0] :OUTPUT ACCEPT [0:0] :POSTROUTING ACCEPT [0:0] -A FORWARD -o ppp0 -p tcp -m tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu COMMIT
Start 和 enable iptables.service
。路由器現在應該完全正常運行,並路由數據。但是,要面向公共Internet使用,還需要通過Simple stateful firewall進行額外的保護。
用shorewall共享連接[編輯 | 編輯原始碼]
詳細配置說明參見Shorewall。
IPv6說明[編輯 | 編輯原始碼]
很有用的參考: IPv6 和 wikipedia:IPv6。
唯一本地地址[編輯 | 編輯原始碼]
即使ISP沒有提供IPv6地址,仍然可以將路由器設置為IPv6模式。除非禁用IPv6,否則所有接口都會分配唯一的 fe80::/10
地址。
對於內部網絡,已保留地址塊 fc00::/7
。這些地址保證是唯一的,且不可從開放的網際網路路由。屬於 fc00::/7
的地址稱為 Unique Local Addresses。要在內部網絡生成和使用 generate a ULA /64 block,如希望使用 fd00:aaaa:bbbb:cccc::/64
,我們首先要在內部接口上分配靜態IPv6地址。修改上面的 intern0-profile
,添加以下一行:
Address6=('fd00:aaaa:bbbb:cccc::1/64')
這樣將ULA添加到內部網絡接口。就路由器而言,這是唯一需要配置的地方。
全局單播地址[編輯 | 編輯原始碼]
如果ISP或WAN網絡可以訪問IPv6 Internet,則可以將全局鏈路地址分配給路由器,並通過 SLAAC傳播到內部網絡。全局單播前綴通常是靜態或通過前綴委派提供的。
靜態IPv6前綴[編輯 | 編輯原始碼]
如果ISP提供靜態前綴,則編輯 /etc/netctl/extern0-profile
配置文件,簡單添加IPv6地址和前綴即可:
Address6=('2002:1:2:3:4:5:6:7/64')
可以在使用上述ULA地址之外,同時使用此功能。
通過DHCPv6-PD獲取IPv6前綴[編輯 | 編輯原始碼]
如果ISP通過前綴委派處理IPv6,則可以按照main IPv6 article中的說明進行操作。按照本說明的約定,WAN接口為 extern0
(或如果通過PPPoE連接時是 ppp0
),LAN接口為 intern0
。
路由通告與無狀態自動配置(SLAAC)[編輯 | 編輯原始碼]
要向網絡客戶端正確分發IPv6,需要使用通告守護進程。按照 main IPv6 article 中關於如何設置 radvd
的說明進行操作。按照本說明的約定,LAN接口是 intern0
。可以通告所有前綴,或選擇哪些前綴分配給本地網絡。
可選附加功能[編輯 | 編輯原始碼]
UPnP[編輯 | 編輯原始碼]
上述 shorewall 的配置不包含 UPnP 支持。儘管可能使路由器遭到來自區域網內部的攻擊,然而某些應用要求必須使用UPnP。
要在路由器上啟用UPnP,需要安裝一個UPnPInternet Gateway Device (IGD) protocol。可從官方倉庫安裝 miniupnpd包 。
更詳細信息請查閱 Shorewall guide on UPnP 。
遠程管理[編輯 | 編輯原始碼]
OpenSSH 可用於遠程管理路由器,十分適合運行在「無頭」模式(無顯示器或輸入設備)的機器。
緩存網頁代理[編輯 | 編輯原始碼]
參閱 Squid 如何配置代理為網頁瀏覽加速和/或添加額外的安全層。
時間伺服器[編輯 | 編輯原始碼]
將路由器用作一台時間伺服器,參閱系統時間#時間同步,配置網絡時間協議(NTP)伺服器。
然後配置 shorewall 或者 iptables 允許 NTP 流量流出。
內容過濾[編輯 | 編輯原始碼]
如果需要內容過濾,可以安裝配置 DansGuardian 或者 Privoxy 。
流量共享[編輯 | 編輯原始碼]
流量共享很有用,尤其當區域網中不止一台機器時。基本思路是為不同類型的流量分配優先級。交互型流量(ssh、在線遊戲等)可能需要高優先級,而 P2P 流量可分配低優先級。其他流量介於二者之間。