确定 python 子进程分段是否出错 [英] Determining if a python subprocess segmentation faults

查看:23
本文介绍了确定 python 子进程分段是否出错的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在编写一个对学生程序进行评分的程序,我相信您可以想象,它们有时会出现分段错误.我遇到的问题是,当学生程序分段错误时,没有迹象表明发生了什么.

proc = subprocess.Popen(student_command,标准输出=子进程.PIPE,stderr=subprocess.PIPE)self.stdout, self.stderr = proc.communicate()self.returncode = proc.returncode

我拿起stderrstdoutsubprocess的返回码,但是如果程序段出错,stderr 为空,stdout 为空,返回码为-11.现在我可以查找 -11 退出代码并假设如果这是返回代码,则存在分段错误,但也没有什么可以阻止学生的代码将 -11 作为返回代码,因为学生想返回-11.

你如何判断子进程分段是否出错,而不是仅仅感觉像返回 -11?我真的不太关心标准错误和标准输出中的内容,为此我看到了许多帖子,包括 this 处理获取输出,但我不太关心输出,尽管获得;分段错误"串出标准错误,但我真正需要的是一种明确告诉子进程发生了什么的方法.

解决方案

事实上,在 UNIX 上,尝试返回 -11 的进程通常最终会返回一个正整数.这是因为 wait 系列函数的返回状态实际上是一组位域,其中一个域表示结束进程的信号,另外一个域表示返回值.Python 解码来自这些位域的 wait 返回值.

在大多数系统上,这些字段是无符号的,大小为 8 位,因此您可能会看到如下内容:

<预><代码>>>>导入子流程>>>subprocess.Popen(['python','-c','import os; os.kill(os.getpid(),11)']).wait()-11>>>subprocess.Popen(['python','-c','exit(-11)']).wait()245

在前一种情况下,进程段错误"(通过使用 SIGSEGV 杀死自己),因此 wait 返回 -11.在后一种情况下,进程退出,返回码为 -11,结果 wait 值为 245 (256-11).因此,您可以放心,wait 的任何负返回值都必须表示致命信号,而不是正常返回.但请注意,进程可能会自杀以伪造致命错误.

I am writing a program that grades student programs, and as I am sure you can imagine, they sometimes segmentation fault. The problem I am having is that when the student programs segmentation fault, there is no indication that is what happened.

proc = subprocess.Popen(student_command, 
                        stdout=subprocess.PIPE, 
                        stderr=subprocess.PIPE)
self.stdout, self.stderr = proc.communicate()
self.returncode = proc.returncode

I pick up the stderr, stdout, and the return code from the subprocess, but if the program segmentation faults, stderr is empty, stdout is empty, and the return code is -11. Now I could look for the -11 exit code and assume that if that is the return code there was a segmentation fault, but there is also nothing to prevent a student's code from having -11 as a return code just because the student felt like returning -11.

How do you tell if a subprocess segmentation faults, as opposed to just feeling like returning -11? I don't really care all that much about what is in stderr and stdout, and to that end have seen a number of posts including this that deal with picking up the output, but I don't care all that much about the output, although it would be nice to get the "Segmentation Fault" string out of stderr, but what I really need is a way to definitively tell what happened to the subprocess.

解决方案

Well, in fact, on UNIX, a process that attempts to return -11 will usually end up returning a positive integer instead. This is because the return status from the wait series of functions is actually a set of bitfields, with a field for the signal that ended the process and a separate field for the return value. Python decodes the wait return value from these bitfields.

On most systems, these fields are unsigned and 8 bits in size, so you will probably see something like this:

>>> import subprocess
>>> subprocess.Popen(['python','-c','import os; os.kill(os.getpid(),11)']).wait()
-11
>>> subprocess.Popen(['python','-c','exit(-11)']).wait()
245

In the former case, the process "segfaults" (by killing itself with SIGSEGV), and so wait returns -11. In the latter case, the process exits with a return code of -11, and the resulting wait value is 245 (256-11). You can therefore rest assured that any negative return value from wait must represent a fatal signal, as opposed to a normal return. Note, though, that processes may kill themselves to fake a fatal error.

这篇关于确定 python 子进程分段是否出错的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