diff --git a/config.def.h b/config.def.h index 9855e21..a1f636c 100644 --- a/config.def.h +++ b/config.def.h @@ -10,3 +10,12 @@ static const char *colorname[NUMCOLS] = { /* treat a cleared input like a wrong password (color) */ static const int failonclear = 1; + +/* length of time (seconds) until */ +static const int timeoffset = 60; + +/* should [command] be run only once? */ +static const int runonce = 0; + +/* command to be run after [time] has passed */ +static const char *command = "doas poweroff" diff --git a/slock b/slock index 53777b4..7f65cd7 100755 Binary files a/slock and b/slock differ diff --git a/slock.c b/slock.c index d2f0886..f6345bf 100644 --- a/slock.c +++ b/slock.c @@ -19,11 +19,16 @@ #include #include +#include + #include "arg.h" #include "util.h" char *argv0; +time_t lasttouched; +int runflag = 0; + enum { INIT, INPUT, @@ -140,74 +145,89 @@ readpw(Display *dpy, struct xrandr *rr, struct lock **locks, int nscreens, failure = 0; oldc = INIT; - while (running && !XNextEvent(dpy, &ev)) { - if (ev.type == KeyPress) { - explicit_bzero(&buf, sizeof(buf)); - num = XLookupString(&ev.xkey, buf, sizeof(buf), &ksym, 0); - if (IsKeypadKey(ksym)) { - if (ksym == XK_KP_Enter) - ksym = XK_Return; - else if (ksym >= XK_KP_0 && ksym <= XK_KP_9) - ksym = (ksym - XK_KP_0) + XK_0; - } - if (IsFunctionKey(ksym) || - IsKeypadKey(ksym) || - IsMiscFunctionKey(ksym) || - IsPFKey(ksym) || - IsPrivateKeypadKey(ksym)) - continue; - switch (ksym) { - case XK_Return: - passwd[len] = '\0'; - errno = 0; - if (!(inputhash = crypt(passwd, hash))) - fprintf(stderr, "slock: crypt: %s\n", strerror(errno)); - else - running = !!strcmp(inputhash, hash); - if (running) { - XBell(dpy, 100); - failure = 1; + //while (running && !XNextEvent(dpy, &ev)) { + while (running){ + while (XPending(dpy)){ + XNextEvent(dpy, &ev); + if (ev.type == KeyPress) { + time(&lasttouched); + explicit_bzero(&buf, sizeof(buf)); + num = XLookupString(&ev.xkey, buf, sizeof(buf), &ksym, 0); + if (IsKeypadKey(ksym)) { + if (ksym == XK_KP_Enter) + ksym = XK_Return; + else if (ksym >= XK_KP_0 && ksym <= XK_KP_9) + ksym = (ksym - XK_KP_0) + XK_0; } - explicit_bzero(&passwd, sizeof(passwd)); - len = 0; - break; - case XK_Escape: - explicit_bzero(&passwd, sizeof(passwd)); - len = 0; - break; - case XK_BackSpace: - if (len) - passwd[len--] = '\0'; - break; - default: - if (num && !iscntrl((int)buf[0]) && - (len + num < sizeof(passwd))) { - memcpy(passwd + len, buf, num); - len += num; + if (IsFunctionKey(ksym) || + IsKeypadKey(ksym) || + IsMiscFunctionKey(ksym) || + IsPFKey(ksym) || + IsPrivateKeypadKey(ksym)) + continue; + switch (ksym) { + case XK_Return: + passwd[len] = '\0'; + errno = 0; + if (!(inputhash = crypt(passwd, hash))) + fprintf(stderr, "slock: crypt: %s\n", strerror(errno)); + else + running = !!strcmp(inputhash, hash); + if (running) { + XBell(dpy, 100); + failure = 1; + } + explicit_bzero(&passwd, sizeof(passwd)); + len = 0; + break; + case XK_Escape: + explicit_bzero(&passwd, sizeof(passwd)); + len = 0; + break; + case XK_BackSpace: + if (len) + passwd[len--] = '\0'; + break; + default: + if (num && !iscntrl((int)buf[0]) && + (len + num < sizeof(passwd))) { + memcpy(passwd + len, buf, num); + len += num; + } + break; } - break; - } - color = len ? INPUT : ((failure || failonclear) ? FAILED : INIT); - if (running && oldc != color) { - for (screen = 0; screen < nscreens; screen++) { - XSetWindowBackground(dpy, - locks[screen]->win, - locks[screen]->colors[color]); - XClearWindow(dpy, locks[screen]->win); + color = len ? INPUT : ((failure || failonclear) ? FAILED : INIT); + if (running && oldc != color) { + for (screen = 0; screen < nscreens; screen++) { + XSetWindowBackground(dpy, + locks[screen]->win, + locks[screen]->colors[color]); + XClearWindow(dpy, locks[screen]->win); + } + oldc = color; } - oldc = color; - } - } else if (rr->active && ev.type == rr->evbase + RRScreenChangeNotify) { - rre = (XRRScreenChangeNotifyEvent*)&ev; - for (screen = 0; screen < nscreens; screen++) { - if (locks[screen]->win == rre->window) { - XResizeWindow(dpy, locks[screen]->win, - rre->width, rre->height); - XClearWindow(dpy, locks[screen]->win); + } else if (rr->active && ev.type == rr->evbase + RRScreenChangeNotify) { + rre = (XRRScreenChangeNotifyEvent*)&ev; + for (screen = 0; screen < nscreens; screen++) { + if (locks[screen]->win == rre->window) { + XResizeWindow(dpy, locks[screen]->win, + rre->width, rre->height); + XClearWindow(dpy, locks[screen]->win); + } } + } else for (screen = 0; screen < nscreens; screen++) + XRaiseWindow(dpy, locks[screen]->win); + } + + time_t currenttime; + time(¤ttime); + + if (currenttime >= lasttouched + timeoffset){ + if (!runonce || !runflag){ + runflag = 1; + system(command); } - } else for (screen = 0; screen < nscreens; screen++) - XRaiseWindow(dpy, locks[screen]->win); + } } } @@ -221,6 +241,8 @@ lockscreen(Display *dpy, struct xrandr *rr, int screen) XSetWindowAttributes wa; Cursor invisible; + time(&lasttouched); + if (dpy == NULL || screen < 0 || !(lock = malloc(sizeof(struct lock)))) return NULL; diff --git a/slock.o b/slock.o index 4bb0bc2..286f838 100644 Binary files a/slock.o and b/slock.o differ