0

我已经阅读了最后一个 C++11 草案(n3337 - 它是最后一个吗?),我有一个关于我一直在研究的可能实现的问题。

假设我们有以下代码:

extern "Objective C" {
  class Object {
    public:
      static Object *alloc();
      Object *init();
  };
};

然后打电话

Object *x = Object::alloc()->init();

问题是我不明白是否允许编译器控制外部“X”块的调用约定:想法是“翻译”对 objc_msgSend(blablabla) 的调用 - 这是否符合标准,还是将其视为扩展(因为它不仅会修改符号名称,还会在此处修改复杂的“调用约定”)?当然,我可以通过创建一个称为 __thiscall 的弱函数来实现这一点,然后调用并返回该方法本身 - 但问题仍在继续,它是否符合要求?

谢谢!

4

1 回答 1

1

您描述的所有内容听起来都符合语言链接功能的意图。

班级成员被明确排除在"C"语言联系之外。根据标准 (C++11 §7.5/4) 中的示例,类成员声明中的函数指针类型、extern任何上下文中的声明以及所有其他函数声明都会继承封闭extern "C" {}块。除此之外,您还定义了一个语言链接,"C"但遵循它的例子并不令人惊讶,也许在thisand之间有额外的映射self

根据§7.5/2,要求是开放的:

有条件地支持使用除“C”或“C++”之外的字符串文字,并具有实现定义的语义。[注意:因此,具有实现未知的字符串文字的链接规范需要诊断。— end note ] [ 注意:建议字符串文字的拼写取自定义该语言的文档。例如,Ada(不是 ADA)和 Fortran 或 FORTRAN,取决于年份。——尾注]

您可以在大括号内切换到完全不同的语言,这样就可以了。(尽管从语法上讲,我认为所有内容都应该解析为 C++声明声明序列。)

但是,据此,您应该使用extern "Objective-C"连字符,因为最终文档的标题是“Objective-C 编程语言”。

编辑:可以肯定的是,通过调用objc_msgSend不会影响标准指定的任何内容。它没有说明如何调用 C++ 函数。添加的中间函数只是机器级指令,超出了语言语义,与用于调用 Pascal、Fortran 等的特殊指令没有什么不同,例如通过改变堆栈上参数的顺序。我并不是要将您的方案与“在大括号内切换到完全不同的语言”进行比较,只是为了强调有足够的空间。

extern "C"标准中的规范为例,它通过从根本上改变 ODR 规则打破了很多事情,因为 C 不需要支持任何修改。所以你的计划被允许至少打破那么多。

于 2013-01-31T01:51:04.167 回答