linux 编译指cpu内核,linux内核编译与配置
linux是如何組成的?
答:linux是由用戶空間和內(nèi)核空間組成的
為什么要?jiǎng)澐钟脩艨臻g和內(nèi)核空間?
答:有關(guān)CPU體系結(jié)構(gòu),各處理器可以有多種模式,而LInux這樣的劃分是考慮到系統(tǒng)的
安全性,比如X86可以有4種模式RING0~RING3? RING0特權(quán)模式給LINUX內(nèi)核空間RING3給用戶空間
linux內(nèi)核是如何組成的?
答:linux內(nèi)核由SCI(System Call Interface)系統(tǒng)調(diào)用接口、PM(Process Management)進(jìn)程管理、MM(Memory Management)內(nèi)存管理、Arch、
VFS(Virtual File Systerm)虛擬文件系統(tǒng)、NS(Network Stack)網(wǎng)絡(luò)協(xié)議棧、DD(Device Drivers) 設(shè)備驅(qū)動(dòng)
linux 內(nèi)核源代碼
linux內(nèi)核源代碼是如何組成或目錄結(jié)構(gòu)?
答:?? arc目錄??? 存放一些與CPU體系結(jié)構(gòu)相關(guān)的代碼? 其中第個(gè)CPU子目錄以分解boot,mm,kerner等子目錄
block目錄??? 部分塊設(shè)備驅(qū)動(dòng)代碼
crypto目錄??? 加密、壓縮、CRC校驗(yàn)算法
documentation??? 內(nèi)核文檔
drivers??? ??? 設(shè)備驅(qū)動(dòng)
fs??? ??? 存放各種文件系統(tǒng)的實(shí)現(xiàn)代碼
include??? ??? 內(nèi)核所需要的頭文件。與平臺(tái)無關(guān)的頭文件入在include/linux子目錄下,與平臺(tái)相關(guān)的頭文件則放在相應(yīng)的子目錄中
init??? ??? 內(nèi)核初始化代碼
ipc??? ??? 進(jìn)程間通信的實(shí)現(xiàn)代碼
kernel??? ??? Linux大多數(shù)關(guān)鍵的核心功能者是在這個(gè)目錄實(shí)現(xiàn)(程序調(diào)度,進(jìn)程控制,模塊化)
lib??? ??? 庫文件代碼
mm??? ??? 與平臺(tái)無關(guān)的內(nèi)存管理,與平臺(tái)相關(guān)的放在相應(yīng)的arch/CPU目錄??? net??? ??? 各種網(wǎng)絡(luò)協(xié)議的實(shí)現(xiàn)代碼,注意而不是驅(qū)動(dòng)
samples ??? 內(nèi)核編程的范例
scripts??? ??? 配置內(nèi)核的腳本
security??? SElinux的模塊
sound??? ??? 音頻設(shè)備的驅(qū)動(dòng)程序
usr??? ??? cpip命令實(shí)現(xiàn)程序
virt??? ??? 內(nèi)核虛擬機(jī)
內(nèi)核配置與編譯
一、清除
make clean??? 刪除編譯文件但保留配置文件
make mrproper??? 刪除所有編譯文件和配置文件
make distclean??? 刪除編譯文件、配置文件包括backup備份和patch補(bǔ)丁
二、內(nèi)核配置方式
make config??? 基于文本模式的交互式配置
make menuconfig??? 基于文本模式的菜單配置
make oldconfig??? 使用已有的配置文件(.config),但配置時(shí)會(huì)詢問新增的配置選項(xiàng)
make xconfig??? 圖形化配置
三、make menuconfig一些說明或技巧
在括號(hào)中按“y”表示編譯進(jìn)內(nèi)核,按“m”編譯為模塊,按“n”不選擇,也可以按空格鍵進(jìn)行選擇
注意:內(nèi)核編譯時(shí),編譯進(jìn)內(nèi)核的“y”,和編譯成模塊的“m”是分步編譯的
四、快速配置相應(yīng)體系結(jié)構(gòu)的內(nèi)核配置
我們可以??? 到arch/$cpu/configs目錄下copy相應(yīng)的處理器型號(hào)的配置文件到內(nèi)核源目錄下替換.config文件
五、編譯內(nèi)核
1.
————————————————————————————
make zImage?? 注:zImage只能編譯小于512k的內(nèi)核
make bzImage
同樣我們也可以編譯時(shí)獲取編譯信息,可使用
make zImage V=1
make bzImage V=1
編譯好的內(nèi)核位于??? arch/$cpu/boot/目錄下
————————————————————————————
以上是編譯內(nèi)核make menuconfig時(shí)先“m”選項(xiàng)的編譯? 接下來到編譯“y”模塊,也就是編譯模塊
2.
make modules??? 編譯內(nèi)核模塊
make modules_install??? 安裝內(nèi)核模塊 ------>這個(gè)選項(xiàng)作用是將編譯好的內(nèi)核模塊從內(nèi)核源代碼目錄copy至/lib/modules下
六、制作init ramdisk
mkinitrd initrd-$version $version
/****? mkinitrd initrd-$(可改)version $version(不可改,因?yàn)檫@version是尋找/lib/modules/下相應(yīng)的目錄來制作)? ****/
七、內(nèi)核安裝
復(fù)制內(nèi)核到相關(guān)目錄下再作grub引導(dǎo)也就可以了
1.cp arch/$cpu/boot/bzImage /boot/vmlinux-$version
2.cp $initrd /boot/
3.修改引導(dǎo)器/etc/grub.conf(lio.conf)正確引導(dǎo)即可
#incldue
#include
static int hello_init(void)
{
printk(KERN_WARNING"Hello,world!\n");
return 0;
}
static void hello_exit(void)
{
printk(KERN_INFO"Good,world!\n");
}
module_init(hello_init);
module_exit(hello_exit);
___________hello,world!范例___________________
一、必需模塊函數(shù)
1.加載函數(shù)??? module_init(hello_init);??? 通過module_init宏來指定
2.卸載函數(shù)??? module_exit(hello_exit);??? 通過module_exit宏來指定
編譯模塊多使用makefile
二、可選模塊函數(shù)
1.MODULE_LICENSE("*******"); ??? 許可證申明
2.MODULE_AUTHOR("********");??? 作者申明
3.MODELE_DESCRIPTION("***");??? 模塊描述
4.MODULE_VERSION("V1.0");??? 模塊版本
5.MODULE_ALIAS("*********");??? 模塊別名
三、模塊參數(shù)
通過宏module_param指定模塊參數(shù),模塊參數(shù)用于在加載模塊時(shí)傳遞參數(shù)模塊
module_param(neme,type,perm);
name是模塊參數(shù)名稱
type是參數(shù)類型? type常見值:boot、int、charp(字符串型)
perm是參數(shù)訪問權(quán)限 perm常見值:S_IRUGO、S_IWUSR
S_IRUGO:任何用戶都對sys/module中出現(xiàn)的參數(shù)具有讀權(quán)限
S_IWUSR:允許root用戶修改/sys/module中出現(xiàn)的參數(shù)
/*****——————范例————————*******/
int a = 3;
char *st;
module_param(a,int,S_IRUGO);
module_param(st,charp,S_IRUGO);
/*********————結(jié)束——————**********/
/**********----makefile范例----*************/
ifneq??? ($(KERNELRELFASE),)
obj-m??? :=??? hello.o??? //這里m值多用 obj-(CONFIG_**)代替
else
KDIR??? :=??? /lib/modules/$version/build
all:
make -C $(KDIR) M=$(PWD) modules
clean:
rm -f *.ko *.o *.mod.o *.mod.c *.symyers
endif
/*****這里可以擴(kuò)展多文件makefile 多個(gè)obj-m***********end***************/
/******模塊參數(shù)*****/
#include
#include
MODULE_LICENSE("GPL");
static char *name = "Junroc Jinx";
static int age = 30;
module_param(arg,int,S_IRUGO);
module_param(name,charp,S_IRUGO);
static int hello init(void)
{
printk(KERN_EMERG"Name:%s\n",name);
printk(KERN_EMERG"Age:%d\n",age);
return 0;
}
static void hello_exit(void)
{
printk(KERN_INFA"Module Exit\n");
}
moduleJ_init(hello_init);
module_exit(hello_exit);
/****************/
----------------------------------------------------------------------------
/proc/kallsyms 文檔記錄了內(nèi)核中所有導(dǎo)出的符號(hào)的名字與地址
什么是導(dǎo)出?
答:導(dǎo)出就是把模塊依賴的符號(hào)導(dǎo)進(jìn)內(nèi)核,以便供給其它模塊調(diào)用
為什么導(dǎo)出?
答:不導(dǎo)出依賴關(guān)系就解決不了,導(dǎo)入就失敗
符號(hào)導(dǎo)出使用說明:
EXPORT_SYMBOL(符號(hào)名)
EXPORT_SYMBOL_GPL(符號(hào)名)
其中EXPORT_SYMBOL_GPL只能用于包含GPL許可證的模塊
模塊版本不匹配問題的解決:
1、使用 modprobe --force-modversion??? 強(qiáng)行插入
2、確保編譯內(nèi)核模塊時(shí),所依賴的內(nèi)核代碼版本等同于當(dāng)前正在運(yùn)行的內(nèi)核?? uname -r
----------------------------------------------------------------------
printk內(nèi)核打印:
printk允許根據(jù)嚴(yán)重程度,通過附加不同的“優(yōu)先級”來對消息分類
在定義了8種記錄級別。按照優(yōu)先級遞減分別是:
KERN_EMERG??? "<0>"??? 用于緊急消息,常常崩潰前的消息
KERN_ALERT??? "<1>"??? 需要立刻行動(dòng)的消息
KERN_CRIT??? "<2>"??? 嚴(yán)重情況
KERN_ERR??? "<3>"??? 錯(cuò)誤情況
KERN_WARNING??? "<4>"??? 有問題的警告
KERN_NOTICE??? "<5>"??? 正常情況,但是仍然值得注意
KERN_INFO??? "<6>"??? 信息型消息
KERN_DEBUG??? "<7>"??? 用于調(diào)試消息
沒有指定優(yōu)先級的printk默認(rèn)使用
DEFAULT_MESSAGE_LOGLEVEL優(yōu)先級??? 它是一個(gè)在kernel/printk.c中定義的整數(shù)
控制優(yōu)先級的配置:
/proc/sys/kernel/printk(可以查看或修改)
/*******符號(hào)symbol各模塊依賴范例*****/
--------/********hello.c*********/----
#include
#include
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Junroc Jinx");
MODULE_DESCRIPTION("hello,world module! ");
MODULE_ALIAS("A simple modle test");
extern int add_integar(int a,int b);
extern int sub_integar(int a,int b);
static int __init hello_init()
{
int res = add_integar(1,2);
return 0;
}
static void __exit hello_exit()
{
int res = sub_integar(2,1);
}
module_init(hello_init);
module_exit(hello_exit);
/******hello.c****end**********/
/********start*****calculate.c******/
#include
#include
MODULE_LICENSE("GPL");
int add_integar(int a,int b)
{
return a+b;
}
int sub_integar(int a,int b)
{
return a-b;
}
static int __init sym_init()
{
return 0;
}
static void __exit sym_exit()
{
}
module_init(sym_init);
module_exit(sym_exit);
//EXPORT_SYMBOL(add_integar);
//EXPORT_SYMBOL(sub_integar);
/***********end*****calculte.c****/
總結(jié)
以上是生活随笔為你收集整理的linux 编译指cpu内核,linux内核编译与配置的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 创建 linux分区命令,Linux中创
- 下一篇: Linux怎么查询全部容器时间,linu