version 1.2, 2015/04/20 18:10:09
|
version 1.3, 2015/04/20 18:19:50
|
|
|
*/ | */ |
| |
#include "packing.h" | #include "packing.h" |
|
#include "naming.h" |
|
#include <pal/format.h> |
| |
/** Magic number for MI_Instance objects (binary buffer pack/unpack) */ | /** Magic number for MI_Instance objects (binary buffer pack/unpack) */ |
#define INSTANCE_MAGIC ((MI_Uint32)0x462b9957) | #define INSTANCE_MAGIC ((MI_Uint32)0x462b9957) |
|
|
| |
MI_INLINE void* _Alloc(Batch* batch, size_t size) | MI_INLINE void* _Alloc(Batch* batch, size_t size) |
{ | { |
return batch ? Batch_Get(batch, size) : malloc(size); |
return batch ? Batch_Get(batch, size) : PAL_Malloc(size); |
} |
|
|
|
/* Obtain the self pointer from this instance */ |
|
MI_INLINE Instance* _SelfOf(const MI_Instance* instance) |
|
{ |
|
if (instance && ((Instance*)instance)->self) |
|
return ((Instance*)instance)->self; |
|
else |
|
return (Instance*)instance; |
|
} | } |
| |
static MI_Result _PackField(Buf* buf, const void* field, MI_Type type) | static MI_Result _PackField(Buf* buf, const void* field, MI_Type type) |
|
|
| |
if (f->exists) | if (f->exists) |
{ | { |
if (!f->value.data) |
if (!f->value.data && f->value.size) |
MI_RETURN(MI_RESULT_FAILED); | MI_RETURN(MI_RESULT_FAILED); |
| |
MI_RETURN_ERR(Buf_PackU8A(buf, f->value.data, | MI_RETURN_ERR(Buf_PackU8A(buf, f->value.data, |
|
|
| |
if (f->exists) | if (f->exists) |
{ | { |
if (!f->value.data) |
if (!f->value.data && f->value.size) |
MI_RETURN(MI_RESULT_FAILED); | MI_RETURN(MI_RESULT_FAILED); |
| |
MI_RETURN_ERR(Buf_PackU16A(buf, f->value.data, | MI_RETURN_ERR(Buf_PackU16A(buf, f->value.data, |
|
|
| |
if (f->exists) | if (f->exists) |
{ | { |
if (!f->value.data) |
if (!f->value.data && f->value.size) |
MI_RETURN(MI_RESULT_FAILED); | MI_RETURN(MI_RESULT_FAILED); |
| |
MI_RETURN_ERR(Buf_PackU32A(buf, f->value.data, | MI_RETURN_ERR(Buf_PackU32A(buf, f->value.data, |
|
|
| |
if (f->exists) | if (f->exists) |
{ | { |
if (!f->value.data) |
if (!f->value.data && f->value.size) |
MI_RETURN(MI_RESULT_FAILED); | MI_RETURN(MI_RESULT_FAILED); |
| |
MI_RETURN_ERR(Buf_PackU64A(buf, f->value.data, | MI_RETURN_ERR(Buf_PackU64A(buf, f->value.data, |
|
|
| |
if (f->exists) | if (f->exists) |
{ | { |
if (!f->value.data) |
if (!f->value.data && f->value.size) |
MI_RETURN(MI_RESULT_FAILED); | MI_RETURN(MI_RESULT_FAILED); |
| |
MI_RETURN_ERR(Buf_PackDTA(buf, f->value.data, | MI_RETURN_ERR(Buf_PackDTA(buf, f->value.data, |
|
|
if (f->exists) | if (f->exists) |
{ | { |
MI_RETURN_ERR(Buf_PackStrA(buf, | MI_RETURN_ERR(Buf_PackStrA(buf, |
(const MI_Char**)f->value.data, f->value.size)); |
(const ZChar**)f->value.data, f->value.size)); |
} | } |
break; | break; |
} | } |
|
|
case MI_STRING: | case MI_STRING: |
{ | { |
MI_RETURN_ERR(Buf_UnpackStr( | MI_RETURN_ERR(Buf_UnpackStr( |
buf, (const MI_Char**)&value->string)); |
buf, (const ZChar**)&value->string)); |
| |
break; | break; |
} | } |
|
|
MI_RETURN_ERR(Buf_UnpackDTA(buf, | MI_RETURN_ERR(Buf_UnpackDTA(buf, |
(const MI_Datetime**)&value->datetimea.data, | (const MI_Datetime**)&value->datetimea.data, |
&value->datetimea.size)); | &value->datetimea.size)); |
|
break; |
} | } |
case MI_STRINGA: | case MI_STRINGA: |
{ | { |
MI_RETURN_ERR(Buf_UnpackStrA(buf, | MI_RETURN_ERR(Buf_UnpackStrA(buf, |
(const MI_Char***)&value->stringa.data, &value->stringa.size)); |
(const ZChar***)&value->stringa.data, &value->stringa.size)); |
break; | break; |
} | } |
case MI_INSTANCEA: | case MI_INSTANCEA: |
|
|
MI_Result Instance_Pack( | MI_Result Instance_Pack( |
const MI_Instance* self_, | const MI_Instance* self_, |
MI_Boolean keysOnly, | MI_Boolean keysOnly, |
MI_Boolean (*filterProperty)(const MI_Char* name, void* data), |
MI_Boolean (*filterProperty)(const ZChar* name, void* data), |
void* filterPropertyData, | void* filterPropertyData, |
Buf* buf) | Buf* buf) |
{ | { |
Instance* self = _SelfOf(self_); |
Instance* self = Instance_GetSelf( self_ ); |
MI_ClassDecl* cd = (MI_ClassDecl*)self->classDecl; |
MI_ClassDecl* cd; |
MI_Uint32 i; | MI_Uint32 i; |
| |
/* Check for null arguments */ | /* Check for null arguments */ |
if (!self || !buf) | if (!self || !buf) |
MI_RETURN(MI_RESULT_INVALID_PARAMETER); | MI_RETURN(MI_RESULT_INVALID_PARAMETER); |
| |
|
cd = (MI_ClassDecl*)self->classDecl; |
|
|
/* Pack magic number */ | /* Pack magic number */ |
MI_RETURN_ERR(Buf_PackU32(buf, INSTANCE_MAGIC)); | MI_RETURN_ERR(Buf_PackU32(buf, INSTANCE_MAGIC)); |
| |
|
|
MI_RETURN_ERR(Buf_PackU32(buf, cd->flags)); | MI_RETURN_ERR(Buf_PackU32(buf, cd->flags)); |
| |
/* Pack the classname */ | /* Pack the classname */ |
MI_RETURN_ERR(Buf_PackStr(buf, cd->name)); |
MI_RETURN_ERR(Buf_PackStrLen(buf, cd->name, NameLen(cd->name, cd->code))); |
| |
/* namespace */ | /* namespace */ |
MI_RETURN_ERR(Buf_PackStr(buf, self->nameSpace)); | MI_RETURN_ERR(Buf_PackStr(buf, self->nameSpace)); |
|
|
{ | { |
const MI_PropertyDecl* pd = cd->properties[i]; | const MI_PropertyDecl* pd = cd->properties[i]; |
const void* value = (char*)self + pd->offset; | const void* value = (char*)self + pd->offset; |
|
MI_Char* pName; |
| |
/* Skip non-key properties (for references) */ | /* Skip non-key properties (for references) */ |
if (keysOnly && (pd->flags & MI_FLAG_KEY) == 0) | if (keysOnly && (pd->flags & MI_FLAG_KEY) == 0) |
|
|
/* Pack the flags */ | /* Pack the flags */ |
MI_RETURN_ERR(Buf_PackU32(buf, pd->flags)); | MI_RETURN_ERR(Buf_PackU32(buf, pd->flags)); |
| |
|
pName = pd->name; |
|
if ((pd->flags & MI_FLAG_PARAMETER) && (pd->flags & MI_FLAG_OUT)) |
|
{ |
|
if (pName && pName[0] == ZT('M') && Tcscmp(pName, ZT("MIReturn"))== 0) |
|
pName = ZT("ReturnValue"); |
|
} |
|
|
/* Pack the propety name */ | /* Pack the propety name */ |
MI_RETURN_ERR(Buf_PackStr(buf, pd->name)); |
MI_RETURN_ERR(Buf_PackStrLen( |
|
buf, pName, NameLen(pName, pd->code))); |
| |
/* Pack the propety type */ | /* Pack the propety type */ |
MI_RETURN_ERR(Buf_PackU32(buf, pd->type)); | MI_RETURN_ERR(Buf_PackU32(buf, pd->type)); |
|
|
{ | { |
MI_Uint32 magic; | MI_Uint32 magic; |
MI_Uint32 flags; | MI_Uint32 flags; |
const MI_Char* className; |
const ZChar* className; |
const MI_Char* nameSpace = 0; |
const ZChar* nameSpace = 0; |
MI_Instance* self; | MI_Instance* self; |
| |
/* Check parameters */ | /* Check parameters */ |
|
|
| |
for (i = 0; i < numProperties; i++) | for (i = 0; i < numProperties; i++) |
{ | { |
const MI_Char* name; |
const ZChar* name; |
MI_Uint32 type, prop_flags; | MI_Uint32 type, prop_flags; |
MI_Value value; | MI_Value value; |
const MI_Value* valuePtr; | const MI_Value* valuePtr; |
|
|
| |
MI_Result InstanceToBatch( | MI_Result InstanceToBatch( |
const MI_Instance* instance, | const MI_Instance* instance, |
MI_Boolean (*filterProperty)(const MI_Char* name, void* data), |
MI_Boolean (*filterProperty)(const ZChar* name, void* data), |
void* filterPropertyData, | void* filterPropertyData, |
Batch* batch, | Batch* batch, |
void** ptrOut, | void** ptrOut, |