
内核笔记
内核相关的文章。
程序猿Ricky的日常干货
擅长扫地、打杂、开车。。
展开
-
如何理解进程结构体中的mm和active_mm?
结构体task_struct里面有一个mm成员,和一个active_mm成员。其中mm成员主要是用来区分是用户进程还是内核进程的,对于内核进程来说,mm成员是为NULL空的。进程地址空间的创建当一个进程被创建时会复制对应的mm成员的值为父进程的值,这样子进程就复用了父进程的地址空间。地址空间的切换在进行地址空间切换时,内核是使用active_mm来进行切换的:1 对于一个mm不为NULL的用户进程来说,active_mm = mm2 对于一个mm为NULL的内核线程来说,active_mm原创 2021-05-17 17:48:48 · 1024 阅读 · 0 评论 -
linux进程切换与intel的tss任务切换
本文作者主要想聊聊linux进程切换是如何与intel的tss配合工作的。最近工作中遇到一些问题,引发了我的一些思考,我在看到进程切换做寄存器上下文保存和切换时,涉及到了tss的操作,而我是一头雾水,进而引发了强烈的好奇心,想要探究一下到底是怎么回事。经过网络检索以及内核代码的学习,总算有一些眉目了。首先需要搞懂什么是tss? 它全称叫做task status segment。简单来讲,可以把它理解为是一块内存段,用来保存任务的寄存器信息的,主要用于任务切换时做寄存器的上下文切换,这块内存具有固定的格原创 2020-12-03 00:47:53 · 1653 阅读 · 0 评论 -
从kprobe注销场景来探讨一下synchronize_sched的使用
首先抛出我的问题:当我在编译一个kprobe内核插桩模块时,我是这样实现的,先动态申请一块内存,用于存放我的kprobe结构体,然后执行kprobe的注册,完成一系列的内核数据收集之后,执行kprobe注销操作,最后释放内存,那么大家觉得我这个设计有问题吗?对于初学者可能觉得:没有什么问题呀?kprobe有注册和有注销,内存有申请有释放,怎么出问题的,实际上正确答案就是没有问题。。。哈哈,是不是感觉被我忽悠了一下。下面我来说说我当时的顾虑,由于我是动态申请的内存,kprobe机制是这样的,注册了对应k原创 2020-09-02 22:15:37 · 622 阅读 · 0 评论 -
内核debugfs使用简介
常规接口创建一个debugfs目录:struct dentry *debugfs_create_dir(const char *name, struct dentry *parent);创建一个debugfs文件:struct dentry *debugfs_create_file(const char *name, umode_t mode, s...原创 2020-01-17 18:05:56 · 1027 阅读 · 0 评论 -
内核sysfs的使用简介
sysfs在设备文件创建中的作用内核注册设备驱动时采用的是cdev_add接口,但是对于应用层来说,想要访问设备文件,必须先要创建一个对应设备号的设备文件才可以,比如:mknod上面是一种古老的方式,所有的设备驱动都要手动创建设备文件去访问,当前最流行的方法是利用上层的udev/mdev工具来帮助我们实现这个功能。mdev命令常用在嵌入式系统中,通过编译busybox之后即可拥有该工具。使...原创 2020-01-17 15:02:59 · 1305 阅读 · 0 评论 -
内核镜像vmlinux和Image的区别
arm32平台编译一个压缩后的内核镜像:make zImage最后链接过程的log如下所示: LD vmlinux SYSMAP System.map SYSMAP .tmp_System.map OBJCOPY arch/arm/boot/Image Kernel: arch/arm/boot/Image is ready AS arch/...原创 2020-01-04 13:50:22 · 4689 阅读 · 0 评论 -
内核 seq_file 操作函数
接口APIseq_file 系列函数是为了方便内核导出信息到 sysfs、debugfs、procfs 实现的。以往的内核也存在各种形式的实现,但是都无法避免个别实现会产生一些漏洞,这一套函数实现可以让内核导出信息更加简单和统一稳定,维护起来更加方便。它包含了如下一些接口:int seq_open(struct file *file, const struct seq_operations ...原创 2019-12-17 19:46:38 · 9676 阅读 · 0 评论 -
内核 procfs 使用笔记
procfs 文件创建首先从一个参考实例开始:static int test_proc_show(struct seq_file *m, void *v){ seq_printf(m, "test_proc_show()\n"); return 0;}static int test_proc_open(struct inode *inode, struct file *...原创 2019-12-16 20:11:26 · 774 阅读 · 0 评论 -
Linux电源管理--PM QoS
什么是PM QoSQoS全称叫做Quality of Service,直译过来就是“服务质量”的含义。既然它是服务质量,自然需要有两个主体对象:一个服务方(servicer),一个请求服务方(requester)。PM QoS framework针对两种对象分别提供了电源管理的基础框架和接口。 那么在电源管理的范畴内要如何理解服务质量呢?实际上在这里,服务的定义是请求方对于某一个性能的需求,比如...原创 2019-11-29 11:33:33 · 1863 阅读 · 0 评论 -
内核Makefile中常见变量解释
$(Q)主Makefile:ifeq ("$(origin V)", "command line") KBUILD_VERBOSE = $(V)endififndef KBUILD_VERBOSE KBUILD_VERBOSE = 0endififeq ($(KBUILD_VERBOSE),1) quiet = Q =else quiet...原创 2018-11-06 18:07:18 · 3410 阅读 · 0 评论 -
Trace32 simulator调试以及简单实用命令介绍
Trace32 Simulator debug熟悉高通平台的童鞋可能会比较熟悉,高通有ramdump功能,当系统crash后通过warm reset重启来抓取ram中的数据,然后利用Trace32进行故障现场的查看来排查问题。这实际上用到的就是trace32的simulator功能,也就是仿真器功能,我们只需要获取到设备的内存快照来进行指令集的仿真,以此查看故障现场,而不用真实的连接目标板来实时...原创 2018-12-26 20:52:31 · 39959 阅读 · 3 评论 -
Trace32-ICD和Trace32-ICE的区别
ICD:In Circuit Debugger,ICE:In Circuit Emulator,中文分别为“在线调试器”和“在线仿真器”Trace32是Lauterbach公司开发的一套工具,包括软硬件一起搭配使用,包括了Trace32-ICD和 Trace32-ICE。早期我们只有ICE能够用于CPU的调试,它主要实现方式就是使用一套硬件替代原本想要调试的CPU,以此达到仿真目的,但是需要我们...原创 2018-12-25 18:21:41 · 2566 阅读 · 0 评论 -
bootloader启动参数传递(一)
arm平台 /* * Kernel startup entry point. * --------------------------- * * This is normally called from the decompressor code. The requirements * are: MMU = off, D-cache = off, I-cache = don...原创 2019-01-21 14:20:00 · 1660 阅读 · 0 评论 -
什么是FIT uImage?
全称是flattened image tree uImage,为了更好的支持单个固件的通用性,类似于kernel device tree机制,uboot也需要对这种uImage固件进行支持。FIT uImage中加入多个dtb文件,和ramdisak文件,当然如果需要的话,同样可以支持多个kernel文件。这样的目的就是能够使同一个uImage就能够在uboot中选择特定的kernel/dtb和...原创 2019-01-22 14:30:43 · 4394 阅读 · 0 评论 -
UEFI开发与调试---ImageHandle和ControllerHandle
1.ImageHandle每个uefi module都是一个image,而每个image对应都有一个ImageHandle,其实ImageHandle的类型就是EFI_HANDLEtypedef VOID *EFI_HANDLE;因此实际上每个ImageHandle是一个void*指针,那么也就是说任何结构体都可以传给他,其实通过代码可知在ue...原创 2018-08-03 17:25:40 · 3880 阅读 · 0 评论 -
系统调用SYSCALL_DEFINE详解(Linux-4.x)
SYSCALL_DEFINE定义 #define SYSCALL_DEFINE0(sname) \ SYSCALL_METADATA(_##sname, 0); \ asmlinkage long sys_##sname(void) #define SYSCALL_DEFINE1(name, ...) SYSCA...原创 2019-06-06 17:14:21 · 5485 阅读 · 0 评论 -
文件系统--open系统调用详解
arm64平台关于32位系统调用的定义:#define __NR_open 5__SYSCALL(__NR_open, compat_sys_open)#undef __SYSCALL#define __SYSCALL(nr, sym) [nr] = sym,/* * The sys_call_table array must be 4K aligned to be acces...原创 2019-06-19 17:23:15 · 4203 阅读 · 0 评论 -
VFS虚拟文件系统
基本概念超级块对象磁盘文件系统会包含有一个超级块,该块用于保存磁盘文件系统的一些属性和信息,内核设计了超级块对象用于描述超级块信息,超级块对象是存在于内存中的,超级块存在于磁盘上,因此需要定期同步。文件索引节点对象磁盘文件系统是按照文件节点inode来管理文件的,内核中使用文件节点对象来管理文件节点inode。文件节点对象存在于内存中,而其中的一些数据需要和磁盘中保持同步。目录项对象磁...原创 2019-06-17 20:04:08 · 1407 阅读 · 0 评论 -
Linux 内核console设备实现详解
本文基于Linux-4.141.earlyconearly console,顾名思义,他表示的就是早期的console设备,主要用于在系统启动阶段的内核打印的输出,由于linux内核实际设备驱动模型还没有加载完成,所以早期的启动信息需要一个特殊的console用于输出log。在系统初始化时通过cmdline参数来解析,代码如下:./init/main.c:static int __i...原创 2019-07-11 15:32:15 · 8102 阅读 · 3 评论 -
Linux块设备驱动开发简介
本文基于Linux-4.14文件系统框架Linux内核的文件系统框架图如下所示:gendisk对象Linux中用一个gendisk对象结构体表示一个磁盘分区,这个结构体对象中会包含该分区对应的设备文件的主设备号,次设备号,以及对应的gendisk->fops操作函数,这个块设备操作方法结构体如下所示:struct block_device_operations { int...原创 2019-07-19 17:51:07 · 1420 阅读 · 0 评论 -
Linux内核中使用的数据结构和算法
Radix Tree(基树)在页缓存管理中的使用:页缓存管理中会使用到基树,address_space结构体中包含一个radix tree基树成员,因为每次内核在进行I/O操作前都会检索页高速缓存,也就是address_space结构体,为了提高检索效率,采用基树来管理和检索页高速缓存,会极大提高效率。在2.6以前的内核版本中,页缓存并不是通过基树来检索,而是通过维护一个全局散列表进行检索,...原创 2019-07-26 17:32:06 · 626 阅读 · 0 评论 -
采用usb线刷linux固件的原理
通过其他文章,我已经提到过,一款SOC都是自带BROM的,上电后都首先运行BROM中的代码,那么线刷固件和BROM有什么关系呢?我们接下来来研究下。对于BROM它的作用有两个,一个是用来正常启动固件,另一个就是刷机了。一般BROM中的固化程序会检测当前SOC的状态,到底是刷机状态呢,还是正常启动的状态,它一般是通过检测SOC上的寄存器来判断,并且SOC会引出跟这个寄存器相关的引脚来供硬件工程师添加按原创 2016-05-27 15:08:49 · 1986 阅读 · 0 评论 -
ubuntu下trace32工具安装
mount /mnt/cdrom (if not automatically mounted)mkdir /opt/t32 (or similar)cp -r /mnt/cdrom/files/* /opt/t32/cp /opt/t32/demo/practice/t32.cmm /opt/t32/cp /opt/t32...原创 2018-11-06 17:54:41 · 4132 阅读 · 2 评论 -
内核编译过程中的常用环境变量
##$(Q)主Makefile:ifeq ("$(origin V)", "command line") KBUILD_VERBOSE = $(V)endififndef KBUILD_VERBOSE KBUILD_VERBOSE = 0endififeq ($(KBUILD_VERBOSE),1)原创 2018-09-20 10:24:06 · 1079 阅读 · 0 评论 -
Dynamic DMA mapping Guide
转自蜗窝科技:http://www.wowotech.net 一、前言这是一篇指导驱动工程师如何使用DMA API的文档,为了方便理解,文档中给出了伪代码的例程。另外一篇文档dma-api.txt给出了相关API的简明描述,有兴趣也可以看看那一篇,这两份文档在DMA API的描述方面是一致的。二、从CPU角度看到的地址和从DMA控制器看到的地址有什么不同?在DMA API中涉及好几...转载 2018-04-19 16:58:12 · 758 阅读 · 0 评论 -
wait_queue_head_t和wait_queue_t
本文转自 reille博客: http://velep.com/archives/815.html等待队列在linux内核中有着举足轻重的作用,很多linux驱动都或多或少涉及到了等待队列。因此,对于linux内核及驱动开发者来说,掌握等待队列是必须课之一。 Linux内核的等待队列是以双循环链表为基础数据结构,与进程调度机制紧密结合,能够用于实现核心的异步事件通知机制。它有两种数据结构:等待队列头转载 2016-07-05 18:46:37 · 3025 阅读 · 0 评论 -
devmem调试内核驱动
在Linux开发中着实用到的调试工具并不是很多。devmem的方式是提供给驱动开发人员,在应用层能够侦测内存地址中的数据变化,以此来检测驱动中对内存或者相关配置的正确性验证。 devmem2使用方法: devmem2 { address } [ type [ data ] ] address : 物理地址 type :要访问的数据类型 :转载 2016-07-25 11:17:36 · 1650 阅读 · 0 评论 -
The new way of ioctl()----转自LWN.net
The new way of ioctl()[Posted January 18, 2005 by corbet] The ioctl() system call has long been out of favor among the kernel developers, who see it as a completely uncontrolled entry point into the ke翻译 2016-07-02 12:32:18 · 512 阅读 · 0 评论 -
sysfs/procfs/debugfs简介
Linux内核提供了三种内存文件系统,分别是sysfs、debugfs、procfs,驱动工程师可以通过任意的一种文件系统向用户空间传递信息。Sysfs的挂载点为/sysDebugfs的挂载点为/sys/kernel/debugProcfs的挂载点为/proc这三种形式的文件系统都是内存文件系统,他们中的信息只存在于内存中,下电后即消失。他们的出现旨在提供一种与用户空间交互信息的方式。这三种类原创 2016-07-01 14:49:24 · 2913 阅读 · 0 评论 -
u-boot SPL的理解
uboot分为uboot-spl和uboot两个组成部分。SPL是Secondary Program Loader的简称,第二阶段程序加载器,这里所谓的第二阶段是相对于SOC中的BROM来说的,之前的文章已经有所介绍,SOC启动最先执行的是BROM中的固化程序。BROM会通过检测启动方式来加载第二阶段bootloader。uboot已经是一个bootloader了,那么为什么还多一个uboot sp原创 2016-06-12 14:49:31 · 27047 阅读 · 12 评论 -
内核中的宏定义__init,__initdata,__exitdata
在linux内核中,我们经常会使用到一些宏定义,比如__init,__initdata,__exitdata等等。那么这些宏定义到底什么意思呢?接下来我们就来看一下。kernel/include/linux/init.h: 我们来选择一些常用的宏定义,如下所示:/* These are for everybody (although not all archs will actually d原创 2016-05-31 15:15:32 · 7340 阅读 · 0 评论 -
在内核kbuild中加入arch平台配置项
Kbuild编译内核,需要两中类型文件的支持Makefile和Kconfig。Makefile只是在编译的时候使用,但是内核还需要支持配置功能,所以还需要一个Kconfig用来在make menuconfig的时候进行显示。 不管是新写的驱动代码,还是新添加的平台代码,都需要编写相应的Kconfig和Makefile文件来加入的kbuild中进行编译。要想知道怎么为新的版型添加Kconfig和Ma原创 2016-06-01 17:21:01 · 1294 阅读 · 0 评论 -
arm裸机程序启动流程
Linux系统的引导: 一个SOC拿过来,它是有内部BROM和SRAM的,这个BROM中会固化芯片厂商的最初引导代码,我们叫它RBL(ROM boot loader),它是SOC上电后开始运行的地方,它会判断是哪种启动方式,如果是nand启动,就会从nand的起始地址处读取UBL(user boot loader)并且复制到ARM的内存里面,也就是上面说的片内SRAM,UBL运行在ARM的内存里,原创 2016-05-27 12:25:59 · 5394 阅读 · 0 评论 -
kernel启动过程中的调试打印
内核启动过程中涉及到多个地方,启动过程的代码由汇编代码和C代码组成。其中的打印函数也有多个。 1. 汇编阶段 打印函数包括如下几种: printascii printch printhex8 printhex4 printhex2这些函数定义在kernel/arch/arm/kernel/debug.S中,需要在make menuconfig中使能Kernel low-level原创 2016-05-26 14:59:01 · 4211 阅读 · 0 评论 -
全志方案卡启动固件制作原理
全志SOC的方案,他们的启动卡分区表采用的是MBR分区表。我们通过如下的制作过程可以看出一二。从sunxi论坛上( http://linux-sunxi.org/Bootable_SD_card )来看全志方案的卡启动固件制作过程。首先看一下卡的存储分布图:start size usage 0 8KB Unused, a原创 2016-07-27 11:56:59 · 7487 阅读 · 0 评论 -
ramfs,rootfs,initramfs,initrd
Ramfs是linux中的一个内存文件系统,它的大小是根据当前系统的内存大小动态变化的。也就是说除非系统内存使用完了,不然我们都是可以往ramfs中写入数据的。ramfs只是一个镜像文件,作为一个镜像文件,我们肯定没有办法直接读取其中的内容,那么怎么办呢?在linux中有一种loop设备可以用来读取镜像文件,通过losetup来挂载ramfs当做一个loop设备,然后对其进行挂载,我们就可以进入这个原创 2016-07-27 20:05:27 · 2518 阅读 · 0 评论 -
ARM64内核系统调用添加方法(基于kernel-4.9)
既上一篇介绍了ARM64内核系统调用详解之后,本篇文章来介绍如何添加自己的系统调用到内核中。根据上一篇我们知道如下关键的几点: (1)ARM64的系统调用分为32-bit模式和64-bit模式。 (2)32-bit模式的系统调用syscall定义在头文件arch/arm64/include/asm/unistd32.h (3)64-bit模式的系统调用syscall...原创 2018-04-13 15:02:39 · 4726 阅读 · 1 评论 -
ARM64内核系统调用详解(基于kernel-4.9)
本文以ARM64为例,介绍如何添加系统调用,首先来介绍一些代码执行流程:首先来看异常向量表的配置,内核在arch/arm64/kernel/entry.S汇编代码中设置了异常向量表。/* * Exception vectors. */ .pushsection ".entry.text", "ax" .align 11ENTRY(vectors) ker...原创 2018-04-12 19:49:27 · 11116 阅读 · 0 评论 -
结合early_param/__setup/__setup_param来学习cmdline的解析(基于kernel-4.9)
early_param的定义: #define early_param(str, fn) \ __setup_param(str, fn, fn, 1)__setup的定义如下: #define __setup(str, fn) \ __setup_param(str, ...原创 2018-04-17 20:02:30 · 2113 阅读 · 0 评论 -
由_OF_DECLARE引发对内核SECTION段解析的思考(基于kernel-4.9)
这个宏定义是定义在of.h中的,主要目的就是为了方便解析dts文件的。#ifdef CONFIG_OF#define _OF_DECLARE(table, name, compat, fn, fn_type) \ static const struct of_device_id __of_table_##name \ __used _...原创 2018-04-17 15:08:36 · 2079 阅读 · 0 评论