[PATCH 3/5] wldap32: Move support for search functions to the Unix library.

Hans Leidekker hans at codeweavers.com
Thu Apr 15 05:20:05 CDT 2021


Signed-off-by: Hans Leidekker <hans at codeweavers.com>
---
 dlls/wldap32/dn.c      |   2 +-
 dlls/wldap32/error.c   |   2 +-
 dlls/wldap32/libldap.c |  98 ++++++++-
 dlls/wldap32/libldap.h |  36 ++++
 dlls/wldap32/misc.c    | 250 +++++++++++-----------
 dlls/wldap32/parse.c   |  10 +-
 dlls/wldap32/search.c  | 458 +++++++++++------------------------------
 dlls/wldap32/value.c   |   4 +-
 8 files changed, 379 insertions(+), 481 deletions(-)

diff --git a/dlls/wldap32/dn.c b/dlls/wldap32/dn.c
index 6d1a9711016..b35a5dfe1ac 100644
--- a/dlls/wldap32/dn.c
+++ b/dlls/wldap32/dn.c
@@ -214,7 +214,7 @@ PWCHAR CDECL ldap_get_dnW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry )
 
     if (!ld || !entry) return NULL;
 
-    retU = ldap_get_dn( ld->ld, entry );
+    retU = ldap_get_dn( ld->ld, entry->Request );
 
     ret = strUtoW( retU );
     ldap_memfree( retU );
diff --git a/dlls/wldap32/error.c b/dlls/wldap32/error.c
index c1b678788f0..a56adc11c02 100644
--- a/dlls/wldap32/error.c
+++ b/dlls/wldap32/error.c
@@ -152,7 +152,7 @@ ULONG CDECL WLDAP32_ldap_result2error( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *re
 
     if (!ld || !res) return ~0u;
 
-    ret = map_error( ldap_funcs->ldap_parse_result( ld->ld, res, &error, NULL, NULL, NULL, NULL, free ) );
+    ret = map_error( ldap_funcs->ldap_parse_result( ld->ld, res->Request, &error, NULL, NULL, NULL, NULL, free ) );
     if (ret == WLDAP32_LDAP_SUCCESS)
         ret = error;
     else
diff --git a/dlls/wldap32/libldap.c b/dlls/wldap32/libldap.c
index 11a3707f200..bc1a161127a 100644
--- a/dlls/wldap32/libldap.c
+++ b/dlls/wldap32/libldap.c
@@ -26,6 +26,7 @@
 
 #ifdef HAVE_LDAP
 #include <stdarg.h>
+#include <sys/time.h>
 #ifdef HAVE_LDAP_H
 # include <ldap.h>
 #endif
@@ -49,6 +50,7 @@ C_ASSERT( sizeof(LDAPModU) == sizeof(LDAPMod) );
 C_ASSERT( sizeof(LDAPControlU) == sizeof(LDAPControl) );
 C_ASSERT( sizeof(LDAPSortKeyU) == sizeof(LDAPSortKey) );
 C_ASSERT( sizeof(LDAPVLVInfoU) == sizeof(LDAPVLVInfo) );
+C_ASSERT( sizeof(struct timevalU) == sizeof(struct timeval) );
 
 static LDAPMod *nullattrs[] = { NULL };
 
@@ -294,6 +296,11 @@ int WINAPIV wrap_ber_scanf( void *ber, char *fmt, ... )
     return ret;
 }
 
+int CDECL wrap_ldap_abandon_ext( void *ld, int msgid, LDAPControlU **serverctrls, LDAPControlU **clientctrls )
+{
+    return ldap_abandon_ext( ld, msgid, (LDAPControl **)serverctrls, (LDAPControl **)clientctrls );
+}
+
 int CDECL wrap_ldap_add_ext( void *ld, const char *dn, LDAPModU **attrs, LDAPControlU **serverctrls,
                              LDAPControlU **clientctrls, ULONG *msg )
 {
@@ -309,11 +316,6 @@ int CDECL wrap_ldap_add_ext_s( void *ld, const char *dn, LDAPModU **attrs, LDAPC
                            (LDAPControl **)clientctrls );
 }
 
-void CDECL wrap_ldap_control_free( LDAPControlU *control )
-{
-    ldap_control_free( (LDAPControl *)control );
-}
-
 int CDECL wrap_ldap_compare_ext( void *ld, const char *dn, const char *attrs, struct bervalU *value,
                                  LDAPControlU **serverctrls, LDAPControlU **clientctrls, ULONG *msg )
 {
@@ -329,6 +331,21 @@ int CDECL wrap_ldap_compare_ext_s( void *ld, const char *dn, const char *attrs,
                                (LDAPControl **)serverctrls, (LDAPControl **)clientctrls );
 }
 
