microsoft / WSL

Issues found on WSL
https://docs.microsoft.com/windows/wsl
MIT License
17.26k stars 812 forks source link

netlink should not present WiFi interface as ARPHRD_IEEE80211 #2996

Closed yoursunny closed 5 years ago

yoursunny commented 6 years ago

Windows build number: Microsoft Windows [Version 10.0.16299.248]

What you're doing and what's happening: My laptop has a Atheros QCA9377 WiFi interface. I am trying to run NFD 0.6.1 within Ubuntu environment. Part of this program uses netlink socket to enumerate network interfaces, and determine which network interfaces can be used for UDP multicast. However, netlink reports that wifi0 interface has type ARPHRD_IEEE80211, which indicates the WiFi interface is in monitor mode, and causes NFD to conclude this network interface is unusable.

This is also observable with ip link command:

sunny@sunny5:~$ ip link show wifi0
17: wifi0: <BROADCAST,MULTICAST,UP> mtu 1500 group default qlen 1
    link/ieee802.11 3c:a0:67:f4:11:65

What should be happening instead: The netlink socket should report wifi0 interface as ARPHRD_ETHER type.

As comparison, on a regular Ubuntu machine (Raspberry Pi 3 with Ubuntu Mate 16.04), WiFi interface is correctly presented as ARPHRD_ETHER:

sunny@pimate:~$ ip link show wlan0
4: wlan0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether b8:27:eb:20:b5:e2 brd ff:ff:ff:ff:ff:ff

See also bug report with NFD: https://redmine.named-data.net/issues/4534

therealkenc commented 6 years ago

Pretty sure NFD is not going to fly because socket(AF_NETLINK, SOCK_RAW | SOCK_CLOEXEC, NETLINK_ROUTE) here, which is #2249. As a separate matter WSL doesn't support arp either #2279, but I don't think that's the fundamental issue.

You can try editing the code and return InterfaceType::ETHERNET unilaterally and see what happens (I have not).

Someone else will have to rule on whether ARPHRD_IEEE80211 is "correct" here. I kind of suspect it is correct (for some definition of correct), but not enough to jump the gun.

Pesa commented 6 years ago

Why is socket(AF_NETLINK, SOCK_RAW | SOCK_CLOEXEC, NETLINK_ROUTE) a problem? Based on what I'm reading around, WSL does support NETLINK_ROUTE for link and address messages (RTM_NEWLINK and RTM_NEWADDR), which is all NFD needs. As a matter of fact, ethernet interfaces are detected correctly without any code modifications.

ARP has nothing to do with this, the "ARP" in the names of ARPHRD_* constants is historical I think.

I'm not sure what "correct" means in this context, but the Linux kernel reports wifi interfaces in station mode as ARPHRD_ETHER, I guess because you just send/receive regular ethernet frames on them. ARPHRD_IEEE80211 and other ARPHRD_IEEE80211_* constants are reserved for monitor-mode interfaces, again I guess because they use the raw 802.11 frame format.

therealkenc commented 6 years ago

Why is socket(AF_NETLINK, SOCK_RAW | SOCK_CLOEXEC, NETLINK_ROUTE) a problem?

Looked again and you're correct; if all they are doing is enumerating interfaces you should be fine with that particular call.

ARP has nothing to do with this, the "ARP" in the names of ARPHRD_* constants is historical I think.

Yes that is why I said as a separate matter. It is not related to your fail.

I guess because you just send/receive regular ethernet frames on them

You don't send link layer frames of any type on WSL. I assumed NFD was going to try to do so, since it checks. If it is not, then you can try editing the code and return InterfaceType::ETHERNET unilaterally and see what happens (I have not).

therealkenc commented 6 years ago

I enabled WSL on my laptop for the lulz and it reports link/ieee802.11 as well. I suspect (but can't prove) WSL simply parrots the link encap that the underlying Windows driver reports. [The less likely but possible alternative being WSL sticks ARPHRD_IEEE80211 in there on it's own just because it's a wireless interface and that seemed like a good idea at the time.] It seems from the response you got NFD deliberately ignores such interfaces (as well as say ARPHRD_TUNNEL) by design.

Brian-Perkins commented 6 years ago

WSL is doing a conversion from interface type to the ARPHRD_* type, but the conversion logic is essentially mnemonic (ethernetCsmacd->ARPHRD_ETHER, softwareLoopback->ARPHRD_LOOPBACK, ieee80211->ARPHRD_IEEEE80211, et al.). If Linux always reports ARPHRD_ETHER for all ethernet based interfaces then we can do the same.

Pesa commented 6 years ago

From a quick look at linux kernel sources, ARPHRD_IEEEE80211 is in fact only used for monitor mode in some very old wifi drivers. Modern drivers (mac80211-based) use ARPHRD_ETHER in all interface modes except for monitor mode (NL80211_IFTYPE_MONITOR) where ARPHRD_IEEE80211_RADIOTAP is used.

Brian-Perkins commented 6 years ago

This should be addressed in the Skip-ahead 17627 build.