كيف يمكنني تحديد ما إذا كان محرك الأقراص البعيد به مساحة كافية لكتابة ملف باستخدام C#؟

StackOverflow https://stackoverflow.com/questions/137255

سؤال

كيف يمكنني تحديد ما إذا كان محرك الأقراص البعيد به مساحة كافية لي لتحميل ملف معين باستخدام C# في .Net؟

هل كانت مفيدة؟

المحلول

هناك نوعان من الحلول الممكنة.

  1. استدعاء الدالة Win32 GetDiskFreeSpaceEx.هنا نموذج للبرنامج:

    internal static class Win32
    {
        [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        internal static extern bool GetDiskFreeSpaceEx(string drive, out long freeBytesForUser, out long totalBytes, out long freeBytes);
    
    }
    
    class Program
    {
        static void Main(string[] args)
        {
            long freeBytesForUser;
            long totalBytes;
            long freeBytes;
    
            if (Win32.GetDiskFreeSpaceEx(@"\\prime\cargohold", out freeBytesForUser, out totalBytes, out freeBytes)) {
                Console.WriteLine(freeBytesForUser);
                Console.WriteLine(totalBytes);
                Console.WriteLine(freeBytes);
            }
        }
    }
    
  2. استخدم واجهة إدارة النظام.هناك إجابة أخرى في هذا المنشور تصف هذا.تم تصميم هذه الطريقة بالفعل للاستخدام في لغات البرمجة النصية مثل PowerShell.إنه يؤدي الكثير من الزغب فقط للحصول على الكائن الصحيح.في النهاية، أعتقد أن هذه الطريقة تتلخص في استدعاء GetDiskFreeSpaceEx.

من المحتمل أن ينتهي الأمر بأي شخص يقوم بأي تطوير جدي لـ Windows في C# باستدعاء العديد من وظائف Win32.إطار عمل .NET لا يغطي 100% من واجهة برمجة تطبيقات Win32.سيكشف أي برنامج كبير بسرعة عن الثغرات الموجودة في مكتبات .NET المتوفرة فقط من خلال Win32 API.سأحصل على أحد أغلفة Win32 لـ .NET وأدرجها في مشروعك.سيمنحك هذا إمكانية الوصول الفوري إلى كل واجهة برمجة تطبيقات Win32 تقريبًا.

نصائح أخرى

استخدم WMI

using System.Management;

// Get all the network drives (drivetype=4)
SelectQuery query = new SelectQuery("select Name, VolumeName, FreeSpace from win32_logicaldisk where drivetype=4");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(query);
foreach (ManagementObject drive in searcher.Get())
{
    string Name = (string)drive["Name"];
    string VolumeName = (string)drive["VolumeName"];
    UInt64 freeSpace = (UInt64)drive["FreeSpace"];
}

على أساس (مسروق من) http://www.dreamincode.net/code/snippet1576.htm

هل تتحدث عن تعيين مشاركة شبكة إلى محرك أقراص منطقي على جهاز الكمبيوتر الخاص بك؟

إذا كان الأمر كذلك يمكنك استخدام DriveInfo.

    DriveInfo info = new DriveInfo("X:");

    info.AvailableFreeSpace;

يعمل DriveInfo فقط مع محركات الأقراص المنطقية، لذا إذا كنت تستخدم اسم المشاركة الكاملة (UNC) فقط، فلا أعتقد أن الكود أعلاه سيعمل.

لست متأكدًا مما إذا كان GetDiskFreeSpaceEx يعمل على مشاركات UNC، ولكن إذا كان يستخدم ذلك، وإلا فإليك كيفية تحميل مشاركة UNC على محرك أقراص قانوني:

يحرر يعمل GetDiskFreeSpaceEx على مشاركات UNC، استخدم ذلك... ومع ذلك، كان هذا الرمز يتطلب الكثير من الجهد لحذفه فقط، وهو مفيد إذا كنت تريد في أي وقت تحميل مشاركة UNC كمحرك أقراص محلي في التعليمات البرمجية الخاصة بك.

public class DriveWrapper
{                    
    [StructLayout(LayoutKind.Sequential)]
    public struct NETRESOURCEA
    {
        public int dwScope;
        public int dwType;
        public int dwDisplayType;
        public int dwUsage;
        [MarshalAs(UnmanagedType.LPStr)]
        public string lpLocalName;
        [MarshalAs(UnmanagedType.LPStr)]
        public string lpRemoteName;
        [MarshalAs(UnmanagedType.LPStr)]
        public string lpComment;
        [MarshalAs(UnmanagedType.LPStr)]
        public string lpProvider;
        public override String ToString()
        {
            String str = "LocalName: " + lpLocalName + " RemoteName: " + lpRemoteName
                  + " Comment: " + lpComment + " lpProvider: " + lpProvider;
            return (str);
        }
    }

    [DllImport("mpr.dll")]
    public static extern int WNetAddConnection2A(
          [MarshalAs(UnmanagedType.LPArray)] NETRESOURCEA[] lpNetResource,
          [MarshalAs(UnmanagedType.LPStr)] string lpPassword,
          [MarshalAs(UnmanagedType.LPStr)] string UserName,
          int dwFlags);       
    [DllImport("mpr.dll", CharSet = System.Runtime.InteropServices.CharSet.Auto)]
    private static extern int WNetCancelConnection2A(
          [MarshalAs(UnmanagedType.LPStr)]
        string lpName,
          int dwFlags,
          int fForce
          );

    public int GetDriveSpace(string shareName, string userName, string password)
    {
        NETRESOURCEA[] n = new NETRESOURCEA[1];
        n[0] = new NETRESOURCEA();

        n[0].dwScope = 0;
        n[0].dwType = 0;
        n[0].dwDisplayType = 0;
        n[0].dwUsage = 0;

        n[0].dwType = 1;

        n[0].lpLocalName = "x:";
        n[0].lpRemoteName = shareName;
        n[0].lpProvider = null;

        int res = WNetAddConnection2A(n, userName, password, 1);

        DriveInfo info = new DriveInfo("x:");
        int space = info.AvailableFreeSpace;

        int err = 0;
        err = WNetCancelConnection2A("x:", 0, 1);

        return space;
    }
}
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top