Search
Module:
Directory

   Desktop Functions:

   Smart Device Functions:


Show Recent Changes
Subscribe (RSS)
Misc. Pages
Comments
FAQ
Helpful Tools
Playground
Suggested Reading
Website TODO List
Download Visual Studio Add-In

WNetGetUniversalName (advapi32)
 
.
Summary
TODO - a short description

C# Signature:

[DllImport("mpr.dll")]
[return:MarshalAs(UnmanagedType.U4)]
static extern int WNetGetUniversalName(
    string lpLocalPath,
    [MarshalAs(UnmanagedType.U4)] int dwInfoLevel,
    IntPtr lpBuffer,
    [MarshalAs(UnmanagedType.U4)] ref int lpBufferSize);

VB Signature:

Declare Function WNetGetUniversalName Lib "advapi32.dll" (TODO) As TODO

Constants:

const int UNIVERSAL_NAME_INFO_LEVEL = 0x00000001;
const int REMOTE_NAME_INFO_LEVEL = 0x00000002;

const int ERROR_MORE_DATA = 234;
const int NOERROR = 0;

Wrapper

    using System.Runtime.InteropServices;

    static string GetUniversalName(string localPath)
    {
        // The return value.
        string retVal = null ;

        // The pointer in memory to the structure.
        IntPtr buffer = IntPtr.Zero;

        // Wrap in a try/catch block for cleanup.
        try
        {
        // First, call WNetGetUniversalName to get the size.
        int size = 0;

        // Make the call.
        // Pass IntPtr.Size because the API doesn't like null, even though
        // size is zero.  We know that IntPtr.Size will be
        // aligned correctly.
        int apiRetVal = WNetGetUniversalName(localPath, UNIVERSAL_NAME_INFO_LEVEL, (IntPtr) IntPtr.Size, ref size);

        // If the return value is not ERROR_MORE_DATA, then
        // raise an exception.
        if (apiRetVal != ERROR_MORE_DATA)
            // Throw an exception.
            throw new Win32Exception(apiRetVal);

        // Allocate the memory.
        buffer = Marshal.AllocCoTaskMem(size);

        // Now make the call.
        apiRetVal = WNetGetUniversalName(localPath, UNIVERSAL_NAME_INFO_LEVEL, buffer, ref size);

        // If it didn't succeed, then throw.
        if (apiRetVal != NOERROR)
            // Throw an exception.
            throw new Win32Exception(apiRetVal);

        // Now get the string.  It's all in the same buffer, but
        // the pointer is first, so offset the pointer by IntPtr.Size
        // and pass to PtrToStringAuto.
        retVal = Marshal.PtrToStringAuto(new IntPtr(buffer.ToInt64() + IntPtr.Size));
        }
        finally
        {
        // Release the buffer.
        Marshal.FreeCoTaskMem(buffer);
        }

        // First, allocate the memory for the structure.

        // That's all folks.
        return retVal;
    }

Notes:

Note by Günter Prossliner 2005-08-29

PtrToStringAuto doesn't work on my system. I have tested in on a clean WindowsXP professional maschine. The PtrToStringAuto function just returns garbage. After stepping into the function with the debugger I was looking a the Memory - Windows pointing to the address of "buffer". What I've seen there was a "normal" zero - terminated ANSI String.

After i have changed

retVal = Marshal.PtrToStringAuto(new IntPtr(buffer.ToInt64() + IntPtr.Size));

into

retVal = Marshal.PtrToStringAnsi(new IntPtr(buffer.ToInt64() + IntPtr.Size), size);

all worked fine.

If you take a look at the IL - Code of Marshal.PtrToStringAuto(IntPtr) you can see that this function calls 'kernel32:lstrlen' and 'kernel32:lstrcpy' using a buffer (StringBuilder) with the size of lstrlen.

The code of Marshal.PtrToStringAuto(IntPtr, Int32 size) looks quite different: It checks out the Marshal.SystemDefaultCharSize field and simply calls 'PtrToStringAnsi' or 'PtrToStringUni'.

Tips & Tricks:

Please add some!

Sample Code:

