linux----笔记1---内核

Linux系统大致可分为三层:
靠近硬件的底层是内核,即Linux操作系统常驻内存部分。
中间层是shell层,即操作系统的系统程序部分。
最高层是应用层,即用户程序部分 

内核是Linux操作系统的主要部分,实现进程管理、内存管理、文件系统、设备驱动和网络系统等功能。

Linux操作系统的心脏-内核

区分用户态和内核态目的在于安全考虑:

1.禁止用户程序和底层硬件直接打交道

最简单的例子,如果用户程序往硬件控制寄存器写入不恰当的值,可能导致硬件无法正常工作
2.禁止用户程序访问任意的物理内存
否则可能会破坏其他程序的正常执行,如果对内核所在的地址空间写入数据的话,会导致系统崩溃

用户程序如何同设备打交道?
例如,用户需通过网卡发送数据

1.硬件被linux 内核隔离,只能通过内核实现。
2.不可能直接调用操作系统的函数:不可行,也不安全。
Linux提供的解决方法:系统调用

系统调用的意义:

操作系统为用户态进程与硬件设备进行交互提供了一组接口——系统调用

1.把用户从底层的硬件编程中解放出来
2.极大的提高了系统的安全性
3.使用户程序具有可移植性

内核的核心-进程

Fork()——创建新进程 ,是父进程的一个克隆 

父-子-孙共存的系统必然是一个并发的系统

2  进 程 管 理

1.进程及其状态

简单说来,进程就是程序的一次执行过程

进程至少要有三种基本状态:
运行态、就绪态和封锁态(或等待态)

进程的状态可依据一定的条件和原因而变化

在Linux系统中,进程的模式划分为用户模式和内核模式;

按照进程的功能和运行的程序来分,进程划分为两大类:
   系统进程、用户进程 


用户进程可以在用户模式和内核 模式下运行

系统进程只运行在内核模式

若当前运行的是用户程序、应用程序或者内核之外的系统程序,则在用户模式下运行。
在用户程序执行过程中,如果使用了系统调用,或者发生了中断,就要运行操作系统程序,进程模式变为内核模式。

2.Linux线程

线程和进程是紧密相关的概念

一般来说,Linux系统中的进程应具有:
一段可执行的程序、
专用的系统堆栈空间、
私有的“进程控制块”、
独立的存储空间

而Linux系统中,线程只具有前3个组成部分,
缺少自己的存储空间

进程的结构:
Linux系统中的每个进程都有一个名为task_struct的数据结构,它相当于“进程控制块”;
在进程被创建时,系统从内存中分配一个task_struct的数据结构。
包含下列几方面的信息:
   
进程状态
   
调度信息 
  
标志符
    
内部进程通讯
   
链接信息
    
时间和计时器
   
文件系统
    
虚拟内存
    
处理器信息

进程系统堆栈

每个进程都有一个系统堆栈,用来保存中断现场信息,以及进程进入内核模式后的返回现场信息;

系统堆栈和task_struct数据结构之间存在紧密联系,二者物理存储空间也连在一起 

系统堆栈的大小静态确定

对进程的操作:
1.进程的创建
各个进程构成了树形的进程族系
内核在完成了基本的初始化以后,就有了系统的第一个进程

所有其他的进程和内核线程都由这个原始进程或其子孙进程所创建。

2.进程的等待

父进程创建子进程,往往是让子进程替自己完成某项工作,因此,创建之后,父进程通常需要等待子进程运行结束;

父进程可用系统调用wait( )等待它的子进程终止;

3.进程的终止

进程可使用系统调用exit( )终止自己;
其实现算法如下:

 (1)撤消所有的信号量。

(2)释放其所有的资源,包括存储空间、已打开的文件、工作目录、信号处理表等。

(3)置进程状态为“终止态”(TASK_ZOMBIE)。

(4)向它的父进程发送子进程终止的信号。

(5)执行进程调度。


4.进程调度

进程调度-系统有条不紊的使者
调度算法

调度时机

进程切换

任何程序要占用CPU,真正处于执行状态,就必须经由进程调度
进程调度机制要兼顾以下三种不同进程的需要
1.交互进程:需要经常响应用户操作,着重于系统的响应速度,使得共有一个系统的各个用户,都感到自己在独占系统,典型的交互程序有shell,文本编辑器;

2.批处理进程:也称作“后台作业”,在后台运行,对响应速度无要求,只考虑“平均速度”,如:编译程序、科学计算等;

3.实时进程:对时间有很高要求,不仅考虑平均速度,还对完成任务的时间限制有要求。


1.调度方式

Linux内核的调度方式,基本上采用“抢占式优先级”,

 当进程在用户模式下运行时,在一定条件下(如:时间片用完),内核调度其他进程进入运行;

在选择其他进程时以优先级为基础

1.系统中的每个进程都有个优先权,反映了该进程可以获得CPU使用权的资格;

2.从进程就绪队列中选择一个优先权最高的进程,为其分配一个CPU时间片;

