在mac 10.15.16系统上,编译swoole 4.4.18的时候,在执行make命令时,出现错误提示:`no member named 'signbit' in the global namespace
using ::signbit;`,使得编译总是失败。

对于想在mac使用swoole的开发者而言,多少算是一种挫败。本来兴致冲冲想在mac身上研究一下swoole,却在编译swoole的php插件时栽了这么一个跟头。为了解决这个拦路虎,和朋友问了一圈,无解,又在在网上搜了很多文章,始终未找到解答。

不过,只要真心想解决问题,并且为之努力,机遇还是会到来的。

具体出错信息如下:

In file included from /usr/local/Cellar/php/7.4.7/include/php/main/php.h:33:
In file included from /usr/local/Cellar/php/7.4.7/include/php/Zend/zend.h:27:
In file included from /usr/local/Cellar/php/7.4.7/include/php/Zend/zend_types.h:25:
In file included from /usr/local/Cellar/php/7.4.7/include/php/Zend/zend_portability.h:43:
In file included from /usr/local/Cellar/php/7.4.7/include/php/Zend/zend_config.h:1:
In file included from /usr/local/Cellar/php/7.4.7/include/php/main/../main/php_config.h:2336:
/Library/Developer/CommandLineTools/usr/bin/../include/c++/v1/cmath:317:9: error: 
      no member named 'signbit' in the global namespace
using ::signbit;
      ~~^
/Library/Developer/CommandLineTools/usr/bin/../include/c++/v1/cmath:318:9: error: 
      no member named 'fpclassify' in the global namespace
using ::fpclassify;
      ~~^
/Library/Developer/CommandLineTools/usr/bin/../include/c++/v1/cmath:319:9: error: 
      no member named 'isfinite' in the global namespace; did you mean 'finite'?
using ::isfinite;
      ~~^
/usr/local/include/math.h:749:12: note: 'finite' declared here
extern int finite(double)
           ^

...

/Library/Developer/CommandLineTools/usr/bin/../include/c++/v1/cmath:649:25: error: no template named 'numeric_limits'
  return _FloatBigger ? numeric_limits<_IntT>::max() :  (numeric_limits<_IntT>::max() >> _Bits << _Bits);
                        ^
fatal error: too many errors emitted, stopping now [-ferror-limit=]
177 warnings and 20 errors generated.
make: *** [php_swoole_cxx.lo] Error 1

在网上还找到一篇文章,描述的现象而言,和我遇到的问题是一致的:《Mac 安装 Swoole 报错: error: no member named 'isless' in the global namespace using ::isless;》

最终对我起到帮助的一篇文章是:Catalina C++: Using headers yield error: no member named 'signbit' in the global namespace,其中Niloy Datta的回答帮我解决了难题。

下面引用一下他的发言内容:

Using the command:(使用命令查看include的路径)

gcc -Wp,-v -E -

my #include <...> search sequence:(我的#include查询顺序是)

/usr/local/include
 /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/lib/clang/10.0.1/include
 /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include
 /Library/Developer/CommandLineTools/SDKs/MacOSX10.15.sdk/usr/include
 /Library/Developer/CommandLineTools/SDKs/MacOSX10.15.sdk/System/Library/Frameworks (framework directory)

The reason of #include error is described below:(#include出现错误原因如下)

  • \#include resides in /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include/c++/v1
  • It includes < math.h \>.
  • It searches /usr/local/include directory as this is the first directory to search. There is a math.h in "/usr/local/include/c++/9.3.0/" directory
  • It tries to use this.
  • But expectation was to use the math.h of the same directory /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include/c++/v1
  • The math.h of /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include/c++/v1 include math.h of /usr/local/include using #include_next<math.h>
  • As wrong math.h is included/linked with /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include/c++/v1/cmath, the compilation error happens

The fix:(解决方案)

  1. If we can alter the search order of #include<...> to search /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include/c++/v1 at first, it can be fixed.
  2. Using \#include</Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include/c++/v1/math.h> instead of <math.h> in /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include/c++/v1/cmath

再用中文说明一下

归根结底,其实就是和#include的检索顺序有关系。首先可以通过命令找到自己系统的#include的顺序。在我的系统里边按照 gcc -Wp,-v -E -,结果如下:

clang -cc1 version 11.0.3 (clang-1103.0.32.62) default target x86_64-apple-darwin19.6.0
ignoring nonexistent directory "/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/local/include"
ignoring nonexistent directory "/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/Library/Frameworks"
#include "..." search starts here:
#include <...> search starts here:
 /usr/local/include
 /Library/Developer/CommandLineTools/usr/lib/clang/11.0.3/include
 /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/include
 /Library/Developer/CommandLineTools/usr/include
 /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/System/Library/Frameworks (framework directory)
End of search list.

而能找到math.h的第一个路径,则是/usr/local/include/math.h这个文件,这和预期是不一致的,预期要使用的math.h是其同目录的math.h。因此,我们可以对原来的cmath代码进行调整,将<math.h>改成"math.h"即可。

修改“/Library/Developer/CommandLineTools/usr/include/c++/v1/cmath”中的#include <math.h>为#include "math.h"。

这就是最终的解决方案,按此方法修改后,make命令可以正常进行,swoole可以正常在mac下编译通过了。

标签: none

仅有一条评论

  1. 您好~我是腾讯云+社区的运营,关注了您在分享的技术文章,觉得内容很棒,我们诚挚邀请您加入腾讯云自媒体分享计划。完整福利和申请地址请见:https://cloud.tencent.com/developer/support-plan
    作者申请此计划后将作者的文章进行搬迁同步到社区的专栏下,你只需要简单填写一下表单申请即可,我们会给作者提供包括流量、云服务器、域名等,另外还有些周边礼物。  我们诚挚的邀请您并期待您的加入~
    腾讯云+社区是由腾讯云全新打造的一个技术交流社区,正在引入更多的作者与优质文章,就此社区推出一个自媒体的分享计划。(或遇到任何问题可联系微信 goyagarcia)谢谢

添加新评论