Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/postgresql/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Exception Lablgtk回调中的异常_Exception_Gtk_Ocaml_Lablgtk - Fatal编程技术网

Exception Lablgtk回调中的异常

Exception Lablgtk回调中的异常,exception,gtk,ocaml,lablgtk,Exception,Gtk,Ocaml,Lablgtk,在Lablgtk中,每当回调中出现异常时,都会自动捕获异常并在控制台中打印错误消息,例如: (prog:12345) LablGTK-CRITICAL **: gtk_tree_model_foreach_func: callback raised an exception 这没有给出堆栈跟踪,也没有关于异常的详细信息,因为它被捕获了,所以我自己无法检索此信息 我可以为这种情况启用更详细的日志信息吗?或者防止自动捕获异常?我想最好的方法是手动捕获异常并自己处理 let callbac

在Lablgtk中,每当回调中出现异常时,都会自动捕获异常并在控制台中打印错误消息,例如:

(prog:12345) LablGTK-CRITICAL **: gtk_tree_model_foreach_func: 
    callback raised an exception
这没有给出堆栈跟踪,也没有关于异常的详细信息,因为它被捕获了,所以我自己无法检索此信息


我可以为这种情况启用更详细的日志信息吗?或者防止自动捕获异常?

我想最好的方法是手动捕获异常并自己处理

let callback_print_exn f () =
 try f () with
 e -> my_exn_printer e
假设
val my\u exn\u printer:exn->unit
是您的自定义异常打印机,您只需将代码中的
~callback:f
替换为
~callback:(callback\u print\u exn f)
,即可打印回调异常

当然,您也可以使用该方法将该异常发送给另一个 线程,注册一个将与异常一起传递的“回调id”


关于堆栈跟踪,我不确定您是否可以轻松检索它。由于它是作为回调启动的,您可能想知道所使用的信号以及可以存储在回调处理程序中的信号。

我遇到了另一个类似的问题,但这次很难找到将调用放在何处以拦截异常

幸运的是,这次Glib C代码发出了一条非常具体的错误消息:

GLib-CRITICAL **: Source ID ... was not found when attempting to remove it`
+
grep
引导我找到了实际的C函数,但我找不到绑定到该代码的几个Lablgtk函数中的哪一个是罪魁祸首

因此,我下载了Glib源代码,在代码中添加了一个显式分段错误,对其进行编译,并使用
LD_LIBRARY_PATH
强制加载修改后的Glib版本

然后我用
gdb
运行OCaml二进制文件,得到堆栈跟踪,以及调用Lablgtk函数的精确行号。从那里,它是一个快速的3线补丁


通过使用“严格模式”防止异常被自动捕获,可以避免像这样的黑客攻击(比试图找到拦截呼叫的位置还要快)。我仍然相信这样一个开关应该可以为Lablgtk用户使用,并希望它最终可以使用。

我想您可以自己捕获异常并添加所需的日志记录。有关更多详细信息,您需要在调试模式下编译二进制文件,并使用gdb之类的调试器查看“何处”我想这里的答案确实是“没有更好的方法来实现它”,这似乎表明了这一点。糟糕的是,没有一种“调试模式”,默认情况下不会捕获异常。可能需要重新编译lablgtk来修改此行为。@anol可能,问题是,由于回调可能在代码中的任何时间被调用,异常可能会在任何地方引发,这是您真正不希望发生的事情。