ubuntu打实时内核补丁教程以及安装后显卡驱动问题解决方法

在ubuntu20.04上安装成功,亲测有效

目录

ubuntu打实时内核补丁教程

安装目标系统:ubuntu20.04
电脑配置:i9,2080ti

1、下载实时内核

打开终端,输入

uname -r

查看当前linux内核版本
我的版本是5.8.xxx,查了资料,建议安装与系统自身内核相近版本的实时内核
https://www.kernel.org/pub/linux/kernel/https://www.kernel.org/pub/linux/kernel/projects/rt/去下载linux-5.9.1.tar.gz 和 patch-5.9.1-rt20.patch.gz.
注意这里下载的实时内核版本大家根据自己系统的具体情况来进行下载。

2、解压和打补丁(patch)

tar -xzvf linux-5.9.1.tar.gz
cd linux-5.9.1
gzip -cd ../patch-5.9.1-rt20.patch.gz | patch -p1 --verbose

3、安装依赖和编译安装

sudo apt-get install libncurses-dev libssl-dev
make menuconfig ##还是在linux-5.9.1文件夹下

弹出一个选择界面,选择第一个,找到“Preemption Model”,选择“Fully Preemptible Kernel (RT)”,这样我们安装的才是实时内核。其它选项都保持默认,最后会生成一个“.config”文件,生成之后就退出。
开始编译,“-j16”后面的数字表示你电脑cpu的核数,有几个就写几个,这样可以调动所有cpu资源进行编译,加快编译速度。

make -j16
sudo make modules -j16
sudo make install -j16

中途可能会遇到一个/debian/xxxx的问题,直接

sudo gedit .config

搜索debian,把“”里面的都删除,然后再进行编译(重复上述步骤)

4、修改一些文件,便于之后切换内核

到系统/etc/default路径下,修改grub文件

cd /etc/default
sudo gedit grud

打开之后,更改
GRUB_DEFAULT=0

GRUB_DEFAULT=“1 >0”
注意,这里的输入要严格按照上面的格式来,1后面的空格一定不能少。1 >0表示使用的是系统中的第一个内核(也就是我们刚刚安装好的实时内核),如果想切换其他内核,直接修改0为相应内核版本的序号即可,这个排序直接去/boot/grub/grub.cfg文件(也可以在这里面确认编译安装的实时内核“5.9.1-rt20”在里面(直接搜索相应关键字,在menuentry后面是5.9.1-rt20即可)
另外)中查找,没有明显的序号,直接按出现的顺序排布的,大家可以自己数一数,想切换的内核版本在第几个。(数menuentry后面的内核版本)
保存关闭grub文件

sudo update-grub

5、重启电脑

sudo reboot

重启后,输入

uname -r

查看当前内核版本,可以看到当前已经是5.9.1-rt20的实时内核了

实时内核版本下安装nvidia显卡驱动的问题

大家安装完实时内核后,重启时,会发现电脑显示分辨率不正确了,然后去设置里面更改也没有更高的显示分辨率,输入nvidia-smi也没有弹出显卡驱动信息,这是因为实时内核下的显卡驱动掉了。如果你安装前面的步骤切换回原来的内核版本,再重启,会发现电脑又正常了。如果直接在实时内核下,打开软件更新中心下载显卡驱动是没办法下载的,可能下载刚一完成,就给你弹出个不明的错误,导致显卡驱动安装失败。所以这里再给大家说一说怎么解决实时内核下安装显卡驱动的问题。

1、先切换回之前的内核(非实时)版本

修改grub文件

cd /etc/default
sudo gedit grud

把0改成相应内核版本的序号
我这里改为2(因为是第三个)
更新文件后,重启

sudo update-grub
reboot

2、重装之前内核(非实时)版本下的显卡驱动

这里要使用.run文件安装的方式,因为待会儿在实时内核下安装显卡驱动也需要.run文件
去nvidia官网下载适配自己电脑显卡版本的驱动
我这里下载了456.56版本的.run文件显卡驱动(适配2080ti)
先把dkms这个管理工具装上

sudo apt install dkms

禁用nouveau

sudo gedit /etc/modprobe.d/blacklist.conf

在文件中最后一行插入

blacklist nouveau
options nouveau modeset=0

保存退出
终端中输入,使设置生效并重启

sudo update-initramfs -u
sudo reboot

