ref: a351bcdccdf5a4273bc8dc3360a48fbb8b8aa9ea
dir: /progs/tticker.c.ms/
.P1 .ps -1 .ti -1i .B .BX tticker.c .ps +1 .CW .ps -2 .vs .15i #include <u.h> #include <libc.h> #include <bio.h> #include <thread.h> enum { Npanels = 2 }; Channel*bcastc; // of char* Channel*panelc[Npanels]; // of char* .ps +2 .P2 .P1 .ps -2 .vs .15i typedef struct PArg PArg; struct PArg { Channel* c; // to get new messages from int fd; // to the panel's file. }; .ps +2 .P2 .P1 .ps -2 .vs .15i void consreadthread(void*) { Biobuf bin; char* ln; threadsetname("consread"); Binit(&bin, 0, OREAD); while (ln = Brdstr(&bin, '\en', 0)) sendp(bcastc, ln); sendp(bcastc, nil); Bterm(&bin); threadexits(nil); } .ps +2 .P2 .P1 .ps -2 .vs .15i void bcastthread(void*) { char* msg; int i; threadsetname("bcast"); do { msg = recvp(bcastc); for (i = 0; i < Npanels; i++) if (msg != nil) sendp(panelc[i], strdup(msg)); else sendp(panelc[i], nil); free(msg); } while(msg != nil); threadexits(nil); } .ps +2 .P2 .P1 .ps -2 .vs .15i void panelthread(void* a) { PArg* arg = a; char* msg; threadsetname("panel"); while(msg = recvp(arg->c)){ write(arg->fd, msg, strlen(msg)); free(msg); } threadexits(nil); } .ps +2 .P2 .P1 .ps -2 .vs .15i void threadmain(int, char*[]) { int i; PArg* arg; bcastc = chancreate(sizeof(char*), 0); proccreate(consreadthread, nil, 16*1024); for (i = 0; i < Npanels; i++){ panelc[i] = chancreate(sizeof(char*), 0); arg = malloc(sizeof(*arg)); arg->c = panelc[i]; arg->fd = 1; // to test the program. proccreate(panelthread, arg, 8*1024); } // The current thread used for bcast. bcastthread(nil); } .ps +2 .P2