Resolved Getting shares from a remote computer

aaaron123@roadrunner.com

Well-known member
Joined
Jan 23, 2011
Messages
149
Programming Experience
10+
I've been looking for a sample for getting shares from a remote computer for days. And tried many.
The following is the latest.

I used it like this:
VB.NET:
 Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
        ServerShareCollection = GetSharesFromHost("Server")
        If ServerShareCollection.Shares IsNot Nothing Then
            For Each s As ShareType In ServerShareCollection.Shares
                MsgBox(s.Name)
            Next
        End If
End Sub
Tried different strings for "Server"

Like \\LAPTOP\Users" and \\LAPTOP\ and LAPTOP ...
None work.

LAPTOP being one of the remote nodes on my network.

Can you help?

VB.NET:
  Public Function GetSharesFromHost(ByVal server As String) As ShareCollection
        Dim Shares As New ShareCollection
        Shares.Clear()
        Dim level As Integer = 2
        Dim svr As New StringBuilder(server)
        Dim entriesRead As Integer, totalEntries As Integer, nRet As Integer, hResume As Integer = 0
        Dim pBuffer As IntPtr = IntPtr.Zero

        Try
            nRet = NetShareEnum(svr, level, pBuffer, -1, entriesRead, totalEntries, hResume)

            If ERROR_ACCESS_DENIED = nRet Then
                'Need admin for level 2, drop to level 1
                level = 1
                nRet = NetShareEnum(svr, level, pBuffer, -1, entriesRead, totalEntries, hResume)
            End If

            If 0 = nRet AndAlso entriesRead > 0 Then
                Dim t As Type = IIf((2 = level), GetType(SHARE_INFO_2), GetType(SHARE_INFO_1))
                Dim offset As Integer = Marshal.SizeOf(t)

                Dim i As Integer = 0, lpItem As Integer = pBuffer.ToInt32()
                While i < entriesRead
                    Dim pItem As New IntPtr(lpItem)
                    If 1 = level Then
                        Dim si As SHARE_INFO_1 = DirectCast(Marshal.PtrToStructure(pItem, t), SHARE_INFO_1)
                        Shares.Add(si.netname, "Access Denied", si.ShareType, si.Remark)
                    Else
                        Dim si As SHARE_INFO_2 = DirectCast(Marshal.PtrToStructure(pItem, t), SHARE_INFO_2)
                        Shares.Add(si.shi2_netname, si.shi2_path, si.shi2_type, si.shi2_remark)
                    End If
                    i += 1
                    lpItem += offset
                End While

            End If
            Return Shares
        Finally
            ' Clean up buffer allocated by system
            If IntPtr.Zero <> pBuffer Then
                NetApiBufferFree(pBuffer)
            End If

        End Try
        Return Shares
    End Function
 
Last edited by a moderator:
Solution
It looks like code from here: pinvoke.net: netshareenum (netapi32)

Which works for me except I had to change lpItem As Integer = pBuffer.ToInt32() to lpItem As Long = pBuffer.ToInt64()
(it is also possible to use pBuffer directly instead of pItem and do pBuffer += offset in the loop, but this doesn't change anything)

Both "\\server" and "server" and works.

You can see the shares if you enter "\\server" in Windows Explorer, right?

JohnH

VB.NET Forum Moderator
Staff member
Joined
Dec 17, 2005
Messages
15,609
Location
Norway
Programming Experience
10+
It looks like code from here: pinvoke.net: netshareenum (netapi32)

Which works for me except I had to change lpItem As Integer = pBuffer.ToInt32() to lpItem As Long = pBuffer.ToInt64()
(it is also possible to use pBuffer directly instead of pItem and do pBuffer += offset in the loop, but this doesn't change anything)

Both "\\server" and "server" and works.

You can see the shares if you enter "\\server" in Windows Explorer, right?
 
Solution

aaaron123@roadrunner.com

Well-known member
Joined
Jan 23, 2011
Messages
149
Programming Experience
10+
Which works for me
Everything works for you, after you do your magic.

The code labeled each entry as "Access Denied"

Doesn't sound like I could use this for anything.

Also, I had to give it the server name.

I tried this in desperation, just wanting to get something related to remote shares working.

I need something that works like Windows Explorer.

Now I regret not posting the much longer code relating to Mpr.dll (WNetOpenEnum . . . ) that I've been trying to get working.

You most likely would have solved that for me.

I'll go back to the Mpr application to try again but suspect it'll be the subject of another post.

The one I really like I converted from C# to VB.

I found one thing that VB does different from C# but fixing that was not enough.

Maybe I'll try running the original C# to see what happens.

Of course, if someone post VB code that started with "Entire Network" and worked its way down to the shares the inevitable post would not be necessary. :)



Thanks for fixing the above.
 

JohnH

VB.NET Forum Moderator
Staff member
Joined
Dec 17, 2005
Messages
15,609
Location
Norway
Programming Experience
10+

aaaron123@roadrunner.com

Well-known member
Joined
Jan 23, 2011
Messages
149
Programming Experience
10+
on doc.microsoft I found:
/MANIFESTUAC:"level='highestAvailable' uiAccess='true'"
No reference to what framework (if that matters?)


Also (seems best): level='requireAdministrator'level='requireAdministrator'.

On the internet I found the assembly part of the following:

My app.config file:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.8" />
</startup>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v3">
<security>
<requestedPrivileges>
<requestedExecutionLevel level="requireAdministrator" uiAccess="true"/>
</requestedPrivileges>
</security>
</trustInfo>
</assembly>
</configuration>

When I try to run I get an error message saying the config file is incorrect.
I'm not surprised because I have no idea what the correct versions are.
Or if any of the above applies to Framework 4.8

I am running as an administrator.

I've started VS running as administrator

I believe it's the app that needs what I tried to do above.

Is that correct?

If so, how do I make the app run with administrator rights?
 

JohnH

VB.NET Forum Moderator
Staff member
Joined
Dec 17, 2005
Messages
15,609
Location
Norway
Programming Experience
10+
Just running VS as elevated admin is enough for testing (by right-clicking VS shortcut and select Run as Administrator), then debug runs as admin too.
 

aaaron123@roadrunner.com

Well-known member
Joined
Jan 23, 2011
Messages
149
Programming Experience
10+
Just running VS as elevated admin is enough (by right-clicking VS shortcut and select Run as Administrator), then debug runs as admin too.
I read that was not true. Its to bad that it is true because doing that I still get "Access Denied".
But you don't. Right?

BTW. Can you tell me how to add level='requireAdministrator'level='requireAdministrator' to my app.config file.
I'd like to know how.
All I have in the system generated app.config file the <startup> stuff shown above.
 

JohnH

VB.NET Forum Moderator
Staff member
Joined
Dec 17, 2005
Messages
15,609
Location
Norway
Programming Experience
10+
But you don't. Right?
No, not even as non-elevated.
you tell me how to add level='requireAdministrator'level='requireAdministrator' to my app.config file.
Project properties, Application tab, View Windows Settings brings up the default app.manifest that you can modify.
It takes effect when running the application, if you requireAdministrator and debug from VS non-elevated it ask to restart VS elevated
As standalone app it will ask to elevate it, since no user is elevated even running as admin account, but of course not ask again if you explicitly start the process elevated.
 

Latest posts

Top Bottom