-
Attention!
The programs were written and tested in Windows Seven pro, how the programs will work in Windows eight I don't know
Win x64 Tutorial #2: MessageBox
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
include user32.inc
includelib kernel32.lib
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
.code
WinMain proc
sub rsp,5*8
invoke MessageBox,NULL,&MsgBoxText,&MsgCaption,MB_OK
invoke ExitProcess,NULL
WinMain endp
MsgCaption db "Iczelion's tutorial #2",0
MsgBoxText db "Win64 Assembly is Great!",0
end
bat-file cls
set masm64_path=\masm64\
set filename=%1
if exist %1.rc (
%masm64_path%bin\RC /r %filename%.rc || exit
%masm64_path%bin\cvtres /machine:X64 %filename%.res || exit
%masm64_path%bin\ml64 /Cp /c /I"%masm64_path%Include" %filename%.asm || exit
%masm64_path%bin\link /SUBSYSTEM:WINDOWS /LIBPATH:"%masm64_path%Lib" ^
/entry:WinMain %filename%.obj %filename%.res /LARGEADDRESSAWARE:NO ^
/ALIGN:16 /SECTION:.text,W ^
/BASE:0x400000 /STUB:%masm64_path%\bin\stubby.exe || exit
del %filename%.obj
del %filename%.res
) else (
%masm64_path%bin\ml64 /Cp /c /I"%masm64_path%Include" %filename%.asm || exit
%masm64_path%bin\link /SUBSYSTEM:WINDOWS /LIBPATH:"%masm64_path%Lib" ^
/entry:WinMain %filename%.obj /LARGEADDRESSAWARE:NO ^
/ALIGN:16 /SECTION:.text,W ^
/BASE:0x400000 /STUB:%masm64_path%\bin\stubby.exe || exit
del %filename%.obj
)
Win x64 Tutorial #2a: MessageBox
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
.code
WinMain proc
enter 4*8,0
xor ecx,ecx
mov r9,rcx
lea r8,MsgCaption
lea edx,MsgBoxText
call MessageBox
leave
ret
WinMain endp
MsgCaption db "Iczelion's tutorial #2a",0
MsgBoxText db "Win64 Assembly is Great!",0
end
Win x64 Tutorial #2b: MessageBox
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
include user32.inc
includelib kernel32.lib
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
.code
WinMain proc
push rbp
mov rbp,rsp
sub rsp,30h
invoke GetModuleHandle,NULL
mov x1,rax
invoke LoadIcon,NULL,IDI_APPLICATION
mov x2,rax
invoke LoadCursor,NULL,IDC_ARROW
mov x3,rax
mov rax,x1
mov [rsp+20h],eax
lea ecx,buffer
lea edx,fmt
mov r8,x3
mov r9,x2
call wsprintf
invoke MessageBox,NULL,&buffer,&MsgCaption,MB_OK
invoke ExitProcess,NULL
WinMain endp
MsgCaption db "Iczelion's tutorial #2b",0
fmt db "hCursor = %08Xh",0Ah,"hIcon = %08Xh",0Ah,"hInstance =%08Xh",0
n = $ - fmt + 12
buffer db n dup(?)
x1 dq ?
x2 dq ?
x3 dq ?
end
-
Win x64 Tutorial #3: A Simple Window
include win64a.inc
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov eax,10029h
push rax ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOWTEXT;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
@@: lea ecx,msg
xor edx,edx
xor r8d,r8d
xor r9d,r9d
call GetMessage
lea ecx,msg
call DispatchMessage
jmp @b
WinMain endp
WndProc:cmp edx,WM_DESTROY
je wmDESTROY
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
;---------------------------------------
ClassName db 'Win64 Iczelion lesson #3',0
end
- call fuctions GetModuleHandle, LoadIcon, LoadCursor is unnecessary, they always return the same number, you can see the debugger in advance or in "Tutorial 2b: MessageBox"
- instead PostQuitMessage directly use ExitProcess it will simplify the message loop
-
Win x64 Tutorial #4: Painting with Text
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hwnd equ [rbp+10h]
ps equ [rbp-sizeof PAINTSTRUCT]
expRect equ ps-sizeof RECT
enter sizeof PAINTSTRUCT+sizeof RECT+28h,0
mov hwnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_SIZE
je wmPAINT
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmSIZE: mov r8d,1
xor edx,edx
call InvalidateRect;send WM_PAINT if size changes
jmp wmBYE
wmPAINT: lea edx,ps
call BeginPaint
mov rcx,hwnd
lea rdx,expRect
call GetClientRect
mov qword ptr [rbp-60h],DT_SINGLELINE or DT_CENTER or DT_VCENTER
lea r9,expRect
or r8,-1
lea edx,expTxt
mov rcx,ps.PAINTSTRUCT.hdc
call DrawText
lea edx,ps
mov rcx,hwnd
call EndPaint
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #4: Painting with Text',0
expTxt db 'Win64 assembly with MASM is great and easy',0
end
-
Win x64 Tutorial #5: More about Text
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include gdi32.inc
includelib gdi32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hwnd equ [rbp+10h]
ps equ [rbp-sizeof PAINTSTRUCT]
enter sizeof PAINTSTRUCT+98h,0
mov hwnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmPAINT: lea edx,ps
call BeginPaint
mov edx,OBJ_FONT
mov rcx,ps.PAINTSTRUCT.hdc
call GetCurrentObject
push rax ;default font object
lea rax,expFont
push rax
push DEFAULT_PITCH or FF_SCRIPT
push rbx;DEFAULT_QUALITY
push rbx;CLIP_DEFAULT_PRECIS
push rbx;OUT_DEFAULT_PRECIS
push OEM_CHARSET
push rbx
push rbx
push rbx
push 400
mov r9,rbx
mov r8,rbx
mov edx,12
mov ecx,26
push rbx
push rbx
push rbx
push rbx
call CreateFont
mov rdx,rax
mov rcx,ps.PAINTSTRUCT.hdc
call SelectObject
mov edx,32C8C8h
mov rcx,ps.PAINTSTRUCT.hdc
call SetTextColor
mov edx,0FF0000h
mov rcx,ps.PAINTSTRUCT.hdc
call SetBkColor
lea ecx,expTxt
call lstrlen ;help us to count the string length
push rax
lea r9,expTxt
xor edx,edx
mov r8,rdx
mov rcx,ps.PAINTSTRUCT.hdc
push rbx
push rbx
push rbx
push rbx
call TextOut
add rsp,30h
pop rdx
mov rcx,ps.PAINTSTRUCT.hdc
call SelectObject
lea edx,ps
mov rcx,hwnd
call EndPaint
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #5:More about Text',0
expTxt db 'Win64 assembly with MASM is great and easy',0
expFont db 'script',0
end
-
Win x64 Tutorial #6: Keyboard Input
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include gdi32.inc
includelib gdi32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0;90h,0
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 352
push 512
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hwnd equ [rbp+10h]
ps equ [rbp-sizeof PAINTSTRUCT]
enter sizeof PAINTSTRUCT+20h,0
mov hwnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_CHAR
je wmCHAR
cmp edx,WM_PAINT
je wmPAINT
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCHAR: mov expChar,r8
mov r8d,TRUE
xor edx,edx
call InvalidateRect
jmp wmBYE
wmPAINT: lea edx,ps
call BeginPaint
sub rsp,10h
mov qword ptr [rsp+20h],lengthof Message
lea r9,Message
mov r8d,90
mov edx,192
mov rcx,ps.PAINTSTRUCT.hdc
call TextOut
mov qword ptr [rsp+20h],1
lea r9,expChar
mov r8d,150
mov edx,242
mov rcx,ps.PAINTSTRUCT.hdc
call TextOut
add rsp,10h
lea edx,ps
mov rcx,hwnd
call EndPaint
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #6: Keyboard Input',0
Message db 'Press any key'
expChar dq '?'
end
-
Win x64 Tutorial 7: Mouse Input
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include gdi32.inc
includelib gdi32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hwnd equ [rbp+10h]
ps equ [rbp-sizeof PAINTSTRUCT]
enter sizeof PAINTSTRUCT+30h,0
mov hwnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_LBUTTONDOWN
je wmLBUTTONDOWN
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmLBUTTONDOWN: ;low order lParam = x
;high order lParam = y
mov word ptr expHPoint.x,r9w;eax
shr r9,16
mov expHPoint.y,r9d
or expClick,TRUE
mov r8d,TRUE
xor edx,edx
call InvalidateRect
jmp wmBYE
wmPAINT: lea edx,ps
call BeginPaint
cmp expClick,TRUE
jne wmPAINT_END
mov qword ptr [rsp+20h],lengthof expTxt
lea r9,expTxt
mov r8d,expHPoint.y
mov edx,expHPoint.x
mov rcx,ps.PAINTSTRUCT.hdc
call TextOut
wmPAINT_END: lea edx,ps
mov rcx,hwnd
call EndPaint
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #7:Mouse Input',0
expTxt db 'You clicked here!',0
expClick db 0
expHPoint POINT <0>
end
-
Win x64 Tutorial #7a: Mouse Input
In difference from Lesson 7 Iczelion'a which handles the event by pressing the left click and output only the inscription "You clicked here!", we will handle pressing the left and right mouse click, and will display the inscription "left-clicking" and "right-clicking "and these inscriptions will be so much the importance we assign a constant MAXRECTS. If the number exceeds the number of clicks MAXRECTS is a beep sounds.
include win64a.inc
include gdi32.inc
includelib gdi32.lib
MAXRECTS = 40;the maximum number of processed mouse clicks
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
@@: lea ecx,msg
xor edx,edx
xor r8d,r8d
xor r9d,r9d
call GetMessage
lea ecx,msg
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hwnd equ [rbp+10h]
lParam equ [rbp+28h]
ps equ [rbp-sizeof PAINTSTRUCT]
enter sizeof PAINTSTRUCT+30h,0
mov lParam,r9
xor eax,eax
mov hwnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_LBUTTONDOWN
je wmLBUTTONDOWN
cmp edx,WM_RBUTTONDOWN
je wmRBUTTONDOWN
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmLBUTTONDOWN: ;low order lParam = x
;high order lParam = y
mov eax,80000000h
wmRBUTTONDOWN: add eax,lParam
cmp nextRect,MAXRECTS-1
jge @f
inc nextRect
mov ecx,nextRect
mov [ecx*4+recs],eax
xor edx,edx
mov rcx,hwnd
mov r8d,TRUE
call InvalidateRect
jmp wmBYE
@@: xor ecx,ecx
call MessageBeep
jmp wmBYE
wmPAINT: mov ebx,nextRect
inc ebx;cmp nextRect,-1
jz wmBYE
lea edx,ps
call BeginPaint
mov edx,TRANSPARENT
mov rcx,rax
call SetBkMode
@@: mov eax,[ebx*4+recs-4]
mov ecx,1
shl eax,1
adc ecx,0
shr eax,1
shl ecx,4
xor edx,edx
mov dx,ax;nYStart
shr eax,16
mov r8d,eax;nXStart
mov rax,[PS+ecx]
mov [rsp+20h],rax;cchString
mov r9,[PS+ecx+8];lpString
mov rcx,ps.PAINTSTRUCT.hdc
call TextOut
dec ebx
jnz @b
wmPAINT_END: lea edx,ps
mov rcx,hwnd
call EndPaint
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #7a: Mouse Input',0
text1 db 'right-clicking'
text2 db 'left-clicking'
PS dq 0,0,lengthof text1, text1, lengthof text2, text2
recs dd MAXRECTS dup(?)
nextRect dd -1
end
-
Win x64 Tutorial #8: Menu
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
ZZZ_TEST equ 0
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0;90h,0
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
lea eax,menu_name
push rax ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
enter 20h,0
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCOMMAND:cmp r8,ZZZ_EXIT
je wmDESTROY
show_msg:mov r9,rbx;r9=MB_OK
mov rdx,menu_handlers[r8*8]
lea r8,menu_name
call MessageBox
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8: Menu',0
menu_name db 'ZZZ_Menu',0
test_msg db 'You select menu item TEST',0
open_msg db 'You select menu item OPEN',0
save_msg db 'You select menu item SAVE',0
menu_handlers dq test_msg, open_msg, save_msg
end
rc-file#define ZZZ_TEST 0
#define ZZZ_OPEN 1
#define ZZZ_SAVE 2
#define ZZZ_EXIT 3
ZZZ_Menu MENU
{
POPUP "&File"
{ MENUITEM "&Test",ZZZ_TEST
MENUITEM "&Open",ZZZ_OPEN
MENUITEM "&Save",ZZZ_SAVE
MENUITEM SEPARATOR
MENUITEM "&Exit",ZZZ_EXIT
}
MENUITEM "&Exit",ZZZ_EXIT
}
-
Win x64 Tutorial #25: Simple Bitmap
like Iczelion's tutoral
asm-fileinclude win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
IDB_MYBITMAP equ 100
.code
WinMain proc
local msg:MSG
push rbp
mov rbp,rsp
sub rsp,sizeof MSG
xor ebx,ebx
push 10029h ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shr esi,7;Special CreateWindow position value CW_USEDEFAULT=8000h
push rbx
push rbx
push 320
push 300
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
;---------------------------------------------------------------
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
LOCAL ps:PAINTSTRUCT
LOCAL hMemDC:HDC
LOCAL rect:RECT
push rbp
mov rbp,rsp
sub rsp,sizeof PAINTSTRUCT+sizeof RECT+8+40h
mov hWnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_PAINT
je wmPAINT
leave
jmp DefWindowProc
wmDESTROY:mov rcx,hBitmap
call DeleteObject
xor ecx,ecx
call ExitProcess
wmCREATE:mov edx,IDB_MYBITMAP
mov ecx,IMAGE_BASE
call LoadBitmap
mov hBitmap,rax
jmp wmBYE
wmPAINT:lea edx,ps
call BeginPaint
mov rcx,rax
call CreateCompatibleDC
mov hMemDC,rax
mov rdx,hBitmap
mov rcx,rax
call SelectObject
lea edx,rect
mov rcx,hWnd
call GetClientRect
mov qword ptr [rsp+40h],SRCCOPY
mov [rsp+38h],rbx
mov [rsp+30h],rbx
mov rax,hMemDC
mov [rsp+28h],rax
mov eax,rect.bottom
mov [rsp+20h],rax
mov r9d,rect.right
mov r8,rbx
xor edx,edx
mov rcx,ps.hdc
call BitBlt
mov rcx,hMemDC
call DeleteDC
lea edx,ps
mov rcx,hWnd
call EndPaint
wmBYE: leave
retn
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion lesson #25a',0
hBitmap dq ?
end
rc-file#define IDB_MYBITMAP 100
IDB_MYBITMAP BITMAP "Images\\tweety78.bmp"
but it can be a lot easier
include win64a.inc
include gdi32.inc
includelib gdi32.lib
.code
WinMain proc
local msg:MSG
push rbp
mov rbp,rsp
sub rsp,sizeof MSG
xor ebx,ebx
mov esi,400000h
lea rdi,ClassName
mov qword ptr [rsp+28h],LR_LOADFROMFILE
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
mov edx,edi
mov ecx,esi
call LoadImage
mov rcx,rax
call CreatePatternBrush
push 10029h ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push rax ;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea eax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 305
push 286
push rsi
push rsi
mov r9d,WS_OVERLAPPED or WS_VISIBLE or WS_CAPTION or \
WS_SYSMENU or WS_MINIMIZEBOX
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:cmp edx,WM_DESTROY
je wmDESTROY
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
;---------------------------------------
ClassName db 'Images\tweety78.bmp',0
end
-
those are nice, Mikl :t
i haven't had the chance to play with 64-bit code
but, when i get around to it, these will come in handy
-
Hi, Miki__,
Great Stuff,...I was wondering what MASM 64-bit code looked like,...
Where do you find: win64.inc ???
-
Where do you find: win64.inc ???
Hi, Zen!
On the site http://dsmhelp.narod.ru/environment.htm (http://dsmhelp.narod.ru/environment.htm) you can find a set of lib- and inc-files to create 64-bit applications in assembler, as well as a lot of useful macros. Sorry, but the forum rules do not allow me to attach the zip-file size of 4 MB with lib- and inc- files. You can easily find lib- and inc-files in my attach-files above. (http://www.cyberforum.ru/images/smilies/good3.gif)
-
Thanks, Miki__,
On the site http://dsmhelp.narod.ru/environment.htm you can find a set of lib- and inc-files to create 64-bit applications in assembler, as well as a lot of useful macros.
-
Hi Mikl__,
you're a hard working man. Good work by the way.
Gunther
-
Win x64 Tutorial #8a: Menu and LoadMenu
asm-file
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
ZZZ_TEST equ 0
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
IMAGE_BASE equ 400000h
ZZZ_Menu equ 30
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0;90h,0
xor ebx,ebx
push 10029h ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea eax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
mov edx,ZZZ_Menu
mov ecx,IMAGE_BASE
call LoadMenu
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rax
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
enter 20h,0
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCOMMAND:cmp r8,ZZZ_EXIT
je wmDESTROY
show_msg:mov r9,rbx;r9=MB_OK
mov rdx,menu_handlers[r8*8]
lea r8,menu_name
call MessageBox
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8a: Menu and LoadMenu',0
menu_name db 'ZZZ_Menu',0
test_msg db 'You select menu item TEST',0
open_msg db 'You select menu item OPEN',0
save_msg db 'You select menu item SAVE',0
menu_handlers dq test_msg, open_msg, save_msg
end
rc-file#define ZZZ_TEST 0
#define ZZZ_OPEN 1
#define ZZZ_SAVE 2
#define ZZZ_EXIT 3
#define ZZZ_Menu 30
ZZZ_Menu MENU
{
POPUP "&File"
{ MENUITEM "&Test",ZZZ_TEST
MENUITEM "&Open",ZZZ_OPEN
MENUITEM "&Save",ZZZ_SAVE
MENUITEM SEPARATOR
MENUITEM "&Exit",ZZZ_EXIT
}
MENUITEM "&Exit",ZZZ_EXIT
}
-
Win x64 Tutorial #8b: Menu and template-structure
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
ZZZ_TEST equ 0
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
IMAGE_BASE equ 400000h
;----------------macros------------------
du macro string
local bslash
bslash = 0
irpc c,<string>
if bslash eq 0
if '&c' eq "/"
bslash = 1
elseif '&c'gt 127
db ('&c'- 0B0h),4
else
dw '&c'
endif
else
bslash = 0
if '&c' eq "n"
DW 0Dh,0Ah
elseif '&c' eq "/"
dw '/'
elseif '&c' eq "r"
dw 0Dh
elseif '&c' eq "l"
dw 0Ah
elseif '&c' eq "s"
dw 20h
elseif '&c' eq "c"
dw 3Bh
elseif '&c' eq "t"
dw 9
endif
endif
endm
dw 0
endm
;-----------------------------------------
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0;90h,0
xor ebx,ebx
push 10029h ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea eax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
lea ecx,appMenuTemplate
call LoadMenuIndirect
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rax
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:enter 20h,0
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCOMMAND:cmp r8,ZZZ_EXIT
je wmDESTROY
show_msg:mov r9,rbx;r9=MB_OK
mov rdx,menu_handlers[r8*8]
lea r8,menu_name
call MessageBox
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8b: Menu and template-structure',0
menu_name db 'ZZZ_Menu',0
test_msg db 'You select menu item TEST',0
open_msg db 'You select menu item OPEN',0
save_msg db 'You select menu item SAVE',0
menu_handlers dq test_msg, open_msg, save_msg
align 8
appMenuTemplate dw 1 ; menu template version
dw 4 ; offset from end of this word to menu item list
dd 0 ; menu bar help ID
dd MFT_STRING,MFS_ENABLED,0
dw MFR_POPUP ; first column
du <&File>
dw 0 ; pad to align 4
dd 0 ; popup help ID
dd MFT_STRING,MFS_ENABLED,ZZZ_TEST
dw 0
du <&Test>
dw 0 ; pad to align 4
dd MFT_STRING,MFS_ENABLED,ZZZ_OPEN
dw 0
du <&Open>
dw 0 ; pad to align 4
dd MFT_STRING,MFS_ENABLED,ZZZ_SAVE
dw 0
du <&Save>
dw 0 ; pad to align 4
dd MFT_SEPARATOR,0,0
dw 0,0 ; pad to align 4
dd MFT_STRING,MFS_ENABLED,ZZZ_EXIT
dw MFR_END ; bottom of column
du <&Exit>
dw 0 ; pad to align 4
dd MFT_STRING,MFS_ENABLED,ZZZ_EXIT
dw MFR_END ; second column, last one
du <&Exit>
dw 0 ; pad to align 4
dd 0 ; popup help ID
end
-
Win x64 Tutorial #8c: Program creation menu
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
ZZZ_TEST equ 0
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
IMAGE_BASE equ 400000h
;-----------------------------------------
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0
xor ebx,ebx
push 10029h ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea eax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hWnd equ [rbp+10h]
enter 20h,0
mov hWnd,rcx
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCREATE: call CreatePopupMenu
mov rdi,rax
lea r9,menu_test1
mov r8,rbx;ZZZ_TEST
xor edx,edx;MF_STRING
mov rcx,rdi
call AppendMenu
lea r9,menu_open1
mov r8d,ZZZ_OPEN
xor edx,edx;MF_STRING
mov rcx,rdi
call AppendMenu
lea r9,menu_save1
mov r8d,ZZZ_SAVE
xor edx,edx;MF_STRING
mov rcx,rdi
call AppendMenu
mov r9,rbx
mov r8,rbx
mov edx,MF_SEPARATOR
mov rcx,rdi
call AppendMenu
lea r9,menu_exit1
mov r8d,ZZZ_EXIT
xor edx,edx;MF_STRING
mov rcx,rdi
call AppendMenu
call CreateMenu
mov hMenu,rax
lea r9,menu_file
mov r8,rdi
mov edx,MF_POPUP
mov rcx,rax
call AppendMenu
lea r9,menu_exit1
mov r8d,ZZZ_EXIT
xor edx,edx;MF_STRING
mov rcx,hMenu
call AppendMenu
mov rdx,hMenu
mov rcx,hWnd
call SetMenu
jmp wmBYE
wmCOMMAND:cmp r8,ZZZ_EXIT
je wmDESTROY
show_msg:mov r9,rbx;r9=MB_OK
mov rdx,menu_handlers[r8*8]
lea r8,menu_name
call MessageBox
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8c: Program creation menu',0
menu_file db 'File',0
menu_test1 db 'Test',0
menu_open1 db 'Open',0
menu_save1 db 'Save',0
menu_exit1 db 'Exit',0
menu_name db 'ZZZ_Menu',0
test_msg db 'You select menu item TEST',0
open_msg db 'You select menu item OPEN',0
save_msg db 'You select menu item SAVE',0
menu_handlers dq test_msg, open_msg, save_msg
hMenu dq ?
end
-
Win x64 Tutorial #8d: Creating the dynamic menu
asm-fileinclude win64a.inc
IMAGE_BASE equ 400000h
STYLBTN equ BS_DEFPUSHBUTTON+WS_VISIBLE+WS_CHILD
;-----------------------------------------
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0;90h,0
xor ebx,ebx
push 10029h ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea eax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hWnd equ [rbp+10h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
buffer equ [rbp-sizeof_buffer]
MENI equ buffer-sizeof MENUITEMINFO
sizeof_buffer = 96
enter sizeof MENUITEMINFO+sizeof_buffer+20h,0
mov hWnd,rcx
mov lParam,r9
mov wParam,r8
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_MENUSELECT
je wmMENUSELECT
wmDEFAULT: leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCOMMAND: mov rax,HWNDBTN;проверить, не нажата ли кнопка
cmp lParam,rax
je YES_BUT
cmp word ptr wParam,5;проверить, не выбран ли пункт меню MENUC - выход
je wmDESTROY
cmp word ptr wParam,4;проверить, не выбран ли пункт меню с идентификатором 5
jne wmBYE
YES_BUT:;обработка нажатия кнопки. сначала стереть текст в заголовке
lea r9,SPACE
mov r8,rbx
mov edx,WM_SETTEXT
call SendMessage
dec PRIZN
jns l5
add PRIZN,3;if (PRIZN < 0) PRIZN=2
jmp l5
wmCREATE: add rsp,40h
push rbx
push IMAGE_BASE
push rbx
push rcx;[hWnd]
push 25
push 120
push 10
push 10
mov r9,STYLBTN
lea r8,CPBUT
mov edx,offset CLSBUTN
xor ecx,ecx
sub rsp,20h
call CreateWindowEx
mov HWNDBTN,rax;запомнить дескриптор кнопки
l5: ;загрузить необходимое меню
mov rdx,PRIZN
mov ecx,IMAGE_BASE
call LoadMenu
mov rdx,rax
mov rcx,hWnd
call SetMenu;установить меню
jmp wmBYE
wmMENUSELECT: mov rcx,lParam
jrcxz wmBYE;пропускаем первое сообщение при обращении к меню
test word ptr wParam+2,MF_POPUP;проверяем, что активизировано - пункт меню или заголовок выпадающего меню
setne al
movzx r8,al
;если 0, то в lword wParam идентификатор пункта меню
;если 1, то в lword wParam номер заголовка выпадающего меню
;заполнение структуры для вызова функции GetMenuItemInfo
lea r9,MENI
mov [r9+MENUITEMINFO.cbSize],sizeof MENUITEMINFO
mov [r9+MENUITEMINFO.fMask],MIIM_TYPE
mov [r9+MENUITEMINFO.hSubMenu],rcx;MENI.hSubMenu:=lParam
lea rax,buffer
mov [r9+MENUITEMINFO.dwTypeData],rax;указатель на буфер, получающий необходимую строку
mov [r9+MENUITEMINFO.cch],sizeof_buffer;длина буфера
;получить информацию о выбранном пункте меню
movzx rdx,word ptr wParam
call GetMenuItemInfo
;проверить результат выполнения функции
or rax,rax;cmp eax,0
jz wmBYE
;вывести название пункта меню как заголовок всего окна
lea r9,MENI
mov r9,[r9+MENUITEMINFO.dwTypeData]
mov r8,rbx
mov edx,WM_SETTEXT
mov rcx,hWnd
call SendMessage
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8d: Creating the dynamic menu',0
CPBUT db 'Change menu',0
CLSBUTN db 'BUTTON',0
HWNDBTN dq 0
PRIZN dq 2
SPACE db 30 dup(32),0
end
rc-file#define WS_SYSMENU 0x00080000L
#define WS_MINIMIZEDBOX 0x00020000L
#define WS_MAXIMIZEDBOX 0x00010000L
#define WS_POPUP 0x80000000L
#define DS_3DLOOK 0x0004L
#define st WS_SYSMENU | WS_MINIMIZEDBOX | WS_MAXIMIZEDBOX
#define MENUC 0
#define MENUP 1
#define MENUN 2
MENUN MENU
{
MENUITEM "",0
}
MENUP MENU
{
POPUP "First point"
{
MENUITEM "First",1
MENUITEM "Second",2
}
POPUP "Second point"
{
MENUITEM "Third",3
MENUITEM "Fourth",4
MENUITEM SEPARATOR
POPUP "Else submenu"
{
MENUITEM "Additional point",6
}
MENUITEM "Exit",5
}
}
MENUC MENU
{
POPUP "First set"
{
MENUITEM "White",101
MENUITEM "Grey",102
MENUITEM "Black",103
}
POPUP "Second set"
{
MENUITEM "Red",104
MENUITEM "Blue",105
MENUITEM "Green",106
}
}
-
Win x64 Tutorial #8e: Creating a floating menu
include win64a.inc
IMAGE_BASE equ 400000h
ZZZ_TEST equ 0
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
;-----------------------------------------
.code
WinMain proc
enter sizeof WNDCLASSEX+20h,0
xor ebx,ebx
push 10029h ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea eax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov edi,offset msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hWnd equ [rbp+10h]
rect equ [rbp-18h]
hMenu equ [rbp-20h]
enter sizeof RECT+8+40h+8,0
mov hWnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_RBUTTONDOWN
je wmRBUTTONDOWN
wmDEFAULT: leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmRBUTTONDOWN: call CreatePopupMenu
mov edi,eax;hPopupMenu,eax
call CreateMenu
mov hMenu,rax;hMenu=rbp-20h
mov r9d,offset menu_test1
mov r8,rbx;ZZZ_TEST
xor edx,edx;MF_STRING
mov ecx,edi
call AppendMenu
mov r9d,offset menu_open1
mov r8d,ZZZ_OPEN
xor edx,edx;MF_STRING
mov ecx,edi
call AppendMenu
mov r9d,offset menu_save1
mov r8d,ZZZ_SAVE
xor edx,edx;MF_STRING
mov ecx,edi
call AppendMenu
mov r9,rbx
mov r8,rbx
mov edx,MF_SEPARATOR
mov ecx,edi
call AppendMenu
mov r9d,offset menu_exit1
mov r8d,ZZZ_EXIT
xor edx,edx;MF_STRING
mov ecx,edi
call AppendMenu
mov r9d,offset menu_file
mov r8,rdi
mov edx,MF_POPUP
mov rcx,hMenu
call AppendMenu
mov r9d,offset menu_exit1
mov r8d,ZZZ_EXIT
xor edx,edx;MF_STRING
mov rcx,hMenu
call AppendMenu
mov ecx,edi
xor edx,edx;mov edx,TPM_LEFTALIGN+TPM_LEFTBUTTON
mov r8d,msg.pt.x
mov r9d,msg.pt.y
mov [rsp+30h],rbx
mov rax,hWnd
mov [rsp+28h],rax
mov [rsp+20h],rbx
call TrackPopupMenu
lea rdx,rect;rect=rbp-18h
mov rcx,hWnd
call GetWindowRect
jmp wmBYE
wmCOMMAND: cmp r8,ZZZ_EXIT
je wmDESTROY
show_msg: mov r9,rbx;r9=MB_OK
mov rdx,[menu_handlers+r8*8]
mov r8d,offset menu_name
call MessageBox
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8e: Creating a floating menu',0
menu_file db 'File',0
menu_test1 db 'Test',0
menu_open1 db 'Open',0
menu_save1 db 'Save',0
menu_exit1 db 'Exit',0
menu_name db 'ZZZ_Menu',0
test_msg db 'You select menu item TEST',0
open_msg db 'You select menu item OPEN',0
save_msg db 'You select menu item SAVE',0
menu_handlers dq test_msg, open_msg, save_msg
msg MSG <>
end
-
Win x64 Tutorial #8g: Using the accelerator table
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
ZZZ_TEST equ 0
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
IDM_MENU equ 37
IDR_MAINACCEL equ 105
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0;90h,0
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
push IDM_MENU ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov hwnd,rax
mov ecx,IMAGE_BASE
mov edx,IDR_MAINACCEL
call LoadAccelerators
mov ACC,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
mov r8d,edi
mov rdx,ACC
mov rcx,hwnd
call TranslateAccelerator
or eax,eax
jne @b
mov ecx,edi
call TranslateMessage
jmp @b
WinMain endp
WndProc:
enter 20h,0
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCOMMAND:and r8,11y
cmp r8,ZZZ_EXIT
je wmDESTROY
show_msg:mov r9,rbx;r9=MB_OK
mov rdx,menu_handlers[r8*8]
mov r8d,offset menu_name
call MessageBox
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8g: Using the accelerator table',0
menu_name db 'ZZZ_Menu',0
test_msg db 'You select menu item TEST',0
open_msg db 'You select menu item OPEN',0
save_msg db 'You select menu item SAVE',0
menu_handlers dq test_msg, open_msg, save_msg
ACC dq ?
hwnd dq ?
end
rc-file#define ZZZ_TEST 0
#define ZZZ_OPEN 1
#define ZZZ_SAVE 2
#define ZZZ_EXIT 3
#define IDM_MENU 37
#define IDR_MAINACCEL 105
IDM_MENU MENU
{
POPUP "&File"
{ MENUITEM "&Test\tCtrl+T",ZZZ_TEST
MENUITEM "&Open\tCtrl+O",ZZZ_OPEN
MENUITEM "&Save\tCtrl+S",ZZZ_SAVE
MENUITEM SEPARATOR
MENUITEM "&Exit\tCtrl+X",ZZZ_EXIT
}
MENUITEM "&Exit",ZZZ_EXIT
}
IDR_MAINACCEL ACCELERATORS DISCARDABLE
{
"^T",ZZZ_TEST
"^O",ZZZ_OPEN
"^S",ZZZ_SAVE
"^X",ZZZ_EXIT
}
-
Win64 Tutorial #8h: toolbar
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include gdi32.inc
includelib gdi32.lib
include comctl32.inc
includelib comctl32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
ID_1 equ 0
ID_2 equ 1
ID_3 equ 2
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+70h,0
xor ebx,ebx
add rsp,sizeof WNDCLASSEX+20h
push 10029h ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov rdi,rax
mov qword ptr [rsp+28h],LR_LOADFROMFILE
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
mov edx,offset aMybp1
mov ecx,IMAGE_BASE
call LoadImage
mov edx,sizeof TBBUTTON
mov bl,2
lea rcx,[tbb+edx*2]
@@: mov [rcx+TBBUTTON.iBitmap],ebx
mov [rcx+TBBUTTON.idCommand],ebx;ID_1 ID_2 ID_3
mov [rcx+TBBUTTON.fsState],TBSTATE_ENABLED
or ebx,ebx
jz @f
sub ecx,edx
dec ebx
jmp @b
@@: mov [rsp+60h],rdx;size of structure TBBUTTON
mov edx,18
mov [rsp+58h],rdx;width an higth
mov [rsp+50h],rdx;изображения на каждой кнопке
mov [rsp+48h],rdx;width an higth
mov [rsp+40h],rdx;каждой кнопки
mov qword ptr [rsp+38h],3;число кнопок
mov [rsp+30h],rcx;адрес массива структуры типа TBBUTTON
mov [rsp+28h],rax;идентификатор ресурса с изображением кнопок
mov [rsp+20h],rbx;0
mov r9d,3 ;число изображений кнопок в файле bmp
or r8,-1;идентификатор всей инструментальной панели, который в программе не используется и может быть равен -1
mov edx,WS_CHILD+WS_BORDER+WS_VISIBLE;+TBSTYLE_TOOLTIPS;стиль инструментальной панели
mov ecx,edi;дескриптор главного окна
call CreateToolbarEx
mov ecx,0FF0000h;blue=0FF0000h
call CreateSolidBrush
mov BlueBrush,eax;hBlueBrush
mov ecx,0FF00h;green=0FF00h
call CreateSolidBrush
mov GreenBrush,eax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hWnd equ [rbp+10h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
ps equ [rbp-sizeof PAINTSTRUCT]
enter sizeof PAINTSTRUCT+20h,0
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmPAINT: lea edx,ps
call BeginPaint
mov ecx,sw
jecxz @f
mov r8d,[BlueBrush+ecx*4-4]
mov rcx,rax
lea rdx,ps.PAINTSTRUCT.rcPaint
mov eax,ps.PAINTSTRUCT.rcPaint.right
xchg eax,ps.PAINTSTRUCT.rcPaint.top
mov ps.PAINTSTRUCT.rcPaint.right,eax
call FillRect
@@: lea edx,ps
mov rcx,hWnd
call EndPaint
jmp wmBYE
wmCOMMAND: mov eax,wParam;depending on the value of wParam
;or close the window (wParam=2), or change the color of window (wParam=0 or =1)
jmp [handler+eax*8]
;if wParam=0 or wParam=1 send message WM_PAINT
@0: inc eax
mov [sw],eax
wmSIZE: xor edx,edx
mov r8d,1
mov rcx,hWnd
call InvalidateRect
wmBYE: leave
retn
handler dq @0,@0,wmDESTROY
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8h: toolbar',0
BlueBrush dd ?
GreenBrush dd ?
sw dd 0
tbb TBBUTTON 3 dup(<0>)
aMybp1 db "Images\btns.bmp",0
end
-
Win64 Tutorial #8h: toolbar and tooltips
include win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
ID_1 equ 0
ID_2 equ 1
ID_3 equ 2
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+70h,0
xor ebx,ebx
push 10029h ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW+1;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
add rsp,sizeof WNDCLASSEX+20h
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov rdi,rax
mov qword ptr [rsp+28h],LR_LOADFROMFILE
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
mov edx,offset aMybp1
mov ecx,IMAGE_BASE
call LoadImage
mov edx,sizeof TBBUTTON
mov bl,2
lea rcx,[tbb+edx*2]
@@: mov [rcx+TBBUTTON.iBitmap],ebx;порядковый номер кнопки (кнопки нумеруются от 0)
mov [rcx+TBBUTTON.idCommand],ebx;ID_1 ID_2 ID_3 идентификатор кнопки
mov [rcx+TBBUTTON.fsState],TBSTATE_ENABLED;состояние кнопки.
;Значение TBSTATE_ENABLED разрешает управление с пмощью данной кнопки
or ebx,ebx;заполняем массив с ebx как индекс в массиве от 2 до 0
jz @f
sub ecx,edx;переходим к следующей структуре TBBUTTON
dec ebx
jmp @b
@@: mov [rsp+60h],rdx;size TBBUTTON ;size of structure TBBUTTON
mov edx,18
mov [rsp+58h],rdx;width an higth
mov [rsp+50h],rdx;изображения на каждой кнопке
mov [rsp+48h],rdx;width an higth
mov [rsp+40h],rdx;каждой кнопки
mov qword ptr [rsp+38h],3;число кнопок
mov [rsp+30h],rcx;адрес массива структуры типа TBBUTTON
mov [rsp+28h],rax;идентификатор ресурса с изображением кнопок
mov [rsp+20h],rbx;0
mov r9d,3 ;число изображений кнопок в файле bmp
or r8,-1;идентификатор всей инструментальной панели, который в программе не используется и может быть равен -1
mov edx,WS_CHILD or WS_BORDER or WS_VISIBLE or TBSTYLE_TOOLTIPS;стиль инструментальной панели
mov ecx,edi;дескриптор главного окна
call CreateToolbarEx
mov ecx,0FF0000h;blue=FF0000h
call CreateSolidBrush
mov BlueBrush,eax;hBlueBrush
mov ecx,000FF00h;green=00FF00h
call CreateSolidBrush
mov GreenBrush,eax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hWnd equ [rbp+10h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
ps equ [rbp-sizeof PAINTSTRUCT]
lpttt equ ps-8
enter sizeof PAINTSTRUCT+20h+8,0
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_NOTIFY
je wmNOTIFY
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmPAINT: lea edx,ps
call BeginPaint
mov ecx,sw
;or ecx,ecx
jecxz @f;в sw при старте программы ноль, если sw=0
;тогда не нужно изменять цвет окна
;заполняем окно выбранной кистью из массива кистей
mov r8d,[BlueBrush+ecx*4-4]
mov rcx,rax
lea edx,ps.PAINTSTRUCT.rcPaint
mov eax,ps.PAINTSTRUCT.rcPaint.right
xchg eax,ps.PAINTSTRUCT.rcPaint.top
mov ps.PAINTSTRUCT.rcPaint.right,eax
call FillRect
@@: lea edx,ps
mov rcx,hWnd
call EndPaint
jmp wmBYE
wmNOTIFY: ;r9=[lParam] ;if( LPNMHDR(lParam)->code ==TTN_NEEDTEXT)
cmp dword ptr [r9+NMHDR._code],TTN_NEEDTEXT
jnz wmBYE
mov lpttt,r9 ;LPTOOLTIPTEXT lpttt = (LPTOOLTIPTEXT) lParam;
mov eax,dword ptr [r9+NMHDR.idFrom];switch (lpttt->hdr.idFrom) {
cmp eax,ID_3 ;case ID_1:strcpy(lpttt->szText,"Fill blue");break;
ja wmBYE ;case ID_2:strcpy(lpttt->szText,"Fill green");break;
;case ID_3:strcpy(lpttt->szText,"Exit");
lea ecx,[r9+TOOLTIPTEXT.szText]
mov rdx,[pt+eax*8]
call lstrcpy
jmp wmBYE
wmCOMMAND: mov eax,wParam;depending on the value of wParam
;or close the window (wParam=2), or change the color of window (wParam=0 or =1)
jmp [handler+eax*8]
;if wParam=0 or wParam=1 send message WM_PAINT
@0: inc eax
mov [sw],eax
wmSIZE: mov r8d,TRUE
xor edx,edx
mov rcx,hWnd
call InvalidateRect
wmBYE: leave
retn
handler dq @0,@0,wmDESTROY
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #8i: toolbar and tooltips',0
tbb TBBUTTON 3 dup(<0>)
szText1 db 'Fill blue',0
szText2 db 'Fill green',0
szText3 db 'Exit',0
pt dq szText1,szText2,szText3
aMybp1 db "Images\btns.bmp",0
sw dd 0
BlueBrush dd ?
GreenBrush dd ?
end
-
Great job, Mikl :t
No user-friendly local variables yet?
mov qword ptr [rsp+28h],LR_LOADFROMFILE
mov [rsp+20h],rbx
-
Hi, jj2007!
mov qword ptr [rsp+28h],LR_LOADFROMFILE
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
mov edx,offset aMybp1
mov ecx,IMAGE_BASE
call LoadImage <--
This is not a local variables, this is parameters of procedure LoadImage
see the article of Matt Pietrek Everything You Need To Know To Start Programming 64-Bit Windows Systems (https://msdn.microsoft.com/en-us/magazine/cc300794.aspx)
-
Hi Mikl__,
This is not a local variables, this is parameters of procedure LoadImage
see the article of Matt Pietrek Everything You Need To Know To Start Programming 64-Bit Windows Systems (https://msdn.microsoft.com/en-us/magazine/cc300794.aspx)
great article, by the way. No wonder, it's Matt Pietrek.
Gunther
-
To be truly 64-bit you shouldn't hard code the base address else things like ASLR won't work.
Also, using 'lea reg,var' instead of 'mov reg,offset var' will use rip-relative addressing (at least in ml64).
sub ecx,ecx
call GetModuleHandle
mov hinst,rax
...
lea rdx,aMybp1 ;mov edx,offset aMybp1
mov rcx,hinst ;mov ecx,IMAGE_BASE
call LoadImage
-
mov qword ptr [rsp+28h],LR_LOADFROMFILE
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
mov edx,offset aMybp1
mov ecx,IMAGE_BASE
call LoadImage <--
This is not a local variables, this is parameters of procedure LoadImage
Oops, sorry 8)
Reminds me of the early days of x86 assembly, see \Masm32\examples\exampl07\slickhuh\slickhuh.asm :bgrin:
-
Hi, sinsi!
I write in bat-file ...
/LARGEADDRESSAWARE:NO
...
/BASE:0x400000
so the lines sub ecx,ecx
call GetModuleHandle
mov hinst,rax
is not needed in my examples, hinst always is 400000h, and mov edx,offset var == lea rdx,var
(http://www.cyberforum.ru/images/smilies/smile3.gif)
-
jj2007,
I never pay attention \Masm32\examples\exampl07\slickhuh\slickhuh.asm but the example is quite interesting, why I had not noticed it before? though in \Masm32\examples\exampl07\slickhuh\readme.txt is It uses the EXTERNDEF form of prototype for API functions but makes no use of the parameter data after it, Windows equates occur in their bare number form to ensure they are unintelligible and the API function addresses are called from a meaningless name equated to their address.
To make the code even less readable in a disassembly the parameters for some of the API call are forwarded on the stack and do not occur in the simple order prior to the function call.
the program work and it is most importantly, and a style of writing programs can be any... Assembly language programming is creativity! (http://www.cyberforum.ru/images/smilies/smile3.gif)
-
Win64 Tutorial #9: Child Window Controls
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
ButtonID equ 1
EditID equ 2
IDM_HELLO equ 0
IDM_CLEAR equ 1
IDM_GETTEXT equ 2
IDM_EXIT equ 3
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter sizeof MSG+sizeof WNDCLASSEX+20h,0
xor ebx,ebx
push 10029h ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
mov eax,offset MenuName
push rax ;lpszMenuName
push COLOR_BTNFACE+1;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 485
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov edi,eax
push rbx
push IMAGE_BASE
push EditID
push rdi
push 25
push 200
push 35
push 50
mov r9d,WS_CHILD or WS_VISIBLE or WS_BORDER or ES_LEFT or ES_AUTOHSCROLL
mov r8,rbx
mov edx,offset EditClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov hwndEdit,rax
mov ecx,eax
call SetFocus
push rbx
push IMAGE_BASE
push ButtonID
push rdi
push 25
push 140
push 70
push 70
mov r9d,WS_CHILD or WS_VISIBLE or BS_DEFPUSHBUTTON
mov r8d,offset ButtonText
mov edx,offset ButtonClassName
xor ecx,ecx
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc:
hWnd equ [rbp+10h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
buffer equ [rbp-96]
enter 96+20h,0
mov lParam,r9
mov wParam,r8
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCOMMAND:movzx eax,word ptr wParam
cmp lParam,rbx;0
jnz @f
mov rsi,hwndEdit
jmp [menu_handlers+eax*8]
@@: dec eax ;cmp ax,ButtonID where ButtonID=1
jne wmBYE
mov r9,rbx
mov r8d,IDM_GETTEXT
mov edx,WM_COMMAND
jmp @f
HELLO: mov edx,offset TestString
mov ecx,esi ;hwndEdit
call SetWindowText
mov r9,rbx
mov r8d,VK_END
mov edx,WM_KEYDOWN
mov ecx,esi ;hwndEdit
@@: call SendMessage
jmp wmBYE
CLEAR: xor edx,edx
mov ecx,esi ;hwndEdit
call SetWindowText
jmp wmBYE
GETTEXT: lea edx,buffer
mov r8d,92
mov ecx,esi
call GetWindowText
mov r9,rbx
mov r8d,offset MenuName
lea edx,buffer
xor ecx,ecx
call MessageBox
wmBYE: leave
retn
;---------------------------------------
ClassName db 'Win64 Iczelion lesson #9: Create a button and editing window',0
MenuName db "FirstMenu",0
ButtonClassName db "button",0
ButtonText db "Get Text",0
EditClassName db "edit",0
TestString db "Wow! I'm in an edit box now",0
hwndEdit dq ?
menu_handlers dq HELLO, CLEAR, GETTEXT, wmDESTROY
end
-
Hi, sinsi!
I write in bat-file ...
/LARGEADDRESSAWARE:NO
...
/BASE:0x400000
so the lines sub ecx,ecx
call GetModuleHandle
mov hinst,rax
is not needed in my examples, hinst always is 400000h, and mov edx,offset var == lea rdx,var
(http://www.cyberforum.ru/images/smilies/smile3.gif)
Fair enough, but later versions of link.exe assume '/largeaddressaware:yes' and 'fixed:no', so if someone uses your code without your batch file it will cause problems.
Using 'mov' instead of 'lea' is an extra 3 bytes too. The only catch is that rip-relative is restricted to rip+/-2GB (signed 32-bit displacement).
.text:0000000140001013 48 8D 15 E6 2F 00 00 lea rdx, qword_140004000
.text:000000014000101A 48 BA 00 40 00 40 01 00 00 00 mov rdx, offset qword_140004000
-
if someone uses your code without your batch file it will cause problems.
sinsi,
programmer must be careful, observant and watchful, and a programmer in assembly in the first place (http://www.cyberforum.ru/images/smilies/good3.gif)
-
...a programmer in assembly in the first place
But these are tutorials, to teach someone who probably doesn't know ASM.
If you need to use your batch file it should be in every download then. Call it makeit.bat and it can be run from qeditor.
-
the program work and it is most importantly, and a style of writing programs can be any... Assembly language programming is creativity!
Sure. I've used such techniques, too, for fun and to obfuscate code. And I understand why some people don't like the HLL elements, like .if .else, .repeat ... .until, local variables and so on.
On the other hand, I'd love to establish a database showing the correlation between "HLL hate" and "lines of useful code produced". To give you an idea: currently I have 3,500+ assembler sources in the Masm32 folder and its sub-folders.
-
But these are tutorials, to teach someone who probably doesn't know ASM.
If you need to use your batch file it should be in every download then. Call it makeit.bat and it can be run from qeditor.
Good advice. The same is true for every make script or a shell script under Unix.
Gunther
-
sinsi,
there is bat-file in attachments, and about Call it makeit.bat and it can be run from qeditor.
it's good idea, I'll try to do it
.text:0000000140001013 48 8D 15 E6 2F 00 00 lea rdx, qword_140004000
.text:000000014000101A 48 BA 00 40 00 40 01 00 00 00 mov rdx, offset qword_140004000
.text:00000000004001E8 BA F9 02 40 00 mov edx,offset qword_0004002F9
.text:00000000004001ED 48 8D 15 05 01 00 00 lea rdx, qword_0004002F9
-
Win64 Tutorial #10a: DialogBoxParam+DlgProc
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
IDM_SAYHELLO equ 0
IDM_GETTEXT equ 1
IDM_CLEAR equ 2
IDM_EXIT equ 3
IDC_EDIT equ 0
IDC_BUTTON equ 1
IDC_EXIT equ 2
IDC_MENU equ 100
IDC_DIALOG equ 200
.code
WinMain proc
enter 30h,0
xor ebx,ebx
mov ecx,IMAGE_BASE
mov edx,IDC_DIALOG
mov r8,rbx
mov r9d,offset dialog_procedure
mov qword ptr [esp+20h],IDC_MENU
call DialogBoxParam
xor ecx,ecx
call ExitProcess
WinMain endp
dialog_procedure:
size_of_buffer equ 96
buffer equ [rbp-size_of_buffer]
enter 20h+size_of_buffer,0
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_COMMAND
jne wmBYE
wmCOMMAND:movzx eax,r8w ;movzx eax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz @f
jmp [menu_handlers+eax*8]
@@: dec eax ;cmp eax,IDC_BUTTON=1
jne @f
SAYHELLO:mov r8d,offset expTxt
jmp @0
@@: dec eax ;cmp eax,IDC_EXIT=2
jne wmBYE
mov edx,WM_CLOSE
mov r8,rbx
mov r9,rbx
call SendMessage
jmp wmBYE
wmINITDIALOG:xor edx,edx
call GetDlgItem
mov ecx,eax
call SetFocus
jmp wmBYE
CLEAR: mov r8,rbx
@0: xor edx,edx
call SetDlgItemText
jmp wmBYE
GETTEXT:xor edx,edx
lea r8d,buffer
mov r9d,size_of_buffer
call GetDlgItemText
xor ecx,ecx
mov r9,rcx
mov r8d,offset AppName
lea edx,buffer
call MessageBox
jmp wmBYE
wmCLOSE:xor edx,edx
call EndDialog
wmBYE: xor eax,eax
leave
retn
;---------------------------------------
menu_handlers dq SAYHELLO,GETTEXT,CLEAR,wmCLOSE
expTxt db "Wow! I'm in an edit box now",0
AppName db 'Our First Dialog Box',0
end
rc-file#include "resource.h"
#define IDM_SAYHELLO 0
#define IDM_GETTEXT 1
#define IDM_CLEAR 2
#define IDM_EXIT 3
#define IDC_EDIT 0
#define IDC_BUTTON 1
#define IDC_EXIT 2
#define IDC_MENU 100
#define IDC_DIALOG 200
IDC_DIALOG DIALOG 10, 10, 205, 60
STYLE 0x0004 | DS_CENTER | WS_CAPTION | WS_MINIMIZEBOX |
WS_SYSMENU | WS_VISIBLE | WS_OVERLAPPED | DS_MODALFRAME | DS_3DLOOK
CAPTION "Tutorial 10a: DialogBoxParam+DlgProc"
MENU IDC_MENU
BEGIN
EDITTEXT IDC_EDIT, 15,17,111,13, ES_AUTOHSCROLL | ES_LEFT
DEFPUSHBUTTON "Say Hello", IDC_BUTTON, 141,10,52,13
PUSHBUTTON "E&xit", IDC_EXIT, 141,26,52,13
END
IDC_MENU MENU
BEGIN
POPUP "Test Controls"
BEGIN
MENUITEM "Say Hello",IDM_SAYHELLO
MENUITEM "Get Text",IDM_GETTEXT
MENUITEM "Clear Edit Box",IDM_CLEAR
MENUITEM "", , 0x0800 /*MFT_SEPARATOR*/
MENUITEM "E&xit",IDM_EXIT
END
END
-
Win64 Tutorial #10b: CreateDialogParam+DlgProc
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
IDM_SAYHELLO equ 0
IDM_GETTEXT equ 1
IDM_CLEAR equ 2
IDM_EXIT equ 3
IDC_EDIT equ 0
IDC_BUTTON equ 1
IDC_EXIT equ 2
IDC_MENU equ 100
IDC_DIALOG equ 200
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter 30h+sizeof MSG,0
xor ebx,ebx
mov ecx,IMAGE_BASE
mov edx,IDC_DIALOG
mov r8,rbx
mov r9d,offset dialog_procedure
mov [esp+20h],rbx;IDC_MENU
call CreateDialogParam
mov hWnd,rax
lea edi,msg
message_loop: mov r9,rbx
mov r8,rbx
xor edx,edx
mov ecx,edi
call GetMessage
or eax,eax
jz exit_msg_loop
mov edx,edi
mov rcx,hWnd
call IsDialogMessage
or eax,eax
jnz message_loop
mov ecx,edi
call DispatchMessage
jmp message_loop
exit_msg_loop:xor ecx,ecx
call ExitProcess
WinMain endp
dialog_procedure:
hDlg equ [rbp+10h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
size_of_buffer equ 96
buffer equ [rbp-size_of_buffer]
enter 20h+size_of_buffer,0
mov hDlg,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_COMMAND
jne wmBYE
wmCOMMAND:movzx eax,r8w ;movzx eax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz @f
jmp [menu_handlers+eax*8]; choose menu
; choose button or EditBox
@@: dec eax ;cmp eax,IDC_BUTTON=1
jne @f
SAYHELLO:mov r8d,offset expTxt
jmp @0
@@: dec eax ;cmp eax,IDC_EXIT=2
jne wmBYE
mov edx,WM_CLOSE
mov r8,rbx
mov r9,rbx
call SendMessage
jmp wmBYE
CLEAR: mov r8,rbx
@0: xor edx,edx
call SetDlgItemText
jmp wmBYE
GETTEXT:xor edx,edx
lea r8d,buffer
mov r9d,size_of_buffer
call GetDlgItemText
xor ecx,ecx
mov r9,rcx
mov r8d,offset AppName
lea edx,buffer
call MessageBox
jmp wmBYE
wmCLOSE:mov rcx,hDlg
call DestroyWindow
xor ecx,ecx
call PostQuitMessage
wmBYE: xor eax,eax
leave
retn
;---------------------------------------
menu_handlers dq SAYHELLO,GETTEXT,CLEAR,wmCLOSE
expTxt db "Wow! I'm in an edit box now",0
AppName db 'Our Second Dialog Box',0
hWnd dq ?
end
rc-file#include "resource.h"
#define IDM_SAYHELLO 0
#define IDM_GETTEXT 1
#define IDM_CLEAR 2
#define IDM_EXIT 3
#define IDC_EDIT 0
#define IDC_BUTTON 1
#define IDC_EXIT 2
#define IDC_MENU 100
#define IDC_DIALOG 200
IDC_DIALOG DIALOG 10, 10, 205, 60
STYLE 0x0004 | DS_CENTER | WS_CAPTION | WS_MINIMIZEBOX |
WS_SYSMENU | WS_VISIBLE | WS_OVERLAPPED | DS_MODALFRAME | DS_3DLOOK
CAPTION "Tutorial 10b: CreateDialogParam+DlgProc"
MENU IDC_MENU
BEGIN
EDITTEXT IDC_EDIT, 15,17,111,13, ES_AUTOHSCROLL | ES_LEFT
DEFPUSHBUTTON "Say Hello", IDC_BUTTON, 141,10,52,13
PUSHBUTTON "E&xit", IDC_EXIT, 141,26,52,13
END
IDC_MENU MENU
BEGIN
POPUP "Test Controls"
BEGIN
MENUITEM "Say Hello",IDM_SAYHELLO
MENUITEM "Get Text",IDM_GETTEXT
MENUITEM "Clear Edit Box",IDM_CLEAR
MENUITEM "", , 0x0800 /*MFT_SEPARATOR*/
MENUITEM "E&xit",IDM_EXIT
END
END
-
Win64 Tutorial #10c: CreateDialogParam+WndProc+Class
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
IDM_SAYHELLO equ 0
IDM_GETTEXT equ 1
IDM_CLEAR equ 2
IDM_EXIT equ 3
IDC_EDIT equ 0
IDC_BUTTON equ 1
IDC_EXIT equ 2
IDC_MENU equ 100
IDC_DIALOG equ 200
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter 30h+sizeof MSG+sizeof WNDCLASSEX,0
xor ebx,ebx
push 10029h ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push IDC_MENU ;lpszMenuName
push COLOR_BTNFACE+1;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push DLGWINDOWEXTRA;cbClsExtra & cbWndExtra
mov eax,offset dialog_procedure
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
mov ecx,IMAGE_BASE
mov edx,IDC_DIALOG
mov r8,rbx
mov r9d,offset dialog_procedure
mov [esp+20h],rbx;IDC_MENU
call CreateDialogParam
mov hWnd,rax
lea edi,msg
message_loop: mov r9,rbx
mov r8,rbx
xor edx,edx
mov ecx,edi
call GetMessage
or eax,eax
jz exit_msg_loop
mov edx,edi
mov rcx,hWnd
call IsDialogMessage
or eax,eax
jnz message_loop
mov ecx,edi
call DispatchMessage
jmp message_loop
exit_msg_loop:xor ecx,ecx
call ExitProcess
WinMain endp
dialog_procedure:
hDlg equ [rbp+10h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
size_of_buffer equ 96
buffer equ [rbp-size_of_buffer]
enter 20h+size_of_buffer,0
mov hDlg,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_COMMAND
jne wmBYE
wmCOMMAND:movzx eax,r8w ;movzx eax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz @f
jmp [menu_handlers+eax*8]; choose menu
; choose button or EditBox
@@: dec eax ;cmp eax,IDC_BUTTON=1
jne @f
SAYHELLO:mov r8d,offset expTxt
jmp @0
@@: dec eax ;cmp eax,IDC_EXIT=2
jne wmBYE
mov edx,WM_CLOSE
mov r8,rbx
mov r9,rbx
call SendMessage
jmp wmBYE
CLEAR: mov r8,rbx
@0: xor edx,edx
call SetDlgItemText
jmp wmBYE
GETTEXT:xor edx,edx
lea r8d,buffer
mov r9d,size_of_buffer
call GetDlgItemText
xor ecx,ecx
mov r9,rcx
mov r8d,offset AppName
lea edx,buffer
call MessageBox
jmp wmBYE
wmCLOSE:mov rcx,hDlg
call DestroyWindow
xor ecx,ecx
call PostQuitMessage
wmBYE: xor eax,eax
leave
retn
;---------------------------------------
ClassName db 'DLGCLASS',0
menu_handlers dq SAYHELLO,GETTEXT,CLEAR,wmCLOSE
expTxt db "Wow! I'm in an edit box now",0
AppName db 'Our Third Dialog Box',0
hWnd dq ?
end
rc-file#include "resource.h"
#define IDM_SAYHELLO 0
#define IDM_GETTEXT 1
#define IDM_CLEAR 2
#define IDM_EXIT 3
#define IDC_EDIT 0
#define IDC_BUTTON 1
#define IDC_EXIT 2
#define IDC_MENU 100
#define IDC_DIALOG 200
IDC_DIALOG DIALOG 10, 10, 205, 60
STYLE 0x0004 | DS_CENTER | WS_CAPTION | WS_MINIMIZEBOX |
WS_SYSMENU | WS_VISIBLE | WS_OVERLAPPED | DS_MODALFRAME | DS_3DLOOK
CAPTION "Tutorial 10c: CreateDialogParam+WndProc+Class"
MENU IDC_MENU
BEGIN
EDITTEXT IDC_EDIT, 15,17,111,13, ES_AUTOHSCROLL | ES_LEFT
DEFPUSHBUTTON "Say Hello", IDC_BUTTON, 141,10,52,13
PUSHBUTTON "E&xit", IDC_EXIT, 141,26,52,13
END
IDC_MENU MENU
BEGIN
POPUP "Test Controls"
BEGIN
MENUITEM "Say Hello",IDM_SAYHELLO
MENUITEM "Get Text",IDM_GETTEXT
MENUITEM "Clear Edit Box",IDM_CLEAR
MENUITEM "", , 0x0800 /*MFT_SEPARATOR*/
MENUITEM "E&xit",IDM_EXIT
END
END
-
Win64 Tutorial #10: Dialogs
| DlgProc | DlgProc+WndProc | WndProc+Class |
DialogBoxParam | +10a | +10b | 10c |
CreateDialogParam | +10d | 10e | +10f |
tut10a.asmOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
IDM_SAYHELLO equ 0
IDM_GETTEXT equ 1
IDM_CLEAR equ 2
IDM_EXIT equ 3
IDC_EDIT equ 0
IDC_BUTTON equ 1
IDC_EXIT equ 2
IDC_MENU equ 100
IDC_DIALOG equ 200
.code
WinMain proc
enter 30h,0
xor ebx,ebx
mov qword ptr [rsp+20h],IDC_MENU
mov r9d,offset DlgProc
mov r8,rbx
mov edx,IDC_DIALOG
mov ecx,IMAGE_BASE
call DialogBoxParam
xor ecx,ecx
call ExitProcess
WinMain endp
DlgProc proc
hWnd equ [rbp+10h]
uMsg equ [rbp+18h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
size_of_buffer equ 96
buffer equ [rbp-size_of_buffer]
enter 40h+size_of_buffer,0
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_NCHITTEST
je wmNCHITTEST
cmp edx,WM_COMMAND
je wmCOMMAND
@1: mov rax,FALSE
jmp wmBYE
wmCLOSE:;mov rcx,hWnd
xor edx,edx
call EndDialog
jmp @2
wmINITDIALOG:xor edx,edx
call GetDlgItem
mov ecx,eax
call SetFocus
mov qword ptr [rsp+30h],SWP_NOZORDER OR SWP_NOMOVE OR SWP_NOSIZE OR SWP_FRAMECHANGED OR SWP_NOACTIVATE
mov [rsp+28h],rbx
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
xor edx,edx
mov rcx,hWnd
call SetWindowPos
jmp @1
wmNCHITTEST:call DefWindowProc ; (not DefDlgProc, of course)
cmp rax,HTCLIENT
jnz @f
mov rax,HTCAPTION
@@: mov r8,rax
mov edx,DWL_MSGRESULT
mov rcx,hWnd
call SetWindowLong
jmp @2
wmCOMMAND:movzx eax,r8w ;movzx eax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz @f
jmp [menu_handlers+eax*8]
@@: dec eax ;cmp eax,IDC_BUTTON=1
jne @f
SAYHELLO:mov r8d,offset expTxt
jmp @0
@@: dec eax ;cmp eax,IDC_EXIT=2
jne @2
mov edx,WM_CLOSE
mov r8,rbx
mov r9,rbx
call SendMessage
jmp @2
CLEAR: mov r8,rbx
@0: xor edx,edx
call SetDlgItemText
jmp @2
GETTEXT:xor edx,edx
lea r8d,buffer
mov r9d,size_of_buffer
call GetDlgItemText
xor ecx,ecx
mov r9,rcx
mov r8d,offset AppName
lea edx,buffer
call MessageBox
@2: mov eax,TRUE
wmBYE: leave
retn
menu_handlers dq SAYHELLO,GETTEXT,CLEAR,wmCLOSE
DlgProc endp
;---------------------------------------
expTxt db "Wow! I'm in an edit box now",0
AppName db 'Our First Dialog Box',0
end
tut10a.rc#include "resource.h"
#define IDM_SAYHELLO 0
#define IDM_GETTEXT 1
#define IDM_CLEAR 2
#define IDM_EXIT 3
#define IDC_EDIT 0
#define IDC_BUTTON 1
#define IDC_EXIT 2
#define IDC_MENU 100
#define IDC_DIALOG 200
IDC_DIALOG DIALOGEX 10, 10, 205, 60
STYLE WS_POPUP | WS_SYSMENU | WS_VISIBLE | WS_THICKFRAME | WS_MINIMIZEBOX | WS_MAXIMIZEBOX
EXSTYLE WS_EX_TOPMOST | WS_EX_CLIENTEDGE
CAPTION "Tutorial 10a: DialogBoxParam+DlgProc"
; CLASS "DlgClass"
MENU IDC_MENU
BEGIN
EDITTEXT IDC_EDIT, 15,17,111,13, ES_AUTOHSCROLL | ES_LEFT
DEFPUSHBUTTON "Say Hello", IDC_BUTTON, 141,10,52,13
PUSHBUTTON "E&xit", IDC_EXIT, 141,26,52,13
END
IDC_MENU MENU
BEGIN
POPUP "Test Controls"
BEGIN
MENUITEM "Say Hello",IDM_SAYHELLO
MENUITEM "Get Text",IDM_GETTEXT
MENUITEM "Clear Edit Box",IDM_CLEAR
MENUITEM "", , 0x0800 /*MFT_SEPARATOR*/
MENUITEM "E&xit",IDM_EXIT
END
END
tut10bOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
IDM_SAYHELLO equ 0
IDM_GETTEXT equ 1
IDM_CLEAR equ 2
IDM_EXIT equ 3
IDC_EDIT equ 0
IDC_BUTTON equ 1
IDC_EXIT equ 2
IDC_MENU equ 100
IDC_DIALOG equ 200
.code
WinMain proc
enter 30h,0
xor ebx,ebx
mov ecx,IMAGE_BASE
mov edx,IDC_DIALOG
mov r8,rbx
mov r9d,offset dialog_procedure
mov qword ptr [esp+20h],IDC_MENU
call DialogBoxParam
xor ecx,ecx
call ExitProcess
WinMain endp
align 8
WndProc:
hWnd equ [rbp+10h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
size_of_buffer equ 96
buffer equ [rbp-size_of_buffer]
enter 20h+size_of_buffer,0
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefDlgProc
wmCOMMAND:movzx eax,r8w ;movzx eax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz @f
jmp [menu_handlers+eax*8]
@@: dec eax ;cmp eax,IDC_BUTTON=1
jne @f
SAYHELLO:mov r8d,offset expTxt
jmp @0
@@: dec eax ;cmp eax,IDC_EXIT=2
jne wmBYE
mov edx,WM_CLOSE
mov r8,rbx
mov r9,rbx
call SendMessage
jmp wmBYE
CLEAR: mov r8,rbx
@0: xor edx,edx
call SetDlgItemText
jmp wmBYE
GETTEXT:xor edx,edx
lea r8d,buffer
mov r9d,size_of_buffer
call GetDlgItemText
xor ecx,ecx
mov r9,rcx
mov r8d,offset AppName
lea edx,buffer
call MessageBox
jmp wmBYE
wmCLOSE:xor edx,edx
mov rcx,hWnd
call EndDialog
wmBYE: leave
retn
;----------------------------------------
dialog_procedure:push rbp
mov ebp,esp
sub esp,20h
cmp rdx,WM_INITDIALOG
jne @f
lea r8d,WndProc
mov edx,GWL_WNDPROC
call SetWindowLongPtr
@@: xor eax,eax
leave
retn
;---------------------------------------
menu_handlers dq SAYHELLO,GETTEXT,CLEAR,wmCLOSE
expTxt db "Wow! I'm in an edit box now",0
AppName db 'Our Fifth Dialog Box',0
end
tut10b.rc#include "resource.h"
#define IDM_SAYHELLO 0
#define IDM_GETTEXT 1
#define IDM_CLEAR 2
#define IDM_EXIT 3
#define IDC_EDIT 0
#define IDC_BUTTON 1
#define IDC_EXIT 2
#define IDC_MENU 100
#define IDC_DIALOG 200
IDC_DIALOG DIALOG 10, 10, 250, 60
STYLE 0x0004 | DS_CENTER | WS_CAPTION | WS_MINIMIZEBOX |
WS_SYSMENU | WS_VISIBLE | WS_OVERLAPPED | DS_MODALFRAME | DS_3DLOOK
CAPTION "Tutorial 10b: DialogBoxParam+DlgProc+WndPoc"
MENU IDC_MENU
BEGIN
EDITTEXT IDC_EDIT, 15,17,111,13, ES_AUTOHSCROLL | ES_LEFT
DEFPUSHBUTTON "Say Hello", IDC_BUTTON, 141,10,52,13
PUSHBUTTON "E&xit", IDC_EXIT, 141,26,52,13
END
IDC_MENU MENU
BEGIN
POPUP "Test Controls"
BEGIN
MENUITEM "Say Hello",IDM_SAYHELLO
MENUITEM "Get Text",IDM_GETTEXT
MENUITEM "Clear Edit Box",IDM_CLEAR
MENUITEM "", , 0x0800 /*MFT_SEPARATOR*/
MENUITEM "E&xit",IDM_EXIT
END
END
tut10d.asmOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:rbpFramePrologue
OPTION EPILOGUE:rbpFrameEpilogue
IMAGE_BASE equ 400000h
IDM_SAYHELLO equ 0
IDM_GETTEXT equ 1
IDM_CLEAR equ 2
IDM_EXIT equ 3
IDC_EDIT equ 0
IDC_BUTTON equ 1
IDC_EXIT equ 2
IDC_MENU equ 100
IDC_DIALOG equ 200
.code
WinMain proc
msg equ [rbp-sizeof MSG]
enter 40h+sizeof MSG,0
xor ebx,ebx
mov [rsp+20h],rbx
mov r9d,offset DlgProc
mov r8,rbx
mov edx,IDC_DIALOG
mov ecx,IMAGE_BASE
call CreateDialogParam
mov hWin,rax
lea edi,msg
message_loop:mov r9,rbx
mov r8,rbx
xor edx,edx
mov ecx,edi
call GetMessage
or eax,eax
jz exit_msg_loop
mov edx,edi
mov rcx,hWin
call IsDialogMessage
or eax,eax
jnz message_loop
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp message_loop
exit_msg_loop:xor ecx,ecx
call ExitProcess
WinMain endp
DlgProc proc
hWnd equ [rbp+10h]
uMsg equ [rbp+18h]
wParam equ [rbp+20h]
lParam equ [rbp+28h]
size_of_buffer equ 96
buffer equ [rbp-size_of_buffer]
enter 40h+size_of_buffer,0
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_NCHITTEST
je wmNCHITTEST
cmp edx,WM_COMMAND
je wmCOMMAND
@1: xor eax,eax;mov rax,FALSE
jmp wmBYE
wmCLOSE:call DestroyWindow
xor ecx,ecx
call PostQuitMessage
jmp @2
wmINITDIALOG:mov qword ptr [rsp+30h],SWP_NOZORDER OR SWP_NOMOVE OR SWP_NOSIZE OR SWP_FRAMECHANGED OR SWP_NOACTIVATE
mov [rsp+28h],rbx
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
xor edx,edx
call SetWindowPos
jmp @1
wmNCHITTEST:call DefWindowProc ; (not DefDlgProc, of course)
cmp eax,HTCLIENT
jnz @f
mov eax,HTCAPTION
@@: mov r8,rax
mov edx,DWL_MSGRESULT
mov rcx,hWnd
call SetWindowLong
jmp @2
wmCOMMAND:movzx eax,r8w ;movzx eax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz @f
jmp [menu_handlers+eax*8]
@@: dec eax ;cmp eax,IDC_BUTTON=1
jne @f
SAYHELLO:mov r8d,offset expTxt
jmp @0
@@: dec eax ;cmp eax,IDC_EXIT=2
jne @1
mov edx,WM_CLOSE
mov r8,rbx
mov r9,rbx
call SendMessage
jmp @2
CLEAR: mov r8,rbx
@0: xor edx,edx
call SetDlgItemText
jmp @2
GETTEXT:xor edx,edx
lea r8d,buffer
mov r9d,size_of_buffer
call GetDlgItemText
xor ecx,ecx
mov r9,rcx
mov r8d,offset AppName
lea edx,buffer
call MessageBox
@2: mov eax,TRUE
wmBYE: leave
retn
menu_handlers dq SAYHELLO,GETTEXT,CLEAR,wmCLOSE
DlgProc endp
;---------------------------------------
expTxt db "Wow! I'm in an edit box now",0
AppName db 'Our Fourth Dialog Box',0
hWin dq ?
end
tut10d.rc#include "resource.h"
#define IDM_SAYHELLO 0
#define IDM_GETTEXT 1
#define IDM_CLEAR 2
#define IDM_EXIT 3
#define IDC_EDIT 0
#define IDC_BUTTON 1
#define IDC_EXIT 2
#define IDC_MENU 100
#define IDC_DIALOG 200
IDC_DIALOG DIALOGEX 10, 10, 205, 60
STYLE WS_POPUP | WS_SYSMENU | WS_VISIBLE | WS_THICKFRAME | WS_MINIMIZEBOX | WS_MAXIMIZEBOX
EXSTYLE WS_EX_TOPMOST | WS_EX_CLIENTEDGE
CAPTION "Tutorial 10d: CreateDialogParam+DlgProc"
; CLASS "DlgClass"
MENU IDC_MENU
BEGIN
EDITTEXT IDC_EDIT, 15,17,111,13, ES_AUTOHSCROLL | ES_LEFT
DEFPUSHBUTTON "Say Hello", IDC_BUTTON, 141,10,52,13
PUSHBUTTON "E&xit", IDC_EXIT, 141,26,52,13
END
IDC_MENU MENU
BEGIN
POPUP "Test Controls"
BEGIN
MENUITEM "Say Hello",IDM_SAYHELLO
MENUITEM "Get Text",IDM_GETTEXT
MENUITEM "Clear Edit Box",IDM_CLEAR
MENUITEM "", , 0x0800 /*MFT_SEPARATOR*/
MENUITEM "E&xit",IDM_EXIT
END
END
tut10f.asm OPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
IDM_SAYHELLO equ 0
IDM_GETTEXT equ 1
IDM_CLEAR equ 2
IDM_EXIT equ 3
IDC_EDIT equ 0
IDC_BUTTON equ 1
IDC_EXIT equ 2
IDC_MENU equ 100
IDC_DIALOG equ 200
.code
WinMain proc
msg equ [rbp-sizeof MSG]
push rbp
mov rbp,rsp
sub rsp,sizeof MSG
xor ebx,ebx
push 10029h ;hIconSm
push rbx ;lpszClassName
push IDC_MENU ;lpszMenuName
push COLOR_BTNFACE+1;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push DLGWINDOWEXTRA;cbClsExtra & cbWndExtra
push rbx ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
mov qword ptr [esp+20h],IDC_MENU
mov r9d,offset WndProc
mov r8,rbx
mov edx,IDC_DIALOG
mov ecx,IMAGE_BASE
call DialogBoxParam
xor ecx,ecx
call ExitProcess
WinMain endp
WndProc:
size_of_buffer equ 96
buffer equ [rbp-size_of_buffer]
push rbp
mov rbp,rsp
sub rsp,20h+size_of_buffer
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_COMMAND
jne wmBYE
wmCOMMAND:movzx eax,r8w ;movzx eax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz @f
jmp [menu_handlers+eax*8]
@@: dec eax ;cmp eax,IDC_BUTTON=1
jne @f
SAYHELLO:mov r8d,offset expTxt
jmp @0
@@: dec eax ;cmp eax,IDC_EXIT=2
jne wmBYE
mov edx,WM_CLOSE
mov r8,rbx
mov r9,rbx
call SendMessage
jmp wmBYE
CLEAR: mov r8,rbx
@0: xor edx,edx
call SetDlgItemText
jmp wmBYE
GETTEXT:xor edx,edx
lea r8d,buffer
mov r9d,size_of_buffer
call GetDlgItemText
xor ecx,ecx
mov r9,rcx
mov r8d,offset AppName
lea edx,buffer
call MessageBox
jmp wmBYE
wmCLOSE:xor edx,edx
call EndDialog
wmBYE: xor eax,eax
leave
retn
;---------------------------------------
menu_handlers dq SAYHELLO,GETTEXT,CLEAR,wmCLOSE
expTxt db "Wow! I'm in an edit box now",0
AppName db 'Our Sixth Dialog Box',0
end
tut10f.rc#include "resource.h"
#define IDM_SAYHELLO 0
#define IDM_GETTEXT 1
#define IDM_CLEAR 2
#define IDM_EXIT 3
#define IDC_EDIT 0
#define IDC_BUTTON 1
#define IDC_EXIT 2
#define IDC_MENU 100
#define IDC_DIALOG 200
IDC_DIALOG DIALOGEX 10, 10, 220, 60
STYLE 0x0004 | DS_CENTER | WS_CAPTION | WS_MINIMIZEBOX |
WS_SYSMENU | WS_VISIBLE | WS_OVERLAPPED | DS_MODALFRAME | DS_3DLOOK
CAPTION "Iczelion Tutorial #10f: DialogBoxParam+WndProc+Class"
MENU IDC_MENU
BEGIN
EDITTEXT IDC_EDIT, 15,17,111,13, ES_AUTOHSCROLL | ES_LEFT |WS_TABSTOP
DEFPUSHBUTTON "Say Hello", IDC_BUTTON,141,10,52, 13,WS_TABSTOP
PUSHBUTTON "E&xit", IDC_EXIT, 141,26,52, 13,WS_TABSTOP
END
IDC_MENU MENU
BEGIN
POPUP "Test Controls"
BEGIN
MENUITEM "Get Text", IDM_GETTEXT
MENUITEM "Clear Text", IDM_CLEAR
MENUITEM SEPARATOR
MENUITEM "E&xit", IDM_EXIT
END
END
-
Win64 Tutorial #5a: Painting with Rotation Text
include win64a.inc
include gdi32.inc
includelib gdi32.lib
.code
WinMain proc
local msg:MSG
push rbp
mov rbp,rsp
sub rsp,sizeof MSG+20h
xor ebx,ebx
mov ecx,0FF0000h
call CreateSolidBrush
push 10029h ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push rax;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
mov esi,400000h
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shr esi,7;Special CreateWindow position value CW_USEDEFAULT=8000h
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov r9,rbx
mov r8d,50;создаем таймер #0 на 50mSec
xor edx,edx
mov ecx,eax
call SetTimer
; +---------------------------+
; | entering the message loop |
; +---------------------------+
lea edi,msg
message_loop:mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp message_loop
WinMain endp
WndProc proc hwnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local ps:PAINTSTRUCT
local expRect:RECT
local expSize:POINT
local newFont:qword
local oldFont:qword
push rbp
mov rbp,rsp
sub rsp,sizeof PAINTSTRUCT+sizeof RECT+sizeof POINT+16+20h
mov hwnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_TIMER
je wmTIMER
leave
jmp DefWindowProc
wmDESTROY:xor edx,edx;уничтожаем таймер #0
call KillTimer
xor ecx,ecx
call ExitProcess
wmTIMER:cmp angle,3600; сравниваем угол с 360 градусами
sbb edx,edx;если угол равен 360 делаем угол равным 0
and dword ptr angle,edx
mov r8d,1
xor edx,edx
call InvalidateRect; перерисовываем текст с текущим значением угла
add angle,16 ;увеличиваем угол на 1,6 градуса
jmp wmBYE
wmPAINT:lea edx,ps
call BeginPaint
mov ecx,26
mov edx,12
mov r8,angle
mov r9,r8
mov eax,offset expFont
push rax
push DEFAULT_PITCH or FF_SCRIPT
push rbx;DEFAULT_QUALITY=0
push rbx;CLIP_DEFAULT_PRECIS=0
push rbx;OUT_DEFAULT_PRECIS=0
push OEM_CHARSET
push rbx
push rbx
push rbx
push 400
push rbx
push rbx
push rbx
push rbx
call CreateFont
mov newFont,rax
mov rdx,rax
mov rcx,ps.PAINTSTRUCT.hdc
call SelectObject
mov oldFont,rax
lea edx,expRect
mov rcx,hwnd
call GetClientRect
;---------вывожу текст
mov edx,32C8C8h;RGB=50,200,200 золотистые буквы
mov rcx,ps.PAINTSTRUCT.hdc
call SetTextColor
mov edx,0FF0000h;RGB=0,0,255 на синем фоне
mov rcx,ps.PAINTSTRUCT.hdc
call SetBkColor
lea r9,expSize
mov r8d,sizeof expTxt-1
lea edx,expTxt
mov rcx,ps.PAINTSTRUCT.hdc
call GetTextExtentPoint32
mov qword ptr [rsp+20h],sizeof expTxt
mov r9d,offset expTxt
;---------расчитываю положение начала текста
finit
fld temp3;грузим в FPU коэффициент pi/1800
mov rax,angle
add rax,1800;получили истинный угол
mov temp2,eax
fimul temp2;перевели градусы в радианы
fsincos;в st(0) синус угла, в st(1) косинус
mov eax,expSize.y
mul eax ;получили квадрат высоты текста
mov temp2,eax
mov eax,expSize.x
mul eax ;получили квадрат ширины текста
add temp2,eax;сумма квадратов катетов
shr temp2,2
fild temp2;квадрат гипотенузы=SQR(SIZE.cy)/4 + SQR(SIZE.cx)/4
fsqrt
fistp temp2;получили гипотенузу
fimul temp2;гипотенуза * sin = x
fistp temp1
fimul temp2;гипотенуза * cos = y
fchs;меняем знак y
fistp temp2;-y
mov eax,expRect.bottom
shr eax,1;y-координата середины экрана
add temp2,eax;y-координата начала текста
mov r8d,temp2
mov ecx,expRect.right
shr ecx,1;x-координата середины экрана
add temp1,ecx;x-координата начала текста
mov edx,temp1
mov rcx,ps.hdc
call TextOut
mov rcx,newFont
call DeleteObject;возвращаем системе старый шрифт
mov rdx,oldFont
mov rcx,ps.PAINTSTRUCT.hdc
call SelectObject
lea edx,ps
mov rcx,hwnd
call EndPaint
wmBYE: leave
retn
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #5a: Painting with Rotation Text',0
expTxt db 'Win64 assembly with MASM is great and easy',0
expFont db 'script',0
angle dq 0
temp1 dd ?
temp2 dd ?
temp3 dq 0.00174532925199432957692369;=pi/1800
end
(http://masm32.com/board/index.php?action=dlattach;topic=4190.0;attach=4296;image)
tut05a.zip (http://masm32.com/board/index.php?action=dlattach;topic=4190.0;attach=4081)
-
Hi Mikl__,
thank you for your care. What do you think about this: Should we make a Web site with your examples with the option of download etc?
Gunther
-
Thank you, Gunther!
I wouldn't mind, perhaps you can correct my comments, I don't know English enough
-
Hi Mikl__,
Thank you, Gunther!
I wouldn't mind, perhaps you can correct my comments, I don't know English enough
the comments shouldn't be a large problem. We can do it step by step.
Gunther
-
Well, Gunther,
what should be the first step?
-
Win64 Tutorial #7a: Creating a cursor and icons from file
include win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov ecx,offset FileName
call LoadCursorFromFile
push rax ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push rax ;hCursor
push rax ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc
cmp edx,WM_DESTROY
je wmDESTROY
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #7a: Creating a cursor and icons from file',0
FileName db "Images\cursor.cur",0
end
Win64 Tutorial #7b: Creating a cursor and icons from resources
asm-fileinclude win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
ID_CURSOR = 18
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edx,ID_CURSOR
mov ecx,IMAGE_BASE
call LoadCursor
push rax ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push rax ;hCursor
push rax ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc
cmp edx,WM_DESTROY
je wmDESTROY
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #7b: Creating a cursor and icons from resources',0
end
rc-file#define ID_CURSOR 18
ID_CURSOR CURSOR "Images\\cursor.cur"
Win64 Tutorial #7c: Icon binary datas
include win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
ICON_SIZE = 744 ;taille de Icon.ico (header=22 Image=744) total=766
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov ecx,offset FileName
call LoadCursorFromFile
push rax ;hIconSm
lea edi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push rax ;hCursor
push rax ;hIcon
mov esi,IMAGE_BASE
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov r9d,030000h
or r8,-1
mov edx,ICON_SIZE
mov ecx,offset ptIcon
call CreateIconFromResource
mov hIcon,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND
local ps:PAINTSTRUCT
push rbp
mov ebp,esp
sub esp,sizeof PAINTSTRUCT+20h
mov hWnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmPAINT:lea edx,ps
call BeginPaint
mov r9,hIcon
mov r8d,68
mov edx,134
mov ecx,eax
call DrawIcon
lea edx,ps
mov rcx,hWnd
call EndPaint
wmBYE: leave
retn
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #7-3:Icone datas binaire',0
FileName db 'Images\cursor.cur',0
hIcon dq ?
ptIcon:;sauter le header du fichier d'icone
; пропуск первых 22 байт
db 40,0,0,0,32,0,0,0,64,0,0,0,1,0,4,31 dup(0)
db 128,0,0,128,0,0,0,128,128,0,128,0
db 0,0,128,0,128,0,128,128,0,0,192,192,192,0,128,128
db 128,0,0,0,255,0,0,255,0,0,0,255,255,0,255,0
db 0,0,255,0,255,0,255,255,0,0,255,255,255,0,0,10
db 5 dup(170),160,10 dup(0),3 dup(170),160,12 dup(0)
db 10,170,0,10,4 dup(170),0,128,8 dup(0)
db 10,6 dup(170),168,6 dup(0)
db 8,10,170,160,0,0,0,10,170,170,7 dup(0)
db 170,170,1,16,5 dup(170),168,5 dup(0)
db 10,170,160,17,10,4 dup(170),0,0,0,128,0,0,0
db 74,170,160,16,8 dup(170),160,0,8,0
db 0,170,160,10,9 dup(170),0,128,10
db 3 dup(170),10,170,160,8,6 dup(170),168,0,170
db 170,170,160,0,170,138,160,136,160,4 dup(170),160,10,170
db 170,74,170,170,168,170,15,0,0,10,170,170,170,168,10,170
db 164,10,170,170,10,160,255,0,15,0,10,170,170,0,10,170
db 64,10,160,168,10,160,255,240,15,0,0,0,0,0,10,160
db 0,170,160,8,10,160,4 dup(255),10,0,0,0,0,170
db 170,170,0,128,10,160,255,255,15,255,10,0,0,0,7,10
db 170,160,8,248,10,170,15,240,15,240,170,0,0,0,15,112
db 0,15,255,255,0,170,160,10,168,10,160,128,0,0,15,5 dup(255)
db 128,170,170,170,138,170,8,0,0,0,7,5 dup(255)
db 248,10,170,160,96,0,0,0,0,0,0,6 dup(255)
db 128,0,15,255,247,112,0,0,0,0,9 dup(255)
db 119,119,128,0,128,0,0,6 dup(255)
db 127,136,136,128,8,255,255,248,0,8,127
db 5 dup(255),247,112,8,4 dup(255),240,0,0,15
db 5 dup(255),248,143,5 dup(255),240,0,0,135
db 12 dup(255),248,0,0,0,12 dup(255),0,0,0,0
db 7,10 dup(255),240,5 dup(0),135,8 dup(255),247,7 dup(0)
db 7,6 dup(255),247,8,8 dup(0)
db 8,127,3 dup(255),247,8,10 dup(0)
db 128,0,0,0,8,5 dup(0),192,0
db 255,255,224,0,15,255,240,0,1,255,248,0,0,255,248,0
db 0,127,248,0,0,63,240,0,0,7,224,0,0,3,128,0
db 0,1,15 dup(0),1,0,0,0,3,4 dup(0,0,0,31)
db 0,0,0,63,0,0,0,127,128,0
db 0,63,128,0,0,7,128,0,0,3,128,0,0,3,192,0
db 0,3,192,0,0,3,224,0,0,7,240,0,0,15,248,0
db 0,31,254,0,0,63,255,128,0,255,255,240,3,255
end
-
Mikl__,
what should be the first step?
I'll provide some web space for your examples, the jWasm sources etc. That'll take some time.
Gunther
-
I have time to translate all the Iczelion tutorials on x64
-
Win64 Tutorial #11: More about Dialog Box
asm-file
include win64a.inc
IMAGE_BASE equ 400000h
ZZZ_OPEN equ 0
ZZZ_EXIT equ 1
MAXSIZE equ 256
OUTPUTSIZE equ 512
IDR_MAINMENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov esi,IMAGE_BASE
mov eax,10029h
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg, wParam, lParam
local dlgOpenBuffer [MAXSIZE]:BYTE
strMsgSize equ 512
local strMsg [strMsgSize]:BYTE
push rbp
mov ebp,esp
sub esp,20h+MAXSIZE+strMsgSize
mov esi,offset dlgOpenOfn
mov hWnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CREATE
je wmCREATE
leave
jmp DefWindowProc
wmDESTROY:call DestroyWindow
xor ecx,ecx
call ExitProcess
wmCOMMAND:cmp r8d,ZZZ_OPEN
jnz wmDESTROY
mov ecx,esi;offset dlgOpenOfn.lStructSize
call GetOpenFileName
or eax,eax
jz wmBYE
mov ecx,OUTPUTSIZE
lea rdi,strMsg
mov esi,offset FullPathName
call StringOut1
mov rsi,dlgOpenOfn.lpstrFile
call StringOut1
mov esi,offset FullName
call StringOut1
movzx rsi,dlgOpenOfn.nFileOffset
add rsi,dlgOpenOfn.lpstrFile
call StringOut1
mov esi,offset ExtensionName
call StringOut1
movzx rsi,dlgOpenOfn.nFileExtension
add rsi,dlgOpenOfn.lpstrFile
call StringOut1
mov [rdi],rbx
mov rcx,hWnd
mov r9,rbx;r9=MB_OK
mov r8d,offset ClassName
lea rdx,strMsg
call MessageBox
jmp wmBYE
wmCREATE:lea eax,dlgOpenBuffer
mov [rsi+OPENFILENAME.lpstrFile],rax
wmBYE: leave
retn
WndProc endp
StringOut1 proc
@@: movsb
cmp [rsi],bl
loopnz @b
retn
StringOut1 endp
;---------------------------------------
.data
ClassName db 'Win64 Iczelion''s lesson #11: More about Dialog Box',0
dlgOpenTitle db 'Open File',0
dlgOpenOfn OPENFILENAME <{sizeof OPENFILENAME},,IMAGE_BASE,\
FilterString,,,,,{MAXSIZE},,,,,,,,,,,,,,>
FilterString db 'All Files (*.*)',0,'*.*',0
db 'Text Files (*.txt)',0,'*.txt',0,0
FullPathName db 'The Full Filename with Path is : ',0
FullName db 10,'The Filename is : ',0
ExtensionName db 10,'The Extension is : ',0
end
rc-file#define ZZZ_OPEN 0
#define ZZZ_EXIT 1
#define IDR_MAINMENU 30
IDR_MAINMENU MENU
{
POPUP "&File"
{ MENUITEM "&Open",ZZZ_OPEN
MENUITEM SEPARATOR
MENUITEM "&Exit",ZZZ_EXIT
}
MENUITEM "&Exit",ZZZ_EXIT
}
-
Win64 Tutorial #12: Memory Management, File I/O, GlobalAlloc/Lock/Unlock and GlobalFree
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comdlg32.inc
includelib comdlg32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
MAXSIZE equ 256
MEM_SIZE equ 65535
EditID equ 1
IDR_MAINMENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov esi,IMAGE_BASE
mov eax,10029h
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov rcx,hwndEdit
call SetFocus
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local hMem:QWORD ;handle to the allocated memory block
local pMem:QWORD ;pointer to the allocated memory block
local szReadWrite:QWORD ;number of bytes actually read or write
push rbp
mov ebp,esp
sub esp,30h+4*8
mov edi,offset dlgOpenOfn
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_SIZE
je wmSIZE
leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmSIZE: push TRUE
movzx rax,word ptr lParam+2
push rax
movzx r9,word ptr lParam
xor edx,edx
mov r8,rdx
mov rcx,hwndEdit
push rbx
push rbx
push rbx
push rbx
call MoveWindow
jmp wmBYE
OPEN: mov [rdi+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_PATHMUSTEXIST or\
OFN_LONGNAMES or OFN_EXPLORER or OFN_HIDEREADONLY
mov ecx,edi
call GetOpenFileName
test eax,eax
je @0
push rbx
push FILE_ATTRIBUTE_ARCHIVE
push OPEN_EXISTING
mov r9,rbx
mov r8d,FILE_SHARE_READ or FILE_SHARE_WRITE
mov edx,GENERIC_READ or GENERIC_WRITE
mov ecx,offset dOpenBuffer
push rbx
push rbx
push rbx
push rbx
call CreateFile
mov edi,eax;handle to file
mov edx,MEM_SIZE
mov ecx,GMEM_MOVEABLE or GMEM_ZEROINIT
call GlobalAlloc
mov hMem,rax
mov ecx,eax
call GlobalLock
mov pMem,rax
push rbx
lea r9d,szReadWrite
mov r8d,MEM_SIZE-1
mov rdx,rax;pMem
mov ecx,edi
push rbx
push rbx
push rbx
push rbx
call ReadFile
mov r9,pMem
mov r8,rbx
mov edx,WM_SETTEXT
mov rcx,hwndEdit
call SendMessage
jmp @1
SAVE: mov [rdi+OPENFILENAME.Flags],OFN_LONGNAMES or OFN_EXPLORER or OFN_HIDEREADONLY
mov ecx,edi;&dOpenOfn
call GetSaveFileName
test eax,eax
je @0
push rbx
push FILE_ATTRIBUTE_ARCHIVE
push CREATE_NEW
mov r9,rbx
mov r8d,FILE_SHARE_READ or FILE_SHARE_WRITE
mov edx,GENERIC_READ or GENERIC_WRITE
mov ecx,offset dOpenBuffer
push rbx
push rbx
push rbx
push rbx
call CreateFile
mov edi,eax;hFile
mov edx,MEM_SIZE
mov ecx,GMEM_MOVEABLE or GMEM_ZEROINIT
call GlobalAlloc
mov hMem,rax
mov ecx,eax
call GlobalLock
mov pMem,rax
mov r9,rax ;pMem
mov r8d,MEM_SIZE-1
mov edx,WM_GETTEXT
mov rcx,hwndEdit
call SendMessage
push rbx
lea r9,szReadWrite
mov r8,rax
mov rdx,pMem
mov ecx,edi;hFile
push rbx
push rbx
push rbx
push rbx
call WriteFile
@1: mov ecx,edi;hFile
call CloseHandle
mov rcx,pMem
call GlobalUnlock
mov rcx,hMem
call GlobalFree
@0: mov rcx,hwndEdit
call SetFocus
jmp wmBYE
wmCREATE:mov [rdi+OPENFILENAME.hwndOwner],rcx
push rbx
push IMAGE_BASE
push EditID
push rcx;hWnd
push rbx
push rbx
push rbx
push rbx
mov r9d,WS_VISIBLE or \
WS_CHILD or ES_LEFT or ES_MULTILINE or WS_VSCROLL or WS_HSCROLL or\
ES_AUTOHSCROLL or ES_AUTOVSCROLL
mov r8,rbx
mov edx,offset EditClass
xor ecx,ecx
;-------------------------------
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov hwndEdit,rax
jmp wmBYE
wmCOMMAND:movzx rax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz wmBYE
cmp rax,ZZZ_EXIT
ja wmBYE
jmp [menu_handlers+rax*8]
EXIT: call DestroyWindow
wmBYE: leave
retn
menu_handlers dq wmBYE,OPEN,SAVE,EXIT
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #12: Memory Management, File I/O, GlobalAlloc/Lock/Unlock and GlobalFree',0
dlgOpenTitle db 'Open File',0
align 8
dlgOpenOfn OPENFILENAME <{sizeof OPENFILENAME},,IMAGE_BASE,\
FilterString,,,,dOpenBuffer,{MAXSIZE},,,,,,,,,,,,,,>
FilterString db 'All Files (*.*)',0,'*.*',0
db 'Text Files (*.txt)',0,'*.txt',0,0
dOpenBuffer db MAXSIZE dup(?)
hwndEdit dq ? ;handle for edit control
EditClass db "edit",0
end
rc-file#define ZZZ_OPEN 1
#define ZZZ_SAVE 2
#define ZZZ_EXIT 3
#define IDR_MAINMENU 30
IDR_MAINMENU MENU
{
POPUP "&File"
{ MENUITEM "&Open",ZZZ_OPEN
MENUITEM "&Save As",ZZZ_SAVE
MENUITEM SEPARATOR
MENUITEM "&Exit",ZZZ_EXIT
}
MENUITEM "&Exit",ZZZ_EXIT
}
-
Win64 Tutorial #12b: Memory Management, File I/O, GetProcessHeap, HeapAlloc and HeapFree
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comdlg32.inc
includelib comdlg32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
MAXSIZE equ 256
MEM_SIZE equ 65535
EditID equ 1
IDR_MAINMENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov esi,IMAGE_BASE
mov eax,10029h
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov ecx,eax
call GetMenu
mov hMenu,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local hFile:QWORD ;handle of file
local szReadWrite:QWORD ;number of bytes actually read or write
push rbp
mov ebp,esp
sub esp,30h+4*8
mov edi,offset dlgOpenOfn
mov hWnd,rcx
mov lParam,r9
mov wParam,r8
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_SIZE
je wmSIZE
leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmSIZE: push TRUE
movzx rax,word ptr lParam+2
push rax
movzx r9,word ptr lParam
xor edx,edx
mov r8,rdx
mov rcx,hwndEdit
push rbx
push rbx
push rbx
push rbx
call MoveWindow
jmp wmBYE
OPEN: mov [edi+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_PATHMUSTEXIST or\
OFN_LONGNAMES or OFN_EXPLORER or OFN_HIDEREADONLY
mov ecx,edi
call GetOpenFileName
test eax,eax
je wmBYE
movzx edx,word ptr [edi+OPENFILENAME.nFileOffset]
add edx,offset dOpenBuffer
mov rcx,hWnd
call SetWindowText
push rbx
push FILE_ATTRIBUTE_ARCHIVE
push OPEN_EXISTING
mov r9,rbx
mov r8d,FILE_SHARE_READ or FILE_SHARE_WRITE
mov edx,GENERIC_READ or GENERIC_WRITE
mov ecx,offset dOpenBuffer
push rbx
push rbx
push rbx
push rbx
call CreateFile
mov hFile,rax;handle to file
xor edx,edx
mov ecx,eax
call GetFileSize
mov FileSize,rax
call GetProcessHeap
mov hHeap,rax
mov r8d,MEM_SIZE
mov edx,HEAP_ZERO_MEMORY
mov ecx,eax
call HeapAlloc
mov pMem,rax
push rbx
lea r9d,szReadWrite
mov r8d,MEM_SIZE-1
mov edx,eax;pMem
mov rcx,hFile
push rbx
push rbx
push rbx
push rbx
call ReadFile
mov r9,pMem
mov r8,rbx
mov edx,WM_SETTEXT
mov rcx,hwndEdit
call SendMessage
mov r9,rbx
mov r8d,MF_GRAYED
jmp @f
SAVE: mov [edi+OPENFILENAME.Flags],OFN_LONGNAMES or OFN_EXPLORER or OFN_HIDEREADONLY
mov ecx,edi;&dOpenOfn
call GetSaveFileName
test eax,eax
je wmBYE
movzx edx,word ptr [edi+OPENFILENAME.nFileOffset]
add edx,offset dOpenBuffer
mov rcx,hWnd
call SetWindowText
push rbx
push FILE_ATTRIBUTE_ARCHIVE
push CREATE_NEW
mov r9,rbx
mov r8d,FILE_SHARE_READ or FILE_SHARE_WRITE
mov edx,GENERIC_READ or GENERIC_WRITE
mov ecx,offset dOpenBuffer
push rbx
push rbx
push rbx
push rbx
call CreateFile
mov hFile,rax
mov r9,pMem
mov r8,FileSize
mov edx,WM_GETTEXT
mov rcx,hwndEdit
call SendMessage
push rbx
lea r9,szReadWrite
mov r8,rax
mov rdx,pMem
mov rcx,hFile
push rbx
push rbx
push rbx
push rbx
call WriteFile
mov r8,pMem
xor edx,edx
mov rcx,hHeap
call HeapFree
mov r9d,MF_GRAYED
mov r8,rbx;MF_ENABLED=0
@@: mov edx,edx;IDM_OPEN=0
mov rcx,hMenu
call EnableMenuItem
mov edx,ZZZ_SAVE
mov rcx,hMenu
call EnableMenuItem
mov rcx,hFile
call CloseHandle
jmp wmBYE
wmCREATE:mov [dlgOpenOfn.hwndOwner],rcx
push rbx
push IMAGE_BASE
push EditID
push rcx;hWnd
push rbx
push rbx
push rbx
push rbx
mov r9d,WS_VISIBLE or \
WS_CHILD or ES_LEFT or ES_MULTILINE or WS_VSCROLL or WS_HSCROLL or\
ES_AUTOHSCROLL or ES_AUTOVSCROLL
mov r8,rbx
mov edx,offset EditClass
xor ecx,ecx
;-------------------------------
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov hwndEdit,rax
jmp wmBYE
wmCOMMAND:movzx rax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz wmBYE
cmp rax,ZZZ_EXIT
ja wmBYE
jmp [menu_handlers+eax*8]
EXIT: ;mov rcx,hWnd ;ax=MI_EXIT
call DestroyWindow
wmBYE: leave
retn
menu_handlers dq wmBYE,OPEN,SAVE,EXIT
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #12b: Memory Management, File I/O, GetProcessHeap, HeapAlloc and HeapFree',0
dlgOpenTitle db 'Open File',0
dlgOpenOfn OPENFILENAME <{sizeof OPENFILENAME},,IMAGE_BASE,\
FilterString,,,,dOpenBuffer,{MAXSIZE},,,,,,,,,,,,,,>
FilterString db 'All Files (*.*)',0,'*.*',0
db 'Text Files (*.txt)',0,'*.txt',0,0
dOpenBuffer db MAXSIZE dup(?)
hwndEdit dq ? ;handle for edit control
EditClass db "edit",0
hHeap dq ?
pMem dq ?
FileSize dq ?
hMenu dq ?
end
rc-file#define ZZZ_OPEN 1
#define ZZZ_SAVE 2
#define ZZZ_EXIT 3
#define IDR_MAINMENU 30
IDR_MAINMENU MENU
{
POPUP "&File"
{ MENUITEM "&Open",ZZZ_OPEN
MENUITEM "&Save As",ZZZ_SAVE
MENUITEM SEPARATOR
MENUITEM "&Exit",ZZZ_EXIT
}
MENUITEM "&Exit",ZZZ_EXIT
}
-
Win64 Tutorial #14: Process
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comdlg32.inc
includelib comdlg32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
MI_PROCESS_CREATE equ 1
MI_PROCESS_TERMINATE equ 2
MI_EXIT equ 3
IDR_MAINMENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov esi,IMAGE_BASE
mov eax,10029h
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 400
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov ecx,eax
call GetMenu
mov hMenu,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local progStartInfo:STARTUPINFO
push rbp
mov ebp,esp
sub esp,38h+sizeof STARTUPINFO
mov edi,offset processInfo
mov esi,offset proExitCode
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_INITMENUPOPUP
je wmINITMENUPOPUP
leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmINITMENUPOPUP:mov edx,esi
mov rcx,[rdi+PROCESS_INFORMATION.hProcess]
call GetExitCodeProcess
or eax,eax
jz @f;GetExitCodeProcess_TRUE
cmp dword ptr [rsi],STILL_ACTIVE;cmp [proExitCode],STILL_ACTIVE
jne @f; GetExitCodeProcess_STILL_ACTIVE
mov r9,rbx;MF_ENABLED
mov r8d,MF_GRAYED
jmp @0
@@: mov r9d,MF_GRAYED
mov r8,rbx;MF_ENABLED
@0: xor edx,edx;MI_PROCESS_CREATE
mov rcx,hMenu
call EnableMenuItem
mov r9d,MF_GRAYED
mov r8,rbx;MF_ENABLED
mov edx,MI_PROCESS_TERMINATE
mov rcx,hMenu
call EnableMenuItem
jmp wmBYE
wmCOMMAND:movzx rax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz wmBYE
cmp rax,MI_EXIT
ja wmBYE
jmp [menu_handlers+eax*8]
PROCESS_CREATE:cmp [rdi+PROCESS_INFORMATION.hProcess],rbx
je pi_hProcess_IS_0
mov rcx,[edi+PROCESS_INFORMATION.hProcess]
call CloseHandle
mov [rdi+PROCESS_INFORMATION.hProcess],rbx
pi_hProcess_IS_0:
lea esi,progStartInfo
mov ecx,esi
call GetStartupInfo
push rdi
push rsi
push rbx
push rbx
push NORMAL_PRIORITY_CLASS
push rbx
mov r9,rbx
mov r8,rbx
xor edx,edx
mov ecx,offset progName
push rbx
push rbx
push rbx
push rbx
call CreateProcess
mov rcx,[rdi+PROCESS_INFORMATION.hThread]
call CloseHandle
jmp wmBYE
TERMINATE:mov edx,esi;proExitCode
mov rcx,[rdi+PROCESS_INFORMATION.hProcess]
call GetExitCodeProcess
cmp dword ptr [rsi],STILL_ACTIVE
jne proExitCode_NOT_STILL_ACTIVE;a4;
xor edx,edx
mov rcx,[rdi+PROCESS_INFORMATION.hProcess]
call TerminateProcess
proExitCode_NOT_STILL_ACTIVE:
mov rcx,[rdi+PROCESS_INFORMATION.hProcess]
call CloseHandle
mov [rdi+PROCESS_INFORMATION.hProcess],rbx;0
jmp wmBYE
EXIT: ;mov rcx,hWnd ;ax=MI_EXIT
call DestroyWindow
wmBYE: leave
retn
menu_handlers dq wmBYE,PROCESS_CREATE, TERMINATE, EXIT
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #14: Process',0
hMenu dq ?
proExitCode dq ?;process exit code
progName db 'msgbox.exe',0
processInfo PROCESS_INFORMATION <>
end
rc-file#define MI_PROCESS_CREATE 1
#define MI_PROCESS_TERMINATE 2
#define MI_EXIT 3
#define IDR_MAINMENU 30
IDR_MAINMENU MENU
{
POPUP "&Process"
{
MENUITEM "&Create Process",MI_PROCESS_CREATE
MENUITEM "&Terminate Process",MI_PROCESS_TERMINATE,GRAYED
MENUITEM SEPARATOR
MENUITEM "E&xit",MI_EXIT
}
}
-
Win64 Tutorial #15: Multithreading Programming
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comdlg32.inc
includelib comdlg32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
MI_THREAD_CREATE equ 0
MI_EXIT equ 1
WMU_THREAD_FINISH equ WM_USER + 100h
IDR_MAINMENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov esi,IMAGE_BASE
mov eax,10029h
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 500
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov hWindow,rax
mov ecx,eax
call GetMenu
mov hMenu,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local progStartInfo:STARTUPINFO
push rbp
mov ebp,esp
sub esp,20h
mov hWnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WMU_THREAD_FINISH
je wmu_THREAD_FINISH
leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmu_THREAD_FINISH:mov r9,rbx;MB_OK
mov edx,offset ClassName
mov r8,rdx
xor ecx,ecx
call MessageBox
jmp wmBYE
wmCOMMAND:cmp r8w,MI_THREAD_CREATE
je wmCOMMAND_MI_THREAD_CREATE
cmp r8w,MI_EXIT
jne wmBYE
wmCOMMAND_MI_EXIT:call DestroyWindow;,[hWnd]
jmp wmBYE
wmCOMMAND_MI_THREAD_CREATE:
mov eax,offset tId
push rax
push NORMAL_PRIORITY_CLASS
mov r9,rbx;NULL
mov r8d,offset thread_procedure
xor edx,edx;0
xor ecx,ecx;NULL
push rbx
push rbx
push rbx
push rbx
call CreateThread
mov ecx,eax
call CloseHandle
wmBYE: leave
retn
WndProc endp
;---------------------------------------
thread_procedure proc
sub rsp,5*8
mov rcx,3FFFFFFFh
loopSTART:add eax,eax
dec rcx
jnz loopSTART
loopEND:mov r9,rbx;NULL
mov r8,rbx;NULL
mov edx,WMU_THREAD_FINISH
mov rcx,hWindow
call SendMessage
add rsp,5*8
ret
thread_procedure endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #15: Multithreading Programming',0
hMenu dq ?
hWindow dq ?
tId dd ?
end
rc-file#define MI_THREAD_CREATE 0
#define MI_EXIT 1
#define IDR_MAINMENU 30
IDR_MAINMENU MENU
{
POPUP "&Thread"
{
MENUITEM "&Create Thread",MI_THREAD_CREATE
MENUITEM SEPARATOR
MENUITEM "E&xit",MI_EXIT
}
}
-
Win64 Tutorial #13: Memory Mapped File
asm-fileOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comdlg32.inc
includelib comdlg32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
ZZZ_OPEN equ 1
ZZZ_SAVE equ 2
ZZZ_EXIT equ 3
MAXSIZE equ 256
MEM_SIZE equ 65535
EditID equ 1
IDR_MAINMENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov esi,IMAGE_BASE
mov eax,10029h
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov ecx,eax
call GetMenu
mov hMenu,rax
mov rcx,hwndEdit
call SetFocus
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local hFile:QWORD ;handle of file
local szReadWrite:QWORD ;number of bytes actually read or write
push rbp
mov ebp,esp
sub esp,(30h+2*8+15)and(-16)
mov edi,offset dlgOpenOfn
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_SIZE
je wmSIZE
leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmSIZE: push TRUE
movzx rax,word ptr lParam+2
push rax
movzx r9,word ptr lParam
xor edx,edx
mov r8,rdx
mov rcx,hwndEdit
push rbx
push rbx
push rbx
push rbx
call MoveWindow
jmp wmBYE
OPEN: mov [rdi+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_PATHMUSTEXIST or\
OFN_LONGNAMES or OFN_EXPLORER or OFN_HIDEREADONLY
mov ecx,edi
call GetOpenFileName
test eax,eax
je wmBYE
push rbx ;<- align stack 16h
push rbx
push FILE_ATTRIBUTE_ARCHIVE
push OPEN_EXISTING
mov r9,rbx
mov r8d,FILE_SHARE_READ or FILE_SHARE_WRITE
mov edx,GENERIC_READ or GENERIC_WRITE
mov ecx,offset dOpenBuffer
push rbx
push rbx
push rbx
push rbx
call CreateFile
mov hFile,rax;handle to file
xor edx,edx
mov ecx,eax
call GetFileSize
mov FileSize,rax
movzx edx,word ptr [rdi+OPENFILENAME.nFileOffset]
add edx,offset dOpenBuffer
mov rcx,hWnd
call SetWindowText
;созддание в памяти объекта "проекция файла"
mov [rsp+28h],rbx
mov [rsp+20h],rbx
mov r9,rbx
mov r8d,PAGE_READWRITE
xor edx,edx
mov rcx,hFile
call CreateFileMapping
mov hMapping,rax
;отображение проекции файла на адресное пространство процесса
mov [rsp+20h],rbx
mov r9,rbx
mov r8,rbx
mov edx,FILE_MAP_WRITE
mov ecx,eax
call MapViewOfFile
mov pMapping,rax
mov r9,rax
mov r8,rbx
mov edx,WM_SETTEXT
mov rcx,hwndEdit
call SendMessage
mov r9,rbx
mov r8d,MF_GRAYED
jmp @f
SAVE: mov [rdi+OPENFILENAME.Flags],OFN_LONGNAMES or OFN_EXPLORER or OFN_HIDEREADONLY
mov ecx,edi;&dOpenOfn
call GetSaveFileName
test eax,eax
je wmBYE
push rbx ;<- align stack 16h
push rbx
push FILE_ATTRIBUTE_ARCHIVE
push CREATE_NEW
mov r9,rbx
mov r8d,FILE_SHARE_READ or FILE_SHARE_WRITE
mov edx,GENERIC_READ or GENERIC_WRITE
mov ecx,offset dOpenBuffer
push rbx
push rbx
push rbx
push rbx
call CreateFile
mov hFile,rax
movzx edx,word ptr [rdi+OPENFILENAME.nFileOffset]
add edx,offset dOpenBuffer
mov rcx,hWnd
call SetWindowText
push rbx ;<- align stack 16h
push rbx
lea r9,szReadWrite
mov r8,FileSize
mov rdx,pMapping
mov rcx,hFile
push rbx
push rbx
push rbx
push rbx
call WriteFile
mov rcx,pMapping
call UnmapViewOfFile
mov rcx,pMapping
call CloseHandle
mov rcx,hMapping
call CloseHandle
mov r9d,MF_GRAYED
mov r8,rbx;MF_ENABLED=0
@@: mov edx,edx;IDM_OPEN=0
mov rcx,hMenu
call EnableMenuItem
mov edx,ZZZ_SAVE
mov rcx,hMenu
call EnableMenuItem
mov rcx,hFile
call CloseHandle
jmp wmBYE
wmCREATE:mov [rdi+OPENFILENAME.hwndOwner],rcx
push rbx
push IMAGE_BASE
push EditID
push rcx;hWnd
push rbx
push rbx
push rbx
push rbx
mov r9d,WS_VISIBLE or \
WS_CHILD or ES_LEFT or ES_MULTILINE or WS_VSCROLL or WS_HSCROLL or\
ES_AUTOHSCROLL or ES_AUTOVSCROLL
mov r8,rbx
mov edx,offset EditClass
xor ecx,ecx
;-------------------------------
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov hwndEdit,rax
jmp wmBYE
wmCOMMAND:movzx rax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz wmBYE
cmp rax,ZZZ_EXIT
ja wmBYE
jmp [menu_handlers+eax*8]
EXIT: ;mov rcx,hWnd ;ax=MI_EXIT
call DestroyWindow
wmBYE: leave
retn
menu_handlers dq wmBYE,OPEN,SAVE,EXIT
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #13: Memory Mapped File',0
dlgOpenTitle db 'Open File',0
align 8
dlgOpenOfn OPENFILENAME <{sizeof OPENFILENAME},,IMAGE_BASE,\
FilterString,,,,dOpenBuffer,{MAXSIZE},,,,,,,,,,,,,,>
FilterString db 'All Files (*.*)',0,'*.*',0
db 'Text Files (*.txt)',0,'*.txt',0,0
dOpenBuffer db MAXSIZE dup(?)
hwndEdit dq ? ;handle for edit control
EditClass db "edit",0
hMapping dq ? ;file mapped handle
pMapping dq ?
FileSize dq ?
hMenu dq ?
end
rc-file#define ZZZ_OPEN 1
#define ZZZ_SAVE 2
#define ZZZ_EXIT 3
#define IDR_MAINMENU 30
IDR_MAINMENU MENU
{
POPUP "&File"
{ MENUITEM "&Open",ZZZ_OPEN
MENUITEM "&Save As",ZZZ_SAVE
MENUITEM SEPARATOR
MENUITEM "&Exit",ZZZ_EXIT
}
MENUITEM "&Exit",ZZZ_EXIT
}
-
Win64 Tutorial #18: few kinds of Progress bar
include win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
IDC_PROGRESS equ 1; control IDs
IDC_STATUS equ 2
IDC_TIMER equ 3
btn1 equ 4
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
call InitCommonControls
xor ebx,ebx
mov eax,10029h
mov edi,offset ClassName
mov esi,IMAGE_BASE
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_APPWORKSPACE;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 240
push 400
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW+WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
;--------------------------------------------------
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
;-----------------------------------------
WndProc proc hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
local oldBrush:QWORD
local ps:PAINTSTRUCT
push rbp
mov ebp,esp
sub esp,(20h+sizeof PAINTSTRUCT+8+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_COMMAND
je wmCOMMAND
leave
jmp DefWindowProc
wmPAINT:lea edx,ps
call BeginPaint
mov rdx,blueBrush
mov rcx,ps.hdc
call SelectObject
mov oldBrush,rax
finit
fld angle
fsincos
fmul const_80
fistp tempX
fmul const_80
fchs
fist tempY
mov eax,tempY
add rax,130
push rax ;nYRadial2
mov eax,tempX
add rax,190
push rax ;nXRadial2
push 80 ;nYRadial1
push 190 ;nXRadial1
push 180 ;nBottomRect
mov r9d,270 ;nRightRect
mov r8d,80 ;nTopRect
mov edx,110 ;nLeftRect
mov rcx,ps.hdc
push rbx
push rbx
push rbx
push rbx
call Pie
mov rdx,oldBrush
mov rcx,ps.hdc
call SelectObject
lea edx,ps
mov rcx,hWnd
call EndPaint
jmp wmBYE
wmDESTROY:mov rdx,TimerID
or edx,edx
jne @f
call KillTimer;,hWnd
@@: xor ecx,ecx
call ExitProcess
wmCREATE:mov edi,3
@@: push rbx ;lpParam
push IMAGE_BASE ;hInstance
push IDC_PROGRESS
push hWnd ;hWndParent
push nHeight[rdi*8]
push nWidth[rdi*8]
push y[rdi*8]
push x[rdi*8]
mov r9d,dwStyle[rdi*4]
mov r8,rbx ;lpWindowName
mov edx,offset progressClass;lpClassName
mov ecx,dwExStyle[rdi*4]
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov pb1H[rdi*8],rax
mov r9,rbx
mov r8d,2
mov edx,PBM_SETSTEP
mov ecx,eax
call SendMessage
dec edi
jns @b
;-------------------------------------------------------
push rbx;NULL
push IMAGE_BASE
push btn1
push hWnd
push 30
push 100
push 90
push 10
mov r9d,WS_CHILD + WS_VISIBLE + BS_PUSHBUTTON
mov r8d,offset btn1Txt
mov edx,offset ctlClsNameBtn
xor ecx,ecx;NULL
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov btn1H,rax
;---------------------------------------------------------------
mov r9d,IDC_STATUS
mov r8,hWnd
xor edx,edx;NULL
mov ecx,WS_CHILD + WS_VISIBLE
call CreateStatusWindow
mov hwndStatus,rax
mov ecx,0FF9933h; light blue color
call CreateSolidBrush
mov blueBrush,rax
jmp wmBYE
wmCOMMAND:cmp wParam,BN_CLICKED shl 16 or 4
jne wmBYE
wmCOMMAND_btn1:;create a timer
mov r9d,offset TimerProc
mov r8d,100
mov edx,IDC_TIMER
mov rcx,hWnd
call SetTimer
mov TimerID,rax
xor edx,edx;FALSE
mov rcx,btn1H
call EnableWindow
wmBYE: leave
retn
WndProc endp
TimerProc proc hWnd:HWND
local buffer[16]:BYTE
push rbp
mov ebp,esp
sub esp,20h+10h
mov hWnd,rcx
mov edi,3
@@: mov r9,rbx; step up the progress in
mov r8,rbx;0
mov edx,PBM_STEPIT
mov rcx,pb1H[rdi*8]
call SendMessage
mov r9,rbx
mov r8,rbx
mov edx,PBM_GETPOS
mov rcx,pb1H[rdi*8]
call SendMessage
dec edi
jns @b
lea ecx,buffer
mov edx,offset format
mov r8,rax
call wsprintf
lea r9,buffer
mov r8,rbx
mov edx,SB_SETTEXT
mov rcx,hwndStatus
call SendMessage
mov r8,rbx
xor edx,edx
mov rcx,hWnd
call InvalidateRect
finit
fld delta
fadd angle
fst angle
sub CurrentStep,2
jne wmBYE
mov rdx,TimerID
mov rcx,hWnd
call KillTimer
mov TimerID,0
mov r9d,offset Message
mov r8,rbx;0
mov edx,SB_SETTEXT
mov rcx,hwndStatus
call SendMessage
wmBYE: leave
retn
TimerProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #18: Common Controls',0
progressClass db 'msctls_progress32',0
TimerID dq ?
pb1H dq ?;hwndprogress
pb2H dq ?
pb3H dq ?
pb4H dq ?
sb1H dq ?
btn1H dq ?
hwndStatus dq ?
ctlClsNameBtn db 'BUTTON',0
btn1Txt db 'Click To Start',0
CurrentStep dq 100 ;increase step value
blueBrush dq ?
const_80 dd 80.0
tempX dd ?
tempY dd ?
angle dd 1.57952297305486826711594014548 ;90.5*pi/180
delta dd 0.12548917321839229658081336625 ;7.19*pi/180
dwStyle dd WS_CHILD + WS_VISIBLE,WS_CHILD + WS_VISIBLE + PBS_SMOOTH,\
WS_CHILD + WS_VISIBLE + PBS_VERTICAL,WS_CHILD + WS_VISIBLE + PBS_VERTICAL + PBS_SMOOTH
x dq 10,10,305,350
y dq 10,40,80,80
nHeight dq 22,22,100,100
nWidth dq 367,367,25,25
dwExStyle dd WS_EX_DLGMODALFRAME,WS_EX_DLGMODALFRAME + WS_EX_STATICEDGE,0,0
format db ' Process : %i %%',0
Message db ' 100% Completed',0
end
-
Win64 Tutorial #16: Event Example
asm-file
OPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comdlg32.inc
includelib comdlg32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
IDM_START_THREAD equ 1
IDM_STOP_THREAD equ 2
IDM_EXIT equ 3
WM_FINISH equ WM_USER+100h
IDR_MAINMENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov esi,IMAGE_BASE
mov eax,10029h
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
mov eax,offset WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
push rbx
push rbx
push rbx
push rbx
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 400
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
push rbx
push rbx
push rbx
push rbx
call CreateWindowEx
mov hwnd,rax
mov ecx,eax
call GetMenu
mov hMenu,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
push rbp
mov ebp,esp
sub esp,20h
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_FINISH
je wmFINISH
leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmCREATE:mov r9,rbx;NULL
mov r8,rbx;FALSE
xor edx,edx;FALSE
xor ecx,ecx;NULL
call CreateEvent
mov hEventStart,rax
mov eax,offset ThreadID
push rax
push NORMAL_PRIORITY_CLASS
mov r9,rbx;NULL
mov r8d,offset ThrdProc
xor edx,edx;NULL
xor ecx,ecx;NULL
push rbx
push rbx
push rbx
push rbx
call CreateThread
mov hThread,rax
mov ecx,eax
call CloseHandle
jmp wmBYE
wmCOMMAND:movzx rax,word ptr wParam
cmp r9,rbx ;cmp lParam,0
jnz wmBYE
cmp rax,IDM_EXIT
ja wmBYE
jmp [menu_handlers+eax*8]
START_THREAD:mov rcx,hEventStart
call SetEvent
mov r8d,MF_GRAYED
mov edx,IDM_START_THREAD
mov rcx,hMenu
call EnableMenuItem
mov r8d,MF_ENABLED
mov edx,IDM_STOP_THREAD
mov rcx,hMenu
call EnableMenuItem
jmp wmBYE
STOP_THREAD:mov EventStop,TRUE
mov r8d,MF_ENABLED
mov edx,IDM_START_THREAD
mov rcx,hMenu
call EnableMenuItem
mov r8d,MF_GRAYED
mov edx,IDM_STOP_THREAD
mov rcx,hMenu
call EnableMenuItem
jmp wmBYE
EXIT: ;mov rcx,hWnd ;ax=MI_EXIT
call DestroyWindow
jmp wmBYE
wmFINISH:mov r9,rbx;MB_OK
mov r8d,offset ClassName
mov edx,offset SuccessString
xor ecx,ecx;NULL
call MessageBox
wmBYE: leave
retn
menu_handlers dq wmBYE, START_THREAD, STOP_THREAD, EXIT
WndProc endp
;---------------------------------------
ThrdProc:
sub rsp,5*8
mov edx,INFINITE
mov rcx,hEventStart
call WaitForSingleObject
or ecx,-1
@0: cmp EventStop,FALSE
jz @f
mov r9,rbx;MB_OK
mov r8d,offset SuccessString
mov edx,offset StopString
mov rcx,hwnd
call MessageBox
mov EventStop,FALSE
add rsp,5*8
jmp ThrdProc
@@: add eax,eax
dec rcx
jnz @0
mov r9,rbx;NULL
mov r8,rbx;NULL
mov edx,WM_FINISH
mov rcx,hwnd
call PostMessage
mov r8d,MF_ENABLED
mov edx,IDM_START_THREAD
mov rcx,hMenu
call EnableMenuItem
mov r8d,MF_GRAYED
mov edx,IDM_STOP_THREAD
mov rcx,hMenu
call EnableMenuItem
add rsp,5*8
jmp ThrdProc
; ret
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #16: Event Example',0
SuccessString db "The calculation is completed!",0
StopString db "The thread is stopped",0
EventStop BOOL FALSE
hwnd HANDLE ?
hMenu HANDLE ?
ThreadID dq ?
ExitCode dq ?
hThread dq ?
hEventStart HANDLE ?
end
rc-file
#define IDM_START_THREAD 1
#define IDM_STOP_THREAD 2
#define IDM_EXIT 3
#define IDR_MAINMENU 30
IDR_MAINMENU MENU
{
POPUP "&Thread"
{
MENUITEM "&Run Thread",IDM_START_THREAD
MENUITEM "&Stop Thread",IDM_STOP_THREAD,GRAYED
MENUITEM SEPARATOR
MENUITEM "E&xit",IDM_EXIT
}
}
-
no responses, no questions... (http://www.cyberforum.ru/images/smilies/scratch_one-s_head.gif)
-
If I had started Win64, you would get questions every day :biggrin:
Fantastic job, Mikl :t
-
mille grazie, jj2007 !
-
Thank you for the examples. :t
Just like jj2007, haven't started programming x64 yet.
When I do, this will be a great help.
-
Well, Siekmanski, I hope... (Nou, ik hoop)(http://www.cyberforum.ru/images/smilies/yes.gif)
-
Win64 Tutorial #32: Multiple Document Interface (MDI)
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include shell32.inc
includelib shell32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
IDM_MENU equ 1000
IDM_FILE_EXIT equ 0
IDM_FILE_NEW equ 1
IDM_WINDOW_NEXT equ 2
IDM_WINDOW_PREVIOUS equ 3
MI_CLOSE equ 4
MI_TILEHOR equ 5
MI_TILEVER equ 6
MI_CASCADE equ 7
IDM_HELP_ABOUT equ 8
MI_CLOSE_ALL equ 9
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov edi,offset ClassName
mov eax,10029h
mov esi,IMAGE_BASE
push rax ;hIconSm
push rdi ;lpszClassName
push IDM_MENU ;lpszMenuName
push COLOR_APPWORKSPACE;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push DLGWINDOWEXTRA;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
mov edi,ecx
sub esp,20h
call RegisterClassEx
mov eax,offset MdiChildProc
mov [rdi+WNDCLASSEX.lpfnWndProc],rax
mov [rdi+WNDCLASSEX.cbWndExtra],ebx
mov [rdi+WNDCLASSEX.lpszMenuName],rbx
mov eax,offset MdiChildClassName
mov [rdi+WNDCLASSEX.lpszClassName],rax
mov ecx,edi
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 600
push 800
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE or WS_CLIPCHILDREN
mov edx,offset ClassName
mov r8,rdx ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov hWnd,rax
mov ecx,eax
call GetMenu
mov hMenu,rax
mov edx,1
mov ecx,eax
call GetSubMenu
mov cc.hWindowMenu,rax
mov edi,offset rect
mov edx,edi
mov rcx,hWnd
call GetClientRect
mov eax,offset cc
push rax
push rsi
push rbx
push hWnd
mov eax,[rdi+RECT.bottom]
push rax
mov eax,[rdi+RECT.right]
push rax
push rbx
push rbx
mov r9d,WS_CHILD + WS_VISIBLE + WS_VSCROLL + WS_HSCROLL + WS_CLIPCHILDREN
mov r8,rbx
mov edx,offset MdiClientClassName
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov hClient,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov edx,edi
mov rcx,hClient
call TranslateMDISysAccel
test eax,eax
jnz @b
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWin:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
push rbp
mov ebp,esp
sub esp,20h
mov hWin,rcx
mov wParam,r8
mov lParam,r9
xor ebx,ebx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_SIZE
je wmSIZE
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCOMMAND:mov rax,r8;[wParam]
cmp eax,MI_CLOSE_ALL;5
ja wmBYE
jmp [menu_handlers+rax*8]
New: mov esi,IMAGE_BASE
push rbx;NULL
push rsi;hInstance
shl esi,9
push rbx
push hClient
push rsi
push rsi
push rsi
push rsi
mov r9d,MDIS_ALLCHILDSTYLES
mov edx,offset MdiChildClassName
mov r8,rdx
mov ecx,WS_EX_MDICHILD + WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
jmp wmBYE
Exit: mov rax,hWin
jmp a1
Next: mov r9d,TRUE
jmp a3
Prev: mov r9,rbx
a3: mov r8,rbx
mov edx,WM_MDINEXT
a4: mov rcx,hClient
jmp a2
Horiz: mov r9,rbx
mov r8d,MDITILE_HORIZONTAL
a5: mov edx,WM_MDITILE
jmp a4
Vert: mov r9,rbx
mov r8,rbx
jmp a5
Cascade:mov r9,rbx
mov r8d,MDITILE_SKIPDISABLED
mov edx,WM_MDICASCADE
jmp a4
Close: mov r9,rbx
mov r8,rbx
mov edx,WM_MDIGETACTIVE
mov rcx,hClient
call SendMessage
a1: mov r9,rbx
mov r8,rbx
mov edx,WM_CLOSE
mov rcx,rax
a2: call SendMessage
jmp wmBYE
About: mov r9,rbx
mov r8d,offset AboutMsg
mov edx,offset ClassName
mov rcx,hWin
call ShellAbout
jmp wmBYE
CloseAll:mov r9,rbx
mov r8,rbx
mov edx,WM_MDIGETACTIVE
mov rcx,hClient
call SendMessage
test eax,eax
je wmBYE
mov r9,rbx
mov r8,rbx
mov edx,WM_CLOSE
mov ecx,eax
call SendMessage
jmp CloseAll
wmSIZE: mov edi,offset rect
mov edx,edi
mov rcx,hWin
call GetClientRect
push TRUE
mov eax,[rdi+RECT.bottom]
push rax
mov r9d,[rdi+RECT.right]
mov r8,rbx
xor edx,edx
mov rcx,hClient
sub esp,20h
call MoveWindow
wmBYE: leave
retn
menu_handlers dq Exit,New,Next,Prev,Close,Horiz,Vert,Cascade,About,CloseAll
WndProc endp
MdiChildProc proc
push rbp
mov ebp,esp
sub esp,20h
cmp edx,WM_MDIACTIVATE
jz wmMDIACTIVATE
leave
jmp DefMDIChildProc
wmMDIACTIVATE: mov rax,r9;[lParam2]
cmp rax,rcx;[hChild]
setne bl;MF_ENABLED=0 MF_GRAYED=1
mov r8,rbx
mov edx,MI_CLOSE
mov rcx,hMenu
call EnableMenuItem
mov r8,rbx
mov edx,MI_TILEHOR
mov rcx,hMenu
call EnableMenuItem
mov r8,rbx
mov edx,MI_TILEVER
mov rcx,hMenu
call EnableMenuItem
mov r8,rbx
mov edx,MI_CASCADE
mov rcx,hMenu
call EnableMenuItem
mov r8,rbx
mov edx,IDM_WINDOW_NEXT
mov rcx,hMenu
call EnableMenuItem
mov r8,rbx
mov edx,IDM_WINDOW_PREVIOUS
mov rcx,hMenu
call EnableMenuItem
mov r8,rbx
mov edx,MI_CLOSE_ALL
mov rcx,hMenu
call EnableMenuItem
xor ebx,ebx
leave
retn
MdiChildProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #32: Multiple Document Interface (MDI)',0
MdiChildClassName db 'MDICHILD',0
MdiClientClassName db 'MDICLIENT',0
cc CLIENTCREATESTRUCT <0,2000>
hWnd dq ?
hClient dq ?
hMenu dq ?
rect RECT <>
AboutMsg db 'Mikl__ 2015',0
end
rc-file#define IDM_MENU 1000
#define IDM_FILE_EXIT 0
#define IDM_FILE_NEW 1
#define IDM_WINDOW_NEXT 2
#define IDM_WINDOW_PREVIOUS 3
#define MI_CLOSE 4
#define MI_TILEHOR 5
#define MI_TILEVER 6
#define MI_CASCADE 7
#define IDM_HELP_ABOUT 8
#define MI_CLOSE_ALL 9
IDM_MENU MENU DISCARDABLE
BEGIN
POPUP "&File"
BEGIN
MENUITEM "&New", IDM_FILE_NEW
MENUITEM "&Close\tCtrl+F4",MI_CLOSE,GRAYED
MENUITEM SEPARATOR
MENUITEM "&Exit",IDM_FILE_EXIT
END
POPUP "&Window"
BEGIN
MENUITEM "Tile Horizontal",MI_TILEHOR,GRAYED
MENUITEM "Tile Vertical",MI_TILEVER,GRAYED
MENUITEM "Cascade",MI_CASCADE,GRAYED
MENUITEM "&Next\tCtrl+F6",IDM_WINDOW_NEXT,GRAYED
MENUITEM "&Previous\tShift+Ctrl+F6",IDM_WINDOW_PREVIOUS,GRAYED
MENUITEM "&Close All",MI_CLOSE_ALL,GRAYED
END
POPUP "&Help"
BEGIN
MENUITEM "&About",IDM_HELP_ABOUT
END
END
-
Win64 Tutorial #14: Dynamic Link Libraries
makeDLL64.batcls
set masm64_path=\masm64\
set filename=tut_17a
if exist %filename%.dll del %filename%.dll
%masm64_path%bin\ml64.exe /c /Cp /I %masm64_path%include %filename%.asm || exit
%masm64_path%bin\Link.exe %filename%.obj /LIBPATH:%masm64_path%lib ^
/SUBSYSTEM:WINDOWS /ENTRY:DllMain /DLL /ALIGN:16 ^
/stub:%masm64_path%bin\stubby.exe /SECTION:.text,W /DEF:%filename%.def || exit
del %filename%.obj
del %filename%.exp
tut_17a.defLIBRARY tut_17a
EXPORTS DllMain
EXPORTS TestHello
tut_17a.asmOPTION DOTNAME
include temphls.inc
include win64.inc
include user32.inc
includelib user32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
.code
DllMain proc hInstDLL:QWORD, reason:QWORD, unused:QWORD
sub esp,28h
.if edx==DLL_PROCESS_ATTACH
lea rdx,LoadMsg
.elseif edx==DLL_PROCESS_DETACH
lea rdx,UnloadMsg
.endif
mov r9d,MB_OK
jmp exit
DllMain Endp
TestHello proc
sub esp,28h
lea rdx,HelloMsg
mov r9d,MB_OK + MB_ICONERROR
exit:: lea r8,AppName
xor ecx,ecx
call MessageBox
add esp,28h
mov eax,TRUE
ret
TestHello endp
AppName db "DLL Skeleton",0
HelloMsg db "Hello, you're calling a function in this DLL",0
LoadMsg db "The DLL is loaded",0
UnloadMsg db "The DLL is unloaded",0
end
operating system loads address of TestHello function from dll-file to import sectionOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
includelib tut_17a.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
TestHello PROTO
.code
WinMain proc
sub esp,28h
call [TestHello]
xor ecx,ecx
call ExitProcess
WinMain endp
end
use LoadLibrary to load a DLLOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
.code
WinMain proc
sub esp,28h
mov ecx,offset LibName
call LoadLibrary
or eax,eax;.if eax==NULL ;the dll not found
jnz @f
xor ecx,ecx
mov r9,rcx;MB_OK=0
mov r8d,offset AppName
mov edx,offset DllNotFound
call MessageBox
jmp exit;.else
@@: mov hLib,rax
mov edx,offset FunctionName
mov ecx,eax
call GetProcAddress
or eax,eax;.if eax==NULL ;requested function not found
jnz @f
xor ecx,ecx
mov r9,rcx;MB_OK = 0
mov r8d,offset AppName
mov edx,offset FunctionNotFound
call MessageBox
jmp @0
@@: call rax
@0: mov rcx,hLib
call FreeLibrary
exit: xor ecx,ecx
call ExitProcess
WinMain endp
LibName db "tut_17a.dll",0
FunctionName db "TestHello",0
DllNotFound db "Cannot load library",0
AppName db "Load Library",0
FunctionNotFound db "TestHello function not found",0
hLib dq ?
end
-
Win64 Tutorial #20: Window Subclassing
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov eax,10029h
mov esi,IMAGE_BASE
push rax ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
sub esp,20h
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 240
push 410
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
push rbx
push IMAGE_BASE
push rbx
push rax;hWnd
push 24
push 300
push 20
push 20
mov r9d,WS_CHILD + WS_VISIBLE + WS_BORDER
mov r8,rbx
mov edx,offset ctlClsNameEdit
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov edit1H,rax
mov ecx,eax
call SetFocus
mov r8d,offset edit1_procedure
mov edx,GWL_WNDPROC
mov rcx,edit1H
call SetWindowLongPtr
mov wndProcAddr,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
cmp edx,WM_DESTROY
je wmDESTROY
wmDEFAULT:jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
WndProc endp
edit1_procedure proc hWnd:HWND, uMsg:QWORD, wParam:WPARAM, lParam:LPARAM
push rbp
mov ebp,esp
sub esp,30h
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_KEYDOWN
je edit1_wmKEYDOWN
cmp edx,WM_CHAR
jne a1
edit1_wmCHAR: cmp r8b,VK_BACK ;compare with virtual key BACKSPACE
je a1
cmp r8b,30h ;compare with ascii 0
jb edit1_wmBYE
cmp r8b,39h ;compare with ascii 9
jbe a1
and r8b,-33 ;so our DL become big letter
cmp r8b,41h ;compare with ascii A
jb edit1_wmBYE
cmp r8b,46h ;compare with ascii F
ja edit1_wmBYE ;something else
a1: mov [esp+20h],r9;lParam
mov r9,r8;wParam
mov r8,rdx;uMsg
mov rdx,rcx;hWnd
mov rcx,wndProcAddr
call CallWindowProc
jmp edit1_wmBYE
edit1_wmKEYDOWN: cmp r8b,VK_RETURN ;compare with virtual key RETURN
jne a1
mov r9,rbx;MB_OK
mov r8d,offset ClassName
mov edx,offset edit1Txt1
call MessageBox
mov rcx,hWnd
invoke SetFocus
edit1_wmBYE:
leave
ret
edit1_procedure endp
ClassName db 'Win64 Iczelion''s lesson #20: Window Subclassing',0
ctlClsNameEdit db 'EDIT',0
edit1Txt1 db 'A simple HEX edit control!',0
wndProcAddr dq ?
edit1H dq ?
end
-
Thank you Mikl__ :t
I think I will need these examples in the future
-
mabdelouahab,
آمل أن تستخدموا هذه الأمثلة
-
Hi Mikl__,
do you plan a full set of Iczelion's tutorials for Windows 64-bit? That would be a lot of work. I've ordered web space today, so we could provide the entire material for download.
Gunther
-
Hi, Gunther!
Yes, I do. I plan a full set of Iczelion's tutorials for Windows 64-bit. You may send materials to my e-mail. Part of tutorials x64 is ready. Some of the material will have to finalize with the joint efforts. Comments in asm-files need to be reviewed or possibly write new comments.
-
Hi Mikl__,
Yes, I do. I plan a full set of Iczelion's tutorials for Windows 64-bit. You may send materials to my e-mail. Part of tutorials x64 is ready. Some of the material will have to finalize with the joint efforts. Comments in asm-files need to be reviewed or possibly write new comments.
that's fine. Let's send our contact data via PM, okay?
Gunther
-
Part 1-st
Win64 Tutorial #21: Pipe
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include gdi32.inc
includelib gdi32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
MI_CSCRIPT equ 100
IDC_MENU equ 30
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov eax,10027h
mov esi,IMAGE_BASE
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push IDC_MENU ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
sub rsp,20h
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 350
push 600
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
sub rsp,20h
call CreateWindowEx
push rbx
push IMAGE_BASE
push rbx
push rax
push 280
push 575
push rbx
push rbx
mov r9d,WS_CHILD + WS_VISIBLE + WS_HSCROLL + WS_VSCROLL + ES_MULTILINE + ES_AUTOHSCROLL + ES_AUTOVSCROLL
mov r8,rbx
mov edx,offset ctlClsNameEdit
mov ecx,WS_EX_CLIENTEDGE
sub rsp,20h
call CreateWindowEx
mov edit1H,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
;----------------------------------------
WndProc proc hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
local pipeReadH:QWORD
local pipeWriteH:QWORD
local pro1StartInfo:STARTUPINFO
local pro1Info:PROCESS_INFORMATION
local pipeRead:QWORD
local pipeBuffer[400h]:BYTE
push rbp
mov ebp,esp
sub esp,(48h+3*8+sizeof STARTUPINFO+sizeof PROCESS_INFORMATION+400h+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_CTLCOLOREDIT
je wmCTLCOLOREDIT
leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmSIZE: mov qword ptr [esp+28h],TRUE
mov rax,r9
movzx r9,ax
shr eax,16
mov [esp+20h],rax
mov r8,rbx
xor edx,edx
mov rcx,edit1H
call MoveWindow
jmp wmBYE
wmCTLCOLOREDIT:mov edx,0C9B5AFh
mov rcx,r8
call SetTextColor
xor edx,edx
mov rcx,wParam
call SetBkColor
mov ecx,BLACK_BRUSH
call GetStockObject
jmp wmBYE
wmCOMMAND:cmp r8,0FFFFh and MI_CSCRIPT
jne wmBYE
wmCOMMAND_MI_CSCRIPT:mov edi,offset pipeSecAttr
mov [rdi+SECURITY_ATTRIBUTES.nLength], sizeof SECURITY_ATTRIBUTES
mov [edi+SECURITY_ATTRIBUTES.lpSecurityDescriptor],rbx
mov [edi+SECURITY_ATTRIBUTES.bInheritHandle],TRUE
mov r9,rbx
mov r8,rdi
lea edx,pipeWriteH
lea ecx,pipeReadH
call CreatePipe
or eax,eax;NULL
je MI_CSCRIPT_error_pipe
lea edi,pro1StartInfo
mov [edi+STARTUPINFO.cb],sizeof STARTUPINFO
mov ecx,edi
call GetStartupInfo
mov rax,pipeWriteH
mov [rdi+STARTUPINFO.hStdOutput],rax
mov [rdi+STARTUPINFO.hStdError],rax
mov [rdi+STARTUPINFO.dwFlags],STARTF_USESHOWWINDOW + STARTF_USESTDHANDLES
mov [rdi+STARTUPINFO.wShowWindow],SW_HIDE
;+----------------+
;| create process |
;+----------------+
lea eax,pro1Info
mov [rsp+48h],rax
mov [rsp+40h],rdi
mov [rsp+38h],rbx
mov [rsp+30h],rbx
mov [rsp+28h],rbx
mov qword ptr [rsp+20h],TRUE
mov r9,rbx
mov r8,rbx
mov edx,offset pro1CmdLine
xor ecx,ecx
call CreateProcess
or eax,eax;cmp eax,NULL
je MI_CSCRIPT_error_process
@@: mov rcx,pipeWriteH
call CloseHandle
cmp eax,TRUE
jne @b
mov edx,400h
lea ecx,pipeBuffer
call RtlZeroMemory
mov [rsp+20h],rbx
lea r9,pipeRead
mov r8d,1023
lea edx,pipeBuffer
mov rcx,pipeReadH
call ReadFile
or eax,eax;cmp eax,NULL
je @f
mov r8,rbx
mov r8,-1
mov edx,EM_SETSEL
mov rcx,edit1H
call SendMessage
lea r9,pipeBuffer
mov r8,rbx
mov edx,EM_REPLACESEL
mov rcx,edit1H
call SendMessage
jmp @f
MI_CSCRIPT_error_pipe:mov r9,rbx;MB_OK
mov r8d,offset ClassName
mov edx,offset errStr1
mov rcx,hWnd
call MessageBox
jmp wmBYE
MI_CSCRIPT_error_process:mov r9,rbx;MB_OK
mov r8d,offset ClassName
mov edx,offset errStr2
mov rcx,hWnd
call MessageBox
@@: mov rcx,pipeReadH
call CloseHandle
mov rcx,pro1Info.hProcess
call CloseHandle
mov rcx,pro1Info.hThread
call CloseHandle
wmBYE: leave
retn
WndProc endp
;-----------------------------------------
ClassName db 'Win64 Iczelion''s lesson #21: Pipe',0
ctlClsNameEdit db 'EDIT',0
edit1H dq ?
pipeSecAttr SECURITY_ATTRIBUTES <>
errStr1 db 'Error - Pipe Creation Failed!',0
errStr2 db 'Error - Process Creation Failed!',0
pro1CmdLine db 'ml64 /Cp msgbox.asm /link /subsystem:windows /entry:WinMain',0
end
rc-file#define MI_CSCRIPT 100
#define IDC_MENU 30
IDC_MENU MENU
{
POPUP "&Action"
{ MENUITEM "&Assemble",MI_CSCRIPT
}
}
-
Part 2-nd
the contents of two zip-files need to be unpacked in the same folder
(Restrictions of masm32.forum: 4 zip-files per post, maximum total size 512KB, maximum individual size 512KB)
-
Win64 Tutorial #22: Superclassing Demo
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,(sizeof MSG+15)and(-16)
xor ebx,ebx
mov eax,10029h
mov esi,IMAGE_BASE
push rax ;hIconSm
mov edi,offset ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
sub esp,20h
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 240
push 410
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local editCls:WNDCLASSEX
push rbp
mov ebp,esp
sub esp,(20h+sizeof WNDCLASSEX+15)and(-16)
mov hWnd,rcx
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_DESTROY
je wmDESTROY
wmDEFAULT:leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmCREATE:lea edi,editCls
mov dword ptr [edi+WNDCLASSEX.cbSize],sizeof WNDCLASSEX
mov esi,offset ctlClsNameEdit+3;ClsName="EDIT"
mov r8,rdi
mov edx,esi
xor ecx,ecx
call GetClassInfoEx
sub esi,3
mov rax,[rdi+WNDCLASSEX.lpfnWndProc]
mov wndProcAddr,rax
mov dword ptr [rdi+WNDCLASSEX.lpfnWndProc],offset edit1_procedure
mov dword ptr [rdi+WNDCLASSEX.hInstance],IMAGE_BASE
mov [rdi+WNDCLASSEX.lpszClassName],rsi;OFFSET ctlClsNameEdit ClsName="HEXEDIT"
mov ecx,edi
call RegisterClassEx
mov ebx,5
mov edi,20
@@: push 0;rbx
push IMAGE_BASE
push rbx
push hWnd
push 24
push 300
push rdi
push 20
mov r9d,WS_CHILD + WS_VISIBLE + WS_BORDER
mov r8,0;rbx
mov edx,esi ;offset ctlClsNameEdit
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov [edit1H+8*rbx],rax
mov r9d,0 ;limit to 15 chars
mov r8d,15
mov edx,EM_LIMITTEXT
mov ecx,eax
call SendMessage
add edi,30
dec ebx
jns @b
inc ebx
mov rcx,[edit1H+8*5]
call SetFocus
wmBYE: leave
retn
WndProc endp
edit1_procedure proc hWnd:HWND, uMsg:QWORD, wParam:WPARAM, lParam:LPARAM
push rbp
mov ebp,esp
sub esp,30h
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_KEYDOWN
je edit1_wmKEYDOWN
cmp edx,WM_CHAR
jne @f
edit1_wmCHAR: cmp r8b,VK_BACK ;compare with virtual key BACKSPACE
je @f
cmp r8b,30h ;compare with ascii 0
jb edit1_wmBYE
cmp r8b,39h ;compare with ascii 9
jbe @f
and r8b,-33 ;so our DL become big letter
cmp r8b,41h ;compare with ascii A
jb edit1_wmBYE
cmp r8b,46h ;compare with ascii F
ja edit1_wmBYE ;something else
@@: mov [esp+20h],r9;lParam
mov r9,r8;wParam
mov r8,rdx;uMsg
mov rdx,rcx;hWnd
mov rcx,wndProcAddr
call CallWindowProc
jmp edit1_wmBYE
edit1_wmKEYDOWN: cmp r8b,VK_RETURN ;compare with virtual key RETURN
je wmKEYDOWN_VK_RETURN
cmp r8b,VK_TAB
jne @b
;-----------------------------------------------------
wmKEYDOWN_VK_TAB:mov ecx,VK_SHIFT
call GetKeyState
or eax,eax;test eax,0x80000000
js VK_TAB_PREV;jne VK_TAB_PREV
VK_TAB_NEXT:mov edx,GW_HWNDNEXT;=2
mov rcx,hWnd
call GetWindow
or eax,eax
jne VK_TAB_BYE
xor edx,edx;GW_HWNDFIRST=0
jmp @f
VK_TAB_PREV:mov edx,GW_HWNDPREV;=3
mov rcx,hWnd
call GetWindow
test eax,eax
jne VK_TAB_BYE
mov edx,GW_HWNDLAST;=1
@@: mov rcx,hWnd
call GetWindow
VK_TAB_BYE:mov ecx,eax
jmp @f
wmKEYDOWN_VK_RETURN:
mov r9,rbx;MB_OK
mov r8d,offset ClassName
mov edx,offset edit1Txt1
call MessageBox
mov rcx,hWnd
@@: invoke SetFocus
edit1_wmBYE:
leave
ret
edit1_procedure endp
ClassName db 'Win64 Iczelion''s lesson #22: Superclassing Demo',0
ctlClsNameEdit db 'HEXEDIT',0
edit1Txt1 db 'A simple HEX edit control!',0
wndProcAddr dq ?
edit1H dq 6 dup(?)
end
-
Win64 Tutorial #26: Splash Screen
makedll64.batcls
set masm64_path=\masm64\
set filename=tut_26a
if exist %filename%.dll del %filename%.dll
%masm64_path%bin\RC /r %filename%.rc || exit
%masm64_path%bin\ml64.exe /c /Cp /I %masm64_path%include %filename%.asm || exit
%masm64_path%bin\Link.exe %filename%.obj %filename%.res /LIBPATH:%masm64_path%lib ^
/SUBSYSTEM:WINDOWS /ENTRY:DllEntry /DLL /ALIGN:16 /section:.bss,S ^
/stub:%masm64_path%bin\stubby.exe /DEF:%filename%.def || exit
del %filename%.obj
del %filename%.exp
del %filename%.res
tut_26a.asmOPTION DOTNAME
option casemap:none
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include gdi32.inc
includelib gdi32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
.data
BitmapName db "MySplashBMP",0
ClassName db "SplashWndClass",0
hBitMap dq ?
TimerID dq ?
hInstance dq ?
.code
DllEntry proc hInst:QWORD, reason:QWORD, reserved1:QWORD
sub esp,28h
cmp edx,DLL_PROCESS_ATTACH ; When the dll is loaded
jnz @f
mov hInstance,rcx
call ShowBitMap
@@: add esp,28h
mov eax,TRUE
retn
DllEntry Endp
ShowBitMap proc
LOCAL msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
push 10029h ;hIconSm
lea rdi,ClassName
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW+1;hbrBackground
push 10005h ;hCursor
push 10029h ;hIcon
push hInstance
push rbx ;cbClsExtra & cbWndExtra
lea rax,WndProc
push rax ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
sub esp,20h
call RegisterClassEx
push rbx
push hInstance
push rbx
push rbx
push 250
push 250
push CW_USEDEFAULT
push CW_USEDEFAULT
mov r9d,WS_POPUP or WS_VISIBLE
mov r8,rbx
mov edx,edi
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
or eax,eax
jz @f
mov ecx,edi
call DispatchMessage
jmp @b
@@: leave
retn
ShowBitMap endp
WndProc proc hWnd:QWORD,uMsg:QWORD,wParam:QWORD,lParam:QWORD
LOCAL ps:PAINTSTRUCT
LOCAL hMemoryDC:HDC
LOCAL hOldBmp:QWORD
LOCAL bitmap:BITMAP
LOCAL DlgHeight:QWORD
LOCAL DlgWidth:QWORD
LOCAL DlgRect:RECT
LOCAL DesktopRect:RECT
push rbp
mov ebp,esp
sub esp,(20h+sizeof PAINTSTRUCT+sizeof BITMAP+2*(sizeof RECT)+4*32+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_TIMER
je wmTIMER
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_LBUTTONDOWN
je wmLBUTTONDOWN
leave
jmp DefWindowProc
wmDESTROY:mov rcx,hBitMap
jrcxz @f;.if hBitMap!=0
call DeleteObject
@@: xor ecx,ecx
call PostQuitMessage
jmp wmBYE
wmCREATE:lea rdx,DlgRect
call GetWindowRect
call GetDesktopWindow
mov ecx,eax
lea rdx,DesktopRect
call GetWindowRect
push rbx ;Part of the later call to MoveWindow (no repaint)
mov eax,DlgRect.bottom ;Get the bottom of our dialogs window
sub eax,DlgRect.top ;subtract the y value at the top of our window
mov DlgHeight,rax ;And store it as the dialog's height
push rax ;Push it for the call to MoveWindow
mov r9d,DlgRect.right ;The X coordinate of the right side of our dialog
sub r9d,DlgRect.left ;minus that of the left side
mov DlgWidth,r9 ;gives us the width
mov r8d,DesktopRect.bottom ;Get the bottom of the desktop window
sub r8,DlgHeight ;Subtract the height of our dialog
shr r8,1 ;and divide by 2...this gives the middle of the screen
mov edx,DesktopRect.right ;Get the right side of the desktop
sub rdx,DlgWidth ;Minus the width of our dialog
shr edx,1 ;Divide by 2
mov rcx,hWnd ;Push the window handle
sub esp,20h
call MoveWindow ;Move the window
lea edx,BitmapName
mov rcx,hInstance
call LoadBitmap
mov hBitMap,rax
mov r9,rbx
mov r8d,2000
mov edx,1
mov rcx,hWnd
call SetTimer
mov TimerID,rax
jmp wmBYE
wmTIMER:mov r9,rbx
mov r8,rbx
mov edx,WM_LBUTTONDOWN
mov rcx,hWnd
call SendMessage
mov rdx,TimerID
mov rcx,hWnd
call KillTimer
jmp wmBYE
wmPAINT:lea edx,ps
call BeginPaint
mov ecx,eax
call CreateCompatibleDC
mov hMemoryDC,rax
mov rdx,hBitMap
mov ecx,eax
call SelectObject
mov hOldBmp,rax
lea r8,bitmap
mov edx,sizeof BITMAP
mov rcx,hBitMap
call GetObject
push SRCCOPY
mov eax,bitmap.bmHeight
push rax
mov eax,bitmap.bmWidth
push rax
push rbx
push rbx
push hMemoryDC
push 250
mov r9d,250
mov r8,rbx
xor edx,edx
mov rcx,ps.hdc
sub esp,20h
call StretchBlt
mov rdx,hOldBmp
mov rcx,hMemoryDC
call SelectObject
mov rcx,hMemoryDC
call DeleteDC
lea edx,ps
mov rcx,hWnd
call EndPaint
jmp wmBYE
wmLBUTTONDOWN:call DestroyWindow
wmBYE: leave
retn
WndProc endp
end
tut_26a.defLIBRARY tut_26a.dll
tut_26a.rcMySplashBMP BITMAP "Images\\JourneyStart.bmp"
tut_26b.asmOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
.code
WinMain proc
local msg:MSG
push rbp
mov ecx,offset libName
call LoadLibrary
or eax,eax
je @f
mov ecx,eax
call FreeLibrary
@@: mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov eax,10029h
mov edi,offset ClassName
mov esi,IMAGE_BASE
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
sub esp,20h
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 240
push 400
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
cmp edx,WM_DESTROY
je wmDESTROY
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #26: Splash Screen',0
libName db 'tut_26A.dll',0
end
-
Win64 Tutorial #24: Mouse Hook Demo
makeDLL64.batcls
set masm64_path=\masm64\
set filename=tut_24a
if exist %filename%.dll del %filename%.dll
%masm64_path%bin\ml64.exe /c /Cp /I %masm64_path%include %filename%.asm || exit
%masm64_path%bin\Link.exe %filename%.obj /LIBPATH:%masm64_path%lib ^
/SUBSYSTEM:WINDOWS /ENTRY:DllEntry /DLL /section:.bss,S ^
/stub:%masm64_path%bin\stubby.exe /DEF:%filename%.def || exit
del %filename%.obj
del %filename%.exp
tut_24a.asmOPTION DOTNAME
include temphls.inc
include win64.inc
include user32.inc
includelib user32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
WM_MOUSEHOOK equ WM_USER+6
MOUSEHOOKSTRUCT STRUCT
pt POINT <>
hwnd QWORD ?
wHitTestCode QWORD ?
dwExtraInfo QWORD ?
MOUSEHOOKSTRUCT ENDS
.data?
hInstance dq ?
hHook dq ?
hWnd dq ?
.code
DllEntry proc hInstDLL:QWORD, reason:QWORD, unused:QWORD
mov hInstance,rcx
mov eax,TRUE
ret
DllEntry Endp
MouseProc proc nCode:QWORD,wParam:QWORD,lParam:QWORD
push rbp
mov ebp,esp
sub rsp,20h
mov lParam,r8
mov r9,r8;lParam
mov r8,rdx;wParam
mov edx,ecx;nCode
mov rcx,hHook
call CallNextHookEx
mov rax,lParam
mov rcx,[rax]
call WindowFromPoint
mov rcx,hWnd
mov edx,WM_MOUSEHOOK
mov r8,rax
mov r9d,0
call PostMessage;,hWnd,WM_MOUSEHOOK,eax,0
xor eax,eax
leave
ret
MouseProc endp
InstallHook proc hwnd:QWORD
push rbp
mov ebp,esp
sub esp,20h
mov hWnd,rcx
mov ecx,WH_MOUSE
mov rdx,offset MouseProc
mov r8,hInstance
mov r9d,0
call SetWindowsHookEx;,WH_MOUSE,addr MouseProc,hInstance,NULL
mov hHook,rax
leave
ret
InstallHook endp
UninstallHook proc
push rbp
mov ebp,esp
sub esp,20h
mov rcx,hHook
call UnhookWindowsHookEx
leave
ret
UninstallHook endp
end
tut_24a.defLIBRARY tut_24a
EXPORTS
MouseProc
InstallHook
UninstallHook
asm2.batcls
set masm64_path=\masm64\
set filename=tut_24b
if exist %filename%.exe del %filename%.exe
%masm64_path%bin\RC /r %filename%.rc || exit
%masm64_path%bin\ml64 /Cp /c /I"%masm64_path%Include" %filename%.asm || exit
%masm64_path%bin\link /SUBSYSTEM:WINDOWS /LIBPATH:"%masm64_path%Lib" ^
/entry:WinMain %filename%.obj %filename%.res /LARGEADDRESSAWARE:NO ^
/ALIGN:16 /SECTION:.text,W ^
/BASE:0x400000 /STUB:%masm64_path%bin\stubby.exe || exit
del %filename%.res
del %filename%.obj
tut_24b.asmOPTION DOTNAME
include temphls.inc
include win64.inc
include mymacros.asm
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
includelib tut_24a.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IDD_MAINDLG equ 101
IDC_CLASSNAME equ 1000
IDC_HANDLE equ 1001
IDC_WNDPROC equ 1002
IDC_HOOK equ 1004
IDC_EXIT equ 1005
WM_MOUSEHOOK equ WM_USER+6
IMAGE_BASE equ 400000h
InstallHook proto :QWORD
UninstallHook proto
MouseProc proto :QWORD,:QWORD,:QWORD
DlgFunc proto :QWORD,:QWORD,:QWORD,:QWORD
.data
HookFlag dq FALSE
HookText db "&Hook",0
UnhookText db "&Unhook",0
template db "%lx",0
hHook dq ?
.code
WinMain proc
sub esp,38h
xor ebx,ebx
mov [rsp+20h],rbx
mov r9d,offset DlgFunc
mov r8,rbx
mov edx,IDD_MAINDLG
mov ecx,IMAGE_BASE
call DialogBoxParam;,hInstance,IDD_MAINDLG,NULL,addr DlgFunc,NULL
xor ecx,ecx
call ExitProcess
WinMain endp
DlgFunc proc hDlg:QWORD,uMsg:QWORD,wParam:QWORD,lParam:QWORD
LOCAL hLib:QWORD
LOCAL buffer[128]:byte
LOCAL buffer1[128]:byte
LOCAL rect:RECT
push rbp
mov ebp,esp
sub esp,(38h+8+2*128+sizeof RECT+15)and(-16)
mov hDlg,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_MOUSEHOOK
je wmMOUSEHOOK
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
xor eax,eax;FALSE
leave
retn
wmCLOSE:cmp HookFlag,TRUE
jnz @f
call UninstallHook
@@: xor edx,edx
mov rcx,hDlg
call EndDialog
jmp wmBYE
wmINITDIALOG:lea edi,rect
mov edx,edi
mov rcx,hDlg
call GetWindowRect
mov qword ptr [rsp+30h],SWP_SHOWWINDOW
mov eax,[rdi+RECT.bottom]
mov [rsp+28h],rax
mov eax,[rdi+RECT.right]
mov [rsp+20h],rax
mov r9d,[rdi+RECT.top]
mov r8d,[rdi+RECT.left]
or edx,HWND_TOPMOST
mov rcx,hDlg
call SetWindowPos
jmp wmBYE
wmMOUSEHOOK:mov r9d,128
lea r8,buffer1
mov edx,IDC_HANDLE
;mov rcx,hDlg
call GetDlgItemText
mov r8,wParam
mov edx,offset template
lea ecx,buffer
call wsprintf
lea edx,buffer1
lea ecx,buffer
call lstrcmpi
or eax,eax;.if eax!=0
jz @f
lea r8,buffer
mov edx,IDC_HANDLE
mov rcx,hDlg
call SetDlgItemText
@@: mov r9d,128
lea r8,buffer1
mov edx,IDC_CLASSNAME
mov rcx,hDlg
call GetDlgItemText
mov r8d,128
lea edx,buffer
mov rcx,wParam
call GetClassName
lea edx,buffer1
lea ecx,buffer
call lstrcmpi
or eax,eax;.if eax!=0
jz @f
lea r8,buffer
mov edx,IDC_CLASSNAME
mov rcx,hDlg
call SetDlgItemText
@@: mov r9d,128
lea r8,buffer1
mov edx,IDC_WNDPROC
mov rcx,hDlg
call GetDlgItemText
mov edx,GCL_WNDPROC
mov rcx,wParam
call GetClassLong
mov r8,rax
mov edx,offset template
lea ecx,buffer
call wsprintf
lea edx,buffer1
lea ecx,buffer
call lstrcmpi
or eax,eax;.if eax!=0
jz wmBYE
lea r8,buffer
mov edx,IDC_WNDPROC
mov rcx,hDlg
call SetDlgItemText
jmp wmBYE
wmCOMMAND:cmp r9,rbx;cmp lParam,rbx;.if lParam!=0
jz wmBYE
mov rax,r8;wParam
mov edx,eax
shr edx,16
or edx,edx;.if dx==BN_CLICKED
jnz wmBYE
and eax,0FFFFh
cmp eax,IDC_EXIT
jnz @f
mov r9,rbx
mov r8,rbx
mov edx,WM_CLOSE
mov rcx,hDlg
call SendMessage
jmp wmBYE
@@: cmp HookFlag,rbx;FALSE
jnz @f
mov rcx,hDlg
call InstallHook
or eax,eax; .if eax!=NULL
jz wmBYE
mov HookFlag,TRUE
mov r8d,offset UnhookText
mov edx,IDC_HOOK
mov rcx,hDlg
call SetDlgItemText
jmp wmBYE
@@: call UninstallHook
mov r8d,offset HookText
mov edx,IDC_HOOK
mov rcx,hDlg
call SetDlgItemText
mov HookFlag,rbx;FALSE
mov r8,rbx
mov edx,IDC_CLASSNAME
mov rcx,hDlg
call SetDlgItemText
mov r8,rbx
mov edx,IDC_HANDLE
mov rcx,hDlg
call SetDlgItemText
mov r8,rbx
mov edx,IDC_WNDPROC
mov rcx,hDlg
call SetDlgItemText
wmBYE: leave
mov eax,TRUE
retn
DlgFunc endp
end
tut_24b.rc#define IDD_MAINDLG 101
#define IDC_CLASSNAME 1000
#define IDC_HANDLE 1001
#define IDC_WNDPROC 1002
#define IDC_HOOK 1004
#define IDC_EXIT 1005
#define IDC_STATIC -1
#define DS_MODALFRAME 0x80
#define WS_POPUP 0x80000000
#define WS_CAPTION 0xC00000
#define WS_SYSMENU 0x80000
#define ES_AUTOHSCROLL 0x80
#define ES_READONLY 0x800
IDD_MAINDLG DIALOG DISCARDABLE 0, 0, 229, 85
STYLE DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Iczelion Tutorial #24: Mouse Hook Demo"
FONT 8, "MS Sans Serif"
BEGIN
GROUPBOX "Window Information",IDC_STATIC,7,7,214,67
LTEXT "Class name:",IDC_STATIC,21,22,39,8
EDITTEXT IDC_CLASSNAME,69,20,139,12,ES_AUTOHSCROLL | ES_READONLY
LTEXT "Handle:",IDC_STATIC,33,37,26,8
EDITTEXT IDC_HANDLE,69,36,77,12,ES_AUTOHSCROLL | ES_READONLY
LTEXT "Window Proc:",IDC_STATIC,13,52,46,8
EDITTEXT IDC_WNDPROC,69,51,77,12,ES_AUTOHSCROLL | ES_READONLY
DEFPUSHBUTTON "&Hook",IDC_HOOK,159,35,50,14
PUSHBUTTON "E&xit",IDC_EXIT,159,50,50,14
END
-
Win64 Tutorial #31a: ListView Control
asm-fileinclude win64a.inc
IMAGE_BASE equ 400000h
IDM_MAINMENU equ 10000
IDM_ICON equ LVS_ICON
IDM_SMALLICON equ LVS_SMALLICON
IDM_LIST equ LVS_LIST
IDM_REPORT equ LVS_REPORT
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
call InitCommonControls
mov eax,10029h
mov esi,IMAGE_BASE
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push IDM_MAINMENU;lpszMenuName
push COLOR_WINDOW+1;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 400
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
push rbx;<-- align 10h
push IMAGE_BASE
push rbx;NULL
push rax;hWnd
push 240
push 400
push rbx;0
push rbx;0
mov r9d,LVS_REPORT+WS_CHILD+WS_VISIBLE
mov r8,rbx;NULL
mov edx,offset ListViewClassName
xor ecx,ecx;NULL
sub esp,20h
call CreateWindowEx
mov hList,rax
call InsertColumn
call lv_col_info_fill
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
InsertColumn proc
LOCAL lvc:LV_COLUMN
push rbp
mov ebp,esp
sub esp,(20h+sizeof LV_COLUMN+15)and(-16)
lea r9,lvc
mov [r9+LV_COLUMN.imask],LVCF_TEXT+LVCF_WIDTH
mov eax,offset Heading1
mov [r9+LV_COLUMN.pszText],rax
mov [r9+LV_COLUMN.lx],150
mov r8,rbx;0
mov edx,LVM_INSERTCOLUMN
mov rcx,hList
call SendMessage
lea r9,lvc
mov eax,offset Heading2
mov [r9+LV_COLUMN.pszText],rax
mov [r9+LV_COLUMN.lx],100
mov r8d,1
mov edx,LVM_INSERTCOLUMN
mov rcx,hList
call SendMessage
leave
retn
InsertColumn endp
lv_col_info_fill proc
LOCAL lvItem:LV_ITEM
local old_rdi:QWORD
push rbp
mov ebp,esp
sub esp,(28h+sizeof LV_ITEM+15)and(-16)
mov old_rdi,rdi
xor edi,edi
@@: mov lvItem.imask,LVIF_TEXT + LVIF_PARAM
mov rax,[handle+rdi*8]
mov lvItem.pszText,rax
mov lvItem.iSubItem,0
mov lvItem.iItem,edi
mov lvItem.lParam,edi
lea r9,lvItem
mov r8d,0
mov edx,LVM_INSERTITEM
mov rcx,hList
call SendMessage
mov lvItem.imask,LVIF_TEXT
inc lvItem.iSubItem
mov rax,[handle+rdi*8+8*5]
mov lvItem.pszText,rax
lea r9,lvItem
mov r8d,0
mov edx,LVM_SETITEM
mov rcx,hList
call SendMessage
inc edi
cmp edi,5
jb @b
@0: mov rdi,old_rdi
leave
retn
lv_col_info_fill endp
;------------------------------------------------
lv_param_update proc
LOCAL lvi:LV_ITEM
local old_rdi:QWORD
push rbp
mov ebp,esp
sub esp,(28h+sizeof LV_ITEM+15)and(-16)
mov old_rdi,rdi
mov r9,rbx
mov r8,rbx
mov edx, LVM_GETITEMCOUNT
mov rcx,hList
call SendMessage
mov edi,eax
mov lvi.imask,LVIF_PARAM
mov lvi.iSubItem,0
mov lvi.iItem,0
@@: lea r9,lvi
mov eax,lvi.iItem
mov lvi.lParam,eax
mov r8,rbx;0
mov edx, LVM_SETITEM
mov rcx,hList
call SendMessage
inc lvi.iItem
dec edi
jnz @b;.endw
mov rdi,old_rdi
leave
retn
lv_param_update endp
;------------------------------------------------
lv_compare proc lParam1:QWORD,lParam2:QWORD,lParamSort:QWORD
local buf1[100h]:BYTE
local buf2[100h]:BYTE
local lvi0:LV_ITEM
local old_rdi:QWORD
local old_rsi:QWORD
push rbp
mov ebp,esp
sub esp,(30h+sizeof LV_ITEM+200h+15)and(-16)
mov lParam2,rdx
mov lParamSort,r8
mov lvi0.imask,LVIF_TEXT
lea eax,buf1
mov lvi0.pszText,rax
mov lvi0.cchTextMax,100h
test r8b,00000010b;[lParamSort],1;2
jnz compare_3
compare_1:mov old_rdi,rdi
mov old_rsi,rsi
mov lvi0.iSubItem,1
lea r9,lvi0
mov r8,rcx;[lParam1]
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea esi,buf1
call convert_strhval
mov edi,eax
lea r9,lvi0
mov r8,lParam2
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea esi,buf1
call convert_strhval
test lParamSort,1
jne @f
xchg edi,eax
@@: sub eax,edi
compare_1_exit: mov rdi,old_rdi
mov rsi,old_rsi
leave
retn
compare_3:mov lvi0.iSubItem,0
lea r9,lvi0
mov r8,rcx;[lParam1]
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea ecx,buf2 ;destination
lea edx,buf1 ;source
call lstrcpy
lea r9,lvi0
mov r8,lParam2
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea edx,buf2
lea ecx,buf1
test lParamSort,1
jne @f
xchg edx,ecx
@@: call lstrcmpi
leave
retn
lv_compare endp
;---------------------------------------
convert_strhval proc
push rbp
mov ebp,esp
sub esp,20h
mov ecx,esi
call lstrlen
mov ecx,eax
jrcxz b
xor eax,eax
cdq
@@: imul edx,10
lodsb
lea edx,[rdx+rax-'0']
loop @b
mov eax,edx
b: leave
ret
convert_strhval endp
;----------------------------------------
WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
push rbp
mov ebp,esp
sub esp,30h
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_NOTIFY
je wmNOTIFY
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_DESTROY
je wmDESTROY
wmDEFAULT:leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmNOTIFY:mov rdi,r9;[lParam]
mov rax,[rdi + NMHDR.hwndFrom]
cmp rax,hList
jne wmDEFAULT
cmp [rdi + NMHDR._code],LVN_COLUMNCLICK
jne wmDEFAULT
wmNOTIFY_LVN_COLUMNCLICK:
cmp [rdi + NM_LISTVIEW.iSubItem+4],1
jne COLUMNCLICK_FILE
COLUMNCLICK_SIZE:xor lvSortSize,1
mov r8d,lvSortSize
jmp @f
COLUMNCLICK_FILE:xor lvSortFile,1
mov r8d,lvSortFile
@@: mov r9d,lv_compare
mov edx,LVM_SORTITEMS
mov rcx,hList
call SendMessage
call lv_param_update
jmp wmBYE
wmSIZE: mov eax,r9d;lParam
and r9,0FFFFh
shr eax,16
mov qword ptr [rsp+28h],TRUE
mov [rsp+20h],rax
xor edx,edx
mov r8,rdx
mov rcx,hList
call MoveWindow
wmBYE: leave
ret
WndProc endp
;-------------------------------------------------------------
ClassName db 'Win64 Iczelion''s lesson #31a: ListView Control',0
ListViewClassName db 'SysListView32',0
Heading1 db 'Filename',0
Heading2 db 'Size',0
hList dq ?
hMenu dq ?
lvSortSize dd 0
lvSortFile dd 2
lvI1a db 'Durian',0
lvI1b db '34',0
lvI2a db 'Banana',0
lvI2b db '54',0
lvI3a db 'Watermelon',0
lvI3b db '44',0
lvI4a db 'Apple',0
lvI4b db '55',0
lvI5a db 'Papaya',0
lvI5b db '1',0
handle dq lvI1a,lvI2a,lvI3a,lvI4a,lvI5a,lvI1b,lvI2b,lvI3b,lvI4b,lvI5b
end
rc-file#include "resource.h"
#define IDM_MAINMENU 10000
#define IDM_ICON LVS_ICON
#define IDM_SMALLICON LVS_SMALLICON
#define IDM_LIST LVS_LIST
#define IDM_REPORT LVS_REPORT
IDM_MAINMENU MENU
{
POPUP "&View"
{
MENUITEM "&Icon View",IDM_ICON
MENUITEM "&Small Icon View",IDM_SMALLICON
MENUITEM "&List View", IDM_LIST
MENUITEM "&Report View",IDM_REPORT
}
}
-
Hi Mikl,
You are doing a great job - sometimes I regret that I don't find the time to test coding in 64 bits... :t
-
Ciao, jj2007 !
Sono molto contento... (http://www.cyberforum.ru/images/smilies/yes.gif)
-
Hi Micha,
excellent work, молодец. :t
Gunther
-
Win x64 Tutorial #33: IczEdit version 1.0
rc-file#include "resource.h"
#define IDR_MAINMENU 101
#define IDD_OPTIONDLG 101
#define IDC_BACKCOLORBOX 1000
#define IDC_TEXTCOLORBOX 1001
#define IDC_OK 1002
#define IDC_CANCEL 1003
#define IDM_OPEN 40001
#define IDM_SAVE 40002
#define IDM_CLOSE 40003
#define IDM_SAVEAS 40004
#define IDM_EXIT 40005
#define IDM_COPY 40006
#define IDM_CUT 40007
#define IDM_PASTE 40008
#define IDM_DELETE 40009
#define IDM_SELECTALL 40010
#define IDM_OPTION 40011
#define IDM_UNDO 40012
#define IDM_REDO 40013
IDR_MAINMENU MENU DISCARDABLE
BEGIN
POPUP "&File"
BEGIN
MENUITEM "&Open", IDM_OPEN
MENUITEM "&Close", IDM_CLOSE
MENUITEM "&Save", IDM_SAVE
MENUITEM "Save &As", IDM_SAVEAS
MENUITEM SEPARATOR
MENUITEM "E&xit", IDM_EXIT
END
POPUP "&Edit"
BEGIN
MENUITEM "&Undo", IDM_UNDO
MENUITEM "&Redo", IDM_REDO
MENUITEM "&Copy", IDM_COPY
MENUITEM "C&ut", IDM_CUT
MENUITEM "&Paste", IDM_PASTE
MENUITEM SEPARATOR
MENUITEM "&Delete", IDM_DELETE
MENUITEM SEPARATOR
MENUITEM "Select &All", IDM_SELECTALL
END
MENUITEM "Options", IDM_OPTION
END
IDD_OPTIONDLG DIALOG DISCARDABLE 0, 0, 183, 54
STYLE DS_MODALFRAME | DS_CENTER | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
CAPTION "Options"
FONT 8, "MS Sans Serif"
BEGIN
DEFPUSHBUTTON "OK",IDC_OK,137,7,39,14
PUSHBUTTON "Cancel",IDC_CANCEL,137,25,39,14
GROUPBOX "",IDC_STATIC,5,0,124,49
LTEXT "Background Color:",IDC_STATIC,20,14,60,8
LTEXT "",IDC_BACKCOLORBOX,85,11,28,14,SS_NOTIFY | WS_BORDER
LTEXT "Text Color:",IDC_STATIC,20,33,35,8
LTEXT "",IDC_TEXTCOLORBOX,85,29,28,14,SS_NOTIFY | WS_BORDER
END
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include user32.inc
include comdlg32.inc
include gdi32.inc
include kernel32.inc
includelib gdi32.lib
includelib comdlg32.lib
includelib user32.lib
includelib kernel32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
IDR_MAINMENU equ 101
IDM_OPEN equ 40001
IDM_SAVE equ 40002
IDM_CLOSE equ 40003
IDM_SAVEAS equ 40004
IDM_EXIT equ 40005
IDM_COPY equ 40006
IDM_CUT equ 40007
IDM_PASTE equ 40008
IDM_DELETE equ 40009
IDM_SELECTALL equ 40010
IDM_OPTION equ 40011
IDM_UNDO equ 40012
IDM_REDO equ 40013
IDD_OPTIONDLG equ 101
IDC_BACKCOLORBOX equ 1000
IDC_TEXTCOLORBOX equ 1001
IDC_OK equ 1002
IDC_CANCEL equ 1003
RichEditID equ 300
.code
WinMain proc
LOCAL msg:MSG
local hwnd:QWORD
push rbp
mov ebp,esp
sub esp,(sizeof MSG+8+15)and(-16)
mov ecx,offset RichEditDLL
call LoadLibrary
or eax,eax
jnz @f
mov r9d,MB_OK or MB_ICONERROR
mov r8d,offset ClassName
mov edx,offset NoRichEdit
xor ecx,ecx
call MessageBox
xor ecx,ecx
call ExitProcess
@@: mov hRichEdit,rax
xor ebx,ebx
mov esi,IMAGE_BASE
mov eax,10029h
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW+1;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
sub esp,20h
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hwnd,rax
mov edx,offset rect
mov ecx,eax
call GetClientRect
push rbx;0
push IMAGE_BASE
push RichEditID
push hwnd
mov eax,rect.bottom
push rax
mov eax,rect.right
push rax
push rbx
push rbx
mov r9d,WS_CHILD or WS_VISIBLE or ES_MULTILINE or WS_VSCROLL or WS_HSCROLL or ES_NOHIDESEL
mov r8,rbx;0
mov edx,offset RichEditClass
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov hwndRichEdit,rax
mov r9,rbx
or r8,-1
mov edx,EM_LIMITTEXT
mov rcx,hwndRichEdit
call SendMessage
call SetColor
mov r9,rbx
mov r8,rbx;FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov r9,rbx
mov r8,rbx
mov edx,EM_EMPTYUNDOBUFFER
mov rcx,hwndRichEdit
call SendMessage
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
;-----------------------------------------------------------
StreamInProc proc hFile:QWORD,pBuffer:QWORD, NumBytes:QWORD, pBytesRead:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov qword ptr [esp+20h],0
call ReadFile;,hFile,pBuffer,NumBytes,pBytesRead,0
xor eax,1
leave
retn
StreamInProc endp
;---------------------------------------------------------
StreamOutProc proc hFile:QWORD,pBuffer:QWORD, NumBytes:QWORD, pBytesWritten:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov qword ptr [esp+20h],0
call WriteFile;,hFile,pBuffer,NumBytes,pBytesWritten,0
xor eax,1
leave
retn
StreamOutProc endp
;----------------------------------------------------------
CheckModifyState proc hWnd:QWORD
push rbp
mov ebp,esp
sub esp,20h
mov hWnd,rcx
xor r9d,r9d
mov r8d,r9d
mov edx,EM_GETMODIFY
mov rcx,hwndRichEdit
call SendMessage
or eax,eax;.if eax!=0
jz wmBYE
mov r9d,MB_YESNOCANCEL
mov r8d,offset ClassName
mov edx,offset WannaSave
mov rcx,hWnd
call MessageBox
cmp eax,IDYES;.if eax==IDYES
jnz @f
xor r9d,r9d
mov r8d,IDM_SAVE
mov edx,WM_COMMAND
mov rcx,hWnd
call SendMessage
jmp wmBYE
@@: cmp eax,IDCANCEL;.elseif eax==IDCANCEL
jnz wmBYE
xor eax,eax;mov eax,FALSE
jmp @f
wmBYE: mov eax,TRUE
@@: leave
ret
CheckModifyState endp
;--------------------------------------------------------------
SetColor proc
LOCAL cfm1:CHARFORMAT
push rbp
mov ebp,esp
sub esp,(20h+sizeof CHARFORMAT+15)and(-16)
;Установка цвета фона richedit контрола
mov r9d,BackgroundColor
xor r8,r8;rbx
mov edx,EM_SETBKGNDCOLOR
mov rcx,hwndRichEdit
call SendMessage
;заполняем члены структуры CHARFORMAT, чтобы установить цвет текста
mov edx,sizeof CHARFORMAT
lea ecx,cfm1
call RtlZeroMemory
lea r9,cfm1
mov [r9+CHARFORMAT.cbSize],sizeof CHARFORMAT
mov [r9+CHARFORMAT.dwMask],CFM_COLOR
mov eax,TextColor
mov [r9+CHARFORMAT.crTextColor],eax
mov r8d,SCF_ALL
mov edx,EM_SETCHARFORMAT
mov rcx,hwndRichEdit
call SendMessage
leave
retn
SetColor endp
OptionProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL clr:CHOOSECOLOR
local temp:QWORD
push rbp
mov ebp,esp
sub esp,(28h+sizeof CHOOSECOLOR+15)and(-16)
mov hWnd,rcx
;mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmBYE
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CTLCOLORSTATIC
je wmCTLCOLORSTATIC
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
ret
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
sub eax,IDC_BACKCOLORBOX
cmp eax,IDC_CANCEL-IDC_BACKCOLORBOX
ja wmBYE
jmp handle[rax*8]
CANCEL: xor r9d,r9d;0
mov r8d,r9d
mov edx,WM_CLOSE
;mov rcx,hWnd
call SendMessage
jmp wmBYE
BACKCOLORBOX:
mov edx,sizeof clr
lea ecx,clr
call RtlZeroMemory
mov eax,BackgroundColor
lea ecx,clr
mov [rcx+CHOOSECOLOR.rgbResult],eax
mov [rcx+CHOOSECOLOR.lStructSize],sizeof clr
mov rax,hWnd
mov [rcx+CHOOSECOLOR.hwndOwner],rax
mov [rcx+CHOOSECOLOR.hInstance],IMAGE_BASE
mov eax,offset CustomColors
mov [rcx+CHOOSECOLOR.lpCustColors],rax
mov [rcx+CHOOSECOLOR.Flags],CC_ANYCOLOR or CC_RGBINIT
call ChooseColor
or eax,eax;.if eax!=0
jz wmBYE
mov eax,clr.rgbResult
mov BackgroundColor,eax
mov edx,IDC_BACKCOLORBOX
jmp @f
TEXTCOLORBOX:
mov edx,sizeof clr
lea ecx,clr
call RtlZeroMemory
mov eax,TextColor
lea ecx,clr
mov [rcx+CHOOSECOLOR.rgbResult],eax
mov [rcx+CHOOSECOLOR.lStructSize],sizeof clr
mov rax,hWnd
mov [rcx+CHOOSECOLOR.hwndOwner],rax
mov [rcx+CHOOSECOLOR.hInstance],IMAGE_BASE
mov eax,offset CustomColors
mov [rcx+CHOOSECOLOR.lpCustColors],rax
mov [rcx+CHOOSECOLOR.Flags],CC_ANYCOLOR or CC_RGBINIT
call ChooseColor
or eax,eax;.if eax!=0
jz wmBYE
mov eax,clr.rgbResult
mov TextColor,eax
mov edx,IDC_TEXTCOLORBOX
@@: mov rcx,hWnd
call GetDlgItem
mov r8d,TRUE
xor edx,edx
mov ecx,eax
call InvalidateRect
jmp wmBYE
OK: xor r9d,r9d
mov r8d,r9d
mov edx,EM_GETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov temp,rax
call SetColor
mov r8,temp
xor r9d,r9d
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
xor edx,edx
mov rcx,hWnd
call EndDialog
jmp wmBYE
wmCTLCOLORSTATIC:mov edx,IDC_BACKCOLORBOX
call GetDlgItem
cmp rax,lParam;.if eax==lParam
jnz @f
mov ecx,BackgroundColor
jmp @0
@@: mov edx,IDC_TEXTCOLORBOX
mov rcx,hWnd
call GetDlgItem
cmp rax,lParam;.if eax==lParam
jnz wmDEFAULT
mov ecx,TextColor
@0: call CreateSolidBrush
jmp @f
wmCLOSE:xor edx,edx
call EndDialog
wmBYE: mov eax,TRUE
@@: leave
retn
handle dq BACKCOLORBOX,TEXTCOLORBOX,OK,CANCEL
OptionProc endp
WndProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL chrg:CHARRANGE
LOCAL ofn:OPENFILENAME
LOCAL buffer[256]:BYTE
LOCAL editstream:EDITSTREAM
LOCAL hFile:QWORD
push rbp
mov ebp,esp
sub esp,(40h+sizeof EDITSTREAM+sizeof OPENFILENAME+\
sizeof CHARRANGE+8+256+15)and(-16)
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITMENUPOPUP
je wmINITMENUPOPUP
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_DESTROY
je wmDESTROY
wmDEFAULT:leave
jmp DefWindowProc
wmDESTROY:mov rcx,hRichEdit
call FreeLibrary
xor ecx,ecx
call ExitProcess
wmINITMENUPOPUP:
mov eax,r9d;lParam
or ax,ax;.if ax==0 ; file menu
jnz @f
cmp FileOpened,TRUE;.if FileOpened==TRUE ; a file is already opened
setne bl;в ebx MF_ENABLED=0 или MF_GRAYED=1
mov r8d,ebx;MF_ENABLED
mov edx,IDM_CLOSE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_SAVE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_SAVEAS
mov rcx,wParam
call EnableMenuItem
xor ebx,1
mov r8d,ebx;MF_GRAYED
mov edx,IDM_OPEN
mov rcx,wParam
call EnableMenuItem
xor ebx,ebx
jmp wmBYE
@@: cmp ax,1;.elseif ax==1 ; edit menu
jnz wmBYE
xor r9d,r9d
mov r8d,CF_TEXT
mov edx,EM_CANPASTE
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; .if eax==0 ; no text in the clipboard
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_PASTE
mov rcx,wParam
call EnableMenuItem
xor r9d,r9d
mov r8d,r9d
mov edx,EM_CANUNDO
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; .if eax==0
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_UNDO
mov rcx,wParam
call EnableMenuItem
xor r9d,r9d
mov r8d,r9d
mov edx,EM_CANREDO
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; .if eax==0
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_REDO
mov rcx,wParam
call EnableMenuItem
lea r9,chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov eax,chrg.cpMin
cmp eax,chrg.cpMax
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_COPY
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_CUT
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_DELETE
mov rcx,wParam
call EnableMenuItem
xor ebx,ebx
jmp wmBYE
wmCOMMAND:or r9,r9;.if lParam==0 ; menu commands
jnz wmBYE
movzx eax,r8w;mov eax,wParam
sub eax,IDM_OPEN;.if ax==IDM_OPEN
cmp eax,IDM_REDO-IDM_OPEN
ja wmBYE
jmp handle1[rax*8]
OPEN: mov edx,sizeof ofn
lea ecx,ofn
call RtlZeroMemory
lea ecx,ofn
mov [rcx+OPENFILENAME.lStructSize],sizeof ofn
mov rax,hWnd
mov [rcx+OPENFILENAME.hwndOwner],rax
mov [rcx+OPENFILENAME.hInstance],IMAGE_BASE
mov eax,offset ASMFilterString
mov [rcx+OPENFILENAME.lpstrFilter],rax
mov eax,offset FileName
mov [rcx+OPENFILENAME.lpstrFile],rax
mov byte ptr [FileName],0
mov [rcx+OPENFILENAME.nMaxFile],sizeof FileName
mov [rcx+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_HIDEREADONLY or OFN_PATHMUSTEXIST
call GetOpenFileName
or eax,eax; .if eax!=0
jz wmBYE
mov qword ptr [rsp+30h],0
mov qword ptr [rsp+28h],FILE_ATTRIBUTE_NORMAL
mov qword ptr [rsp+20h],OPEN_EXISTING
mov r9d,NULL
mov r8d,FILE_SHARE_READ
mov edx,GENERIC_READ
mov ecx,offset FileName
call CreateFile
inc eax;.if eax!=INVALID_HANDLE_VALUE
jz @f
dec eax
mov hFile,rax
lea r9,editstream
mov [r9+EDITSTREAM.dwCookie],rax
mov eax,offset StreamInProc
mov [r9+EDITSTREAM.pfnCallback],rax
mov r8d,SF_TEXT
mov edx,EM_STREAMIN
mov rcx,hwndRichEdit
call SendMessage
xor r9d,r9d
mov r8d,FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov rcx,hFile
call CloseHandle
mov FileOpened,TRUE
jmp wmBYE
@@: mov r9d,MB_OK or MB_ICONERROR
mov r8d,offset ClassName
mov edx,offset OpenFileFail
mov rcx,hWnd
call MessageBox
jmp wmBYE
CLOSE1: mov rcx,hWnd
call CheckModifyState
or eax,eax
jz wmBYE
xor edx,edx
mov rcx,hwndRichEdit
call SetWindowText
mov FileOpened,FALSE
jmp wmBYE
SAVE: mov ecx,offset FileName
jmp @f
SAVEAS: mov edx,sizeof ofn
lea ecx,ofn
call RtlZeroMemory
lea ecx,ofn
mov [rcx+OPENFILENAME.lStructSize],sizeof ofn
mov rax,hWnd
mov [rcx+OPENFILENAME.hwndOwner],rax
mov [rcx+OPENFILENAME.hInstance],IMAGE_BASE
mov eax,offset ASMFilterString
mov [rcx+OPENFILENAME.lpstrFilter],rax
mov eax,offset AlternateFileName
mov [rcx+OPENFILENAME.lpstrFile],rax
mov byte ptr [AlternateFileName],0
mov [rcx+OPENFILENAME.nMaxFile],sizeof AlternateFileName
mov [rcx+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_HIDEREADONLY or OFN_PATHMUSTEXIST
call GetSaveFileName
or eax,eax;.if eax!=0
jz wmBYE
mov ecx,offset AlternateFileName
@@: mov qword ptr [rsp+30h],0
mov qword ptr [rsp+28h],FILE_ATTRIBUTE_NORMAL
mov qword ptr [rsp+20h],CREATE_ALWAYS
mov r9d,NULL
mov r8d,FILE_SHARE_READ
mov edx,GENERIC_WRITE
call CreateFile
inc eax;.if eax!=INVALID_HANDLE_VALUE
jz wmBYE
dec eax
mov hFile,rax
lea r9,editstream
mov [r9+EDITSTREAM.dwCookie],rax
mov eax,offset StreamOutProc
mov [r9+EDITSTREAM.pfnCallback],rax
mov r8d,SF_TEXT
mov edx,EM_STREAMOUT
mov rcx,hwndRichEdit
call SendMessage
xor r9d,r9d
mov r8d,FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov rcx,hFile
call CloseHandle
jmp wmBYE
COPY: mov edx,WM_COPY
jmp @19
CUT: mov edx,WM_CUT
jmp @19
PASTE: mov edx,WM_PASTE
jmp @19
DELETE1:xor r9d,r9d
mov r8d,TRUE
mov edx,EM_REPLACESEL
jmp @21
SELECTALL:
mov chrg.cpMin,0
mov chrg.cpMax,-1
lea r9,chrg
mov edx,EM_EXSETSEL
jmp @20
UNDO: mov edx,EM_UNDO
jmp @19
REDO: mov edx,EM_REDO
@19: xor r9d,r9d
@20: xor r8d,r8d
@21: mov rcx,hwndRichEdit
jmp @f
EXIT: mov edx,WM_CLOSE
xor r9d,r9d
mov r8d,r9d
mov rcx,hWnd
@@: call SendMessage
jmp wmBYE
OPTIONS:mov qword ptr [rsp+20h],0
mov r9d,offset OptionProc
mov r8,hWnd
mov edx,IDD_OPTIONDLG
mov ecx,IMAGE_BASE
call DialogBoxParam
jmp wmBYE
wmCLOSE:;mov rcx,hWnd
call CheckModifyState
or eax,eax; .if eax==TRUE
jz wmBYE
mov rcx,hWnd
call DestroyWindow
jmp wmBYE
wmSIZE: mov eax,r9d;lParam
and r9,0FFFFh
shr eax,16
mov qword ptr [rsp+28h],TRUE
mov [rsp+20h],rax
xor edx,edx
mov r8,rdx
mov rcx,hwndRichEdit
call MoveWindow
wmBYE: leave
ret
handle1 dq OPEN,SAVE,CLOSE1,SAVEAS,EXIT,COPY,CUT,PASTE,DELETE1
dq SELECTALL,OPTIONS,UNDO,REDO
WndProc endp
;----------------------------------------------------------------
ClassName db 'IczEdit version 1.0',0
RichEditDLL db "riched20.dll",0
RichEditClass db "RichEdit20A",0
NoRichEdit db "Cannot find riched20.dll",0
ASMFilterString db "ASM Source code (*.asm)",0,"*.asm",0
db "All Files (*.*)",0,"*.*",0,0
OpenFileFail db "Cannot open the file",0
WannaSave db "The data in the control is modified. Want to save it?",0
FileOpened dq FALSE
BackgroundColor dd 0FFFFFFh; default to white
TextColor dd 0 ; default to black
hRichEdit dq ?
hwndRichEdit dq ?
FileName db 256 dup(?)
AlternateFileName db 256 dup(?)
CustomColors dd 16 dup(?)
rect RECT <?>
end
-
Win x64 Tutorial #34: IczEdit version 2.0
due to limitations of forum message should not contain more than 20,000 characters
we divide the text into two parts
rc-file#include "resource.h"
#define IDC_NEXT 1003
#define IDR_MAINMENU 101
#define IDD_OPTIONDLG 101
#define IDD_FINDDLG 102
#define IDD_GOTODLG 103
#define IDD_REPLACEDLG 104
#define IDR_MAINACCEL 105
#define IDC_BACKCOLORBOX 1000
#define IDC_TEXTCOLORBOX 1001
#define IDC_OK 1002
#define IDC_CANCEL 1003
#define IDC_FINDEDIT 1000
#define IDC_MATCHCASE 1001
#define IDC_REPLACEEDIT 1001
#define IDC_WHOLEWORD 1002
#define IDC_DOWN 1003
#define IDC_UP 1004
#define IDC_LINENO 1005
#define IDM_OPEN 40001
#define IDM_SAVE 40002
#define IDM_CLOSE 40003
#define IDM_SAVEAS 40004
#define IDM_EXIT 40005
#define IDM_COPY 40006
#define IDM_CUT 40007
#define IDM_PASTE 40008
#define IDM_DELETE 40009
#define IDM_SELECTALL 40010
#define IDM_OPTION 40011
#define IDM_UNDO 40012
#define IDM_REDO 40013
#define IDM_FIND 40014
#define IDM_FINDNEXT 40015
#define IDM_REPLACE 40016
#define IDM_GOTOLINE 40017
#define IDM_FINDPREV 40018
IDR_MAINMENU MENU DISCARDABLE
BEGIN
POPUP "&File"
BEGIN
MENUITEM "&Open", IDM_OPEN
MENUITEM "&Close", IDM_CLOSE
MENUITEM "&Save", IDM_SAVE
MENUITEM "Save &As", IDM_SAVEAS
MENUITEM SEPARATOR
MENUITEM "E&xit", IDM_EXIT
END
POPUP "&Edit"
BEGIN
MENUITEM "&Undo", IDM_UNDO
MENUITEM "&Redo", IDM_REDO
MENUITEM "&Copy", IDM_COPY
MENUITEM "C&ut", IDM_CUT
MENUITEM "&Paste", IDM_PASTE
MENUITEM SEPARATOR
MENUITEM "&Delete", IDM_DELETE
MENUITEM SEPARATOR
MENUITEM "Select &All", IDM_SELECTALL
END
POPUP "&Search"
BEGIN
MENUITEM "&Find...\tCtrl+F", IDM_FIND
MENUITEM "Find &Next\tF3", IDM_FINDNEXT
MENUITEM "Find &Prev.\tCtrl+F3", IDM_FINDPREV
MENUITEM "&Replace..\tCtrl+R", IDM_REPLACE
MENUITEM SEPARATOR
MENUITEM "&Go To Line\tCtrl+G", IDM_GOTOLINE
END
MENUITEM "Options", IDM_OPTION
END
IDD_OPTIONDLG DIALOG DISCARDABLE 0, 0, 183, 54
STYLE DS_MODALFRAME | DS_CENTER | WS_POPUP | WS_VISIBLE | WS_CAPTION |
WS_SYSMENU
CAPTION "Options"
FONT 8, "MS Sans Serif"
BEGIN
DEFPUSHBUTTON "OK",IDC_OK,137,7,39,14
PUSHBUTTON "Cancel",IDC_CANCEL,137,25,39,14
GROUPBOX "",IDC_STATIC,5,0,124,49
LTEXT "Background Color:",IDC_STATIC,20,14,60,8
LTEXT "",IDC_BACKCOLORBOX,85,11,28,14,SS_NOTIFY | WS_BORDER
LTEXT "Text Color:",IDC_STATIC,20,33,35,8
LTEXT "",IDC_TEXTCOLORBOX,85,29,28,14,SS_NOTIFY | WS_BORDER
END
IDD_FINDDLG DIALOG DISCARDABLE 0, 0, 186, 54
STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
CAPTION "Find.."
FONT 8, "MS Sans Serif"
BEGIN
EDITTEXT IDC_FINDEDIT,42,3,94,12,ES_AUTOHSCROLL
CONTROL "Match Case",IDC_MATCHCASE,"Button",BS_AUTOCHECKBOX |
WS_TABSTOP,6,24,54,10
CONTROL "Whole Word",IDC_WHOLEWORD,"Button",BS_AUTOCHECKBOX |
WS_TABSTOP,6,37,56,10
CONTROL "Down",IDC_DOWN,"Button",BS_AUTORADIOBUTTON | WS_TABSTOP,
83,27,35,10
CONTROL "Up",IDC_UP,"Button",BS_AUTORADIOBUTTON | WS_TABSTOP,83,
38,25,10
DEFPUSHBUTTON "OK",IDC_OK,141,3,39,12
PUSHBUTTON "Cancel",IDC_CANCEL,141,18,39,12
LTEXT "Find what:",IDC_STATIC,5,4,34,8
GROUPBOX "Direction",IDC_STATIC,70,18,64,32
END
IDD_GOTODLG DIALOGEX 0, 0, 106, 30
STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
EXSTYLE WS_EX_TOOLWINDOW
CAPTION "Go To Line"
FONT 8, "MS Sans Serif", 0, 0, 0x1
BEGIN
EDITTEXT IDC_LINENO,29,4,35,11,ES_AUTOHSCROLL | ES_NUMBER,
WS_EX_CLIENTEDGE
DEFPUSHBUTTON "OK",IDC_OK,70,4,31,11
PUSHBUTTON "Cancel",IDC_CANCEL,70,17,31,11
LTEXT "Line :",IDC_STATIC,8,5,18,8
END
IDD_REPLACEDLG DIALOG DISCARDABLE 0, 0, 186, 33
STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
CAPTION "Replace"
FONT 8, "MS Sans Serif"
BEGIN
EDITTEXT IDC_FINDEDIT,51,3,84,12,ES_AUTOHSCROLL
EDITTEXT IDC_REPLACEEDIT,51,17,84,11,ES_AUTOHSCROLL
DEFPUSHBUTTON "OK",IDC_OK,142,3,39,11
PUSHBUTTON "Cancel",IDC_CANCEL,142,17,39,11
LTEXT "Find what:",IDC_STATIC,3,4,34,8
LTEXT "Replace with",IDC_STATIC,3,18,42,8
END
IDR_MAINACCEL ACCELERATORS DISCARDABLE
BEGIN
"F", IDM_FIND, VIRTKEY, CONTROL, NOINVERT
"G", IDM_GOTOLINE, VIRTKEY, CONTROL, NOINVERT
"R", IDM_REPLACE, VIRTKEY, CONTROL, NOINVERT
VK_F3, IDM_FINDNEXT, VIRTKEY, NOINVERT
VK_F3, IDM_FINDPREV, VIRTKEY, CONTROL, NOINVERT
END
asm-file (part first)OPTION DOTNAME
include temphls.inc
include win64.inc
include user32.inc
include comdlg32.inc
include gdi32.inc
include kernel32.inc
includelib gdi32.lib
includelib comdlg32.lib
includelib user32.lib
includelib kernel32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
IDR_MAINMENU equ 101
IDM_OPEN equ 40001
IDM_SAVE equ 40002
IDM_CLOSE equ 40003
IDM_SAVEAS equ 40004
IDM_EXIT equ 40005
IDM_COPY equ 40006
IDM_CUT equ 40007
IDM_PASTE equ 40008
IDM_DELETE equ 40009
IDM_SELECTALL equ 40010
IDM_OPTION equ 40011
IDM_UNDO equ 40012
IDM_REDO equ 40013
IDM_FIND equ 40014
IDM_FINDNEXT equ 40015
IDM_REPLACE equ 40016
IDM_GOTOLINE equ 40017
IDM_FINDPREV equ 40018
IDD_OPTIONDLG equ 101
IDD_FINDDLG equ 102
IDD_GOTODLG equ 103
IDD_REPLACEDLG equ 104
IDR_MAINACCEL equ 105
IDC_BACKCOLORBOX equ 1000
IDC_TEXTCOLORBOX equ 1001
IDC_OK equ 1002
IDC_CANCEL equ 1003
IDC_FINDEDIT equ 1000
IDC_MATCHCASE equ 1001
IDC_REPLACEEDIT equ 1001
IDC_WHOLEWORD equ 1002
IDC_DOWN equ 1003
IDC_UP equ 1004
IDC_LINENO equ 1005
RichEditID equ 300
.code
WinMain proc
LOCAL msg:MSG
local hwnd:QWORD
push rbp
mov ebp,esp
sub esp,(sizeof MSG+8+15)and(-16)
mov ecx,offset RichEditDLL
call LoadLibrary
or eax,eax
jnz @f
mov r9d,MB_OK or MB_ICONERROR
mov r8d,offset AppName
mov edx,offset NoRichEdit
xor ecx,ecx
call MessageBox
xor ecx,ecx
call ExitProcess
@@: mov hRichEdit,rax
mov byte ptr [FindBuffer],0
mov byte ptr [ReplaceBuffer],0
xor ebx,ebx
mov esi,IMAGE_BASE
mov eax,10029h
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW+1;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
sub esp,20h
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hwnd,rax
mov edx,offset rect
mov ecx,eax
call GetClientRect
push rbx;0
push IMAGE_BASE
push RichEditID
push hwnd
mov eax,rect.bottom
push rax
mov eax,rect.right
push rax
push rbx
push rbx
mov r9d,WS_CHILD or WS_VISIBLE or ES_MULTILINE or WS_VSCROLL or WS_HSCROLL or ES_NOHIDESEL
mov r8d,ebx;0
mov edx,offset RichEditClass
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov hwndRichEdit,rax
mov r9,rbx;0
or r8,-1
mov edx,EM_LIMITTEXT
mov rcx,hwndRichEdit
call SendMessage
call SetColor
mov r9,rbx;0
mov r8,rbx;FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
; mov r9d,ENM_MOUSEEVENTS
; xor r8d,r8d
; mov edx,EM_SETEVENTMASK
; mov rcx,hwndRichEdit
; call SendMessage
mov r9,rbx;0
mov r8,rbx;0
mov edx,EM_EMPTYUNDOBUFFER
mov rcx,hwndRichEdit
call SendMessage
mov ecx,IDR_MAINACCEL
mov edx,IMAGE_BASE
call LoadAccelerators
mov hAccel,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov edx,edi
mov rcx,hSearch
call IsDialogMessage
or eax,eax;.if eax==FALSE
jnz @b
mov r8,rdi
mov rdx,hAccel
mov rcx,hwnd
call TranslateAccelerator
or eax,eax;.if eax==0
jnz @b
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
StreamInProc proc hFile:QWORD,pBuffer:QWORD, NumBytes:QWORD, pBytesRead:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov qword ptr [esp+20h],0
call ReadFile;,hFile,pBuffer,NumBytes,pBytesRead,0
xor eax,1
leave
retn
StreamInProc endp
StreamOutProc proc hFile:QWORD,pBuffer:QWORD, NumBytes:QWORD, pBytesWritten:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov qword ptr [esp+20h],0
call WriteFile;,hFile,pBuffer,NumBytes,pBytesWritten,0
xor eax,1
leave
retn
StreamOutProc endp
CheckModifyState proc hWnd:QWORD
push rbp
mov ebp,esp
sub esp,20h
mov hWnd,rcx
xor r9d,r9d
xor r8d,r8d
mov edx,EM_GETMODIFY
mov rcx,hwndRichEdit
call SendMessage
or eax,eax;.if eax!=0
jz wmBYE
mov r9d,MB_YESNOCANCEL
mov r8d,offset AppName
mov edx,offset WannaSave
mov rcx,hWnd
call MessageBox
cmp eax,IDYES;.if eax==IDYES
jnz @f
xor r9d,r9d
mov r8d,IDM_SAVE
mov edx,WM_COMMAND
mov rcx,hWnd
call SendMessage
jmp wmBYE
@@: cmp eax,IDCANCEL;.elseif eax==IDCANCEL
jnz wmBYE
xor eax,eax;mov eax,FALSE
jmp @f
wmBYE: mov eax,TRUE
@@: leave
ret
CheckModifyState endp
SetColor proc
local cfm:CHARFORMAT
push rbp
mov ebp,esp
sub esp,(20h+sizeof CHARFORMAT+15)and(-16)
mov r9d,BackgroundColor
xor r8d,r8d
mov edx,EM_SETBKGNDCOLOR
mov rcx,hwndRichEdit
call SendMessage
mov edx,sizeof CHARFORMAT
lea ecx,cfm
call RtlZeroMemory
lea r9d,cfm
mov [r9+CHARFORMAT.cbSize],sizeof CHARFORMAT
mov [r9+CHARFORMAT.dwMask],CFM_COLOR
mov eax,TextColor
mov [r9+CHARFORMAT.crTextColor],eax
mov r8d,SCF_ALL
mov edx,EM_SETCHARFORMAT
mov rcx,hwndRichEdit
call SendMessage
leave
retn
SetColor endp
OptionProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL clr:CHOOSECOLOR
local temp:QWORD
push rbp
mov ebp,esp
sub esp,(28h+sizeof CHOOSECOLOR+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmBYE
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CTLCOLORSTATIC
je wmCTLCOLORSTATIC
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
ret
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
sub eax,IDC_BACKCOLORBOX
cmp eax,IDC_CANCEL-IDC_BACKCOLORBOX
ja wmBYE
jmp handle[rax*8]
CANCEL: xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
call SendMessage
jmp wmBYE
BACKCOLORBOX:
mov edx,sizeof clr
lea ecx,clr
call RtlZeroMemory
lea ecx,clr
mov [rcx+CHOOSECOLOR.lStructSize],sizeof clr
mov rax,hWnd
mov [rcx+CHOOSECOLOR.hwndOwner],rax
mov [rcx+CHOOSECOLOR.hInstance],IMAGE_BASE
mov eax,BackgroundColor
mov [rcx+CHOOSECOLOR.rgbResult],eax
mov eax,offset CustomColors
mov [rcx+CHOOSECOLOR.lpCustColors],rax
mov [rcx+CHOOSECOLOR.Flags],CC_ANYCOLOR or CC_RGBINIT
call ChooseColor
or eax,eax;.if eax!=0
jz wmBYE
mov eax,clr.rgbResult
mov BackgroundColor,eax
mov edx,IDC_BACKCOLORBOX
jmp @f
TEXTCOLORBOX:
mov edx,sizeof clr
lea ecx,clr
call RtlZeroMemory
lea ecx,clr
mov [rcx+CHOOSECOLOR.lStructSize],sizeof clr
mov rax,hWnd
mov [rcx+CHOOSECOLOR.hwndOwner],rax
mov [rcx+CHOOSECOLOR.hInstance],IMAGE_BASE
mov eax,TextColor
mov [rcx+CHOOSECOLOR.rgbResult],eax
mov eax,offset CustomColors
mov [rcx+CHOOSECOLOR.lpCustColors],rax
mov [rcx+CHOOSECOLOR.Flags],CC_ANYCOLOR or CC_RGBINIT
call ChooseColor
or eax,eax;.if eax!=0
jz wmBYE
mov eax,clr.rgbResult
mov TextColor,eax
mov edx,IDC_TEXTCOLORBOX
@@: mov rcx,hWnd
call GetDlgItem
mov r8d,TRUE
xor edx,edx
mov ecx,eax
call InvalidateRect
jmp wmBYE
OK: xor r9d,r9d
xor r8d,r8d
mov edx,EM_GETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov temp,rax
call SetColor
mov r8,temp
xor r9d,r9d
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
xor edx,edx
mov rcx,hWnd
call EndDialog
jmp wmBYE
wmCTLCOLORSTATIC:mov edx,IDC_BACKCOLORBOX
call GetDlgItem
cmp rax,lParam;.if eax==lParam
jnz @f
mov ecx,BackgroundColor
jmp @0
@@: mov edx,IDC_TEXTCOLORBOX
mov rcx,hWnd
call GetDlgItem
cmp rax,lParam;.if eax==lParam
jnz wmDEFAULT
mov ecx,TextColor
@0: call CreateSolidBrush
jmp @1
wmCLOSE:xor edx,edx
mov rcx,hWnd
call EndDialog
wmBYE: mov eax,TRUE
@1: leave
retn
handle dq BACKCOLORBOX,TEXTCOLORBOX,OK,CANCEL
OptionProc endp
to be continue
-
Win x64 Tutorial #34: IczEdit version 2.0
asm-file (part second)SearchProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
ret
wmINITDIALOG:mov hSearch,rcx;hWnd
;===================================================
; Select the default search down option
;===================================================
mov r9d,IDC_DOWN
mov r8d,IDC_UP
mov edx,IDC_DOWN
;mov rcx,hWnd
call CheckRadioButton
mov eax,offset FindBuffer
mov [rsp+20h],rax
xor r9d,r9d
mov r8d,WM_SETTEXT
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call SendDlgItemMessage
jmp wmBYE
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
sub eax,IDC_OK
cmp eax,IDC_CANCEL-IDC_OK
ja wmBYE
jmp handle3[rax*8]
OK3: mov uFlags,0
mov r9d,offset findtext.chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov r9d,sizeof FindBuffer
mov r8d,offset FindBuffer
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call GetDlgItemText
or eax,eax;.if eax!=0
jz wmBYE
mov edx,IDC_DOWN
mov rcx,hWnd
call IsDlgButtonChecked
cmp eax,BST_CHECKED
jnz @10
or uFlags,FR_DOWN
mov eax,findtext.chrg.cpMin
cmp eax,findtext.chrg.cpMax
jz @f
mov eax,findtext.chrg.cpMax
mov findtext.chrg.cpMin,eax
@@: mov findtext.chrg.cpMax,-1
jmp @f
@10: mov findtext.chrg.cpMax,0
@@: mov edx,IDC_MATCHCASE
mov rcx,hWnd
call IsDlgButtonChecked
cmp eax,BST_CHECKED
jnz @f
or uFlags,FR_MATCHCASE
@@: mov edx,IDC_WHOLEWORD
mov rcx,hWnd
call IsDlgButtonChecked
cmp eax,BST_CHECKED
jnz @f
or uFlags,FR_WHOLEWORD
@@: mov eax,offset FindBuffer
mov findtext.lpstrText,rax
mov r9d,offset findtext
mov r8d,uFlags
mov edx,EM_FINDTEXTEX
mov rcx,hwndRichEdit
call SendMessage
inc eax;.if eax!=-1
jz wmBYE
mov r9d,offset findtext.chrgText
xor r8d,r8d
mov edx,EM_EXSETSEL
mov rcx,hwndRichEdit
call SendMessage
jmp wmBYE
CANCEL3:xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
mov rcx,hWnd
call SendMessage
jmp wmBYE
wmCLOSE:xor edx,edx
mov hSearch,rdx
;mov rcx,hWnd
call EndDialog
wmBYE: mov eax,TRUE
leave
ret
handle3 dq OK3,CANCEL3
SearchProc endp
;-------------------------------------
ReplaceProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL settext:SETTEXTEX
push rbp
mov ebp,esp
sub esp,(20h+sizeof SETTEXTEX+15)and(-16)
mov hWnd,rcx
;mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
retn
wmINITDIALOG:mov hSearch,rcx;hWnd
mov r8d,offset FindBuffer
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call SetDlgItemText
mov r8d,offset ReplaceBuffer
mov edx,IDC_REPLACEEDIT
mov rcx,hWnd
call SetDlgItemText
jmp wmBYE
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
sub eax,IDC_OK
cmp eax,IDC_CANCEL-IDC_OK
ja wmBYE
jmp handle2[rax*8]
CANCEL: xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
mov rcx,hWnd
call SendMessage
jmp wmBYE
OK: mov r9d,sizeof FindBuffer
mov r8d,offset FindBuffer
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call GetDlgItemText
mov r9d,sizeof ReplaceBuffer
mov r8d,offset ReplaceBuffer
mov edx,IDC_REPLACEEDIT
mov rcx,hWnd
call GetDlgItemText
mov findtext.chrg.cpMin,0
mov findtext.chrg.cpMax,-1
mov eax,offset FindBuffer
mov findtext.lpstrText,rax
mov settext.flags,ST_SELECTION
mov settext.codepage,CP_ACP
@@: mov r9d,offset findtext
mov r8d,FR_DOWN
mov edx,EM_FINDTEXTEX
mov rcx,hwndRichEdit
call SendMessage
inc eax;.if eax==-1
jz wmBYE;.break
mov r9d,offset findtext.chrgText
xor r8d,r8d
mov edx,EM_EXSETSEL
mov rcx,hwndRichEdit
call SendMessage
mov r9d,offset ReplaceBuffer
lea r8,settext
mov edx,EM_SETTEXTEX
mov rcx,hwndRichEdit
call SendMessage
jmp @b
wmCLOSE:xor edx,edx
mov hSearch,rdx
;mov rcx,hWnd
call EndDialog
wmBYE: mov eax,TRUE
leave
retn
handle2 dq OK,CANCEL
ReplaceProc endp
;---------------------------------------------
GoToProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL LineNo:QWORD
LOCAL chrg:CHARRANGE
push rbp
mov ebp,esp
sub esp,(28h+sizeof CHARRANGE+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_COMMAND
je wmCOMMAND
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
retn
wmINITDIALOG:mov hSearch,rcx;hWnd
jmp wmBYE
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
cmp ax,IDCANCEL
jnz @f
xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
call SendMessage
jmp wmBYE
@@: cmp ax,IDOK
jnz wmBYE
;Когда пользователь набирает номер строки и нажимает кнопку 'Ok',
;начинаем операцию
xor r9d,r9d;FALSE
xor r8d,r8d
mov edx,IDC_LINENO
mov rcx,hWnd
call GetDlgItemInt
mov LineNo,rax
;Получаем номер строки из edit control'а
xor r9d,r9d
xor r8d,r8d
mov edx,EM_GETLINECOUNT
mov rcx,hwndRichEdit
invoke SendMessage
cmp rax,LineNo
jbe wmBYE
;Получаем количество строк в контроле. Проверяем, не указал ли
;пользователь номер строки, который выходит за рамки допустимых
;значений.
xor r9d,r9d
mov r8,LineNo
mov edx,EM_LINEINDEX
mov rcx,hwndRichEdit
call SendMessage
;Если номер строки правильный, мы передвигает курсор к первому символу в
;этой строке. Поэтому мы посылаем сообщение EM_LINEINDEX контролу
;richedit. Это сообщение возвращает индекс первого символа
;в заданной строке. Мы посылаем номер строки через wParam,
;а получаем индекс символа
;Чтобы установить текущее выделение, в этот раз мы используем
;EM_SETSEL, потому что индексы символов уже не находятся в структуре
;CHARRANGE, что сохраняет нам две инструкции (помещение этих индексов
;в структуру CHARRANGE).
mov r9,rax
mov r8,rax
mov edx,EM_SETSEL
mov rcx,hwndRichEdit
call SendMessage
;Курсор не будет отображен, пока контрол RichEdit не получит фокус.
;Поэтому мы вызываем SetFocus
mov rcx,hwndRichEdit
call SetFocus
jmp wmBYE
wmCLOSE:xor edx,edx
mov hSearch,rdx
call EndDialog
wmBYE: mov eax,TRUE
leave
ret
GoToProc endp
;--------------------------------------------------
PrepareEditMenu proc hSubMenu:QWORD
LOCAL chrg:CHARRANGE
push rbp
mov ebp,esp
sub esp,(20h+sizeof CHARRANGE+15)and(-16)
mov hSubMenu,rcx
;=============================================================================
; Check whether there is some text in the clipboard. If so, we enable the paste menuitem
;=============================================================================
xor r9d,r9d
mov r8d,CF_TEXT
mov edx,EM_CANPASTE
mov rcx,hwndRichEdit
call SendMessage
or eax,eax;.if eax==0 ; no text in the clipboard
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_PASTE
mov rcx,hSubMenu
call EnableMenuItem
;==========================================================
; check whether the undo queue is empty
;==========================================================
xor r9d,r9d
xor r8d,r8d
mov edx,EM_CANUNDO
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; .if eax==0
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_UNDO
mov rcx,hSubMenu
call EnableMenuItem
;=========================================================
; check whether the redo queue is empty
;=========================================================
xor r9d,r9d
xor r8d,r8d
mov edx,EM_CANREDO
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; .if eax==0
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_REDO
mov rcx,hSubMenu
call EnableMenuItem
;=========================================================
; check whether there is a current selection in the richedit control.
; If there is, we enable the cut/copy/delete menuitem
;=========================================================
lea r9,chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov eax,chrg.cpMin
cmp eax,chrg.cpMax; .if eax==chrg.cpMax ; no current selection
; no current selection
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_COPY
mov rcx,hSubMenu
call EnableMenuItem
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_CUT
mov rcx,hSubMenu
call EnableMenuItem
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_DELETE
mov rcx,hSubMenu
call EnableMenuItem
xor ebx,ebx
leave
ret
PrepareEditMenu endp
;-------------------------------------------
WndProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL ofn:OPENFILENAME
LOCAL buffer[256]:BYTE
LOCAL editstream:EDITSTREAM
LOCAL hFile:QWORD
LOCAL hPopup:QWORD
LOCAL old_rsi:QWORD
LOCAL pt:POINT
LOCAL chrg:CHARRANGE
push rbp
mov ebp,esp
sub esp,(40h+sizeof OPENFILENAME+256+sizeof EDITSTREAM+\
3*8+sizeof POINT+sizeof CHARRANGE+15)and(-16)
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_NOTIFY
je wmNOTIFY
cmp edx,WM_INITMENUPOPUP
je wmINITMENUPOPUP
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_DESTROY
je wmDESTROY
wmDEFAULT:leave
jmp DefWindowProc
wmDESTROY:mov rcx,hRichEdit
call FreeLibrary
xor ecx,ecx
call ExitProcess
wmNOTIFY:mov old_rsi,rsi
mov rsi,r9;lParam;assume esi:ptr NMHDR
cmp [rsi+NMHDR._code],EN_MSGFILTER;.if [esi]._code==EN_MSGFILTER
jnz @f;assume esi:ptr MSGFILTER
cmp [rsi+MSGFILTER.msg],WM_RBUTTONDOWN;.if [esi].msg==WM_RBUTTONDOWN
jnz @f
mov rcx,hWnd
call GetMenu
mov edx,1
mov ecx,eax
call GetSubMenu
mov hPopup,rax
mov ecx,eax;hPopup
call PrepareEditMenu
mov rdx,[rsi+MSGFILTER.lParam]
mov ecx,edx
and edx,0FFFFh
shr ecx,16
mov pt.x,edx
mov pt.y,ecx
lea edx,pt
mov rcx,hWnd
call ClientToScreen
mov qword ptr [rsp+30h],NULL
mov rax,hWnd
mov [rsp+28h],rax
mov qword ptr [rsp+20h],NULL
mov r9d,pt.y
mov r8d,pt.x
mov edx,TPM_LEFTALIGN or TPM_BOTTOMALIGN
mov rcx,hPopup
call TrackPopupMenu
@@: mov rsi,old_rsi
jmp wmBYE
wmINITMENUPOPUP:
mov eax,r9d;lParam
or ax,ax;.if ax==0; file menu
jnz @0
cmp FileOpened,TRUE;.if FileOpened==TRUE ; a file is already opened
setne bl;в ebx MF_ENABLED=0 или MF_GRAYED=1
mov r8d,ebx;MF_ENABLED
mov edx,IDM_CLOSE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_SAVE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_SAVEAS
mov rcx,wParam
call EnableMenuItem
xor ebx,1
mov r8d,ebx;MF_GRAYED
mov edx,IDM_OPEN
mov rcx,wParam
call EnableMenuItem
xor ebx,ebx
jmp wmBYE; .endif
@0: cmp ax,1;.elseif ax==1 ; edit menu
jnz @f
mov rcx,wParam
call PrepareEditMenu
jmp wmBYE
@@: cmp ax,2;.elseif ax==2 ; search menu bar
jnz wmBYE
cmp FileOpened,TRUE;.if FileOpened==TRUE
setne bl;в ebx MF_ENABLED=0 или MF_GRAYED=1
mov r8d,ebx;MF_ENABLED
mov edx,IDM_FIND
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_FINDNEXT
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_FINDPREV
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_REPLACE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_GOTOLINE
mov rcx,wParam
call EnableMenuItem
xor ebx,ebx
jmp wmBYE
wmCOMMAND:
or r9,r9;.if lParam==0 ; menu commands
jnz wmBYE
mov eax,r8d;mov eax,wParam
sub eax,IDM_OPEN;.if ax==IDM_OPEN
cmp eax,IDM_FINDPREV-IDM_OPEN
ja wmBYE
jmp handle1[rax*8]
OPEN: mov edx,sizeof OPENFILENAME
lea ecx,ofn
call RtlZeroMemory
lea ecx,ofn
mov [rcx+OPENFILENAME.lStructSize],sizeof ofn
mov rax,hWnd
mov [rcx+OPENFILENAME.hwndOwner],rax
mov [rcx+OPENFILENAME.hInstance],IMAGE_BASE
mov eax,offset ASMFilterString
mov [rcx+OPENFILENAME.lpstrFilter],rax
mov eax,offset FileName
mov [rcx+OPENFILENAME.lpstrFile],rax
mov byte ptr [FileName],0
mov [rcx+OPENFILENAME.nMaxFile],sizeof FileName
mov [rcx+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_HIDEREADONLY or OFN_PATHMUSTEXIST
call GetOpenFileName
or eax,eax; .if eax!=0
jz wmBYE
mov qword ptr [rsp+30h],0
mov qword ptr [rsp+28h],FILE_ATTRIBUTE_NORMAL
mov qword ptr [rsp+20h],OPEN_EXISTING
mov r9d,NULL
mov r8d,FILE_SHARE_READ
mov edx,GENERIC_READ
mov ecx,offset FileName
call CreateFile
inc eax;.if eax!=INVALID_HANDLE_VALUE
jz @f
dec eax
mov hFile,rax
;================================================================
; stream the text into the richedit control
;================================================================
lea r9,editstream
mov [r9+EDITSTREAM.dwCookie],rax
mov eax,offset StreamInProc
mov [r9+EDITSTREAM.pfnCallback],rax
mov r8d,SF_TEXT
mov edx,EM_STREAMIN
mov rcx,hwndRichEdit
call SendMessage
;==========================================================
; Initialize the modify state to false
;==========================================================
xor r9d,r9d
mov r8d,FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov rcx,hFile
call CloseHandle
mov FileOpened,TRUE
jmp wmBYE
@@: mov r9d,MB_OK or MB_ICONERROR
mov r8d,offset AppName
mov edx,offset OpenFileFail
mov rcx,hWnd
call MessageBox
jmp wmBYE
CLOSE1: mov rcx,hWnd
call CheckModifyState
or eax,eax;.if eax==TRUE
jz wmBYE
xor edx,edx
mov rcx,hwndRichEdit
call SetWindowText
mov FileOpened,FALSE
jmp wmBYE
SAVE: mov ecx,offset FileName
jmp @f
SAVEAS:
mov edx,sizeof ofn
lea ecx,ofn
call RtlZeroMemory
lea ecx,ofn
mov [rcx+OPENFILENAME.lStructSize],sizeof ofn
mov rax,hWnd
mov [rcx+OPENFILENAME.hwndOwner],rax
mov [rcx+OPENFILENAME.hInstance],IMAGE_BASE
mov eax,offset ASMFilterString
mov [rcx+OPENFILENAME.lpstrFilter],rax
mov eax,offset AlternateFileName
mov [rcx+OPENFILENAME.lpstrFile],rax
mov byte ptr [AlternateFileName],0
mov [rcx+OPENFILENAME.nMaxFile],sizeof AlternateFileName
mov [rcx+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_HIDEREADONLY or OFN_PATHMUSTEXIST
call GetSaveFileName
or eax,eax;.if eax!=0
jz wmBYE
mov ecx,offset AlternateFileName
@@: mov qword ptr [rsp+30h],0
mov qword ptr [rsp+28h],FILE_ATTRIBUTE_NORMAL
mov qword ptr [rsp+20h],CREATE_ALWAYS
mov r9d,NULL
mov r8d,FILE_SHARE_READ
mov edx,GENERIC_WRITE
call CreateFile
inc eax;.if eax!=INVALID_HANDLE_VALUE
jz wmBYE
dec eax
mov hFile,rax
;================================================================
; stream the text to the file
;==============================================================
lea r9,editstream
mov [r9+EDITSTREAM.dwCookie],rax
mov eax,offset StreamOutProc
mov [r9+EDITSTREAM.pfnCallback],rax
mov r8d,SF_TEXT
mov edx,EM_STREAMOUT
mov rcx,hwndRichEdit
call SendMessage
;==========================================================
; Initialize the modify state to false
;==========================================================
xor r9d,r9d
mov r8d,FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov rcx,hFile
call CloseHandle
jmp wmBYE
COPY:
mov edx,WM_COPY
jmp @19
CUT:
mov edx,WM_CUT
jmp @19
PASTE:
mov edx,WM_PASTE
jmp @19
DELETE1:
xor r9d,r9d
mov r8d,TRUE
mov edx,EM_REPLACESEL
jmp @21
SELECTALL:
mov chrg.cpMin,0
mov chrg.cpMax,-1
lea r9,chrg
mov edx,EM_EXSETSEL
jmp @20
UNDO:
mov edx,EM_UNDO
jmp @19
REDO:
mov edx,EM_REDO
@19: xor r9d,r9d
@20: xor r8d,r8d
@21: mov rcx,hwndRichEdit
call SendMessage
jmp wmBYE
OPTIONS:mov qword ptr [rsp+20h],0
mov r9d,offset OptionProc
mov r8,hWnd
mov edx,IDD_OPTIONDLG
mov ecx,IMAGE_BASE
call DialogBoxParam
jmp wmBYE
FIND: cmp hSearch,0;.if hSearch==0
jnz wmBYE
mov r9d,offset SearchProc
mov edx,IDD_FINDDLG
jmp @f
REPLACE:cmp hSearch,0;.if hSearch==0
jnz wmBYE
mov r9d,offset ReplaceProc
mov edx,IDD_REPLACEDLG
jmp @f
GOTOLINE:cmp hSearch,0;.if hSearch==0
jnz wmBYE
mov r9d,offset GoToProc
mov edx,IDD_GOTODLG
@@: mov ecx,IMAGE_BASE
mov r8,hWnd
mov qword ptr [rsp+20h],0
call CreateDialogParam
jmp wmBYE
FINDNEXT:mov ecx,offset FindBuffer
call lstrlen
or eax,eax;.if eax!=0
jz wmBYE
mov r9d,offset findtext.chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov eax,findtext.chrg.cpMin
cmp eax,findtext.chrg.cpMax;.if eax!=findtext.chrg.cpMax
jz @f
mov eax,findtext.chrg.cpMax
mov findtext.chrg.cpMin,eax
@@: mov findtext.chrg.cpMax,-1
mov r8d,FR_DOWN
jmp @f
FINDPREV:
mov ecx,offset FindBuffer
call lstrlen
or eax,eax;.if eax!=0
jz wmBYE
mov r9d,offset findtext.chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov findtext.chrg.cpMax,0
xor r8d,r8d
@@: mov eax,offset FindBuffer
mov findtext.lpstrText,rax
mov r9d,offset findtext
mov edx,EM_FINDTEXTEX
mov rcx,hwndRichEdit
call SendMessage
inc eax;.if eax!=-1
jz wmBYE
mov r9d,offset findtext.chrgText
xor r8d,r8d
mov edx,EM_EXSETSEL
mov rcx,hwndRichEdit
call SendMessage
jmp wmBYE
EXIT: xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
mov rcx,hWnd
call SendMessage
jmp wmBYE
wmCLOSE:call CheckModifyState
or eax,eax ;.if eax==TRUE
jz wmBYE
mov rcx,hWnd
call DestroyWindow
jmp wmBYE
wmSIZE: mov eax,r9d;lParam
and r9,0FFFFh
shr eax,16
mov qword ptr [rsp+28h],TRUE
mov [rsp+20h],rax
xor edx,edx
mov r8,rdx
mov rcx,hwndRichEdit
call MoveWindow
wmBYE: leave
ret
handle1 dq OPEN,SAVE,CLOSE1,SAVEAS,EXIT,COPY,CUT,PASTE,DELETE1,SELECTALL
dq OPTIONS,UNDO,REDO,FIND,FINDNEXT,REPLACE,GOTOLINE,FINDPREV
WndProc endp
;----------------------------------------------------------------
ClassName db "IczEditClass",0
AppName db "IczEdit version 2.0",0
RichEditDLL db "riched20.dll",0
RichEditClass db "RichEdit20A",0
NoRichEdit db "Cannot find riched20.dll",0
ASMFilterString db "ASM Source code (*.asm)",0,"*.asm",0
db "All Files (*.*)",0,"*.*",0,0
OpenFileFail db "Cannot open the file",0
WannaSave db "The data in the control is modified. Want to save it?",0
FileOpened dq FALSE
BackgroundColor dd 0FFFFFFh; default to white
TextColor dd 0 ; default to black
hSearch dq ? ; handle to the search/replace dialog box
hAccel dq ?
hRichEdit dq ?
hwndRichEdit dq ?
FileName db 256 dup(?)
AlternateFileName db 256 dup(?)
CustomColors dd 16 dup(?)
FindBuffer db 256 dup(?)
ReplaceBuffer db 256 dup(?)
uFlags dd ?
findtext FINDTEXTEX <>
rect RECT <?>
end
-
Hi Micha,
Эти интересные комментарии на русском языке.
Gunther
-
Hi, Gunter !
This is a test program, when the programs will be ready must to insert comments in any language, as long as the programmer captured the essence of the fragment
Dies ist ein Testprogramm, das Programm bereit, Kommentare in allen Sprachen einsetzen zu können, so lange wie der Programmierer die Essenz des Fragments
-
Micha,
This is a test program, when the programs will be ready must to insert comments in any language, as long as the programmer captured the essence of the fragment
Dies ist ein Testprogramm, das Programm bereit, Kommentare in allen Sprachen einsetzen zu können, so lange wie der Programmierer die Essenz des Fragments
that's clear, no offense. I made a little joke, not more.
Gunther
-
Win x64 Tutorial #31b: listview
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comctl32.inc
includelib comctl32.lib
include gdi32.inc
includelib gdi32.lib
include ole32.inc
includelib ole32.lib
include shell32.inc
includelib shell32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
M_MAIN equ 10000
MI_ICON equ 0
MI_SMALLICON equ 2
MI_LIST equ 3
MI_REPORT equ 1
.code
WinMain proc
local msg:MSG
local rect:RECT
push rbp
mov ebp,esp
sub esp,(20h+sizeof MSG+sizeof RECT+15)and(-16)
xor ebx,ebx
call InitCommonControls
mov edi,offset ClassName
mov eax,10027h
mov esi,IMAGE_BASE
; +------------------------------+
; | registering the window class |
; +------------------------------+
push rax ;hIconSm
push rdi ;lpszClassName
push M_MAIN ;lpszMenuName
push COLOR_WINDOW+1;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov rcx,rsp ;addr WNDCLASSEX
call RegisterClassEx
; +--------------------------+
; | creating the main window |
; +--------------------------+
push rbx
push rsi
shl esi,9
push rbx
push rbx
push 240
push 400
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW+WS_VISIBLE
mov r8d,edi
mov edx,edi
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov hwnd,rax
lea edx,rect
mov ecx,eax
call GetClientRect
push rbx;<-- align 10h
push IMAGE_BASE
push rbx
push hwnd
mov eax,rect.bottom
push rax
mov eax,rect.right
push rax
push rbx
push rbx
mov r9d,LVS_REPORT + WS_CHILD + WS_VISIBLE
mov r8,rbx
mov edx,offset ctlClsNameLv
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hList,rax
call lv_col_insert
call lv_col_info_fill
mov r9d,0C9B5AFh
mov r8,rbx
mov edx,LVM_SETTEXTCOLOR
mov rcx,hList
call SendMessage
mov r9d,50352Eh
mov r8,rbx
mov edx,LVM_SETBKCOLOR
mov rcx,hList
call SendMessage
mov r9d,50352Eh
mov r8,rbx
mov edx,LVM_SETTEXTBKCOLOR
mov rcx,hList
call SendMessage
mov rcx,hwnd
call GetMenu
mov menuH,rax
mov qword ptr [rsp+20h],MF_CHECKED
mov r9d,MI_REPORT
mov r8d,MI_LIST
mov edx,MI_ICON
mov ecx,eax
call CheckMenuRadioItem
lea edi,msg
;+---------------------------+
;| entering the message loop |
;+---------------------------+
window_message_loop_start:
mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp window_message_loop_start
WinMain endp
;+----------------------+
;| the window procedure |
;+----------------------+
WndProc proc hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
push rbp
mov ebp,esp
sub esp,30h
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
mov rdi,r9;lParam
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_NOTIFY
je wmNOTIFY
cmp edx,WM_COMMAND
je wmCOMMAND
wmDEFAULT:leave
jmp DefWindowProc
wmDESTROY:xor ecx,ecx
call ExitProcess
wmSIZE: mov eax,r9d;eax=[lParam]
shr eax,16;eax=[lParam+2]
and r9,0FFFFh
mov qword ptr [rsp+28h],TRUE
mov [rsp+20h],rax
xor edx,edx
mov r8,rdx
mov rcx,hList
call MoveWindow
jmp wmBYE
wmNOTIFY:mov rdi,r9;lParam
mov rax,[rdi + NMHDR.hwndFrom]
cmp rax,hList
jne wmDEFAULT
cmp [rdi + NMHDR._code],LVN_COLUMNCLICK
je wmNOTIFY_LVN_COLUMNCLICK
cmp [rdi + NMHDR._code],NM_DBLCLK
jne wmDEFAULT
wmNOTIFY_NM_DBLCLK:call lv_item_focus
jmp wmBYE
wmNOTIFY_LVN_COLUMNCLICK:
cmp [rdi + NM_LISTVIEW.iSubItem+4],1
jne COLUMNCLICK_FILE
COLUMNCLICK_SIZE:xor lvSortSize,1
mov r8d,lvSortSize
jmp @f
COLUMNCLICK_FILE:xor lvSortFile,1
mov r8d,lvSortFile
@@: mov r9d,offset lv_compare
mov edx,LVM_SORTITEMS
mov rcx,hList
call SendMessage
call lv_param_update
jmp wmBYE
wmCOMMAND:or r9,r9;cmp [lParam],0
jne wmBYE
mov edx,GWL_STYLE
mov rcx,hList
call GetWindowLongPtr
and eax,not LVS_TYPEMASK
movzx edi,word ptr wParam
or eax,edi
mov r8,rax
mov edx,GWL_STYLE
mov rcx,hList
call SetWindowLongPtr
push MF_CHECKED
mov r9,rdi
mov r8d,MI_LIST
mov edx,MI_ICON
mov rcx,menuH
call CheckMenuRadioItem
wmBYE: leave
retn
WndProc endp
lv_item_focus proc
local lvi4:LV_ITEM
local buf4[256]:BYTE
push rbp
mov ebp,esp
sub esp,(20h+sizeof LV_ITEM+256+15)and(-16)
mov r9d,LVNI_FOCUSED
or r8d,-1
mov edx,LVM_GETNEXTITEM
mov rcx,hList
call SendMessage
lea r9,lvi4
mov lvi4.iItem,eax
mov lvi4.iSubItem,0;ebx
mov lvi4.imask,LVIF_TEXT
lea eax,buf4
mov lvi4.pszText,rax
mov lvi4.cchTextMax,256
xor r8d,r8d
mov edx,LVM_GETITEM
mov rcx,hList
call SendMessage
xor r9d,r9d;MB_OK
mov r8d,offset ClassName
lea edx,buf4
xor ecx,ecx
call MessageBox
leave
retn
lv_item_focus endp
lv_param_update proc
local lvi1:LV_ITEM
local old_rdi:QWORD
push rbp
mov ebp,esp
sub esp,(28h+sizeof LV_ITEM+15)and(-16)
mov old_rdi,rdi
xor r9d,r9d
xor r8d,r8d
mov edx,LVM_GETITEMCOUNT
mov rcx,hList
call SendMessage
mov edi,eax
mov lvi1.imask,LVIF_PARAM
mov lvi1.iSubItem,0
mov lvi1.iItem,0
mov lvi1.lParam,0
or eax,eax
je wmBYE
@@: lea r9,lvi1
xor r8d,r8d
mov edx,LVM_SETITEM
mov rcx,hList
call SendMessage
inc lvi1.iItem
inc lvi1.lParam
dec edi
jnz @b
wmBYE: mov rdi,old_rdi
leave
retn
lv_param_update endp
convert_strhval proc
sub esp,28h
mov ecx,esi
call lstrlen
or eax,eax
je f12
mov ecx,eax
xor eax,eax
cqo
@@: imul edx,10 ; edx=edx*10
lodsb ; mov al,[esi]/inc esi
lea edx,[rax+rdx-'0'] ; edx=edx*10+eax
loop @b
mov eax,edx
f12: add esp,28h
retn
convert_strhval endp
lv_compare proc lParam1:QWORD,lParam2:QWORD,lParamSort:QWORD
local lvi0:LV_ITEM
local buf1[255]:BYTE
local buf2[255]:BYTE
local old_rdi:QWORD
local old_rsi:QWORD
push rbp
mov ebp,esp
sub esp,(30h+510+sizeof LV_ITEM+15)and(-16)
mov lParam1,rcx
mov lParam2,rdx
mov lParamSort,r8
mov old_rdi,rdi
mov old_rsi,rsi
mov lvi0.imask,LVIF_TEXT
lea eax,buf1
mov lvi0.pszText,rax
mov lvi0.cchTextMax,255
cmp lParamSort,1
ja compare_3
compare_1:lea r9,lvi0
mov [r9+LV_ITEM.iSubItem],1
mov r8,lParam1
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea esi,buf1
call convert_strhval
mov edi,eax
lea r9,lvi0
mov r8,lParam2
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea esi,buf1
call convert_strhval
sub edi,eax
cmp lParamSort,1
jne compare_3_exit
mov eax,edi
jmp compare_3_exit
compare_3:lea r9,lvi0
mov [r9+LV_ITEM.iSubItem],0
mov r8,lParam1
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea ecx,buf2 ;destination
lea edx,buf1 ;source
call lstrcpy
lea r9,lvi0
mov r8,lParam2
mov edx,LVM_GETITEMTEXT
mov rcx,hList
call SendMessage
lea edx,buf2
lea ecx,buf1
cmp lParamSort,3
jne @f
xchg edx,ecx
@@: call lstrcmpi
compare_3_exit:mov rdi,old_rdi
mov rsi,old_rsi
leave
ret
lv_compare endp
lv_col_insert proc
local lvCol:LV_COLUMN
push rbp
mov ebp,esp
sub esp,(20h+sizeof LV_COLUMN+15)and(-16)
mov lvCol.imask,LVCF_TEXT + LVCF_WIDTH
mov eax,offset lvTxt1
mov lvCol.pszText,rax
mov lvCol.lx,150
lea r9,lvCol
mov r8,rbx
mov edx,LVM_INSERTCOLUMN
mov rcx,hList
call SendMessage
or lvCol.imask,LVCF_FMT
mov lvCol.fmt,LVCFMT_RIGHT
mov eax,offset lvTxt2
mov lvCol.pszText,rax
mov lvCol.lx,100
lea r9,lvCol
mov r8d,1
mov edx,LVM_INSERTCOLUMN
mov rcx,hList
call SendMessage
leave
retn
lv_col_insert endp
lv_col_info_fill proc
local old_rdi:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov old_rdi,rdi
mov edx,offset fData
mov ecx,offset fTxt1
call FindFirstFile
inc eax ; eax = INVALID_HANDLE_VALUE ?
je fill_exit
dec eax
mov fFileH,rax
xor edi,edi
fill_start:cmp fData.dwFileAttributes,FILE_ATTRIBUTE_DIRECTORY
je @f
call lv_col_info_insert
inc edi
@@: mov edx,offset fData
mov rcx,fFileH
call FindNextFile
or eax,eax ; eax <> 0 ?
jne fill_start
fill_end:mov rcx,fFileH
call FindClose
fill_exit:mov rdi,old_rdi
leave
retn
lv_col_info_fill endp
lv_col_info_insert proc
local lvi2:LV_ITEM
local buf3[20]:BYTE
push rbp
mov ebp,esp
sub esp,(20h+20+sizeof LV_ITEM+15)and(-16)
lea r9,lvi2
mov [r9+LV_ITEM.imask],LVIF_TEXT + LVIF_PARAM
mov eax,offset fData.cFileName
mov [r9+LV_ITEM.pszText],rax
mov [r9+LV_ITEM.iSubItem],ebx
mov [r9+LV_ITEM.iItem],edi;?
mov [r9+LV_ITEM.lParam],edi
mov r8,rbx
mov edx,LVM_INSERTITEM
mov rcx,hList
call SendMessage
mov lvi2.imask,LVIF_TEXT
inc lvi2.iSubItem
lea eax,buf3
mov lvi2.pszText,rax
mov r8d,fData.nFileSizeLow
mov edx,offset lvTxt3
mov ecx,eax
call wsprintf
lea r9,lvi2
mov r8,rbx
mov edx,LVM_SETITEM
mov rcx,hList
call SendMessage
leave
ret
lv_col_info_insert endp
;------------------------------------------------------------------------
hwnd dq ?
ClassName db 'Win64 Iczelion''s lesson #31b: listview',0
ctlClsNameLv db 'SysListView32',0
hList dq ?
lvTxt1 db 'File Name',0
lvTxt2 db 'Size',0
lvTxt3 db '%lu',0
lvSortSize dd 0
lvSortFile dd 2;0
menuH dq ?
fFileH dq ?
fData WIN32_FIND_DATA <>
fTxt1 db '*.*',0
end
rc-file#define MI_ICON 0
#define MI_REPORT 1
#define MI_SMALLICON 2
#define MI_LIST 3
#define M_MAIN 10000
M_MAIN MENU
{
POPUP "&View"
{ MENUITEM "Lar&ge Icons",MI_ICON
MENUITEM "S&mall Icons",MI_SMALLICON
MENUITEM "&List",MI_LIST
MENUITEM "&Details",MI_REPORT
}
}
-
Wow!
tut33.zip (181.14 kB - downloaded 129 times.)
with an average of about 20 downloads somebody's attention was drawn to this particular tut33.zip (http://www.cyberforum.ru/images/smilies/scratch_one-s_head.gif)
wildly popular!
-
Win x64 Tutorial #37a: The simplest animation
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comctl32.inc
includelib comctl32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
ACM_OPEN = WM_USER + 100
ACS_AUTOPLAY = 4
ID_ANIMATE = 101
.code
WinMain proc
local msg:MSG
local hwnd:QWORD
push rbp
mov ebp,esp
sub esp,sizeof MSG+8
xor ebx,ebx
mov esi,IMAGE_BASE
mov eax,10027h
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
push rbx
push rbx
push 244
push 300
push 300
push 300
mov r9d,WS_CAPTION or WS_SYSMENU or WS_VISIBLE
mov r8d,edi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hwnd,rax
push rbx
push rsi;IMAGE_BASE
push ID_ANIMATE
push rax;hwnd
push 128
push 162
push 48
push 66
mov r9d,WS_CHILD+WS_VISIBLE+WS_TABSTOP+ACS_AUTOPLAY
mov r8d,offset NoText
mov edx,offset Animate32
mov ecx,WS_EX_STATICEDGE+WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov eax,offset AviFile
mov [rsp+20h],rax
mov r9d,IMAGE_BASE
mov r8d,ACM_OPEN
mov edx,ID_ANIMATE
mov rcx,hwnd
call SendDlgItemMessage
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc: cmp edx,WM_DESTROY
je wmDESTROY
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
;---------------------------------------
ClassName db 'Win64 Iczelion''s Tutorial #37a: Animation',0
AviFile db 'skeleton.avi',0
Animate32 db "SysAnimate32"
NoText db 0
end
There are asm-, exe-, bat-files and skeleton.avi in attachment
-
Win x64 Tutorial #37b: Slightly more complex player of avi/wmv-files
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comctl32.inc
includelib comctl32.lib
include winmm.inc
includelib winmm.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
MCI_ANIM_OPEN_PARMS STRUCT
dwCallback QWORD ?
wDeviceID DWORD ?
lpstrDeviceType QWORD ?
lpstrElementName QWORD ?
lpstrAlias QWORD ?
dwStyle DWORD ?
hWndParent QWORD ?
MCI_ANIM_OPEN_PARMS ENDS
MCI_ANIM_PLAY_PARMS STRUCT
dwCallback QWORD ?
dwFrom DWORD ?
dwTo DWORD ?
dwSpeed DWORD ?
MCI_ANIM_PLAY_PARMS ENDS
MCI_GENERIC_PARMS STRUCT
dwCallback QWORD ?
MCI_GENERIC_PARMS ENDS
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov esi,IMAGE_BASE
mov eax,10027h
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9
push rbx
push rbx
push 508;640x480
push 645
push rsi
push rsi
mov r9d,WS_CAPTION or WS_SYSMENU or WS_MINIMIZEBOX or WS_VISIBLE
mov r8d,edi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
local buff[96]:BYTE
push rbp
mov ebp,esp
sub esp,(20h+96+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_CREATE
je wmCREATE
cmp edx,MM_MCINOTIFY
je mmMCINOTIFY
leave
jmp DefWindowProc
wmDESTROY:mov r9d,offset mciCP
xor r8d,r8d
mov edx,MCI_CLOSE
mov ecx,mciOP.wDeviceID
call mciSendCommand
xor ecx,ecx
call ExitProcess
wmCREATE:mov mciOP.hWndParent,rcx
mov r9d,offset mciOP
mov r8d,MCI_WAIT or MCI_OPEN_ELEMENT or MCI_ANIM_OPEN_WS or MCI_ANIM_OPEN_PARENT
mov edx,MCI_OPEN
xor ecx,ecx
call mciSendCommand
or eax,eax
je @f
CALL MCIError
;--------------------------------------------------------------------- EOF AVI
mmMCINOTIFY:;mov rcx,hWnd
call DestroyWindow
jmp wmBYE
;-------------------------------------------------------------------- Play AVI
@@: mov rax,hWnd
mov mciPP.dwCallback,rax
mov r9d,offset mciPP
mov r8d,MCI_NOTIFY
mov edx,MCI_PLAY
mov ecx,mciOP.wDeviceID
call mciSendCommand
or eax,eax
je wmBYE
MCIError:sub esp,28h
mov r8d,96
lea edx,buff
mov ecx,eax
call mciGetErrorString
mov r9d,MB_OK or MB_ICONSTOP
mov r8d,offset aMCIError
lea edx,buff
mov rcx,hWnd
call MessageBox
wmBYE: leave
ret
WndProc endp
ClassName db 'Win64 Iczelion''s Tutorial #37b: Animation',0
mciOP MCI_ANIM_OPEN_PARMS <0,0,DeviceType,ElementName,0,WS_CHILD,0>
mciPP MCI_ANIM_PLAY_PARMS <0>
mciCP MCI_GENERIC_PARMS <1>
aMCIError db "MCI Error",0
DeviceType DB 'AVIVideo',0
ElementName DB 'movie.wmv',0
end
-
Win x64 Tutorial #37с: play AVI-files using the ShellExecute
asm-fileinclude win64.inc
include shell32.inc
includelib shell32.lib
include comctl32.inc
includelib comctl32.lib
.code
WinMain proc
sub esp,7*8
mov qword ptr [rsp+28h],SW_SHOWNORMAL
xor ecx,ecx
mov [rsp+20h],rcx
xor r9d,r9d
mov r8d,offset szFilm
mov edx,offset szOpen
call ShellExecute
add esp,7*8
ret
WinMain endp
szFilm db 'movie.wmv',0
szOpen db 'open',0
end
If you want to modify the program - insert call of the function GetOpenFileName and upload the name of file in the second parameter instead of a fixed szFilm, if you want to full-screen playback, then you change SW_SHOWNORMAL to SW_SHOWMAXIMIZED.
-
Win x64 Tutorial #37d: play AVI-files using the ShellExecuteEx
typedef struct _SHELLEXECUTEINFO {
DWORD cbSize;
ULONG fMask;
HWND hwnd;
LPCTSTR lpVerb;
LPCTSTR lpFile;
LPCTSTR lpParameters;
LPCTSTR lpDirectory;
int nShow;
HINSTANCE hInstApp;
LPVOID lpIDList;
LPCTSTR lpClass;
HKEY hkeyClass;
DWORD dwHotKey;
union {
HANDLE hIcon;
HANDLE hMonitor;
} DUMMYUNIONNAME;
HANDLE hProcess;
} SHELLEXECUTEINFO, *LPSHELLEXECUTEINFO;
asm-fileOPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include shell32.inc
includelib shell32.lib
include comctl32.inc
includelib comctl32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
.code
WinMain proc
sub esp,8 ;<--16bit align
xor ebx,ebx
push rbx ;rcx+68h hProcess
push rbx ;rcx+60h hMonitor
push rbx ;rcx+58h hIcon
push rbx ;rcx+54h dwHotKey
push rbx ;rcx+4Ch hkeyClass
push rbx ;rcx+44h lpClass
push rbx ;rcx+3Ch lpIDList
push SW_SHOWNORMAL;rcx+30h nShow rcx+34h hInstapp
push rbx ;rcx+28h lpdirectory
push rbx ;rcx+20h lpParameters
db 68h
dd szFilm ;rcx+18h lpFile
db 68h
dd szOpen ;rcx+10h lpVerb
push rbx ;rcx+08h hWnd
mov rax,(1500h shl 32 + 70h) ;cbSize=sizeof SHELLEXECUTEINFO fMask=1500h
push rax ;rcx+0 cbSize rcx+4 fMask
mov ecx,esp ;<-- SHELLEXECUTEINFO
call ShellExecuteEx
xor ecx,ecx
call ExitProcess
WinMain endp
szFilm db 'movie.wmv',0
szOpen db 'open',0
end
-
Win x64 Tutorial #37e: Yet another video-player
asm-fileinclude win64a.inc
include shell32.inc
includelib shell32.lib
include comdlg32.inc
includelib comdlg32.lib
include msvfw32.inc
includelib msvfw32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
MENU_FILE equ 0
MENU_CD equ 1
MENU_VIDEODISK equ 2
MENU_VIDEOPLAYER equ 3
MENU_FULLSCREEN equ 4
MENU_ABOUT equ 5
MCIWNDF_NOAUTOSIZEWINDOW equ 0001h
MCIWNDF_NOPLAYBAR equ 0002h
MCIWNDF_NOAUTOSIZEMOVIE equ 0004h
MCIWNDF_NOMENU equ 0008h
MCIWNDF_SHOWNAME equ 0010h
MCIWNDF_SHOWPOS equ 0020h
MCIWNDF_SHOWMODE equ 0040h
MCIWNDF_SHOWALL equ 0070h
MCIWNDF_NOTIFYMODE equ 0100h
MCIWNDF_NOTIFYPOS equ 0200h
MCIWNDF_NOTIFYSIZE equ 0400h
MCIWNDF_NOTIFYERROR equ 1000h
MCIWNDF_NOTIFYALL equ 1F00h
MCIWNDF_NOTIFYANSI equ 0080h
MCIWNDF_NOTIFYMEDIAA equ 0880h
MCIWNDF_NOTIFYMEDIAW equ 0800h
;IFDEF __UNICODE__
; MCIWNDF_NOTIFYMEDIA equ MCIWNDF_NOTIFYMEDIAW
;ELSE
; MCIWNDF_NOTIFYMEDIA equ MCIWNDF_NOTIFYMEDIAA
;ENDIF
MCIWNDF_RECORD equ 2000h
MCIWNDF_NOERRORDLG equ 4000h
MCIWNDF_NOOPEN equ 8000h
MCIWNDM_GETDEVICEID equ WM_USER+100
MCIWNDM_GETSTART equ WM_USER+103
MCIWNDM_GETLENGTH equ WM_USER+104
MCIWNDM_GETEND equ WM_USER+105
MCIWNDM_EJECT equ WM_USER+107
MCIWNDM_SETZOOM equ WM_USER+108
MCIWNDM_GETZOOM equ WM_USER+109
MCIWNDM_SETVOLUME equ WM_USER+110
MCIWNDM_GETVOLUME equ WM_USER+111
MCIWNDM_SETSPEED equ WM_USER+112
MCIWNDM_GETSPEED equ WM_USER+113
MCIWNDM_SETREPEAT equ WM_USER+114
MCIWNDM_GETREPEAT equ WM_USER+115
MCIWNDM_REALIZE equ WM_USER+118
MCIWNDM_VALIDATEMEDIA equ WM_USER+121
MCIWNDM_PLAYFROM equ WM_USER+122
MCIWNDM_PLAYTO equ WM_USER+123
MCIWNDM_GETPALETTE equ WM_USER+126
MCIWNDM_SETPALETTE equ WM_USER+127
MCIWNDM_SETTIMERS equ WM_USER+129
MCIWNDM_SETACTIVETIMER equ WM_USER+130
MCIWNDM_SETINACTIVETIMER equ WM_USER+131
MCIWNDM_GETACTIVETIMER equ WM_USER+132
MCIWNDM_GETINACTIVETIMER equ WM_USER+133
MCIWNDM_CHANGESTYLES equ WM_USER+135
MCIWNDM_GETSTYLES equ WM_USER+136
MCIWNDM_GETALIAS equ WM_USER+137
MCIWNDM_PLAYREVERSE equ WM_USER+139
MCIWNDM_GET_SOURCE equ WM_USER+140
MCIWNDM_PUT_SOURCE equ WM_USER+141
MCIWNDM_GET_DEST equ WM_USER+142
MCIWNDM_PUT_DEST equ WM_USER+143
MCIWNDM_CAN_PLAY equ WM_USER+144
MCIWNDM_CAN_WINDOW equ WM_USER+145
MCIWNDM_CAN_RECORD equ WM_USER+146
MCIWNDM_CAN_SAVE equ WM_USER+147
MCIWNDM_CAN_EJECT equ WM_USER+148
MCIWNDM_CAN_CONFIG equ WM_USER+149
MCIWNDM_PALETTEKICK equ WM_USER+150
MCIWNDM_OPENINTERFACE equ WM_USER+151
MCIWNDM_SETOWNER equ WM_USER+152
MCIWNDM_GETMODEA equ WM_USER+106
MCIWNDM_GETMODEW equ WM_USER+206
MCIWNDM_SETTIMEFORMATA equ WM_USER+119
MCIWNDM_SETTIMEFORMATW equ WM_USER+219
MCIWNDM_GETTIMEFORMATA equ WM_USER+120
MCIWNDM_GETTIMEFORMATW equ WM_USER+220
MCIWNDM_GETFILENAMEA equ WM_USER+124
MCIWNDM_GETFILENAMEW equ WM_USER+224
MCIWNDM_GETDEVICEA equ WM_USER+125
MCIWNDM_GETDEVICEW equ WM_USER+225
MCIWNDM_GETERRORA equ WM_USER+128
MCIWNDM_GETERRORW equ WM_USER+228
MCIWNDM_NEWA equ WM_USER+134
MCIWNDM_NEWW equ WM_USER+234
MCIWNDM_RETURNSTRINGA equ WM_USER+138
MCIWNDM_RETURNSTRINGW equ WM_USER+238
MCIWNDM_OPENA equ WM_USER+153
MCIWNDM_OPENW equ WM_USER+252
MCIWNDM_SENDSTRINGA equ WM_USER+101
MCIWNDM_SENDSTRINGW equ WM_USER+201
MCIWNDM_GETPOSITIONA equ WM_USER+102
MCIWNDM_GETPOSITIONW equ WM_USER+202
MCIWNDM_NOTIFYMODE equ WM_USER+200
MCIWNDM_NOTIFYPOS equ WM_USER+201
MCIWNDM_NOTIFYSIZE equ WM_USER+202
MCIWNDM_NOTIFYMEDIA equ WM_USER+203
MCIWNDM_NOTIFYERROR equ WM_USER+205
.code
WinMain proc
local buffer[128]:BYTE
local msg:MSG
push rbp
mov ebp,esp
sub esp,(30h+sizeof MSG+128+15)and(-16)
xor ebx,ebx
lea eax,buffer
mov pBuffer,rax
mov r9d,offset MediaFileName;имя устройства или путь к файлу
mov r8d,WS_VISIBLE or WS_OVERLAPPEDWINDOW or MCIWNDF_NOMENU;стиль
mov edx,IMAGE_BASE;идентификатор приложения
xor ecx,ecx ;идентификатор родительского окна
call MCIWndCreate
mov mcihWnd,rax
mov edx,TRUE
mov ecx,eax;mcihWnd
invoke DragAcceptFiles
;-----------------------------------------------
xor edx,edx;FALSE
mov rcx,mcihWnd
call GetSystemMenu
mov hMenu,rax;в edi handleMenu
; дописываю новые пункты в системное меню
xor esi,esi
@@: mov rax,[handle1+rsi*8]
mov [rsp+20h],rax
mov r9d,esi
mov r8d,MF_BYPOSITION
mov edx,esi
mov rcx,hMenu
call InsertMenu
inc esi
cmp esi,5
jna @b
mov r8d,offset WndProc
mov edx,GWL_WNDPROC
mov rcx,mcihWnd
invoke SetWindowLongPtr
mov prevWindow,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8,rbx
mov r9,rbx
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:QWORD,uMsg:QWORD,wParam:QWORD,lParam:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_SYSCOMMAND
je wmSYSCOMMAND
cmp edx,WM_DROPFILES
je wmDROPFILES
cmp edx,MM_MCINOTIFY
je mmMCINOTIFY
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_DESTROY
jne default
wmDESTROY: xor ecx,ecx
call ExitProcess
mmMCINOTIFY:mov edx,SW_MINIMIZE or SW_SHOWNORMAL
mov rcx,hWnd
call ShowWindow
xor r9d,r9d; FALSE
mov r8d,MCIWNDF_NOMENU
mov edx,MCIWNDM_CHANGESTYLES
mov rcx,hWnd
call SendMessage
mov r9d,offset szStop
xor r8d,r8d
mov edx,MCIWNDM_SENDSTRINGA
mov rcx,hWnd
call SendMessage
jmp default
wmDROPFILES:mov r9d,128
mov r8,pBuffer
xor edx,edx
mov rcx,wParam
call DragQueryFile
mov rcx,wParam
call DragFinish
jmp a1
wmSYSCOMMAND:
mov eax,r8d;wParam
cmp eax,MENU_ABOUT
ja default
jmp [handle+rax*8]
wmCLOSE:mov r9d,offset szStop
xor r8d,r8d
mov edx,MCIWNDM_SENDSTRINGA
mov rcx,hWnd
call SendMessage
mov r9d,offset szClose
xor r8d,r8d
mov edx,MCIWNDM_SENDSTRINGA
mov rcx,hWnd
call SendMessage
mov rcx,hWnd
call DestroyWindow
jmp default
mnuFILE:mov rdx,pBuffer
mov [rdx],rbx; ноль в начало буфера для названия файла
;заполняю OPENFILENAME
push rbx; <-- align 16-bits
push rbx;lpTemplateName
push rbx;lpfnHook
push rbx;lCustData
push rbx;lpstrDefExt
push OFN_FILEMUSTEXIST or OFN_PATHMUSTEXIST or OFN_LONGNAMES \
or OFN_EXPLORER or OFN_HIDEREADONLY;Flags & nFileOffset & nFileExtension
push rbx;lpstrTitle
push rbx;lpstrInitialDir
push rbx;nMaxFileTitle
push rbx;lpstrFileTitle
push 124;nMaxFile
push rbx;lpstrFile
push rbx;nMaxCustFilter & nFilterIndex
push rbx;lpstrCustomFilter
mov eax,offset LoadFileFilter
push rax;lpstrFilter
push IMAGE_BASE;hInstance
push hWnd;hwndOwner
push sizeof OPENFILENAME;lStructSize
;----------------------------------------------------
mov ecx,esp;адрес OPENFILENAME
mov edi,ecx
call GetOpenFileName
test eax,eax
jz wmCLOSE; если не выбран никакой файл
movzx edx,word ptr [rdi+OPENFILENAME.nFileExtension]
add rdx,[rdi+OPENFILENAME.lpstrFile];offset LoadFileBuffer
;add esp,4Ch; удаляю OPENFILENAME
mov eax,[rdx];в регисре еах расширение файла
or eax,202020h;приводим к нижнему регистру
cmp eax,"adc"
jnz a1
mnuCD: mov r8d,offset cdaudioDev
jmp @f
mnuVIDEODISK: mov r8d,offset videodiscDev
jmp @f;wmBYE
mnuVIDEOPLAYER: mov r8d,offset szVideoPlayer
@@: mov rcx,pBuffer
call lstrcpy
a1: mov r9d,offset szStop
xor r8d,r8d
mov edx,MCIWNDM_SENDSTRINGA
mov rcx,hWnd
call SendMessage
mov r9,pBuffer
xor r8d,r8d
mov edx,MCIWNDM_OPENA
mov rcx,hWnd
call SendMessage
test eax,eax
jnz NoMedia; .if eax = 0
mov r9d,offset szPlay
xor r8d,r8d
mov edx,MCIWNDM_SENDSTRINGA
mov rcx,hWnd
call SendMessage
test eax,eax
jnz NoMedia; .if eax = 0
mov edx,SW_SHOWNORMAL
mov rcx,hWnd
call ShowWindow
xor r9d,r9d
mov r8d,MCIWNDF_NOPLAYBAR
mov edx,MCIWNDM_CHANGESTYLES
mov rcx,hWnd
call SendMessage
mov r9d,100
xor r8d,r8d
mov edx,MCIWNDM_SETZOOM
mov rcx,hWnd;hWnd
call SendMessage
mov flag_fullscreen,TRUE
jmp @f
NoMedia:mov flag_fullscreen,rbx;FALSE
mov r9d,offset szClose
xor r8d,r8d
mov edx,MCIWNDM_SENDSTRINGA
mov rcx,hWnd
call SendMessage
mov r9d,MCIWNDF_NOPLAYBAR
mov r8d,MCIWNDF_NOPLAYBAR
mov edx,MCIWNDM_CHANGESTYLES
mov rcx,hWnd
call SendMessage
@@: mov edx,TRUE
mov rcx,mcihWnd
call DragAcceptFiles
jmp default
mnuFULLSCREEN:mov edx,SW_SHOWNORMAL
mov rcx,hWnd
call ShowWindow
mov r9d,offset szPlayfullscreen
xor r8d,r8d
mov edx,MCIWNDM_SENDSTRINGA
mov rcx,hWnd
call SendMessage
test eax,eax;.if eax=0
jnz default
mov r9d,MCIWNDF_NOPLAYBAR
mov r8d,MCIWNDF_NOPLAYBAR
mov edx,MCIWNDM_CHANGESTYLES
mov rcx,hWnd;hWnd
call SendMessage
jmp default
mnuABOUT:mov r9d,MB_OK+MB_ICONINFORMATION
mov r8d,offset szAbout
mov edx,offset szAboutText
mov rcx,hWnd
call MessageBox
default:mov rax,lParam
mov [rsp+20h],rax
mov r9,wParam
mov r8,uMsg
mov rdx,hWnd
mov rcx,prevWindow
call CallWindowProc
leave
retn
handle dq mnuFILE,mnuCD,mnuVIDEODISK,mnuVIDEOPLAYER,mnuFULLSCREEN,mnuABOUT
WndProc endp
;---------------------------------------
mcihWnd dq ?
prevWindow dq ?
pBuffer dq ?
hMenu dq ?
flag_fullscreen dq FALSE
szFile db "File",0
szCD db "Audio CD",0
szVideoDisk db "Video CD",0
szVideoPlayer db "vcr",0
szFullScreen db "Full screen",0
LoadFileFilter db "All files",0,"*",0,0;
szAbout db "About program...",0
szPlay db "PLAY",0
szStop db "STOP",0
szClose db "CLOSE",0
szPlayfullscreen db "PLAY FULLSCREEN NOTIFY",0
szAboutText db "Mini-media player",0Dh,0Ah,\
"Based on JTG coding",0
cdaudioDev db "cdaudio",0
vcrExt db "UNKNOWN",0
videodiscDev db "videodisk",0
MediaFileName db "movie.wmv"
handle1 dq szFile,szCD,szVideoDisk,szVideoPlayer,szFullScreen,szAbout
end
-
Win x64 Tutorial #37f: video-player and Component Object Model
OPTION DOTNAME
include temphls.inc
include win64.inc
include kernel32.inc
includelib kernel32.lib
include user32.inc
includelib user32.lib
include comctl32.inc
includelib comctl32.lib
include comdlg32.inc
includelib comdlg32.lib
include ole32.inc
includelib ole32.lib
OPTION PROLOGUE:none
OPTION EPILOGUE:none
IMAGE_BASE equ 400000h
;-------------------------------
CLSCTX_INPROC_SERVER equ 1
WM_GRAPHNOTIFY equ 40Dh
Size_of_buffer equ 100h
;-------------------------------
; IGraphBuilder virtual method table
;-------------------------------
IGraphBuilderVtbl STRUCT
;IUnknown methods
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
;IGraphBuilder methods
AddFilter QWORD ?
RemoveFilter QWORD ?
EnumFilters QWORD ?
FindFilterByName QWORD ?
ConnectDirect QWORD ?
Reconnect QWORD ?
Disconnect QWORD ?
SetDefaultSyncSource QWORD ?
Connect QWORD ?
Render QWORD ?
RenderFile QWORD ?
AddSourceFilter QWORD ?
SetLogFile QWORD ?
Abort QWORD ?
ShouldOperationContinue QWORD ?
IGraphBuilderVtbl ENDS
;-------------------------------
IMediaControlVtbl STRUCT
;IUnknown methods
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
;IMediaControl methods
GetTypeInfoCount QWORD ?
GetTypeInfo QWORD ?
GetIDsOfNames QWORD ?
Invoke_ QWORD ?
Run QWORD ?
Pause_ QWORD ?
Stop QWORD ?
GetState QWORD ?
RenderFile QWORD ?
AddSourceFilter QWORD ?
get_FilterCollection QWORD ?
get_RegFilterCollection QWORD ?
StopWhenReady QWORD ?
IMediaControlVtbl ENDS
;-------------------------------
; IMediaEventEx virtual method table
;-------------------------------
IMediaEventExVtbl STRUCT
;IUnknown methods
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
;IMediaEventEx methods
GetTypeInfoCount QWORD ?
GetTypeInfo QWORD ?
GetIDsOfNames QWORD ?
Invoke_ QWORD ?
GetEventHandle QWORD ?
GetEvent QWORD ?
WaitForCompletion QWORD ?
CancelDefaultHandling QWORD ?
RestoreDefaultHandling QWORD ?
FreeEventParams QWORD ?
SetNotifyWindow QWORD ?
SetNotifyFlags QWORD ?
GetNotifyFlags QWORD ?
IMediaEventExVtbl ENDS
;-----------------------------------------------------
; IGraphBuilder virtual method table
;-----------------------------------------------------
IGraphBuilderVtbl STRUCT
;IUnknown methods
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
;IGraphBuilder methods
AddFilter QWORD ?
RemoveFilter QWORD ?
EnumFilters QWORD ?
FindFilterByName QWORD ?
ConnectDirect QWORD ?
Reconnect QWORD ?
Disconnect QWORD ?
SetDefaultSyncSource QWORD ?
Connect QWORD ?
Render QWORD ?
RenderFile QWORD ?
AddSourceFilter QWORD ?
SetLogFile QWORD ?
Abort QWORD ?
ShouldOperationContinue QWORD ?
IGraphBuilderVtbl ENDS
;-----------------------------------------------------
; IVideoWindow virtual method table
;------------------------------------------------
IVideoWindowVtbl STRUCT
;IUnknown methods
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
;IVideoWindow methods
GetTypeInfoCount QWORD ?
GetTypeInfo QWORD ?
GetIDsOfNames QWORD ?
Invoke_ QWORD ?
put_Caption QWORD ?
get_Caption QWORD ?
put_WindowStyle QWORD ?
get_WindowStyle QWORD ?
put_WindowStyleEx QWORD ?
get_WindowStyleEx QWORD ?
put_AutoShow QWORD ?
get_AutoShow QWORD ?
put_WindowState QWORD ?
get_WindowState QWORD ?
put_BackgroundPalette QWORD ?
get_BackgroundPalette QWORD ?
put_Visible QWORD ?
get_Visible QWORD ?
put_Left QWORD ?
get_Left QWORD ?
put_Width QWORD ?
get_Width QWORD ?
put_Top QWORD ?
get_Top QWORD ?
put_Height QWORD ?
get_Height QWORD ?
put_Owner QWORD ?
get_Owner QWORD ?
put_MessageDrain QWORD ?
get_MessageDrain QWORD ?
get_BorderColor QWORD ?
put_BorderColor QWORD ?
get_FullScreenMode QWORD ?
put_FullScreenMode QWORD ?
SetWindowForeground QWORD ?
NotifyOwnerMessage QWORD ?
SetWindowPosition QWORD ?
GetWindowPosition QWORD ?
GetMinIdealImageSize QWORD ?
GetMaxIdealImageSize QWORD ?
GetRestorePosition QWORD ?
HideCursor QWORD ?
IsCursorHidden QWORD ?
IVideoWindowVtbl ENDS
.code
WinMain proc
local bufferANSI[Size_of_buffer]:BYTE
local bufferUNICODE[Size_of_buffer*2]:BYTE
local pGraph:QWORD
local pControl:QWORD
local pEvent:QWORD
local pWindow:QWORD
push rbp
mov ebp,esp
sub esp,(30h+4*8+sizeof Size_of_buffer*3+15)and(-16)
;AVIOpenFile-------------------------------------------------
;fill OPENFILENAME
push rbx ;<--- align 16 bytes
push rbx;lpTemplateName
push rbx;lpfnHook
push rbx;lCustData
push rbx;lpstrDefExt
push OFN_FILEMUSTEXIST or OFN_PATHMUSTEXIST or OFN_LONGNAMES or \
OFN_EXPLORER or OFN_HIDEREADONLY;Flags & nFileOffset & nFileExtension
push rbx;lpstrTitle
push rbx;lpstrInitialDir
push rbx;nMaxFileTitle
push rbx;lpstrFileTitle
push Size_of_buffer;nMaxFile
lea eax,bufferANSI
push rax;lpstrFile
push rbx;nMaxCustFilter & nFilterIndex
push rbx;lpstrCustomFilter
mov eax,offset Filter
push rax;lpstrFilter
push IMAGE_BASE;hInstance
push rbx;hwndOwner
push sizeof OPENFILENAME;lStructSize
;----------------------------------------------------
mov ecx,esp;адрес OPENFILENAME
mov esi,ecx;
call GetOpenFileName
test eax,eax
jz Exit ; user clicks "Cancel"
inc count
mov qword ptr [rsp+28h],Size_of_buffer*2
lea eax,bufferUNICODE
mov [rsp+20h],rax
or r9d,-1
lea r8d,bufferANSI
xor edx,edx
xor ecx,ecx
call MultiByteToWideChar
;AVIInit -----------------------------------------
xor ecx,ecx
call CoInitialize
lea eax,pGraph
mov [rsp+20h],rax
mov r9d,offset ID_IGraphBuilder
mov r8d,CLSCTX_INPROC_SERVER
xor edx,edx
mov ecx,offset CLSID_FilterGraph
call CoCreateInstance
test eax,eax
jnz Exit ;Unable to create GraphBuilder
inc count
lea r8d,pControl
mov edx,offset ID_IMediaControl
mov rcx,pGraph
mov eax,[rcx]
call [rax].IMediaControlVtbl.QueryInterface;pMC->QueryInterface(IID_IMediaEventEx, (void **)&pME);
test eax,eax
jnz Exit ;Unable to get interface IMediaControl
inc count
lea r8d,pEvent
mov edx,offset ID_IMediaEventEx
mov rcx,pGraph
mov eax,[rcx]
call [rax].IMediaEventExVtbl.QueryInterface
test eax,eax
jnz Exit ;Unable to get interface IMediaEventEx
inc count
lea r8d,pWindow
mov edx,offset ID_IVideoWindow
mov rcx,pGraph
mov eax,[rcx]
call [rax].IVideoWindowVtbl.QueryInterface;pMC->QueryInterface(IID_IVideoWindow, (void**)&pVW);
;AVIRenderFile----------------------------------------------
xor r8d,r8d
lea rdx,bufferUNICODE
mov rcx,pGraph
mov eax,[rcx]
call [rax].IGraphBuilderVtbl.RenderFile;pGB->RenderFile(FileNameW, NULL);
test eax,eax
jnz Exit ;We can not open file
inc count
;AVIPlay-----------------------------------
mov rcx,pControl
mov eax,[rcx]
call [rax].IMediaControlVtbl.Run ;pMC->Run()
;------------------------------------------
lea r8d,pWindow
mov edx,INFINITE
mov rcx,pEvent
mov eax,[rcx]
call [rax].IMediaEventExVtbl.WaitForCompletion
;AVIClose------------------------------------------
mov rcx,pControl
mov eax,[rcx]
call [rax].IMediaControlVtbl.Release
mov rcx,pEvent
mov eax,[rcx]
call [rax].IMediaEventExVtbl.Release
mov rcx,pGraph
mov eax,[rcx]
call [rax].IGraphBuilderVtbl.Release
call CoUninitialize
;---------------------------------------
Exit: xor r9d,r9d
xor r8d,r8d
mov eax,count
mov rdx,[hande+rax*8]
xor ecx,ecx
call MessageBox
xor ecx,ecx
call ExitProcess
WinMain endp
;---------------------------------------
CLSID_FilterGraph GUID <0E436EBB3h,524Fh,11CEh,{09Fh,053h,0,020h,0AFh,0Bh,0A7h,70h}>
;db "NB10"; dd 3031424Eh
ID_IGraphBuilder GUID <056A868A9h,0AD4h,11CEh,{0B0h,03Ah,0,20h,0AFh,0Bh,0A7h,70h}>;56A868A9h, 11CE0AD4h, 20003AB0h, 70A70BAFh
ID_IMediaControl GUID <056A868B1h,0AD4h,11CEh,{0B0h,03Ah,0,20h,0AFh,0Bh,0A7h,70h}>;56A868B1h, 11CE0AD4h, 20003AB0h, 70A70BAFh
ID_IMediaEventEx GUID <056A868B6h,0AD4h,11CEh,{0B0h,03Ah,0,20h,0AFh,0Bh,0A7h,70h}>;56A868C0h, 11CE0AD4h, 20003AB0h, 70A70BAFh
ID_IVideoWindow GUID <056A868B4h,0AD4h,11CEh,{0B0h,03Ah,0,20h,0AFh,0Bh,0A7h,70h}>
Filter db "Video files *.avi; *.qt; *.mov; *.mpg; *.mpeg; *.m1v; *.vob",0
db " *.qt; *.mov; *.mpg; *.mpeg; *.m1v; *.vob; *.wmv",0,0
szAVIOpenError db "Unable to open the video file",0
szGoodbye db "Bye-bye!",0
hande dq str1,str2,str3,str4,szAVIOpenError,szGoodbye
str1 db "Do not select any media files!",0
str2 db "Unable to create GraphBuilder",0
str3 db "Unable to get interface IMediaControl",0
str4 db 'Unable to get interface IMEdiaEvent',0
count dd 0
end
-
to All
Work on the project "Iczelion's Tutoral x64" supposed to work together with the exchange of opinions, bugs, suggestions. Judging by the number of downloads interested in the project about 20 people. I'm interested in whether the examples were run under Windows Seven or Eight or Windows XP x64. Which applications worked without error, and any errors and what these mistakes were concluded. Please do not be silent, feedback is very important for work on the project
Excuse me for my bad english (http://www.cyberforum.ru/images/smilies/blush2.gif)
-
I've checked some of them in W7 64bits and seem to be ok. Thank you.
-
muchas gracias, avcaballero
-
Win x64 Tutorial #27: Tooltip Example
asm-fileinclude win64a.inc
IMAGE_BASE equ 400000h
IDD_MAINDIALOG equ 101
.code
WinMain proc
sub esp,38h
xor r8d,r8d
mov [rsp+20h],r8
mov r9d,offset dialog_procedure
mov edx,IDD_MAINDIALOG
mov ecx,IMAGE_BASE
call DialogBoxParam
xor ecx,ecx
call ExitProcess
call InitCommonControls
WinMain endp
dialog_procedure proc hDlg:QWORD,uMsg:QWORD,wParam:QWORD,lParam:QWORD
local ti:TOOLINFO
local rect:RECT
push rbp
mov ebp,esp
sub esp,(20h+sizeof TOOLINFO+sizeof RECT+15)and(-16)
mov hDlg,rcx
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_CLOSE
je wmCLOSE
xor eax,eax
jmp wmBYE
wmINITDIALOG:xor ecx,ecx
mov esi,IMAGE_BASE
push rcx
push rsi
push rcx
push rcx
shl esi,9
push rsi
push rsi
push rsi
push rsi
mov r9d,TTS_ALWAYSTIP
xor r8d,r8d
mov edx,offset ToolTipsClassName
sub esp,20h
call CreateWindowEx
mov hwndTool,rax
mov ti.cbSize,sizeof TOOLINFO
mov ti.uFlags,TTF_SUBCLASS
mov rcx,hDlg
mov ti.hwnd,rcx
lea edx,rect
call GetWindowRect
mov ebx,3
@@: lea ecx,rect
mov r9d,ebx
mov r8,handle[rbx*8]
lea edx,ti
call SetDlgToolArea
dec ebx
jns @b
lea r8d,ti
mov edx,offset EnumChild
mov rcx,hDlg
call EnumChildWindows
jmp wmBYE
wmCLOSE:xor edx,edx
;mov rcx,hDlg
call EndDialog
wmBYE: leave
ret
dialog_procedure endp
EnumChild proc hwndChild:QWORD,lParam:QWORD
local buffer[256]:BYTE
push rbp
mov ebp,esp
sub esp,(20h+256+15)and(-16)
mov lParam,rdx
mov [rdx+TOOLINFO.uId],rcx;rcx=hwndChild
or [rdx+TOOLINFO.uFlags],TTF_IDISHWND
mov r8d,255
lea edx,buffer
;mov rcx,hwndChild
invoke GetWindowText
lea eax,buffer
mov r9,lParam
mov [r9+TOOLINFO.lpszText],rax
xor r8d,r8d
mov edx,TTM_ADDTOOL
mov rcx,hwndTool
call SendMessage
leave
retn
EnumChild endp
SetDlgToolArea proc lprect:QWORD,lpti:QWORD,lpText:QWORD,id:QWORD
push rbp
mov ebp,esp
sub esp,20h
jmp [handels+r9*8]
id_0: mov [rdx+TOOLINFO.Rect.left],0
mov [rdx+TOOLINFO.Rect.top],0
mov eax,[rcx+RECT.right]
sub eax,[rcx+RECT.left]
shr eax,1
mov [rdx+TOOLINFO.Rect.right],eax
mov eax,[rcx+RECT.bottom]
sub eax,[rcx+RECT.top]
shr eax,1
jmp wmBYE
id_1: mov eax,[rcx+RECT.right]
sub eax,[rcx+RECT.left]
shr eax,1
inc eax
mov [rdx+TOOLINFO.Rect.left],eax
mov [rdx+TOOLINFO.Rect.top],0
mov eax,[rcx+RECT.right]
sub eax,[rcx+RECT.left]
jmp a1
id_2: mov [rdx+TOOLINFO.Rect.left],0
mov eax,[rcx+RECT.bottom]
sub eax,[rcx+RECT.top]
shr eax,1
inc eax
mov [rdx+TOOLINFO.Rect.top],eax
mov eax,[rcx+RECT.right]
sub eax,[rcx+RECT.left]
shr eax,1
jmp a1
id_3: mov eax,[rcx+RECT.right]
sub eax,[rcx+RECT.left]
shr eax,1
inc eax
mov [rdx+TOOLINFO.Rect.left],eax
mov eax,[rcx+RECT.bottom]
sub eax,[rcx+RECT.top]
shr eax,1
inc eax
mov [rdx+TOOLINFO.Rect.top],eax
mov eax,[rcx+RECT.right]
sub eax,[rcx+RECT.left]
a1: mov [rdx+TOOLINFO.Rect.right],eax
mov eax,[rcx+RECT.bottom]
sub eax,[rcx+RECT.top]
wmBYE: mov [rdx+TOOLINFO.Rect.bottom],eax
mov [rdx+TOOLINFO.lpszText],r8;lpText
mov r9d,edx;lpti
xor r8d,r8d;NULL
mov edx,TTM_ADDTOOL
mov rcx,hwndTool
call SendMessage
leave
ret
handels dq id_0, id_1, id_2, id_3
SetDlgToolArea endp
;---------------------------------------------------------
ToolTipsClassName db "Tooltips_class32",0
MainDialogText1 db "This is the upper left area of the dialog",0
MainDialogText2 db "This is the upper right area of the dialog",0
MainDialogText3 db "This is the lower left area of the dialog",0
MainDialogText4 db "This is the lower right area of the dialog",0
handle dq MainDialogText1,MainDialogText2,MainDialogText3,MainDialogText4
hwndTool dq ?
end
rc-file#include "resource.h"
#define IDD_MAINDIALOG 101
#define IDC_OK 1000
#define IDC_EXIT 1001
IDD_MAINDIALOG DIALOG DISCARDABLE 0, 0, 229, 96
STYLE DS_MODALFRAME | DS_3DLOOK | WS_POPUP | WS_VISIBLE | WS_CAPTION |
WS_SYSMENU | DS_CENTER
CAPTION "Tooltip Example"
FONT 8, "MS Sans Serif"
BEGIN
PUSHBUTTON "", -1,0, -4,115,51,WS_VISIBLE+BS_GROUPBOX
PUSHBUTTON "", -1,114,43,115,53,WS_VISIBLE+BS_GROUPBOX
PUSHBUTTON "OK",IDC_OK,55,68,50,14
PUSHBUTTON "E&xit",IDC_EXIT,123,68,50,14
END
-
Win x64 Tutorial #23-1: TrayIcon Demo
asm-fileinclude win64a.inc
include shell32.inc
includelib shell32.lib
IMAGE_BASE equ 400000h
WM_SHELLNOTIFY equ WM_USER+5
IDI_TRAY equ 0
IDM_RESTORE equ 1000
IDM_EXIT equ 1010
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov esi,IMAGE_BASE
mov ecx,offset FileName
call LoadCursorFromFile
mov note.hIcon,rax
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 350
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
xor r8d,r8d
xor r9d,r9d
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
local pt:POINT
push rbp
mov ebp,esp
sub esp,(40h+sizeof POINT+15)and(-16)
mov hWnd,rcx
mov wParam,r8
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_SHELLNOTIFY
je wmSHELLNOTIFY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_SIZE
je wmSIZE
leave
jmp DefWindowProc
wmDESTROY:mov rcx,hPopupMenu
call DestroyMenu
xor ecx,ecx
call ExitProcess
wmCREATE:mov note.hWnd,rcx;rcx=hWnd
call CreatePopupMenu
mov hPopupMenu,rax
mov r9d,offset RestoreString
mov r8d,IDM_RESTORE
xor edx,edx;mov edx,MF_STRING
mov ecx,eax;hPopupMenu
call AppendMenu
mov r9d,offset ExitString
mov r8d,IDM_EXIT
xor edx,edx;mov edx,MF_STRING
mov rcx,hPopupMenu
call AppendMenu
jmp wmBYE
wmSHELLNOTIFY:or r8,r8;.if wParam==IDI_TRAY
jne wmBYE
cmp r9,WM_RBUTTONDOWN
jne @f
wmSHELLNOTIFY_WM_RBUTTONDOWN:
lea ecx,pt
call GetCursorPos
mov rcx,hWnd
call SetForegroundWindow
mov [rsp+30h],rbx;0
mov rax,hWnd
mov [rsp+28h],rax
mov [rsp+20h],rbx;0
mov r9d,pt.y
mov r8d,pt.x
mov edx,TPM_RIGHTALIGN
mov rcx,hPopupMenu
call TrackPopupMenu
xor r9d,r9d
xor r8d,r8d
mov edx,WM_NULL
mov rcx,hWnd
call PostMessage
jmp wmBYE
@@: cmp r9,WM_LBUTTONDBLCLK
jne wmBYE
wmSHELLNOTIFY_WM_LBUTTONDBLCLK:
xor r9d,r9d;0
mov r8d,IDM_RESTORE
mov edx,WM_COMMAND
mov rcx,hWnd
call SendMessage
jmp wmBYE
wmCOMMAND:or r9,r9;.if lParam==0 message is not from control
jnz wmBYE
mov edx,offset note
mov ecx,NIM_DELETE
call Shell_NotifyIcon
mov rcx,hWnd
cmp word ptr wParam,IDM_RESTORE
jne @f
wmCOMMAND_IDM_RESTORE:
mov edx,SW_RESTORE
call ShowWindow
jmp wmBYE
@@: call DestroyWindow
jmp wmBYE
wmSIZE: cmp r8d,SIZE_MINIMIZED;.if wParam==SIZE_MINIMIZED
jnz wmBYE
xor edx,edx;mov edx,SW_HIDE
call ShowWindow
mov edx,offset note
xor ecx,ecx;mov ecx,NIM_ADD
call Shell_NotifyIcon
wmBYE: leave
retn
WndProc endp
;---------------------------------------
RestoreString db "&Restore",0
ExitString db "E&xit Program",0
FileName db "..\Images\Cursor.cur",0
note label NOTIFYICONDATA
dd sizeof NOTIFYICONDATA,0
dq ?
dd IDI_TRAY
dd NIF_ICON+NIF_MESSAGE+NIF_TIP
dd WM_SHELLNOTIFY,0
dq ?
ClassName db 'Win64 Iczelion''s lesson #23-1: TrayIcon Demo'
db 64-(lengthof ClassName) dup(0)
hPopupMenu dq ?
end
-
Win x64 Tutorial #23-2: TrayIcon Demo
asm-fileinclude win64a.inc
include shell32.inc
includelib shell32.lib
IMAGE_BASE equ 400000h
WM_SHELLNOTIFY equ WM_USER+5
IDI_TRAY equ 0
IDM_SHOWHIDE equ 100
IDM_EXIT equ 101
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov esi,IMAGE_BASE
mov ecx,offset FileName
call LoadCursorFromFile
mov note.hIcon,rax
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 350
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
xor r8d,r8d
xor r9d,r9d
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
local pt:POINT
push rbp
mov ebp,esp
sub esp,(40h+sizeof POINT+15)and(-16)
mov hWnd,rcx
mov wParam,r8
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_SHELLNOTIFY
je wmSHELLNOTIFY
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_SYSCOMMAND
je wmSYSCOMMAND
defwndproc:leave
jmp DefWindowProc
wmDESTROY:mov edx,offset note
mov ecx,NIM_DELETE
call Shell_NotifyIcon
mov rcx,hPopupMenu
call DestroyMenu
xor ecx,ecx
call ExitProcess
wmCOMMAND:or r9,r9;.if lParam==0 message is not from control
jnz wmBYE
cmp word ptr wParam,IDM_SHOWHIDE
je showhide
cmp word ptr wParam,IDM_EXIT
jne wmBYE
@@: call DestroyWindow
jmp wmBYE
wmSYSCOMMAND:cmp r8,SC_MINIMIZE; when user presses "minimize" button, main window
jne defwndproc; should be hidden
showhide:xor showflag,1
mov edx,showflag
lea edx,[rdx+rdx*4]
call ShowWindow
jmp wmBYE
wmSHELLNOTIFY:or r8,r8;.if wParam==IDI_TRAY WM_SHELLNOTIFY handler - here we handle actions
jne wmBYE; like clicking on our icon
cmp r9,WM_LBUTTONDOWN
je showhide
cmp r9,WM_RBUTTONDOWN
jne wmBYE
wmSHELLNOTIFY_WM_RBUTTONDOWN:
lea ecx,pt
call GetCursorPos
mov rcx,hWnd
call SetForegroundWindow
mov [rsp+30h],rbx;0
mov rax,hWnd
mov [rsp+28h],rax
mov [rsp+20h],rbx;0
mov r9d,pt.y
mov r8d,pt.x
mov edx,TPM_RIGHTALIGN
mov rcx,hPopupMenu
call TrackPopupMenu
xor r9d,r9d
xor r8d,r8d
mov edx,WM_NULL
mov rcx,hWnd
call PostMessage
jmp wmBYE
wmCREATE:mov note.hWnd,rcx;rcx=hWnd
mov edx,offset note
xor ecx,ecx;NIM_ADD=0
call Shell_NotifyIcon
call CreatePopupMenu
mov hPopupMenu,rax
mov r9d,offset szShowHide
mov r8d,IDM_SHOWHIDE
xor edx,edx;MF_STRING=0
mov ecx,eax;hPopupMenu
call AppendMenu
mov r9d,offset szExit
mov r8d,IDM_EXIT
xor edx,edx;MF_STRING=0
mov rcx,hPopupMenu
call AppendMenu
wmBYE: leave
retn
WndProc endp
;---------------------------------------
szShowHide db "&Show/Hide",0
szExit db "E&xit",0
FileName db "..\Images\Cursor.cur",0
showflag dd 1 ;if main window is visible showflag=1
note label NOTIFYICONDATA
dd sizeof NOTIFYICONDATA,0
dq ?
dd IDI_TRAY
dd NIF_ICON+NIF_MESSAGE+NIF_TIP
dd WM_SHELLNOTIFY,0
dq ?
ClassName db 'Win64 Iczelion''s lesson #23-2: TrayIcon Demo'
db 64-(lengthof ClassName) dup(0)
hPopupMenu dq ?
end
-
Win x64 Tutorial #23-3: TrayIcon Animation
asm-fileinclude win64a.inc
include shell32.inc
includelib shell32.lib
IMAGE_BASE equ 400000h
WM_SHELLNOTIFY equ WM_USER+5
IDI_TRAY equ 0
IDM_SHOWHIDE equ 100
IDM_EXIT equ 101
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
mov esi,IMAGE_BASE
mov ecx,offset FileName
call LoadCursorFromFile
mov note.hIcon,rax
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 200
push 408
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
lea edi,msg
@@: mov ecx,edi
xor edx,edx
xor r8d,r8d
xor r9d,r9d
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
local ps:PAINTSTRUCT
push rbp
mov ebp,esp
sub esp,(40h+sizeof PAINTSTRUCT+20h+15)and(-16)
mov hWnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_TIMER
je wmTIMER
cmp edx,WM_PAINT
je wmPAINT
defwndproc:leave
jmp DefWindowProc
wmDESTROY:xor edx,edx
call KillTimer
mov edx,offset note
mov ecx,NIM_DELETE
call Shell_NotifyIcon
xor ecx,ecx
call ExitProcess
wmPAINT:lea edx,ps
call BeginPaint
mov r9,note.hIcon
mov r8d,100
mov edx,330
mov ecx,eax
call DrawIcon
lea edx,ps
mov rcx,hWnd
call EndPaint
jmp wmBYE
wmTIMER:mov rdx,index
inc edx
cmp dl,11
jb @f
xor edx,edx
@@: mov index,rdx
mov rdx,[hIcon2+rdx*8]
mov note.hIcon,rdx
mov edx,offset note
mov ecx,NIM_MODIFY
call Shell_NotifyIcon
mov r8d,TRUE
xor edx,edx
mov rcx,hWnd
call InvalidateRect;send WM_PAINT
jmp wmBYE
wmCREATE:mov note.hWnd,rcx;rcx=hWnd
mov edx,offset note
xor ecx,ecx;NIM_ADD=0
call Shell_NotifyIcon
mov ebx,11
@@: mov qword ptr [rsp+28h],0
mov r9d,16
mov [rsp+20h],r9
mov r8d,IMAGE_ICON
mov edx,ebx
mov ecx,IMAGE_BASE
call LoadImage
mov hIcon2[rbx*8-8],rax
dec ebx
jnz @b
xor r9d,r9d
mov r8d,500
xor edx,edx
mov rcx,hWnd
call SetTimer
wmBYE: leave
retn
WndProc endp
;---------------------------------------
FileName db "..\Images\Cursor.cur",0
note label NOTIFYICONDATA
dd sizeof NOTIFYICONDATA,0
dq ?
dd IDI_TRAY
dd NIF_ICON+NIF_MESSAGE+NIF_TIP
dd WM_SHELLNOTIFY,0
dq ?
ClassName db 'Win64 Iczelion''s lesson #23-2: TrayIcon Animation'
db 64-(lengthof ClassName) dup(0)
index dq 0
hIcon2 dq 12 dup(?)
end
rc-file#define icon1 1
#define icon2 2
#define icon3 3
#define icon4 4
#define icon5 5
#define icon6 6
#define icon7 7
#define icon8 8
#define icon9 9
#define icon10 10
#define icon11 11
icon1 ICON "..\\Images\\01.ico"
icon2 ICON "..\\Images\\02.ico"
icon3 ICON "..\\Images\\03.ico"
icon4 ICON "..\\Images\\04.ico"
icon5 ICON "..\\Images\\05.ico"
icon6 ICON "..\\Images\\06.ico"
icon7 ICON "..\\Images\\07.ico"
icon8 ICON "..\\Images\\08.ico"
icon9 ICON "..\\Images\\09.ico"
icon10 ICON "..\\Images\\10.ico"
icon11 ICON "..\\Images\\11.ico"
-
Win x64 Tutorial #5a: few ways of Text output
asm-fileinclude win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
.code
WinMain proc
local msg:MSG
local WinDim:RECT
local hwnd:QWORD
local tci:TCITEMA
push rbp
mov ebp,esp
sub esp,(sizeof MSG+sizeof RECT+sizeof TCITEMA+8+15)and(-16)
call InitCommonControls
xor ebx,ebx
mov esi,IMAGE_BASE
mov eax,10027h
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push COLOR_WINDOW;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hwnd,rax
lea edx,WinDim
mov ecx,eax
call GetClientRect
push rbx
push IMAGE_BASE
push rbx
push hwnd
mov eax,WinDim.bottom
push rax
mov eax,WinDim.right
push rax
push rbx
push rbx
mov r9d,WS_VISIBLE or WS_TABSTOP or WS_CHILD
mov r8d,offset NullString
mov edx,offset aSysTabControl32
mov ecx,WS_EX_RIGHTSCROLLBAR
sub esp,20h
call CreateWindowEx
mov hTabWnd,rax
push rbx
push IMAGE_BASE
push rbx
push rax
push 256
push 512
push 180
push 120
mov r9d,SS_LEFT or WS_CHILD
mov r8d,offset expTxt0
mov edx,offset aStatic
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hStaticText,rax
mov tci.imask,TCIF_TEXT
or tci.iImage, -1
@@: mov rax,handle1[rbx*8]
mov tci.pszText,rax
mov tci.lParam,rbx
neg rax
add rax,handle1[rbx*8+8]
mov tci.cchTextMax,eax
lea r9d,tci
mov r8d,ebx
mov edx,TCM_INSERTITEMA
mov rcx,hTabWnd
call SendMessage
inc ebx
cmp bl,8
jb @b
xor ebx,ebx
; mov pptxt.x,0
; mov pptxt.y,40
; mov pptxt.n,expTxt7-expTxt6
; mov eax,offset expTxt6
; mov pptxt.lpStr,rax
; mov pptxt.uiFlags,ETO_OPAQUE
; mov pptxt.icl.left,0
; mov pptxt.icl.top,0
; mov pptxt.icl.right,100
; mov pptxt.icl.bottom,200
; mov pptxt.pdx,0
lea edi,msg
@@: mov ecx,edi
xor edx,edx
xor r8d,r8d
xor r9d,r9d
call GetMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
WndProc proc hWnd:QWORD,uMsg:QWORD,wParam:QWORD,lParam:QWORD
local expRect:RECT
local ps:PAINTSTRUCT
local hdc:QWORD
push rbp
mov ebp,esp
sub esp,(48h+sizeof PAINTSTRUCT+sizeof RECT+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_NOTIFY
je wmNOTIFY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_CTLCOLORSTATIC;WM_CTLCOLORSTATIC=138h
je wmCTLCOLORSTATIC
wmDEFAULT:leave
jmp DefWindowProc
wmDESTROY: xor ecx,ecx
call ExitProcess
wmCTLCOLORSTATIC:mov edx,0DEEBEFh
mov ecx,r8d
call SetBkColor
mov ecx,NULL_BRUSH
call GetStockObject
jmp wmBYE
wmNOTIFY:cmp [r9+NMHDR._code],TCN_SELCHANGE
jne wmDEFAULT
xor r9d,r9d
xor r8d,r8d
mov edx,TCM_GETCURSEL
mov rcx,hTabWnd
call SendMessage
mov _Page,eax
mov r9d,offset ClassName
xor r8d,r8d
mov edx,WM_SETTEXT
mov rcx,hWnd
call SendMessage
mov edx,SW_HIDE
mov rcx,hStaticText
call ShowWindow
; xor r8d,r8d
; xor edx,edx
; mov rcx,hWnd
; call InvalidateRect
; jmp wmBYE
wmPAINT:lea edx,expRect
mov rcx,hTabWnd
call GetClientRect
add expRect.bottom,400
lea edx,ps
mov rcx,hWnd
call BeginPaint
lea edx,expRect
mov rcx,hTabWnd
call GetClientRect
add expRect.top,40
mov rcx,hTabWnd
call GetDC
mov hdc,rax
mov r8d,COLOR_BTNFACE+1
lea edx,expRect
mov ecx,eax
call FillRect
mov edx,TRANSPARENT
mov rcx,hdc
call SetBkMode
mov eax,_Page
jmp [handle+rax*8];Tab selection
ExtTextOut1::mov qword ptr [rsp+38h],0;rbx
mov qword ptr [rsp+30h],lengthof expTxt2-1
mov eax,offset expTxt2
mov [rsp+28h],rax
lea eax,expRect
mov [rsp+20h],rax
xor r9d,r9d
mov r8d,40
mov edx,40
mov rcx,hdc
call ExtTextOut
jmp a1
STATICText::mov edx,SW_SHOW
mov rcx,hStaticText
call ShowWindow
jmp a1
DrawTextEx1::
mov qword ptr [rsp+28h],0;rbx
mov qword ptr [rsp+20h],DT_LEFT or DT_WORDBREAK or DT_EXPANDTABS or \
DT_END_ELLIPSIS or DT_MODIFYSTRING or DT_WORD_ELLIPSIS
lea r9,expRect
or r8,-1
mov edx,offset expTxt5
mov rcx,hdc
call DrawTextEx
jmp a1
PolyTextOut1::mov r8d,6
mov edx,offset pptxt
mov rcx,hdc
call PolyTextOut
jmp a1
TextOut1::mov qword ptr [rsp+20h],lengthof expTxt3A-1
mov r9d,offset expTxt3A
mov r8d,100
mov edx,40
mov rcx,hdc
call TextOut
mov qword ptr [rsp+20h],lengthof expTxt3B-1
mov r9d,offset expTxt3B
mov r8d,120
mov edx,40
mov rcx,hdc
call TextOut
mov qword ptr [rsp+20h],lengthof expTxt3C-1
mov r9d,offset expTxt3C
mov r8d,140
mov edx,40
mov rcx,hdc
call TextOut
mov qword ptr [rsp+20h],lengthof expTxt3D-1
mov r9d,offset expTxt3D
mov r8d,160
mov edx,40
mov rcx,hdc
call TextOut
mov qword ptr [rsp+20h],lengthof expTxt3E-1
mov r9d,offset expTxt3E
mov r8d,180
mov edx,40
mov rcx,hdc
call TextOut
jmp a1
DrawText1::mov qword ptr [rsp+20h],DT_WORDBREAK
lea r9d,expRect
or r8,-1
mov edx,offset expTxt1
mov rcx,hdc
call DrawText
jmp a1
TabbedTextOut1::mov qword ptr [rsp+38h],0;rbx
mov qword ptr [rsp+30h],0;rbx
mov qword ptr [rsp+28h],0;rbx
or qword ptr [rsp+20h],-1
mov r9d,offset expTxt4
mov r8d,40
mov edx,40
mov rcx,hdc
call TabbedTextOut
jmp a1
SetText1::mov r9d,offset expTxt7
xor r8d,r8d
mov edx,WM_SETTEXT
mov rcx,hWnd
call SendMessage
a1: mov rdx,hdc
mov rcx,hTabWnd
call ReleaseDC
lea edx,ps
mov rcx,hWnd
call EndPaint
wmBYE: leave
ret
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #5a: few ways of Text output'
NullString db 0
hTabWnd dq ?
aSysTabControl32 db "SysTabControl32",0
tab0 db "Static",0
tab1 db "DrawTextEx",0
tab2 db "TextOut",0
tab3 db "TabbedTextOut",0
tab4 db "DrawText",0
tab5 db "PolyTextOut",0
tab6 db "ExtTextOut",0
tab7 db "SetText",0
handle1 dq tab0,tab1,tab2,tab3,tab4,tab5,tab6,tab7,handle1
handle dq STATICText,DrawTextEx1,TextOut1,TabbedTextOut1,DrawText1
dq PolyTextOut1,ExtTextOut1,SetText1
;---------------------------------------------------------------------------------------------
expTxt0 db '1) Text output using STATIC ', 10,' Understands newlines and tabs line ', 10
db 'does not require processing WM_PAINT messages',0
;---------------------------------------------------------------------------------------------
expTxt1 db '5) To display multiple lines of text within the boundaries of a given rectangular area using DrawText API ', 10,' description ', 10
db 'function DrawText (DC: HDC; Str: PChar; Count: Integer; var Rect: TRect; Format: Word): Integer;', 10
db 'Draws fopmatipovanny text. Type fopmatipovaniya indicated PARAMETERS Format. If not explicitly dt_NoClip, ', 10
db 'text vypezaetsya in ogpanichivayuschy ppyamougolnik.', 10, 'PARAMETERS:', 10
db 'DC: symbols are device context.', 10, 'Str: you draw with string. If Count = -1, it must end with a null character. ', 10
db 'Rect: TRect, ogpanichivayuschy text.', 10, 'Format: One or more constants: dt_Bottom, dt_CalcRect, dt_Center, dt_ExpandTabs,', 10
db 'dt_ExternalLeading, dt_Left, dt_NoClip, dt_NoPrefix, dt_Right, dt_SingleLine, dt_TabStop, dt_Top, dt_VCenter and', 10
db 'dt_WordBreak. See. Section "Flags fopmatipovaniya text DURING pisovanii, dt_" in Chapter 1. ', 10
db 'Return value: The height of the text.', 10, 'function is in a file user32.dll',0
;---------------------------------------------------------------------------------------------
expTxt2 db '7) ExtTextOut function allows you to output text string '
db 'in the specified rectangle using the current font and manages Background mode',0;разобраться
;---------------------------------------------------------------------------------------------
expTxt3A db '3) Text output using TextOut. Function displays the text ',0
expTxt3B db 'in the given coordinates, which are always given with respect',0
expTxt3C db 'to the (upper left corner) of the window. Does not understand hyphens and',0
expTxt3D db 'tabs line. When redrawing the workspace required to provide processing',0
expTxt3E db 'WM_PAINT. To display these lines TextOut function calls five times!',0
;---------------------------------------------------------------------------------------------
expTxt4 db 'To create a multi-column table with aligned columns of text, use ',9,' TabbedTextOut API',0
;---------------------------------------------------------------------------------------------
expTxt5 db '2) The DrawText function draws formatted text in the specified rectangle. It formats the text according to the specified method (expanding tabs, justifying characters, breaking lines, and so forth). '
db ' To specify additional formatting options, use the DrawTextEx function.',0
;---------------------------------------------------------------------------------------------
expTxt6a db '6) API draws several strings using the font and text colors currently selected in the specified device context. '
expTxt6b db 'BOOL PolyTextOut('
expTxt6c db ' HDC hdc, // handle of device context'
expTxt6d db ' CONST POLYTEXT *pptxt, // address of array of structures that identify strings'
expTxt6e db ' int cStrings // number of structures in array'
expTxt6f db ' );'
;---------------------------------------------------------------------------------------------
expTxt7 db 'Text output in the window title through SendMessage',0
expTxt8 db 'Text output using PolyTextOut API',0
pptxt POLYTEXT <0,40,expTxt6b-expTxt6a,expTxt6a,ETO_OPAQUE,{0,0,100,200},0>
POLYTEXT <0,60,expTxt6c-expTxt6b,expTxt6b,ETO_OPAQUE,{0,0,100,200},0>
POLYTEXT <0,80,expTxt6d-expTxt6c,expTxt6c,ETO_OPAQUE,{0,0,100,200},0>
POLYTEXT <0,100,expTxt6e-expTxt6d,expTxt6d,ETO_OPAQUE,{0,0,100,200},0>
POLYTEXT <0,120,expTxt6f-expTxt6e,expTxt6e,ETO_OPAQUE,{0,0,100,200},0>
POLYTEXT <0,140,expTxt7-expTxt6f,expTxt6f,ETO_OPAQUE,{0,0,100,200},0>
aStatic db 'STATIC',0
hStaticText dq ?
_Page dd ?
end
-
Win x64 Tutorial #35: IczEdit version 3.0
rc-file#include "c:\\masm64\\include\\resource.h"
#define IDC_NEXT 1003
#define IDR_MAINMENU 101
#define IDD_OPTIONDLG 101
#define IDD_FINDDLG 102
#define IDD_GOTODLG 103
#define IDD_REPLACEDLG 104
#define IDR_MAINACCEL 105
#define IDC_BACKCOLORBOX 1000
#define IDC_TEXTCOLORBOX 1001
#define IDC_OK 1002
#define IDC_CANCEL 1003
#define IDC_FINDEDIT 1000
#define IDC_MATCHCASE 1001
#define IDC_REPLACEEDIT 1001
#define IDC_WHOLEWORD 1002
#define IDC_DOWN 1003
#define IDC_UP 1004
#define IDC_LINENO 1005
#define IDM_OPEN 40001
#define IDM_SAVE 40002
#define IDM_CLOSE 40003
#define IDM_SAVEAS 40004
#define IDM_EXIT 40005
#define IDM_COPY 40006
#define IDM_CUT 40007
#define IDM_PASTE 40008
#define IDM_DELETE 40009
#define IDM_SELECTALL 40010
#define IDM_OPTION 40011
#define IDM_UNDO 40012
#define IDM_REDO 40013
#define IDM_FIND 40014
#define IDM_FINDNEXT 40015
#define IDM_REPLACE 40016
#define IDM_GOTOLINE 40017
#define IDM_FINDPREV 40018
IDR_MAINMENU MENU DISCARDABLE
BEGIN
POPUP "&File"
BEGIN
MENUITEM "&Open", IDM_OPEN
MENUITEM "&Close", IDM_CLOSE
MENUITEM "&Save", IDM_SAVE
MENUITEM "Save &As", IDM_SAVEAS
MENUITEM SEPARATOR
MENUITEM "E&xit", IDM_EXIT
END
POPUP "&Edit"
BEGIN
MENUITEM "&Undo", IDM_UNDO
MENUITEM "&Redo", IDM_REDO
MENUITEM "&Copy", IDM_COPY
MENUITEM "C&ut", IDM_CUT
MENUITEM "&Paste", IDM_PASTE
MENUITEM SEPARATOR
MENUITEM "&Delete", IDM_DELETE
MENUITEM SEPARATOR
MENUITEM "Select &All", IDM_SELECTALL
END
POPUP "&Search"
BEGIN
MENUITEM "&Find...\tCtrl+F", IDM_FIND
MENUITEM "Find &Next\tF3", IDM_FINDNEXT
MENUITEM "Find &Prev.\tCtrl+F3", IDM_FINDPREV
MENUITEM "&Replace..\tCtrl+R", IDM_REPLACE
MENUITEM SEPARATOR
MENUITEM "&Go To Line\tCtrl+G", IDM_GOTOLINE
END
MENUITEM "Options", IDM_OPTION
END
IDD_OPTIONDLG DIALOG DISCARDABLE 0, 0, 183, 54
STYLE DS_MODALFRAME | DS_CENTER | WS_POPUP | WS_VISIBLE | WS_CAPTION |
WS_SYSMENU
CAPTION "Options"
FONT 8, "MS Sans Serif"
BEGIN
DEFPUSHBUTTON "OK",IDC_OK,137,7,39,14
PUSHBUTTON "Cancel",IDC_CANCEL,137,25,39,14
GROUPBOX "",IDC_STATIC,5,0,124,49
LTEXT "Background Color:",IDC_STATIC,20,14,60,8
LTEXT "",IDC_BACKCOLORBOX,85,11,28,14,SS_NOTIFY | WS_BORDER
LTEXT "Text Color:",IDC_STATIC,20,33,35,8
LTEXT "",IDC_TEXTCOLORBOX,85,29,28,14,SS_NOTIFY | WS_BORDER
END
IDD_FINDDLG DIALOG DISCARDABLE 0, 0, 186, 54
STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
CAPTION "Find.."
FONT 8, "MS Sans Serif"
BEGIN
EDITTEXT IDC_FINDEDIT,42,3,94,12,ES_AUTOHSCROLL
CONTROL "Match Case",IDC_MATCHCASE,"Button",BS_AUTOCHECKBOX |
WS_TABSTOP,6,24,54,10
CONTROL "Whole Word",IDC_WHOLEWORD,"Button",BS_AUTOCHECKBOX |
WS_TABSTOP,6,37,56,10
CONTROL "Down",IDC_DOWN,"Button",BS_AUTORADIOBUTTON | WS_TABSTOP,
83,27,35,10
CONTROL "Up",IDC_UP,"Button",BS_AUTORADIOBUTTON | WS_TABSTOP,83,
38,25,10
DEFPUSHBUTTON "OK",IDC_OK,141,3,39,12
PUSHBUTTON "Cancel",IDC_CANCEL,141,18,39,12
LTEXT "Find what:",IDC_STATIC,5,4,34,8
GROUPBOX "Direction",IDC_STATIC,70,18,64,32
END
IDD_GOTODLG DIALOGEX 0, 0, 106, 30
STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
EXSTYLE WS_EX_TOOLWINDOW
CAPTION "Go To Line"
FONT 8, "MS Sans Serif", 0, 0, 0x1
BEGIN
EDITTEXT IDC_LINENO,29,4,35,11,ES_AUTOHSCROLL | ES_NUMBER,
WS_EX_CLIENTEDGE
DEFPUSHBUTTON "OK",IDC_OK,70,4,31,11
PUSHBUTTON "Cancel",IDC_CANCEL,70,17,31,11
LTEXT "Line :",IDC_STATIC,8,5,18,8
END
IDD_REPLACEDLG DIALOG DISCARDABLE 0, 0, 186, 33
STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
CAPTION "Replace"
FONT 8, "MS Sans Serif"
BEGIN
EDITTEXT IDC_FINDEDIT,51,3,84,12,ES_AUTOHSCROLL
EDITTEXT IDC_REPLACEEDIT,51,17,84,11,ES_AUTOHSCROLL
DEFPUSHBUTTON "OK",IDC_OK,142,3,39,11
PUSHBUTTON "Cancel",IDC_CANCEL,142,17,39,11
LTEXT "Find what:",IDC_STATIC,3,4,34,8
LTEXT "Replace with",IDC_STATIC,3,18,42,8
END
IDR_MAINACCEL ACCELERATORS DISCARDABLE
BEGIN
"F", IDM_FIND, VIRTKEY, CONTROL, NOINVERT
"G", IDM_GOTOLINE, VIRTKEY, CONTROL, NOINVERT
"R", IDM_REPLACE, VIRTKEY, CONTROL, NOINVERT
VK_F3, IDM_FINDNEXT, VIRTKEY, NOINVERT
VK_F3, IDM_FINDPREV, VIRTKEY, CONTROL, NOINVERT
END
wordfile.txt[ASSEMBLY]
C1=aaa aad aam aas adc add and arpl bound bsf bsr bswap bt btc btr bts call cbw cdq clc cld cli clts cmc cmov cmp cmps cmpsb cmpsd cmpsw cmpxchg cmpxchg8b cpuid cwd cwde daa das dec div emms enter esc fcmov fcomi fwait hlt idiv imul in inc ins insb insd insw int into invd invlpg iret iretd ja jae jb jbe jc jcxz je jecxz jg jge jl jle jmp jna jnae jnb jnbe jnc jne jng jnge jnl jnle jno jnp jns jnz jo jp jpe jpo js jz lahf lar lds lea leave les lfs lgdt lgs lidt lldt lmsw lock lods lodsb lodsd lodsw loop loope loopne loopnz loopz lsl lss ltr mov movd movq movs movsb movsd movsw movsx movzx msw mul neg nop not or out outs outsb outsd outsw packsswb packssdw paddb paddw paddd paddsb paddsw paddusb paddusw pand pandn
C2=%out .186 .286 .286c .286p .287 .386 .386p .387 .8086 .8087 .alpha .seq .code .const .cref .data .data? .err .err1 .err2 .errb .errdef .errdif .erre .fardata .fardata? .lall .lfcond .list .model .msfloat .radix .sall .sfcond .stack .type .xall .xcref .xlist @curseg @filename @code @codesize @datasize @const @data @data? @fardata @fardata? @stack align assume at byte comm comment common compact d db dd df dosseg dup fq dt dw dword else end endif endm endp ends eq equ even exitm extrn far ge group h high huge ifdef include includelib irp irpc label large le length low local lt macro mask medium memory name near offset org page para proc public purge q record rept seg segment shl short size shr small stack struct subttl this tiny title type use16 use32 width word xor
C3=ah al ax bh bl bp bx ch cl cs cx dh di dl ds dx eax ebx ecx edi edx esi es ip si sp
C4=.if .else .elseif .endif .while .endw
C5=setng setnge setnl setnle setno setnp setns setnz seto setp setpe setpo sets setz sgdt shld shrd sidt sldt smsw stc std sti stos stosb stosd stosw str sub test verr verw wbinvd wrmsr xadd xchg xlat xlatb invoke addr
C6=pcmpeqb pcmpeqw pcmpeqd pcmpgtb pcmpgtw pcmpgtd pmulhw pmullw pmaddwd pop popa popad popf popfd por psllw pslld psllq psrlw psrld psrlq psraw psrad psubb psubw psubd psubsb psubsw psubusb psubusw punpckhbw punpckhwd punpckhdq punpcklbw punpcklwd punpckldq push pusha pushad pushf pushfd rcl rcr rdmsr rdpmc rdtsc rep repe repne repnz repz ret retf retn rol ror rsm sahf sal sar sbb scas scasb scasd scasw setae setb setbe setc sete setg setge setl setle setna setnae setnb setnc setne
C7=
C8=
C9=
C10=
asm-file first partinclude win64a.inc
include comdlg32.inc
include gdi32.inc
includelib gdi32.lib
includelib comdlg32.lib
IMAGE_BASE equ 400000h
WORDINFO struct
WordLen dd ? ; the length of the word: used as a quick comparison
pszWord dd ? ; pointer to the word
pColor dd ? ; point to the dword that contains the color used to hilite the word
NextLink dd ? ; point to the next WORDINFO structure
WORDINFO ends
IDR_MAINMENU equ 101
IDM_OPEN equ 40001
IDM_SAVE equ 40002
IDM_CLOSE equ 40003
IDM_SAVEAS equ 40004
IDM_EXIT equ 40005
IDM_COPY equ 40006
IDM_CUT equ 40007
IDM_PASTE equ 40008
IDM_DELETE equ 40009
IDM_SELECTALL equ 40010
IDM_OPTION equ 40011
IDM_UNDO equ 40012
IDM_REDO equ 40013
IDM_FIND equ 40014
IDM_FINDNEXT equ 40015
IDM_REPLACE equ 40016
IDM_GOTOLINE equ 40017
IDM_FINDPREV equ 40018
IDD_OPTIONDLG equ 101
IDD_FINDDLG equ 102
IDD_GOTODLG equ 103
IDD_REPLACEDLG equ 104
IDR_MAINACCEL equ 105
IDC_BACKCOLORBOX equ 1000
IDC_TEXTCOLORBOX equ 1001
IDC_OK equ 1002
IDC_CANCEL equ 1003
IDC_FINDEDIT equ 1000
IDC_MATCHCASE equ 1001
IDC_REPLACEEDIT equ 1001
IDC_WHOLEWORD equ 1002
IDC_DOWN equ 1003
IDC_UP equ 1004
IDC_LINENO equ 1005
RichEditID equ 300
.code
WinMain proc
LOCAL msg:MSG
local hwnd:QWORD
push rbp
mov ebp,esp
sub esp,(sizeof MSG+8+15)and(-16)
mov ecx,offset RichEditDLL
call LoadLibrary
or eax,eax
jnz @f
mov r9d,MB_OK or MB_ICONERROR
mov r8d,offset ClassName
mov edx,offset NoRichEdit
xor ecx,ecx
call MessageBox
xor ecx,ecx
call ExitProcess
@@: mov hRichEdit,rax
mov byte ptr [FindBuffer],0
mov byte ptr [ReplaceBuffer],0
invoke GetProcessHeap
mov hMainHeap,rax
;===========================================================
; Load the words to be hilighted
;===========================================================
call FillHiliteInfo
xor ebx,ebx
mov esi,IMAGE_BASE
mov eax,10027h
mov edi,offset ClassName
push rax ;hIconSm
push rdi ;lpszClassName
push IDR_MAINMENU;lpszMenuName
push COLOR_WINDOW+1;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW or WS_VISIBLE
mov r8d,edi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hwnd,rax
mov edx,offset Rect
mov ecx,eax
call GetClientRect
push rbx;0
push IMAGE_BASE
push RichEditID
push hwnd
mov eax,Rect.bottom
push rax
mov eax,Rect.right
push rax
push rbx
push rbx
mov r9d,WS_CHILD or WS_VISIBLE or ES_MULTILINE or WS_VSCROLL or WS_HSCROLL or ES_NOHIDESEL
mov r8d,ebx
mov edx,offset RichEditClass
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
mov hwndRichEdit,rax
;=======================================================
; Check the richedit version
;=======================================================
mov r9d,TO_SIMPLELINEBREAK
mov r8d,TO_SIMPLELINEBREAK
mov edx,EM_SETTYPOGRAPHYOPTIONS
mov rcx,hwndRichEdit
call SendMessage
mov r9d,1
mov r8d,1
mov edx,EM_GETTYPOGRAPHYOPTIONS
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; means this message is not processed
mov RichEditVersion,2
je @f
inc RichEditVersion
;=============================================================================
; Make it emulate system edit control so the text color update doesn't take very long
;=============================================================================
mov r9d,SES_EMULATESYSEDIT
mov r8d,SES_EMULATESYSEDIT
mov edx,EM_SETEDITSTYLE
mov rcx,hwndRichEdit
call SendMessage
;=======================================================
; Subclass the richedit control
;=======================================================
@@: mov r8d,offset NewRichEditProc
mov edx,GWL_WNDPROC
mov rcx,hwndRichEdit
call SetWindowLongPtr
mov OldWndProc,rax
;=============================================================
; Set the text limit. The default is 64K
;=============================================================
mov r9d,ebx;0
or r8d,-1
mov edx,EM_LIMITTEXT
mov rcx,hwndRichEdit
call SendMessage
-
asm-file second part
;=============================================================
; Set the default text/background color
;=============================================================
call SetColor
mov r9d,ebx;0
mov r8d,ebx;FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
;============================================================
; set event mask
;============================================================
mov r9d,ENM_MOUSEEVENTS
xor r8d,r8d
mov edx,EM_SETEVENTMASK
mov rcx,hwndRichEdit
call SendMessage
mov r9d,ebx;0
mov r8d,ebx;0
mov edx,EM_EMPTYUNDOBUFFER
mov rcx,hwndRichEdit
call SendMessage
mov edx,IDR_MAINACCEL
mov ecx,IMAGE_BASE
call LoadAccelerators
mov hAccel,rax
lea edi,msg
@@: mov ecx,edi
xor edx,edx
mov r8d,ebx
mov r9d,ebx
call GetMessage
mov edx,edi
mov rcx,hSearch
call IsDialogMessage
or eax,eax;.if eax==FALSE
jnz @b
mov r9d,edi
mov rdx,hAccel
mov rcx,hwnd
call TranslateAccelerator
or eax,eax;.if eax==0
jnz @b
mov ecx,edi
call TranslateMessage
mov ecx,edi
call DispatchMessage
jmp @b
WinMain endp
StreamInProc proc hFile:QWORD,pBuffer:QWORD, NumBytes:QWORD, pBytesRead:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov qword ptr [esp+20h],0
call ReadFile;,hFile,pBuffer,NumBytes,pBytesRead,0
xor eax,1
leave
retn
StreamInProc endp
StreamOutProc proc hFile:QWORD,pBuffer:QWORD, NumBytes:QWORD, pBytesWritten:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov qword ptr [esp+20h],0
call WriteFile;hFile,pBuffer,NumBytes,pBytesWritten,0
xor eax,1
leave
retn
StreamOutProc endp
CheckModifyState proc hWnd:QWORD
push rbp
mov ebp,esp
sub esp,20h
mov hWnd,rcx
xor r9d,r9d
xor r8d,r8d
mov edx,EM_GETMODIFY
mov rcx,hwndRichEdit
call SendMessage
or eax,eax;.if eax!=0
jz wmBYE
mov r9d,MB_YESNOCANCEL
mov r8d,offset ClassName
mov edx,offset WannaSave
mov rcx,hWnd
call MessageBox
cmp eax,IDYES;.if eax==IDYES
jnz @f
xor r9d,r9d
mov r8d,IDM_SAVE
mov edx,WM_COMMAND
mov rcx,hWnd
call SendMessage
jmp wmBYE
@@: cmp eax,IDCANCEL;.elseif eax==IDCANCEL
jnz wmBYE
xor eax,eax;mov eax,FALSE
jmp @f
wmBYE: mov eax,TRUE
@@: leave
ret
CheckModifyState endp
SetColor proc
LOCAL cfm:CHARFORMAT
push rbp
mov ebp,esp
sub esp,(20h+sizeof CHARFORMAT+15)and(-16)
mov r9d,BackgroundColor
xor r8d,r8d
mov edx,EM_SETBKGNDCOLOR
mov rcx,hwndRichEdit
call SendMessage
mov edx,sizeof CHARFORMAT
lea ecx,cfm
call RtlZeroMemory
lea r9d,cfm
mov [r9+CHARFORMAT.cbSize],sizeof CHARFORMAT
mov [r9+CHARFORMAT.dwMask],CFM_COLOR
mov eax,TextColor
mov [r9+CHARFORMAT.crTextColor],eax
mov r8d,SCF_ALL
mov edx,EM_SETCHARFORMAT
mov rcx,hwndRichEdit
call SendMessage
leave
ret
SetColor endp
OptionProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL clr:CHOOSECOLOR
local temp:QWORD
push rbp
mov ebp,esp
sub esp,(28h+sizeof CHOOSECOLOR+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmBYE
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CTLCOLORSTATIC
je wmCTLCOLORSTATIC
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
ret
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
sub eax,IDC_BACKCOLORBOX
cmp eax,IDC_CANCEL-IDC_BACKCOLORBOX
ja wmBYE
jmp handle[rax*8]
CANCEL: xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
;mov rcx,hWnd
call SendMessage
jmp wmBYE
BACKCOLORBOX:
mov edx,sizeof clr
lea ecx,clr
call RtlZeroMemory
lea ecx,clr
mov [rcx+CHOOSECOLOR.lStructSize],sizeof clr
mov rax,hWnd
mov [rcx+CHOOSECOLOR.hwndOwner],rax
mov [rcx+CHOOSECOLOR.hInstance],IMAGE_BASE
mov eax,BackgroundColor
mov [rcx+CHOOSECOLOR.rgbResult],eax
mov eax,offset CustomColors
mov [rcx+CHOOSECOLOR.lpCustColors],rax
mov [rcx+CHOOSECOLOR.Flags],CC_ANYCOLOR or CC_RGBINIT
call ChooseColor
or eax,eax;.if eax!=0
jz wmBYE
mov eax,clr.rgbResult
mov BackgroundColor,eax
mov edx,IDC_BACKCOLORBOX
jmp @f
TEXTCOLORBOX:
mov edx,sizeof clr
lea ecx,clr
call RtlZeroMemory
mov eax,TextColor
lea ecx,clr
mov [rcx+CHOOSECOLOR.rgbResult],eax
mov [rcx+CHOOSECOLOR.lStructSize],sizeof clr
mov rax,hWnd
mov [rcx+CHOOSECOLOR.hwndOwner],rax
mov [rcx+CHOOSECOLOR.hInstance],IMAGE_BASE
mov eax,offset CustomColors
mov [rcx+CHOOSECOLOR.lpCustColors],rax
mov [rcx+CHOOSECOLOR.Flags],CC_ANYCOLOR or CC_RGBINIT
call ChooseColor
or eax,eax;.if eax!=0
jz wmBYE
mov eax,clr.rgbResult
mov TextColor,eax
mov edx,IDC_TEXTCOLORBOX
@@: mov rcx,hWnd
call GetDlgItem
mov r8d,TRUE
xor edx,edx
mov ecx,eax
call InvalidateRect
jmp wmBYE
;==================================================================================
; Save the modify state of the richedit control because changing the text color changes the
; modify state of the richedit control.
;==================================================================================
OK: xor r9d,r9d
xor r8d,r8d
mov edx,EM_GETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov temp,rax
call SetColor
mov r8,temp
xor r9d,r9d
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
xor edx,edx
mov rcx,hWnd
call EndDialog
jmp wmBYE
wmCTLCOLORSTATIC:mov edx,IDC_BACKCOLORBOX
call GetDlgItem
cmp rax,lParam;.if eax==lParam
jnz @f
mov ecx,BackgroundColor
jmp @0
@@: mov edx,IDC_TEXTCOLORBOX
mov rcx,hWnd
call GetDlgItem
cmp rax,lParam;.if eax==lParam
jnz wmDEFAULT
mov ecx,TextColor
@0: call CreateSolidBrush
jmp @f
wmCLOSE:xor edx,edx
mov rcx,hWnd
call EndDialog
wmBYE: mov eax,TRUE
@@: leave
retn
handle dq BACKCOLORBOX,TEXTCOLORBOX,OK,CANCEL
OptionProc endp
SearchProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
push rbp
mov ebp,esp
sub esp,30h
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
ret
wmINITDIALOG:mov hSearch,rcx;hWnd
;===================================================
; Select the default search down option
;===================================================
mov r9d,IDC_DOWN
mov r8d,IDC_UP
mov edx,IDC_DOWN
;mov rcx,hWnd
call CheckRadioButton
db 48h;mov eax,offset FindBuffer
dd 202444C7h,FindBuffer;mov [rsp+20h],rax
xor r9d,r9d
mov r8d,WM_SETTEXT
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call SendDlgItemMessage
jmp wmBYE
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
sub eax,IDC_OK
cmp eax,IDC_CANCEL-IDC_OK
ja wmBYE
jmp handle3[rax*8]
OK3: mov uFlags,0
mov r9d,offset findtext.chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov r9d,sizeof FindBuffer
mov r8d,offset FindBuffer
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call GetDlgItemText
or eax,eax;.if eax!=0
jz wmBYE
mov edx,IDC_DOWN
mov rcx,hWnd
call IsDlgButtonChecked
cmp eax,BST_CHECKED
jnz @10
or uFlags,FR_DOWN
mov eax,findtext.chrg.cpMin
cmp eax,findtext.chrg.cpMax
jz @f
mov eax,findtext.chrg.cpMax
mov findtext.chrg.cpMin,eax
@@: mov findtext.chrg.cpMax,-1
jmp @f
@10: mov findtext.chrg.cpMax,0
@@: mov edx,IDC_MATCHCASE
mov rcx,hWnd
call IsDlgButtonChecked
cmp eax,BST_CHECKED
jnz @f
or uFlags,FR_MATCHCASE
@@: mov edx,IDC_WHOLEWORD
mov rcx,hWnd
call IsDlgButtonChecked
cmp eax,BST_CHECKED
jnz @f
or uFlags,FR_WHOLEWORD
@@: mov eax,offset FindBuffer
mov findtext.lpstrText,rax
mov r9d,offset findtext
mov r8d,uFlags
mov edx,EM_FINDTEXTEX
mov rcx,hwndRichEdit
call SendMessage
inc eax;.if eax!=-1
jz wmBYE
mov r9d,offset findtext.chrgText
xor r8d,r8d
mov edx,EM_EXSETSEL
mov rcx,hwndRichEdit
call SendMessage
jmp wmBYE
CANCEL3:xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
mov rcx,hWnd
call SendMessage
jmp wmBYE
wmCLOSE:xor edx,edx
mov hSearch,rdx
;mov rcx,hWnd
call EndDialog
wmBYE: mov eax,TRUE
leave
retn
handle3 dq OK3,CANCEL3
SearchProc endp
ReplaceProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL settext:SETTEXTEX
push rbp
mov ebp,esp
sub esp,(20h+sizeof SETTEXTEX+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
retn
wmINITDIALOG:mov hSearch,rcx;hWnd
mov r8d,offset FindBuffer
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call SetDlgItemText
mov r8d,offset ReplaceBuffer
mov edx,IDC_REPLACEEDIT
mov rcx,hWnd
call SetDlgItemText
jmp wmBYE
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
sub eax,IDC_OK
cmp eax,IDC_CANCEL-IDC_OK
ja wmBYE
jmp handle2[rax*8]
CANCEL: xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
mov rcx,hWnd
call SendMessage
jmp wmBYE
OK: mov r9d,sizeof FindBuffer
mov r8d,offset FindBuffer
mov edx,IDC_FINDEDIT
mov rcx,hWnd
call GetDlgItemText
mov r9d,sizeof ReplaceBuffer
mov r8d,offset ReplaceBuffer
mov edx,IDC_REPLACEEDIT
mov rcx,hWnd
call GetDlgItemText
mov findtext.chrg.cpMin,0
mov findtext.chrg.cpMax,-1
mov eax,offset FindBuffer
mov findtext.lpstrText,rax
mov settext.flags,ST_SELECTION
mov settext.codepage,CP_ACP
@@: mov r9d,offset findtext
mov r8d,FR_DOWN
mov edx,EM_FINDTEXTEX
mov rcx,hwndRichEdit
call SendMessage
inc eax;.if eax==-1
jz wmBYE;.break
mov r9d,offset findtext.chrgText
xor r8d,r8d
mov edx,EM_EXSETSEL
mov rcx,hwndRichEdit
call SendMessage
mov r9d,offset ReplaceBuffer
lea r8,settext
mov edx,EM_SETTEXTEX
mov rcx,hwndRichEdit
call SendMessage
jmp @b
wmCLOSE:xor edx,edx
mov hSearch,rdx
;mov rcx,hWnd
call EndDialog
wmBYE: mov eax,TRUE
leave
retn
handle2 dq OK,CANCEL
ReplaceProc endp
GoToProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL LineNo:QWORD
LOCAL chrg:CHARRANGE
push rbp
mov ebp,esp
sub esp,(28h+sizeof CHARRANGE+15)and(-16)
mov hWnd,rcx
mov wParam,r8
mov lParam,r9
cmp edx,WM_INITDIALOG
je wmINITDIALOG
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_COMMAND
je wmCOMMAND
wmDEFAULT:xor eax,eax;mov eax,FALSE
leave
retn
wmINITDIALOG:mov hSearch,rcx;hWnd
jmp wmBYE
wmCOMMAND:mov eax,r8d;wParam
shr eax,16
or eax,eax;.if ax==BN_CLICKED
jnz wmBYE
mov eax,r8d;wParam
cmp ax,IDC_CANCEL
jnz @f
xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
call SendMessage
jmp wmBYE
@@: cmp ax,IDC_OK
jnz wmBYE
xor r9d,r9d;FALSE
xor r8d,r8d
mov edx,IDC_LINENO
mov rcx,hWnd
call GetDlgItemInt
mov LineNo,rax
xor r9d,r9d
xor r8d,r8d
mov edx,EM_GETLINECOUNT
mov rcx,hwndRichEdit
invoke SendMessage
cmp rax,LineNo
jbe wmBYE
xor r9d,r9d
mov r8,LineNo
mov edx,EM_LINEINDEX
mov rcx,hwndRichEdit
call SendMessage
mov r9,rax
mov r8,rax
mov edx,EM_SETSEL
mov rcx,hwndRichEdit
call SendMessage
mov rcx,hwndRichEdit
call SetFocus
jmp wmBYE
wmCLOSE:xor edx,edx
mov hSearch,rdx
call EndDialog
wmBYE: mov eax,TRUE
leave
ret
GoToProc endp
PrepareEditMenu proc hSubMenu:QWORD
LOCAL chrg:CHARRANGE
push rbp
mov ebp,esp
sub esp,(20h+sizeof CHARRANGE+15)and(-16)
mov hSubMenu,rcx
;=============================================================================
; Check whether there is some text in the clipboard. If so, we enable the paste menuitem
;=============================================================================
xor r9d,r9d
mov r8d,CF_TEXT
mov edx,EM_CANPASTE
mov rcx,hwndRichEdit
call SendMessage
or eax,eax;.if eax==0 ; no text in the clipboard
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_PASTE
mov rcx,hSubMenu
call EnableMenuItem
;==========================================================
; check whether the undo queue is empty
;==========================================================
xor r9d,r9d
xor r8d,r8d
mov edx,EM_CANUNDO
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; .if eax==0
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_UNDO
mov rcx,hSubMenu
call EnableMenuItem
;=========================================================
; check whether the redo queue is empty
;=========================================================
xor r9d,r9d
xor r8d,r8d
mov edx,EM_CANREDO
mov rcx,hwndRichEdit
call SendMessage
or eax,eax; .if eax==0
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_REDO
mov rcx,hSubMenu
call EnableMenuItem
;=========================================================
; check whether there is a current selection in the richedit control.
; If there is, we enable the cut/copy/delete menuitem
;=========================================================
lea r9,chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov eax,chrg.cpMin
cmp eax,chrg.cpMax
; no current selection
sete bl;MF_ENABLED=0 MF_GRAYED=1
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_COPY
mov rcx,hSubMenu
call EnableMenuItem
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_CUT
mov rcx,hSubMenu
call EnableMenuItem
mov r8d,ebx;MF_GRAYED/MF_ENABLED
mov edx,IDM_DELETE
mov rcx,hSubMenu
call EnableMenuItem
xor ebx,ebx
leave
ret
PrepareEditMenu endp
asm-file third part[code];----------------------------------------------------------
;функция ParseBuffer принимает буфер, содержащий слова, которые должны быть
;выделены, парсит их на отдельные слова и сохраняет каждое из них в массиве
;структур WORDINFO, к которому можно получить доступ из ASMSyntaxArray.
;---------------------------------------------------------------------
ParseBuffer proc hHeap:QWORD,pBuffer:QWORD, nSize:QWORD, ArrayOffset:QWORD,pArray:QWORD
LOCAL buffer[128]:BYTE
LOCAL InProgress:QWORD
LOCAL old_rdi:QWORD
LOCAL old_rsi:QWORD
LOCAL old_rcx:QWORD
push rbp
mov ebp,esp
sub esp,(20h+128+4*8+15)and(-16)
mov hHeap,rcx
mov pBuffer,rdx
mov nSize,r8
mov ArrayOffset,r9
mov old_rdi,rdi
mov old_rsi,rsi
mov InProgress,FALSE
;InProgress - флаг, который дает возможность определить, начался ли процесс
;сканирования. Если значение равно FALSE, тогда edi указывает на буфер,
;который будет содержать слово, взятое нами из списка слов. esi указывает на
;строку-список слов. Чтобы упростить поиск, приводим все символы к нижнему
;регистру.
lea edi,buffer
mov rsi,pBuffer
mov ecx,esi
call CharLower
mov rcx,nSize
jrcxz @f
;Сканируем весь список слов в буфере, ориентируясь по пробелам или табуляции,
;по которым определяем конец или начало слова. Если оказывается, что байт не
;является пробелом, тогда копируем его в буфер, где создается слово, а затем
;продолжаем поиск.
SearchLoop:cmp byte ptr [rsi]," "
je EndOfWord
cmp byte ptr [rsi],9 ; tab
je EndOfWord
mov InProgress,TRUE
movsb;mov al,byte ptr [rsi]
dec esi
SkipIt: inc esi
loop SearchLoop
@@: jmp Finished
EndOfWord:cmp InProgress,TRUE
jne SkipIt
WordFound:mov byte ptr [rdi],0
mov old_rcx,rcx
;========================================================
; store the word in a WORDINFO structure
;========================================================
mov r8d,sizeof WORDINFO
mov edx,HEAP_ZERO_MEMORY
mov rcx,hHeap
call HeapAlloc
mov edi,eax
lea ecx,buffer
call lstrlen
mov [rdi+WORDINFO.WordLen],eax
mov rcx,ArrayOffset
mov [rdi+WORDINFO.pColor],ecx
inc eax
mov r8d,eax
mov edx,HEAP_ZERO_MEMORY
mov rcx,hHeap
call HeapAlloc
lea edx,buffer
mov [rdi+WORDINFO.pszWord],eax
mov ecx,eax
call lstrcpy
mov rax,pArray
movzx rdx,byte ptr buffer
lea eax,[rax+4*rdx]
cmp dword ptr [rax],0
jz @f
mov ecx,dword ptr [rax]
mov [rdi+WORDINFO.NextLink],ecx
@@: mov dword ptr [rax],edi
mov rcx,old_rcx
lea edi,buffer
mov InProgress,FALSE
jmp SkipIt
Finished:cmp InProgress,TRUE
jnz a2
;========================================================
; store the word in a WORDINFO structure
;========================================================
mov r8d,sizeof WORDINFO
mov edx,HEAP_ZERO_MEMORY
mov rcx,hHeap
call HeapAlloc
mov edi,eax
lea ecx,buffer
call lstrlen
mov [rdi+WORDINFO.WordLen],eax
mov rcx,ArrayOffset
mov [rdi+WORDINFO.pColor],ecx
inc eax
mov r8d,eax
mov edx,HEAP_ZERO_MEMORY
mov rcx,hHeap
call HeapAlloc
mov [rdi+WORDINFO.pszWord],eax
lea esi,buffer
mov ecx,eax
mov edx,esi
call lstrcpy
mov rax,pArray
movzx edx,byte ptr [esi];buffer
lea eax,[rax+rdx*4]
cmp dword ptr [rax],0
jz @f
mov ecx,dword ptr [rax]
mov [rdi+WORDINFO.NextLink],ecx
@@: mov dword ptr [rax],edi
a2: mov rsi,old_rsi
mov rdi,old_rdi
leave
retn
ParseBuffer endp
FillHiliteInfo proc
LOCAL buffer[1024]:BYTE
local CKeyIndex:QWORD
local ASMColorArrayIndex:QWORD
LOCAL BlockSize:QWORD
LOCAL pTemp:QWORD
LOCAL old_rdi:QWORD
LOCAL temp1:QWORD
LOCAL temp2:QWORD
push rbp
mov ebp,esp
sub esp,(30h+1024+5*8+15)and(-16)
mov old_rdi,rdi
;===================================================================
; Zero out the array
;===================================================================
mov edx,sizeof ASMSyntaxArray
mov ecx,offset ASMSyntaxArray
call RtlZeroMemory
;===================================================================
; obtaining the path of this program instance
;===================================================================
mov r8d,sizeof buffer
lea edi,buffer
mov edx,edi
mov ecx,IMAGE_BASE
call GetModuleFileName
mov temp1,rdi
mov ecx,eax
dec ecx
add edi,ecx
std
mov al,"\"
repne scasb
cld
add edi,2
mov temp2,rsi
mov esi,offset WordFileName;mov byte ptr [rdi],0
mov ecx,sizeof WordFileName;mov edx,offset WordFileName
rep movsb;lea ecx,buffer
mov rsi,temp2;call lstrcat
mov rdi,temp1;
;==================================================================
; Check whether the file exists
;==================================================================
mov ecx,edi;lea ecx,buffer
call GetFileAttributes
inc eax;.if eax!=-1
jz a0
-
; allocate a block of memory from the heap for the strings
mov BlockSize,1024*10
mov r8,BlockSize
xor edx,edx
mov rcx,hMainHeap
call HeapAlloc
mov pTemp,rax
mov eax,offset C1Key
mov CKeyIndex,rax
mov eax,offset ASMColorArray
mov ASMColorArrayIndex,rax
@@: mov [rsp+28h],rdi;rax
mov rax,BlockSize
mov [rsp+20h],rax
mov r9,pTemp
mov r8d,offset ZeroString
mov rdx,CKeyIndex
mov ecx,offset ASMSection
call GetPrivateProfileString
or eax,eax;.if eax!=0
jz @f
inc eax
cmp rax,BlockSize ; the buffer is too small
jnz a2
add BlockSize,1024*10
mov r9,BlockSize
mov r8,pTemp
xor edx,edx
mov rcx,hMainHeap
call HeapReAlloc
mov pTemp,rax
jmp @B
a2: mov ecx,10;offset ASMSyntaxArray
a4: mov temp1,rcx
db 48h;mov ecx,offset ASMSyntaxArray
dd 202444C7h,ASMSyntaxArray;mov [rsp+20h],rcx
mov r9,ASMColorArrayIndex
mov r8d,eax
mov rdx,pTemp
mov rcx,hMainHeap
call ParseBuffer
add CKeyIndex,3
add ASMColorArrayIndex,4
@@: mov [rsp+28],rdi
mov rax,BlockSize
mov [rsp+20h],rax
mov r9,pTemp
mov r8d,offset ZeroString
mov rdx,CKeyIndex
mov ecx,offset ASMSection
call GetPrivateProfileString
or eax,eax;.if eax!=0
jz a3
inc eax
cmp rax,BlockSize ; the buffer is too small
jnz a3
add BlockSize,1024*10
mov r9,BlockSize
mov r8,pTemp
xor edx,edx
mov rcx,hMainHeap
call HeapReAlloc
mov pTemp,rax
jmp @B
a3: mov rcx,temp1
dec ecx;loop a4
jnz a4
mov r8,pTemp
xor edx,edx
mov rcx,hMainHeap
call HeapFree
a0: mov rdi,old_rdi
leave
ret
FillHiliteInfo endp
NewRichEditProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL hdc:QWORD
LOCAL hOldFont:QWORD
LOCAL FirstChar:QWORD
LOCAL rect:RECT
LOCAL txtrange:TEXTRANGE
LOCAL buffer[1024*10]:BYTE
LOCAL hRgn:QWORD
LOCAL hOldRgn:QWORD
LOCAL RealRect:RECT
LOCAL pString:QWORD
LOCAL BufferSize:QWORD
LOCAL pt:POINT
push rbp
mov ebp,esp
sub esp,(30h+8*7+2*(sizeof RECT)+sizeof TEXTRANGE+\
sizeof POINT+1024*10+15)and(-16)
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_CLOSE
je wmCLOSE
wmDEFAULT:mov [rsp+20h],r9
mov r9,r8
mov r8d,edx
mov edx,ecx
mov rcx,OldWndProc
call CallWindowProc
leave
retn
wmPAINT:push rdi
push rsi
sub esp,30h
mov rcx,hWnd
call HideCaret
mov rax,lParam
mov [rsp+20h],rax
mov r9,wParam
mov r8,uMsg
mov rdx,hWnd
mov rcx,OldWndProc
call CallWindowProc
add esp,10h
mov edx,eax
mov rcx,hWnd
call GetDC
mov hdc,rax
mov edx,TRANSPARENT
mov ecx,eax
call SetBkMode
; Do syntax hiliting here!
lea edi,rect
mov r9d,edi;lea r9d,rect
xor r8d,r8d
mov edx,EM_GETRECT
mov rcx,hWnd
call SendMessage
mov r9d,edi;lea r9d,rect
xor r8d,r8d
mov edx,EM_CHARFROMPOS
mov rcx,hWnd
call SendMessage
; obtain the line number
xor r9d,r9d
mov r8d,eax
mov edx,EM_LINEFROMCHAR
mov rcx,hWnd
call SendMessage
xor r9d,r9d
mov r8d,eax
mov edx,EM_LINEINDEX
mov rcx,hWnd
call SendMessage
mov txtrange.chrg.cpMin,eax
mov FirstChar,rax
lea r9d,rect.right
xor r8d,r8d
mov edx,EM_CHARFROMPOS
mov rcx,hWnd
call SendMessage
mov txtrange.chrg.cpMax,eax
mov esi,edi
lea edi,RealRect
movsq;
;mov eax,rect.left
;mov RealRect.left,eax
;mov eax, rect.top
;mov RealRect.top,eax
movsq;
;mov eax, rect.right
;mov RealRect.right,eax
;mov eax,rect.bottom
;mov RealRect.bottom,eax
mov r9d,RealRect.bottom
mov r8d,RealRect.right
mov edx,RealRect.top
mov ecx,RealRect.left
call CreateRectRgn
mov hRgn,rax
mov edx,eax;hRgn
mov rcx,hdc
call SelectObject
mov hOldRgn,rax
mov edx,CommentColor
mov rcx,hdc
call SetTextColor
; Get the visible text into buffer
lea eax,buffer
mov txtrange.lpstrText,rax
lea r9d,txtrange
xor r8d,r8d
mov edx,EM_GETTEXTRANGE
mov rcx,hWnd
call SendMessage
add esp,20h
mov esi,eax ; esi == size of the text
cmp esi,0
jbe @0
mov BufferSize,rax
; Search for comments first
mov edi,offset ASMSyntaxArray
push rdi
push rbx
lea edi,buffer
mov edx,edi ; used as the reference point
mov ecx,esi
mov al,";"
ScanMore:
repne scasb
jne NoMoreHit
NextSkip: dec edi
inc ecx
mov pString,rdi
mov ebx,edi
sub ebx,edx
add rbx,FirstChar
mov txtrange.chrg.cpMin,ebx
; search the end of line or the end of buffer
push rax
mov al,0Dh
repne scasb
pop rax
HiliteTheComment: cmp ecx,0
jbe @1
mov byte ptr [rdi-1],0
@1: mov ebx,edi
sub ebx,edx
add rbx,FirstChar
mov txtrange.chrg.cpMax,ebx
push rax
push rbx
push rcx
push rdx
push rsi
push rdi
; Now we must search the range for the tabs
mov rdi,pString
mov esi,txtrange.chrg.cpMax
sub esi,txtrange.chrg.cpMin; esi contains the length of the buffer
mov eax,esi
push rdi
push rdi
@3: cmp byte ptr [rdi],9
jnz @4
mov byte ptr [rdi],0
@4: inc edi
dec eax
jnz @3
pop rdi
pop rdi
jmp @5; .while esi>0
@6: cmp byte ptr [rdi],0
jz @7
sub esp,20h
mov ecx,edi
call lstrlen
add esp,20h
push rax
push rax
mov ecx,edi
lea edx,buffer
sub ecx,edx
add rcx,FirstChar
cmp RichEditVersion,3
jnz @8
sub esp,20h
mov r9d,ecx
lea r8d,rect
mov edx,EM_POSFROMCHAR
mov rcx,hWnd
call SendMessage
add esp,20h
jmp @9; .else
@8: sub esp,20h
xor r9d,r9d
mov r8d,ecx
mov edx,EM_POSFROMCHAR
mov rcx,hWnd
call SendMessage
add esp,20h
movzx ecx,ax
mov rect.left,ecx
shr eax,16
mov rect.top,eax
@9: sub esp,30h
mov qword ptr [rsp+20h],0
lea r9d,rect
or r8,-1
mov edx,edi
mov rcx,hdc
call DrawText
add esp,30h
pop rax
pop rax
add edi,eax
sub esi,eax
jmp @5; .else
@7: inc edi
dec esi
@5: cmp esi,0
ja @6
mov edx,txtrange.chrg.cpMax
sub edx,txtrange.chrg.cpMin
sub esp,20h
mov rcx,pString
call RtlZeroMemory
add esp,20h
pop rdi
pop rsi
pop rdx
pop rcx
pop rbx
pop rax
cmp ecx,0
jnbe ScanMore
NoMoreHit: pop rbx
pop rdi
; Now that the comments are out of our way, Get rid of the separators
mov rcx,BufferSize
lea esi,buffer
jrcxz @10; .while ecx>0
@11: lodsb;mov al,byte ptr [esi]
cmp al,'.'
je @14
cmp al,"%"
je @14
cmp al,'0'
jb @12
cmp al,'9'
jbe @14
cmp al,"?";3Fh
jb @12
cmp al,"[";5B
jb @14
cmp al,"\";60h
jbe @12
cmp al,"{";7B
jb @14
cmp al,"~";7F
ja @14
@12: mov byte ptr [rsi-1],0
@14: loop @11
; Begin the search
lea esi,buffer
@10: mov rcx,BufferSize
test ecx,ecx
jz @0; .while ecx>0
@16: cmp byte ptr [rsi],0
jz @17
push rcx
sub esp,20h
mov ecx,esi
call lstrlen
add esp,20h
push rax
mov edx,eax ; edx contains the length of the string
movzx eax,byte ptr [esi]
cmp al,"A";.if al>="A" && al<="Z"
jb @f
cmp al,"Z"
ja @f
add al,20h;"a"
@@: lea eax,[rdi+rax*4]; edi contains the pointer to the WORDINFO pointer array
cmp dword ptr [rax],0
jz @19
mov eax,[rax]
jmp @20
@21: cmp edx,[eax+WORDINFO.WordLen]
jnz @22
push rax
push rbx
push rcx
push rdx
push rsi
push rdi
sub esp,20h
mov edx,esi
mov ecx,[rax+WORDINFO.pszWord]
call lstrcmpi
add esp,20h
or eax,eax;.if eax==0
jnz @23
pop rdi
pop rsi
pop rdx
pop rcx
pop rbx
pop rax
; hilite the word
mov ecx,esi
lea edx,buffer
sub ecx,edx
add rcx,FirstChar
push rax
push rbx
push rcx
push rdx
push rsi
push rdi
cmp [RichEditVersion],3
jnz @24
sub esp,20h
mov r9d,ecx
lea r8d,rect
mov edx,EM_POSFROMCHAR
mov rcx,hWnd
call SendMessage
add esp,20h
jmp @25;.else
@24: sub esp,20h
xor r9d,r9d
mov r8d,ecx
mov edx,EM_POSFROMCHAR
mov rcx,hWnd
call SendMessage
add esp,20h
movzx ecx,ax
mov rect.left,ecx
shr eax,16
mov rect.top,eax
@25: pop rdi
pop rsi
pop rdx
pop rcx
pop rbx
pop rax
mov edx,[eax+WORDINFO.pColor]
sub esp,20h
mov edx,dword ptr [edx]
mov rcx,hdc
call SetTextColor
sub esp,10h
mov qword ptr [rsp+20h],0
lea r9d,rect
or r8d,-1
mov edx,esi
mov rcx,hdc
call DrawText
add esp,30h
jmp @19;.endif
@23: pop rdi
pop rsi
pop rdx
pop rcx
pop rbx
pop rax
@22: mov eax,[eax+WORDINFO.NextLink]
@20: or eax,eax;.endw
jnz @21;.endif
@19: pop rax
pop rcx
add esi,eax
sub ecx,eax
jmp @15;.else
@17: inc esi
dec ecx
@15: jnz @16
@0: sub esp,20h
mov rdx,hOldRgn
mov rcx,hdc
call SelectObject
mov rcx,hRgn
call DeleteObject
mov rdx,hOldFont
mov rcx,hdc
call SelectObject
mov rdx,hdc
mov rcx,hWnd
call ReleaseDC
mov rcx,hWnd
call ShowCaret
add esp,20h
pop rax
pop rsi
pop rdi
leave
retn
wmCLOSE:mov r8,OldWndProc
mov edx,GWL_WNDPROC
call SetWindowLongPtr;hWnd
NewRichEditProc endp
WndProc proc hWnd:QWORD, uMsg:QWORD, wParam:QWORD, lParam:QWORD
LOCAL ofn:OPENFILENAME
LOCAL buffer[256]:BYTE
LOCAL editstream:EDITSTREAM
LOCAL hFile:QWORD
LOCAL hPopup:QWORD
LOCAL old_rsi:QWORD
LOCAL pt:POINT
LOCAL chrg:CHARRANGE
push rbp
mov ebp,esp
sub esp,(40h+sizeof OPENFILENAME+256+sizeof EDITSTREAM+\
3*8+sizeof POINT+sizeof CHARRANGE+15)and(-16)
mov hWnd,rcx
mov uMsg,rdx
mov wParam,r8
mov lParam,r9
cmp edx,WM_NOTIFY
je wmNOTIFY
cmp edx,WM_INITMENUPOPUP
je wmINITMENUPOPUP
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_CLOSE
je wmCLOSE
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_DESTROY
je wmDESTROY
wmDEFAULT:leave
jmp DefWindowProc
wmDESTROY:mov rcx,hRichEdit
call FreeLibrary
xor ecx,ecx
call ExitProcess
wmNOTIFY:mov old_rsi,rsi
mov rsi,r9;lParam
cmp [rsi+NMHDR._code],EN_MSGFILTER;.if [esi]._code==EN_MSGFILTER
jnz @f;assume esi:ptr MSGFILTER
cmp [rsi+MSGFILTER.msg],WM_RBUTTONDOWN;.if [esi].msg==WM_RBUTTONDOWN
jnz @f
mov rcx,hWnd
call GetMenu
mov edx,1
mov ecx,eax
call GetSubMenu
mov hPopup,rax
mov ecx,eax;hPopup
call PrepareEditMenu
mov rdx,[rsi+MSGFILTER.lParam]
mov ecx,edx
and edx,0FFFFh
shr ecx,16
mov pt.x,edx
mov pt.y,ecx
lea edx,pt
mov rcx,hWnd
call ClientToScreen
mov qword ptr [rsp+30h],NULL
mov rax,hWnd
mov [rsp+28h],rax
mov qword ptr [rsp+20h],NULL
mov r9d,pt.y
mov r8d,pt.x
mov edx,TPM_LEFTALIGN or TPM_BOTTOMALIGN
mov rcx,hPopup
call TrackPopupMenu
@@: mov rsi,old_rsi
jmp wmBYE
wmINITMENUPOPUP:
mov eax,r9d;lParam
or ax,ax;.if ax==0; file menu
jnz @0
cmp FileOpened,TRUE; a file is already opened
setne bl;в ebx MF_ENABLED=0 или MF_GRAYED=1
mov r8d,ebx;MF_ENABLED
mov edx,IDM_CLOSE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_SAVE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_SAVEAS
mov rcx,wParam
call EnableMenuItem
xor ebx,1
mov r8d,ebx;MF_GRAYED
mov edx,IDM_OPEN
mov rcx,wParam
call EnableMenuItem
xor ebx,ebx
jmp wmBYE
@0: cmp ax,1;.elseif ax==1 ; edit menu
jnz @f
mov rcx,wParam
call PrepareEditMenu
jmp wmBYE
@@: cmp ax,2;.elseif ax==2 ; search menu bar
jnz wmBYE
cmp FileOpened,TRUE;.if FileOpened==TRUE
setne bl;в ebx MF_ENABLED=0 или MF_GRAYED=1
mov r8d,ebx;MF_ENABLED
mov edx,IDM_FIND
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_FINDNEXT
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_FINDPREV
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_REPLACE
mov rcx,wParam
call EnableMenuItem
mov r8d,ebx;MF_ENABLED
mov edx,IDM_GOTOLINE
mov rcx,wParam
call EnableMenuItem
xor ebx,ebx
jmp wmBYE
wmCOMMAND:
or r9,r9;.if lParam==0 ; menu commands
jnz wmBYE
mov eax,r8d;mov eax,wParam
sub eax,IDM_OPEN;.if ax==IDM_OPEN
cmp eax,IDM_FINDPREV-IDM_OPEN
ja wmBYE
jmp handle1[rax*8]
OPEN: mov edx,sizeof OPENFILENAME
lea ecx,ofn
call RtlZeroMemory
lea ecx,ofn
mov [rcx+OPENFILENAME.lStructSize],sizeof ofn
mov rax,hWnd
mov [rcx+OPENFILENAME.hwndOwner],rax
mov [rcx+OPENFILENAME.hInstance],IMAGE_BASE
mov eax,offset ASMFilterString
mov [rcx+OPENFILENAME.lpstrFilter],rax
mov eax,offset FileName
mov [rcx+OPENFILENAME.lpstrFile],rax
mov byte ptr [FileName],0
mov [rcx+OPENFILENAME.nMaxFile],sizeof FileName
mov [rcx+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_HIDEREADONLY or OFN_PATHMUSTEXIST
call GetOpenFileName
or eax,eax; .if eax!=0
jz wmBYE
mov qword ptr [rsp+30h],0
mov qword ptr [rsp+28h],FILE_ATTRIBUTE_NORMAL
mov qword ptr [rsp+20h],OPEN_EXISTING
xor r9d,r9d
mov r8d,FILE_SHARE_READ
mov edx,GENERIC_READ
mov ecx,offset FileName
call CreateFile
inc eax;.if eax!=INVALID_HANDLE_VALUE
jz @f
dec eax
mov hFile,rax
; stream the text into the richedit control
lea r9,editstream
mov [r9+EDITSTREAM.dwCookie],rax
mov eax,offset StreamInProc
mov [r9+EDITSTREAM.pfnCallback],rax
mov r8d,SF_TEXT
mov edx,EM_STREAMIN
mov rcx,hwndRichEdit
call SendMessage
; Initialize the modify state to false
xor r9d,r9d
xor r8d,r8d
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov rcx,hFile
call CloseHandle
mov FileOpened,TRUE
jmp wmBYE
@@: mov r9d,MB_OK or MB_ICONERROR
mov r8d,offset ClassName
mov edx,offset OpenFileFail
mov rcx,hWnd
call MessageBox
jmp wmBYE
CLOSE1: mov rcx,hWnd
call CheckModifyState
or eax,eax;.if eax==TRUE
jz wmBYE
xor edx,edx
mov rcx,hwndRichEdit
call SetWindowText
mov FileOpened,FALSE
jmp wmBYE
SAVE: mov ecx,offset FileName
jmp @f
SAVEAS: mov edx,sizeof ofn
lea ecx,ofn
call RtlZeroMemory
lea ecx,ofn
mov [rcx+OPENFILENAME.lStructSize],sizeof ofn
mov rax,hWnd
mov [rcx+OPENFILENAME.hwndOwner],rax
mov [rcx+OPENFILENAME.hInstance],IMAGE_BASE
mov eax,offset ASMFilterString
mov [rcx+OPENFILENAME.lpstrFilter],rax
mov eax,offset AlternateFileName
mov [rcx+OPENFILENAME.lpstrFile],rax
mov byte ptr [AlternateFileName],0
mov [rcx+OPENFILENAME.nMaxFile],sizeof AlternateFileName
mov [rcx+OPENFILENAME.Flags],OFN_FILEMUSTEXIST or OFN_HIDEREADONLY or OFN_PATHMUSTEXIST
call GetSaveFileName
or eax,eax;.if eax!=0
jz wmBYE
mov ecx,offset AlternateFileName
@@: mov qword ptr [rsp+30h],0
mov qword ptr [rsp+28h],FILE_ATTRIBUTE_NORMAL
mov qword ptr [rsp+20h],CREATE_ALWAYS
mov r9d,NULL
mov r8d,FILE_SHARE_READ
mov edx,GENERIC_WRITE
call CreateFile
inc eax;.if eax!=INVALID_HANDLE_VALUE
jz wmBYE
dec eax
mov hFile,rax
; stream the text to the file
lea r9,editstream
mov [r9+EDITSTREAM.dwCookie],rax
mov eax,offset StreamOutProc
mov [r9+EDITSTREAM.pfnCallback],rax
mov r8d,SF_TEXT
mov edx,EM_STREAMOUT
mov rcx,hwndRichEdit
call SendMessage
; Initialize the modify state to false
xor r9d,r9d
mov r8d,FALSE
mov edx,EM_SETMODIFY
mov rcx,hwndRichEdit
call SendMessage
mov rcx,hFile
call CloseHandle
jmp wmBYE
COPY:
mov ecx,WM_COPY;invoke SendMessage,hwndRichEdit,WM_COPY,0,0
jmp @19
CUT:
mov ecx,WM_CUT;invoke SendMessage,hwndRichEdit,WM_CUT,0,0
jmp @19
PASTE:
mov ecx,WM_PASTE;invoke SendMessage,hwndRichEdit,WM_PASTE,0,0
jmp @19
DELETE1:
xor r9d,r9d
mov r8d,TRUE
mov edx,EM_REPLACESEL
jmp @21;invoke SendMessage,hwndRichEdit,EM_REPLACESEL,TRUE,0
SELECTALL:
mov chrg.cpMin,0
mov chrg.cpMax,-1
lea r9,chrg
mov edx,EM_EXSETSEL
jmp @20;invoke SendMessage,hwndRichEdit,EM_EXSETSEL,0,addr chrg
UNDO:
mov ecx,EM_UNDO;invoke SendMessage,hwndRichEdit,EM_UNDO,0,0
jmp @19
REDO:
mov edx,EM_REDO
@19: xor r9d,r9d
@20: xor r8d,r8d
@21: mov rcx,hwndRichEdit
call SendMessage;invoke SendMessage,hwndRichEdit,0,0
jmp wmBYE
OPTIONS:mov qword ptr [rsp+20h],0
mov r9d,offset OptionProc
mov r8,hWnd
mov edx,IDD_OPTIONDLG
mov ecx,IMAGE_BASE
call DialogBoxParam;invoke DialogBoxParam,hInstance,IDD_OPTIONDLG,hWnd,addr OptionProc,0
jmp wmBYE
FIND: cmp hSearch,0;.if hSearch==0
jnz wmBYE
mov r9d,offset SearchProc
mov edx,IDD_FINDDLG
jmp @f
REPLACE:cmp hSearch,0;.if hSearch==0
jnz wmBYE
mov r9d,offset ReplaceProc
mov edx,IDD_REPLACEDLG
jmp @f
GOTOLINE:cmp hSearch,0;.if hSearch==0
jnz wmBYE
mov r9d,offset GoToProc
mov edx,IDD_GOTODLG
@@: mov ecx,IMAGE_BASE
mov r8,hWnd
mov qword ptr [rsp+20h],0
call CreateDialogParam
jmp wmBYE
FINDNEXT:mov ecx,offset FindBuffer
call lstrlen
or eax,eax;.if eax!=0
jz wmBYE
mov r9d,offset findtext.chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov eax,findtext.chrg.cpMin
cmp eax,findtext.chrg.cpMax
jz @f
mov eax,findtext.chrg.cpMax
mov findtext.chrg.cpMin,eax
@@: mov findtext.chrg.cpMax,-1
mov r8d,FR_DOWN
jmp @f
FINDPREV:
mov ecx,offset FindBuffer
call lstrlen
or eax,eax;.if eax!=0
jz wmBYE
mov r9d,offset findtext.chrg
xor r8d,r8d
mov edx,EM_EXGETSEL
mov rcx,hwndRichEdit
call SendMessage
mov findtext.chrg.cpMax,0
xor r8d,r8d
@@: mov eax,offset FindBuffer
mov findtext.lpstrText,rax
mov r9d,offset findtext
mov edx,EM_FINDTEXTEX
mov rcx,hwndRichEdit
call SendMessage;invoke SendMessage,hwndRichEdit,EM_FINDTEXTEX,0,addr findtext
inc eax;.if eax!=-1
jz wmBYE
mov r9d,offset findtext.chrgText
xor r8d,r8d
mov edx,EM_EXSETSEL
mov rcx,hwndRichEdit
call SendMessage;invoke SendMessage,hwndRichEdit,EM_EXSETSEL,0,addr findtext.chrgText
jmp wmBYE
EXIT: xor r9d,r9d
xor r8d,r8d
mov edx,WM_CLOSE
mov rcx,hWnd
call SendMessage
jmp wmBYE
wmCLOSE:call CheckModifyState;,hWnd
or eax,eax;.if eax==TRUE
jz wmBYE
mov rcx,hWnd
call DestroyWindow
jmp wmBYE
wmSIZE: mov eax,r9d;lParam
and r9,0FFFFh
shr eax,16
mov qword ptr [rsp+28h],TRUE
mov [rsp+20h],rax
xor edx,edx
mov r8,rdx
mov rcx,hwndRichEdit
call MoveWindow
wmBYE: leave
ret
handle1 dq OPEN,SAVE,CLOSE1,SAVEAS,EXIT,COPY,CUT,PASTE,DELETE1,SELECTALL
dq OPTIONS,UNDO,REDO,FIND,FINDNEXT,REPLACE,GOTOLINE,FINDPREV
WndProc endp
ClassName db 'Win64 Iczelion''s lesson #35: IczEdit version 3.0',0
RichEditDLL db "riched20.dll",0
RichEditClass db "RichEdit20A",0
NoRichEdit db "Cannot find riched20.dll",0
ASMFilterString db "ASM Source code (*.asm)",0,"*.asm",0
db "All Files (*.*)",0,"*.*",0,0
OpenFileFail db "Cannot open the file",0
WannaSave db "The data in the control is modified. Want to save it?",0
FileOpened dq FALSE
BackgroundColor dd 0FFFFFFh ; default to white
TextColor dd 0 ; default to black
WordFileName db "\wordfile.txt",0
ASMSection db "ASSEMBLY",0
C1Key db "C1",0
C2Key db "C2",0
C3Key db "C3",0
C4Key db "C4",0
C5Key db "C5",0
C6Key db "C6",0
C7Key db "C7",0
C8Key db "C8",0
C9Key db "C9",0
C10Key db "C10",0
ZeroString db 0
ASMColorArray dd 0FF0000h,0805F50h,0FFh,666F00h,44F0h,5F8754h,4 dup(0FF0000h)
CommentColor dd 808000h
hInstance dq IMAGE_BASE
hRichEdit dq ?
hwndRichEdit dq ?
FileName db 256 dup(?)
AlternateFileName db 256 dup(?)
CustomColors dd 16 dup(?)
FindBuffer db 256 dup(?)
ReplaceBuffer db 256 dup(?)
uFlags dd ?
findtext FINDTEXTEX <>
ASMSyntaxArray dd 256 dup(?)
hSearch dq ? ; handle to the search/replace dialog box
hAccel dq ?
hMainHeap dq ? ; heap handle
OldWndProc dq ?
RichEditVersion dq ?
Rect RECT <?>
end
-
I think after all that positive feed back it is time give some not that friendly feed back (:badgrin:), so here are some thoughts on the code...
IMAGE_BASE equ 400000h
OK, the programmer choose the image base or it is fixed(!) - so far so good ...
mov esi,IMAGE_BASE
...
push rsi ;hInstance
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
but that is really interesting: there is a relationship between the module's base address and CW_USEDEFAULT!
I curios how useful it is for a WinAPI tutorial, to use trick code to transform one magic value into an other one rather than just using the corresponding equate.
STYLBTN equ BS_DEFPUSHBUTTON+WS_VISIBLE+WS_CHILD
dangerous habit
push 10029h ;hIconSm
push 10005h ;hCursor
push 10029h ;hIcon
The author does know it better than Microsoft?
...
YES_BUT:;обработка нажатия кнопки. сначала стереть текст в заголовке
...
mov HWNDBTN,rax;запомнить дескриптор кнопки
l5: ;загрузить необходимое меню
...
jrcxz wmBYE;пропускаем первое сообщение при обращении к меню
test word ptr wParam+2,MF_POPUP;проверяем, что активизировано - пункт меню или заголовок выпадающего меню
setne al
movzx r8,al
;если 0, то в lword wParam идентификатор пункта меню
;если 1, то в lword wParam номер заголовка выпадающего меню
...
;заполнение структуры для вызова функции GetMenuItemInfo
...
Ah ... OK.
db 48h;mov ecx,offset ASMSyntaxArray
dd 202444C7h,ASMSyntaxArray;mov [rsp+20h],rcx
Is a there a special reason to encode instruction by hand?
Maybe I did overlooked it, but where is the discussion about the calling convention?
regards,
qWord
-
Hi, qWord!
I am glad that you are interested in this topic
About IMAGE_BASE equ 400000h
see my discussion with sinsi on page #3 (http://masm32.com/board/index.php?topic=4190.30)
push 10029h ;hIconSm
push 10005h ;hCursor
push 10029h ;hIcon
The author does know it better than Microsoft?
see page #1 (http://masm32.com/board/index.php?topic=4190.0) tool "Win x64 Tutorial #2b: MessageBox"
about comments in russian - This is a test program, when the programs will be ready must to insert comments in any language, as long as the programmer captured the essence of the fragment
And I'm sorry for my bad english
-
Win x64 Tutorial #10: a dozen ways to create a dialogue
| |DlgProc | |WndProc+Class | |DlgProc+WndProc |
DialogBoxParam | |10a | |10f | |10e |
CreateDialogParam | |10b | |10c | |10d |
DialogBoxIndirectParam | |10g | |10i | |10k |
CreateDialogIndirectParam | |10h | |10j | |10l |
-
Win x64 Tutorial #19: Tree View Demo
asm-fileinclude win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
IDB_TREE equ 4006
ZZZ_Menu equ 30
IDM_EXPANDALL equ 0
IDM_COLLAPSEALL equ 1
IDM_EXIT equ 2
ID_TREEVIEW equ 44
.code
WinMain proc
local msg:MSG
push rbp
mov ebp,esp
sub esp,sizeof MSG
xor ebx,ebx
call InitCommonControls
mov eax,10027h
mov edi,offset ClassName
mov esi,IMAGE_BASE
push rax ;hIconSm
push rdi ;lpszClassName
push ZZZ_Menu ;lpszMenuName
push COLOR_APPWORKSPACE;hbrBackground
push 10005h ;hCursor
push rax ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push 260;rsi
push 385;rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW+WS_VISIBLE
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
mov ecx,WS_EX_CLIENTEDGE
sub esp,20h
call CreateWindowEx
;----------------------------------
@@: lea ecx,msg
xor edx,edx
xor r8d,r8d
xor r9d,r9d
call GetMessage
lea ecx,msg
call DispatchMessage
jmp @b
WinMain endp
;-----------------------------------------
WndProc proc hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM
local tvis:TV_INSERTSTRUCT
local old_rdi:QWORD
local ps:PAINTSTRUCT
local tvhit:TV_HITTESTINFO
push rbp
mov ebp,esp
sub esp,(20h+sizeof TV_HITTESTINFO+sizeof TV_INSERTSTRUCT+\
sizeof PAINTSTRUCT+8+15)and(-16)
mov hWnd,rcx
mov lParam,r9
mov old_rdi,rdi
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_NOTIFY
je wmNOTIFY
cmp edx,WM_LBUTTONUP
je wmLBUTTONUP
cmp edx,WM_CREATE
je wmCREATE
cmp edx,WM_COMMAND
je wmCOMMAND
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_MOUSEMOVE
je wmMOUSEMOVE
leave
jmp DefWindowProc
wmMOUSEMOVE:cmp DragMode,TRUE
jnz wmBYE
movzx ecx,r9w;word ptr lParam
movzx edx,word ptr lParam+2
mov tvhit.pt.x,ecx ; eax is the horizontal position of the drag image
mov tvhit.pt.y,edx ; ecx is the vertical position
call ImageList_DragMove
xor ecx,ecx;FALSE
call ImageList_DragShowNolock
lea r9,tvhit ; check if an item is hit
xor r8d,r8d;NULL
mov edx,TVM_HITTEST
mov rcx,hWndTree
call SendMessage
or eax,eax;.if eax!=NULL
jz @f
mov r9,rax
mov r8d,TVGN_DROPHILITE
mov edx,TVM_SELECTITEM
mov rcx,hWndTree
call SendMessage
@@: mov ecx,TRUE
call ImageList_DragShowNolock
jmp wmBYE
wmCOMMAND:cmp r8d,IDM_EXIT
ja wmBYE
jmp handle[r8*8]
handle dq wmEXPANDALL,wmCOLLAPSEALL,wmDESTROY
wmEXPANDALL:mov r9,hParent0
mov r8d,TVE_EXPAND
mov edx,TVM_EXPAND
mov rcx,hWndTree
call SendMessage
mov r9,hParent1
mov r8d,TVE_EXPAND
mov edx,TVM_EXPAND
mov rcx,hWndTree
call SendMessage
mov r9,hParent2
mov r8d,TVE_EXPAND
mov edx,TVM_EXPAND
mov rcx,hWndTree
call SendMessage
mov r9,hChild3
mov r8d,TVE_EXPAND
mov edx,TVM_EXPAND
mov rcx,hWndTree
call SendMessage
jmp wmBYE
wmCOLLAPSEALL:mov r9,hParent0
mov r8d,TVE_COLLAPSE
mov edx,TVM_EXPAND
mov rcx,hWndTree
call SendMessage
jmp wmBYE
wmDESTROY:xor ecx,ecx
call ExitProcess
wmSIZE: lea edx,ps
;mov rcx,hWnd
call BeginPaint
mov r8d,GreenBrush
mov ecx,eax
lea edx,ps.rcPaint
call FillRect
lea edx,ps
mov rcx,hWnd
call EndPaint
jmp wmBYE
wmCREATE:push rbx;NULL
push IMAGE_BASE;hInstance
push ID_TREEVIEW
push rcx;hWnd
push 200
push 200
push rbx
push rbx
mov r9d,WS_CHILD or WS_VISIBLE or TVS_HASLINES or \
TVS_HASBUTTONS or TVS_LINESATROOT or WS_CLIPSIBLINGS
xor r8d,r8d;NULL
mov edx,offset TreeViewClass
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hWndTree,rax
mov r9d,0FF00h
xor r8d,r8d;0
mov edx,TVM_SETBKCOLOR
mov rcx,hWndTree
call SendMessage
;---------- [Get the Imagelist] ----------
mov qword ptr [rsp+20h],10
mov r9d,5
mov r8d,ILC_COLOR16
mov edx,16
mov ecx,edx ;16
call ImageList_Create
mov hImageList,rax
mov edx,IDB_TREE
mov ecx,IMAGE_BASE;hInstance
call LoadBitmap
mov edi,eax;mov hBitmap,rax
xor r8d,r8d;NULL
mov edx,eax;hBitmap
mov rcx,hImageList
call ImageList_Add
mov ecx,edi;hBitmap
call DeleteObject
mov r9,hImageList
xor r8d,r8d;0
mov edx,TVM_SETIMAGELIST
mov rcx,hWndTree
call SendMessage
;---------- [Fill the tree] ----------
mov r9d,TVI_ROOT
xor r8d,r8d;0
mov edx,TVM_DELETEITEM
mov rcx,hWndTree
call SendMessage
mov tvis.hParent,rbx;NULL
mov tvis.hInsertAfter,TVI_ROOT
mov tvis.item.imask,TVIF_TEXT or TVIF_IMAGE or TVIF_SELECTEDIMAGE
mov eax,offset Parent0
mov tvis.item.pszText,rax
mov tvis.item.iImage,ebx;0
mov tvis.item.iSelectedImage,1
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hParent0,rax
mov tvis.hParent,rax
mov eax,offset Parent1
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hParent1,rax
mov tvis.hParent,rax
mov tvis.hInsertAfter,TVI_LAST
mov eax,offset Child1
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hChild1,rax
mov eax,offset Child2
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hChild2,rax
mov eax,offset Child3
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hChild3,rax
mov tvis.hParent,rax
mov eax,offset Child4
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hChild4,rax
mov eax,offset Child5
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hChild5,rax
mov rax,hParent1
mov tvis.hParent,rax
mov eax,offset Child6
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hChild6,rax
mov rax,hParent0
mov tvis.hParent,rax
mov tvis.hInsertAfter,TVI_LAST
mov tvis.item.imask,TVIF_TEXT or TVIF_IMAGE or TVIF_SELECTEDIMAGE
mov eax,offset Parent2
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hParent2,rax
mov tvis.hParent,rax
mov eax,offset Child7
mov tvis.item.pszText,rax
lea r9,tvis
xor r8d,r8d;0
mov edx,TVM_INSERTITEM
mov rcx,hWndTree
call SendMessage
mov hChild7,rax
mov ecx,000FF00h;green=00FF00h
call CreateSolidBrush
mov GreenBrush,eax
jmp wmBYE
wmLBUTTONUP:cmp DragMode,TRUE
jnz wmBYE
mov rcx,hWndTree
call ImageList_DragLeave
call ImageList_EndDrag
mov rcx,hDragImageList
call ImageList_Destroy
xor r9d,r9d; Get the currently hilited item
mov r8d,TVGN_DROPHILITE
mov edx,TVM_GETNEXTITEM
mov rcx,hWndTree
call SendMessage
mov r9,rax
mov r8d,TVGN_CARET
mov edx,TVM_SELECTITEM
mov rcx,hWndTree
call SendMessage
xor r9d,r9d
mov r8d,TVGN_DROPHILITE
mov edx,TVM_SELECTITEM
mov rcx,hWndTree
call SendMessage
call ReleaseCapture
mov DragMode,FALSE
jmp wmBYE
wmNOTIFY:cmp r8d,ID_TREEVIEW ; Treeview?
jne wmBYE
cmp [r9+NM_TREEVIEW.hdr._code],TVN_ITEMEXPANDING
jne @f
cmp [r9+NM_TREEVIEW.action],TVE_COLLAPSE
jne wmBYE
xor r9d,r9d
mov r8d,TVGN_CARET
mov edx,TVM_SELECTITEM
mov rcx,hWndTree
call SendMessage
jmp wmBYE
@@: cmp [r9+NM_TREEVIEW.hdr._code],TVN_BEGINDRAG
jnz wmBYE
mov rdi,r9;lParam
mov r9,[rdi+NM_TREEVIEW.itemNew.hItem]
xor r8d,r8d
mov edx,TVM_CREATEDRAGIMAGE
mov rcx,hWndTree
call SendMessage
mov hDragImageList,rax
xor r9d,r9d
xor r8d,r8d
xor edx,edx
mov rcx,hDragImageList
call ImageList_BeginDrag
mov r8d,[rdi+NM_TREEVIEW.ptDrag.y]
mov edx,[rdi+NM_TREEVIEW.ptDrag.x]
mov rcx,hWndTree
call ImageList_DragEnter
mov rcx,hWnd
call SetCapture
mov DragMode,TRUE
wmBYE: mov rdi,old_rdi
leave
xor eax,eax
retn
WndProc endp
;---------------------------------------
ClassName db 'Win64 Iczelion''s lesson #19: Tree View Demo',0
TreeViewClass db "SysTreeView32",0
Parent0 db 'Zero',0
Parent1 db 'One',0
Parent2 db 'Two',0
Child1 db 'Eight',0
Child2 db 'Four',0
Child3 db 'Five',0
Child4 db 'Six',0
Child5 db 'Seven',0
Child6 db 'Three',0
Child7 db 'Nine',0
DragMode db FALSE
GreenBrush dd ?
hWndTree dq ?
hParent0 dq ?
hParent1 dq ?
hParent2 dq ?
hChild1 dq ?
hChild2 dq ?
hChild3 dq ?
hChild4 dq ?
hChild5 dq ?
hChild6 dq ?
hChild7 dq ?
hImageList dq ?
hDragImageList dq ?
end
rc-file#define IDB_TREE 4006
#define IDM_EXPANDALL 0
#define IDM_COLLAPSEALL 1
#define IDM_EXIT 2
#define ZZZ_Menu 30
IDB_TREE BITMAP "Images\\list.bmp"
ZZZ_Menu MENU
{
POPUP "Treeview"
{ MENUITEM "Expand all",IDM_EXPANDALL
MENUITEM "Collapse all",IDM_COLLAPSEALL
MENUITEM SEPARATOR
MENUITEM "&Exit",IDM_EXIT
}
}
-
164129 views of topic. It is well. The translation from x32 to x64 was finished. What would you like to supplement the tutorial? Drivers? Graphics? Working with the console? What else? Sorry for my bad english...
-
What else? It's holiday time, take a rest. You've done a fantastic job :t
Maybe you could put all your code into one fat archive. The forum has always been very stable, so I am not worried that this thread might disappear for technical reasons, but still, everything in one archive could be handy.
Don't worry about your English, it's definitely good enough!
-
Something not very good need:
/LARGEADDRESSAWARE:NO
-
I use /LARGEADDRESSAWARE:NO to quickly get 32-bit code running as 64-bit, but ultimately you want to get rid of it to get full benefit of 64-bit. So one sensible suggestion for Mikl__, now that you've done the first level of conversion (without large addresses) go thru it again and put in large address capability. That's how I do 32-bit conversion, in two stages. It's easier (IMHO) than immediately going all the way to large addresses, which requires converting more dwords to qwords, more "e"'s to "r"'s (like, eax to rax) etc
-
Hi, ToutEnMasm!
in phrase Something not very good need: /LARGEADDRESSAWARE:NO
the keyword is Something
Win x64 Tutorial #3a:Window with unrectangular shape
asm-fileinclude win64a.inc
include gdi32.inc
includelib gdi32.lib
IMAGE_BASE equ 400000h
bmpWidth equ 200
bmpHeight equ 200
.code
WinMain proc
local msg:MSG
local j:DWORD
local i:DWORD
local bpp:DWORD
local hWnd:QWORD
local ResRgn:DWORD
local maskBitmap:QWORD
local bi:BITMAP
enter (30h+sizeof MSG+4*4+8*2+sizeof BITMAP+15)and(-16),0
xor ebx,ebx
mov esi,IMAGE_BASE
mov edi,offset ClassName
mov qword ptr [rsp+28h],LR_LOADFROMFILE
mov [rsp+20h],rbx
xor r9d,r9d
xor r8d,r8d
mov edx,edi
mov ecx,esi
call LoadImage
mov maskBitmap,rax
mov ecx,eax
call CreatePatternBrush
mov ecx,10027h
push rcx ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push rax ;hbrBackground
push 10005h ;hCursor
push rcx ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
db 68h
dd WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
mov ecx,esp ;addr WNDCLASSEX
call RegisterClassEx
push rbx
push rsi ;rsi=400000h
shl esi,9 ;rsi=CW_USEDEFAULT
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
mov r9d,WS_OVERLAPPEDWINDOW
mov r8,rdi ;offset ClassName
mov edx,edi ;offset ClassName
xor ecx,ecx
sub esp,20h
call CreateWindowEx
mov hWnd,rax
xor r8d,r8d
mov edx,GWL_STYLE
mov ecx,eax
call SetWindowLongPtr
lea edi,bi
mov r8d,edi
mov edx,sizeof BITMAP
mov rcx,maskBitmap
call GetObject
movzx edi,[rdi+BITMAP.mBitsPixel]
shr edi,3
mov bpp,edi;bpp = bi.bmBitsPixel / 8
imul edi,bmpHeight*bmpWidth
call GetProcessHeap
mov r8d,edi
mov edx,HEAP_NO_SERIALIZE
mov ecx,eax
call HeapAlloc
mov esi,eax
mov r8d,eax
mov edx,edi
mov rcx,maskBitmap
call GetBitmapBits
xor r9d,r9d
xor r8d,r8d
xor edx,edx
xor ecx,ecx
call CreateRectRgn
mov ResRgn,eax
;--------------------------------------------------
comment $
for (i = 0; i < bi.bmHeight; i++)
{
startx=-1;
for (j = 0; j < bi.bmWidth; j++)
{
pixel = *(DWORD*)(pBits + (i * bi.bmWidth +
j) * bpp) << (32 - bi.bmBitsPixel);
if (pixel != TransPixel)
{
if (startx<0)
{
startx = j;
} else if (j == (bi.bmWidth - 1))
{
Rgn = CreateRectRgn( startx, i, j, i + 1 );
CombineRgn( ResRgn, ResRgn, Rgn, RGN_OR);
startx=-1;
}
} else if (startx>=0)
{
Rgn = CreateRectRgn(startx, i, j, i + 1);
CombineRgn(ResRgn, ResRgn, Rgn, RGN_OR);
startx=-1;
}
}
}
$
;-------------------------------------------------
mov edi,[rsi] ;edi=TransPixel
xor ecx,ecx ;ecx = 0
mov i,ebx ;i=0
;--------------------------------------------------
.1: mov j,ebx ;j=0
.2: mov eax,j
cmp [rsi],edi ;pixel == TransPixel ?
jz @f
or ecx,ecx ;eax != 0 ?
jnz .3
mov ecx,eax ;ecx=j
jmp .3 ;if(pixel != TransPixel && ecx == 0) ecx=j;
@@: jrcxz .3 ;ecx == 0 ?
mov edx,i ;if(pixel == TransPixel && ecx > 0)
mov r9d,edx
inc r9d ;r9d=i+1
mov r8d,eax ;r8=j
inc ecx
call CreateRectRgn ;hRgn=CreateRectRgn(ecx,i,j-1,i+1);
mov r9d,RGN_OR
mov r8d,eax
mov edx,ResRgn
mov ecx,edx
call CombineRgn
xor ecx,ecx ;ecx = 0
.3: add esi,bpp
inc j
cmp byte ptr j,bmpWidth
jb .2
inc i
cmp byte ptr i,bmpHeight
&nb