Linux信号——信号的产生(1)

news2025/4/3 5:51:08

注:信号vs信号量:两者没有任何关系!

信号是什么?

Linux系统提供的,让用户(进程)给其他进程发送异步信息的一种方式。

进程看待信号的方式:

1.信号在没有发生的时候,进程已经知道信号发生时该如何处理。

2.进程能够认识进程,很早之前,有人给进程中设置了识别特定信号的方式。

3.信号到来的时候,进程正在处理更重要的事情,进程暂时不能处理到来的信号,进程必须暂时要将到来的信号进行临时保存。

4.信号到了,可以不立即处理,可以在合适的时间处理。

5.信号是随时产生的,进程无法准确预料,所以信号是异步发送的。

为什么要有信号?

系统要求进程要有随时响应外部信号的能力,随后做出反应。

信号的具体知识

以这个时间轴进行学习
在这里插入图片描述

信号的产生

常见信号

数组和名字都可以标识信号,名字其实就是宏。
使用kill命令查看信号。
在这里插入图片描述
1-31为常用信号,右下的红框中是实时信号。
没有0,没有32,33 信号,共62个信号

信号的处理的方式——signal

a. 默认动作
b. 自定义处理信号——捕捉
c. 忽略了信号——是处理了信号吗?是的,处理方式就是忽略。
实际执行信号的处理动作称之为信号的递达,也就是以上三种方式。

signal函数

#include <signal.h>

typedef void (*sighandler_t)(int);
sighandler_t signal(int signum, sighandler_t handler);

参数说明:
signum:信号编号(如 SIGINT、SIGTERM)。
handler:信号处理函数,可以是:
SIG_DFL:恢复默认行为。
SIG_IGN:忽略信号。
自定义函数指针:用户定义的处理函数。

返回值:(类型函数指针)
成功时返回之前的处理函数的地址。
失败时返回 SIG_ERR。

产生信号的第一种方式:kill命令

kill -9 进程pid :发送一个信号,杀死一个进程

#include<iostream>
#include<unistd.h>
#include<sys/types.h>
#include<signal.h>
int main()
{
    while(true)
    {
        std::cout << "I am activing...,pid:" << getpid() << std::endl;
        sleep(1);
    }
    return 0;
}

结果:
使用命令kill -9 1121788
在这里插入图片描述
进程被杀死。


kill -2 进程pid :发送一个信号,默认行为是使进程自己终止。

1.默认行为——进程自己终止

#include<iostream>
#include<unistd.h>
#include<sys/types.h>
#include<signal.h>
int main()
{
    while(true)
    {
        std::cout << "I am activing...,pid:" << getpid() << std::endl;
        sleep(1);
    }
    return 0;
}

结果:
在运行的进程中使用kill -2 1121490
在这里插入图片描述
进程自己终止。

2.自定义处理信号——捕捉

例子:

#include<iostream>
#include<unistd.h>
#include<sys/types.h>
#include<signal.h>
void handler(int signo)
{
    std::cout << "get a sig, number is: "<< signo << std::endl;
}
int main()
{
    //signal调用完了,handler方法会被立即执行吗?不会,只是设置对应信号的处理方法。
    //未来我们收到对应的信号才执行handler方法。
    //未来进程如果一直没有收到SIGINT,handler也就永远不会被调用。
    signal(SIGINT,handler);//handler(SIGINT)
    while(true)
    {
        std::cout << "I am activing...,pid:" << getpid() << std::endl;
        sleep(1);
    }
    return 0;
}

结果:
在运行的进程中使用kill -2 1120892
在这里插入图片描述
默认行为被更改成其他方法。

3.忽略信号

#include<iostream>
#include<unistd.h>
#include<sys/types.h>
#include<signal.h>
int main()
{
    signal(SIGINT,SIG_IGN);//ignore忽略
    while(true)
    {
        std::cout << "I am activing...,pid:" << getpid() << std::endl;
        sleep(1);
    }
    return 0;
}

结果:
在运行的进程中使用kill -2 1120892
在这里插入图片描述
进程无任何反应——这条信号被忽略。

产生信号的第二种方式:键盘产生信号

Ctrl + c 被操作系统解释成2号信号
Ctrl + \ 被操作系统解释成3号信号

