如何在 OpenVPN 服务器上为客户端设置 NAT?

如何在 OpenVPN 服务器上为客户端设置 NAT?

我在 Oracle Cloud 中创建了一个 VM 实例,用作我的 OpenVPN 服务器。我能够将我的客户端(Android 手机)连接到服务器,但无法访问互联网。

在我看来,问题出在 iptables 中的 NAT 配置上。

有人能帮我解决这个问题吗?我已经尝试了将近一周,但没有成功。

我的配置如下:

/etc/openvpn/服务器/服务器.conf

;local a.b.c.d
port 443
proto tcp
;proto udp
;dev tap
dev tun
;dev-node MyTap
ca ca.crt
cert Lyra.crt
key Lyra.key  
;dh dh2048.pem
dh none
;topology subnet
server 10.8.0.0 255.255.255.0
ifconfig-pool-persist ipp.txt
;server-bridge 10.8.0.4 255.255.255.0 10.8.0.50 10.8.0.100
;server-bridge
;push "route 192.168.10.0 255.255.255.0"
;push "route 192.168.20.0 255.255.255.0"
;client-config-dir ccd
;route 192.168.40.128 255.255.255.248
;learn-address ./script
push "redirect-gateway def1 bypass-dhcp"
push "dhcp-option DNS 208.67.222.222"
push "dhcp-option DNS 208.67.220.220"
;client-to-client
;duplicate-cn
keepalive 10 120
;tls-auth ta.key 0 # This file is secret
tls-crypt ta.key
;cipher AES-256-CBC
cipher AES-256-GCM
auth SHA256
;compress lz4-v2
;push "compress lz4-v2"
;comp-lzo
;max-clients 100
user nobody
group nobody
persist-key
persist-tun
status openvpn-status.log
log         openvpn.log
;log-append  openvpn.log
verb 3
;mute 20
explicit-exit-notify 0

/etc/openvpn/服务器/openvpn.log

OpenVPN 2.4.7 x86_64-pc-linux-gnu [SSL (OpenSSL)] [LZO] [LZ4] [EPOLL] [PKCS11] [MH/PKTINFO] [AEAD] built on Sep  5 2019
library versions: OpenSSL 1.1.1f  31 Mar 2020, LZO 2.10
Outgoing Control Channel Encryption: Cipher 'AES-256-CTR' initialized with 256 bit key
Outgoing Control Channel Encryption: Using 256 bit message hash 'SHA256' for HMAC authentication
Incoming Control Channel Encryption: Cipher 'AES-256-CTR' initialized with 256 bit key
Incoming Control Channel Encryption: Using 256 bit message hash 'SHA256' for HMAC authentication
ROUTE_GATEWAY 10.0.0.1/255.255.255.0 IFACE=ens3 HWADDR=00:00:17:02:e1:8d
TUN/TAP device tun0 opened
TUN/TAP TX queue length set to 100
/sbin/ip link set dev tun0 up mtu 1500
/sbin/ip addr add dev tun0 local 10.8.0.1 peer 10.8.0.2
/sbin/ip route add 10.8.0.0/24 via 10.8.0.2
Could not determine IPv4/IPv6 protocol. Using AF_INET
Socket Buffers: R=[131072->131072] S=[16384->16384]
Listening for incoming TCP connection on [AF_INET][undef]:443
TCPv4_SERVER link local (bound): [AF_INET][undef]:443
TCPv4_SERVER link remote: [AF_UNSPEC]
MULTI: multi_init called, r=256 v=256
IFCONFIG POOL: base=10.8.0.4 size=62, ipv6=0
ifconfig_pool_read(), in='mirza_s8,10.8.0.4', TODO: IPv6
succeeded -> ifconfig_pool_set()
IFCONFIG POOL LIST
mirza_s8,10.8.0.4
MULTI: TCP INIT maxclients=1024 maxevents=1028
Initialization Sequence Completed
TCP connection established with [AF_INET]103.208.70.45:56043
103.208.70.45:56043 TLS: Initial packet from [AF_INET]103.208.70.45:56043, sid=37acebde bb02752b
103.208.70.45:56043 VERIFY OK: depth=1, CN=Cygnus
103.208.70.45:56043 VERIFY OK: depth=0, CN=mirza_s8
103.208.70.45:56043 peer info: IV_VER=3.git:released:3e56f9a6:Release
103.208.70.45:56043 peer info: IV_PLAT=android
103.208.70.45:56043 peer info: IV_NCP=2
103.208.70.45:56043 peer info: IV_TCPNL=1
103.208.70.45:56043 peer info: IV_PROTO=2
103.208.70.45:56043 peer info: IV_AUTO_SESS=1
103.208.70.45:56043 peer info: IV_GUI_VER=net.openvpn.connect.android_3.2.2-5027
103.208.70.45:56043 peer info: IV_SSO=openurl
103.208.70.45:56043 WARNING: 'link-mtu' is used inconsistently, local='link-mtu 1551', remote='link-mtu 1523'
103.208.70.45:56043 Control Channel: TLSv1.3, cipher TLSv1.3 TLS_AES_256_GCM_SHA384, 384 bit EC, curve: secp384r1
103.208.70.45:56043 [mirza_s8] Peer Connection Initiated with [AF_INET]103.208.70.45:56043
mirza_s8/103.208.70.45:56043 MULTI_sva: pool returned IPv4=10.8.0.6, IPv6=(Not enabled)
mirza_s8/103.208.70.45:56043 MULTI: Learn: 10.8.0.6 -> mirza_s8/103.208.70.45:56043
mirza_s8/103.208.70.45:56043 MULTI: primary virtual IP for mirza_s8/103.208.70.45:56043: 10.8.0.6
mirza_s8/103.208.70.45:56043 PUSH: Received control message: 'PUSH_REQUEST'
mirza_s8/103.208.70.45:56043 SENT CONTROL [mirza_s8]: 'PUSH_REPLY,redirect-gateway def1 bypass-dhcp,dhcp-option DNS 208.67.222.222,dhcp-option DNS 208.67.220.220,route>
mirza_s8/103.208.70.45:56043 Outgoing Data Channel: Cipher 'AES-256-GCM' initialized with 256 bit key
mirza_s8/103.208.70.45:56043 Incoming Data Channel: Cipher 'AES-256-GCM' initialized with 256 bit key