+void CDECL wrap_ldap_control_free( LDAPControlU *control )
+{
+    ldap_control_free( (LDAPControl *)control );
+}
+
+int CDECL wrap_ldap_count_entries( void *ld, void *chain )
+{
+    return ldap_count_entries( ld, chain );
+}
+
+int CDECL wrap_ldap_count_references( void *ld, void *chain )
+{
+    return ldap_count_references( ld, chain );
+}
+
 int CDECL wrap_ldap_create_sort_control( void *ld, LDAPSortKeyU **keylist, int critical, LDAPControlU **control )
 {
     return ldap_create_sort_control( ld, (LDAPSortKey **)keylist, critical, (LDAPControl **)control );
@@ -352,17 +369,57 @@ int CDECL wrap_ldap_delete_ext_s( void *ld, const char *dn, LDAPControlU **serve
     return ldap_delete_ext_s( ld, dn ? dn : "", (LDAPControl **)serverctrls, (LDAPControl **)clientctrls );
 }
 
+char * CDECL wrap_ldap_first_attribute( void *ld, void *entry, void **ber )
+{
+    return ldap_first_attribute( ld, entry, (BerElement **)ber );
+}
+
+void * CDECL wrap_ldap_first_entry( void *ld, void *chain )
+{
+    return ldap_first_entry( ld, chain );
+}
+
+void * CDECL wrap_ldap_first_reference( void *ld, void *chain )
+{
+    return ldap_first_reference( ld, chain );
+}
+
 void CDECL wrap_ldap_memfree( void *ptr )
 {
     return ldap_memfree( ptr );
 }
 
+int CDECL wrap_ldap_msgfree( void *msg )
+{
+    return ldap_msgfree( msg );
+}
+
+char * CDECL wrap_ldap_next_attribute( void *ld, void *entry, void *ber )
+{
+    return ldap_next_attribute( ld, entry, ber );
+}
+
+void * CDECL wrap_ldap_next_entry( void *ld, void *entry )
+{
+    return ldap_next_entry( ld, entry );
+}
+
+void * CDECL wrap_ldap_next_reference( void *ld, void *entry )
+{
+    return ldap_next_reference( ld, entry );
+}
+
 int CDECL wrap_ldap_parse_result( void *ld, void *res, int *errcode, char **matcheddn, char **errmsg,
                                   char ***referrals, LDAPControlU ***serverctrls, int free )
 {
     return ldap_parse_result( ld, res, errcode, matcheddn, errmsg, referrals, (LDAPControl ***)serverctrls, free );
 }
 
+int CDECL wrap_ldap_result( void *ld, int msgid, int all, struct timevalU *timeout, void **result )
+{
+    return ldap_result( ld, msgid, all, (struct timeval *)timeout, (LDAPMessage **)result );
+}
+
 int CDECL wrap_ldap_sasl_bind( void *ld, const char *dn, const char *mech, struct bervalU *cred,
                                LDAPControlU **serverctrls, LDAPControlU **clientctrls, int *msgid )
 {
@@ -393,6 +450,23 @@ int CDECL wrap_ldap_sasl_interactive_bind_s( void *ld, const char *dn, const cha
                                          wrap_sasl_interact, defaults );
 }
 
+int CDECL wrap_ldap_search_ext( void *ld, const char *base, int scope, const char *filter, char **attrs, int attrsonly,
+                                LDAPControlU **serverctrls, LDAPControlU **clientctrls, struct timevalU *timeout,
+                                int sizelimit, ULONG *msg )
+{
+    return ldap_search_ext( ld, base, scope, filter, attrs, attrsonly, (LDAPControl **)serverctrls,
+                            (LDAPControl **)clientctrls, (struct timeval *)timeout, sizelimit, (int *)msg );
+}
+
+int CDECL wrap_ldap_search_ext_s( void *ld, const char *base, int scope, const char *filter, char **attrs,
+                                  int attrsonly, LDAPControlU **serverctrls, LDAPControlU **clientctrls,
+                                  struct timevalU *timeout, int sizelimit, void **result )
+{
+    return ldap_search_ext_s( ld, base, scope, filter, attrs, attrsonly, (LDAPControl **)serverctrls,
+                              (LDAPControl **)clientctrls, (struct timeval *)timeout, sizelimit,
+                              (LDAPMessage **)result );
+}
+
 int CDECL wrap_ldap_unbind_ext( void *ld, LDAPControlU **serverctrls, LDAPControlU **clientctrls )
 {
     return ldap_unbind_ext( ld, (LDAPControl **)serverctrls, (LDAPControl **)clientctrls );
@@ -422,20 +496,33 @@ static const struct ldap_funcs funcs =
     wrap_ber_skip_tag,
     wrap_ber_printf,
     wrap_ber_scanf,
+    wrap_ldap_abandon_ext,
     wrap_ldap_add_ext,
     wrap_ldap_add_ext_s,
     wrap_ldap_compare_ext,
     wrap_ldap_compare_ext_s,
     wrap_ldap_control_free,
+    wrap_ldap_count_entries,
+    wrap_ldap_count_references,
     wrap_ldap_create_sort_control,
     wrap_ldap_create_vlv_control,
     wrap_ldap_delete_ext,
     wrap_ldap_delete_ext_s,
+    wrap_ldap_first_attribute,
+    wrap_ldap_first_entry,
+    wrap_ldap_first_reference,
     wrap_ldap_memfree,
+    wrap_ldap_msgfree,
+    wrap_ldap_next_attribute,
+    wrap_ldap_next_entry,
+    wrap_ldap_next_reference,
     wrap_ldap_parse_result,
+    wrap_ldap_result,
     wrap_ldap_sasl_bind,
     wrap_ldap_sasl_bind_s,
     wrap_ldap_sasl_interactive_bind_s,
+    wrap_ldap_search_ext,
+    wrap_ldap_search_ext_s,
     wrap_ldap_unbind_ext,
     wrap_ldap_unbind_ext_s,
     wrap_ldap_value_free_len,
@@ -448,5 +535,4 @@ NTSTATUS CDECL __wine_init_unix_lib( HMODULE module, DWORD reason, const void *p
     *(const struct ldap_funcs **)ptr_out = &funcs;
     return STATUS_SUCCESS;
 }
-
 #endif /* HAVE_LDAP */
diff --git a/dlls/wldap32/libldap.h b/dlls/wldap32/libldap.h
index 5ebc5bacd54..f307eaf4327 100644
--- a/dlls/wldap32/libldap.h
+++ b/dlls/wldap32/libldap.h
@@ -60,6 +60,12 @@ typedef struct
     void           *ldvlv_extradata;
 } LDAPVLVInfoU;
 
+typedef struct timevalU
+{
+    unsigned long tv_sec;
+    unsigned long tv_usec;
+} LDAP_TIMEVALU;
+
 #ifndef SASL_CB_LIST_END
 #define SASL_CB_LIST_END    0
 #define SASL_CB_USER        0x4001
@@ -90,6 +96,7 @@ extern unsigned int CDECL wrap_ber_skip_tag(void *, unsigned int *) DECLSPEC_HID
 extern int WINAPIV wrap_ber_printf(void *, char *, ...) DECLSPEC_HIDDEN;
 extern int WINAPIV wrap_ber_scanf(void *, char *, ...) DECLSPEC_HIDDEN;
 
+extern int CDECL wrap_ldap_abandon_ext(void *, int, LDAPControlU **, LDAPControlU **) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_add_ext(void *, const char *, LDAPModU **, LDAPControlU **, LDAPControlU **,
                                    ULONG *) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_add_ext_s(void *, const char *, LDAPModU **, LDAPControlU **,
@@ -99,19 +106,33 @@ extern int CDECL wrap_ldap_compare_ext(void *, const char *, const char *, struc
 extern int CDECL wrap_ldap_compare_ext_s(void *, const char *, const char *, struct bervalU *, LDAPControlU **,
                                          LDAPControlU **) DECLSPEC_HIDDEN;
 extern void CDECL wrap_ldap_control_free(LDAPControlU *) DECLSPEC_HIDDEN;
+extern int CDECL wrap_ldap_count_entries(void *, void *) DECLSPEC_HIDDEN;
+extern int CDECL wrap_ldap_count_references(void *, void *) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_create_sort_control(void *, LDAPSortKeyU **, int, LDAPControlU **) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_create_vlv_control(void *, LDAPVLVInfoU *, LDAPControlU **) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_delete_ext(void *, const char *, LDAPControlU **, LDAPControlU **, ULONG *) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_delete_ext_s(void *, const char *, LDAPControlU **, LDAPControlU **) DECLSPEC_HIDDEN;
+extern char * CDECL wrap_ldap_first_attribute(void *, void *, void **) DECLSPEC_HIDDEN;
+extern void * CDECL wrap_ldap_first_entry(void *, void *) DECLSPEC_HIDDEN;
+extern void * CDECL wrap_ldap_first_reference(void *, void *) DECLSPEC_HIDDEN;
 extern void CDECL wrap_ldap_memfree(void *) DECLSPEC_HIDDEN;
+extern int CDECL wrap_ldap_msgfree(void *) DECLSPEC_HIDDEN;
+extern char * CDECL wrap_ldap_next_attribute(void *, void *, void *) DECLSPEC_HIDDEN;
+extern void * CDECL wrap_ldap_next_entry(void *, void *) DECLSPEC_HIDDEN;
+extern void * CDECL wrap_ldap_next_reference(void *, void *) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_parse_result(void *, void *, int *, char **, char **, char ***, LDAPControlU ***,
                                         int) DECLSPEC_HIDDEN;
+extern int CDECL wrap_ldap_result(void *, int, int, struct timevalU *, void **) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_sasl_bind(void *, const char *, const char *, struct bervalU *, LDAPControlU **,
                                      LDAPControlU **, int *) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_sasl_bind_s(void *, const char *, const char *, struct bervalU *, LDAPControlU **,
                                        LDAPControlU **, struct bervalU **) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_sasl_interactive_bind_s(void *, const char *, const char *, LDAPControlU **,
                                                    LDAPControlU **, unsigned int, void *) DECLSPEC_HIDDEN;
+extern int CDECL wrap_ldap_search_ext(void *, const char *, int, const char *, char **, int, LDAPControlU **,
+                                      LDAPControlU **, struct timevalU *, int, ULONG *) DECLSPEC_HIDDEN;
+extern int CDECL wrap_ldap_search_ext_s(void *, const char *, int, const char *, char **, int, LDAPControlU **,
+                                        LDAPControlU **, struct timevalU *, int, void **) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_unbind_ext(void *, LDAPControlU **, LDAPControlU **) DECLSPEC_HIDDEN;
 extern int CDECL wrap_ldap_unbind_ext_s(void *, LDAPControlU **, LDAPControlU **) DECLSPEC_HIDDEN;
 extern void CDECL wrap_ldap_value_free_len(struct bervalU **) DECLSPEC_HIDDEN;
@@ -131,6 +152,7 @@ struct ldap_funcs
     int (WINAPIV *ber_printf)(void *, char *, ...);
     int (WINAPIV *ber_scanf)(void *, char *, ...);
 
+    int (CDECL *ldap_abandon_ext)(void *, int, LDAPControlU **, LDAPControlU **);
     int (CDECL *ldap_add_ext)(void *, const char *, LDAPModU **, LDAPControlU **, LDAPControlU **, ULONG *);
     int (CDECL *ldap_add_ext_s)(void *, const char *, LDAPModU **, LDAPControlU **, LDAPControlU **);
     int (CDECL *ldap_compare_ext)(void *, const char *, const char *, struct bervalU *, LDAPControlU **,
@@ -138,18 +160,32 @@ struct ldap_funcs
     int (CDECL *ldap_compare_ext_s)(void *, const char *, const char *, struct bervalU *, LDAPControlU **,
                                     LDAPControlU **);
     void (CDECL *ldap_control_free)(LDAPControlU *);
+    int (CDECL *ldap_count_entries)(void *, void *);
+    int (CDECL *ldap_count_references)(void *, void *);
     int (CDECL *ldap_create_sort_control)(void *, LDAPSortKeyU **, int, LDAPControlU **);
     int (CDECL *ldap_create_vlv_control)(void *, LDAPVLVInfoU *, LDAPControlU **);
     int (CDECL *ldap_delete_ext)(void *, const char *, LDAPControlU **, LDAPControlU **, ULONG *);
     int (CDECL *ldap_delete_ext_s)(void *, const char *, LDAPControlU **, LDAPControlU **);
+    char * (CDECL *ldap_first_attribute)(void *, void *, void **);
+    void * (CDECL *ldap_first_entry)(void *, void *);
+    void * (CDECL *ldap_first_reference)(void *, void *);
     void (CDECL *ldap_memfree)(void *);
+    int (CDECL *ldap_msgfree)(void *);
+    char * (CDECL *ldap_next_attribute)(void *, void *, void *);
+    void * (CDECL *ldap_next_entry)(void *, void *);
+    void * (CDECL *ldap_next_reference)(void *, void *);
     int (CDECL *ldap_parse_result)(void *, void *, int *, char **, char **, char ***, LDAPControlU ***, int);
+    int (CDECL *ldap_result)(void *, int, int, struct timevalU *, void **);
     int (CDECL *ldap_sasl_bind)(void *, const char *, const char *, struct bervalU *, LDAPControlU **, LDAPControlU **,
                                 int *);
     int (CDECL *ldap_sasl_bind_s)(void *, const char *, const char *, struct bervalU *, LDAPControlU **,
                                   LDAPControlU **, struct bervalU **);
     int (CDECL *ldap_sasl_interactive_bind_s)(void *, const char *, const char *, LDAPControlU **, LDAPControlU **,
                                               unsigned int, void *);
+    int (CDECL *ldap_search_ext)(void *, const char *, int, const char *, char **, int, LDAPControlU **,
+                                 LDAPControlU **, struct timevalU *, int, ULONG *);
+    int (CDECL *ldap_search_ext_s)(void *, const char *, int, const char *, char **, int, LDAPControlU **,
+                                   LDAPControlU **, struct timevalU *, int, void **);
     int (CDECL *ldap_unbind_ext)(void *, LDAPControlU **, LDAPControlU **);
     int (CDECL *ldap_unbind_ext_s)(void *, LDAPControlU **, LDAPControlU **);
     void (CDECL *ldap_value_free_len)(struct bervalU **);
diff --git a/dlls/wldap32/misc.c b/dlls/wldap32/misc.c
index dd1a1ef3f12..234b84d42f9 100644
--- a/dlls/wldap32/misc.c
+++ b/dlls/wldap32/misc.c
@@ -18,22 +18,14 @@
  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
  */
 
-#include "config.h"
-#include "wine/port.h"
-
 #include <stdarg.h>
-#include <stdio.h>
-#ifdef HAVE_LDAP_H
-#include <ldap.h>
-#endif
-
 #include "windef.h"
 #include "winbase.h"
 #include "winnls.h"
 
-#include "winldap_private.h"
-#include "wldap32.h"
 #include "wine/debug.h"
+#include "wine/heap.h"
+#include "winldap_private.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(wldap32);
 
@@ -52,16 +44,10 @@ WINE_DEFAULT_DEBUG_CHANNEL(wldap32);
  */
 ULONG CDECL WLDAP32_ldap_abandon( WLDAP32_LDAP *ld, ULONG msgid )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
-
     TRACE( "(%p, 0x%08x)\n", ld, msgid );
 
     if (!ld) return ~0u;
-    ret = map_error( ldap_abandon_ext( ld->ld, msgid, NULL, NULL ));
-
-#endif
-    return ret;
+    return map_error( ldap_funcs->ldap_abandon_ext( ld->ld, msgid, NULL, NULL ) );
 }
 
 /***********************************************************************
@@ -69,7 +55,7 @@ ULONG CDECL WLDAP32_ldap_abandon( WLDAP32_LDAP *ld, ULONG msgid )
  *
  * See ldap_check_filterW.
  */
-ULONG CDECL ldap_check_filterA( WLDAP32_LDAP *ld, PCHAR filter )
+ULONG CDECL ldap_check_filterA( WLDAP32_LDAP *ld, char *filter )
 {
     ULONG ret;
     WCHAR *filterW = NULL;
@@ -77,11 +63,7 @@ ULONG CDECL ldap_check_filterA( WLDAP32_LDAP *ld, PCHAR filter )
     TRACE( "(%p, %s)\n", ld, debugstr_a(filter) );
 
     if (!ld) return WLDAP32_LDAP_PARAM_ERROR;
-
-    if (filter) {
-        filterW = strAtoW( filter );
-        if (!filterW) return WLDAP32_LDAP_NO_MEMORY;
-    }
+    if (filter && !(filterW = strAtoW( filter ))) return WLDAP32_LDAP_NO_MEMORY;
 
     ret = ldap_check_filterW( ld, filterW );
 
@@ -102,7 +84,7 @@ ULONG CDECL ldap_check_filterA( WLDAP32_LDAP *ld, PCHAR filter )
  *  Success: LDAP_SUCCESS
  *  Failure: An LDAP error code.
  */
-ULONG CDECL ldap_check_filterW( WLDAP32_LDAP *ld, PWCHAR filter )
+ULONG CDECL ldap_check_filterW( WLDAP32_LDAP *ld, WCHAR *filter )
 {
     TRACE( "(%p, %s)\n", ld, debugstr_w(filter) );
 
@@ -155,16 +137,10 @@ WLDAP32_LDAP * CDECL ldap_conn_from_msg( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *
  */
 ULONG CDECL WLDAP32_ldap_count_entries( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
-
     TRACE( "(%p, %p)\n", ld, res );
 
     if (!ld) return ~0u;
-    ret = ldap_count_entries( ld->ld, res );
-
-#endif
-    return ret;
+    return ldap_funcs->ldap_count_entries( ld->ld, res->Request );
 }
 
 /***********************************************************************
@@ -182,16 +158,10 @@ ULONG CDECL WLDAP32_ldap_count_entries( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *r
  */
 ULONG CDECL WLDAP32_ldap_count_references( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP_COUNT_REFERENCES
-
     TRACE( "(%p, %p)\n", ld, res );
 
     if (!ld) return 0;
-    ret = ldap_count_references( ld->ld, res );
-
-#endif
-    return ret;
+    return ldap_funcs->ldap_count_references( ld->ld, res->Request );
 }
 
 static ULONG get_escape_size( PCHAR src, ULONG srclen )
@@ -213,7 +183,7 @@ static ULONG get_escape_size( PCHAR src, ULONG srclen )
     return size + 1;
 }
 
-static void escape_filter_element( PCHAR src, ULONG srclen, PCHAR dst )
+static void escape_filter_element( char *src, ULONG srclen, char *dst )
 {
     ULONG i;
     static const char fmt[] = "\\%02X";
@@ -236,22 +206,17 @@ static void escape_filter_element( PCHAR src, ULONG srclen, PCHAR dst )
  *
  * See ldap_escape_filter_elementW.
  */
-ULONG CDECL ldap_escape_filter_elementA( PCHAR src, ULONG srclen, PCHAR dst, ULONG dstlen )
+ULONG CDECL ldap_escape_filter_elementA( char *src, ULONG srclen, char *dst, ULONG dstlen )
 {
-    ULONG len;
+    ULONG len = get_escape_size( src, srclen );
 
     TRACE( "(%p, 0x%08x, %p, 0x%08x)\n", src, srclen, dst, dstlen );
 
-    len = get_escape_size( src, srclen );
     if (!dst) return len;
+    if (!src || dstlen < len) return WLDAP32_LDAP_PARAM_ERROR;
 
-    if (!src || dstlen < len)
-        return WLDAP32_LDAP_PARAM_ERROR;
-    else
-    {
-        escape_filter_element( src, srclen, dst );
-        return WLDAP32_LDAP_SUCCESS;
-    }
+    escape_filter_element( src, srclen, dst );
+    return WLDAP32_LDAP_SUCCESS;
 }
 
 /***********************************************************************
@@ -269,13 +234,12 @@ ULONG CDECL ldap_escape_filter_elementA( PCHAR src, ULONG srclen, PCHAR dst, ULO
  *  Success: LDAP_SUCCESS
  *  Failure: An LDAP error code.
  */
-ULONG CDECL ldap_escape_filter_elementW( PCHAR src, ULONG srclen, PWCHAR dst, ULONG dstlen )
+ULONG CDECL ldap_escape_filter_elementW( char *src, ULONG srclen, WCHAR *dst, ULONG dstlen )
 {
-    ULONG len;
+    ULONG len = get_escape_size( src, srclen );
 
     TRACE( "(%p, 0x%08x, %p, 0x%08x)\n", src, srclen, dst, dstlen );
 
-    len = get_escape_size( src, srclen );
     if (!dst) return len;
 
     /* no matter what you throw at it, this is what native returns */
@@ -287,29 +251,29 @@ ULONG CDECL ldap_escape_filter_elementW( PCHAR src, ULONG srclen, PWCHAR dst, UL
  *
  * See ldap_first_attributeW.
  */
-PCHAR CDECL ldap_first_attributeA( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry,
-    WLDAP32_BerElement** ptr )
+char * CDECL ldap_first_attributeA( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry, WLDAP32_BerElement **ber )
 {
-    PCHAR ret = NULL;
-#ifdef HAVE_LDAP
+    char *ret = NULL;
     WCHAR *retW;
 
-    TRACE( "(%p, %p, %p)\n", ld, entry, ptr );
+    TRACE( "(%p, %p, %p)\n", ld, entry, ber );
 
     if (!ld || !entry) return NULL;
-    retW = ldap_first_attributeW( ld, entry, ptr );
 
-    ret = strWtoA( retW );
-    ldap_memfreeW( retW );
+    retW = ldap_first_attributeW( ld, entry->Request, ber );
+    if (retW)
+    {
+        ret = strWtoA( retW );
+        ldap_memfreeW( retW );
+    }
 
-#endif
     return ret;
 }
 
 /***********************************************************************
  *      ldap_first_attributeW     (WLDAP32.@)
  *
- * Get the first attribute for a given entry. 
+ * Get the first attribute for a given entry.
  *
  * PARAMS
  *  ld    [I] Pointer to an LDAP context.
@@ -323,29 +287,26 @@ PCHAR CDECL ldap_first_attributeA( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry,
  * NOTES
  *  Use ldap_memfree to free the returned string.
  */
-PWCHAR CDECL ldap_first_attributeW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry,
-    WLDAP32_BerElement** ptr )
+WCHAR * CDECL ldap_first_attributeW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry, WLDAP32_BerElement **ptr )
 {
-    PWCHAR ret = NULL;
-#ifdef HAVE_LDAP
-    BerElement *berU;
+    WCHAR *ret = NULL;
+    WLDAP32_BerElement *ber;
     char *retU;
+    void *berU;
 
     TRACE( "(%p, %p, %p)\n", ld, entry, ptr );
 
     if (!ld || !entry) return NULL;
 
-    retU = ldap_first_attribute( ld->ld, entry, &berU );
-    if (retU)
+    retU = ldap_funcs->ldap_first_attribute( ld->ld, entry->Request, &berU );
+    if (retU && (ber = heap_alloc( sizeof(*ber) )))
     {
-        WLDAP32_BerElement *ber = heap_alloc( sizeof(*ber) );
         ber->opaque = (char *)berU;
         *ptr = ber;
         ret = strUtoW( retU );
-        ldap_memfree( retU );
     }
 
-#endif
+    ldap_funcs->ldap_memfree( retU );
     return ret;
 }
 
@@ -363,20 +324,24 @@ PWCHAR CDECL ldap_first_attributeW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry
  *  Failure: NULL
  *
  * NOTES
- *  The returned entry will be freed when the message is freed. 
+ *  The returned entry will be freed when the message is freed.
  */
 WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_first_entry( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *res )
 {
-#ifdef HAVE_LDAP
+    void *msgU;
 
     TRACE( "(%p, %p)\n", ld, res );
 
     if (!ld || !res) return NULL;
-    return ldap_first_entry( ld->ld, res );
 
-#else
+    msgU = ldap_funcs->ldap_first_entry( ld->ld, res->Request );
+    if (msgU)
+    {
+        assert( msgU == res->Request );
+        return res;
+    }
+
     return NULL;
-#endif
 }
 
 /***********************************************************************
@@ -394,16 +359,20 @@ WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_first_entry( WLDAP32_LDAP *ld, WLDAP32_
  */
 WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_first_reference( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *res )
 {
-#ifdef HAVE_LDAP_FIRST_REFERENCE
+    void *msgU;
 
     TRACE( "(%p, %p)\n", ld, res );
 
     if (!ld) return NULL;
-    return ldap_first_reference( ld->ld, res );
 
-#else
+    msgU = ldap_funcs->ldap_first_reference( ld->ld, res->Request );
+    if (msgU)
+    {
+        assert( msgU == res->Request );
+        return res;
+    }
+
     return NULL;
-#endif
 }
 
 /***********************************************************************
@@ -411,7 +380,7 @@ WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_first_reference( WLDAP32_LDAP *ld, WLDA
  *
  * See ldap_memfreeW.
  */
-void CDECL ldap_memfreeA( PCHAR block )
+void CDECL ldap_memfreeA( char *block )
 {
     TRACE( "(%p)\n", block );
     strfreeA( block );
@@ -425,7 +394,7 @@ void CDECL ldap_memfreeA( PCHAR block )
  * PARAMS
  *  block [I] Pointer to memory block to be freed.
  */
-void CDECL ldap_memfreeW( PWCHAR block )
+void CDECL ldap_memfreeW( WCHAR *block )
 {
     TRACE( "(%p)\n", block );
     strfreeW( block );
@@ -441,14 +410,21 @@ void CDECL ldap_memfreeW( PWCHAR block )
  */
 ULONG CDECL WLDAP32_ldap_msgfree( WLDAP32_LDAPMessage *res )
 {
-    ULONG ret = WLDAP32_LDAP_SUCCESS;
-#ifdef HAVE_LDAP
+    WLDAP32_LDAPMessage *entry, *list = res;
 
     TRACE( "(%p)\n", res );
-    ldap_msgfree( res );
 
-#endif
-    return ret;
+    if (!res) return WLDAP32_LDAP_SUCCESS;
+
+    ldap_funcs->ldap_msgfree( res->Request );
+    while (list)
+    {
+        entry = list;
+        list = entry->lm_next;
+        heap_free( entry );
+    }
+
+    return WLDAP32_LDAP_SUCCESS;
 }
 
 /***********************************************************************
@@ -456,22 +432,22 @@ ULONG CDECL WLDAP32_ldap_msgfree( WLDAP32_LDAPMessage *res )
  *
  * See ldap_next_attributeW.
  */
-PCHAR CDECL ldap_next_attributeA( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry,
-    WLDAP32_BerElement *ptr )
+char * CDECL ldap_next_attributeA( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry, WLDAP32_BerElement *ptr )
 {
-    PCHAR ret = NULL;
-#ifdef HAVE_LDAP
+    char *ret = NULL;
     WCHAR *retW;
 
     TRACE( "(%p, %p, %p)\n", ld, entry, ptr );
 
     if (!ld || !entry || !ptr) return NULL;
-    retW = ldap_next_attributeW( ld, entry, ptr );
 
-    ret = strWtoA( retW );
-    ldap_memfreeW( retW );
+    retW = ldap_next_attributeW( ld, entry->Request, ptr );
+    if (retW)
+    {
+        ret = strWtoA( retW );
+        ldap_memfreeW( retW );
+    }
 
-#endif
     return ret;
 }
 
@@ -493,25 +469,22 @@ PCHAR CDECL ldap_next_attributeA( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry,
  *  Free the returned string after each iteration with ldap_memfree.
  *  When done iterating and when ptr != NULL, call ber_free( ptr, 0 ).
  */
-PWCHAR CDECL ldap_next_attributeW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry,
-    WLDAP32_BerElement *ber )
+WCHAR * CDECL ldap_next_attributeW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry, WLDAP32_BerElement *ptr )
 {
-    PWCHAR ret = NULL;
-#ifdef HAVE_LDAP
+    WCHAR *ret = NULL;
     char *retU;
 
-    TRACE( "(%p, %p, %p)\n", ld, entry, ber );
+    TRACE( "(%p, %p, %p)\n", ld, entry, ptr );
 
-    if (!ld || !entry) return NULL;
+    if (!ld || !entry || !ptr) return NULL;
 
-    retU = ldap_next_attribute( ld->ld, entry, (BerElement *)ber->opaque );
+    retU = ldap_funcs->ldap_next_attribute( ld->ld, entry->Request, ptr->opaque );
     if (retU)
     {
         ret = strUtoW( retU );
-        ldap_memfree( retU );
+        ldap_funcs->ldap_memfree( retU );
     }
 
-#endif
     return ret;
 }
 
@@ -533,16 +506,23 @@ PWCHAR CDECL ldap_next_attributeW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry,
  */
 WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_next_entry( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry )
 {
-#ifdef HAVE_LDAP
+    WLDAP32_LDAPMessage *msg = NULL;
+    void *msgU;
 
     TRACE( "(%p, %p)\n", ld, entry );
 
     if (!ld || !entry) return NULL;
-    return ldap_next_entry( ld->ld, entry );
 
-#else
-    return NULL;
-#endif
+    if (entry->lm_next) return entry->lm_next;
+
+    msgU = ldap_funcs->ldap_next_entry( ld->ld, entry->Request );
+    if (msgU && (msg = heap_alloc_zero( sizeof(*msg) )))
+    {
+        msg->Request = msgU;
+        entry->lm_next = msg;
+    }
+
+    return msg;
 }
 
 /***********************************************************************
@@ -563,16 +543,23 @@ WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_next_entry( WLDAP32_LDAP *ld, WLDAP32_L
  */
 WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_next_reference( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry )
 {
-#ifdef HAVE_LDAP_NEXT_REFERENCE
+    WLDAP32_LDAPMessage *msg = NULL;
+    void *msgU;
 
     TRACE( "(%p, %p)\n", ld, entry );
 
     if (!ld || !entry) return NULL;
-    return ldap_next_reference( ld->ld, entry );
 
-#else
-    return NULL;
-#endif
+    if (entry->lm_next) return entry->lm_next;
+
+    msgU = ldap_funcs->ldap_next_reference( ld->ld, entry->Request );
+    if (msgU && (msg = heap_alloc_zero( sizeof(*msg) )))
+    {
+        msg->Request = msgU;
+        entry->lm_next = msg;
+    }
+
+    return msg;
 }
 
 /***********************************************************************
@@ -611,18 +598,31 @@ WLDAP32_LDAPMessage * CDECL WLDAP32_ldap_next_reference( WLDAP32_LDAP *ld, WLDAP
  *  to immediately return any available results. Free returned results
  *  with ldap_msgfree.
  */
-ULONG CDECL WLDAP32_ldap_result( WLDAP32_LDAP *ld, ULONG msgid, ULONG all,
-    struct l_timeval *timeout, WLDAP32_LDAPMessage **res )
+ULONG CDECL WLDAP32_ldap_result( WLDAP32_LDAP *ld, ULONG msgid, ULONG all, struct l_timeval *timeout,
+    WLDAP32_LDAPMessage **res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    WLDAP32_LDAPMessage *msg;
+    struct timevalU timeval;
+    void *msgU = NULL;
+    ULONG ret;
 
     TRACE( "(%p, 0x%08x, 0x%08x, %p, %p)\n", ld, msgid, all, timeout, res );
 
     if (!ld || !res || msgid == ~0u) return ~0u;
-    ret = ldap_result( ld->ld, msgid, all, (struct timeval *)timeout, res );
 
-#endif
+    if (timeout)
+    {
+        timeval.tv_sec = timeout->tv_sec;
+        timeval.tv_usec = timeout->tv_usec;
+    }
+
+    ret = ldap_funcs->ldap_result( ld->ld, msgid, all, timeout ? &timeval : NULL, &msgU );
+    if (msgU && (msg = heap_alloc_zero( sizeof(*msg) )))
+    {
+        msg->Request = msgU;
+        *res = msg;
+    }
+
     return ret;
 }
 
@@ -635,7 +635,7 @@ ULONG CDECL WLDAP32_ldap_result( WLDAP32_LDAP *ld, ULONG msgid, ULONG all,
  *  src    [I] Wide character string to convert.
  *  srclen [I] Size of string to convert, in characters.
  *  dst    [O] Pointer to a buffer that receives the converted string.
- *  dstlen [I] Size of the destination buffer in characters. 
+ *  dstlen [I] Size of the destination buffer in characters.
  *
  * RETURNS
  *  The number of characters written into the destination buffer.
@@ -643,7 +643,7 @@ ULONG CDECL WLDAP32_ldap_result( WLDAP32_LDAP *ld, ULONG msgid, ULONG all,
  * NOTES
  *  Set dstlen to zero to ask for the required buffer size.
  */
-int CDECL LdapUnicodeToUTF8( LPCWSTR src, int srclen, LPSTR dst, int dstlen )
+int CDECL LdapUnicodeToUTF8( const WCHAR *src, int srclen, char *dst, int dstlen )
 {
     return WideCharToMultiByte( CP_UTF8, 0, src, srclen, dst, dstlen, NULL, NULL );
 }
@@ -657,7 +657,7 @@ int CDECL LdapUnicodeToUTF8( LPCWSTR src, int srclen, LPSTR dst, int dstlen )
  *  src    [I] UTF8 string to convert.
  *  srclen [I] Size of string to convert, in characters.
  *  dst    [O] Pointer to a buffer that receives the converted string.
- *  dstlen [I] Size of the destination buffer in characters. 
+ *  dstlen [I] Size of the destination buffer in characters.
  *
  * RETURNS
  *  The number of characters written into the destination buffer.
@@ -665,7 +665,7 @@ int CDECL LdapUnicodeToUTF8( LPCWSTR src, int srclen, LPSTR dst, int dstlen )
  * NOTES
  *  Set dstlen to zero to ask for the required buffer size.
  */
-int CDECL LdapUTF8ToUnicode( LPCSTR src, int srclen, LPWSTR dst, int dstlen )
+int CDECL LdapUTF8ToUnicode( const char *src, int srclen, WCHAR *dst, int dstlen )
 {
     return MultiByteToWideChar( CP_UTF8, 0, src, srclen, dst, dstlen );
 }
diff --git a/dlls/wldap32/parse.c b/dlls/wldap32/parse.c
index 6bde8542bec..bbaa7b1f842 100644
--- a/dlls/wldap32/parse.c
+++ b/dlls/wldap32/parse.c
@@ -99,7 +99,7 @@ ULONG CDECL ldap_parse_extended_resultW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *
     if (!ld) return WLDAP32_LDAP_PARAM_ERROR;
     if (!result) return WLDAP32_LDAP_NO_RESULTS_RETURNED;
 
-    ret = map_error( ldap_parse_extended_result( ld->ld, result, &oidU, (struct berval **)data, free ) );
+    ret = map_error( ldap_parse_extended_result( ld->ld, result->Request, &oidU, (struct berval **)data, free ) );
 
     if (oid) {
         *oid = strUtoW( oidU );
@@ -153,18 +153,18 @@ ULONG CDECL ldap_parse_referenceA( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *messag
  * NOTES
  *  Free the referrals with ldap_value_free.
  */
-ULONG CDECL ldap_parse_referenceW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *message,
+ULONG CDECL ldap_parse_referenceW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *result,
     PWCHAR **referrals )
 {
     ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
 #ifdef HAVE_LDAP_PARSE_REFERENCE
     char **referralsU = NULL;
 
-    TRACE( "(%p, %p, %p)\n", ld, message, referrals );
+    TRACE( "(%p, %p, %p)\n", ld, result, referrals );
 
     if (!ld) return ~0u;
 
-    ret = map_error( ldap_parse_reference( ld->ld, message, &referralsU, NULL, 0 ));
+    ret = map_error( ldap_parse_reference( ld->ld, result->Request, &referralsU, NULL, 0 ));
 
     *referrals = strarrayUtoW( referralsU );
     ldap_memfree( referralsU );
@@ -249,7 +249,7 @@ ULONG CDECL ldap_parse_resultW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *result,
 
     if (!ld) return WLDAP32_LDAP_PARAM_ERROR;
 
-    ret = map_error( ldap_parse_result( ld->ld, result, (int *)retcode, &matchedU, &errorU,
+    ret = map_error( ldap_parse_result( ld->ld, result->Request, (int *)retcode, &matchedU, &errorU,
                                         &referralsU, &serverctrlsU, free ));
 
     if (matched) *matched = strUtoW( matchedU );
diff --git a/dlls/wldap32/search.c b/dlls/wldap32/search.c
index 88ecb541c92..b4bf204f817 100644
--- a/dlls/wldap32/search.c
+++ b/dlls/wldap32/search.c
@@ -18,57 +18,34 @@
  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
  */
 
-#include "config.h"
-#include "wine/port.h"
-
 #include <stdarg.h>
-#ifdef HAVE_LDAP_H
-#include <ldap.h>
-#endif
-
 #include "windef.h"
 #include "winbase.h"
 #include "winnls.h"
 
-#include "winldap_private.h"
-#include "wldap32.h"
 #include "wine/debug.h"
+#include "wine/heap.h"
+#include "winldap_private.h"
 
-#ifdef HAVE_LDAP
 WINE_DEFAULT_DEBUG_CHANNEL(wldap32);
-#endif
 
 /***********************************************************************
  *      ldap_searchA     (WLDAP32.@)
  *
  * See ldap_searchW.
  */
-ULONG CDECL ldap_searchA( WLDAP32_LDAP *ld, PCHAR base, ULONG scope, PCHAR filter,
-    PCHAR attrs[], ULONG attrsonly )
+ULONG CDECL ldap_searchA( WLDAP32_LDAP *ld, char *base, ULONG scope, char *filter, char **attrs, ULONG attrsonly )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    ULONG ret = WLDAP32_LDAP_NO_MEMORY;
     WCHAR *baseW = NULL, *filterW = NULL, **attrsW = NULL;
 
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x)\n", ld, debugstr_a(base),
-           scope, debugstr_a(filter), attrs, attrsonly );
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x)\n", ld, debugstr_a(base), scope, debugstr_a(filter), attrs, attrsonly );
 
     if (!ld) return ~0u;
 
-    if (base) {
-        baseW = strAtoW( base );
-        if (!baseW) goto exit;
-    }
-    if (filter) {
-        filterW = strAtoW( filter );
-        if (!filterW) goto exit;
-    }
-    if (attrs) {
-        attrsW = strarrayAtoW( attrs );
-        if (!attrsW) goto exit;
-    }
+    if (base && !(baseW = strAtoW( base ))) goto exit;
+    if (filter && !(filterW = strAtoW( filter ))) goto exit;
+    if (attrs && !(attrsW = strarrayAtoW( attrs ))) goto exit;
 
     ret = ldap_searchW( ld, baseW, scope, filterW, attrsW, attrsonly );
 
@@ -76,8 +53,6 @@ exit:
     strfreeW( baseW );
     strfreeW( filterW );
     strarrayfreeW( attrsW );
-
-#endif
     return ret;
 }
 
@@ -104,49 +79,14 @@ exit:
  *  the operation. Cancel the operation by calling ldap_abandon
  *  with the message ID.
  */
-ULONG CDECL ldap_searchW( WLDAP32_LDAP *ld, PWCHAR base, ULONG scope, PWCHAR filter,
-    PWCHAR attrs[], ULONG attrsonly )
+ULONG CDECL ldap_searchW( WLDAP32_LDAP *ld, WCHAR *base, ULONG scope, WCHAR *filter, WCHAR **attrs, ULONG attrsonly )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
-    char *baseU = NULL, *filterU = NULL, **attrsU = NULL;
-    int msg;
-
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x)\n", ld, debugstr_w(base),
-           scope, debugstr_w(filter), attrs, attrsonly );
-
-    if (!ld) return ~0u;
+    ULONG ret, msg;
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x)\n", ld, debugstr_w(base), scope, debugstr_w(filter), attrs, attrsonly );
 
-    if (base) {
-        baseU = strWtoU( base );
-        if (!baseU) goto exit;
-    }
-    if (filter) {
-        filterU = strWtoU( filter );
-        if (!filterU) goto exit;
-    }
-    if (attrs) {
-        attrsU = strarrayWtoU( attrs );
-        if (!attrsU) goto exit;
-    }
-
-    ret = ldap_search_ext( ld->ld, baseU, scope, filterU, attrsU, attrsonly,
-                           NULL, NULL, NULL, 0, &msg );
-
-    if (ret == LDAP_SUCCESS)
-        ret = msg;
-    else
-        ret = ~0u;
-
-exit:
-    strfreeU( baseU );
-    strfreeU( filterU );
-    strarrayfreeU( attrsU );
-
-#endif
-    return ret;
+    ret = ldap_search_extW( ld, base, scope, filter, attrs, attrsonly, NULL, NULL, 0, 0, &msg );
+    if (ret == WLDAP32_LDAP_SUCCESS) return msg;
+    return ~0u;
 }
 
 /***********************************************************************
@@ -154,47 +94,26 @@ exit:
  *
  * See ldap_search_extW.
  */
-ULONG CDECL ldap_search_extA( WLDAP32_LDAP *ld, PCHAR base, ULONG scope,
-    PCHAR filter, PCHAR attrs[], ULONG attrsonly, PLDAPControlA *serverctrls,
-    PLDAPControlA *clientctrls, ULONG timelimit, ULONG sizelimit, ULONG *message )
+ULONG CDECL ldap_search_extA( WLDAP32_LDAP *ld, char *base, ULONG scope, char *filter, char **attrs, ULONG attrsonly,
+    LDAPControlA **serverctrls, LDAPControlA **clientctrls, ULONG timelimit, ULONG sizelimit, ULONG *message )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    ULONG ret = WLDAP32_LDAP_NO_MEMORY;
     WCHAR *baseW = NULL, *filterW = NULL, **attrsW = NULL;
     LDAPControlW **serverctrlsW = NULL, **clientctrlsW = NULL;
 
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, 0x%08x, 0x%08x, %p)\n",
-           ld, debugstr_a(base), scope, debugstr_a(filter), attrs, attrsonly,
-           serverctrls, clientctrls, timelimit, sizelimit, message );
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, 0x%08x, 0x%08x, %p)\n", ld, debugstr_a(base), scope,
+           debugstr_a(filter), attrs, attrsonly, serverctrls, clientctrls, timelimit, sizelimit, message );
 
     if (!ld) return WLDAP32_LDAP_PARAM_ERROR;
 
-    if (base) {
-        baseW = strAtoW( base );
-        if (!baseW) goto exit;
-    }
-    if (filter)
-    {
-        filterW = strAtoW( filter );
-        if (!filterW) goto exit;
-    }
-    if (attrs) {
-        attrsW = strarrayAtoW( attrs );
-        if (!attrsW) goto exit;
-    }
-    if (serverctrls) {
-        serverctrlsW = controlarrayAtoW( serverctrls );
-        if (!serverctrlsW) goto exit;
-    }
-    if (clientctrls) {
-        clientctrlsW = controlarrayAtoW( clientctrls );
-        if (!clientctrlsW) goto exit;
-    }
+    if (base && !(baseW = strAtoW( base ))) goto exit;
+    if (filter && !(filterW = strAtoW( filter ))) goto exit;
+    if (attrs && !(attrsW = strarrayAtoW( attrs ))) goto exit;
+    if (serverctrls && !(serverctrlsW = controlarrayAtoW( serverctrls ))) goto exit;
+    if (clientctrls && !(clientctrlsW = controlarrayAtoW( clientctrls ))) goto exit;
 
-    ret = ldap_search_extW( ld, baseW, scope, filterW, attrsW, attrsonly,
-                            serverctrlsW, clientctrlsW, timelimit, sizelimit, message );
+    ret = ldap_search_extW( ld, baseW, scope, filterW, attrsW, attrsonly, serverctrlsW, clientctrlsW, timelimit,
+                            sizelimit, message );
 
 exit:
     strfreeW( baseW );
@@ -202,8 +121,6 @@ exit:
     strarrayfreeW( attrsW );
     controlarrayfreeW( serverctrlsW );
     controlarrayfreeW( clientctrlsW );
-
-#endif
     return ret;
 }
 
