I am working with both TCP and UDP in an environment in which both IPv4 and IPv6 addresses exist. I recently got into trouble and traced the issue to the fact that I was attempting to bind to a local IPv6 address and then sendto (UDP) or connect (TCP) to a remote IPv4 address.

It is necessary to bind to a local address explicitly because I need to be able to control which interface is used for communications.

My question is, what is the best practice here? My current approach is to test whether the remote address is v4 or v6 and find a local address of the same type to bind to. Is that ideal? It seems like if the remote address is v6 but there are no local v6 addresses, then there should be a way to make it still work, since IPv4 can be embedded into v6, but I'm not sure of the mechanics necessary to ensure that. If the remote is v4 but there are only v6 addresses locally, there may be nothing I can do, but maybe there is if the local v6 address is v4 compatible?

I'm actually doing this in Java but I prefer to ask in this forum since it's more domain-specific, and the particular API calls are less important than what needs to happen conceptually. I am primarily interested in link-local communication for now if that makes a difference.