You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

无法终止Python Popen启动的adb logcat及Logger进程,求解决方法

无法终止adb logcat及关联Logger进程的排查与解决

问题背景

以下Python代码可正常拉取安卓设备日志并传入Logger生成目标文本文件,但无法终止两个进程。尝试过terminate()、os.kill(process.pid, signal.SIGKILL)、preexec_fn、os.killpg()等方法后,Logger仍在后台运行。

代码示例

def startLogger(logger_dir):
    command0 = 'adb logcat -c'
    command1 = 'adb logcat'
    command2 = 'python3 '+logger_dir+'main.py'

    clear_logcat = subprocess.run(command0.split())
    logcatHandle = subprocess.Popen(command1.split(),stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=False)
    loggerHandle = subprocess.Popen(command2.split(),stdin=logcatHandle.stdout,shell=False)
    return logcatHandle, loggerHandle

def closeLogger(logcatInstance, loggerInstance):
    loggerInstance.kill() #Killing it first so that it doesn't break the input PIPE
    logcatInstance.kill()
    return logcatInstance, loggerInstance

def main():
    logger_dir = '/Users/Desktop/logger/'
    print("Starting Logger")
    logcatHandle, loggerHandle = startLogger(logger_dir)
    time.sleep(10)
    logcat, logger = closeLogger(logcatHandle, loggerHandle)

main()

排查与解决思路

  • 子进程脱离父进程控制:你启动的python3 main.py可能创建了独立子进程,仅杀死父进程的话,子进程会被系统进程接管继续运行。可以用ps aux | grep main.py查看进程树,确认是否存在这类情况。
  • 管道未正确关闭导致阻塞:杀死loggerHandle后,logcatHandle的stdout管道可能未被关闭,导致adb logcat无法正常退出。创建子进程时添加close_fds=True,确保父进程操作时关闭未使用的文件描述符:
    logcatHandle = subprocess.Popen(
        command1.split(),
        stdout=subprocess.PIPE,
        stderr=subprocess.PIPE,
        shell=False,
        close_fds=True
    )
    loggerHandle = subprocess.Popen(
        command2.split(),
        stdin=logcatHandle.stdout,
        shell=False,
        close_fds=True
    )
    
  • 进程组未整体销毁:如果目标进程启动了进程组,单独杀死单个进程无效。创建子进程时设置start_new_session=True,让进程成为新会话领头进程,再用os.killpg杀死整个进程组:
    修改进程创建代码:
    logcatHandle = subprocess.Popen(
        command1.split(),
        stdout=subprocess.PIPE,
        stderr=subprocess.PIPE,
        shell=False,
        start_new_session=True
    )
    loggerHandle = subprocess.Popen(
        command2.split(),
        stdin=logcatHandle.stdout,
        shell=False,
        start_new_session=True
    )
    
    修改关闭逻辑:
    import os
    import signal
    
    def closeLogger(logcatInstance, loggerInstance):
        try:
            os.killpg(os.getpgid(loggerInstance.pid), signal.SIGKILL)
        except ProcessLookupError:
            pass
        try:
            os.killpg(os.getpgid(logcatInstance.pid), signal.SIGKILL)
        except ProcessLookupError:
            pass
        return logcatInstance, loggerInstance
    
  • 检查main.py自身退出逻辑:有可能main.py内部存在忽略SIGKILL信号的逻辑,或者处理输入时陷入无限循环(未正确处理EOF)。可以单独运行python3 /Users/Desktop/logger/main.py,手动输入EOF(Ctrl+D)测试是否能正常退出,排查main.py自身问题。

内容的提问来源于stack exchange,提问作者Priyansh Gupta

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.20 19:12:40