@@ -235,63 +152,38 @@ exit:
  *  the operation. Cancel the operation by calling ldap_abandon
  *  with the message ID.
  */
-ULONG CDECL ldap_search_extW( WLDAP32_LDAP *ld, PWCHAR base, ULONG scope,
-    PWCHAR filter, PWCHAR attrs[], ULONG attrsonly, PLDAPControlW *serverctrls,
-    PLDAPControlW *clientctrls, ULONG timelimit, ULONG sizelimit, ULONG *message )
+ULONG CDECL ldap_search_extW( WLDAP32_LDAP *ld, WCHAR *base, ULONG scope, WCHAR *filter, WCHAR **attrs,
+    ULONG attrsonly, LDAPControlW **serverctrls, LDAPControlW **clientctrls, ULONG timelimit, ULONG sizelimit,
+    ULONG *message )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    ULONG ret = WLDAP32_LDAP_NO_MEMORY;
     char *baseU = NULL, *filterU = NULL, **attrsU = NULL;
-    LDAPControl **serverctrlsU = NULL, **clientctrlsU = NULL;
-    struct timeval tv, *tvp = NULL;
+    LDAPControlU **serverctrlsU = NULL, **clientctrlsU = NULL;
+    struct timevalU timevalU;
 
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, 0x%08x, 0x%08x, %p)\n",
-           ld, debugstr_w(base), scope, debugstr_w(filter), attrs, attrsonly,
-           serverctrls, clientctrls, timelimit, sizelimit, message );
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, 0x%08x, 0x%08x, %p)\n", ld, debugstr_w(base), scope,
+           debugstr_w(filter), attrs, attrsonly, serverctrls, clientctrls, timelimit, sizelimit, message );
 
     if (!ld) return ~0u;
 
