【linux学习指南】初识Linux进程信号与使用

news2024/11/26 7:28:37

请添加图片描述

文章目录

  • 📝信号快速认识
    • 📶⽣活⻆度的信号
    • 📶 技术应⽤⻆度的信号
      • 🌉 前台进程(键盘)
      • 🌉⼀个系统函数
    • 📶信号概念
    • 📶查看信号
  • 🌠 信号处理
    • 🌉 忽略此信号
    • 🌉 执⾏该信号的默认处理动作。
    • 🌉 切换状态函数
  • 🚩总结


📝信号快速认识

📶⽣活⻆度的信号

  • 你在⽹上买了很多件商品,再等待不同商品快递的到来。但即便快递没有到来,你也知道快递来临时,你该怎么处理快递。也就是你能“识别快递”
  • 当快递员到了你楼下,你也收到快递到来的通知,但是你正在打游戏,需5min之后才能去取快递。那么在在这5min之内,你并没有下去去取快递,但是你是知道有快递到来了。也就是取快递的⾏为并不是⼀定要⽴即执⾏,可以理解成“在合适的时候去取”。
  • 在收到通知,再到你拿到快递期间,是有⼀个时间窗⼝的,在这段时间,你并没有拿到快递,但是你知道有⼀个快递已经来了。本质上是你“记住了有⼀个快递要去取”
  • 当你时间合适,顺利拿到快递之后,就要开始处理快递了。⽽处理快递⼀般⽅式有三种:
  • 1.执⾏默认动作(幸福的打开快递,使⽤商品)
  • 2.执⾏⾃定义动作(快递是零⻝,你要送给你你的⼥朋友)
    1. 忽略快递(快递拿上来之后,扔掉床头,继续开⼀把游戏)

快递到来的整个过程,对你来讲是异步的,你不能准确断定快递员什么时候给你打电话

基本结论

  1. 你怎么能识别信号呢?识别信号是内置的,进程识别信号,是内核程序员写的内置特性。
  2. 信号产⽣之后,你知道怎么处理吗?知道。如果信号没有产⽣,你知道怎么处理信号吗?知道。所以,信号的处理⽅法,在信号产⽣之前,已经准备好了。
  3. 处理信号,⽴即处理吗?我可能正在做优先级更⾼的事情,不会⽴即处理?什么时候?合适的时候。
  4. 信号到来|信号保存 |信号处理
  5. 怎么进⾏信号处理啊?a.默认b.忽略c.⾃定义,后续都叫做信号捕捉。
    在这里插入图片描述

📶 技术应⽤⻆度的信号

🌉 前台进程(键盘)

样例:
sig.cc:

#include <iostream>
#include <unistd.h>

int main()
{
    while(true)
    {
        std::cout<< "I am a process, I am wiat signal!" <<std::endl;
        sleep(1);
    }
    return 0;
}

Makefile:

BIN=sig
OBJS=$(SRCS:.cc=.o)
SRCS=$(shell ls *.cc)
CC=g++

$(BIN):$(OBJS)
	$(CC) -o $@ $^ -std=c++11

%.o:%.cc
	$(CC) -c $< -std=c++11

.PHONY:clean
clean:
	rm -f $(BIN) $(OBJS)

⽤⼾输⼊命令,在Shell下启动⼀个前台进程
⽤⼾按下程Ctrl+C
,这个键盘输⼊产⽣⼀个硬件中断,被OS获取,解释成信号,发送给⽬标前台进
前台进程因为收到信号,进⽽引起进程退出
在这里插入图片描述

🌉⼀个系统函数

指令:

man signal

而其实,ctrl+C的本质是向前台进程发送|SIGINT|2号信号,我们证明一下,这里需要引入一个系统调用函数

NAME
       signal - ANSI C signal handling

SYNOPSIS
       #include <signal.h>

       typedef void (*sighandler_t)(int);

       sighandler_t signal(int signum, sighandler_t handler);

参数说明:
signum:信号编号[后⾯解释,只需要知道是数字即可]
handler:函数指针,表⽰更改信号的处理动作,当收到对应的信号,就回调执⾏handler⽅法

在这里插入图片描述

代码:

#include <iostream>
#include <unistd.h>
#include <signal.h>

void handler(int signumber)
{
    std::cout<<"我是:"<<getpid() <<",我获得一个信号:"<< signumber <<std::endl;
}

int main()
{
    std::cout<<"我是进程: "<<getpid() <<std::endl;
    signal(SIGINT/*2*/, handler);
    while(true)
    {
        std::cout<<"I am a process, I am waiting signal!"<< std::endl;
        sleep(1);
    }
    return 0;
}

