ubuntu 20.04 LTS にて strongswan を使用したVPNを構築する(PSK)

ubuntuにstrongswanをインストールし、PSKを使用したVPN接続を構成します。

サーバ証明書を利用した接続は以下から。

https://qiita.com/Higemal/items/26897a50e02a4c043b6b

# ■環境
**OS:** `Ubuntu 20.04.6 LTS`
**strongswan:** `5.8.2-1ubuntu3.5`

# ■構成
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201787/9c4d28d5-c0c0-cc95-3daa-89abefaf7229.png)

VM環境につき、複数のセグメントを使用しています。

LAN | IP/MASK | 用途 | Left-VM | Right-VM
--- | --- | --- | --- | ---
Management | 192.168.142.0/24 | 管理用ネットワーク | 〇 | 〇
Internal | 10.0.1.0/24 | VPN接続用ネットワーク | 〇 | 〇
Service1 | 172.16.1.0/24 | Left側独立セグメント | 〇 | －
Service2 | 172.16.2.0/24 | Right側独立セグメント | － | 〇


# ■手順概要
1.VM/OS作成　※割愛
2.カーネルパラメータ設定
3.strongswanインストール
4.strongswan設定
5.strongswan起動

設定後に接続試験として以下を行います。

6.ルーティング設定
7.ping疎通確認



# 1.VM/OS作成
VPN用のVMの作成およびOSインストールを行います。
※特別な設定を行わないため割愛

:::note warn
本環境ではファイアウォールを無効化して構成します。
必要に応じて有効化・通信設定追加を行ってください。

```text:FW無効化
# ufw disable
```
:::

<br>

# 2.カーネルパラメータ設定
カーネルパラメータの設定変更を行います。

:::note warn
以降は`root`権限で操作を実行します。
:::

```text:カーネルパラメータ設定
# vi /etc/sysctl.conf
----------------------------
net.ipv4.ip_forward = 1 
net.ipv6.conf.all.forwarding = 1 
net.ipv4.conf.all.accept_redirects = 0 
net.ipv4.conf.all.send_redirects = 0
```

```text:カーネルパラメータ更新
# sysctl -p
```

```text:カーネルパラメータ一覧表示
# sysctl -a
```
parameter | 設定内容
--- | ---
net.ipv4.ip_forward = 1 | あるNICから来たパケットを別のNICへ送出する(IPv4)
net.ipv6.conf.all.forwarding = 1  | あるNICから来たパケットを別のNICへ送出する(IPv6)
net.ipv4.conf.all.accept_redirects = 0  | ICMPリダイレクトされたパケットの受入無効化
net.ipv4.conf.all.send_redirects = 0 | ICMPリダイレクトされたパケットの送出無効化


<br>

# 3.strongswanインストール
以下コマンドにてインストールを実施します。
```text:strongswan-install
# apt update
# apt install -y strongswan
```

<br>

# 4.strongswan設定
strongswan設定として、以下ファイルを操作します。
`/etc/ipsec.conf` : VPN設定ファイル
`/etc/ipsec.secrets` : VPN接続情報ファイル

### 4-1. /etc/ipsec.conf設定
以下設定をLeft側/Right側のサーバに設定します。

```text:/etc/ipsec.conf(Left)
# vi /etc/ipsec.conf
----------------------------
config setup
        charondebug="all"
        uniqueids=yes
conn left-to-right
        type=tunnel
        auto=start
        keyexchange=ikev2
        authby=secret
        left=10.0.1.111
        leftsubnet=172.16.1.0/24
        right=10.0.1.112
        rightsubnet=172.16.2.0/24
        ike=aes256-sha256-modp4096
        esp=aes256-sha256-modp4096
        aggressive=no
        keyingtries=%forever
        ikelifetime=28800s
        lifetime=3600s
        dpddelay=30s
        dpdtimeout=120s
        dpdaction=restart
```

```text:/etc/ipsec.conf(Right)
# vi /etc/ipsec.conf
----------------------------
config setup
        charondebug="all"
        uniqueids=yes
conn left-to-right
        type=tunnel
        auto=add
        keyexchange=ikev2
        authby=secret
        left=10.0.1.112
        leftsubnet=172.16.2.0/24 
        right=10.0.1.111
        rightsubnet=172.16.1.0/24 
        ike=aes256-sha256-modp4096
        esp=aes256-sha256-modp4096
        aggressive=no
        keyingtries=%forever
        ikelifetime=28800s
        lifetime=3600s
        dpddelay=30s
        dpdtimeout=120s
        dpdaction=restart
```