-    if (base) {
-        baseU = strWtoU( base );
-        if (!baseU) goto exit;
-    }
-    if (filter) {
-        filterU = strWtoU( filter );
-        if (!filterU) goto exit;
-    }
-    if (attrs) {
-        attrsU = strarrayWtoU( attrs );
-        if (!attrsU) goto exit;
-    }
-    if (serverctrls) {
-        serverctrlsU = controlarrayWtoU( serverctrls );
-        if (!serverctrlsU) goto exit;
-    }
-    if (clientctrls) {
-        clientctrlsU = controlarrayWtoU( clientctrls );
-        if (!clientctrlsU) goto exit;
-    }
-
-    if (timelimit)
-    {
-        tv.tv_sec = timelimit;
-        tv.tv_usec = 0;
-        tvp = &tv;
-    }
+    if (base && !(baseU = strWtoU( base ))) goto exit;
+    if (filter && !(filterU = strWtoU( filter ))) goto exit;
+    if (attrs && !(attrsU = strarrayWtoU( attrs ))) goto exit;
+    if (serverctrls && !(serverctrlsU = controlarrayWtoU( serverctrls ))) goto exit;
+    if (clientctrls && !(clientctrlsU = controlarrayWtoU( clientctrls ))) goto exit;
 
-    ret = map_error( ldap_search_ext( ld->ld, baseU, scope, filterU, attrsU, attrsonly,
-                                      serverctrlsU, clientctrlsU, tvp, sizelimit, (int *)message ));
+    timevalU.tv_sec = timelimit;
+    timevalU.tv_usec = 0;
 