产生信号的第三种方式:系统调用

kill 系统调用函数

对任意进程发送任意信号。

#include <sys/types.h>
#include <signal.h>

int kill(pid_t pid, int sig);

参数说明:
pid目标进程的进程 ID,具体行为取决于其取值:
>0:发送信号给 PID 为 pid 的进程。
=0:发送信号给当前进程组内的所有进程。

sig:要发送的信号编号(如 SIGTERM、SIGKILL)。

返回值:
成功返回 0,失败返回 -1,并设置 errno 。

例子:自定义mykill函数

#include<iostream>
#include<unistd.h>
#include<sys/types.h>
#include<signal.h>
#include<errno.h>
#include<string.h>
using namespace std;

//mykill -9 pid
int main(int argc,char* argv[])
{
    if(argc != 3)
    {
        cout << "Usage: " << argv[0] << " -signumber pid" << endl;
        return 1;
    }

    int signumber = stoi(argv[1]+1);
    int pid = stoi(argv[2]);

    int n = kill(pid, signumber);
    if(n < 0)
    {
        cerr << "kill error, " << strerror(errno) << endl;
    }
    return 0;
}


raise 系统调用函数

对当前进程发送任意信号。

#include <signal.h>

int raise(int sig);  // 向当前进程发送信号 sig

参数说明:
sig: 信号编号(如 SIGINT、SIGTERM)。
返回值:
成功返回 0,失败返回非 0。

abort系统调用函数

对当前进程发送6号信号。

#include <stdlib.h>  // 必须包含的头文件

void abort(void);

**参数说明:**无(void)。
**返回值:**无返回值(void)。

产生信号的第四种方式:软件条件

alarm函数
对当前进程等待 seconds 秒后发送14号信号。

#include <unistd.h>

unsigned int alarm(unsigned int seconds);

参数说明: seconds – 定时器的时间(秒)。若为 0,表示取消之前设置的定时器。
返回值:
返回之前尚未触发的定时器的剩余秒数。
若之前没有定时器,返回 0。

例子: 向当前进程5秒后发送14号信号,终止进程。

int main()
{
    alarm(5);//响一次

    int cnt = 0;
    while(true)
    {
        sleep(1);
        cout<< "cnt: "<< cnt++ << endl;
    }
    return 0;
}

结果: 向进程发送了14号信号,终止进程
在这里插入图片描述
注:闹钟只响一次。

例: 关于alarm的返回值

#include<iostream>
#include<unistd.h>
#include<sys/types.h>
#include<signal.h>
using namespace std;

int g_cnt = 0;
int ret = 0;

void handler(int sig)
{
    std::cout << "get a sig: "<< sig <<" g_cnt: "<< g_cnt <<endl;
    int n = alarm(2);
    cout<<"剩余时间:"<< n <<endl;
}

int main()
{
    signal( 2 ,handler);

    alarm(50);//响一次

    int cnt = 0;
    while(true)
    {
        sleep(1);
        cout<< "cnt: "<< cnt++ << endl;
    }
    return 0;
}

结果: 在 cnt:3 时按下 Ctrl + C
在这里插入图片描述
这时获取alarm的返回值是剩余时间。

产生信号的第五种方式:异常

  1. 除0错误
    例子:
#include<iostream>
#include<unistd.h>

int main()
{
    int a = 10;
    a = a/0;

    while(true) sleep(1);
    return 0;

}

出现除0错误。
结果:发送8号信号(SIGFPE)
在这里插入图片描述

  1. 野指针问题
    例子:
#include<iostream>
#include<unistd.h>

int main()
{
    int *p = nullptr;
   *p = 100;//野指针

    while(true) sleep(1);
    return 0;

}

结果:发送11号信号(SIGEGV)
在这里插入图片描述

关于信号产生的各种情况的理解

信号保存在进程的PCB中,且以位图的方式保存在PCB中。
在PCB中以 uint32_t pending 变量进行保存。在这里插入图片描述
给进程发送信号,其实就是写入信号。向进程PCB中写入信号数据,PCB是内核数据结构,只有操作系统有权限写入,若用户想写入,操作系统提供系统调用供用户使用。
所以以上的信号产生的5种方式,实际上最终都是交给操作系统进行最后向进程写入信号的操作。

