“Nenhuma versão de símbolo para module_layout” ao tentar carregar o usbhid.ko

27

Estou tentando criar meu próprio módulo usbhid.ko, mas depois que compilei, não consigo carregar o módulo. dmesgdiz no symbol version for module_layout. Eu estou querendo saber qual é o problema? Eu já usei a fonte do kernel fornecida pelo Ubuntu e também verifiquei se a versão do kernel é a mesma.

SpecC
fonte

Respostas:

22

Especificamente, qual o problema é que, quando você construiu seu módulo, a árvore de origem do kernel provavelmente estava sem o arquivo Modules.symvers. O sistema kbuild realmente alerta sobre isso quando você constrói seu módulo. Se Modules.symvers estiver ausente, você verá:

Aviso: está faltando a versão do símbolo dump /usr/src/linux-2.6.34-12/Modules.symvers; Os módulos não terão dependências e modificações.

Se o seu kernel CONFIG_MODVERSIONShabilitou, durante a fase modpost de construção do driver, ele executará scripts / mod / modpost com a opção -m. Se você for corajoso e dê uma olhada no código- fonte scripts / mod / modpost.c , verá que a opção -m adiciona o símbolo _module_layout_ do vmlinux, no entanto, se você não tiver o Modules.symvers do kernel, você não receberá o valor CRC desse símbolo e receberá esta mensagem de erro.

Portanto, existem duas maneiras de contornar isso.

1) execute uma compilação completa do seu kernel em execução para gerar o Modules.symvers e depois reconstrua o seu módulo. [http://www.mjmwired.net/kernel/Documentation/kbuild/modules.txt[[1]

51  === 2. How to Build External Modules
52  
53  To build external modules, you must have a prebuilt kernel available
54  that contains the configuration and header files used in the build.
55  Also, the kernel must have been built with modules enabled. If you are
56  using a distribution kernel, there will be a package for the kernel you
57  are running provided by your distribution.
58  
59  An alternative is to use the "make" target "modules_prepare." This will
60  make sure the kernel contains the information required. The target
61  exists solely as a simple way to prepare a kernel source tree for
62  building external modules.
63  
64  NOTE: "modules_prepare" will not build Module.symvers even if
65  CONFIG_MODVERSIONS is set; therefore, a full kernel build needs to be
66  executed to make module versioning work.

2) A outra opção é dizer ao modprobe estúpido que ignore toda essa porcaria e carregue seu módulo de qualquer maneira:

modprobe -f <module>

Eu tendem a favorecer a opção 2 :)

Dan Gora
fonte
1
+1 para "diga ao modprobe estúpido que ignore toda essa porcaria e carregue seu módulo de qualquer maneira".
Hayri Uğur Koltuk 10/03
Eu tentei 2 e descobri que o módulo não carrega automaticamente no momento da inicialização. existe uma maneira de -f no momento da inicialização?
Justin Zhang
17

Tenha os pacotes linux-headerse linux-sourcecorrespondentes ao seu kernel instalados. Por exemplo, para o kernel, 3.2.0-27-generic-paevocê precisa:

  1. linux-headers-3.2.0-27-generic-pae e
  2. linux-source-3.2.0-27-generic-pae.

Caso a versão dos pacotes acima não corresponda à sua versão do kernel em execução, você precisará substituí-lo $(uname -r)pela string de versão do pacote do kernel instalado acima.
Para o exemplo acima, a versão do pacote é 3.2.0-27-generic-pae. Quando você executa uname -re sua saída é algo diferente, 3.2.0-27-generic-paeé necessário substituir cada um $(uname -r)abaixo para corresponder à cadeia de versão dos pacotes instalados.

  1. cd /usr/src/linux-source-$Version e descompacte o arquivo .tar.bz2 no lugar e o CD no diretório extraído - acho que você já fez isso
  2. cp /boot/config-$(uname -r) .config no diretório de origem do kernel
  3. cp /usr/src/linux-headers-$(uname -r)/Module.symvers . no diretório de origem do kernel

Depois de fazer isso, no diretório de origem do kernel, faça o seguinte:

  1. make prepare
  2. make scripts
  3. make M=drivers/usb/serial- mude o caminho depois M=para atender às suas necessidades

Infelizmente, não sei como construir um módulo específico, mantendo-o Module.symversintocado. Fazer make drivers/usb/serial/option.ko, por exemplo, mata o Module.symversarquivo e você acaba com o problema original. Usar o M=parâmetro não o mata, mas você precisa criar todos os módulos no caminho especificado - e ainda não encontrei uma maneira de contornar isso.

Radu C
fonte
Esta parece ser a melhor maneira de fazer as coisas, no caso de você está compilando o módulo na mesma versão árvore ...
Treviño
2

Você deve usar a configuração do kernel precisamente idêntica antes da execução make prepare. Além disso, se você estiver construindo fora da árvore, precisará construí-lo com os cabeçalhos do kernel precisamente idênticos que correspondem ao kernel atualmente em execução (ou o de destino se você não estiver executando no momento da compilação).

Daniel T Chen
fonte
"make mrproper", "cp / boot / config - $ (uname -r) .config", "make oldconfig", "make prepare", "make scripts" Eu usei estas instruções para preparar a compilação. Gostaria de saber se copiei o arquivo de configuração correto? parece que existe apenas uma configuração que corresponde à minha versão do kernel em / boot /. desculpe-me pela formatação, pois a caixa de comentários não tem formato ....
SpecC
Sim, isso parece correto. Onde você está chamando a construção e, se não for do diretório de nível superior, que valor SUBDIRS você está passando?
Daniel T Chen
Obrigado pela resposta. quando tentei construir o usbhid.ko. Eu usei este comando "make modules SUBDIRS = drivers / hid / usbhid"
SpecC
quando executei o comando "make modules SUBDIRS = drivers / hid / usbhid", recebo o seguinte aviso "AVISO: O dump da versão do símbolo /usr/src/linux-source-2.6.31/Module.symvers está ausente; os módulos terão sem dependências e modversões. "
SpecC 25/11
@ Specpec Ao investigar seu problema, atualize sua pergunta original com as etapas que você está executando. Então Dan atualizará sua resposta, e você continuará atualizando até descobrir, em vez de uma série de comentários que acabam enterrados, consulte o guia para obter mais dicas: meta.askubuntu.com/questions/257/how-does-ask
Jorge Castro