/*
 * MPR WNet functions
 *
 * Copyright 1999 Ulrich Weigand
 * Copyright 2004 Juan Lang
 * Copyright 2007 Maarten Lankhorst
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

#include <stdarg.h>
#include "windef.h"
#include "winbase.h"
#include "winnls.h"
#include "winioctl.h"
#include "winnetwk.h"
#include "npapi.h"
#include "winreg.h"
#include "winuser.h"
#define WINE_MOUNTMGR_EXTENSIONS
#include "ddk/mountmgr.h"
#include "wine/debug.h"
#include "wine/unicode.h"
#include "mprres.h"
#include "wnetpriv.h"

WINE_DEFAULT_DEBUG_CHANNEL(mpr);

/* Data structures representing network service providers.  Assumes only one
 * thread creates them, and that they are constant for the life of the process
 * (and therefore doesn't synchronize access).
 * FIXME: only basic provider data and enumeration-related data are implemented
 * so far, need to implement the rest too.
 */
typedef struct _WNetProvider
{
    HMODULE           hLib;
    PWSTR             name;
    PF_NPGetCaps      getCaps;
    DWORD             dwSpecVersion;
    DWORD             dwNetType;
    DWORD             dwEnumScopes;
    PF_NPOpenEnum     openEnum;
    PF_NPEnumResource enumResource;
    PF_NPCloseEnum    closeEnum;
    PF_NPGetResourceInformation getResourceInformation;
    PF_NPAddConnection addConnection;
    PF_NPAddConnection3 addConnection3;
} WNetProvider, *PWNetProvider;

typedef struct _WNetProviderTable
{
    LPWSTR           entireNetwork;
    DWORD            numAllocated;
    DWORD            numProviders;
    WNetProvider     table[1];
} WNetProviderTable, *PWNetProviderTable;

#define WNET_ENUMERATOR_TYPE_NULL     0
#define WNET_ENUMERATOR_TYPE_GLOBAL   1
#define WNET_ENUMERATOR_TYPE_PROVIDER 2
#define WNET_ENUMERATOR_TYPE_CONTEXT  3

/* An WNet enumerator.  Note that the type doesn't correspond to the scope of
 * the enumeration; it represents one of the following types:
 * - a 'null' enumeration, one that contains no members
 * - a global enumeration, one that's executed across all providers
 * - a provider-specific enumeration, one that's only executed by a single
 *   provider
 * - a context enumeration.  I know this contradicts what I just said about
 *   there being no correspondence between the scope and the type, but it's
 *   necessary for the special case that a "Entire Network" entry needs to
 *   be enumerated in an enumeration of the context scope.  Thus an enumeration
 *   of the context scope results in a context type enumerator, which morphs
 *   into a global enumeration (so the enumeration continues across all
 *   providers).
 */
typedef struct _WNetEnumerator
{
    DWORD          enumType;
    DWORD          providerIndex;
    HANDLE         handle;
    BOOL           providerDone;
    DWORD          dwScope;
    DWORD          dwType;
    DWORD          dwUsage;
    LPNETRESOURCEW lpNet;
} WNetEnumerator, *PWNetEnumerator;

#define BAD_PROVIDER_INDEX (DWORD)0xffffffff

/* Returns an index (into the global WNetProviderTable) of the provider with
 * the given name, or BAD_PROVIDER_INDEX if not found.
 */
static DWORD _findProviderIndexW(LPCWSTR lpProvider);

static PWNetProviderTable providerTable;

/*
 * Global provider table functions
 */

static void _tryLoadProvider(PCWSTR provider)
{
    static const WCHAR servicePrefix[] = { 'S','y','s','t','e','m','\\',
     'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\',
     'S','e','r','v','i','c','e','s','\\',0 };
    static const WCHAR serviceFmt[] = { '%','s','%','s','\\',
     'N','e','t','w','o','r','k','P','r','o','v','i','d','e','r',0 };
    WCHAR serviceName[MAX_PATH];
    HKEY hKey;

    TRACE("%s\n", debugstr_w(provider));
    snprintfW(serviceName, sizeof(serviceName) / sizeof(WCHAR), serviceFmt,
     servicePrefix, provider);
    serviceName[sizeof(serviceName) / sizeof(WCHAR) - 1] = '\0';
    if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, serviceName, 0, KEY_READ, &hKey) ==
     ERROR_SUCCESS)
    {
        static const WCHAR szProviderPath[] = { 'P','r','o','v','i','d','e','r',
         'P','a','t','h',0 };
        WCHAR providerPath[MAX_PATH];
        DWORD type, size = sizeof(providerPath);

        if (RegQueryValueExW(hKey, szProviderPath, NULL, &type,
         (LPBYTE)providerPath, &size) == ERROR_SUCCESS && (type == REG_SZ || type == REG_EXPAND_SZ))
        {
            static const WCHAR szProviderName[] = { 'N','a','m','e',0 };
            PWSTR name = NULL;

            if (type == REG_EXPAND_SZ)
            {
                WCHAR path[MAX_PATH];
                if (ExpandEnvironmentStringsW(providerPath, path, MAX_PATH)) lstrcpyW( providerPath, path );
            }

            size = 0;
            RegQueryValueExW(hKey, szProviderName, NULL, NULL, NULL, &size);
            if (size)
            {
                name = HeapAlloc(GetProcessHeap(), 0, size);
                if (RegQueryValueExW(hKey, szProviderName, NULL, &type,
                 (LPBYTE)name, &size) != ERROR_SUCCESS || type != REG_SZ)
                {
                    HeapFree(GetProcessHeap(), 0, name);
                    name = NULL;
                }
            }
            if (name)
            {
                HMODULE hLib = LoadLibraryW(providerPath);

                if (hLib)
                {
#define MPR_GETPROC(proc) ((PF_##proc)GetProcAddress(hLib, #proc))

                    PF_NPGetCaps getCaps = MPR_GETPROC(NPGetCaps);

                    TRACE("loaded lib %p\n", hLib);
                    if (getCaps)
                    {
                        PWNetProvider provider =
                         &providerTable->table[providerTable->numProviders];

                        provider->hLib = hLib;
                        provider->name = name;
                        TRACE("name is %s\n", debugstr_w(name));
                        provider->getCaps = getCaps;
                        provider->dwSpecVersion = getCaps(WNNC_SPEC_VERSION);
                        provider->dwNetType = getCaps(WNNC_NET_TYPE);
                        TRACE("net type is 0x%08x\n", provider->dwNetType);
                        provider->dwEnumScopes = getCaps(WNNC_ENUMERATION);
                        if (provider->dwEnumScopes)
                        {
                            TRACE("supports enumeration\n");
                            provider->openEnum = MPR_GETPROC(NPOpenEnum);
                            TRACE("NPOpenEnum %p\n", provider->openEnum);
                            provider->enumResource = MPR_GETPROC(NPEnumResource);
                            TRACE("NPEnumResource %p\n", provider->enumResource);
                            provider->closeEnum = MPR_GETPROC(NPCloseEnum);
                            TRACE("NPCloseEnum %p\n", provider->closeEnum);
                            provider->getResourceInformation = MPR_GETPROC(NPGetResourceInformation);
                            TRACE("NPGetResourceInformation %p\n", provider->getResourceInformation);
                            if (!provider->openEnum ||
                                !provider->enumResource ||
                                !provider->closeEnum)
                            {
                                provider->openEnum = NULL;
                                provider->enumResource = NULL;
                                provider->closeEnum = NULL;
                                provider->dwEnumScopes = 0;
                                WARN("Couldn't load enumeration functions\n");
                            }
                        }
                        provider->addConnection = MPR_GETPROC(NPAddConnection);
                        provider->addConnection3 = MPR_GETPROC(NPAddConnection3);
                        TRACE("NPAddConnection %p\n", provider->addConnection);
                        TRACE("NPAddConnection3 %p\n", provider->addConnection3);
                        providerTable->numProviders++;
                    }
                    else
                    {
                        WARN("Provider %s didn't export NPGetCaps\n",
                         debugstr_w(provider));
                        HeapFree(GetProcessHeap(), 0, name);
                        FreeLibrary(hLib);
                    }

#undef MPR_GETPROC
                }
                else
                {
                    WARN("Couldn't load library %s for provider %s\n",
                     debugstr_w(providerPath), debugstr_w(provider));
                    HeapFree(GetProcessHeap(), 0, name);
                }
            }
            else
            {
                WARN("Couldn't get provider name for provider %s\n",
                 debugstr_w(provider));
            }
        }
        else
            WARN("Couldn't open value %s\n", debugstr_w(szProviderPath));
        RegCloseKey(hKey);
    }
    else
        WARN("Couldn't open service key for provider %s\n",
         debugstr_w(provider));
}

void wnetInit(HINSTANCE hInstDll)
{
    static const WCHAR providerOrderKey[] = { 'S','y','s','t','e','m','\\',
     'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\',
     'C','o','n','t','r','o','l','\\',
     'N','e','t','w','o','r','k','P','r','o','v','i','d','e','r','\\',
     'O','r','d','e','r',0 };
     static const WCHAR providerOrder[] = { 'P','r','o','v','i','d','e','r',
      'O','r','d','e','r',0 };
    HKEY hKey;

    if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, providerOrderKey, 0, KEY_READ, &hKey)
     == ERROR_SUCCESS)
    {
        DWORD size = 0;

        RegQueryValueExW(hKey, providerOrder, NULL, NULL, NULL, &size);
        if (size)
        {
            PWSTR providers = HeapAlloc(GetProcessHeap(), 0, size);

            if (providers)
            {
                DWORD type;

                if (RegQueryValueExW(hKey, providerOrder, NULL, &type,
                 (LPBYTE)providers, &size) == ERROR_SUCCESS && type == REG_SZ)
                {
                    PWSTR ptr;
                    DWORD numToAllocate;

                    TRACE("provider order is %s\n", debugstr_w(providers));
                    /* first count commas as a heuristic for how many to
                     * allocate space for */
                    for (ptr = providers, numToAllocate = 1; ptr; )
                    {
                        ptr = strchrW(ptr, ',');
                        if (ptr) {
                            numToAllocate++;
                            ptr++;
                        }
                    }
                    providerTable =
                     HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
                     sizeof(WNetProviderTable)
                     + (numToAllocate - 1) * sizeof(WNetProvider));
                    if (providerTable)
                    {
                        PWSTR ptrPrev;
                        int entireNetworkLen;
                        LPCWSTR stringresource;

                        entireNetworkLen = LoadStringW(hInstDll,
                         IDS_ENTIRENETWORK, (LPWSTR)&stringresource, 0);
                        providerTable->entireNetwork = HeapAlloc(
                         GetProcessHeap(), 0, (entireNetworkLen + 1) *
                         sizeof(WCHAR));
                        if (providerTable->entireNetwork)
                        {
                            memcpy(providerTable->entireNetwork, stringresource, entireNetworkLen*sizeof(WCHAR));
                            providerTable->entireNetwork[entireNetworkLen] = 0;
                        }
                        providerTable->numAllocated = numToAllocate;
                        for (ptr = providers; ptr; )
                        {
                            ptrPrev = ptr;
                            ptr = strchrW(ptr, ',');
                            if (ptr)
                                *ptr++ = '\0';
                            _tryLoadProvider(ptrPrev);
                        }
                    }
                }
                HeapFree(GetProcessHeap(), 0, providers);
            }
        }
        RegCloseKey(hKey);
    }
}

