当前位置: 首页 > news >正文

Linux-进程信号

目录

  • 概念
  • 信号产生
  • 信号注册
  • 信号注销
  • 信号处理
    • 实例
  • 信号的基本应用

概念

进程信号:
概念:信号就是软件中断。信号就是用于向进程通知某个事件的产生,打断进程当前操作,去处理这个事件。
linux中信号的种类:使用kill -l命令查看所有信号–62种
1~31:非可靠信号(有可能会造成事件丢失)
34~64:可靠信号(不会丢失事件)
信号的生命周期:产生信号->在进程pcb中注册信号->注销信号->处理信号

信号产生

信号的产生
硬件产生
ctrl+c 退出进程
ctrl+| 退出进程
ctrl+z 暂停进程,此时ps -aux | grep 进程名称 可以看到进程处于停止状态。jobs:查看作业,通过fg 作业id:让停止作业继续运行
软件产生
kill命令发送信号给指定进程 kill -signum pid
kill命令杀死一个进程的原理:默认给进程发送了终止信号
int kill(pid_t pid, int sig); 给pid进程发送sig信号
int raise(int sig); – 给进程自身发送一个指定的信号
unsigned int alarm(unsigned int seconds);
–sec秒之后给进程自身发送一个时钟信号–SIGALRM
void abort(void); – 给进程自身发送一个SIGABRT信号
int sigqueue(pid_t pid, int sig, const union sigval value);
给一个进程发送信号的同时携带一个数据过去

信号注册

信号的注册
注册:在进程中注册一个信号让进程直到自己收到了某个信号
修改pending位图(用于标记是否收到了某个信号),添加一个信号信息节点
非可靠:如果信号没有被注册,则注册;否则什么都不做。链表中不会出现相同非可靠信号信息节点
可靠:不管信号是否注册,都会注册一下。链表中有可能又多个相同的信号信息节点。
sigqueue-双向链表 – 表示有多少信号

信号注销

信号的注销
注销:将信号信息进程pcb中一处(修改位图,删除节点)
非可靠:删除节点,修改位图为0
可靠:删除一个信号节点,检查链表中是否还有相同节点,没有则修改位图

信号处理

信号的处理
处理:信号的处理也叫信号的递达,实际上就是打断进程当前的操作,去执行进程的对应信号处理函数。
信号的处理方式:
1.默认处理方式
2.忽略处理方式
3.自定义处理方式–用户自己定义信号的处理回调函数
typedef void(*sighandler_t)(int);
sighandler_t signal(int signum, sighandler_t handler);
signum:信号值-表示要修改哪个信号的处理方式
handler:新的信号处理方式
SIG_DEL-默认;SIG_IGN-忽略;自定义函数的名称
返回值:成功则返回当前信号原来的处理方式

自定义处理方式的信号捕捉流程
信号是从程序运行从内核态返回用户态之前处理的。
程序处理信号时在内核态,当遇到回调函数自定义时,因为自定义函数是用户自己写的,返回用户态执行,完成后如果还有信号则继续返回内核态进行,当信号处理完成后返回用户态主流程。
程序运行可以通过中断,异常,系统调用从用户态运行切换到内核态

#include<stdio.h>
#include<unistd.h>
#include<stdlib.h>
#include<signal.h>void sigcb(int signo)
{printf("recv signal:%d\n", signo);printf("时间到了\n");alarm(3);
}
int main(int argc, char *argv[])
{signal(信号,处理方式)signal(SIGALRM, sigcb);kill(进程ID,信号值)//kill(getpid(), SIGINT);//raise(SIGINT);alarm(3);while(1){printf("-----\n");sleep(1);}return 0;
}

阻塞:信号的阻塞–阻止信号被递达
一个信号被阻塞后,依然收到这个信号会注册,但是暂时不被处理
pcb中有pending位图-未决信号结合;还有阻塞信号集合
如果要阻塞一个信号,就是在进程的阻塞信号集合中标记这个信号
具体操作:
int sigprocmask(int how, const sigset_t *set, sigset_t *oldset);
how:操作类型
SIG_BLOCK-- 阻塞set集合的信号 block = block | set
SIG_UNBLOCK – 将set集合中的信号解除阻塞 block &= ~set
SIG_SETMASK–将set集合中的信号设置为阻塞集合的信号block=set
返回值:成功返回0;失败返回-1

