【问题标题】:c++ unknown calling conventionc++ 未知调用约定
【发布时间】:2019-06-27 05:31:06
【问题描述】:

我正在构建的一个包(SPRNG,链接是here,但对于这个问题是不必要的)在我不熟悉的某些地方使用了调用语法。对于我之前的依赖堆栈(带有 OpenMPI 1.10.1 的 Intel 16.0),它可以工作。不幸的是,我当前的堆栈(带有 OpenMPI 3.1.3 的 Intel 19)不喜欢它。我不是c++ 的人,除非必要,否则我也不想大幅修改包。

示例代码为:

#include <mpi.h>

int main(int argc, char *argv[]) {
  int myid;

  MPI::Init(argc, argv);
  myid = MPI::COMM_WORLD.Get_rank();
}

在之前的堆栈中,这似乎很好:

$ mpic++ --version
icpc (ICC) 16.0.0 20150815
Copyright (C) 1985-2015 Intel Corporation.  All rights reserved.

$ mpirun --version
mpirun (Open MPI) 1.10.1

Report bugs to http://www.open-mpi.org/community/help/
$ mpic++ sprng_issue.cpp
<no errors>

但是有了新的堆栈:

$ mpic++ --version
icpc (ICC) 19.0.1.144 20181018
Copyright (C) 1985-2018 Intel Corporation.  All rights reserved.

$ mpirun --version
mpirun (Open MPI) 3.1.3

Report bugs to http://www.open-mpi.org/community/help/
$ mpic++ sprng_issue.cpp 
sprng_issue.cpp(6): error: name followed by "::" must be a class or namespace name
    MPI::Init(argc, argv);
    ^

sprng_issue.cpp(7): error: name followed by "::" must be a class or namespace name
    myid = MPI::COMM_WORLD.Get_rank();
           ^

compilation aborted for sprng_issue.cpp (code 2)

我的问题是:

  1. 这个调用方法有名字吗?我很难搜索,因为它只是。它有多奇怪/旧/非标准?

  2. 是否有编译器标志(Intel 或其他)来启用旧版行为?

  3. 还有什么其他的建议可以让你轻松通过,而无需大量修改包代码?

【问题讨论】:

  • 代码是完全标准的 C++。它要么是对 MPI 类的静态方法 Init 的调用,要么是对命名空间 MPI 中的全局函数 Init 的调用,具体取决于 MPI 是类还是命名空间(这是不可能的)从给出的代码告诉)。为什么它不能与您的新工具一起使用也很难说。给出的代码没有任何问题。答案可能就在&lt;mpi.h&gt; 头文件中。
  • PS 调用约定一般是指不同的问题,即编译器为函数调用生成的机器码。您的代码是完全正常的 C++,问题是为什么您的新编译器不接受它。

标签: c++ syntax mpi icc


【解决方案1】:

C++ 绑定多年前已从标准中删除,并且默认情况下它们不再在 Open MPI 中构建。

从长远来看,您应该对代码进行现代化改造(使用普通的 C 绑定,或其他抽象层,例如 Boost.MPI)。

同时,您可以使用 configure --enable-mpi-cxx 简单地重建 Open MPI。

【讨论】:

  • 所以不工作的绑定是c++ 绑定,但c 是?
  • 除非您明确要求,否则不会构建C++ 绑定。 C 绑定总是建立的。
猜你喜欢
  • 2011-12-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-01-05
  • 1970-01-01
  • 2023-04-03
  • 2017-06-03
  • 1970-01-01
相关资源
最近更新 更多