Linux編程:3、進程通信-信號

一、進程通信概述

(一)進程通信的目的

在企業開發中,一個項目常常需要多個進程共同協作,而這些進程之間需要進行通信(交換信息)以便協作。本章內容主要圍繞信號講解,其它進程通信的常用方式請期待后續文章的發布

(二)進程通信的常用方式

  1. 信號
  2. 信號量
  3. 匿名管道
  4. 命名管道
  5. 共享內存
  6. 消息隊列
  7. 本地套接字

二、信號的基本概念

(一)信號的定義

在 Linux 編程中,信號(Signal)是一種異步通信機制,用于通知進程系統中發生了某種事件。它類似于軟件中斷,可打斷進程的正常執行流,使其處理特定事件。

(二)信號的快速入門實例

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <signal.h>void signal_handler(int arg) {printf("Received signal: %d\n", arg);
}int main(void) {int count = 1;signal(SIGINT, signal_handler);while (1) {printf("working...%d\n", count++);sleep(1);}return 0;
}

程序啟動后,按下ctrl + c會向當前進程發送SIGINT信號,觸發signal_handler處理函數。?


三、信號的分類

這里我只顯示常用的,不常用的信號如果你們遇到了問一下AI就行了

(一)非實時信號(1-31)

  1. 特點:不支持排隊,可能造成信號丟失。

  2. 常見非實時信號

  3. 信號屬性值默認處理方式定義描述
    SIGHUP1Term用戶終端連接結束時發出
    SIGINT2Term鍵盤輸入Ctrl+c時發出,通知前臺進程
    SIGKILL9Term程序員使用kill -9指令發出
    SIGCHLD17Ign子進程結束時父進程收到的信號
    SIGSTOP19Stop停止進程執行(暫停不結束)
    SIGTSTP20Stop鍵盤按下Ctrl+Z時發出
  4. 處理方式

    • Term:終止進程
    • Ign:忽略信號
    • Core:終止進程并產生 core dump 文件
    • Stop:暫停進程
    • Continue:讓停止的進程繼續執行至

