FreeBSD adds one to the VT number returned by the GET_ACTIVE ioctl, so
to match things up, the wrapper here subtracted by one. This lead to
ttyv0 being named VT 0. This had the side-effect of VT numbering not
matching expectations, and switching not behaving as intended.
Align numbers with expectations, and move the required subtraction to
terminal_open, so that VT 1 matches ttyv0.
Path check was done on /dev/dri/card and /dev/dri/renderD. However,
/dev/dri/by-path is a thing, and on FreeBSD, /dev/dri/ symlinks to
Relax Linux check to /dev/dri/, and add FreeBSD check for /dev/drm/.
If a background event was queued during call dispatch, and no unread
data was left on the socket, there would be no incentive for the user to
call dispatch, and as a result, the events would never be executed.
Execute events at the end of IPC calls that read from the socket to
Dispatch on IPC call only dispatched until the first message was
successfully processed. This could lead to premature dispatch
termination if a background event was received during an IPC call.
Instead, continue dispatching until a non-bg opcode is reported or an
error is received.
The seat activation logic did not correctly handle VT switching and
switching between multiple sessions.
Session switching on VT-bound seats is now performed using a VT switch,
taking advantage of VT signals to perform the actual switch. This
simplifies switching logic and makes it more robust.
Signal handling relied on poll(2) being interrupted by signals, followed
by a check for signal handlers flagging a signal as received. This only
allowed signals that were received during poll(2) to be handled
Implement the usual self-pipe implementation, where signal handlers
write an arbitrary byte to a polled file descriptor to ensure proper
level-triggered signal handling.