重启后验证

lsmod | grep nouveau

回车无任何反应,则表示成功
卸载之前的显卡驱动

sudo apt-get remove --purge nvidia*

运行xxx.run文件(显卡驱动安装包)

chmod +x xxx.run
./xxx.run

开始安装显卡驱动
弹出以第一个有关dkms的截面选择yes,其它的都选no
安装完成后,重启电脑,打开终端,输入

nvidia-smi

查看显卡驱动版本

3、切换回实时内核(按照上面的步骤)

4、在实时内核下安装显卡驱动

这里要感谢一位大佬(大佬名字忘记了,这是他为解决这个问题在GitHub上发布的脚本)写的.sh脚本,他这个脚本实现了在实时内核下安装显卡驱动。脚本如下

#!/bin/bash

BUILD_BASE=`pwd`
NV_FILE="NVIDIA-Linux-x86_64-xxx.run"  # 这里改成自己下载的.run文件名(之前安装过的)
#NV_URL="https://us.download.nvidia.cn/XFree86/Linux-x86_64/430.50/${NV_FILE}"  # 之前已经下好了显卡驱动.run文件,就不用从网上下载了,直接注释掉,而且如果要下载的话,则慢
NEED_TO_COMPILE_NV_KO=1

function clean_env() {

    [ -d ./${NV_DIR} ] && rm -rf ./${NV_DIR}
}

function check_env() {
    
    # check if in rt kernel
    uname -r | grep rt 1>/dev/null 2>&1 
    if [ $? -ne 0 ]
    then
        echo "Not in rt kernel, Please install apollo kernel and reboot machine first."
        exit 2
    fi

    # check if nv ko already in kernel
    if [ ! -f /lib/modules/`uname -r`/kernel/drivers/video/nvidia.ko ]
    then
        export NEED_TO_COMPILE_NV_KO=1
    fi
}

function prepare_nv() {

    ## download nv install file from nvidia home page 
    #if [ ! -f ./${NV_FILE} ]
    #then
    #   echo "Downloading ${NV_FILE} from nvidia website..."
    #    wget ${NV_URL} -O ${NV_FILE}
    #    if [ $? -ne 0 ]
    #    then
    #        echo "Downloading ${NV_FILE} failed, please check your network connection!"
    #        rm -rf ./${NV_FILE}
    #        exit 1
    #    fi
    #fi
    ###########上面是下载驱动的代码,我们已经提前下载好了,就不需要这段代码了,直接注释掉############

    # +x 
    chmod +x ./${NV_FILE}
    echo "Extracting nvidia install run file..."
    ./${NV_FILE} -x 1>/dev/null 2>&1
    NV_DIR="`echo ${NV_FILE} | awk -F '.run' '{print $1}'`"
    NV_VERSION="`echo ${NV_FILE} | awk -F '-' '{print $4}' | awk -F '.run' '{print $1}'`"

    export NV_DIR
    export NV_VERSION
    export NVIDIA_SOURCE="${NV_DIR}/kernel"
}

