LINUX进程间的通信(IPC)--信号

一、概念

信号通信,其实就是内核向用户空间进程发送信号,只有内核才能发信号,用户空间进程不能发送信号。信号已经是存在内核中的了,不需要用户自己创建。

信号通信的框架
        * 信号的发送(发送信号进程):kill raise alarm
        * 信号的接收(接收信号进程) : pause() sleep while(1)
        * 信号的处理(接收信号进程) :signal

二、相关函数

1.信号的发送(发送信号进程)

所需头文件:
#include<signal.h>
#include<sys/types.h>
函数原型: int kill(pid_t pid, int sig);
参数:
函数传入值: pid
        正数:要接收信号的进程的进程号
        0:信号被发送到所有和 pid 进程在同一个进程组的进程
        ‐1:信号发给所有的进程表中的进程 ( 除了进程号最大的进程外 )
sig :信号
函数返回值:成功 0 出错 ‐1
示例:
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <signal.h>int main(int argc,char *argv[])
{int pid,sig;if(argc != 3){printf("输入错误\n");return -1;}sig = atoi(argv[1]);pid = atoi(argv[2]);printf("pid = %d,sig = %d\n",pid,sig);int rnt = kill(pid,sig);if(rnt == 0){printf("杀死进程%d成功\n",pid);}return 0;
}
~   
运行结果:

2.raise: 发信号给自己 == kill(getpid(), sig)

所需头文件:
#include<signal.h>
#include<sys/types.h>
函数原型: int raise(int sig);
参数:
函数传入值: sig :信号
函数返回值:
成功 0 出错 ‐1
示例:
#include <stdio.h>
#include <signal.h>
#include <sys/types.h>
#include <unistd.h>int main()
{printf("hello;\n");//int rnt = raise(9);int rnt = kill(getpid(),9);if(rnt == 0){printf("杀死自己成功\n");}printf("world\n");return 0;
}

运行结果:

3.alarm : 发送闹钟信号的函数

alarm raise 函数的比较:
        相同点:让内核发送信号给当前进程
        不同点:
                alarm 只会发送SIGALARM 信号
                alarm 会让内核定时一段时间之后发送信号, raise 会让内核立刻发信号
所需头文件 #include <unistd.h>
函数原型 unsigned int alarm(unsigned int seconds)
参数:
seconds :指定秒数
返回值:
        成功:如果调用此alarm() 前,进程中已经设置了闹钟时间,则 返回上一个闹钟时间的剩余时间,否则返回 0
        出错:‐1
示例:
#include <stdio.h>
#include <signal.h>
#include <unistd.h>int main()
{int i;alarm(5);printf("alarm start\n");for(i =0 ;i<20;i++){sleep(1);printf("i = %d\n",i);}return 0;
}

运行结果:

4.信号的接收

接收信号的进程,要有什么条件:要想使接收的进程能收到信号,这个进程不能结束 : sleep        
pause:进程状态为 S (休眠)
函数原型 int pause(void);
函数返回值:
成功: 0 ,出错: ‐1
示例:
#include <stdio.h>
#include <signal.h>
#include <unistd.h>int main()
{int i,rnt;printf("pause start\n");pause();for(i =0 ;i<20;i++){sleep(1);printf("i = %d\n",i);}return 0;
}

运行结果:

5.信号的处理

收到信号的进程,应该怎样处理? 处理的方式:
        1.进程的默认处理方式(内核为用户进程设置的默认处理方式)
                A:忽略B :终止进程 C: 暂停
        2.自己的处理方式:
                自己处理信号的方法告诉内核,这样你的进程收到了这个信号就会采用你自己的的处理方式、
函数原型 void (*signal(int signum, void (*handler)(int)))(int);
参数:
signum 指定信号
handler:
        1.SIG_IGN:忽略该信号。
        2.SIG_DFL:采用系统默认方式处理信号
        3.自定义的信号处理函数指针
