Часть 1. первые шаги
Содержание:
Options
-V, —version | Print the version of modinfo, and exit. |
-F, —field field name | Only print the value of the field named field name. Field names are case-insensitive. Common field names are author, description, license, parm, depends, and alias. There are often multiple fields for a given field name, for instance parm, alias, and depends. Multiple values are printed one per line. The special field name, file name, lists the file name of the module. |
-k kernel | Provide information about a kernel other than the running one. This switch is particularly useful for distributions needing to extract information from a newly-installed (but not yet running) set of kernel modules. |
-0, —null | Use the ASCII NULL character to separate field values, instead of a newline. This switch is useful for parsing field data, because a newline might be part of a field’s value. |
-a, -d, -l, -p, -n | These are shortcuts for displaying the fields author, description, license, parm, and file name. |
Examples
modinfo snd
Display all available information about the snd Linux kernel module. Output will resemble the following:
file name: /lib/modules/3.2.0-4-686-pae/kernel/sound/core/snd.ko alias: char-major-116-* license: GPL description: Advanced Linux Sound Architecture driver for sound cards. author: Jaroslav Kysela <> license: GPL description: Jack detection support for ALSA author: Mark Brown <> depends: soundcore intree: Y vermagic: 3.2.0-4-686-pae SMP mod_unload modversions 686 parm: slots:Module names assigned to the slots. (array of charp) parm: major:Major # for sound driver. (int) parm: cards_limit:Count of auto-loadable sound cards. (int)
modinfo -F parm snd
Display all parm (parameter) fields for the snd Linux kernel module. Output will resemble the following (Note that the field name does not prefix the field values):
slots:Module names assigned to the slots. (array of charp) major:Major # for sound driver. (int) cards_limit:Count of auto-loadable sound cards. (int)
Управление модулями вручную
Управление модулями ядра производится с помощью утилит, предоставляемых пакетом . Вы можете использовать эти утилиты вручную.
Примечание: Если вы обновили ваше ядро, но ещё не перезагрузились, modprobe не сработает без каких либо уведомлений об ошибках и завершится с ошибкой 1, потому что путь больше не существует. Проверьте вручную существование этого пути, если modprobe не работает, чтобы убедиться, что это ваш случай.
Загрузка модуля:
# modprobe module_name
Загрузка модуля из другого места (для тех модулей, которых нет в ):
# insmod filename
Выгрузка модуля:
# modprobe -r module_name
Альтернативный вариант выгрузки модуля:
# rmmod module_name
Benefits of modprobed-db with make localmodconfig in custom kernels
- Reduced kernel footprint on FS
- Reduced compilation time
Comparisons using version 3.8.8-1 of the Arch kernel (from ABS):
Note: The modprobed.db on the test machine contains 209 lines; YMMV based on specific usage and needs.
Machine CPU | # of threads | make localmodconfig | # of Modules | Modules’ Size on HDD | Compilation Time |
Intel i7-3770K @ 4.50 GHz | 8 | No | 3,025 | 129 MB | 7 min 37 sec |
Intel i7-3770K @ 4.50 GHz | 8 | Yes | 230 | 18 MB | 1 min 13 sec |
Intel Q9550 @ 3.40 GHz | 4 | No | 3,025 | 129 MB | 14 min 21 sec |
Intel Q9550 @ 3.40 GHz | 4 | Yes | 230 | 18 MB | 2 min 20 sec |
Intel E5200 @ 3.33 GHz | 2 | No | 3,025 | 129 MB | 34 min 35 sec |
Intel E5200 @ 3.33 GHz | 2 | Yes | 230 | 18 MB | 5 min 46 sec |
- 13x less modules built
- 7x less space
- 6x less compilation time
Number of modules found by:
find /scratch/linux-3.8 -name '*.ko' | wc -l
Size on HDD found by:
find /scratch/linux-3.8 -name '*.ko' -print0 | xargs -0 du -ch
Compilation time found by entering a preconfigured linux-3.8.8 (using stock Arch config):
$ time make -jx modules
Examples
The following series of commands illustrate a common way to use modprobe. Each command is prefixed with sudo, since they require root permissions:
sudo ln -s /path/to/your-kernel-module.ko /lib/modules/`uname -r`
sudo depmod -a
sudo modprobe your-kernel-module
These commands perform the following operations:
- In the first command, we use ln to create a symbolic link to our module file in the directory /lib/modules/kernel-release. The command uname -r, enclosed in back quotes, is executed by the shell and translates to the appropriate string representing our kernel release version.
- In the second command, an updated dependency list is generated by depmod -a to make sure that the module we’re installing is aware of all existing modules and dependencies. This dependency list will be used by modprobe when installing the module in the third command.
- modprobe installs the kernel module.
Examples
The following series of commands illustrate a common way to use depmod. Each command is prefixed with sudo, since they require root permissions:
sudo ln -s /path/to/your-kernel-module.ko /lib/modules/`uname -r`
sudo depmod -a
sudo modprobe your-kernel-module
These commands perform the following operations:
- In the first command, we use ln to create a symbolic link to our module file in the directory /lib/modules/kernel-release. The command uname -r, enclosed in back quotes, is executed by the shell and translates to the appropriate string representing our kernel release version.
- In the second command, an updated dependency list is generated by depmod -a to make sure that the module we’re installing is aware of all existing modules and dependencies. This dependency list will be used by modprobe when installing the module in the third command.
- modprobe installs the kernel module.
Blacklisting
Blacklisting, in the context of kernel modules, is a mechanism to prevent the kernel module from loading. This could be useful if, for example, the associated hardware is not needed, or if loading that module causes problems: for instance there may be two kernel modules that try to control the same piece of hardware, and loading them together would result in a conflict.
Some modules are loaded as part of the initramfs. will print out all automatically detected modules: to prevent the initramfs from loading some of those modules, blacklist them in a .conf file under and it shall be added in by the hook during image generation. Running will list all modules pulled in by the various hooks (e.g. hook, hook, etc.). Remember to add that .conf file to the array in if you do not have the hook in your array (e.g. you have deviated from the default configuration), and once you have blacklisted the modules regenerate the initramfs, and reboot afterwards.
Using files in /etc/modprobe.d/
Create a file inside and append a line for each module you want to blacklist, using the keyword. If for example you want to prevent the module from loading:
/etc/modprobe.d/nobeep.conf
# Do not load the 'pcspkr' module on boot. blacklist pcspkr
Note: The command will blacklist a module so that it will not be loaded automatically, but the module may be loaded if another non-blacklisted module depends on it or if it is loaded manually.
However, there is a workaround for this behaviour; the command instructs modprobe to run a custom command instead of inserting the module in the kernel as normal, so you can force the module to always fail loading with:
/etc/modprobe.d/blacklist.conf
... install module_name /bin/true ...
This will effectively blacklist that module and any other that depends on it.
Using kernel command line
Tip: This can be very useful if a broken module makes it impossible to boot your system.
You can also blacklist modules from the bootloader.
Simply add to your bootloader’s kernel line, as described in Kernel parameters.
Note: When you are blacklisting more than one module, note that they are separated by commas only. Spaces or anything else might presumably break the syntax.
Troubleshooting
Modules do not load
In case a specific module does not load and the boot log (accessible with ) says that the module is blacklisted, but the directory does not show a corresponding entry, check another modprobe source folder at for blacklisting entries.
A module will not be loaded if the «vermagic» string contained within the kernel module does not match the value of the currently running kernel. If it is known that the module is compatible with the current running kernel the «vermagic» check can be ignored with .
Warning: Ignoring the version checks for a kernel module can cause a kernel to crash or a system to exhibit undefined behavior due to incompatibility. Use only with the utmost caution.
Запрет загрузки
В терминах модулей ядра blacklisting означает механизм, предотвращающий загрузку какого-то модуля. Это может понадобиться, например если вам не нужна работа какого-то оборудования или если загрузка данного модуля вызывает проблемы: например, могут быть два модуля ядра, которые пытаются управлять одним и тем же оборудованием, и их совместная загрузка приводит к конфликту.
Некоторые модули загружаются как часть initramfs. Команда напечатает все автоматически обнаруженные модули: для предотвращения initramfs от загрузки каких-то из этих модулей, занесите их в чёрный список в . Команда отобразит все модули, которые необходимы некоторым хукам (например, хук, хук и т.д.). Не забудьте добавить этот файл в секцию в , если вы этого ещё не сделали, пересоберите initramfs после того, как вы запретили загрузку модулей, а затем перезагрузитесь.
С помощью файлов в /etc/modprobe.d/
Создайте файл в и добавьте строку для каждого модуля, который вы хотите запретить, используя ключевое слово . Например, если вы хотите запретить загружать модуль :
/etc/modprobe.d/nobeep.conf
# Do not load the 'pcspkr' module on boot. blacklist pcspkr
Примечание: Команда запретит автоматическую загрузку модуля, но этот модуль всё равно может загрузиться, если от него зависит какой-то не запрещённый модуль или если он загружен вручную.
Можно изменить такое поведение. Команда заставляет modprobe запускать вашу собственную команду вместо вставки модуля в ядро как обычно. Поэтому вы можете насильно сделать так, чтобы модуль никогда не загружался:
/etc/modprobe.d/blacklist.conf
... install module_name /bin/false ...
Это запретит данный модуль и все модули, зависящие от него.
С помощью командной строки ядра
Совет: Это может очень помочь, если неправильный модуль не даёт загрузиться вашей системе.
Вы также можете запрещать модули из загрузчика.
Просто добавьте в вашем загрузчике в строку ядра, как описано в параметрах ядра.
Примечание: Когда вы запрещаете несколько модулей, обратите внимание, что они разделяются только запятой. Пробелы или что-либо ещё могут нарушить синтаксис.
Recommendations
It is recommended that users install the package and then «use» the system for a good amount of time to allow the database to grow based on usage and capture everything the system needs before building a kernel with a make localmodconfig. Some suggested actions to allow appropriate modules to load and get cataloged:
- Insert every kind of removable media (USB, DVD, CD, etc.)
- Use every device on the machine (wifi, network, USB stuff like cameras, ipods, etc.)
- Mount every kind of filesystem one might typically use including ext2/3/4, fat, vfat, CIFS shares, NFS shares, etc.
- Use as many applications (that one would normally use) as possible in order to capture modules on which they depend. For example, IP blocking/filtering software like AUR.
- Users who plan to mount iso image file should do so (this will make sure to capture the loop and isofs modules).
- Users requiring encryption software such as should make sure to load it, and mount some encrypted containers to ensure that the needed crypto modules are in the db.
- Try-out different Linux-kernels; they may include modules not enabled in the default/other kernel(s)
Strategy
The idea is that modprobe will look first in the directory containing modules compiled for the current release of the kernel. If the module isn’t found there, modprobe looks in the directory common to the kernel version (for example, 2.0, 2.2). If the module still isn’t found, modprobe looks in the directory containing modules for a default release, and so on.
When you install a new Linux, the modules should be moved to a directory related to the release (and version) of the kernel you are installing. Then, do a symlink from this directory to the default directory.
Each time you compile a new kernel, the command make modules_install creates a new directory, but won’t change the default link.
When you get a module unrelated to the kernel distribution, place it in one of the version-independent directories under /lib/modules.
This is the default strategy, which can be overridden in /etc/modules.conf.
1.2.1. Прежде, чем продолжить
Прежде, чем мы приступим к программированию, необходимо
обсудить еще ряд моментов. Любая система имеет свои
отличительные черты и каждый из нас имеет разный багаж
знаний. Написать, скомпилировать и запустить свою первую
программу «Hello World!» для многих может оказаться
довольно сложной задачей. Однако, после преодоления этого
начального препятствия, работа, как правило, продвигается без
особых проблем.
1.2.1.1.
Механизм контроля версий
Модули, скомпилированные с одним ядром, могут не
загружаться другим ядром, если в ядре включен механизм
проверки версий модулей. В большинстве дистрибутивов ядро
собирается с такой поддержкой. Мы не собираемся обсуждать
проблему контроля версий в этой книге, поэтому нам остается
порекомендовать, в случае возникновения проблем,
пересобрать ядро без поддержки механизма контроля
версий.
1.2.1.2. Работа в
XWindow
Мы настоятельно рекомендуем скачать и опробовать все
примеры, обсуждаемые в книге. Кроме того, мы настаиваем на
том, чтобы всю работу, связанную с редактированием исходных
текстов, компиляцией и запуском модулей, вы выполняли из
текстовой консоли. Поверьте нашему опыту, XWindow не
подходит для выполнения подобных задач.
Модули не могут использовать функцию printf() для вывода не экран, но они
могут регистрировать сообщения об ошибках, которые в
конечном итоге попадают на экран, но только в текстовой
консоли. Если же модуль загружается из окна терминала,
например xterm, то эти сообщения
будут попадать только в системный журнал и не будут
выводиться на экран. Чтобы видеть выводимые сообщения на
экране, работайте в текстовой консоли (от
переводчика: при опробовании примеров из книги мне
не удалось вывести ни одного сообщения на экран, так что
ищите ваши сообщения в системном журнале, в моем случае это
был файл /var/log/kern.log).
Анатомия модуля ядра
Загружаемые модули ядра имеют ряд фундаментальных отличий от элементов, интегрированных непосредственно в ядро, а также от обычных программ. Обычная программа содержит главную процедуру (main)в отличие от загружаемого модуля, содержащего функции входа и выхода (в версии 2.6 эти функции можно именовать как угодно). Функция входа вызывается, когда модуль загружается в ядро, а функция выхода – соответственно при выгрузке из ядра. Поскольку функции входа и выхода являются пользовательскими, для указания назначения этих функций используются макросы и . Загружаемый модуль содержит также набор обязательных и дополнительных макросов. Они определяют тип лицензии, автора и описание модуля, а также другие параметры. Пример очень простого загружаемого модуля приведен на рисунке 1.
Рисунок 1. Код простого загружаемого модуля.
Версия 2.6 ядра Linux предоставляет новый, более простой метод создания загружаемых модулей. После того как модуль создан, можно использовать обычные пользовательские инструменты для управления модулями (несмотря на изменения внутреннего устройства):
(устанавливает модуль),
(удаляет модуль),
(контейнер для
и ),
(для создания зависимостей между модулями) и
(для поиска значений в модулях макроса).
За дополнительной информацией о создании загружаемых модулей для ядра версии 2.6 обратитесь к ссылкам в разделе .
Examples
To list all active kernel modules, run lsmod at the command line:
lsmod
This is essentially the same as running «cat /proc/modules«, but the information is formatted a little nicer. You’ll see three columns of information:
- Module: the name of the module. This is usually the name of the module file, minus the extension (.o or .ko), but it may have a custom name, which can be specified as an option when the module is inserted with the insmod command.
- Size: the amount of memory used by the resident module, in bytes.
- Used by: This column contains a number representing how many instances of the module are being used. If the number is zero, the module is not currently being used. Text after the number represents any available information about what is using the module: this is commonly a device name, a filesystem identifier, or the name of another module.
Output of lsmod will resemble the following:
Module Size Used by fuse 52176 3 cryptd 14125 0 aes_i586 16647 2 aes_generic 32970 1 aes_i586 parport_pc 22036 0 ppdev 12651 0 lp 12797 0 parport 31254 3 lp,ppdev,parport_pc bnep 17288 2 rfcomm 28626 0 bluetooth 103791 10 rfcomm,bnep cpufreq_conservative 12987 0 cpufreq_stats 12762 0 cpufreq_powersave 12422 0 cpufreq_userspace 12520 0 loop 17810 0 uvcvideo 56896 0 videodev 61658 1 uvcvideo media 13692 2 videodev,uvcvideo snd_hda_codec_realtek 142267 1 arc4 12418 2 joydev 17010 0 ath9k 58983 0 snd_hda_intel 21786 2 ath9k_common 12648 1 ath9k snd_hda_codec 63477 2 snd_hda_intel,snd_hda_codec_realtek ath9k_hw 311433 2 ath9k_common,ath9k i915 321557 3 drm_kms_helper 22738 1 i915 drm 146387 4 drm_kms_helper,i915 i2c_algo_bit 12713 1 i915 snd_hwdep 12943 1 snd_hda_codec snd_pcm 53461 2 snd_hda_codec,snd_hda_intel snd_page_alloc 12867 2 snd_pcm,snd_hda_intel ath 17114 3 ath9k_hw,ath9k_common,ath9k mac80211 171389 1 ath9k acer_wmi 21651 0 sparse_keymap 12680 1 acer_wmi iTCO_wdt 16945 0 acpi_cpufreq 12807 1 snd_seq 39512 0 snd_seq_device 13016 1 snd_seq snd_timer 22356 2 snd_seq,snd_pcm snd 42761 12 snd_timer,snd_seq_device,snd_seq,snd_pcm,snd_hwdep,snd_hda_codec,snd_hda_intel,snd_hda_codec_realtek coretemp 12770 0 cfg80211 113445 3 mac80211,ath,ath9k rts_pstor 226667 0 rfkill 18516 5 cfg80211,acer_wmi,bluetooth iTCO_vendor_support 12632 1 iTCO_wdt i2c_i801 12670 0 psmouse 59609 0 i2c_core 19116 6 i2c_i801,i2c_algo_bit,drm,drm_kms_helper,i915,videodev pcspkr 12515 0 soundcore 12921 1 snd mperf 12421 1 acpi_cpufreq evdev 17225 10 serio_raw 12803 0 ac 12552 0 processor 27565 1 acpi_cpufreq video 17459 1 i915 battery 12986 0 power_supply 13283 2 battery,ac wmi 13051 1 acer_wmi button 12817 1 i915 ext4 306996 2 crc16 12327 2 ext4,bluetooth jbd2 56426 1 ext4 mbcache 12938 1 ext4 microcode 17558 0 hid_logitech_dj 13049 0 usbhid 31554 1 hid_logitech_dj hid 64284 2 usbhid,hid_logitech_dj sg 21476 0 sd_mod 35425 4 crc_t10dif 12332 1 sd_mod thermal 13103 0 thermal_sys 17752 3 thermal,video,processor uhci_hcd 22337 0 ahci 24917 3 libahci 18373 1 ahci libata 125014 2 libahci,ahci ehci_hcd 39631 0 usbcore 104555 5 ehci_hcd,uhci_hcd,usbhid,uvcvideo scsi_mod 135081 4 libata,sd_mod,sg,rts_pstor r8169 41830 0 mii 12595 1 r8169 usb_common 12338 1 usbcore
Дальнейшее изучение
Это был лишь общий обзор процессов управления модулями в ядре. Лучшим источником дополнительной информации об управлении модулями является сам исходный код. Основные функции управления модулями содержатся в ./linux/kernel/module.c (и соответствующем файле заголовка ./linux/include/linux/module.h). Несколько функций, зависящих от архитектуры, находятся в ./linux/arch/<arch>/kernel/module.c. Наконец, функция автозагрузки ядра (которая автоматически загружает модуль из ядра при необходимости) находится в файле ./linux/kernel/kmod.c. Эта функция включается при помощи параметра настройки .
Похожие темы
- Anatomy of Linux loadable kernel modules (EN) — оригинал статьи.
- Посетите блог Расти Рассела «Bleeding Edge», посвященный его текущим разработкам для ядра Linux. Расти – ведущий разработчик новой архитектуры модулей Linux.(EN)
- Руководство по программированию модулей ядра Linux, хотя слегка устарело, содержит большое количество подробной информации о загружаемых модулях и их разработке. (EN)
- В статье «Доступ к ядру Linux с помощью файловой системы /proc»
(developerWorks, март 2006 г.) приведен подробный обзор программирования загружаемых модулей ядра с использованием файловой системы /proc. -
Подробнее узнать о работе системы вызовов можно из статьи
«Kernel command using
Linux system calls» (EN)
(developerWorks, март 2007 г.). - Чтобы узнать больше о ядре Linux, прочтите первую статью Тима «Анатомия ядра Linux» (developerWorks, июнь 2007 г.) из этой серии, в которой дан общий обзор ядра Linux и некоторых его интересных особенностей.
- Прочитайте великолепное введение в формат ELF »
Standards
and specs: An unsung hero: the hardworking ELF» (EN) (developerWorks, декабрь 2005 г.). ELF является стандартным форматом объектных файлов для Linux. ELF — это гибкий формат файлов, охватывающий исполняемые образы, объектные файлы, общие библиотеки и даже дампы ядра. Более подробную информацию можно найти также в справочнике по формату (EN) (документ PDF) и в подробной
книге по форматам ELF (EN). - На сайте
Captain’s Universe
имеется великолепное введение в сборку загружаемых модулей с примерами make-файлов. Процесс сборки загружаемых модулей в ядре версии 2.6 был изменен (к лучшему).(EN) - Имеется несколько утилит для установки, удаления и управления модулями.(EN) Модули устанавливаются в ядро командой
, а удаляются командой
. Для запроса о том, какие модули сейчас загружены в ядро, используйте команду
. Поскольку модули могут зависеть друг от друга, существует команда
для создания файла зависимостей. Для автоматической загрузки зависимых модулей до загрузки основного модуля используйте команду
(оболочка команды ). Наконец, прочесть информацию загружаемого модуля можно при помощи команды
. - Статья «Linkers and Loaders» (EN)
в журнале Linux Journal (ноябрь 2002 г.) содержит замечательное введение в работу редакторов связей и загрузчиков, использующих файлы ELF (включая разрешение символов и перемещение). -
В
разделе Linux сайта developerWorks
имеются и другие ресурсы для Linux-разработчиков. Ознакомьтесь также с
самыми популярными статьями и руководствами. (EN) -
Ознакомьтесь с разделами
советов и
учебных пособий по Linux на developerWorks.
-
Используйте
ознакомительные версии ПО IBM,
которые можно загрузить непосредственно с developerWorks, в вашем следующем проекте разработки для Linux. (EN)
Протокол транспортного уровня
На этом уровне обеспечивается обработка таких IP-протоколов, как: UDP, TCP, SCTP и т.д., которые описаны в файле <linux/in.h>.
/* Standard well-defined IP protocols. */ enum { IPPROTO_IP = 0, /* Dummy protocol for TCP */ IPPROTO_ICMP = 1, /* Internet Control Message Protocol */ IPPROTO_IGMP = 2, /* Internet Group Management Protocol */ ... IPPROTO_TCP = 6, /* Transmission Control Protocol */ ... IPPROTO_UDP = 17, /* User Datagram Protocol */ ... IPPROTO_SCTP = 132, /* Stream Control Transport Protocol */ ... IPPROTO_RAW = 255, /* Raw IP packets */ }
Для установки обработчика протоколов транспортного уровня существует специальный API, объявленный в <net/protocol.h>.
//данная структура используется для регистрации протоколов struct net_protocol { int (*handler)( struct sk_buff *skb ); void (*err_handler)( struct sk_buff *skb, u32 info ); int (*gso_send_check)( struct sk_buff *skb ); struct sk_buff *(*gso_segment)( struct sk_buff *skb, int features ); struct sk_buff **(*gro_receive)( struct sk_buff **head, struct sk_buff *skb ); int (*gro_complete)( struct sk_buff *skb ); unsigned int no_policy:1, netns_ok:1; }; // второй параметр функций inet_..._protocol – это константа из списка IPPROTO_* int inet_add_protocol( const struct net_protocol *prot, unsigned char num ); int inet_del_protocol( const struct net_protocol *prot, unsigned char num );
В листинге 2 представлен пример модуля, устанавливающего обработчик для протокола транспортного уровня.
Листинг 2. Пример реализации протокола транспортного уровня (файл trn_proto.c)
#include <linux/module.h> #include <linux/init.h> #include <net/protocol.h> int test_proto_rcv( struct sk_buff *skb ) { printk( KERN_INFO "Packet received with length: %u\n", skb->len ); return skb->len; }; static struct net_protocol test_proto = { .handler = test_proto_rcv, .err_handler = 0, .no_policy = 0, }; #define PROTO IPPROTO_RAW static int __init my_init( void ) { int ret; if( ( ret = inet_add_protocol( &test_proto, PROTO ) ) < 0 ) { printk( KERN_INFO "proto init: can't add protocol\n"); return ret; }; printk( KERN_INFO "proto module loaded\n" ); return 0; } static void __exit my_exit( void ) { inet_del_protocol( &test_proto, PROTO ); printk( KERN_INFO "proto module unloaded\n" ); } module_init( my_init ); module_exit( my_exit ); MODULE_AUTHOR( "Oleg Tsiliuric" ); MODULE_LICENSE( "GPL v2" );
Установим и проверим функционирование нашего модуля для протокола :
$ sudo insmod trn_proto.ko $ lsmod | head -n2 Module Size Used by trn_proto 780 0 $ cat /proc/modules | grep proto trn_proto 780 0 - Live 0xf9a26000 $ ls -R /sys/module/trn_proto /sys/module/trn_proto: holders initstate notes refcnt sections srcversion ... $ sudo rmmod trn_proto $ dmesg | tail -n60 | grep -v ^audit proto module loaded proto module unloaded
Но если попытаться установить обработчик для уже обрабатываемого (т.е. установленного) протокола (например, IPPROTO_TPC), то возникнет следующая ошибка.
$ sudo insmod trn_proto.ko insmod: error inserting 'trn_proto.ko': -1 Operation not permitted $ dmesg | tail -n60 | grep -v ^audit proto init: can't add protocol $ lsmod | grep proto $
Как видно, здесь возникла уже упоминавшаяся ранее сложность.
Поэтому если вы планируете реализовать поддержку нового (или не использующегося в системе) протокола, то в системе может не оказаться инструментов для его тестирования, и предварительно необходимо будет создать тестовые приложения прикладного уровня.
Если же попытаться смоделировать работу нового протокола под видом уже существующего (например, IPPROTO_UDP), то вам сначала понадобится удалить существующий обработчик данного протокола, что может нарушить работоспособность системы (например, в случае с IPPROTO_UDP такое действие приведет к разрушению системы разрешения доменных имён DNS).