init.c revision 1.2
1/* $NetBSD: init.c,v 1.2 2020/08/11 13:15:41 christos Exp $ */ 2 3/* init.c - initialize relay backend */ 4/* $OpenLDAP$ */ 5/* This work is part of OpenLDAP Software <http://www.openldap.org/>. 6 * 7 * Copyright 2004-2020 The OpenLDAP Foundation. 8 * Portions Copyright 2004 Pierangelo Masarati. 9 * All rights reserved. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted only as authorized by the OpenLDAP 13 * Public License. 14 * 15 * A copy of this license is available in the file LICENSE in the 16 * top-level directory of the distribution or, alternatively, at 17 * <http://www.OpenLDAP.org/license.html>. 18 */ 19/* ACKNOWLEDGEMENTS: 20 * This work was initially developed by Pierangelo Masarati for inclusion 21 * in OpenLDAP Software. 22 */ 23 24#include <sys/cdefs.h> 25__RCSID("$NetBSD: init.c,v 1.2 2020/08/11 13:15:41 christos Exp $"); 26 27#include "portable.h" 28 29#include <stdio.h> 30#include <ac/string.h> 31 32#include "slap.h" 33#include "config.h" 34#include "back-relay.h" 35 36static ConfigDriver relay_back_cf; 37 38static ConfigTable relaycfg[] = { 39 { "relay", "relay", 2, 2, 0, 40 ARG_MAGIC|ARG_DN|ARG_QUOTE, 41 relay_back_cf, "( OLcfgDbAt:5.1 " 42 "NAME 'olcRelay' " 43 "DESC 'Relay DN' " 44 "SYNTAX OMsDN " 45 "SINGLE-VALUE )", 46 NULL, NULL }, 47 { NULL } 48}; 49 50static ConfigOCs relayocs[] = { 51 { "( OLcfgDbOc:5.1 " 52 "NAME 'olcRelayConfig' " 53 "DESC 'Relay backend configuration' " 54 "SUP olcDatabaseConfig " 55 "MAY ( olcRelay " 56 ") )", 57 Cft_Database, relaycfg}, 58 { NULL, 0, NULL } 59}; 60 61static int 62relay_back_cf( ConfigArgs *c ) 63{ 64 relay_back_info *ri = ( relay_back_info * )c->be->be_private; 65 int rc = 0; 66 67 if ( c->op == SLAP_CONFIG_EMIT ) { 68 if ( ri != NULL && !BER_BVISNULL( &ri->ri_realsuffix ) ) { 69 value_add_one( &c->rvalue_vals, &ri->ri_realsuffix ); 70 return 0; 71 } 72 return 1; 73 74 } else if ( c->op == LDAP_MOD_DELETE ) { 75 if ( !BER_BVISNULL( &ri->ri_realsuffix ) ) { 76 ch_free( ri->ri_realsuffix.bv_val ); 77 BER_BVZERO( &ri->ri_realsuffix ); 78 ri->ri_bd = NULL; 79 return 0; 80 } 81 return 1; 82 83 } else { 84 BackendDB *bd; 85 86 assert( ri != NULL ); 87 assert( BER_BVISNULL( &ri->ri_realsuffix ) ); 88 89 if ( c->be->be_nsuffix == NULL ) { 90 snprintf( c->cr_msg, sizeof( c->cr_msg), 91 "\"relay\" directive " 92 "must appear after \"suffix\"" ); 93 Log2( LDAP_DEBUG_ANY, LDAP_LEVEL_ERR, 94 "%s: %s.\n", c->log, c->cr_msg ); 95 rc = 1; 96 goto relay_done; 97 } 98 99 if ( !BER_BVISNULL( &c->be->be_nsuffix[ 1 ] ) ) { 100 snprintf( c->cr_msg, sizeof( c->cr_msg), 101 "relaying of multiple suffix " 102 "database not supported" ); 103 Log2( LDAP_DEBUG_ANY, LDAP_LEVEL_ERR, 104 "%s: %s.\n", c->log, c->cr_msg ); 105 rc = 1; 106 goto relay_done; 107 } 108 109 bd = select_backend( &c->value_ndn, 1 ); 110 if ( bd == NULL ) { 111 snprintf( c->cr_msg, sizeof( c->cr_msg), 112 "cannot find database " 113 "of relay dn \"%s\" " 114 "in \"olcRelay <dn>\"\n", 115 c->value_dn.bv_val ); 116 Log2( LDAP_DEBUG_CONFIG, LDAP_LEVEL_ERR, 117 "%s: %s.\n", c->log, c->cr_msg ); 118 119 } else if ( bd->be_private == c->be->be_private ) { 120 snprintf( c->cr_msg, sizeof( c->cr_msg), 121 "relay dn \"%s\" would call self " 122 "in \"relay <dn>\" line\n", 123 c->value_dn.bv_val ); 124 Log2( LDAP_DEBUG_ANY, LDAP_LEVEL_ERR, 125 "%s: %s.\n", c->log, c->cr_msg ); 126 rc = 1; 127 goto relay_done; 128 } 129 130 ri->ri_realsuffix = c->value_ndn; 131 BER_BVZERO( &c->value_ndn ); 132 133relay_done:; 134 ch_free( c->value_dn.bv_val ); 135 ch_free( c->value_ndn.bv_val ); 136 } 137 138 return rc; 139} 140 141int 142relay_back_initialize( BackendInfo *bi ) 143{ 144 bi->bi_init = 0; 145 bi->bi_open = 0; 146 bi->bi_config = 0; 147 bi->bi_close = 0; 148 bi->bi_destroy = 0; 149 150 bi->bi_db_init = relay_back_db_init; 151 bi->bi_db_config = config_generic_wrapper; 152 bi->bi_db_open = relay_back_db_open; 153#if 0 154 bi->bi_db_close = relay_back_db_close; 155#endif 156 bi->bi_db_destroy = relay_back_db_destroy; 157 158 bi->bi_op_bind = relay_back_op_bind; 159 bi->bi_op_search = relay_back_op_search; 160 bi->bi_op_compare = relay_back_op_compare; 161 bi->bi_op_modify = relay_back_op_modify; 162 bi->bi_op_modrdn = relay_back_op_modrdn; 163 bi->bi_op_add = relay_back_op_add; 164 bi->bi_op_delete = relay_back_op_delete; 165 bi->bi_extended = relay_back_op_extended; 166 bi->bi_entry_release_rw = relay_back_entry_release_rw; 167 bi->bi_entry_get_rw = relay_back_entry_get_rw; 168 bi->bi_operational = relay_back_operational; 169 bi->bi_has_subordinates = relay_back_has_subordinates; 170 171 bi->bi_cf_ocs = relayocs; 172 173 return config_register_schema( relaycfg, relayocs ); 174} 175 176int 177relay_back_db_init( Backend *be, ConfigReply *cr) 178{ 179 relay_back_info *ri; 180 181 be->be_private = NULL; 182 183 ri = (relay_back_info *) ch_calloc( 1, RELAY_INFO_SIZE ); 184 if ( ri == NULL ) { 185 return -1; 186 } 187 188 ri->ri_bd = NULL; 189 BER_BVZERO( &ri->ri_realsuffix ); 190 ri->ri_massage = 0; 191 192 be->be_cf_ocs = be->bd_info->bi_cf_ocs; 193 194 be->be_private = (void *)ri; 195 196 return 0; 197} 198 199int 200relay_back_db_open( Backend *be, ConfigReply *cr ) 201{ 202 relay_back_info *ri = (relay_back_info *)be->be_private; 203 204 assert( ri != NULL ); 205 206 if ( !BER_BVISNULL( &ri->ri_realsuffix ) ) { 207 ri->ri_bd = select_backend( &ri->ri_realsuffix, 1 ); 208 209 /* must be there: it was during config! */ 210 if ( ri->ri_bd == NULL ) { 211 snprintf( cr->msg, sizeof( cr->msg), 212 "cannot find database " 213 "of relay dn \"%s\" " 214 "in \"olcRelay <dn>\"\n", 215 ri->ri_realsuffix.bv_val ); 216 Log1( LDAP_DEBUG_ANY, LDAP_LEVEL_ERR, 217 "relay_back_db_open: %s.\n", cr->msg ); 218 219 return 1; 220 } 221 222 /* inherit controls */ 223 AC_MEMCPY( be->bd_self->be_ctrls, ri->ri_bd->be_ctrls, sizeof( be->be_ctrls ) ); 224 225 } else { 226 /* inherit all? */ 227 AC_MEMCPY( be->bd_self->be_ctrls, frontendDB->be_ctrls, sizeof( be->be_ctrls ) ); 228 } 229 230 return 0; 231} 232 233int 234relay_back_db_close( Backend *be, ConfigReply *cr ) 235{ 236 return 0; 237} 238 239int 240relay_back_db_destroy( Backend *be, ConfigReply *cr) 241{ 242 relay_back_info *ri = (relay_back_info *)be->be_private; 243 244 if ( ri ) { 245 if ( !BER_BVISNULL( &ri->ri_realsuffix ) ) { 246 ch_free( ri->ri_realsuffix.bv_val ); 247 } 248 ch_free( ri ); 249 } 250 251 return 0; 252} 253 254#if SLAPD_RELAY == SLAPD_MOD_DYNAMIC 255 256/* conditionally define the init_module() function */ 257SLAP_BACKEND_INIT_MODULE( relay ) 258 259#endif /* SLAPD_RELAY == SLAPD_MOD_DYNAMIC */ 260