函数返回值
成功:设置之前的信号处理方式
出错: ‐1
signal 函数有二个参数,第一个参数是一个整形变量(信号值),第二个参数是一个函数指针,是我们自己写的处理函
数;这个函数的返回值是一个函数指针。

1.示例:自定义的信号处理函数指针

#include <stdio.h>
#include <signal.h>
#include <unistd.h>
void myfun(int signum)
{int i;while(i<5){printf("signum = %d,i = %d\n",signum,i);i++;sleep(1);}
}
int main()
{int i,rnt;signal(14,myfun);//14信号是定时器到时发出printf("alarm start\n");alarm(7);for(i =0 ;i<10;i++){sleep(1);printf("i = %d\n",i);}return 0;
}

运行结果:
PS:回调函数执行完之后会重新回到主函数继续执行

2.示例:忽略该信号

#include <stdio.h>
#include <signal.h>
#include <unistd.h>
void myfun(int signum)
{int i;while(i<5){printf("signum = %d,i = %d\n",signum,i);i++;sleep(1);}
}
int main()
{int i,rnt;signal(14,myfun);//14信号是定时器到时发出printf("alarm start\n");alarm(7);signal(14,SIG_IGN);for(i =0 ;i<10;i++){sleep(1);printf("i = %d\n",i);}return 0;
}

运行结果:

3.示例:采用系统默认方式处理信号

#include <stdio.h>
#include <signal.h>
#include <unistd.h>
void myfun(int signum)
{int i;while(i<5){printf("signum = %d,i = %d\n",signum,i);i++;sleep(1);}
}
int main()
{int i,rnt;signal(14,SIG_DFL);printf("alarm start\n");alarm(7);for(i =0 ;i<10;i++){sleep(1);printf("i = %d\n",i);}return 0;
}

运行结果:

三、信号灯

信号灯集合(可以包含多个信号灯) IPC 对象是一个信号的集合(多个信号量) 一个信号灯有多个信号量。

1.相关函数

1.函数原型: int semget(key_t key, int nsems, int semflg);

功能:创建一个新的信号量或获取一个已经存在的信号量的键值。
函数参数:
key 和信号灯集关联的 key
nsems: 信号灯集中包含的信号灯数目
semflg 信号灯集的访问权限
函数返回值:
成功:信号灯集 ID
出错: ‐1

2.函数原型:int semctl ( int semid, int semnum, int cmd…union semun arg(不是地址));

功能:控制信号量,删除信号量或初始化信号量
函数参数:
semid :信号灯集 ID
semnum: 要修改的信号灯编号
cmd :
        GETVAL:获取信号灯的值
        SETVAL:设置信号灯的值
        IPC_RMID:从系统中删除信号灯集合
函数返回值:
成功: 0
出错: ‐1

三、PV操作

int semop(int semid ,struct sembuf *sops ,size_t nsops);
功能:用户改变信号量的值。也就是使用资源还是释放资源使用权
参数:
semid : 信号量的标识码。也就是 semget ()的返回值
sops 是一个指向结构体数组的指针。
        struct sembuf{
        unsigned short sem_num;   // 信号灯编号;
        short sem_op;                        //对该信号量的操作。‐1 ,P 操作, 1 V 操作
        short sem_flg;                        //0阻塞,1非阻塞
        };
sem_op : 操作信号灯的个数
// 如果其值为正数,该值会加到现有的信号内含值中。通常用于释放所控资源的使用权;如果 sem_op 的值为负 数,而其绝对值又大于信号的现值,操作将会阻塞,直到信号值大于或等于sem_op 的绝对值。通常用于获取资源的使用 权;如果sem_op 的值为 0 ,则操作将暂时阻塞,直到信号的值变为 0

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

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

相关文章

JS图形引擎汇总

1、leaferjs leaferjs绚丽多彩的 HTML5 Canvas 2D 图形渲染引擎&#xff0c;可结合 AI 绘图、生成界面。 提供了丰富的 UI 绘图元素&#xff0c;和开箱即用的功能&#xff0c;如自动布局、图形编辑、SVG 导出&#xff0c;方便与 Figma、Sketch 等产品进行数据交换。并为跨平台…

