Go程序当父进程被kill,子进程也自动退出的问题记录

news2024/10/2 20:34:57

平常我们启动一个后台进程,会通过nouhp &的方式启动,这样可以在退出终端会话的时候,进程仍然可以继续在后台执行(进程的父进程id会从原来的bash进程变成1)
在go程序中,通过nouhp &的方式启动子进程,预期是即使父进程挂掉,子进程也能继续执行
但是测试过程中发现,当父进程被kill,子进程也会自动退出

首先需要了解下什么是SIGHUP和SIGTERM

1.SIGHUP(Hangup)信号通常是由终端或控制台断开时产生的信号
    它的作用是通知进程重新读取其配置文件,或者让进程重新初始化,以便于适应新的环境。
    在进程收到该信号时,一般会在日志中记录相关信息,然后进行优雅的退出或重新初始化。
2.SIGTERM(Terminate)信号是进程终止信号
    它通常是由kill命令发送给进程的。它的作用是请求进程正常地退出,
    进程在接收到该信号后,可以在清理后退出。
    如果进程没有处理SIGTERM信号,则可以使用kill -9命令强制杀死进程。

正常情况下,一个程序如果没有进行特别处理,那么收到SIGHUP、SIGTERM信号都会退出

通常我们在一个终端会话中启动一个进程,如果只是通过&后台启动,那么当会话关闭的时候,进程也会自动退出
这是因为会话关闭的时候,会向子进程发送SIGHUP信号,导致子进程也跟着退出
而nohup的作用就是忽略NOHUP信号,避免进程退出

go程序中可以用signal.Notify监听SIGHUP信号修改默认行为,示例代码:

package main
 
import (
    "fmt"
    "os"
    "os/signal"
    "syscall"
)
 
func main() {
    // 创建一个channel用于接收信号
    signals := make(chan os.Signal, 1)
 
    // 注册信号
    signal.Notify(signals, syscall.SIGTERM, syscall.SIGHUP)
 
    // 在goroutine中等待信号
    go func() {
        for {
            select {
            case sig := <-signals:
                switch sig {
                case syscall.SIGTERM:
                    fmt.Println("Received SIGTERM, shutting down gracefully...")
                    // 做一些清理工作
                    os.Exit(0)
                case syscall.SIGHUP:
                    fmt.Println("Received SIGHUP, reloading configuration...")
                    // 重新加载配置
                }
            }
        }
    }()
 
    // 主进程继续执行其他任务
    fmt.Println("Server started...")
    select {}
}

通过在子进程中用signal.Notify监听SIGHUP、SIGTERM信号,并打印日志,来进行测试(kill -1发送SIGHUP信号,kill发送SIGTERM信号)
查看日志发现,父进程被kill,子进程会收到SIGTERM信号
而nohup只是忽略SIGHUP信号,所以使用nohup启动自然就不能防止子进程退出了

解决方案是启动子进程时,修改子进程进程组id,这样子进程就不会收到SIGTERM信号了
Go示例代码:

package main
 
import (
    "fmt"
    "os/exec"
    "strings"
    "syscall"
)
 
func main() {
    //这里child是上面子进程编译成的二进制程序
    cmd := exec.Command("/bin/bash", "-c", "./child")
    //SysProcAttr 字段被设置为 Setpgid 为 true,这将使子进程的进程组 ID 与其父进程不同。Pdeathsig 被设置为空信号,这意味着子进程在父进程退出时不会收到任何信号
    cmd.SysProcAttr = &syscall.SysProcAttr{
        Setpgid:   true,
        Pdeathsig: syscall.Signal(0),
    }
    output, err := cmd.CombinedOutput()
    rs := strings.TrimSpace(string(output))
    if err != nil {
        fmt.Println("Command execution failed:", err, "rs:", rs)
        os.Exit(1)
    }
    fmt.Println("rs:", rs)
}

ps -eo pid,ppid,pgrp,session,comm
可以通过这个命令来查看进程进程组id

还有一种情况要注意,即使不用Setpgid,使用kill -9的方式杀父进程,子进程也是不会退出的
针对一些希望父进程结束的时候,子进程也被跟着退出的场景,要么谨慎使用kill -9,要么自己做好进程退出的机制处理

