I've been trying to get the serial number of a compact flash card on a Windows CE 4.2 device using EVC++ 4.0, using IOCTL_DISK_GET_STORAGEID and the STORAGE_IDENTIFICATION structure it populates. (relevant MSDN Pages linked below)
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/wceddk40/html/_wceddk_ioctl_disk_get_storageid.asp
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/wceddk40/html/_wceddk_storage_identification.asp
The following code produces the following result
<result>
the message box at the end returns the follow value as the serial, minus the inverted comma's
" 04A38A1CA33A3100A5"
I know for a fact that the serial number of the CF-Card is -> Volume Serial Number : 0xc7019d4
second result gathered by using xp shell command -> "fsutil fsinfo volumeinfo g:\" (where g:\ is my local CF-Card Drive
</result>
<Code>
#include "stdafx.h"
#include <windows.h>
#include <winioctl.h>
#define IOCTL_DISK_BASE FILE_DEVICE_DISK
#define IOCTL_DISK_GET_STORAGEID CTL_CODE(IOCTL_DISK_BASE, 0x709, METHOD_BUFFERED, FILE_ANY_ACCESS)
typedef struct _STORAGE_IDENTIFICATION {
DWORD dwSize;
DWORD dwFlags;
DWORD dwManufactureIDOffset;
DWORD dwSerialNumOffset;
} STORAGE_IDENTIFICATION, *PSTORAGE_IDENTIFICATION;
#define MANUFACTUREID_INVALID 0x01
#define SERIALNUM_INVALID 0x02
int WINAPI WinMain( HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
HANDLE hDisk = CreateFile(_T("\\PCMCIA-CF Card\\Vol:"), GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, 0, NULL);
if (!hDisk) return -1;
PSTORAGE_IDENTIFICATION pStoreInfo = (PSTORAGE_IDENTIFICATION) new BYTE[100];
if (!pStoreInfo) {
CloseHandle(hDisk);
return -1;
}
DWORD dwBytesRet;
if (!DeviceIoControl(hDisk, IOCTL_DISK_GET_STORAGEID, NULL, 0, pStoreInfo, 100, &dwBytesRet, NULL)) { //3000 changed to 46
DWORD err = GetLastError();
delete [] pStoreInfo;
CloseHandle(hDisk);
return -1;
}
TCHAR tStr[200];
if (dwBytesRet)
{
unsigned char *SerialNo=(((BYTE *)pStoreInfo)+pStoreInfo->dwSerialNumOffset);
int i =0;
while (SerialNo[i]!=0 && i < (int)(dwBytesRet-pStoreInfo->dwSerialNumOffset))
{
tStr[i] = (TCHAR)SerialNo[i];
i++;
}
tStr[i] = 0;
}
delete [] pStoreInfo;
CloseHandle(hDisk);
MessageBox(NULL, tStr, _T("HDD Serial No"), MB_OK);
return 0;
}
</Code>
<ReleventInfo>
On running the pStoreInfo structure fills with the following data
DWORD dwSize; = 46
DWORD dwFlags; = 0
DWORD dwManufactureIDOffset; = 16
DWORD dwSerialNumOffset; = 25
</ReleventInfo>
Please could anyone point out if I'm doing something stupid, or provide an explanation as to why this code behaves in this manner.
Any commentary or advise is welcome
Regards,
Bm
---
Those who live by the sword, get shot by those who don’t.