From 2c54ae82a49f6df7f7c76d333d3fe00a0b1cff28 Mon Sep 17 00:00:00 2001 From: Jeffrey Altman Date: Fri, 18 Sep 2009 10:41:14 -0400 Subject: [PATCH] Windows: Improve WKSSRC and SRVSVC compatibility with Windows This commit includes several changes to improve compatibility with Windows (in particular Windows 2000). 1. Specify a Lan Workgroup name. We use "AFS". 2. Ensure that the server name returned does not include leading slash or backslash characters. The name provided might include them but they are not part of the name and cannot be returned. 3. The NetrWkstaGetInfo and NetrServerGetInfo responses must be consistent. Otherwise, the Explorer Shell will get confused and refuse to provide access to the server shares. This commit also includes some minor comment changes. LICENSE MIT Reviewed-on: http://gerrit.openafs.org/466 Tested-by: Asanka Herath Reviewed-by: Asanka Herath Tested-by: Jeffrey Altman Reviewed-by: Jeffrey Altman --- src/WINNT/afsd/rpc_srvsvc.c | 28 +++++++++++++++++++--------- src/WINNT/afsd/rpc_wkssvc.c | 23 ++++++++++++++++------- 2 files changed, 35 insertions(+), 16 deletions(-) diff --git a/src/WINNT/afsd/rpc_srvsvc.c b/src/WINNT/afsd/rpc_srvsvc.c index d59e8ae..0e3d0e4 100644 --- a/src/WINNT/afsd/rpc_srvsvc.c +++ b/src/WINNT/afsd/rpc_srvsvc.c @@ -31,6 +31,7 @@ #include "ms-srvsvc.h" #include "msrpc.h" #include "afsd.h" +#include "smb.h" #include #define AFS_VERSION_STRINGS #include "AFS_component_version_number.h" @@ -305,10 +306,11 @@ NetrIntGenerateSharePath(wchar_t *ServerName, cm_fid_t *fidp) else wcellname = L""; + for ( s=ServerName; *s == '\\' || *s == '/'; s++); hr = StringCchPrintfW( remark, sizeof(remark)/sizeof(remark[0]), - L"\\%s\\%s\\%u.%u.%u", - ServerName, wcellname, + L"\\\\%s\\%s\\%u.%u.%u", + s, wcellname, fidp->volume, fidp->vnode, fidp->unique); if (hr == S_OK) @@ -927,13 +929,15 @@ NET_API_STATUS NetrServerGetInfo( /* [in] */ DWORD Level, /* [switch_is][out] */ LPSERVER_INFO InfoStruct) { + wchar_t *s; + osi_Log1(afsd_logp, "NetrServerGetInfo level %u", Level); /* - * How much space do we need and do we have that much room? - * For now, just assume we can return everything in one shot - * because the reality is that in this function call we do - * not know the max size of the RPC response. - */ + * How much space do we need and do we have that much room? + * For now, just assume we can return everything in one shot + * because the reality is that in this function call we do + * not know the max size of the RPC response. + */ switch (Level) { case 103: InfoStruct->ServerInfo103 = calloc(1, sizeof(SERVER_INFO_103)); @@ -953,6 +957,12 @@ NET_API_STATUS NetrServerGetInfo( return ERROR_NOT_ENOUGH_MEMORY; } + /* + * Remove any leading slashes since they are not part of the + * server name. + */ + for ( s=ServerName; *s == '\\' || *s == '/'; s++); + switch (Level) { case 103: InfoStruct->ServerInfo103->sv103_capabilities = 0; @@ -969,13 +979,13 @@ NET_API_STATUS NetrServerGetInfo( case 101: InfoStruct->ServerInfo101->sv101_version_major = AFSPRODUCT_VERSION_MAJOR; InfoStruct->ServerInfo101->sv101_version_minor = AFSPRODUCT_VERSION_MINOR; - InfoStruct->ServerInfo101->sv101_type = SV_TYPE_SERVER_UNIX; + InfoStruct->ServerInfo101->sv101_type = SV_TYPE_WORKSTATION | SV_TYPE_SERVER | SV_TYPE_SERVER_UNIX; InfoStruct->ServerInfo101->sv101_comment = wcsdup(wAFSVersion); /* fall-through */ case 100: InfoStruct->ServerInfo100->sv100_platform_id = SV_PLATFORM_ID_AFS; /* The Netbios Name */ - InfoStruct->ServerInfo100->sv100_name = wcsdup(ServerName); + InfoStruct->ServerInfo100->sv100_name = _wcsupr(wcsdup(s)); return 0; case 502: case 503: diff --git a/src/WINNT/afsd/rpc_wkssvc.c b/src/WINNT/afsd/rpc_wkssvc.c index 7aca170..8438967 100644 --- a/src/WINNT/afsd/rpc_wkssvc.c +++ b/src/WINNT/afsd/rpc_wkssvc.c @@ -38,14 +38,16 @@ unsigned long NetrWkstaGetInfo( /* [in] */ unsigned long Level, /* [switch_is][out] */ LPWKSTA_INFO WkstaInfo) { + wchar_t *s; + osi_Log1(afsd_logp, "NetrWkstaGetInfo level %u", Level); /* - * How much space do we need and do we have that much room? - * For now, just assume we can return everything in one shot - * because the reality is that in this function call we do - * not know the max size of the RPC response. - */ + * How much space do we need and do we have that much room? + * For now, just assume we can return everything in one shot + * because the reality is that in this function call we do + * not know the max size of the RPC response. + */ switch (Level) { case 100: WkstaInfo->WkstaInfo100 = calloc(1, sizeof(WKSTA_INFO_100)); @@ -56,12 +58,19 @@ unsigned long NetrWkstaGetInfo( return ERROR_NOT_ENOUGH_MEMORY; } + /* + * Remove any leading slashes since they are not part of the + * server name. + */ + for ( s=ServerName; *s == '\\' || *s == '/'; s++); + switch (Level) { case 100: + WkstaInfo->WkstaInfo100->wki100_computername = _wcsupr(wcsdup(s)); + WkstaInfo->WkstaInfo100->wki100_langroup = _wcsdup(L"AFS"); WkstaInfo->WkstaInfo100->wki100_platform_id = PLATFORM_ID_AFS; - WkstaInfo->WkstaInfo100->wki100_computername = wcsdup(ServerName); WkstaInfo->WkstaInfo100->wki100_ver_major = AFSPRODUCT_VERSION_MAJOR; - WkstaInfo->WkstaInfo100->wki100_ver_major = AFSPRODUCT_VERSION_MINOR; + WkstaInfo->WkstaInfo100->wki100_ver_minor = AFSPRODUCT_VERSION_MINOR; return 0; case 502: case 1013: -- 1.9.4