I have 2 different applications, a sender and a receiver. the Sender will send a message over to the receiver, who will decode the message and print to the console. However, I keep getting segmentation fault error.
Both sender and receiver application have the same TestContainer.h and TestContainer.cpp.
Casting method
template<class To,class From>To cast(From v)
{
return static_cast<To>(static_cast<const void*>)(v);
}
Sender application
int main()
{
TestContainer tc;
tc.setDesc("this is a message");
const char* castedData = cast<const char*>(&tc);
const TestContainer test_tc = cast<const TestContainer*>(castedData);
// i get back "this is a message",so the casting is working
cout << "message content: " << test_tc->getDesc() <<endl;
TaoSender;
TaoSender.send(castedData);
return 1;
}
Receiver Application
void push(const RtecEventComm::EventSet& events)
{
const char* receivedData;
events[0].data.any_value >>= receivedData;
cout << "data received: " << receivedData << endl;
const TestContainer rcv_tc = cast<const TestContainer*>(receivedData);
cout << "message content: " << rcv_tc->getDesc() <<endl; // error(segmentation fault)
}
TestContainer.h and TestContainer.cpp
class TestContainer{
public
TestContainer();
virtual ~TestContainer();
const std:string& getDesc () const {
return desc;
}
void setDesc(const std::string& desc) {
this->desc = desc;
}
private
std::string desc;
}
#include TestContainer.h
TestContainer::TestContainer(){}
TestContainer::~TestContainer(){}
The value of castedData at the sender and the value of receivedData at the receiver is the same, so I guess the message sending is correct.
However,at the Receiver, after converting the receivedData buffer to a Testcontainer pointer and attempting to access the desc, I get a segmentation fault error.
I also tried casting back to Testcontainer in the Sender, and I am able to access the desc. So what did I miss out?
Although the code in your question contains errors, if I understand you correctly you are trying to push the representation of an object over a pipe or other channel to another process, where you reconstruct the object and try to use it.
You could do this with "Plain Old Data" objects, but the
TestContainerclass has virtual methods and therefore it is not POD. In most implementations of C++, objects of typeTestContainerwill contain a vtable pointer which refers to a table allocated within the process' address space. The address of this table will likely be different in different processes. Therefore, copying the representation of theTestContainerobject byte-by-byte to another process will lead to crashes when you try to call a virtual method.TestContainerinstances also contain astd::string. Astringallocates storage to hold the string contents and this storage will be outside the objecet itself. Transmitting the byte representation of thestringas part ofTestContainerresults in reconstruction at the other end of astringthat holds a pointer to a memory address in another process. Within the receiver, that memory address will refer to something else. Hence, thestringwill not be successfully reconstructed.To send objects between processes you need to properly transmit them in a form that is independent of memory addresses contained within (whether that be a vtable pointer, a pointer member, or a pointer member of a an opaque member such as a
string). The process of converting data to such a form is called serialization. There are libraries available to assist with this, but nothing in the standard library.