3.运行过程中,当前进程的优先级随时间递减,从而经过一段时间后,以前优先级较低的进程就相对“提升”了优先级,有机会运行;

4.当所有进程优先级都变为0时,就重新计算一次优先级。

调度策略——三种不同的调度策略

SCHED_FIFO
适合于短实时进程, 对时间性要求比较强,每次运行所需时间较短
SCHED_RR
适合于运行时间较长的实时进程,也叫“时间片轮转法” 。
     
当时间片用完时,该进程被送回相同优先级队列的末尾,
因此,进程从创建到完成需要经过多次循环调用;
SCHED_OTHER
 适合于交互式的分时进程,这类进程的优先权取决于两个因素:
1、进程剩余时间配额:若已经用完配给的时间,则优先权为0
       
2、进程的优先数:沿袭UNIX的方法

3.调度的时机
当前进程使用系统调用,使自己进入睡眠状态,主动让出一段时间的CPU使用权。

进程终止,永久地放弃对CPU的使用。

当唤醒一个睡眠进程时,发现被唤醒的进程比当前进程更有资格运行。

一个进程通过执行系统调用,来改变调度策略或者降低自身的优先权,从而引起立即调度。

4.调度算法
调度算法比较简单,以便减少频繁调度时的系统开销。
首先查找所有就绪队列中的进程,选出优先级最高、且在内存的一个进程;

如果队列中有实时进程,那么将优先运行;

如果需要运行的进程不是当前进程,那么当前进程就被挂起,并且保存它的现场,

然后为选中的进程恢复其运行现场;



shell基本工作原理

Linux系统提供给用户的最重要的系统程序是shell命令,
它不属于内核部分,基本功能是解释并执行用户输入的各种命令,实现用户与Linux内核的接口。
系统初次启动后,系统为每个终端用户建立一个进程,以执行shell解释程序。


文 件 系 统

Linux系统的一个重要特征,就是支持多种不同的文件系统,
如:ext, FAT, ext2, ext3, MINIX, MS DOS, SYSV等。


目前,Linux主要使用的文件系统是ext3

ext3是ext2的升级版本,其主要优点是:
  在ext2的基础上加入了记录数据的日志功能

1  ext2文件系统
与其他文件系统一样,文件信息都保存在数据块中,
所有数据块的大小都是一样的

介质上的第一个数据块,只有根文件系统才有引导程序

块组的构造

包含超级块、组描述结构、块位图、索引节点位图、索引节点表和数据块。
1)超级块(Superblock)
超级块中包含有文件系统本身的大小和形式的基本信息
例如:
块组号码 、数据块大小 、每组数据块的个数、空闲块 、空闲索引节点 、第一个索引节点 

2)块组描述结构(Block Group Descriptor) 

每个数据块组都有一个描述它的数据结构,即块组描述结构。

3)索引节点(Inode)
每个文件都有惟一一个索引节点,起着文件控制块的作用
利用这种数据结构可对文件进行控制和管理。

索引节点有两种形式:盘索引节点、内存索引节点


4)多重索引结构

如果文件索引表很大,则把索引表整个放在内存中是不合适的,在使用过程中很可能需要扩充空间;


此外,单一索引表已经无法满足灵活性和节省内存的要求;

为此,提出多重索引结构,采用间接索引的方式,进行几级寻址,最末尾的数据块中存储文件具体内容;

文件系统在查找文件时,根据路径名和文件名,搜索对应的索引节点,找到该文件的数据块;

ext2中的目录项

当创建一个文件时,就构成一个目录项,并添加到相应的目录文件中

一个目录文件可以包含很多目录项,每个目录项包含的信息有:
索引节点号

目录项长度

名字长度

文件类型
文件名字

例如:要读取文件/home/meng/m1.c

1.文件系统首先按照超级块中根目录的索引节点,
找到根目录的数据块,从中找到表示home文件的目录项,得到相应索引节点的号码;

2.接着在节点中找到存放home数据块的地址,从中找到meng对应的目录项,
得到相应的索引节点号码;

3.再由meng目录文件中获取m1.c文件的索引节点号码,通过这个节点就可以访问m1.c文件。


Linux系统中每个进程控制块都有两个数据结构,用来描述进程与文件相关信息。


files_struct保存该进程打开文件的有关信息。最多打开256个文件


每个块组中包含一个块位示图,和一个索引节点位示图


位示图管理块组的数据块,具体方法是:

利用一串二进位的值来反映该块组中数据块的分配情况
也称作位向量(Bit  Vector)法。
0表示空闲,1表示已分配





2  虚拟文件系统

Linux系统可以支持多种文件系统,为此,必须使用一种统一的接口,
这就是虚拟文件系统VFS(Virtual File System).


VFS是一个软件层,是用户应用程序与具体文件系统实现之间的抽象层:

对用户界面:
 一组标准的、抽象的文件操作,以系统调用提供
如read()、write()、open()等

对具体文件系统界面
主体是file_operations结构,全是函数指针,提供函数跳转表。


