Linux Day09

news2025/1/22 8:04:56

目录

一、进程替换

二、Linux信号的使用

2.1  kill() 发送信号

2.2  signal() 改变进程对信号的响应方式

2.3 处理僵死进程

2.3.1 在信号处理函数中调用wait

2.3.2  Linux特有的

2.3.3 结果


一、进程替换

linux上创造一个新进程,没有create创建方法,而是通过fork+exec系列,先将进程复制一份,将子进程替换成另外一个进程,这样就相当于创建一个进程

 ps -f和bash没有任何关系,为什么ps -f的父进程是bash,因为bash将自己复制了一份,然后将ps -f替换了它的子进程,从而有了创造了该指令。

#include <unistd.h>
exec 系类方法介绍以 execl 为例:
  /*
*path:新替换的程序的路径名称
*arg :传给新程序主函数的第一个参数,一般为程序的名字
*arg 后面是剩余参数列表,参数个数可变,必须以空指针作为最后一个参数
*/
i nt execl( const char * path, const char * arg,...);
int execlp( const char * file, const char * arg,...);
int execle( const char * path, const char * arg,..., char * const envp[]);
  int execv( const char * path, char * const argv[]);
int execvp( const char * file, char * const argv[]);
int execve( const char * path, char * const argv[], char * const envp[]);
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<unistd.h>
#include<string.h>
#include <sys/wait.h>
int main(int agrc,char*argv[],char*envp[]){
    printf("main pid=%d,ppid=%d\n",getpid(),getppid());
    pid_t pid=fork();
    assert(pid!=-1);
    if(pid==0)
    {
        printf("child pid=%d,ppid=%d\n",getpid(),getppid());
        char*myenvp[10]={"MYSTR=hello"};
        execl("/bin/ps","ps","-f",(char*)0);
        execlp("ps","ps","-f",(char*)0);
        execle("/usr/bin/ps","ps","-f",(char*)0,myenvp);

        char* myargv[]={"ps","-f",0};
        execv("/usr/bin/ps",myargv);
        execvp("ps",myargv);
        execve("/usr/bin/ps",myargv,envp);
        printf("execl error");
        exit(0);
    }
    wait(NULL);
    exit(0);
}

结果

二、Linux信号的使用

信号是系统响应某个条件而产生的事件,进程接收到信号会执行相应的操作。
信号的值在系统源码中的定义如下:
1. #define SIGHUP 1
2. #define SIGINT 2 //键盘按下 Ctrl+c 时,会产生该信号
3. #define SIGQUIT 3
4. #define SIGILL 4
5. #define SIGTRAP 5
6. #define SIGABRT 6
7. #define SIGIOT 6
8. #define SIGBUS 7
9. #define SIGFPE 8
10. #define SIGKILL 9 //该信号的响应方式不允许改变
11. #define SIGUSR1 10
12. #define SIGSEGV 11
13. #define SIGUSR2 12
14. #define SIGPIPE 13 //读端关闭的描述符,写端写入时产生,该信
号会终止程序
15. #define SIGALRM 14
16. #define SIGTERM 15 //系统 kill 命令默认发送的信号
17. #define SIGSTKFLT 16
18. #define SIGCHLD 17 //子进程结束后,会默认给父进程发送该信
19. #define SIGCONT 18
20. #define SIGSTOP 19
21. #define SIGTSTP 20
22. #define SIGTTIN 21
23. #define SIGTTOU 22
24. #define SIGURG 23

2.1  kill() 发送信号

kill() 可以向指定的进程发送指定的信号:
int kill(pid_t pid, int sig);
pid > 0 指定将信号发送个那个进程
pid == 0 信号被发送到和当前进程在同一个进程组的进程
pid == -1 将信号发送给系统上有权限发送的所有的进程
pid < -1 将信号发送给进程组 id 等于 pid 绝对值,并且有权限发送的所有的进程。
sig 指定发送信号的类型。
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<unistd.h>
#include<string.h>
#include<signal.h>
int main(int argc,char*argv[])
{
    if(argc!=3)
    {
        printf("argc err\n");
        exit(1);
    }
    int pid=atoi(argv[1]);
    int sig=atoi(argv[2]);
    if(kill(pid,sig)==-1)
    {
        printf("kill err\n");
    }
    exit(0);
}

