version 1.37.2.2, 2005/01/20 18:04:04
|
version 1.37.2.3, 2005/01/24 21:28:53
|
Line 1
|
Line 1
|
/* rwm.c - rewrite/remap operations */ |
/* rwm.c - rewrite/remap operations */ |
/* $OpenLDAP: pkg/ldap/servers/slapd/overlays/rwm.c,v 1.37.2.1 2004/12/30 21:29:58 kurt Exp $ */ |
/* $OpenLDAP: pkg/ldap/servers/slapd/overlays/rwm.c,v 1.45 2005/01/20 21:44:54 ando Exp $ */ |
/* This work is part of OpenLDAP Software <http://www.openldap.org/>. |
/* This work is part of OpenLDAP Software <http://www.openldap.org/>. |
* |
* |
* Copyright 2003-2005 The OpenLDAP Foundation. |
* Copyright 2003-2005 The OpenLDAP Foundation. |
Line 121 rwm_op_add( Operation *op, SlapReply *rs
|
Line 121 rwm_op_add( Operation *op, SlapReply *rs
|
/* Count number of attributes in entry */ |
/* Count number of attributes in entry */ |
isupdate = be_shadow_update( op ); |
isupdate = be_shadow_update( op ); |
for ( i = 0, ap = &op->oq_add.rs_e->e_attrs; *ap; ) { |
for ( i = 0, ap = &op->oq_add.rs_e->e_attrs; *ap; ) { |
struct berval mapped; |
|
Attribute *a; |
Attribute *a; |
|
|
if ( !isupdate && (*ap)->a_desc->ad_type->sat_no_user_mod ) { |
if ( (*ap)->a_desc == slap_schema.si_ad_objectClass || |
|
(*ap)->a_desc == slap_schema.si_ad_structuralObjectClass ) |
|
{ |
|
int j, last; |
|
|
|
for ( last = 0; !BER_BVISNULL( &(*ap)->a_vals[ last ] ); last++ ) |
|
/* count values */ ; |
|
last--; |
|
for ( j = 0; !BER_BVISNULL( &(*ap)->a_vals[ j ] ); j++ ) { |
|
struct ldapmapping *mapping = NULL; |
|
|
|
( void )rwm_mapping( &rwmap->rwm_oc, &(*ap)->a_vals[ j ], |
|
&mapping, RWM_MAP ); |
|
if ( mapping == NULL ) { |
|
if ( rwmap->rwm_at.drop_missing ) { |
|
/* FIXME: we allow to remove objectClasses as well; |
|
* if the resulting entry is inconsistent, that's |
|
* the relayed database's business... |
|
*/ |
|
ch_free( (*ap)->a_vals[ j ].bv_val ); |
|
if ( last > j ) { |
|
(*ap)->a_vals[ j ] = (*ap)->a_vals[ last ]; |
|
} |
|
BER_BVZERO( &(*ap)->a_vals[ last ] ); |
|
last--; |
|
j--; |
|
} |
|
|
|
} else { |
|
ch_free( (*ap)->a_vals[ j ].bv_val ); |
|
ber_dupbv( &(*ap)->a_vals[ j ], &mapping->m_dst ); |
|
} |
|
} |
|
|
|
} else if ( !isupdate && (*ap)->a_desc->ad_type->sat_no_user_mod ) { |
goto next_attr; |
goto next_attr; |
} |
|
|
|
rwm_map( &rwmap->rwm_at, &(*ap)->a_desc->ad_cname, |
} else { |
&mapped, RWM_MAP ); |
struct ldapmapping *mapping = NULL; |
if ( BER_BVISNULL( &mapped ) || BER_BVISEMPTY( &mapped ) ) { |
|
goto cleanup_attr; |
|
} |
|
|
|
if ( (*ap)->a_desc->ad_type->sat_syntax |
( void )rwm_mapping( &rwmap->rwm_at, &(*ap)->a_desc->ad_cname, |
== slap_schema.si_syn_distinguishedName ) |
&mapping, RWM_MAP ); |
{ |
if ( mapping == NULL ) { |
/* |
if ( rwmap->rwm_at.drop_missing ) { |
* FIXME: rewrite could fail; in this case |
goto cleanup_attr; |
* the operation should give up, right? |
} |
*/ |
|
#ifdef ENABLE_REWRITE |
|
rc = rwm_dnattr_rewrite( op, rs, "addAttrDN", |
|
(*ap)->a_vals, |
|
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
|
#else /* ! ENABLE_REWRITE */ |
|
rc = 1; |
|
rc = rwm_dnattr_rewrite( op, rs, &rc, (*ap)->a_vals, |
|
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
|
#endif /* ! ENABLE_REWRITE */ |
|
if ( rc ) { |
|
goto cleanup_attr; |
|
} |
} |
|
|
} else if ( (*ap)->a_desc == slap_schema.si_ad_ref ) { |
if ( (*ap)->a_desc->ad_type->sat_syntax |
|
== slap_schema.si_syn_distinguishedName ) |
|
{ |
|
/* |
|
* FIXME: rewrite could fail; in this case |
|
* the operation should give up, right? |
|
*/ |
|
#ifdef ENABLE_REWRITE |
|
rc = rwm_dnattr_rewrite( op, rs, "addAttrDN", |
|
(*ap)->a_vals, |
|
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
|
#else /* ! ENABLE_REWRITE */ |
|
rc = 1; |
|
rc = rwm_dnattr_rewrite( op, rs, &rc, (*ap)->a_vals, |
|
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
|
#endif /* ! ENABLE_REWRITE */ |
|
if ( rc ) { |
|
goto cleanup_attr; |
|
} |
|
|
|
} else if ( (*ap)->a_desc == slap_schema.si_ad_ref ) { |
#ifdef ENABLE_REWRITE |
#ifdef ENABLE_REWRITE |
rc = rwm_referral_rewrite( op, rs, "referralAttrDN", |
rc = rwm_referral_rewrite( op, rs, "referralAttrDN", |
(*ap)->a_vals, |
(*ap)->a_vals, |
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
#else /* ! ENABLE_REWRITE */ |
#else /* ! ENABLE_REWRITE */ |
rc = 1; |
rc = 1; |
rc = rwm_referral_rewrite( op, rs, &rc, (*ap)->a_vals, |
rc = rwm_referral_rewrite( op, rs, &rc, (*ap)->a_vals, |
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
(*ap)->a_nvals ? &(*ap)->a_nvals : NULL ); |
#endif /* ! ENABLE_REWRITE */ |
#endif /* ! ENABLE_REWRITE */ |
if ( rc != LDAP_SUCCESS ) { |
if ( rc != LDAP_SUCCESS ) { |
goto cleanup_attr; |
goto cleanup_attr; |
|
} |
|
} |
|
|
|
if ( mapping != NULL ) { |
|
assert( mapping->m_dst_ad ); |
|
(*ap)->a_desc = mapping->m_dst_ad; |
} |
} |
} |
} |
|
|
|
|
next_attr:; |
next_attr:; |
ap = &(*ap)->a_next; |
ap = &(*ap)->a_next; |
continue; |
continue; |
Line 281 rwm_op_compare( Operation *op, SlapReply
|
Line 323 rwm_op_compare( Operation *op, SlapReply
|
} |
} |
|
|
} else { |
} else { |
|
assert( mapping->m_dst_ad ); |
ad = mapping->m_dst_ad; |
ad = mapping->m_dst_ad; |
} |
} |
|
|
Line 360 rwm_op_modify( Operation *op, SlapReply
|
Line 403 rwm_op_modify( Operation *op, SlapReply
|
|
|
isupdate = be_shadow_update( op ); |
isupdate = be_shadow_update( op ); |
for ( mlp = &op->oq_modify.rs_modlist; *mlp; ) { |
for ( mlp = &op->oq_modify.rs_modlist; *mlp; ) { |
int is_oc = 0; |
int is_oc = 0; |
Modifications *ml; |
Modifications *ml; |
|
struct ldapmapping *mapping = NULL; |
if ( !isupdate && (*mlp)->sml_desc->ad_type->sat_no_user_mod ) { |
|
goto next_mod; |
|
} |
|
|
|
if ( (*mlp)->sml_desc == slap_schema.si_ad_objectClass |
if ( (*mlp)->sml_desc == slap_schema.si_ad_objectClass |
|| (*mlp)->sml_desc == slap_schema.si_ad_structuralObjectClass ) { |
|| (*mlp)->sml_desc == slap_schema.si_ad_structuralObjectClass ) |
|
{ |
is_oc = 1; |
is_oc = 1; |
|
|
|
} else if ( !isupdate && (*mlp)->sml_desc->ad_type->sat_no_user_mod ) { |
|
goto next_mod; |
|
|
} else { |
} else { |
struct ldapmapping *m; |
|
int drop_missing; |
int drop_missing; |
|
|
drop_missing = rwm_mapping( &rwmap->rwm_at, &(*mlp)->sml_desc->ad_cname, &m, RWM_MAP ); |
drop_missing = rwm_mapping( &rwmap->rwm_at, |
if ( drop_missing || ( m != NULL && BER_BVISNULL( &m->m_dst ) ) ) |
&(*mlp)->sml_desc->ad_cname, |
|
&mapping, RWM_MAP ); |
|
if ( drop_missing || ( mapping != NULL && BER_BVISNULL( &mapping->m_dst ) ) ) |
{ |
{ |
goto cleanup_mod; |
goto cleanup_mod; |
} |
} |
|
|
if ( m ) { |
|
/* use new attribute description */ |
|
assert( m->m_dst_ad ); |
|
(*mlp)->sml_desc = m->m_dst_ad; |
|
} |
|
} |
} |
|
|
if ( (*mlp)->sml_values != NULL ) { |
if ( (*mlp)->sml_values != NULL ) { |
if ( is_oc ) { |
if ( is_oc ) { |
int last, j; |
int last, j; |
|
|
for ( last = 0; !BER_BVISNULL( &(*mlp)->sml_values[last] ); last++ ) |
for ( last = 0; !BER_BVISNULL( &(*mlp)->sml_values[ last ] ); last++ ) |
/* count values */ ; |
/* count values */ ; |
last--; |
last--; |
|
|
for ( j = 0; !BER_BVISNULL( &(*mlp)->sml_values[j] ); j++ ) { |
for ( j = 0; !BER_BVISNULL( &(*mlp)->sml_values[ j ] ); j++ ) { |
struct berval mapped = BER_BVNULL; |
struct ldapmapping *mapping = NULL; |
|
|
rwm_map( &rwmap->rwm_oc, |
( void )rwm_mapping( &rwmap->rwm_oc, &(*mlp)->sml_values[ j ], |
&(*mlp)->sml_values[j], |
&mapping, RWM_MAP ); |
&mapped, RWM_MAP ); |
if ( mapping == NULL ) { |
if ( BER_BVISNULL( &mapped ) || BER_BVISEMPTY( &mapped ) ) { |
if ( rwmap->rwm_at.drop_missing ) { |
/* FIXME: we allow to remove objectClasses as well; |
/* FIXME: we allow to remove objectClasses as well; |
* if the resulting entry is inconsistent, that's |
* if the resulting entry is inconsistent, that's |
* the relayed database's business... |
* the relayed database's business... |
*/ |
*/ |
#if 0 |
ch_free( (*mlp)->sml_values[ j ].bv_val ); |
goto cleanup_mod; |
if ( last > j ) { |
#endif |
(*mlp)->sml_values[ j ] = (*mlp)->sml_values[ last ]; |
if ( last > j ) { |
} |
(*mlp)->sml_values[j] = (*mlp)->sml_values[last]; |
BER_BVZERO( &(*mlp)->sml_values[ last ] ); |
BER_BVZERO( &(*mlp)->sml_values[last] ); |
last--; |
|
j--; |
} |
} |
last--; |
|
|
|
} else { |
} else { |
ch_free( (*mlp)->sml_values[j].bv_val ); |
ch_free( (*mlp)->sml_values[ j ].bv_val ); |
ber_dupbv( &(*mlp)->sml_values[j], &mapped ); |
ber_dupbv( &(*mlp)->sml_values[ j ], &mapping->m_dst ); |
} |
} |
} |
} |
|
|
Line 461 rwm_op_modify( Operation *op, SlapReply
|
Line 500 rwm_op_modify( Operation *op, SlapReply
|
} |
} |
|
|
next_mod:; |
next_mod:; |
|
if ( mapping != NULL ) { |
|
/* use new attribute description */ |
|
assert( mapping->m_dst_ad ); |
|
(*mlp)->sml_desc = mapping->m_dst_ad; |
|
} |
|
|
mlp = &(*mlp)->sml_next; |
mlp = &(*mlp)->sml_next; |
continue; |
continue; |
|
|
Line 777 rwm_attrs( Operation *op, SlapReply *rs,
|
Line 822 rwm_attrs( Operation *op, SlapReply *rs,
|
* about duplicate values?) */ |
* about duplicate values?) */ |
isupdate = be_shadow_update( op ); |
isupdate = be_shadow_update( op ); |
for ( ap = a_first; *ap; ) { |
for ( ap = a_first; *ap; ) { |
struct ldapmapping *m; |
struct ldapmapping *mapping; |
int drop_missing; |
int drop_missing; |
int last; |
int last; |
Attribute *a; |
Attribute *a; |
Line 786 rwm_attrs( Operation *op, SlapReply *rs,
|
Line 831 rwm_attrs( Operation *op, SlapReply *rs,
|
{ |
{ |
/* go on */ ; |
/* go on */ ; |
|
|
} else if ( op->ors_attrs != NULL && |
} else { |
!SLAP_USERATTRS( rs->sr_attr_flags ) && |
drop_missing = rwm_mapping( &rwmap->rwm_at, |
!ad_inlist( (*ap)->a_desc, op->ors_attrs ) ) |
&(*ap)->a_desc->ad_cname, &mapping, RWM_REMAP ); |
{ |
if ( drop_missing || ( mapping != NULL && BER_BVISEMPTY( &mapping->m_dst ) ) ) |
|
{ |
|
goto cleanup_attr; |
|
} |
|
|
|
if ( mapping != NULL ) { |
|
(*ap)->a_desc = mapping->m_dst_ad; |
|
} |
|
|
|
if ( op->ors_attrs != NULL && |
|
!SLAP_USERATTRS( rs->sr_attr_flags ) && |
|
!ad_inlist( (*ap)->a_desc, op->ors_attrs ) ) |
|
{ |
|
goto cleanup_attr; |
|
} |
|
} |
|
|
|
if ( (*ap)->a_desc == slap_schema.si_ad_entryDN ) { |
|
/* will be generated by frontend */ |
goto cleanup_attr; |
goto cleanup_attr; |
} |
} |
|
|
Line 799 rwm_attrs( Operation *op, SlapReply *rs,
|
Line 862 rwm_attrs( Operation *op, SlapReply *rs,
|
goto next_attr; |
goto next_attr; |
} |
} |
|
|
drop_missing = rwm_mapping( &rwmap->rwm_at, |
|
&(*ap)->a_desc->ad_cname, &m, RWM_REMAP ); |
|
if ( drop_missing || ( m != NULL && BER_BVISEMPTY( &m->m_dst ) ) ) { |
|
goto cleanup_attr; |
|
} |
|
|
|
for ( last = 0; !BER_BVISNULL( &(*ap)->a_vals[last] ); last++ ) |
for ( last = 0; !BER_BVISNULL( &(*ap)->a_vals[last] ); last++ ) |
/* just count */ ; |
/* just count */ ; |
|
|
Line 877 rwm_attrs( Operation *op, SlapReply *rs,
|
Line 934 rwm_attrs( Operation *op, SlapReply *rs,
|
} |
} |
} |
} |
|
|
if ( m != NULL ) { |
if ( mapping != NULL ) { |
/* rewrite the attribute description */ |
/* rewrite the attribute description */ |
assert( m->m_dst_ad ); |
assert( mapping->m_dst_ad ); |
(*ap)->a_desc = m->m_dst_ad; |
(*ap)->a_desc = mapping->m_dst_ad; |
} |
} |
|
|
next_attr:; |
next_attr:; |