+    ret = map_error( ldap_funcs->ldap_search_ext( ld->ld, baseU, scope, filterU, attrsU, attrsonly,
+                                                  serverctrlsU, clientctrlsU, timelimit ? &timevalU : NULL, sizelimit,
+                                                  message ) );
 exit:
     strfreeU( baseU );
     strfreeU( filterU );
     strarrayfreeU( attrsU );
     controlarrayfreeU( serverctrlsU );
     controlarrayfreeU( clientctrlsU );
-
-#endif
     return ret;
 }
 
@@ -300,46 +192,27 @@ exit:
  *
  * See ldap_search_ext_sW.
  */
-ULONG CDECL ldap_search_ext_sA( WLDAP32_LDAP *ld, PCHAR base, ULONG scope,
-    PCHAR filter, PCHAR attrs[], ULONG attrsonly, PLDAPControlA *serverctrls,
-    PLDAPControlA *clientctrls, struct l_timeval* timeout, ULONG sizelimit, WLDAP32_LDAPMessage **res )
+ULONG CDECL ldap_search_ext_sA( WLDAP32_LDAP *ld, char *base, ULONG scope, char *filter, char **attrs,
+    ULONG attrsonly, LDAPControlA **serverctrls, LDAPControlA **clientctrls, struct l_timeval *timeout,
+    ULONG sizelimit, WLDAP32_LDAPMessage **res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    ULONG ret = WLDAP32_LDAP_NO_MEMORY;
     WCHAR *baseW = NULL, *filterW = NULL, **attrsW = NULL;
     LDAPControlW **serverctrlsW = NULL, **clientctrlsW = NULL;
 
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, %p, 0x%08x, %p)\n",
-           ld, debugstr_a(base), scope, debugstr_a(filter), attrs, attrsonly,
-           serverctrls, clientctrls, timeout, sizelimit, res );
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, %p, 0x%08x, %p)\n", ld, debugstr_a(base), scope,
+           debugstr_a(filter), attrs, attrsonly, serverctrls, clientctrls, timeout, sizelimit, res );
 
     if (!ld || !res) return WLDAP32_LDAP_PARAM_ERROR;
 
