我有一段代码如下:
try
raise Exit (* body *)
with
| e ->
Printexc.record_backtrace true;
printf "Unexpected exception : %s\n" (Printexc.to_string e);
let x = Printexc.get_backtrace () in
print_string x;
Printexc.print_backtrace stdout
body
中的代码确实引发了异常,并显示Unexpected exception : Pervasives.Exit
,但它不会打印任何回溯。
我使用-g
和export OCAMLRUNPARAM=b
编译文件,是否有人知道无法打印回溯的原因?
答案 0 :(得分:1)
我的代码中没有看到很多函数,因此很可能没有要打印的堆栈跟踪。请在此处查看上一个答案:Printing stack traces
今天让我感到震惊的是,一个可能的问题是OCAMLRUNPARAM实际上并未在您的过程中设置。通过make(1)命令传递环境变量可能很棘手。一个原因是Makefile中的每一行都由不同的shell执行。
影响回溯的另一个因素是内联。如果你的功能很复杂,这可能不会影响你。但您可以使用-inline 0
关闭几乎所有内联。这不可能在没有堆栈跟踪和堆栈跟踪之间产生差异。它可能会在更短和更长的堆栈跟踪之间产生影响。
这是一个内联有所作为的实验:
$ cat m.ml
try
let f () : int = raise Exit
in let g () = f () + 2
in let h () = g () + 3
in let main () = Printf.printf "%d\n" (h () + 4)
in main ()
with
e -> Printf.printf "%s" (Printexc.get_backtrace ())
$ ocamlopt -inline 10 -g -o m m.ml
$ OCAMLRUNPARAM=b m
Raised by primitive operation at file "m.ml", line 3, characters 18-22
$ ocamlopt -inline 0 -g -o m m.ml
$ OCAMLRUNPARAM=b m
Raised at file "m.ml", line 2, characters 27-31
Called from file "m.ml", line 3, characters 18-22
Called from file "m.ml", line 4, characters 18-22
Called from file "m.ml", line 5, characters 43-47
Called from file "m.ml", line 6, characters 7-14