/* This needs cleaning up -- errr but I'm paid by the hour so I don't have the time. I mostly ripped the wrapper and modified it. It provides an alternative to pointer arithmetic though...*/

    /*
    typedef struct _REMOTE_NAME_INFO
            {
                LPTSTR lpUniversalName;  LPTSTR lpConnectionName;  LPTSTR lpRemainingPath;
            } REMOTE_NAME_INFO;

      • /

    [StructLayout(LayoutKind.Sequential)]
    struct _REMOTE_NAME_INFO
    {
        public IntPtr lpUniversalName;
        public IntPtr lpConnectionName;  
        public IntPtr lpRemainingPath;
    }

    public struct RemoteNameInfo
    {
        public string universalName;
        public string connectionName;
        public string remainingPath;
    }

    public class WNet
    {
        const int UNIVERSAL_NAME_INFO_LEVEL = 0x00000001;
        const int REMOTE_NAME_INFO_LEVEL = 0x00000002;

        const int ERROR_MORE_DATA = 234;
        const int NOERROR = 0;

        [DllImport("mpr.dll", CharSet=CharSet.Unicode)]
        [return:MarshalAs(UnmanagedType.U4)]
        private static extern int WNetGetUniversalNameW(
            string lpLocalPath,
            [MarshalAs(UnmanagedType.U4)] int dwInfoLevel,
            IntPtr lpBuffer,
            [MarshalAs(UnmanagedType.U4)] ref int lpBufferSize);

    public static    RemoteNameInfo GetRemoteNameInfo(string localPath)
        {
            // The return value.
            RemoteNameInfo retVal  ;
            _REMOTE_NAME_INFO rni;

            // The pointer in memory to the structure.
            IntPtr buffer = IntPtr.Zero;

            // Wrap in a try/catch block for cleanup.
            try
            {
                // First, call WNetGetUniversalName to get the size.
                int size = 0;

                // Make the call.
                // Pass IntPtr.Size because the API doesn't like null, even though
                // size is zero.  We know that IntPtr.Size will be
                // aligned correctly.
                int apiRetVal = WNetGetUniversalNameW(localPath, REMOTE_NAME_INFO_LEVEL, (IntPtr) IntPtr.Size, ref size);

                // If the return value is not ERROR_MORE_DATA, then
                // raise an exception.
                if (apiRetVal != ERROR_MORE_DATA)
                    // Throw an exception.
                    throw new Win32Exception(apiRetVal);

                // Allocate the memory.
                buffer = Marshal.AllocCoTaskMem(size);

                // Now make the call.
                apiRetVal = WNetGetUniversalNameW(localPath, REMOTE_NAME_INFO_LEVEL, buffer, ref size);

                // If it didn't succeed, then throw.
                if (apiRetVal != NOERROR)
                    // Throw an exception.
                    throw new Win32Exception(apiRetVal);

                // Now get the string.  It's all in the same buffer, but
                // the pointer is first, so offset the pointer by IntPtr.Size
                // and pass to PtrToStringAuto.
                //retVal = Marshal.PtrToStringAuto(new IntPtr(buffer.ToInt64() + IntPtr.Size));

                rni = (_REMOTE_NAME_INFO) Marshal.PtrToStructure(buffer,typeof(_REMOTE_NAME_INFO));

                retVal.connectionName = Marshal.PtrToStringAuto(rni.lpConnectionName);
                retVal.remainingPath = Marshal.PtrToStringAuto(rni.lpRemainingPath);
                retVal.universalName = Marshal.PtrToStringAuto(rni.lpUniversalName);

                return retVal;
            }
            finally
            {
                // Release the buffer.
                Marshal.FreeCoTaskMem(buffer);
            }

            // First, allocate the memory for the structure.

            // That's all folks.

        }

    }

Alternative Managed API:

Do you know one? Please contribute it!

Documentation

Please edit this page!

Do you have...

  • helpful tips or sample code to share for using this API in managed code?
  • corrections to the existing content?
  • variations of the signature you want to share?
  • additional languages you want to include?

Select "Edit This Page" on the right hand toolbar and edit it! Or add new pages containing supporting types needed for this API (structures, delegates, and more).

 
Access PInvoke.net directly from VS:
Terms of Use
Find References
Show Printable Version
Revisions