-    if (base) {
-        baseW = strAtoW( base );
-        if (!baseW) goto exit;
-    }
-    if (filter) {
-        filterW = strAtoW( filter );
-        if (!filterW) goto exit;
-    }
-    if (attrs) {
-        attrsW = strarrayAtoW( attrs );
-        if (!attrsW) goto exit;
-    }
-    if (serverctrls) {
-        serverctrlsW = controlarrayAtoW( serverctrls );
-        if (!serverctrlsW) goto exit;
-    }
-    if (clientctrls) {
-        clientctrlsW = controlarrayAtoW( clientctrls );
-        if (!clientctrlsW) goto exit;
-    }
+    if (base && !(baseW = strAtoW( base ))) goto exit;
+    if (filter && !(filterW = strAtoW( filter ))) goto exit;
+    if (attrs && !(attrsW = strarrayAtoW( attrs ))) goto exit;
+    if (serverctrls && !(serverctrlsW = controlarrayAtoW( serverctrls ))) goto exit;
+    if (clientctrls && !(clientctrlsW = controlarrayAtoW( clientctrls ))) goto exit;
 
-    ret = ldap_search_ext_sW( ld, baseW, scope, filterW, attrsW, attrsonly,
-                              serverctrlsW, clientctrlsW, timeout, sizelimit, res );
+    ret = ldap_search_ext_sW( ld, baseW, scope, filterW, attrsW, attrsonly, serverctrlsW, clientctrlsW, timeout,
+                              sizelimit, res );
 
 exit:
     strfreeW( baseW );