参考资料:
https://blog.csdn.net/qq_34021712/article/details/115587702
https://cloud.tencent.com/developer/article/1497217
https://www.jianshu.com/p/e147d856074c%20

在这里插入图片描述

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

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

相关文章

干货| Vue小程序开发技术原理

目前应用最广的三大前端框架分别是Vue、 React 和 Angular 。其中&#xff0c;不管是 BAT 大厂&#xff0c;还是创业公司&#xff0c;Vue 都有广泛的应用。如今&#xff0c;再随着移动开发小程序的蓬勃发展&#xff0c;Vue也广泛应用到了小程序开发当中。今天&#xff0c;就来详…

嵌入式 STM32 SHT31温湿度传感器

目录 简介 1、原理图 2、时序说明 数据传输 起始信号 结束信号 3、SHT31读写数据 SHT31指令集 读数据 温湿度转换 4、温湿度转换应用 sht3x初始化 读取温湿度 简介 什么是SHT31&#xff1f; 一主机多从机--通过寻址的方式--每个从机都有唯一的地址&…

linux--多线程(一)

文章目录Linux线程的概念线程的优点线程的缺点线程异常线程的控制创建线程线程ID以及进程地址空间终止线程线程等待线程分离线程互斥进程线程间的互斥相关概念互斥量mutex有线程安全问题的售票系统查看ticket--部分的汇编代码互斥量的接口互斥量实现原理探究可重入和线程安全常…

三重积分为何不能直接带入积分区域?搞懂这些,重积分基本可以了

积分的积分区域及被积表达式 重点&#xff1a;积分的结果均为数值&#xff0c;仅与被积表达式和积分区间有关&#xff01;&#xff01;&#xff01; 1.如何一下子区分一重积分&#xff0c;二重积分&#xff0c;三重积分&#xff1f; 看积分区间和被积表达式&#xff1a; 一重…

React教程详解一(props、state、refs、生命周期)

文章略长&#xff0c;耐心读完&#xff0c;受益匪浅哦~ 目录 前言 简介 JSX 面向组件编程 state props refs 组件生命周期 前言 简介 React框架由Facebook开发&#xff0c;和Vue框架一样&#xff0c;都是用于构建用户界面的JavaScript库&#xff1b; 它有如下三个特…

PHP - ChatGpt 学习 仅供参考

由于最近ChatGpt 大火&#xff0c;但是门槛来说是对于大家最头疼的环节&#xff0c; 由此ChatGpt 有一个API 可以仅供大伙对接 让我来说下资质&#xff1a; 1&#xff1a;首先要搞得到一个 ChatGpt 的账户&#xff0c; 会获得一个KEY&#xff0c;该key为访问API核心&#xff0…

jenkins漏洞集合

目录 CVE-2015-8103 反序列化远程代码执行 CVE-2016-0788 Jenkins CI和LTS 远程代码执行漏洞 CVE-2016-0792 低权限用户命令执行 CVE-2016-9299 代码执行 CVE-2017-1000353 Jenkins-CI 远程代码执行 CVE-2018-1000110 用户枚举 CVE-2018-1000861 远程命令执行 CVE-2018…

ChatGPT文章自动发布WordPress

WordPress可以用ChatGPT发文章吗&#xff1f;答案是肯定的&#xff0c;ChatGPT官方有提供api接口&#xff0c;多以目前有很多的SEO工具具有自动文章生成自动发布的功能&#xff0c;使用SEO工具&#xff0c;我们可以通过疑问词和关键词进行文章生成&#xff0c;并定时发布到我们…

软测入门(三)Selenium(Web自动化测试基础)

Selenium&#xff08;Web端自动测试&#xff09; Selenium是一个用于Web应用程序测试的工具&#xff1a;中文是硒 开源跨平台&#xff1a;linux、windows、mac核心&#xff1a;可以在多个浏览器上进行自动化测试多语言 Selenium WebDriver控制原理 Selenium Client Library…

Linux基础——连接Xshell7

