2 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
4 * Copyright 1998-2014 The OpenLDAP Foundation.
5 * Portions Copyright 2008 Pierangelo Masarati.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted only as authorized by the OpenLDAP
12 * A copy of this license is available in the file LICENSE in the
13 * top-level directory of the distribution or, alternatively, at
14 * <http://www.OpenLDAP.org/license.html>.
17 * This work was initially developed by Pierangelo Masarati
18 * for inclusion in OpenLDAP Software.
24 #include <ac/stdlib.h>
25 #include <ac/string.h>
31 ldap_create_deref_control_value(
34 struct berval *value )
36 BerElement *ber = NULL;
40 if ( ld == NULL || value == NULL || ds == NULL )
43 ld->ld_errno = LDAP_PARAM_ERROR;
44 return LDAP_PARAM_ERROR;
47 assert( LDAP_VALID( ld ) );
51 ld->ld_errno = LDAP_SUCCESS;
53 ber = ldap_alloc_ber_with_options( ld );
55 ld->ld_errno = LDAP_NO_MEMORY;
59 tag = ber_printf( ber, "{" /*}*/ );
60 if ( tag == LBER_ERROR ) {
61 ld->ld_errno = LDAP_ENCODING_ERROR;
65 for ( i = 0; ds[i].derefAttr != NULL; i++ ) {
68 tag = ber_printf( ber, "{s{" /*}}*/ , ds[i].derefAttr );
69 if ( tag == LBER_ERROR ) {
70 ld->ld_errno = LDAP_ENCODING_ERROR;
74 for ( j = 0; ds[i].attributes[j] != NULL; j++ ) {
75 tag = ber_printf( ber, "s", ds[i].attributes[ j ] );
76 if ( tag == LBER_ERROR ) {
77 ld->ld_errno = LDAP_ENCODING_ERROR;
82 tag = ber_printf( ber, /*{{*/ "}N}" );
83 if ( tag == LBER_ERROR ) {
84 ld->ld_errno = LDAP_ENCODING_ERROR;
89 tag = ber_printf( ber, /*{*/ "}" );
90 if ( tag == LBER_ERROR ) {
91 ld->ld_errno = LDAP_ENCODING_ERROR;
95 if ( ber_flatten2( ber, value, 1 ) == -1 ) {
96 ld->ld_errno = LDAP_NO_MEMORY;
108 ldap_create_deref_control(
112 LDAPControl **ctrlp )
116 if ( ctrlp == NULL ) {
117 ld->ld_errno = LDAP_PARAM_ERROR;
121 ld->ld_errno = ldap_create_deref_control_value( ld, ds, &value );
122 if ( ld->ld_errno == LDAP_SUCCESS ) {
123 ld->ld_errno = ldap_control_create( LDAP_CONTROL_X_DEREF,
124 iscritical, &value, 0, ctrlp );
125 if ( ld->ld_errno != LDAP_SUCCESS ) {
126 LDAP_FREE( value.bv_val );
134 ldap_derefresponse_free( LDAPDerefRes *dr )
137 LDAPDerefRes *drnext = dr->next;
140 LDAP_FREE( dr->derefAttr );
141 LDAP_FREE( dr->derefVal.bv_val );
143 for ( dv = dr->attrVals; dv; ) {
144 LDAPDerefVal *dvnext = dv->next;
145 LDAP_FREE( dv->type );
146 ber_bvarray_free( dv->vals );
158 ldap_parse_derefresponse_control(
161 LDAPDerefRes **drp2 )
167 LDAPDerefRes *drhead = NULL, **drp;
169 if ( ld == NULL || ctrl == NULL || drp2 == NULL ) {
171 ld->ld_errno = LDAP_PARAM_ERROR;
172 return LDAP_PARAM_ERROR;
175 /* Create a BerElement from the berval returned in the control. */
176 ber = ber_init( &ctrl->ldctl_value );
179 ld->ld_errno = LDAP_NO_MEMORY;
183 /* Extract the count and cookie from the control. */
185 for ( tag = ber_first_element( ber, &len, &last );
187 tag = ber_next_element( ber, &len, last ) )
193 dr = LDAP_CALLOC( 1, sizeof(LDAPDerefRes) );
196 tag = ber_scanf( ber, "{ao", &dr->derefAttr, &dr->derefVal );
197 if ( tag == LBER_ERROR ) {
201 tag = ber_peek_tag( ber, &len );
202 if ( tag == (LBER_CONSTRUCTED|LBER_CLASS_CONTEXT) ) {
203 for ( tag = ber_first_element( ber, &len, &last2 );
205 tag = ber_next_element( ber, &len, last2 ) )
209 dv = LDAP_CALLOC( 1, sizeof(LDAPDerefVal) );
211 tag = ber_scanf( ber, "{a[W]}", &dv->type, &dv->vals );
212 if ( tag == LBER_ERROR ) {
221 tag = ber_scanf( ber, "}" );
222 if ( tag == LBER_ERROR ) {
235 if ( tag == LBER_ERROR ) {
236 if ( drhead != NULL ) {
237 ldap_derefresponse_free( drhead );
241 ld->ld_errno = LDAP_DECODING_ERROR;
245 ld->ld_errno = LDAP_SUCCESS;
252 ldap_parse_deref_control(
260 ld->ld_errno = LDAP_PARAM_ERROR;
266 if ( ctrls == NULL ) {
267 ld->ld_errno = LDAP_CONTROL_NOT_FOUND;
271 c = ldap_control_find( LDAP_CONTROL_X_DEREF, ctrls, NULL );
273 /* No deref control was found. */
274 ld->ld_errno = LDAP_CONTROL_NOT_FOUND;
278 ld->ld_errno = ldap_parse_derefresponse_control( ld, c, drp );