dtja73027 2019-03-10 03:39
浏览 386
已采纳

调用cmd.Process.Kill()后,进程不会死

I've a program that tracks file change and should restart a specified process on file change.

I use cmd.Process.Kill() to kill previous process but it keeps alive after Kill() called.

Some piece of code related to process start from project:

// ShellPlugin allows to run shell commands in task runner 
type ShellPlugin struct {
    scope  *scope.Scope
    params Params
    log    logging.Logger
    done chan bool
}

// Call calls a plugin
func (p *ShellPlugin) Call(tx *job.RunContext, r plugins.JobRunner) (err error) {
    defer close(p.done)

    // process: /bin/sh -c ping google.com
    cmd, err := p.params.createProcess(p.scope)
    if err != nil {
        return fmt.Errorf("failed to create process to execute command '%s': %s", p.params.Command, err)
    }

    p.log.Debug("command: '%s'", p.params.Command)
    p.log.Debug(`starting process "%s"...`, strings.Join(cmd.Args, " "))

    if err = cmd.Start(); err != nil {
        return fmt.Errorf(`failed to execute command "%s": %s`, strings.Join(cmd.Args, " "), err)
    }

    go func() {
        select {
        case <- p.done:
            p.log.Debug("received stop signal")
            if err := cmd.Process.Kill(); err != nil {
                p.log.Warn("kill: %s", err.Error())
            }
            p.log.Debug("Killed")
        }
    }()

    if err := cmd.Wait(); err != nil {
        return formatExitError(err)
    }

    p.log.Debug("done")
    return nil
}

// Cancel called when task should be canceled
func (p *ShellPlugin) Cancel(ctx *job.RunContext) error {
    p.done <- true
    return nil
}

Call() starts job and Cancel() cancel it. Both called in separate goroutine.

Full source code is here

  • 写回答

1条回答 默认 最新

  • dongyan1548 2019-03-10 04:19
    关注

    The issue was that the main process sh was killed but child process sleep was still alive.

    The solution was to assign process group to the main process and kill a whole process group.

    // assign process group
    cmd.SysProcAttr = &syscall.SysProcAttr{Setpgid: true}
    
    // Kill pg
    syscall.Kill(-cmd.Process.Pid, syscall.SIGKILL)
    

    Solution was found here

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 pyqt怎么把滑块和输入框相互绑定,求解决!
  • ¥20 wpf datagrid单元闪烁效果失灵
  • ¥15 券商软件上市公司信息获取问题
  • ¥100 ensp启动设备蓝屏,代码clock_watchdog_timeout
  • ¥15 Android studio AVD启动不了
  • ¥15 陆空双模式无人机怎么做
  • ¥15 想咨询点问题,与算法转换,负荷预测,数字孪生有关
  • ¥15 C#中的编译平台的区别影响
  • ¥15 软件供应链安全是跟可靠性有关还是跟安全性有关?
  • ¥15 电脑蓝屏logfilessrtsrttrail问题