@@ -347,8 +220,6 @@ exit:
     strarrayfreeW( attrsW );
     controlarrayfreeW( serverctrlsW );
     controlarrayfreeW( clientctrlsW );
-
-#endif
     return ret;
 }
 
@@ -378,47 +249,49 @@ exit:
  * NOTES
  *  Call ldap_msgfree to free the results.
  */
-ULONG CDECL ldap_search_ext_sW( WLDAP32_LDAP *ld, PWCHAR base, ULONG scope,
-    PWCHAR filter, PWCHAR attrs[], ULONG attrsonly, PLDAPControlW *serverctrls,
-    PLDAPControlW *clientctrls, struct l_timeval* timeout, ULONG sizelimit, WLDAP32_LDAPMessage **res )
+ULONG CDECL ldap_search_ext_sW( WLDAP32_LDAP *ld, WCHAR *base, ULONG scope, WCHAR *filter, WCHAR **attrs,
+    ULONG attrsonly, LDAPControlW **serverctrls, LDAPControlW **clientctrls, struct l_timeval *timeout,
+    ULONG sizelimit, WLDAP32_LDAPMessage **res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    ULONG ret = WLDAP32_LDAP_NO_MEMORY;
     char *baseU = NULL, *filterU = NULL, **attrsU = NULL;
-    LDAPControl **serverctrlsU = NULL, **clientctrlsU = NULL;
-
-    ret = WLDAP32_LDAP_NO_MEMORY;
+    LDAPControlU **serverctrlsU = NULL, **clientctrlsU = NULL;
+    struct timevalU timevalU;
+    void *msgU = NULL;
 
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, %p, 0x%08x, %p)\n",
-           ld, debugstr_w(base), scope, debugstr_w(filter), attrs, attrsonly,
-           serverctrls, clientctrls, timeout, sizelimit, res );
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p, %p, 0x%08x, %p)\n", ld, debugstr_w(base), scope,
+           debugstr_w(filter), attrs, attrsonly, serverctrls, clientctrls, timeout, sizelimit, res );
 
     if (!ld || !res) return WLDAP32_LDAP_PARAM_ERROR;
 
-    if (base) {
-        baseU = strWtoU( base );
-        if (!baseU) goto exit;
-    }
-    if (filter) {
-        filterU = strWtoU( filter );
-        if (!filterU) goto exit;
-    }
-    if (attrs) {
-        attrsU = strarrayWtoU( attrs );
-        if (!attrsU) goto exit;
-    }
-    if (serverctrls) {
-        serverctrlsU = controlarrayWtoU( serverctrls );
-        if (!serverctrlsU) goto exit;
-    }
-    if (clientctrls) {
-        clientctrlsU = controlarrayWtoU( clientctrls );
-        if (!clientctrlsU) goto exit;
+    if (base && !(baseU = strWtoU( base ))) goto exit;
+    if (filter && !(filterU = strWtoU( filter ))) goto exit;
+    if (attrs && !(attrsU = strarrayWtoU( attrs ))) goto exit;
+    if (serverctrls && !(serverctrlsU = controlarrayWtoU( serverctrls ))) goto exit;
+    if (clientctrls && !(clientctrlsU = controlarrayWtoU( clientctrls ))) goto exit;
+
+    if (timeout)
+    {
+        timevalU.tv_sec = timeout->tv_sec;
+        timevalU.tv_usec = timeout->tv_usec;
     }
 
-    ret = map_error( ldap_search_ext_s( ld->ld, baseU, scope, filterU, attrsU, attrsonly,
-                                        serverctrlsU, clientctrlsU, (struct timeval *)timeout,
-                                        sizelimit, res ));
+    ret = map_error( ldap_funcs->ldap_search_ext_s( ld->ld, baseU, scope, filterU, attrsU, attrsonly, serverctrlsU,
+                                                    clientctrlsU, timeout ? &timevalU : NULL, sizelimit, &msgU ) );
+    if (msgU)
+    {
+        WLDAP32_LDAPMessage *msg = heap_alloc_zero( sizeof(*msg) );
+        if (msg)
+        {
+            msg->Request = msgU;
+            *res = msg;
+        }
+        else
+        {
+            ldap_funcs->ldap_msgfree( msgU );
+            ret = WLDAP32_LDAP_NO_MEMORY;
+        }
+    }
 
 exit:
     strfreeU( baseU );
@@ -426,8 +299,6 @@ exit:
     strarrayfreeU( attrsU );
     controlarrayfreeU( serverctrlsU );
     controlarrayfreeU( clientctrlsU );
-
-#endif
     return ret;
 }
 
@@ -436,32 +307,20 @@ exit:
  *
  * See ldap_search_sW.
  */
