适用:Ubuntu 20.04 / 22.04 / 24.04
目标:打 PREEMPT_RT 实时补丁,手动编译安装实时内核
硬件推荐:x86_64 PC / NVIDIA Jetson 嵌入式(步骤通用,仅源码分支有区别)
sudo apt updatesudo apt install build-essential libncurses-dev bison flex libssl-dev libelf-dev dwarves git cpufrequtils# 可选:用于打包deb内核sudo apt install libdebconf-kde-dev
1、版本匹配核心规则
内核版本必须和 RT 补丁版本完全一致
例:linux-6.6.38 → rt 补丁 patch-6.6.38-rt49.patch.xz
uname -a查看当前系统内核版本,例如:
Linux ubuntu-YogaPro-16s-IRP8 6.8.0-124-generic #124~22.04.1-Ubuntu SMP PREEMPT_DYNAMIC Tue May 26 21:05:19 UTC x86_64 x86_64 x86_64 GNU/Linux
Ubuntu 22.04,当前内核 6.8.0-124-generic,x86_64 笔记本 Yoga Pro 16s IRP8
必须下载 6.8 系列主线内核 + 同版本 rt 补丁
查看当前主线稳定RT版本:
https://cdn.kernel.org/pub/linux/kernel/projects/rt/
sudo apt updatesudo apt install -y build-essential libncurses-dev bison flex libssl-dev libelf-dev dwarves git cpufrequtils rt-tests
mkdir ~/kernel_rt_6.8 && cd ~/kernel_rt_6.8# 主线6.8源码wget -c https://mirrors.edge.kernel.org/pub/linux/kernel/v6.x/linux-6.8.2.tar.xz# 6.8 系列rt补丁合集wget -c https://mirrors.edge.kernel.org/pub/linux/kernel/projects/rt/6.8/patch-6.8.2-rt11.patch.xz# 解压源码tar -xf linux-6.8.2.tar.xzcd linux-6.8.2# 打入RT补丁xz -dc ../patch-6.8.2-rt11.patch.xz | patch -p1
拷贝当前系统硬件配置:
cp /boot/config-$(uname -r) .config
设置编译选项:
make menuconfig
编译:
make menuconfig# 1. 根儿案例setup -> Preemption Model 选 Fully Preemptible Kernel (RT)# 2. Timer frequency = 1000Hz# 3. Local version 填 -rt11# 保存退出yes "" | make olddefconfig# 编译make -j$(nproc)make modules -j$(nproc)# 安装# 安装模块时自动删除调试符号,模块体积直接缩水90%sudo make INSTALL_MOD_STRIP=1 modules_installsudo make install
脚本设置.config
# 1. 设置 Fully Preemptible Kernel (RT)./scripts/config --enable CONFIG_PREEMPT_RT# 2. 设置 Timer frequency 1000Hz./scripts/config --set-val CONFIG_HZ 1000# 3. 设置 Local version./scripts/config --set-val CONFIG_LOCALVERSION "-rt11"# 修复证书编译报错核心两行./scripts/config --disable CONFIG_SYSTEM_TRUSTED_KEYS./scripts/config --disable CONFIG_SYSTEM_REVOCATION_KEYS# 自动补齐依赖、校验配置(必执行)make olddefconfig
1、开启 RT 完全抢占(6.x内核为CONFIG_PREEMPT_RT,5.x为CONFIG_PREEMPT_RT_FULL)
./scripts/config --enable CONFIG_PREEMPT_RT
内部会自动配套开启:CONFIG_PREEMPT、CONFIG_PREEMPT_RT 相关依赖,不用手动开。
2、定时器 1000Hz
./scripts/config --set-val CONFIG_HZ 1000
3、内核版本后缀 -rt11
./scripts/config --set-val CONFIG_LOCALVERSION "-rt11"
编译后 uname -r 会显示类似 5.15.xx-rt11。
验证是否修改成功
# 查看抢占模式grep CONFIG_PREEMPT_RT_FULL .config# 查看时钟频率grep CONFIG_HZ .config# 查看本地版本grep CONFIG_LOCALVERSION .config
编译时如果报如下错误:
ubuntu@ubuntu-YogaPro-16s-IRP8:~/kernel_rt_6.8/linux-6.8.2$ make -j$(nproc)mkdir -p /home/ubuntu/kernel_rt_6.8/linux-6.8.2/tools/objtool && make O=/home/ubuntu/kernel_rt_6.8/linux-6.8.2 subdir=tools/objtool --no-print-directory -C objtoolmkdir -p /home/ubuntu/kernel_rt_6.8/linux-6.8.2/tools/bpf/resolve_btfids && make O=/home/ubuntu/kernel_rt_6.8/linux-6.8.2 subdir=tools/bpf/resolve_btfids --no-print-directory -C bpf/resolve_btfidsINSTALL libsubcmd_headersINSTALL libsubcmd_headersCALL scripts/checksyscalls.shmake[3]: *** No rule to make target 'debian/canonical-certs.pem', needed by 'certs/x509_certificate_list'. Stop.make[2]: *** [scripts/Makefile.build:481: certs] Error 2make[2]: *** Waiting for unfinished jobs....CHK kernel/kheaders_data.tar.xzmake[1]: *** [/home/ubuntu/kernel_rt_6.8/linux-6.8.2/Makefile:1921: .] Error 2make: *** [Makefile:240: __sub-make] Error 2
报错原因
Ubuntu 官方内核打包依赖 debian/canonical-certs.pem 证书文件,主线源码 / RT 补丁源码里没有这个文件,编译签名证书环节直接中断。
两种根治方案(推荐方案 1,关闭内核签名,最省事)
方案 1:命令行关闭系统证书签名(无需下载证书,一键修复)
在内核源码根目录执行:
# 关闭Canonical系统信任证书./scripts/config --disable CONFIG_SYSTEM_TRUSTED_KEYS# 关闭系统吊销证书列表./scripts/config --disable CONFIG_SYSTEM_REVOCATION_KEYS# 无交互刷新配置yes "" | make olddefconfig
然后再编译:
make -j$(nproc)
方案 2:如果你需要开启证书签名(不推荐,麻烦)
手动创建空文件绕过检测:
mkdir -p debiantouch debian/canonical-certs.pem
然后再执行编译,但后续模块签名会失效,本地编译自用完全没必要。
安装后重新启动报
error: out of memory
原因为:
你直接 make modules_install 没有剥离调试符号,编译出来的内核模块体积巨大,Ubuntu 自动生成的 initrd.img-6.8.2-rt11 动辄几百 MB,开机加载内存盘直接爆内存 OOM 卡死。
开机按delete或F2键,选择正常内核进入系统,然后修改:
sudo vi /etc/initramfs-tools/initramfs.conf
MODULES=most改为MODULES=dep
most:打包几乎所有硬件驱动(体积爆炸,你当前问题元凶)
dep:仅自动识别你当前电脑挂载根盘必需的驱动,体积直接压缩 70% 以上
# 删除boot下旧的rt内核文件cd /bootsudo rm -f vmlinuz-6.8.2-rt11 initrd.img-6.8.2-rt11 config-6.8.2-rt11 System.map-6.8.2-rt11# 删除臃肿未剥离符号的模块sudo rm -rf /lib/modules/6.8.2-rt11
重新编译:
cd ~/kernel_rt_6.8/linux-6.8.2# 安装模块时自动删除调试符号,模块体积直接缩水90%sudo make INSTALL_MOD_STRIP=1 modules_installsudo make install
uname -aLinux ubuntu-YogaPro-16s-IRP8 6.8.2-rt11 #1 SMP PREEMPT_RT Tue Jun 23 18:14:36 CST 2026 x86_64 x86_64 x86_64 GNU/Linux
先看当前抢占模式简易判断
cat /sys/kernel/realtime
输出 1 = PREEMPT_RT 已启用;0 = 普通抢占内核。
查看内核启动参数抢占标识
cat /proc/cmdline
RT 内核通常会带 preempt=full 或 preempt=rt。
输出结果:
BOOT_IMAGE=/boot/vmlinuz-6.8.2-rt11 root=UUID=fd505579-ee80-4ad3-9cad-5e1ec31f1043 ro quiet splash vt.handoff=7
修改/etc/default/grub
找到 GRUB_CMDLINE_LINUX_DEFAULT,替换成(示例隔离 CPU4、5,你可根据自己 CPU 核心数调整):
GRUB_CMDLINE_LINUX_DEFAULT="quiet splash vt.handoff=7 preempt=rt isolcpus=4,5 nohz_full=4,5 rcu_nocbs=4,5 rcu_nocb_poll"sudo update-grub
修改完之后必须执行sudo update-grub
正常 RT 内核输出示例:
grep PREEMPT /boot/config-$(uname -r)
CONFIG_PREEMPT=yCONFIG_PREEMPT_RT=yCONFIG_PREEMPT_COUNT=yCONFIG_PREEMPT_DYNAMIC=y
配套实时内核前置检查完整命令集
# 1. 确认实时开关cat /sys/kernel/realtime# 2. 读取内核完整配置grep PREEMPT /boot/config-$(uname -r)# 3. 检查用户实时权限ulimit -r -l# 4. 临时设置CPU性能模式(降低延迟)sudo cpupower frequency-set -g performance
系统基础实时配置(测试前必须优化)
1、关闭 CPU 节能:禁用 cpufreq、intel_pstate、turbo boost
# 固定CPU最高频率echo performance | tee /sys/devices/system/cpu/cpu*/cpufreq/scaling_governor# 关闭节能C-stateecho 1 | tee /sys/devices/cpu/cpu*/cpuidle/state*/disable
2、隔离 CPU 核心(irqaffinity、isolcpus)
内核启动参数添加:
isolcpus=18,19 nohz_full=18,19 rcu_nocbs=18,19
3、关闭内存交换、透明巨页
swapoff -aecho never > /sys/kernel/mm/transparent_hugepage/enabled
4、提升测试进程实时优先级
chrt -f -p 99 ./test_app # SCHED_FIFO 最高优先级99
核心时延测试工具(分内核态 / 用户态)
基础用法
# Debian/Ubuntuapt install rt-tests# RHEL/CentOSdnf install rt-tests
参数说明:
# 单CPU隔离测试,跑30分钟,打印统计sudo cyclictest -t1 -p99 -i1000 -l1800000 --histfile=hist.txt -m
多核隔离标准测试(核心用法)
# 使用隔离CPU 2,禁止迁移,高精度时钟cyclictest -a2 -p99 -m -S -i10000
-a2:绑定线程到 CPU2
-m:锁内存 mlockall,避免缺页中断
-S:标准统计输出(min/avg/max)
结果解读
运行结束输出:
T: 0 ( 2827) P:99 C:12345 Min:0 Avg:7 Max:487# Min最小时延、Avg平均、Max最大时延(单位us)
实时指标标准(工业硬实时)
工控裸金属无负载:最大抖动<50us
带少量外设负载:<100us
若 max>1000us:存在严重抢占阻断(驱动、内核线程、中断干扰)
hackbench:内核调度压力测试
模拟大量进程 / 线程切换,施压调度器,放大实时抖动
hackbench -l 100000
配合 cyclictest 并行运行,复现高负载下最大时延。
latencytop:定位内核时延来源(根因分析)
安装
apt install latencytop
#捕获全局内核延迟阻塞点latencytop
可直观看到:
哪些内核函数关闭抢占(spinlock、驱动阻塞)
中断处理耗时过长
RCU、workqueue 延迟
ftrace:内核级精准追踪(高级调试)
用于定位最大时延根源,RT 内核排障神器
开启抢占延迟追踪
mount -t tracefs none /sys/kernel/tracingecho preemptirqsoff > /sys/kernel/tracing/trace_eventecho 10000 > /sys/kernel/tracing/buffer_size_kbecho 1 > /sys/kernel/tracing/tracing_on# 后台跑cyclictest,完成后关闭echo 0 > /sys/kernel/tracing/tracing_oncat /sys/kernel/tracing/trace > delay_log.txt
可抓到关中断 / 关抢占的完整调用栈,定位劣质驱动、内核模块。
stress-ng:制造系统负载极限测试
模拟 IO、内存、CPU、中断压力,验证极端场景实时性
# 多核CPU+内存压力,后台跑cyclicteststress-ng --cpu 4 --vm 2 --timeout 30m
三、中断实时性测试(硬件关键项)
cat /proc/interrupts# 将设备中断绑定到非实时核心,避免抢占实时任务echo f0 > /proc/irq/xx/smp_affinity
捕获长时间关中断代码,这是实时抖动头号来源。
echo irqsoff > /sys/kernel/tracing/trace_event
四、自定义用户态实时程序测试(C 代码示例)
测试高精度周期任务,统计抖动,验证 SCHED_FIFO/SCHED_DEADLINE
#include <stdio.h>#include <stdlib.h>#include <pthread.h>#include <sched.h>#include <time.h>#include <sys/mman.h>#define PERIOD_NS 1000000 // 1ms周期#define TEST_LOOP 1000000int main(){mlockall(MCL_CURRENT|MCL_FUTURE);struct sched_param sp;sp.sched_priority = 99;pthread_setschedparam(pthread_self(), SCHED_FIFO, &sp);struct timespec t_start, t_now;long long min = 1e9, avg = 0, max = 0;clock_gettime(CLOCK_MONOTONIC, &t_start);for(int i=0; i<TEST_LOOP; i++){// 等待下一个周期t_start.tv_nsec += PERIOD_NS;if(t_start.tv_nsec >= 1000000000){t_start.tv_sec++;t_start.tv_nsec -= 1000000000;}clock_nanosleep(CLOCK_MONOTONIC, TIMER_ABSTIME, &t_start, NULL);// 计算实际延迟clock_gettime(CLOCK_MONOTONIC, &t_now);long long delta = (t_now.tv_sec - t_start.tv_sec)*1000000 + (t_now.tv_nsec - t_start.tv_nsec)/1000;if(delta < min) min = delta;if(delta > max) max = delta;avg += delta;}printf("Min: %lld us | Avg: %lld us | Max: %lld us\n", min, avg/TEST_LOOP, max);return 0;}
编译:gcc rt_test.c -o rt_test -lpthread -lrt
运行:sudo ./rt_test
补充:笔记本跑 RT 前必做优化(Yoga Pro 16s)
1、锁住 CPU 性能模式
echo performance | sudo tee /sys/devices/system/cpu/cpu*/cpufreq/scaling_governor
2、关闭 swap 防止缺页抖动
sudo swapoff -a
3、关闭透明大页
echo never | sudo tee /sys/kernel/mm/transparent_hugepage/enabled