parameter | 設定内容
--- | ---
charondebug | ログ出力量設定
uniqueids | 接続IDについて枯渇時に再利用を許可するか
conn | 接続名
type | 接続タイプ(tunnel,transport,passthrough,drop)
auto | 接続自動設定(start,add,ignore)
keyexchange | ikeプロトコルバージョン(ikeのみ)
authby | 認証方式(secret,never,null,rsasig,...)
left | 自身のVPN用IPアドレス
leftsubnet | 自身側のプライベートサブネット
right | 他方のVPN用IPアドレス
rightsubnet | 他方側のプライベートサブネット
ike | アルゴリズム指定（※）
esp | アルゴリズム指定（※）
aggressive | アグレッシブモードの使用
keyingtries | 認証試行回数
ikelifetime | 再認証間隔
lifetime | 接続最長時間
dpddelay | ハートビート間隔
dpdtimeout | タイムアウト間隔
dpdaction | タイムアウト時の動作(restart,hold,clear)

>(※)アルゴリズム指定については以下のような形式で記載
　　`encryption - integrity[-prf] - dhgroup`
>
>dhgroupについては以下形式で表記
>![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201787/12a4fea1-9eed-80aa-eb96-4cae5bdabfc0.png)
>https://docs.strongswan.org/docs/5.9/config/IKEv2CipherSuites.html


その他詳細は以下のマニュアルを参照のこと。

https://libreswan.org/man/ipsec.conf.5.html

https://wiki.strongswan.org/projects/strongswan/wiki/ConfigSetupSection






### 4-2. /etc/ipsec.secrets設定
secret認証を設定します。
最初にランダム文字列を以下コマンドにて生成します。

```text:urandom
# head -c 24 /dev/urandom | base64
QmYEuiBdXBZ9ogtemaVDpA4N+WlbGIJu
```

`/etc/ipsec.secret`ファイルに認証設定を追加します。
左側アドレス、右側アドレス、認証方式、認証文字列(secret)を記載します。

```text:/etc/ipsec.secrets(Left)
# vi /etc/ipsec.secrets
----------------------------
10.0.1.111 10.0.1.112 : PSK "QmYEuiBdXBZ9ogtemaVDpA4N+WlbGIJu"
```

```text:/etc/ipsec.secrets(Right)
# vi /etc/ipsec.secrets
----------------------------
10.0.1.112 10.0.1.111 : PSK "QmYEuiBdXBZ9ogtemaVDpA4N+WlbGIJu" 
```

:::note warn
VPN構成時に`/etc/ipsec.secret`ファイルは権限が`600`となっている必要があります。
```text:check
# ls -l /etc/ipsec.secrets
-rw------- 1 root root 237 10月 29 20:47 /etc/ipsec.secrets
```
:::


<br>


# 5.strongswan起動
`ipsec`コマンドを利用してVPN接続を構成します。

```text:ipsec-restart
# ipsec restart
```

ステータス確認にて`Security Associations (1 up, 0 connecting):`と表示されればVPN接続されています。

```text:ipsec-status
# ipsec status
Security Associations (1 up, 0 connecting):
left-to-right[3]: ESTABLISHED 4 hours ago, 10.0.1.111[10.0.1.111]...10.0.1.112[10.0.1.112]
left-to-right{19}:  INSTALLED, TUNNEL, reqid 2, ESP SPIs: c3093721_i c2623932_o
left-to-right{19}:   172.16.1.0/24 === 172.16.2.0/24
```

<br>
<br>

# ■接続確認構成
接続確認用の構成として、Left側／Right側にそれぞれ追加でVMを作成して通信を発生させます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201787/2e5dd748-6d1b-88d1-eaa0-8da6c6c2b50f.png)

<br>

# 6.ルーティング設定
追加した疎通試験用VMにて、Left側/Right側のVPNサーバのNICをゲートウェイとするルーティング設定を実施します。

