improvements to monitor backend: added a log entry that lists the current log level and can be modified via protocol at runtime, to change the log level; minor improvements; fixed a problem in dealing with dn normalization

This commit is contained in:
Pierangelo Masarati 2001-12-10 09:50:06 +00:00
parent fe45b74798
commit 95f1740aa6
15 changed files with 724 additions and 35 deletions

View File

@ -220,7 +220,6 @@ Please try again later.\r\n"
#define SLAPD_SCHEMA_DN "cn=Subschema"
/* dn of the default "monitor" subentry */
#define SLAPD_MONITOR_DN "cn=Monitor"
#define SLAPD_MONITOR_NDN "CN=MONITOR"
#if 0
/* dn of the default "config" subentry */
#define SLAPD_CONFIG_DN "cn=Config"

View File

@ -1,12 +1,12 @@
# $OpenLDAP$
SRCS = init.c search.c compare.c abandon.c \
SRCS = init.c search.c compare.c abandon.c modify.c bind.c \
cache.c entry.c \
backend.c database.c thread.c conn.c rww.c \
backend.c database.c thread.c conn.c rww.c log.c \
dummy.c
OBJS = init.o search.o compare.o abandon.o \
OBJS = init.o search.o compare.o abandon.o modify.o bind.o \
cache.o entry.o \
backend.o database.o thread.o conn.o rww.o \
backend.o database.o thread.o conn.o rww.o log.o \
dummy.o
LDAP_INCDIR= ../../../include

View File