2.2  signal() 改变进程对信号的响应方式

#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<unistd.h>
#include<signal.h>
#include<string.h>
void fun_sig(int sig){
    printf("sig=%d",sig);
}
int main(){
    signal(SIGINT,fun_sig);
    while(1){
        printf("main run\n");
        sleep(1);
    }
    exit(0);
}

 结果:

ctrl+c的信号值为2,与内核达成协议,当有ctrl+c时执行fun_sig()函数。

如果想要结束该进程 :

1.新建一个窗口,查看该进程编号,结束该进程

2.Ctrl +/

 signal(SIGINT,SIG_IGN);忽略 ,如果再ctrl+c,系统不会终止,会继续执行

signal(SIGINT,SIG_DFL);默认,如果再ctrl+c,系统终止

signal(SIGINT,fun_sig);

#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<unistd.h>
#include<signal.h>
#include<string.h>
void fun_sig(int sig){
    printf("sig=%d\n",sig);
    signal(sig,SIG_DFL);
}
int main(){
   // signal(sig,SIG_DFL);//默认
   // signal(sig,SIG_IGN);//忽略
    signal(SIGINT,fun_sig);//自定义
    while(1){
        printf("main run\n");
        sleep(1);
    }
    exit(0);
}

结果

当第一次使用ctrl+c时,调用自定义函数,返回该信号的值,第二次使用ctrl+c调用系统默认的,结束了该进程。

2.3 处理僵死进程

2.3.1 在信号处理函数中调用wait

#include<stdio.h>
#include<stdlib.h>
#include<unistd.h>
#include<string.h>
#include<signal.h>
#include<sys/wait.h>
void fun_sig(int sig)
{
    printf("sig=%d\n",sig);
    wait(NULL);
}
int main()
{
    char*s=NULL;
    int n=0;
    signal(SIGCHLD,fun_sig);
    pid_t pid=fork();
    if(pid==-1){
        exit(1);
    }
    if(pid==0)
    {
        s="child";
        n=3;
    }
    else
    {
        s="parent";
        n=7;
    }
    int i=0;
    for(;i<n;i++){
        printf("s=%s,pid=%d\n",s,getpid());
        sleep(1);
    }
    exit(0);

}

2.3.2  Linux特有的

signal(SIGCHLD,SIG_IGN);

#include<stdio.h>
#include<stdlib.h>
#include<unistd.h>
#include<string.h>
#include<signal.h>
#include<sys/wait.h>
void fun_sig(int sig)
{
    printf("sig=%d\n",sig);
    wait(NULL);
}
int main()
{
    char*s=NULL;
    int n=0;
    signal(SIGCHLD,SIG_IGN);
    pid_t pid=fork();
    if(pid==-1){
        exit(1);
    }
    if(pid==0)
    {
        s="child";
        n=3;
    }
    else
    {
        s="parent";
        n=7;
    }
    int i=0;
    for(;i<n;i++){
        printf("s=%s,pid=%d\n",s,getpid());
        sleep(1);
    }
    exit(0);

}

2.3.3 结果

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/895316.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【Mysql】MVCC版本机制的多并发

&#x1f307;个人主页&#xff1a;平凡的小苏 &#x1f4da;学习格言&#xff1a;命运给你一个低的起点&#xff0c;是想看你精彩的翻盘&#xff0c;而不是让你自甘堕落&#xff0c;脚下的路虽然难走&#xff0c;但我还能走&#xff0c;比起向阳而生&#xff0c;我更想尝试逆风…

