diff options
author | cvsadm <cvsadm> | 2005-01-21 00:44:34 +0000 |
---|---|---|
committer | cvsadm <cvsadm> | 2005-01-21 00:44:34 +0000 |
commit | b2093e3016027d6b5cf06b3f91f30769bfc099e2 (patch) | |
tree | cf58939393a9032182c4fbc4441164a9456e82f8 /ldap/servers/slapd/csnset.c | |
download | ds-b2093e3016027d6b5cf06b3f91f30769bfc099e2.tar.gz ds-b2093e3016027d6b5cf06b3f91f30769bfc099e2.tar.xz ds-b2093e3016027d6b5cf06b3f91f30769bfc099e2.zip |
Moving NSCP Directory Server from DirectoryBranch to TRUNK, initial drop. (foxworth)ldapserver7x
Diffstat (limited to 'ldap/servers/slapd/csnset.c')
-rw-r--r-- | ldap/servers/slapd/csnset.c | 360 |
1 files changed, 360 insertions, 0 deletions
diff --git a/ldap/servers/slapd/csnset.c b/ldap/servers/slapd/csnset.c new file mode 100644 index 00000000..700cbc82 --- /dev/null +++ b/ldap/servers/slapd/csnset.c @@ -0,0 +1,360 @@ +/** BEGIN COPYRIGHT BLOCK + * Copyright 2001 Sun Microsystems, Inc. + * Portions copyright 1999, 2001-2003 Netscape Communications Corporation. + * All rights reserved. + * END COPYRIGHT BLOCK **/ + +#include "slap.h" +#include "slapi-private.h" + +static const CSNSet *csnset_get_csnset_node_from_csn(const CSNSet *csnset, const CSN *csn); +static const CSNSet *csnset_get_csnset_node_from_type(const CSNSet *csnset, CSNType t); +static CSNSet *csnset_get_previous_csnset_node(CSNSet *csnset, const CSN *csn); + +/* + * The CSN is always added to the end of the list. + */ +void +csnset_add_csn(CSNSet **csnset, CSNType t, const CSN *csn) +{ + if(csn!=NULL) + { + CSNSet *newcsn= (CSNSet*)slapi_ch_malloc(sizeof(CSNSet)); + newcsn->type= t; + csn_init_by_csn(&newcsn->csn,csn); + newcsn->next= NULL; + { + CSNSet **p= csnset; + CSNSet *n= *csnset; + while(n!=NULL) + { + p= &(n->next); + n= n->next; + } + *p= newcsn; + } + } +} + +/* + * The CSN is inserted into the list at the appropriate point.. + */ +void +csnset_insert_csn(CSNSet **csnset, CSNType t, const CSN *csn) +{ + if((csn!=NULL) && (*csnset==NULL)) + { + csnset_add_csn(csnset, t, csn); + } + else if(csn!=NULL) + { + CSNSet *newcsn= (CSNSet*)slapi_ch_malloc(sizeof(CSNSet)); + CSNSet *f= csnset_get_previous_csnset_node(*csnset, csn); + newcsn->type= t; + csn_init_by_csn(&newcsn->csn,csn); + if(f==NULL) + { + /* adding to the list head */ + newcsn->next= *csnset; + *csnset= newcsn; + } + else + { + newcsn->next= f->next; + f->next= newcsn; + } + } +} + +/* + * Find the CSN of the given type and update it. + */ +void +csnset_update_csn(CSNSet **csnset, CSNType t, const CSN *csn) +{ + const CSNSet *f= csnset_get_csnset_node_from_type(*csnset, t); + if(f==NULL) + { + csnset_add_csn(csnset,t,csn); + } + else + { + if (csn_compare(csn, (CSN*)(&f->csn)) > 0) + { + csn_init_by_csn((CSN*)(&f->csn),csn); + } + } +} + +/* + * Check if the set CSN of CSNs contains a given CSN. + */ +int +csnset_contains(const CSNSet *csnset, const CSN *csn) +{ + const CSNSet *f= csnset_get_csnset_node_from_csn(csnset, csn); + return(f!=NULL); +} + +/* + * Remove the first CSN of the given type. + */ +void +csnset_remove_csn(CSNSet **csnset, CSNType t) +{ + CSNSet **p= csnset; + CSNSet *n= *csnset; + while(n!=NULL) + { + if(n->type==t) + { + *p= n->next; + slapi_ch_free((void**)&n); + } + else + { + p= &n->next; + n= n->next; + } + } +} + +void +csnset_free(CSNSet **csnset) +{ + csnset_purge(csnset, NULL); +} + +/* + * Get the first CSN of the given type. + */ +const CSN * +csnset_get_csn_of_type(const CSNSet *csnset, CSNType t) +{ + const CSN *csn= NULL; + const CSNSet *f= csnset_get_csnset_node_from_type(csnset, t); + if(f!=NULL) + { + csn= &f->csn; + } + return csn; +} + +const CSN * +csnset_get_previous_csn(const CSNSet *csnset, const CSN *csn) +{ + const CSN *prevcsn= NULL; + CSNSet *f= csnset_get_previous_csnset_node((CSNSet*)csnset, csn); + if(f!=NULL) + { + prevcsn= &f->csn; + } + return prevcsn; +} + +const CSN * +csnset_get_last_csn(const CSNSet *csnset) +{ + const CSN *csn= NULL; + const CSNSet *n= csnset; + while(n!=NULL) + { + if(n->next==NULL) + { + csn= &n->csn; + } + n= n->next; + } + return csn; +} + +void* +csnset_get_first_csn (const CSNSet *csnset, CSN **csn, CSNType *t) +{ + if (csnset) + { + *csn = (CSN*)&csnset->csn; + *t = csnset->type; + return (void*)csnset; + } + else + return NULL; +} + +void* +csnset_get_next_csn (const CSNSet *csnset, void *cookie, CSN **csn, CSNType *t) +{ + CSNSet *node; + + if (csnset && cookie) + { + node = ((CSNSet*)cookie)->next; + if (node) + { + *csn = (CSN*)&node->csn; + *t = node->type; + return node; + } + else + return NULL; + } + else + return NULL; +} + +static CSNSet * +csnset_get_previous_csnset_node(CSNSet *csnset, const CSN *csn) +{ + CSNSet *f= NULL; + CSNSet *p= NULL; + CSNSet *n= csnset; + while(n!=NULL) + { + if(csn_compare(&n->csn, csn)>0) + { + f= p; + n= NULL; + } + else + { + p= n; + n= n->next; + if(n==NULL) + { + /* Got to the end of the list... */ + f= p; + } + } + } + return f; +} + +static const CSNSet * +csnset_get_csnset_node_from_csn(const CSNSet *csnset, const CSN *csn) +{ + const CSNSet *f= NULL; + const CSNSet *n= csnset; + while(n!=NULL) + { + if(csn_compare(&n->csn, csn)==0) + { + f= n; + n= NULL; + } + else + { + n= n->next; + } + } + return f; +} + +static const CSNSet * +csnset_get_csnset_node_from_type(const CSNSet *csnset, CSNType t) +{ + const CSNSet *f= NULL; + const CSNSet *n= csnset; + while(n!=NULL) + { + if(n->type==t) + { + f= n; + n= NULL; + } + else + { + n= n->next; + } + } + return f; +} + +/* + * Remove any CSNs older than csnUpTo. If csnUpTo is NULL, + * remove all CSNs. + */ +void +csnset_purge(CSNSet **csnset, const CSN *csnUpTo) +{ + if (csnset != NULL) + { + CSNSet *n = *csnset, *nprev = NULL, *nnext; + while (n != NULL) + { + if (NULL == csnUpTo || (csn_compare(&n->csn, csnUpTo) < 0)) + { + nnext = n->next; + if (*csnset == n) + { + /* Deletion of head */ + *csnset = nnext; + } + else if (nprev) + { + /* nprev was not purged, but n will be */ + nprev->next = nnext; + } + slapi_ch_free((void**)&n); + n = nnext; + } + else + { + nprev = n; + n = n->next; + } + } + } +} + +size_t +csnset_string_size(CSNSet *csnset) +{ + size_t s= 0; + CSNSet *n= csnset; + while(n!=NULL) + { + /* sizeof(;vucsn-011111111222233334444) */ + s+= 1 + LDIF_CSNPREFIX_MAXLENGTH + _CSN_VALIDCSN_STRLEN; + n= n->next; + } + return s; +} + +size_t +csnset_size(CSNSet *csnset) +{ + size_t s= 0; + CSNSet *n= csnset; + while(n!=NULL) + { + s+= sizeof(CSNSet); + n= n->next; + } + return s; +} + +CSNSet * +csnset_dup(const CSNSet *csnset) +{ + CSNSet *newcsnset= NULL; + const CSNSet *n= csnset; + while(n!=NULL) + { + csnset_add_csn(&newcsnset,n->type,&n->csn); + n= n->next; + } + return newcsnset; +} + +void +csnset_as_string(const CSNSet *csnset,char *s) +{ + const CSNSet *n= csnset; + while(n!=NULL) + { + csn_as_attr_option_string(n->type,&n->csn,s); + /* sizeof(;vucsn-011111111222233334444) */ + s+= 1 + LDIF_CSNPREFIX_MAXLENGTH + _CSN_VALIDCSN_STRLEN; + n= n->next; + } +} |