【问题标题】:Is there a way to test whether thread safe functions are available in the C standard library?有没有办法测试 C 标准库中是否提供线程安全函数?
【发布时间】:2013-02-07 23:28:41
【问题描述】:

关于较新版本的 C 标准库中的thread safe functions,是否有一种跨平台的方式来判断它们是否可以通过预处理器定义获得?我指的是localtime_r()等函数。

如果没有标准的方式,GCC中可靠的方式是什么? [编辑] 还是带有 unistd.h 的 posix 系统?

【问题讨论】:

  • 这就是 autoconf 的诞生。
  • 最好使用 Autoconf。 Autoconf 将为您创建测试。
  • 同上,但使用 CMake ;)
  • 如果可以使用预处理器完成,他们就不必发明 autoconf、CMake 等了。
  • 这些函数在 POSIX 中是强制性的,因此如果在包含 unistd.h 之后将 _POSIX_VERSION 定义为与 POSIX 的合理最新版本匹配的内容,则这些函数必须可用。

标签: c libc


【解决方案1】:

没有标准的测试方法,这意味着无法在所有平台上测试它。 autoconf 之类的工具将创建一个调用此函数的微型 C 程序,然后尝试编译和链接它。它可以工作,看起来该函数存在,如果不存在,则它可能不存在(或编译器选项错误,需要设置适当的CFLAGS)。

所以你基本上有 6 个选项:

  1. 要求它们存在。您的代码只能在它们存在的平台上运行;时期。如果它们不存在,编译将失败,但这不是您的问题,因为平台违反了您的最低要求。

  2. 避免使用它们。如果您使用非线程安全的,可能受全局锁(例如互斥锁)保护,它们是否存在都没有关系。当然,您的代码只能在具有 POSIX 互斥锁的平台上运行,但是,如果平台没有 POSIX 互斥锁,它也不会有 POSIX 线程,如果它没有 POSIX 线程(我猜你可能正在使用 POSIX 线程 w /o 支持任何替代方案),你为什么要首先担心线程安全?

  3. 在运行时决定。根据平台,要么做一个“弱链接”,所以你可以在运行时测试是否找到了函数(如果没有,指向函数的指针将指向NULL)或者动态解析符号使用 dlsym() 之类的东西(它也不是真正可移植的,但在 Linux/UNIX 世界中得到广泛支持)。但是,在这种情况下,如果在运行时未找到该函数,则需要回退。

  4. 使用类似autoconf 的工具、具有类似功能的其他工具或您自己的配置脚本在开始编译之前确定这一点(并且可能根据结果设置预处理器宏)。在这种情况下,您还需要一个备用解决方案。

  5. 限制使用知名平台。这个功能在某个平台上是否可用通常是已知的(一旦可用,以后也不会消失)。大多数平台都公开了预处理器宏来测试这是什么类型的平台,有时甚至是哪个版本。例如。如果您知道 GNU/Linux、Android、Free/Open/NetBSD、Solaris、iOS 和 MacOS X 都提供此功能,请测试您是否正在为这些平台之一进行编译,如果是,请使用它。如果代码是为另一个平台编译的(或者如果您无法确定是哪个平台),它可能会或可能不会提供此功能,但由于您无法确定,最好安全并使用后备。

  6. 让用户决定。要么总是使用后备,除非用户已经表示支持或者反过来做(这可能更有意义),总是假设它在那里,万一编译失败,提供一种用户可以强制你的代码进入“兼容性”的方法mode”,通过某种方式指定线程安全函数不可用(例如,通过设置环境变量或使用不同的 make 目标)。当然,对于(可怜的)用户来说,这是最不方便的方法。

【讨论】:

  • @vonbrand 查看我对 R.. 评论的回复评论。
  • 我真的很喜欢 R.. 的评论,因为它在很多方面确实满足了我的问题。它基本上是对您的子部分 (5) 的更具体的答案,这就是我对 GCC 后续问题的理解。谢谢你的文章,非常好!
猜你喜欢
  • 2020-09-23
  • 1970-01-01
  • 2013-11-27
  • 2021-10-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-06-15
  • 2013-02-28
相关资源
最近更新 更多