Win x64 Tutorial #38l: Master Boot Record
The
CreateFile function can open not only files, but also disk devices. For opening of the first disk of the computer is used the name "\\.\PhysicalDrive0", for opening of the logical section "C:" is used name "\\.\C:". After opening of the device it is possible to use the functions
ReadFile and
WriteFile, that is to read and write directly to clusters and sectors of a disk. The function
DeviceIOControl allows to obtain static information on a disk or to execute formatting of a disk. The program allows to read the Master Boot Record of a disk. When opening the device "\\.\PhysicalDrive0" the Master Boot Record of a disk is in the beginning of the hypothetical file.
bat-file
cls
set masm64_path=\masm64\
set filename=%1
del %filename%.exe
%masm64_path%bin\ml64 /Cp /c /I"%masm64_path%Include" %filename%.asm || exit
%masm64_path%bin\link /SUBSYSTEM:CONSOLE /LIBPATH:"%masm64_path%Lib" ^
/entry:WinMain %filename%.obj /LARGEADDRESSAWARE:NO ^
/ALIGN:16 /BASE:0x400000 /STUB:%masm64_path%\bin\stubby.exe || exit
del %filename%.obj
asm-file
include win64a.inc
MAXSCREENX = 49
MAXSCREENY = 36
.code
WinMain proc
local hIn:qword
local hOut:qword
local hFile:qword
local szReadWrite:qword
local FileSize:qword
local ConsoleWindow:SMALL_RECT
local cci:CONSOLE_CURSOR_INFO
local MOUSE_KEY:INPUT_RECORD
local i:dword
local buffer1[512+3]:byte
local buffer2[3*512]:byte
local buffer3:qword
push rbp
mov ebp,esp
sub esp,(38h+6*8+4+515+3*512+sizeof SMALL_RECT+\
sizeof CONSOLE_CURSOR_INFO+INPUT_RECORD+15)and(-16)
xor ebx,ebx
call FreeConsole
call AllocConsole
mov ecx,STD_INPUT_HANDLE
call GetStdHandle
mov hIn,rax
mov ecx,STD_OUTPUT_HANDLE
call GetStdHandle
mov hOut,rax
mov rcx,rax;hOut ; hConsoleOutput
call GetLargestConsoleWindowSize
; eax return in 31-16 bits: dwCoord.y
; 15-00 bits: dwCoord.x
lea r8d,ConsoleWindow ; lpConsoleWindow
mov [r8],ebx
; ConsoleWindow.Left = 0 ConsoleWindow.Top = 0
sub ax, MAXSCREENX
sbb edx, edx
and ax, dx
add ax, MAXSCREENX-1
mov [r8+SMALL_RECT.Right],ax
shr eax, 16
sub eax, MAXSCREENY
sbb edx, edx
and eax, edx
add eax, MAXSCREENY-1
mov [r8+SMALL_RECT.Bottom],ax
mov edx,TRUE ; bAbsolute
mov rcx,hOut ; hConsoleOutput
call SetConsoleWindowInfo
mov edx,MAXSCREENY*10000h+MAXSCREENX;dwCoord
mov rcx,hOut ; hConsoleOutput
call SetConsoleScreenBufferSize;establish the new size of a window of the console
mov ecx,offset Str0
call SetConsoleTitle
;hide cursor----------------------------------------
lea edx,cci ; lpConsoleCursorInfo
mov rcx,hOut ; hConsoleOutput
call GetConsoleCursorInfo
lea edx,cci ; lpConsoleCursorInfo
mov [rdx+CONSOLE_CURSOR_INFO.bVisible],FALSE
mov rcx,hOut ; hConsoleOutput
call SetConsoleCursorInfo
;------------------------------------------------------
;open physical drive
mov [rsp+30h],rbx ;it has to be equal 0
mov [rsp+28h],rbx ;attribute of the file (if create it)
mov qword ptr [rsp+20h],OPEN_EXISTING ;how to open
xor r9d,r9d;0 ;the pointer on security attr
mov r8d,FILE_SHARE_WRITE ;mode of the general access
mov edx,GENERIC_READ ;access mode
mov ecx,offset filename ;file name
call CreateFile ;open file
inc eax ;eax == INVALID_HANDLE_VALUE ?
jz EXIT
dec eax
mov hFile,rax
;alignment on limit of the double word
lea eax,buffer1
add eax,3
and eax,-4
mov buffer3,rax
;read from Partition Table
mov [rsp+20h],rbx ;0
lea r9d,szReadWrite
mov r8d,512
mov rdx,rax ;pMem2
mov rcx,hFile
call ReadFile
;-------------------------------------------
lea edi,buffer2
mov esi,offset Str2
mov ecx,sizeof Str2
rep movsb
mov rsi,buffer3
mov FileSize,sizeof Str2
mov i,ebx
@@: lodsq
bswap rax
mov r9d,eax
mov [rsp+20h],r9
shr rax,32
mov r9d,eax
lodsq
bswap rax
mov edx,eax
mov [rsp+30h],rdx
shr rax,32
mov [rsp+28h],rax
mov r8d,i
mov edx,offset fmt
mov rcx,rdi
call wsprintf
add edi,eax
add FileSize,rax
inc i
cmp i,512/16
jb @b
mov esi,offset Str1
mov ecx,sizeof Str1
rep movsb
add FileSize,sizeof Str1
;to bring buffer contents to the console
mov [rsp+20h],rbx ;0
lea r9d,szReadWrite
mov r8,FileSize
lea edx,buffer2
mov rcx,hOut
call WriteConsole
;close handle and file----------------------
mov rcx,hFile
call CloseHandle ; close file
mov rcx,hOut ; hObject
call CloseHandle ; close file
;--------------------------------------------------------
@@: lea r9d,szReadWrite
mov r8d,1
lea edx,MOUSE_KEY
mov rcx,hIn
call ReadConsoleInput
lea eax,MOUSE_KEY
cmp [rax+INPUT_RECORD.EventType],MOUSE_EVENT
je @b
cmp [rax+INPUT_RECORD.EventType],KEY_EVENT
jne @b
cmp [rax+INPUT_RECORD.KeyEvent.wVirtualKeyCode],VK_ESCAPE
jne @b
;---------------------------------------------------------
EXIT: mov rcx,hIn ; hObject
call CloseHandle
call FreeConsole
mov ecx,ecx
call ExitProcess
WinMain endp
fmt db ' %.04X0 ',0BAh,' %.08X %.08X ',0B3h,' %.08X %.08X ',0BAh,0Dh,0Ah,0
Str0 db 'Master Boot Record',0
Str1 db 7 dup(20h),0C8h,19 dup (0CDh),0CFh,19 dup (0CDh),0BCh,13,10,\
'For exit press ESC or CTRL+C or CTRL+Break'
;имя устройства (первый диск)
filename db "\\.\PhysicalDrive0",0
Str2 db 10 dup(20h),'0 1 2 3 4 5 6 7 8 9 A B C D E F',0Dh,0Ah,\
7 dup(20h),0C9h,19 dup (0CDh),0D1h,19 dup (0CDh),0BBh,0Dh,0Ah
end