nmcliコマンドで接続名に対しルーティングを設定し、接続名の停止/起動を行います。
（`Wired connection 2`はnmcli接続名になります）
```text:Routing(Left)
# nmcli conn mod "Wired connection 2" +ipv4.routes "172.16.2.0/24 172.16.1.111"
# nmcli c d "Wired connection 2" 
# nmcli c u "Wired connection 2" 

# ip route
default via 192.168.142.2 dev ens34 proto static metric 100
default via 172.16.1.111 dev ens35 proto static metric 20101
169.254.0.0/16 dev ens34 scope link metric 1000
172.16.1.0/24 dev ens35 proto kernel scope link src 172.16.1.101 metric 101
172.16.2.0/24 via 172.16.1.111 dev ens35 proto static metric 101
192.168.142.0/24 dev ens34 proto kernel scope link src 192.168.142.101 metric 100
```

```text:Routing(Right)
# nmcli conn mod "Wired connection 2" +ipv4.routes "172.16.1.0/24 172.16.2.112"
# nmcli c d "Wired connection 2" 
# nmcli c u "Wired connection 2" 

# ip route
default via 192.168.142.2 dev ens34 proto static metric 102
default via 172.16.2.112 dev ens35 proto static metric 20103
169.254.0.0/16 dev ens34 scope link metric 1000
172.16.1.0/24 via 172.16.2.112 dev ens35 proto static metric 103
172.16.2.0/24 dev ens35 proto kernel scope link src 172.16.2.102 metric 103
192.168.142.0/24 dev ens34 proto kernel scope link src 192.168.142.102 metric 102
```

<br>

# 7.ping疎通確認
pingおよびtracertouteで疎通確認を実施します。
問題なく疎通できることが確認できました。

```text:ping/traceroute(Left)
# ping 172.16.2.102
PING 172.16.2.102 (172.16.2.102) 56(84) bytes of data.
64 bytes from 172.16.2.102: icmp_seq=1 ttl=62 time=3.11 ms
64 bytes from 172.16.2.102: icmp_seq=2 ttl=62 time=1.41 ms
64 bytes from 172.16.2.102: icmp_seq=3 ttl=62 time=1.32 ms
64 bytes from 172.16.2.102: icmp_seq=4 ttl=62 time=1.29 ms
--- 172.16.2.102 ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3005ms
rtt min/avg/max/mdev = 1.287/1.781/3.114/0.770 ms

# traceroute 172.16.2.102
traceroute to 172.16.2.102 (172.16.2.102), 30 hops max, 60 byte packets
 1  _gateway (172.16.1.111)  0.599 ms  0.536 ms  0.513 ms
 2  172.16.2.112 (172.16.2.112)  1.702 ms  1.692 ms  1.628 ms
 3  172.16.2.102 (172.16.2.102)  2.026 ms *  1.864 ms
```

```text:ping/traceroute(Right)
# ping 172.16.1.101
PING 172.16.1.101 (172.16.1.101) 56(84) bytes of data.
64 bytes from 172.16.1.101: icmp_seq=1 ttl=62 time=2.43 ms
64 bytes from 172.16.1.101: icmp_seq=2 ttl=62 time=1.36 ms
64 bytes from 172.16.1.101: icmp_seq=3 ttl=62 time=1.94 ms
64 bytes from 172.16.1.101: icmp_seq=4 ttl=62 time=1.27 ms
--- 172.16.1.101 ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3006ms
rtt min/avg/max/mdev = 1.271/1.748/2.427/0.467 ms

# traceroute 172.16.1.101
traceroute to 172.16.1.101 (172.16.1.101), 30 hops max, 60 byte packets
 1  _gateway (172.16.2.112)  0.623 ms  0.573 ms  0.567 ms
 2  172.16.1.111 (172.16.1.111)  1.528 ms  1.519 ms  1.491 ms
 3  172.16.1.101 (172.16.1.101)  2.321 ms  2.279 ms  2.226 ms
```


# ■参考

**ipsec.conf.5**
https://libreswan.org/man/ipsec.conf.5.html

**ipsec.conf: conn <name>**
https://wiki.strongswan.org/projects/strongswan/wiki/connsection

**IKEv2 Cipher Suites**
https://docs.strongswan.org/docs/5.9/config/IKEv2CipherSuites.html

**Debian および Ubuntu で Strongswan を使用して IPsec ベースの VPN をセットアップする方法**
https://ja.linux-console.net/?p=890