ip a 显示 ens3

2: ens3: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 9000 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:00:17:02:e1:8d brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.9/24 brd 10.0.0.255 scope global ens3
       valid_lft forever preferred_lft forever
    inet6 fe80::200:17ff:fe02:e18d/64 scope link
       valid_lft forever preferred_lft forever

iptables -t nat -L -n -v

Chain PREROUTING (policy ACCEPT 1389 packets, 95043 bytes)
 pkts bytes target     prot opt in     out     source               destination

Chain INPUT (policy ACCEPT 19 packets, 1080 bytes)
 pkts bytes target     prot opt in     out     source               destination

Chain OUTPUT (policy ACCEPT 985 packets, 87235 bytes)
 pkts bytes target     prot opt in     out     source               destination

Chain POSTROUTING (policy ACCEPT 299 packets, 31308 bytes)
 pkts bytes target     prot opt in     out     source               destination
 3063  226K MASQUERADE  all  --  *      ens3    10.0.0.0/8           0.0.0.0/0
    0     0 MASQUERADE  all  --  *      ens3    10.8.0.0/24          0.0.0.0/0

/etc/ufw/before.rules

# START OPENVPN RULES
# NAT table rules
*nat
:POSTROUTING ACCEPT [0:0]
# Allow traffic from OpenVPN client to ens3 (change to the interface you discovered!)
-A POSTROUTING -s 10.8.0.0/8 -o ens3 -j MASQUERADE
COMMIT
# END OPENVPN RULES

sysctl net.ipv4.ip_forward

net.ipv4.ip_forward = 1

答案1

您似乎已经正确设置了 NAT,但 MTU 设置不正确。它应该低于 1500(可能要低很多),以确保隧道流量在穿越互联网时不会碎片化。

在我的生产 OpenVPN 服务器上,我设置了:mssfix 1350一年多来一直非常稳定。虽然默认值为 1450,但这似乎会给各种网络链接带来麻烦,这些链接的 MTU 显然莫名其妙地低于 1500。不应将此值设置为低于该值,1328因为较小的值会破坏隧道 IPv6。

答案2

我发现我的 iptables FOWARD 链策略在启动后总是设置为 DROP。

因此,我使用以下规则修复了我的 OpenVPN NAT 问题:

#!/bin/bash
/sbin/iptables -A FORWARD -i tun+ -j ACCEPT
/sbin/iptables -A FORWARD -o tun+ -j ACCEPT

我在 /etc/rc.local 中设置了这些规则并将其 chmod 设置为 755。

相关内容