1 /* $NetBSD: getvalues.c,v 1.3 2021/08/14 16:14:56 christos Exp $ */
2
3 /* $OpenLDAP$ */
4 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
5 *
6 * Copyright 1998-2021 The OpenLDAP Foundation.
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted only as authorized by the OpenLDAP
11 * Public License.
12 *
13 * A copy of this license is available in the file LICENSE in the
14 * top-level directory of the distribution or, alternatively, at
15 * <http://www.OpenLDAP.org/license.html>.
16 */
17 /* Portions Copyright (c) 1990 Regents of the University of Michigan.
18 * All rights reserved.
19 */
20
21 #include <sys/cdefs.h>
22 __RCSID("$NetBSD: getvalues.c,v 1.3 2021/08/14 16:14:56 christos Exp $");
23
24 #include "portable.h"
25
26 #include <stdio.h>
27
28 #include <ac/stdlib.h>
29
30 #include <ac/ctype.h>
31 #include <ac/socket.h>
32 #include <ac/string.h>
33 #include <ac/time.h>
34
35 #include "ldap-int.h"
36
37 char **
ldap_get_values(LDAP * ld,LDAPMessage * entry,LDAP_CONST char * target)38 ldap_get_values( LDAP *ld, LDAPMessage *entry, LDAP_CONST char *target )
39 {
40 BerElement ber;
41 char *attr;
42 int found = 0;
43 char **vals;
44
45 assert( ld != NULL );
46 assert( LDAP_VALID( ld ) );
47 assert( entry != NULL );
48 assert( target != NULL );
49
50 Debug0( LDAP_DEBUG_TRACE, "ldap_get_values\n" );
51
52 ber = *entry->lm_ber;
53
54 /* skip sequence, dn, sequence of, and snag the first attr */
55 if ( ber_scanf( &ber, "{x{{a" /*}}}*/, &attr ) == LBER_ERROR ) {
56 ld->ld_errno = LDAP_DECODING_ERROR;
57 return( NULL );
58 }
59
60 if ( strcasecmp( target, attr ) == 0 )
61 found = 1;
62
63 /* break out on success, return out on error */
64 while ( ! found ) {
65 LDAP_FREE(attr);
66 attr = NULL;
67
68 if ( ber_scanf( &ber, /*{*/ "x}{a" /*}*/, &attr ) == LBER_ERROR ) {
69 ld->ld_errno = LDAP_DECODING_ERROR;
70 return( NULL );
71 }
72
73 if ( strcasecmp( target, attr ) == 0 )
74 break;
75
76 }
77
78 LDAP_FREE(attr);
79 attr = NULL;
80
81 /*
82 * if we get this far, we've found the attribute and are sitting
83 * just before the set of values.
84 */
85
86 if ( ber_scanf( &ber, "[v]", &vals ) == LBER_ERROR ) {
87 ld->ld_errno = LDAP_DECODING_ERROR;
88 return( NULL );
89 }
90
91 return( vals );
92 }
93
94 struct berval **
ldap_get_values_len(LDAP * ld,LDAPMessage * entry,LDAP_CONST char * target)95 ldap_get_values_len( LDAP *ld, LDAPMessage *entry, LDAP_CONST char *target )
96 {
97 BerElement ber;
98 char *attr;
99 int found = 0;
100 struct berval **vals;
101
102 assert( ld != NULL );
103 assert( LDAP_VALID( ld ) );
104 assert( entry != NULL );
105 assert( target != NULL );
106
107 Debug0( LDAP_DEBUG_TRACE, "ldap_get_values_len\n" );
108
109 ber = *entry->lm_ber;
110
111 /* skip sequence, dn, sequence of, and snag the first attr */
112 if ( ber_scanf( &ber, "{x{{a" /* }}} */, &attr ) == LBER_ERROR ) {
113 ld->ld_errno = LDAP_DECODING_ERROR;
114 return( NULL );
115 }
116
117 if ( strcasecmp( target, attr ) == 0 )
118 found = 1;
119
120 /* break out on success, return out on error */
121 while ( ! found ) {
122 LDAP_FREE( attr );
123 attr = NULL;
124
125 if ( ber_scanf( &ber, /*{*/ "x}{a" /*}*/, &attr ) == LBER_ERROR ) {
126 ld->ld_errno = LDAP_DECODING_ERROR;
127 return( NULL );
128 }
129
130 if ( strcasecmp( target, attr ) == 0 )
131 break;
132 }
133
134 LDAP_FREE( attr );
135 attr = NULL;
136
137 /*
138 * if we get this far, we've found the attribute and are sitting
139 * just before the set of values.
140 */
141
142 if ( ber_scanf( &ber, "[V]", &vals ) == LBER_ERROR ) {
143 ld->ld_errno = LDAP_DECODING_ERROR;
144 return( NULL );
145 }
146
147 return( vals );
148 }
149
150 int
ldap_count_values(char ** vals)151 ldap_count_values( char **vals )
152 {
153 int i;
154
155 if ( vals == NULL )
156 return( 0 );
157
158 for ( i = 0; vals[i] != NULL; i++ )
159 ; /* NULL */
160
161 return( i );
162 }
163
164 int
ldap_count_values_len(struct berval ** vals)165 ldap_count_values_len( struct berval **vals )
166 {
167 return( ldap_count_values( (char **) vals ) );
168 }
169
170 void
ldap_value_free(char ** vals)171 ldap_value_free( char **vals )
172 {
173 LDAP_VFREE( vals );
174 }
175
176 void
ldap_value_free_len(struct berval ** vals)177 ldap_value_free_len( struct berval **vals )
178 {
179 ber_bvecfree( vals );
180 }
181
182 char **
ldap_value_dup(char * const * vals)183 ldap_value_dup( char *const *vals )
184 {
185 char **new;
186 int i;
187
188 if( vals == NULL ) {
189 return NULL;
190 }
191
192 for( i=0; vals[i]; i++ ) {
193 ; /* Count the number of values */
194 }
195
196 if( i == 0 ) {
197 return NULL;
198 }
199
200 new = LDAP_MALLOC( (i+1)*sizeof(char *) ); /* Alloc array of pointers */
201 if( new == NULL ) {
202 return NULL;
203 }
204
205 for( i=0; vals[i]; i++ ) {
206 new[i] = LDAP_STRDUP( vals[i] ); /* Dup each value */
207 if( new[i] == NULL ) {
208 LDAP_VFREE( new );
209 return NULL;
210 }
211 }
212 new[i] = NULL;
213
214 return new;
215 }
216
217