void wnetFree(void)
{
    if (providerTable)
    {
        DWORD i;

        for (i = 0; i < providerTable->numProviders; i++)
        {
            HeapFree(GetProcessHeap(), 0, providerTable->table[i].name);
            FreeModule(providerTable->table[i].hLib);
        }
        HeapFree(GetProcessHeap(), 0, providerTable->entireNetwork);
        HeapFree(GetProcessHeap(), 0, providerTable);
        providerTable = NULL;
    }
}

static DWORD _findProviderIndexW(LPCWSTR lpProvider)
{
    DWORD ret = BAD_PROVIDER_INDEX;

    if (providerTable && providerTable->numProviders)
    {
        DWORD i;

        for (i = 0; i < providerTable->numProviders &&
         ret == BAD_PROVIDER_INDEX; i++)
            if (!strcmpW(lpProvider, providerTable->table[i].name))
                ret = i;
    }
    return ret;
}

/*
 * Browsing Functions
 */

static LPNETRESOURCEW _copyNetResourceForEnumW(LPNETRESOURCEW lpNet)
{
    LPNETRESOURCEW ret;

    if (lpNet)
    {
        ret = HeapAlloc(GetProcessHeap(), 0, sizeof(NETRESOURCEW));
        if (ret)
        {
            size_t len;

            *ret = *lpNet;
            ret->lpLocalName = ret->lpComment = ret->lpProvider = NULL;
            if (lpNet->lpRemoteName)
            {
                len = strlenW(lpNet->lpRemoteName) + 1;
                ret->lpRemoteName = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
                if (ret->lpRemoteName)
                    strcpyW(ret->lpRemoteName, lpNet->lpRemoteName);
            }
        }
    }
    else
        ret = NULL;
    return ret;
}

static void _freeEnumNetResource(LPNETRESOURCEW lpNet)
{
    if (lpNet)
    {
        HeapFree(GetProcessHeap(), 0, lpNet->lpRemoteName);
        HeapFree(GetProcessHeap(), 0, lpNet);
    }
}

static PWNetEnumerator _createNullEnumerator(void)
{
    PWNetEnumerator ret = HeapAlloc(GetProcessHeap(),
     HEAP_ZERO_MEMORY, sizeof(WNetEnumerator));

    if (ret)
        ret->enumType = WNET_ENUMERATOR_TYPE_NULL;
    return ret;
}

static PWNetEnumerator _createGlobalEnumeratorW(DWORD dwScope, DWORD dwType,
 DWORD dwUsage, LPNETRESOURCEW lpNet)
{
    PWNetEnumerator ret = HeapAlloc(GetProcessHeap(),
     HEAP_ZERO_MEMORY, sizeof(WNetEnumerator));

    if (ret)
    {
        ret->enumType = WNET_ENUMERATOR_TYPE_GLOBAL;
        ret->dwScope = dwScope;
        ret->dwType  = dwType;
        ret->dwUsage = dwUsage;
        ret->lpNet   = _copyNetResourceForEnumW(lpNet);
    }
    return ret;
}

static PWNetEnumerator _createProviderEnumerator(DWORD dwScope, DWORD dwType,
 DWORD dwUsage, DWORD index, HANDLE handle)
{
    PWNetEnumerator ret;

    if (!providerTable || index >= providerTable->numProviders)
        ret = NULL;
    else
    {
        ret = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(WNetEnumerator));
        if (ret)
        {
            ret->enumType      = WNET_ENUMERATOR_TYPE_PROVIDER;
            ret->providerIndex = index;
            ret->dwScope       = dwScope;
            ret->dwType        = dwType;
            ret->dwUsage       = dwUsage;
            ret->handle        = handle;
        }
    }
    return ret;
}

static PWNetEnumerator _createContextEnumerator(DWORD dwScope, DWORD dwType,
 DWORD dwUsage)
{
    PWNetEnumerator ret = HeapAlloc(GetProcessHeap(),
     HEAP_ZERO_MEMORY, sizeof(WNetEnumerator));

    if (ret)
    {
        ret->enumType = WNET_ENUMERATOR_TYPE_CONTEXT;
        ret->dwScope = dwScope;
        ret->dwType  = dwType;
        ret->dwUsage = dwUsage;
    }
    return ret;
}

/* Thunks the array of wide-string LPNETRESOURCEs lpNetArrayIn into buffer
 * lpBuffer, with size *lpBufferSize.  lpNetArrayIn contains *lpcCount entries
 * to start.  On return, *lpcCount reflects the number thunked into lpBuffer.
 * Returns WN_SUCCESS on success (all of lpNetArrayIn thunked), WN_MORE_DATA
 * if not all members of the array could be thunked, and something else on
 * failure.
 */
static DWORD _thunkNetResourceArrayWToA(const NETRESOURCEW *lpNetArrayIn,
 const DWORD *lpcCount, LPVOID lpBuffer, const DWORD *lpBufferSize)
{
    DWORD i, numToThunk, totalBytes, ret;
    LPSTR strNext;

    if (!lpNetArrayIn)
        return WN_BAD_POINTER;
    if (!lpcCount)
        return WN_BAD_POINTER;
    if (*lpcCount == -1)
        return WN_BAD_VALUE;
    if (!lpBuffer)
        return WN_BAD_POINTER;
    if (!lpBufferSize)
        return WN_BAD_POINTER;

    for (i = 0, numToThunk = 0, totalBytes = 0; i < *lpcCount; i++)
    {
        const NETRESOURCEW *lpNet = lpNetArrayIn + i;

        totalBytes += sizeof(NETRESOURCEA);
        if (lpNet->lpLocalName)
            totalBytes += WideCharToMultiByte(CP_ACP, 0, lpNet->lpLocalName,
             -1, NULL, 0, NULL, NULL);
        if (lpNet->lpRemoteName)
            totalBytes += WideCharToMultiByte(CP_ACP, 0, lpNet->lpRemoteName,
             -1, NULL, 0, NULL, NULL);
        if (lpNet->lpComment)
            totalBytes += WideCharToMultiByte(CP_ACP, 0, lpNet->lpComment,
             -1, NULL, 0, NULL, NULL);
        if (lpNet->lpProvider)
            totalBytes += WideCharToMultiByte(CP_ACP, 0, lpNet->lpProvider,
             -1, NULL, 0, NULL, NULL);
        if (totalBytes < *lpBufferSize)
            numToThunk = i + 1;
    }
    strNext = (LPSTR)((LPBYTE)lpBuffer + numToThunk * sizeof(NETRESOURCEA));
    for (i = 0; i < numToThunk; i++)
    {
        LPNETRESOURCEA lpNetOut = (LPNETRESOURCEA)lpBuffer + i;
        const NETRESOURCEW *lpNetIn = lpNetArrayIn + i;

        memcpy(lpNetOut, lpNetIn, sizeof(NETRESOURCEA));
        /* lie about string lengths, we already verified how many
         * we have space for above
         */
        if (lpNetIn->lpLocalName)
        {
            lpNetOut->lpLocalName = strNext;
            strNext += WideCharToMultiByte(CP_ACP, 0, lpNetIn->lpLocalName, -1,
             lpNetOut->lpLocalName, *lpBufferSize, NULL, NULL);
        }
        if (lpNetIn->lpRemoteName)
        {
            lpNetOut->lpRemoteName = strNext;
            strNext += WideCharToMultiByte(CP_ACP, 0, lpNetIn->lpRemoteName, -1,
             lpNetOut->lpRemoteName, *lpBufferSize, NULL, NULL);
        }
        if (lpNetIn->lpComment)
        {
            lpNetOut->lpComment = strNext;
            strNext += WideCharToMultiByte(CP_ACP, 0, lpNetIn->lpComment, -1,
             lpNetOut->lpComment, *lpBufferSize, NULL, NULL);
        }
        if (lpNetIn->lpProvider)
        {
            lpNetOut->lpProvider = strNext;
            strNext += WideCharToMultiByte(CP_ACP, 0, lpNetIn->lpProvider, -1,
             lpNetOut->lpProvider, *lpBufferSize, NULL, NULL);
        }
    }
    ret = numToThunk < *lpcCount ? WN_MORE_DATA : WN_SUCCESS;
    TRACE("numToThunk is %d, *lpcCount is %d, returning %d\n", numToThunk,
     *lpcCount, ret);
    return ret;
}

/* Thunks the array of multibyte-string LPNETRESOURCEs lpNetArrayIn into buffer
 * lpBuffer, with size *lpBufferSize.  lpNetArrayIn contains *lpcCount entries
 * to start.  On return, *lpcCount reflects the number thunked into lpBuffer.
 * Returns WN_SUCCESS on success (all of lpNetArrayIn thunked), WN_MORE_DATA
 * if not all members of the array could be thunked, and something else on
 * failure.
 */