实例

先自定义特定信号的处理方式–做打印收到了哪个信号 signal
将所有信号阻塞 sigprocmask block
让程序运行停下来,在这期间给进程发送信号getchar
解除这些信号的阻塞,查看信号处理结果 sigprocmask unblock

#include<stdio.h>
#include<unistd.h>
#include<stdlib.h>
#include<signal.h>void sigcb(int signo)
{printf("recv signal:%d\n", signo);
}
int main(int argc, char *argv[])
{signal(SIGINT, sigcb);signal(40, sigcb);sigset_t set;sigemptyset(&set);sigfillset(&set);//zu sesigprocmask(SIG_BLOCK, &set, NULL);printf("回车后,继续运行\n");getchar();printf("解除信号阻塞,查看结果\n");sigprocmask(SIG_UNBLOCK, &set, NULL);while(1){sleep(1);}return 0;
}

通过实例,按三次ctrl c,输入四次kill -40命令。最终结果显示ctrl c一次,kill -40四次。
因为ctrl c是SIGINT,在前31属于不可靠信号,因此同时发送阻塞只保留一个。kill -40属于可靠信号,每次发送都保留,等阻塞结束后依次回调。

两个比较特殊的信号:SIGKILL/SIGSTOP 这两个信号不可被阻塞,不可被自定义,不可被忽略,说白了就是无法修改处理方式。

信号的基本应用

信号的基本应用:
SIGCHLD信号:一个子进程退出后,给父进程发送的子进程状态改变信号
但是SIGCHLD默认处理方式就是什么都不做
要避免僵尸进程,则需要在父进程中wait阻塞等待。
如果不想阻塞等待,则可以使用信号来解决
自定义SIGCHLD信号的处理方式,在回调函数中调用waitpid接口
SIGCHLD是一个非可靠信号–意味着多个子进程同时退出,有可能丢失事件
signal(SIGCHLD,SIG_IGN);–显式忽略

#include<stdio.h>
#include<unistd.h>
#include<stdlib.h>
#include<signal.h>
#include<sys/wait.h>void sigcb(int no)
{printf("son fork exit\n");waitpid(-1, NULL, 0);
}
int main(int argc, char *argv[])
{signal(SIGCHLD, sigcb);pid_t pid = fork();if(pid == 0){ sleep(3);exit(0);}while(1){printf("------\n");sleep(1);}return 0;
}

waitpid();有子进程退出返回值>0;没有子进程退出返回值==0;出错<0
wait(-1, NULL, WNOHANG)
-1:等待任意一个子进程的退出
NULL:返回值不关心
WNOHANG:将接口设置为非阻塞

SIGPIPE:管道所有读端被关闭则write出发异常对应的信号
SIGPIPE信号默认处理方式就是退出进程,若不想退出则需要自定义/忽略

#include<stdio.h>
#include<unistd.h>
#include<stdlib.h>
#include<errno.h>
#include<fcntl.h>
#include<sys/stat.h>
#include<string.h>
#include<signal.h>void sigcb(int no)
{printf("all pipe read is close\n");
}
int main(int argc, char *argv[])
{
//更换信号处理方式signal(SIGPIPE, sigcb);umask(0);char *fifo_name = "./test.fifo";int ret = mkfifo(fifo_name, 0664);if(ret < 0 && errno != EEXIST){perror("mkfifo error");return -1;}int fd = open(fifo_name, O_WRONLY);if(fd < 0){perror("open error");return -1;}while(1){char buf[1024] = {0};scanf("%s", buf);int ret = write(fd, buf, strlen(buf));if(ret < 0){perror("write error");return -1;}}close(fd);return 0;
}

关键字:volatile
功能:保持内存可见性–让cpu每次访问变量的时候都从内存中重新获取数据
目的:防止编译器过度优化

可重入函数与不可重入函数:
函数的重入:在不同的执行流程中(main、signal)同时进入一个函数进行执行。
不可重入:一个函数重入后,有可能会造成数据二义或者逻辑混乱。
可重入:一个函数重入后,不会出现问题。
函数是否可重入的重点:一个函数中是否对全局数据进行不受保护的非原子操作(是-不可重入)

