[prev in list] [next in list] [prev in thread] [next in thread] 

List:       wine-devel
Subject:    Patch for [Bug 14222] RpcBindingSetAuthInfo(Ex) fails with
From:       Stefan Kuhr <winesku () googlemail ! com>
Date:       2009-09-28 17:56:34
Message-ID: 81a474f0909281056i59c3dfcu427a7bc42c71cf83 () mail ! gmail ! com
[Download RAW message or body]

Hello everyone,

please find attached a patch for Bug 14222. IIRC I sent a similar
patch a year ago or so and never received feedback why it was
rejected. Austin encouraged me to send it again, so please if it is
unacceptable, let me know why.


The patch will make RPC clients work that are written for Windows 2000
(and later), where the negotiate provider performs an automatic
fallback to NTLM, if Kerberos is not possible, both in workgroup and
domain scenarios. Currently, Wine doesn't have a negotiate and a
Kerberos provider. This patch allows clients requesting Negotiate to
get the NTLM provider and will still work, even if one day negotiate
and Kerberos providers will be added to Wine.

Cheers,

-- 
Stefan

["0001-Fallback-from-negotiate-to-ntlm-if-no-negotiate-prov.patch" (application/octet-stream)]

From dec025c21523c88dcfdd98549697d6067f74b83e Mon Sep 17 00:00:00 2001
From: Stefan Kuhr <winesku@googlemail.com>
Date: Mon, 28 Sep 2009 19:26:21 +0200
Subject: Fallback from negotiate to ntlm if no negotiate provider is present

---
 dlls/rpcrt4/rpc_binding.c |   66 +++++++++++++++++++++++++++++++++++---------
 1 files changed, 52 insertions(+), 14 deletions(-)

diff --git a/dlls/rpcrt4/rpc_binding.c b/dlls/rpcrt4/rpc_binding.c
index 29e0709..cc3cf41 100644
--- a/dlls/rpcrt4/rpc_binding.c
+++ b/dlls/rpcrt4/rpc_binding.c
@@ -1563,13 +1563,6 @@ RpcBindingSetAuthInfoExA( RPC_BINDING_HANDLE Binding, RPC_CSTR ServerPrincName,
     return RPC_S_UNKNOWN_AUTHN_LEVEL;
   }
 
-  /* RPC_C_AUTHN_WINNT ignores the AuthzSvr parameter */
-  if (AuthzSvr && AuthnSvc != RPC_C_AUTHN_WINNT)
-  {
-    FIXME("unsupported AuthzSvr %u\n", AuthzSvr);
-    return RPC_S_UNKNOWN_AUTHZ_SERVICE;
-  }
-
   r = EnumerateSecurityPackagesA(&package_count, &packages);
   if (r != SEC_E_OK)
   {
@@ -1581,6 +1574,23 @@ RpcBindingSetAuthInfoExA( RPC_BINDING_HANDLE Binding, RPC_CSTR ServerPrincName,
     if (packages[i].wRPCID == AuthnSvc)
         break;
 
+  /* FIXME: A negotiate provider should be implemented */
+
+  if (i == package_count && RPC_C_AUTHN_GSS_NEGOTIATE==AuthnSvc)
+  {
+    /* If the caller requested RPC_C_AUTHN_GSS_NEGOTIATE and we only can offer
+    RPC_C_AUTHN_WINNT, we should allow the caller to use RPC_C_AUTHN_WINNT.
+    After all, the caller specified that NTLM would be sufficient, so if 
+    we have NTLM, we give it to the caller: */
+
+    for (i = 0; i < package_count; i++)
+      if (packages[i].wRPCID == RPC_C_AUTHN_WINNT)
+      {
+        AuthnSvc = RPC_C_AUTHN_WINNT;
+        break;
+      }
+  }
+
   if (i == package_count)
   {
     FIXME("unsupported AuthnSvc %u\n", AuthnSvc);
@@ -1588,6 +1598,16 @@ RpcBindingSetAuthInfoExA( RPC_BINDING_HANDLE Binding, RPC_CSTR ServerPrincName,
     return RPC_S_UNKNOWN_AUTHN_SERVICE;
   }
 
+  /* RPC_C_AUTHN_WINNT ignores the AuthzSvr parameter */
+  if (AuthzSvr && AuthnSvc != RPC_C_AUTHN_WINNT)
+  {
+    FIXME("unsupported AuthzSvr %u\n", AuthzSvr);
+    FreeContextBuffer(packages);
+    return RPC_S_UNKNOWN_AUTHZ_SERVICE;
+  }
+
+
+
   TRACE("found package %s for service %u\n", packages[i].Name, AuthnSvc);
   r = AcquireCredentialsHandleA(NULL, packages[i].Name, SECPKG_CRED_OUTBOUND, NULL,
                                 AuthIdentity, NULL, NULL, &cred, &exp);
@@ -1693,13 +1713,6 @@ RpcBindingSetAuthInfoExW( RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName,
     return RPC_S_UNKNOWN_AUTHN_LEVEL;
   }
 
-  /* RPC_C_AUTHN_WINNT ignores the AuthzSvr parameter */
-  if (AuthzSvr && AuthnSvc != RPC_C_AUTHN_WINNT)
-  {
-    FIXME("unsupported AuthzSvr %u\n", AuthzSvr);
-    return RPC_S_UNKNOWN_AUTHZ_SERVICE;
-  }
-
   r = EnumerateSecurityPackagesW(&package_count, &packages);
   if (r != SEC_E_OK)
   {
@@ -1711,6 +1724,23 @@ RpcBindingSetAuthInfoExW( RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName,
     if (packages[i].wRPCID == AuthnSvc)
         break;
 
+  /* FIXME: A negotiate provider should be implemented */
+
+  if (i == package_count && RPC_C_AUTHN_GSS_NEGOTIATE==AuthnSvc)
+  {
+    /* If the caller requested RPC_C_AUTHN_GSS_NEGOTIATE and we only can offer
+    RPC_C_AUTHN_WINNT, we should allow the caller to use RPC_C_AUTHN_WINNT.
+    After all, the caller specified that NTLM would be sufficient, so if 
+    we have NTLM, we give it to the caller: */
+
+    for (i = 0; i < package_count; i++)
+      if (packages[i].wRPCID == RPC_C_AUTHN_WINNT)
+      {
+        AuthnSvc = RPC_C_AUTHN_WINNT;
+        break;
+      }
+  }
+
   if (i == package_count)
   {
     FIXME("unsupported AuthnSvc %u\n", AuthnSvc);
@@ -1718,6 +1748,14 @@ RpcBindingSetAuthInfoExW( RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName,
     return RPC_S_UNKNOWN_AUTHN_SERVICE;
   }
 
+  /* RPC_C_AUTHN_WINNT ignores the AuthzSvr parameter */
+  if (AuthzSvr && AuthnSvc != RPC_C_AUTHN_WINNT)
+  {
+    FIXME("unsupported AuthzSvr %u\n", AuthzSvr);
+    FreeContextBuffer(packages);
+    return RPC_S_UNKNOWN_AUTHZ_SERVICE;
+  }
+
   TRACE("found package %s for service %u\n", debugstr_w(packages[i].Name), AuthnSvc);
   r = AcquireCredentialsHandleW(NULL, packages[i].Name, SECPKG_CRED_OUTBOUND, NULL,
                                 AuthIdentity, NULL, NULL, &cred, &exp);
-- 
1.5.4.3





[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic