首页 > 其他分享 >Docker kill 1无效

Docker kill 1无效

时间:2022-11-08 22:24:05浏览次数:90  
标签:无效 pid kill 信号 进程 sig Docker 捕获

前言

我们在平常强制停用一个进程的时候, 会选择什么命令? 一般在测试使, 不考虑程序突然中断带来的影响, 直接使用kill -9 pid强制停止就行.

但是, 就在刚刚, 我启动了一个docker容器, 进入容器后执行命令kill -9 1没有任何效果??? 啊这, 为什么呀?

尝试

为了解释这个现象, 我进行了一系列测试, 这里简单说一下, 具体过程就不细写了:

  • 其他进程: 使用kill -9杀掉pid不为1的进程, 是可以杀掉的
  • 其他信号: 编写进程捕获其他信号(如SIGTERM), 进程可以正常捕获

经过测试得出结论, pid为1的进程不会处理信号SIGKILL

解惑

那么为什么会这样呢? 我们知道, SIGKILL信号进程是不能捕获的, 只能执行操作系统规定的行为, 那么就有两个合理的猜测:

  1. 操作系统忽略了, 没有将信号发送给进程
  2. 进程收到了信号, 只是pid=1的进程忽略了

那么究竟是怎么回事呢? 我找了些资料, 大概了解了此过程. 在man手册中也有介绍.

首先, pid=1是操作系统的守护进程, 其他所有的进程都是通过这个进程来启动的. 操作系统在发送信号时, 会进行是否忽略的判断, 这里以Linux 6.0为例, 判断的方法名称为sig_task_ignored, 对其进行简单分析:

static bool sig_task_ignored(struct task_struct *t, int sig, bool force)
{
	// ...
  /*
  分析一下其中各个判断: 
  unlikely(t->signal->flags & SIGNAL_UNKILLABLE)
  	进程的 SIGNAL_UNKILLABLE 标志位是否为 true
  	在每个 pid namespace 的 init 进程创建时, 都会标记此标志
  	源码位置可见(我也没看懂...): https://github.com/torvalds/linux/blob/v6.0/kernel/fork.c#L2442
  	结果: init 进程恒为 true
  handler == SIGDFL
  	判断信号的处理是否是默认的, 如果进程自己捕获了则为 false
  !(force && sig_kernel_only(sig))
  	force: 同一个 pid namespace 发送信号时, 恒为0
  	sig_kernel_only: 判断信号是否为 SIGSTOP 或 SIGKILL
  	结果: 因此, 此条件恒为 true
  结果: 对于 init 进程来说, 第一个和第三个条件都恒为true, 因此是否忽略完全在于此信号进程是否进行了捕获
  */
	if (unlikely(t->signal->flags & SIGNAL_UNKILLABLE) &&
	    handler == SIG_DFL && !(force && sig_kernel_only(sig)))
		return true;
	// ...
}

因此, init进程, 若捕获了信号则能收到, 否则收不到. 而在所有的信号中(可通过 kill -l查看), SIGSTOP/SIGKILL这两个信号是不允许进程捕获的.

那么如何知道进程是否主动捕获了信号呢? 可以使用命令: cat proc/347/status | grep SigCgt, 将16进制转为2进制, 最右侧为1说明进程捕获了信号1. 具体可见这里

至此, 已经基本解决了之前的疑惑.

解决

  1. 在宿主机中执行kill. 因为容器中的守护进程在宿主机中的pid并不为1

  2. docker run --init. 启动容器的时候添加--init参数, 这样容器会启动一个守护进程来转发, 你运行的进程就不是守护进程啦.

    原文地址: https://hujingnb.com/archives/864

标签:无效,pid,kill,信号,进程,sig,Docker,捕获
From: https://www.cnblogs.com/hujingnb/p/16871422.html

相关文章

  • phpstrom docker swoole win10
    构建镜像dockerfile点击查看代码#现在我们需要配置一些东西。#编译参数,用于指定Swoole版本ARGswoole_ver#保存到环境变量,如果没有传递就给默认值ENVSWOOLE_......
  • docker 快速部署 elasticseach kafa mysql redis pgsql etcd
    version:"3"services:pgsql:container_name:pgsqlimage:postgres:latestprivileged:trueenvironment:POSTGRES_PASSWORD:password......
  • docker-compose 搭建 InfluxDB Cluster
    InfluxDBCluster官网GitHub:chengshiwen/influxdb-clusterWiki文档:chengshiwen/influxdb-cluster/wiki下载地址:chengshiwen/influxdb-cluster/releases网络架构图......
  • docker 镜像仓库之私有云单机仓库Docker Registry
    Docker仓库分为公有云仓库和私有云仓库公有云仓库:由互联网公司对外公开的仓库官方阿里云等第三方仓库私有云仓库:组织内部搭建的仓库,一般只为组织内部使......
  • docker安装LuaJIT WEB应用防火墙
    安装包请见https://www.jianshu.com/p/b81656764613Dockerfile#FROMubuntuFROMcentosMAINTAINERG00G1SCOPYnginx-1.16.0/usr/local/src/nginx-1.16.0COPYLua......
  • Docker 知识汇总
    centos安装docker#!/bin/bashsudoyumremovedocker\docker-client\docker-client-latest\docker-com......
  • Docker笔记
    安装安装yum工具yuminstall-yyum-utils\device-mapper-persistent-data\lvm2--skip-broken更新本地镜像源#设置docker镜像源yum......
  • docker 命令学习
    启动docker-compose:docker-composeup-d列出所有容器:docker-composeps停止容器:docker-composestop停止正在运行的容器,可以通过docker-composestart再次启动查......
  • Springboot +Docker 架构的项目中,怎么修改设置JVM堆内存的大小?
    在项目的dockerfile文件中设定      【参数解析】在Java应用程序启动时,添加如下参数并设置大小:参数说明-Xmx设置JVM最大可用堆内存大小......
  • 最高法-建设工程合同无效不适用双方返还原则,只适用折价补偿
    (2016)最高法民申701号  中国瑞林工程技术有限公司与安徽圣来光电科技有限公司建设工程设计合同纠纷申诉、申请民事裁定书关键词:建设工程  合同无效  双方返还申请......