NetworkManager.cs 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. using System.Globalization;
  2. using System.IO;
  3. using MediaBrowser.Common.Implementations.Networking;
  4. using MediaBrowser.Common.Net;
  5. using MediaBrowser.Model.IO;
  6. using MediaBrowser.Model.Net;
  7. using System;
  8. using System.Collections.Generic;
  9. using System.Linq;
  10. using System.Runtime.InteropServices;
  11. namespace MediaBrowser.ServerApplication.Networking
  12. {
  13. /// <summary>
  14. /// Class NetUtils
  15. /// </summary>
  16. public class NetworkManager : BaseNetworkManager, INetworkManager
  17. {
  18. /// <summary>
  19. /// Gets the network shares.
  20. /// </summary>
  21. /// <param name="path">The path.</param>
  22. /// <returns>IEnumerable{NetworkShare}.</returns>
  23. public IEnumerable<NetworkShare> GetNetworkShares(string path)
  24. {
  25. return new ShareCollection(path).OfType<Share>().Select(ToNetworkShare);
  26. }
  27. /// <summary>
  28. /// To the network share.
  29. /// </summary>
  30. /// <param name="share">The share.</param>
  31. /// <returns>NetworkShare.</returns>
  32. private NetworkShare ToNetworkShare(Share share)
  33. {
  34. return new NetworkShare
  35. {
  36. Name = share.NetName,
  37. Path = share.Path,
  38. Remark = share.Remark,
  39. Server = share.Server,
  40. ShareType = ToNetworkShareType(share.ShareType)
  41. };
  42. }
  43. /// <summary>
  44. /// To the type of the network share.
  45. /// </summary>
  46. /// <param name="shareType">Type of the share.</param>
  47. /// <returns>NetworkShareType.</returns>
  48. /// <exception cref="System.ArgumentException">Unknown share type</exception>
  49. private NetworkShareType ToNetworkShareType(ShareType shareType)
  50. {
  51. if (shareType.HasFlag(ShareType.Special))
  52. {
  53. return NetworkShareType.Special;
  54. }
  55. if (shareType.HasFlag(ShareType.Device))
  56. {
  57. return NetworkShareType.Device;
  58. }
  59. if (shareType.HasFlag(ShareType.Disk))
  60. {
  61. return NetworkShareType.Disk;
  62. }
  63. if (shareType.HasFlag(ShareType.IPC))
  64. {
  65. return NetworkShareType.Ipc;
  66. }
  67. if (shareType.HasFlag(ShareType.Printer))
  68. {
  69. return NetworkShareType.Printer;
  70. }
  71. throw new ArgumentException("Unknown share type");
  72. }
  73. /// <summary>
  74. /// Uses the DllImport : NetServerEnum with all its required parameters
  75. /// (see http://msdn.microsoft.com/library/default.asp?url=/library/en-us/netmgmt/netmgmt/netserverenum.asp
  76. /// for full details or method signature) to retrieve a list of domain SV_TYPE_WORKSTATION
  77. /// and SV_TYPE_SERVER PC's
  78. /// </summary>
  79. /// <returns>Arraylist that represents all the SV_TYPE_WORKSTATION and SV_TYPE_SERVER
  80. /// PC's in the Domain</returns>
  81. private IEnumerable<string> GetNetworkDevicesInternal()
  82. {
  83. //local fields
  84. const int MAX_PREFERRED_LENGTH = -1;
  85. var SV_TYPE_WORKSTATION = 1;
  86. var SV_TYPE_SERVER = 2;
  87. var buffer = IntPtr.Zero;
  88. var tmpBuffer = IntPtr.Zero;
  89. var entriesRead = 0;
  90. var totalEntries = 0;
  91. var resHandle = 0;
  92. var sizeofINFO = Marshal.SizeOf(typeof(_SERVER_INFO_100));
  93. try
  94. {
  95. //call the DllImport : NetServerEnum with all its required parameters
  96. //see http://msdn.microsoft.com/library/default.asp?url=/library/en-us/netmgmt/netmgmt/netserverenum.asp
  97. //for full details of method signature
  98. var ret = NativeMethods.NetServerEnum(null, 100, ref buffer, MAX_PREFERRED_LENGTH, out entriesRead, out totalEntries, SV_TYPE_WORKSTATION | SV_TYPE_SERVER, null, out resHandle);
  99. //if the returned with a NERR_Success (C++ term), =0 for C#
  100. if (ret == 0)
  101. {
  102. //loop through all SV_TYPE_WORKSTATION and SV_TYPE_SERVER PC's
  103. for (var i = 0; i < totalEntries; i++)
  104. {
  105. //get pointer to, Pointer to the buffer that received the data from
  106. //the call to NetServerEnum. Must ensure to use correct size of
  107. //STRUCTURE to ensure correct location in memory is pointed to
  108. tmpBuffer = new IntPtr((int)buffer + (i * sizeofINFO));
  109. //Have now got a pointer to the list of SV_TYPE_WORKSTATION and
  110. //SV_TYPE_SERVER PC's, which is unmanaged memory
  111. //Needs to Marshal data from an unmanaged block of memory to a
  112. //managed object, again using STRUCTURE to ensure the correct data
  113. //is marshalled
  114. var svrInfo = (_SERVER_INFO_100)Marshal.PtrToStructure(tmpBuffer, typeof(_SERVER_INFO_100));
  115. //add the PC names to the ArrayList
  116. if (!string.IsNullOrEmpty(svrInfo.sv100_name))
  117. {
  118. yield return svrInfo.sv100_name;
  119. }
  120. }
  121. }
  122. }
  123. finally
  124. {
  125. //The NetApiBufferFree function frees
  126. //the memory that the NetApiBufferAllocate function allocates
  127. NativeMethods.NetApiBufferFree(buffer);
  128. }
  129. }
  130. /// <summary>
  131. /// Gets available devices within the domain
  132. /// </summary>
  133. /// <returns>PC's in the Domain</returns>
  134. public IEnumerable<FileSystemEntryInfo> GetNetworkDevices()
  135. {
  136. return GetNetworkDevicesInternal().Select(c => new FileSystemEntryInfo
  137. {
  138. Name = c,
  139. Path = NetworkPrefix + c,
  140. Type = FileSystemEntryType.NetworkComputer
  141. });
  142. }
  143. /// <summary>
  144. /// Gets the network prefix.
  145. /// </summary>
  146. /// <value>The network prefix.</value>
  147. private string NetworkPrefix
  148. {
  149. get
  150. {
  151. var separator = Path.DirectorySeparatorChar.ToString(CultureInfo.InvariantCulture);
  152. return separator + separator;
  153. }
  154. }
  155. }
  156. }