在EM_ASM_INT中声明多元素数组会中断编译

时间:2015-09-04 23:39:43

标签: emscripten

我试图在EM_ASM样式的宏中声明一个多元素数组。当我使用普通的旧EM_ASM时,这很好用:

EM_ASM({var a = [1,2];});

但是,在任何返回值的EM_ASM样式宏中执行此操作似乎会使编译器感到困惑。

例如:

 EM_ASM_INT_V({var a = [1,2]; return 1;});

给我这些错误:

  

错误:为类似函数的宏提供了太多参数         调用

     

test.cc:4:3:注意:不能在宏参数的开头使用初始化列表

     

test.cc:4:3:错误:使用未声明的标识符' EM_ASM_INT_V'

EM_ASM_INTEM_ASM_DOUBLEEM_ASM_DOUBLE_V也是如此(无论我是否向他们提供适当的参数并返回)。如果我声明一个1元素数组:

 EM_ASM_INT_V({var a = [1]; return 1;});
一切都很好。使用大括号括起来的Javascript对象也会发生这种情况 - 单个元素(例如{val1: 1})很好,但不止于此(例如{val1: 1, val2: 2})会给我同样的错误。

我目前的解决方法是单独将其他元素推送到数组:

 EM_ASM_INT_V({var a = [1];
               a.push(2); 
               return 1;});

这很有效,但它非常笨重。

我查看了Emscripten github页面上的相关问题,但无法找到。我做错了什么,或者这是一个错误?任何人都有更好的解决方法吗?

1 个答案:

答案 0 :(得分:1)

我认为问题与宏调用中的逗号有关。逗号在括号内被忽略,但不在括号,括号或尖括号中,因此它将您的第一个参数拆分为两个:{var a = [12]; return 1;},这显然是有问题的。

我没有看过EM_ASM的定义,但由于它只期望一个参数,我的猜测是,如果它不止一个,它会自动用逗号粘在一起。但是,其他EM_ASM_ *宏不知道期望多少个参数,所以他们不能这样做。

至于修复,通常可以包括额外的括号。对于您的示例,您应该能够使用:

EM_ASM_INT_V({var a = ([1,2]); return 1;});

圆括号不会伤害任何东西,但会保持宏观参数粘合在一起(有时它不是那么容易,但通常是这样)。

我知道在预处理器规范中修复这个问题已经很长一段时间了 - 希望有一天它会发生。当在宏调用中包含模板时,它变得特别烦人,因为在这些情况下,没有简单的方法来包围括号中的所有内容。

编辑:我检查了EM_ASM定义,实际上它是一个可变参数宏,它将参数粘合在一起。