Chip Studio

常用链接

统计

最新评论

硬盘参数读取类型

 写了一个类型,用于读取硬盘物理参数。基本测试通过,容量计算上好象有些问题

/****************************************************
Module:    DiskType.h
Notices:   Copyright (c) 2008 WangYu
*****************************************************/

#ifndef __DISKTYPE
#define __DISKTYPE

#include <iostream>
#include <string>
#include <sstream>
#include <windows.h>

using namespace std;


typedef   struct   _GETVERSIONOUTPARAMS   {    
    BYTE   bVersion;       
    BYTE   bRevision;      
    BYTE   bReserved;    
    BYTE   bIDEDeviceMap;       
    DWORD   fCapabilities;    
    DWORD   dwReserved[4];     
}   GETVERSIONOUTPARAMS,   *PGETVERSIONOUTPARAMS,   *LPGETVERSIONOUTPARAMS;    

typedef   struct   _IDEREGS   {    
    BYTE   bFeaturesReg;        
    BYTE   bSectorCountReg;      
    BYTE   bSectorNumberReg;    
    BYTE   bCylLowReg;         
    BYTE   bCylHighReg;        
    BYTE   bDriveHeadReg;      
    BYTE   bCommandReg;     
    BYTE   bReserved;          
}   IDEREGS,   *PIDEREGS,   *LPIDEREGS;    

typedef   struct   _SENDCMDINPARAMS   {    
    DWORD   cBufferSize;     
    IDEREGS   irDriveRegs;          
    BYTE   bDriveNumber;      
    
    BYTE   bReserved[3];      
    DWORD   dwReserved[4];     
      
}   SENDCMDINPARAMS,   *PSENDCMDINPARAMS,   *LPSENDCMDINPARAMS;   

typedef   struct   _DRIVERSTATUS   {   
    BYTE   bDriverError;       
      
    BYTE   bIDEStatus;   
      
     
    BYTE   bReserved[2];        
    DWORD   dwReserved[2];       
}   DRIVERSTATUS,   *PDRIVERSTATUS,   *LPDRIVERSTATUS;   

typedef   struct   _SENDCMDOUTPARAMS   {   
    DWORD         cBufferSize;       
    DRIVERSTATUS   DriverStatus;       
    BYTE       bBuffer[512];         
     
}   SENDCMDOUTPARAMS,   *PSENDCMDOUTPARAMS,   *LPSENDCMDOUTPARAMS;   

typedef   struct   _IDSECTOR   {   
    USHORT   wGenConfig;   
    USHORT   wNumCyls;   
    USHORT   wReserved;   
    USHORT   wNumHeads;   
    USHORT   wBytesPerTrack;   
    USHORT   wBytesPerSector;   
    USHORT   wSectorsPerTrack;   
    USHORT   wVendorUnique[3];   
    CHAR   sSerialNumber[20];   
    USHORT   wBufferType;   
    USHORT   wBufferSize;   
    USHORT   wECCSize;   
    CHAR   sFirmwareRev[8];   
    CHAR   sModelNumber[40];   
    USHORT   wMoreVendorUnique;   
    USHORT   wDoubleWordIO;   
    USHORT   wCapabilities;   
    USHORT   wReserved1;   
    USHORT   wPIOTiming;   
    USHORT   wDMATiming;   
    USHORT   wBS;   
    USHORT   wNumCurrentCyls;   
    USHORT   wNumCurrentHeads;   
    USHORT   wNumCurrentSectorsPerTrack;   
    ULONG   ulCurrentSectorCapacity;   
    USHORT   wMultSectorStuff;   
    ULONG   ulTotalAddressableSectors;   
    USHORT   wSingleWordDMA;   
    USHORT   wMultiWordDMA;   
    BYTE   bReserved[128];   
}   IDSECTOR,   *PIDSECTOR;   

const DWORD DFP_GET_VERSION = 0x00074080;   
const DWORD DFP_SEND_DRIVE_COMMAND = 0x0007c084;   
const DWORD DFP_RECEIVE_DRIVE_DATA = 0x0007c088;   

