
format PE64 GUI 5.0
entry start

include 'win64a.inc'

section '.text' code readable executable

frame
	 start: xor	ecx, ecx
		invoke	GetModuleHandle, rcx

		mov	[wc.hInstance],rax
		invoke	LoadIcon,0,IDI_APPLICATION
		mov	[wc.hIcon],rax
		mov	[wc.hIconSm],rax
		invoke	LoadCursor,0,IDC_ARROW
		mov	[wc.hCursor],rax
		invoke	RegisterClassEx,wc
endf
		test	rax,rax
		jnz	@F

	  .Err: invoke	MessageBox,NULL,_error,NULL,MB_ICONERROR+MB_OK

	    @@: invoke	CreateWindowEx, \
			WS_EX_CLIENTEDGE + WS_EX_STATICEDGE, _class, \
			_title, WS_VISIBLE + WS_BORDER + WS_SYSMENU + WS_MINIMIZEBOX, \
			CW_USEDEFAULT, CW_USEDEFAULT, 800, 600, \
			NULL, NULL, [wc.hInstance], NULL

		or	rax, rax
		jz	.Err

	; Windows message pump.

		xor	edx, edx
		mov	r8, rdx
		mov	r9, rdx
		mov	rbx, msg

	    @@: push	rdx
		push	r8
		push	r9
frame
		invoke	GetMessage, rbx, rdx, r8, r9
		or	rax, rax		  ; Bail when NULL is passed
		jz	@F

		invoke	TranslateMessage, rbx
		invoke	DispatchMessage, rcx
endf
		pop	r9
		pop	r8
		pop	rdx
		jmp	@B

	    @@: invoke	ExitProcess,[msg.wParam]

		align	32

proc WindowProc uses rbx rsi rdi, hwnd,wmsg,wparam,lparam

; Note that first four parameters are passed in registers,
; while names given in the declaration of procedure refer to the stack
; space reserved for them - you may store them there to be later accessible
; if the contents of registers gets destroyed. This may look like:
;       mov     [hwnd],rcx
;       mov     [wmsg],edx
;       mov     [wparam],r8
;       mov     [lparam],r9

	cmp	edx,WM_DESTROY
	je	.wmdestroy

  .defwndproc:
	invoke	DefWindowProc,rcx,rdx,r8,r9
	jmp	.finish

  .wmdestroy:
	invoke	PostQuitMessage,0
	xor	eax,eax

  .finish:
	ret

endp

section '.data' data readable writeable

  _title TCHAR 'Generic Application',0
  _class TCHAR 'GENERIC',0
  _error TCHAR 'Startup failed.',0

  wc WNDCLASSEX sizeof.WNDCLASSEX,0,WindowProc,0,0,NULL,NULL,NULL,COLOR_APPWORKSPACE+1,NULL,_class,NULL

  msg MSG

section '.idata' import data readable writeable

  library kernel32,'KERNEL32.DLL',\
	  user32,'USER32.DLL'

  include 'api\kernel32.inc'
  include 'api\user32.inc'