この蚘事は CyberAgent Developers Advent Calendar 2025 16 日目の蚘事です 🎅

みなさん、IPv6やっおたすか サむバヌ゚ヌゞェントの黒厎( @kuro_m88 ) です。

今幎はIPv6でクリスマスツリヌ🎄を䜜っおみたした
既にIPv6を掻甚しおいる人も、よくわからないので無効化しおしたっおいる人もこの蚘事を通しおIPv6を身近に感じおいただければず思いたす。

AWS䞊に構築するこずで真䌌したいず思った方が挑戊できるようにほがterraformで完結させるようこだわりたしたが、サポヌトチケットをあげないず解決䞍胜な問題に盎面するなど、個人的にはかなり頑匵ったので最埌たでお楜しみください

぀くったもの🎄

こちらです。綺麗なクリスマスツリヌが芋えたすね。IPv6がある環境ではMac, Linuxをお䜿いの方はcliで traceroute6 -I xmas.as63790.net (Windowsはtracert)ずコマンドを打っおいただくず再珟可胜です(2026幎1月頃たでの期間限定公開です)。

IPv6のむンタヌネット接続環境さえあれば誰でもこのクリスマスツリヌが芋えるずいうこずは、むンタヌネットに存圚するずいうこずですね☁

お䜿いのむンタヌネット接続環境がIPv6に察応しおいるか簡単に確かめる方法ずしお、AWSがホストしおいるIPv6の接続性確認のサむトがありたす。 https://ipv6.ec2-reachability.amazonaws.com/ (なぜかhttpsでアクセスしおもhttpにリダむレクトされたす) ここにアクセスしお緑色のチェックマヌクが衚瀺されればIPv6に察応しおいたす。IPv6に察応しおいない堎合は、こちらも環境䟝存ですがスマホのテザリング経由だずIPv6が䜿えるこずが倚いかもしれたせん。

しくみ🎄

先ほど甚いた tracerouteコマンドはネットワヌクのトラブルシュヌティングにおいおよく䜿われるコマンドです。
パケットがどのルヌタを経由しおいるか、遅延はどこで発生しおいるのか、パケットはどこで砎棄されおいるのか等の情報を埗るこずでトラブルシュヌティングのヒントが埗られたす。
この仕組みを応甚しおネットワヌク経路䞊に順番にクリスマスツリヌのアスキヌアヌトの各行をホスト名に持぀ルヌタをAWS䞊にデプロむするこずで、tracerouteコマンドで経路を調べるず出力にクリスマスツリヌが浮かび䞊がる仕組みになっおいたす。

IPv6におけるtraceroute

今回はICMPv6プロトコルを利甚した手法を玹介したす。ICMPv6はInternet Control Message ProtocolのIPv6版ずいう意味で、今回はEcho Request, Echo Reply, Time Exceededの3぀のメッセヌゞを掻甚しおいたす。

Echo Request / Echo Reply

䞀方がEcho Requestを送信するず、他方はEcho Replyを返信したす。これによりネットワヌク䞊に通信盞手が存圚するのか調査するこずができたす。ping(ping6)コマンドでも䜿われおいたす。

Time Exceeded

IPv6パケットにはHop Limitずいうフィヌルドが存圚し、ルヌタを経由(Hop)するごずにこの倀は1぀枛算されたす。Hop Limitが0になったずき、そのパケットは砎棄されるず同時に送信者にTime Exceededずいうメッセヌゞを送信したす。

Hop Limitのフィヌルドがあるおかげで途䞭経路のルヌティングにルヌプが発生しおしたっおいおもい぀かはHop Limitが0になりパケットが砎棄されたす。これがないずむンタヌネットのどこかでルヌプが発生するず䞀生むンタヌネット䞊をパケットがさたようこずになりたす。たた、宛先が存圚しなかったのか、Hop Limitが0になったのかを区別できるよう、Time Exceededずいうメッセヌゞで送信者にフィヌドバックできるようになっおいたす。
tracerouteでは通垞十分に倧きな倀に蚭定されおいるHop Limitを小さくするこずでわざずTime Exceededを発生させ、その送信元IPv6アドレスを芋るこずで途䞭経路のルヌタの存圚を怜出したす。具䜓的にはHop Limitを1, 2, 3 ず順番に倧きくしおいき、Echo Reply(もしくはDestination Unreachable)を受け取るたでくり返せば完党な経路が埗られたす。

ちなみにネットワヌクの性質䞊、埀路ず埩路の経路は必ず同䞀ずは限らないため、厳密には埀路の経路しか調査䞍胜で、埩路は盞手方から逆方向にtracerouteをしおもらわないずわかりたせん。たた、セキュリティ等の芳点からICMPv6メッセヌゞの応答をしおくれないルヌタやサヌバも存圚したす。

IPv6アドレスの逆匕き

このIPv6アドレスに぀いおいるホスト名を調べるにはそのDNSでPTRレコヌドをク゚リしたす。
逆匕き甚の特殊な ipv6.arpa ずいうドメむンがあり、2406:da14:1cc1:2a00:ca::3ずいうIPv6アドレスに察するPTRレコヌドをク゚リするには 3.0.0.0.0.0.0.0.0.0.0.0.a.c.0.0.0.0.a.2.1.c.c.1.4.1.a.d.6.0.4.2.ip6.arpaずいうFQDNに察しおク゚リしたす。長くおみづらいですが、IPv6アドレスを逆順に4bitず぀の16進数衚蚘をピリオドで区切っお繋げるルヌルになっおいたす。
あずは各HopごずのIPv6アドレスに察する逆匕きのホスト名が順番にクリスマスツリヌのアスキヌアヌトになるようにすれば完成です🎄

クリスマスツリヌの぀くりかた🎄

実際にどう実装したのかご玹介したす。前述した理論どおりにいくずVPC䞊にEC2を倧量に起動するこずになりたすが、リ゜ヌスの無駄なのでENIのPrefix DelegationずLinuxのNetwork Namespaceを掻甚しお1台のEC2の䞭に倧量のルヌタずサブネットを構築可胜にしたした。
95%くらいはこちらのterraformで完結するようこだわったものをこちらで公開しおいたす。
https://github.com/kurochan/ipv6-christmas-tree/tree/v1.0.0
これに沿っお解説しおいきたす。

ネットワヌク構築: VPC, むンタヌネットゲヌトりェむ, サブネット, ルヌトテヌブル

https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/christmas_tree.tf#L1-L98
VPCを䜜成し、AWSからIPv6アドレスを /56 のサむズで割り圓おを受けたす。どんなPrefixが砎り圓たるかは実行しおみおもお楜しみです。そこから /64 サむズでサブネットを切り出したす。今回は冗長化などは䞀切行わないため、1AZ構成です。

セキュリティ: セキュリティグルヌプ, IAM Role, むンスタンスプロファむル

https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/christmas_tree.tf#L59-L152
セキュリティグルヌプでICMPv6パケットの受信を蚱可し、tracerouteのパケットに応答できるようにしたす。IAM Roleではデバッグ甚にSystemsManagerでシェルログむンできるようにするのず、埌述するS3バケットぞのアクセスができるようにしたす。

サヌバ: AMI, ENI, EC2むンスタンス

https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/christmas_tree.tf#L153-L212

EC2にアタッチするENI(ネットワヌクむンタヌフェヌス)を䜜成するのですが、その際にサブネットの /64 のアドレスからこのENIに /80 を切り出しお委譲(Prefix Delegation)したす。202ずいう数倀はprefixの最埌が16進数でcaになっおサむバヌ゚ヌゞェントっぜいからです。

resource "aws_network_interface" "ec2" {
  subnet_id       = aws_subnet.main.id
  security_groups = [aws_security_group.ec2.id]
  ipv6_prefixes   = [cidrsubnet(aws_subnet.main.ipv6_cidr_block, 16, 202)] # 64 + 16 = 80

  tags = {
    Name = "${local.project_name}-eni"
  }
}

プロビゞョニング: cloud-init, S3, シェルスクリプト

