有没有办法在新的线程池线程创建时被通知(例如通过事件或回调)?我正在开发一个使用 P/Invoke 调用 pjlib 库的 .Net 控制台应用程序。该库要求使用其任何 API 的每个线程必须先通过 pj_thread_register API 进行注册:
我想,如果可以在每个新线程池线程被创建时得到通知(通过在新线程的上下文中调用回调函数),那么就可以使用该回调函数仅注册新线程一次。是否有一种方法接收此类通知?
或者,我可以在主线程或某些专用线程上使用 SynchronizationContext(例如 Stephen Cleary 的 AsyncContext 或 Stephen Toub 的 AsyncPump),并在创建它们时立即注册它们,但这意味着需要重新设计应用程序,可能朝着演员模型的方向发展,是否有其他方法来面对这种情况?
当尝试从未注册的线程调用任何 pjlib 函数时,库实际上会断言并显示以下消息:向 PJLIB 注册通过外部或本地 API 创建的线程。必须在注册线程的上下文中调用此函数。当由外部函数或 API 调用创建线程时,必须使用 pj_thread_register() 将其“注册”到 PJLIB 中,以便它可以与 PJLIB 的框架协作。在注册期间需要维护一些数据,并且这些数据必须在线程的生命周期内保持可用。
现在,应用程序的业务逻辑使用了Calling pjlib from unknown/external thread. You must
register external threads with pj_thread_register()
before calling any pjlib functions.
async
和 await
,因为它是控制台应用程序,所以 SynchronizationContext 为空,这意味着所有的继续都将在线程池线程上运行,包括对 pjsip API 的 P/Invoke 调用,需要在调用任何 pjsip API 之前调用 pj_thread_register()
,以确保新创建的线程池线程不会在注册自己之前尝试使用任何 pjsip API。我想,如果可以在每个新线程池线程被创建时得到通知(通过在新线程的上下文中调用回调函数),那么就可以使用该回调函数仅注册新线程一次。是否有一种方法接收此类通知?
或者,我可以在主线程或某些专用线程上使用 SynchronizationContext(例如 Stephen Cleary 的 AsyncContext 或 Stephen Toub 的 AsyncPump),并在创建它们时立即注册它们,但这意味着需要重新设计应用程序,可能朝着演员模型的方向发展,是否有其他方法来面对这种情况?
[ThreadStatic] static bool _pjInitialized = false;
if (!_pjInitialized) PjThreadRegister();
- undefinedvar status = pj_thread_register(Thread.CurrentThread.Name, desc, ref t);
。Thread.CurrentThread.Name可能为空,但是在查看pj_thread_register的实现(无论是在Windows还是Unix上),在使用pj_ansi_snprintf(thread->obj_name, sizeof(thread->obj_name), cstr_thread_name, thread->idthread);
之前,会对const char *cstr_thread_name
进行空检查,因此这不是一个问题。无论如何,选择一个有意义的名称都是明智的(例如用于日志记录)。 - undefined