对于异常问题的解释

  1. 除0错误
    在这里插入图片描述
  2. 野指针
    在这里插入图片描述

总结

在这里插入图片描述

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

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

相关文章

【机器学习】——机器学习思考总结

摘要 这篇文章深入探讨了机器学习中的数据相关问题&#xff0c;重点分析了神经网络&#xff08;DNN&#xff09;的学习机制&#xff0c;包括层级特征提取、非线性激活函数、反向传播和梯度下降等关键机制。同时&#xff0c;文章还讨论了数据集大小的标准、机器学习训练数据量的…

JMeter进行分布式压测

从机&#xff1a; 1、确认防火墙是否关闭&#xff1b; 2、打开网络设置&#xff0c;关闭多余端口&#xff1b;&#xff08;避免远程访问不到&#xff09; 3、打开JMeter/bin 目录底下的jmeter.properties&#xff1b; remove_hosts设置当前访问地址&#xff0c;192.XXXXX&…

快速入手-基于Django-rest-framework的第三方认证插件(SimpleJWT)权限认证扩展返回用户等其他信息(十一)

1、修改serializer.py&#xff0c;增加自定义类 # 自定义用户登录token等返回信息 class MyTokenObtainPair(TokenObtainPairView): def post(self, request, *args, **kwargs): serializer self.get_serializer(datarequest.data) try: serializer.is_valid(raise_exceptio…

关于IP免实名的那些事

IP技术已成为个人与企业保护隐私、提升网络效率的重要工具。其核心原理是通过中介服务器转发用户请求&#xff0c;隐藏真实IP地址&#xff0c;从而实现匿名访问、突破地域限制等目标。而“免实名”代理IP的出现&#xff0c;进一步简化了使用流程&#xff0c;用户无需提交身份信…

【SQL性能优化】预编译SQL:从注入防御到性能飞跃

&#x1f525; 开篇&#xff1a;直面SQL的"阿喀琉斯之踵" 假设你正在开发电商系统&#x1f6d2;&#xff0c;当用户搜索商品时&#xff1a; -- 普通SQL拼接&#xff08;危险&#xff01;&#xff09; String sql "SELECT * FROM products WHERE name "…

SQL Server从安装到入门一文掌握应用能力。

本篇文章主要讲解,SQL Server的安装教程及入门使用的基础知识,通过本篇文章你可以快速掌握SQL Server的建库、建表、增加、查询、删除、修改等基本数据库操作能力。 作者:任聪聪 日期:2025年3月31日 一、SQL Server 介绍: SQL Server 是微软旗下的一款主流且优质的数据库…

力扣HOT100之矩阵:54. 螺旋矩阵

这道题之前在代码随想录里刷过类似的&#xff0c;还有印象&#xff0c;我就按照当初代码随想录的思路做了一下&#xff0c;结果怎么都做不对&#xff0c;因为按照代码随想录的边界条件设置&#xff0c;当行数和列数都为奇数时&#xff0c;最后一个元素无法被添加到数组中&#…

5.1 WPF路由事件以及文本样式

一、路由事件 WPF中存在一种路由事件&#xff08;routed event&#xff09;&#xff0c;该事件将发送到包含该控件所在层次的所有控件&#xff0c;如果不希望继续向更高的方向传递&#xff0c;只要设置e.Handled true即可。 这种从本控件-->父控件->父的父控件的事件&am…

Python数据可视化-第1章-数据可视化与matplotlib

环境 开发工具 VSCode库的版本 numpy1.26.4 matplotlib3.10.1 ipympl0.9.7教材 本书为《Python数据可视化》一书的配套内容&#xff0c;本章为第1章 数据可视化与matplotlib 本文主要介绍了什么是数据集可视化&#xff0c;数据可视化的目的&#xff0c;常见的数据可视化方式…

Flutter敏感词过滤实战:基于AC自动机的高效解决方案

Flutter敏感词过滤实战&#xff1a;基于AC自动机的高效解决方案 在社交、直播、论坛等UGC场景中&#xff0c;敏感词过滤是保障平台安全的关键防线。本文将深入解析基于AC自动机的Flutter敏感词过滤实现方案&#xff0c;通过原理剖析实战代码性能对比&#xff0c;带你打造毫秒级…

