1726 líneas
45 KiB
C
1726 líneas
45 KiB
C
#include "cmPrefix.h"
|
|
#include "cmGlobal.h"
|
|
#include "cmRpt.h"
|
|
#include "cmErr.h"
|
|
#include "cmCtx.h"
|
|
#include "cmMem.h"
|
|
#include "cmMallocDebug.h"
|
|
#include "cmLinkedHeap.h"
|
|
#include "cmSerialize.h"
|
|
|
|
|
|
#define cmSrVersion (0)
|
|
|
|
#ifdef cmBIG_ENDIAN
|
|
#define _cmSrSwap16(v) (v)
|
|
#define _cmSrSwap32(v) (v)
|
|
#define _cmSrSwapFl (0)
|
|
#else
|
|
#define _cmSrSwap16(v) (v)
|
|
#define _cmSrSwap32(v) (v)
|
|
#define _cmSrSwapFl (1)
|
|
#endif
|
|
|
|
|
|
typedef struct
|
|
{
|
|
const char* label;
|
|
unsigned typeId;
|
|
unsigned byteCnt;
|
|
bool swapFl;
|
|
} _cmSrPrim_t;
|
|
|
|
|
|
struct _cmSrStruct_str;
|
|
|
|
// structure field desc record
|
|
typedef struct _cmSrField_str
|
|
{
|
|
const _cmSrPrim_t* primPtr;
|
|
struct _cmSrStruct_str* structPtr;
|
|
bool arrayFl;
|
|
struct _cmSrField_str* linkPtr;
|
|
} _cmSrField_t;
|
|
|
|
// structure description record
|
|
typedef struct _cmSrStruct_str
|
|
{
|
|
unsigned typeId;
|
|
_cmSrField_t* fieldList;
|
|
struct _cmSrStruct_str* linkPtr;
|
|
} _cmSrStruct_t;
|
|
|
|
// state records track the format for read/write operations
|
|
typedef struct _cmSrState_str
|
|
{
|
|
_cmSrStruct_t* structPtr; // this states current structure
|
|
_cmSrField_t* fieldPtr; // this states current field
|
|
struct _cmSrState_str* linkPtr; // prev state on stack
|
|
unsigned arrayCnt; // array count for this struct array
|
|
unsigned arrayIdx; // current array index for this struct array
|
|
} _cmSrState_t;
|
|
|
|
// data records are formed by each write operation
|
|
typedef struct _cmSrData_str
|
|
{
|
|
unsigned typeId;
|
|
unsigned eleCnt;
|
|
unsigned byteCnt;
|
|
void* dataPtr;
|
|
bool arrayFl;
|
|
bool swapFl;
|
|
struct _cmSrData_str* linkPtr;
|
|
} _cmSrData_t;
|
|
|
|
|
|
typedef struct
|
|
{
|
|
cmErr_t err;
|
|
|
|
cmLHeapH_t lhH;
|
|
|
|
_cmSrStruct_t* structList;
|
|
|
|
_cmSrState_t* wrStackPtr;
|
|
_cmSrData_t* wrDataList;
|
|
char* wrDataBufPtr;
|
|
unsigned wrDataBufByteCnt;
|
|
|
|
_cmSrState_t* rdStackPtr;
|
|
const void* rdDataBufPtr;
|
|
unsigned rdDataBufByteCnt;
|
|
const char* rdCursorPtr;
|
|
unsigned rdVersion;
|
|
unsigned rdFlags;
|
|
|
|
cmSrRC_t lastRC;
|
|
|
|
} _cmSr_t;
|
|
|
|
_cmSrPrim_t _cmSrPrimArray[] =
|
|
{
|
|
{"char", kCharSrId, sizeof(char), false },
|
|
{"uchar", kUCharSrId, sizeof(char), false },
|
|
{"short", kShortSrId, sizeof(short), true },
|
|
{"ushort", kUShortSrId, sizeof(unsigned short), true },
|
|
{"int", kIntSrId, sizeof(int), true },
|
|
{"uint", kUIntSrId, sizeof(unsigned), true },
|
|
{"long", kLongSrId, sizeof(long), true },
|
|
{"ulong", kLongSrId, sizeof(unsigned long), true },
|
|
{"float", kFloatSrId, sizeof(float), false },
|
|
{"double", kDoubleSrId, sizeof(double), false },
|
|
{"bool", kBoolSrId, sizeof(bool), sizeof(bool)>1 },
|
|
{"<invalid>", kInvalidSrId, 0, false }
|
|
};
|
|
|
|
cmSrH_t cmSrNullHandle = { NULL };
|
|
|
|
|
|
void _cmSrPrint( _cmSr_t* p, const char* fmt, ... )
|
|
{
|
|
va_list vl;
|
|
va_start(vl,fmt);
|
|
//p->rptFuncPtr(p->rptUserPtr,fmt,vl);
|
|
cmRptVPrintf( p->err.rpt, fmt, vl );
|
|
va_end(vl);
|
|
}
|
|
|
|
/*
|
|
cmSrRC_t _cmSrErrorV( cmSrRC_t rc, _cmSr_t* p, const char* fmt, va_list vl )
|
|
{
|
|
const int bufCharCnt = 511;
|
|
char buf[bufCharCnt+1];
|
|
snprintf(buf,bufCharCnt,"Serializer Error code:%i ",rc);
|
|
unsigned n = strlen(buf);
|
|
vsnprintf(buf+n,bufCharCnt-n,fmt,vl);
|
|
buf[bufCharCnt]=0;
|
|
_cmSrPrint(p,"%s\n",buf);
|
|
p->lastRC = rc;
|
|
return rc;
|
|
}
|
|
*/
|
|
|
|
cmSrRC_t _cmSrError( cmSrRC_t rc, _cmSr_t* p, const char* fmt, ... )
|
|
{
|
|
va_list vl;
|
|
va_start(vl,fmt);
|
|
cmErrVMsg(&p->err,rc,fmt,vl);
|
|
va_end(vl);
|
|
return rc;
|
|
}
|
|
|
|
_cmSr_t* _cmSrHandleToPtr( cmSrH_t h )
|
|
{
|
|
assert( h.h != NULL );
|
|
return (_cmSr_t*)h.h;
|
|
}
|
|
|
|
const _cmSrPrim_t* _cmSrIdToPrimPtr( unsigned primId )
|
|
{
|
|
unsigned i;
|
|
for(i=0; _cmSrPrimArray[i].typeId != kInvalidSrId; ++i)
|
|
if( _cmSrPrimArray[i].typeId == primId )
|
|
return _cmSrPrimArray + i;
|
|
|
|
return NULL;
|
|
}
|
|
|
|
_cmSrStruct_t* _cmSrIdToStructPtr( _cmSr_t* p, unsigned typeId )
|
|
{
|
|
_cmSrStruct_t* sp = p->structList;
|
|
for(; sp != NULL; sp = sp->linkPtr )
|
|
if( sp->typeId == typeId )
|
|
return sp;
|
|
return NULL;
|
|
}
|
|
|
|
void _cmSrClearStructList( _cmSr_t* p )
|
|
{
|
|
_cmSrStruct_t* csp = p->structList;
|
|
while( csp != NULL )
|
|
{
|
|
_cmSrStruct_t* nsp = csp->linkPtr;
|
|
|
|
_cmSrField_t* cfp = csp->fieldList;
|
|
|
|
while( cfp != NULL )
|
|
{
|
|
_cmSrField_t* nfp = cfp->linkPtr;
|
|
|
|
cmLHeapFree(p->lhH,cfp);
|
|
|
|
cfp = nfp;
|
|
}
|
|
|
|
|
|
cmLHeapFree(p->lhH,csp);
|
|
|
|
csp = nsp;
|
|
}
|
|
|
|
p->structList = NULL;
|
|
}
|
|
|
|
void _cmSrClearDataList( _cmSr_t* p )
|
|
{
|
|
|
|
_cmSrData_t* cdp = p->wrDataList;
|
|
|
|
while( cdp != NULL )
|
|
{
|
|
_cmSrData_t* ndp = cdp->linkPtr;
|
|
|
|
cmLHeapFree( p->lhH, cdp );
|
|
|
|
cdp = ndp;
|
|
}
|
|
|
|
p->wrDataList = NULL;
|
|
}
|
|
|
|
cmSrRC_t _cmSrPopStateStack( _cmSr_t* p, _cmSrState_t** stackPtrPtr )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSrState_t* stackPtr = *stackPtrPtr;
|
|
_cmSrState_t* sp = stackPtr;
|
|
|
|
assert( sp != NULL );
|
|
|
|
stackPtr = sp->linkPtr;
|
|
|
|
if( sp->arrayCnt != cmInvalidCnt && sp->arrayIdx != sp->arrayCnt )
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "A type %i structure array field promised %i elements but only %i written.",sp->structPtr->typeId,sp->arrayCnt,sp->arrayIdx);
|
|
|
|
cmLHeapFree(p->lhH,sp);
|
|
*stackPtrPtr = stackPtr;
|
|
|
|
return rc;
|
|
}
|
|
|
|
void _cmSrClearStateStack( _cmSr_t* p, _cmSrState_t** stackPtrPtr )
|
|
{
|
|
while( *stackPtrPtr != NULL )
|
|
if( _cmSrPopStateStack( p, stackPtrPtr ) != kOkSrRC )
|
|
break;
|
|
}
|
|
|
|
|
|
cmSrRC_t _cmSrFree( _cmSr_t* p )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
|
|
_cmSrClearDataList(p);
|
|
_cmSrClearStateStack(p,&p->wrStackPtr);
|
|
_cmSrClearStateStack(p,&p->rdStackPtr);
|
|
cmMemPtrFree(&p->wrDataBufPtr);
|
|
cmLHeapDestroy( &p->lhH );
|
|
|
|
cmMemPtrFree(&p);
|
|
return rc;
|
|
}
|
|
|
|
|
|
cmSrRC_t cmSrAlloc( cmSrH_t* hp, cmCtx_t* ctx )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = cmMemAllocZ( _cmSr_t, 1 );
|
|
|
|
cmErrSetup(&p->err,&ctx->rpt,"Serializer");
|
|
|
|
p->structList = NULL;
|
|
p->lastRC = kOkSrRC;
|
|
|
|
if( cmLHeapIsValid( p->lhH = cmLHeapCreate(1024,ctx)) == false )
|
|
{
|
|
rc = _cmSrError( kLHeapFailSrRC, p, "Linked heap initialization failed.");
|
|
goto errLabel;
|
|
}
|
|
|
|
hp->h = p;
|
|
errLabel:
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t cmSrFree( cmSrH_t* hp )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = NULL;
|
|
|
|
if( hp == NULL )
|
|
return kOkSrRC;
|
|
|
|
if( cmSrIsValid(*hp) == false )
|
|
return kOkSrRC;
|
|
|
|
p = _cmSrHandleToPtr(*hp);
|
|
|
|
if(( rc = _cmSrFree(p)) != kOkSrRC )
|
|
goto errLabel;
|
|
|
|
hp->h = NULL;
|
|
|
|
errLabel:
|
|
return rc;
|
|
}
|
|
|
|
bool cmSrIsValid( cmSrH_t h )
|
|
{ return h.h != NULL; }
|
|
|
|
cmSrRC_t cmSrLastErrorCode( cmSrH_t h )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
return p->lastRC;
|
|
}
|
|
|
|
cmSrRC_t cmSrGetAndClearLastErrorCode( cmSrH_t h )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
cmSrRC_t rc = p->lastRC;
|
|
p->lastRC = kOkSrRC;
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t cmSrFmtReset( cmSrH_t h )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
|
|
_cmSrClearStructList(p);
|
|
|
|
p->lastRC = kOkSrRC;
|
|
|
|
return cmSrWrReset(h);
|
|
}
|
|
|
|
cmSrRC_t cmSrFmtDefineStruct( cmSrH_t h, unsigned structTypeId )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
_cmSrStruct_t* structPtr = NULL;
|
|
|
|
assert( structTypeId >= kStructSrId );
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return p->lastRC;
|
|
|
|
if( structTypeId < kStructSrId )
|
|
{
|
|
rc = _cmSrError( kParamErrSrRC, p, "The structure type id %i is no greater than or equal to %i. (kStructSrId)",structTypeId,kStructSrId );
|
|
goto errLabel;
|
|
}
|
|
|
|
if( _cmSrIdToStructPtr( p, structTypeId ) != NULL)
|
|
{
|
|
rc = _cmSrError( kParamErrSrRC, p, "The structure type id %i is already in use.",structTypeId );
|
|
goto errLabel;
|
|
}
|
|
|
|
if(( structPtr = (_cmSrStruct_t*)cmLHeapAllocZ( p->lhH, sizeof(_cmSrStruct_t))) == NULL )
|
|
{
|
|
rc = _cmSrError( kLHeapFailSrRC, p, "New structure allocate failed.");
|
|
goto errLabel;
|
|
}
|
|
|
|
structPtr->typeId = structTypeId;
|
|
structPtr->linkPtr = p->structList;
|
|
p->structList = structPtr;
|
|
|
|
errLabel:
|
|
return rc;
|
|
|
|
}
|
|
|
|
|
|
cmSrRC_t _cmSrFmtField( cmSrH_t h, unsigned typeId, bool arrayFl )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSrStruct_t* structPtr = NULL;
|
|
const _cmSrPrim_t* primPtr = NULL;
|
|
_cmSrField_t* fieldPtr = NULL;
|
|
_cmSrField_t* cfp = NULL;
|
|
_cmSrField_t* pfp = NULL;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return p->lastRC;
|
|
|
|
if( typeId >= kStructSrId )
|
|
{
|
|
if(( structPtr = _cmSrIdToStructPtr( p, typeId )) == NULL )
|
|
{
|
|
rc = _cmSrError( kParamErrSrRC, p, "The structure associated with the type id %i could not be found.",typeId);
|
|
goto errLabel;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if( (typeId==kInvalidSrId) || ((primPtr = _cmSrIdToPrimPtr( typeId )) == NULL) )
|
|
{
|
|
rc = _cmSrError( kParamErrSrRC, p, "Type primitive type id %i is not valid.",typeId);
|
|
goto errLabel;
|
|
}
|
|
}
|
|
|
|
if(( fieldPtr = (_cmSrField_t*)cmLHeapAllocZ( p->lhH, sizeof(_cmSrField_t))) == NULL )
|
|
{
|
|
rc = _cmSrError( kLHeapFailSrRC, p, "Field allocation failed for type %i.",typeId );
|
|
goto errLabel;
|
|
}
|
|
|
|
fieldPtr->primPtr = primPtr;
|
|
fieldPtr->structPtr = structPtr;
|
|
fieldPtr->arrayFl = arrayFl;
|
|
|
|
pfp = NULL;
|
|
cfp = p->structList->fieldList;
|
|
|
|
for(; cfp != NULL; cfp = cfp->linkPtr )
|
|
pfp = cfp;
|
|
|
|
if( pfp == NULL )
|
|
p->structList->fieldList = fieldPtr;
|
|
else
|
|
pfp->linkPtr = fieldPtr;
|
|
|
|
errLabel:
|
|
return rc;
|
|
|
|
}
|
|
|
|
cmSrRC_t cmSrFmtStruct( cmSrH_t h, unsigned id ) { return _cmSrFmtField(h,id, false); }
|
|
cmSrRC_t cmSrFmtChar( cmSrH_t h ) { return _cmSrFmtField(h,kCharSrId, false); }
|
|
cmSrRC_t cmSrFmtUChar( cmSrH_t h ) { return _cmSrFmtField(h,kUCharSrId, false); }
|
|
cmSrRC_t cmSrFmtShort( cmSrH_t h ) { return _cmSrFmtField(h,kShortSrId, false); }
|
|
cmSrRC_t cmSrFmtUShort( cmSrH_t h ) { return _cmSrFmtField(h,kUShortSrId, false); }
|
|
cmSrRC_t cmSrFmtLong( cmSrH_t h ) { return _cmSrFmtField(h,kLongSrId, false); }
|
|
cmSrRC_t cmSrFmtULong( cmSrH_t h ) { return _cmSrFmtField(h,kULongSrId, false); }
|
|
cmSrRC_t cmSrFmtInt( cmSrH_t h ) { return _cmSrFmtField(h,kIntSrId, false); }
|
|
cmSrRC_t cmSrFmtUInt( cmSrH_t h ) { return _cmSrFmtField(h,kUIntSrId, false); }
|
|
cmSrRC_t cmSrFmtFloat( cmSrH_t h ) { return _cmSrFmtField(h,kFloatSrId, false); }
|
|
cmSrRC_t cmSrFmtDouble( cmSrH_t h ) { return _cmSrFmtField(h,kDoubleSrId, false); }
|
|
cmSrRC_t cmSrFmtBool( cmSrH_t h ) { return _cmSrFmtField(h,kBoolSrId, false); }
|
|
|
|
cmSrRC_t cmSrFmtStructV( cmSrH_t h, unsigned id ){ return _cmSrFmtField(h,id, true); }
|
|
cmSrRC_t cmSrFmtCharV( cmSrH_t h ) { return _cmSrFmtField(h,kCharSrId, true); }
|
|
cmSrRC_t cmSrFmtUCharV( cmSrH_t h ) { return _cmSrFmtField(h,kUCharSrId, true); }
|
|
cmSrRC_t cmSrFmtShortV( cmSrH_t h ) { return _cmSrFmtField(h,kShortSrId, true); }
|
|
cmSrRC_t cmSrFmtUShortV( cmSrH_t h ) { return _cmSrFmtField(h,kUShortSrId, true); }
|
|
cmSrRC_t cmSrFmtLongV( cmSrH_t h ) { return _cmSrFmtField(h,kLongSrId, true); }
|
|
cmSrRC_t cmSrFmtULongV( cmSrH_t h ) { return _cmSrFmtField(h,kULongSrId, true); }
|
|
cmSrRC_t cmSrFmtIntV( cmSrH_t h ) { return _cmSrFmtField(h,kIntSrId, true); }
|
|
cmSrRC_t cmSrFmtUIntV( cmSrH_t h ) { return _cmSrFmtField(h,kUIntSrId, true); }
|
|
cmSrRC_t cmSrFmtFloatV( cmSrH_t h ) { return _cmSrFmtField(h,kFloatSrId, true); }
|
|
cmSrRC_t cmSrFmtDoubleV( cmSrH_t h ) { return _cmSrFmtField(h,kDoubleSrId, true); }
|
|
cmSrRC_t cmSrFmtBoolV( cmSrH_t h ) { return _cmSrFmtField(h,kBoolSrId, true); }
|
|
|
|
|
|
cmSrRC_t cmSrDefFmt( cmSrH_t h, unsigned structTypeId, ... )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
va_list vl;
|
|
va_start(vl,structTypeId);
|
|
|
|
if((rc = cmSrFmtDefineStruct( h, structTypeId )) != kOkSrRC )
|
|
goto errLabel;
|
|
|
|
unsigned typeId = kCharSrId;
|
|
|
|
while( typeId != kInvalidSrId )
|
|
{
|
|
typeId = va_arg(vl,unsigned);
|
|
|
|
if( typeId == kInvalidSrId )
|
|
break;
|
|
|
|
bool arrayFl = cmIsFlag(typeId,kArraySrFl);
|
|
|
|
typeId = cmClrFlag(typeId,kArraySrFl);
|
|
|
|
if(( rc = _cmSrFmtField(h,typeId,arrayFl)) != kOkSrRC )
|
|
goto errLabel;
|
|
|
|
}
|
|
|
|
errLabel:
|
|
va_end(vl);
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t cmSrFmtPrint( cmSrH_t h )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
cmSrRC_t rc = kOkSrRC;
|
|
|
|
|
|
const _cmSrStruct_t* sp = p->structList;
|
|
|
|
for(; sp != NULL; sp = sp->linkPtr )
|
|
{
|
|
_cmSrPrint( p, "struct: %i", sp->typeId );
|
|
unsigned indent = 2;
|
|
|
|
const _cmSrField_t* fp = sp->fieldList;
|
|
|
|
for(; fp != NULL; fp = fp->linkPtr )
|
|
{
|
|
unsigned i;
|
|
char sp[ indent+1 ];
|
|
sp[indent]=0;
|
|
for(i=0; i<indent; ++i)
|
|
sp[i] = ' ';
|
|
|
|
|
|
if( fp->primPtr != NULL )
|
|
_cmSrPrint( p, "%s prim: %i %s%s", sp, fp->primPtr->byteCnt, fp->primPtr->label, fp->arrayFl?"[]":"" );
|
|
else
|
|
{
|
|
_cmSrPrint( p, "%s struct: %i %s", sp, fp->structPtr->typeId, fp->arrayFl?"[]":"" );
|
|
indent += 2;
|
|
}
|
|
}
|
|
}
|
|
|
|
_cmSrPrint(p,"\n");
|
|
|
|
return rc;
|
|
}
|
|
|
|
|
|
|
|
cmSrRC_t _cmSrPushStateStack( _cmSr_t* p, unsigned structTypeId, _cmSrState_t** stackPtrPtr )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
|
|
_cmSrStruct_t* refStructPtr;
|
|
|
|
_cmSrState_t* stackPtr = *stackPtrPtr;
|
|
|
|
// if this is the base structure then the wr stack will be empty
|
|
if( stackPtr == NULL )
|
|
refStructPtr = p->structList;
|
|
else
|
|
{
|
|
// the wr stack contains members so this structure type should be the same as the current field type
|
|
assert( stackPtr->fieldPtr != NULL );
|
|
refStructPtr = stackPtr->fieldPtr->structPtr;
|
|
}
|
|
|
|
// no reference structure exists
|
|
if( refStructPtr == NULL )
|
|
{
|
|
// if the write state stack is empty then the structList must also be empty
|
|
if( stackPtr == NULL )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "Cannot write data without first providing the data format.");
|
|
goto errLabel;
|
|
}
|
|
else
|
|
{
|
|
// the data format has been described but the current format field is not a structure
|
|
assert( stackPtr->fieldPtr->primPtr != NULL );
|
|
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "Format violation. Expected primitive type:'%s'.", cmStringNullGuard(stackPtr->fieldPtr->primPtr->label ));
|
|
goto errLabel;
|
|
}
|
|
}
|
|
|
|
// if wrong type of structure
|
|
if( refStructPtr->typeId != structTypeId )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "Format violation. Expected structure type:%i instead of structure type:%i.",refStructPtr->typeId,structTypeId );
|
|
goto errLabel;
|
|
|
|
}
|
|
|
|
// allocate the new structure state
|
|
_cmSrState_t* wsp = (_cmSrState_t*)cmLHeapAllocZ( p->lhH, sizeof(_cmSrState_t));
|
|
assert( wsp != NULL );
|
|
|
|
// push the new structure state on the stack
|
|
wsp->structPtr = refStructPtr;
|
|
wsp->fieldPtr = NULL;
|
|
wsp->linkPtr = stackPtr;
|
|
wsp->arrayCnt = cmInvalidCnt;
|
|
wsp->arrayIdx = cmInvalidIdx;
|
|
stackPtr = wsp;
|
|
|
|
*stackPtrPtr = stackPtr;
|
|
|
|
errLabel:
|
|
return rc;
|
|
}
|
|
|
|
|
|
cmSrRC_t cmSrWrReset( cmSrH_t h )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
|
|
_cmSrClearStateStack(p,&p->wrStackPtr);
|
|
p->wrStackPtr = NULL;
|
|
|
|
_cmSrClearDataList(p);
|
|
|
|
cmMemPtrFree(&p->wrDataBufPtr);
|
|
p->wrDataBufByteCnt = 0;
|
|
|
|
|
|
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t _cmSrOnStruct( _cmSr_t* p, unsigned structTypeId, _cmSrState_t** stackPtrPtr )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return p->lastRC;
|
|
|
|
if((rc = _cmSrPushStateStack(p,structTypeId,stackPtrPtr)) != kOkSrRC )
|
|
goto errLabel;
|
|
|
|
_cmSrState_t* stackPtr = *stackPtrPtr;
|
|
|
|
// the base structure is never an array so it's linkPtr is NULL
|
|
if( stackPtr->linkPtr != NULL )
|
|
{
|
|
stackPtr->linkPtr->arrayIdx += 1;
|
|
|
|
if( stackPtr->linkPtr->arrayIdx > stackPtr->linkPtr->arrayCnt )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "The structure array is out of bounds (array count:%i).",stackPtr->linkPtr->arrayIdx );
|
|
goto errLabel;
|
|
}
|
|
}
|
|
|
|
*stackPtrPtr = stackPtr;
|
|
|
|
errLabel:
|
|
return rc;
|
|
|
|
}
|
|
|
|
cmSrRC_t cmSrWrStructBegin( cmSrH_t h, unsigned structTypeId )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
return _cmSrOnStruct( p, structTypeId, &p->wrStackPtr );
|
|
}
|
|
|
|
cmSrRC_t cmSrWrStructEnd( cmSrH_t h )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
assert( p->wrStackPtr != NULL );
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return p->lastRC;
|
|
|
|
return _cmSrPopStateStack(p, &p->wrStackPtr);
|
|
}
|
|
|
|
|
|
cmSrRC_t _cmSrWrField( cmSrH_t h, unsigned typeId, const void* dataPtr, unsigned eleCnt )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
_cmSrField_t* refFieldPtr = NULL;
|
|
unsigned refTypeId = cmInvalidId;
|
|
unsigned dataByteCnt = 0;
|
|
_cmSrData_t* dataRecdPtr = NULL;
|
|
bool swapFl = false;
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return p->lastRC;
|
|
|
|
// verify the write stack exists
|
|
if( p->wrStackPtr == NULL )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "The reference format is unexpectedly empty.");
|
|
goto errLabel;
|
|
}
|
|
|
|
//
|
|
// advance the current field
|
|
//
|
|
|
|
// if cur state fieldPtr is NULL then this is the first field in a structure
|
|
if( p->wrStackPtr->fieldPtr == NULL )
|
|
p->wrStackPtr->fieldPtr = p->wrStackPtr->structPtr->fieldList;
|
|
else
|
|
p->wrStackPtr->fieldPtr = p->wrStackPtr->fieldPtr->linkPtr;
|
|
|
|
// verify that a reference field exists
|
|
refFieldPtr = p->wrStackPtr->fieldPtr;
|
|
|
|
if( refFieldPtr == NULL )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "The format reference structure has run out of fields.");
|
|
goto errLabel;
|
|
}
|
|
|
|
// validate the array status of this field
|
|
if( refFieldPtr->arrayFl==false && eleCnt>1 )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "The format reference indicates that this field is not an array however an array element count (%i) was given.",eleCnt);
|
|
goto errLabel;
|
|
}
|
|
|
|
// get the reference type id
|
|
refTypeId = refFieldPtr->primPtr == NULL ? refFieldPtr->structPtr->typeId : refFieldPtr->primPtr->typeId;
|
|
|
|
|
|
// verify that the type being written matches the reference type
|
|
if( refTypeId != typeId )
|
|
{
|
|
const char* refLbl = "struct";
|
|
const char* cmtLbl = refLbl;
|
|
|
|
if( refFieldPtr->primPtr != NULL )
|
|
refLbl = refFieldPtr->primPtr->label;
|
|
|
|
if( typeId < kStructSrId )
|
|
cmtLbl = _cmSrIdToPrimPtr( typeId )->label;
|
|
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "Format violation: Exepected type %i (%s) but received %i (%s).", refTypeId,refLbl,typeId,cmtLbl);
|
|
goto errLabel;
|
|
}
|
|
|
|
if( typeId < kStructSrId )
|
|
{
|
|
dataByteCnt += refFieldPtr->primPtr->byteCnt * eleCnt;
|
|
swapFl = refFieldPtr->primPtr->swapFl && _cmSrSwapFl;
|
|
}
|
|
else
|
|
{
|
|
p->wrStackPtr->arrayCnt = eleCnt;
|
|
p->wrStackPtr->arrayIdx = 0;
|
|
}
|
|
|
|
dataRecdPtr = (_cmSrData_t*)cmLHeapAllocZ( p->lhH, sizeof(_cmSrData_t) + dataByteCnt );
|
|
|
|
// iniit the new data recd
|
|
dataRecdPtr->typeId = typeId;
|
|
dataRecdPtr->eleCnt = eleCnt;
|
|
dataRecdPtr->byteCnt = dataByteCnt;
|
|
dataRecdPtr->arrayFl = refFieldPtr->arrayFl;
|
|
dataRecdPtr->swapFl = swapFl;
|
|
dataRecdPtr->linkPtr = NULL;
|
|
dataRecdPtr->dataPtr = dataRecdPtr + 1;
|
|
|
|
if( dataByteCnt > 0 )
|
|
memcpy( dataRecdPtr->dataPtr, dataPtr, dataByteCnt );
|
|
|
|
// link the new data recd to the end of the data chain
|
|
_cmSrData_t* dp = p->wrDataList;
|
|
for(; dp != NULL; dp = dp->linkPtr )
|
|
if( dp->linkPtr == NULL )
|
|
break;
|
|
|
|
if( p->wrDataList == NULL )
|
|
p->wrDataList = dataRecdPtr;
|
|
else
|
|
dp->linkPtr = dataRecdPtr;
|
|
|
|
errLabel:
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t cmSrWrStruct( cmSrH_t h, unsigned structTypeId, unsigned eleCnt )
|
|
{ return _cmSrWrField(h,structTypeId,NULL,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrChar( cmSrH_t h, char val )
|
|
{ return _cmSrWrField(h,kCharSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrUChar( cmSrH_t h, unsigned char val )
|
|
{ return _cmSrWrField(h,kUCharSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrShort( cmSrH_t h, short val )
|
|
{ return _cmSrWrField(h,kShortSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrUShort( cmSrH_t h, unsigned short val )
|
|
{ return _cmSrWrField(h,kUShortSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrLong( cmSrH_t h, long val )
|
|
{ return _cmSrWrField(h,kLongSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrULong( cmSrH_t h, unsigned long val )
|
|
{ return _cmSrWrField(h,kULongSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrInt( cmSrH_t h, int val )
|
|
{ return _cmSrWrField(h,kIntSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrUInt( cmSrH_t h, unsigned val )
|
|
{ return _cmSrWrField(h,kUIntSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrFloat( cmSrH_t h, float val )
|
|
{ return _cmSrWrField(h,kFloatSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrDouble( cmSrH_t h, double val )
|
|
{ return _cmSrWrField(h,kDoubleSrId,&val,1); }
|
|
|
|
cmSrRC_t cmSrWrBool( cmSrH_t h, bool val )
|
|
{ return _cmSrWrField(h,kBoolSrId,&val,1); }
|
|
|
|
|
|
cmSrRC_t cmSrWrStr( cmSrH_t h, const char* val )
|
|
{
|
|
const char* ns = "";
|
|
if( val == NULL )
|
|
val = ns;
|
|
return _cmSrWrField(h,kCharSrId,val,strlen(val)+1);
|
|
}
|
|
|
|
cmSrRC_t _cmSrWrArrayField( cmSrH_t h, unsigned typeId, const void* val, unsigned eleCnt )
|
|
{
|
|
if( val == NULL || eleCnt == 0 )
|
|
{
|
|
val = NULL;
|
|
eleCnt = 0;
|
|
}
|
|
|
|
return _cmSrWrField(h,typeId,val,eleCnt);
|
|
}
|
|
|
|
cmSrRC_t cmSrWrCharV( cmSrH_t h, const char* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kCharSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrUCharV( cmSrH_t h, const unsigned char* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kUCharSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrShortV( cmSrH_t h, const short* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kShortSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrUShortV( cmSrH_t h, const unsigned short* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kUShortSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrLongV( cmSrH_t h, const long* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kLongSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrULongV( cmSrH_t h, const unsigned long* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kULongSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrIntV( cmSrH_t h, const int* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kIntSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrUIntV( cmSrH_t h, const unsigned* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kUIntSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrFloatV( cmSrH_t h, const float* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kFloatSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrDoubleV( cmSrH_t h, const double* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kDoubleSrId,val,eleCnt); }
|
|
|
|
cmSrRC_t cmSrWrBoolV( cmSrH_t h, const bool* val, unsigned eleCnt )
|
|
{ return _cmSrWrArrayField(h,kBoolSrId,val,eleCnt); }
|
|
|
|
|
|
void _cmSrCopyDataToBuf( void* dstPtr, const void* srcPtr, unsigned byteCnt, unsigned typeId, bool swapFl, unsigned eleCnt )
|
|
{
|
|
|
|
if( !swapFl )
|
|
{
|
|
memcpy(dstPtr,srcPtr,byteCnt);
|
|
return;
|
|
}
|
|
|
|
switch( typeId )
|
|
{
|
|
case kShortSrId:
|
|
case kUShortSrId:
|
|
{
|
|
unsigned i;
|
|
const short* sp = (const short*)srcPtr;
|
|
short* dp = (short*)dstPtr;
|
|
for(i=0; i<eleCnt; ++i)
|
|
dp[i] = _cmSrSwap16(sp[i]);
|
|
}
|
|
break;
|
|
|
|
case kLongSrId:
|
|
case kULongSrId:
|
|
case kIntSrId:
|
|
case kUIntSrId:
|
|
{
|
|
unsigned i;
|
|
const long* sp = (const long*)srcPtr;
|
|
long* dp = (long*)dstPtr;
|
|
for(i=0; i<eleCnt; ++i)
|
|
dp[i] = _cmSrSwap32(sp[i]);
|
|
}
|
|
break;
|
|
|
|
default:
|
|
assert(0);
|
|
}
|
|
}
|
|
|
|
void* cmSrWrAllocBuf( cmSrH_t h, unsigned* bufByteCntPtr )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
_cmSrData_t* cdp = p->wrDataList;;
|
|
|
|
assert( bufByteCntPtr != NULL );
|
|
|
|
*bufByteCntPtr = 0;
|
|
p->wrDataBufByteCnt = 2 * sizeof(unsigned); // header words
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return NULL;
|
|
|
|
|
|
// determine the data buf size
|
|
for(; cdp!=NULL; cdp = cdp->linkPtr )
|
|
{
|
|
// include spcme for structure type id
|
|
if( cdp->typeId >= kStructSrId )
|
|
p->wrDataBufByteCnt += sizeof(unsigned);
|
|
|
|
// include spcme for array element count
|
|
if( cdp->arrayFl )
|
|
p->wrDataBufByteCnt += sizeof(unsigned);
|
|
|
|
// include spcme for cmtual data
|
|
p->wrDataBufByteCnt += cdp->byteCnt;
|
|
|
|
}
|
|
|
|
// allocate the data buffer
|
|
p->wrDataBufPtr = cmMemResizeZ( char, p->wrDataBufPtr, p->wrDataBufByteCnt );
|
|
|
|
cdp = p->wrDataList;
|
|
|
|
char* dp = p->wrDataBufPtr;
|
|
char* ep = dp + p->wrDataBufByteCnt;
|
|
|
|
// header version
|
|
*(unsigned*)dp = _cmSrSwap32(cmSrVersion);
|
|
dp += sizeof(unsigned);
|
|
|
|
// header flags
|
|
*(unsigned*)dp = _cmSrSwap32(0);
|
|
dp += sizeof(unsigned);
|
|
|
|
// fill the data buffer
|
|
for(; cdp!=NULL; cdp=cdp->linkPtr)
|
|
{
|
|
// structure data records contain only the typeId and optionally an array count
|
|
if( cdp->typeId >= kStructSrId )
|
|
{
|
|
*((unsigned*)dp) = _cmSrSwap32(cdp->typeId);
|
|
dp += sizeof(unsigned);
|
|
assert(dp <= ep);
|
|
}
|
|
|
|
// array data elements begin with a element count
|
|
if( cdp->arrayFl )
|
|
{
|
|
*((unsigned*)dp) = _cmSrSwap32(cdp->eleCnt);
|
|
dp += sizeof(unsigned);
|
|
assert(dp <= ep);
|
|
}
|
|
|
|
// copy data into buf
|
|
if( cdp->byteCnt > 0 )
|
|
{
|
|
assert( cdp->typeId < kStructSrId );
|
|
_cmSrCopyDataToBuf(dp, cdp->dataPtr, cdp->byteCnt, cdp->typeId, cdp->swapFl, cdp->eleCnt );
|
|
//memcpy( dp, cdp->dataPtr, cdp->byteCnt );
|
|
dp += cdp->byteCnt;
|
|
assert(dp <= ep);
|
|
}
|
|
|
|
}
|
|
|
|
*bufByteCntPtr = p->wrDataBufByteCnt;
|
|
|
|
_cmSrClearDataList(p);
|
|
|
|
return p->wrDataBufPtr;
|
|
}
|
|
|
|
void* cmSrWrGetBuf( cmSrH_t h, unsigned* bufByteCntPtr )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
assert( bufByteCntPtr != NULL);
|
|
*bufByteCntPtr = p->wrDataBufByteCnt;
|
|
return p->wrDataBufPtr;
|
|
}
|
|
|
|
unsigned _cmSrProcUInt( _cmSr_t* p )
|
|
{
|
|
unsigned val = _cmSrSwap32(*(unsigned*)p->rdCursorPtr);
|
|
*(unsigned*)p->rdCursorPtr = val;
|
|
p->rdCursorPtr += sizeof(unsigned);
|
|
return val;
|
|
}
|
|
|
|
cmSrRC_t _cmSrProcBuf( _cmSr_t* p, _cmSrStruct_t* structPtr )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
const _cmSrField_t* cfp = structPtr->fieldList;
|
|
|
|
for(; cfp != NULL; cfp = cfp->linkPtr )
|
|
{
|
|
unsigned eleCnt = 1;
|
|
|
|
// if this is a structure
|
|
if( cfp->structPtr != NULL )
|
|
{
|
|
unsigned structTypeId = _cmSrProcUInt(p);
|
|
|
|
if( structTypeId != cfp->structPtr->typeId )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "Expected type id:%i encountered type id:%i",cfp->structPtr->typeId,structTypeId);
|
|
goto errLabel;
|
|
}
|
|
}
|
|
|
|
// if this is an array
|
|
if( cfp->arrayFl )
|
|
eleCnt = _cmSrProcUInt(p);
|
|
|
|
|
|
// if this is a primitive type
|
|
if( cfp->primPtr != NULL )
|
|
{
|
|
unsigned dataByteCnt = eleCnt * cfp->primPtr->byteCnt;
|
|
|
|
_cmSrCopyDataToBuf( (void*)p->rdCursorPtr, p->rdCursorPtr, dataByteCnt, cfp->primPtr->typeId, cfp->primPtr->swapFl & _cmSrSwapFl, eleCnt );
|
|
p->rdCursorPtr += dataByteCnt;
|
|
}
|
|
else // this is a structure type
|
|
{
|
|
unsigned i;
|
|
for(i=0; i<eleCnt; ++i)
|
|
if((rc = _cmSrProcBuf(p,cfp->structPtr)) != kOkSrRC )
|
|
goto errLabel;
|
|
}
|
|
}
|
|
errLabel:
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t cmSrRdProcessBuffer( cmSrH_t h, void* buf, unsigned bufByteCnt )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
|
|
p->rdDataBufPtr = buf;
|
|
p->rdDataBufByteCnt = bufByteCnt;
|
|
p->rdCursorPtr = buf;
|
|
|
|
// process the header
|
|
_cmSrProcUInt(p);
|
|
_cmSrProcUInt(p);
|
|
|
|
if((rc = _cmSrProcBuf(p,p->structList)) != kOkSrRC )
|
|
goto errLabel;
|
|
|
|
errLabel:
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t cmSrRdSetup( cmSrH_t h, const void* buf, unsigned bufByteCnt )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
|
|
p->rdDataBufPtr = buf;
|
|
p->rdDataBufByteCnt = bufByteCnt;
|
|
p->rdCursorPtr = buf;
|
|
_cmSrClearStateStack(p,&p->rdStackPtr);
|
|
p->rdStackPtr = NULL;
|
|
|
|
// buffer must at least contain a header
|
|
assert( bufByteCnt >= 2 * sizeof(unsigned) );
|
|
|
|
p->rdVersion = (*(unsigned*)p->rdCursorPtr);
|
|
p->rdCursorPtr += sizeof(unsigned);
|
|
|
|
p->rdFlags = (*(unsigned*)p->rdCursorPtr);
|
|
p->rdCursorPtr += sizeof(unsigned);
|
|
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t cmSrRdStructBegin( cmSrH_t h, unsigned structTypeId )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
|
|
return _cmSrOnStruct( p, structTypeId, &p->rdStackPtr );
|
|
}
|
|
|
|
cmSrRC_t cmSrRdStructEnd( cmSrH_t h )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
assert( p->rdStackPtr != NULL );
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return p->lastRC;
|
|
|
|
return _cmSrPopStateStack(p,&p->rdStackPtr);
|
|
}
|
|
|
|
cmSrRC_t _cmSrRead( _cmSr_t* p, unsigned typeId, const void** dataPtrPtr, unsigned* dataByteCntPtr, unsigned* eleCntPtr )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSrField_t* refFieldPtr = NULL;
|
|
unsigned refTypeId = cmInvalidId;
|
|
unsigned eleCnt = 1;
|
|
|
|
if( eleCntPtr != NULL )
|
|
*eleCntPtr = 0;
|
|
|
|
if( dataByteCntPtr != NULL )
|
|
*dataByteCntPtr = 0;
|
|
|
|
if( dataPtrPtr != NULL )
|
|
*dataPtrPtr = NULL;
|
|
|
|
if( p->lastRC != kOkSrRC )
|
|
return p->lastRC;
|
|
|
|
// verify the write stack exists - all fields exists inside structures so the stack must have at least one element
|
|
if( p->rdStackPtr == NULL )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "The reference format is unexpectedly empty.");
|
|
goto errLabel;
|
|
}
|
|
|
|
//
|
|
// advance the current field
|
|
//
|
|
|
|
// if cur state fieldPtr is NULL then this is the first field in a structure
|
|
if( p->rdStackPtr->fieldPtr == NULL )
|
|
p->rdStackPtr->fieldPtr = p->rdStackPtr->structPtr->fieldList;
|
|
else
|
|
p->rdStackPtr->fieldPtr = p->rdStackPtr->fieldPtr->linkPtr;
|
|
|
|
// verify that a reference field exists
|
|
refFieldPtr = p->rdStackPtr->fieldPtr;
|
|
|
|
if( refFieldPtr == NULL )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "The format reference structure has run out of fields.");
|
|
goto errLabel;
|
|
}
|
|
|
|
|
|
// get the reference type id
|
|
refTypeId = refFieldPtr->primPtr == NULL ? refFieldPtr->structPtr->typeId : refFieldPtr->primPtr->typeId;
|
|
|
|
// verify that the type being written matches the reference type
|
|
if( refTypeId != typeId )
|
|
{
|
|
const char* refLbl = "struct";
|
|
const char* cmtLbl = refLbl;
|
|
|
|
if( refFieldPtr->primPtr != NULL )
|
|
refLbl = refFieldPtr->primPtr->label;
|
|
|
|
if( typeId < kStructSrId )
|
|
cmtLbl = _cmSrIdToPrimPtr( typeId )->label;
|
|
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "Format violation: Exepected type %i (%s) but received %i (%s).", refTypeId,refLbl,typeId,cmtLbl);
|
|
goto errLabel;
|
|
}
|
|
|
|
// if this is a primitive type
|
|
if( typeId < kStructSrId )
|
|
{
|
|
unsigned byteCnt = refFieldPtr->primPtr->byteCnt;
|
|
|
|
if( refFieldPtr->arrayFl )
|
|
{
|
|
eleCnt = *(unsigned*)p->rdCursorPtr;
|
|
|
|
byteCnt *= eleCnt;
|
|
p->rdCursorPtr += sizeof(unsigned);
|
|
|
|
if( eleCntPtr == NULL )
|
|
{
|
|
rc = _cmSrError( kFormatViolationSrRC, p, "A scalar read was performed where an array was expected. type:%s array count:%i.",refFieldPtr->primPtr->label,eleCnt);
|
|
goto errLabel;
|
|
}
|
|
|
|
*eleCntPtr = eleCnt;
|
|
}
|
|
|
|
*dataPtrPtr = p->rdCursorPtr;
|
|
*dataByteCntPtr = byteCnt;
|
|
p->rdCursorPtr += byteCnt;
|
|
|
|
}
|
|
else // this is a structure type
|
|
{
|
|
unsigned structTypeId = structTypeId = *(unsigned*)p->rdCursorPtr;
|
|
|
|
p->rdCursorPtr += sizeof(unsigned);
|
|
|
|
if( refFieldPtr->arrayFl )
|
|
{
|
|
eleCnt = *(unsigned*)p->rdCursorPtr;
|
|
p->rdCursorPtr += sizeof(unsigned);
|
|
}
|
|
|
|
p->rdStackPtr->arrayCnt = eleCnt;
|
|
p->rdStackPtr->arrayIdx = 0;
|
|
|
|
assert(eleCntPtr != NULL );
|
|
*eleCntPtr = eleCnt;
|
|
}
|
|
|
|
errLabel:
|
|
return rc;
|
|
}
|
|
|
|
|
|
cmSrRC_t cmSrReadStruct( cmSrH_t h, unsigned structTypeId, unsigned* arrayCnt )
|
|
{
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
return _cmSrRead(p, structTypeId, NULL, NULL, arrayCnt );
|
|
}
|
|
|
|
|
|
|
|
cmSrRC_t _cmSrReadScalar( cmSrH_t h, unsigned typeId, void* valPtr, unsigned scalarByteCnt )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
const void* dataPtr = NULL;
|
|
unsigned dataByteCnt = 0;
|
|
|
|
|
|
if((rc= _cmSrRead(p,typeId, &dataPtr, &dataByteCnt, NULL )) != kOkSrRC )
|
|
return rc;
|
|
|
|
memcpy(valPtr,dataPtr,dataByteCnt);
|
|
|
|
return rc;
|
|
}
|
|
|
|
cmSrRC_t _cmSrReadV( cmSrH_t h, unsigned typeId, const void** valPtrPtr, unsigned scalarByteCnt, unsigned* eleCntPtr )
|
|
{
|
|
cmSrRC_t rc = kOkSrRC;
|
|
_cmSr_t* p = _cmSrHandleToPtr(h);
|
|
unsigned dataByteCnt = 0;
|
|
|
|
if((rc= _cmSrRead(p,typeId, valPtrPtr, &dataByteCnt, eleCntPtr )) != kOkSrRC )
|
|
return rc;
|
|
|
|
assert( dataByteCnt = scalarByteCnt * (*eleCntPtr));
|
|
|
|
return rc;
|
|
}
|
|
|
|
|
|
|
|
cmSrRC_t cmSrReadChar( cmSrH_t h, char* valPtr )
|
|
{ return _cmSrReadScalar( h, kCharSrId, valPtr, sizeof(char)); }
|
|
|
|
cmSrRC_t cmSrReadUChar( cmSrH_t h, unsigned char* valPtr )
|
|
{ return _cmSrReadScalar( h, kUCharSrId, valPtr, sizeof(unsigned char)); }
|
|
|
|
cmSrRC_t cmSrReadShort( cmSrH_t h, short* valPtr )
|
|
{ return _cmSrReadScalar( h, kShortSrId, valPtr, sizeof(short)); }
|
|
|
|
cmSrRC_t cmSrReadUShort( cmSrH_t h, unsigned short* valPtr )
|
|
{ return _cmSrReadScalar( h, kUShortSrId, valPtr, sizeof(unsigned short)); }
|
|
|
|
cmSrRC_t cmSrReadLong( cmSrH_t h, long* valPtr)
|
|
{ return _cmSrReadScalar( h, kLongSrId, valPtr, sizeof(long)); }
|
|
|
|
cmSrRC_t cmSrReadULong( cmSrH_t h, unsigned long* valPtr )
|
|
{ return _cmSrReadScalar( h, kULongSrId, valPtr, sizeof(unsigned long)); }
|
|
|
|
cmSrRC_t cmSrReadInt( cmSrH_t h, int* valPtr)
|
|
{ return _cmSrReadScalar( h, kIntSrId, valPtr, sizeof(int)); }
|
|
|
|
cmSrRC_t cmSrReadUInt( cmSrH_t h, unsigned* valPtr )
|
|
{ return _cmSrReadScalar( h, kUIntSrId, valPtr, sizeof(unsigned int)); }
|
|
|
|
cmSrRC_t cmSrReadFloat( cmSrH_t h, float* valPtr )
|
|
{ return _cmSrReadScalar( h, kFloatSrId, valPtr, sizeof(float)); }
|
|
|
|
cmSrRC_t cmSrReadDouble( cmSrH_t h, double* valPtr )
|
|
{ return _cmSrReadScalar( h, kDoubleSrId, valPtr, sizeof(double)); }
|
|
|
|
cmSrRC_t cmSrReadBool( cmSrH_t h, bool* valPtr )
|
|
{ return _cmSrReadScalar( h, kBoolSrId, valPtr, sizeof(bool)); }
|
|
|
|
|
|
|
|
cmSrRC_t cmSrReadCharV( cmSrH_t h, char** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kCharSrId, (const void**)valPtrPtr, sizeof(char), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadUCharV( cmSrH_t h, unsigned char** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kUCharSrId, (const void**)valPtrPtr, sizeof(unsigned char), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadShortV( cmSrH_t h, short** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kShortSrId, (const void**)valPtrPtr, sizeof(short), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadUShortV( cmSrH_t h, unsigned short** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kUShortSrId, (const void**)valPtrPtr, sizeof(unsigned short), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadLongV( cmSrH_t h, long** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kLongSrId, (const void**)valPtrPtr, sizeof(long), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadULongV( cmSrH_t h, unsigned long** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kULongSrId, (const void**)valPtrPtr, sizeof(unsigned long), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadIntV( cmSrH_t h, int** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kIntSrId, (const void**)valPtrPtr, sizeof(int), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadUIntV( cmSrH_t h, unsigned** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kUIntSrId, (const void**)valPtrPtr, sizeof(unsigned int), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadFloatV( cmSrH_t h, float** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kFloatSrId, (const void**)valPtrPtr, sizeof(float), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadDoubleV( cmSrH_t h, double** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kDoubleSrId, (const void**)valPtrPtr, sizeof(double), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadBoolV( cmSrH_t h, bool** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kBoolSrId, (const void**)valPtrPtr, sizeof(bool), eleCntPtr); }
|
|
|
|
|
|
|
|
cmSrRC_t cmSrReadCharCV( cmSrH_t h, const char** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kCharSrId, (const void**)valPtrPtr, sizeof(char), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadUCharCV( cmSrH_t h, const unsigned char** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kUCharSrId, (const void**)valPtrPtr, sizeof(unsigned char), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadShortCV( cmSrH_t h, const short** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kShortSrId, (const void**)valPtrPtr, sizeof(short), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadUShortCV( cmSrH_t h, const unsigned short** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kUShortSrId, (const void**)valPtrPtr, sizeof(unsigned short), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadLongCV( cmSrH_t h, const long** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kLongSrId, (const void**)valPtrPtr, sizeof(long), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadULongCV( cmSrH_t h, const unsigned long** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kULongSrId, (const void**)valPtrPtr, sizeof(unsigned long), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadIntCV( cmSrH_t h, const int** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kIntSrId, (const void**)valPtrPtr, sizeof(int), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadUIntCV( cmSrH_t h, const unsigned** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kUIntSrId, (const void**)valPtrPtr, sizeof(unsigned int), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadFloatCV( cmSrH_t h, const float** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kFloatSrId, (const void**)valPtrPtr, sizeof(float), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadDoubleCV( cmSrH_t h, const double** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kDoubleSrId, (const void**)valPtrPtr, sizeof(double), eleCntPtr); }
|
|
|
|
cmSrRC_t cmSrReadBoolCV( cmSrH_t h, const bool** valPtrPtr, unsigned* eleCntPtr )
|
|
{ return _cmSrReadV( h, kBoolSrId, (const void**)valPtrPtr, sizeof(bool), eleCntPtr); }
|
|
|
|
|
|
|
|
|
|
unsigned cmSrRdStruct( cmSrH_t h, unsigned structTypeId )
|
|
{
|
|
unsigned eleCnt;
|
|
return cmSrReadStruct(h,structTypeId,&eleCnt) == kOkSrRC ? eleCnt : cmInvalidCnt;
|
|
}
|
|
|
|
char cmSrRdChar( cmSrH_t h )
|
|
{
|
|
char val;
|
|
return cmSrReadChar(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
unsigned char cmSrRdUChar( cmSrH_t h )
|
|
{
|
|
unsigned char val;
|
|
return cmSrReadUChar(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
short cmSrRdShort( cmSrH_t h )
|
|
{
|
|
short val;
|
|
return cmSrReadShort(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
unsigned short cmSrRdUShort( cmSrH_t h )
|
|
{
|
|
unsigned short val;
|
|
return cmSrReadUShort(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
long cmSrRdLong( cmSrH_t h )
|
|
{
|
|
long val;
|
|
return cmSrReadLong(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
unsigned long cmSrRdULong( cmSrH_t h )
|
|
{
|
|
unsigned long val;
|
|
return cmSrReadULong(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
int cmSrRdInt( cmSrH_t h )
|
|
{
|
|
int val;
|
|
return cmSrReadInt(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
unsigned int cmSrRdUInt( cmSrH_t h )
|
|
{
|
|
unsigned val;
|
|
return cmSrReadUInt(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
float cmSrRdFloat( cmSrH_t h )
|
|
{
|
|
float val;
|
|
return cmSrReadFloat(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
double cmSrRdDouble( cmSrH_t h )
|
|
{
|
|
double val;
|
|
return cmSrReadDouble(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
bool cmSrRdBool( cmSrH_t h )
|
|
{
|
|
bool val;
|
|
return cmSrReadBool(h,&val) == kOkSrRC ? val : 0;
|
|
}
|
|
|
|
|
|
|
|
|
|
char* cmSrRdCharV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
char* valPtr;
|
|
return cmSrReadCharV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
unsigned char* cmSrRdUCharV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
unsigned char* valPtr;
|
|
return cmSrReadUCharV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
short* cmSrRdShortV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
short* valPtr;
|
|
return cmSrReadShortV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
unsigned short* cmSrRdUShortV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
unsigned short* valPtr;
|
|
return cmSrReadUShortV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
long* cmSrRdLongV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
long* valPtr;
|
|
return cmSrReadLongV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
unsigned long* cmSrRdULongV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
unsigned long* valPtr;
|
|
return cmSrReadULongV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
int* cmSrRdIntV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
int* valPtr;
|
|
return cmSrReadIntV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
unsigned int* cmSrRdUIntV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
unsigned* valPtr;
|
|
return cmSrReadUIntV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
float* cmSrRdFloatV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
float* valPtr;
|
|
return cmSrReadFloatV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
double* cmSrRdDoubleV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
double* valPtr;
|
|
return cmSrReadDoubleV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
bool* cmSrRdBoolV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
bool* valPtr;
|
|
return cmSrReadBoolV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
|
|
|
|
|
|
const char* cmSrRdCharCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const char* valPtr;
|
|
return cmSrReadCharCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const unsigned char* cmSrRdUCharCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const unsigned char* valPtr;
|
|
return cmSrReadUCharCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const short* cmSrRdShortCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const short* valPtr;
|
|
return cmSrReadShortCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const unsigned short* cmSrRdUShortCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const unsigned short* valPtr;
|
|
return cmSrReadUShortCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const long* cmSrRdLongCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const long* valPtr;
|
|
return cmSrReadLongCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const unsigned long* cmSrRdULongCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const unsigned long* valPtr;
|
|
return cmSrReadULongCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const int* cmSrRdIntCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const int* valPtr;
|
|
return cmSrReadIntCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const unsigned int* cmSrRdUIntCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const unsigned* valPtr;
|
|
return cmSrReadUIntCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const float* cmSrRdFloatCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const float* valPtr;
|
|
return cmSrReadFloatCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const double* cmSrRdDoubleCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const double* valPtr;
|
|
return cmSrReadDoubleCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
const bool* cmSrRdBoolCV( cmSrH_t h, unsigned* eleCntPtr)
|
|
{
|
|
const bool* valPtr;
|
|
return cmSrReadBoolCV(h,&valPtr,eleCntPtr) == kOkSrRC ? valPtr : NULL;
|
|
}
|
|
|
|
//{ { label:cmSerialEx }
|
|
//(
|
|
// cmSrTest() is a serializer example function.
|
|
//)
|
|
|
|
//[
|
|
|
|
cmSrRC_t cmSrTest( cmCtx_t* ctx )
|
|
{
|
|
unsigned i,j,k;
|
|
cmSrRC_t rc = kOkSrRC;
|
|
cmSrH_t h;
|
|
unsigned bufByteCnt;
|
|
const void* bufPtr;
|
|
|
|
|
|
enum
|
|
{
|
|
kVectSrId = kStructSrId, // nested structure id
|
|
kVectArrSrId // outer structure id
|
|
};
|
|
|
|
// nested structure
|
|
typedef struct
|
|
{
|
|
float* data;
|
|
unsigned cnt;
|
|
} vect;
|
|
|
|
// outer structure
|
|
typedef struct
|
|
{
|
|
unsigned cnt;
|
|
vect* vectArray;
|
|
} vectArray;
|
|
|
|
float vd0[] = { 0, 1, 2, 3, 4};
|
|
float vd1[] = { 10, 11, 12 };
|
|
unsigned vn = 2;
|
|
vect v[] = { {vd0,5}, {vd1,3} };
|
|
vectArray va = { vn, v };
|
|
|
|
if(( rc = cmSrAlloc( &h, ctx )) != kOkSrRC )
|
|
goto errLabel;
|
|
|
|
// repeat format processes to test cmSrFormatReset()
|
|
for(k=0; k<2; ++k)
|
|
{
|
|
cmSrFmtReset(h);
|
|
|
|
// Define the format of nested structures first
|
|
//
|
|
// Long Form:
|
|
// cmSrFmtDefineStruct(h,kVectSrId);
|
|
// cmSrFmtFloatV(h );
|
|
// cmSrFmtUInt(h );
|
|
//
|
|
// Short Form:
|
|
cmSrDefFmt(h, kVectSrId, kFloatVSrId, kUIntSrId, kInvalidSrId );
|
|
|
|
// Define the format of the outer structure last
|
|
//
|
|
// Long Form:
|
|
// cmSrFmtDefineStruct(h,kVectArrSrId);
|
|
// cmSrFmtUInt(h );
|
|
// cmSrFmtStructV(h, kVectSrId );
|
|
//
|
|
// Short Form:
|
|
cmSrDefFmt(h, kVectArrSrId, kUIntSrId, kVectSrId | kArraySrFl, kInvalidSrId );
|
|
|
|
cmSrFmtPrint(h);
|
|
|
|
// repeat write process to test cmSrWrReset()
|
|
for(j=0; j<2; ++j)
|
|
{
|
|
cmSrWrReset(h);
|
|
|
|
cmSrWrStructBegin( h, kVectArrSrId );
|
|
cmSrWrUInt( h, vn );
|
|
cmSrWrStruct( h, kVectSrId, vn );
|
|
|
|
for(i=0; i<vn; ++i)
|
|
{
|
|
cmSrWrStructBegin( h, kVectSrId );
|
|
cmSrWrFloatV( h, va.vectArray[i].data, va.vectArray[i].cnt );
|
|
cmSrWrUInt( h, va.vectArray[i].cnt );
|
|
cmSrWrStructEnd(h);
|
|
}
|
|
|
|
cmSrWrStructEnd(h);
|
|
|
|
bufByteCnt = 0;
|
|
bufPtr = cmSrWrAllocBuf( h, &bufByteCnt );
|
|
}
|
|
|
|
// The serialized buffer has the following format:
|
|
// Words Bytes
|
|
// ----- ----- -----------------------------------------
|
|
// 1 4 [ uint (2) ]
|
|
// 2 8 [ id (11) ][ cnt (2) ]
|
|
// 6 24 [ cnt (5) ][0.0][1.0][2.0][3.0][4.0]
|
|
// 1 4 [ uint (5) ]
|
|
// 4 16 [ cnt (3) ][10.][11.][12.]
|
|
// 1 4 [ uint (3) ]
|
|
// ----- ----
|
|
// 14 60
|
|
//
|
|
|
|
unsigned n0,n1,n2,n3;
|
|
const float* fArr;
|
|
|
|
cmSrRdProcessBuffer(h, (void*)bufPtr, bufByteCnt );
|
|
cmSrRdSetup( h, bufPtr, bufByteCnt );
|
|
|
|
cmSrRdStructBegin( h, kVectArrSrId );
|
|
cmSrReadUInt( h, &n0 );
|
|
cmSrReadStruct( h, kVectSrId, &n1 );
|
|
for(i=0; i<n1; ++i)
|
|
{
|
|
cmSrRdStructBegin( h, kVectSrId );
|
|
cmSrReadFloatCV( h, &fArr, &n2 );
|
|
cmSrReadUInt( h, &n3 );
|
|
cmSrRdStructEnd( h );
|
|
}
|
|
|
|
|
|
cmSrRdSetup( h, bufPtr, bufByteCnt );
|
|
|
|
cmSrRdStructBegin( h, kVectArrSrId );
|
|
n0 = cmSrRdUInt( h );
|
|
n1 = cmSrRdStruct( h, kVectSrId );
|
|
for(i=0; i<n1; ++i)
|
|
{
|
|
cmSrRdStructBegin( h, kVectSrId );
|
|
fArr = cmSrRdFloatV( h, &n2 );
|
|
n3 = cmSrRdUInt( h );
|
|
cmSrRdStructEnd( h );
|
|
|
|
for(j=0; j<n2; ++j)
|
|
printf("%f ",fArr[j]);
|
|
printf("\n");
|
|
}
|
|
}
|
|
|
|
errLabel:
|
|
cmSrFree(&h);
|
|
|
|
return rc;
|
|
}
|
|
|
|
//]
|
|
//}
|