static DWORD _thunkNetResourceArrayAToW(const NETRESOURCEA *lpNetArrayIn,
 const DWORD *lpcCount, LPVOID lpBuffer, const DWORD *lpBufferSize)
{
    DWORD i, numToThunk, totalBytes, ret;
    LPWSTR strNext;

    if (!lpNetArrayIn)
        return WN_BAD_POINTER;
    if (!lpcCount)
        return WN_BAD_POINTER;
    if (*lpcCount == -1)
        return WN_BAD_VALUE;
    if (!lpBuffer)
        return WN_BAD_POINTER;
    if (!lpBufferSize)
        return WN_BAD_POINTER;

    for (i = 0, numToThunk = 0, totalBytes = 0; i < *lpcCount; i++)
    {
        const NETRESOURCEA *lpNet = lpNetArrayIn + i;

        totalBytes += sizeof(NETRESOURCEW);
        if (lpNet->lpLocalName)
            totalBytes += MultiByteToWideChar(CP_ACP, 0, lpNet->lpLocalName,
             -1, NULL, 0) * sizeof(WCHAR);
        if (lpNet->lpRemoteName)
            totalBytes += MultiByteToWideChar(CP_ACP, 0, lpNet->lpRemoteName,
             -1, NULL, 0) * sizeof(WCHAR);
        if (lpNet->lpComment)
            totalBytes += MultiByteToWideChar(CP_ACP, 0, lpNet->lpComment,
             -1, NULL, 0) * sizeof(WCHAR);
        if (lpNet->lpProvider)
            totalBytes += MultiByteToWideChar(CP_ACP, 0, lpNet->lpProvider,
             -1, NULL, 0) * sizeof(WCHAR);
        if (totalBytes < *lpBufferSize)
            numToThunk = i + 1;
    }
    strNext = (LPWSTR)((LPBYTE)lpBuffer + numToThunk * sizeof(NETRESOURCEW));
    for (i = 0; i < numToThunk; i++)
    {
        LPNETRESOURCEW lpNetOut = (LPNETRESOURCEW)lpBuffer + i;
        const NETRESOURCEA *lpNetIn = lpNetArrayIn + i;

        memcpy(lpNetOut, lpNetIn, sizeof(NETRESOURCEW));
        /* lie about string lengths, we already verified how many
         * we have space for above
         */
        if (lpNetIn->lpLocalName)
        {
            lpNetOut->lpLocalName = strNext;
            strNext += MultiByteToWideChar(CP_ACP, 0, lpNetIn->lpLocalName,
             -1, lpNetOut->lpLocalName, *lpBufferSize);
        }
        if (lpNetIn->lpRemoteName)
        {
            lpNetOut->lpRemoteName = strNext;
            strNext += MultiByteToWideChar(CP_ACP, 0, lpNetIn->lpRemoteName,
             -1, lpNetOut->lpRemoteName, *lpBufferSize);
        }
        if (lpNetIn->lpComment)
        {
            lpNetOut->lpComment = strNext;
            strNext += MultiByteToWideChar(CP_ACP, 0, lpNetIn->lpComment,
             -1, lpNetOut->lpComment, *lpBufferSize);
        }
        if (lpNetIn->lpProvider)
        {
            lpNetOut->lpProvider = strNext;
            strNext += MultiByteToWideChar(CP_ACP, 0, lpNetIn->lpProvider,
             -1, lpNetOut->lpProvider, *lpBufferSize);
        }
    }
    ret = numToThunk < *lpcCount ? WN_MORE_DATA : WN_SUCCESS;
    TRACE("numToThunk is %d, *lpcCount is %d, returning %d\n", numToThunk,
     *lpcCount, ret);
    return ret;
}

/*********************************************************************
 * WNetOpenEnumA [MPR.@]
 *
 * See comments for WNetOpenEnumW.
 */
