00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "includes.h"
00024
00025 #ifdef HAVE_LDAP
00026
00027
00028
00029
00030 static ADS_STATUS ads_do_search_retry_internal(ADS_STRUCT *ads, const char *bind_path, int scope,
00031 const char *expr,
00032 const char **attrs, void *args,
00033 LDAPMessage **res)
00034 {
00035 ADS_STATUS status = ADS_SUCCESS;
00036 int count = 3;
00037 char *bp;
00038
00039 *res = NULL;
00040
00041 if (!ads->ld &&
00042 time(NULL) - ads->last_attempt < ADS_RECONNECT_TIME) {
00043 return ADS_ERROR(LDAP_SERVER_DOWN);
00044 }
00045
00046 bp = SMB_STRDUP(bind_path);
00047
00048 if (!bp) {
00049 return ADS_ERROR_NT(NT_STATUS_NO_MEMORY);
00050 }
00051
00052 *res = NULL;
00053
00054
00055
00056
00057 if (ads->auth.flags & ADS_AUTH_ANON_BIND) {
00058 status = ads_do_search(ads, bp, scope, expr, attrs, res);
00059 } else {
00060 status = ads_do_search_all_args(ads, bp, scope, expr, attrs, args, res);
00061 }
00062 if (ADS_ERR_OK(status)) {
00063 DEBUG(5,("Search for %s in <%s> gave %d replies\n",
00064 expr, bp, ads_count_replies(ads, *res)));
00065 SAFE_FREE(bp);
00066 return status;
00067 }
00068
00069 while (--count) {
00070
00071 if (*res)
00072 ads_msgfree(ads, *res);
00073 *res = NULL;
00074
00075 DEBUG(3,("Reopening ads connection to realm '%s' after error %s\n",
00076 ads->config.realm, ads_errstr(status)));
00077
00078 if (ads->ld) {
00079 ldap_unbind(ads->ld);
00080 }
00081
00082 ads->ld = NULL;
00083 status = ads_connect(ads);
00084
00085 if (!ADS_ERR_OK(status)) {
00086 DEBUG(1,("ads_search_retry: failed to reconnect (%s)\n",
00087 ads_errstr(status)));
00088 ads_destroy(&ads);
00089 SAFE_FREE(bp);
00090 return status;
00091 }
00092
00093 *res = NULL;
00094
00095
00096
00097
00098 if (ads->auth.flags & ADS_AUTH_ANON_BIND) {
00099 status = ads_do_search(ads, bp, scope, expr, attrs, res);
00100 } else {
00101 status = ads_do_search_all_args(ads, bp, scope, expr, attrs, args, res);
00102 }
00103
00104 if (ADS_ERR_OK(status)) {
00105 DEBUG(5,("Search for filter: %s, base: %s gave %d replies\n",
00106 expr, bp, ads_count_replies(ads, *res)));
00107 SAFE_FREE(bp);
00108 return status;
00109 }
00110 }
00111 SAFE_FREE(bp);
00112
00113 if (!ADS_ERR_OK(status)) {
00114 DEBUG(1,("ads reopen failed after error %s\n",
00115 ads_errstr(status)));
00116 }
00117 return status;
00118 }
00119
00120 ADS_STATUS ads_do_search_retry(ADS_STRUCT *ads, const char *bind_path,
00121 int scope, const char *expr,
00122 const char **attrs, LDAPMessage **res)
00123 {
00124 return ads_do_search_retry_internal(ads, bind_path, scope, expr, attrs, NULL, res);
00125 }
00126
00127 ADS_STATUS ads_do_search_retry_args(ADS_STRUCT *ads, const char *bind_path,
00128 int scope, const char *expr,
00129 const char **attrs, void *args,
00130 LDAPMessage **res)
00131 {
00132 return ads_do_search_retry_internal(ads, bind_path, scope, expr, attrs, args, res);
00133 }
00134
00135
00136 ADS_STATUS ads_search_retry(ADS_STRUCT *ads, LDAPMessage **res,
00137 const char *expr, const char **attrs)
00138 {
00139 return ads_do_search_retry(ads, ads->config.bind_path, LDAP_SCOPE_SUBTREE,
00140 expr, attrs, res);
00141 }
00142
00143 ADS_STATUS ads_search_retry_dn(ADS_STRUCT *ads, LDAPMessage **res,
00144 const char *dn,
00145 const char **attrs)
00146 {
00147 return ads_do_search_retry(ads, dn, LDAP_SCOPE_BASE,
00148 "(objectclass=*)", attrs, res);
00149 }
00150
00151 ADS_STATUS ads_search_retry_extended_dn(ADS_STRUCT *ads, LDAPMessage **res,
00152 const char *dn,
00153 const char **attrs,
00154 enum ads_extended_dn_flags flags)
00155 {
00156 ads_control args;
00157
00158 args.control = ADS_EXTENDED_DN_OID;
00159 args.val = flags;
00160 args.critical = True;
00161
00162 return ads_do_search_retry_args(ads, dn, LDAP_SCOPE_BASE,
00163 "(objectclass=*)", attrs, &args, res);
00164 }
00165
00166 ADS_STATUS ads_search_retry_sid(ADS_STRUCT *ads, LDAPMessage **res,
00167 const DOM_SID *sid,
00168 const char **attrs)
00169 {
00170 char *dn, *sid_string;
00171 ADS_STATUS status;
00172
00173 sid_string = sid_binstring_hex(sid);
00174 if (sid_string == NULL) {
00175 return ADS_ERROR(LDAP_NO_MEMORY);
00176 }
00177
00178 if (!asprintf(&dn, "<SID=%s>", sid_string)) {
00179 SAFE_FREE(sid_string);
00180 return ADS_ERROR(LDAP_NO_MEMORY);
00181 }
00182
00183 status = ads_do_search_retry(ads, dn, LDAP_SCOPE_BASE,
00184 "(objectclass=*)", attrs, res);
00185 SAFE_FREE(dn);
00186 SAFE_FREE(sid_string);
00187 return status;
00188 }
00189
00190 #endif