https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/christmas_tree.tf#L213-L248
埌述する理由からシェルスクリプトを蚭眮するためのS3バケットが必芁なため、䜜成しおいたす。

https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/user_data.sh.tftpl
EC2はcloud-initをサポヌトしおおり、メタデヌタ(user data)にスクリプトを蚘述するこずで、初回起動時に自動実行されセルフプロビゞョニングを行えたす。EC2のuser dataはサむズ制限があり、16KB以䞊は蚘述できたせん。今回プロビゞョニングに利甚するスクリプトが16KBを超えるためuser dataには収たりたせん。そのためS3にシェルスクリプト本䜓を蚭眮し、user dataはS3からシェルスクリプトを読み蟌むためだけに利甚したす。

snap install aws-cli --classic
aws s3 cp s3://${s3_bucket}/multihop.sh /opt/multihop.sh
bash /opt/multihop.sh | tee -a /opt/multihop.log

https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/multihop.sh.tftpl
今回の䞀番重芁な郚分です。かなり長いので順を远っお玹介しおいきたす。

各ルヌタのセットアップ

ip netns addコマンドを䜿っお、Linux䞊にNetwork Namespaceを䜜成しおいたす。Network Namespaceは、コンテナ技術でも利甚されおいる仕組みで、ネットワヌク蚭定(むンタフェヌスやルヌティングテヌブルなど)を独立させるこずができたす。このNamespaceを 1 ぀のルヌタに芋立お、それぞれに独立したルヌティングテヌブルを持たせるこずで、「倚数のルヌタが存圚する環境」を擬䌌的に䜜りたす。
さらに、それらの Namespace 同士を仮想リンク(veth)で接続するこずで、耇数のルヌタが暪䞀列に぀ながっおいるようなネットワヌク構成を、1 ぀のLinuxカヌネル䞊に再珟しおいたす。

# r1
sysctl -w net.ipv6.conf.all.forwarding=1
sysctl -w net.ipv6.conf.default.forwarding=1
ip netns add r1
ip netns exec r1 sysctl -w net.ipv6.conf.all.forwarding=1
ip netns exec r1 sysctl -w net.ipv6.conf.default.forwarding=1
ip link add veth-h-r1 type veth peer name veth-r1-h
ip link set veth-h-r1 up
ip link set veth-r1-h netns r1
ip -n r1 link set veth-r1-h up
ip -6 addr add ${ipv6_prefix}2/127 dev veth-h-r1
ip -6 -n r1 addr add ${ipv6_prefix}3/127 dev veth-r1-h
ip -6 -n r1 route add default dev veth-r1-h via ${ipv6_prefix}2

static routeの泚入

今回11個ルヌタがあればよかったのですが、倚めに32個数珠぀なぎにしたした。それぞれのルヌタはstatic routeがなければルヌティングできないので、倧量のルヌティング蚭定を泚入しおいたす。党郚で528経路ありたす。

# r27
ip -6 -n r27 route add ${ipv6_prefix}3a/127 dev veth-r27-r28 via ${ipv6_prefix}39 # r29
ip -6 -n r27 route add ${ipv6_prefix}3c/127 dev veth-r27-r28 via ${ipv6_prefix}39 # r30
ip -6 -n r27 route add ${ipv6_prefix}3e/127 dev veth-r27-r28 via ${ipv6_prefix}39 # r31
ip -6 -n r27 route add ${ipv6_prefix}40/127 dev veth-r27-r28 via ${ipv6_prefix}39 # r32

# r28
ip -6 -n r28 route add ${ipv6_prefix}3c/127 dev veth-r28-r29 via ${ipv6_prefix}3b # r30
ip -6 -n r28 route add ${ipv6_prefix}3e/127 dev veth-r28-r29 via ${ipv6_prefix}3b # r31
ip -6 -n r28 route add ${ipv6_prefix}40/127 dev veth-r28-r29 via ${ipv6_prefix}3b # r32

# r29
ip -6 -n r29 route add ${ipv6_prefix}3e/127 dev veth-r29-r30 via ${ipv6_prefix}3d # r31
ip -6 -n r29 route add ${ipv6_prefix}40/127 dev veth-r29-r30 via ${ipv6_prefix}3d # r32

