17dd7cddfSDavid du Colombier #include <u.h>
27dd7cddfSDavid du Colombier #include <libc.h>
37dd7cddfSDavid du Colombier #include <draw.h>
47dd7cddfSDavid du Colombier #include <cursor.h>
57dd7cddfSDavid du Colombier #include <event.h>
67dd7cddfSDavid du Colombier
77dd7cddfSDavid du Colombier typedef struct Slave Slave;
87dd7cddfSDavid du Colombier typedef struct Ebuf Ebuf;
97dd7cddfSDavid du Colombier
107dd7cddfSDavid du Colombier struct Slave
117dd7cddfSDavid du Colombier {
127dd7cddfSDavid du Colombier int pid;
13*14cc0f53SDavid du Colombier Ebuf *head; /* queue of messages for this descriptor */
147dd7cddfSDavid du Colombier Ebuf *tail;
157dd7cddfSDavid du Colombier int (*fn)(int, Event*, uchar*, int);
167dd7cddfSDavid du Colombier };
177dd7cddfSDavid du Colombier
187dd7cddfSDavid du Colombier struct Ebuf
197dd7cddfSDavid du Colombier {
207dd7cddfSDavid du Colombier Ebuf *next;
217dd7cddfSDavid du Colombier int n; /* number of bytes in buf */
227dd7cddfSDavid du Colombier uchar buf[EMAXMSG];
237dd7cddfSDavid du Colombier };
247dd7cddfSDavid du Colombier
257dd7cddfSDavid du Colombier static Slave eslave[MAXSLAVE];
267dd7cddfSDavid du Colombier static int Skeyboard = -1;
277dd7cddfSDavid du Colombier static int Smouse = -1;
287dd7cddfSDavid du Colombier static int Stimer = -1;
297dd7cddfSDavid du Colombier static int logfid;
307dd7cddfSDavid du Colombier
317dd7cddfSDavid du Colombier static int nslave;
327dd7cddfSDavid du Colombier static int parentpid;
337dd7cddfSDavid du Colombier static int epipe[2];
34*14cc0f53SDavid du Colombier
357dd7cddfSDavid du Colombier static int eforkslave(ulong);
367dd7cddfSDavid du Colombier static void extract(void);
377dd7cddfSDavid du Colombier static void ekill(void);
387dd7cddfSDavid du Colombier static int enote(void *, char *);
39*14cc0f53SDavid du Colombier
407dd7cddfSDavid du Colombier static int mousefd;
417dd7cddfSDavid du Colombier static int cursorfd;
427dd7cddfSDavid du Colombier
437dd7cddfSDavid du Colombier static
447dd7cddfSDavid du Colombier Ebuf*
ebread(Slave * s)457dd7cddfSDavid du Colombier ebread(Slave *s)
467dd7cddfSDavid du Colombier {
477dd7cddfSDavid du Colombier Ebuf *eb;
489a747e4fSDavid du Colombier Dir *d;
499a747e4fSDavid du Colombier ulong l;
507dd7cddfSDavid du Colombier
517dd7cddfSDavid du Colombier for(;;){
529a747e4fSDavid du Colombier d = dirfstat(epipe[0]);
539a747e4fSDavid du Colombier if(d == nil)
547dd7cddfSDavid du Colombier drawerror(display, "events: eread stat error");
559a747e4fSDavid du Colombier l = d->length;
569a747e4fSDavid du Colombier free(d);
579a747e4fSDavid du Colombier if(s->head && l==0)
587dd7cddfSDavid du Colombier break;
597dd7cddfSDavid du Colombier extract();
607dd7cddfSDavid du Colombier }
617dd7cddfSDavid du Colombier eb = s->head;
627dd7cddfSDavid du Colombier s->head = s->head->next;
637dd7cddfSDavid du Colombier if(s->head == 0)
647dd7cddfSDavid du Colombier s->tail = 0;
657dd7cddfSDavid du Colombier return eb;
667dd7cddfSDavid du Colombier }
677dd7cddfSDavid du Colombier
687dd7cddfSDavid du Colombier ulong
event(Event * e)697dd7cddfSDavid du Colombier event(Event *e)
707dd7cddfSDavid du Colombier {
717dd7cddfSDavid du Colombier return eread(~0UL, e);
727dd7cddfSDavid du Colombier }
737dd7cddfSDavid du Colombier
747dd7cddfSDavid du Colombier ulong
eread(ulong keys,Event * e)757dd7cddfSDavid du Colombier eread(ulong keys, Event *e)
767dd7cddfSDavid du Colombier {
777dd7cddfSDavid du Colombier Ebuf *eb;
787dd7cddfSDavid du Colombier int i, id;
797dd7cddfSDavid du Colombier
807dd7cddfSDavid du Colombier if(keys == 0)
817dd7cddfSDavid du Colombier return 0;
827dd7cddfSDavid du Colombier for(;;){
837dd7cddfSDavid du Colombier for(i=0; i<nslave; i++)
847dd7cddfSDavid du Colombier if((keys & (1<<i)) && eslave[i].head){
857dd7cddfSDavid du Colombier id = 1<<i;
867dd7cddfSDavid du Colombier if(i == Smouse)
877dd7cddfSDavid du Colombier e->mouse = emouse();
887dd7cddfSDavid du Colombier else if(i == Skeyboard)
897dd7cddfSDavid du Colombier e->kbdc = ekbd();
907dd7cddfSDavid du Colombier else if(i == Stimer)
917dd7cddfSDavid du Colombier eslave[i].head = 0;
927dd7cddfSDavid du Colombier else{
937dd7cddfSDavid du Colombier eb = ebread(&eslave[i]);
947dd7cddfSDavid du Colombier e->n = eb->n;
957dd7cddfSDavid du Colombier if(eslave[i].fn)
967dd7cddfSDavid du Colombier id = (*eslave[i].fn)(id, e, eb->buf, eb->n);
977dd7cddfSDavid du Colombier else
987dd7cddfSDavid du Colombier memmove(e->data, eb->buf, eb->n);
997dd7cddfSDavid du Colombier free(eb);
1007dd7cddfSDavid du Colombier }
1017dd7cddfSDavid du Colombier return id;
1027dd7cddfSDavid du Colombier }
1037dd7cddfSDavid du Colombier extract();
1047dd7cddfSDavid du Colombier }
1057dd7cddfSDavid du Colombier }
1067dd7cddfSDavid du Colombier
1077dd7cddfSDavid du Colombier int
ecanmouse(void)1087dd7cddfSDavid du Colombier ecanmouse(void)
1097dd7cddfSDavid du Colombier {
1107dd7cddfSDavid du Colombier if(Smouse < 0)
1117dd7cddfSDavid du Colombier drawerror(display, "events: mouse not initialized");
1127dd7cddfSDavid du Colombier return ecanread(Emouse);
1137dd7cddfSDavid du Colombier }
1147dd7cddfSDavid du Colombier
1157dd7cddfSDavid du Colombier int
ecankbd(void)1167dd7cddfSDavid du Colombier ecankbd(void)
1177dd7cddfSDavid du Colombier {
1187dd7cddfSDavid du Colombier if(Skeyboard < 0)
1197dd7cddfSDavid du Colombier drawerror(display, "events: keyboard not initialzed");
1207dd7cddfSDavid du Colombier return ecanread(Ekeyboard);
1217dd7cddfSDavid du Colombier }
1227dd7cddfSDavid du Colombier
1237dd7cddfSDavid du Colombier int
ecanread(ulong keys)1247dd7cddfSDavid du Colombier ecanread(ulong keys)
1257dd7cddfSDavid du Colombier {
1269a747e4fSDavid du Colombier Dir *d;
1277dd7cddfSDavid du Colombier int i;
1289a747e4fSDavid du Colombier ulong l;
1297dd7cddfSDavid du Colombier
1307dd7cddfSDavid du Colombier for(;;){
1317dd7cddfSDavid du Colombier for(i=0; i<nslave; i++)
1327dd7cddfSDavid du Colombier if((keys & (1<<i)) && eslave[i].head)
1337dd7cddfSDavid du Colombier return 1;
1349a747e4fSDavid du Colombier d = dirfstat(epipe[0]);
1359a747e4fSDavid du Colombier if(d == nil)
1367dd7cddfSDavid du Colombier drawerror(display, "events: ecanread stat error");
1379a747e4fSDavid du Colombier l = d->length;
1389a747e4fSDavid du Colombier free(d);
1399a747e4fSDavid du Colombier if(l == 0)
1407dd7cddfSDavid du Colombier return 0;
1417dd7cddfSDavid du Colombier extract();
1427dd7cddfSDavid du Colombier }
1437dd7cddfSDavid du Colombier }
1447dd7cddfSDavid du Colombier
1457dd7cddfSDavid du Colombier ulong
estartfn(ulong key,int fd,int n,int (* fn)(int,Event *,uchar *,int))1467dd7cddfSDavid du Colombier estartfn(ulong key, int fd, int n, int (*fn)(int, Event*, uchar*, int))
1477dd7cddfSDavid du Colombier {
1487dd7cddfSDavid du Colombier char buf[EMAXMSG+1];
1497dd7cddfSDavid du Colombier int i, r;
1507dd7cddfSDavid du Colombier
1517dd7cddfSDavid du Colombier if(fd < 0)
1527dd7cddfSDavid du Colombier drawerror(display, "events: bad file descriptor");
1537dd7cddfSDavid du Colombier if(n <= 0 || n > EMAXMSG)
1547dd7cddfSDavid du Colombier n = EMAXMSG;
1557dd7cddfSDavid du Colombier i = eforkslave(key);
1567dd7cddfSDavid du Colombier if(i < MAXSLAVE){
1577dd7cddfSDavid du Colombier eslave[i].fn = fn;
1587dd7cddfSDavid du Colombier return 1<<i;
1597dd7cddfSDavid du Colombier }
1607dd7cddfSDavid du Colombier buf[0] = i - MAXSLAVE;
1617dd7cddfSDavid du Colombier while((r = read(fd, buf+1, n))>0)
1627dd7cddfSDavid du Colombier if(write(epipe[1], buf, r+1)!=r+1)
1637dd7cddfSDavid du Colombier break;
1647dd7cddfSDavid du Colombier buf[0] = MAXSLAVE;
1657dd7cddfSDavid du Colombier write(epipe[1], buf, 1);
1667dd7cddfSDavid du Colombier _exits(0);
1677dd7cddfSDavid du Colombier return 0;
1687dd7cddfSDavid du Colombier }
1697dd7cddfSDavid du Colombier
1707dd7cddfSDavid du Colombier ulong
estart(ulong key,int fd,int n)1717dd7cddfSDavid du Colombier estart(ulong key, int fd, int n)
1727dd7cddfSDavid du Colombier {
1737dd7cddfSDavid du Colombier return estartfn(key, fd, n, nil);
1747dd7cddfSDavid du Colombier }
1757dd7cddfSDavid du Colombier
1767dd7cddfSDavid du Colombier ulong
etimer(ulong key,int n)1777dd7cddfSDavid du Colombier etimer(ulong key, int n)
1787dd7cddfSDavid du Colombier {
1797dd7cddfSDavid du Colombier char t[2];
1807dd7cddfSDavid du Colombier
1817dd7cddfSDavid du Colombier if(Stimer != -1)
1827dd7cddfSDavid du Colombier drawerror(display, "events: timer started twice");
1837dd7cddfSDavid du Colombier Stimer = eforkslave(key);
1847dd7cddfSDavid du Colombier if(Stimer < MAXSLAVE)
1857dd7cddfSDavid du Colombier return 1<<Stimer;
1867dd7cddfSDavid du Colombier if(n <= 0)
1877dd7cddfSDavid du Colombier n = 1000;
1887dd7cddfSDavid du Colombier t[0] = t[1] = Stimer - MAXSLAVE;
1897dd7cddfSDavid du Colombier do
1907dd7cddfSDavid du Colombier sleep(n);
1917dd7cddfSDavid du Colombier while(write(epipe[1], t, 2) == 2);
1927dd7cddfSDavid du Colombier t[0] = MAXSLAVE;
1937dd7cddfSDavid du Colombier write(epipe[1], t, 1);
1947dd7cddfSDavid du Colombier _exits(0);
1957dd7cddfSDavid du Colombier return 0;
1967dd7cddfSDavid du Colombier }
1977dd7cddfSDavid du Colombier
1987dd7cddfSDavid du Colombier static void
ekeyslave(int fd)1997dd7cddfSDavid du Colombier ekeyslave(int fd)
2007dd7cddfSDavid du Colombier {
2017dd7cddfSDavid du Colombier Rune r;
2027dd7cddfSDavid du Colombier char t[3], k[10];
2037dd7cddfSDavid du Colombier int kr, kn, w;
2047dd7cddfSDavid du Colombier
2057dd7cddfSDavid du Colombier if(eforkslave(Ekeyboard) < MAXSLAVE)
2067dd7cddfSDavid du Colombier return;
2077dd7cddfSDavid du Colombier kn = 0;
2087dd7cddfSDavid du Colombier t[0] = Skeyboard;
2097dd7cddfSDavid du Colombier for(;;){
2107dd7cddfSDavid du Colombier while(!fullrune(k, kn)){
2117dd7cddfSDavid du Colombier kr = read(fd, k+kn, sizeof k - kn);
2129a747e4fSDavid du Colombier if(kr <= 0)
2139a747e4fSDavid du Colombier goto breakout;
2147dd7cddfSDavid du Colombier kn += kr;
2157dd7cddfSDavid du Colombier }
2167dd7cddfSDavid du Colombier w = chartorune(&r, k);
2177dd7cddfSDavid du Colombier kn -= w;
2187dd7cddfSDavid du Colombier memmove(k, &k[w], kn);
2197dd7cddfSDavid du Colombier t[1] = r;
2207dd7cddfSDavid du Colombier t[2] = r>>8;
2219a747e4fSDavid du Colombier if(write(epipe[1], t, 3) != 3)
2229a747e4fSDavid du Colombier break;
2237dd7cddfSDavid du Colombier }
2249a747e4fSDavid du Colombier breakout:;
2259a747e4fSDavid du Colombier t[0] = MAXSLAVE;
2269a747e4fSDavid du Colombier write(epipe[1], t, 1);
2279a747e4fSDavid du Colombier _exits(0);
2287dd7cddfSDavid du Colombier }
2297dd7cddfSDavid du Colombier
2307dd7cddfSDavid du Colombier void
einit(ulong keys)2317dd7cddfSDavid du Colombier einit(ulong keys)
2327dd7cddfSDavid du Colombier {
2337dd7cddfSDavid du Colombier int ctl, fd;
2347dd7cddfSDavid du Colombier char buf[256];
2357dd7cddfSDavid du Colombier
2367dd7cddfSDavid du Colombier parentpid = getpid();
2377dd7cddfSDavid du Colombier if(pipe(epipe) < 0)
2387dd7cddfSDavid du Colombier drawerror(display, "events: einit pipe");
2397dd7cddfSDavid du Colombier atexit(ekill);
2407dd7cddfSDavid du Colombier atnotify(enote, 1);
2417dd7cddfSDavid du Colombier snprint(buf, sizeof buf, "%s/mouse", display->devdir);
2427dd7cddfSDavid du Colombier mousefd = open(buf, ORDWR|OCEXEC);
2437dd7cddfSDavid du Colombier if(mousefd < 0)
2447dd7cddfSDavid du Colombier drawerror(display, "einit: can't open mouse\n");
2457dd7cddfSDavid du Colombier snprint(buf, sizeof buf, "%s/cursor", display->devdir);
2467dd7cddfSDavid du Colombier cursorfd = open(buf, ORDWR|OCEXEC);
2477dd7cddfSDavid du Colombier if(cursorfd < 0)
2487dd7cddfSDavid du Colombier drawerror(display, "einit: can't open cursor\n");
2497dd7cddfSDavid du Colombier if(keys&Ekeyboard){
2507dd7cddfSDavid du Colombier snprint(buf, sizeof buf, "%s/cons", display->devdir);
2517dd7cddfSDavid du Colombier fd = open(buf, OREAD);
2527dd7cddfSDavid du Colombier if(fd < 0)
2537dd7cddfSDavid du Colombier drawerror(display, "events: can't open console");
2547dd7cddfSDavid du Colombier snprint(buf, sizeof buf, "%s/consctl", display->devdir);
2557dd7cddfSDavid du Colombier ctl = open("/dev/consctl", OWRITE|OCEXEC);
2567dd7cddfSDavid du Colombier if(ctl < 0)
2577dd7cddfSDavid du Colombier drawerror(display, "events: can't open consctl");
2587dd7cddfSDavid du Colombier write(ctl, "rawon", 5);
2597dd7cddfSDavid du Colombier for(Skeyboard=0; Ekeyboard & ~(1<<Skeyboard); Skeyboard++)
2607dd7cddfSDavid du Colombier ;
2617dd7cddfSDavid du Colombier ekeyslave(fd);
2627dd7cddfSDavid du Colombier }
2637dd7cddfSDavid du Colombier if(keys&Emouse){
2647dd7cddfSDavid du Colombier estart(Emouse, mousefd, 1+4*12);
2657dd7cddfSDavid du Colombier for(Smouse=0; Emouse & ~(1<<Smouse); Smouse++)
2667dd7cddfSDavid du Colombier ;
2677dd7cddfSDavid du Colombier }
2687dd7cddfSDavid du Colombier }
2697dd7cddfSDavid du Colombier
2707dd7cddfSDavid du Colombier static void
extract(void)2717dd7cddfSDavid du Colombier extract(void)
2727dd7cddfSDavid du Colombier {
2737dd7cddfSDavid du Colombier Slave *s;
2747dd7cddfSDavid du Colombier Ebuf *eb;
2757dd7cddfSDavid du Colombier int i, n;
2767dd7cddfSDavid du Colombier uchar ebuf[EMAXMSG+1];
2777dd7cddfSDavid du Colombier
2787dd7cddfSDavid du Colombier /* avoid generating a message if there's nothing to show. */
2797dd7cddfSDavid du Colombier /* this test isn't perfect, though; could do flushimage(display, 0) then call extract */
2807dd7cddfSDavid du Colombier /* also: make sure we don't interfere if we're multiprocessing the display */
2817dd7cddfSDavid du Colombier if(display->locking){
2827dd7cddfSDavid du Colombier /* if locking is being done by program, this means it can't depend on automatic flush in emouse() etc. */
2837dd7cddfSDavid du Colombier if(canqlock(&display->qlock)){
2847dd7cddfSDavid du Colombier if(display->bufp > display->buf)
2857dd7cddfSDavid du Colombier flushimage(display, 1);
2867dd7cddfSDavid du Colombier unlockdisplay(display);
2877dd7cddfSDavid du Colombier }
2887dd7cddfSDavid du Colombier }else
2897dd7cddfSDavid du Colombier if(display->bufp > display->buf)
2907dd7cddfSDavid du Colombier flushimage(display, 1);
2917dd7cddfSDavid du Colombier loop:
2927dd7cddfSDavid du Colombier if((n=read(epipe[0], ebuf, EMAXMSG+1)) < 0
2937dd7cddfSDavid du Colombier || ebuf[0] >= MAXSLAVE)
2947dd7cddfSDavid du Colombier drawerror(display, "eof on event pipe");
2957dd7cddfSDavid du Colombier if(n == 0)
2967dd7cddfSDavid du Colombier goto loop;
2977dd7cddfSDavid du Colombier i = ebuf[0];
2987dd7cddfSDavid du Colombier if(i >= nslave || n <= 1)
2997dd7cddfSDavid du Colombier drawerror(display, "events: protocol error: short read");
3007dd7cddfSDavid du Colombier s = &eslave[i];
3017dd7cddfSDavid du Colombier if(i == Stimer){
3027dd7cddfSDavid du Colombier s->head = (Ebuf *)1;
3037dd7cddfSDavid du Colombier return;
3047dd7cddfSDavid du Colombier }
3057dd7cddfSDavid du Colombier if(i == Skeyboard && n != 3)
3067dd7cddfSDavid du Colombier drawerror(display, "events: protocol error: keyboard");
3077dd7cddfSDavid du Colombier if(i == Smouse){
3087dd7cddfSDavid du Colombier if(n < 1+1+2*12)
3097dd7cddfSDavid du Colombier drawerror(display, "events: protocol error: mouse");
3107dd7cddfSDavid du Colombier if(ebuf[1] == 'r')
3117dd7cddfSDavid du Colombier eresized(1);
3127dd7cddfSDavid du Colombier /* squash extraneous mouse events */
3137dd7cddfSDavid du Colombier if((eb=s->tail) && memcmp(eb->buf+1+2*12, ebuf+1+1+2*12, 12)==0){
3147dd7cddfSDavid du Colombier memmove(eb->buf, &ebuf[1], n - 1);
3157dd7cddfSDavid du Colombier return;
3167dd7cddfSDavid du Colombier }
3177dd7cddfSDavid du Colombier }
3187dd7cddfSDavid du Colombier /* try to save space by only allocating as much buffer as we need */
3197dd7cddfSDavid du Colombier eb = malloc(sizeof(*eb) - sizeof(eb->buf) + n - 1);
3207dd7cddfSDavid du Colombier if(eb == 0)
3217dd7cddfSDavid du Colombier drawerror(display, "events: protocol error 4");
3227dd7cddfSDavid du Colombier eb->n = n - 1;
3237dd7cddfSDavid du Colombier memmove(eb->buf, &ebuf[1], n - 1);
3247dd7cddfSDavid du Colombier eb->next = 0;
3257dd7cddfSDavid du Colombier if(s->head)
3267dd7cddfSDavid du Colombier s->tail = s->tail->next = eb;
3277dd7cddfSDavid du Colombier else
3287dd7cddfSDavid du Colombier s->head = s->tail = eb;
3297dd7cddfSDavid du Colombier }
3307dd7cddfSDavid du Colombier
3317dd7cddfSDavid du Colombier static int
eforkslave(ulong key)3327dd7cddfSDavid du Colombier eforkslave(ulong key)
3337dd7cddfSDavid du Colombier {
3347dd7cddfSDavid du Colombier int i, pid;
3357dd7cddfSDavid du Colombier
3367dd7cddfSDavid du Colombier for(i=0; i<MAXSLAVE; i++)
3377dd7cddfSDavid du Colombier if((key & ~(1<<i)) == 0 && eslave[i].pid == 0){
3387dd7cddfSDavid du Colombier if(nslave <= i)
3397dd7cddfSDavid du Colombier nslave = i + 1;
3407dd7cddfSDavid du Colombier /*
3417dd7cddfSDavid du Colombier * share the file descriptors so the last child
3427dd7cddfSDavid du Colombier * out closes all connections to the window server.
3437dd7cddfSDavid du Colombier */
3447dd7cddfSDavid du Colombier switch(pid = rfork(RFPROC)){
3457dd7cddfSDavid du Colombier case 0:
3467dd7cddfSDavid du Colombier return MAXSLAVE+i;
3477dd7cddfSDavid du Colombier case -1:
3487dd7cddfSDavid du Colombier fprint(2, "events: fork error\n");
3497dd7cddfSDavid du Colombier exits("fork");
3507dd7cddfSDavid du Colombier }
3517dd7cddfSDavid du Colombier eslave[i].pid = pid;
3527dd7cddfSDavid du Colombier eslave[i].head = eslave[i].tail = 0;
3537dd7cddfSDavid du Colombier return i;
3547dd7cddfSDavid du Colombier }
3557dd7cddfSDavid du Colombier drawerror(display, "events: bad slave assignment");
3567dd7cddfSDavid du Colombier return 0;
3577dd7cddfSDavid du Colombier }
3587dd7cddfSDavid du Colombier
3597dd7cddfSDavid du Colombier static int
enote(void * v,char * s)3607dd7cddfSDavid du Colombier enote(void *v, char *s)
3617dd7cddfSDavid du Colombier {
3629a747e4fSDavid du Colombier char t[1];
3637dd7cddfSDavid du Colombier int i, pid;
3647dd7cddfSDavid du Colombier
3657dd7cddfSDavid du Colombier USED(v, s);
3667dd7cddfSDavid du Colombier pid = getpid();
3679a747e4fSDavid du Colombier if(pid != parentpid){
3689a747e4fSDavid du Colombier for(i=0; i<nslave; i++){
3699a747e4fSDavid du Colombier if(pid == eslave[i].pid){
3709a747e4fSDavid du Colombier t[0] = MAXSLAVE;
3719a747e4fSDavid du Colombier write(epipe[1], t, 1);
3729a747e4fSDavid du Colombier break;
3739a747e4fSDavid du Colombier }
3749a747e4fSDavid du Colombier }
3759a747e4fSDavid du Colombier return 0;
3769a747e4fSDavid du Colombier }
3779a747e4fSDavid du Colombier close(epipe[0]);
3789a747e4fSDavid du Colombier epipe[0] = -1;
3799a747e4fSDavid du Colombier close(epipe[1]);
3809a747e4fSDavid du Colombier epipe[1] = -1;
3817dd7cddfSDavid du Colombier for(i=0; i<nslave; i++){
3827dd7cddfSDavid du Colombier if(pid == eslave[i].pid)
3837dd7cddfSDavid du Colombier continue; /* don't kill myself */
3847dd7cddfSDavid du Colombier postnote(PNPROC, eslave[i].pid, "die");
3857dd7cddfSDavid du Colombier }
3867dd7cddfSDavid du Colombier return 0;
3877dd7cddfSDavid du Colombier }
3887dd7cddfSDavid du Colombier
3897dd7cddfSDavid du Colombier static void
ekill(void)3907dd7cddfSDavid du Colombier ekill(void)
3917dd7cddfSDavid du Colombier {
3927dd7cddfSDavid du Colombier enote(0, 0);
3937dd7cddfSDavid du Colombier }
3947dd7cddfSDavid du Colombier
3957dd7cddfSDavid du Colombier Mouse
emouse(void)3967dd7cddfSDavid du Colombier emouse(void)
3977dd7cddfSDavid du Colombier {
3987dd7cddfSDavid du Colombier Mouse m;
3997dd7cddfSDavid du Colombier Ebuf *eb;
4007dd7cddfSDavid du Colombier static but[2];
4017dd7cddfSDavid du Colombier int b;
4027dd7cddfSDavid du Colombier
4037dd7cddfSDavid du Colombier if(Smouse < 0)
4047dd7cddfSDavid du Colombier drawerror(display, "events: mouse not initialized");
4057dd7cddfSDavid du Colombier eb = ebread(&eslave[Smouse]);
4067dd7cddfSDavid du Colombier m.xy.x = atoi((char*)eb->buf+1+0*12);
4077dd7cddfSDavid du Colombier m.xy.y = atoi((char*)eb->buf+1+1*12);
4087dd7cddfSDavid du Colombier b = atoi((char*)eb->buf+1+2*12);
409a8453668SDavid du Colombier m.buttons = b;
4107dd7cddfSDavid du Colombier m.msec = atoi((char*)eb->buf+1+3*12);
4117dd7cddfSDavid du Colombier if (logfid)
4127dd7cddfSDavid du Colombier fprint(logfid, "b: %d xy: %P\n", m.buttons, m.xy);
4137dd7cddfSDavid du Colombier free(eb);
4147dd7cddfSDavid du Colombier return m;
4157dd7cddfSDavid du Colombier }
4167dd7cddfSDavid du Colombier
4177dd7cddfSDavid du Colombier int
ekbd(void)4187dd7cddfSDavid du Colombier ekbd(void)
4197dd7cddfSDavid du Colombier {
4207dd7cddfSDavid du Colombier Ebuf *eb;
4217dd7cddfSDavid du Colombier int c;
4227dd7cddfSDavid du Colombier
4237dd7cddfSDavid du Colombier if(Skeyboard < 0)
4247dd7cddfSDavid du Colombier drawerror(display, "events: keyboard not initialzed");
4257dd7cddfSDavid du Colombier eb = ebread(&eslave[Skeyboard]);
4267dd7cddfSDavid du Colombier c = eb->buf[0] + (eb->buf[1]<<8);
4277dd7cddfSDavid du Colombier free(eb);
4287dd7cddfSDavid du Colombier return c;
4297dd7cddfSDavid du Colombier }
4307dd7cddfSDavid du Colombier
4317dd7cddfSDavid du Colombier void
emoveto(Point pt)4327dd7cddfSDavid du Colombier emoveto(Point pt)
4337dd7cddfSDavid du Colombier {
4347dd7cddfSDavid du Colombier char buf[2*12+2];
4357dd7cddfSDavid du Colombier int n;
4367dd7cddfSDavid du Colombier
4377dd7cddfSDavid du Colombier n = sprint(buf, "m%d %d", pt.x, pt.y);
4387dd7cddfSDavid du Colombier write(mousefd, buf, n);
4397dd7cddfSDavid du Colombier }
4407dd7cddfSDavid du Colombier
4417dd7cddfSDavid du Colombier void
esetcursor(Cursor * c)4427dd7cddfSDavid du Colombier esetcursor(Cursor *c)
4437dd7cddfSDavid du Colombier {
4447dd7cddfSDavid du Colombier uchar curs[2*4+2*2*16];
4457dd7cddfSDavid du Colombier
4467dd7cddfSDavid du Colombier if(c == 0)
4477dd7cddfSDavid du Colombier write(cursorfd, curs, 0);
4487dd7cddfSDavid du Colombier else{
4497dd7cddfSDavid du Colombier BPLONG(curs+0*4, c->offset.x);
4507dd7cddfSDavid du Colombier BPLONG(curs+1*4, c->offset.y);
4517dd7cddfSDavid du Colombier memmove(curs+2*4, c->clr, 2*2*16);
4527dd7cddfSDavid du Colombier write(cursorfd, curs, sizeof curs);
4537dd7cddfSDavid du Colombier }
4547dd7cddfSDavid du Colombier }
4557dd7cddfSDavid du Colombier
4567dd7cddfSDavid du Colombier int
ereadmouse(Mouse * m)4577dd7cddfSDavid du Colombier ereadmouse(Mouse *m)
4587dd7cddfSDavid du Colombier {
4597dd7cddfSDavid du Colombier int n;
4607dd7cddfSDavid du Colombier char buf[128];
4617dd7cddfSDavid du Colombier
4627dd7cddfSDavid du Colombier do{
4637dd7cddfSDavid du Colombier n = read(mousefd, buf, sizeof(buf));
4647dd7cddfSDavid du Colombier if(n < 0) /* probably interrupted */
4657dd7cddfSDavid du Colombier return -1;
4667dd7cddfSDavid du Colombier n = eatomouse(m, buf, n);
4677dd7cddfSDavid du Colombier }while(n == 0);
4687dd7cddfSDavid du Colombier return n;
4697dd7cddfSDavid du Colombier }
4707dd7cddfSDavid du Colombier
4717dd7cddfSDavid du Colombier int
eatomouse(Mouse * m,char * buf,int n)4727dd7cddfSDavid du Colombier eatomouse(Mouse *m, char *buf, int n)
4737dd7cddfSDavid du Colombier {
4747dd7cddfSDavid du Colombier if(n != 1+4*12){
4757dd7cddfSDavid du Colombier werrstr("atomouse: bad count");
4767dd7cddfSDavid du Colombier return -1;
4777dd7cddfSDavid du Colombier }
4787dd7cddfSDavid du Colombier
4797dd7cddfSDavid du Colombier if(buf[0] == 'r')
4807dd7cddfSDavid du Colombier eresized(1);
4817dd7cddfSDavid du Colombier m->xy.x = atoi(buf+1+0*12);
4827dd7cddfSDavid du Colombier m->xy.y = atoi(buf+1+1*12);
4837dd7cddfSDavid du Colombier m->buttons = atoi(buf+1+2*12);
4847dd7cddfSDavid du Colombier m->msec = atoi(buf+1+3*12);
4857dd7cddfSDavid du Colombier return n;
4867dd7cddfSDavid du Colombier }
487