PSI update
r1464 | ffr | 2007-02-12 12:20:21 +1100 (Mon, 12 Feb 2007) | 2 lines
This commit is contained in:
committed by
Douglas Clowes
parent
634f2023b1
commit
3168325921
353
hipadaba.c
353
hipadaba.c
@@ -38,6 +38,10 @@ static void DeleteNodeData(pHdb node){
|
||||
DeleteCallbackChain(node->writeCallbacks);
|
||||
DeleteCallbackChain(node->updateCallbacks);
|
||||
DeleteCallbackChain(node->readCallbacks);
|
||||
DeleteCallbackChain(node->treeChangeCallbacks);
|
||||
if(node->properties != NULL){
|
||||
DeleteStringDict(node->properties);
|
||||
}
|
||||
|
||||
if(node->name != NULL){
|
||||
free(node->name);
|
||||
@@ -52,8 +56,24 @@ static void DeleteNodeData(pHdb node){
|
||||
}
|
||||
free(node);
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
static int InvokeCallbackChain(pHdbCallback root, pHdb node,
|
||||
void *callData, hdbValue v){
|
||||
pHdbCallback current = root;
|
||||
int status;
|
||||
|
||||
while(current != NULL){
|
||||
status = current->userCallback(current->userData,callData,
|
||||
node,v);
|
||||
if(status != 1){
|
||||
return status;
|
||||
}
|
||||
current = current->next;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
void RemoveHdbNodeFromParent(pHdb node){
|
||||
void RemoveHdbNodeFromParent(pHdb node, void *callData){
|
||||
pHdb parent = NULL;
|
||||
pHdb current = NULL;
|
||||
|
||||
@@ -68,6 +88,8 @@ void RemoveHdbNodeFromParent(pHdb node){
|
||||
current = current->next;
|
||||
}
|
||||
current->next = current->next->next;
|
||||
InvokeCallbackChain(parent->treeChangeCallbacks,
|
||||
parent,callData,parent->value);
|
||||
}
|
||||
}
|
||||
/*-----------------------------------------------------------------------*/
|
||||
@@ -174,22 +196,6 @@ static pHdbCallback DeleteForInternalID(pHdbCallback root, int id){
|
||||
}
|
||||
return result;
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
static int InvokeCallbackChain(pHdbCallback root, pHdb node,
|
||||
void *callData, hdbValue v){
|
||||
pHdbCallback current = root;
|
||||
int status;
|
||||
|
||||
while(current != NULL){
|
||||
status = current->userCallback(current->userData,callData,
|
||||
node,v);
|
||||
if(status != 1){
|
||||
return status;
|
||||
}
|
||||
current = current->next;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
/*----------------------------------------------------------------------*/
|
||||
char *hdbTrim(char *str)
|
||||
{
|
||||
@@ -270,9 +276,9 @@ hdbValue makeHdbValue(int datatype, int length){
|
||||
case HIPINTAR:
|
||||
case HIPINTVARAR:
|
||||
val.arrayLength = length;
|
||||
val.v.intArray = malloc(length*sizeof(long));
|
||||
val.v.intArray = malloc(length*sizeof(int));
|
||||
if(val.v.intArray != NULL){
|
||||
memset(val.v.intArray,0,length*sizeof(long));
|
||||
memset(val.v.intArray,0,length*sizeof(int));
|
||||
}
|
||||
break;
|
||||
case HIPFLOATAR:
|
||||
@@ -285,15 +291,71 @@ hdbValue makeHdbValue(int datatype, int length){
|
||||
break;
|
||||
case HIPTEXT:
|
||||
val.v.text = strdup("UNKNOWN");
|
||||
val.arrayLength = length;
|
||||
break;
|
||||
}
|
||||
return val;
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
hdbValue makeHdbData(int datatype, int length, void *data){
|
||||
hdbValue val;
|
||||
|
||||
memset(&val,0,sizeof(hdbValue));
|
||||
val.dataType = datatype;
|
||||
|
||||
switch(datatype){
|
||||
case HIPINT:
|
||||
if(data != NULL){
|
||||
memcpy(&val.v.intValue,data,sizeof(int));
|
||||
}
|
||||
break;
|
||||
case HIPFLOAT:
|
||||
if(data != NULL){
|
||||
memcpy(&val.v.doubleValue,data,sizeof(double));
|
||||
}
|
||||
break;
|
||||
case HIPINTAR:
|
||||
case HIPINTVARAR:
|
||||
val.arrayLength = length;
|
||||
val.v.intArray = malloc(length*sizeof(int));
|
||||
if(val.v.intArray != NULL){
|
||||
memset(val.v.intArray,0,length*sizeof(int));
|
||||
}
|
||||
if(data != NULL){
|
||||
memcpy(val.v.intArray,data,length*sizeof(int));
|
||||
}
|
||||
break;
|
||||
case HIPFLOATAR:
|
||||
case HIPFLOATVARAR:
|
||||
val.arrayLength = length;
|
||||
val.v.floatArray = malloc(length*sizeof(double));
|
||||
if(val.v.floatArray != NULL){
|
||||
memset(val.v.floatArray,0,length*sizeof(double));
|
||||
}
|
||||
if(data != NULL){
|
||||
memcpy(val.v.floatArray,data,length*sizeof(double));
|
||||
}
|
||||
break;
|
||||
case HIPTEXT:
|
||||
if(data != NULL){
|
||||
val.v.text = strdup((char *)data);
|
||||
} else {
|
||||
val.v.text = strdup("UNKNOWN");
|
||||
}
|
||||
val.arrayLength = strlen(val.v.text);
|
||||
break;
|
||||
case HIPOBJ:
|
||||
val.v.obj = data;
|
||||
break;
|
||||
}
|
||||
return val;
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
hdbValue MakeHdbInt(int initValue){
|
||||
hdbValue result;
|
||||
|
||||
result.dataType = HIPINT;
|
||||
result.arrayLength = 1;
|
||||
result.v.intValue = initValue;
|
||||
return result;
|
||||
}
|
||||
@@ -302,6 +364,7 @@ hdbValue MakeHdbFloat(double initValue){
|
||||
hdbValue result;
|
||||
|
||||
result.dataType = HIPFLOAT;
|
||||
result.arrayLength = 1;
|
||||
result.v.doubleValue = initValue;
|
||||
return result;
|
||||
}
|
||||
@@ -311,10 +374,11 @@ hdbValue MakeHdbText(char *initText){
|
||||
|
||||
result.dataType = HIPTEXT;
|
||||
result.v.text = initText;
|
||||
result.arrayLength = strlen(initText);
|
||||
return result;
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
hdbValue MakeHdbIntArray(int length, long *data){
|
||||
hdbValue MakeHdbIntArray(int length, int *data){
|
||||
hdbValue result;
|
||||
|
||||
result.dataType = HIPINTAR;
|
||||
@@ -409,6 +473,13 @@ int compareHdbValue(hdbValue v1, hdbValue v2){
|
||||
}
|
||||
return 1;
|
||||
break;
|
||||
case HIPOBJ:
|
||||
if(v2.v.obj == v1.v.obj) {
|
||||
return 1;
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
@@ -422,6 +493,35 @@ int cloneHdbValue(hdbValue *source, hdbValue *clone){
|
||||
clone->dataType = source->dataType;
|
||||
return copyHdbValue(source, clone);
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
int getHdbValueLength(hdbValue v){
|
||||
int length = 0;
|
||||
switch(v.dataType){
|
||||
case HIPNONE:
|
||||
break;
|
||||
case HIPINT:
|
||||
length = sizeof(int);
|
||||
break;
|
||||
case HIPFLOAT:
|
||||
length = sizeof(double);
|
||||
break;
|
||||
case HIPINTAR:
|
||||
case HIPINTVARAR:
|
||||
length = v.arrayLength * sizeof(int);
|
||||
break;
|
||||
case HIPFLOATAR:
|
||||
case HIPFLOATVARAR:
|
||||
length = v.arrayLength * sizeof(double);
|
||||
break;
|
||||
case HIPTEXT:
|
||||
length = strlen(v.v.text);
|
||||
break;
|
||||
case HIPOBJ:
|
||||
length = sizeof(void *);
|
||||
break;
|
||||
}
|
||||
return length;
|
||||
}
|
||||
/*================= node functions ========================================*/
|
||||
pHdb MakeHipadabaNode(char *name, int datatype, int length){
|
||||
pHdb pNew = NULL;
|
||||
@@ -434,15 +534,19 @@ pHdb MakeHipadabaNode(char *name, int datatype, int length){
|
||||
pNew->magic = HDBMAGICK;
|
||||
pNew->name = strdup(name);
|
||||
pNew->value.dataType = datatype;
|
||||
pNew->properties = CreateStringDict();
|
||||
if(pNew->properties == NULL || pNew->name == NULL){
|
||||
return NULL;
|
||||
}
|
||||
switch(datatype){
|
||||
case HIPINTAR:
|
||||
case HIPINTVARAR:
|
||||
pNew->value.arrayLength = length;
|
||||
pNew->value.v.intArray = malloc(length*sizeof(long));
|
||||
pNew->value.v.intArray = malloc(length*sizeof(int));
|
||||
if(pNew->value.v.intArray == NULL){
|
||||
return NULL;
|
||||
}
|
||||
memset(pNew->value.v.intArray,0,length*sizeof(long));
|
||||
memset(pNew->value.v.intArray,0,length*sizeof(int));
|
||||
break;
|
||||
case HIPFLOATAR:
|
||||
case HIPFLOATVARAR:
|
||||
@@ -454,16 +558,20 @@ pHdb MakeHipadabaNode(char *name, int datatype, int length){
|
||||
memset(pNew->value.v.floatArray,0,length*sizeof(double));
|
||||
break;
|
||||
case HIPTEXT:
|
||||
pNew->value.arrayLength = length;
|
||||
pNew->value.v.text = strdup("UNKNOWN");
|
||||
break;
|
||||
}
|
||||
return pNew;
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
void AddHipadabaChild(pHdb parent, pHdb child){
|
||||
void AddHipadabaChild(pHdb parent, pHdb child, void *callData){
|
||||
pHdb current = NULL, prev = NULL;
|
||||
|
||||
assert(parent != NULL && child != NULL);
|
||||
assert(parent != NULL);
|
||||
if(child == NULL){
|
||||
return;
|
||||
}
|
||||
|
||||
current = parent->child;
|
||||
child->mama = parent;
|
||||
@@ -481,16 +589,18 @@ void AddHipadabaChild(pHdb parent, pHdb child){
|
||||
child->next = NULL;
|
||||
prev->next = child;
|
||||
}
|
||||
InvokeCallbackChain(parent->treeChangeCallbacks,
|
||||
parent,callData,parent->value);
|
||||
}
|
||||
/*--------------------------------------------------------------------------*/
|
||||
void DeleteHipadabaNode(pHdb node){
|
||||
void DeleteHipadabaNode(pHdb node, void *callData){
|
||||
pHdb current = NULL, tmp = NULL;
|
||||
|
||||
if(node == NULL){
|
||||
return;
|
||||
}
|
||||
|
||||
RemoveHdbNodeFromParent(node);
|
||||
RemoveHdbNodeFromParent(node, callData);
|
||||
|
||||
DeleteNodeData(node);
|
||||
}
|
||||
@@ -637,6 +747,14 @@ void AppendHipadabaCallback(pHdb node, int type, pHdbCallback newCB){
|
||||
current = node->readCallbacks;
|
||||
}
|
||||
break;
|
||||
case HCBTREE:
|
||||
if(node->treeChangeCallbacks == NULL){
|
||||
node->treeChangeCallbacks = newCB;
|
||||
return;
|
||||
} else {
|
||||
current = node->treeChangeCallbacks;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
@@ -649,7 +767,6 @@ void AppendHipadabaCallback(pHdb node, int type, pHdbCallback newCB){
|
||||
newCB->previous = current;
|
||||
}
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
/*---------------------------------------------------------------------------*/
|
||||
void PrependHipadabaCallback(pHdb node, int type, pHdbCallback newCB){
|
||||
switch(type){
|
||||
@@ -683,6 +800,16 @@ void PrependHipadabaCallback(pHdb node, int type, pHdbCallback newCB){
|
||||
node->readCallbacks = newCB;
|
||||
}
|
||||
break;
|
||||
case HCBTREE:
|
||||
if(node->treeChangeCallbacks == NULL){
|
||||
node->treeChangeCallbacks = newCB;
|
||||
return;
|
||||
} else {
|
||||
newCB->next = node->treeChangeCallbacks;
|
||||
node->treeChangeCallbacks->previous = newCB;
|
||||
node->treeChangeCallbacks = newCB;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
@@ -695,6 +822,7 @@ void RemoveHipadabaCallback(pHdb root, int id){
|
||||
root->writeCallbacks = DeleteForID(root->writeCallbacks,id);
|
||||
root->updateCallbacks = DeleteForID(root->updateCallbacks,id);
|
||||
root->readCallbacks = DeleteForID(root->readCallbacks,id);
|
||||
root->treeChangeCallbacks = DeleteForID(root->treeChangeCallbacks,id);
|
||||
|
||||
current = root->child;
|
||||
while(current != NULL){
|
||||
@@ -709,6 +837,7 @@ void InternalRemoveHipadabaCallback(pHdb root, int internalID){
|
||||
root->writeCallbacks = DeleteForInternalID(root->writeCallbacks,internalID);
|
||||
root->updateCallbacks = DeleteForInternalID(root->updateCallbacks,internalID);
|
||||
root->readCallbacks = DeleteForInternalID(root->readCallbacks,internalID);
|
||||
root->treeChangeCallbacks = DeleteForInternalID(root->treeChangeCallbacks,internalID);
|
||||
|
||||
current = root->child;
|
||||
while(current != NULL){
|
||||
@@ -741,24 +870,26 @@ int copyHdbValue(hdbValue *source, hdbValue *target){
|
||||
break;
|
||||
case HIPINTAR:
|
||||
case HIPINTVARAR:
|
||||
if(target->arrayLength != source->arrayLength){
|
||||
if(target->arrayLength != source->arrayLength || target->v.intArray == NULL){
|
||||
if(target->v.intArray != NULL){
|
||||
free(target->v.intArray);
|
||||
}
|
||||
target->v.intArray = malloc(source->arrayLength * sizeof(long));
|
||||
target->v.intArray = malloc(source->arrayLength * sizeof(int));
|
||||
if(target->v.intArray == NULL){
|
||||
return 0;
|
||||
}
|
||||
memset(target->v.intArray,0,source->arrayLength * sizeof(long));
|
||||
memset(target->v.intArray,0,source->arrayLength * sizeof(int));
|
||||
target->arrayLength = source->arrayLength;
|
||||
}
|
||||
for(i = 0; i < source->arrayLength; i++){
|
||||
target->v.intArray[i] = source->v.intArray[i];
|
||||
if(source->v.intArray != NULL){
|
||||
for(i = 0; i < source->arrayLength; i++){
|
||||
target->v.intArray[i] = source->v.intArray[i];
|
||||
}
|
||||
}
|
||||
break;
|
||||
case HIPFLOATAR:
|
||||
case HIPFLOATVARAR:
|
||||
if(target->arrayLength != source->arrayLength){
|
||||
if(target->arrayLength != source->arrayLength || target->v.floatArray == NULL){
|
||||
if(target->v.floatArray != NULL){
|
||||
free(target->v.floatArray);
|
||||
}
|
||||
@@ -768,10 +899,15 @@ int copyHdbValue(hdbValue *source, hdbValue *target){
|
||||
}
|
||||
memset(target->v.floatArray,0,source->arrayLength * sizeof(double));
|
||||
target->arrayLength = source->arrayLength;
|
||||
}
|
||||
if(source->v.floatArray != NULL){
|
||||
for(i = 0; i < source->arrayLength; i++){
|
||||
target->v.floatArray[i] = source->v.floatArray[i];
|
||||
}
|
||||
}
|
||||
for(i = 0; i < source->arrayLength; i++){
|
||||
target->v.floatArray[i] = source->v.floatArray[i];
|
||||
}
|
||||
break;
|
||||
case HIPOBJ:
|
||||
target->v.obj = source->v.obj;
|
||||
break;
|
||||
default:
|
||||
/*
|
||||
@@ -812,4 +948,149 @@ int GetHipadabaPar(pHdb node, hdbValue *v, void *callData){
|
||||
copyHdbValue(&node->value,v);
|
||||
return 1;
|
||||
}
|
||||
/*----------------------------------------------------------------------------*/
|
||||
static int calcDataLength(pHdb node, int testLength){
|
||||
int length = 0;
|
||||
|
||||
length = getHdbValueLength(node->value);
|
||||
if(node->value.dataType == HIPFLOATVARAR ||
|
||||
node->value.dataType == HIPINTVARAR ||
|
||||
node->value.dataType == HIPTEXT){
|
||||
length = testLength;
|
||||
}
|
||||
return length;
|
||||
}
|
||||
/*--------------------------------------------------------------------------*/
|
||||
int SetHdbPar(pHdb node, int dataType, void *data, int length,
|
||||
void *callData){
|
||||
int status;
|
||||
hdbValue v;
|
||||
|
||||
if(node->value.dataType == HIPNONE){
|
||||
return 1;
|
||||
}
|
||||
|
||||
if(dataType != node->value.dataType){
|
||||
return HDBTYPEMISMATCH;
|
||||
}
|
||||
if(length != calcDataLength(node,length)){
|
||||
return HDBLENGTHMISMATCH;
|
||||
}
|
||||
|
||||
v = makeHdbData(dataType, length, data);
|
||||
status = InvokeCallbackChain(node->writeCallbacks, node, callData, v);
|
||||
if(status == 1) {
|
||||
copyHdbValue(&v,&node->value);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
/*--------------------------------------------------------------------------*/
|
||||
int UpdateHdbPar(pHdb node, int dataType, void *data, int length,
|
||||
void *callData){
|
||||
int status;
|
||||
hdbValue v;
|
||||
|
||||
if(node->value.dataType == HIPNONE){
|
||||
return 1;
|
||||
}
|
||||
|
||||
if(dataType != node->value.dataType){
|
||||
return HDBTYPEMISMATCH;
|
||||
}
|
||||
if(length != calcDataLength(node,length)){
|
||||
return HDBLENGTHMISMATCH;
|
||||
}
|
||||
|
||||
v = makeHdbData(dataType,length,data);
|
||||
|
||||
status = InvokeCallbackChain(node->updateCallbacks, node, callData, v);
|
||||
if(status == 1) {
|
||||
copyHdbValue(&v,&node->value);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
int GetHdbPar(pHdb node, int dataType, void *data, int length,
|
||||
void *callData){
|
||||
int status, toCopy;
|
||||
hdbValue v;
|
||||
|
||||
if(dataType != node->value.dataType){
|
||||
return HDBTYPEMISMATCH;
|
||||
}
|
||||
|
||||
if(length != calcDataLength(node,length)){
|
||||
return HDBLENGTHMISMATCH;
|
||||
}
|
||||
|
||||
status = InvokeCallbackChain(node->readCallbacks, node, callData, v);
|
||||
if(status != 1 ){
|
||||
return status;
|
||||
}
|
||||
switch(dataType){
|
||||
case HIPNONE:
|
||||
break;
|
||||
case HIPINT:
|
||||
memcpy(data,&node->value.v.intValue,sizeof(int));
|
||||
break;
|
||||
case HIPFLOAT:
|
||||
memcpy(data,&node->value.v.doubleValue,sizeof(double));
|
||||
break;
|
||||
case HIPINTAR:
|
||||
case HIPINTVARAR:
|
||||
memcpy(data,node->value.v.intArray,
|
||||
node->value.arrayLength*sizeof(int));
|
||||
break;
|
||||
case HIPTEXT:
|
||||
toCopy = strlen(node->value.v.text);
|
||||
if(toCopy > length){
|
||||
toCopy = length;
|
||||
}
|
||||
memcpy(data,&node->value.v.text, toCopy);
|
||||
break;
|
||||
case HIPFLOATAR:
|
||||
case HIPFLOATVARAR:
|
||||
memcpy(data,node->value.v.floatArray,
|
||||
node->value.arrayLength*sizeof(double));
|
||||
break;
|
||||
case HIPOBJ:
|
||||
memcpy(data,&node->value.v.obj,sizeof(void *));
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
/*============================= Property Functions ==========================*/
|
||||
void SetHdbProperty(pHdb node, char *key, char *value){
|
||||
if(node != NULL && key != NULL && node->properties != NULL){
|
||||
if(StringDictExists(node->properties, key)){
|
||||
StringDictUpdate(node->properties,key,value);
|
||||
} else {
|
||||
StringDictAddPair(node->properties,key,value);
|
||||
}
|
||||
}
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
int GetHdbProperty(pHdb node, char *key, char *value, int len){
|
||||
if(node != NULL && node->properties != NULL){
|
||||
return StringDictGet(node->properties,key,value,len);
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
void InitHdbPropertySearch(pHdb node){
|
||||
if(node != NULL && node->properties != NULL){
|
||||
StringDictKillScan(node->properties);
|
||||
}
|
||||
}
|
||||
/*--------------------------------------------------------------------------*/
|
||||
const char *GetNextHdbProperty(pHdb node, char *value ,int len){
|
||||
if(node != NULL && node->properties != NULL) {
|
||||
return StringDictGetNext(node->properties, value, len);
|
||||
} else {
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user