//不可重入
#include<stdio.h>
#include<unistd.h>
#include<stdlib.h>
#include<signal.h>int a = 0, b = 0;int test()
{a++;sleeo(1);b++;printf("%d + %d = %d\n",a, b, a+b);
}void sigcb(int no)
{test();
}int main(int argc, char *argv[])
{signal(SIGINT, sigcb);test();return 0;
}

相关文章:

Linux-进程信号

目录 概念信号产生信号注册信号注销信号处理实例 信号的基本应用 概念 进程信号&#xff1a; 概念&#xff1a;信号就是软件中断。信号就是用于向进程通知某个事件的产生&#xff0c;打断进程当前操作&#xff0c;去处理这个事件。 linux中信号的种类&#xff1a;使用kill -l命…...

Linux服务器安装jdk

背景: 安装JDK是我们java程序在服务器运行的必要条件,下面描述几个简单的命令就可再服务器上成功安装jdk 命令总览: yum update -y yum list | grep jdk yum -y install java-1.8.0-openjdk java -version 1.查看可安装版本 yum list | grep jdk 2.如果查不到可先进行 yum upd…...

基于 HBase Phoenix 构建实时数仓(2)—— HBase 完全分布式安装

目录 一、开启 HDFS 机柜感知 1. 增加 core-site.xml 配置项 2. 创建机柜感知脚本 3. 创建机柜配置信息文件 4. 分发相关文件到其它节点 5. 重启 HDFS 使机柜感知生效 二、主机规划 三、安装配置 HBase 完全分布式集群 1. 在所有节点上配置环境变量 2. 解压、配置环境…...

equals()与==的区别