(二)實時信號(32-64)(不常用

  1. 特點:支持排隊,不會造成信號丟失。
  2. 范圍:從SIGRTMIN(34)到SIGRTMAX(64),如SIGRTMIN+1SIGRTMIN+2等。

四、信號的發送方式

(一)自動發送

例如在終端按下ctrl + c,會自動向前臺進程發送SIGINT信號至。

(二)使用 kill 系統調用

  1. 函數原型int kill(pid_t pid, int sig);
  2. 功能:向指定進程(pid)發送指定信號(sig),成功返回 0,失敗返回 - 1 至。
  3. 代碼:
    #include <stdio.h>
    #include <stdlib.h>
    #include <sys/types.h>
    #include <sys/wait.h>
    #include <unistd.h>
    int main(void)
    {pid_t pid = fork();if (pid < 0) {perror("fork failed.");exit(1);}if (pid == 0) {int count = 1;while (1) {printf("child process worked. %d\n", count++);sleep(1);}}else {int n;while (1) {printf("\nPlease select: 1)Stop child process 2)Continue child ""process 3)Killchild process\n");scanf("%d", &n);switch (n) {case 1:kill(pid, SIGSTOP);break;case 2:kill(pid, SIGCONT);break;case 3:kill(pid, SIGKILL);break;default:break;}if (n == 3) {int status;waitpid(pid, &status, 0);  // 等待子進程結束并回收子進程break;}}}return 0;
    }

(三)使用 kill 命令

  1. 本質:kill 命令的內部實現調用了 kill 系統調用。
  2. 示例kill -9 2483?相當于pid = 2483,調用了kill(2483, SIGKILL)函數

五、信號的處理方式

(一)signal 函數

這個函數不如sigaction安全,建議編程時盡量用sigaction,代碼演示在信號屏蔽之后

  1. 函數原型sighandler_t signal(int signum, sighandler_t handler);
  2. 參數
    • signum:除SIGKILLSIGSTOP外的任意信號
    • handler:可以是SIG_IGN(忽略信號)、SIG_DFL(恢復默認處理)或自定義處理函數指針
  3. 返回值:成功返回上一次的 handler,失敗返回SIG_ERR至。

(二)sigaction 函數

  1. 優勢:比signal更健壯。
  2. 函數原型int sigaction(int signum, const struct sigaction *act, struct sigaction *oldact);
  3. 結構體sigaction
    struct sigaction {void (*sa_handler)(int);void (*sa_sigaction)(int, siginfo_t *, void *);sigset_t sa_mask;int sa_flags;void (*sa_restorer)(void);
    };
  4. sa_flags常用選項
    • SA_RESTART:被信號打斷的系統調用自動重新發起
    • SA_NOCLDSTOP:子進程暫停 / 繼續時父進程不接收SIGCHLD
    • SA_SIGINFO:使用sa_sigaction作為處理函數至。

六、信號屏蔽字與信號集操作

(一)信號屏蔽字的處理

  1. 默認處理:當信號處理函數被調用時,內核自動將當前信號加入進程的信號屏蔽字,處理結束后恢復至。
  2. 自定義處理函數int sigprocmask(int how, const sigset_t *set, sigset_t *oldset);
    • howSIG_BLOCK(阻塞信號集)、SIG_UNBLOCK(解除阻塞)、SIG_SETMASK(設置新屏蔽集)至。

(二)信號集相關函數

  1. sigemptyset(sigset_t *set):初始化信號集為空
  2. sigfillset(sigset_t *set):初始化信號集包含所有信號
  3. sigaddset(sigset_t *set, int signum):添加信號到信號集
  4. sigdelset(sigset_t *set, int signum):從信號集刪除信號
  5. sigismember(const sigset_t *set, int signum):判斷信號是否在集合中至。

七、代碼演示?

#include <signal.h>   // 包含信號處理相關函數聲明,如sigaction、sigprocmask等
#include <stdio.h>    
#include <stdlib.h>   
#include <unistd.h>   // 包含Unix系統函數,如sleep、fork等// 信號處理函數,當接收到信號時被調用
void sig_handler(int signum)
{printf("Received signal: %d\n", signum);  // 打印接收到的信號編號
}int main(void)
{struct sigaction act;  // 定義sigaction結構體,用于設置信號處理方式act.sa_handler = sig_handler;  // 設置信號處理函數為sig_handleract.sa_flags   = 0;  // 清空標志位,使用默認處理行為// 清空信號屏蔽集,確保初始時不屏蔽任何信號sigemptyset(&act.sa_mask);// 設置SIGINT信號的處理方式為act中定義的處理方式sigaction(SIGINT, &act, 0);  printf("5 秒后,將屏蔽信號 SIGINT\n");// 倒計時5秒,期間可接收SIGINT信號for (int i = 5; i >= 1; i--) {printf("%d\n", i);sleep(1);}// 初始化信號集mask并將SIGINT添加到其中sigset_t mask;sigemptyset(&mask);sigaddset(&mask, SIGINT);// 阻塞mask中的信號(SIGINT),并保存原來的信號屏蔽字sigset_t old_mask;sigprocmask(SIG_BLOCK, &mask, &old_mask);printf("已經將 SIGINT 添加到信號集\n");// 檢查是否有懸而未決的信號(即被阻塞但未處理的信號)sigset_t pend_mask;sigpending(&pend_mask);if (sigismember(&pend_mask, SIGINT)) {printf("SIGINI 被掛起了\n");}printf("5 秒后,將恢復信號屏蔽字\n");// 倒計時5秒,期間SIGINT信號會被阻塞for (int i = 5; i >= 1; i--) {printf("%d\n", i);sleep(1);}// 恢復之前保存的信號屏蔽字,解除對SIGINT的阻塞sigprocmask(SIG_SETMASK, &old_mask, 0);printf("信號屏蔽字已恢復\n");while (1) {sleep(1);}return 0;
}

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/87158.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/87158.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/87158.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

深度解析Vue.js組件開發與實戰案例

一、Vue.js組件化思想 Vue.js的核心思想之一就是組件化開發。組件系統是Vue的一個重要概念,它允許我們使用小型、獨立和通常可復用的組件構建大型應用。在Vue中,組件本質上是一個擁有預定義選項的Vue實例。 1.1 為什么需要組件化 代碼復用:避免重復造輪子,提高開發效率可…

TensorFlow 2.0 與 Python 3.11 兼容性

TensorFlow 2.0 與 Python 3.11 兼容性 TensorFlow 2.0 官方版本對 Python 3.11 的支持有限&#xff0c;可能出現兼容性問題。建議使用 TensorFlow 2.10 或更高版本&#xff0c;這些版本已適配 Python 3.11。若需強制運行&#xff0c;可通過以下方式解決依賴沖突&#xff1a; …

MyBatisPlus 全面學習路徑

MyBatisPlus 全面學習路徑 學習目錄 第一部分&#xff1a;MyBatisPlus 基礎 MyBatisPlus 簡介與核心特性快速入門與環境搭建核心功能&#xff1a;BaseMapper 與 CRUD 接口條件構造器&#xff08;Wrapper&#xff09;詳解ActiveRecord 模式主鍵策略與通用枚舉 第二部分&…

React16,17,18,19更新對比

文章目錄 前言一、16更新二、17更新三、18更新四、19更新總結 前言 總結react 16&#xff0c;17&#xff0c;18&#xff0c;19所更新的內容&#xff0c;并且部分會涉及到原理講解。 一、16更新 1、在16.8之前更新&#xff0c;還是基于class組件的升級和維護更新。并且更新了一…

【git】有兩個遠程倉庫時的推送、覆蓋、合并問題

當你執行 git pull origin develop(或默認的 git pull)時,Git 會把遠端 origin/develop 的提交合并到你本地的 develop,如果遠端已經丟掉(或從未包含)你之前在私庫(priv)里提交過的改動,那這些改動就會被「覆蓋」,看起來就像「本地修改沒了」。 要解決這個問題,分…

Spring Boot 集成國內AI,包含文心一言、通義千問和訊飛星火平臺實戰教程

Spring Boot 集成國內AI&#xff0c;包含文心一言、通義千問和訊飛星火平臺實戰教程 一、項目結構二、添加Maven依賴三、配置API密鑰 (application.yml)四、配置類1. AI配置類 (AiProperties.java)2. 啟用配置類 (AiConfig.java) 五、服務層實現1. 文心一言服務 (WenxinService…

Elastic Search 學習筆記

1. Elasticsearch 是什么&#xff1f;有哪些應用場景&#xff1f; Elasticsearch 整體原理流程&#xff1f; Elasticsearch 是一個為海量數據提供近實時搜索和分析能力的分布式搜索引擎&#xff0c;廣泛應用于全文檢索、日志分析和大數據處理場景中。 Elasticsearch 整體原理…

動態規劃之斐波那契數(一)

解法一&#xff1a;遞歸 class Solution { public:int fib(int n) {if(n<2) return n;return fib(n-1)fib(n-2);} }; 解法二&#xff1a;dp class Solution { public:int fib(int N) {if (N < 1) return N;int dp[2];dp[0] 0;dp[1] 1;for (int i 2; i < N; i) {…

如何設置爬蟲的訪問頻率?

設置爬蟲的訪問頻率是爬蟲開發中的一個重要環節&#xff0c;尤其是在爬取大型網站&#xff08;如1688&#xff09;時&#xff0c;合理的訪問頻率可以避免對目標網站造成過大負擔&#xff0c;同時也能降低被封禁的風險。以下是一些常見的方法和建議&#xff0c;幫助你合理設置爬…

前端面試六之axios

一、axios簡介 Axios 是一個基于 Promise 的 HTTP 客戶端&#xff0c;用于瀏覽器和 Node.js 環境。在瀏覽器端&#xff0c;Axios 的底層實現是基于原生的 XMLHttpRequest&#xff08;XHR&#xff09;。它對 XHR 進行了封裝&#xff0c;增加了 Promise 支持、自動轉換 JSON 數據…

模板方法模式Template Method Pattern

模式定義 定義一個操作中算法的骨架&#xff0c;而將一些步驟延遲到子類中&#xff0c;模板方法使得子類可以不改變一個算法的結構即可重定義該算法的某些特定步驟 類行為型模式 模式結構 AbstractClass&#xff1a;抽象類ConcreteClass&#xff1a;具體子類 只有類之間的繼…

【行云流水AI筆記】游戲里面的強化學習使用場景

強化學習在游戲中的應用已從早期的棋類博弈擴展到現代復雜游戲的全流程優化&#xff0c;以下是結合最新技術進展的核心應用場景及典型案例&#xff1a; 一、競技游戲的策略突破 1. 策略博弈類游戲 代表案例&#xff1a;AlphaGo/AlphaZero&#xff08;圍棋&#xff09;、Alph…

使用Python和PyTorch框架,基于RetinaNet模型進行目標檢測,包含數據準備、模型訓練、評估指標計算和可視化

下面是一個完整的實現方案,使用Python和PyTorch框架,基于RetinaNet模型進行目標檢測,包含數據準備、模型訓練、評估指標計算和可視化。 import os import numpy as np import matplotlib.pyplot as plt import torch import torchvision from torchvision.models.detection…

springboot服務如何獲取pod當前ip方案及示例

在 Kubernetes 集群中&#xff0c;Spring Boot 服務獲取 Pod 當前 IP 的方案主要有兩種&#xff1a;通過環境變量注入 或 通過 Java 代碼動態獲取網絡接口 IP。以下是兩種方案的詳細說明及示例&#xff1a; 方案一&#xff1a;通過 Kubernetes Downward API 注入環境變量 原理…

1.MySQL三層結構

1.所謂安裝的Mysql數據庫&#xff0c;就是在電腦上安裝了一個數據庫管理系統&#xff08;【DBMS】database manage system&#xff09;&#xff0c;這個管理程序可以管理多個數據庫。 2.一個數據庫中可以創建多個表&#xff0c;以保存數據&#xff08;信息&#xff09;。【數據…

[深度學習]目標檢測基礎

目錄 一、實驗目的 二、實驗環境 三、實驗內容 3.1 LM_BoundBox 3.1.1 實驗代碼 3.1.2 實驗結果 3.2 LM_Anchor 3.2.1 實驗代碼 3.2.2 實驗結果 3.3 LM_Multiscale-object-detection 3.3.1 實驗代碼 3.3.2 實驗結果 四、實驗小結 一、實驗目的 了解python語…

ALOHA機器人平臺:低成本、高精度雙臂操作及其進展深度解析

原創1從感知決策到具身智能的技術躍遷與挑戰(基座模型與VLA模型)2ALOHA機器人平臺&#xff1a;低成本、高精度雙臂操作及其進展深度解析3(上)通用智能體與機器人Transformer&#xff1a;Gato和RT-1技術解析及與LLM Transformer的異同4(下)通用智能體與機器人Transformer&#x…

C++: 類 Class 的基礎用法

&#x1f3f7;? 標簽&#xff1a;C、面向對象、類、構造函數、成員函數、封裝、繼承、多態 &#x1f4c5; 更新時間&#xff1a;2025年6月15日 &#x1f4ac; 歡迎在評論區留言交流你的理解與疑問&#xff01; 文章目錄 前言一、什么是類&#xff1f;二、類的定義1.基本語法2.…

Java EE與Jakarta EE命名空間區別

在 Java 生態中&#xff0c;javax 和 jakarta 代表了 企業級 Java 規范&#xff08;Java EE/Jakarta EE&#xff09;的命名空間演進&#xff0c;核心區別在于歸屬權和管理組織的變更。以下是詳細對比&#xff1a; 1. 歷史背景 javax&#xff1a; 源自 Java EE&#xff08;Java …

2 Studying《Arm A715 Technical Reference Manual》

目錄 2. The Cortex?A715 core 2.1 Cortex?A715 core features 2.2 Cortex?A715 core confifiguration options 2.3 DSU-110 dependent features 2.4 Supported standards and specifications 2.6 Design tasks 3. Technical overview 3.1 Core components 3.2 Int…