Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
658 views
in Technique[技术] by (71.8m points)

c++ - Copying (using assignment) a structure to a structure inside a union causing seg fault

I wrote the following code:

#include <iostream>
#include <string>
#include <cstring>

struct bar
{
  std::string s3;
  std::string s4;
}Bar;

union foo
{
  char * s1;
  char * s2;
  bar    b1;

  foo(){};
  ~foo(){};
}Foo;


int main ()
{
  foo f1;
  bar b2;

  std::string temp("s3");
  b2.s3 = temp;
  b2.s4 = temp;

  //f1.b1 = b2;                           //-- This Fails (Seg faults)

  /*
    #0  0x00002b9fede74d25 in std::string::_Rep::_M_dispose(std::allocator<char> const&) [clone .part.12] ()
        from /usr/local/lib64/libstdc++.so.6
    #1  0x00002b9fede75f09 in std::string::assign(std::string const&) () from /usr/local/lib64/libstdc++.so.6
    #2  0x0000000000400ed1 in bar::operator= (this=0x7fff3f20ece0) at un.cpp:5
    #3  0x0000000000400cdb in main () at un.cpp:31
  */

  memcpy( &f1.b1, &b2, sizeof(b2) );  //-- This Works 

  std::cout << f1.b1.s3 << " " << f1.b1.s4 << std::endl;
  return 0;
} 

Can you please explain why the segmentation fault ? I am unable to decipher what that the data in the back trace suggests.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

std::string has a non-trivial constructor, that initializes its internal members. Therefore, your struct bar is no POD structure.

Unions only support POD (this is relaxed in C++11). The compiler cannot decide which constructor of which of the union's members to call. Imagine following situation:

unition MyUnion {
  std::string s;
  std::vector v;
};

Should it use vector's or string's constructor to initialize the object?

So in your situation, when you assign the string to the union's string, the internal data is not initalized, which causes random errors.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...