示波器选择导出至USB闪存盘的三种格式(bmp、set、csv)

如下图所示&#xff0c;一般由示波器导出至U盘中&#xff0c;一共有三种文件格式。 1、当前屏幕图像(*.bmp) BMP 文件格式&#xff08;全称是位图文件格式&#xff0c;Bitmap Image File&#xff09;是一种图像文件格式&#xff0c;用于存储数字图像。它是一种无损图像格式&am…

m3u8转MP4(网页视频下载)(超细教程, 有手就行)

准备工作 什么是m3u8文件 记事本打开m3u8文件&#xff1a; #EXTM3U #EXT-X-VERSION:3 #EXT-X-TARGETDURATION:4 #EXT-X-MEDIA-SEQUENCE:0 #EXT-X-KEY:METHODAES-128,URI"https://xxxx/key.key" #EXTINF:3.336667, #EXTINF:1.668333, clvHz13123499.ts #EXTINF:2.03…

【uniapp离线打包】(基于Android studio)

文章目录 uniapp打包官方教程入口一、准备工作(工具三大件)二、准备工作&#xff08;Android壳和uniapp包&#xff09;导入Android壳生成uniapp包将uniapp包导入android壳 三、准备工作&#xff08;证书、&#xff09;准备Android平台离线签名证书 四、修改配置参数build.gradl…

AI为什么无法替代律师?

AI能否真正取代律师&#xff1f;一探究竟&#xff01; ©作者|LuMiQ 来源|神州问学 引言 数字化时代&#xff0c;AI技术正如催化剂般加速各行业的变革&#xff1a;在医疗界&#xff0c;它犹如医生的“第二双眼睛”&#xff0c;精准分析影像&#xff1b;制造业里&#xff…

ofcms代码审计

1 SSTI模板注入 1.1 通过阅读pom.xml,使用了freemaker开源组件 1.2 找到对应的模版新增页面,并注入payload,点击保存 最重要的是,找到模板注入请求的后端API 注入的命令为:<#assign value="freemarker.template.utility.Execute"?new()>${value("c…

WIFI 接收机和发射机同步问题+CFO/SFO频率偏移问题

Synchronization Between Sender and Receiver & CFO Correction 解决同步问题和频率偏移问题是下面论文的关键&#xff0c;接下来结合论文进行详细解读 解读论文&#xff1a;Verification and Redesign of OFDM Backscatter 论文pdf&#xff1a;https://www.usenix.org/s…

ChatGPT自学指南:宝藏参考书大盘点

ChatGPT是基于人工智能领域的自然语言处理技术&#xff0c;使用深度学习技术构建的一个大型语言模型。具体地说&#xff0c;ChatGPT是建立在OpenAI的GPT-4系列模型之上的&#xff0c;使用了大量的语言数据和预训练技术&#xff0c;可以生成高质量的文本&#xff0c;并且在准确度…

二叉树--堆(下卷)

二叉树–堆&#xff08;下卷&#xff09; 如果有还没看过上卷的&#xff0c;可以看这篇&#xff0c;链接如下&#xff1a; http://t.csdnimg.cn/HYhax 向上调整算法 堆的插⼊ 将新数据插⼊到数组的尾上&#xff0c;再进⾏向上调整算法&#xff0c;直到满⾜堆。 &#x1f4…

根据空域图信息构造飞机航线图以及飞行轨迹模拟matlab仿真

目录 1.程序功能描述 2.测试软件版本以及运行结果展示 3.核心程序 4.本算法原理 4.1 航路网络建模 4.2 航线图构建 4.3 飞行轨迹模拟的具体步骤 5.完整程序 1.程序功能描述 空域图是指航空领域中的一种图形表示方式&#xff0c;它涵盖了空中交通管理所需要的各种信息&a…

如何处理selenium Webdriver中的文本框?

