1 /* ldap-int.h - defines & prototypes internal to the LDAP library */
2 /* $OpenLDAP: pkg/ldap/libraries/libldap/ldap-int.h,v 1.168.2.7 2008/02/11 23:26:41 kurt Exp $ */
3 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
5 * Copyright 1998-2008 The OpenLDAP Foundation.
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>.
16 /* Portions Copyright (c) 1995 Regents of the University of Michigan.
17 * All rights reserved.
24 #define LDAP_THREAD_SAFE 1
27 #include "../liblber/lber-int.h"
30 #include <ldap_pvt_thread.h>
33 #ifdef HAVE_CYRUS_SASL
34 /* the need for this should be removed */
35 #ifdef HAVE_SASL_SASL_H
36 #include <sasl/sasl.h>
41 #define SASL_MAX_BUFF_SIZE (0xffffff)
42 #define SASL_MIN_BUFF_SIZE 4096
45 /* for struct timeval */
49 #define TV2MILLISEC(tv) (((tv)->tv_sec * 1000) + ((tv)->tv_usec/1000))
52 * Support needed if the library is running in the kernel
54 #if LDAP_INT_IN_KERNEL
56 * Platform specific function to return a pointer to the
57 * process-specific global options.
59 * This function should perform the following functions:
60 * Allocate and initialize a global options struct on a per process basis
61 * Use callers process identifier to return its global options struct
62 * Note: Deallocate structure when the process exits
64 # define LDAP_INT_GLOBAL_OPT() ldap_int_global_opt()
65 struct ldapoptions
*ldap_int_global_opt(void);
67 # define LDAP_INT_GLOBAL_OPT() (&ldap_int_global_options)
70 #define ldap_debug ((LDAP_INT_GLOBAL_OPT())->ldo_debug)
78 #define Debug( level, fmt, arg1, arg2, arg3 ) \
79 do { if ( ldap_debug & level ) \
80 ldap_log_printf( NULL, (level), (fmt), (arg1), (arg2), (arg3) ); \
83 #define LDAP_Debug( subsystem, level, fmt, arg1, arg2, arg3 )\
84 ldap_log_printf( NULL, (level), (fmt), (arg1), (arg2), (arg3) )
88 #define Debug( level, fmt, arg1, arg2, arg3 ) ((void)0)
89 #define LDAP_Debug( subsystem, level, fmt, arg1, arg2, arg3 ) ((void)0)
91 #endif /* LDAP_DEBUG */
93 #define LDAP_DEPRECATED 1
100 #define LDAP_URL_PREFIX "ldap://"
101 #define LDAP_URL_PREFIX_LEN STRLENOF(LDAP_URL_PREFIX)
102 #define LDAPS_URL_PREFIX "ldaps://"
103 #define LDAPS_URL_PREFIX_LEN STRLENOF(LDAPS_URL_PREFIX)
104 #define LDAPI_URL_PREFIX "ldapi://"
105 #define LDAPI_URL_PREFIX_LEN STRLENOF(LDAPI_URL_PREFIX)
106 #ifdef LDAP_CONNECTIONLESS
107 #define LDAPC_URL_PREFIX "cldap://"
108 #define LDAPC_URL_PREFIX_LEN STRLENOF(LDAPC_URL_PREFIX)
110 #define LDAP_URL_URLCOLON "URL:"
111 #define LDAP_URL_URLCOLON_LEN STRLENOF(LDAP_URL_URLCOLON)
113 #define LDAP_REF_STR "Referral:\n"
114 #define LDAP_REF_STR_LEN STRLENOF(LDAP_REF_STR)
115 #define LDAP_LDAP_REF_STR LDAP_URL_PREFIX
116 #define LDAP_LDAP_REF_STR_LEN LDAP_URL_PREFIX_LEN
118 #define LDAP_DEFAULT_REFHOPLIMIT 5
120 #define LDAP_BOOL_REFERRALS 0
121 #define LDAP_BOOL_RESTART 1
122 #define LDAP_BOOL_TLS 3
123 #define LDAP_BOOL_CONNECT_ASYNC 4
125 #define LDAP_BOOLEANS unsigned long
126 #define LDAP_BOOL(n) ((LDAP_BOOLEANS)1 << (n))
127 #define LDAP_BOOL_GET(lo, bool) \
128 ((lo)->ldo_booleans & LDAP_BOOL(bool) ? -1 : 0)
129 #define LDAP_BOOL_SET(lo, bool) ((lo)->ldo_booleans |= LDAP_BOOL(bool))
130 #define LDAP_BOOL_CLR(lo, bool) ((lo)->ldo_booleans &= ~LDAP_BOOL(bool))
131 #define LDAP_BOOL_ZERO(lo) ((lo)->ldo_booleans = 0)
134 * This structure represents both ldap messages and ldap responses.
135 * These are really the same, except in the case of search responses,
136 * where a response has multiple messages.
140 ber_int_t lm_msgid
; /* the message id */
141 ber_tag_t lm_msgtype
; /* the message type */
142 BerElement
*lm_ber
; /* the ber encoded message contents */
143 struct ldapmsg
*lm_chain
; /* for search - next msg in the resp */
144 struct ldapmsg
*lm_chain_tail
;
145 struct ldapmsg
*lm_next
; /* next response */
146 time_t lm_time
; /* used to maintain cache */
156 char *lt_ciphersuite
;
164 * structure representing get/set'able options
165 * which have global defaults.
169 #define LDAP_UNINITIALIZED 0x0
170 #define LDAP_INITIALIZED 0x1
171 #define LDAP_VALID_SESSION 0x2
172 #define LDAP_TRASHED_SESSION 0xFF
174 #ifdef LDAP_CONNECTIONLESS
175 #define LDAP_IS_UDP(ld) ((ld)->ld_options.ldo_is_udp)
176 void* ldo_peer
; /* struct sockaddr* */
181 /* per API call timeout */
182 struct timeval ldo_tm_api
;
183 struct timeval ldo_tm_net
;
185 ber_int_t ldo_version
;
187 ber_int_t ldo_timelimit
;
188 ber_int_t ldo_sizelimit
;
193 LDAP_TLS_CONNECT_CB
*ldo_tls_connect_cb
;
194 void* ldo_tls_connect_arg
;
195 struct ldaptls ldo_tls_info
;
196 #define ldo_tls_certfile ldo_tls_info.lt_certfile
197 #define ldo_tls_keyfile ldo_tls_info.lt_keyfile
198 #define ldo_tls_dhfile ldo_tls_info.lt_dhfile
199 #define ldo_tls_cacertfile ldo_tls_info.lt_cacertfile
200 #define ldo_tls_cacertdir ldo_tls_info.lt_cacertdir
201 #define ldo_tls_ciphersuite ldo_tls_info.lt_ciphersuite
202 #define ldo_tls_crlfile ldo_tls_info.lt_crlfile
204 int ldo_tls_require_cert
;
205 #ifdef HAVE_OPENSSL_CRL
206 int ldo_tls_crlcheck
;
210 LDAPURLDesc
*ldo_defludp
;
213 char* ldo_defbinddn
; /* bind dn */
215 #ifdef HAVE_CYRUS_SASL
216 char* ldo_def_sasl_mech
; /* SASL Mechanism(s) */
217 char* ldo_def_sasl_realm
; /* SASL realm */
218 char* ldo_def_sasl_authcid
; /* SASL authentication identity */
219 char* ldo_def_sasl_authzid
; /* SASL authorization identity */
221 /* SASL Security Properties */
222 struct sasl_security_properties ldo_sasl_secprops
;
225 int ldo_refhoplimit
; /* limit on referral nesting */
227 /* LDAPv3 server and client controls */
228 LDAPControl
**ldo_sctrls
;
229 LDAPControl
**ldo_cctrls
;
231 /* LDAP rebind callback function */
232 LDAP_REBIND_PROC
*ldo_rebind_proc
;
233 void *ldo_rebind_params
;
234 LDAP_NEXTREF_PROC
*ldo_nextref_proc
;
235 void *ldo_nextref_params
;
236 LDAP_URLLIST_PROC
*ldo_urllist_proc
;
237 void *ldo_urllist_params
;
239 LDAP_BOOLEANS ldo_booleans
; /* boolean options */
244 * structure for representing an LDAP server connection
246 typedef struct ldap_conn
{
248 #ifdef HAVE_CYRUS_SASL
249 void *lconn_sasl_authctx
; /* context for bind */
250 void *lconn_sasl_sockctx
; /* for security layer */
253 time_t lconn_created
; /* time */
254 time_t lconn_lastused
; /* time */
255 int lconn_rebind_inprogress
; /* set if rebind in progress */
256 char ***lconn_rebind_queue
; /* used if rebind in progress */
258 #define LDAP_CONNST_NEEDSOCKET 1
259 #define LDAP_CONNST_CONNECTING 2
260 #define LDAP_CONNST_CONNECTED 3
261 LDAPURLDesc
*lconn_server
;
262 BerElement
*lconn_ber
; /* ber receiving on this conn. */
264 struct ldap_conn
*lconn_next
;
269 * structure used to track outstanding requests
271 typedef struct ldapreq
{
272 ber_int_t lr_msgid
; /* the message id */
273 int lr_status
; /* status of request */
274 #define LDAP_REQST_COMPLETED 0
275 #define LDAP_REQST_INPROGRESS 1
276 #define LDAP_REQST_CHASINGREFS 2
277 #define LDAP_REQST_NOTCONNECTED 3
278 #define LDAP_REQST_WRITING 4
279 int lr_refcnt
; /* count of references */
280 int lr_outrefcnt
; /* count of outstanding referrals */
281 int lr_abandoned
; /* the request has been abandoned */
282 ber_int_t lr_origid
; /* original request's message id */
283 int lr_parentcnt
; /* count of parent requests */
284 ber_tag_t lr_res_msgtype
; /* result message type */
285 ber_int_t lr_res_errno
; /* result LDAP errno */
286 char *lr_res_error
; /* result error string */
287 char *lr_res_matched
;/* result matched DN string */
288 BerElement
*lr_ber
; /* ber encoded request contents */
289 LDAPConn
*lr_conn
; /* connection used to send request */
290 struct berval lr_dn
; /* DN of request, in lr_ber */
291 struct ldapreq
*lr_parent
; /* request that spawned this referral */
292 struct ldapreq
*lr_child
; /* first child request */
293 struct ldapreq
*lr_refnext
; /* next referral spawned */
294 struct ldapreq
*lr_prev
; /* previous request */
295 struct ldapreq
*lr_next
; /* next request */
299 * structure for client cache
301 #define LDAP_CACHE_BUCKETS 31 /* cache hash table size */
302 typedef struct ldapcache
{
303 LDAPMessage
*lc_buckets
[LDAP_CACHE_BUCKETS
];/* hash table */
304 LDAPMessage
*lc_requests
; /* unfulfilled reqs */
305 long lc_timeout
; /* request timeout */
306 ber_len_t lc_maxmem
; /* memory to use */
307 ber_len_t lc_memused
; /* memory in use */
308 int lc_enabled
; /* enabled? */
309 unsigned long lc_options
; /* options */
310 #define LDAP_CACHE_OPT_CACHENOERRS 0x00000001
311 #define LDAP_CACHE_OPT_CACHEALLERRS 0x00000002
315 * structure containing referral request info for rebind procedure
317 typedef struct ldapreqinfo
{
324 * structure representing an ldap connection
328 Sockbuf
*ld_sb
; /* socket descriptor & buffer */
330 struct ldapoptions ld_options
;
332 #define ld_valid ld_options.ldo_valid
333 #define ld_debug ld_options.ldo_debug
335 #define ld_deref ld_options.ldo_deref
336 #define ld_timelimit ld_options.ldo_timelimit
337 #define ld_sizelimit ld_options.ldo_sizelimit
339 #define ld_defbinddn ld_options.ldo_defbinddn
340 #define ld_defbase ld_options.ldo_defbase
341 #define ld_defhost ld_options.ldo_defhost
342 #define ld_defport ld_options.ldo_defport
344 #define ld_refhoplimit ld_options.ldo_refhoplimit
346 #define ld_sctrls ld_options.ldo_sctrls
347 #define ld_cctrls ld_options.ldo_cctrls
348 #define ld_rebind_proc ld_options.ldo_rebind_proc
349 #define ld_rebind_params ld_options.ldo_rebind_params
350 #define ld_nextref_proc ld_options.ldo_nextref_proc
351 #define ld_nextref_params ld_options.ldo_nextref_params
352 #define ld_urllist_proc ld_options.ldo_urllist_proc
353 #define ld_urllist_params ld_options.ldo_urllist_params
355 #define ld_version ld_options.ldo_version
357 unsigned short ld_lberoptions
;
365 /* do not mess with these */
366 LDAPRequest
*ld_requests
; /* list of outstanding requests */
367 LDAPMessage
*ld_responses
; /* list of outstanding responses */
369 #ifdef LDAP_R_COMPILE
370 ldap_pvt_thread_mutex_t ld_conn_mutex
;
371 ldap_pvt_thread_mutex_t ld_req_mutex
;
372 ldap_pvt_thread_mutex_t ld_res_mutex
;
375 ber_len_t ld_nabandoned
;
376 ber_int_t
*ld_abandoned
; /* array of abandoned requests */
378 LDAPCache
*ld_cache
; /* non-null if cache is initialized */
380 /* do not mess with the rest though */
382 LDAPConn
*ld_defconn
; /* default connection */
383 LDAPConn
*ld_conns
; /* list of server connections */
384 void *ld_selectinfo
; /* platform specifics for select */
386 #define LDAP_VALID(ld) ( (ld)->ld_valid == LDAP_VALID_SESSION )
387 #define LDAP_TRASHED(ld) ( (ld)->ld_valid == LDAP_TRASHED_SESSION )
388 #define LDAP_TRASH(ld) ( (ld)->ld_valid = LDAP_TRASHED_SESSION )
390 #ifdef LDAP_R_COMPILE
391 LDAP_V ( ldap_pvt_thread_mutex_t
) ldap_int_resolv_mutex
;
393 #ifdef HAVE_CYRUS_SASL
394 LDAP_V( ldap_pvt_thread_mutex_t
) ldap_int_sasl_mutex
;
398 #ifdef LDAP_R_COMPILE
399 #define LDAP_NEXT_MSGID(ld, id) \
400 ldap_pvt_thread_mutex_lock( &(ld)->ld_req_mutex ); \
401 id = ++(ld)->ld_msgid; \
402 ldap_pvt_thread_mutex_unlock( &(ld)->ld_req_mutex )
404 #define LDAP_NEXT_MSGID(ld, id) id = ++(ld)->ld_msgid
412 ldap_int_bisect_find( ber_int_t
*v
, ber_len_t n
, ber_int_t id
, int *idxp
);
414 ldap_int_bisect_insert( ber_int_t
**vp
, ber_len_t
*np
, int id
, int idx
);
416 ldap_int_bisect_delete( ber_int_t
**vp
, ber_len_t
*np
, int id
, int idx
);
422 LDAP_V ( struct ldapoptions
) ldap_int_global_options
;
424 LDAP_F ( void ) ldap_int_initialize
LDAP_P((struct ldapoptions
*, int *));
425 LDAP_F ( void ) ldap_int_initialize_global_options
LDAP_P((
426 struct ldapoptions
*, int *));
429 /* simple macros to realloc for now */
430 #define LDAP_MALLOC(s) (ber_memalloc_x((s),NULL))
431 #define LDAP_CALLOC(n,s) (ber_memcalloc_x((n),(s),NULL))
432 #define LDAP_REALLOC(p,s) (ber_memrealloc_x((p),(s),NULL))
433 #define LDAP_FREE(p) (ber_memfree_x((p),NULL))
434 #define LDAP_VFREE(v) (ber_memvfree_x((void **)(v),NULL))
435 #define LDAP_STRDUP(s) (ber_strdup_x((s),NULL))
436 #define LDAP_STRNDUP(s,l) (ber_strndup_x((s),(l),NULL))
438 #define LDAP_MALLOCX(s,x) (ber_memalloc_x((s),(x)))
439 #define LDAP_CALLOCX(n,s,x) (ber_memcalloc_x((n),(s),(x)))
440 #define LDAP_REALLOCX(p,s,x) (ber_memrealloc_x((p),(s),(x)))
441 #define LDAP_FREEX(p,x) (ber_memfree_x((p),(x)))
442 #define LDAP_VFREEX(v,x) (ber_memvfree_x((void **)(v),(x)))
443 #define LDAP_STRDUPX(s,x) (ber_strdup_x((s),(x)))
444 #define LDAP_STRNDUPX(s,l,x) (ber_strndup_x((s),(l),(x)))
449 LDAP_F (void) ldap_int_error_init( void );
454 LDAP_F (void) ldap_int_utils_init
LDAP_P(( void ));
460 LDAP_F (int) ldap_log_printf
LDAP_P((LDAP
*ld
, int level
, const char *fmt
, ...)) LDAP_GCCATTR((format(printf
, 3, 4)));
465 LDAP_F (void) ldap_add_request_to_cache
LDAP_P(( LDAP
*ld
, ber_tag_t msgtype
,
466 BerElement
*request
));
467 LDAP_F (void) ldap_add_result_to_cache
LDAP_P(( LDAP
*ld
, LDAPMessage
*result
));
468 LDAP_F (int) ldap_check_cache
LDAP_P(( LDAP
*ld
, ber_tag_t msgtype
, BerElement
*request
));
473 LDAP_F (int) ldap_int_put_controls
LDAP_P((
475 LDAPControl
*const *ctrls
,
478 LDAP_F (int) ldap_int_client_controls
LDAP_P((
480 LDAPControl
**ctrlp
));
485 LDAP_F (int) ldap_int_next_line_tokens
LDAP_P(( char **bufp
, ber_len_t
*blenp
, char ***toksp
));
491 LDAP_F (int) ldap_open_defconn( LDAP
*ld
);
492 LDAP_F (int) ldap_int_open_connection( LDAP
*ld
,
493 LDAPConn
*conn
, LDAPURLDesc
*srvlist
, int async
);
499 LDAP_V (int) ldap_int_tblsize
;
500 LDAP_F (void) ldap_int_ip_init( void );
503 LDAP_F (int) ldap_int_timeval_dup( struct timeval
**dest
,
504 const struct timeval
*tm
);
505 LDAP_F (int) ldap_connect_to_host( LDAP
*ld
, Sockbuf
*sb
,
506 int proto
, const char *host
, int port
, int async
);
507 LDAP_F (int) ldap_int_poll( LDAP
*ld
, ber_socket_t s
,
508 struct timeval
*tvp
);
510 #if defined(HAVE_TLS) || defined(HAVE_CYRUS_SASL)
511 LDAP_V (char *) ldap_int_hostname
;
512 LDAP_F (char *) ldap_host_connected_to( Sockbuf
*sb
,
516 LDAP_F (int) ldap_int_select( LDAP
*ld
, struct timeval
*timeout
);
517 LDAP_F (void *) ldap_new_select_info( void );
518 LDAP_F (void) ldap_free_select_info( void *sip
);
519 LDAP_F (void) ldap_mark_select_write( LDAP
*ld
, Sockbuf
*sb
);
520 LDAP_F (void) ldap_mark_select_read( LDAP
*ld
, Sockbuf
*sb
);
521 LDAP_F (void) ldap_mark_select_clear( LDAP
*ld
, Sockbuf
*sb
);
522 LDAP_F (int) ldap_is_read_ready( LDAP
*ld
, Sockbuf
*sb
);
523 LDAP_F (int) ldap_is_write_ready( LDAP
*ld
, Sockbuf
*sb
);
529 LDAP_F (int) ldap_connect_to_path( LDAP
*ld
, Sockbuf
*sb
,
530 const char *path
, int async
);
531 #endif /* LDAP_PF_LOCAL */
536 LDAP_F (ber_int_t
) ldap_send_initial_request( LDAP
*ld
, ber_tag_t msgtype
,
537 const char *dn
, BerElement
*ber
, ber_int_t msgid
);
538 LDAP_F (BerElement
*) ldap_alloc_ber_with_options( LDAP
*ld
);
539 LDAP_F (void) ldap_set_ber_options( LDAP
*ld
, BerElement
*ber
);
541 LDAP_F (int) ldap_send_server_request( LDAP
*ld
, BerElement
*ber
, ber_int_t msgid
, LDAPRequest
*parentreq
, LDAPURLDesc
**srvlist
, LDAPConn
*lc
, LDAPreqinfo
*bind
);
542 LDAP_F (LDAPConn
*) ldap_new_connection( LDAP
*ld
, LDAPURLDesc
**srvlist
, int use_ldsb
, int connect
, LDAPreqinfo
*bind
);
543 LDAP_F (LDAPRequest
*) ldap_find_request_by_msgid( LDAP
*ld
, ber_int_t msgid
);
544 LDAP_F (void) ldap_return_request( LDAP
*ld
, LDAPRequest
*lr
, int freeit
);
545 LDAP_F (void) ldap_free_request( LDAP
*ld
, LDAPRequest
*lr
);
546 LDAP_F (void) ldap_free_connection( LDAP
*ld
, LDAPConn
*lc
, int force
, int unbind
);
547 LDAP_F (void) ldap_dump_connection( LDAP
*ld
, LDAPConn
*lconns
, int all
);
548 LDAP_F (void) ldap_dump_requests_and_responses( LDAP
*ld
);
549 LDAP_F (int) ldap_chase_referrals( LDAP
*ld
, LDAPRequest
*lr
,
550 char **errstrp
, int sref
, int *hadrefp
);
551 LDAP_F (int) ldap_chase_v3referrals( LDAP
*ld
, LDAPRequest
*lr
,
552 char **refs
, int sref
, char **referralsp
, int *hadrefp
);
553 LDAP_F (int) ldap_append_referral( LDAP
*ld
, char **referralsp
, char *s
);
554 LDAP_F (int) ldap_int_flush_request( LDAP
*ld
, LDAPRequest
*lr
);
559 LDAP_F (const char *) ldap_int_msgtype2str( ber_tag_t tag
);
564 LDAP_F (BerElement
*) ldap_build_search_req
LDAP_P((
571 LDAPControl
**sctrls
,
572 LDAPControl
**cctrls
,
581 LDAP_F (int) ldap_ld_free
LDAP_P((
584 LDAPControl
**sctrls
,
585 LDAPControl
**cctrls
));
587 LDAP_F (int) ldap_send_unbind
LDAP_P((
590 LDAPControl
**sctrls
,
591 LDAPControl
**cctrls
));
596 LDAP_F (LDAPURLDesc
*) ldap_url_dup
LDAP_P((
597 LDAPURLDesc
*ludp
));
599 LDAP_F (LDAPURLDesc
*) ldap_url_duplist
LDAP_P((
600 LDAPURLDesc
*ludlist
));
602 LDAP_F (int) ldap_url_parsehosts
LDAP_P((
603 LDAPURLDesc
**ludlist
,
607 LDAP_F (char *) ldap_url_list2hosts
LDAP_P((
608 LDAPURLDesc
*ludlist
));
614 LDAP_F (int) ldap_int_sasl_init
LDAP_P(( void ));
616 LDAP_F (int) ldap_int_sasl_open
LDAP_P((
617 LDAP
*ld
, LDAPConn
*conn
,
619 LDAP_F (int) ldap_int_sasl_close
LDAP_P(( LDAP
*ld
, LDAPConn
*conn
));
621 LDAP_F (int) ldap_int_sasl_external
LDAP_P((
622 LDAP
*ld
, LDAPConn
*conn
,
623 const char* authid
, ber_len_t ssf
));
625 LDAP_F (int) ldap_int_sasl_get_option
LDAP_P(( LDAP
*ld
,
626 int option
, void *arg
));
627 LDAP_F (int) ldap_int_sasl_set_option
LDAP_P(( LDAP
*ld
,
628 int option
, void *arg
));
629 LDAP_F (int) ldap_int_sasl_config
LDAP_P(( struct ldapoptions
*lo
,
630 int option
, const char *arg
));
632 LDAP_F (int) ldap_int_sasl_bind
LDAP_P((
636 LDAPControl
**, LDAPControl
**,
638 /* should be passed in client controls */
640 LDAP_SASL_INTERACT_PROC
*interact
,
644 LDAP_F (char *) ldap_int_parse_numericoid
LDAP_P((
652 LDAP_F (int) ldap_int_tls_config
LDAP_P(( LDAP
*ld
,
653 int option
, const char *arg
));
655 LDAP_F (int) ldap_int_tls_start
LDAP_P(( LDAP
*ld
,
656 LDAPConn
*conn
, LDAPURLDesc
*srv
));
658 LDAP_F (void) ldap_int_tls_destroy
LDAP_P(( struct ldapoptions
*lo
));
663 LDAP_F (char **) ldap_value_dup
LDAP_P((
664 char *const *vals
));
668 #endif /* _LDAP_INT_H */