Impossibile caricare il modulo: non è d'accordo sulla versione del simbolo module_layout


12

Seguendo questo tutorial per scrivere il mio primo driver.

Il Makefile è:

# Makefile – makefile of our first driver

# if KERNELRELEASE is defined, we've been invoked from the
# kernel build system and can use its language.
ifneq (${KERNELRELEASE},)
    obj-m := ofd.o
# Otherwise we were called directly from the command line.
# Invoke the kernel build system.
else
    KERNEL_SOURCE := /usr/src/linux 3.8
    PWD := $(shell pwd)
default:
    ${MAKE} -C ${KERNEL_SOURCE} SUBDIRS=${PWD} modules

clean:
    ${MAKE} -C ${KERNEL_SOURCE} SUBDIRS=${PWD} clean
endif

E il codice del driver è:

* ofd.c – Our First Driver code */
#include <linux/module.h>
#include <linux/version.h>
#include <linux/kernel.h>

static int __init ofd_init(void) /* Constructor */
{
    printk(KERN_INFO "Namaskar: ofd registered");
    return 0;
}

static void __exit ofd_exit(void) /* Destructor */
{
    printk(KERN_INFO "Alvida: ofd unregistered");
}

module_init(ofd_init);
module_exit(ofd_exit);

MODULE_LICENSE("GPL");
MODULE_AUTHOR("Anil Kumar Pugalia <email_at_sarika-pugs_dot_com>");
MODULE_DESCRIPTION("Our First Driver");

Non ci sono errori durante make. Ma quando uso insmod ofd.konon riesco a caricarlo. In dmesgesso dice:

non è d'accordo sulla versione del simbolo module_layout

  • uname -r restituisce '3.8.0-38-generico' e anche la fonte del kernel 3.8.
  • modprobe -f ofd.ko fallisce anche

Anche:

#56~precise1-Ubuntu SMP Thu Mar 13 16:23:47 UTC 2014
$ lsb_release -a
No LSB modules are available.
Distributor ID: Ubuntu
Description:    Ubuntu 12.04.4 LTS
Release:    12.04
Codename:   precise

Che cosa sta succedendo?


Alcuni commenti ovvi. Il primo è che la sorgente del kernel è esattamente la stessa del kernel Ubuntu? Dovresti usare il sorgente del kernel Ubuntu corrispondente esattamente al tuo kernel. L'upstream probabilmente non funzionerà, poiché le distribuzioni rattoppano i loro kernel. In secondo luogo, dopo aver compilato le intestazioni del kernel, non è necessario il sorgente del kernel. Le intestazioni dovrebbero anche essere disponibili come pacchetto binario. Puoi anche dare un'occhiata al Debian Kernel Handbook , che contiene materiale istruttivo sui kernel ecc. Su Debian, che si applica anche a Ubuntu.
Faheem Mitha,

Risposte:


13

Il kernel di Linux contiene strutture di dati il ​​cui layout varia non solo da una versione all'altra ma anche in base alle opzioni di compilazione. Di conseguenza, quando compili un modulo del kernel, devi avere non solo i file di intestazione dal sorgente del kernel, ma anche alcuni file di intestazione che vengono generati durante la compilazione del kernel. La semplice decompressione del sorgente del kernel non è sufficiente.

Con i kernel creati con il CONFIG_MODVERSIONS, il numero di versione può differire, ma il layout delle strutture dati deve essere lo stesso. Questa opzione è attivata nei kernel di Ubuntu. Con questa opzione, oltre alle intestazioni, i moduli devono essere compilati sul Module.symversfile corretto . Ubuntu, come la maggior parte delle distribuzioni, include questo file nello stesso pacchetto delle intestazioni del kernel risultanti dalla compilazione. Viene chiamato il pacchetto dell'intestazione del kernel Ubuntu , ad es .linux-headers-VERSION-VARIANTlinux-headers-3.8.0-38-generic

Con kernel CONFIG_MODVERSIONScompilati senza il (che può essere il caso se hai compilato il tuo kernel), il controllo durante il caricamento di un modulo è un semplice controllo di versione. Puoi prendere il sorgente del kernel decompresso, copiare quello .configche è stato usato durante la compilazione del tuo kernel in esecuzione ed eseguire make modules_prepare. Spetta a te verificare che qualsiasi patch che hai apportato al kernel non influisca sulla compatibilità binaria.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.