代码之家  ›  专栏  ›  技术社区  ›  user299208

如何告诉家长线程是用p螺纹在C++中完成的?

  •  3
  • user299208  · 技术社区  · 16 年前

    我有一个TCP服务器应用程序,它使用POSIX线程和C++在一个新线程中服务每个客户端。

    当客户机断开连接时,我想用某种方法告诉main()线程这个线程已经完成,main()可以删除这个对象并记录类似“client disconnected”的内容。

    8 回复  |  直到 16 年前
        1
  •  2
  •   Rob Lachlan    16 年前

    我能看到的最直接的方法是连接线程。看到了吗 here . 其思想是,在join调用中,命令线程将等待工作线程退出,然后继续。

    或者,您可以使用一些共享变量和互斥锁来汇总某些内容。

        2
  •  2
  •   Tyler McHenry    16 年前

    如果子线程在完成时确实正在退出(而不是等待更多的工作),则父线程可以调用 pthread_join

    显然,如果父线程正在做其他事情,它就不能一直阻塞 pthread_连接 ,所以您需要一种方法来向主线程发送消息,让它调用 pthread_连接 . 有许多IPC机制可以用于此目的,但是在您的特定情况下(TCP服务器),我怀疑主线程可能是 select pipe 创建一个逻辑管道,并使管道的读取描述符成为主线程从中选择的描述符之一。

    pthread_连接 在该线程上,然后在连接完成时执行其他任何操作。

    注意,你没有 打电话 在完成的子线程上,除非需要其返回值。但是,如果子线程从什么时候开始就可以访问共享资源,那么这样做通常是个好主意 pthread_连接

        3
  •  2
  •   David Titarenco    16 年前

    pthreads返回 0 errno 如果有什么不起作用。

    int ret, joined;
    ret = pthread_create(&thread, NULL, connect, (void*) args);
    joined = pthread_join(&thread, NULL);
    

    joined 为零,线程完成。清理线程的对象。

        4
  •  1
  •   jschmier    16 年前

    虽然可以实现IPC机制,以便在其他线程即将终止时通知主线程,但是如果您想在某个线程终止时执行某些操作,则应该尝试让终止线程自己执行。

    pthread_cleanup_push() 建立一个当线程被取消或退出时要调用的例程。另一个选择可能是使用 pthread_key_create() 创建一个特定于线程的键和析构函数。

    如果你不想打电话 pthread_join() 由于阻塞,您应该通过在创建线程或调用时将其设置为选项来分离客户端线程 pthread_detach() .

        5
  •  0
  •   David Gelhar    16 年前

    您可以使用一个由“要删除的线程对象”组成的队列,用互斥体保护对该队列的访问,然后用pthread条件变量发出信号,指示队列中有可用的内容。

    但你真的想这么做吗?一个更好的模型是,每个线程只需清理自身,而不必首先担心与主线程同步。

        6
  •  0
  •   torak    16 年前

    pthread_join 将阻止主线程的执行。鉴于对这个问题的描述,我认为它不能提供理想的解决方案。

    volatile )或者某种依赖的操作系统机制。记住,您希望在呼叫时被阻止 listen

        7
  •  0
  •   Potatoswatter    16 年前

    正如其他人所提到的,处理 鉴于 穿 pthread_join . 但是pthread的一个弱点是将来自多个源的信息汇集到一个同步流中。(或者,你可以说它的强项是性能。)

    到目前为止,最简单的解决方案是在工作线程中处理清理。记录断开连接(在日志中添加互斥锁),根据需要删除资源,并退出工作线程而不向父线程发出信号。

        8
  •  0
  •   Aleksandar    14 年前

    我遇到了和你描述的完全一样的问题。打开~300个客户机连接后,我的Linux应用程序无法创建新线程,因为pthread_join从未被调用。对我来说,pthread_tryjoin_np的使用有帮助。

    • 有一个包含所有打开的线程描述符的映射
    • 在打开新的客户机线程之前,我从主线程迭代map并为map中记录的每个线程调用pthread_tryjoin_np。如果线程完成了,则调用的结果为零,这意味着我可以从该线程中清除资源。同时pthread_tryjoin_np负责释放线程资源。如果pthread_tryjoin_np call返回的数字与0不同,这意味着线程仍在运行,我什么也不做。

    潜在的问题是,我不认为pthread_tryjoin_np是部分正式的POSIX标准,所以这个解决方案可能不可移植。

    推荐文章