VFS在一个简单文件复制操作中的作用:
假设用户输入shell命令:$ cp   /floppy/TEST   /tmp/test 
在cp命令中,通过VFS提供的系统调用接口进行文件操作。

inf=open("/floppy/TEST",O_RDONLY,0);
outf=open("/tmp/test",O_WRONLY|O_CREAT|O_TRUNC,0600);
do{
  i=read(inf,buf,4096);
  write(outf,buf,i);
}while(i);
close(outf);
close(inf);

VFS支持的文件系统类型

基于磁盘的文件系统:
 管理在本地磁盘分区中可用的存储空间。

网络文件系统:
用于访问属于其他网络计算机的文件系统所包含的文件

特殊文件系统

文件系统的安装与拆卸:

在系统初启时,往往只有一个文件系统安装上,即:根文件系统,主要包括
保证系统正常运行的操作系统代码文件,以及语言编译程序、命令解释程序、命令处理程序、以及用户文件;

根文件系统一旦安装上,则在整个系统运行过程中是不能卸载的;


其他的文件系统(例如,由软盘构成的文件系统),可以根据需要(如从硬盘向软盘复制文件),作为子系统动态地安装到主系统


VFS有下列主要对象类型:

超级块对象(superblock )
存放文件系统相关信息:例如文件系统控制块


索引节点对象(inode )
存放具体文件的一般信息:文件控制块/inode


目录项对象(dentry )
存放目录项与文件的链接信息


文件对象(file )
存放已打开的文件和进程之间交互的信息


VFS索引节点缓存和目录缓存

为了加快对系统中所有已经安装文件系统的存取,VFS提供了索引节点缓存——把当前使用的索引节点保存在高速缓存中。

为了能够很快地从中找到所需的VFS索引节点,采用散列(hash)方法

数据块缓冲区

Linux系统采用多重缓冲技术,来平滑和加快文件信息从内存到磁盘的传输;

一个缓冲区由两部分组成:存放数据的缓冲区和一个缓冲控制块; 

所有处于“空闲”状态的buffer_head 都链入自由链中,它只有一条。

具有相同散列值的缓冲区组成一条散列队列.

内 存 管 理

Linux系统采用了虚拟内存管理机制,就是交换和请求分页存储管理技术:

地址映射机制

请页机制

内存分配和回收机制

 交换机制

缓存和刷新机制




物理内存有限,是一种稀缺资源

32位系统中,每个进程独立的占有4G虚拟空间

虚拟内存优势:

用户程序开发方便

保护内核不受恶意或者无意的破坏


隔离各个用户进程

物理内存获取过程:

用户程序请求物理内存
内核分配物理页面
内核填写对应页表项 
用户程序获得物理内存

内存管理的核心内容是

物理内存管理 和 虚拟空间管理

1  请求分页机制
分页的概念
逻辑空间分页:进程的逻辑地址空间划分为大小相等的页面
内存空间分页:内存也划分成相同大小的存储块;
逻辑地址表示:地址结构如图所示

内存分配原则:以内存块为单位分给进程,并且进程的页面可以装在物理上不连续的内存块中

页表:由于页号连续,而块号不一定连续,为了找到进程的每个页面对应内存中的物理块号,为每个进程建立页表。

Linux的多级页表

每个进程的虚拟存储空间可达4GB,分为两个部分:

                 系统空间1G + 用户空间3G

Linux系统中页面大小为4K,因此,进程的虚存空间要划分为4G/4K=220个页面

内存页的分配与释放


Linux系统采用两种方法来管理内存页

位图:记录内存单元的使用情况

链表:记录已分配的内存单元和空闲的内存单元

采用双向链表结构将内存单元连接起来,可以加速空闲内存的查找,或链表处理操作。

进 程 通 信

系统中的进程与内核之间,以及不同的进程之间,需要进行通信和协调,最常用的通信方式是:

信号机制

管道文件
System V IPC(内部进程通信)机制

1.信号概念

信号(signal,称为软中断)机制:是在软件层次上对中断机制的一种模拟。
异步进程可以通过彼此发送信号来实现简单通信。

1.接收信号的进程,在运行过程中检测自身是否收到信号;

2.若收到信号,则转去执行预先规定好的信号处理程序;

3.再返回原先正在执行的进程

除了内核和超级用户之外,并不是每个进程都可以向其他进程发送信号;普通进程只能向具有相同uid和gid的进程发送信号。


2  管道文件

$grep m?.c | wc –l


执行上述命令时,就要创建一个管道文件,和两个进程

1.命令grep m?.c对应一个进程,向管道文件中写入信息,称为“写进程”;

2.命令wc –l对应另一个进程,从管道文件中读取信息,称为“读进程”


由系统自动处理上述两个进程间的同步、调度和缓冲。

管道文件允许两个进程按先入先出(FIFO)的方式传送数据

  

posted @ 2013-05-12 19:21  wust小吴  阅读(278)  评论(0编辑  收藏  举报