最近的GTK 3.22仍然是Boehm GC友好(线程问题)吗?

时间:2017-03-31 13:13:37

标签: c linux multithreading gtk boehm-gc

Boehm's conservative garbage collector非常有用(例如Bigloo正在使用它,Guile正在使用类似的东西......等等,尤其是在Linux上(这是我唯一的操作系统)关心;如果重要的话,我正在使用Debian / Sid / x86-64,libgc-dev包是版本1:7.4.2-8,所以Boehm GC是7.4.2。)

然而, Boehm的GC 需要知道使用它的每个线程。其gc_pthreads_redirects.h(或多或少内部)标头文件正在重新定义pthread_create

# define pthread_create GC_pthread_create

实际上,Boehm的GC需要在新的线程调用堆栈中尽早调用GC_register_my_thread(而GC_pthread_create正在这样做。)

过去,Glib(2.46)提供了一种使用struct GMemVTable which is deprecated 重新定义内存分配的方法,不再使用(我的Debian的libglib2.02.0-dev包是版本{{1 }})。有一个g_mem_gc_friendly global boolean但是在查看Glib源代码时,它只是在释放它们之前清除内存区域。

最近的GTK3(我的2.50.3-2包有版本libgtk-3-dev)使用(间接)3.22.11-1创建线程(可能与Dbus相关,也可能与GtkTextView相关...)通过Glib thread functions。除了通过修补源代码之外,没有办法通知该线程创建。我害怕比我安装的任何GTK回调(例如使用g_signal_connect)可能会从这些线程调用。或者,如果我使用某些可能使用(或访问)某些pthread_create -ed缓冲区的方法对GTK小部件进行子类化,则可能会发生灾难。

另一方面,GTK中有一个强大的编码规则,所有GTK操作都应该只在主线程中发生。引用Gdk3 Threads页面:

  

GTK + ,但 线程安全。您应该只使用线程GC_malloc中的GTK +和GDK,并调用gtk_init()。这通常被称为“主线程”。

如果我自己遵循此规则,我确信没有内部GTK代码可以从某个非主线程调用我的回调(使用Boehm GC)?

我的直觉是,如果从GTK内部(不是直接通过我的代码)从主线程外部调用gtk_main(),就会发生灾难 (因为这些GTK内部线程还没有用GC_alloc启动;可能会调用我的一些代码,例如因为我正在创建一些现有的GTK小部件,或者因为我连接了一些GTK信号,即使我没有我自己在主线程之外使用GTK和Boehm GC编写代码。)。

关键是Boehm的GC需要扫描每个可能使用它的线程中的每个堆栈。

FWIW,我在GTK bugzilla上报告了可能的bug#780815

一个典型的例子是来自GTK-3.22.11 tarball的GC_pthread_creategtk+-3.22.11/examples/application9/通过pthread_create

g_application_run非常间接g_bus_get_sync is called

1 个答案:

答案 0 :(得分:0)

GTK +不是用垃圾收集器编写的。您必须修改GDK及其构建的库,以调用GC_ *分配函数以使其工作。简单地通知GC额外的GLib线程似乎不是解决方案。

也就是说,如果GTK +及其使用的库由与Boehm GC不同的堆支持,这可能不是问题。您的应用程序可能并非完全没有内存泄漏和其他问题,但至少您编写的所有代码都将正确GC。