前回IKEv1ベースで設定し常時接続出来なかったのでIKEv2で再チャレンジしました。最終的にWindowsでは繋がるもののMacでは繋がりませんでした。悲しみ。

事前調査

DDNS準備

  • 証明書のSAN指定が必要なので何かドメインを用意する。SANにはIPアドレスを直指定できるはずだが、なんか挙動が変わるらしい
  • 無ければ適当なDDNSで取ってくる
  • 手持ちのドメインがあればそれでも良い

証明書準備

  • 証明書の生成は LibreSSL 3.3.6 で実施した。普通にOpenSSLでも大丈夫なはず
  • openssl x509 コマンドはCSRの中にあるExtensionsを読んでくれないのでextfileで指定する

CA証明書

  • 各種証明書を作るためのルートCA証明書にはbasicConstraintsが必要
  1. 以下の内容で ext_ca.txt を作成(コメント部分は無くてもいい)
     # critical は"重要"ぐらいの意味合いで、この属性の検証が必須になるらしい
     # CA:true はCA証明書であることの明示
     # pathlen:0 は中間CAの作成を認めない設定
     basicConstraints = critical, CA:true, pathlen:0
    
  2. 以下コマンドで鍵と証明書発行
     # 鍵生成
     openssl genrsa -out ca.key 4096
     # リクエスト生成
     openssl req -new -key ca.key -out ca.csr -subj "/CN=FlexVPN-RootCA"
     # 自己署名でCA証明書作成。有効期限は10年
     openssl x509 -req -in ca.csr -out ca.crt -days 3650 -extfile ext_ca.txt -signkey ca.key
    

サーバ証明書

  • 上の方にあるStrongSwanドキュメントに沿う
  1. 以下の内容で ext_server.txt を作成(コメント部分は無くてもいい)
     # EKUの指定。ServerAuthが必須
     extendedKeyUsage = serverAuth
     # SANの指定。CNに指定してもいいらしいが、SANの方が近代的な気がするのでSANでやる
     # server.example.comは用意したドメインに置き換える(DDNSなどで用意したやつ)
     # クライアント側で「接続先」に指定する値と一致させないとハマるのでよく考える
     subjectAltName = DNS:server.example.com
    
  2. 以下コマンドで鍵と証明書発行
     # 鍵生成
     openssl genrsa -out server.key 4096
     # リクエスト生成
     openssl req -new -key server.key -out server.csr -subj "/CN=FlexVPN-Server"
     # CA鍵で証明書作成。有効期限は1年
     openssl x509 -req -in server.csr -out server.crt -days 365 -extfile ext_server.txt -CA ca.crt -CAkey ca.key -set_serial 10
     # インポート用にpkcs#12でまとめる。展開用パスワードは雑に123456
     openssl pkcs12 -export -in server.crt -inkey server.key -out server.pfx -CAfile ca.crt -chain -password pass:123456
    

クライアント証明書

  1. 以下の内容で ext_client.txt を作成(コメント部分は無くてもいい)
     # EKUの指定。serverAuth, clientAuth両方入れる
     # 891FJ=>Clientの向きでの認証も走るため、ServerAuthを入れる
     # ClientAuthは多分要らないが、Ciscoのドキュメント的には必要らしいのでとりあえず入れる。あっても困らない
     extendedKeyUsage = serverAuth, clientAuth
    
  2. 以下コマンドで鍵と証明書発行
     # 鍵生成
     openssl genrsa -out client.key 4096
     # リクエスト生成
     openssl req -new -key client.key -out client.csr -subj "/CN=FlexVPN-Client"
     # CA鍵で証明書作成。有効期限は1年
     openssl x509 -req -in client.csr -out client.crt -days 365 -extfile ext_client.txt -CA ca.crt -CAkey ca.key -set_serial 20
     # インポート用にpkcs#12でまとめる。展開用パスワードは雑に123456
     openssl pkcs12 -export -in client.crt -inkey client.key -out client.pfx -CAfile ca.crt -chain -password pass:123456
    

証明書転送

  1. 適当なUSBメモリにserver.pfxをコピーして891FJにつなぐ
    • うまく認識しない場合はformat usbflash0:で一回USBメモリを空にしてから再チャレンジ
  2. 以下コマンドでインポート
     # 中身確認
     show usbflash0:
     # インポートする。完了したらUSBメモリは抜いて良い
     crypto pki import FLEXVPN_TRUSTPOINT pkcs12 usbflash0:SERVER.PFX password 123456
     # 証明書をインポートするとデフォルトで revocation-check crl が入ってしまうので切る
     crypto pki trustpoint FLEXVPN_TRUSTPOINT
      revocation-check none
     exit
     # 良い感じに読まれたか見る。ルートCA証明書も入っているはず
     show crypto pki certificates verbose
    

891FJ設定

# FlexVPNで使う認可の設定
aaa new-model
aaa authorization network FLEXVPN_AUTHZ local

# クライアントに配るIPアドレス
ip local pool FLEXVPN_POOL 192.168.30.51 192.168.30.100

# IKEv2プロポーザルの定義
crypto ikev2 proposal FLEXVPN_PROPOSAL
 # Macの場合は DiffieHellmanGroup Default: 14 とある
 # Windowsの標準機能で作るとDH2になるのでそれも加える。ただ確実に弱い
 # (変えるにはPowerShell経由のコマンドが必要で面倒)
 group 2 14
 # EncryptionAlgorithm Default: AES-256
 encryption aes-cbc-256
 # IntegrityAlgorithm Default: SHA2-256
 integrity sha256
exit

