Rob Shearman : ntdsapi: Implement DsMakeSpnW.

Alexandre Julliard julliard at winehq.org
Fri Jan 25 07:06:08 CST 2008


Module: wine
Branch: master
Commit: dbcac92819ef905d4bb5d44cbd8ea2542c64da2f
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=dbcac92819ef905d4bb5d44cbd8ea2542c64da2f

Author: Rob Shearman <rob at codeweavers.com>
Date:   Thu Jan 24 18:37:10 2008 +0000

ntdsapi: Implement DsMakeSpnW.

---

 dlls/ntdsapi/Makefile.in     |    2 +-
 dlls/ntdsapi/ntdsapi.c       |   80 ++++++++++++++++++++++++++++++++++++++++-
 dlls/ntdsapi/tests/ntdsapi.c |   12 ------
 3 files changed, 79 insertions(+), 15 deletions(-)

diff --git a/dlls/ntdsapi/Makefile.in b/dlls/ntdsapi/Makefile.in
index 0d9e955..2649a36 100644
--- a/dlls/ntdsapi/Makefile.in
+++ b/dlls/ntdsapi/Makefile.in
@@ -4,7 +4,7 @@ SRCDIR    = @srcdir@
 VPATH     = @srcdir@
 MODULE    = ntdsapi.dll
 IMPORTLIB = libntdsapi.$(IMPLIBEXT)
-IMPORTS   = kernel32
+IMPORTS   = user32 kernel32
 
 C_SRCS = \
 	ntdsapi.c
diff --git a/dlls/ntdsapi/ntdsapi.c b/dlls/ntdsapi/ntdsapi.c
index f8fd98c..bad284c 100644
--- a/dlls/ntdsapi/ntdsapi.c
+++ b/dlls/ntdsapi/ntdsapi.c
@@ -21,8 +21,10 @@
 #include "windef.h"
 #include "winbase.h"
 #include "winerror.h"
+#include "winuser.h"
 #include "ntdsapi.h"
 #include "wine/debug.h"
+#include "wine/unicode.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(ntdsapi);
 
