
funcionalidad wpa3 para el chip WiFi en un MacBook Pro de 2014
wl cerrado)Apple/Broadcom nunca le dio al BCM4360 (14e4:43a0) WPA3. Su único controlador para Linux es el blob cerrado broadcom-sta (wl); brcmfmac no puede manejarlo. Esto añade WPA3-SAE + PMF 802.11w completo a ese blob cerrado — enteramente desde software del host, sin código fuente del firmware.
Probado en el aire contra un AP solo WPA3, con MFP requerido: autenticación SAE → asociación → 4-way → datos CCMP, estable, y resistente a ataques de deauth-flood y SA-Query teardown.
El blob es un .o ELF reubicable y sin depurar (no es una imagen de firmware final) — esa es toda la razón por la que esto funciona. No lo reescribimos; enlazamos nuevo C contra él y redirigimos algunos puntos de llamada:
wpa_supplicant ejecuta SAE + el 4-way (la criptografía del blob es solo SHA-1; SAE necesita SHA-256).wl_cfg80211_hybrid.c, wl_linux.c) puentea auth/assoc/keys.auth para que acepte SAE (alg=3).objcopy --globalize-symbol — hacer que ~10 funciones internas del blob sean llamables desde nuestro C.wl_reloc.py — reescribir .rela.text para que las llamadas del blob a wlc_recv/wlc_sendauth/wlc_authresp_client terminen en nuestros hooks __wrap_*.Eso es suficiente para manejar tramas SAE por el aire, inyectar el RSN IE de wpa_supplicant en el assoc-req, instalar claves derivadas del espacio de usuario, y añadir PMF por software (eliminar deauth sin protección; SW-CCMP responder SA-Queries).
Herramientas: Ghidra (headless), nm, objdump, strings, un sniffer en modo monitor (iw + tcpdump).
# 1. The blob ships inside broadcom-sta and is NOT stripped (~4091 syms) -> Ghidra recovers names.
GHIDRA=/opt/ghidra
$GHIDRA/support/analyzeHeadless ./proj wl -import wlc_hybrid.o_amd64 \
-analysisTimeoutPerFile 3600 # auto-analyze, then decompile in the GUI
# 2. Triage what's present BEFORE picking a strategy (absent crypto must move host-side):
nm wlc_hybrid.o_amd64 | grep -iE 'sha256|sae|bip|igtk|mmie' # -> empty here
nm wlc_hybrid.o_amd64 | grep -iE 'wpa|akm|sup|sendauth|key_insert'
# 3. Verify any offset before you patch it (.text vaddr V == file offset V+0x40 in this blob):
objdump -d --start-address=0x47d40 --stop-address=0x47d60 wlc_hybrid.o_amd64
Estrategia: comenzar en los puntos de entrada cfg80211 en el pegamento abierto (wl_cfg80211_connect, wl_set_auth_type) y seguir los iovars (auth, wpa_auth, wsec) dentro del blob. Descompilar lo que alcanzan: la puerta AKM (bcmpwa_akm2WPAauth), la FSM join/auth (wlc_join_BSS + el avanzador auth→assoc en 0x5b79d), el despachador RX (wlc_recv), y la ruta PMK/key (wlc_sup_set_pmk, wlc_key_insert). Verificar cada dirección con objdump.
.o reubicable y sin depurar (file, nm). Una imagen de firmware sin depurar no funcionará de esta manera.set_pmk/key-insert.build.sh (--add-symbol re_auth_advance=..., la lista globalize) y patches/wl_reloc.py (los objetivos __wrap_*).wl_linux.c (wlc+0x6a8 txq, bsscfg+0x320 assoc, scb+0x18 bss) — estos son de diseño y difieren por versión del blob.--add-symbol estaba desviada por un dígito hexadecimal (0x15b79d vs 0x5b79d), cayendo en medio de una instrucción → call <basura> → fallo NX. La pista es la advertencia de compilación objtool: ... can't find starting instruction; verificar que cada símbolo sintético sea un inicio de función real.dmesg --follow por SSH a una segunda máquina — vacía el oops antes del reinicio.sme->ie de wpa_supplicant en .connect y apuntar el buffer IE del assoc-req del blob (*(bsscfg+0x320)+0x30) a él — también satisface la comprobación RSN-IE del 4-way.-22 — solo el IGTK (BIP, idx 4); el motor de claves HW no tiene ranura BIP. Necesita headers del kernel, gcc, binutils, python3. El blob no está en este repositorio (propietario).
# 1. Get the pristine blob from broadcom-sta 6.30.223.271:
# hybrid-v35_64-nodebug-pcoem-6_30_223_271.tar.gz -> lib/wlc_hybrid.o_amd64
cp /path/to/wlc_hybrid.o_amd64 wl-src/lib/wlc_hybrid.o_amd64.orig
# 2. Build:
./build.sh # -> wl-src/wl.ko (or download it from Releases)
sudo rmmod b43 brcmfmac bcma ssb wl 2>/dev/null # free the card
sudo insmod wl-src/wl.ko # wlan0 appears
NetworkManager maneja WPA3-SAE a través de este controlador — solo usa la GUI wifi: elige tu red, ingresa la contraseña, listo. NM lo guarda y se reconecta automáticamente en cada arranque. Equivalente en CLI:
nmcli con add type wifi ifname wlan0 con-name w ssid "YOUR_SSID"
nmcli con modify w wifi-sec.key-mgmt sae wifi-sec.psk "YOUR_PASS" 802-11-wireless-security.pmf 3
nmcli con up w # NM does SAE + 4-way + DHCP
(Alternativa independiente: sudo ./examples/connect.sh wlan0 examples/wpa3-sae.conf.example.)
sudo dkms/install.sh
Registra el controlador con DKMS (se reconstruye automáticamente en actualizaciones del kernel), pone en lista negra los controladores conflictivos del kernel + el wl estándar, y carga el nuestro al arrancar antes de NetworkManager. Luego conéctate desde la GUI wifi. Detalles y el único problema de DKMS: dkms/README.md. Para una reconstrucción manual única, ejecuta ./build.sh → wl-src/wl.ko.
El controlador imprime depuración detallada de WPA3/PMF por defecto. Siléncialo en tiempo de ejecución (o permanentemente):
echo 0 | sudo tee /sys/module/wl/parameters/re_verbose # this boot
echo 'options wl re_verbose=0' | sudo tee /etc/modprobe.d/wl-quiet.conf # permanent
wlc_hybrid.o_amd64) es propietario de Broadcom — obténlo de broadcom-sta tú mismo. El wl.ko en Releases lo incluye (misma situación que el broadcom-sta-dkms de Debian).dmesgccm(aes)) para leer la consulta y emitir una respuesta cifrada.