23

我并不主张这将是一个好主意,但我发现你可以通过eval在足够大的输入字符串上运行来使 Python 崩溃(检查 2.7 和 3.2):

def kill_python(N):
    S = '+'.join((str(n) for n in xrange(N)))
    return eval(S)

在我的计算机S上可以很好地生成,但是对于大约 的值N>74900,Python 将失败并显示Segmentation fault (core dumped). 解释器可以处理的字符串(或解析树)的长度是否有限制?

注意:我不需要这样做,对我来说这是一个更深层次的问题,反映了我对盒子里发生的事情的无知。我想了解为什么 Python 在这里失败了,而且是灾难性的(为什么不抛出异常?)

4

1 回答 1

18

此问题是由 CPython 编译器中的堆栈溢出引起的。重现相同问题的简单方法是

>>> code = compile("1" + "+1" * 1000000, "", "eval")
Segmentation fault

这证明段错误发生在编译阶段,而不是评估期间。(当然这也很容易用 gdb 确认。)

[旁注:对于较小的表达式,编译器无论如何都会在此处应用常量折叠,因此在代码执行期间唯一发生的事情就是加载结果:

>>> code = compile("1" + "+1" * 1000, "", "eval")
>>> eval(code)
1001
>>> dis.dis(code)
  1           0 LOAD_CONST            1000 (1001)
              3 RETURN_VALUE        

旁注结束。]

此问题是一个已知缺陷。Python 开发人员在源代码分发目录Lib/test/crashers中收集了几种使 Python 解释器崩溃的方法。与此问题相对应的是Lib/test/crashers/compiler_recursion.py.

于 2012-07-24T21:44:01.187 回答