Что такое linux-headers?
Это заголовочные файлы, являющиеся частью исходного кода ядра. Они содержат описания внешних интерфейсов, структур данных и макросов. Эти файлы необходимы для сборки модулей ядра, обеспечивая актуальность данных для бинарной совместимости.
Пользовательские программы обращаются к
Модули ядра обращаются к
#kernel #theory
Это заголовочные файлы, являющиеся частью исходного кода ядра. Они содержат описания внешних интерфейсов, структур данных и макросов. Эти файлы необходимы для сборки модулей ядра, обеспечивая актуальность данных для бинарной совместимости.
Пользовательские программы обращаются к
/usr/include заголовкам.Модули ядра обращаются к
/usr/src/linux-headers-$(uname -r) заголовкам.#kernel #theory
✍6❤3👍1🆒1
Встроенные и загружаемые модули ядра
Встроенные модули - это те, которые встроены в ядро на этапе его сборки.
Загружаемые модули - обычно от сторонних поставщиков, могут существовать только отдельно и загружаться в память на этапе исполнения.
Показывает загружаемые модули:
Показывает встроенные модули:
Показывает как встроенные так и загружаемые модули:
Встроенные модули отмечаются как: CONFIG_SCSI=y (встроенная в ядро функциональность), а загружаемые как CONFIG_SCSI=m (отдельные .ko файлы, которые запускает
CONFIG_SCSI взят для примера.
Некоторые модули не видны в выводе
#kernel #utils
Встроенные модули - это те, которые встроены в ядро на этапе его сборки.
Загружаемые модули - обычно от сторонних поставщиков, могут существовать только отдельно и загружаться в память на этапе исполнения.
Показывает загружаемые модули:
$ lsmod
Показывает встроенные модули:
$ cat /lib/modules/$(uname -r)/modules.builtin
Показывает как встроенные так и загружаемые модули:
$ ls /sys/module
Встроенные модули отмечаются как: CONFIG_SCSI=y (встроенная в ядро функциональность), а загружаемые как CONFIG_SCSI=m (отдельные .ko файлы, которые запускает
kmod при необходимости).CONFIG_SCSI взят для примера.
Некоторые модули не видны в выводе
lsmod, но видны в modinfo потому что они являются (builtin). #kernel #utils
👍4✍1❤1❤🔥1
Замена системных вызовов с помощью модулей ядра
Из книги https://tldp.org/LDP/lkmpg/2.6/lkmpg.pdf:
You can even write modules to replace the kernel's system calls, which we'll do shortly. Crackers often make use of this sort of thing for backdoors or trojans, but you can write your own modules to do more benign things, like have the kernel write Tee hee, that tickles! everytime someone tries to delete a file on your system.
Другими словами: существует возможность создания модулей для ядра операционной системы, которые могут заменять системные вызовы. Это может использоваться как злоумышленниками для создания бэкдоров и троянов, так и для более безобидных задач, таких как добавление пользовательского сообщения при попытке удаления файла.
#kernel #books
Из книги https://tldp.org/LDP/lkmpg/2.6/lkmpg.pdf:
You can even write modules to replace the kernel's system calls, which we'll do shortly. Crackers often make use of this sort of thing for backdoors or trojans, but you can write your own modules to do more benign things, like have the kernel write Tee hee, that tickles! everytime someone tries to delete a file on your system.
Другими словами: существует возможность создания модулей для ядра операционной системы, которые могут заменять системные вызовы. Это может использоваться как злоумышленниками для создания бэкдоров и троянов, так и для более безобидных задач, таких как добавление пользовательского сообщения при попытке удаления файла.
#kernel #books
👨💻1
Что такое GRUB?
GRUB (GRand Unified Bootloader) в основном предназначен для загрузки операционной системы. Он управляет процессом загрузки, позволяя пользователю выбрать операционную систему или ядро, которое он хочет загрузить, и затем передает управление этому выбранному ядру.
Основная функция загрузчика Linux включает в себя возможность выполнять следующие задачи:
* выбирать одно из нескольких ядер;
* переключаться между наборами параметров ядра;
* разрешить пользователю вручную переопределять и редактировать имена и параметры образов ядра;
* обеспечить поддержку загрузки других операционных систем;
Файл конфигурации GRUB, который отображается при нажатии кнопки
2. Процесс выключения (или перезагрузки) управляется самим операционным ядром (kernel) и операционной системой, которые выполняют последовательность действий для корректного завершения всех процессов, демонтирования файловых систем и отключения питания.
Таким образом, когда вы выключаете систему, GRUB не играет никакой роли. Его задача завершается после того, как операционная система была успешно загружена.
#kernel #theory
GRUB (GRand Unified Bootloader) в основном предназначен для загрузки операционной системы. Он управляет процессом загрузки, позволяя пользователю выбрать операционную систему или ядро, которое он хочет загрузить, и затем передает управление этому выбранному ядру.
Основная функция загрузчика Linux включает в себя возможность выполнять следующие задачи:
* выбирать одно из нескольких ядер;
* переключаться между наборами параметров ядра;
* разрешить пользователю вручную переопределять и редактировать имена и параметры образов ядра;
* обеспечить поддержку загрузки других операционных систем;
Файл конфигурации GRUB, который отображается при нажатии кнопки
e в меню GRUB, можно прочитать в файле /boot/grub/grub.cfg на диске. Однако, не рекомендуется редактировать этот файл напрямую, так как он обычно генерируется автоматически с помощью команды update-grub, которая использует шаблоны и настройки из /etc/default/grub и скриптов в /etc/grub.d/
1. GRUB не участвует в процессе выключения. Его роль ограничивается начальной фазой загрузки системы.2. Процесс выключения (или перезагрузки) управляется самим операционным ядром (kernel) и операционной системой, которые выполняют последовательность действий для корректного завершения всех процессов, демонтирования файловых систем и отключения питания.
Таким образом, когда вы выключаете систему, GRUB не играет никакой роли. Его задача завершается после того, как операционная система была успешно загружена.
#kernel #theory
✍11❤🔥3👍2
Что такое Аудит и для чего он нужен?
Нужен для отслеживания критичных с точки зрения безопасности системных событий:
* запуск и завершение работы системы;
* чтение, запись и изменение прав доступа к файлам;
* инициация сетевых соединений;
* попытки неудачной авторизации в системе;
* изменение сетевых настроек;
* изменение информации о пользователях и группах;
* запуск и остановка приложений;
* выполнение системных вызовов;
Ни одно из названных событий не может произойти без использования системных вызовов ядра. Чтобы их отслеживать, достаточно просто перехватывать соответствующие системные вызовы. Именно это и делает подсистема аудита. Когда я работал системным программистом, то часто приходилось взаимодействовать с аудитом (для отладки).
Конфигурация:
После
События 1000 пользователя:
Поиск событий по коду выхода:
Искать события open:
Номера всех системных вызовов:
#kernel #security #utils
Нужен для отслеживания критичных с точки зрения безопасности системных событий:
* запуск и завершение работы системы;
* чтение, запись и изменение прав доступа к файлам;
* инициация сетевых соединений;
* попытки неудачной авторизации в системе;
* изменение сетевых настроек;
* изменение информации о пользователях и группах;
* запуск и остановка приложений;
* выполнение системных вызовов;
Ни одно из названных событий не может произойти без использования системных вызовов ядра. Чтобы их отслеживать, достаточно просто перехватывать соответствующие системные вызовы. Именно это и делает подсистема аудита. Когда я работал системным программистом, то часто приходилось взаимодействовать с аудитом (для отладки).
$ apt-get install -y auditd
$ systemctl status auditd
Конфигурация:
/etc/audit/auditd.conf
Выполнить программу и отследить ее события (работает наподобие strace):$ autrace <path-to-program>
После
autrace:$ ausearch -i -p <pid>
События 1000 пользователя:
$ ausearch -ui 1000
Поиск событий по коду выхода:
$ ausearch -i -e -13
Искать события open:
$ ausearch -ui 1000 -sc open
Номера всех системных вызовов:
$ ausyscall --dump
#kernel #security #utils
✍7👍1
Kernel panic - это критическая ошибка в операционной системе, когда система не может продолжать работу из-за серьезных проблем. Часто это связано с аппаратными сбоями, такими как неисправность оперативной памяти, процессора. Также это может быть вызвано невозможностью найти и смонтировать корневую файловую систему, запуском некорректных драйверов или ошибок в процессе инициализации (initramfs). Система может пытаться использовать несуществующие ресурсы, что приводит к этому состоянию.
#kernel #theory
#kernel #theory
👀6✍5🔥2🤡1
——— НАВИГАЦИЯ ———
GIT: #git
Жвачка: #fun
Ядро: #kernel
Разное: #misc
ПО: #software
Игры: #games
Книги: #books
Люди: #people
Сборка: #build
Утилиты: #utils
Теория: #theory
Debian: #debian
Оболочка: #shell
СПО: #opensource
Память: #memory
Терминал: #terminal
Мои мысли: #thoughts
Безопасность: #security
Информация канала: #info
Конфигурационные файлы: #dotfiles
Кто я: https://xn--r1a.website/krxnotes/246
Откуда берется информация: https://xn--r1a.website/krxnotes/500
Поддержать канал:
GIT: #git
Жвачка: #fun
Ядро: #kernel
Разное: #misc
ПО: #software
Игры: #games
Книги: #books
Люди: #people
Сборка: #build
Утилиты: #utils
Теория: #theory
Debian: #debian
Оболочка: #shell
СПО: #opensource
Память: #memory
Терминал: #terminal
Мои мысли: #thoughts
Безопасность: #security
Информация канала: #info
Конфигурационные файлы: #dotfiles
Кто я: https://xn--r1a.website/krxnotes/246
Откуда берется информация: https://xn--r1a.website/krxnotes/500
Поддержать канал:
2202 2036 6907 4603
Спасибо, что читаете!👍21❤2
Кризис в продвижении Rust в ядро из-за опасений усложнения сопровождения
Оказывается не всё так просто как хотелось, война между С и Rust, а точнее между инженерами, которые продвигают разные подходы. Кто же победит?
https://www.opennet.ru/opennews/art.shtml?num=62685
#kernel
Оказывается не всё так просто как хотелось, война между С и Rust, а точнее между инженерами, которые продвигают разные подходы. Кто же победит?
https://www.opennet.ru/opennews/art.shtml?num=62685
#kernel
🤔2🌚2⚡1
Библиотечные функции и системные вызовы
Библиотечные функции - верхний уровень, работает в пространстве пользователя, обеспечивает более удобный интерфейс к функциям, которые выполняют работу (системным вызовам). То есть библиотечные функции обращаются к системным вызовам.
Системные вызовы - работают в привилегированном режиме от имени ядра и предоставляются самим ядром. Например, библиотечная функция printf() формирует строку, в соответствии с заданным форматом, и передает ее низкоуровневому системному вызову write(), который и выводит строку на устройство стандартного вывода.
Цепочка: Программа обращается к библиотечным функциям, находясь в пользовательском режиме. Затем библиотечная функция обращается к системным вызовам. Системные вызовы уже работают в режиме привилегированном (являются частью ядра). Затем когда системный вызов завершает работу, он возвращает управление библиотечной функции и происходит обратный переход в пользовательский режим.
Unix производит переключение из пространства пользователя в пространство ядра всякий раз, когда приложение делает системный вызов или приостанавливается аппаратным прерыванием. Например, код модуля исполняется в пространстве ядра, а обычная программа, исполняется в пространстве пользователя (прикладное ПО).
#kernel #theory
Библиотечные функции - верхний уровень, работает в пространстве пользователя, обеспечивает более удобный интерфейс к функциям, которые выполняют работу (системным вызовам). То есть библиотечные функции обращаются к системным вызовам.
Системные вызовы - работают в привилегированном режиме от имени ядра и предоставляются самим ядром. Например, библиотечная функция printf() формирует строку, в соответствии с заданным форматом, и передает ее низкоуровневому системному вызову write(), который и выводит строку на устройство стандартного вывода.
Цепочка: Программа обращается к библиотечным функциям, находясь в пользовательском режиме. Затем библиотечная функция обращается к системным вызовам. Системные вызовы уже работают в режиме привилегированном (являются частью ядра). Затем когда системный вызов завершает работу, он возвращает управление библиотечной функции и происходит обратный переход в пользовательский режим.
Unix производит переключение из пространства пользователя в пространство ядра всякий раз, когда приложение делает системный вызов или приостанавливается аппаратным прерыванием. Например, код модуля исполняется в пространстве ядра, а обычная программа, исполняется в пространстве пользователя (прикладное ПО).
#kernel #theory
✍5❤5👍1🤝1
Частый вопрос на позицию системного инженера Linux
В Linux нет технологии которая бы позволяла залезть процессу в память другого процесса. Но почему это может GDB (GNU Debugger)? Это возможно благодаря тому, что GDB использует отладочные интерфейсы ядра Linux (например, системный вызов
Файл
- Значение 0: Разрешает отладку всех процессов
- Значение 1: Разрешает отладку только процессов с тем же UID
- Значение 2: Запрещает отладку процессов с другим UID
#kernel #theory #security
В Linux нет технологии которая бы позволяла залезть процессу в память другого процесса. Но почему это может GDB (GNU Debugger)? Это возможно благодаря тому, что GDB использует отладочные интерфейсы ядра Linux (например, системный вызов
ptrace), которые позволяют отслеживать и изменять состояние других процессов, включая доступ к их памяти для чтения и записи. Таким образом, хотя само ядро Linux не предоставляет прямого доступа к памяти других процессов, GDB может использовать специальные механизмы для отладки и анализа процессов.Файл
/proc/sys/kernel/yama/ptrace_scope контролирует степень безопасности работы ptrace.- Значение 0: Разрешает отладку всех процессов
- Значение 1: Разрешает отладку только процессов с тем же UID
- Значение 2: Запрещает отладку процессов с другим UID
#kernel #theory #security
✍7❤3🙏2👍1
Компоненты ядра операционной системы Linux
1. Process Scheduler (SCHED)
Планировщик процессов, отвечает за контроль над доступом процессов к CPU. Обеспечивает такое поведение ядра, при котором все процессы имеют справедливый доступ к центральному процессору.
2. Memory Manager (MM)
Менеджер памяти, обеспечивает различным процессам безопасный доступ к основной памяти системы. Кроме того, MM обеспечивает работу виртуальной памяти, которая позволяет процессам использовать больше памяти, чем реально доступно в системе. Выделенная, но неиспользуемая память вытесняется на файловую систему, и при необходимости - возвращается из неё обратно в память (swapping).
3. Virtual File System (VFS)
Уровень абстракции поверх конкретной реализации файловой системы. Целью VFS является обеспечение единообразного доступа клиентских приложений к различным типам файловых систем.
4. Network Interface (NET)
Сетевые интерфейсы, обеспечивает работу с различными сетевыми стандартами и сетевым оборудованием.
5. Inter-Process Communication (IPC)
Межпроцессное взаимодействие, обмен данными между потоками одного или разных процессов, реализуется посредством механизмов, предоставляемых ядром OC или процессом.
#kernel #theory
1. Process Scheduler (SCHED)
Планировщик процессов, отвечает за контроль над доступом процессов к CPU. Обеспечивает такое поведение ядра, при котором все процессы имеют справедливый доступ к центральному процессору.
2. Memory Manager (MM)
Менеджер памяти, обеспечивает различным процессам безопасный доступ к основной памяти системы. Кроме того, MM обеспечивает работу виртуальной памяти, которая позволяет процессам использовать больше памяти, чем реально доступно в системе. Выделенная, но неиспользуемая память вытесняется на файловую систему, и при необходимости - возвращается из неё обратно в память (swapping).
3. Virtual File System (VFS)
Уровень абстракции поверх конкретной реализации файловой системы. Целью VFS является обеспечение единообразного доступа клиентских приложений к различным типам файловых систем.
4. Network Interface (NET)
Сетевые интерфейсы, обеспечивает работу с различными сетевыми стандартами и сетевым оборудованием.
5. Inter-Process Communication (IPC)
Межпроцессное взаимодействие, обмен данными между потоками одного или разных процессов, реализуется посредством механизмов, предоставляемых ядром OC или процессом.
#kernel #theory
⚡9✍4👍3
strace
Отследить работу процесса a.out:
Вывод в файл log:
Отслеживание конкретного процесса:
Отследить встроенную команду:
Например, команда 'mount -t nfs ...' возвращает отрицательный статус, можно проанализировать вывод утилиты strace:
Разбор:
-s1024 длина сообщений будет полная, а не обрезанная (32 длиной).
-f отслеживать дочерние процессы (если они будут созданы -
-i указатель инструкции во время системного вызова.
-k трассировка выполнения отслеживаемых процессов.
-n номера системных вызовов.
Данные трюки я использовал при отладке ПО. Работая системным программистом часто приходилось пользоваться strace. Если strace не работает, можно обратиться к файлу
#kernel #utils
Отследить работу процесса a.out:
$ strace a.out
Вывод в файл log:
$ strace -o my-log a.out
Отслеживание конкретного процесса:
$ strace -p <pid>
Отследить встроенную команду:
$ strace bash -c 'cd /tmp'
Например, команда 'mount -t nfs ...' возвращает отрицательный статус, можно проанализировать вывод утилиты strace:
$ strace -o mount.strace -s1024 -f -i -k -n mount -t nfs <path> <to-path>
Разбор:
-s1024 длина сообщений будет полная, а не обрезанная (32 длиной).
-f отслеживать дочерние процессы (если они будут созданы -
fork()).-i указатель инструкции во время системного вызова.
-k трассировка выполнения отслеживаемых процессов.
-n номера системных вызовов.
Данные трюки я использовал при отладке ПО. Работая системным программистом часто приходилось пользоваться strace. Если strace не работает, можно обратиться к файлу
/proc/sys/kernel/yama/ptrace_scope, про него описано в man 2 ptrace.#kernel #utils
👍23✍4❤3
Как смотреть журналы (dmesg и journalctl)
journalctl - системный журнал (читает
Вывод в реальном времени:
Отобразить сегодняшние записи:
Вывести только err уровень:
err, warning уровни:
Показывает журнал конкретного сервиса:
dmesg - системный журнал ядра (читает
less вывод:
Читабельный формат:
Показывает уровень (приоритет):
Вывод в реальном времени:
В сумме:
Зачистить dmesg:
#kernel #utils
journalctl - системный журнал (читает
/var/log/journal).Вывод в реальном времени:
$ journalctl -f
Отобразить сегодняшние записи:
$ journalctl -S today
Вывести только err уровень:
$ journalctl -S today -p err
err, warning уровни:
$ journalctl -S today -p 3..4
Показывает журнал конкретного сервиса:
$ journalctl -u <name>.service
dmesg - системный журнал ядра (читает
/var/log/kern.log или напрямую из ядра).less вывод:
$ dmesg -H
Читабельный формат:
$ dmesg -T
Показывает уровень (приоритет):
$ dmesg -x
Вывод в реальном времени:
$ dmesg -w
В сумме:
$ dmesg -HTx
Зачистить dmesg:
$ dmesg -C
#kernel #utils
👍22❤10✍3❤🔥1🤔1
LFS (Linux From Scratch)
LFS (Linux From Scratch) — это проект (и книга), который учит создавать Linux-дистрибутив буквально с нуля — вы компилируете и собираете каждый компонент вручную, начиная с ядра, libc, bash, gcc и далее.
- Получается минимальная, полностью самостоятельная система, не зависящая от других дистрибутивов.
- Процесс долгий, требует глубокого понимания Linux, компиляции, зависимостей.
- Система после сборки обычно не содержит ничего лишнего, только самые необходимые компоненты — всё остальное вы добавляете самостоятельно.
- LFS не предназначен для повседневного использования как обычный дистрибутив — это, прежде всего, учебный и исследовательский проект.
- На основе LFS можно строить свои собственные дистрибутивы, полностью контролируя набор программ и конфигураций.
LFS стоит использовать, если вы хотите глубоко разобраться во внутреннем устройстве Linux, получить максимальную свободу и контроль над каждым компонентом системы, экспериментировать с нетипичными настройками, патчами и структурой, а также если вас не устраивают стандартные дистрибутивы и вы готовы потратить много времени на ручную сборку и решение возникающих проблем. Кроме того, LFS подходит для создания минимальных систем под специфические задачи, например, для встраиваемых устройств или проведения экспериментов.
Ссылка: https://www.linuxfromscratch.org
Ссылка: https://ru.wikipedia.org/wiki/Linux_From_Scratch
Перевод книги на русский: https://book.linuxfromscratch.ru
#kernel #books #build
LFS (Linux From Scratch) — это проект (и книга), который учит создавать Linux-дистрибутив буквально с нуля — вы компилируете и собираете каждый компонент вручную, начиная с ядра, libc, bash, gcc и далее.
- Получается минимальная, полностью самостоятельная система, не зависящая от других дистрибутивов.
- Процесс долгий, требует глубокого понимания Linux, компиляции, зависимостей.
- Система после сборки обычно не содержит ничего лишнего, только самые необходимые компоненты — всё остальное вы добавляете самостоятельно.
- LFS не предназначен для повседневного использования как обычный дистрибутив — это, прежде всего, учебный и исследовательский проект.
- На основе LFS можно строить свои собственные дистрибутивы, полностью контролируя набор программ и конфигураций.
LFS стоит использовать, если вы хотите глубоко разобраться во внутреннем устройстве Linux, получить максимальную свободу и контроль над каждым компонентом системы, экспериментировать с нетипичными настройками, патчами и структурой, а также если вас не устраивают стандартные дистрибутивы и вы готовы потратить много времени на ручную сборку и решение возникающих проблем. Кроме того, LFS подходит для создания минимальных систем под специфические задачи, например, для встраиваемых устройств или проведения экспериментов.
Ссылка: https://www.linuxfromscratch.org
Ссылка: https://ru.wikipedia.org/wiki/Linux_From_Scratch
Перевод книги на русский: https://book.linuxfromscratch.ru
#kernel #books #build
👍23❤17✍3🔥1😱1
kernel-hardening-checker
Это инструмент и библиотека для Linux, предназначенная для проверки конфигурации ядра на соответствие рекомендациям по усилению безопасности (security hardening) и противодействию эксплойтам. Он позволяет выявить, какие конфигурации ядра включены, а какие нет, помогая администраторам настроить систему на более безопасный уровень работы.
Установка:
# Пакет проходит проверку и скоро появится в ветке sid (unstable)
Проверяет указанный файл конфигурации ядра Linux на включённые меры харденига и выводит отчёт с рекомендациями, опция
> GitHub
#kernel #security #utils #opensource #software
Это инструмент и библиотека для Linux, предназначенная для проверки конфигурации ядра на соответствие рекомендациям по усилению безопасности (security hardening) и противодействию эксплойтам. Он позволяет выявить, какие конфигурации ядра включены, а какие нет, помогая администраторам настроить систему на более безопасный уровень работы.
Установка:
# Пакет проходит проверку и скоро появится в ветке sid (unstable)
Проверяет указанный файл конфигурации ядра Linux на включённые меры харденига и выводит отчёт с рекомендациями, опция
-c указывает путь к конфигу:$ kernel-hardening-checker -c /boot/config-6.1.0-32-amd64
> GitHub
#kernel #security #utils #opensource #software
🆒10❤2
Отладка ядра
Отладка ядра Linux напрямую (например, через
Линус Торвальдс много раз подчёркивал: ядро — это не та система, которую нужно отлаживать классическим способом (breakpoint -> step -> step). Правильный подход — использовать трассировки и профилирование. То есть не "останавливать мир", а собирать информацию во время работы системы.
Итог: полноценная пошаговая отладка ядра на той же машине, где оно выполняется, невозможна и бессмысленна. Правильный путь — инструменты вроде
#kernel
Отладка ядра Linux напрямую (например, через
gdb и vmlinux) обычно малоэффективна. Даже если загрузить символьный файл, большинство переменных будет отображаться как optimized out. Это происходит потому, что ядро нельзя собрать с флагом -O0: без оптимизаций оно будет слишком медленным, нестабильным и во многих случаях просто не загрузится. Поэтому vmlinux полезен в основном для просмотра структуры данных и отдельных символов, но не для полноценной пошаговой отладки.Линус Торвальдс много раз подчёркивал: ядро — это не та система, которую нужно отлаживать классическим способом (breakpoint -> step -> step). Правильный подход — использовать трассировки и профилирование. То есть не "останавливать мир", а собирать информацию во время работы системы.
Итог: полноценная пошаговая отладка ядра на той же машине, где оно выполняется, невозможна и бессмысленна. Правильный путь — инструменты вроде
printk, ftrace, perf, bpftrace, kprobes, tracepoints. Они дают детальную картину происходящего без остановки системы.#kernel
👍10✍4👎2
Как модули попадают в ядро Linux
Когда ядро обнаруживает необходимость в тех или иных функциональных возможностях, ещё не загруженных в память, оно вызывает helper
Утилиты
У модулей есть alias. Например, модуль
Это значит, что
(Примечание:
Затем
Например, модуль
Затем
Для загрузки модулей, собранных вне дерева ядра, полезно иметь включённый CONFIG_MODVERSIONS=y
Он не обязателен для загрузки модулей в принципе, но позволяет обеспечивать совместимость символов между версиями ядра и модулей (versioned symbols), что уменьшает риск получить ошибку при
#kernel #utils
Когда ядро обнаруживает необходимость в тех или иных функциональных возможностях, ещё не загруженных в память, оно вызывает helper
kmod (через механизмы uevent/hotplug). Kmod в свою очередь запускает утилиту modprobe, а уже modprobe вызывает insmod. Посмотреть можно так:$ systemctl status kmod
Утилиты
modprobe, insmod, modinfo и другие - это просто ссылки на /bin/kmod, они ничем не отличаются как отдельные бинарники. Всем заправляет один kmod, можно вызвать /bin/kmod напрямую и он сам определит, какую "утилиту" вы имели в виду.kmod и modprobe запускаются ядром автоматически, когда требуется загрузка определённого модуля. modprobe принимает на вход имя модуля или его alias.У модулей есть alias. Например, модуль
qrtr в выводе lsmod имеет такое имя. Его alias можно посмотреть в /lib/modules/*/modules.alias. Например: net-pf-42 -> qrtrЭто значит, что
modprobe можно передавать один и тот же модуль:$ modinfo qrtr
$ modprobe net-pf-42
(Примечание:
modinfo ищет только по реальному имени файла модуля, alias понимает modprobe)Затем
modprobe просматривает /lib/modules/*/modules.dep. Этот файл описывает модули, которые требуют загрузки других модулей перед своей загрузкой - то есть зависимости. Файл создается командой:$ depmod -a
Например, модуль
qrtr-mhi.ko запрашивает загрузку qrtr.ko и mhi.ko:kernel/net/qrtr/qrtr-mhi.ko: kernel/net/qrtr/qrtr.ko kernel/drivers/bus/mhi/host/mhi.ko
Затем
modprobe вызывает insmod (указывая путь из /lib/modules/*/), который загружает сначала зависимые модули, затем нужный модуль.insmod довольно "глуп" в отношении нахождения модулей, поэтому принимает абсолютные пути и нужный порядок вручную:$ insmod /lib/modules/2.6.11/kernel/fs/fat/fat.ko
$ insmod /lib/modules/2.6.11/kernel/fs/msdos/msdos.ko
modprobe более "умный" - он ориентируется по modules.dep, поэтому достаточно передать имя:$ modprobe msdos
Для загрузки модулей, собранных вне дерева ядра, полезно иметь включённый CONFIG_MODVERSIONS=y
Он не обязателен для загрузки модулей в принципе, но позволяет обеспечивать совместимость символов между версиями ядра и модулей (versioned symbols), что уменьшает риск получить ошибку при
insmod.#kernel #utils
👍10
Процессы в ядре Linux
В ядре существует понятие "ядерных потоков" или "потоков ядра" (
Есть также процессы
Каждый
Но не каждый
#kernel
В ядре существует понятие "ядерных потоков" или "потоков ядра" (
kernel threads, kthreads) - это легковесные процессы, которые выполняются полностью в пространстве ядра и никогда не переходят в пространство пользователя. Они используются для различных фоновых задач: управление устройствами, обработка событий, обслуживание подсистем ядра и другие служебные функции. Большинство kthreads создаются при загрузке системы или динамически ядром по мере необходимости.Есть также процессы
kworker (kernel worker). Это универсальные фоновые рабочие потоки, обслуживающие работу подсистем workqueue. Они выполняют задачи, которые были отложены другими частями ядра: обработка таймеров, deferred work, обслуживание драйверов, ввод-вывод, управление памятью и многое другое. Kworker‑процессы автоматически создаются ядром, масштабируются по количеству CPU и не связаны с конкретным приложением - они обслуживают всю систему.kthread - это любой обычный поток ядра, созданный через kthread_create. Он выполняет свою собственную задачу, прописанную автором кода.kworker - это специальный тип kthread, который используется подсистемой workqueue. Эти потоки создаются и управляются автоматически ядром, а не вручную.Каждый
kworker - это kthread.Но не каждый
kthread - kworker.#kernel
👍15✍2❤1🤣1
ioctl()
Input/Output Control.
Это системный вызов в UNIX‑подобных системах, который позволяет отправлять драйверу устройства специальные команды, выходящие за рамки обычных операций read/write. Каждое устройство само определяет набор своих команд, поэтому
Команды для
Используется для:
1. Выполнения операций, специфичных для устройства (например, очистка буфера).
2. Запроса информации, недоступной через read.
3. Настройки параметров драйвера или устройства.
4. Любых других операций, для которых нет стандартных системных вызовов.
Пример работы выглядит так.
В пользовательской программе вызывается команда:
Эта команда не читает данные напрямую, а сообщает драйверу: "выполни действие IOCTL_GET_MSG". Обычно для таких команд используются макросы
В драйвере эти команды обрабатываются функцией
Таким образом,
пользовательское приложение отправляет запрос -> драйвер получает код команды -> выполняет нужное действие -> возвращает результат.
Это простой способ расширить возможности устройства так, как нужно автору драйвера, не изобретая собственные протоколы поверх read/write.
#kernel
Input/Output Control.
Это системный вызов в UNIX‑подобных системах, который позволяет отправлять драйверу устройства специальные команды, выходящие за рамки обычных операций read/write. Каждое устройство само определяет набор своих команд, поэтому
ioctl даёт гибкий, но низкоуровневый механизм управления.Команды для
ioctl разрабатываются создателями драйверов устройств и могут варьироваться от драйвера к драйверу. Это мощный инструмент, но он также может быть опасным, так как позволяет выполнять низкоуровневые операции, которые могут повредить данные или аппаратное обеспечение, если они используются неправильно.Используется для:
1. Выполнения операций, специфичных для устройства (например, очистка буфера).
2. Запроса информации, недоступной через read.
3. Настройки параметров драйвера или устройства.
4. Любых других операций, для которых нет стандартных системных вызовов.
Пример работы выглядит так.
В пользовательской программе вызывается команда:
ioctl(fd, IOCTL_GET_MSG, buffer)
Эта команда не читает данные напрямую, а сообщает драйверу: "выполни действие IOCTL_GET_MSG". Обычно для таких команд используются макросы
_IOR, _IOW и _IOWR:#define IOCTL_GET_MSG _IOR(MAJOR_NUM, 1, char*)
_IOR — получить данные из драйвера_IOW — отправить данные драйверу_IOWR — и отправить, и получитьВ драйвере эти команды обрабатываются функцией
ioctl, указанной в структуре file_operations:struct file_operations Fops = {
.read = device_read,
.write = device_write,
.open = device_open,
.release = device_release,
.unlocked_ioctl = device_ioctl, // основной обработчик ioctl
.compat_ioctl = device_ioctl // нужен только для 32‑бит -> 64‑бит совместимости
};Таким образом,
ioctl создаёт "канал команд":пользовательское приложение отправляет запрос -> драйвер получает код команды -> выполняет нужное действие -> возвращает результат.
Это простой способ расширить возможности устройства так, как нужно автору драйвера, не изобретая собственные протоколы поверх read/write.
#kernel
✍11👍5❤1❤🔥1🔥1🤣1
Rust
Компилируемый системный язык, ориентированный на безопасность памяти и отсутствие неопределённого поведения, без GC (garbage collector). Позволяет писать низкоуровневый код с производительностью на уровне C/C++, но значительно безопаснее благодаря модели владения и строгой типизации.
Где полезен:
- Backend: высоконагруженные сервисы (Actix, Axum), микросервисы.
- Системное программирование: драйверы, ОС‑компоненты, сетевые стеки.
- WebAssembly: написание высокопроизводительных частей веб‑приложений.
- Безопасная работа с параллелизмом: многопоточные сервисы и runtime‑системы.
- Инструменты и CLI: cargo, ripgrep, fd, starship — многие современные утилиты пишутся на Rust.
Плюсы:
- Высокая производительность, сравнимая с C/C++.
- Отличная экосистема: crates.io, tokio, serde, tracing.
- Cargo: один из лучших менеджеров пакетов/сборки в мире.
- Строгий анализ на этапе компиляции предотвращает целые классы ошибок.
- Безопасность памяти без garbage collector — нет segfault, нет use‑after‑free.
Минусы/реалии:
- Компиляция тяжелее и медленнее, чем у C.
- Встраивание Rust в очень старые экосистемы (например, firmware) может быть сложным.
- Иногда низкоуровневые операции требуют unsafe (компилятор снимает с себя ответственность).
- Крутая кривая обучения из‑за модели владения и borrow checker (строго контролирует доступ к памяти).
Rust vs C/C++:
- Безопаснее C/C++ благодаря строгой модели владения.
- Но C всё ещё проще интегрировать в старые системы и ABI стабильнее.
- Производительность сопоставима или выше, особенно в многопоточных задачах.
- Для embedded Rust часто удобнее C++, но не всегда доступен на самых низких MCU.
Rust в ядре Linux:
- Rust официально принят в mainline Linux (начиная с 6.1).
- Поддержка пока ограничена, но активно развивается.
- Можно писать драйверы и части подсистем ядра, но API Rust в ядре ещё не полный.
- В ядро Rust включён не для переписывания всего, а для безопасных новых драйверов.
- Модули ядра на Rust уже возможны, но только те, которые используют предоставленный Rust‑абстракционный слой (kernel crate).
Где Rust нужен в Linux:
- Пользовательские утилиты: многие современные CLI (ripgrep, exa, fd, bat, starship) уже стандарт-де-факто.
- Внутренние абстракции ядра: безопасные обёртки над указателями, блокировками, refcount, pinning.
- Рендеринг и графика: wgpu (кроссплатформенный WebGPU/Vulkan/Metal/DX12 backend), rend3.
- Игры: на Rust пишут игры и игровые движки с поддержкой Linux (Bevy, Fyrox, Amethyst).
- Новые драйверы: сетевые, USB, storage, сенсоры — безопасное ядро без use-after-free.
- Аудио и DSP: rodio, kira, cpal.
- WebAssembly: выполнение WASM‑модулей на Linux (wasmtime, wasmer).
- DevOps/инфраструктура: контейнерные рантаймы, файловые утилиты, CI‑инструменты.
- Сетевые сервисы: высокопроизводительные backend‑приложения под Linux (Axum, Actix).
- Security‑инструменты: сканеры, песочницы, анализаторы (Rust популярен в security‑комьюнити).
- Файловые системы и блочные устройства: есть исследования и эксперименты по FUSE‑драйверам на Rust.
Сложность:
- Порог входа выше среднего.
- Но после понимания модели владения продуктивность высокая.
- Отлично подходит для кода, где важна безопасность + скорость.
Итог: Rust — мощный системный язык, который сочетает скорость C с безопасностью на уровне высокоуровневых языков (Rust ведёт себя по скорости как C). Подходит для драйверов, системного ПО, сетевых сервисов и CLI. Linux уже официально поддерживает Rust, и будущее ядра включает постепенное расширение Rust‑подсистем для безопасных драйверов и новых модулей.
#misc #kernel
Компилируемый системный язык, ориентированный на безопасность памяти и отсутствие неопределённого поведения, без GC (garbage collector). Позволяет писать низкоуровневый код с производительностью на уровне C/C++, но значительно безопаснее благодаря модели владения и строгой типизации.
Где полезен:
- Backend: высоконагруженные сервисы (Actix, Axum), микросервисы.
- Системное программирование: драйверы, ОС‑компоненты, сетевые стеки.
- WebAssembly: написание высокопроизводительных частей веб‑приложений.
- Безопасная работа с параллелизмом: многопоточные сервисы и runtime‑системы.
- Инструменты и CLI: cargo, ripgrep, fd, starship — многие современные утилиты пишутся на Rust.
Плюсы:
- Высокая производительность, сравнимая с C/C++.
- Отличная экосистема: crates.io, tokio, serde, tracing.
- Cargo: один из лучших менеджеров пакетов/сборки в мире.
- Строгий анализ на этапе компиляции предотвращает целые классы ошибок.
- Безопасность памяти без garbage collector — нет segfault, нет use‑after‑free.
Минусы/реалии:
- Компиляция тяжелее и медленнее, чем у C.
- Встраивание Rust в очень старые экосистемы (например, firmware) может быть сложным.
- Иногда низкоуровневые операции требуют unsafe (компилятор снимает с себя ответственность).
- Крутая кривая обучения из‑за модели владения и borrow checker (строго контролирует доступ к памяти).
Rust vs C/C++:
- Безопаснее C/C++ благодаря строгой модели владения.
- Но C всё ещё проще интегрировать в старые системы и ABI стабильнее.
- Производительность сопоставима или выше, особенно в многопоточных задачах.
- Для embedded Rust часто удобнее C++, но не всегда доступен на самых низких MCU.
Rust в ядре Linux:
- Rust официально принят в mainline Linux (начиная с 6.1).
- Поддержка пока ограничена, но активно развивается.
- Можно писать драйверы и части подсистем ядра, но API Rust в ядре ещё не полный.
- В ядро Rust включён не для переписывания всего, а для безопасных новых драйверов.
- Модули ядра на Rust уже возможны, но только те, которые используют предоставленный Rust‑абстракционный слой (kernel crate).
Где Rust нужен в Linux:
- Пользовательские утилиты: многие современные CLI (ripgrep, exa, fd, bat, starship) уже стандарт-де-факто.
- Внутренние абстракции ядра: безопасные обёртки над указателями, блокировками, refcount, pinning.
- Рендеринг и графика: wgpu (кроссплатформенный WebGPU/Vulkan/Metal/DX12 backend), rend3.
- Игры: на Rust пишут игры и игровые движки с поддержкой Linux (Bevy, Fyrox, Amethyst).
- Новые драйверы: сетевые, USB, storage, сенсоры — безопасное ядро без use-after-free.
- Аудио и DSP: rodio, kira, cpal.
- WebAssembly: выполнение WASM‑модулей на Linux (wasmtime, wasmer).
- DevOps/инфраструктура: контейнерные рантаймы, файловые утилиты, CI‑инструменты.
- Сетевые сервисы: высокопроизводительные backend‑приложения под Linux (Axum, Actix).
- Security‑инструменты: сканеры, песочницы, анализаторы (Rust популярен в security‑комьюнити).
- Файловые системы и блочные устройства: есть исследования и эксперименты по FUSE‑драйверам на Rust.
Сложность:
- Порог входа выше среднего.
- Но после понимания модели владения продуктивность высокая.
- Отлично подходит для кода, где важна безопасность + скорость.
Итог: Rust — мощный системный язык, который сочетает скорость C с безопасностью на уровне высокоуровневых языков (Rust ведёт себя по скорости как C). Подходит для драйверов, системного ПО, сетевых сервисов и CLI. Linux уже официально поддерживает Rust, и будущее ядра включает постепенное расширение Rust‑подсистем для безопасных драйверов и новых модулей.
#misc #kernel
💊9✍5👻5❤3👎3⚡2🔥2🆒1🦄1