在这里插入图片描述
思考:

  • 这⾥进程为什么不退出?
  • 这个例⼦能说明哪些问题?信号处理,是⾃⼰处理
  • 请将⽣活例⼦和Ctrl-C 信号处理过程相结合,解释⼀下信号处理过程?进程就是你,
    操作系统就是快递员,信号就是快递,发信号的过程就类似给你打电

注意:

  1. 要注意的是,signal函数仅仅是设置了特定信号的捕捉⾏为处理⽅式,并不是直接调⽤处理动作。如果后续特定信号没有产⽣,设置的捕捉函数永远也不会被调⽤!!
  2. Ctrl-C 产⽣的信号只能发给前台进程。⼀个命令后⾯加个&可以放到后台运⾏,这样Shell不必等待进程结束就可以接受新的命令,启动新的进程。
  3. Shell可以同时运⾏⼀个前台进程和任意多个后台进程,只有前台进程才能接到像Ctrl-C这种控制键产⽣的信号。
  4. 前台进程在运⾏过程中⽤⼾随时可能按下Ctrl-C⽽产⽣⼀个信号,也就是说该进程的⽤⼾空间代码执⾏到任何地⽅都有可能收到SIGINT 信号⽽终⽌,所以信号相对于进程的控制流程来说是异步(Asynchronous)的。
  5. 可以渗透&和nohup

📶信号概念

信号是进程之间事件异步通知的⼀种⽅式,属于软中断。

📶查看信号

每个信号都有⼀个编号和⼀个宏定义名称,这些宏定义可以在signal.h中找到,例如其中有定义

#define SIGINT 2

在这里插入图片描述

在这里插入图片描述

编号34以上的是实时信号,本章只讨论编号34以下的信号,不讨论实时信号。这些信号各⾃在什么条件下产⽣,默认的处理动作是什么,在signal(7)中都有详细说明:

 man 7 signal

在这里插入图片描述

🌠 信号处理

(sigaction 函数稍后详细介绍),可选的处理动作有以下三种:

🌉 忽略此信号

#include <iostream>
#include <unistd.h>
#include <signal.h>

void handler(int signumber)
{
    std::cout<<"我是:"<<getpid() <<",我获得一个信号:"<< signumber <<std::endl;
}

int main()
{
    std::cout<<"我是进程: "<<getpid() <<std::endl;
    signal(SIGINT/*2*/, SIG_IGN);// 设置忽略信号的宏
 
    while(true)
    {
        std::cout<<"I am a process, I am waiting signal!"<< std::endl;
        sleep(1);
    }
    return 0;
}

在这里插入图片描述

🌉 执⾏该信号的默认处理动作。

default默认行为SIG_DFL

#include <iostream>
#include <unistd.h>
#include <signal.h>

void handler(int signumber)
{
    std::cout<<"我是:"<<getpid() <<",我获得一个信号:"<< signumber <<std::endl;
}

int main()
{
    std::cout<<"我是进程: "<<getpid() <<std::endl;
    // signal(SIGINT/*2*/, SIG_IGN);// 设置忽略信号的宏
    signal(SIGINT/*2*/, SIG_DFL);// 输⼊ctrl+c,进程退出,就是默认动作
 
 
    while(true)
    {
        std::cout<<"I am a process, I am waiting signal!"<< std::endl;
        sleep(1);
    }
    return 0;
}

在这里插入图片描述

🌉 切换状态函数

其实这里就是转到用户自定义的handler函数

提供⼀个信号处理函数,要求内核在处理该信号时切换到⽤⼾态执⾏这个处理函数,这种⽅式称为⾃定义捕捉(Catch)⼀个信号。

#include <signal.h>  
#include <stdio.h>  
#include <unistd.h>  

void signal_handler(int signum) {  
    // 自定义的信号处理函数  
    printf("Caught signal %d\n", signum);  
    // 在这里执行需要在用户态下运行的代码  
    // ...  
}  

int main() {  
    // 注册信号处理函数  
    signal(SIGINT, signal_handler);  

    printf("Press Ctrl+C to send SIGINT signal...\n");  
    while (1) {  
        // 等待信号到来  
        pause();  
    }  

    return 0;  
}

注意看源码:

/* Fake signal functions.  */

#define	SIG_ERR	 ((__sighandler_t) -1)	/* Error return.  */
#define	SIG_DFL	 ((__sighandler_t)  0)	/* Default action.  */
#define	SIG_IGN	 ((__sighandler_t)  1)	/* Ignore signal.  */
/* Type of a signal handler.  */
typedef void (*__sighandler_t) (int);

