hammerspoon
hammerspoon copied to clipboard
Inconsistent Behavior of `win:application()` for Exited Applications Inside vs. Outside Coroutines
Obligatory massive thank you Chris's, Steven, A-Ron and other maintainers first of all, Hammerspoon has been indispensable in improving my productivity and enjoyment working 😇
Issue Description
win:application()
, when called inside a coroutine on a hs.window
object whose associated application has exited, returns the hs.window instance that the :application() method was called on, rather than nil, as is observed when calling the same method from outside a coroutine.
Environment
- Hammerspoon 0.9.100
- MacOS Sonoma 14.1.2
Steps to Reproduce
Here is a simplified init.lua to reproduce the issue:
bugDemoTimer = hs.timer.doAfter(1, function()
local app = hs.application.open("TextEdit", 1, true)
local win = app:mainWindow()
app:kill()
hs.timer.usleep(100000)
hs.printf("In regular function, app = %s", win:application())
coroutine.resume(coroutine.create(function()
hs.printf("In coroutine, app = %s", win:application())
end))
end)
Expected Behavior
Regardless of the context (inside or outside a coroutine), win:application()
should return nil
when the associated application has exited.
Actual Behavior
Script output:
********
02:05:46 LuaSkin: Unable to fetch NSRunningApplication for pid: 41593
********
02:05:46 In regular function, app = nil
********
02:05:46 LuaSkin: Unable to fetch NSRunningApplication for pid: 41593
********
02:05:46 In coroutine, app = hs.window: (0x600000bd3538)
Potentially related issues
https://github.com/Hammerspoon/hammerspoon/issues/3536 - although window:application()
seems to rely on HSApplication's initWithPid method, not hs.application.get
https://github.com/Hammerspoon/hammerspoon/issues/2394 - Also seems to be hs.application.get related
My guess would be due to the difference in behavior between coroutines and regular functions, there is something odd going on with the stack frame variable or memory management within coroutines and LuaSkin. I wonder if somehow the value of the win variable is getting copied into the place of the return value of the application() method when it comes back to Lua?
initWithPid looks fairly straightforward, so I'm quite stumped as to how the value of the hs.window is ending up being returned from the application method.