@ -144,6 +144,13 @@ struct monitorinfo {
#define SLAPD_MONITOR_WRITEW_DN \
SLAPD_MONITOR_WRITEW_RDN "," SLAPD_MONITOR_DN
#define SLAPD_MONITOR_LOG 9
#define SLAPD_MONITOR_LOG_NAME "Log"
#define SLAPD_MONITOR_LOG_RDN \
"cn=" SLAPD_MONITOR_LOG_NAME
#define SLAPD_MONITOR_LOG_DN \
SLAPD_MONITOR_LOG_RDN "," SLAPD_MONITOR_DN
struct monitorsubsys {
int mss_type;
char *mss_name;
@ -155,9 +162,16 @@ struct monitorsubsys {
#define MONITOR_HAS_VOLATILE_CH( mp ) \
( ( mp )->mp_flags & MONITOR_F_VOLATILE_CH )
/* initialize entry and subentries */
int ( *mss_init )( BackendDB * );
/* update existing dynamic entry and subentries */
int ( *mss_update )( struct monitorinfo *, Entry * );
int ( *mss_create )( struct monitorinfo *, const char *ndn, Entry *, Entry ** );
/* create new dynamic subentries */
int ( *mss_create )( struct monitorinfo *, const char *ndn,
Entry *, Entry ** );
/* modify entry and subentries */
int ( *mss_modify )( struct monitorinfo *, Entry *,
Modifications *modlist );
};
extern struct monitorsubsys monitor_subsys[];
@ -172,7 +186,7 @@ extern int monitor_cache_cmp LDAP_P(( const void *c1, const void *c2 ));
extern int monitor_cache_dup LDAP_P(( void *c1, void *c2 ));
extern int monitor_cache_add LDAP_P(( struct monitorinfo *mi, Entry *e ));
extern int monitor_cache_get LDAP_P(( struct monitorinfo *mi, const char *ndn, Entry **ep ));
extern int monitor_cache_dn2entry LDAP_P(( struct monitorinfo *mi, const char *ndn, Entry **ep ));
extern int monitor_cache_dn2entry LDAP_P(( struct monitorinfo *mi, const char *ndn, Entry **ep, Entry **matched ));
extern int monitor_cache_lock LDAP_P(( Entry *e ));
extern int monitor_cache_release LDAP_P(( struct monitorinfo *mi, Entry *e ));
@ -182,6 +196,7 @@ extern int monitor_cache_release LDAP_P(( struct monitorinfo *mi, Entry *e ));
extern int monitor_entry_update LDAP_P(( struct monitorinfo *mi, Entry *e ));
extern int monitor_entry_create LDAP_P(( struct monitorinfo *mi, const char *ndn, Entry *e_parent, Entry **ep ));
extern int monitor_entry_modify LDAP_P(( struct monitorinfo *mi, Entry *e, Modifications *modlist ));
LDAP_END_DECL

View File

@ -174,7 +174,8 @@ int
monitor_cache_dn2entry(
struct monitorinfo *mi,
const char *ndn,
Entry **ep
Entry **ep,
Entry **matched
)
{
int rc;
@ -186,6 +187,9 @@ monitor_cache_dn2entry(
assert( mi != NULL );
assert( ndn != NULL );
assert( ep != NULL );
assert( matched != NULL );
*matched = NULL;
rc = monitor_cache_get( mi, ndn, ep );
if ( !rc && *ep != NULL ) {
@ -194,7 +198,7 @@ monitor_cache_dn2entry(
/* try with parent/ancestors */
p_ndn = dn_parent( NULL, ndn );
rc = monitor_cache_dn2entry( mi, p_ndn, &e_parent );
rc = monitor_cache_dn2entry( mi, p_ndn, &e_parent, matched );
if ( rc || e_parent == NULL) {
return( -1 );
}
@ -205,7 +209,12 @@ monitor_cache_dn2entry(
/* parent entry generates volatile children */
rc = monitor_entry_create( mi, ndn, e_parent, ep );
}
monitor_cache_release( mi, e_parent );
if ( !rc ) {
monitor_cache_release( mi, e_parent );
} else {
*matched = e_parent;
}
return( rc );
}

View File

@ -51,6 +51,55 @@ monitor_back_compare(
AttributeAssertion *ava
)
{
return( 0 );
struct monitorinfo *mi = (struct monitorinfo *) be->be_private; int rc;
Entry *e, *matched = NULL;
Attribute *a;
/* get entry with reader lock */
monitor_cache_dn2entry( mi, ndn, &e, &matched );
if ( e == NULL ) {
send_ldap_result( conn, op, LDAP_NO_SUCH_OBJECT,
matched ? matched->e_dn : NULL,
NULL, NULL, NULL );
if ( matched ) {
monitor_cache_release( mi, matched );
}
return( 0 );
}
rc = access_allowed( be, conn, op, e, ava->aa_desc,
ava->aa_value, ACL_COMPARE );
if ( !rc ) {
send_ldap_result( conn, op, LDAP_INSUFFICIENT_ACCESS,
NULL, NULL, NULL, NULL );
rc = 1;
goto return_results;
}
rc = LDAP_NO_SUCH_ATTRIBUTE;
for ( a = attrs_find( e->e_attrs, ava->aa_desc );
a != NULL;
a = attrs_find( a->a_next, ava->aa_desc )) {
rc = LDAP_COMPARE_FALSE;
if ( value_find( ava->aa_desc, a->a_vals, ava->aa_value ) == 0 ) {
rc = LDAP_COMPARE_TRUE;
break;
}
}
send_ldap_result( conn, op, rc, NULL, NULL, NULL, NULL );
if( rc != LDAP_NO_SUCH_ATTRIBUTE ) {
rc = 0;
}
return_results:;
monitor_cache_release( mi, e );
return( rc );
}

View File

@ -85,6 +85,28 @@ monitor_entry_create(
return( 0 );
}
int
monitor_entry_modify(
struct monitorinfo *mi,
Entry *e,
Modifications *modlist
)
{
struct monitorentrypriv *mp;
assert( mi != NULL );
assert( e != NULL );
assert( e->e_private != NULL );
mp = ( struct monitorentrypriv * )e->e_private;
if ( mp->mp_info && mp->mp_info->mss_modify ) {
return ( *mp->mp_info->mss_modify )( mi, e, modlist );
}
return( 0 );
}
int
monitor_entry_test_flags(
struct monitorentrypriv *mp,

View File

@ -63,6 +63,15 @@ extern int monitor_back_compare LDAP_P(( BackendDB *bd,
extern int monitor_back_abandon LDAP_P(( BackendDB *bd,
Connection *conn, Operation *op, ber_int_t msgid ));
extern int monitor_back_modify LDAP_P(( BackendDB *bd,
Connection *conn, Operation *op,
const char *dn, const char *ndn, Modifications *ml ));
extern int monitor_back_bind LDAP_P(( BackendDB *bd,
Connection *conn, Operation *op,
const char *dn, const char *ndn, int method,
struct berval *cred, char** edn ));
LDAP_END_DECL
#endif /* _MONITOR_EXTERNAL_H */

View File

@ -61,63 +61,80 @@ struct monitorsubsys monitor_subsys[] = {
MONITOR_F_NONE,
NULL, /* init */
NULL, /* update */
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_DATABASE, SLAPD_MONITOR_DATABASE_NAME,
NULL, NULL, NULL,
MONITOR_F_PERSISTENT_CH,
monitor_subsys_database_init,
NULL, /* update */
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_BACKEND, SLAPD_MONITOR_BACKEND_NAME,
NULL, NULL, NULL,
MONITOR_F_PERSISTENT_CH,
monitor_subsys_backend_init,
NULL, /* update */
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_THREAD, SLAPD_MONITOR_THREAD_NAME,
NULL, NULL, NULL,
MONITOR_F_NONE,
NULL, /* init */
monitor_subsys_thread_init,
monitor_subsys_thread_update,
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_SASL, SLAPD_MONITOR_SASL_NAME,
NULL, NULL, NULL,
MONITOR_F_NONE,
NULL, /* init */
NULL, /* update */
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_TLS, SLAPD_MONITOR_TLS_NAME,
NULL, NULL, NULL,
MONITOR_F_NONE,
NULL, /* init */
NULL, /* update */
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_CONN, SLAPD_MONITOR_CONN_NAME,
NULL, NULL, NULL,
MONITOR_F_VOLATILE_CH,
monitor_subsys_conn_init,
monitor_subsys_conn_update,
monitor_subsys_conn_create
monitor_subsys_conn_create,
NULL /* modify */
}, {
SLAPD_MONITOR_READW, SLAPD_MONITOR_READW_NAME,
NULL, NULL, NULL,
MONITOR_F_NONE,
NULL, /* init */
monitor_subsys_readw_update,
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_WRITEW, SLAPD_MONITOR_WRITEW_NAME,
NULL, NULL, NULL,
MONITOR_F_NONE,
NULL, /* init */
monitor_subsys_writew_update,
NULL /* create */
NULL, /* create */
NULL /* modify */
}, {
SLAPD_MONITOR_LOG, SLAPD_MONITOR_LOG_NAME,
NULL, NULL, NULL,
MONITOR_F_NONE,
monitor_subsys_log_init,
NULL, /* update */
NULL, /* create */
monitor_subsys_log_modify
}, { -1, NULL }
};
@ -145,11 +162,11 @@ monitor_back_initialize(
bi->bi_db_close = NULL;
bi->bi_db_destroy = monitor_back_db_destroy;
bi->bi_op_bind = NULL;
bi->bi_op_bind = monitor_back_bind;
bi->bi_op_unbind = NULL;
bi->bi_op_search = monitor_back_search;
bi->bi_op_compare = monitor_back_compare;
bi->bi_op_modify = NULL;
bi->bi_op_modify = monitor_back_modify;
bi->bi_op_modrdn = NULL;
bi->bi_op_add = NULL;
bi->bi_op_delete = NULL;
@ -189,7 +206,7 @@ monitor_back_db_init(
Entry *e, *e_tmp;
struct monitorentrypriv *mp;
int i;
char buf[1024];
char buf[1024], *ndn;
const char *text;
if ( monitor_defined ) {
@ -205,8 +222,11 @@ monitor_back_db_init(
}
monitor_defined++;
charray_add( &be->be_suffix, SLAPD_MONITOR_DN );
ber_bvecadd( &be->be_nsuffix, ber_bvstr( SLAPD_MONITOR_NDN ));
ndn = ch_strdup( SLAPD_MONITOR_DN );
charray_add( &be->be_suffix, ndn );
dn_normalize( ndn );
ber_bvecadd( &be->be_nsuffix, ber_bvstr( ndn ) );
ch_free( ndn );
mi = ( struct monitorinfo * )ch_calloc( sizeof( struct monitorinfo ), 1 );
ldap_pvt_thread_mutex_init( &mi->mi_cache_mutex );
@ -358,11 +378,15 @@ monitor_back_open(
{
BackendDB *be;
struct monitorsubsys *ms;
char *ndn;
/*
* adds the monitor backend
*/
be = select_backend( SLAPD_MONITOR_NDN, 0 );
ndn = ch_strdup( SLAPD_MONITOR_DN );
dn_normalize( ndn );
be = select_backend( ndn , 0 );
ch_free( ndn );
if ( be == NULL ) {
#ifdef NEW_LOGGING
LDAP_LOG(( "operation", LDAP_LEVEL_CRIT,

View File

@ -0,0 +1,500 @@
/* log.c - deal with log subsystem */
/*
* Copyright 1998-2000 The OpenLDAP Foundation, All Rights Reserved.
* COPYING RESTRICTIONS APPLY, see COPYRIGHT file
*/
/*
* Copyright 2001 The OpenLDAP Foundation, All Rights Reserved.
* COPYING RESTRICTIONS APPLY, see COPYRIGHT file
*
* Copyright 2001, Pierangelo Masarati, All rights reserved. <ando@sys-net.it>
*
* This work has beed deveolped for the OpenLDAP Foundation
* in the hope that it may be useful to the Open Source community,
* but WITHOUT ANY WARRANTY.
*
* Permission is granted to anyone to use this software for any purpose
* on any computer system, and to alter it and redistribute it, subject
* to the following restrictions:
*
* 1. The author and SysNet s.n.c. are not responsible for the consequences
* of use of this software, no matter how awful, even if they arise from
* flaws in it.
*
* 2. The origin of this software must not be misrepresented, either by
* explicit claim or by omission. Since few users ever read sources,
* credits should appear in the documentation.
*
* 3. Altered versions must be plainly marked as such, and must not be
* misrepresented as being the original software. Since few users
* ever read sources, credits should appear in the documentation.
* SysNet s.n.c. cannot be responsible for the consequences of the
* alterations.
*
* 4. This notice may not be removed or altered.
*/
#include "portable.h"
#include <stdio.h>
#include <ac/string.h>
#include "slap.h"
#include "lutil.h"
#include "ldif.h"
#include "back-monitor.h"
/*
* log mutex
*/
ldap_pvt_thread_mutex_t monitor_log_mutex;
static struct {
int i;
const char *s;
} int_2_level[] = {
{ LDAP_DEBUG_TRACE, "Trace" },
{ LDAP_DEBUG_PACKETS, "Packets" },
{ LDAP_DEBUG_ARGS, "Args" },
{ LDAP_DEBUG_CONNS, "Conns" },
{ LDAP_DEBUG_BER, "BER" },
{ LDAP_DEBUG_FILTER, "Filter" },
{ LDAP_DEBUG_CONFIG, "Config" }, /* useless */
{ LDAP_DEBUG_ACL, "ACL" },
{ LDAP_DEBUG_STATS, "Stats" },
{ LDAP_DEBUG_STATS2, "Stats2" },
{ LDAP_DEBUG_SHELL, "Shell" },
{ LDAP_DEBUG_PARSE, "Parse" },
{ LDAP_DEBUG_CACHE, "Cache" },
{ LDAP_DEBUG_INDEX, "Index" },
{ 0, NULL }
};
static int loglevel2int( const char *str );
static const char * int2loglevel( int n );
static int add_values( Entry *e, Modification *mod, int *newlevel );
static int delete_values( Entry *e, Modification *mod, int *newlevel );
static int replace_values( Entry *e, Modification *mod, int *newlevel );
/*
* initializes log subentry
*/
int
monitor_subsys_log_init(
BackendDB *be
)
{
struct monitorinfo *mi;
Entry *e;
int i;
struct monitorentrypriv *mp;
struct berval val, *bv[2] = { &val, NULL };
ldap_pvt_thread_mutex_init( &monitor_log_mutex );
mi = ( struct monitorinfo * )be->be_private;
if ( monitor_cache_get( mi, monitor_subsys[SLAPD_MONITOR_LOG].mss_ndn,
&e ) ) {
#ifdef NEW_LOGGING
LDAP_LOG(( "operation", LDAP_LEVEL_CRIT,
"monitor_subsys_log_init: "
"unable to get entry '%s'\n",
monitor_subsys[SLAPD_MONITOR_LOG].mss_ndn ));
#else
Debug( LDAP_DEBUG_ANY,
"monitor_subsys_log_init: "
"unable to get entry '%s'\n%s%s",
monitor_subsys[SLAPD_MONITOR_LOG].mss_ndn,
"", "" );
#endif
return( -1 );
}
/* initialize the debug level */
for ( i = 0; int_2_level[ i ].i != 0; i++ ) {
if ( int_2_level[ i ].i & ldap_syslog ) {
val.bv_val = ( char * )int_2_level[ i ].s;
val.bv_len = strlen( val.bv_val );
attr_merge( e, monitor_ad_desc, bv );
}
}
monitor_cache_release( mi, e );
return( 0 );
}
int
monitor_subsys_log_modify(
struct monitorinfo *mi,
Entry *e,
Modifications *modlist
)
{
int rc = LDAP_OTHER;
int newlevel = ldap_syslog;
Attribute *save_attrs;
Modifications *ml;
ldap_pvt_thread_mutex_lock( &monitor_log_mutex );
save_attrs = e->e_attrs;
e->e_attrs = attrs_dup( e->e_attrs );
for ( ml = modlist; ml != NULL; ml = ml->sml_next ) {
Modification *mod = &ml->sml_mod;
/*
* Operational attributes
*/
#if 0
if ( mod->sm_desc == slap_schema.si_ad_modifyTimestamp
|| mod->sm_desc == slap_schema.si_ad_modifiersName ) {
( void ) attr_delete( &e->e_attrs, mod->sm_desc );
rc = attr_merge( e, mod->sm_desc, mod->sm_bvalues );
if ( rc != 0 ) {
rc = LDAP_OTHER;
break;
}
continue;
/*
* unhandled operational attributes
*/
} else if ( is_at_operational( mod->sm_desc->ad_type ) ) {
continue;
#else
if ( is_at_operational( mod->sm_desc->ad_type ) ) {
( void ) attr_delete( &e->e_attrs, mod->sm_desc );
rc = attr_merge( e, mod->sm_desc, mod->sm_bvalues );
if ( rc != 0 ) {
rc = LDAP_OTHER;
break;
}
continue;
#endif
/*
* only the monitor description attribute can be modified
*/
} else if ( mod->sm_desc != monitor_ad_desc ) {
rc = LDAP_UNWILLING_TO_PERFORM;
break;
}
switch ( mod->sm_op ) {
case LDAP_MOD_ADD:
rc = add_values( e, mod, &newlevel );
break;
case LDAP_MOD_DELETE:
rc = delete_values( e, mod, &newlevel );
break;
case LDAP_MOD_REPLACE:
rc = replace_values( e, mod, &newlevel );
break;
default:
rc = LDAP_OPERATIONS_ERROR;
break;
}
if ( rc != LDAP_SUCCESS ) {
break;
}
}
/* set the new debug level */
if ( rc == LDAP_SUCCESS ) {
const char *text;
static char textbuf[1024];
#if 0 /* need op */
/* check for abandon */
ldap_pvt_thread_mutex_lock( &op->o_abandonmutex );
if ( op->o_abandon ) {
ldap_pvt_thread_mutex_unlock( &op->o_abandonmutex );
rc = SLAPD_ABANDON;
goto cleanup;
}
#endif
/* check that the entry still obeys the schema */
rc = entry_schema_check( e, save_attrs, &text, textbuf,
sizeof( textbuf ) );
if ( rc != LDAP_SUCCESS ) {
goto cleanup;
}
ldap_syslog = newlevel;
#if 0
slap_debug = newlevel;
lutil_set_debug_level( "slapd", slap_debug );
ber_set_option(NULL, LBER_OPT_DEBUG_LEVEL, &slap_debug);
ldap_set_option(NULL, LDAP_OPT_DEBUG_LEVEL, &slap_debug);
ldif_debug = slap_debug;
#endif
}
cleanup:;
if ( rc == LDAP_SUCCESS ) {
attrs_free( save_attrs );
} else {
attrs_free( e->e_attrs );
e->e_attrs = save_attrs;
}
ldap_pvt_thread_mutex_unlock( &monitor_log_mutex );
return( rc );
}
static int
loglevel2int( const char *str )
{
int i;
for ( i = 0; int_2_level[ i ].i != 0; i++ ) {
if ( strcasecmp( str, int_2_level[ i ].s ) == 0 ) {
return int_2_level[ i ].i;
}
}
return 0;
}
static const char *
int2loglevel( int n )
{
int i;
for ( i = 0; int_2_level[ i ].i != 0; i++ ) {
if ( int_2_level[ i ].i == n ) {
return int_2_level[ i ].s;
}
}
return NULL;
}
static int
check_constraints( Modification *mod, int *newlevel )
{
int i;
for ( i = 0; mod->sm_bvalues && mod->sm_bvalues[i] != NULL; i++ ) {
int len, l;
const char *s;
l = loglevel2int( mod->sm_bvalues[i]->bv_val );
if ( !l ) {
return LDAP_CONSTRAINT_VIOLATION;
}
s = int2loglevel( l );
len = strlen( s );
assert( len == mod->sm_bvalues[i]->bv_len );
AC_MEMCPY( mod->sm_bvalues[i]->bv_val, s, len );
*newlevel |= l;
}
return LDAP_SUCCESS;
}
static int
add_values( Entry *e, Modification *mod, int *newlevel )
{
Attribute *a;
int i, rc;
MatchingRule *mr = mod->sm_desc->ad_type->sat_equality;
rc = check_constraints( mod, newlevel );
if ( rc != LDAP_SUCCESS ) {
return rc;
}
a = attr_find( e->e_attrs, mod->sm_desc );
if ( a != NULL ) {
/* "description" SHOULD have appropriate rules ... */
if ( mr == NULL || !mr->smr_match ) {
return LDAP_INAPPROPRIATE_MATCHING;
}
for ( i = 0; mod->sm_bvalues[i] != NULL; i++ ) {
int rc;
int j;
const char *text = NULL;
struct berval *asserted;
rc = value_normalize( mod->sm_desc,
SLAP_MR_EQUALITY,
mod->sm_bvalues[i],
&asserted,
&text );
if ( rc != LDAP_SUCCESS ) {
return rc;
}
for ( j = 0; a->a_vals[j] != NULL; j++ ) {
int match;
int rc = value_match( &match, mod->sm_desc, mr,
SLAP_MR_VALUE_SYNTAX_MATCH,
a->a_vals[j], asserted, &text );
if ( rc == LDAP_SUCCESS && match == 0 ) {
ber_bvfree( asserted );
return LDAP_TYPE_OR_VALUE_EXISTS;
}
}
ber_bvfree( asserted );
}
}
/* no - add them */
if ( attr_merge( e, mod->sm_desc, mod->sm_bvalues ) != 0 ) {
/* this should return result return of attr_merge */
return LDAP_OTHER;
}
return LDAP_SUCCESS;
}
static int
delete_values( Entry *e, Modification *mod, int *newlevel )
{
int i, j, k, found, rc, nl = 0;
Attribute *a;
char *desc = mod->sm_desc->ad_cname.bv_val;
MatchingRule *mr = mod->sm_desc->ad_type->sat_equality;
rc = check_constraints( mod, &nl );
if ( rc != LDAP_SUCCESS ) {
return rc;
}
*newlevel &= ~nl;
/* delete the entire attribute */
if ( mod->sm_bvalues == NULL ) {
int rc = attr_delete( &e->e_attrs, mod->sm_desc );
if ( rc ) {
rc = LDAP_NO_SUCH_ATTRIBUTE;
} else {
*newlevel = 0;
rc = LDAP_SUCCESS;
}
return rc;
}
if ( mr == NULL || !mr->smr_match ) {
/* disallow specific attributes from being deleted if
* no equality rule */
return LDAP_INAPPROPRIATE_MATCHING;
}
/* delete specific values - find the attribute first */
if ( (a = attr_find( e->e_attrs, mod->sm_desc )) == NULL ) {
return( LDAP_NO_SUCH_ATTRIBUTE );
}
/* find each value to delete */
for ( i = 0; mod->sm_bvalues[i] != NULL; i++ ) {
int rc;
const char *text = NULL;
struct berval *asserted;
rc = value_normalize( mod->sm_desc,
SLAP_MR_EQUALITY,
mod->sm_bvalues[i],
&asserted,
&text );
if( rc != LDAP_SUCCESS ) return rc;
found = 0;
for ( j = 0; a->a_vals[j] != NULL; j++ ) {
int match;
int rc = value_match( &match, mod->sm_desc, mr,
SLAP_MR_VALUE_SYNTAX_MATCH,
a->a_vals[j], asserted, &text );
if( rc == LDAP_SUCCESS && match != 0 ) {
continue;
}
/* found a matching value */
found = 1;
/* delete it */
ber_bvfree( a->a_vals[j] );
for ( k = j + 1; a->a_vals[k] != NULL; k++ ) {
a->a_vals[k - 1] = a->a_vals[k];
}
a->a_vals[k - 1] = NULL;
break;
}
ber_bvfree( asserted );
/* looked through them all w/o finding it */
if ( ! found ) {
return LDAP_NO_SUCH_ATTRIBUTE;
}
}
/* if no values remain, delete the entire attribute */
if ( a->a_vals[0] == NULL ) {
/* should already be zero */
*newlevel = 0;
if ( attr_delete( &e->e_attrs, mod->sm_desc ) ) {
return LDAP_NO_SUCH_ATTRIBUTE;
}
}
return LDAP_SUCCESS;
}
static int
replace_values( Entry *e, Modification *mod, int *newlevel )
{
int i, rc;
*newlevel = 0;
rc = check_constraints( mod, newlevel );
if ( rc != LDAP_SUCCESS ) {
return rc;
}
rc = attr_delete( &e->e_attrs, mod->sm_desc );
if ( rc != LDAP_SUCCESS && rc != LDAP_NO_SUCH_ATTRIBUTE ) {
return rc;
}
if ( mod->sm_bvalues != NULL &&
attr_merge( e, mod->sm_desc, mod->sm_bvalues ) != 0 ) {
return LDAP_OTHER;
}
return LDAP_SUCCESS;
}

View File

@ -60,6 +60,7 @@ int monitor_subsys_database_init LDAP_P(( BackendDB *be ));
/*
* threads
*/
int monitor_subsys_thread_init LDAP_P(( BackendDB *be ));
int monitor_subsys_thread_update LDAP_P(( struct monitorinfo *mi, Entry *e ));
/*
@ -79,5 +80,11 @@ int monitor_subsys_readw_update LDAP_P(( struct monitorinfo *mi, Entry *e ));
*/
int monitor_subsys_writew_update LDAP_P(( struct monitorinfo *mi, Entry *e ));
/*
* log
*/
int monitor_subsys_log_init LDAP_P(( BackendDB *be ));
int monitor_subsys_log_modify LDAP_P(( struct monitorinfo *mi, Entry *e, Modifications *modlist ));
LDAP_END_DECL
#endif

View File

@ -127,7 +127,7 @@ monitor_back_search(
{
struct monitorinfo *mi = (struct monitorinfo *) be->be_private;
int rc;
Entry *e;
Entry *e, *matched = NULL;
int nentries = 0;
#ifdef NEW_LOGGING
@ -139,10 +139,14 @@ monitor_back_search(
/* get entry with reader lock */
monitor_cache_dn2entry( mi, nbase, &e );
monitor_cache_dn2entry( mi, nbase, &e, &matched );
if ( e == NULL ) {
send_ldap_result( conn, op, LDAP_NO_SUCH_OBJECT,
NULL, NULL, NULL, NULL );
matched ? matched->e_dn : NULL,
NULL, NULL, NULL );
if ( matched ) {
monitor_cache_release( mi, matched );
}
return( 0 );
}

View File

@ -41,6 +41,52 @@
#include "slap.h"
#include "back-monitor.h"
/*
* * initializes log subentry
* */
int
monitor_subsys_thread_init(
BackendDB *be
)
{
struct monitorinfo *mi;
Entry *e;
struct monitorentrypriv *mp;
struct berval val, *bv[2] = { &val, NULL };
static char buf[1024];
mi = ( struct monitorinfo * )be->be_private;
if ( monitor_cache_get( mi,
monitor_subsys[SLAPD_MONITOR_THREAD].mss_ndn,
&e ) ) {
#ifdef NEW_LOGGING
LDAP_LOG(( "operation", LDAP_LEVEL_CRIT,
"monitor_subsys_thread_init: "
"unable to get entry '%s'\n",
monitor_subsys[SLAPD_MONITOR_THREAD].mss_ndn ));
#else
Debug( LDAP_DEBUG_ANY,
"monitor_subsys_thread_init: "
"unable to get entry '%s'\n%s%s",
monitor_subsys[SLAPD_MONITOR_THREAD].mss_ndn,
"", "" );
#endif
return( -1 );
}
/* initialize the thread number */
snprintf( buf, sizeof( buf ), "max=%d", connection_pool_max );
val.bv_val = buf;
val.bv_len = strlen( val.bv_val );
attr_merge( e, monitor_ad_desc, bv );
monitor_cache_release( mi, e );
return( 0 );
}
int
monitor_subsys_thread_update(
@ -55,15 +101,15 @@ monitor_subsys_thread_update(
bv[0] = &val;
bv[1] = NULL;
snprintf( buf, sizeof( buf ), "threads=%d",
snprintf( buf, sizeof( buf ), "backload=%d",
ldap_pvt_thread_pool_backload( &connection_pool ) );
if ( ( a = attr_find( e->e_attrs, monitor_ad_desc ) ) != NULL ) {
for ( b = a->a_vals; b[0] != NULL; b++ ) {
if ( strncmp( b[0]->bv_val, "threads=",
sizeof( "threads=" ) - 1 ) == 0 ) {
free( b[0]->bv_val );
if ( strncmp( b[0]->bv_val, "backload=",
sizeof( "backload=" ) - 1 ) == 0 ) {
ber_bvfree( b[0] );
b[0] = ber_bvstrdup( buf );
break;
}

View File

@ -446,6 +446,9 @@ read_config( const char *fname )
ldap_pvt_thread_pool_maxthreads( &connection_pool, c );
/* save for later use */
connection_pool_max = c;
/* get pid file name */
} else if ( strcasecmp( cargv[0], "pidfile" ) == 0 ) {
if ( cargc < 2 ) {

View File

@ -39,6 +39,7 @@ char **g_argv;
* global variables that need mutex protection
*/
ldap_pvt_thread_pool_t connection_pool;
int connection_pool_max = SLAP_MAX_WORKER_THREADS;
ldap_pvt_thread_mutex_t gmtime_mutex;
#if defined( SLAPD_CRYPT ) || defined( SLAPD_SPASSWD )
ldap_pvt_thread_mutex_t passwd_mutex;
@ -106,7 +107,7 @@ slap_init( int mode, const char *name )
(void) ldap_pvt_thread_initialize();
ldap_pvt_thread_pool_init(&connection_pool, SLAP_MAX_WORKER_THREADS, 0);
ldap_pvt_thread_pool_init(&connection_pool, connection_pool_max, 0);
ldap_pvt_thread_mutex_init( &entry2str_mutex );
ldap_pvt_thread_mutex_init( &replog_mutex );

View File

@ -921,6 +921,7 @@ LDAP_SLAPD_V (time_t) starttime;
#define slap_get_time() time( NULL )
LDAP_SLAPD_V (ldap_pvt_thread_pool_t) connection_pool;
LDAP_SLAPD_V (int) connection_pool_max;
LDAP_SLAPD_V (ldap_pvt_thread_mutex_t) entry2str_mutex;
LDAP_SLAPD_V (ldap_pvt_thread_mutex_t) replog_mutex;