首页
社区
课程
招聘
[已解决]汇编使用DeviceIoControl读取硬盘序列号问题
发表于: 2009-2-5 05:18 9821

[已解决]汇编使用DeviceIoControl读取硬盘序列号问题

2009-2-5 05:18
9821
Local     szOut:GETVERSIONINPARAMS
Local     dwRet,hDevice

invoke        CreateFile,CTEXT("\\.\PHYSICALDRIVE0"),GENERIC_READ or GENERIC_WRITE,FILE_SHARE_READ or FILE_SHARE_WRITE,0,OPEN_EXISTING,NULL,NULL

.if     hDevice != ERROR_INVALID_HANDLE
mov    hDevice,eax
invoke        DeviceIoControl,hDevice,SMART_GET_VERSION,0,0,addr szOut,sizeof szOut,addr dwRet,0
.endif
invoke        CloseHandle,hDevice

DRIVERSTATUS STRUCT

bDriverError        DB        ?
bIDEStatus        DB        ?
bReserved        DB        2        DUP        (?)
dwReserved        DD        2        DUP        (2)

DRIVERSTATUS ENDS

GETVERSIONINPARAMS STRUCT

        cBufferSzie        DD        ?
        DriverStatus        DRIVERSTATUS        <>
        bBuffer                DB        512        (?)

GETVERSIONINPARAMS ENDS

这样写对吗 ?????请教了