# 上で作ったプロポーザルを使うポリシー。vrfを使っていればここで紐づける
crypto ikev2 policy FLEXVPN_POLICY
 proposal FLEXVPN_PROPOSAL
 # どのインターフェイスでも使えるようにする(絞る場合はVRFを作ったりmatch addressにしたりする)
 match fvrf any
exit

# IKEv2の認証などが通った後に、クライアントに使わせる各種パラメータを指定するポリシー
crypto ikev2 authorization policy FLEXVPN_AUTHZ_POLICY
 # クライアントに使わせるIPアドレスのプール
 pool FLEXVPN-POOL
 # クライアントに使わせるDNSサーバ。アドブロックDNSを使ってる場合はここらへんに指定する
 dns 8.8.8.8 8.8.4.4
 # クライアントに使わせるデフォルトドメイン名。無くてもいい気がする
 def-domain myhome.test
exit

# 証明書マップ すぐ下で使う
crypto pki certificate map FLEXVPN_CERT_MAP 10
 # issuerのCNがFlexVPN-RootCAの証明書全て
 issuer-name eq cn=FlexVPN-RootCA
exit

# IKEv2のプロファイル 仮想インターフェースに紐づける
crypto ikev2 profile FLEXVPN_IKEV2_PROFILE
 # 証明書マップに一致する場合このプロファイルを使わせる
 match certificate FLEXVPN_CERT_MAP
 # ローカル側ID。とりあえず証明書のSANと合わせておく
 identity local fqdn server.example.com
 # クライアントから891FJへの認証。証明書ベースでやる
 authentication local rsa-sig
 # 891FJからクライアントへの認証。これは無効化したりanyにしたりはできない。この1行のせいでMacで繋がらないはず(多分)
 authentication remote rsa-sig
 # どの証明書とCAを使うか
 pki trustpoint FLEXVPN_TRUSTPOINT
 # 認証が通った後、なにを使わせるか
 aaa authorization group cert list FLEXVPN_AUTHZ FLEXVPN_AUTHZ_POLICY
 # Dead Peer Detection。クライアントの死活監視
 dpd 30 10 on-demand
 # 接続した後クライアントが繋がる仮想インターフェイスのテンプレート。下の方でVirtual-Templateとして定義する
 virtual-template 10
exit

# IPSecで使うセキュリティプロトコルやらアルゴリズムやらを決める
crypto ipsec transform-set FLEXVPN_IPSEC_TS esp-aes 256 esp-sha-hmac
 mode tunnel
exit

# IPSecのパラメータ一式を決めるプロファイル
crypto ipsec profile FLEXVPN_IPSEC_PROFILE
 # すぐ上で決めたトランスフォームセット
 set transform-set FLEXVPN_IPSEC_TS
exit

# 仮想インターフェイスに紐づくIPアドレスを持つだけのLoopbackインターフェイス
interface loopback 10
 ip address 192.168.30.1 255.255.255.255
exit

# 仮想インターフェイス。Templateとあるように、クライアントが接続する度にVirtual-Accessインターフェイスが増えていく
interface Virtual-Template 10 type tunnel
 # loopbackを作らず直接指定したら動かなかった
 ip unnumbered loopback 10
 # 大抵の場合は891FJでNAPTしているはずなので書く。NAPTしてなければ不要
 ip nat inside
 # IPv4でトンネルを張る
 tunnel mode ipsec ipv4
 # トンネルにIKEv2とIPSecのプロファイルを紐づける
 tunnel protection ipsec profile FLEXVPN_IPSEC_PROFILE ikev2-profile FLEXVPN_IKEV2_PROFILE
exit

# 既にWAN側INにACLがかかっている場合、UDPの500と4500を開ける。4500はNAT関連なので891FJがグローバルアドレス持っていれば不要なはず
# ESPは要らないらしい(UDPでカプセル化される)
ip access-list extended v4WanIn
 permit udp any host 192.168.1.10 eq isakmp non500-isakmp
exit

# CEFを切らないとセグメント間通信の戻りパケットが届かなかった。どう考えてもおかしい
no ip cef

Windows11設定

普通に証明書をインポートする

  1. 作成した client.pfx をダブルクリック
  2. インポートウィザードが起動するのでローカルコンピュータを選んで次へ
  3. ファイルパスは入っているはずなので次へ
  4. パスワードに123456を入れて次へ
  5. 証明書の種類に基づいて自動的に証明書ストアを選択する の方を選んで次へ

その後、普通にVPNを作成する

  1. 設定 -> ネットワークとインターネット -> VPN -> VPNを追加
    • VPNプロバイダー: ビルトイン
    • 接続名: 適当に書く
    • サーバー名またはアドレス: 事前に用意したドメイン 証明書のSANと必ず合わせる
    • VPNの種類: IKEv2
    • サインインの種類: 証明書
  2. 設定 -> ネットワークとインターネット -> ネットワークの詳細設定 -> ネットワークアダプターオプションの詳細 -> 作成したVPNを選んでから「この接続の設定を変更する」 -> セキュリティタブ
    • 認証: コンピューターの証明書を使う を選ぶ
  3. 右下ネットワークアイコンからVPN接続

Mac設定

  • どう設定しても繋がらなかった。かなしい
  • mac側ログは log stream --debug --predicate 'process == "NEIKEv2Provider"' で出る
    • NO_PROPOSAL_CHOSEN とか出るので何か間違えている気がする
    • なにもわからない
  • 891FJ側ログは debug crypto ikev2 で出る
    • Callback received for the validate proposal - FAILED. とか言っているのでやっぱりプロポーザルが正しく選択されていない
    • なにもわからない