But I don't know to do this in AutoHotkey. e.g. I can't find a documents related with the address of working dir in PEB.It might be in the poorly documented "Process Environment Block" (PEB). If so, you can use ReadProcessMemory to read another process's PEB.
[SOLVED]get other process's working dir
Click to download Chinese resource for AutoHotkey.
Recommended: AutoHotkey_L My code is based on it or similar versions, e.g. AutoHotkey_H.
Together with AutoHotkey, we grow and march forward. No matter how the future will be, this period of days is still epic.
objWMIService := ComObjGet( "winmgmts:{impersonationLevel=impersonate}!\\.\root\cimv2" ) colItems := objWMIService.ExecQuery("Select * from Win32_Process")._NewEnum While colItems[objItem] MsgBox % objItem.ExecutablePathModify the loop to match the process your after.
Or make a list ( multi line concat ) and then match out the specific process you want..
hth .
don't duplicate, iterate!
for Item in ComObjGet( "winmgmts:" ).ExecQuery("Select * from Win32_Process") MsgBox % Item.ExecutablePath
But note that the executable's path is not necessarily same as the its working directory.
My Scripts are written for the latest released version of AutoHotkey.
Need a secure, accessible place to backup your stuff? Use Dropbox!
Very truenote that the executable's path is not necessarily same as the its working directory.
Thanks rbrtryn
don't duplicate, iterate!
Edit: My potential fix didn't work, just goes to show I'm still quite bad at COM syntax.
All empty key values or just some?I'd like to point out that, at least on my system, this returns an unholy number of blanks
don't duplicate, iterate!
My Scripts are written for the latest released version of AutoHotkey.
Need a secure, accessible place to backup your stuff? Use Dropbox!
I would have said your code didn't work if it only contained blanks
edit: turns out it's an AutoIt3 UDF function. _WinAPI_GetProcessWorkingDirectory($PID = 0)
It's part of the WinAPIEx.au3 UDF. Anyway, it loops through calls to ReadProcessMemory via DllCall. It shouldn't be too difficult to translate to ahk.
The source can be downloaded.
"Some people, when confronted with a problem, think I know, I'll use regular expressions. Now they have two problems."
- Jamie Zawinski
On my system the ones that come up blank are all system processes:
System Idle Process System csrss.exe svchost.exe alg.exe OSPPSVC.EXE wmiprvse.exeAll of the other processes return the correct path.
My Scripts are written for the latest released version of AutoHotkey.
Need a secure, accessible place to backup your stuff? Use Dropbox!
All of the other processes return the correct path.
I think this misses the main point. The objective is to get the working directory of the target process. The function I referenced does this. I have a "ReRun" utility that monitors the active window for programs. If it's not Explorer or the current process, then I store the info. One such is the working directory. I don't want to post au3 code in an ahk forum(for some reason.. if it was .vbs I wouldn't feel trepidation) but if you were to look at the code it does everything with simple API. Either way you have to loop through the processes. But why invoke COM when you're not going to really use it for anything else in the app in most cases?
My ReRun app stores buttons for 32 programs in a Gui where each button has the program icon. They all have the working directory noted. Which leads me to believe the API method is pretty reliable.
You can get the UDF with the _WinAPI_GetProcessWorkingDirectory() function here:
<!-- m -->http://www.autoitscr... ... apiex-udf/<!-- m -->
There's maybe 3 DllCalls to convert to ahk syntax. That's it.
"Some people, when confronted with a problem, think I know, I'll use regular expressions. Now they have two problems."
- Jamie Zawinski
Well, IMO using two lines of code via COM is better than reinventing the wheel with a whole other function.
On my system the ones that come up blank are all system processes:System Idle Process System csrss.exe svchost.exe alg.exe OSPPSVC.EXE wmiprvse.exeAll of the other processes return the correct path.
I don't know what all is coming up blank for my system (because there's 0 info in the MsgBox), but it's around a 3:1 ratio of blank:useful for the 30+ MsgBox I get. Is there a way to get the directory for only the active window btw? I would find that very useful.
Agreed! At the same time there are places for commands like WinGet ( see below )..Well, IMO using two lines of code via COM is better than reinventing the wheel with a whole other function.
Some may be running in memory others may be deliberately hidden.I don't know what all is coming up blank for my system (because there's 0 info in the MsgBox), but it's around a 3:1 ratio of blank:useful for the 30+ MsgBox I get.
You just need to filter out the empty key values.
ProcDirList:="" for Item in ComObjGet( "winmgmts:" ).ExecQuery("Select * from Win32_Process") ProcDirList .= ((Item:=Item.ExecutablePath) ? Item "`n`r" : "" ) MsgBox % ProcDirList
Is there a way to get the directory for only the active window btw? I would find that very useful.
WinGet, ProcPath, ProcessPath, A MsgBox % ProcPath
don't duplicate, iterate!
"Some people, when confronted with a problem, think I know, I'll use regular expressions. Now they have two problems."
- Jamie Zawinski
In the case of WMI, there are things you simply can't do without going 3rd party which probably use it anyway. I dont know.
What ever works I guess.
don't duplicate, iterate!