class DiskType{
    friend ostream& operator<<(ostream& , const DiskType&);
public:
    DiskType(int theDisk = 0)
    {
        j = theDisk;
        GetDiskInfo();
    }
    ostringstream errmsg;
protected:
    void ChangeByteOrder(PCHAR, USHORT);
    void GetDiskInfo(void);
private:
    GETVERSIONOUTPARAMS   vers;   
    SENDCMDINPARAMS   in;   
    SENDCMDOUTPARAMS   out;   
    HANDLE   h;   
    DWORD   i;   
    BYTE   j;   

    char   hd[80];   
    PIDSECTOR   phdinfo;   
    char   s[41];   

    string Module, Firmware, Serial;
    ostringstream Capacity;
};

#endif

/******************************************************
Module:    DiskType.cpp
Notices:   Copyright (c) 2008 WangYu
******************************************************/

#include "DiskType.h"

inline void DiskType::GetDiskInfo()
{
    ZeroMemory(&vers,sizeof(vers));    
    sprintf(hd,"\\\\.\\PhysicalDrive%d",j);    
    h=CreateFile(hd, GENERIC_READ|GENERIC_WRITE, FILE_SHARE_READ|FILE_SHARE_WRITE, 0, OPEN_EXISTING, 0, 0);    
    if(!DeviceIoControl(h, DFP_GET_VERSION, 0, 0, &vers, sizeof(vers), &i, 0))
        CloseHandle(h);    
    //If   IDE   identify   command   not   supported,   fails    
    if(!(vers.fCapabilities & 1))
    {    
        errmsg << "Error:   IDE   identify   command   not   supported." << endl;    
        CloseHandle(h);    
        return;    
    }    
    //Identify   the   IDE   drives    
    ZeroMemory(&in,sizeof(in));    
    ZeroMemory(&out,sizeof(out));    
    if(j&1)
        in.irDriveRegs.bDriveHeadReg=0xb0;    
    else    
        in.irDriveRegs.bDriveHeadReg=0xa0;    
    if(vers.fCapabilities & (16>>j) )
    {    
        //We   don't   detect   a   ATAPI   device.    
        errmsg << "Drive   "<< (int)(j+1) << "   is   a   ATAPI   device,   we   don't   detect   it" << endl;    
    }else    
        in.irDriveRegs.bCommandReg=0xec;    
    in.bDriveNumber=j;    
    in.irDriveRegs.bSectorCountReg=1;    
    in.irDriveRegs.bSectorNumberReg=1;    
    in.cBufferSize=512;    
    if(!DeviceIoControl(h, DFP_RECEIVE_DRIVE_DATA, &in, sizeof(in), &out, sizeof(out), &i, 0))
    {    
        errmsg << "DeviceIoControl   failed:DFP_RECEIVE_DRIVE_DATA" << endl;    
        CloseHandle(h);    
        return;    
    }    
    phdinfo=(PIDSECTOR)out.bBuffer;

    memcpy(s,phdinfo->sModelNumber,40);    
    s[40]=0;    
    ChangeByteOrder(s,40);    
    Module = s;

    memcpy(s,phdinfo->sFirmwareRev,8);    
    s[8]=0;    
    ChangeByteOrder(s,8);    
    Firmware = s;

    memcpy(s,phdinfo->sSerialNumber,20);    
    s[20]=0;    
    ChangeByteOrder(s,20);    
    Serial = s;
    Capacity << phdinfo->ulTotalAddressableSectors/2/1024<< "M" << endl;
    CloseHandle(h);
}

inline void DiskType::ChangeByteOrder(PCHAR szString,USHORT uscStrSize)    
{    

    USHORT   i;    
    CHAR   temp;    
    for(i = 0; i < uscStrSize; i += 2)    
    {    
        temp = szString[i];    
        szString[i] = szString[i+1];    
        szString[i+1] = temp;    
    }    
}    

inline ostream& operator<<(ostream& os, const DiskType& dt)
{
    os << "Module Number: "
       << dt.Module << endl
       << "Firmware   rev: "
       << dt.Firmware << endl
       << "Serial Number: "
       << dt.Serial << endl
       << "Capacity: "
       << dt.Capacity.str() << endl
       << "other message ---- " << endl
       << dt.errmsg.str();
    return os;
}

int main()
{
    DiskType dt;
    cout << dt;
    return 0;
}





posted on 2008-02-02 04:50 MyChip 阅读(1837) 评论(0)  编辑 收藏 引用 所属分类: C/C++/CLIWindows核心VC/MFC


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理