We now retrieve and unflatten the target BMessage successfully,

though we don't yet create child nodes for the contained fields.



git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@42287 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Rene Gollent
2011-06-23 00:08:58 +00:00
parent a1d3b4af1e
commit 29a6c81bcd
@@ -8,7 +8,9 @@
#include <new>
#include <AutoDeleter.h>
#include <Message.h>
#include <MessagePrivate.h>
#include "Architecture.h"
#include "StringValue.h"
@@ -19,6 +21,39 @@
#include "ValueNodeContainer.h"
// minimal replica of BMessage's class structure for
// extracting fields
class BMessageValue {
public:
uint32 what;
virtual ~BMessageValue();
struct message_header;
struct field_header;
message_header* fHeader;
field_header* fFields;
uint8* fData;
uint32 fFieldsAvailable;
size_t fDataAvailable;
mutable BMessage* fOriginal;
BMessage* fQueueLink;
// fQueueLink is used by BMessageQueue to build a linked list
void* fArchivingPointer;
uint32 fReserved[8];
virtual void _ReservedMessage1();
virtual void _ReservedMessage2();
virtual void _ReservedMessage3();
};
// #pragma mark - BMessageValueNode
@@ -77,21 +112,74 @@ BMessageValueNode::ResolvedLocationAndValue(ValueLoader* valueLoader,
addressData.SetTo(location->PieceAt(0).address);
TRACE_LOCALS("Address: 0x%" B_PRIx64 "\n", addressData.ToUInt64());
TRACE_LOCALS("BMessage: Address: 0x%" B_PRIx64 "\n",
addressData.ToUInt64());
uint8 buffer[sizeof(BMessage)];
error = valueLoader->LoadRawValue(addressData, sizeof(BMessage), buffer);
uint8 classBuffer[sizeof(BMessage)];
error = valueLoader->LoadRawValue(addressData, sizeof(BMessage),
classBuffer);
if (error != B_OK)
return error;
#if APPS_DEBUGGER_TRACE_STACK_FRAME_LOCALS
if (error == B_OK) {
BMessage* message = (BMessage*)buffer;
TRACE_LOCALS("Loaded BMessage('%c%c%c%c')\n",
char((message->what >> 24) & 0xff),
char((message->what >> 16) & 0xff),
char((message->what >> 8) & 0xff),
char(message->what & 0xff));
BVariant headerAddress;
BMessageValue* value = (BMessageValue*)classBuffer;
headerAddress.SetTo((target_addr_t)value->fHeader);
uint8 headerBuffer[sizeof(BMessage::message_header)];
error = valueLoader->LoadRawValue(headerAddress, sizeof(headerBuffer),
headerBuffer);
TRACE_LOCALS("BMessage: Header Address: 0x%" B_PRIx64 ", result: %ld\n",
headerAddress.ToUInt64(), error);
if (error != B_OK)
return error;
BMessage::message_header* header = (BMessage::message_header*)headerBuffer;
size_t fieldsSize = header->field_count * sizeof(BMessage::field_header);
size_t totalMessageSize = sizeof(BMessage::message_header)
+ fieldsSize + header->data_size;
uint8* messageBuffer = new(std::nothrow)uint8[totalMessageSize];
if (messageBuffer == NULL)
return B_NO_MEMORY;
memset(messageBuffer, 0, totalMessageSize);
ArrayDeleter<uint8> deleter(messageBuffer);
// This more or less follows the logic of BMessage::Flatten
// in order to reconstruct the flattened buffer ; thus if the
// internal representation of that changes, this will have to
// follow suit
header->what = value->what;
uint8* currentBuffer = messageBuffer;
memcpy(currentBuffer, header,
sizeof(BMessage::message_header));
if (fieldsSize > 0) {
headerAddress.SetTo((target_addr_t)value->fFields);
currentBuffer += sizeof(BMessage::message_header);
error = valueLoader->LoadRawValue(headerAddress, fieldsSize,
currentBuffer);
TRACE_LOCALS("BMessage: Field Header Address: 0x%" B_PRIx64
", result: %ld\n", headerAddress.ToUInt64(), error);
if (error != B_OK)
return error;
headerAddress.SetTo((target_addr_t)value->fData);
currentBuffer += fieldsSize;
error = valueLoader->LoadRawValue(headerAddress, header->data_size,
currentBuffer);
TRACE_LOCALS("BMessage: Data Address: 0x%" B_PRIx64 ", result: %ld\n",
headerAddress.ToUInt64(), error);
if (error != B_OK)
return B_ERROR;
}
#endif
BMessage message;
error = message.Unflatten((const char *)messageBuffer);
TRACE_LOCALS("BMessage: Unflatten result: %s\n", strerror(error));
if (error != B_OK)
return error;
return B_BAD_VALUE;
}