AWS Multi-VPC ENI Attachments を使ってみる

# 1. はじめに
- 2023/10/26に、「[Multi-VPC ENI Attachments](https://aws.amazon.com/jp/about-aws/whats-new/2023/10/multi-vpc-eni-attachments/)」という新機能が発表され、即日利用可能とのこと。
- 今までも1つのインスタンスに対して、同一VPC内の複数のENIをアタッチすることはできたが、今回のアップデートでは、別のVPCのENIもアタッチできるようになった様子。
- 基本的な動作確認及び、「こういうことやったらどうなるのかな？」という構成をいくつか試してみる。

:::note info 
とりあえず新機能をマニュアルなしでやってみた感じなので、認識誤りなど含む可能性あり。随時修正、更新する。
2023/10/28 構成の検証を2件追記。
2023/10/29 2つENIを持つインスタンスをルータとして使用する設定を追記。 
:::

# 2. 基本動作確認

- 最もベーシックな以下の構成をもとに、基本動作を確認する。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/189302/e97f5368-cbd4-c94a-340a-0dea24be9839.png)

## VPC/Subnetの作成
- CIDRの重複しない、VPC-A(10.0.0.0/16)、VPC-B(172.16.0.0/16)を作成する。
- VPC-Aのsubnet(10.0.0.0/24)、VPC-Bのsubnet(172.16.0.0/24)は共にus-west-1a。(Multi-VPC ENI Attachmentsの利用前提条件として、AZが同一であること)

## ENI検証用インスタンスの作成
- VPC-Aのsubnet(10.0.0.0/24)を指定して、Instance-A(ENI検証用)を作成する。
    - SecurityGroupで以下のInboundを許可しておく。
        - 10.0.0.0/16
        - 172.16.0.0/16
- Instance-Aに、普通にENIが1個アタッチされていることを確認する。
![002.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/189302/879f6c6b-0b71-bc39-a135-b9d70d0c77cf.png)


## 疎通確認用インスタンスの作成
- VPC-Bのsubnet(172.16.0.0/24)を指定して、Instance-B(対向疎通確認用)を作成する。
    - SecurityGroupで以下のInboundを許可しておく。
        - 10.0.0.0/16
        - 172.16.0.0/16

## 追加用ENIの作成
- VPC-Bのsubnet(172.16.0.0/24)を指定して、ENIを作成する。SecurityGroupはInstance-Bと同じものとする。

## Instance-Aへの別VPCのENIの追加
- 普通はマネコンを用いて、インスタンスに対してENIを追加アタッチできるが、2023/10/27時点で、マネコンのENI追加画面上に、他VPCのENIが出てこない。そのためCLIを用いてアタッチ作業を行う。こちらの記事「[複数のVPCにEC2インスタンスを接続する](https://dev.classmethod.jp/articles/attatch-ec2-to-multiple-vpc/)」を参照した。

```
[ec2-user@ip-10-0-0-156 ~]$ aws ec2 attach-network-interface --device-index 1 --instance-id i-xxxxxx(Instance-AのID) --network-interface-id eni-xxxxxx(追加するENIのID)
{
    "AttachmentId": "eni-attach-xxxxxxxxxxxxxxx",
    "NetworkCardIndex": 0
}
```
- Instance-Aに別VPCのENIが追加されたことを確認する。

![003.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/189302/0c42fc26-0d61-d097-7baf-1a31f8988537.png)

- Instance-AのOS(Amazon Linux 2023)では以下のように認識される。
```
[ec2-user@ip-10-0-0-133 ~]$ ifconfig
enX0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 9001
        inet 10.0.0.133  netmask 255.255.255.0  broadcast 10.0.0.255
        inet6 fe80::fa:97ff:febf:e127  prefixlen 64  scopeid 0x20<link>
        ether 02:fa:97:bf:e1:27  txqueuelen 1000  (Ethernet)
        RX packets 2242  bytes 269365 (263.0 KiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 2728  bytes 290915 (284.0 KiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

enX1: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 9001
        inet 172.16.0.11  netmask 255.255.255.0  broadcast 172.16.0.255
        inet6 fe80::5e:3bff:fe17:918b  prefixlen 64  scopeid 0x20<link>
        ether 02:5e:3b:17:91:8b  txqueuelen 1000  (Ethernet)
        RX packets 17  bytes 2312 (2.2 KiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 35  bytes 5876 (5.7 KiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

lo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536
        inet 127.0.0.1  netmask 255.0.0.0
        inet6 ::1  prefixlen 128  scopeid 0x10<host>
        loop  txqueuelen 1000  (Local Loopback)
        RX packets 12  bytes 1020 (1020.0 B)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 12  bytes 1020 (1020.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

[ec2-user@ip-10-0-0-133 ~]$ route
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
default         ip-10-0-0-1.us- 0.0.0.0         UG    512    0        0 enX0
default         ip-172-16-0-1.u 0.0.0.0         UG    522    0        0 enX1
ip-10-0-0-0.us- 0.0.0.0         255.255.255.0   U     512    0        0 enX0
ip-10-0-0-1.us- 0.0.0.0         255.255.255.255 UH    512    0        0 enX0
ip-10-0-0-2.us- 0.0.0.0         255.255.255.255 UH    512    0        0 enX0
ip-172-16-0-0.u 0.0.0.0         255.255.255.0   U     522    0        0 enX1
ip-172-16-0-1.u 0.0.0.0         255.255.255.255 UH    522    0        0 enX1
ip-172-16-0-2.u 0.0.0.0         255.255.255.255 UH    522    0        0 enX1
[ec2-user@ip-10-0-0-133 ~]$
```

## VPC-A内のInstance-AからVPC-B内のInstance-Bへの疎通確認
- 以下のように、VPC Peeringなどがないにも関わらず、ping疎通が可能になる。

```
[ec2-user@ip-10-0-0-133 ~]$ ping 172.16.0.44
PING 172.16.0.44 (172.16.0.44) 56(84) bytes of data.
64 bytes from 172.16.0.44: icmp_seq=1 ttl=127 time=0.879 ms
64 bytes from 172.16.0.44: icmp_seq=2 ttl=127 time=0.496 ms
64 bytes from 172.16.0.44: icmp_seq=3 ttl=127 time=0.512 ms
```

# 3. 気になること確認

## 3.1  VPC-A/VPC-B間の疎通可否

### ENIを2つアタッチしたインスタンスを経由して、VPC-AのインスタンスとVPC-Bのインスタンスを疎通させることが可能か？

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/189302/e61beefa-32f0-5c1a-9842-bfdb33dad018.png)

