🐇明明跟你说过:个人主页
🏅个人专栏:《Linux :从菜鸟到飞鸟的逆袭》🏅
🔖行路有良友,便是天堂🔖
目录
一、前言
1、Linux的起源与发展
1991年,芬兰赫尔辛基大学的学生林纳斯·托瓦兹(Linus Torvalds)开始编写一个新的操作系统内核,这个内核最初被称为“Freax”。他的初衷只是想学习操作系统内核的开发,并为自己的个人计算机编写一个操作系统。然而,当他将这个内核发布在Internet上并开放源代码后,全球各地的程序员开始参与到这个项目中来,共同完善这个内核。最终,这个内核被命名为Linux,这个名字是由Linus Torvalds的名字和Unix操作系统的名字组合而成的。
Linux从一开始就坚持源代码的公开和免费使用,任何人都可以对其进行修改和分发。这种开放性和自由性吸引了大量的开发者和用户,使得Linux逐渐成长并成熟起来。如今,Linux已经发展成为一个性能稳定、功能强大的多用户网络操作系统,支持32位和64位硬件,能运行主要的Unix工具软件、应用程序和网络协议。同时,Linux也有上百种不同的发行版,如基于社区开发的Debian、ArchLinux,以及基于商业开发的Red Hat Enterprise Linux、SUSE、Oracle Linux等。
2、进程的概念
在Linux操作系统中,进程(Process)是计算机中的程序关于某数据集合上的一次运行活动,是系统进行资源分配和调度的基本单位,是操作系统结构的基础。从内核的观点看,进程的目的就是担当分配系统资源(CPU时间、内存等)的基本单位。
进程的特点
- 动态性:进程是程序的一次执行过程,是动态产生和消亡的。
- 并发性:任何进程都可以同其他进程一起并发执行。
- 独立性:进程是一个能独立运行的基本单位,同时也是系统分配资源和调度的独立单位。
- 异步性:由于进程间的相互制约,使进程具有执行的间断性,即进程按各自独立的、不可预知的速度向前推进。
- 结构性:进程由程序、数据和进程控制块三部分组成。
二、查看进程信息
1、ps命令的使用
ps 命令在 Unix 和类 Unix 系统(如 Linux)中用于显示当前进程的详细信息。它可以以多种方式展示进程的状态,如按照用户、CPU 使用率、内存使用量等。
以下是一些常见的 ps 命令用法和选项:
1. 显示所有进程:
ps -e
或者更常用的
ps -ef
- -e 选项表示选择所有进程,-f 选项表示全格式显示(full format)。
2. 显示特定用户的进程:
ps -u 用户名
例如,要显示用户 john 的所有进程,可以使用:
ps -u john
3. 按照 CPU 使用率排序:
ps -eo pid,user,%cpu,%mem,args --sort=-%cpu
这将按照 CPU 使用率降序排序进程,并显示 PID、用户名、CPU 使用率、内存使用率和命令名。
4. 显示进程树:
虽然 ps 本身不提供进程树视图,但可以使用 pstree 命令或结合 ps 和 grep 来模拟它。例如,要显示以 PID 1234 为根的进程树,可以使用:
pstree -p 1234
或者,使用 ps 和 grep(这不是真正的进程树,但可以提供一些信息):
ps -ef --forest | grep 1234
5. 仅显示指定进程的详细信息:
可以使用 grep 与 ps 结合来仅显示特定进程的详细信息。例如,要查找名为 nginx 的所有进程,可以使用:
ps -ef | grep nginx
注意:在上面的命令中,grep nginx 本身也会作为一个进程显示在结果中。因此,通常会看到两个包含 nginx 的行,其中一个是实际的 nginx 进程,另一个是 grep 命令本身。
6. 实时查看进程状态:
使用 watch 命令与 ps 结合可以实时查看进程状态。例如:
watch -n 1 ps -eo pid,user,%cpu,%mem,args --sort=-%cpu
这将每秒更新一次 CPU 使用率最高的进程列表。
7. 其他常用选项:
- -l:长格式显示。
- -o:自定义输出格式。例如,ps -eo pid,user,cmd 仅显示 PID、用户名和命令名。
- --no-headers:不显示标题行。
- --sort:按照指定列排序。例如,--sort=-%mem 按内存使用量降序排序。
2、top命令的使用
top 命令是 Unix 和 Linux 系统中常用的实时进程监控工具,它可以动态地显示系统中运行的进程信息,包括 CPU 和内存使用情况、运行时间等。top 命令不仅提供了类似于 ps 命令的静态视图,还可以动态刷新,以便实时监控系统性能。
基本用法
top
输出说明
执行 top 命令后,会显示一个包含多个字段的表格,其中包括:
1. 系统信息(顶部几行):
- uptime:系统运行时间。
- tasks:任务(进程)的总数以及它们的状态(运行、停止、休眠等)。
- cpu(s):每个 CPU 的使用情况,包括用户态、系统态、空闲、IO等待等。
- mem:物理内存使用情况。
- swap:交换空间使用情况。
2. 进程信息(表格部分):
- PID:进程ID。
- USER:进程所属用户。
- PR:优先级。
- NI:nice值。
- VIRT:虚拟内存使用量。
- RES:常驻内存使用量。
- SHR:共享内存使用量。
- S:进程状态(例如 R=运行,S=睡眠,Z=僵尸进程)。
- %CPU:CPU使用率。
- %MEM:内存使用率。
- TIME+:进程使用的总CPU时间。
- COMMAND:执行的命令。
常见交互命令
在 top 运行时,可以通过按键与之交互:
- h:显示帮助信息。
- q:退出 top。
- k:杀死进程,提示输入PID和信号(默认是 SIGTERM)。
- r:重新设定进程优先级(nice值),提示输入PID和新的优先级。
- P:按CPU使用率排序(默认)。
- M:按内存使用率排序。
- T:按运行时间排序。
- c:切换显示命令的完整路径和参数。
- 1:切换显示每个CPU的使用情况。
实用示例
1. 显示特定用户的进程:
- 启动 top 后按 u,然后输入用户名,可以只显示该用户的进程。
2. 设置刷新间隔:
- 启动 top 后按 d,然后输入秒数,可以设置刷新间隔时间(默认是3秒)。
3. 显示特定进程的信息:
- 启动 top 后按 /,然后输入进程名称,可以只显示与该名称匹配的进程。
4. 输出重定向到文件:
使用 -b 选项以批处理模式运行,并将输出重定向到文件:
top -b -n 1 > top_output.txt
这将运行一次 top,并将输出保存到 top_output.txt 文件中。
5. 显示更多(或更少)字段:
- 启动 top 后按 f,可以选择需要显示的字段。
6. 按字段排序:
- 启动 top 后按 O(大写字母 O),然后选择要按其排序的字段。
高级用法
1. 监控特定进程的资源使用:
例如监控 PID 为 1234 的进程:
top -p 1234
2. 自动退出:
运行一定次数后自动退出:
top -n 5
这将刷新 5 次后退出。
三、进程管理
1、启动进程
在 Linux 中,可以通过命令行直接启动进程。启动进程的方法有多种,包括运行可执行文件、启动脚本或通过一些系统命令来启动特定的服务。
1. 直接运行可执行文件
如果有一个可执行文件或脚本,可以直接在命令行中运行它:
./my_executable
如果可执行文件不在当前目录,可能需要提供路径:
/home/user/bin/my_executable
2. 使用 sh 或 bash 运行脚本
对于 shell 脚本,可以使用 sh 或 bash 命令来运行它们:
sh my_script.sh
或
bash my_script.sh
3. 运行后台进程
如果希望进程在后台运行,可以在命令末尾加上 &:
./my_executable &
这将启动进程并将其置于后台运行,允许你继续使用当前的 shell 会话。
4. 使用 nohup 命令
nohup 命令用于在后台运行进程,并确保即使用户注销(logout),进程也会继续运行:
nohup ./my_executable &
输出通常会被重定向到 nohup.out 文件中,除非另行指定。
5. 使用 systemctl 启动服务
对于系统服务,可以使用 systemctl 命令来启动它们。需要管理员权限时,可以使用 sudo:
sudo systemctl start my_service
6. 使用 service 命令(较旧的系统)
在一些较旧的系统中,使用 service 命令来启动服务:
sudo service my_service start
2、终止进程
kill 命令是 Unix 和 Linux 系统中用于发送信号给进程的命令,最常见的用途是终止进程。它不仅限于杀死进程,还可以发送各种信号,以控制进程的行为。
基本语法
kill [options] <pid>...
pid 是要发送信号的进程 ID(PID)。可以是一个或多个进程 ID。
常用选项和信号
1. 默认信号(TERM,15):发送终止信号(SIGTERM),请求进程正常终止。
kill <pid>
2. 终止信号(KILL,9):强制终止进程(SIGKILL),无法被捕获或忽略。
kill -9 <pid>
3. 挂起信号(HUP,1):重新加载配置文件或重新初始化(SIGHUP),常用于重新加载守护进程配置。
kill -HUP <pid>
4. 用户定义信号(USR1,10 和 USR2,12):用户自定义操作信号(SIGUSR1 和 SIGUSR2),可以由用户定义和捕获。
kill -USR1 <pid>
查看信号列表
可以使用 kill -l 来列出所有可用的信号及其对应的数字:
kill -l
使用 pkill 和 killall
1. pkill:按进程名称发送信号
pkill <process_name>
例如,终止所有名为 httpd 的进程:
pkill httpd
2. killall:按进程名称发送信号
killall <process_name>
例如,强制终止所有名为 firefox 的进程:
killall -9 firefox
3、进程调度与优先级调整
在 Linux 操作系统中,进程调度和优先级调整是确保系统高效运行和资源合理分配的重要机制。调度器决定了进程的执行顺序和时间片,而优先级则影响调度器对进程的选择。
进程调度
调度器
Linux 主要使用以下几种调度器:
1. 完全公平调度器 (CFS):
- CFS 是 Linux 的默认调度器,旨在提供公平的 CPU 时间分配。
- 使用红黑树数据结构管理进程,并根据每个进程的虚拟运行时间决定调度。
2. 实时调度器:
- 实时调度策略包括 SCHED_FIFO(先进先出)和 SCHED_RR(轮转)。
- 适用于需要严格时间约束的实时任务,优先级高于普通进程。
调度策略
- SCHED_OTHER:默认的非实时时间共享调度策略。
- SCHED_BATCH:适用于批处理作业,减少交互性。
- SCHED_IDLE:适用于极低优先级的后台任务。
优先级调整
静态优先级和动态优先级
- 静态优先级:由用户或系统管理员通过 nice 或 renice 命令设置,范围从 -20(最高优先级)到 19(最低优先级)。
- 动态优先级:由内核动态调整,用于平衡系统负载和响应性。
调整优先级的命令
1. nice 命令:启动进程时设置优先级
nice -n <niceness> command
例如:
nice -n 10 ./my_program
2. renice 命令:调整运行中进程的优先级
renice <niceness> -p <pid>
四、进程间通信(IPC)
1、IPC的概念
IPC(Inter-Process Communication,进程间通信)是指在多道程序设计环境下,不同进程之间进行数据交换和共享信息的一种机制。在现代操作系统中,进程间通信是非常常见和重要的,它允许不同进程之间协作完成任务、共享资源和信息,提高系统的效率和灵活性。
2、管道(Pipe)
管道(Pipe)是一种用于进程间通信的机制,它允许一个进程的输出直接作为另一个进程的输入。管道可以实现单向通信,其中一个进程将数据写入管道,而另一个进程则从管道中读取数据。
特点和原理
- 单向通信:管道是单向的,即数据只能从一个方向流动。通常分为父进程到子进程的管道(标准输出到标准输入)和子进程到父进程的管道(标准输出到标准输入)。
- 基于文件描述符:在 Linux 中,管道实际上是一种文件描述符。数据被写入管道时,实际上是写入了文件描述符的写端;而从管道读取数据时,则是从文件描述符的读端读取数据。
- 进程间直接通信:管道连接了两个进程的标准输入和标准输出,使得它们可以直接通信,而不需要借助于临时文件或其他 IPC 机制。
3、命名管道(FIFO)
命名管道(Named Pipe),也称为 FIFO(First In, First Out),是一种特殊类型的文件系统对象,用于进程间通信。与普通管道不同的是,命名管道在文件系统中有一个路径名,可以像普通文件一样通过路径名访问,而不仅仅是在进程间传递数据。
特点和原理
- 路径名:命名管道在文件系统中有一个路径名,可以通过这个路径名访问。它以文件的形式存在于文件系统中,有一个唯一的路径。
- 进程间通信:命名管道允许不相关的进程之间通过读写文件的方式进行通信。一个进程可以将数据写入命名管道,而另一个进程则可以从该管道读取数据。
- 基于文件的通信:与普通文件一样,命名管道也是基于文件的通信方式,因此可以在不同的进程间共享数据。
4、信号(Signal)
信号(Signal)是一种在 Unix 和类 Unix 操作系统中用于进程间通信的机制,用于通知进程发生了某种事件。信号可以由操作系统、其他进程或进程自身生成,并被发送给目标进程。接收信号的进程可以采取特定的动作来处理信号,例如执行预定义的处理程序或者忽略信号。
特点和原理
- 异步通知:信号是一种异步通知机制,它可以随时中断目标进程的执行,无需目标进程的显式请求。
- 事件通知:信号通常用于通知目标进程发生了某种事件,如进程终止、键盘输入、定时器超时等。
- 处理方式:接收信号的进程可以选择如何处理信号,包括执行默认操作、执行用户定义的信号处理函数、忽略信号等。
- 预定义信号:操作系统提供了一些预定义的信号,如 SIGINT(中断信号,通常由 Ctrl+C 发送)和 SIGTERM(终止信号,通常用于请求进程正常退出)等。
常见的信号
Unix/Linux 系统提供了多种信号,具体的信号值和含义可以在系统头文件 signal.h 中找到。以下是一些常见的信号:
- SIGINT:中断信号,通常由用户在终端按下 Ctrl+C 发送,用于终止进程。
- SIGTERM:终止信号,用于请求进程正常退出。
- SIGKILL:强制终止信号,无法被忽略或捕获,用于强制终止进程。
- SIGALRM:定时器信号,通常用于定时器超时。
- SIGUSR1 和 SIGUSR2:用户定义的信号,可以由用户定义和捕获。
信号处理
接收信号的进程可以选择如何处理信号,包括以下几种方式:
- 执行默认操作:对于大多数信号,操作系统提供了默认的处理方式,例如终止进程或者忽略信号。
- 执行信号处理函数:进程可以注册信号处理函数,当接收到信号时执行相应的处理逻辑。可以使用 signal() 或 sigaction() 函数来注册信号处理函数。
- 忽略信号:进程可以选择忽略某些信号,对于忽略的信号,系统不会做任何处理。
💕💕💕每一次的分享都是一次成长的旅程,感谢您的陪伴和关注。希望这些关于Linux的文章能陪伴您走过技术的一段旅程,共同见证成长和进步!😺😺😺
🧨🧨🧨让我们一起在技术的海洋中探索前行,共同书写美好的未来!!!