int real_kbmode;
struct termios real_saved_attribs;
struct ev_fd *real_efd;
+ bool real_delayed;
};
struct uterm_vt_master {
* be used for backwards-compatibility.
*/
+static void real_delayed(struct ev_eloop *eloop, void *unused, void *data)
+{
+ struct uterm_vt *vt = data;
+
+ log_debug("enter VT %d %p during startup", vt->real_num, vt);
+ vt->real_delayed = false;
+ ev_eloop_unregister_idle_cb(eloop, real_delayed, vt);
+ vt_call(vt, UTERM_VT_ACTIVATE);
+}
+
static void real_sig_enter(struct uterm_vt *vt, struct signalfd_siginfo *info)
{
struct vt_stat vts;
if (vts.v_active != vt->real_num)
return;
- if (vt->active)
+ if (vt->real_delayed) {
+ vt->real_delayed = false;
+ ev_eloop_unregister_idle_cb(vt->vtm->eloop, real_delayed, vt);
+ } else if (vt->active) {
log_warning("activating VT %d even though it's already active",
vt->real_num);
- else
+ } else {
uterm_input_wake_up(vt->input);
+ }
log_debug("enter VT %d %p due to VT signal", vt->real_num, vt);
ioctl(vt->real_fd, VT_RELDISP, VT_ACKACQ);
if (vts.v_active != vt->real_num)
return;
- if (!vt->active)
+ if (vt->real_delayed) {
+ vt->real_delayed = false;
+ ev_eloop_unregister_idle_cb(vt->vtm->eloop, real_delayed, vt);
+ uterm_input_sleep(vt->input);
+ } else if (!vt->active) {
log_warning("deactivating VT %d even though it's not active",
vt->real_num);
- else
+ } else {
uterm_input_sleep(vt->input);
+ }
log_debug("leaving VT %d %p due to VT signal", vt->real_num, vt);
vt_call(vt, UTERM_VT_DEACTIVATE);
goto err_setmode;
}
+ if (vts.v_active == vt->real_num) {
+ ret = ev_eloop_register_idle_cb(vt->vtm->eloop, real_delayed,
+ vt);
+ if (ret) {
+ log_error("cannot register idle cb for VT switch");
+ goto err_kbdmode;
+ }
+ vt->real_delayed = true;
+ uterm_input_wake_up(vt->input);
+ }
+
return 0;
+err_kbdmode:
+ ret = ioctl(vt->real_fd, KDSKBMODE, vt->real_kbmode);
+ if (ret)
+ log_error("cannot reset VT KBMODE to %d (%d): %m",
+ vt->real_kbmode, errno);
err_setmode:
memset(&mode, 0, sizeof(mode));
mode.mode = VT_AUTO;
log_debug("closing VT %d", vt->real_num);
+ vt_call(vt, UTERM_VT_DEACTIVATE);
+ if (vt->real_delayed) {
+ vt->real_delayed = false;
+ ev_eloop_unregister_idle_cb(vt->vtm->eloop, real_delayed, vt);
+ uterm_input_sleep(vt->input);
+ }
+
ret = ioctl(vt->real_fd, KDSKBMODE, vt->real_kbmode);
if (ret)
log_error("cannot reset VT KBMODE to %d (%d): %m",