- 上記の構成(Instance-Aのiptables利用)での疎通ができることを確認した。
- Instance-AのOSでipフォワーディングを有効化。
- Instance-Aのiptablesの設定は以下。

```
sudo iptables -t nat -A PREROUTING -p tcp --dport 80 -j DNAT --to-destination 172.16.0.44:80
sudo iptables -t nat -A POSTROUTING -p tcp -d 172.16.0.44 --dport 80 -j MASQUERADE
``` 
- Instance-Cで 「curl 10.0.0.133」して、Instance-A経由でInstance-Bのnginxにアクセスできる。



![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/189302/3df3d448-f49d-daa0-3a28-c5a5a4f1bbfb.png)

- 上記の構成(Instance-Aを普通にルータとして使用)での疎通も可能なことを確認した。
- Instance-AのOSでipフォワーディングを有効化。
- Instance-AにアタッチしたENI2つで、「送信元/送信先チェック」を無効にする。
- VPC-Aのsubnet(10.0.0.0/24)に紐づくルートテーブルにおいて、VPC-Bのsubnet(172.16.0.0/24)へのターゲット(パケットの出し先)としてInstance-AのENIを設定する。VPC-B側でも同様に設定する。
- Instance-Cで「ping 172.16.0.44」を実行すると、pingが成功する。

## 3.2 VPCやSubnetのCIDR重複

### VPCやSubnetのCIDR重複があるとどうなるのか？

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/189302/0b6b0096-bcd7-7e49-b558-fda30808d37d.png)
- VPC-A(10.0.0.0/16) と全く同じCIDR/subnet構成を持つVPC-C(10.0.0.0/16)を用意する。
- VPC-Cのsubnet(10.0.0.0/24)にENIを作成し、それをInstance-Aにアタッチすることができた。
- その時のOSでの認識は以下。
```
[ec2-user@ip-10-0-0-133 ~]$ ifconfig
enX0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 9001
        inet 10.0.0.133  netmask 255.255.255.0  broadcast 10.0.0.255
        inet6 fe80::fa:97ff:febf:e127  prefixlen 64  scopeid 0x20<link>
        ether 02:fa:97:bf:e1:27  txqueuelen 1000  (Ethernet)
        RX packets 92480  bytes 31771708 (30.2 MiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 81384  bytes 8507428 (8.1 MiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

enX1: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 9001
        inet 10.0.0.44  netmask 255.255.255.0  broadcast 10.0.0.255
        inet6 fe80::94:b0ff:fe4e:e1db  prefixlen 64  scopeid 0x20<link>
        ether 02:94:b0:4e:e1:db  txqueuelen 1000  (Ethernet)
        RX packets 32  bytes 2676 (2.6 KiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 62  bytes 8053 (7.8 KiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

lo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536
        inet 127.0.0.1  netmask 255.0.0.0
        inet6 ::1  prefixlen 128  scopeid 0x10<host>
        loop  txqueuelen 1000  (Local Loopback)
        RX packets 34  bytes 3484 (3.4 KiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 34  bytes 3484 (3.4 KiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
```
- Instance-AからInstance-Cへのpingは成功、Instance-Dへは失敗する。

```
[ec2-user@ip-10-0-0-133 ~]$ ping 10.0.0.187
PING 10.0.0.187 (10.0.0.187) 56(84) bytes of data.
64 bytes from 10.0.0.187: icmp_seq=1 ttl=127 time=0.724 ms
64 bytes from 10.0.0.187: icmp_seq=2 ttl=127 time=0.572 ms
64 bytes from 10.0.0.187: icmp_seq=3 ttl=127 time=0.413 ms
64 bytes from 10.0.0.187: icmp_seq=4 ttl=127 time=0.535 ms
^C
--- 10.0.0.187 ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3142ms
rtt min/avg/max/mdev = 0.413/0.561/0.724/0.110 ms
[ec2-user@ip-10-0-0-133 ~]$ ping 10.0.0.89
PING 10.0.0.89 (10.0.0.89) 56(84) bytes of data.
From 10.0.0.133 icmp_seq=1 Destination Host Unreachable
From 10.0.0.133 icmp_seq=2 Destination Host Unreachable
From 10.0.0.133 icmp_seq=3 Destination Host Unreachable
^C
--- 10.0.0.89 ping statistics ---
5 packets transmitted, 0 received, +3 errors, 100% packet loss, time 4181ms
pipe 3
```

# 4. 所感
- 取り急ぎ基本動作の確認を行ったので記事公開する。様々な設計パターンを追加検証したい。