文本框或字段在整个网页中广泛使用,本文将介绍如何在Java中使用Selenium Webdriver处理文本框。可以有各种文本字段,我们将尝试包括其中的大多数,并执行各种操作,如清除和输入文本。 我们将使用我们的Selenium游乐场网站- testkru,与各种文本框进行交互。您也可以使用同一…

藏文词典查单词,藏汉双语解释,推荐使用《藏语翻译通》App

《藏语翻译通》App推出了藏文词典、藏汉大词典、新术语等全新在线查单词功能。 藏汉互译 《藏语翻译通》App的核心功能之一是藏汉互译。用户只需输入中文或藏文&#xff0c;即可获得翻译结果。 藏文词典查单词 掌握一门语言&#xff0c;词汇是基础。《藏语翻译通》App内置藏…

诱骗IoT恶意软件跟踪CC服务器

工作背景 在分析 IoT 僵尸网络时&#xff0c;识别C&C 服务器至关重要。C&C 服务器的 IP 地址一直都是商业威胁情报的重要组成部分&#xff0c;由于 C&C 服务器通信协议日渐复杂并且活跃周期较短&#xff0c;时效性和准确性也非常重要。如果可以自动化识别 IoT 恶意…

力扣100题——128题

题目 ************************************************ 解&#xff08;哈希&#xff09; VS完整代码 #include<iostream> #include<vector> #include<unordered_set> #include<utility> #include<algorithm> using namespace std; int n, nu…

二叉树(2)

目录 2.5 二叉树的存储结构 3.二叉树的顺序结构及实现 3.1二叉树的顺序结构 3.2堆的概念以及结构 3.3堆的实现 3.4堆的代码实现 3.5堆的应用 书接上回&#xff0c;我们继续学习二叉树的知识 2.5 二叉树的存储结构 二叉树一般可以使用两种数据结构&#xff0c;一种顺序…

AI绘画模型之:UNet、Imagen 与 DeepFloyd IF

重磅推荐专栏: 《大模型AIGC》 《课程大纲》 《知识星球》 本专栏致力于探索和讨论当今最前沿的技术趋势和应用领域,包括但不限于ChatGPT和Stable Diffusion等。我们将深入研究大型模型的开发和应用,以及与之相关的人工智能生成内容(AIGC)技术。通过深入的技术解析和实践经…

2024西安铁一中集训DAY27 ---- 模拟赛((bfs,dp) + 整体二分 + 线段树合并 + (扫描线 + 线段树))

文章目录 前言时间安排及成绩题解A. 倒水&#xff08;bfs dp&#xff09;B. 让他们连通&#xff08;整体二分 按秩合并并查集 / kruskal重构树&#xff09;C. 通信网络&#xff08;线段树合并 二分&#xff09;D. 3SUM&#xff08;扫描线 线段树&#xff09; 前言 T1没做出…

基于STM32瑞士军刀--【FreeRTOS开发】学习笔记(四)|| 同步 / 互斥 / 通信方法简介

本文概念部分粘贴自韦东山老师同步与互斥。 韦东山老师《FreeRTOS入门与工程实践(基于DshanMCU-103)》书籍获取 同步&互斥概念 一句话理解同步与互斥&#xff1a;我等你用完厕所&#xff0c;我再用厕所。 什么叫同步&#xff1f;就是&#xff1a;哎哎哎&#xff0c;我正在…

Linux中进程通信之信号

信号 信号通信&#xff0c;其实就是内核向用户空间进程发送信号&#xff0c;只有内核才能发信号&#xff0c;用户空间进程不能发送信号。 关于信号指令的查看&#xff1a;kill -l 例如我们之前使用的kill -9 pid用于杀死一个进程 使用一个死循环 成功发送kill -9指令&#x…

键盘输入数据的过程

当我们在键盘中按下按键的时候&#xff0c;键盘会向我们的 CPU 发送硬件中断&#xff08;也就是给 CPU 特定的针脚发送信号&#xff09;&#xff0c;该硬件中断有着自己的中断号&#xff0c;然后 CPU 内的寄存器就会记录下该中断号&#xff0c;然后会在操作系统中的中断向量表&…