让我们来逐一分析:

  1. #define SIG_ERR ((__sighandler_t) -1): 这个宏定义了 SIG_ERR,它被赋值为 -1,类型为 __sighandler_t。这通常用作 signal() 函数的返回值,表示发生错误。

  2. #define SIG_DFL ((__sighandler_t) 0): 这个宏定义了 SIG_DFL,它被赋值为 0,类型为 __sighandler_t。这用于指定使用默认的信号处理函数。

  3. #define SIG_IGN ((__sighandler_t) 1): 这个宏定义了 SIG_IGN,它被赋值为 1,类型为 __sighandler_t。这用于指定忽略该信号。

其实SIG_DFLSIG_IGN就是把0,1强转为函数指针类型


🚩总结

请添加图片描述

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

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

相关文章

今天你学C++了吗?——C++中的类与对象(第二集)

♥♥♥~~~~~~欢迎光临知星小度博客空间~~~~~~♥♥♥ ♥♥♥零星地变得优秀~也能拼凑出星河~♥♥♥ ♥♥♥我们一起努力成为更好的自己~♥♥♥ ♥♥♥如果这一篇博客对你有帮助~别忘了点赞分享哦~♥♥♥ ♥♥♥如果有什么问题可以评论区留言或者私信我哦~♥♥♥ ✨✨✨✨✨✨ 个…

Anaconda3 2024 jupyter notebook 配置默认文件路径

我的版本如下&#xff1a; 第一步&#xff1a; 打开命令行anaconda prompt &#xff0c; 敲下面命令生成配置文件 jupyter notebook --generate-config 如下图&#xff1a; 修改配置jupyter_notebook_config.py 文件中搜索c.ServerApp.root_dir &#xff08; 对于 Anac…

【抓包专题】burpsuitProxifier小程序抓包

抓包系列文章 burpsuit&Proxifier&小程序抓包 抓包系列文章前言一、工具下载二、获取证书并安装到本地三、抓包测试 前言 抓包是进行渗透的第一步&#xff0c;包都抓不到&#xff0c;渗透就不要谈了&#xff0c;废话少说&#xff0c;开干 一、工具下载 Proxifier安装使…

springboot 异步 @Async 的日常使用及失效场景

文章目录 springboot 异步 Async 的日常使用引言一、Async 使用位置二、Async 使用三、注解 Async 失效的情况&#xff08;1&#xff09;调用同一个类中的异步方法&#xff08;内部调用&#xff09;&#xff08;2&#xff09;未使用 EnableAsync 注解&#xff08;3&#xff09;…

WebGIS技术汇总

WebGIS系统通常都围绕地图进行内容表达&#xff0c;但并不是有地图就一定是WebGIS&#xff0c;所以有必要讨论下基于Web的地图API分类及应用场景。 Web上的Map API主要分类如下几类&#xff1a; Charts&#xff1a;以D3.js&#xff0c;Echarts等为代表。LBS&#xff1a;以高德…

使用Vue3来实现一个倒计时器以及倒计时任务

本内容使用Vue3&#xff0c;以及element-plus辅助开发。 首先展示倒计时器的功能&#xff1a; 手动设置倒计时器的倒计时时间开始倒计时按钮暂停倒计时按钮重新开始倒计时按钮 其次展示倒计时任务管理界面功能&#xff1a; 创建倒计时任务选择任务并进行倒计时删除任务 目录 一…

VMware Workstation 虚拟机运行卡顿解决方案

前言 由于我们网站主力是模拟器多开&#xff0c;VMware虚拟机纯属我个人使用的经验&#xff0c;仅供参考。顺带一提&#xff1a;多开鸭的系统精简掉的是Hyper-V&#xff0c;跟VMware完全没有任何关系&#xff0c;Hyper-V跟雷电这些模拟器会冲突&#xff0c;但是移除之后不会影…

GitLab|应用部署

创建docker-compose.yaml文件 输入docker-compose配置 version: 3.8 services:gitlab:image: gitlab/gitlab-ce:15.11.2-ce.0restart: alwayscontainer_name: gitlab-ceprivileged: truehostname: 192.168.44.235environment:TZ: Asia/ShanghaiGITLAB_OMNIBUS_CONFIG: |exter…

ssm182在线作业管理系统的设计与实现+vue(论文+源码)_kaic

设计题目&#xff1a;在线作业管理系统的设计与实现 摘 要 网络技术和计算机技术发展至今&#xff0c;已经拥有了深厚的理论基础&#xff0c;并在现实中进行了充分运用&#xff0c;尤其是基于计算机运行的软件更是受到各界的关注。加上现在人们已经步入信息时代&#xff0c;所…

