Quando servono davvero i kernel headers
Su AlmaLinux 9 e Rocky Linux 9 i kernel headers non sono un dettaglio cosmetico: servono quando devi compilare moduli esterni rispetto al kernel, per esempio driver DKMS, agent di sicurezza, moduli per filesystem, software di virtualizzazione o componenti vendor che non arrivano già compilati per il tuo kernel.
Il punto pratico è semplice: i header devono corrispondere al kernel installato e, nella maggior parte dei casi, a quello in esecuzione. Se installi il pacchetto sbagliato, la compilazione può partire e poi fallire con errori del tipo missing /lib/modules/.../build, simboli non trovati o incompatibilità tra versioni.
Qui non stiamo parlando del kernel “generico” o del pacchetto sorgente completo del kernel. Su queste distribuzioni il caso normale è installare il pacchetto di sviluppo corretto dal repository di sistema, verificare che il repository richiesto sia abilitato e controllare che il filesystem esponga i collegamenti giusti sotto /lib/modules/$(uname -r)/.
Verifica iniziale: kernel in esecuzione e pacchetti disponibili
Prima di toccare il sistema, conviene raccogliere due informazioni: quale kernel è attivo e quali pacchetti sono già presenti. Questo evita di installare headers o development package che non combaciano con la macchina.
Esegui questi controlli:
uname -r
rpm -q kernel kernel-core kernel-devel kernel-headers
ls -l /lib/modules/$(uname -r)/build
ls -l /lib/modules/$(uname -r)/source
Interpretazione rapida:
- se
kernel-develnon è installato, di solito manca il materiale necessario per compilare moduli; - se
/lib/modules/$(uname -r)/buildnon esiste o punta male, il pacchetto non è allineato al kernel corrente; - se hai appena aggiornato il sistema ma non hai riavviato, il kernel in esecuzione può essere più vecchio di quello per cui hai già i pacchetti installati.
Nota importante: su RHEL-like 9 la parola “headers” viene spesso usata in modo generico, ma nella pratica per compilare moduli il pacchetto davvero utile è quasi sempre kernel-devel. Il pacchetto kernel-headers serve a esporre header user-space per la compilazione di alcune componenti, ma non sostituisce il development tree del kernel per i moduli esterni.
Differenza tra kernel-headers e kernel-devel
Questo è il punto che genera più confusione. Su AlmaLinux 9 e Rocky Linux 9 i due pacchetti non sono equivalenti.
- kernel-headers: espone header necessari a parte del software user-space che interagisce con il kernel o con le ABI del sistema.
- kernel-devel: contiene i file per compilare moduli kernel e integrare software che deve agganciarsi al kernel in esecuzione.
Se il tuo obiettivo è installare headers per una compilazione classica di moduli, il comando giusto è quasi sempre quello che installa kernel-devel. Se invece stai seguendo un requisito specifico di un software che chiede esplicitamente kernel-headers, installa anche quello, ma non confondere il risultato con il development tree del kernel.
In altre parole: per compilare moduli esterni, kernel-devel è la base; kernel-headers è complementare. Se non distingui i due casi, rischi di avere un sistema che “sembra” preparato ma poi fallisce al primo build serio.
Installazione standard con dnf
La via più pulita è usare i repository standard della distribuzione. Se la macchina ha accesso a internet e i repo sono configurati correttamente, il flusso normale è questo:
sudo dnf install -y kernel-devel kernel-headers
Dopo l’installazione, verifica che il pacchetto kernel-devel corrisponda alla versione del kernel attivo o, se non hai ancora riavviato dopo un update, almeno alla versione che andrai a usare al prossimo boot:
rpm -q kernel-devel kernel-headers
rpm -qa 'kernel*' | sort
Il controllo più concreto resta il link di build:
readlink -f /lib/modules/$(uname -r)/build
Se il comando restituisce un path valido sotto /usr/src/kernels/, sei sulla strada giusta. Se invece il link non esiste, c’è un disallineamento da correggere prima di procedere con il software che dipende dai moduli.
Scenario tipico: il kernel è stato aggiornato ma il sistema non è stato riavviato
Questo è uno dei casi più comuni in produzione: il sistema ha già scaricato il nuovo kernel e magari anche il relativo kernel-devel, ma il nodo continua a girare sul kernel vecchio. In quel caso l’installazione “sembra” a posto, però la compilazione fallisce perché i file presenti non corrispondono al kernel attualmente in esecuzione.
Per capirlo, confronta la versione del kernel attivo con quella del pacchetto installato:
uname -r
rpm -q kernel-devel
Se le versioni non coincidono, hai due strade:
- riavviare la macchina nel kernel per cui hai i pacchetti corretti;
- installare il pacchetto
kernel-develche corrisponde esattamente al kernel in esecuzione, se disponibile nei repository.
In ambienti con finestre di manutenzione strette, il riavvio è spesso la soluzione più pulita. Se però il nodo è critico e devi evitare downtime, conviene verificare prima se il package matching è già presente e basta solo riallineare il boot successivo.
Repository mancanti, CRB e casi offline
Su AlmaLinux 9 e Rocky Linux 9 alcuni pacchetti richiesti da software di terze parti arrivano da repository aggiuntivi. In particolare può servire il repository CRB per dipendenze di build o librerie accessorie. Non sempre riguarda direttamente i headers del kernel, ma spesso il problema emerge nello stesso momento: installi i pacchetti di build, e la catena si ferma su una dipendenza mancante.
Controlla i repository attivi con:
sudo dnf repolist
sudo dnf config-manager --set-enabled crb
Se la macchina è offline o isolata, il criterio cambia: devi verificare che il mirror interno contenga i pacchetti corretti per la stessa release della macchina. In quel caso il controllo non è “installare e basta”, ma confrontare il contenuto del repository con la versione del sistema:
cat /etc/os-release
rpm -q --queryformat '%{VERSION}-%{RELEASE}\n' kernel-devel
Se il mirror non ha il pacchetto corretto, non forzare installazioni da sorgenti miste o da release diverse: il costo di un modulo compilato contro ABI sbagliate è quasi sempre più alto del tempo necessario a sistemare il repository.
Verifica pratica con un modulo esterno
Il modo migliore per confermare che gli headers siano davvero a posto è provare una compilazione reale. Se usi DKMS o un driver vendor, il loro log è la prova utile; in alternativa puoi osservare se il tool di build trova il tree del kernel senza errori.
Due controlli ricorrenti:
- il percorso
/lib/modules/$(uname -r)/buildesiste e punta al tree corretto; - il comando di build non si ferma su errori di intestazione o simboli mancanti.
Se stai usando DKMS, il log più utile è spesso sotto /var/lib/dkms/. Un errore classico è il seguente: il modulo cerca l’albero di compilazione ma trova un kernel-devel non allineato o incompleto. In quel caso il messaggio è più affidabile del “pacchetto installato” visto da rpm.
sudo dkms status
sudo find /var/lib/dkms -maxdepth 3 -type f | sort
sudo journalctl -xe --no-pager | tail -n 50
Se il modulo compila ma poi non si carica, il problema non è più “headers mancanti”: devi guardare firma del modulo, Secure Boot, permessi o compatibilità del driver. Gli headers ti portano solo fino alla build, non risolvono il caricamento del modulo.
Installazione in ambienti con Secure Boot o policy restrittive
Su sistemi con Secure Boot attivo, il fatto che i kernel headers siano installati non significa che il modulo possa essere caricato. La compilazione può andare a buon fine, ma il kernel può rifiutare il modulo non firmato. È un errore di livello diverso, ma nelle operazioni di installazione viene spesso scambiato per “headers mancanti”.
La verifica minima è questa:
mokutil --sb-state
journalctl -k --no-pager | tail -n 50
Se il kernel rifiuta un modulo, nel log vedrai indicazioni esplicite su firma o policy. In quel caso la soluzione non è reinstallare i headers, ma gestire la firma del modulo, la registrazione della chiave MOK o la policy di boot aziendale. È una distinzione importante: evita di inseguire il livello sbagliato.
Procedura consigliata in ordine operativo
Se vuoi fare le cose senza tentativi casuali, il flusso più pulito è questo:
- verifica il kernel in esecuzione con
uname -r; - controlla se
kernel-develekernel-headerssono installati conrpm -q kernel-devel kernel-headers; - controlla il link
/lib/modules/$(uname -r)/build; - installa o riallinea i pacchetti con
sudo dnf install -y kernel-devel kernel-headers; - se il kernel è stato aggiornato e non hai riavviato, valuta il reboot controllato;
- rilancia la compilazione del modulo o del software che dipende dagli headers;
- se fallisce ancora, apri il log del tool specifico prima di cambiare altri pacchetti.
Questa sequenza riduce il rumore: prima fai corrispondere kernel e pacchetti, poi verifichi il build tree, infine guardi il log applicativo. Saltare direttamente alla reinstallazione è il modo più rapido per perdere tempo, soprattutto su host con repository misti o con aggiornamenti parziali.
Controlli finali dopo l’installazione
Dopo aver installato i pacchetti, i controlli che contano davvero sono tre: presenza del pacchetto giusto, link di build corretto, e compilazione reale senza errori. Tutto il resto è contorno.
rpm -q kernel-devel kernel-headers
readlink -f /lib/modules/$(uname -r)/build
ls -ld /usr/src/kernels/$(uname -r)*
Se il tuo software richiede un comando di test specifico, usalo subito. Per esempio, molti pacchetti DKMS espongono uno stato sintetico che è più utile del semplice elenco RPM. In alternativa, il successo del primo rebuild è la conferma più concreta che la macchina è pronta.
Se invece il sistema continua a fallire, non dare per scontato che il problema siano ancora gli headers. Le cause successive da verificare sono: repository non allineato, kernel vecchio in esecuzione, modulo non firmato, dipendenze di build mancanti, o path corrotti sotto /lib/modules.
Errori frequenti e come leggerli senza perdere tempo
Ci sono alcuni messaggi che si ripetono spesso e che conviene riconoscere subito.
- file not found: /lib/modules/.../build — di solito manca
kernel-develo non coincide con il kernel attivo. - invalid module format — il modulo è stato compilato per un kernel diverso o con opzioni incompatibili.
- permission denied / operation not permitted durante il caricamento — spesso non è un problema di headers, ma di policy, Secure Boot o permessi.
- missing symbols — il development tree non è quello giusto, oppure il vendor richiede una specifica build del kernel.
Leggere bene il primo errore utile fa risparmiare tempo. Il kernel è molto esplicito quando qualcosa non combacia; il problema nasce quando si cerca di correggere il livello sbagliato. Se il log parla di firma, non reinstallare i headers. Se parla di build tree mancante, non inseguire il firewall. Se parla di symbol mismatch, non fermarti al pacchetto RPM installato.
Conclusione operativa: cosa ricordare su AlmaLinux 9 e Rocky Linux 9
La regola utile è questa: per compilare moduli esterni su AlmaLinux 9 e Rocky Linux 9, installa e allinea kernel-devel al kernel in esecuzione; aggiungi kernel-headers quando il software lo richiede esplicitamente. Non trattare i due pacchetti come sinonimi.
Se il sistema è aggiornato ma non riavviato, il mismatch è il primo sospetto. Se la macchina usa repository parziali o mirror interni, verifica che la release sia coerente. Se Secure Boot è attivo, separa il tema headers dal tema firma dei moduli. E se un driver o un agente continua a fallire dopo l’installazione, guarda il log del tool di build prima di cambiare altra configurazione.
In pratica: prima fai combaciare versione del kernel, pacchetti e tree di compilazione; poi risolvi il resto. È la differenza tra una correzione pulita e una serie di tentativi che spostano solo il problema da un layer all’altro.
Commenti (0)
Nessun commento ancora.
Segnala contenuto
Elimina commento
Eliminare definitivamente questo commento?
L'azione non si può annullare.