Android3:布局

一。线性布局 创建项目Linear Layout Example activity_main.xml <?xml version"1.0" encoding"utf-8"?><LinearLayout xmlns:android"http://schemas.android.com/apk/res/android"android:layout_width"match_parent"an…

微信转账警示!切莫在此时输入密码

微信已经成为我们日常生活中不可或缺的社交工具&#xff0c;通过微信红包和转账完成支付也变得非常普遍。 然而&#xff0c;正如人们常说的&#xff0c;树大招风。随着微信的广泛使用&#xff0c;骗子们也愈发猖獗&#xff0c;他们利用微信进行诈骗活动&#xff0c;使许多人遭受…

手把手教你快速使用java与cpp的互相调用

在jni的开发过程中&#xff0c;如果需要实现java和c之间的接口调用&#xff0c;就要定义一个方法来实现&#xff0c;如果有多个接口调用&#xff0c;就需要定义多个方法来实现&#xff0c;这里介绍一种抽象的接口&#xff0c;只需要分别定义一个javaCallCpp和cppCallJava方法就…

Spring框架入门以及 ioc的三种注入方式

目录 一、Spring是什么&#xff0c;它能够做什么 spring的组成 二、什么是控制反转&#xff08;或依赖注入&#xff09; 三、 如何在spring当中定义和配置一个JavaBean 四、注入方式 1.构造函数注入 2.Setter方法注入 3.自动装配 五、简单属性配置与复杂属性配置 简单…

AIGC:【LLM(六)】——Dify:一个易用的 LLMOps 平台

文章目录 一.简介1.1 LLMOps1.2 Dify 二.核心能力三.Dify安装3.1 快速启动3.2 配置 四.Dify使用五.调用开源模型六.接通闭源模型七.在 Dify.AI 探索不同模型潜力7.1 快速切换&#xff0c;测验不同模型的表现7.2 降低模型能力对比和选择的成本 一.简介 1.1 LLMOps LLMOps&…

vue vs react

vue 简介&#xff1a;渐进式 JavaScript 框架 来源&#xff1a;最初由 Evan You &#xff08;尤雨溪&#xff09;于2014年开发。Evan You之前在Google研究过AngularJS&#xff0c;并提取了Angular的部分特性以提供一个更轻量级的框架 版本&#xff1a; vue 1x&#xff1a;2014…

Android 源码下载(详细版)

经典好文推荐,通过阅读本文,您将收获以下知识点: 一、下载AOSP前的准备 二、国内网络下 clone 清华大学开源软件镜像 三、编写Python脚本,开始下载android-10.0.0_r40 源码 四、源码下载工具包 五、参考文献 一、下载AOSP前的准备 想在国内网络下载AOSP源码,需要电脑配置如…

MySQL之索引和事务

索引什么是索引索引怎么用索引的原理 事务使用事务事务特性MySQL隔离级别 索引 什么是索引 索引包含数据表所有记录的引用指针&#xff1b;你可以对某一列或者多列创建索引和指定不同的类型&#xff08;唯一索引、主键索引、普通索引等不同类型&#xff1b;他们底层实现也是不…

Nginx 配置文件的完整指南 (一)

文章目录 一、简介1.1 配置文件一览 二、全局配置2.0 user2.1 worker_processes2.2 events模块2.3 http模块 三、server模块3.1 listen3.2 server_name3.3 location&#xff1a;请求处理位置 Nginx 配置文件的完整指南 (二) 一、简介 Nginx是一款高性能的Web服务器和反向代理服…

数字孪生三维可视化系统开发平台有哪些优点

随着企业数字化发展的深入&#xff0c;迅速增多的场景化需求要求企业具备更加灵活、敏捷、易用的应用开发能力。而高效、便捷、易用、低本的数字孪生系统制作也是大势所趋&#xff0c;数字孪生公司深圳华锐视点基于3d可视化、数字孪生和VR虚拟仿真技术搭建了3D数字孪生编辑器&a…

