Linux操作系统综述

“操作系统其实就像一个软件外包公司,其内核就相当于这家外包公司的老板。所以接下来的整个 课程中,请你将自己的角色切换成这家软件外包公司的老板,设身处地地去理解操作系统是如何 协调各种资源,帮客户做成事情的。”                                                    ——刘超

 

Linux常见的系统调用

进程管理 

首先,我们得有个项目,那就要有立项服务。对应到Linux操作系统中就是创建进程。 创建进程的系统调用叫fork。在Linux里,要创建一个新的进程,需要一个老的进程调用fork来实现,其中老的进程叫作父进程(Parent Process),新的进程叫作子进程(Child Process)。 

创建新进程使用的方式是:当父进程调用fork创建进程的时候,子进程将各个子系统为父进程创建的 数据结构也全部拷贝了一份,甚至连程序代码也是拷贝过来的,原因是如果全部重头来过复杂得很。

对于fork系统调用的返回值,如果当前进程是子进程,就返回0; 如果当前进程是父进程,就返回子进程的进程号。这样首先在返回值这里就有了一个区分,然后 通过if-else语句判断,如果是父进程,还接着做原来应该做的事情;如果是子进程,需要请求另 一个系统调用execve来执行另一个程序,这个时候,子进程和父进程就彻底分道扬镳了,也即产生了一个分支(fork)了。

 新进程都是父进程fork出来的,那到底谁是第一个呢?启动的时候先创建一个所有用户进程的“祖宗进程”。

有个系统调用 waitpid,父进程可以调用它,将子进程的进程号作为参数传给它,这样父进程就知道子进程运行完了没有,成功与否。 所以说,所有子项目最终都是老板,也就是祖宗进程fork过来的,因而它要对整个公司的项目执 行负最终的责任。

内存管理

在操作系统中,每个进程都有自己的内存,互相之间不干扰,有独立的进程内存空间。

进程的内存空间来 讲,放程序代码的这部分,我们称为代码段(Code Segment)

对于进程的内存空间来讲,放进程运行中产生数据的这部分,我们称为数据段(Data Segment)。其中局部变量的部分,在当前函数执行的时候起作用,当进入另一个函数时,这个变量就释放了;也有动态分配的,会较长时间保存,指明才销毁的,这部分称为堆 (Heap)

进程不用内存的时候就不去管,只有当进程真的要用内存了才会使用内存管理的系统调用,并且只有真的写入数据的时候,发现没有对应的物理内存,才会触发一个中断,现分配内存。

brk和mmap系统调用

当分配的内存数量比较小的时候,使用brk,会和原来的堆的数据连在一起; 当分配的内存数量比较大的时候,使用mmap, 会重新划分一块区域

文件管理

程序、文档、照片等,哪怕关机再开机也能不丢的,就需要放在文件系统里面。 

文件之所以能做到这一点,一方面是因为介质,另一方面是因为格式。 

对于文件的操作,下面这六个系统调用是最重要的:

对于已经有的文件,可以使用open打开这个文件,close关闭这个文件;

对于没有的文件,可以使用creat创建文件;

打开文件以后,可以使用lseek跳到文件的某个位置;

可以对文件的内容进行读写,读的系统调用是read,写是write

Linux里有一个特点,那就是一切皆文件

 每个文件,Linux都会分配一个文件描述符(File Descriptor),这是一个整数。有了这个文件 描述符,我们就可以使用系统调用,查看或者干预进程运行的方方面面

信号处理 

当项目遇到异常情况,例如项目中断,做到一半不做了。这时候就需要发送一个信号(Signal) 给项目组。经常遇到的信号有以下几种:

  • 在执行一个程序的时候,在键盘输入“CTRL+C”,这就是中断的信号,正在执行的命令就会 中止退出;
  • 如果非法访问内存,例如你跑到别人的会议室,可能会看到不该看的东西;
  • 硬件故障,设备出了问题,当然要通知项目组;
  • 用户进程通过kill函数,将一个用户信号发送给另一个进程。

当项目组收到信号的时候,项目组需要决定如何处理这些异常情况。对于一些不严重的信号,可以忽略,该干啥干啥,但是像SIGKILL(用于终止一个进程的信号) 和SIGSTOP(用于中止一个进程的信号)是不能忽略的,可以执行对于该信号的默认动作。每种 信号都定义了默认的动作,例如硬件故障,默认终止;也可以提供信号处理函数,可以通过 sigaction系统调用,注册一个信号处理函数。

进程间通信

发个消息,不需要一段很长的数据,这种方式称为消息队列(Message Queue)。 这个消息队列是在内核里的,我们可以通过msgget创建一 个新的队列,msgsnd将消息发送到消息队列,而消息接收方可以使用msgrcv从队列中取消 息。

信息比较大的时候,可以使用共享内存的方式,也即两个项目组共享一 个会议室(这样数据就不需要拷贝来拷贝去)。大家都到这个会议室来,就可以完成沟通了。这 时候,我们可以通过shmget创建一个共享内存块,通过shmat将共享内存映射到自己的内存空 间,然后就可以读写了。

但是,两个项目组共同访问一个会议室里的数据,就会存在“竞争”的问题。如果大家同时修改 同一块数据咋办?这就需要有一种方式,让不同的人能够排他地访问,这就是信号量的机制 Semaphore。

网络通信

不同机器的通过网络相互通信,要遵循相同的网络协议,也即TCP/IP网络协议栈。网络服务是通过套接字Socket来提供服务的。在通信之前,双方都要建立一个Socket。

中介与Glibc

 Glibc是Linux下使用的开源的标准C库,它是GNU发布的libc库。Glibc为程序员提供丰富的 API,除了例如字符串处理、数学运算等用户态服务之外,最重要的是封装了操作系统提供的系 统服务,即系统调用的封装。 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值