Odoo/OpenERP 和 psql 命令行的快速参考总结

Odoo/OpenERP 和 psql 命令行的快速参考总结 psql 命令行选项 选项意义-a从脚本中响应所有输入-A取消表数据输出的对齐模式-c <查询>仅运行一个简单的查询&#xff0c;然后退出-d <数据库名>指定连接的数据库名&#xff08;默认为当前登录用户名&#xff09;-e回显…

Vue中使用antd-table组件时,树形表格展开配置不生效-defaultExpandedRowKeys-默认展开配置不生效

defaultExpandedRowKeys属性 defaultExpandAllRows这个属性仅仅是用来设置默认值的,只在第一次渲染的时候起作用,后续再去改变,无法实现响应式 解决方案一 a-table表格添加key属性,当每次获取值时,动态改变key,以达到重新渲染的效果 <a-table:key="tableKey"…

VRRP交换机三层架构综合实验

题目要求&#xff1a; 1&#xff0c;内网Ip地址使用172.16.0.0/16分配 说明可以划分多个子网&#xff0c;图中有2个VLAN&#xff0c;可以根据VLAN划分 2&#xff0c;sw1和SW2之间互为备份 互为备份通常通过VRRP&#xff08;虚拟路由冗余协议&#xff09;来实现。VRRP会在两个…

基于卷积神经网络的眼疾识别系统,resnet50,efficentnet(pytorch框架,python代码)

更多图像分类、图像识别、目标检测、图像分割等项目可从主页查看 功能演示&#xff1a; 眼疾识别系统resnet50&#xff0c;efficentnet&#xff0c;卷积神经网络&#xff08;pytorch框架&#xff0c;python代码&#xff09;_哔哩哔哩_bilibili &#xff08;一&#xff09;简介…

基于srpingboot智慧校园管理服务平台的设计与实现(源码+文档+部署讲解)

技术范围&#xff1a;SpringBoot、Vue、SSM、HLMT、Jsp、PHP、Nodejs、Python、爬虫、数据可视化、小程序、安卓app、大数据、物联网、机器学习等设计与开发。 主要内容&#xff1a;免费功能设计、开题报告、任务书、中期检查PPT、系统功能实现、代码编写、论文编写和辅导、论…

【力扣hot100题】(026)合并两个有序链表

可以创建一个新链表记录答案&#xff1a; /*** Definition for singly-linked list.* struct ListNode {* int val;* ListNode *next;* ListNode() : val(0), next(nullptr) {}* ListNode(int x) : val(x), next(nullptr) {}* ListNode(int x, ListNode *…

TCP网络编程与多进程并发实践

一、引言 在网络编程中&#xff0c;TCP&#xff08;传输控制协议&#xff09;是一种面向连接的、可靠的、基于字节流的传输层通信协议。而多进程并发则是一种提高服务器处理能力的有效手段&#xff0c;允许服务器同时处理多个客户端的请求。本文将详细介绍如何使用 TCP 协议进…

visio导出pdf公式变形

情况描述导出为pdf后&#xff0c;mathtype写的公式就变形了 但是导出为png和jpg就是正常 解决方法就是 需要下载一个Adobe Acrobat

【学习笔记】计算机网络(六)

第6章应用层 文章目录 第6章应用层6.1 域名系统DNS6.1.1 域名系统概述6.1.2 互联网的域名结构6.1.3 域名服务器域名服务器的分区管理DNS 域名服务器的层次结构域名服务器的可靠性域名解析过程-两种查询方式DNS 高速缓存机制 6.2 文件传送协议6.2.1 FTP 概述6.2.2 FTP 的基本工作…

量子退火与机器学习(2):少量实验即可找到新材料,黑盒优化➕量子退火

使用量子退火和因子分解机设计新材料 这篇文章是东京大学的一位博士生的毕业论文中的主要贡献。 结合了黑盒优化和量子退火&#xff0c;是融合的非常好的一篇文章&#xff0c;在此分享给大家。 https://journals.aps.org/prresearch/abstract/10.1103/PhysRevResearch.2.0133…