2 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
4 * Copyright 1998-2008 The OpenLDAP Foundation.
5 * Portions Copyright 2007 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 developed by Pierangelo Masarati for inclusion in
24 #include <ac/stdlib.h>
25 #include <ac/string.h>
30 #ifdef LDAP_CONTROL_X_SESSION_TRACKING
33 * Client-side of <draft-wahl-ldap-session-03>
37 ldap_create_session_tracking_value(
39 char *sessionSourceIp,
40 char *sessionSourceName,
42 struct berval *sessionTrackingIdentifier,
43 struct berval *value )
45 BerElement *ber = NULL;
48 struct berval ip, name, oid, id;
56 ld->ld_errno = LDAP_PARAM_ERROR;
59 return LDAP_PARAM_ERROR;
62 assert( LDAP_VALID( ld ) );
64 /* check sizes according to I.D. */
65 if ( sessionSourceIp == NULL ) {
69 ber_str2bv( sessionSourceIp, 0, 0, &ip );
70 /* NOTE: we're strict because we don't want
71 * to send out bad data */
72 if ( ip.bv_len > 128 ) goto param_error;
75 if ( sessionSourceName == NULL ) {
76 BER_BVSTR( &name, "" );
79 ber_str2bv( sessionSourceName, 0, 0, &name );
80 /* NOTE: we're strict because we don't want
81 * to send out bad data */
82 if ( name.bv_len > 65536 ) goto param_error;
85 ber_str2bv( formatOID, 0, 0, &oid );
86 /* NOTE: we're strict because we don't want
87 * to send out bad data */
88 if ( oid.bv_len > 1024 ) goto param_error;
90 if ( sessionTrackingIdentifier == NULL ||
91 sessionTrackingIdentifier->bv_val == NULL )
96 id = *sessionTrackingIdentifier;
100 value->bv_val = NULL;
103 ber = ldap_alloc_ber_with_options( ld );
105 ld->ld_errno = LDAP_NO_MEMORY;
109 tag = ber_printf( ber, "{OOOO}", &ip, &name, &oid, &id );
110 if ( tag == LBER_ERROR ) {
111 ld->ld_errno = LDAP_ENCODING_ERROR;
115 if ( ber_flatten2( ber, value, 1 ) == -1 ) {
116 ld->ld_errno = LDAP_NO_MEMORY;
128 * NOTE: this API is bad; it could be much more efficient...
131 ldap_create_session_tracking_control(
133 char *sessionSourceIp,
134 char *sessionSourceName,
136 struct berval *sessionTrackingIdentifier,
137 LDAPControl **ctrlp )
141 if ( ctrlp == NULL ) {
142 ld->ld_errno = LDAP_PARAM_ERROR;
146 ld->ld_errno = ldap_create_session_tracking_value( ld,
147 sessionSourceIp, sessionSourceName, formatOID,
148 sessionTrackingIdentifier, &value );
149 if ( ld->ld_errno == LDAP_SUCCESS ) {
150 ld->ld_errno = ldap_control_create( LDAP_CONTROL_X_SESSION_TRACKING,
151 0, &value, 0, ctrlp );
152 if ( ld->ld_errno != LDAP_SUCCESS ) {
153 LDAP_FREE( value.bv_val );
161 ldap_parse_session_tracking_control(
181 ld->ld_errno = LDAP_PARAM_ERROR;
184 /* NOTE: we want the caller to get all or nothing;
185 * we could allow some of the pointers to be NULL,
186 * if one does not want part of the data */
187 return LDAP_PARAM_ERROR;
195 ber = ber_init( &ctrl->ldctl_value );
198 ld->ld_errno = LDAP_NO_MEMORY;
202 tag = ber_skip_tag( ber, &len );
203 if ( tag != LBER_SEQUENCE ) {
208 /* sessionSourceIp */
209 tag = ber_peek_tag( ber, &len );
210 if ( tag == LBER_DEFAULT ) {
216 tag = ber_skip_tag( ber, &len );
220 /* should be LDAP_DECODING_ERROR,
221 * but we're liberal in what we accept */
223 tag = ber_scanf( ber, "o", ip );
226 /* sessionSourceName */
227 tag = ber_peek_tag( ber, &len );
228 if ( tag == LBER_DEFAULT ) {
234 tag = ber_skip_tag( ber, &len );
238 /* should be LDAP_DECODING_ERROR,
239 * but we're liberal in what we accept */
241 tag = ber_scanf( ber, "o", name );
245 tag = ber_peek_tag( ber, &len );
246 if ( tag == LBER_DEFAULT ) {
252 ld->ld_errno = LDAP_DECODING_ERROR;
257 /* should be LDAP_DECODING_ERROR,
258 * but we're liberal in what we accept */
260 tag = ber_scanf( ber, "o", oid );
263 /* FIXME: should check if it is an OID... leave it to the caller */
265 /* sessionTrackingIdentifier */
266 tag = ber_peek_tag( ber, &len );
267 if ( tag == LBER_DEFAULT ) {
273 tag = ber_skip_tag( ber, &len );
278 /* should be LDAP_DECODING_ERROR,
279 * but we're liberal in what we accept */
282 tag = ber_scanf( ber, "o", id );
286 tag = ber_skip_tag( ber, &len );
287 if ( tag == LBER_DEFAULT && len == 0 ) {
292 (void)ber_free( ber, 1 );
294 if ( tag == LBER_ERROR ) {
295 return LDAP_DECODING_ERROR;
301 #endif /* LDAP_CONTROL_X_SESSION_TRACKING */