Я работал с пользовательской программой writeread.c
(именуемой здесь ), используя драйвер ftdi_sio
Linux.
Я работал со стандартным ftdi_sio
, который поставляется с Ubuntu Lucid, который я использую, а затем, в качестве проверки работоспособности, решил пересобрать ftdi_sio
из исходного кода. Я не хотел загружать весь исходный код ядра, поэтому я выбрал так называемое «построение модулей вне дерева»:
... что означает, что вы можете установить только пакеты linux-headers-*
(вместо того, чтобы установить весь linux-source-*
) - и соответствующий источник модуля ядра - для сборки модуля ядра.
Итак, я в основном получил следующие файлы в папке:
и run make
- и ftdi_sio.ko
объекты ядра компилируются, что также может быть insmod
-ed без проблем.
Проблема теперь здесь - пока я работаю на низких скоростях (115200 бит / с), нет видимой разницы между: загрузкой драйвера 'vanilla' ( с использованием sudo modprobe ftdi_sio
); и загрузка нового встроенного драйвера ( с использованием sudo modprobe usbserial; sudo insmod /path/to/ftdi_sio.ko
) - в отношении производительности программы пользователя (writeread.c
).
Однако, если я попытаюсь сделать то же самое на скорости 2000000 бит / с, то драйвер 'vanilla' будет работать нормально - тогда как драйвер сборки вызовет segfault программы userland (writeread.c
). В частности, этот segfault произошел при free()
-ing ресурсах памяти - потому что драйвер в конечном итоге будет читать больше байтов из петлевого соединения, чем он сам записал бы! Тем не менее, это само по себе не так важно для этого обсуждения, потому что я наконец-то нашел способ заставить работать встроенную ftdi_sio
( Edit: только что заметил, что аналогичная процедура также приведена в External Linux kernel Зависимости модуля R # 2238581 - Переполнение стека ):
$ sudo modprobe -r ftdi_sio # remove 'vanilla' driver from memory
...
# build the driver
$ cd /path/to/ftdi_sio_2.6.32/
$ make clean && make
# check vanilla version
$ ls -la /lib/modules/2.6.32-25-generic/kernel/drivers/usb/serial/ftdi_sio.ko
-rw-r--r-- 1 root root 102396 2010-10-17 01:47 /lib/modules/2.6.32-25-generic/kernel/drivers/usb/serial/ftdi_sio.ko
# (re)move the 'vanilla' kernel object
$ sudo mv /lib/modules/2.6.32-25-generic/kernel/drivers/usb/serial/ftdi_sio.ko ~/Desktop/ftdi_sio_orig.ko
# symlink our built version, as if it is the 'vanilla' one
$ sudo ln -s /path/to/ftdi_sio_2.6.32/ftdi_sio.ko /lib/modules/2.6.32-25-generic/kernel/drivers/usb/serial/
# check
$ ls -la /lib/modules/2.6.32-25-generic/kernel/drivers/usb/serial/ftdi_sio.ko
lrwxrwxrwx 1 root root 57 2010-10-26 12:49 /lib/modules/2.6.32-25-generic/kernel/drivers/usb/serial/ftdi_sio.ko -> /path/to/ftdi_sio_2.6.32/ftdi_sio.ko
# call depmod
$ sudo depmod
# !! plug in USB at this point, built driver autoloads;
# however, running `writeread.c` will segfault!
# !! REBOOT at this point
# after reboot:
# !! plug in USB at this point, built driver autoloads;
# and `writeread.c` runs without segfault
Итак, мой вопрос : кто-нибудь может мне уточнить, почему - даже после запуска depmod
- мне все еще приходится перезагружаться, чтобы встроенный драйвер вел себя правильно ? Другими словами: есть ли какая-либо другая команда, которую я мог бы вызвать (, может быть, после depmod
), чтобы драйвер работал правильно при загрузке, без перезагрузки?
Причина, по которой я спрашиваю, заключается в том, что я подозреваю, что при каждой перекомпиляции модуля ядра таблица символов будет меняться - поэтому для обеспечения ее правильной работы мне придется запускать depmod
и перезагружаться после каждой время сборки драйвера - что, я думаю, было бы утомительно :) Итак, было бы неплохо иметь возможность перестроить модуль ядра и использовать его в одном сеансе - без перезагрузки.
Ну, заранее спасибо за любые ответы,
Ура !!
Makefile:
CONFIG_MODULE_FORCE_UNLOAD=y
# flags passed to gcc for compilation - -v:verbose, -H:show include files
# KBUILD_CFLAGS += -v
# for debugging make itself, use --debug=i in make command for targets
# debug build:
EXTRA_CFLAGS=-g -O0
KVERSION = $(shell uname -r)
obj-m += ftdi_sio.o
all:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) modules
clean:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) clean