@@ -52,11 +54,85 @@ DWORD WINAPI DsMakeSpnW(LPCWSTR svc_class, LPCWSTR svc_name,
                         LPCWSTR inst_name, USHORT inst_port,
                         LPCWSTR ref, DWORD *spn_length, LPWSTR spn)
 {
-    FIXME("(%s,%s,%s,%d,%s,%p,%p): stub!\n", debugstr_w(svc_class),
+    DWORD new_spn_length;
+    INT len;
+    LPWSTR p;
+
+    TRACE("(%s,%s,%s,%d,%s,%p,%p)\n", debugstr_w(svc_class),
             debugstr_w(svc_name), debugstr_w(inst_name), inst_port,
             debugstr_w(ref), spn_length, spn);
 
-    return ERROR_CALL_NOT_IMPLEMENTED;
+    if (!svc_class || !svc_name)
+        return ERROR_INVALID_PARAMETER;
+
+    new_spn_length = strlenW(svc_class) + 1 /* for '/' */ + 1 /* for terminating '\0' */;
+    if (inst_name)
+        new_spn_length += strlenW(inst_name);
+    else
+        new_spn_length += strlenW(svc_name);
+    if (inst_port)
+    {
+        USHORT n = inst_port;
+        new_spn_length += 1 /* for ':' */;
+        do
+        {
+            n /= 10;
+            new_spn_length++;
+        } while (n != 0);
+    }
+    if (inst_name)
+        new_spn_length += 1 /* for '/' */ + strlenW(svc_name);
+
+    if (*spn_length < new_spn_length)
+    {
+        *spn_length = new_spn_length;
+        return ERROR_BUFFER_OVERFLOW;
+    }
+    *spn_length = new_spn_length;
+
+    p = spn;
+    len = strlenW(svc_class);
+    memcpy(p, svc_class, len * sizeof(WCHAR));
+    p += len;
+    *p = '/';
+    p++;
+    if (inst_name)
+    {
+        len = strlenW(inst_name);
+        memcpy(p, inst_name, len * sizeof(WCHAR));
+        p += len;
+        *p = '\0';
+    }
+    else
+    {
+        len = strlenW(svc_name);
+        memcpy(p, svc_name, len * sizeof(WCHAR));
+        p += len;
+        *p = '\0';
+    }
+
+    if (inst_port)
+    {
+        static const WCHAR percentU[] = {'%','u',0};
+        *p = ':';
+        p++;
+        wsprintfW(p, percentU, inst_port);
+        p += strlenW(p);
+    }
+
+    if (inst_name)
+    {
+        *p = '/';
+        p++;
+        len = strlenW(svc_name);
+        memcpy(p, svc_name, len * sizeof(WCHAR));
+        p += len;
+        *p = '\0';
+    }
+
+    TRACE("spn = %s\n", debugstr_w(spn));
+
+    return ERROR_SUCCESS;
 }
 
 DWORD WINAPI DsMakeSpnA(LPCSTR svc_class, LPCSTR svc_name,
diff --git a/dlls/ntdsapi/tests/ntdsapi.c b/dlls/ntdsapi/tests/ntdsapi.c
index 70cbe3e..ac5dd19 100644
--- a/dlls/ntdsapi/tests/ntdsapi.c
+++ b/dlls/ntdsapi/tests/ntdsapi.c
@@ -54,53 +54,41 @@ static void test_DsMakeSpn(void)
 
     spn_length = sizeof(spn)/sizeof(spn[0]);
     ret = DsMakeSpnW(NULL, NULL, NULL, 0, NULL, &spn_length, spn);
-    todo_wine
     ok(ret == ERROR_INVALID_PARAMETER, "DsMakeSpnW should have failed with ERROR_INVALID_PARAMETER instead of %d\n", ret);
 
     spn_length = sizeof(spn)/sizeof(spn[0]);
     ret = DsMakeSpnW(NULL, wszServiceHost, NULL, 0, NULL, &spn_length, spn);
-    todo_wine
     ok(ret == ERROR_INVALID_PARAMETER, "DsMakeSpnW should have failed with ERROR_INVALID_PARAMETER instead of %d\n", ret);
 
     spn_length = sizeof(spn)/sizeof(spn[0]);
     ret = DsMakeSpnW(wszServiceClass, wszServiceHost, NULL, 0, NULL, &spn_length, spn);
-    todo_wine {
     ok(ret == ERROR_SUCCESS, "DsMakeSpnW should have succeeded instead of failing with %d\n", ret);
     ok(!lstrcmpW(spn, wszSpn1), "DsMakeSpnW returned unexpected SPN %s\n", wine_dbgstr_w(spn));
     ok(spn_length == lstrlenW(wszSpn1) + 1, "DsMakeSpnW should have returned spn_length of %d instead of %d\n", lstrlenW(wszSpn1) + 1, spn_length);
-    }
 
     spn_length = sizeof(spn)/sizeof(spn[0]);
     ret = DsMakeSpnW(wszServiceClass, wszServiceHost, wszInstanceName, 0, NULL, &spn_length, spn);
-    todo_wine {
     ok(ret == ERROR_SUCCESS, "DsMakeSpnW should have succeeded instead of failing with %d\n", ret);
     ok(!lstrcmpW(spn, wszSpn2), "DsMakeSpnW returned unexpected SPN %s\n", wine_dbgstr_w(spn));
     ok(spn_length == lstrlenW(wszSpn2) + 1, "DsMakeSpnW should have returned spn_length of %d instead of %d\n", lstrlenW(wszSpn2) + 1, spn_length);
-    }
 
     spn_length = sizeof(spn)/sizeof(spn[0]);
     ret = DsMakeSpnW(wszServiceClass, wszServiceHost, wszInstanceName, 555, NULL, &spn_length, spn);
-    todo_wine {
     ok(ret == ERROR_SUCCESS, "DsMakeSpnW should have succeeded instead of failing with %d\n", ret);
     ok(!lstrcmpW(spn, wszSpn3), "DsMakeSpnW returned unexpected SPN %s\n", wine_dbgstr_w(spn));
     ok(spn_length == lstrlenW(wszSpn3) + 1, "DsMakeSpnW should have returned spn_length of %d instead of %d\n", lstrlenW(wszSpn3) + 1, spn_length);
-    }
 
     spn_length = sizeof(spn)/sizeof(spn[0]);
     ret = DsMakeSpnW(wszServiceClass, wszServiceHost, wszInstanceName, 555, wszReferrer, &spn_length, spn);
-    todo_wine {
     ok(ret == ERROR_SUCCESS, "DsMakeSpnW should have succeeded instead of failing with %d\n", ret);
     ok(!lstrcmpW(spn, wszSpn4), "DsMakeSpnW returned unexpected SPN %s\n", wine_dbgstr_w(spn));
     ok(spn_length == lstrlenW(wszSpn4) + 1, "DsMakeSpnW should have returned spn_length of %d instead of %d\n", lstrlenW(wszSpn4) + 1, spn_length);
-    }
 
     spn_length = sizeof(spn)/sizeof(spn[0]);
     ret = DsMakeSpnW(wszServiceClass, wszServiceHost, NULL, 555, wszReferrer, &spn_length, spn);
-    todo_wine {
     ok(ret == ERROR_SUCCESS, "DsMakeSpnW should have succeeded instead of failing with %d\n", ret);
     ok(!lstrcmpW(spn, wszSpn5), "DsMakeSpnW returned unexpected SPN %s\n", wine_dbgstr_w(spn));
     ok(spn_length == lstrlenW(wszSpn5) + 1, "DsMakeSpnW should have returned spn_length of %d instead of %d\n", lstrlenW(wszSpn5) + 1, spn_length);
-    }
 }
 
 START_TEST( ntdsapi )




More information about the wine-cvs mailing list