Session log: Legion Pro 7 AW88399 smart amp kernel patch build & install

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-03-21 04:55:01 -07:00
parent a706f6a94b
commit cf2b229be5

View File

@@ -0,0 +1,174 @@
# Session Log: 2026-03-21
## Session Summary
Continued work on fixing the terrible speaker sound quality on the Lenovo Legion Pro 7 16IAX10H (CachyOS workstation). Previous session (2026-03-20) diagnosed the root cause and applied initial fixes (forced SOF driver, EasyEffects EQ). This session discovered that the SOF driver alone was insufficient because the **Awinic AW88399 smart amplifiers** were not integrated into the audio pipeline, and built a custom kernel with the community patch to fix it.
### Key Decisions
- Used the community patch from `nadimkobeissi/16iax10h-linux-sound-saga` GitHub repo rather than attempting to write our own driver
- Built a full CachyOS kernel package (not DKMS) because the patch modifies existing kernel source files (ACPI scan, serial-multi-instantiate, alc269.c, aw88399.c ASoC driver)
- Installed UCM2 config modifications for proper speaker routing
- Used BUILDDIR on main disk after tmpfs (16GB) ran out of space during kernel extraction
### Problems Encountered
1. **tmpfs too small** - Initial `makepkg` in `/tmp` failed with "No space left on device" because the kernel source + build artifacts exceed 16GB. Fixed by moving build to `/home/guru/kernel-build/` with `BUILDDIR` override.
2. **Missing build deps** - `bc`, `cpio`, `rust`, `rust-bindgen`, `rust-src` needed installation.
## Hardware Details
- **Laptop**: Lenovo Legion Pro 7 16IAX10H (DMI product: 83F5)
- **Audio Controller**: Intel 800 Series ACE (PCI `80:1f.3`), PCI SSID `17aa:3d6c`
- **Codec**: Realtek ALC287, codec SSID `17aa:3906`
- **Smart Amplifier**: Awinic AW88399 on I2C (ACPI: `AWDZ8399:00`, path: `\_SB_.PC02.I2C2.SPKR`)
- **Kernel**: 6.19.9-1-cachyos with SOF driver (`sof-audio-pci-intel-mtl`)
- **SOF Firmware**: `intel/sof-ipc4/arl-s/sof-arl-s.ri` v2.14.1.1
- **SOF Topology**: `intel/sof-ipc4-tplg/sof-hda-generic.tplg`
## Root Cause Analysis
The sound was terrible because:
1. **SOF driver loaded but using generic HDA topology** - no smart amp integration
2. **AW88399 kernel module loaded with 0 references** - `snd_soc_aw88399` was loaded but nothing used it because there was no HDA side-codec bridge driver
3. **Wrong codec fixup** - Kernel picked fixup for PCI SSID `17aa:0000` (generic/none) instead of `17aa:3906` because the PCI subsystem ID is actually `17aa:3d6c` which had no quirk entry
4. **No HDA side-codec bridge** - The stock kernel has `CONFIG_SND_SOC_AW88399=m` (ASoC driver) but NOT `CONFIG_SND_HDA_SCODEC_AW88399` (the HDA bridge driver that connects ALC287 to the I2C amps) - this driver doesn't exist in mainline Linux as of kernel 6.19
## Fix Applied
### Source: Community Patch
- Repository: https://github.com/nadimkobeissi/16iax10h-linux-sound-saga
- Patch: `16iax10h-audio-linux-6.19.8.patch` (979 lines, 10 files)
- Related issues: CachyOS #687, #707; Kernel Bugzilla #218329
- Status: NOT upstreamed to mainline kernel; $2,000 bounty exists for upstream submission
### What the Patch Does
1. **Creates new HDA side-codec bridge driver** (`snd-hda-scodec-aw88399`, `snd-hda-scodec-aw88399-i2c`) - connects ALC287 HDA codec to AW88399 amps via I2C
2. **Adds ACPI ignore entry** for `AWDZ8399` in `drivers/acpi/scan.c` so serial-multi-instantiate handles it
3. **Adds serial-multi-instantiate node** for `aw88399-hda` with 2 instances
4. **Adds HDA fixup entries** in `alc269.c`: `ALC287_FIXUP_LENOVO_LEGION_AW88399` for SSIDs `17aa:3906`, `17aa:3907`, `17aa:3938`
5. **Exports functions** from ASoC `aw88399.c`: `aw88399_start()`, `aw88399_stop()`, `aw88399_init()`, `aw88399_request_firmware_file()`
6. **Removes ACPI match** from ASoC driver to prevent binding conflict with HDA side-codec
7. **DMI-based L/R channel swap** for products 83F5, 83RU, 83F4 (hardware wiring issue)
### Files Created/Modified on System
#### Firmware
- **Created**: `/lib/firmware/aw88399_acf.bin` (amplifier calibration firmware from Windows driver)
#### UCM2 Configs
- **Backed up**: `/usr/share/alsa/ucm2/HDA/HiFi-analog.conf.bak`
- **Backed up**: `/usr/share/alsa/ucm2/HDA/HiFi-mic.conf.bak`
- **Modified**: `/usr/share/alsa/ucm2/HDA/HiFi-analog.conf` (from community repo)
- **Modified**: `/usr/share/alsa/ucm2/HDA/HiFi-mic.conf` (from community repo)
#### Kernel Build
- **Build directory**: `/home/guru/kernel-build/`
- **PKGBUILD**: Modified CachyOS PKGBUILD with `aw88399-hda-scodec.patch` added to source array and `CONFIG_SND_HDA_SCODEC_AW88399=m`, `CONFIG_SND_HDA_SCODEC_AW88399_I2C=m` enabled
- **Built packages**:
- `/home/guru/kernel-build/linux-cachyos-6.19.9-1-x86_64.pkg.tar.zst` (147MB)
- `/home/guru/kernel-build/linux-cachyos-headers-6.19.9-1-x86_64.pkg.tar.zst` (37MB)
#### Kernel Installed
- Packages installed via `sudo pacman -U`
- Initramfs regenerated automatically
- Limine bootloader config updated automatically
### Previous Session Fixes Still Active
- `/etc/modprobe.d/sof-force.conf` - forces SOF driver (`dsp_driver=3`)
- `~/.local/share/easyeffects/output/Legion-Speakers-v2.json` - EasyEffects EQ preset
- EasyEffects sink set as default audio output
## Configuration Changes
### Packages Installed This Session
- `bc` (kernel build dep)
- `cpio` (kernel build dep)
- `rust` (kernel build dep - LTO kernel)
- `rust-bindgen` (kernel build dep)
- `rust-src` (kernel build dep)
### Kernel Config Added
```
CONFIG_SND_HDA_SCODEC_AW88399=m
CONFIG_SND_HDA_SCODEC_AW88399_I2C=m
```
## Pending/Incomplete Tasks
### REBOOT REQUIRED
The patched kernel is installed but requires a reboot to take effect.
### Post-Reboot Verification
Run these commands after reboot:
```bash
# Verify AW88399 HDA side-codec loaded
sudo dmesg | grep -i aw88399
# Verify modules loaded with references > 0
lsmod | grep aw88399
# Verify correct codec fixup (should show 17aa:3906 not 17aa:0000)
sudo dmesg | grep -i "fixup.*17aa"
# Check audio devices
wpctl status
# Verify serial-multi-instantiate created I2C devices
ls /sys/bus/i2c/devices/ | grep -i aw
# Reset UCM and restart audio
alsaucm -c hw:1 reset
alsaucm -c hw:1 reload
systemctl --user restart pipewire pipewire-pulse wireplumber
```
### If Sound Still Bad After Reboot
1. Check if EasyEffects is still routing correctly: `wpctl set-default <easyeffects_sink_id>`
2. May need to reconfigure EasyEffects if device names/IDs change
3. Verify firmware loaded: `sudo dmesg | grep aw88399_acf`
### If Reboot Breaks Audio Completely
1. Boot LTS kernel from Limine menu
2. Or boot a btrfs snapshot (available in Limine)
3. Or remove the patched kernel: `sudo pacman -S linux-cachyos` (reinstall from repo)
4. Restore UCM2 backups:
```bash
sudo cp /usr/share/alsa/ucm2/HDA/HiFi-analog.conf.bak /usr/share/alsa/ucm2/HDA/HiFi-analog.conf
sudo cp /usr/share/alsa/ucm2/HDA/HiFi-mic.conf.bak /usr/share/alsa/ucm2/HDA/HiFi-mic.conf
```
### Cleanup After Verification
- Remove `/home/guru/kernel-build/build/` (large build artifacts)
- Remove `/tmp/16iax10h-linux-sound-saga/` and `/tmp/linux-cachyos/`
- Keep `/home/guru/kernel-build/PKGBUILD` and patch for future kernel rebuilds
### Future Kernel Updates
When CachyOS pushes a new kernel update, the AW88399 patch will be lost. Need to either:
1. Rebuild with the patch each time (keep PKGBUILD + patch in `/home/guru/kernel-build/`)
2. Watch for upstream inclusion (Kernel Bugzilla #218329)
3. Watch CachyOS issues #687 and #707 for native inclusion
## Reference Information
### Key URLs
- Community fix repo: https://github.com/nadimkobeissi/16iax10h-linux-sound-saga
- CachyOS Issue #687: https://github.com/CachyOS/linux-cachyos/issues/687
- CachyOS Issue #707: https://github.com/CachyOS/linux-cachyos/issues/707
- Kernel Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=218329
- CachyOS Forum thread: https://discuss.cachyos.org/t/new-fix-for-lenovo-legion-pro-7i-16iax10h-with-alc3306-codec/18889/1
### Key File Paths
- Kernel build dir: `/home/guru/kernel-build/`
- SOF force config: `/etc/modprobe.d/sof-force.conf`
- AW88399 firmware: `/lib/firmware/aw88399_acf.bin`
- UCM2 configs: `/usr/share/alsa/ucm2/HDA/HiFi-analog.conf`, `HiFi-mic.conf`
- UCM2 backups: same path with `.bak` extension
- EasyEffects preset: `~/.local/share/easyeffects/output/Legion-Speakers-v2.json`
### PCI/Device IDs
- PCI device: `80:1f.3` (Intel 800 Series ACE)
- PCI vendor/device: `8086:7f50`
- PCI subsystem: `17aa:3d6c`
- Codec SSID: `17aa:3906`
- ACPI amp device: `AWDZ8399:00`
- I2C amp addresses: `0x34` (right speaker), `0x35` (left speaker)
- DMI product: `83F5`