在Java中 可以对基本类型进行比较,比较的是值是否相等 也可以对引用类型(对象)进行比较,比较的是引用变量所指向的空间地址 public static void main(String[] args) {int a 10;int b 10;System.out.println(ab);//true// 基本类型比较,比较值是否相等String s1 new Stri…...

什么是数据采集与监视控制系统(SCADA)?

SCADA数据采集是一种用于监控和控制工业过程的系统。它可以实时从现场设备获得数据并将其传输到中央计算机&#xff0c;以便进行监控和控制。SCADA数据采集系统通常使用传感器、仪表和控制器收集各种类型的数据&#xff0c;例如温度、压力、流量等&#xff0c;然后将这些数据汇…...

基于SpringBoot+Vue+ElementUI+Mybatis前后端分离管理系统超详细教程(五)——多条件搜索并分页展示

前后端数据交互 书接上文&#xff0c;我们上节课通过前后端数据交互实现了分页查询和单条件搜索分页查询的功能&#xff0c;最后留了个小尾巴&#xff0c;就是把其他两个搜索条件&#xff08;email,address&#xff09;也加进来&#xff0c;实现多条件搜索并分页展示。这节课我…...

鸿蒙实战开发Camera组件:【相机】

相机组件支持相机业务的开发&#xff0c;开发者可以通过已开放的接口实现相机硬件的访问、操作和新功能开发&#xff0c;最常见的操作如&#xff1a;预览、拍照和录像等。 基本概念 拍照 此功能用于拍摄采集照片。 预览 此功能用于在开启相机后&#xff0c;在缓冲区内重复采集…...

政安晨:【深度学习处理实践】(三)—— 处理时间序列的数据准备

在深度学习中&#xff0c;对时间序列的处理主要涉及到以下几个方面&#xff1a; 序列建模&#xff1a;深度学习可以用于对时间序列进行建模。常用的模型包括循环神经网络&#xff08;Recurrent Neural Networks, RNN&#xff09;和长短期记忆网络&#xff08;Long Short-Term M…...

PCL不同格式点云读取速度(Binary和ASCII )

首先说明一点&#xff1a;Binary(二进制)格式点云文件进行读取时要比Ascll码格式点云读取时要快的多&#xff0c;尤其是对于大型的点云文件&#xff0c;如几百万、甚至几千万个点云的情况下。 今天遇到了一种情况&#xff0c;在写项目的时候进行点云读取&#xff0c;读取的时候…...

Neo4J图数据库入门示例

前言 - Neo4j和MySQL的区别 Neo4j 和 MySQL 是两种不同类型的数据库&#xff0c;它们在数据模型、用途、性能和查询语言等方面有着显著的区别。以下是它们的主要区别&#xff1a; 数据模型&#xff1a; Neo4j 是一种图数据库&#xff0c;它使用图数据模型来存储和查询数据。在…...

牛客每日一题之 二维前缀和

题目介绍&#xff1a; 题目链接&#xff1a;【模板】二维前缀和_牛客题霸_牛客网 先举两个简单的例子&#xff0c;来帮大家理解题目&#xff0c;注意理解二维前缀和要先要一维前缀和的基础&#xff0c;不了解的可以看我上一篇博客。 若x11&#xff0c;y11, x23, y2 3,这是要…...

动态规划 Leetcode 70 爬楼梯

爬楼梯 Leetcode 70 学习记录自代码随想录 假设你正在爬楼梯。需要 n 阶你才能到达楼顶。 每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢&#xff1f; 示例 1&#xff1a; 输入&#xff1a;n 2 输出&#xff1a;2 解释&#xff1a;有两种方法可以爬到…...

(未解决)macOS matplotlib 中文是方框

reference&#xff1a; Mac OS系统下实现python matplotlib包绘图显示中文(亲测有效)_mac plt 中文值-CSDN博客 module ‘matplotlib.font_manager‘ has no attribute ‘_rebuild‘解决方法_font_manager未解析-CSDN博客 # 问题描述&#xff08;笑死 显而易见 # solve 找到…...

深入探讨C#中的递归算法

一、什么是递归算法&#xff1f; 递归是指一个函数或方法在执行过程中调用自身的情况。递归算法是编程中常见的一种解决问题的方法。它将一个问题分解成一个或多个与原问题相似但规模更小的子问题&#xff0c;然后通过解决这些子问题来解决原问题。递归算法通常用于解决重复性的…...

三款顶级开源RAG (检索增强生成)工具:Verba、Unstructured 和 Neum

三款顶级开源RAG (检索增强生成)工具&#xff1a;Verba、Unstructured 和 Neum 概述 随着企业对话式数据处理需求的提升&#xff0c;面临的挑战是数据隐私性和缺乏企业级解决方案。虽然类似LangChain能在短时间内构建RAG应用&#xff0c;但忽视了文档解析、多来源数据ETL、批量…...

VC++、MFC中操作excel时,CRange中get_EntireRow()和get_EntireColumn()函数的用法及区别是什么?

在VC和MFC中操作Excel时&#xff0c;通过COM接口与Excel交互时&#xff0c;CRange 对象&#xff08;或更准确地说是 Excel::Range 对象&#xff09;代表一个单元格范围。CRange 类提供了一系列方法来获取或操作这个范围内的单元格。其中&#xff0c;get_EntireRow() 和 get_Ent…...

npm 操作报错记录1- uninstall 卸载失效

npm 操作报错记录1- uninstall 卸载失效 1、问题描述 安装了包 vue/cli-plugin-eslint4.5.0 vue/eslint-config-prettier9.0.0 但是没有使用 -d &#xff0c;所以想重新安装&#xff0c;就使用 uninstall 命令卸载&#xff0c;结果卸载了没反应&#xff0c;也没有报错&#xf…...

openCV保存图像

保存图像 //保存为png透明通道vector<int>opts;opts.push_back(IMWRITE_PAM_FORMAT_RGB_ALPHA);imwrite("D:/img_bgra.png", img, opts);//保存为单通道灰度图像img cv::imread(imagePath.toStdString(), IMREAD_GRAYSCALE);vector<int> opts_gray;opts…...

mac 配置.bash_profile不生效问题

1、问题描述 mac系统中配置了环境变量只能在当前终端生效&#xff0c;切换了终端就无效了&#xff0c;查了下问题所在。mac系统会预装一个终极shell - zsh&#xff0c;环境变量读取在 .zshrc 文件下。 2、解决方案 1、切换终端到bash 切换终端到bash chsh -s /bin/bash 切换终端…...

【Cesium for Supermap】S3MTiles图层box裁剪

效果图&#xff1a; 代码&#xff1a; let viewer new Cesium.Viewer(cesiumContainer);// 添加SuperMap iServer发布的S3M缓存服务let promise viewer.scene.addS3MTilesLayerByScp("http://www.supermapol.com/realspace/services/3D-BIMbuilding/rest/realspace/data…...

高频面试之3Zookeeper

高频面试之3Zookeeper 文章目录 高频面试之3Zookeeper3.1 常用命令3.2 选举机制3.3 Zookeeper符合法则中哪两个&#xff1f;3.4 Zookeeper脑裂3.5 Zookeeper用来干嘛了 3.1 常用命令 ls、get、create、delete、deleteall3.2 选举机制 半数机制&#xff08;过半机制&#xff0…...

【SQL学习笔记1】增删改查+多表连接全解析(内附SQL免费在线练习工具)

可以使用Sqliteviz这个网站免费编写sql语句&#xff0c;它能够让用户直接在浏览器内练习SQL的语法&#xff0c;不需要安装任何软件。 链接如下&#xff1a; sqliteviz 注意&#xff1a; 在转写SQL语法时&#xff0c;关键字之间有一个特定的顺序&#xff0c;这个顺序会影响到…...

工业自动化时代的精准装配革新:迁移科技3D视觉系统如何重塑机器人定位装配

AI3D视觉的工业赋能者 迁移科技成立于2017年&#xff0c;作为行业领先的3D工业相机及视觉系统供应商&#xff0c;累计完成数亿元融资。其核心技术覆盖硬件设计、算法优化及软件集成&#xff0c;通过稳定、易用、高回报的AI3D视觉系统&#xff0c;为汽车、新能源、金属制造等行…...

IoT/HCIP实验-3/LiteOS操作系统内核实验(任务、内存、信号量、CMSIS..)

文章目录 概述HelloWorld 工程C/C配置编译器主配置Makefile脚本烧录器主配置运行结果程序调用栈 任务管理实验实验结果osal 系统适配层osal_task_create 其他实验实验源码内存管理实验互斥锁实验信号量实验 CMISIS接口实验还是得JlINKCMSIS 简介LiteOS->CMSIS任务间消息交互…...

实现弹窗随键盘上移居中

实现弹窗随键盘上移的核心思路 在Android中&#xff0c;可以通过监听键盘的显示和隐藏事件&#xff0c;动态调整弹窗的位置。关键点在于获取键盘高度&#xff0c;并计算剩余屏幕空间以重新定位弹窗。 // 在Activity或Fragment中设置键盘监听 val rootView findViewById<V…...

html-<abbr> 缩写或首字母缩略词

定义与作用 <abbr> 标签用于表示缩写或首字母缩略词&#xff0c;它可以帮助用户更好地理解缩写的含义&#xff0c;尤其是对于那些不熟悉该缩写的用户。 title 属性的内容提供了缩写的详细说明。当用户将鼠标悬停在缩写上时&#xff0c;会显示一个提示框。 示例&#x…...

html css js网页制作成品——HTML+CSS榴莲商城网页设计(4页)附源码

目录 一、&#x1f468;‍&#x1f393;网站题目 二、✍️网站描述 三、&#x1f4da;网站介绍 四、&#x1f310;网站效果 五、&#x1fa93; 代码实现 &#x1f9f1;HTML 六、&#x1f947; 如何让学习不再盲目 七、&#x1f381;更多干货 一、&#x1f468;‍&#x1f…...

CVE-2020-17519源码分析与漏洞复现(Flink 任意文件读取)

漏洞概览 漏洞名称&#xff1a;Apache Flink REST API 任意文件读取漏洞CVE编号&#xff1a;CVE-2020-17519CVSS评分&#xff1a;7.5影响版本&#xff1a;Apache Flink 1.11.0、1.11.1、1.11.2修复版本&#xff1a;≥ 1.11.3 或 ≥ 1.12.0漏洞类型&#xff1a;路径遍历&#x…...

使用LangGraph和LangSmith构建多智能体人工智能系统

现在&#xff0c;通过组合几个较小的子智能体来创建一个强大的人工智能智能体正成为一种趋势。但这也带来了一些挑战&#xff0c;比如减少幻觉、管理对话流程、在测试期间留意智能体的工作方式、允许人工介入以及评估其性能。你需要进行大量的反复试验。 在这篇博客〔原作者&a…...

【C++特殊工具与技术】优化内存分配(一):C++中的内存分配

目录 一、C 内存的基本概念​ 1.1 内存的物理与逻辑结构​ 1.2 C 程序的内存区域划分​ 二、栈内存分配​ 2.1 栈内存的特点​ 2.2 栈内存分配示例​ 三、堆内存分配​ 3.1 new和delete操作符​ 4.2 内存泄漏与悬空指针问题​ 4.3 new和delete的重载​ 四、智能指针…...