2 * Copyright 2002-2003 Sun Microsystems, Inc. All rights reserved.
3 * Use is subject to license terms.
6 #pragma ident "%Z%%M% %I% %E% SMI"
9 * The contents of this file are subject to the Netscape Public
10 * License Version 1.1 (the "License"); you may not use this file
11 * except in compliance with the License. You may obtain a copy of
12 * the License at http://www.mozilla.org/NPL/
14 * Software distributed under the License is distributed on an "AS
15 * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
16 * implied. See the License for the specific language governing
17 * rights and limitations under the License.
19 * The Original Code is Mozilla Communicator client code, released
22 * The Initial Developer of the Original Code is Netscape
23 * Communications Corporation. Portions created by Netscape are
24 * Copyright (C) 1998-1999 Netscape Communications Corporation. All
30 * Copyright (c) 1990 Regents of the University of Michigan.
31 * All rights reserved.
39 static char copyright
[] = "@(#) Copyright (c) 1990 Regents of the University of Michigan.\nAll rights reserved.\n";
46 ldap_unbind( LDAP
*ld
)
48 LDAPDebug( LDAP_DEBUG_TRACE
, "ldap_unbind\n", 0, 0, 0 );
50 return( ldap_ld_free( ld
, NULL
, NULL
, 1 ) );
56 ldap_unbind_s( LDAP
*ld
)
58 return( ldap_ld_free( ld
, NULL
, NULL
, 1 ));
64 ldap_unbind_ext( LDAP
*ld
, LDAPControl
**serverctrls
,
65 LDAPControl
**clientctrls
)
67 return( ldap_ld_free( ld
, serverctrls
, clientctrls
, 1 ));
72 * Dispose of the LDAP session ld, including all associated connections
73 * and resources. If close is non-zero, an unbind() request is sent as well.
76 ldap_ld_free( LDAP
*ld
, LDAPControl
**serverctrls
,
77 LDAPControl
**clientctrls
, int close
)
79 LDAPMessage
*lm
, *next
;
80 int err
= LDAP_SUCCESS
;
81 LDAPRequest
*lr
, *nextlr
;
83 if ( !NSLDAPI_VALID_LDAP_POINTER( ld
)) {
84 return( LDAP_PARAM_ERROR
);
87 if ( ld
->ld_sbp
->sb_naddr
== 0 ) {
88 LDAP_MUTEX_LOCK( ld
, LDAP_REQ_LOCK
);
89 /* free LDAP structure and outstanding requests/responses */
90 for ( lr
= ld
->ld_requests
; lr
!= NULL
; lr
= nextlr
) {
92 nsldapi_free_request( ld
, lr
, 0 );
94 LDAP_MUTEX_UNLOCK( ld
, LDAP_REQ_LOCK
);
96 /* free and unbind from all open connections */
97 LDAP_MUTEX_LOCK( ld
, LDAP_CONN_LOCK
);
98 while ( ld
->ld_conns
!= NULL
) {
99 nsldapi_free_connection( ld
, ld
->ld_conns
, serverctrls
,
100 clientctrls
, 1, close
);
102 LDAP_MUTEX_UNLOCK( ld
, LDAP_CONN_LOCK
);
107 for ( i
= 0; i
< ld
->ld_sbp
->sb_naddr
; ++i
) {
108 NSLDAPI_FREE( ld
->ld_sbp
->sb_addrs
[ i
] );
110 NSLDAPI_FREE( ld
->ld_sbp
->sb_addrs
);
111 NSLDAPI_FREE( ld
->ld_sbp
->sb_fromaddr
);
114 LDAP_MUTEX_LOCK( ld
, LDAP_RESP_LOCK
);
115 for ( lm
= ld
->ld_responses
; lm
!= NULL
; lm
= next
) {
119 LDAP_MUTEX_UNLOCK( ld
, LDAP_RESP_LOCK
);
121 /* call cache unbind function to allow it to clean up after itself */
122 if ( ld
->ld_cache_unbind
!= NULL
) {
123 LDAP_MUTEX_LOCK( ld
, LDAP_CACHE_LOCK
);
124 (void)ld
->ld_cache_unbind( ld
, 0, 0 );
125 LDAP_MUTEX_UNLOCK( ld
, LDAP_CACHE_LOCK
);
128 /* call the dispose handle I/O callback if one is defined */
129 if ( ld
->ld_extdisposehandle_fn
!= NULL
) {
131 * We always pass the session extended I/O argument to
132 * the dispose handle callback.
134 ld
->ld_extdisposehandle_fn( ld
, ld
->ld_ext_session_arg
);
137 if ( ld
->ld_error
!= NULL
)
138 NSLDAPI_FREE( ld
->ld_error
);
139 if ( ld
->ld_matched
!= NULL
)
140 NSLDAPI_FREE( ld
->ld_matched
);
141 if ( ld
->ld_host
!= NULL
)
142 NSLDAPI_FREE( ld
->ld_host
);
143 if ( ld
->ld_ufnprefix
!= NULL
)
144 NSLDAPI_FREE( ld
->ld_ufnprefix
);
145 if ( ld
->ld_filtd
!= NULL
)
146 ldap_getfilter_free( ld
->ld_filtd
);
147 if ( ld
->ld_abandoned
!= NULL
)
148 NSLDAPI_FREE( ld
->ld_abandoned
);
149 if ( ld
->ld_sbp
!= NULL
)
150 ber_sockbuf_free( ld
->ld_sbp
);
151 if ( ld
->ld_defhost
!= NULL
)
152 NSLDAPI_FREE( ld
->ld_defhost
);
153 if ( ld
->ld_servercontrols
!= NULL
)
154 ldap_controls_free( ld
->ld_servercontrols
);
155 if ( ld
->ld_clientcontrols
!= NULL
)
156 ldap_controls_free( ld
->ld_clientcontrols
);
157 if ( ld
->ld_preferred_language
!= NULL
)
158 NSLDAPI_FREE( ld
->ld_preferred_language
);
159 nsldapi_iostatus_free( ld
);
160 #ifdef LDAP_SASLIO_HOOKS
161 if ( ld
->ld_def_sasl_mech
!= NULL
)
162 NSLDAPI_FREE( ld
->ld_def_sasl_mech
);
163 if ( ld
->ld_def_sasl_realm
!= NULL
)
164 NSLDAPI_FREE( ld
->ld_def_sasl_realm
);
165 if ( ld
->ld_def_sasl_authcid
!= NULL
)
166 NSLDAPI_FREE( ld
->ld_def_sasl_authcid
);
167 if ( ld
->ld_def_sasl_authzid
!= NULL
)
168 NSLDAPI_FREE( ld
->ld_def_sasl_authzid
);
172 * XXXmcs: should use cache function pointers to hook in memcache
174 if ( ld
->ld_memcache
!= NULL
) {
175 ldap_memcache_set( ld
, NULL
);
178 /* free all mutexes we have allocated */
179 nsldapi_mutex_free_all( ld
);
180 NSLDAPI_FREE( ld
->ld_mutex
);
182 NSLDAPI_FREE( (char *) ld
);
190 nsldapi_send_unbind( LDAP
*ld
, Sockbuf
*sb
, LDAPControl
**serverctrls
,
191 LDAPControl
**clientctrls
)
196 LDAPDebug( LDAP_DEBUG_TRACE
, "nsldapi_send_unbind\n", 0, 0, 0 );
198 /* create a message to send */
199 if (( err
= nsldapi_alloc_ber_with_options( ld
, &ber
))
205 LDAP_MUTEX_LOCK( ld
, LDAP_MSGID_LOCK
);
206 msgid
= ++ld
->ld_msgid
;
207 LDAP_MUTEX_UNLOCK( ld
, LDAP_MSGID_LOCK
);
209 if ( ber_printf( ber
, "{itn", msgid
, LDAP_REQ_UNBIND
) == -1 ) {
211 err
= LDAP_ENCODING_ERROR
;
212 LDAP_SET_LDERRNO( ld
, err
, NULL
, NULL
);
216 if (( err
= nsldapi_put_controls( ld
, serverctrls
, 1, ber
))
222 /* send the message */
223 if ( nsldapi_ber_flush( ld
, sb
, ber
, 1, 0 ) != 0 ) {
225 err
= LDAP_SERVER_DOWN
;
226 LDAP_SET_LDERRNO( ld
, err
, NULL
, NULL
);
230 return( LDAP_SUCCESS
);