One end of your IPv6 tunnel pings the other, and only one direction ever answers. The interface is up, the route looks right, and nothing in the log explains it. The address you assigned is the subnet-router anycast address, which is not a host address at all, and on a two-endpoint link it has exactly one delivery target: the sender. No timeout value repairs that, because the address is not doing what you think it does.

The symptom that points at the address

Every host on the link answers except the one whose interface identifier is all zeroes. A packet addressed to that form is delivered to a router on the subnet by definition, so on a point-to-point tunnel it comes back to the machine that sent it. From the far end this reads as an unreachable peer; from the near end it reads as silence. Swap in a different identifier from the same prefix and the symptom disappears with no other change, which is the confirmation to get before touching routes.

The all-zero identifier is reserved as anycast

RFC 4291 keeps the all-zero interface identifier as the subnet-router anycast address, so a /64 such as 2001:db8:4a::/64 contains no usable host at 2001:db8:4a::. The reservation earns its place: router advertisements and neighbour discovery address that form, and a router answers for the prefix it serves. Assigning that value to a tunnel endpoint hands a router role to a leaf, which is why nothing comes back. Any other identifier in the prefix works as a host, so the repair is usually one digit.

Treat the reservation as a role you are not entitled to occupy from a tunnel endpoint, rather than as a quirk to route around.

Assign host addresses and route the prefix

Pick ::1 and ::2 for the two ends, add one with ip -6 addr add 2001:db8:4a::2/64 dev tun0, and then route the remote prefix rather than trying to address it. A route for 2001:db8:4a::/64 out of the tunnel makes the far side reachable; the address alone only makes the local interface configured.

For a full tunnel there is a third step, a default route for global unicast through the device, which is the IPv6 equivalent of sending everything into the tunnel. Skip it and IPv6 keeps using the physical link while IPv4 travels inside the tunnel, so the host leaks precisely the traffic you believed was covered. Confirm with ip -6 route get 2001:4860:4860::8888 and read which device it names instead of assuming the answer.

Multicast is refused before routing

Android validates addresses and routes for VpnService.Builder through LinkAddress, and that constructor refuses multicast outright. Hand it a multicast prefix as a route and the result is a bad LinkAddress parameters failure rather than a route, which is a validation answer and not a network one. The refusal matches the medium: a point-to-point tun device has no link-layer multicast, so a group route on it has no delivery model to install. Group addresses are created and consumed by the stack itself rather than configured by hand.

IPv6 all-nodes and solicited-node addresses fall under the same rule. The interface carries them because the stack put them there, not because a policy intended them.

What a tunnel can carry instead

Moving multicast discovery across a tunnel needs a layer that understands group membership: a TAP bridge presenting an Ethernet segment, an application-level relay, or a routing protocol told explicitly which peers to replicate to. None of that exists in the VpnService model, where the application reads and writes packets and has no call that joins a group for the tunnel. Either add the component that does understand groups or drop the requirement from the design.

Unicast, by contrast, needs nothing extra beyond the addresses and routes above, which is why tunnels are usually expected to carry it and then blamed when a discovery protocol fails.

Three checks before you assign anything

Confirm the address is not the anycast form, confirm it is not multicast, and confirm the prefix is routed rather than merely assigned to the device. Then send your test to a destination that is a real host, because a ping aimed at the anycast address measures the sender and tells you nothing about the path. Keep those three checks in the change record so the next deployment does not rediscover them.

A route the platform never installed cannot be debugged by waiting longer, and an address that was never a host cannot be repaired by a better ping.

Lahatsoratra mifandraika