1 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
3 * Copyright 1998-2006 The OpenLDAP Foundation.
4 * Copyright 2006 Hans Leidekker
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted only as authorized by the OpenLDAP
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>.
15 /* Portions Copyright (C) The Internet Society (1999)
16 * ASN.1 fragments are from RFC 2696; see RFC for full legal notices.
22 #include <ac/stdlib.h>
23 #include <ac/string.h>
28 /* ---------------------------------------------------------------------------
29 ldap_create_page_control_value
31 Create and encode the value of the paged results control (RFC 2696).
33 ld (IN) An LDAP session handle
34 pagesize (IN) Page size requested
35 cookie (IN) Opaque structure used by the server to track its
36 location in the search results. NULL on the
38 value (OUT) Control value, SHOULD be freed by calling
39 ldap_memfree() when done.
41 pagedResultsControl ::= SEQUENCE {
42 controlType 1.2.840.113556.1.4.319,
43 criticality BOOLEAN DEFAULT FALSE,
44 controlValue searchControlValue }
46 searchControlValue ::= SEQUENCE {
47 size INTEGER (0..maxInt),
48 -- requested page size from client
49 -- result set size estimate from server
52 ---------------------------------------------------------------------------*/
55 ldap_create_page_control_value(
58 struct berval *cookie,
59 struct berval *value )
61 BerElement *ber = NULL;
63 struct berval null_cookie = { 0, NULL };
65 if ( ld == NULL || value == NULL ||
66 pagesize < 1 || pagesize > LDAP_MAXINT )
69 ld->ld_errno = LDAP_PARAM_ERROR;
70 return LDAP_PARAM_ERROR;
73 assert( LDAP_VALID( ld ) );
78 if ( cookie == NULL ) {
79 cookie = &null_cookie;
82 ber = ldap_alloc_ber_with_options( ld );
84 ld->ld_errno = LDAP_NO_MEMORY;
88 tag = ber_printf( ber, "{iO}", pagesize, cookie );
89 if ( tag == LBER_ERROR ) {
90 ld->ld_errno = LDAP_ENCODING_ERROR;
94 if ( ber_flatten2( ber, value, 1 ) == -1 ) {
95 ld->ld_errno = LDAP_NO_MEMORY;
107 /* ---------------------------------------------------------------------------
108 ldap_create_page_control
110 Create and encode a page control.
112 ld (IN) An LDAP session handle
113 pagesize (IN) Page size requested
114 cookie (IN) Opaque structure used by the server to track its
115 location in the search results. NULL on the
117 value (OUT) Control value, SHOULD be freed by calling
118 ldap_memfree() when done.
119 iscritical (IN) Criticality
120 ctrlp (OUT) LDAP control, SHOULD be freed by calling
121 ldap_control_free() when done.
123 pagedResultsControl ::= SEQUENCE {
124 controlType 1.2.840.113556.1.4.319,
125 criticality BOOLEAN DEFAULT FALSE,
126 controlValue searchControlValue }
128 searchControlValue ::= SEQUENCE {
129 size INTEGER (0..maxInt),
130 -- requested page size from client
131 -- result set size estimate from server
132 cookie OCTET STRING }
134 ---------------------------------------------------------------------------*/
137 ldap_create_page_control(
140 struct berval *cookie,
142 LDAPControl **ctrlp )
147 if ( ctrlp == NULL ) {
148 ld->ld_errno = LDAP_PARAM_ERROR;
152 ld->ld_errno = ldap_create_page_control_value( ld,
153 pagesize, cookie, &value );
154 if ( ld->ld_errno == LDAP_SUCCESS ) {
155 if ((ber = ldap_alloc_ber_with_options(ld)) == NULL) {
156 ld->ld_errno = LDAP_NO_MEMORY;
157 return LDAP_NO_MEMORY;
160 ld->ld_errno = ldap_create_control( LDAP_CONTROL_PAGEDRESULTS,
161 ber, iscritical, ctrlp );
162 if ( ld->ld_errno == LDAP_SUCCESS ) {
163 (*ctrlp)->ldctl_value = value;
165 LDAP_FREE( value.bv_val );
174 /* ---------------------------------------------------------------------------
175 ldap_parse_pageresponse_control
177 Decode a page control.
179 ld (IN) An LDAP session handle
180 ctrl (IN) The page response control
181 count (OUT) The number of entries in the page.
182 cookie (OUT) Opaque cookie. Use ldap_memfree() to
183 free the bv_val member of this structure.
185 ---------------------------------------------------------------------------*/
188 ldap_parse_pageresponse_control(
192 struct berval *cookie )
198 if ( ld == NULL || ctrl == NULL || cookie == NULL ) {
200 ld->ld_errno = LDAP_PARAM_ERROR;
201 return LDAP_PARAM_ERROR;
204 /* Create a BerElement from the berval returned in the control. */
205 ber = ber_init( &ctrl->ldctl_value );
208 ld->ld_errno = LDAP_NO_MEMORY;
212 /* Extract the count and cookie from the control. */
213 tag = ber_scanf( ber, "{io}", &count, cookie );
216 if ( tag == LBER_ERROR ) {
217 ld->ld_errno = LDAP_DECODING_ERROR;
219 ld->ld_errno = LDAP_SUCCESS;
221 if ( countp != NULL ) {
222 *countp = (unsigned long)count;
229 /* ---------------------------------------------------------------------------
230 ldap_parse_page_control
232 Decode a page control.
234 ld (IN) An LDAP session handle
235 ctrls (IN) Response controls
236 count (OUT) The number of entries in the page.
237 cookie (OUT) Opaque cookie. Use ldap_memfree() to
238 free the bv_val member of this structure.
240 ---------------------------------------------------------------------------*/
243 ldap_parse_page_control(
247 struct berval **cookiep )
250 struct berval cookie;
252 if ( cookiep == NULL ) {
253 ld->ld_errno = LDAP_PARAM_ERROR;
257 if ( ctrls == NULL ) {
258 ld->ld_errno = LDAP_CONTROL_NOT_FOUND;
262 c = ldap_find_control( LDAP_CONTROL_PAGEDRESULTS, ctrls );
264 /* No page control was found. */
265 ld->ld_errno = LDAP_CONTROL_NOT_FOUND;
269 ld->ld_errno = ldap_parse_pageresponse_control( ld, c, countp, &cookie );
270 if ( ld->ld_errno == LDAP_SUCCESS ) {
271 *cookiep = LDAP_MALLOC( sizeof( struct berval * ) );
272 if ( *cookiep == NULL ) {
273 ld->ld_errno = LDAP_NO_MEMORY;