sites

public wiki contents of suckless.org
git clone git://git.suckless.org/sites
Log | Files | Refs

dmenu-qalc-5.2.diff (6671B)


      1 diff -up dmenu-5.2/config.mk dmenu-qalc-5.2/config.mk
      2 --- dmenu-5.2/config.mk	2022-10-04 13:36:58.000000000 -0400
      3 +++ dmenu-qalc-5.2/config.mk	2023-10-27 19:29:48.197693355 -0400
      4 @@ -24,7 +24,7 @@ INCS = -I$(X11INC) -I$(FREETYPEINC)
      5  LIBS = -L$(X11LIB) -lX11 $(XINERAMALIBS) $(FREETYPELIBS)
      6  
      7  # flags
      8 -CPPFLAGS = -D_DEFAULT_SOURCE -D_BSD_SOURCE -D_XOPEN_SOURCE=700 -D_POSIX_C_SOURCE=200809L -DVERSION=\"$(VERSION)\" $(XINERAMAFLAGS)
      9 +CPPFLAGS = -D_DEFAULT_SOURCE -D_GNU_SOURCE -D_BSD_SOURCE -D_XOPEN_SOURCE=700 -D_POSIX_C_SOURCE=200809L -DVERSION=\"$(VERSION)\" $(XINERAMAFLAGS)
     10  CFLAGS   = -std=c99 -pedantic -Wall -Os $(INCS) $(CPPFLAGS)
     11  LDFLAGS  = $(LIBS)
     12  
     13 diff -up dmenu-5.2/dmenu.1 dmenu-qalc-5.2/dmenu.1
     14 --- dmenu-5.2/dmenu.1	2022-10-04 13:36:58.000000000 -0400
     15 +++ dmenu-qalc-5.2/dmenu.1	2023-10-27 19:28:48.676578875 -0400
     16 @@ -40,6 +40,9 @@ which lists programs in the user's $PATH
     17  .B \-b
     18  dmenu appears at the bottom of the screen.
     19  .TP
     20 +.B \-C
     21 +dmenu becomes a calculator.
     22 +.TP
     23  .B \-f
     24  dmenu grabs the keyboard before reading stdin if not reading from a tty. This
     25  is faster, but will lock up X until stdin reaches end\-of\-file.
     26 diff -up dmenu-5.2/dmenu.c dmenu-qalc-5.2/dmenu.c
     27 --- dmenu-5.2/dmenu.c	2022-10-04 13:36:58.000000000 -0400
     28 +++ dmenu-qalc-5.2/dmenu.c	2023-10-27 20:00:21.438467597 -0400
     29 @@ -7,6 +7,11 @@
     30  #include <strings.h>
     31  #include <time.h>
     32  #include <unistd.h>
     33 +#include <errno.h>
     34 +#include <fcntl.h>
     35 +#include <signal.h>
     36 +#include <sys/prctl.h>
     37 +#include <sys/select.h>
     38  
     39  #include <X11/Xlib.h>
     40  #include <X11/Xatom.h>
     41 @@ -34,6 +39,12 @@ struct item {
     42  	int out;
     43  };
     44  
     45 +static struct {
     46 +  pid_t pid;
     47 +  int enable, in[2], out[2];
     48 +  char buf[256];
     49 +} qalc;
     50 +
     51  static char text[BUFSIZ] = "";
     52  static char *embed;
     53  static int bh, mw, mh;
     54 @@ -228,8 +239,81 @@ grabkeyboard(void)
     55  }
     56  
     57  static void
     58 +init_qalc(void)
     59 +{
     60 +  pipe(qalc.in);
     61 +  pipe2(qalc.out, O_NONBLOCK);
     62 +  qalc.pid = fork();
     63 +  if (qalc.pid == -1)
     64 +    die("failed to fork for qalc");
     65 +  if (qalc.pid == 0) {
     66 +    dup2(qalc.in[0], STDIN_FILENO);
     67 +    dup2(qalc.out[1], STDOUT_FILENO);
     68 +    close(qalc.in[1]);
     69 +    close(qalc.out[0]);
     70 +    prctl(PR_SET_PDEATHSIG, SIGTERM);
     71 +    execl("/usr/bin/qalc", "qalc", "-c0", "-t", NULL);
     72 +    die ("execl qalc failed");
     73 +  } else { // parent
     74 +    close(qalc.in[0]);
     75 +    close(qalc.out[1]);
     76 +    items = malloc(sizeof(struct item)*2);
     77 +    items[0].text = malloc(LENGTH(qalc.buf));
     78 +    strcpy(items[0].text, "no result");
     79 +    items[1].out = 0;
     80 +    items[1].text = NULL;
     81 +  }
     82 +}
     83 +
     84 +static void
     85 +recv_qalc(void)
     86 +{
     87 +  ssize_t r = read(qalc.out[0], qalc.buf, LENGTH(qalc.buf));
     88 +
     89 +  if (r < 0)
     90 +    die("error reading qalc.out");
     91 +
     92 +  if (qalc.buf[0] == '\n') {
     93 +    int i;
     94 +    for (i = 3; i < LENGTH(qalc.buf) && qalc.buf[i] != '\n'; ++i)
     95 +      items[0].text[i-3] = qalc.buf[i];
     96 +    items[0].text[i-3] = 0;
     97 +    if (r != LENGTH(qalc.buf))
     98 +      return;
     99 +  }
    100 +
    101 +  while (read(qalc.out[0], qalc.buf, LENGTH(qalc.buf)) != -1)
    102 +    ; // empty the pipe
    103 +  if (errno != EAGAIN && errno != EWOULDBLOCK)
    104 +    die("error emptying qalc.out");
    105 +}
    106 +
    107 +static void
    108 +send_qalc(void)
    109 +{
    110 +  int s = strlen(text);
    111 +  text[s] = '\n';
    112 +  write(qalc.in[1], text, s+1);
    113 +  text[s] = 0;
    114 +}
    115 +
    116 +static void
    117 +match_qalc(void)
    118 +{
    119 +  matches = matchend = NULL;
    120 +  appenditem(items, &matches, &matchend);
    121 +  curr = sel = matches;
    122 +  calcoffsets();
    123 +}
    124 +
    125 +static void
    126  match(void)
    127  {
    128 +  if (qalc.enable) {
    129 +    match_qalc();
    130 +    return;
    131 +  }
    132 +
    133  	static char **tokv = NULL;
    134  	static int tokn = 0;
    135  
    136 @@ -524,6 +608,9 @@ insert:
    137  		break;
    138  	}
    139  
    140 +  if (qalc.enable)
    141 +    send_qalc();
    142 +
    143  draw:
    144  	drawmenu();
    145  }
    146 @@ -573,37 +660,52 @@ run(void)
    147  {
    148  	XEvent ev;
    149  
    150 -	while (!XNextEvent(dpy, &ev)) {
    151 -		if (XFilterEvent(&ev, win))
    152 -			continue;
    153 -		switch(ev.type) {
    154 -		case DestroyNotify:
    155 -			if (ev.xdestroywindow.window != win)
    156 -				break;
    157 -			cleanup();
    158 -			exit(1);
    159 -		case Expose:
    160 -			if (ev.xexpose.count == 0)
    161 -				drw_map(drw, win, 0, 0, mw, mh);
    162 -			break;
    163 -		case FocusIn:
    164 -			/* regrab focus from parent window */
    165 -			if (ev.xfocus.window != win)
    166 -				grabfocus();
    167 -			break;
    168 -		case KeyPress:
    169 -			keypress(&ev.xkey);
    170 -			break;
    171 -		case SelectionNotify:
    172 -			if (ev.xselection.property == utf8)
    173 -				paste();
    174 -			break;
    175 -		case VisibilityNotify:
    176 -			if (ev.xvisibility.state != VisibilityUnobscured)
    177 -				XRaiseWindow(dpy, win);
    178 -			break;
    179 -		}
    180 -	}
    181 +  fd_set rfds;
    182 +  int xfd = ConnectionNumber(dpy);
    183 +
    184 +  for (;;) {
    185 +    FD_ZERO(&rfds);
    186 +    FD_SET(xfd, &rfds);
    187 +    FD_SET(qalc.out[0], &rfds);
    188 +
    189 +    if (select(MAX(xfd, qalc.out[0])+1, &rfds, NULL, NULL, NULL) > 0) {
    190 +      if (qalc.enable && FD_ISSET(qalc.out[0], &rfds)) {
    191 +        recv_qalc();
    192 +        drawmenu();
    193 +      }
    194 +      while (XPending(dpy) && !XNextEvent(dpy, &ev)) {
    195 +        if (XFilterEvent(&ev, win))
    196 +          continue;
    197 +        switch(ev.type) {
    198 +          case DestroyNotify:
    199 +            if (ev.xdestroywindow.window != win)
    200 +              break;
    201 +            cleanup();
    202 +            exit(1);
    203 +          case Expose:
    204 +            if (ev.xexpose.count == 0)
    205 +              drw_map(drw, win, 0, 0, mw, mh);
    206 +            break;
    207 +          case FocusIn:
    208 +            /* regrab focus from parent window */
    209 +            if (ev.xfocus.window != win)
    210 +              grabfocus();
    211 +            break;
    212 +          case KeyPress:
    213 +            keypress(&ev.xkey);
    214 +            break;
    215 +          case SelectionNotify:
    216 +            if (ev.xselection.property == utf8)
    217 +              paste();
    218 +            break;
    219 +          case VisibilityNotify:
    220 +            if (ev.xvisibility.state != VisibilityUnobscured)
    221 +              XRaiseWindow(dpy, win);
    222 +            break;
    223 +        }
    224 +      }
    225 +    }
    226 +  }
    227  }
    228  
    229  static void
    230 @@ -710,7 +812,7 @@ setup(void)
    231  static void
    232  usage(void)
    233  {
    234 -	die("usage: dmenu [-bfiv] [-l lines] [-p prompt] [-fn font] [-m monitor]\n"
    235 +	die("usage: dmenu [-bCfiv] [-l lines] [-p prompt] [-fn font] [-m monitor]\n"
    236  	    "             [-nb color] [-nf color] [-sb color] [-sf color] [-w windowid]");
    237  }
    238  
    239 @@ -727,6 +829,8 @@ main(int argc, char *argv[])
    240  			exit(0);
    241  		} else if (!strcmp(argv[i], "-b")) /* appears at the bottom of the screen */
    242  			topbar = 0;
    243 +		else if (!strcmp(argv[i], "-C"))   /* grabs keyboard before reading stdin */
    244 +			qalc.enable = 1;
    245  		else if (!strcmp(argv[i], "-f"))   /* grabs keyboard before reading stdin */
    246  			fast = 1;
    247  		else if (!strcmp(argv[i], "-i")) { /* case-insensitive item matching */
    248 @@ -777,7 +881,10 @@ main(int argc, char *argv[])
    249  		die("pledge");
    250  #endif
    251  
    252 -	if (fast && !isatty(0)) {
    253 +	if (qalc.enable) {
    254 +		init_qalc();
    255 +		grabkeyboard();
    256 +	} else if (fast && !isatty(0)) {
    257  		grabkeyboard();
    258  		readstdin();
    259  	} else {