[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

收藏
免费 0
支持
分享
最新回复 (3)
雪    币: 496
活跃值: (2158)
能力值: ( LV12,RANK:210 )
在线值:
发帖
回帖
粉丝
2
楼主强,用汇编写代码。膜拜。我什么时候能达到你的程度就好了。
2009-2-5 16:10
0
雪    币: 108
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
我老菜了 刚学
2009-2-5 19:07
0
雪    币: 108
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
4
问题解决了 以下是代码来自MengXP

;by MengXP
;2007.11.11
;修正: 使用IOCTL_DISK_GET_DRIVE_GEOMETRY获取硬盘容量

.386
.Model Flat,StdCall
Option CaseMap :None

Include Windows.inc
Include User32.inc
Include Kernel32.inc
Include winioctl.inc

IncludeLib User32.lib
IncludeLib Kernel32.lib

IDEREGS        struct
    bFeaturesReg        db ?        ;// 特征寄存器(用于SMART命令)
    bSectorCountReg        db ?        ;// 扇区数目寄存器
    bSectorNumberReg        db ?        ;// 开始扇区寄存器
    bCylLowReg                db ?        ;// 开始柱面低字节寄存器
    bCylHighReg                db ?        ;// 开始柱面高字节寄存器
    bDriveHeadReg        db ?        ;// 驱动器/磁头寄存器
    bCommandReg                db ?        ;// 指令寄存器
    bReserved                db ?        ;// 保留
IDEREGS        ends

SENDCMDINPARAMS        struct
    cBufferSize                dd ?                ;// 缓冲区字节数
    irDriveRegs                IDEREGS <>        ;// IDE寄存器组
    bDriveNumber        db ?                ;// 驱动器号
    bReserved                db 3 dup(?)        ;// 保留
    dwReserved                dd 4 dup(?)        ;// 保留
    bBuffer                db ?                ;// 输入缓冲区(此处象征性地包含1字节)
SENDCMDINPARAMS        ends

.Data
szInfo                db 1024 dup(?)
szInfoFmt        db "硬盘型号: %s",13,10
                db "硬盘大小: %d GB",13,10
                db "硬盘缓存: %d KB",13,10
                db "硬盘序号: %s",0
hDevice                dd ?
stIn                SENDCMDINPARAMS <>
stOut                dd 256 dup(?)                ;输出缓冲区就不定义结构了
dwReturnBytes        dd ?
stDG                DISK_GEOMETRY <>

dwDriveSize        dd ?
dwCacheSize        dd ?
szDriveName        db 48 dup(?)
szSerialNum        db 24 dup(?)

.Code
Start:
        mov        stIn.irDriveRegs.bCommandReg,0ECh        ;IDE_ATA_IDENTIFY
        mov        stIn.cBufferSize,0
        mov        stOut,512        ;返回缓冲区大小
       
        invoke        CreateFile,CTEXT("\\.\PhysicalDrive0"),GENERIC_READ or GENERIC_WRITE,FILE_SHARE_READ or FILE_SHARE_WRITE,NULL,OPEN_EXISTING,0,NULL
        mov        hDevice,eax
        invoke        DeviceIoControl,hDevice,0007C088h,addr stIn,sizeof SENDCMDINPARAMS - 1,addr stOut,256*4,addr dwReturnBytes,0
       
        lea        esi,stOut
        add        esi,16                ;跳过头部直接到达512字节数据
       
        movzx        eax,word ptr [esi+42]        ;取缓存大小 KB
        xor        edx,edx
        mov        ecx,2
        div        ecx
        mov        dwCacheSize,eax
       
        xor        ecx,ecx
        .While        ecx < 40        ;按字整理硬盘型号数据
                mov        ax,word ptr [esi+54+ecx]
                xchg        ah,al
                mov        word ptr [esi+54+ecx],ax
                add        ecx,2
        .EndW
        invoke        RtlMoveMemory,addr szDriveName,addr [esi+54],40
       
        xor        ecx,ecx
        .While        ecx < 20        ;按字整理硬盘序列号数据
                mov        ax,word ptr [esi+20+ecx]
                xchg        ah,al
                mov        word ptr [esi+20+ecx],ax
                add        ecx,2
        .EndW
        invoke        RtlMoveMemory,addr szSerialNum,addr [esi+20],20
       
        invoke        DeviceIoControl,hDevice,IOCTL_DISK_GET_DRIVE_GEOMETRY,0,0,addr stDG,sizeof DISK_GEOMETRY,addr dwReturnBytes,0
        invoke        CloseHandle,hDevice
       
        lea        esi,stDG
        mov        eax,[esi]
        mov        edx,[esi+4]
        mov        ecx,stDG.TracksPerCylinder
        mul        ecx
        mov        ecx,stDG.SectorsPerTrack
        mul        ecx
        mov        ecx,stDG.BytesPerSector
        mul        ecx
        mov        ecx,1000*1000*1000
        div        ecx
        mov        dwDriveSize,eax
       
        invoke        wsprintf,addr szInfo,addr szInfoFmt,addr szDriveName,dwDriveSize,dwCacheSize,addr szSerialNum
        invoke        MessageBox,0,addr szInfo,0,0
        invoke        ExitProcess,0
End        Start

数据结构补充

输出结构

DRIVERSTATUS        STRUCT                                                               
                bDriverError                             DB                ?                                                       
        bIDEStatus                DB                ?                                                       
        bReserved                DB                2                dup        (?)               
        dwReserved                DD                2                dup        (?)               

DRIVERSTATUS        ENDS                                                                       
SENDCMDOUTPARAMS        STRUCT                                                       

        cBufferSize                DD                ?                                                       
        sDriverStatus        DRIVERSTATUS                <>                       
        bBuffer                        DB                2                dup        (?)               

SENDCMDOUTPARAMS        ENDS

---------------------------------------------------------------------------------
返回信息结构

IDINFO STRUCT       

        wGenConfig                                DW                ?
        wNumCyls                                        DW                ?
        wReserved2                                DW                ?
        wNumHeads                                DW                ?
        wReserved4                                DW                ?
        wReserved5                                DW                ?
        wNumSectorsPerTrack        DW                ?
        wVendorUnique                        DW                3                dup                (?)
        sSerialNumber                        DW                20                dup                (?)
        wBufferType                                DW                ?
        wBufferSize                                DW                ?
        wECCSize                                        DW                ?
        sFirmwareRev                        DW                8                dup                (?)
        sModelNumber                        DW                40                dup                (?)
        wMoreVendorUnique                DW                ?
        wReserved48                                DW                ?
        reserved1                                DW                ?
        DMA                                                DW                ?
        LBA                                                DW                ?
        DisIORDY                                        DW                ?
        IORDY                                                DW                ?
        SoftReset                                DW                ?
        Overlap                                        DW                ?
        Queue                                                DW                ?
        InlDMA                                        DW                ?
        wReserved1                                DW                ?
        wPIOTiming                                DW                ?
        wDMATiming                                DW                ?
        CHSNumber                                DW                ?
        CycleNumber                                DW                ?
        UnltraDMA                                DW                ?
        reserved                                        DW                ?
        wNumCurCyls                                DW                ?
        wNumCurHeads                        DW                ?
        wNumCurSectorsPerTrack                DW                ?
        wCurSectorsLow                        DW                ?
        wCurSectorsHigh                DW                ?
        CurNumber                                DW                ?
        Multi                                                DW                ?
        reserved2                                DW                ?
        dwTotalSectors                        DW                ?
        wSingleWordDMA                        DW                ?
        Mode0                                                DW                ?
        Mode1                                                DW                ?
        Mode2                                                DW                ?
        Reserved3                                DW                ?
        Mode0Sel                                        DW                ?
        Mode1Sel                                        DW                ?
        Mode2Sel                                        DW                ?
        wMultiWordDMA                        DW                ?
        AdvPOIModes                                DW                ?
        reserved4                                DW                ?
        wMinMultiWordDMACycle                DW                ?
        wRecMultiWordDMACycle                DW                ?
        wMinPIONoFlowCycle                        DW                ?
        wMinPOIFlowCycle                                DW                ?
        wReserved69                                DW                11                dup                (?)
        Reserved5                                DW                ?
        ATA1                                                DW                ?
        ATA2                                                DW                ?
        ATA3                                                DW                ?
        ATA4                                                DW                ?
        ATA5                                                DW                ?          
        ATA6                                                DW                ?
        ATA7                                                DW                ?
        ATA8                                                DW                ?
        ATA9                                                DW                ?
        ATA10                                                DW                ?
        ATA11                                                DW                ?
        ATA12                                                DW                ?
        ATA13                                                DW                ?
        ATA14                                                DW                ?
        Reserved6                                DW                ?
        wMinorVersion                        DW                ?
        wReserved82                                DW                6                dup                (?)
        rMode0                                        DW                ?
        rMode1                                        DW                ?       
        rMode2                                        DW                ?       
        rMode3                                        DW                ?       
        rMode4                                        DW                ?       
        rMode5                                        DW                ?       
        rMode6                                        DW                ?       
        rMode7                                        DW                ?       
        sMode0Sel                                DW                ?       
        sMode1Sel                                DW                ?       
        sMode2Sel                                DW                ?       
        sMode3Sel                                DW                ?       
        sMode4Sel                                DW                ?       
        sMode5Sel                                DW                ?
        sMode6Sel                                DW                ?       
        sMode7Sel                                DW                ?
        wReserved89                                DW                167                dup                (?)

IDINFO ENDS

参考说明

typedef struct _IDINFO
{
USHORT  wGenConfig;     // WORD 0: 基本信息字
USHORT  wNumCyls;     // WORD 1: 柱面数
USHORT  wReserved2;     // WORD 2: 保留
USHORT  wNumHeads;     // WORD 3: 磁头数
USHORT  wReserved4;        // WORD 4: 保留
USHORT  wReserved5;        // WORD 5: 保留
USHORT  wNumSectorsPerTrack;  // WORD 6: 每磁道扇区数
USHORT  wVendorUnique[3];   // WORD 7-9: 厂家设定值
CHAR    sSerialNumber[20];   // WORD 10-19:序列号
USHORT  wBufferType;    // WORD 20: 缓冲类型
USHORT  wBufferSize;    // WORD 21: 缓冲大小
USHORT  wECCSize;     // WORD 22: ECC校验大小
CHAR    sFirmwareRev[8];   // WORD 23-26: 固件版本
CHAR    sModelNumber[40];   // WORD 27-46: 内部型号
USHORT  wMoreVendorUnique;   // WORD 47: 厂家设定值
USHORT  wReserved48;    // WORD 48: 保留
struct {
  USHORT  reserved1:8;
  USHORT  DMA:1;     // 1=支持DMA
  USHORT  LBA:1;     // 1=支持LBA
  USHORT  DisIORDY:1;    // 1=可不使用IORDY
  USHORT  IORDY:1;    // 1=支持IORDY
  USHORT  SoftReset:1;   // 1=需要ATA软启动
  USHORT  Overlap:1;    // 1=支持重叠操作
  USHORT  Queue:1;    // 1=支持命令队列
  USHORT  InlDMA:1;    // 1=支持交叉存取DMA
} wCapabilities;     // WORD 49: 一般能力
USHORT  wReserved1;     // WORD 50: 保留
USHORT  wPIOTiming;     // WORD 51: PIO时序
USHORT  wDMATiming;     // WORD 52: DMA时序
struct {
  USHORT  CHSNumber:1;   // 1=WORD 54-58有效
  USHORT  CycleNumber:1;   // 1=WORD 64-70有效
  USHORT  UnltraDMA:1;   // 1=WORD 88有效
  USHORT  reserved:13;
} wFieldValidity;     // WORD 53: 后续字段有效性标志
USHORT  wNumCurCyls;    // WORD 54: CHS可寻址的柱面数
USHORT  wNumCurHeads;    // WORD 55: CHS可寻址的磁头数
USHORT  wNumCurSectorsPerTrack;  // WORD 56: CHS可寻址每磁道扇区数
USHORT  wCurSectorsLow;    // WORD 57: CHS可寻址的扇区数低位字
USHORT  wCurSectorsHigh;   // WORD 58: CHS可寻址的扇区数高位字
struct {
  USHORT  CurNumber:8;   // 当前一次性可读写扇区数
  USHORT  Multi:1;    // 1=已选择多扇区读写
  USHORT  reserved1:7;
} wMultSectorStuff;     // WORD 59: 多扇区读写设定
ULONG  dwTotalSectors;    // WORD 60-61: LBA可寻址的扇区数
USHORT  wSingleWordDMA;    // WORD 62: 单字节DMA支持能力
struct {
  USHORT  Mode0:1;    // 1=支持模式0 (4.17Mb/s)
  USHORT  Mode1:1;    // 1=支持模式1 (13.3Mb/s)
  USHORT  Mode2:1;    // 1=支持模式2 (16.7Mb/s)
  USHORT  Reserved1:5;
  USHORT  Mode0Sel:1;    // 1=已选择模式0
  USHORT  Mode1Sel:1;    // 1=已选择模式1
  USHORT  Mode2Sel:1;    // 1=已选择模式2
  USHORT  Reserved2:5;
} wMultiWordDMA;     // WORD 63: 多字节DMA支持能力
struct {
  USHORT  AdvPOIModes:8;   // 支持高级POI模式数
  USHORT  reserved:8;
} wPIOCapacity;      // WORD 64: 高级PIO支持能力
USHORT  wMinMultiWordDMACycle;  // WORD 65: 多字节DMA传输周期的最小值
USHORT  wRecMultiWordDMACycle;  // WORD 66: 多字节DMA传输周期的建议值
USHORT  wMinPIONoFlowCycle;   // WORD 67: 无流控制时PIO传输周期的最小值
USHORT  wMinPOIFlowCycle;   // WORD 68: 有流控制时PIO传输周期的最小值
USHORT  wReserved69[11];   // WORD 69-79: 保留
struct {
  USHORT  Reserved1:1;
  USHORT  ATA1:1;     // 1=支持ATA-1
  USHORT  ATA2:1;     // 1=支持ATA-2
  USHORT  ATA3:1;     // 1=支持ATA-3
  USHORT  ATA4:1;     // 1=支持ATA/ATAPI-4
  USHORT  ATA5:1;     // 1=支持ATA/ATAPI-5
  USHORT  ATA6:1;     // 1=支持ATA/ATAPI-6
  USHORT  ATA7:1;     // 1=支持ATA/ATAPI-7
  USHORT  ATA8:1;     // 1=支持ATA/ATAPI-8
  USHORT  ATA9:1;     // 1=支持ATA/ATAPI-9
  USHORT  ATA10:1;    // 1=支持ATA/ATAPI-10
  USHORT  ATA11:1;    // 1=支持ATA/ATAPI-11
  USHORT  ATA12:1;    // 1=支持ATA/ATAPI-12
  USHORT  ATA13:1;    // 1=支持ATA/ATAPI-13
  USHORT  ATA14:1;    // 1=支持ATA/ATAPI-14
  USHORT  Reserved2:1;
} wMajorVersion;     // WORD 80: 主版本
USHORT  wMinorVersion;    // WORD 81: 副版本
USHORT  wReserved82[6];    // WORD 82-87: 保留
struct {
  USHORT  Mode0:1;    // 1=支持模式0 (16.7Mb/s)
  USHORT  Mode1:1;    // 1=支持模式1 (25Mb/s)
  USHORT  Mode2:1;    // 1=支持模式2 (33Mb/s)
  USHORT  Mode3:1;    // 1=支持模式3 (44Mb/s)
  USHORT  Mode4:1;    // 1=支持模式4 (66Mb/s)
  USHORT  Mode5:1;    // 1=支持模式5 (100Mb/s)
  USHORT  Mode6:1;    // 1=支持模式6 (133Mb/s)
  USHORT  Mode7:1;    // 1=支持模式7 (166Mb/s) ???
  USHORT  Mode0Sel:1;    // 1=已选择模式0
  USHORT  Mode1Sel:1;    // 1=已选择模式1
  USHORT  Mode2Sel:1;    // 1=已选择模式2
  USHORT  Mode3Sel:1;    // 1=已选择模式3
  USHORT  Mode4Sel:1;    // 1=已选择模式4
  USHORT  Mode5Sel:1;    // 1=已选择模式5
  USHORT  Mode6Sel:1;    // 1=已选择模式6
  USHORT  Mode7Sel:1;    // 1=已选择模式7
} wUltraDMA;      // WORD 88:  Ultra DMA支持能力
USHORT    wReserved89[167];   // WORD 89-255
} IDINFO, *PIDINFO;
2009-2-6 09:39
0
游客
登录 | 注册 方可回帖
返回