Patrick Welche <prlw1@cam.ac.uk>
[netbsd-mini2440.git] / external / bsd / openldap / dist / libraries / libldap / pagectrl.c
blob8aac0c892a4ee644b9a7b1896574e5fa1d9a68ee
1 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
3 * Copyright 1998-2008 The OpenLDAP Foundation.
4 * Copyright 2006 Hans Leidekker
5 * All rights reserved.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted only as authorized by the OpenLDAP
9 * Public License.
11 * A copy of this license is available in the file LICENSE in the
12 * top-level directory of the distribution or, alternatively, at
13 * <http://www.OpenLDAP.org/license.html>.
16 #include "portable.h"
18 #include <stdio.h>
19 #include <ac/stdlib.h>
20 #include <ac/string.h>
21 #include <ac/time.h>
23 #include "ldap-int.h"
25 /* ---------------------------------------------------------------------------
26 ldap_create_page_control_value
28 Create and encode the value of the paged results control (RFC 2696).
30 ld (IN) An LDAP session handle
31 pagesize (IN) Page size requested
32 cookie (IN) Opaque structure used by the server to track its
33 location in the search results. NULL on the
34 first call.
35 value (OUT) Control value, SHOULD be freed by calling
36 ldap_memfree() when done.
38 pagedResultsControl ::= SEQUENCE {
39 controlType 1.2.840.113556.1.4.319,
40 criticality BOOLEAN DEFAULT FALSE,
41 controlValue searchControlValue }
43 searchControlValue ::= SEQUENCE {
44 size INTEGER (0..maxInt),
45 -- requested page size from client
46 -- result set size estimate from server
47 cookie OCTET STRING }
49 ---------------------------------------------------------------------------*/
51 int
52 ldap_create_page_control_value(
53 LDAP *ld,
54 ber_int_t pagesize,
55 struct berval *cookie,
56 struct berval *value )
58 BerElement *ber = NULL;
59 ber_tag_t tag;
60 struct berval null_cookie = { 0, NULL };
62 if ( ld == NULL || value == NULL ||
63 pagesize < 1 || pagesize > LDAP_MAXINT )
65 if ( ld )
66 ld->ld_errno = LDAP_PARAM_ERROR;
67 return LDAP_PARAM_ERROR;
70 assert( LDAP_VALID( ld ) );
72 value->bv_val = NULL;
73 value->bv_len = 0;
75 if ( cookie == NULL ) {
76 cookie = &null_cookie;
79 ber = ldap_alloc_ber_with_options( ld );
80 if ( ber == NULL ) {
81 ld->ld_errno = LDAP_NO_MEMORY;
82 return ld->ld_errno;
85 tag = ber_printf( ber, "{iO}", pagesize, cookie );
86 if ( tag == LBER_ERROR ) {
87 ld->ld_errno = LDAP_ENCODING_ERROR;
88 goto done;
91 if ( ber_flatten2( ber, value, 1 ) == -1 ) {
92 ld->ld_errno = LDAP_NO_MEMORY;
95 done:;
96 if ( ber != NULL ) {
97 ber_free( ber, 1 );
100 return ld->ld_errno;
104 /* ---------------------------------------------------------------------------
105 ldap_create_page_control
107 Create and encode a page control.
109 ld (IN) An LDAP session handle
110 pagesize (IN) Page size requested
111 cookie (IN) Opaque structure used by the server to track its
112 location in the search results. NULL on the
113 first call.
114 value (OUT) Control value, SHOULD be freed by calling
115 ldap_memfree() when done.
116 iscritical (IN) Criticality
117 ctrlp (OUT) LDAP control, SHOULD be freed by calling
118 ldap_control_free() when done.
120 pagedResultsControl ::= SEQUENCE {
121 controlType 1.2.840.113556.1.4.319,
122 criticality BOOLEAN DEFAULT FALSE,
123 controlValue searchControlValue }
125 searchControlValue ::= SEQUENCE {
126 size INTEGER (0..maxInt),
127 -- requested page size from client
128 -- result set size estimate from server
129 cookie OCTET STRING }
131 ---------------------------------------------------------------------------*/
134 ldap_create_page_control(
135 LDAP *ld,
136 ber_int_t pagesize,
137 struct berval *cookie,
138 int iscritical,
139 LDAPControl **ctrlp )
141 struct berval value;
143 if ( ctrlp == NULL ) {
144 ld->ld_errno = LDAP_PARAM_ERROR;
145 return ld->ld_errno;
148 ld->ld_errno = ldap_create_page_control_value( ld,
149 pagesize, cookie, &value );
150 if ( ld->ld_errno == LDAP_SUCCESS ) {
151 ld->ld_errno = ldap_control_create( LDAP_CONTROL_PAGEDRESULTS,
152 iscritical, &value, 0, ctrlp );
153 if ( ld->ld_errno != LDAP_SUCCESS ) {
154 LDAP_FREE( value.bv_val );
158 return ld->ld_errno;
162 /* ---------------------------------------------------------------------------
163 ldap_parse_pageresponse_control
165 Decode a page control.
167 ld (IN) An LDAP session handle
168 ctrl (IN) The page response control
169 count (OUT) The number of entries in the page.
170 cookie (OUT) Opaque cookie. Use ldap_memfree() to
171 free the bv_val member of this structure.
173 ---------------------------------------------------------------------------*/
176 ldap_parse_pageresponse_control(
177 LDAP *ld,
178 LDAPControl *ctrl,
179 ber_int_t *countp,
180 struct berval *cookie )
182 BerElement *ber;
183 ber_tag_t tag;
184 ber_int_t count;
186 if ( ld == NULL || ctrl == NULL || cookie == NULL ) {
187 if ( ld )
188 ld->ld_errno = LDAP_PARAM_ERROR;
189 return LDAP_PARAM_ERROR;
192 /* Create a BerElement from the berval returned in the control. */
193 ber = ber_init( &ctrl->ldctl_value );
195 if ( ber == NULL ) {
196 ld->ld_errno = LDAP_NO_MEMORY;
197 return ld->ld_errno;
200 /* Extract the count and cookie from the control. */
201 tag = ber_scanf( ber, "{io}", &count, cookie );
202 ber_free( ber, 1 );
204 if ( tag == LBER_ERROR ) {
205 ld->ld_errno = LDAP_DECODING_ERROR;
206 } else {
207 ld->ld_errno = LDAP_SUCCESS;
209 if ( countp != NULL ) {
210 *countp = (unsigned long)count;
214 return ld->ld_errno;
217 /* ---------------------------------------------------------------------------
218 ldap_parse_page_control
220 Decode a page control.
222 ld (IN) An LDAP session handle
223 ctrls (IN) Response controls
224 count (OUT) The number of entries in the page.
225 cookie (OUT) Opaque cookie. Use ldap_memfree() to
226 free the bv_val member of this structure.
228 ---------------------------------------------------------------------------*/
231 ldap_parse_page_control(
232 LDAP *ld,
233 LDAPControl **ctrls,
234 ber_int_t *countp,
235 struct berval **cookiep )
237 LDAPControl *c;
238 struct berval cookie;
240 if ( cookiep == NULL ) {
241 ld->ld_errno = LDAP_PARAM_ERROR;
242 return ld->ld_errno;
245 if ( ctrls == NULL ) {
246 ld->ld_errno = LDAP_CONTROL_NOT_FOUND;
247 return ld->ld_errno;
250 c = ldap_control_find( LDAP_CONTROL_PAGEDRESULTS, ctrls, NULL );
251 if ( c == NULL ) {
252 /* No page control was found. */
253 ld->ld_errno = LDAP_CONTROL_NOT_FOUND;
254 return ld->ld_errno;
257 ld->ld_errno = ldap_parse_pageresponse_control( ld, c, countp, &cookie );
258 if ( ld->ld_errno == LDAP_SUCCESS ) {
259 *cookiep = LDAP_MALLOC( sizeof( struct berval ) );
260 if ( *cookiep == NULL ) {
261 ld->ld_errno = LDAP_NO_MEMORY;
262 } else {
263 **cookiep = cookie;
267 return ld->ld_errno;