五千年(敝帚自珍)

主题:c++ help. -- spin

共:💬12 🌺12 新:
全看树展主题 · 分页首页 上页
/ 1
下页 末页
家园 c++ help.

I got error: cannot bind packed field 'aa.AA::a' to 'int&' as compiling a hello c++ file with gcc3.4,gcc-4.1 and gcc4.2.

#include <iostream>

using namespace std;

struct AA

{

int a;

double b;

}__attribute__((packed));

void func(int &aa, double &bb)

{

aa = 10;

bb = 99.9;

}

int main()

{

struct AA aa;

func(aa.a, aa.b);

cout << aa.a << " " << aa.b;

}

Google does not help much. I grab a setence from gcc/cp/call.c which seems explain this error but I can't understand it. Can anyone help.

from gcc/cp/call.c

/* If the reference is volatile or non-const, we cannot create a temporary. */

/* If the source is a packed field, and we must use a copy constructor, then building the target expr will require binding the field to the reference parameter to the copy constructor, and we'll end up with an infinite loop. If we can use a bitwise copy, then we'll be OK. */

关键词(Tags): #gcc#packed
家园 【原创】

#include <iostream>

using namespace std;

struct AA

{

int a;

double b;

}__attribute__((packed));

void func(int *aa, double *bb)

{

*aa = 10;

*bb = 99.9;

}

int main()

{

struct AA aa;

func(&aa.a, &aa.b);

cout << aa.a << " " << aa.b <<endl;

}

关键词(Tags): #c++
家园 Well, interesting

The following seems to work, but I don't know

if it will solve your real problem.

Been programming C a lot?

"struct AA aa;"?

"AA aa;" is enough in C-plus-plus:))

--------------------------------------------------

#include <iostream>

using namespace std;

struct AA

{

int a;

double b;

}__attribute__((packed));

void func(int &aa, double &bb)

{

aa = 10;

bb = 99.9;

}

int main()

{

AA aa;

int &n = aa.a;

double &d = aa.b;

func(n,d);

cout << aa.a << " " << aa.b<<endl;

return 0;

}

家园 很久没碰这个了

估计您这个是学校的功课,我就试试。

FUNCTION的定义如此:

void func(int &aa, double &bb)

那就是说需要两个地址参数(Parameters, address-type)

但您调用这个FUNCTION的时候,如此

func(aa.a, aa.b)

这就是说您是传了aa.a, aa.b的两个数值(Value)进去,而不是aa.a, aa.b的地址,所以编译出错。

另外一个比较明显的错误是这个:

aa = 10;

bb = 99.9;

这样做是在试图改变两个地址变量,而非把10, 和99.9放到两个指定的地址里。

虽然没有编译器试一下,但楼下华大的代码应该是正确的。 

建议下点功夫,把地址,指针的概念搞清楚,不然学C/C++会很辛苦。

家园 您说的不对。请进-----------

C-plus-plus有一个不同于C的地方,就是多了一个"reference".原搂主的帖子里的"func"之parameters均为references,而不是pointers.

注意:int &aa, 而不是 int *aa。所以他pass的不是value,而是reference。这个没有错。

他的程序之所以有编译错误,关键是在那个__attribute__((packed))

上面。如果除去,就可以编译了。但是为什么出错了,我尚未搞懂。

家园 花谢兼惭愧

足足有7年没碰这个了,惭愧得很。。。

家园 别别。呵呵。我们都在学习之中啊。
家园 大致上是这么回事吧

一个object被pack以后,里面的member alignment就乱了,不再是地址边界了。而reference需要知道一个可以access的地址。所以就出问题了。

家园 那为什么

int &n = aa.a;

就没问题呢?

和func(int &aa..., 同样都是references啊。

puzzling,唉!

家园 斗胆推测一下

int &n = aa.a;

这个方法工作,是因为func对变量n进行操作,而不是对aa直接进行操作。aa被packed,但n没有。

我猜packed的作用大概是为了增强struct的密封性,不许对其member单独直接写操作。

int &n = aa.a;是对其member的读操作,可以允许的。

不知编译器的参考书是如何解释这个packed的?

家园 操作不同啊

= operator可以解决这个alignment问题,但越过call context的传递不行。具体跟实现方式有关,就要去看gcc的程序了。楼主原文最后引的注释就是在说这回事吧。

家园 多谢各位,逐篇花,网上也说了两个解决方案

一个就是[华大]说的,用指针

还有一个就是[觉昌安塔克世]兄建议的,用临时变量

主要是这个程序在gcc3.3,gcc3.2是可以通过的

兄弟我不是搞it的,主要是某人遇到这个问题,为了讨好某人,我容易么我。

全看树展主题 · 分页首页 上页
/ 1
下页 末页


有趣有益,互惠互利;开阔视野,博采众长。
虚拟的网络,真实的人。天南地北客,相逢皆朋友

Copyright © cchere 西西河