/* * process to notify other servers of changes * (also reads in new databases) */ void notifyproc(void) { Request req; switch(rfork(RFPROC|RFNOTEG|RFMEM|RFNOWAIT)){ case -1: return; case 0: break; default: return; } procsetname("notify slaves"); memset(&req, 0, sizeof req); req.isslave = 1; /* don't fork off subprocesses */ for(;;){ getactivity(&req, 0); notify_areas(owned, &req); putactivity(0); sleep(60*1000); } }
void main(int argc, char *argv[]) { int len, rcode; char tname[32]; char *err, *ext = ""; unsigned char buf[64*1024], callip[IPaddrlen]; DNSmsg reqmsg, repmsg; Request req; alarm(2*60*1000); cfg.cachedb = 1; ARGBEGIN{ case 'd': debug++; break; case 'f': dbfile = EARGF(usage()); break; case 'r': cfg.resolver = 1; break; case 'R': norecursion = 1; break; case 'x': ext = EARGF(usage()); break; default: usage(); break; }ARGEND if(debug < 2) debug = 0; if(argc > 0) getcaller(argv[0]); cfg.inside = 1; dninit(); snprint(mntpt, sizeof mntpt, "/net%s", ext); if(myipaddr(ipaddr, mntpt) < 0) sysfatal("can't read my ip address"); dnslog("dnstcp call from %s to %I", caller, ipaddr); memset(callip, 0, sizeof callip); parseip(callip, caller); db2cache(1); memset(&req, 0, sizeof req); setjmp(req.mret); req.isslave = 0; procsetname("main loop"); /* loop on requests */ for(;; putactivity(0)){ now = time(nil); memset(&repmsg, 0, sizeof repmsg); len = readmsg(0, buf, sizeof buf); if(len <= 0) break; getactivity(&req, 0); req.aborttime = timems() + S2MS(15*Min); rcode = 0; memset(&reqmsg, 0, sizeof reqmsg); err = convM2DNS(buf, len, &reqmsg, &rcode); if(err){ dnslog("server: input error: %s from %s", err, caller); free(err); break; } if (rcode == 0) { if(reqmsg.qdcount < 1){ dnslog("server: no questions from %s", caller); break; } else if(reqmsg.flags & Fresp){ dnslog("server: reply not request from %s", caller); break; } else if((reqmsg.flags & Omask) != Oquery){ dnslog("server: op %d from %s", reqmsg.flags & Omask, caller); break; } } if(debug) dnslog("[%d] %d: serve (%s) %d %s %s", getpid(), req.id, caller, reqmsg.id, reqmsg.qd->owner->name, rrname(reqmsg.qd->type, tname, sizeof tname)); /* loop through each question */ while(reqmsg.qd) if(reqmsg.qd->type == Taxfr) dnzone(&reqmsg, &repmsg, &req); else { dnserver(&reqmsg, &repmsg, &req, callip, rcode); reply(1, &repmsg, &req); rrfreelist(repmsg.qd); rrfreelist(repmsg.an); rrfreelist(repmsg.ns); rrfreelist(repmsg.ar); } rrfreelist(reqmsg.qd); /* qd will be nil */ rrfreelist(reqmsg.an); rrfreelist(reqmsg.ns); rrfreelist(reqmsg.ar); if(req.isslave){ putactivity(0); _exits(0); } } refreshmain(mntpt); }
/* * a process to act as a dns server for outside reqeusts */ void dnudpserver(char *mntpt) { volatile int fd, len, op, rcode; char *volatile err; volatile char tname[32]; volatile uchar buf[Udphdrsize + Maxudp + 1024]; volatile DNSmsg reqmsg, repmsg; Inprogress *volatile p; volatile Request req; Udphdr *volatile uh; /* * fork sharing text, data, and bss with parent. * stay in the same note group. */ switch(rfork(RFPROC|RFMEM|RFNOWAIT)){ case -1: break; case 0: break; default: return; } fd = -1; restart: procsetname("udp server announcing"); if(fd >= 0) close(fd); while((fd = udpannounce(mntpt)) < 0) sleep(5000); // procsetname("udp server"); memset(&req, 0, sizeof req); if(setjmp(req.mret)) putactivity(0); req.isslave = 0; req.id = 0; req.aborttime = 0; /* loop on requests */ for(;; putactivity(0)){ procsetname("served %d udp; %d alarms", stats.qrecvdudp, stats.alarms); memset(&repmsg, 0, sizeof repmsg); memset(&reqmsg, 0, sizeof reqmsg); alarm(60*1000); len = read(fd, buf, sizeof buf); alarm(0); if(len <= Udphdrsize) goto restart; redistrib(buf, len); uh = (Udphdr*)buf; len -= Udphdrsize; // dnslog("read received UDP from %I to %I", // ((Udphdr*)buf)->raddr, ((Udphdr*)buf)->laddr); getactivity(&req, 0); req.aborttime = timems() + Maxreqtm; // req.from = smprint("%I", ((Udphdr*)buf)->raddr); req.from = smprint("%I", buf); rcode = 0; stats.qrecvdudp++; err = convM2DNS(&buf[Udphdrsize], len, &reqmsg, &rcode); if(err){ /* first bytes in buf are source IP addr */ dnslog("server: input error: %s from %I", err, buf); free(err); goto freereq; } if (rcode == 0) if(reqmsg.qdcount < 1){ dnslog("server: no questions from %I", buf); goto freereq; } else if(reqmsg.flags & Fresp){ dnslog("server: reply not request from %I", buf); goto freereq; } op = reqmsg.flags & Omask; if(op != Oquery && op != Onotify){ dnslog("server: op %d from %I", reqmsg.flags & Omask, buf); goto freereq; } if(debug || (trace && subsume(trace, reqmsg.qd->owner->name))) dnslog("%d: serve (%I/%d) %d %s %s", req.id, buf, uh->rport[0]<<8 | uh->rport[1], reqmsg.id, reqmsg.qd->owner->name, rrname(reqmsg.qd->type, tname, sizeof tname)); p = clientrxmit(&reqmsg, buf); if(p == nil){ if(debug) dnslog("%d: duplicate", req.id); goto freereq; } if (Logqueries) { RR *rr; for (rr = reqmsg.qd; rr; rr = rr->next) syslog(0, "dnsq", "id %d: (%I/%d) %d %s %s", req.id, buf, uh->rport[0]<<8 | uh->rport[1], reqmsg.id, reqmsg.qd->owner->name, rrname(reqmsg.qd->type, tname, sizeof tname)); } /* loop through each question */ while(reqmsg.qd){ memset(&repmsg, 0, sizeof repmsg); switch(op){ case Oquery: dnserver(&reqmsg, &repmsg, &req, buf, rcode); break; case Onotify: dnnotify(&reqmsg, &repmsg, &req); break; } /* send reply on fd to address in buf's udp hdr */ reply(fd, buf, &repmsg, &req); freeanswers(&repmsg); } p->inuse = 0; freereq: free(req.from); req.from = nil; freeanswers(&reqmsg); if(req.isslave){ putactivity(0); _exits(0); } } }
void activatebulk(void) { vector<Creature *> temppool = activatable_liberals(); if(temppool.size()==0)return; int page=0; char str[80]; int selectedactivity=0; do { erase(); set_color(COLOR_WHITE,COLOR_BLACK,0); printfunds(0,1,"Money: "); set_color(COLOR_WHITE,COLOR_BLACK,0); move(0,0); addstr("Activate Uninvolved Liberals"); move(1,0); addstr("----CODE NAME------------CURRENT ACTIVITY---------------------------------------"); move(1,51); addstr("BULK ACTIVITY"); if(selectedactivity==0)set_color(COLOR_WHITE,COLOR_BLACK,1); else set_color(COLOR_WHITE,COLOR_BLACK,0); move(2,51); addstr("1 - Engaging in Liberal Activism"); if(selectedactivity==1)set_color(COLOR_WHITE,COLOR_BLACK,1); else set_color(COLOR_WHITE,COLOR_BLACK,0); move(3,51); addstr("2 - Legal Fundraising"); if(selectedactivity==2)set_color(COLOR_WHITE,COLOR_BLACK,1); else set_color(COLOR_WHITE,COLOR_BLACK,0); move(4,51); addstr("3 - Illegal Fundraising"); if(selectedactivity==3)set_color(COLOR_WHITE,COLOR_BLACK,1); else set_color(COLOR_WHITE,COLOR_BLACK,0); move(5,51); addstr("4 - Checking Polls"); if(selectedactivity==4)set_color(COLOR_WHITE,COLOR_BLACK,1); else set_color(COLOR_WHITE,COLOR_BLACK,0); move(6,51); addstr("5 - Stealing Cars"); if(selectedactivity==5)set_color(COLOR_WHITE,COLOR_BLACK,1); else set_color(COLOR_WHITE,COLOR_BLACK,0); move(7,51); addstr("6 - Community Service"); int y=2; for(int p=page*19;p<temppool.size()&&p<page*19+19;p++) { set_color(COLOR_WHITE,COLOR_BLACK,0); move(y,0); addch(y+'A'-2);addstr(" - "); addstr(temppool[p]->name); move(y,25); set_activity_color(temppool[p]->activity.type); getactivity(str,temppool[p]->activity); addstr(str); /*if(temppool[p]->activity.type==ACTIVITY_TROUBLE) { addstr(" ($"); itoa(temppool[p]->activity.arg,num,10); addstr(num); addstr(")"); }*/ y++; } set_color(COLOR_WHITE,COLOR_BLACK,0); move(22,0); addstr("Press a Letter to Assign an Activity. Press a Number to select an Activity."); move(23,0); addpagestr(); refresh(); int c=getch(); translategetch(c); //PAGE UP if((c==interface_pgup||c==KEY_UP||c==KEY_LEFT)&&page>0)page--; //PAGE DOWN if((c==interface_pgdn||c==KEY_DOWN||c==KEY_RIGHT)&&(page+1)*19<temppool.size())page++; if(c>='a'&&c<='s') { int p=page*19+(int)(c-'a'); if(p<temppool.size()) { switch(selectedactivity) { case 0: //Activism if(temppool[p]->get_attribute(ATTRIBUTE_WISDOM,true)>7) temppool[p]->activity.type=ACTIVITY_COMMUNITYSERVICE; else if(temppool[p]->get_attribute(ATTRIBUTE_WISDOM,true)>4) temppool[p]->activity.type=ACTIVITY_TROUBLE; else { if(temppool[p]->get_skill(SKILL_COMPUTERS)>2) temppool[p]->activity.type=ACTIVITY_HACKING; else if(temppool[p]->get_skill(SKILL_ART)>1) { temppool[p]->activity.type=ACTIVITY_GRAFFITI; temppool[p]->activity.arg=-1; } else temppool[p]->activity.type=ACTIVITY_TROUBLE; } break; case 1: //Fundraising if(temppool[p]->get_skill(SKILL_ART)>1) temppool[p]->activity.type=ACTIVITY_SELL_ART; else if(temppool[p]->get_skill(SKILL_MUSIC)>1) temppool[p]->activity.type=ACTIVITY_SELL_MUSIC; else if(temppool[p]->get_skill(SKILL_TAILORING)>1) temppool[p]->activity.type=ACTIVITY_SELL_TSHIRTS; else temppool[p]->activity.type=ACTIVITY_DONATIONS; break; case 2: //Illegal Fundraising if(temppool[p]->get_skill(SKILL_COMPUTERS)>1) temppool[p]->activity.type=ACTIVITY_CCFRAUD; #ifndef ZEROMORAL else if(temppool[p]->get_skill(SKILL_SEDUCTION)>1 && temppool[p]->age >=18) #else else if(temppool[p]->get_skill(SKILL_SEDUCTION)>1) #endif temppool[p]->activity.type=ACTIVITY_PROSTITUTION; else temppool[p]->activity.type=ACTIVITY_SELL_DRUGS; break; case 3: //Check polls temppool[p]->activity.type=ACTIVITY_POLLS; break; case 4: //Steal cars temppool[p]->activity.type=ACTIVITY_STEALCARS; break; case 5: //Volunteer temppool[p]->activity.type=ACTIVITY_COMMUNITYSERVICE; break; } } } if(c>='1'&&c<='6') { selectedactivity=c-'1'; } if(c==10||c==ESC)break; }while(1);
/* base - activate the uninvolved */ void activate(void) { vector<Creature *> temppool = activatable_liberals(); if(temppool.size()==0)return; sortliberals(temppool,activesortingchoice[SORTINGCHOICE_ACTIVATE]); int page=0; char str[80]; char num[20]; do { erase(); set_color(COLOR_WHITE,COLOR_BLACK,0); printfunds(0,1,"Money: "); move(0,0); addstr("Activate Uninvolved Liberals"); move(1,0); addstr("----CODE NAME------------SKILL---HEALTH---LOCATION------------------------------"); move(1,57); addstr("ACTIVITY"); int y=2; for(int p=page*19;p<temppool.size()&&p<page*19+19;p++) { set_color(COLOR_WHITE,COLOR_BLACK,0); move(y,0); addch(y+'A'-2);addstr(" - "); addstr(temppool[p]->name); char bright=0; int skill=0; for(int sk=0;sk<SKILLNUM;sk++) { skill+=temppool[p]->get_skill(sk); if(temppool[p]->get_skill_ip(sk)>=100+(10*temppool[p]->get_skill(sk))&& temppool[p]->get_skill(sk)<temppool[p]->skill_cap(sk,true))bright=1; } set_color(COLOR_WHITE,COLOR_BLACK,bright); move(y,25); itoa(skill,num,10); addstr(num); printhealthstat(*temppool[p],y,33,TRUE); if(mode==REVIEWMODE_JUSTICE)set_color(COLOR_YELLOW,COLOR_BLACK,1); else set_color(COLOR_WHITE,COLOR_BLACK,0); move(y,42); addstr(location[temppool[p]->location]->getname(true)); move(y,57); // Let's add some color here... set_activity_color(temppool[p]->activity.type); getactivity(str,temppool[p]->activity); addstr(str); y++; } set_color(COLOR_WHITE,COLOR_BLACK,0); move(22,0); addstr("Press a Letter to Assign an Activity."); move(23,0); addpagestr(); addstr(" T to sort people."); move(24,0); addstr("Press Z to assign simple tasks in bulk."); refresh(); int c=getch(); translategetch(c); //PAGE UP if((c==interface_pgup||c==KEY_UP||c==KEY_LEFT)&&page>0)page--; //PAGE DOWN if((c==interface_pgdn||c==KEY_DOWN||c==KEY_RIGHT)&&(page+1)*19<temppool.size())page++; if(c>='a'&&c<='s') { int p=page*19+(int)(c-'a'); if(p<temppool.size()) { activate(temppool[p]); } } if(c=='t') { sorting_prompt(SORTINGCHOICE_ACTIVATE); sortliberals(temppool,activesortingchoice[SORTINGCHOICE_ACTIVATE],true); } if(c=='z') { activatebulk(); } if(c==10||c==ESC)break; }while(1); }
/* location and squad header */ void locheader(void) { char num[20]; if(activesquad!=NULL && activesquad->squad[0]->location!=-1) { if(location[activesquad->squad[0]->location]->siege.siege) { if(location[activesquad->squad[0]->location]->siege.underattack)set_color(COLOR_RED,COLOR_BLACK,1); else set_color(COLOR_YELLOW,COLOR_BLACK,1); } else set_color(COLOR_WHITE,COLOR_BLACK,0); } else if(selectedsiege!=-1) { if(location[selectedsiege]->siege.siege) { if(location[selectedsiege]->siege.underattack)set_color(COLOR_RED,COLOR_BLACK,1); else set_color(COLOR_YELLOW,COLOR_BLACK,1); } else set_color(COLOR_WHITE,COLOR_BLACK,0); } else set_color(COLOR_WHITE,COLOR_BLACK,0); move(0,0); if(activesquad!=NULL && activesquad->squad[0]->location!=-1) { addstr(location[activesquad->squad[0]->location]->getname()); addstr(", "); } else { if(selectedsiege==-1) { addstr("No Squad Selected"); addstr(", "); } else { addstr(location[selectedsiege]->getname()); addstr(", "); } } switch(month) { case 1:addstr("Jan");break; case 2:addstr("Feb");break; case 3:addstr("Mar");break; case 4:addstr("Apr");break; case 5:addstr("May");break; case 6:addstr("Jun");break; case 7:addstr("Jul");break; case 8:addstr("Aug");break; case 9:addstr("Sep");break; case 10:addstr("Oct");break; case 11:addstr("Nov");break; case 12:addstr("Dec");break; } addstr(". "); itoa(day,num,10); addstr(num); addstr(", "); itoa(year,num,10); addstr(num); if(activesquad==NULL && selectedsiege==-1) { set_color(COLOR_BLACK,COLOR_BLACK,1); move(3,6); addstr("To form a new squad:"); move(4,6); addstr("1) R - Review Assets and Form Squads"); move(5,6); addstr("2) Press Z to Assemble a New Squad"); set_color(COLOR_WHITE,COLOR_BLACK,0); } printfunds(0,1,"Money: "); if(activesquad!=NULL) { set_color(COLOR_WHITE,COLOR_BLACK,1); char str[80]; getactivity(str,activesquad->activity); if(activesquad->activity.type==ACTIVITY_NONE) { int count=0;char haveact=0; for(int p=0;p<6;p++) { if(activesquad->squad[p]==NULL)continue; count++; if(activesquad->squad[p]->activity.type!=ACTIVITY_NONE) { getactivity(str,activesquad->squad[p]->activity); haveact=1; } } if(haveact&&count>1)strcpy(str,"Acting Individually"); } move(0,41); addstr(str); } }
/* base - activate sleepers */ void activate_sleepers(void) { vector<Creature *> temppool; // Comb the pool of Liberals for sleeper agents for(int p=0; p<pool.size(); p++) { // Select only sleepers that can work if(pool[p]->alive==true&& pool[p]->flag & CREATUREFLAG_SLEEPER&& pool[p]->align==ALIGN_LIBERAL&& pool[p]->hiding==false&& pool[p]->clinic==false&& pool[p]->dating==false) { temppool.push_back(pool[p]); } } if(temppool.size()==0)return; sortliberals(temppool,activesortingchoice[SORTINGCHOICE_ACTIVATESLEEPERS]); int page=0; char str[80]; do { erase(); set_color(COLOR_WHITE,COLOR_BLACK,0); printfunds(0,1,"Money: "); move(0,0); addstr("Activate Sleeper Agents"); makedelimiter(1,0); move(1,4); addstr("CODE NAME"); move(1,25); addstr("JOB"); move(1,42); addstr("SITE"); move(1,57); addstr("ACTIVITY"); int y=2; for(int p=page*9; p<temppool.size()&&p<page*9+9; p++) { set_color(COLOR_WHITE,COLOR_BLACK,0); move(y,0); addch((y-2)/2+'A'); addstr(" - "); addstr(temppool[p]->name); move(y,25); getrecruitcreature(str,temppool[p]->type); addstr(str); move(y+1,6); addstr("Effectiveness: "); if(temppool[p]->infiltration > 0.8f) { set_color(COLOR_RED,COLOR_BLACK,1); } else if(temppool[p]->infiltration > 0.6f) { set_color(COLOR_MAGENTA,COLOR_BLACK,1); } else if(temppool[p]->infiltration > 0.4f) { set_color(COLOR_YELLOW,COLOR_BLACK,1); } else if(temppool[p]->infiltration > 0.2f) { set_color(COLOR_WHITE,COLOR_BLACK,1); } else if(temppool[p]->infiltration > 0.1f) { set_color(COLOR_WHITE,COLOR_BLACK,0); } else { set_color(COLOR_GREEN,COLOR_BLACK,0); } char num[10]; itoa(static_cast<int>(temppool[p]->infiltration*100),num,10); addstr(num); addstr("%"); move(y,42); set_color(COLOR_WHITE,COLOR_BLACK,0); addshortname(location[temppool[p]->worklocation]); move(y,57); // Let's add some color here... set_activity_color(temppool[p]->activity.type); getactivity(str,temppool[p]->activity); addstr(str); y+=2; } set_color(COLOR_WHITE,COLOR_BLACK,0); move(22,0); addstr("Press a Letter to Assign an Activity."); move(23,0); addpagestr(); addstr(" T to sort people."); set_color(COLOR_WHITE,COLOR_BLACK,0); refresh(); int c=getch(); translategetch(c); //PAGE UP if((c==interface_pgup||c==KEY_UP||c==KEY_LEFT)&&page>0)page--; //PAGE DOWN if((c==interface_pgdn||c==KEY_DOWN||c==KEY_RIGHT)&&(page+1)*9<temppool.size())page++; if(c>='a'&&c<='s') { int p=page*9+(int)(c-'a'); if(p<temppool.size()) { activate_sleeper(temppool[p]); } } if(c=='t') { sorting_prompt(SORTINGCHOICE_ACTIVATESLEEPERS); sortliberals(temppool,activesortingchoice[SORTINGCHOICE_ACTIVATESLEEPERS],true); } if(c==10)break; } while(1); }
void io(void) { volatile long n; volatile uchar mdata[IOHDRSZ + Maxfdata]; Job *volatile job; Mfile *volatile mf; volatile Request req; memset(&req, 0, sizeof req); /* * a slave process is sometimes forked to wait for replies from other * servers. The master process returns immediately via a longjmp * through 'mret'. */ if(setjmp(req.mret)) putactivity(0); req.isslave = 0; stop = 0; while(!stop){ procsetname("%d %s/dns Twrites of %d 9p rpcs read; %d alarms", stats.qrecvd9p, mntpt, stats.qrecvd9prpc, stats.alarms); n = read9pmsg(mfd[0], mdata, sizeof mdata); if(n<=0){ dnslog("error reading 9P from %s: %r", mntpt); sleep(2000); /* don't thrash after read error */ return; } stats.qrecvd9prpc++; job = newjob(); if(convM2S(mdata, n, &job->request) != n){ freejob(job); continue; } mf = newfid(job->request.fid, 0); if(debug) dnslog("%F", &job->request); getactivity(&req, 0); req.aborttime = timems() + Maxreqtm; req.from = "9p"; switch(job->request.type){ default: warning("unknown request type %d", job->request.type); break; case Tversion: rversion(job); break; case Tauth: rauth(job); break; case Tflush: rflush(job); break; case Tattach: rattach(job, mf); break; case Twalk: rwalk(job, mf); break; case Topen: ropen(job, mf); break; case Tcreate: rcreate(job, mf); break; case Tread: rread(job, mf); break; case Twrite: /* &req is handed to dnresolve() */ rwrite(job, mf, &req); break; case Tclunk: rclunk(job, mf); break; case Tremove: rremove(job, mf); break; case Tstat: rstat(job, mf); break; case Twstat: rwstat(job, mf); break; } freejob(job); /* * slave processes die after replying */ if(req.isslave){ putactivity(0); _exits(0); } putactivity(0); } /* kill any udp server, notifier, etc. processes */ postnote(PNGROUP, getpid(), "die"); sleep(1000); }
void ioproc0(void *v) { long n; Mfile *mf; uchar mdata[IOHDRSZ + Maxfdata]; Request req; Job *job; USED(v); for(;;){ n = read9pmsg(mfd[0], mdata, sizeof mdata); if(n <= 0){ syslog(0, logfile, "error reading mntpt: %r"); break; } job = newjob(); if(convM2S(mdata, n, &job->request) != n){ freejob(job); continue; } if(debug) syslog(0, logfile, "%F", &job->request); getactivity(&req); req.aborttime = now + 60; /* don't spend more than 60 seconds */ mf = nil; switch(job->request.type){ case Tversion: case Tauth: case Tflush: break; case Tattach: mf = newfid(job->request.fid, 1); if(mf == nil){ sendmsg(job, "fid in use"); goto skip; } break; default: mf = newfid(job->request.fid, 0); if(mf == nil){ sendmsg(job, "unknown fid"); goto skip; } break; } switch(job->request.type){ default: syslog(1, logfile, "unknown request type %d", job->request.type); break; case Tversion: rversion(job); break; case Tauth: rauth(job); break; case Tflush: rflush(job); break; case Tattach: rattach(job, mf); break; case Twalk: rwalk(job, mf); break; case Topen: ropen(job, mf); break; case Tcreate: rcreate(job, mf); break; case Tread: rread(job, mf); break; case Twrite: rwrite(job, mf, &req); break; case Tclunk: rclunk(job, mf); break; case Tremove: rremove(job, mf); break; case Tstat: rstat(job, mf); break; case Twstat: rwstat(job, mf); break; } skip: freejob(job); putactivity(); } }