function install_lib() {
   
    NV_LIB_OUTPUT_PATH="/usr/lib/x86_64-linux-gnu/"
    NV_BIN_OUTPUT_PATH="/usr/bin/"

    [ -f ./${NV_DIR}/libnvidia-ml.so.${NV_VERSION} ] && /bin/cp -f ./${NV_DIR}/libnvidia-ml.so.${NV_VERSION} ${NV_LIB_OUTPUT_PATH}
    [ -f ./${NV_DIR}/libnvidia-fatbinaryloader.so.${NV_VERSION} ] && /bin/cp -f ./${NV_DIR}/libnvidia-fatbinaryloader.so.${NV_VERSION} ${NV_LIB_OUTPUT_PATH}
    [ -f ./${NV_DIR}/libnvidia-ptxjitcompiler.so.${NV_VERSION} ] && /bin/cp -f ./${NV_DIR}/libnvidia-ptxjitcompiler.so.${NV_VERSION} ${NV_LIB_OUTPUT_PATH}
    [ -f ./${NV_DIR}/libcuda.so.${NV_VERSION} ] && /bin/cp -f ./${NV_DIR}/libcuda.so.${NV_VERSION} ${NV_LIB_OUTPUT_PATH}
    [ -f ./${NV_DIR}/nvidia-modprobe ] && /bin/cp -f ./${NV_DIR}/nvidia-modprobe ${NV_BIN_OUTPUT_PATH}
    [ -f ./${NV_DIR}/nvidia-smi ] && /bin/cp -f ./${NV_DIR}/nvidia-smi ${NV_BIN_OUTPUT_PATH}

    chmod +x /usr/bin/nvidia*
    chmod +s /usr/bin/nvidia-modprobe

    # link for nvidia
    /bin/rm -rf /usr/lib/x86_64-linux-gnu/libnvidia-ml.so.1  /usr/lib/x86_64-linux-gnu/libnvidia-ml.so
    /bin/ln -s /usr/lib/x86_64-linux-gnu/libnvidia-ml.so.${NV_VERSION} /usr/lib/x86_64-linux-gnu/libnvidia-ml.so.1
    /bin/ln -s /usr/lib/x86_64-linux-gnu/libnvidia-ml.so.1 /usr/lib/x86_64-linux-gnu/libnvidia-ml.so

    /bin/rm -rf /usr/lib/x86_64-linux-gnu/libcuda.so  /usr/lib/x86_64-linux-gnu/libcuda.so.1
    /bin/ln -s /usr/lib/x86_64-linux-gnu/libcuda.so.${NV_VERSION} /usr/lib/x86_64-linux-gnu/libcuda.so.1
    /bin/ln -s /usr/lib/x86_64-linux-gnu/libcuda.so.1 /usr/lib/x86_64-linux-gnu/libcuda.so

    # take effect
    /sbin/ldconfig 1>/dev/null 2>&1
}

function build_nv() {

    if [ ${NEED_TO_COMPILE_NV_KO} == 0 ]
    then
        return
    fi

    NVIDIA_MOD_REL_PATH='kernel/drivers/video'
    NVIDIA_OUTPUT_PATH="/lib/modules/`uname -r`/${NVIDIA_MOD_REL_PATH}"
    CPUNUM=`cat /proc/cpuinfo | grep processor | wc | awk -F " " '{print $1}'`

    export IGNORE_PREEMPT_RT_PRESENCE=true
    cd ${NVIDIA_SOURCE} && make -j ${CPUNUM} module
    cd ${BUILD_BASE}

    unset IGNORE_PREEMPT_RT_PRESENCE

    mkdir -p ${NVIDIA_OUTPUT_PATH}

    [ -f ${NVIDIA_SOURCE}/nvidia.ko ] && cp ${NVIDIA_SOURCE}/nvidia.ko ${NVIDIA_OUTPUT_PATH}
    [ -f ${NVIDIA_SOURCE}/nvidia-modeset.ko ] && cp ${NVIDIA_SOURCE}/nvidia-modeset.ko ${NVIDIA_OUTPUT_PATH}
    [ -f ${NVIDIA_SOURCE}/nvidia-drm.ko ] && cp ${NVIDIA_SOURCE}/nvidia-drm.ko ${NVIDIA_OUTPUT_PATH}
    [ -f ${NVIDIA_SOURCE}/nvidia-uvm.ko ] && cp ${NVIDIA_SOURCE}/nvidia-uvm.ko ${NVIDIA_OUTPUT_PATH}

    depmod -a
}

# check environment
check_env

# prepare for nvidia
prepare_nv

# build nvidia.ko
build_nv

# install user lib
install_lib

# clean environment
clean_env

echo "Done to install nvidia kernel driver and user libraries."

打开终端,输入

sudo gedit install_nvidia.sh

打开之后,复制上面的脚本代码粘贴进去。(注意,一定要在ubuntu系统下操作,如果是在Windows系统编辑后再拷过去的话,脚本需要“sed -i ‘s/\r$//’ yourfile”才能运行)
对代码中的内容按照自己的安装要求进行修改,修改部分在上面注明了。
修改完毕后,执行

chmod +x ./install_nvidia.sh
sudo ./install_nvidia.sh

等待安装,完成后重启

电脑分辨率又正常了,说明在实时内核下已经装上了显卡驱动
输入

nvidia-smi

出现显卡驱动信息,说明显卡驱动安装正常!!!

上一篇:nvidia-smi指令报错:Failed to initialize NVML: Driver解决


下一篇:解决Ubuntu重启之后NVIDIA驱动屡次失效:报错NVIDIA-SMI has failed because it couldn't communicate with the NVIDI