windows的磁盤操作之五——獲取物理磁盤上的所有邏輯分區號

本節討論與上一節相反的操作,根據物理驅動器號獲取該磁盤上的所有分區號。DeviceIoControl函數並沒有提供操作碼來直接完成此操作,所以需要稍微繞個圈子來實現這項功能。

大體思路爲,先通過GetLogicalDrives函數獲得系統中所有分區號,然後過濾掉非硬盤分區(例如軟驅、光驅),再過濾掉不屬於指定物理磁盤的分區,最後剩下的就是我們所需要的分區號了。
 
代碼如下
/******************************************************************************
* Function: get disk's drive letters from physical number
*           e.g. 0-->{C, D, E} (disk0 has 3 drives, C:, D: and E:)
* input: phyDriveNumber, disk's physical number
* output: letters, letters array
* return: Succeed, the amount of letters
*         Fail, -1
******************************************************************************/
DWORD GetPartitionLetterFromPhysicalDrive(DWORD phyDriveNumber, CHAR **letters)
{
    DWORD mask;
    DWORD driveType;
    DWORD bmLetters;
    DWORD diskNumber;
    CHAR path[DISK_PATH_LEN]; 
    CHAR letter;
    DWORD letterNum;
    WORD i;
    CHAR *p;
 
    bmLetters = GetLogicalDrives();
    if (0 == bmLetters)
    {
        return (DWORD)-1;
    }
 
    letterNum = 0;
    for (i = 0; i < sizeof(DWORD) * 8; i++)
    {
        mask = 0x1u << i;
        if ((mask & bmLetters) == 0)        //get one letter
        {
            continue;
        }
        letter = (CHAR)(0x41 + i);    //ASCII change
        sprintf(path, "%c:\\", letter);
        driveType = GetDriveType(path);
        if (driveType != DRIVE_FIXED)
        {
            bmLetters &= ~mask;     //clear this bit
            continue;
        }
        diskNumber = GetPhysicalDriveFromPartitionLetter(letter);
        if (diskNumber != phyDriveNumber)
        {
            bmLetters &= ~mask;     //clear this bit
            continue;
        }
        letterNum++;
    }
 
    //build the result
    *letters = (CHAR *)malloc(letterNum);
    if (NULL == *letters)
    {
        return (DWORD)-1;
    }
    p = *letters;
    for (i = 0; i < sizeof(DWORD) * 8; i++)
    {
        mask = 0x1u << i;
        if ((mask & bmLetters) == 0)
        {
            continue;
        }
        letter = (CHAR)(0x41 + i);    //ASCII change
        *p = letter;
        p++;
    }
   
    return letterNum;
}
 
代碼分析
函數輸入參數DWORD phyDriveNumber爲物理磁盤號,例如012……。
函數輸出參數CHAR **letters爲獲得的邏輯分區號數組指針。由於一塊物理盤上可能有多個分區,所以用數組存放求得的多個分區號。
函數返回值爲分區數量。
1. 調用函數GetLogicalDrives獲得所有分區號。注意函數GetLogicalDrives返回值爲位圖形時,例如第0位代表A:,第2位代表C: 等等。
2. 對獲得的邏輯分區逐個檢測。
調用函數GetDriveType獲得分區類型,如果類型不爲硬盤(driveType != DRIVE_FIXED),將此位清0
調用函數GetPhysicalDriveFromPartitionLetter(詳見第四節http://cutebunny.blog.51cto.com/301216/624379)查詢該邏輯分區所屬的物理分區號,如果不爲phyDriveNumber,將此位清0
經過上兩項條件過濾後的位圖存儲了我們所需的邏輯分區號。
3. *letters分配空間,並將位圖轉換爲盤符字母存儲在數組中。
 
 
 
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章