Skip to content

Implement dual-stack support#861

Open
DerEnderKeks wants to merge 4 commits intohome-assistant-libs:masterfrom
DerEnderKeks:dual-stack
Open

Implement dual-stack support#861
DerEnderKeks wants to merge 4 commits intohome-assistant-libs:masterfrom
DerEnderKeks:dual-stack

Conversation

@DerEnderKeks
Copy link
Copy Markdown
Contributor

@DerEnderKeks DerEnderKeks commented Feb 24, 2024

This PR adds support for IPv6 and thus dual-stack. It contains two changes:

  1. Unsetting the Host header when requesting the /setup/eureka_info endpoint, as I noticed that my NVIDIA Shield blocks any request (empty body with status code 403) when a domain is set in the header, at least when requesting via IPv6.
  2. Using a dual-stack socket and IPv6-mapped addresses for the protobuf socket. This remains fully compatible with legacy IPv4, as long as the host can open IPv6 sockets, which any OS from at least the last decade should be able to do.

Let me know if I overlooked anything, but the Youtube example now works fine with both, IPv4 and IPv6.

Comment thread pychromecast/dial.py Outdated
@emontnemery
Copy link
Copy Markdown
Collaborator

Please fix the CI issues

Copy link
Copy Markdown
Collaborator

@emontnemery emontnemery left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Some hosts will have ipv6 disabled, and creating an ipv6 socket will fail, the IPV6 specifics needs to be wrapped with an OSError check with fall back to IPv4.

@DerEnderKeks
Copy link
Copy Markdown
Contributor Author

The socket will now fall back to IPv4, for systems that are misconfigured to have IPv6 disabled ;)

Comment thread pychromecast/socket_client.py Outdated
Comment thread pychromecast/socket_client.py Outdated
@emontnemery
Copy link
Copy Markdown
Collaborator

@DerEnderKeks please don't amend your previous commit when making changes, it makes it hard to review
(this project always squashes before merge, so no matter how many commits are on your branch, it will end up as a single commit)

@DerEnderKeks
Copy link
Copy Markdown
Contributor Author

Alright (although I always consider it an unnessacary loss of information when you squash PRs into a single commit).
I fixed the formatting, the check should pass now.

@elupus
Copy link
Copy Markdown
Collaborator

elupus commented Aug 29, 2024

Is there any need/benefit of the new happy eyeball stuff you working on @bdraco

@bdraco
Copy link
Copy Markdown
Member

bdraco commented Aug 29, 2024

All of that work is for asyncio so it wouldn’t apply here

Comment thread pychromecast/socket_client.py Outdated
# falling back to IPv4 on systems without IPv6
new_sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

new_sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks strange to me. We are not making sure the socket type matches the data returned from getaddrinfo. The creation of the socket should be postponed until we have resolved the name using getaddrinfo

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There isn't really a need to match the socket to the resolved address type, as the dual-stack socket can connect to both types. If it falls back to a v4-only socket and only a v6 address is returned, it would fail to connect either way,

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I dont agree, if we are using getaddrinfo to get the host info, we should respect what it return.

By using an INET6 socket with IPV6_V6ONLY disabled, legacy IPv4 can still be reached. To connect to v4 IPs, the addresses are mapped to IPv6. IPv6 addresses are only used when a hostname resolves to one and the system has a non-local IPv6 available. For hosts with IPv6 completely disabled for some reason, the socket falls back to v4-only.
@elupus
Copy link
Copy Markdown
Collaborator

elupus commented Sep 14, 2025

Since this sort of died out. I rebased the pull and added iteration over getaddrinfo results. @DerEnderKeks could you test if these changes work for your use case?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants