关于win32汇编中的wsprintf
正在学习小甲鱼老师的win32汇编,为了学习窗口消息,在消息过程中写了几段简单的程序:捕捉WM_LBUTTONDOWN的鼠标消息,把点击的鼠标坐标显示在窗口中:
;--------变量定义
szZBText db 'X坐标是%d,Y坐标是%d',0
szZBBuffer db 20 dup (?)
wZB_X dw ?
wZB_Y dw ?
;--------消息过程函数处理WM_PAINT和WM_LBUTTONDOWN部分
.if eax == WM_PAINT
invoke BeginPaint,hWnd,addr @stPs
mov @hDc,eax
invoke GetClientRect,hWnd,addr @stRect
invoke DrawText,@hDc,addr szZBBuffer,-1,\
addr @stRect,\
DT_SINGLELINE or DT_CENTER or DT_VCENTER
invoke EndPaint,hWnd,addr @stPs
.elseif eax == WM_LBUTTONDOWN
mov eax,lParam
mov wZB_X,ax ;lPARAM参数的低16位表示坐标X
mov cl,16
shr eax,cl ;高16位右移至ax寄存器
mov wZB_Y,ax
invoke wsprintf,addr szZBBuffer,addr szZBText,wZB_X,wZB_Y
invoke InvalidateRect,hWnd,NULL,1
现在的问题是X坐标显示正确,Y坐标显示是一个很大的数。
但是如果我只显示一个X或者Y就是正确的:
invoke wsprintf,addr szZBBuffer,addr szZBText,wZB_X 或
invoke wsprintf,addr szZBBuffer,addr szZBText,wZB_Y
有大神能看下原因吗,个人感觉是不是wsprintf的参数设置错了?{:10_245:}
20个字节够吗?
已找到原因:
和缓存区大小关系不大,就算只申请了1字节,wsprintf函数还是会把后面大得多的字符串拷贝进缓存区(所谓的内存溢出),第一个参数只是地址而已,整个函数并无长度检测机制。
考虑可能是wsprintf函数把第3个参数及以后的参数当成32位(DWORD)处理,所以重新定义wZB_X、wZB_Y为dword类型就行了。
当然后面处理的时候要用EAX给他们赋值了。
页:
[1]