<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Fri, Jul 11, 2014 at 7:18 AM, Kurt von Laven <span dir="ltr"><<a href="mailto:kurt@endlessm.com" target="_blank">kurt@endlessm.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><span style="font-family:arial,sans-serif;font-size:13px">Hello folks,</span><div style="font-family:arial,sans-serif;font-size:13px">
<br></div><div style="font-family:arial,sans-serif;font-size:13px">Apologies if anybody is getting this message twice; I originally posted on <a href="mailto:dbus@lists.freedesktop.org" target="_blank">dbus@lists.freedesktop.org</a> and was directed here. </div>



<div style="font-family:arial,sans-serif;font-size:13px"><br></div><div style="font-family:arial,sans-serif;font-size:13px">I am attempting to listen to the SessionRemoved signal from the <a href="http://www.freedesktop.org/wiki/Software/systemd/logind/" target="_blank">login manager</a>. I have no trouble in the case where the user logs out and waits for ~15 seconds before shutting down, but when the user shuts down the system without first logging out I don't hear the SessionRemoved signal in time. I would've thought that inhibiting shutdown (by calling the <a href="http://www.freedesktop.org/wiki/Software/systemd/inhibit/" target="_blank">Inhibit method of the login manager</a>) would be the appropriate way to keep my process alive long enough to record the SessionRemoved signal before my process gets killed. Apparently that is not the case though. I am fairly certain that I am actually inhibiting shutdown, because my process shows up when I call ListInhibitors in <a href="https://wiki.gnome.org/action/show/Apps/DFeet" target="_blank">D-Feet</a>.</div>



<div style="font-family:arial,sans-serif;font-size:13px"><br></div><div style="font-family:arial,sans-serif;font-size:13px">In case it's relevant, I'm using the delay mode of the inhibit method, and my process runs as root.</div>
</div></blockquote><div><br></div><div><div>Inhibitors do not make any sense here. You're inhibiting not just the final power-off of the machine, but the <b>entire</b> shutdown process, <i>including the stopping of login sessions</i>, so you would not see SessionRemoved until after you release the inhibitor anyway.</div>
</div><div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div style="font-family:arial,sans-serif;font-size:13px">
To test whether my process was running in the user session, I called <a href="http://linux.about.com/library/cmd/blcmdl2_getsid.htm" target="_blank">getsid (0)</a>. It returned the PID of my process, which does not match the session ID of the SessionRemoved signals I was able to record. Is this a legitimate way to verify that my process isn't running in the user session? My original assumption was that my process couldn't possibly be in the user session because I am able to hear the SessionRemoved signal when the user logs out and waits for ~15 seconds. Is that a bad assumption to make?</div>
</div></blockquote><div><br></div><div><div>No, this is the wrong method. logind's sessions have nothing to do with getsid() and POSIX sessions (which are limited to the point of being completely useless).</div><div><br>
</div><div>To see if you're running within a logind session, the preferred way is <b>sd_pid_get_session(0, &session_id)</b>. Alternatively, you can:</div><div><br></div><div>a) check the $XDG_SESSION_ID variable, which will contain the session ID if you're inside one,</div>
<div>b) check the cgroups of your process (e.g. in /proc/self/cgroup), which will show you as being in "/user.slice/user-%s.slice/session-%d.scope".</div><div><br></div><div>Note that there is no supported way for escaping a user session. But if you run your program as a system service (from a .service unit), then it won't be put in a session in the first place.</div>
</div><div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div style="font-family:arial,sans-serif;font-size:13px">
I was advised that some shutdown commands bypass logind, so I tried shutting down several different ways (systemctl shutdown, shutdown now, sudo shutdown now, calling Shutdown method on org.gnome.SessionManager from D-Feet, and the typical GUI way). In all cases I got the same result: I didn't hear the SessionRemoved signal.</div>
</div></blockquote><div><br></div><div>logind is just a "proxy" for purposes of polkit authorization (which cannot be done in pid 1); it only forwards the shutdown request to systemd (PID 1). Even tools that use the old SysVinit "/dev/initctl" method still result in the same request, and systemd performs the same shutdown process.</div>
<div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div style="font-family:arial,sans-serif;font-size:13px">
If anyone has any suggestions on how to debug this or knows what I am missing here, that would be greatly appreciated. Please let me know if any additional details would be helpful.</div></div></blockquote><div><br></div>
<div>If I remember correctly the details of systemd boot process, the best approach would be to run your monitor-thingy in a system service (a .service unit), and <b>order the service "Before=systemd-user-sessions.service"</b>. That way, during boot, it will be started <i>before</i> any session gets created, and the opposite happens during shutdown – your service will be stopped <i>after</i> all sessions are removed.</div>
</div><div><br></div>-- <br><div dir="ltr">Mantas Mikulėnas <<a href="mailto:grawity@gmail.com" target="_blank">grawity@gmail.com</a>></div>
</div></div>