LeetCode-632. Smallest Range Covering Elements from K Lists [C++][Java]

目录 题目描述 解题思路 【C】 【Java】 LeetCode-632. Smallest Range Covering Elements from K Listshttps://leetcode.com/problems/smallest-range-covering-elements-from-k-lists/description/ 题目描述 You have k lists of sorted integers in non-decreasing o…

指针的奥秘:深入探索内存的秘密

前言 在计算机编程的广阔天地中&#xff0c;指针作为一种独特的数据类型&#xff0c;它不仅是C语言的核心&#xff0c;也是理解计算机内存管理的基石。指针的概念虽然强大&#xff0c;但对于初学者来说&#xff0c;它常常是学习过程中的一个难点。本文旨在揭开指针的神秘面纱&a…

⭐ Unity 资源管理解决方案:Addressable_ Demo演示

一、使用Addressable插件的好处&#xff1a; 1.自动管理依赖关系 2.方便资源卸载 3.自带整合好的资源管理界面 4.支持远程资源加载和热更新 二、使用步骤 安装组件 1.创建资源分组 2.将资源加入资源组 3.打包资源 4.加载资源 三种方式可以加载 using System.Collections…

红日靶场-4

环境搭建 我们这里会拿到三台主机&#xff0c;一台web主机&#xff0c;一台win7主机&#xff0c;一台DC主机 机器密码 WEB主机 ubuntu:ubuntu WIN7主机 douser:Dotest123 (DC)WIN2008主机 administrator:Test2008 登陆后需修改密码&#xff0c;我这里修改为1qazWSX 网络配…

使用八爪鱼爬虫抓取汽车网站数据,分析舆情数据

我是做汽车行业的&#xff0c;可以用八爪鱼爬虫抓取汽车之家和微博上的汽车文章内容&#xff0c;分析各种电动汽车口碑数据。 之前&#xff0c;我写过很多Python网络爬虫的案例&#xff0c;使用requests、selenium等技术采集数据&#xff0c;这次尝试去采集小米SU7在微博、汽车…

具有多个表盘、心率传感器、指南针和游戏的 DIY 智能手表

在此&#xff0c;我们将使用所学到的知识&#xff0c;结合使用硬件和软件组件从头开始创建自己的智能手表。在项目的这一部分&#xff0c;您将被指导完成组装硬件组件、设置软件以及配置智能手表的设置和功能的过程。到本项目结束时&#xff0c;您将拥有一款功能齐全的智能手表…

Django+Nginx+uwsgi网站Channels+redis+daphne多人在线聊天实现粘贴上传图片

在DjangoNginxuwsgi网站Channelsredisdaphne多人在线的基础上&#xff08;详见DjangoNginxuwsgi网站使用Channelsredisdaphne实现简单的多人在线聊天及消息存储功能-CSDN博客&#xff09;&#xff0c;实现在输入框粘贴或打开本地图片&#xff0c;上传到网站后返回图片路径&…

[ubuntu]编译共享内存读取出现read.c:(.text+0x1a): undefined reference to `shm_open‘问题解决方案

问题log /tmp/ccByifPx.o: In function main: read.c:(.text0x1a): undefined reference to shm_open read.c:(.text0xd9): undefined reference to shm_unlink collect2: error: ld returned 1 exit status 程序代码 #include <stdio.h> #include <stdlib.h> #…

Otter 安装流程

优质博文&#xff1a;IT-BLOG-CN 一、背景 随着公司的发展&#xff0c;订单库的数据目前已达到千万级别&#xff0c;需要进行分表分库&#xff0c;就需要对数据进行迁移&#xff0c;我们使用了otter&#xff0c;这里简单整理下&#xff0c;otter 的安装过程&#xff0c;希望对…

wsl2的Ubuntu18.04安装ros和anaconda

参考&#xff1a;超详细 WSL2 安装 ros 和 anaconda_wsl2安装anaconda-CSDN博客 一.安装ros 1. 更换系统源 输入 wget http://fishros.com/install -O fishros && . fishros 和上面的链接一样&#xff0c;依次输入5-2-1 2. 安装ros 输入 wget http://fishros.c…

鸿蒙NEXT开发案例:字数统计

【引言】 本文将通过一个具体的案例——“字数统计”组件&#xff0c;来探讨如何在鸿蒙NEXT框架下实现这一功能。此组件不仅能够统计用户输入文本中的汉字、中文标点、数字、以及英文字符的数量&#xff0c;还具有良好的用户界面设计&#xff0c;使用户能够直观地了解输入文本…