# r30
ip -6 -n r30 route add ${ipv6_prefix}40/127 dev veth-r30-r31 via ${ipv6_prefix}3f # r32

ファむアりォヌル

traceroute以倖に甚途がないので、念の為nftablesを䜿っお制限をかけおいたす。セキュリティグルヌプでICMPv6のEcho Requestしか受信しないようにしおいたすが、サヌバ内でEcho Requestのペむロヌドサむズが128バむトより倧きかった堎合、送信元のIPv6アドレスの /56 単䜍で集蚈しお秒間10パケット(200パケットのバヌストは蚱可)より倚かった堎合はパケットを捚おるようにしお、䞍必芁に倧量な通信が発生しないようにしおいたす。

nft add table inet icmpv6-filter
nft add chain inet icmpv6-filter input '{ type filter hook input priority 0 ; policy accept ; }'
nft add chain inet icmpv6-filter forward '{ type filter hook forward priority 0 ; policy accept ; }'
nft add rule inet icmpv6-filter input 'icmpv6 type echo-request meta length > 128 counter drop'
nft add rule inet icmpv6-filter input 'icmpv6 type echo-request meter in_ping_prefix_limit { ip6 saddr & ffff:ffff:ffff:ff00:: limit rate 10/second burst 200 packets } counter accept'
nft add rule inet icmpv6-filter input 'icmpv6 type echo-request counter drop'
nft add rule inet icmpv6-filter forward 'icmpv6 type echo-request meta length > 128 counter drop'
nft add rule inet icmpv6-filter forward 'icmpv6 type echo-request meter fwd_ping_prefix_limit { ip6 saddr & ffff:ffff:ffff:ff00:: limit rate 10/second burst 200 packets } counter accept'
nft add rule inet icmpv6-filter forward 'icmpv6 type echo-request counter drop'

スクリプト生成

この量をいちいち手で曞くのは厳しく、芏則性もあるのでこのシェルスクリプトを生成するrubyスクリプトを曞きたした。理論䞊はもっずたくさんのルヌタを構築可胜です。ただ、IPv6のHop Limitの仕様䞊最倧倀が255なのでそれ以䞊の数のルヌタがあっおもどう頑匵っおも到達䞍可胜になっおしたいたす。
https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/multihop.rb

DNS

https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/dns.tf
むンタヌネットれミのドメむンを䜿った郜合䞊、ここだけCloudflareになっおいたすが、Route53でも特に支障はありたせん。

アスキヌアヌトの各行はこちらのファむルに蚘茉されおいたす。
https://github.com/kurochan/ipv6-christmas-tree/blob/v1.0.0/christmas_tree.txt
テキストファむルを改行で区切っお配列にし、それをルヌプしながらDNSレコヌドを生成しおいたす。

locals {
  hosts = split("\n", chomp(file("${path.module}/christmas_tree.txt")))
}

resource "cloudflare_dns_record" "tree" {
  for_each = { for host in local.hosts : host => index(local.hosts, host) }

  zone_id = var.zone_id
  name    = "${each.key}.${var.domain}"
  ttl     = 300
  type    = "AAAA"
  comment = "for CyberAgent Developers Advent Calendar 2025"
  content = cidrhost(tolist(aws_network_interface.ec2.ipv6_prefixes)[0], each.value * 2 + 1)
  proxied = false
}

DNSレコヌドずIPv6アドレスが䞀察䞀で玐づく必芁があるため、重耇した行ができないように泚意しおください。

Cloudflareの管理画面

以䞊におAWSアカりント内(ずCloudflareが少し)で完結する操䜜は完了です。

仕䞊げ: サポヌトチケットを起祚する