-ULONG CDECL ldap_search_sA( WLDAP32_LDAP *ld, PCHAR base, ULONG scope, PCHAR filter,
-    PCHAR attrs[], ULONG attrsonly, WLDAP32_LDAPMessage **res )
+ULONG CDECL ldap_search_sA( WLDAP32_LDAP *ld, char *base, ULONG scope, char *filter, char **attrs, ULONG attrsonly,
+    WLDAP32_LDAPMessage **res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    ULONG ret = WLDAP32_LDAP_NO_MEMORY;
     WCHAR *baseW = NULL, *filterW = NULL, **attrsW = NULL;
 
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p)\n", ld, debugstr_a(base),
-           scope, debugstr_a(filter), attrs, attrsonly, res );
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p)\n", ld, debugstr_a(base), scope, debugstr_a(filter), attrs,
+           attrsonly, res );
 
     if (!ld || !res) return WLDAP32_LDAP_PARAM_ERROR;
 
-    if (base) {
-        baseW = strAtoW( base );
-        if (!baseW) goto exit;
-    }
-    if (filter) {
-        filterW = strAtoW( filter );
-        if (!filterW) goto exit;
-    }
-    if (attrs) {
-        attrsW = strarrayAtoW( attrs );
-        if (!attrsW) goto exit;
-    }
+    if (base && !(baseW = strAtoW( base ))) goto exit;
+    if (filter && !(filterW = strAtoW( filter ))) goto exit;
+    if (attrs && !(attrsW = strarrayAtoW( attrs ))) goto exit;
 
     ret = ldap_search_sW( ld, baseW, scope, filterW, attrsW, attrsonly, res );
 
@@ -469,8 +328,6 @@ exit:
     strfreeW( baseW );
     strfreeW( filterW );
     strarrayfreeW( attrsW );
-
-#endif
     return ret;
 }
 
@@ -496,43 +353,12 @@ exit:
  * NOTES
  *  Call ldap_msgfree to free the results.
  */
-ULONG CDECL ldap_search_sW( WLDAP32_LDAP *ld, PWCHAR base, ULONG scope, PWCHAR filter,
-    PWCHAR attrs[], ULONG attrsonly, WLDAP32_LDAPMessage **res )
+ULONG CDECL ldap_search_sW( WLDAP32_LDAP *ld, WCHAR *base, ULONG scope, WCHAR *filter, WCHAR **attrs, ULONG attrsonly,
+    WLDAP32_LDAPMessage **res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
-    char *baseU = NULL, *filterU = NULL, **attrsU = NULL;
-
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p)\n", ld, debugstr_w(base),
-           scope, debugstr_w(filter), attrs, attrsonly, res );
-
-    if (!ld || !res) return WLDAP32_LDAP_PARAM_ERROR;
-
-    if (base) {
-        baseU = strWtoU( base );
-        if (!baseU) goto exit;
-    }
-    if (filter) {
-        filterU = strWtoU( filter );
-        if (!filterU) goto exit;
-    }
-    if (attrs) {
-        attrsU = strarrayWtoU( attrs );
-        if (!attrsU) goto exit;
-    }
-
-    ret = map_error( ldap_search_ext_s( ld->ld, baseU, scope, filterU, attrsU, attrsonly,
-                                        NULL, NULL, NULL, 0, res ));
-
-exit:
-    strfreeU( baseU );
-    strfreeU( filterU );
-    strarrayfreeU( attrsU );
-
-#endif
-    return ret;
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p)\n", ld, debugstr_w(base), scope, debugstr_w(filter), attrs,
+           attrsonly, res );
+    return ldap_search_ext_sW( ld, base, scope, filter, attrs, attrsonly, NULL, NULL, NULL, 0, res );
 }
 
 /***********************************************************************
@@ -540,44 +366,27 @@ exit:
  *
  * See ldap_search_stW.
  */
-ULONG CDECL ldap_search_stA( WLDAP32_LDAP *ld, const PCHAR base, ULONG scope,
-    const PCHAR filter, PCHAR attrs[], ULONG attrsonly,
-    struct l_timeval *timeout, WLDAP32_LDAPMessage **res )
+ULONG CDECL ldap_search_stA( WLDAP32_LDAP *ld, const PCHAR base, ULONG scope, const PCHAR filter, char **attrs,
+    ULONG attrsonly, struct l_timeval *timeout, WLDAP32_LDAPMessage **res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
+    ULONG ret = WLDAP32_LDAP_NO_MEMORY;
     WCHAR *baseW = NULL, *filterW = NULL, **attrsW = NULL;
 
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p)\n", ld,
-           debugstr_a(base), scope, debugstr_a(filter), attrs,
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p)\n", ld, debugstr_a(base), scope, debugstr_a(filter), attrs,
            attrsonly, timeout, res );
 
     if (!ld || !res) return WLDAP32_LDAP_PARAM_ERROR;
 
-    if (base) {
-        baseW = strAtoW( base );
-        if (!baseW) goto exit;
-    }
-    if (filter) {
-        filterW = strAtoW( filter );
-        if (!filterW) goto exit;
-    }
-    if (attrs) {
-        attrsW = strarrayAtoW( attrs );
-        if (!attrsW) goto exit;
-    }
+    if (base && !(baseW = strAtoW( base ))) goto exit;
+    if (filter && !(filterW = strAtoW( filter ))) goto exit;
+    if (attrs && !(attrsW = strarrayAtoW( attrs ))) goto exit;
 
-    ret = ldap_search_stW( ld, baseW, scope, filterW, attrsW, attrsonly,
-                           timeout, res );
+    ret = ldap_search_stW( ld, baseW, scope, filterW, attrsW, attrsonly, timeout, res );
 
 exit:
     strfreeW( baseW );
     strfreeW( filterW );
     strarrayfreeW( attrsW );
-
-#endif
     return ret;
 }
 
@@ -604,43 +413,10 @@ exit:
  * NOTES
  *  Call ldap_msgfree to free the results.
  */
-ULONG CDECL ldap_search_stW( WLDAP32_LDAP *ld, const PWCHAR base, ULONG scope,
-    const PWCHAR filter, PWCHAR attrs[], ULONG attrsonly,
-    struct l_timeval *timeout, WLDAP32_LDAPMessage **res )
+ULONG CDECL ldap_search_stW( WLDAP32_LDAP *ld, const PWCHAR base, ULONG scope, const PWCHAR filter, WCHAR **attrs,
+    ULONG attrsonly, struct l_timeval *timeout, WLDAP32_LDAPMessage **res )
 {
-    ULONG ret = WLDAP32_LDAP_NOT_SUPPORTED;
-#ifdef HAVE_LDAP
-    char *baseU = NULL, *filterU = NULL, **attrsU = NULL;
-
-    ret = WLDAP32_LDAP_NO_MEMORY;
-
-    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p)\n", ld,
-           debugstr_w(base), scope, debugstr_w(filter), attrs,
+    TRACE( "(%p, %s, 0x%08x, %s, %p, 0x%08x, %p, %p)\n", ld, debugstr_w(base), scope, debugstr_w(filter), attrs,
            attrsonly, timeout, res );
-
-    if (!ld || !res) return WLDAP32_LDAP_PARAM_ERROR;
-
-    if (base) {
-        baseU = strWtoU( base );
-        if (!baseU) goto exit;
-    }
-    if (filter) {
-        filterU = strWtoU( filter );
-        if (!filterU) goto exit;
-    }
-    if (attrs) {
-        attrsU = strarrayWtoU( attrs );
-        if (!attrsU) goto exit;
-    }
-
-    ret = map_error( ldap_search_ext_s( ld->ld, baseU, scope, filterU, attrsU, attrsonly,
-                                        NULL, NULL, (struct timeval *)timeout, 0, res ));
-
-exit:
-    strfreeU( baseU );
-    strfreeU( filterU );
-    strarrayfreeU( attrsU );
-
-#endif
-    return ret;
+    return ldap_search_ext_sW( ld, base, scope, filter, attrs, attrsonly, NULL, NULL, timeout, 0, res );
 }
diff --git a/dlls/wldap32/value.c b/dlls/wldap32/value.c
index ff13289b309..a7d7d44244f 100644
--- a/dlls/wldap32/value.c
+++ b/dlls/wldap32/value.c
@@ -228,7 +228,7 @@ PWCHAR * CDECL ldap_get_valuesW( WLDAP32_LDAP *ld, WLDAP32_LDAPMessage *entry, P
     attrU = strWtoU( attr );
     if (!attrU) return NULL;
 
-    bv = ldap_get_values_len( ld->ld, entry, attrU );
+    bv = ldap_get_values_len( ld->ld, entry->Request, attrU );
     if (bv)
     {
         retU = bv2str_array( bv );
@@ -305,7 +305,7 @@ struct WLDAP32_berval ** CDECL ldap_get_values_lenW( WLDAP32_LDAP *ld,
     attrU = strWtoU( attr );
     if (!attrU) return NULL;
 
-    ret = ldap_get_values_len( ld->ld, message, attrU );
+    ret = ldap_get_values_len( ld->ld, message->Request, attrU );
 
     strfreeU( attrU );
     return (struct WLDAP32_berval **)ret;
-- 
2.30.2




More information about the wine-devel mailing list