From: Rein Tollevik Date: Sun, 21 Nov 2010 15:31:38 +0000 (+0000) Subject: ITS#6709: Wait for active mods to finish before initiating new consumers. X-Git-Tag: MIGRATION_CVS2GIT~415 X-Git-Url: https://git.sur5r.net/?a=commitdiff_plain;h=877fc0ab3729f6ba6512528c3c0def1c1067bee0;p=openldap ITS#6709: Wait for active mods to finish before initiating new consumers. --- diff --git a/servers/slapd/overlays/syncprov.c b/servers/slapd/overlays/syncprov.c index cd6a1889ef..adf012cedd 100644 --- a/servers/slapd/overlays/syncprov.c +++ b/servers/slapd/overlays/syncprov.c @@ -133,6 +133,7 @@ typedef struct syncprov_info_t { int si_numops; /* number of ops since last checkpoint */ int si_nopres; /* Skip present phase */ int si_usehint; /* use reload hint */ + int si_active; /* True if there are active mods */ time_t si_chklast; /* time of last checkpoint */ Avlnode *si_mods; /* entries being modified */ sessionlog *si_logs; @@ -1377,6 +1378,11 @@ syncprov_op_cleanup( Operation *op, SlapReply *rs ) syncmatches *sm, *snext; modtarget *mt, mtdummy; + ldap_pvt_thread_mutex_lock( &si->si_ops_mutex ); + if ( si->si_active ) + si->si_active--; + ldap_pvt_thread_mutex_unlock( &si->si_ops_mutex ); + for (sm = opc->smatches; sm; sm=snext) { snext = sm->sm_next; syncprov_free_syncop( sm->sm_op ); @@ -1977,6 +1983,7 @@ syncprov_op_mod( Operation *op, SlapReply *rs ) ldap_pvt_thread_mutex_lock( &si->si_ops_mutex ); have_psearches = ( si->si_ops != NULL ); + si->si_active++; ldap_pvt_thread_mutex_unlock( &si->si_ops_mutex ); cbsize = sizeof(slap_callback) + sizeof(opcookie) + @@ -2411,6 +2418,20 @@ syncprov_op_search( Operation *op, SlapReply *rs ) sop->s_inuse = 1; ldap_pvt_thread_mutex_lock( &si->si_ops_mutex ); + while ( si->si_active ) { + /* Wait for active mods to finish before proceeding, as they + * may already have inspected the si_ops list looking for + * consumers to replicate the change to. Using the log + * doesn't help, as we may finish playing it before the + * active mods gets added to it. + */ + ldap_pvt_thread_mutex_unlock( &si->si_ops_mutex ); + if ( slapd_shutdown ) + return SLAPD_ABANDON; + if ( !ldap_pvt_thread_pool_pausecheck( &connection_pool )) + ldap_pvt_thread_yield(); + ldap_pvt_thread_mutex_lock( &si->si_ops_mutex ); + } sop->s_next = si->si_ops; si->si_ops = sop; ldap_pvt_thread_mutex_unlock( &si->si_ops_mutex );