个人简介&#xff1a;云计算网络运维专业人员&#xff0c;了解运维知识&#xff0c;掌握TCP/IP协议&#xff0c;每天分享网络运维知识与技能。座右铭&#xff1a;海不辞水&#xff0c;故能成其大&#xff1b;山不辞石&#xff0c;故能成其高。个人主页&#xff1a;小李会科技的…

复位理论基础

先收集资料&#xff0c;了解当前常用的基础理论和实现方式 复位 初始化微控制器内部电路 将所有寄存器恢复成默认值确认MCU的工作模式禁止全局中断关闭外设将IO设置为高阻输入状态等待时钟趋于稳定从固定地址取得复位向量并开始执行 造成复位的原因 有多种引起复位的因素&…

客户关系管理挑战:如何保持客户满意度并提高业绩?

当今&#xff0c;各行业市场竞争愈发激烈&#xff0c;对于保持客户满意度并提高业绩是每个企业都面临的挑战。而客户关系管理则是实现这一目标的关键&#xff0c;因为它涉及到与客户的互动和沟通&#xff0c;以及企业提供优质的产品和服务。在本文中&#xff0c;我们将探讨客户…

使用Geth搭建多节点私有链

使用Geth搭建多节点私有链 步骤 1.编辑初始化配置文件genesis.json {"config": {"chainId": 6668,"homesteadBlock": 0,"eip150Block": 0,"eip150Hash": "0x000000000000000000000000000000000000000000000000000000…

JDK下载安装与环境

&#x1f972; &#x1f978; &#x1f90c; &#x1fac0; &#x1fac1; &#x1f977; &#x1f43b;‍❄️&#x1f9a4; &#x1fab6; &#x1f9ad; &#x1fab2; &#x1fab3; &#x1fab0; &#x1fab1; &#x1fab4; &#x1fad0; &#x1fad2; &#x1fad1;…

回暖!“数”说城市烟火气背后

“人间烟火气&#xff0c;最抚凡人心”。在全国各地政策支持以及企业的积极生产运营下&#xff0c;经济、社会、生活各领域正加速回暖&#xff0c;“烟火气”在城市中升腾&#xff0c;信心和希望正在每个人心中燃起。 发展新阶段&#xff0c;高效统筹经济发展和公共安全&#…

JavaEE进阶第六课:SpringBoot配置文件

上篇文章介绍了SpringBoot的创建和使用&#xff0c;这篇文章我们将会介绍SpringBoot配置文件 目录1.配置文件的作用2.配置文件的格式2.1 .properties语法2.1.1.properties的缺点2.2 .yml语法2.2.1优点分析2.2.2配置与读取对象2.2.3配置与读取集合2.2.4补充说明3.设置不同环境的…

陪诊小程序开发|陪诊小程序有哪些功能

陪诊小程序主要就是一款为服务一些无法单独或者很难单独完成就诊流程的人&#xff0c;提供线上下单寻求专业人员陪同就医的一款小程序&#xff0c;陪诊员线上接单&#xff0c;线下为患者提供专业的医疗陪同就医服务。相对于陪诊小程序开发多少钱很多人更想知道陪诊小程序有哪些…

动态规划:leetcode 139.单词拆分、多重背包问题

leetcode 139.单词拆分leetcode 139.单词拆分给定一个非空字符串 s 和一个包含非空单词的列表 wordDict&#xff0c;判定 s 是否可以被空格拆分为一个或多个在字典中出现的单词。说明&#xff1a;拆分时可以重复使用字典中的单词。你可以假设字典中没有重复的单词。示例 1&…

数据库设计规范1

数据库设计规范1 1.所有的表都必须有几个公共字段 这里建有删除标识&#xff0c;代表着我们所有的删除都是软删除。所以我们的删除操作其实是updata 2.id等数字类型的字段&#xff0c;不能知识bigint&#xff0c;应该是bigint unsigned 3.varchar默认长度为32&#xff0c;不…

MTK平台开发入门到精通(Thermal篇)热管理介绍

文章目录 一、热管理组成二、Linux Thermal Framework2.1、thermal_zone 节点2.2、cooling_device 节点三、Thermal zones沉淀、分享、成长,让自己和他人都能有所收获!😄 📢本篇文章将介绍MTK平台的热管理机制,热管理机制是为了防止模组在高温下工作导致硬件损坏而存在的…