CFG_HIDDEN,
CFG_MONITORING,
CFG_SERVERID,
+ CFG_SORTVALS,
CFG_LAST
};
{ "OLcfgBkAt", "OLcfgAt:1" },
{ "OLcfgDbAt", "OLcfgAt:2" },
{ "OLcfgOvAt", "OLcfgAt:3" },
+ { "OLcfgCtAt", "OLcfgAt:4" }, /* contrib modules */
{ "OLcfgOc", "OLcfg:4" },
{ "OLcfgGlOc", "OLcfgOc:0" },
{ "OLcfgBkOc", "OLcfgOc:1" },
{ "OLcfgDbOc", "OLcfgOc:2" },
{ "OLcfgOvOc", "OLcfgOc:3" },
+ { "OLcfgCtOc", "OLcfgOc:4" }, /* contrib modules */
/* Syntaxes. We should just start using the standard names and
* document that they are predefined and available for users
{ "OMsBoolean", "OMsyn:7" },
{ "OMsDN", "OMsyn:12" },
{ "OMsDirectoryString", "OMsyn:15" },
+ { "OMsIA5String", "OMsyn:26" },
{ "OMsInteger", "OMsyn:27" },
{ "OMsOID", "OMsyn:38" },
{ "OMsOctetString", "OMsyn:40" },
* OLcfgOv{Oc|At}:3 -> chain
* OLcfgOv{Oc|At}:4 -> accesslog
* OLcfgOv{Oc|At}:5 -> valsort
- * (FIXME: separate arc for contribware?)
- * OLcfgOv{Oc|At}:6 -> smbk5pwd
* OLcfgOv{Oc|At}:7 -> distproc
* OLcfgOv{Oc|At}:8 -> dynlist
* OLcfgOv{Oc|At}:9 -> dds
{ "sockbuf_max_incoming_auth", "max", 2, 2, 0, ARG_BER_LEN_T,
&sockbuf_max_incoming_auth, "( OLcfgGlAt:62 NAME 'olcSockbufMaxIncomingAuth' "
"SYNTAX OMsInteger SINGLE-VALUE )", NULL, NULL },
+ { "sortvals", "attr", 2, 0, 0, ARG_MAGIC|CFG_SORTVALS,
+ &config_generic, "( OLcfgGlAt:83 NAME 'olcSortVals' "
+ "DESC 'Attributes whose values will always be sorted' "
+ "EQUALITY caseIgnoreMatch "
+ "SYNTAX OMsDirectoryString )", NULL, NULL },
{ "subordinate", "[advertise]", 1, 2, 0, ARG_DB|ARG_MAGIC,
&config_subordinate, "( OLcfgDbAt:0.15 NAME 'olcSubordinate' "
"SYNTAX OMsDirectoryString SINGLE-VALUE )", NULL, NULL },
"olcIndexSubstrIfMaxLen $ olcIndexSubstrIfMinLen $ "
"olcIndexSubstrAnyLen $ olcIndexSubstrAnyStep $ olcLocalSSF $ "
"olcLogLevel $ "
- "olcPasswordCryptSaltFormat $ olcPidFile $ "
+ "olcPasswordCryptSaltFormat $ olcPasswordHash $ olcPidFile $ "
"olcPluginLogFile $ olcReadOnly $ olcReferral $ "
"olcReplogFile $ olcRequires $ olcRestrict $ olcReverseLookup $ "
"olcRootDSE $ "
"NAME 'olcFrontendConfig' "
"DESC 'OpenLDAP frontend configuration' "
"AUXILIARY "
- "MAY ( olcDefaultSearchBase $ olcPasswordHash ) )",
+ "MAY ( olcDefaultSearchBase $ olcPasswordHash $ olcSortVals ) )",
Cft_Database, NULL, NULL },
#ifdef SLAPD_MODULES
{ "( OLcfgGlOc:8 "
static ServerID *sid_list;
+typedef struct ADlist {
+ struct ADlist *al_next;
+ AttributeDescription *al_desc;
+} ADlist;
+
+static ADlist *sortVals;
+
static int
config_generic(ConfigArgs *c) {
int i;
case CFG_SSTR_IF_MIN:
c->value_int = index_substr_if_minlen;
break;
+ case CFG_SORTVALS: {
+ ADlist *sv;
+ rc = 1;
+ for ( sv = sortVals; sv; sv = sv->al_next ) {
+ value_add_one( &c->rvalue_vals, &sv->al_desc->ad_cname );
+ rc = 0;
+ }
+ } break;
#ifdef SLAPD_MODULES
case CFG_MODLOAD: {
ModPaths *mp = c->private;
break;
case CFG_OC: {
- CfEntryInfo *ce = c->ca_entry->e_private;
- /* can't modify the hardcoded schema */
- if ( ce->ce_parent->ce_type == Cft_Global )
- return 1;
+ CfEntryInfo *ce;
+ /* Can be NULL when undoing a failed add */
+ if ( c->ca_entry ) {
+ ce = c->ca_entry->e_private;
+ /* can't modify the hardcoded schema */
+ if ( ce->ce_parent->ce_type == Cft_Global )
+ return 1;
+ }
}
cfn = c->private;
if ( c->valx < 0 ) {
break;
case CFG_ATTR: {
- CfEntryInfo *ce = c->ca_entry->e_private;
- /* can't modify the hardcoded schema */
- if ( ce->ce_parent->ce_type == Cft_Global )
- return 1;
+ CfEntryInfo *ce;
+ /* Can be NULL when undoing a failed add */
+ if ( c->ca_entry ) {
+ ce = c->ca_entry->e_private;
+ /* can't modify the hardcoded schema */
+ if ( ce->ce_parent->ce_type == Cft_Global )
+ return 1;
+ }
}
cfn = c->private;
if ( c->valx < 0 ) {
}
}
break;
+ case CFG_SORTVALS:
+ if ( c->valx < 0 ) {
+ ADlist *sv;
+ for ( sv = sortVals; sv; sv = sortVals ) {
+ sortVals = sv->al_next;
+ sv->al_desc->ad_type->sat_flags &= ~SLAP_AT_SORTED_VAL;
+ ch_free( sv );
+ }
+ } else {
+ ADlist *sv, **prev;
+ int i = 0;
+
+ for ( prev = &sortVals, sv = sortVals; i < c->valx; i++ ) {
+ prev = &sv->al_next;
+ sv = sv->al_next;
+ }
+ sv->al_desc->ad_type->sat_flags &= ~SLAP_AT_SORTED_VAL;
+ *prev = sv->al_next;
+ ch_free( sv );
+ }
+ break;
case CFG_LIMITS:
/* FIXME: there is no limits_free function */
return(1);
break;
+ case CFG_SORTVALS: {
+ ADlist *svnew = NULL, *svtail, *sv;
+
+ for ( i = 1; i < c->argc; i++ ) {
+ AttributeDescription *ad = NULL;
+ const char *text;
+ int rc;
+
+ rc = slap_str2ad( c->argv[i], &ad, &text );
+ if ( rc ) {
+ snprintf( c->cr_msg, sizeof( c->cr_msg ), "<%s> unknown attribute type #%d",
+ c->argv[0], i );
+sortval_reject:
+ Debug(LDAP_DEBUG_ANY, "%s: %s %s\n",
+ c->log, c->cr_msg, c->argv[i] );
+ for ( sv = svnew; sv; sv = svnew ) {
+ svnew = sv->al_next;
+ ch_free( sv );
+ }
+ return 1;
+ }
+ if (( ad->ad_type->sat_flags & SLAP_AT_ORDERED ) ||
+ ad->ad_type->sat_single_value ) {
+ snprintf( c->cr_msg, sizeof( c->cr_msg ), "<%s> inappropriate attribute type #%d",
+ c->argv[0], i );
+ goto sortval_reject;
+ }
+ sv = ch_malloc( sizeof( ADlist ));
+ sv->al_desc = ad;
+ if ( !svnew ) {
+ svnew = sv;
+ } else {
+ svtail->al_next = sv;
+ }
+ svtail = sv;
+ }
+ sv->al_next = NULL;
+ for ( sv = svnew; sv; sv = sv->al_next )
+ sv->al_desc->ad_type->sat_flags |= SLAP_AT_SORTED_VAL;
+ for ( sv = sortVals; sv && sv->al_next; sv = sv->al_next );
+ if ( sv )
+ sv->al_next = svnew;
+ else
+ sortVals = svnew;
+ }
+ break;
+
case CFG_ACL:
/* Don't append to the global ACL if we're on a specific DB */
i = c->valx;
return(0);
}
+/* For RE23 compatibility we allow this in the global entry
+ * but we now defer it to the frontend entry to allow modules
+ * to load new hash types.
+ */
static int
config_passwd_hash(ConfigArgs *c) {
int i;
if (c->op == SLAP_CONFIG_EMIT) {
struct berval bv;
+ /* Don't generate it in the global entry */
+ if ( c->table == Cft_Global )
+ return 1;
for (i=0; default_passwd_hash && default_passwd_hash[i]; i++) {
ber_str2bv(default_passwd_hash[i], 0, 0, &bv);
value_add_one(&c->rvalue_vals, &bv);
}
return i ? 0 : 1;
} else if ( c->op == LDAP_MOD_DELETE ) {
+ /* Deleting from global is a no-op, only the frontendDB entry matters */
+ if ( c->table == Cft_Global )
+ return 0;
if ( c->valx < 0 ) {
ldap_charray_free( default_passwd_hash );
default_passwd_hash = NULL;
}
return 0;
}
- if(default_passwd_hash) {
- Debug(LDAP_DEBUG_ANY, "%s: "
- "already set default password_hash\n",
- c->log, 0, 0);
- return(1);
- }
for(i = 1; i < c->argc; i++) {
if(!lutil_passwd_scheme(c->argv[i])) {
snprintf( c->cr_msg, sizeof( c->cr_msg ), "<%s> scheme not available", c->argv[0] );
} else {
ldap_charray_add(&default_passwd_hash, c->argv[i]);
}
- if(!default_passwd_hash) {
- snprintf( c->cr_msg, sizeof( c->cr_msg ), "<%s> no valid hashes found", c->argv[0] );
- Debug(LDAP_DEBUG_ANY, "%s: %s\n",
- c->log, c->cr_msg, 0 );
- return(1);
- }
+ }
+ if(!default_passwd_hash) {
+ snprintf( c->cr_msg, sizeof( c->cr_msg ), "<%s> no valid hashes found", c->argv[0] );
+ Debug(LDAP_DEBUG_ANY, "%s: %s\n",
+ c->log, c->cr_msg, 0 );
+ return(1);
}
return(0);
}
*/
if ( ct && ml->sml_values ) {
delrec *d;
- for (i=0; ml->sml_values[i].bv_val; i++);
+ i = ml->sml_numvals;
d = ch_malloc( sizeof(delrec) + (i - 1)* sizeof(int));
d->nidx = i;
d->next = NULL;
if ( ct->arg_type & ARG_NO_INSERT ) {
Attribute *a = attr_find( e->e_attrs, ml->sml_desc );
if ( a ) {
- for (i = 0; a->a_vals[i].bv_val; i++ );
- navals = i;
+ navals = a->a_numvals;
}
}
for ( i=0; !BER_BVISNULL( &ml->sml_values[i] ); i++ ) {
ber_bvarray_free( a->a_vals );
a->a_vals = NULL;
a->a_nvals = NULL;
+ a->a_numvals = 0;
}
oidm_unparse( &bv, NULL, NULL, 1 );
attr_merge_normalize( e, cfAd_om, bv, NULL );
ber_bvarray_free( a->a_vals );
a->a_vals = NULL;
a->a_nvals = NULL;
+ a->a_numvals = 0;
}
at_unparse( &bv, NULL, NULL, 1 );
attr_merge_normalize( e, cfAd_attr, bv, NULL );
ber_bvarray_free( a->a_vals );
a->a_vals = NULL;
a->a_nvals = NULL;
+ a->a_numvals = 0;
}
oc_unparse( &bv, NULL, NULL, 1 );
attr_merge_normalize( e, cfAd_oc, bv, NULL );