Модуль ядра может вообще не быть драйвером устройства.
Термин «драйвер ядра» не вполне определен, но давайте попробуем.
Это модуль ядра, который не управляет каким-либо аппаратным обеспечением, поэтому его нельзя разумно считать «драйвером устройства»:
#include
#include
MODULE_LICENSE("GPL");
static int myinit(void)
{
printk(KERN_INFO "hello init\n");
return 0;
}
static void myexit(void)
{
printk(KERN_INFO "hello exit\n");
}
module_init(myinit)
module_exit(myexit)
После сборки вы можете использовать его с:
insmod hello.ko
и он печатает hello init
в dmesg
.
Однако существуют модули ядра, которые не являются драйверами устройств, но на самом деле полезны, например, модули, предоставляющие информацию об отладке ядра/производительности.
Драйверы устройств обычно также являются модулями ядра.
Пример чего-то, что является «драйвером устройства», сгенерировать немного сложнее, поскольку для управления им требуется аппаратное обеспечение, а описание аппаратного обеспечения, как правило, сложное.
Однако, используя QEMU или другие эмуляторы, мы можем создавать программные модели реального или упрощенного оборудования, что является отличным способом научиться общаться с оборудованием. Вот простой пример минимального драйвера устройства PCI: https://github.com/cirosantilli/linux-kernel-module-cheat/blob/6788a577c394a2fc512d8f3df0806d84dc09f355/kernel_module/hello.c
Затем мы видим, что в x86, общение с оборудованием сводится к:
in
и out
инструкциям, например, https://stackoverflow.com/questions/3215878/what-are-in-out-instructions-in-x86-used-for/33444273#33444273Эти операции, как правило, не могут выполняться из пространства пользователя , как объяснено в: В чем разница между пространством пользователя и пространством ядра? Однако есть некоторые исключения: https://stackoverflow.com/questions/7986260/linux-interrupt-handling-in- пространство пользователя.
Затем ядро предлагает API более высокого уровня, чтобы сделать такое взаимодействие с оборудованием более простым и переносимым:
request_irq
для обработки прерыванийioreadX
и сопоставление памяти ввода-вывода