My laptop has an Intel Corporation Wireless 8260 (rev 3a) wireless card. It says so right in the lspci -v output:
02:00.0 Network controller: Intel Corporation Wireless 8260 (rev 3a)
Subsystem: Intel Corporation Dual Band Wireless-AC 8260
Flags: bus master, fast devsel, latency 0, IRQ 327
Memory at dc400000 (64-bit, non-prefetchable) [size=8K]
Capabilities: [c8] Power Management version 3
Capabilities: [d0] MSI: Enable+ Count=1/1 Maskable- 64bit+
Capabilities: [40] Express Endpoint, MSI 00
Capabilities: [100] Advanced Error Reporting
Capabilities: [140] Device Serial Number a4-34-d9-ff-ff-38-91-54
Capabilities: [14c] Latency Tolerance Reporting
Capabilities: [154] L1 PM Substates
Kernel driver in use: iwlwifi
Kernel modules: iwlwifi
However, in Linux it’s been dropping out and going slow and all sorts of rubbish. Looking in dmesg you can typically see stuff like (edited):
Loaded firmware version: 22.361476.0
iwlwifi 0000:02:00.0: 0x00000084 | NMI_INTERRUPT_UNKNOWN
Lots more red text here...
So can we fix it? Like Bob the Builder, yes we can – but it’s a two-step…
Part 1 – Kernel Modules
The 8260 card uses the iwlwifi kernel module, and the microcode for that is stored in /lib/firmware.
Specifically, you’re looking for the files: iwlwifi-8000C-SOME_NUMBER.ucode.
So for example, I see the following:
r3dux [ /lib/firmware ]$ ls -alh /lib/firmware/iwlwifi-8000C*
-rw-r--r-- 1 root root 1.7M Oct 5 21:35 /lib/firmware/iwlwifi-8000C-13.ucode
-rw-r--r-- 1 root root 2.3M Oct 5 21:35 /lib/firmware/iwlwifi-8000C-16.ucode
-rw-r--r-- 1 root root 2.3M Oct 5 21:35 /lib/firmware/iwlwifi-8000C-21.ucode
-rw-r--r-- 1 root root 2.1M Oct 5 21:35 /lib/firmware/iwlwifi-8000C-22.ucode
The kernel seems to pick the highest number in the 8000C range, so it’ll pick the 8000C-22 variant. Only this is borked. To revert to the previous 21 revision, simply rename the file extension of the 22 version to something different, for example:
sudo mv /lib/firmware/iwlwifi-8000C-22.ucode /lib/firmware/iwlwifi-8000C-22.ucode.BORKED
However, at least in my experience, this isn’t enough to stop the module crash/restart issues – so we need to…
Part 2 – Disable Wireless N
If I just do the above, I still get issues in dmesg where the wireless card’s crashing and resetting itself – so to bypass the failing code, we need to disable wireless N (and only use B/G). Sure, this is going to be slower than N, but it’s going to be faster than a borked version of N – so off we go…
The parameters to the iwlwifi module include one called 11n_disable – and to set that on boot we need to have a /etc/modprobe.d folder (create the directory if necessary), then into that put a file with any name ending in .conf such as iwlwifi.conf (makes sense, right?) with the following contents:
options iwlwifi 11n_disable=1
Once that’s in and saved, reboot and your wireless should work properly again – no dmesg crash data, no slow-downs, no bullshit.
There are actually a few different values that can be used, but “1” works for me. The array of valid values for the 11n_disable property can be seen by entering:
And the current settings can be checked by hitting:
With the 21 revision of the microcode and wireless-N disabled you should find your wireless card now works properly. Huzzah!
Misc
You may want to know that I did this on an Arch Linux system (kernel: 4.8.13-1-ARCH linux-firmware: 20161005.9c71af9-1), and that I also set my regulatory authority code which controls allowable wireless frequencies/channels (via installing the crda package and setting the config to my local country, which is Australia, so “AU” – further reading: https://wiki.archlinux.org/index.php/Wireless_network_configuration#Respecting_the_regulatory_domain) – although I’m not sure if changing the regulatory domain actually did anything to the above fix instructions. Thought I’d mention it all the same.
Cheers!