【Axure高保真原型】JS日期选择器筛选中继器表格

今天和大家分享JS日期选择器筛选中继器表格的原型模板&#xff0c;通过调用浏览器的日期选择器&#xff0c;所以可以获取真实的日历效果&#xff0c;具体包括哪一年二月份有29天&#xff0c;几号对应星期几&#xff0c;都是真实的&#xff0c;获取日期值后&#xff0c;通过交互…

python 使用 pdf2image 库将PDF转换为图片

在 Ubuntu 上实现网络穿透&#xff1a;手把手教你搭建FRPS服务器 初环境步骤一&#xff1a;安装pdf2image库步骤二&#xff1a;导入必要的库步骤三&#xff1a;指定PDF文件路径步骤四&#xff1a;将PDF转换为图片步骤五&#xff1a;保存图像为图片文件完整代码运行结果 在数字化…

Linux内核常用调试技巧汇总

printk printk共有8个等级&#xff0c;从0-7&#xff0c;等级依次降低。 打印等级可以通过修改/proc/sys/kernel/printk来改变。 查看printk等级&#xff1a; cat /proc/sys/kernel/printk 7 4 1 7打开内核所有打印&#xff1a; echo 8 > /proc/sys/kernel/printk 动态…

VK36W1D浴缸,洁具高灵敏度电容式单点液体水位检测触摸芯片资料介绍

产品品牌&#xff1a;永嘉微电/VINKA 产品型号&#xff1a;VK36W1D 封装形式&#xff1a;SOT23-6L 产品年份&#xff1a;新年份 &#xff08;C21-163&#xff09; 产品特点&#xff1a;VK36W1D具有1个触摸检测通道&#xff0c;可用来检测水从无到有和水从有到无的动作。该…

神经网络论文研读-多模态方向-综述研读(上)

翻译以机翻为主 原文目录 前言 图1&#xff1a;LMU印章&#xff08;左&#xff09;风格转移到梵高的向日葵绘画&#xff08;中&#xff09;并与提示混合 - 梵高&#xff0c;向日葵 -通过CLIPVGAN&#xff08;右&#xff09;。在过去的几年中&#xff0c;自然语言处理&#xff…

【MySQL系列】表内容的基本操作(增删查改)

「前言」文章内容大致是对MySQL表内容的基本操作&#xff0c;即增删查改。 「归属专栏」MySQL 「主页链接」个人主页 「笔者」枫叶先生(fy) 目录 一、MySQL表内容的增删查改1.1 Create1.1.1 单行数据全列插入1.1.2 多行数据指定列插入1.1.3 插入否则更新1.1.4 数据替换 1.2 Ret…

Vue 2自定义指令入门

Vue 2自定义指令入门 Vue自定义指令允许我们在DOM元素上添加自己想要的行为来扩展Vue的功能。 一个自定义指令需要一个名称和一个定义对象。在定义对象中&#xff0c;你可以使用一些钩子函数来控制指令的行为&#xff1a; bind&#xff1a;在指令被绑定到元素上时使用&#…

ShardingSphere 可观测 SQL 指标监控

ShardingSphere并不负责如何采集、存储以及展示应用性能监控的相关数据&#xff0c;而是将SQL解析与SQL执行这两块数据分片的最核心的相关信息发送至应用性能监控系统&#xff0c;并交由其处理。 换句话说&#xff0c;ShardingSphere仅负责产生具有价值的数据&#xff0c;并通过…

类加载 - 双亲委派机制详解

1、类加载器有哪些 启动类加载器&#xff08;Bootstrap Class Loader&#xff09;&#xff1a;它是Java虚拟机的一部分&#xff0c;负责加载Java核心类库&#xff0c;如java.lang包中的类。它是最顶层的类加载器&#xff0c;由C实现&#xff0c;不是Java类。 扩展类加载器&…