--> Skip to main content
Pelajar Koding

follow us

Vb.Net: Get Hard Disk Manufacture/ Factory Serial Number

So many question about how to get hard disk physical serial number, and mostly answered by using WMI. And it doesn't solve my problem. I used to use HDSN code that I got from Planet Source Code when I was still using Visual Basic 6 (VB6). And now with VB.NET I need the same result but I couldn't get it with WMI. Is there any other way to get  Factory Serial Number without WMI? Finally I got the best solution using DeviceIOControl that I got from a blog named jo0ls' .Net stuff . And I adapt it to my code to fulfill my need. Here are the steps. First I created a windows form project/solution named HDDSerial Number, add a module name SerialNumber.vb and type below codes: Imports System.Runtime.InteropServices Imports Microsoft.Win32.SafeHandles Imports System.Security Imports System.ComponentModel Imports System.Text Module SerialNumber   _   Private Class NativeMethods       "kernel32" , SetLastError:= True )> _       Public Shared Function CreateFile( _        ByVal FileName As String , _        ByVal DesiredAccess As Integer , _        ByVal ShareMode As Integer , _        ByVal SecurityAttributes As IntPtr , _        ByVal CreationDisposition As Integer , _        ByVal FlagsAndAttributes As Integer , _        ByVal hTemplateFile As IntPtr) As SafeFileHandle       End Function       "kernel32.dll" , SetLastError:= True )> _       Friend Shared Function DeviceIoControl( _           ByVal deviceHandle As SafeFileHandle, _           ByVal controlCode As Integer , _           ByRef inBuffer As ATA_PASS_THROUGH_EX_WITH_BUFFERS, _           ByVal inBufferSize As Integer , _           ByRef outBuffer As ATA_PASS_THROUGH_EX_WITH_BUFFERS, _           ByVal outBufferSize As Integer , _           ByRef bytesReturned As Integer , _           ByVal overlapped1 As IntPtr) As Boolean       End Function   End Class   _   Private Structure ATA_PASS_THROUGH_EX       Public Length As Short       Public AtaFlags As Short       Public PathId As Byte       Public TargetId As Byte       Public Lun As Byte       Public ReservedAsUchar As Byte       Public DataTransferLength As Integer       Public TimeOutValue As Integer       Public ReservedAsUlong As Integer       Public DataBufferOffset As IntPtr       _       Public PreviousTaskFile() As Byte       _       Public CurrentTaskFile() As Byte   End Structure   _   Private Structure ATA_PASS_THROUGH_EX_WITH_BUFFERS       Public Apt As ATA_PASS_THROUGH_EX       _       Public Data() As Byte   End Structure   Public Enum HDINFO       HD_MODEL_NUMBER = 0       HD_SERIAL_NUMBER = 1       HD_FIRMWARE_REVISION = 2   End Enum   Public Function HDDInfo( ByVal InfoType As HDINFO) As String       Dim letter As Char = "c"       Const GenericRead As Integer = &H80000000       Const GenericWrite As Integer = &H40000000       Const FileShareRead As Integer = 1       Const FileShareWrite As Integer = 2       Const OpenExisting As Integer = 3       Dim drivePath As String = String .Concat( "\\.\" & letter & ":" )       Using driveHandle As SafeFileHandle = NativeMethods.CreateFile( _        drivePath, _        GenericRead Or GenericWrite, _        FileShareRead Or FileShareWrite, _        IntPtr.Zero, _        OpenExisting, _        0, _        IntPtr.Zero)           If driveHandle.IsInvalid Then              Return "CreateFile ERROR: " & ( New Win32Exception).Message           End If           Dim apex As New ATA_PASS_THROUGH_EX           apex.Length = Marshal.SizeOf(apex)           ' ATA_FLAGS_DATA_IN           apex.AtaFlags = 2           ' The command returns a 512 byte package of berita.           apex.DataTransferLength = 512           apex.TimeOutValue = 10 ' 10 second timeout.           apex.DataBufferOffset = Marshal.OffsetOf( _                     GetType (ATA_PASS_THROUGH_EX_WITH_BUFFERS), "Data" )           ' This contains the command we are requesting.           apex.CurrentTaskFile = New Byte(7)           'the command "IDENTIFY DEVICE"           apex.CurrentTaskFile(6) = &HEC           Dim apexb As New ATA_PASS_THROUGH_EX_WITH_BUFFERS           apexb.Apt = apex           Dim inBufferSize As Integer = Marshal.SizeOf( _                    GetType (ATA_PASS_THROUGH_EX_WITH_BUFFERS))           Dim bytesReturned As Integer           Const IOCTL_ATA_PASS_THROUGH As Integer = &H4D02C           Dim result As Boolean = NativeMethods.DeviceIoControl( _                                   driveHandle, IOCTL_ATA_PASS_THROUGH, _                                   apexb, inBufferSize, apexb, inBufferSize, _                                   bytesReturned, IntPtr.Zero)           If result = False Then               Return "DeviceIOControl ERROR: " & ( New Win32Exception).Message           End If           Select Case InfoType               Case HDINFO.HD_SERIAL_NUMBER                   Return GetString(apexb.Data, 20, 20)               Case HDINFO.HD_FIRMWARE_REVISION                   Return GetString(apexb.Data, 46, 8)               Case HDINFO.HD_MODEL_NUMBER                   Return GetString(apexb.Data, 54, 40)               Case Else                   Return Nothing           End Select       End Using   End Function   Private Function GetString( ByVal bytes() As Byte , _                              ByVal offset As Integer , _                              ByVal length As Integer ) As String       ' The strings are slightly weird - endianness?       ' If you use ASCII.GetBytes Then Each character       ' pair is reversed.       Dim sb As New StringBuilder()       For i As Integer = offset To offset + length - 1 Step 2           sb.Append(Chr(bytes(i + 1)))           sb.Append(Chr(bytes(i)))       Next       Return RTrim(LTrim(sb.ToString))   End Function End Module Set UI of Form1 Text "Hardisk Serial Number", add 3 labels and 3 TextBoxes. Name textboxes as txtSerialNumber, txtModel, and txtFirmware. Then type below code: Imports System.Management Public Class Form1     Private Sub Form1_Load( ByVal sender As Object, _           ByVal e As EventArgs) Handles MyBase .Load         Try             txtSerialNumber.Text = HDDInfo(HDINFO.HD_SERIAL_NUMBER)             txtModel.Text = HDDInfo(HDINFO.HD_MODEL_NUMBER)             txtFirmware.Text = HDDInfo(HDINFO.HD_FIRMWARE_REVISION)         Catch ex As Exception             MsgBox(ex.Message)         End Try     End Sub End Class Test run, then here is my PC result: Notes: Don't forget to Run as Administrator so application could work properly on Vista, Windows 7, and Windows 8. Reference: http://stackoverflow.com/questions/782053/get-hdd-and-not-volume-serial-number-on-vista-ultimate-64-bit http://jo0ls-dotnet-stuff.blogspot.co.id/2011/02/getting-hard-disk-drive-informasi-with.html Click here if you like this article.
Sumber http://rani-irsan.blogspot.com

You Might Also Like:

Comment Policy: Silahkan tuliskan komentar Anda yang sesuai dengan topik postingan halaman ini. Komentar yang berisi tautan tidak akan ditampilkan sebelum disetujui.
Buka Komentar