Date and Time Picker Control: set date (macro functions) Topic is solved

Get help with using AutoHotkey (v1.1 and older) and its commands and hotkeys
User avatar
jeeswg
Posts: 6902
Joined: 19 Dec 2016, 01:58
Location: UK

Date and Time Picker Control: set date (macro functions)

12 Nov 2017, 15:49

I have a function to set the date of an internal/external DTP control.

According to this link you can use a macro function to achieve this.
DTM_SETSYSTEMTIME message (Windows)
https://msdn.microsoft.com/en-us/librar ... s.85).aspx

Can you use macro functions in AutoHotkey via DllCall? If so, in which dll is the DateTime_SetSystemtime macro stored? Thanks.

Code: Select all

;warning: dealing with the memory of an external process, can potentially cause it to crash
q:: ;DTP control - set date/time
ControlGet, hCtl, Hwnd,, SysDateTimePick321, A
JEE_DTPSetDate(hCtl, 20060504030201)
return

;==================================================

JEE_DTPSetDate(hCtl, vDate)
{
	vLen := StrLen(vDate)
	if !RegExMatch(vLen, "^(4|6|8|10|12|14|17)$")
		return
	vScriptPID := DllCall("kernel32\GetCurrentProcessId", UInt)
	WinGet, vPID, PID, % "ahk_id " hCtl
	if (vPID = vScriptPID)
		vIsLocal := 1, vPIs64 := (A_PtrSize=8)

	if (vLen < 17)
		vDate .= SubStr(19990101000000000, vLen+1) ;17 characters: Y M D H M S M
	vDate := RegExReplace(vDate, "(....)(..)(..)(..)(..)(..)(...)", "$1-$2-0-$3-$4-$5-$6-$7")
	vSize := 16
	VarSetCapacity(SYSTEMTIME, 16, 0)
	Loop, Parse, vDate, % "-"
		NumPut(A_LoopField, &SYSTEMTIME, (A_Index*2)-2, "UShort")

	;GDT_VALID := 0
	if vIsLocal
		SendMessage, 0x1002, 0, % &SYSTEMTIME,, % "ahk_id " hCtl ;DTM_SETSYSTEMTIME := 0x1002
	else
	{
		if !hProc := JEE_DCOpenProcess(0x438, 0, vPID)
			return
		if !pBuf := JEE_DCVirtualAllocEx(hProc, 0, vSize, 0x3000, 0x4)
			return
		JEE_DCWriteProcessMemory(hProc, pBuf, &SYSTEMTIME, vSize, 0)
		SendMessage, 0x1002, 0, % pBuf,, % "ahk_id " hCtl ;DTM_SETSYSTEMTIME := 0x1002
		JEE_DCVirtualFreeEx(hProc, pBuf, 0, 0x8000)
		JEE_DCCloseHandle(hProc)
	}
}

;==================================================


JEE_DCOpenProcess(vAccess, hInherit, vPID)
{
	return DllCall("kernel32\OpenProcess", UInt,vAccess, Int,hInherit, UInt,vPID, Ptr)
}
JEE_DCVirtualAllocEx(hProc, vAddress, vSize, vAllocType, vProtect)
{
	return DllCall("kernel32\VirtualAllocEx", Ptr,hProc, Ptr,vAddress, UPtr,vSize, UInt,vAllocType, UInt,vProtect, Ptr)
}
JEE_DCWriteProcessMemory(hProc, vBAddress, pBuf, vSize, vWritten)
{
	return DllCall("kernel32\WriteProcessMemory", Ptr,hProc, Ptr,vBAddress, Ptr,pBuf, UPtr,vSize, Ptr,vWritten)
}
JEE_DCReadProcessMemory(hProc, vBAddress, pBuf, vSize, vRead)
{
	return DllCall("kernel32\ReadProcessMemory", Ptr,hProc, Ptr,vBAddress, Ptr,pBuf, UPtr,vSize, Ptr,vRead)
}
JEE_DCVirtualFreeEx(hProc, vAddress, vSize, vFreeType)
{
	return DllCall("kernel32\VirtualFreeEx", Ptr,hProc, Ptr,vAddress, UPtr,vSize, UInt,vFreeType)
}
JEE_DCCloseHandle(hObject) ;e.g. hProc
{
	return DllCall("kernel32\CloseHandle", Ptr,hObject)
}