DWORD WINAPI WNetOpenEnumA( DWORD dwScope, DWORD dwType, DWORD dwUsage,
                            LPNETRESOURCEA lpNet, LPHANDLE lphEnum )
{
    DWORD ret;

    TRACE( "(%08X, %08X, %08X, %p, %p)\n",
	    dwScope, dwType, dwUsage, lpNet, lphEnum );

    if (!lphEnum)
        ret = WN_BAD_POINTER;
    else if (!providerTable || providerTable->numProviders == 0)
    {
        *lphEnum = NULL;
        ret = WN_NO_NETWORK;
    }
    else
    {
        if (lpNet)
        {
            LPNETRESOURCEW lpNetWide = NULL;
            BYTE buf[1024];
            DWORD size = sizeof(buf), count = 1;
            BOOL allocated = FALSE;

            ret = _thunkNetResourceArrayAToW(lpNet, &count, buf, &size);
            if (ret == WN_MORE_DATA)
            {
                lpNetWide = HeapAlloc(GetProcessHeap(), 0,
                 size);
                if (lpNetWide)
                {
                    ret = _thunkNetResourceArrayAToW(lpNet, &count, lpNetWide,
                     &size);
                    allocated = TRUE;
                }
                else
                    ret = WN_OUT_OF_MEMORY;
            }
            else if (ret == WN_SUCCESS)
                lpNetWide = (LPNETRESOURCEW)buf;
            if (ret == WN_SUCCESS)
                ret = WNetOpenEnumW(dwScope, dwType, dwUsage, lpNetWide,
                 lphEnum);
            if (allocated)
                HeapFree(GetProcessHeap(), 0, lpNetWide);
        }
        else
            ret = WNetOpenEnumW(dwScope, dwType, dwUsage, NULL, lphEnum);
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*********************************************************************
 * WNetOpenEnumW [MPR.@]
 *
 * Network enumeration has way too many parameters, so I'm not positive I got
 * them right.  What I've got so far:
 *
 * - If the scope is RESOURCE_GLOBALNET, and no LPNETRESOURCE is passed,
 *   all the network providers should be enumerated.
 *
 * - If the scope is RESOURCE_GLOBALNET, and LPNETRESOURCE is passed, and
 *   and neither the LPNETRESOURCE's lpRemoteName nor the LPNETRESOURCE's
 *   lpProvider is set, all the network providers should be enumerated.
 *   (This means the enumeration is a list of network providers, not that the
 *   enumeration is passed on to the providers.)
 *
 * - If the scope is RESOURCE_GLOBALNET, and LPNETRESOURCE is passed, and the
 *   resource matches the "Entire Network" resource (no remote name, no
 *   provider, comment is the "Entire Network" string), a RESOURCE_GLOBALNET
 *   enumeration is done on every network provider.
 *
 * - If the scope is RESOURCE_GLOBALNET, and LPNETRESOURCE is passed, and
 *   the LPNETRESOURCE's lpProvider is set, enumeration will be passed through
 *   only to the given network provider.
 *
 * - If the scope is RESOURCE_GLOBALNET, and LPNETRESOURCE is passed, and
 *   no lpProvider is set, enumeration will be tried on every network provider,
 *   in the order in which they're loaded.
 *
 * - The LPNETRESOURCE should be disregarded for scopes besides
 *   RESOURCE_GLOBALNET.  MSDN states that lpNet must be NULL if dwScope is not
 *   RESOURCE_GLOBALNET, but Windows doesn't return an error if it isn't NULL.
 *
 * - If the scope is RESOURCE_CONTEXT, MS includes an "Entire Network" net
 *   resource in the enumerated list, as well as any machines in your
 *   workgroup.  The machines in your workgroup come from doing a
 *   RESOURCE_CONTEXT enumeration of every Network Provider.
 */
DWORD WINAPI WNetOpenEnumW( DWORD dwScope, DWORD dwType, DWORD dwUsage,
                            LPNETRESOURCEW lpNet, LPHANDLE lphEnum )
{
    DWORD ret;

    TRACE( "(%08X, %08X, %08X, %p, %p)\n",
          dwScope, dwType, dwUsage, lpNet, lphEnum );

    if (!lphEnum)
        ret = WN_BAD_POINTER;
    else if (!providerTable || providerTable->numProviders == 0)
    {
        *lphEnum = NULL;
        ret = WN_NO_NETWORK;
    }
    else
    {
        switch (dwScope)
        {
            case RESOURCE_GLOBALNET:
                if (lpNet)
                {
                    if (lpNet->lpProvider)
                    {
                        DWORD index = _findProviderIndexW(lpNet->lpProvider);

                        if (index != BAD_PROVIDER_INDEX)
                        {
                            if (providerTable->table[index].openEnum &&
                             providerTable->table[index].dwEnumScopes & WNNC_ENUM_GLOBAL)
                            {
                                HANDLE handle;
                                PWSTR RemoteName = lpNet->lpRemoteName;

                                if ((lpNet->dwUsage & RESOURCEUSAGE_CONTAINER) &&
                                    RemoteName && !strcmpW(RemoteName, lpNet->lpProvider))
                                    lpNet->lpRemoteName = NULL;

                                ret = providerTable->table[index].openEnum(
                                 dwScope, dwType, dwUsage, lpNet, &handle);
                                if (ret == WN_SUCCESS)
                                {
                                    *lphEnum = _createProviderEnumerator(
                                     dwScope, dwType, dwUsage, index, handle);
                                    ret = *lphEnum ? WN_SUCCESS :
                                     WN_OUT_OF_MEMORY;
                                }

                                lpNet->lpRemoteName = RemoteName;
                            }
                            else
                                ret = WN_NOT_SUPPORTED;
                        }
                        else
                            ret = WN_BAD_PROVIDER;
                    }
                    else if (lpNet->lpRemoteName)
                    {
                        *lphEnum = _createGlobalEnumeratorW(dwScope,
                         dwType, dwUsage, lpNet);
                        ret = *lphEnum ? WN_SUCCESS : WN_OUT_OF_MEMORY;
                    }
                    else
                    {
                        if (lpNet->lpComment && !strcmpW(lpNet->lpComment,
                         providerTable->entireNetwork))
                        {
                            /* comment matches the "Entire Network", enumerate
                             * global scope of every provider
                             */
                            *lphEnum = _createGlobalEnumeratorW(dwScope,
                             dwType, dwUsage, lpNet);
                        }
                        else
                        {
                            /* this is the same as not having passed lpNet */
                            *lphEnum = _createGlobalEnumeratorW(dwScope,
                             dwType, dwUsage, NULL);
                        }
                        ret = *lphEnum ? WN_SUCCESS : WN_OUT_OF_MEMORY;
                    }
                }
                else
                {
                    *lphEnum = _createGlobalEnumeratorW(dwScope, dwType,
                     dwUsage, lpNet);
                    ret = *lphEnum ? WN_SUCCESS : WN_OUT_OF_MEMORY;
                }
                break;
            case RESOURCE_CONTEXT:
                *lphEnum = _createContextEnumerator(dwScope, dwType, dwUsage);
                ret = *lphEnum ? WN_SUCCESS : WN_OUT_OF_MEMORY;
                break;
            case RESOURCE_REMEMBERED:
            case RESOURCE_CONNECTED:
                *lphEnum = _createNullEnumerator();
                ret = *lphEnum ? WN_SUCCESS : WN_OUT_OF_MEMORY;
                break;
            default:
                WARN("unknown scope 0x%08x\n", dwScope);
                ret = WN_BAD_VALUE;
        }
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*********************************************************************
 * WNetEnumResourceA [MPR.@]
 */
DWORD WINAPI WNetEnumResourceA( HANDLE hEnum, LPDWORD lpcCount,
                                LPVOID lpBuffer, LPDWORD lpBufferSize )
{
    DWORD ret;

    TRACE( "(%p, %p, %p, %p)\n", hEnum, lpcCount, lpBuffer, lpBufferSize );

    if (!hEnum)
        ret = WN_BAD_POINTER;
    else if (!lpcCount)
        ret = WN_BAD_POINTER;
    else if (!lpBuffer)
        ret = WN_BAD_POINTER;
    else if (!lpBufferSize)
        ret = WN_BAD_POINTER;
    else if (*lpBufferSize < sizeof(NETRESOURCEA))
    {
        *lpBufferSize = sizeof(NETRESOURCEA);
        ret = WN_MORE_DATA;
    }
    else
    {
        DWORD localCount = *lpcCount, localSize = *lpBufferSize;
        LPVOID localBuffer = HeapAlloc(GetProcessHeap(), 0, localSize);

        if (localBuffer)
        {
            ret = WNetEnumResourceW(hEnum, &localCount, localBuffer,
             &localSize);
            if (ret == WN_SUCCESS || (ret == WN_MORE_DATA && localCount != -1))
            {
                /* FIXME: this isn't necessarily going to work in the case of
                 * WN_MORE_DATA, because our enumerator may have moved on to
                 * the next provider.  MSDN states that a large (16KB) buffer
                 * size is the appropriate usage of this function, so
                 * hopefully it won't be an issue.
                 */
                ret = _thunkNetResourceArrayWToA(localBuffer, &localCount,
                 lpBuffer, lpBufferSize);
                *lpcCount = localCount;
            }
            HeapFree(GetProcessHeap(), 0, localBuffer);
        }
        else
            ret = WN_OUT_OF_MEMORY;
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

static DWORD _countProviderBytesW(PWNetProvider provider)
{
    DWORD ret;

    if (provider)
    {
        ret = sizeof(NETRESOURCEW);
        ret += 2 * (strlenW(provider->name) + 1) * sizeof(WCHAR);
    }
    else
        ret = 0;
    return ret;
}

static DWORD _enumerateProvidersW(PWNetEnumerator enumerator, LPDWORD lpcCount,
 LPVOID lpBuffer, const DWORD *lpBufferSize)
{
    DWORD ret;

    if (!enumerator)
        return WN_BAD_POINTER;
    if (enumerator->enumType != WNET_ENUMERATOR_TYPE_GLOBAL)
        return WN_BAD_VALUE;
    if (!lpcCount)
        return WN_BAD_POINTER;
    if (!lpBuffer)
        return WN_BAD_POINTER;
    if (!lpBufferSize)
        return WN_BAD_POINTER;
    if (*lpBufferSize < sizeof(NETRESOURCEA))
        return WN_MORE_DATA;

    if (!providerTable || enumerator->providerIndex >= 
     providerTable->numProviders)
        ret = WN_NO_MORE_ENTRIES;
    else
    {
        DWORD bytes = 0, count = 0, countLimit, i;
        LPNETRESOURCEW resource;
        LPWSTR strNext;

        countLimit = *lpcCount == -1 ?
         providerTable->numProviders - enumerator->providerIndex : *lpcCount;
        while (count < countLimit && bytes < *lpBufferSize)
        {
            DWORD bytesNext = _countProviderBytesW(
             &providerTable->table[count + enumerator->providerIndex]);

            if (bytes + bytesNext < *lpBufferSize)
            {
                bytes += bytesNext;
                count++;
            }
        }
        strNext = (LPWSTR)((LPBYTE)lpBuffer + count * sizeof(NETRESOURCEW));
        for (i = 0, resource = lpBuffer; i < count; i++, resource++)
        {
            resource->dwScope = RESOURCE_GLOBALNET;
            resource->dwType = RESOURCETYPE_ANY;
            resource->dwDisplayType = RESOURCEDISPLAYTYPE_NETWORK;
            resource->dwUsage = RESOURCEUSAGE_CONTAINER |
             RESOURCEUSAGE_RESERVED;
            resource->lpLocalName = NULL;
            resource->lpRemoteName = strNext;
            strcpyW(resource->lpRemoteName,
             providerTable->table[i + enumerator->providerIndex].name);
            strNext += strlenW(resource->lpRemoteName) + 1;
            resource->lpComment = NULL;
            resource->lpProvider = strNext;
            strcpyW(resource->lpProvider,
             providerTable->table[i + enumerator->providerIndex].name);
            strNext += strlenW(resource->lpProvider) + 1;
        }
        enumerator->providerIndex += count;
        *lpcCount = count;
        ret = count > 0 ? WN_SUCCESS : WN_MORE_DATA;
    }
    TRACE("Returning %d\n", ret);
    return ret;
}

/* Advances the enumerator (assumed to be a global enumerator) to the next
 * provider that supports the enumeration scope passed to WNetOpenEnum.  Does
 * not open a handle with the next provider.
 * If the existing handle is NULL, may leave the enumerator unchanged, since
 * the current provider may support the desired scope.
 * If the existing handle is not NULL, closes it before moving on.
 * Returns WN_SUCCESS on success, WN_NO_MORE_ENTRIES if there is no available
 * provider, and another error on failure.
 */
static DWORD _globalEnumeratorAdvance(PWNetEnumerator enumerator)
{
    if (!enumerator)
        return WN_BAD_POINTER;
    if (enumerator->enumType != WNET_ENUMERATOR_TYPE_GLOBAL)
        return WN_BAD_VALUE;
    if (!providerTable || enumerator->providerIndex >=
     providerTable->numProviders)
        return WN_NO_MORE_ENTRIES;

    if (enumerator->providerDone)
    {
        DWORD dwEnum = 0;
        enumerator->providerDone = FALSE;
        if (enumerator->handle)
        {
            providerTable->table[enumerator->providerIndex].closeEnum(
             enumerator->handle);
            enumerator->handle = NULL;
            enumerator->providerIndex++;
        }
        if (enumerator->dwScope == RESOURCE_CONNECTED)
            dwEnum = WNNC_ENUM_LOCAL;
        else if (enumerator->dwScope == RESOURCE_GLOBALNET)
            dwEnum = WNNC_ENUM_GLOBAL;
        else if (enumerator->dwScope == RESOURCE_CONTEXT)
            dwEnum = WNNC_ENUM_CONTEXT;
        for (; enumerator->providerIndex < providerTable->numProviders &&
         !(providerTable->table[enumerator->providerIndex].dwEnumScopes
         & dwEnum); enumerator->providerIndex++)
            ;
    }
    return enumerator->providerIndex < providerTable->numProviders ?
     WN_SUCCESS : WN_NO_MORE_ENTRIES;
}

/* "Passes through" call to the next provider that supports the enumeration
 * type.
 * FIXME: if one call to a provider's enumerator succeeds while there's still
 * space in lpBuffer, I don't call to the next provider.  The caller may not
 * expect that it should call EnumResourceW again with a return value of
 * WN_SUCCESS (depending what *lpcCount was to begin with).  That means strings
 * may have to be moved around a bit, ick.
 */
static DWORD _enumerateGlobalPassthroughW(PWNetEnumerator enumerator,
 LPDWORD lpcCount, LPVOID lpBuffer, LPDWORD lpBufferSize)
{
    DWORD ret;

    if (!enumerator)
        return WN_BAD_POINTER;
    if (enumerator->enumType != WNET_ENUMERATOR_TYPE_GLOBAL)
        return WN_BAD_VALUE;
    if (!lpcCount)
        return WN_BAD_POINTER;
    if (!lpBuffer)
        return WN_BAD_POINTER;
    if (!lpBufferSize)
        return WN_BAD_POINTER;
    if (*lpBufferSize < sizeof(NETRESOURCEW))
        return WN_MORE_DATA;

    ret = _globalEnumeratorAdvance(enumerator);
    if (ret == WN_SUCCESS)
    {
        ret = providerTable->table[enumerator->providerIndex].
         openEnum(enumerator->dwScope, enumerator->dwType,
         enumerator->dwUsage, enumerator->lpNet,
         &enumerator->handle);
        if (ret == WN_SUCCESS)
        {
            ret = providerTable->table[enumerator->providerIndex].
             enumResource(enumerator->handle, lpcCount, lpBuffer,
             lpBufferSize);
            if (ret != WN_MORE_DATA)
                enumerator->providerDone = TRUE;
        }
    }
    TRACE("Returning %d\n", ret);
    return ret;
}

static DWORD _enumerateGlobalW(PWNetEnumerator enumerator, LPDWORD lpcCount,
 LPVOID lpBuffer, LPDWORD lpBufferSize)
{
    DWORD ret;

    if (!enumerator)
        return WN_BAD_POINTER;
    if (enumerator->enumType != WNET_ENUMERATOR_TYPE_GLOBAL)
        return WN_BAD_VALUE;
    if (!lpcCount)
        return WN_BAD_POINTER;
    if (!lpBuffer)
        return WN_BAD_POINTER;
    if (!lpBufferSize)
        return WN_BAD_POINTER;
    if (*lpBufferSize < sizeof(NETRESOURCEW))
        return WN_MORE_DATA;
    if (!providerTable)
        return WN_NO_NETWORK;

    switch (enumerator->dwScope)
    {
        case RESOURCE_GLOBALNET:
            if (enumerator->lpNet)
                ret = _enumerateGlobalPassthroughW(enumerator, lpcCount,
                 lpBuffer, lpBufferSize);
            else
                ret = _enumerateProvidersW(enumerator, lpcCount, lpBuffer,
                 lpBufferSize);
            break;
        case RESOURCE_CONTEXT:
            ret = _enumerateGlobalPassthroughW(enumerator, lpcCount, lpBuffer,
             lpBufferSize);
            break;
        default:
            WARN("unexpected scope 0x%08x\n", enumerator->dwScope);
            ret = WN_NO_MORE_ENTRIES;
    }
    TRACE("Returning %d\n", ret);
    return ret;
}

static DWORD _enumerateProviderW(PWNetEnumerator enumerator, LPDWORD lpcCount,
 LPVOID lpBuffer, LPDWORD lpBufferSize)
{
    if (!enumerator)
        return WN_BAD_POINTER;
    if (enumerator->enumType != WNET_ENUMERATOR_TYPE_PROVIDER)
        return WN_BAD_VALUE;
    if (!enumerator->handle)
        return WN_BAD_VALUE;
    if (!lpcCount)
        return WN_BAD_POINTER;
    if (!lpBuffer)
        return WN_BAD_POINTER;
    if (!lpBufferSize)
        return WN_BAD_POINTER;
    if (!providerTable)
        return WN_NO_NETWORK;
    if (enumerator->providerIndex >= providerTable->numProviders)
        return WN_NO_MORE_ENTRIES;
    if (!providerTable->table[enumerator->providerIndex].enumResource)
        return WN_BAD_VALUE;
    return providerTable->table[enumerator->providerIndex].enumResource(
     enumerator->handle, lpcCount, lpBuffer, lpBufferSize);
}

static DWORD _enumerateContextW(PWNetEnumerator enumerator, LPDWORD lpcCount,
 LPVOID lpBuffer, LPDWORD lpBufferSize)
{
    DWORD ret;
    size_t cchEntireNetworkLen, bytesNeeded;

    if (!enumerator)
        return WN_BAD_POINTER;
    if (enumerator->enumType != WNET_ENUMERATOR_TYPE_CONTEXT)
        return WN_BAD_VALUE;
    if (!lpcCount)
        return WN_BAD_POINTER;
    if (!lpBuffer)
        return WN_BAD_POINTER;
    if (!lpBufferSize)
        return WN_BAD_POINTER;
    if (!providerTable)
        return WN_NO_NETWORK;

    cchEntireNetworkLen = strlenW(providerTable->entireNetwork) + 1;
    bytesNeeded = sizeof(NETRESOURCEW) + cchEntireNetworkLen * sizeof(WCHAR);
    if (*lpBufferSize < bytesNeeded)
    {
        *lpBufferSize = bytesNeeded;
        ret = WN_MORE_DATA;
    }
    else
    {
        LPNETRESOURCEW lpNet = lpBuffer;

        lpNet->dwScope = RESOURCE_GLOBALNET;
        lpNet->dwType = enumerator->dwType;
        lpNet->dwDisplayType = RESOURCEDISPLAYTYPE_ROOT;
        lpNet->dwUsage = RESOURCEUSAGE_CONTAINER;
        lpNet->lpLocalName = NULL;
        lpNet->lpRemoteName = NULL;
        lpNet->lpProvider = NULL;
        /* odd, but correct: put comment at end of buffer, so it won't get
         * overwritten by subsequent calls to a provider's enumResource
         */
        lpNet->lpComment = (LPWSTR)((LPBYTE)lpBuffer + *lpBufferSize -
         (cchEntireNetworkLen * sizeof(WCHAR)));
        strcpyW(lpNet->lpComment, providerTable->entireNetwork);
        ret = WN_SUCCESS;
    }
    if (ret == WN_SUCCESS)
    {
        DWORD bufferSize = *lpBufferSize - bytesNeeded;

        /* "Entire Network" entry enumerated--morph this into a global
         * enumerator.  enumerator->lpNet continues to be NULL, since it has
         * no meaning when the scope isn't RESOURCE_GLOBALNET.
         */
        enumerator->enumType = WNET_ENUMERATOR_TYPE_GLOBAL;
        ret = _enumerateGlobalW(enumerator, lpcCount,
         (LPBYTE)lpBuffer + bytesNeeded, &bufferSize);
        if (ret == WN_SUCCESS)
        {
            /* reflect the fact that we already enumerated "Entire Network" */
            (*lpcCount)++;
            *lpBufferSize = bufferSize + bytesNeeded;
        }
        else
        {
            /* the provider enumeration failed, but we already succeeded in
             * enumerating "Entire Network"--leave type as global to allow a
             * retry, but indicate success with a count of one.
             */
            ret = WN_SUCCESS;
            *lpcCount = 1;
            *lpBufferSize = bytesNeeded;
        }
    }
    TRACE("Returning %d\n", ret);
    return ret;
}

/*********************************************************************
 * WNetEnumResourceW [MPR.@]
 */
DWORD WINAPI WNetEnumResourceW( HANDLE hEnum, LPDWORD lpcCount,
                                LPVOID lpBuffer, LPDWORD lpBufferSize )
{
    DWORD ret;

    TRACE( "(%p, %p, %p, %p)\n", hEnum, lpcCount, lpBuffer, lpBufferSize );

    if (!hEnum)
        ret = WN_BAD_POINTER;
    else if (!lpcCount)
        ret = WN_BAD_POINTER;
    else if (!lpBuffer)
        ret = WN_BAD_POINTER;
    else if (!lpBufferSize)
        ret = WN_BAD_POINTER;
    else if (*lpBufferSize < sizeof(NETRESOURCEW))
    {
        *lpBufferSize = sizeof(NETRESOURCEW);
        ret = WN_MORE_DATA;
    }
    else
    {
        PWNetEnumerator enumerator = (PWNetEnumerator)hEnum;

        switch (enumerator->enumType)
        {
            case WNET_ENUMERATOR_TYPE_NULL:
                ret = WN_NO_MORE_ENTRIES;
                break;
            case WNET_ENUMERATOR_TYPE_GLOBAL:
                ret = _enumerateGlobalW(enumerator, lpcCount, lpBuffer,
                 lpBufferSize);
                break;
            case WNET_ENUMERATOR_TYPE_PROVIDER:
                ret = _enumerateProviderW(enumerator, lpcCount, lpBuffer,
                 lpBufferSize);
                break;
            case WNET_ENUMERATOR_TYPE_CONTEXT:
                ret = _enumerateContextW(enumerator, lpcCount, lpBuffer,
                 lpBufferSize);
                break;
            default:
                WARN("bogus enumerator type!\n");
                ret = WN_NO_NETWORK;
        }
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*********************************************************************
 * WNetCloseEnum [MPR.@]
 */
DWORD WINAPI WNetCloseEnum( HANDLE hEnum )
{
    DWORD ret;

    TRACE( "(%p)\n", hEnum );

    if (hEnum)
    {
        PWNetEnumerator enumerator = (PWNetEnumerator)hEnum;

        switch (enumerator->enumType)
        {
            case WNET_ENUMERATOR_TYPE_NULL:
                ret = WN_SUCCESS;
                break;
            case WNET_ENUMERATOR_TYPE_GLOBAL:
                if (enumerator->lpNet)
                    _freeEnumNetResource(enumerator->lpNet);
                if (enumerator->handle)
                    providerTable->table[enumerator->providerIndex].
                     closeEnum(enumerator->handle);
                ret = WN_SUCCESS;
                break;
            case WNET_ENUMERATOR_TYPE_PROVIDER:
                if (enumerator->handle)
                    providerTable->table[enumerator->providerIndex].
                     closeEnum(enumerator->handle);
                ret = WN_SUCCESS;
                break;
            default:
                WARN("bogus enumerator type!\n");
                ret = WN_BAD_HANDLE;
        }
        HeapFree(GetProcessHeap(), 0, hEnum);
    }
    else
        ret = WN_BAD_HANDLE;
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*********************************************************************
 * WNetGetResourceInformationA [MPR.@]
 *
 * See WNetGetResourceInformationW
 */
DWORD WINAPI WNetGetResourceInformationA( LPNETRESOURCEA lpNetResource,
                                          LPVOID lpBuffer, LPDWORD cbBuffer,
                                          LPSTR *lplpSystem )
{
    DWORD ret;

    TRACE( "(%p, %p, %p, %p)\n",
           lpNetResource, lpBuffer, cbBuffer, lplpSystem );

    if (!providerTable || providerTable->numProviders == 0)
        ret = WN_NO_NETWORK;
    else if (lpNetResource)
    {
        LPNETRESOURCEW lpNetResourceW = NULL;
        DWORD size = 1024, count = 1;
        DWORD len;

        lpNetResourceW = HeapAlloc(GetProcessHeap(), 0, size);
        ret = _thunkNetResourceArrayAToW(lpNetResource, &count, lpNetResourceW, &size);
        if (ret == WN_MORE_DATA)
        {
            HeapFree(GetProcessHeap(), 0, lpNetResourceW);
            lpNetResourceW = HeapAlloc(GetProcessHeap(), 0, size);
            if (lpNetResourceW)
                ret = _thunkNetResourceArrayAToW(lpNetResource,
                        &count, lpNetResourceW, &size);
            else
                ret = WN_OUT_OF_MEMORY;
        }
        if (ret == WN_SUCCESS)
        {
            LPWSTR lpSystemW = NULL;
            LPVOID lpBufferW;
            size = 1024;
            lpBufferW = HeapAlloc(GetProcessHeap(), 0, size);
            if (lpBufferW)
            {
                ret = WNetGetResourceInformationW(lpNetResourceW,
                        lpBufferW, &size, &lpSystemW);
                if (ret == WN_MORE_DATA)
                {
                    HeapFree(GetProcessHeap(), 0, lpBufferW);
                    lpBufferW = HeapAlloc(GetProcessHeap(), 0, size);
                    if (lpBufferW)
                        ret = WNetGetResourceInformationW(lpNetResourceW,
                            lpBufferW, &size, &lpSystemW);
                    else
                        ret = WN_OUT_OF_MEMORY;
                }
                if (ret == WN_SUCCESS)
                {
                    ret = _thunkNetResourceArrayWToA(lpBufferW,
                            &count, lpBuffer, cbBuffer);
                    HeapFree(GetProcessHeap(), 0, lpNetResourceW);
                    lpNetResourceW = lpBufferW;
                    size = sizeof(NETRESOURCEA);
                    size += WideCharToMultiByte(CP_ACP, 0, lpNetResourceW->lpRemoteName,
                            -1, NULL, 0, NULL, NULL);
                    size += WideCharToMultiByte(CP_ACP, 0, lpNetResourceW->lpProvider,
                            -1, NULL, 0, NULL, NULL);

                    len = WideCharToMultiByte(CP_ACP, 0, lpSystemW,
                                      -1, NULL, 0, NULL, NULL);
                    if ((len) && ( size + len < *cbBuffer))
                    {
                        *lplpSystem = (char*)lpBuffer + *cbBuffer - len;
                        WideCharToMultiByte(CP_ACP, 0, lpSystemW, -1,
                             *lplpSystem, len, NULL, NULL);
                         ret = WN_SUCCESS;
                    }
                    else
                        ret = WN_MORE_DATA;
                }
                else
                    ret = WN_OUT_OF_MEMORY;
                HeapFree(GetProcessHeap(), 0, lpBufferW);
            }
            else
                ret = WN_OUT_OF_MEMORY;
            HeapFree(GetProcessHeap(), 0, lpSystemW);
        }
        HeapFree(GetProcessHeap(), 0, lpNetResourceW);
    }
    else
        ret = WN_NO_NETWORK;

    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*********************************************************************
 * WNetGetResourceInformationW [MPR.@]
 *
 * WNetGetResourceInformationW function identifies the network provider
 * that owns the resource and gets information about the type of the resource.
 *
 * PARAMS:
 *  lpNetResource    [ I]    the pointer to NETRESOURCEW structure, that
 *                          defines a network resource.
 *  lpBuffer         [ O]   the pointer to buffer, containing result. It
 *                          contains NETRESOURCEW structure and strings to
 *                          which the members of the NETRESOURCEW structure
 *                          point.
 *  cbBuffer         [I/O] the pointer to DWORD number - size of buffer
 *                          in bytes.
 *  lplpSystem       [ O]   the pointer to string in the output buffer,
 *                          containing the part of the resource name without
 *                          names of the server and share.
 *
 * RETURNS:
 *  NO_ERROR if the function succeeds. System error code if the function fails.
 */

DWORD WINAPI WNetGetResourceInformationW( LPNETRESOURCEW lpNetResource,
                                          LPVOID lpBuffer, LPDWORD cbBuffer,
                                          LPWSTR *lplpSystem )
{
    DWORD ret = WN_NO_NETWORK;
    DWORD index;

    TRACE( "(%p, %p, %p, %p)\n",
           lpNetResource, lpBuffer, cbBuffer, lplpSystem);

    if (!(lpBuffer))
        ret = WN_OUT_OF_MEMORY;
    else if (providerTable != NULL)
    {
        /* FIXME: For function value of a variable is indifferent, it does
         * search of all providers in a network.
         */
        for (index = 0; index < providerTable->numProviders; index++)
        {
            if(providerTable->table[index].getCaps(WNNC_DIALOG) &
                WNNC_DLG_GETRESOURCEINFORMATION)
            {
                if (providerTable->table[index].getResourceInformation)
                    ret = providerTable->table[index].getResourceInformation(
                        lpNetResource, lpBuffer, cbBuffer, lplpSystem);
                else
                    ret = WN_NO_NETWORK;
                if (ret == WN_SUCCESS)
                    break;
            }
        }
    }
    if (ret)
        SetLastError(ret);
    return ret;
}

/*********************************************************************
 * WNetGetResourceParentA [MPR.@]
 */
DWORD WINAPI WNetGetResourceParentA( LPNETRESOURCEA lpNetResource,
                                     LPVOID lpBuffer, LPDWORD lpBufferSize )
{
    FIXME( "(%p, %p, %p): stub\n",
           lpNetResource, lpBuffer, lpBufferSize );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetGetResourceParentW [MPR.@]
 */
DWORD WINAPI WNetGetResourceParentW( LPNETRESOURCEW lpNetResource,
                                     LPVOID lpBuffer, LPDWORD lpBufferSize )
{
    FIXME( "(%p, %p, %p): stub\n",
           lpNetResource, lpBuffer, lpBufferSize );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}



/*
 * Connection Functions
 */

/*********************************************************************
 *  WNetAddConnectionA [MPR.@]
 */
DWORD WINAPI WNetAddConnectionA( LPCSTR lpRemoteName, LPCSTR lpPassword,
                                 LPCSTR lpLocalName )
{
    NETRESOURCEA resourcesA;

    memset(&resourcesA, 0, sizeof(resourcesA));
    resourcesA.lpRemoteName = (LPSTR)lpRemoteName;
    resourcesA.lpLocalName = (LPSTR)lpLocalName;
    return WNetUseConnectionA(NULL, &resourcesA, lpPassword, NULL, 0, NULL, 0, NULL);
}

/*********************************************************************
 *  WNetAddConnectionW [MPR.@]
 */
DWORD WINAPI WNetAddConnectionW( LPCWSTR lpRemoteName, LPCWSTR lpPassword,
                                 LPCWSTR lpLocalName )
{
    NETRESOURCEW resourcesW;

    memset(&resourcesW, 0, sizeof(resourcesW));
    resourcesW.lpRemoteName = (LPWSTR)lpRemoteName;
    resourcesW.lpLocalName = (LPWSTR)lpLocalName;
    return WNetUseConnectionW(NULL, &resourcesW, lpPassword, NULL, 0, NULL, 0, NULL);
}

/*********************************************************************
 *  WNetAddConnection2A [MPR.@]
 */
DWORD WINAPI WNetAddConnection2A( LPNETRESOURCEA lpNetResource,
                                  LPCSTR lpPassword, LPCSTR lpUserID,
                                  DWORD dwFlags )
{
    return WNetUseConnectionA(NULL, lpNetResource, lpPassword, lpUserID, dwFlags,
                              NULL, 0, NULL);
}

/*********************************************************************
 * WNetAddConnection2W [MPR.@]
 */
DWORD WINAPI WNetAddConnection2W( LPNETRESOURCEW lpNetResource,
                                  LPCWSTR lpPassword, LPCWSTR lpUserID,
                                  DWORD dwFlags )
{
    return WNetUseConnectionW(NULL, lpNetResource, lpPassword, lpUserID, dwFlags,
                              NULL, 0, NULL);
}

/*********************************************************************
 * WNetAddConnection3A [MPR.@]
 */
DWORD WINAPI WNetAddConnection3A( HWND hwndOwner, LPNETRESOURCEA lpNetResource,
                                  LPCSTR lpPassword, LPCSTR lpUserID,
                                  DWORD dwFlags )
{
    return WNetUseConnectionA(hwndOwner, lpNetResource, lpPassword, lpUserID,
                              dwFlags, NULL, 0, NULL);
}

/*********************************************************************
 * WNetAddConnection3W [MPR.@]
 */
DWORD WINAPI WNetAddConnection3W( HWND hwndOwner, LPNETRESOURCEW lpNetResource,
                                  LPCWSTR lpPassword, LPCWSTR lpUserID,
                                  DWORD dwFlags )
{
    return WNetUseConnectionW(hwndOwner, lpNetResource, lpPassword, lpUserID,
                              dwFlags, NULL, 0, NULL);
}

struct use_connection_context
{
    HWND hwndOwner;
    NETRESOURCEW *resource;
    NETRESOURCEA *resourceA; /* only set for WNetUseConnectionA */
    WCHAR *password;
    WCHAR *userid;
    DWORD flags;
    void *accessname;
    DWORD *buffer_size;
    DWORD *result;
    DWORD (*pre_set_accessname)(struct use_connection_context*);
    void  (*set_accessname)(struct use_connection_context*);
};

static DWORD use_connection_pre_set_accessnameW(struct use_connection_context *ctxt)
{
    if (ctxt->accessname && ctxt->buffer_size && *ctxt->buffer_size)
    {
        DWORD len;

        if (ctxt->resource->lpLocalName)
            len = strlenW(ctxt->resource->lpLocalName);
        else
            len = strlenW(ctxt->resource->lpRemoteName);

        if (++len > *ctxt->buffer_size)
        {
            *ctxt->buffer_size = len;
            return ERROR_MORE_DATA;
        }
    }
    else
        ctxt->accessname = NULL;

    return ERROR_SUCCESS;
}

static void use_connection_set_accessnameW(struct use_connection_context *ctxt)
{
    WCHAR *accessname = ctxt->accessname;
    if (ctxt->resource->lpLocalName)
        strcpyW(accessname, ctxt->resource->lpLocalName);
    else
        strcpyW(accessname, ctxt->resource->lpRemoteName);
}

static DWORD wnet_use_connection( struct use_connection_context *ctxt )
{
    WNetProvider *provider;
    DWORD index, ret, caps;

    if (!providerTable || providerTable->numProviders == 0)
        return WN_NO_NETWORK;

    if (!ctxt->resource)
        return ERROR_INVALID_PARAMETER;

    if (!ctxt->resource->lpProvider)
    {
        FIXME("Networking provider selection is not implemented.\n");
        return WN_NO_NETWORK;
    }

    if (!ctxt->resource->lpLocalName && (ctxt->flags & CONNECT_REDIRECT))
    {
        FIXME("Locale device selection is not implemented.\n");
        return WN_NO_NETWORK;
    }

    if (ctxt->flags & CONNECT_INTERACTIVE)
        return ERROR_BAD_NET_NAME;

    index = _findProviderIndexW(ctxt->resource->lpProvider);
    if (index == BAD_PROVIDER_INDEX)
        return ERROR_BAD_PROVIDER;

    provider = &providerTable->table[index];
    caps = provider->getCaps(WNNC_CONNECTION);
    if (!(caps & (WNNC_CON_ADDCONNECTION | WNNC_CON_ADDCONNECTION3)))
        return ERROR_BAD_PROVIDER;

    if ((ret = ctxt->pre_set_accessname(ctxt)))
        return ret;

    ret = WN_ACCESS_DENIED;
    if ((caps & WNNC_CON_ADDCONNECTION3) && provider->addConnection3)
        ret = provider->addConnection3(ctxt->hwndOwner, ctxt->resource, ctxt->password, ctxt->userid, ctxt->flags);
    else if ((caps & WNNC_CON_ADDCONNECTION) && provider->addConnection)
        ret = provider->addConnection(ctxt->resource, ctxt->password, ctxt->userid);

    if (ret == WN_SUCCESS && ctxt->accessname)
        ctxt->set_accessname(ctxt);

    return ret;
}

/*****************************************************************
 *  WNetUseConnectionW [MPR.@]
 */
DWORD WINAPI WNetUseConnectionW( HWND hwndOwner, NETRESOURCEW *resource, LPCWSTR password,
    LPCWSTR userid, DWORD flags, LPWSTR accessname, DWORD *buffer_size, DWORD *result )
{
    struct use_connection_context ctxt;

    TRACE( "(%p, %p, %p, %s, 0x%08X, %p, %p, %p)\n",
           hwndOwner, resource, password, debugstr_w(userid), flags,
           accessname, buffer_size, result );

    ctxt.hwndOwner = hwndOwner;
    ctxt.resource = resource;
    ctxt.resourceA = NULL;
    ctxt.password = (WCHAR*)password;
    ctxt.userid = (WCHAR*)userid;
    ctxt.flags = flags;
    ctxt.accessname = accessname;
    ctxt.buffer_size = buffer_size;
    ctxt.result = result;
    ctxt.pre_set_accessname = use_connection_pre_set_accessnameW;
    ctxt.set_accessname = use_connection_set_accessnameW;

    return wnet_use_connection(&ctxt);
}

static DWORD use_connection_pre_set_accessnameA(struct use_connection_context *ctxt)
{
    if (ctxt->accessname && ctxt->buffer_size && *ctxt->buffer_size)
    {
        DWORD len;

        if (ctxt->resourceA->lpLocalName)
            len = strlen(ctxt->resourceA->lpLocalName);
        else
            len = strlen(ctxt->resourceA->lpRemoteName);

        if (++len > *ctxt->buffer_size)
        {
            *ctxt->buffer_size = len;
            return ERROR_MORE_DATA;
        }
    }
    else
        ctxt->accessname = NULL;

    return ERROR_SUCCESS;
}

static void use_connection_set_accessnameA(struct use_connection_context *ctxt)
{
    char *accessname = ctxt->accessname;
    if (ctxt->resourceA->lpLocalName)
        strcpy(accessname, ctxt->resourceA->lpLocalName);
    else
        strcpy(accessname, ctxt->resourceA->lpRemoteName);
}

static LPWSTR strdupAtoW( LPCSTR str )
{
    LPWSTR ret;
    INT len;

    if (!str) return NULL;
    len = MultiByteToWideChar( CP_ACP, 0, str, -1, NULL, 0 );
    ret = HeapAlloc( GetProcessHeap(), 0, len * sizeof(WCHAR) );
    if (ret) MultiByteToWideChar( CP_ACP, 0, str, -1, ret, len );
    return ret;
}

static void netresource_a_to_w( NETRESOURCEA *resourceA, NETRESOURCEW *resourceW )
{
    resourceW->dwScope = resourceA->dwScope;
    resourceW->dwType = resourceA->dwType;
    resourceW->dwDisplayType = resourceA->dwDisplayType;
    resourceW->dwUsage = resourceA->dwUsage;
    resourceW->lpLocalName = strdupAtoW(resourceA->lpLocalName);
    resourceW->lpRemoteName = strdupAtoW(resourceA->lpRemoteName);
    resourceW->lpComment = strdupAtoW(resourceA->lpComment);
    resourceW->lpProvider = strdupAtoW(resourceA->lpProvider);
}

static void free_netresourceW( NETRESOURCEW *resource )
{
    HeapFree(GetProcessHeap(), 0, resource->lpLocalName);
    HeapFree(GetProcessHeap(), 0, resource->lpRemoteName);
    HeapFree(GetProcessHeap(), 0, resource->lpComment);
    HeapFree(GetProcessHeap(), 0, resource->lpProvider);
}

/*****************************************************************
 *  WNetUseConnectionA [MPR.@]
 */
DWORD WINAPI WNetUseConnectionA( HWND hwndOwner, NETRESOURCEA *resource,
    LPCSTR password, LPCSTR userid, DWORD flags, LPSTR accessname,
    DWORD *buffer_size, DWORD *result )
{
    struct use_connection_context ctxt;
    NETRESOURCEW resourceW;
    DWORD ret;

    TRACE( "(%p, %p, %p, %s, 0x%08X, %p, %p, %p)\n", hwndOwner, resource, password, debugstr_a(userid), flags,
        accessname, buffer_size, result );

    netresource_a_to_w(resource, &resourceW);

    ctxt.hwndOwner = hwndOwner;
    ctxt.resource = &resourceW;
    ctxt.resourceA = resource;
    ctxt.password = strdupAtoW(password);
    ctxt.userid = strdupAtoW(userid);
    ctxt.flags = flags;
    ctxt.accessname = accessname;
    ctxt.buffer_size = buffer_size;
    ctxt.result = result;
    ctxt.pre_set_accessname = use_connection_pre_set_accessnameA;
    ctxt.set_accessname = use_connection_set_accessnameA;

    ret = wnet_use_connection(&ctxt);

    free_netresourceW(&resourceW);
    HeapFree(GetProcessHeap(), 0, ctxt.password);
    HeapFree(GetProcessHeap(), 0, ctxt.userid);

    return ret;
}

/*********************************************************************
 *  WNetCancelConnectionA [MPR.@]
 */
DWORD WINAPI WNetCancelConnectionA( LPCSTR lpName, BOOL fForce )
{
    FIXME( "(%s, %d), stub\n", debugstr_a(lpName), fForce );

    return WN_SUCCESS;
}

/*********************************************************************
 *  WNetCancelConnectionW [MPR.@]
 */
DWORD WINAPI WNetCancelConnectionW( LPCWSTR lpName, BOOL fForce )
{
    FIXME( "(%s, %d), stub\n", debugstr_w(lpName), fForce );

    return WN_SUCCESS;
}

/*********************************************************************
 *  WNetCancelConnection2A [MPR.@]
 */
DWORD WINAPI WNetCancelConnection2A( LPCSTR lpName, DWORD dwFlags, BOOL fForce )
{
    FIXME( "(%s, %08X, %d), stub\n", debugstr_a(lpName), dwFlags, fForce );

    return WN_SUCCESS;
}

/*********************************************************************
 *  WNetCancelConnection2W [MPR.@]
 */
DWORD WINAPI WNetCancelConnection2W( LPCWSTR lpName, DWORD dwFlags, BOOL fForce )
{
    FIXME( "(%s, %08X, %d), stub\n", debugstr_w(lpName), dwFlags, fForce );

    return WN_SUCCESS;
}

/*****************************************************************
 *  WNetRestoreConnectionA [MPR.@]
 */
DWORD WINAPI WNetRestoreConnectionA( HWND hwndOwner, LPCSTR lpszDevice )
{
    FIXME( "(%p, %s), stub\n", hwndOwner, debugstr_a(lpszDevice) );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*****************************************************************
 *  WNetRestoreConnectionW [MPR.@]
 */
DWORD WINAPI WNetRestoreConnectionW( HWND hwndOwner, LPCWSTR lpszDevice )
{
    FIXME( "(%p, %s), stub\n", hwndOwner, debugstr_w(lpszDevice) );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/**************************************************************************
 * WNetGetConnectionA [MPR.@]
 *
 * RETURNS
 * - WN_BAD_LOCALNAME     lpLocalName makes no sense
 * - WN_NOT_CONNECTED     drive is a local drive
 * - WN_MORE_DATA         buffer isn't big enough
 * - WN_SUCCESS           success (net path in buffer)
 *
 * FIXME: need to test return values under different errors
 */
DWORD WINAPI WNetGetConnectionA( LPCSTR lpLocalName,
                                 LPSTR lpRemoteName, LPDWORD lpBufferSize )
{
    DWORD ret;

    if (!lpLocalName)
        ret = WN_BAD_POINTER;
    else if (!lpBufferSize)
        ret = WN_BAD_POINTER;
    else if (!lpRemoteName && *lpBufferSize)
        ret = WN_BAD_POINTER;
    else
    {
        int len = MultiByteToWideChar(CP_ACP, 0, lpLocalName, -1, NULL, 0);

        if (len)
        {
            PWSTR wideLocalName = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));

            if (wideLocalName)
            {
                WCHAR wideRemoteStatic[MAX_PATH];
                DWORD wideRemoteSize = sizeof(wideRemoteStatic) / sizeof(WCHAR);

                MultiByteToWideChar(CP_ACP, 0, lpLocalName, -1, wideLocalName, len);

                /* try once without memory allocation */
                ret = WNetGetConnectionW(wideLocalName, wideRemoteStatic,
                 &wideRemoteSize);
                if (ret == WN_SUCCESS)
                {
                    int len = WideCharToMultiByte(CP_ACP, 0, wideRemoteStatic,
                     -1, NULL, 0, NULL, NULL);

                    if (len <= *lpBufferSize)
                    {
                        WideCharToMultiByte(CP_ACP, 0, wideRemoteStatic, -1,
                         lpRemoteName, *lpBufferSize, NULL, NULL);
                        ret = WN_SUCCESS;
                    }
                    else
                    {
                        *lpBufferSize = len;
                        ret = WN_MORE_DATA;
                    }
                }
                else if (ret == WN_MORE_DATA)
                {
                    PWSTR wideRemote = HeapAlloc(GetProcessHeap(), 0,
                     wideRemoteSize * sizeof(WCHAR));

                    if (wideRemote)
                    {
                        ret = WNetGetConnectionW(wideLocalName, wideRemote,
                         &wideRemoteSize);
                        if (ret == WN_SUCCESS)
                        {
                            if (len <= *lpBufferSize)
                            {
                                WideCharToMultiByte(CP_ACP, 0, wideRemoteStatic,
                                 -1, lpRemoteName, *lpBufferSize, NULL, NULL);
                                ret = WN_SUCCESS;
                            }
                            else
                            {
                                *lpBufferSize = len;
                                ret = WN_MORE_DATA;
                            }
                        }
                        HeapFree(GetProcessHeap(), 0, wideRemote);
                    }
                    else
                        ret = WN_OUT_OF_MEMORY;
                }
                HeapFree(GetProcessHeap(), 0, wideLocalName);
            }
            else
                ret = WN_OUT_OF_MEMORY;
        }
        else
            ret = WN_BAD_LOCALNAME;
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/* find the network connection for a given drive; helper for WNetGetConnection */
static DWORD get_drive_connection( WCHAR letter, LPWSTR remote, LPDWORD size )
{
    char buffer[1024];
    struct mountmgr_unix_drive *data = (struct mountmgr_unix_drive *)buffer;
    HANDLE mgr;
    DWORD ret = WN_NOT_CONNECTED;
    DWORD bytes_returned;

    if ((mgr = CreateFileW( MOUNTMGR_DOS_DEVICE_NAME, GENERIC_READ|GENERIC_WRITE,
                            FILE_SHARE_READ|FILE_SHARE_WRITE, NULL, OPEN_EXISTING,
                            0, 0 )) == INVALID_HANDLE_VALUE)
    {
        ERR( "failed to open mount manager err %u\n", GetLastError() );
        return ret;
    }
    memset( data, 0, sizeof(*data) );
    data->letter = letter;
    if (DeviceIoControl( mgr, IOCTL_MOUNTMGR_QUERY_UNIX_DRIVE, data, sizeof(*data),
                         data, sizeof(buffer), &bytes_returned, NULL ))
    {
        char *p, *mount_point = buffer + data->mount_point_offset;
        DWORD len;

        if (data->mount_point_offset && !strncmp( mount_point, "unc/", 4 ))
        {
            mount_point += 2;
            mount_point[0] = '\\';
            for (p = mount_point; *p; p++) if (*p == '/') *p = '\\';

            len = MultiByteToWideChar( CP_UNIXCP, 0, mount_point, -1, NULL, 0 );
            if (len > *size)
            {
                *size = len;
                ret = WN_MORE_DATA;
            }
            else
            {
                *size = MultiByteToWideChar( CP_UNIXCP, 0, mount_point, -1, remote, *size);
                ret = WN_SUCCESS;
            }
        }
    }
    CloseHandle( mgr );
    return ret;
}

/**************************************************************************
 * WNetGetConnectionW [MPR.@]
 *
 * FIXME: need to test return values under different errors
 */
DWORD WINAPI WNetGetConnectionW( LPCWSTR lpLocalName,
                                 LPWSTR lpRemoteName, LPDWORD lpBufferSize )
{
    DWORD ret;

    TRACE("(%s, %p, %p)\n", debugstr_w(lpLocalName), lpRemoteName,
     lpBufferSize);

    if (!lpLocalName)
        ret = WN_BAD_POINTER;
    else if (!lpBufferSize)
        ret = WN_BAD_POINTER;
    else if (!lpRemoteName && *lpBufferSize)
        ret = WN_BAD_POINTER;
    else if (!lpLocalName[0])
        ret = WN_BAD_LOCALNAME;
    else
    {
        if (lpLocalName[1] == ':')
        {
            switch(GetDriveTypeW(lpLocalName))
            {
            case DRIVE_REMOTE:
                ret = get_drive_connection( lpLocalName[0], lpRemoteName, lpBufferSize );
                break;
            case DRIVE_REMOVABLE:
            case DRIVE_FIXED:
            case DRIVE_CDROM:
                TRACE("file is local\n");
                ret = WN_NOT_CONNECTED;
                break;
            default:
                ret = WN_BAD_LOCALNAME;
            }
        }
        else
            ret = WN_BAD_LOCALNAME;
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/**************************************************************************
 * WNetSetConnectionA [MPR.@]
 */
DWORD WINAPI WNetSetConnectionA( LPCSTR lpName, DWORD dwProperty,
                                 LPVOID pvValue )
{
    FIXME( "(%s, %08X, %p): stub\n", debugstr_a(lpName), dwProperty, pvValue );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/**************************************************************************
 * WNetSetConnectionW [MPR.@]
 */
DWORD WINAPI WNetSetConnectionW( LPCWSTR lpName, DWORD dwProperty,
                                 LPVOID pvValue )
{
    FIXME( "(%s, %08X, %p): stub\n", debugstr_w(lpName), dwProperty, pvValue );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*****************************************************************
 * WNetGetUniversalNameA [MPR.@]
 */
DWORD WINAPI WNetGetUniversalNameA ( LPCSTR lpLocalPath, DWORD dwInfoLevel,
                                     LPVOID lpBuffer, LPDWORD lpBufferSize )
{
    DWORD err, size;

    FIXME( "(%s, 0x%08X, %p, %p): stub\n",
           debugstr_a(lpLocalPath), dwInfoLevel, lpBuffer, lpBufferSize);

    switch (dwInfoLevel)
    {
    case UNIVERSAL_NAME_INFO_LEVEL:
    {
        LPUNIVERSAL_NAME_INFOA info = lpBuffer;

        if (GetDriveTypeA(lpLocalPath) != DRIVE_REMOTE)
        {
            err = ERROR_NOT_CONNECTED;
            break;
        }

        size = sizeof(*info) + lstrlenA(lpLocalPath) + 1;
        if (*lpBufferSize < size)
        {
            err = WN_MORE_DATA;
            break;
        }
        info->lpUniversalName = (char *)info + sizeof(*info);
        lstrcpyA(info->lpUniversalName, lpLocalPath);
        err = WN_NO_ERROR;
        break;
    }
    case REMOTE_NAME_INFO_LEVEL:
        err = WN_NO_NETWORK;
        break;

    default:
        err = WN_BAD_VALUE;
        break;
    }

    SetLastError(err);
    return err;
}

/*****************************************************************
 * WNetGetUniversalNameW [MPR.@]
 */
DWORD WINAPI WNetGetUniversalNameW ( LPCWSTR lpLocalPath, DWORD dwInfoLevel,
                                     LPVOID lpBuffer, LPDWORD lpBufferSize )
{
    DWORD err, size;

    FIXME( "(%s, 0x%08X, %p, %p): stub\n",
           debugstr_w(lpLocalPath), dwInfoLevel, lpBuffer, lpBufferSize);

    switch (dwInfoLevel)
    {
    case UNIVERSAL_NAME_INFO_LEVEL:
    {
        LPUNIVERSAL_NAME_INFOW info = lpBuffer;

        if (GetDriveTypeW(lpLocalPath) != DRIVE_REMOTE)
        {
            err = ERROR_NOT_CONNECTED;
            break;
        }

        size = sizeof(*info) + (lstrlenW(lpLocalPath) + 1) * sizeof(WCHAR);
        if (*lpBufferSize < size)
        {
            err = WN_MORE_DATA;
            break;
        }
        info->lpUniversalName = (LPWSTR)((char *)info + sizeof(*info));
        lstrcpyW(info->lpUniversalName, lpLocalPath);
        err = WN_NO_ERROR;
        break;
    }
    case REMOTE_NAME_INFO_LEVEL:
        err = WN_NO_NETWORK;
        break;

    default:
        err = WN_BAD_VALUE;
        break;
    }

    if (err != WN_NO_ERROR) SetLastError(err);
    return err;
}



/*
 * Other Functions
 */

/**************************************************************************
 * WNetGetUserA [MPR.@]
 *
 * FIXME: we should not return ourselves, but the owner of the drive lpName
 */
DWORD WINAPI WNetGetUserA( LPCSTR lpName, LPSTR lpUserID, LPDWORD lpBufferSize )
{
    if (GetUserNameA( lpUserID, lpBufferSize )) return WN_SUCCESS;
    return GetLastError();
}

/*****************************************************************
 * WNetGetUserW [MPR.@]
 *
 * FIXME: we should not return ourselves, but the owner of the drive lpName
 */
DWORD WINAPI WNetGetUserW( LPCWSTR lpName, LPWSTR lpUserID, LPDWORD lpBufferSize )
{
    if (GetUserNameW( lpUserID, lpBufferSize )) return WN_SUCCESS;
    return GetLastError();
}

/*********************************************************************
 * WNetConnectionDialog [MPR.@]
 */
DWORD WINAPI WNetConnectionDialog( HWND hwnd, DWORD dwType )
{
    FIXME( "(%p, %08X): stub\n", hwnd, dwType );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetConnectionDialog1A [MPR.@]
 */
DWORD WINAPI WNetConnectionDialog1A( LPCONNECTDLGSTRUCTA lpConnDlgStruct )
{
    FIXME( "(%p): stub\n", lpConnDlgStruct );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetConnectionDialog1W [MPR.@]
 */
DWORD WINAPI WNetConnectionDialog1W( LPCONNECTDLGSTRUCTW lpConnDlgStruct )
{
    FIXME( "(%p): stub\n", lpConnDlgStruct );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetDisconnectDialog [MPR.@]
 */
DWORD WINAPI WNetDisconnectDialog( HWND hwnd, DWORD dwType )
{
    FIXME( "(%p, %08X): stub\n", hwnd, dwType );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetDisconnectDialog1A [MPR.@]
 */
DWORD WINAPI WNetDisconnectDialog1A( LPDISCDLGSTRUCTA lpConnDlgStruct )
{
    FIXME( "(%p): stub\n", lpConnDlgStruct );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetDisconnectDialog1W [MPR.@]
 */
DWORD WINAPI WNetDisconnectDialog1W( LPDISCDLGSTRUCTW lpConnDlgStruct )
{
    FIXME( "(%p): stub\n", lpConnDlgStruct );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetGetLastErrorA [MPR.@]
 */
DWORD WINAPI WNetGetLastErrorA( LPDWORD lpError,
                                LPSTR lpErrorBuf, DWORD nErrorBufSize,
                                LPSTR lpNameBuf, DWORD nNameBufSize )
{
    FIXME( "(%p, %p, %d, %p, %d): stub\n",
           lpError, lpErrorBuf, nErrorBufSize, lpNameBuf, nNameBufSize );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetGetLastErrorW [MPR.@]
 */
DWORD WINAPI WNetGetLastErrorW( LPDWORD lpError,
                                LPWSTR lpErrorBuf, DWORD nErrorBufSize,
                         LPWSTR lpNameBuf, DWORD nNameBufSize )
{
    FIXME( "(%p, %p, %d, %p, %d): stub\n",
           lpError, lpErrorBuf, nErrorBufSize, lpNameBuf, nNameBufSize );

    SetLastError(WN_NO_NETWORK);
    return WN_NO_NETWORK;
}

/*********************************************************************
 * WNetGetNetworkInformationA [MPR.@]
 */
DWORD WINAPI WNetGetNetworkInformationA( LPCSTR lpProvider,
                                         LPNETINFOSTRUCT lpNetInfoStruct )
{
    DWORD ret;

    TRACE( "(%s, %p)\n", debugstr_a(lpProvider), lpNetInfoStruct );

    if (!lpProvider)
        ret = WN_BAD_POINTER;
    else
    {
        int len;

        len = MultiByteToWideChar(CP_ACP, 0, lpProvider, -1, NULL, 0);
        if (len)
        {
            LPWSTR wideProvider = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));

            if (wideProvider)
            {
                MultiByteToWideChar(CP_ACP, 0, lpProvider, -1, wideProvider,
                 len);
                ret = WNetGetNetworkInformationW(wideProvider, lpNetInfoStruct);
                HeapFree(GetProcessHeap(), 0, wideProvider);
            }
            else
                ret = WN_OUT_OF_MEMORY;
        }
        else
            ret = GetLastError();
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*********************************************************************
 * WNetGetNetworkInformationW [MPR.@]
 */
DWORD WINAPI WNetGetNetworkInformationW( LPCWSTR lpProvider,
                                         LPNETINFOSTRUCT lpNetInfoStruct )
{
    DWORD ret;

    TRACE( "(%s, %p)\n", debugstr_w(lpProvider), lpNetInfoStruct );

    if (!lpProvider)
        ret = WN_BAD_POINTER;
    else if (!lpNetInfoStruct)
        ret = WN_BAD_POINTER;
    else if (lpNetInfoStruct->cbStructure < sizeof(NETINFOSTRUCT))
        ret = WN_BAD_VALUE;
    else
    {
        if (providerTable && providerTable->numProviders)
        {
            DWORD providerIndex = _findProviderIndexW(lpProvider);

            if (providerIndex != BAD_PROVIDER_INDEX)
            {
                lpNetInfoStruct->cbStructure = sizeof(NETINFOSTRUCT);
                lpNetInfoStruct->dwProviderVersion =
                 providerTable->table[providerIndex].dwSpecVersion;
                lpNetInfoStruct->dwStatus = NO_ERROR;
                lpNetInfoStruct->dwCharacteristics = 0;
                lpNetInfoStruct->dwHandle = 0;
                lpNetInfoStruct->wNetType =
                 HIWORD(providerTable->table[providerIndex].dwNetType);
                lpNetInfoStruct->dwPrinters = -1;
                lpNetInfoStruct->dwDrives = -1;
                ret = WN_SUCCESS;
            }
            else
                ret = WN_BAD_PROVIDER;
        }
        else
            ret = WN_NO_NETWORK;
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*****************************************************************
 *  WNetGetProviderNameA [MPR.@]
 */
DWORD WINAPI WNetGetProviderNameA( DWORD dwNetType,
                                   LPSTR lpProvider, LPDWORD lpBufferSize )
{
    DWORD ret;

    TRACE("(0x%08x, %s, %p)\n", dwNetType, debugstr_a(lpProvider),
     lpBufferSize);

    if (!lpProvider)
        ret = WN_BAD_POINTER;
    else if (!lpBufferSize)
        ret = WN_BAD_POINTER;
    else
    {
        if (providerTable)
        {
            DWORD i;

            ret = WN_NO_NETWORK;
            for (i = 0; i < providerTable->numProviders &&
             HIWORD(providerTable->table[i].dwNetType) != HIWORD(dwNetType);
             i++)
                ;
            if (i < providerTable->numProviders)
            {
                DWORD sizeNeeded = WideCharToMultiByte(CP_ACP, 0,
                 providerTable->table[i].name, -1, NULL, 0, NULL, NULL);

                if (*lpBufferSize < sizeNeeded)
                {
                    *lpBufferSize = sizeNeeded;
                    ret = WN_MORE_DATA;
                }
                else
                {
                    WideCharToMultiByte(CP_ACP, 0, providerTable->table[i].name,
                     -1, lpProvider, *lpBufferSize, NULL, NULL);
                    ret = WN_SUCCESS;
                    /* FIXME: is *lpBufferSize set to the number of characters
                     * copied? */
                }
            }
        }
        else
            ret = WN_NO_NETWORK;
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}

/*****************************************************************
 *  WNetGetProviderNameW [MPR.@]
 */
DWORD WINAPI WNetGetProviderNameW( DWORD dwNetType,
                                   LPWSTR lpProvider, LPDWORD lpBufferSize )
{
    DWORD ret;

    TRACE("(0x%08x, %s, %p)\n", dwNetType, debugstr_w(lpProvider),
     lpBufferSize);

    if (!lpProvider)
        ret = WN_BAD_POINTER;
    else if (!lpBufferSize)
        ret = WN_BAD_POINTER;
    else
    {
        if (providerTable)
        {
            DWORD i;

            ret = WN_NO_NETWORK;
            for (i = 0; i < providerTable->numProviders &&
             HIWORD(providerTable->table[i].dwNetType) != HIWORD(dwNetType);
             i++)
                ;
            if (i < providerTable->numProviders)
            {
                DWORD sizeNeeded = strlenW(providerTable->table[i].name) + 1;

                if (*lpBufferSize < sizeNeeded)
                {
                    *lpBufferSize = sizeNeeded;
                    ret = WN_MORE_DATA;
                }
                else
                {
                    strcpyW(lpProvider, providerTable->table[i].name);
                    ret = WN_SUCCESS;
                    /* FIXME: is *lpBufferSize set to the number of characters
                     * copied? */
                }
            }
        }
        else
            ret = WN_NO_NETWORK;
    }
    if (ret)
        SetLastError(ret);
    TRACE("Returning %d\n", ret);
    return ret;
}