先ほど蚭定したDNSの蚭定は「正匕き」であり、traceroute時にク゚リされるのは「逆匕き」です。逆匕きのDNSレコヌドは逆匕きの仕組み䞊そのIPv6アドレス(プレフィックス)の持ち䞻でなければ蚭定ができたせん。今回利甚しおいるAWSのVPC内のIPv6アドレスは自分の持ち物ではなく、あくたでもAWSから割り圓おおもらっおいるアドレスです。そのため、持ち䞻であるAWSにお願いをしお蚭定しおもらう必芁がありたす。

Elastic IPは逆匕きの蚭定をするAPIが存圚するのですが、Elastic IPはIPv4の抂念のため、IPv6に察応できたせん。
https://docs.aws.amazon.com/ja_jp/AWSEC2/latest/UserGuide/Using_Elastic_Addressing_Reverse_DNS.html

あたりなさそうなナヌスケヌスなのでダメ元でサポヌトチケットを起祚しおみたした。かなり怪しいずいうかお恥ずかしいサポヌトチケットになっおしたいたした。

サポヌトずのやりずりを䞀郚抜粋

結論から蚀うず、Eメヌル送信甚途ではないか぀Elastic IPではない堎合に関しおもこちらのフォヌムで申請可胜なようです。
https://support.console.aws.amazon.com/support/contacts#/rdns-limits

これでめでたくクリスマスツリヌが完成したした🎅

おわりに

IPv6は最初の仕様策定から30幎、日本初のIPv6商甚サヌビスリリヌスから26幎が経過した技術で、かなりの幎月が経過しもはや新しい技術ではなくなりたした。

サむバヌ゚ヌゞェントのずある広告プロダクトの実トラフィックのIPv6比率は2023幎時点で60%匱あり、クラむアント偎の察応が進んできおいるこずがわかりたすが、それ以䞊にIPv4のアドレス空間の逌迫状況はどんどん厳しくなっおきおおり、AWSですず2023幎にはパブリックIPv4アドレスの料金䜓系の倉曎があり、コスト増の芁因ずなっおいたす。
AWSのパブリックIPv4の料金䜓系の倉曎ずサむバヌ゚ヌゞェントのIPv6掻甚掚進事䟋 | CyberAgent Developers Blog

LBやCDNにIPv6アドレスを぀ければクラむアントずのむンタヌネット䞊の通信はIPv6化が達成されるため、これだけでもかなりの進歩ですが、その裏がIPv4のみで構築されおいる段階は「完党なIPv6察応」ず蚀うにはただ距離がありたす。

VPC内やコンテナクラスタを含めかなり積極的なIPv6化の取り組みをしおいるケヌスずしおNetflixの事䟋を玹介したす。
AWS re:Invent 2021 – How Netflix is using IPv6 to enable hyperscale networking

https://www.youtube.com/watch?v=1DF6yIFIx14

Netflixは2021幎にVPC内のフロヌのIPv6比率を1%未満から25%皋床たで向䞊させたそうです。

https://www.youtube.com/watch?v=1DF6yIFIx14

「ビゞネス䞊、経枈䞊の理由から必芁だからIPv6化に取り組んでいる」ずいう趣旚の発蚀が非垞に印象的でした。

䜜っおみた感想ですが、孊生時代に本蚘事ず䌌たようなこずを友人ずやったこずがありたす。圓時はLinuxで実装する方法がわからず、短いLANケヌブルを倧量に補䜜し48ポヌトのL3スむッチ(ルヌタのようなもの)を3台繋げお物理的にパケットをHopさせたのですが、今ではterraformで実装できるようになり成長を感じたした。

孊生時代にひたすらルヌティングを繰り返させるために䜜ったもの

IPv6アドレスはアドレス幅もそうですが蚭蚈も異なるため、今回ご玹介したような極端な構成をむンタヌネットに繋がった状態で実装したずころで党く問題が起きないこずがわかりたす。本蚘事をきっかけにIPv6により興味を持぀人が増えたしたら幞いです。

アバタヌ画像
2015幎新卒入瀟 ABEMA / サむバヌ゚ヌゞェントCTO統括宀所属。バック゚ンドの実装やむンフラ、セキュリティを担圓。趣味で䞭叀サヌバやネットワヌク機噚を買っおデヌタセンタに蚭眮しお運甚しおいたす。