;==================================================
homepage | tutorials | wish list | fun threads | donate
WARNING: copy your posts/messages before hitting Submit as you may lose them due to CAPTCHA
User avatar
jeeswg
Posts: 6902
Joined: 19 Dec 2016, 01:58
Location: UK

Re: Date and Time Picker Control: set date (macro functions)

20 Nov 2017, 16:07

I wrote some code to try to find a dll with a function called DateTime_SetSystemtime, but it didn't find one:

Code: Select all

;DllListExports() - List of Function exports of a DLL - AutoHotkey Community
;https://autohotkey.com/boards/viewtopic.php?f=6&t=4563

q:: ;attempt to find a dll with a function called DateTime_SetSystemtime
vDir1 := "C:\Windows\System32"
Loop, Files, % vDir1 "\*.dll", F
{
	vPath := A_LoopFileFullPath
	SplitPath, vPath, vDll
	vText := StrReplace(DllListExports(vDll), "`n", "`r`n") "`r`n"
	;if InStr(vText, "RtlMoveMemory") ;in kernel32.dll and ntdll.dll
	if InStr(vText, "DateTime_SetSystemtime")
		MsgBox, % Clipboard := vPath "`r`n" vText
}
MsgBox, % "done"
return
I found that DateTime_SetSystemtime is mentioned in CommCtrl.h:

Code: Select all

// BOOL DateTime_SetSystemtime(HWND hdp, DWORD gd, LPSYSTEMTIME pst)
//   if gd==GDT_NONE, sets datetimepick to None (DTS_SHOWNONE only)
//   if gd==GDT_VALID, sets datetimepick to *pst
//   returns TRUE on success, FALSE on error (such as bad params)
#define DTM_SETSYSTEMTIME   (DTM_FIRST + 2)
#define DateTime_SetSystemtime(hdp, gd, pst)    (BOOL)SNDMSG(hdp, DTM_SETSYSTEMTIME, (WPARAM)(gd), (LPARAM)(pst))
I thought that perhaps RtlMoveMemory and DateTime_SetSystemtime were similar, but now I notice that one uses the word 'routine' and the other uses the word 'macro'.
RtlMoveMemory routine (Windows Drivers)
https://msdn.microsoft.com/en-us/librar ... s.85).aspx
DateTime_SetSystemtime macro (Windows)
https://msdn.microsoft.com/en-us/librar ... s.85).aspx

It's not important to me be able to use the DateTime_SetSystemtime macro, I can use PostMessage/SendMessage, however, I was curious as to how to use it/if it was possible to use it via DllCall, and (a bit of a long shot) curious as to whether it would allow you to deal with memory in another process without using a remote buffer.

Btw I found a RtlMoveMemory function in both kernel32.dll and ntdll.dll.

Btw also I found a reference to a macro function rather than PostMessage/SendMessage, in the AHK source code, which first got me interested in this question. When searching for messages in the source code, you may actually need to search for the macro functions instead. Plus, I've done a bit of C++, and so was curious as to how to use macro functions in C++ (the AHK source code is written in C++).
homepage | tutorials | wish list | fun threads | donate
WARNING: copy your posts/messages before hitting Submit as you may lose them due to CAPTCHA
Helgef
Posts: 4709
Joined: 17 Jul 2016, 01:02
Contact:

Re: Date and Time Picker Control: set date (macro functions)  Topic is solved

20 Nov 2017, 17:17

The macro is just telling the compiler to call SendMessageA/W, with some parameters, that is, it is basically nothing but text replacement at compile time. So no, there is nothing to call via dllcall, you should just call SendMessage.

Cheers.

Edit: Similarily, RtlMoveMemory is just calling memmove.

Return to “Ask for Help (v1)”

Who is online

Users browsing this forum: ahabse7en and 257 guests