137da2899SCharles.Forsyth /* Link with -lfpe. See man pages for fpc
237da2899SCharles.Forsyth * and /usr/include/sigfpe.h, sys/fpu.h.
337da2899SCharles.Forsyth */
437da2899SCharles.Forsyth #include "dat.h"
537da2899SCharles.Forsyth #include "fns.h"
637da2899SCharles.Forsyth #include "error.h"
737da2899SCharles.Forsyth #include <time.h>
837da2899SCharles.Forsyth #include <ulocks.h>
937da2899SCharles.Forsyth #include <termios.h>
1037da2899SCharles.Forsyth #include <sigfpe.h>
1137da2899SCharles.Forsyth #include <sys/prctl.h>
1237da2899SCharles.Forsyth #include <sys/fpu.h>
1337da2899SCharles.Forsyth #include <sys/cachectl.h>
1437da2899SCharles.Forsyth #undef _POSIX_SOURCE /* SGI incompetence */
1537da2899SCharles.Forsyth #include <signal.h>
1637da2899SCharles.Forsyth #define _BSD_TIME
1737da2899SCharles.Forsyth /* for gettimeofday(), which isn't POSIX,
1837da2899SCharles.Forsyth * but is fairly common
1937da2899SCharles.Forsyth */
2037da2899SCharles.Forsyth #include <sys/time.h>
2137da2899SCharles.Forsyth #define _POSIX_SOURCE
2237da2899SCharles.Forsyth #include <pwd.h>
2337da2899SCharles.Forsyth
2437da2899SCharles.Forsyth extern int rebootargc;
2537da2899SCharles.Forsyth extern char** rebootargv;
2637da2899SCharles.Forsyth
2737da2899SCharles.Forsyth int gidnobody = -1;
2837da2899SCharles.Forsyth int uidnobody = -1;
2937da2899SCharles.Forsyth Proc** Xup;
3037da2899SCharles.Forsyth
3137da2899SCharles.Forsyth #define MAXSPROC 30000 /* max procs == MAXPID */
3237da2899SCharles.Forsyth static int sproctbl[MAXSPROC];
3337da2899SCharles.Forsyth
3437da2899SCharles.Forsyth enum
3537da2899SCharles.Forsyth {
3637da2899SCharles.Forsyth KSTACK = 64*1024,
3737da2899SCharles.Forsyth DELETE = 0x7F
3837da2899SCharles.Forsyth };
3937da2899SCharles.Forsyth char *hosttype = "Irix";
4037da2899SCharles.Forsyth char *cputype = "mips";
4137da2899SCharles.Forsyth
4237da2899SCharles.Forsyth extern int dflag;
4337da2899SCharles.Forsyth
4437da2899SCharles.Forsyth void
pexit(char * msg,int t)4537da2899SCharles.Forsyth pexit(char *msg, int t)
4637da2899SCharles.Forsyth {
4737da2899SCharles.Forsyth Osenv *e;
4837da2899SCharles.Forsyth
4937da2899SCharles.Forsyth lock(&procs.l);
5037da2899SCharles.Forsyth if(up->prev)
5137da2899SCharles.Forsyth up->prev->next = up->next;
5237da2899SCharles.Forsyth else
5337da2899SCharles.Forsyth procs.head = up->next;
5437da2899SCharles.Forsyth
5537da2899SCharles.Forsyth if(up->next)
5637da2899SCharles.Forsyth up->next->prev = up->prev;
5737da2899SCharles.Forsyth else
5837da2899SCharles.Forsyth procs.tail = up->prev;
5937da2899SCharles.Forsyth
6037da2899SCharles.Forsyth sproctbl[getpid()] = -1;
6137da2899SCharles.Forsyth
6237da2899SCharles.Forsyth unlock(&procs.l);
6337da2899SCharles.Forsyth
6437da2899SCharles.Forsyth /* print("pexit: %s: %s\n", up->text, msg); /**/
6537da2899SCharles.Forsyth e = up->env;
6637da2899SCharles.Forsyth if(e != nil) {
6737da2899SCharles.Forsyth closefgrp(e->fgrp);
6837da2899SCharles.Forsyth closepgrp(e->pgrp);
6937da2899SCharles.Forsyth closeegrp(e->egrp);
7037da2899SCharles.Forsyth closesigs(e->sigs);
7137da2899SCharles.Forsyth }
7237da2899SCharles.Forsyth free(up->prog);
7337da2899SCharles.Forsyth free(up);
7437da2899SCharles.Forsyth exit(0);
7537da2899SCharles.Forsyth }
7637da2899SCharles.Forsyth
7737da2899SCharles.Forsyth static void
tramp(void * p,size_t stacksz)7837da2899SCharles.Forsyth tramp(void *p, size_t stacksz)
7937da2899SCharles.Forsyth {
8037da2899SCharles.Forsyth up = p;
8137da2899SCharles.Forsyth up->sigid = getpid();
8237da2899SCharles.Forsyth up->func(up->arg);
8337da2899SCharles.Forsyth pexit("", 0);
8437da2899SCharles.Forsyth }
8537da2899SCharles.Forsyth
86*1343b7e5Sforsyth void
kproc(char * name,void (* func)(void *),void * arg,int flags)8737da2899SCharles.Forsyth kproc(char *name, void (*func)(void*), void *arg, int flags)
8837da2899SCharles.Forsyth {
8937da2899SCharles.Forsyth Proc *p;
9037da2899SCharles.Forsyth Pgrp *pg;
9137da2899SCharles.Forsyth Fgrp *fg;
9237da2899SCharles.Forsyth Egrp *eg;
9337da2899SCharles.Forsyth int pid;
9437da2899SCharles.Forsyth int id;
9537da2899SCharles.Forsyth int i;
9637da2899SCharles.Forsyth
9737da2899SCharles.Forsyth p = newproc();
9837da2899SCharles.Forsyth
9937da2899SCharles.Forsyth if(flags & KPDUPPG) {
10037da2899SCharles.Forsyth pg = up->env->pgrp;
10137da2899SCharles.Forsyth incref(&pg->r);
10237da2899SCharles.Forsyth p->env->pgrp = pg;
10337da2899SCharles.Forsyth }
10437da2899SCharles.Forsyth if(flags & KPDUPFDG) {
10537da2899SCharles.Forsyth fg = up->env->fgrp;
10637da2899SCharles.Forsyth incref(&fg->r);
10737da2899SCharles.Forsyth p->env->fgrp = fg;
10837da2899SCharles.Forsyth }
10937da2899SCharles.Forsyth if(flags & KPDUPENVG) {
11037da2899SCharles.Forsyth eg = up->env->egrp;
11137da2899SCharles.Forsyth incref(&eg->r);
11237da2899SCharles.Forsyth p->env->egrp = eg;
11337da2899SCharles.Forsyth }
11437da2899SCharles.Forsyth
11537da2899SCharles.Forsyth p->env->uid = up->env->uid;
11637da2899SCharles.Forsyth p->env->gid = up->env->gid;
11737da2899SCharles.Forsyth kstrdup(&p->env->user, up->env->user);
11837da2899SCharles.Forsyth
11937da2899SCharles.Forsyth strcpy(p->text, name);
12037da2899SCharles.Forsyth
12137da2899SCharles.Forsyth p->func = func;
12237da2899SCharles.Forsyth p->arg = arg;
12337da2899SCharles.Forsyth
12437da2899SCharles.Forsyth lock(&procs.l);
12537da2899SCharles.Forsyth if(procs.tail != nil) {
12637da2899SCharles.Forsyth p->prev = procs.tail;
12737da2899SCharles.Forsyth procs.tail->next = p;
12837da2899SCharles.Forsyth }
12937da2899SCharles.Forsyth else {
13037da2899SCharles.Forsyth procs.head = p;
13137da2899SCharles.Forsyth p->prev = nil;
13237da2899SCharles.Forsyth }
13337da2899SCharles.Forsyth procs.tail = p;
13437da2899SCharles.Forsyth
13537da2899SCharles.Forsyth for(i = 1; i < MAXSPROC; i++) {
13637da2899SCharles.Forsyth if(sproctbl[i] == -1) {
13737da2899SCharles.Forsyth break;
13837da2899SCharles.Forsyth }
13937da2899SCharles.Forsyth }
14037da2899SCharles.Forsyth
14137da2899SCharles.Forsyth if(i==MAXSPROC)
14237da2899SCharles.Forsyth return -1;
14337da2899SCharles.Forsyth
14437da2899SCharles.Forsyth sproctbl[i] = -i - 1; /* temporary hold of table index outside of lock */
14537da2899SCharles.Forsyth
14637da2899SCharles.Forsyth unlock(&procs.l);
14737da2899SCharles.Forsyth
14837da2899SCharles.Forsyth pid = sprocsp(tramp, PR_SALL, p, 0, KSTACK);
14937da2899SCharles.Forsyth
150*1343b7e5Sforsyth if(pid >= 0)
15137da2899SCharles.Forsyth sproctbl[i] = pid;
15237da2899SCharles.Forsyth else
15337da2899SCharles.Forsyth sproctbl[i] = -1;
15437da2899SCharles.Forsyth }
15537da2899SCharles.Forsyth
15637da2899SCharles.Forsyth void
osblock(void)15737da2899SCharles.Forsyth osblock(void)
15837da2899SCharles.Forsyth {
15937da2899SCharles.Forsyth blockproc(up->sigid);
16037da2899SCharles.Forsyth }
16137da2899SCharles.Forsyth
16237da2899SCharles.Forsyth void
osready(Proc * p)16337da2899SCharles.Forsyth osready(Proc *p)
16437da2899SCharles.Forsyth {
16537da2899SCharles.Forsyth unblockproc(p->sigid);
16637da2899SCharles.Forsyth }
16737da2899SCharles.Forsyth
16837da2899SCharles.Forsyth void
trapUSR1(void)16937da2899SCharles.Forsyth trapUSR1(void)
17037da2899SCharles.Forsyth {
17137da2899SCharles.Forsyth int intwait;
17237da2899SCharles.Forsyth
17337da2899SCharles.Forsyth intwait = up->intwait;
17437da2899SCharles.Forsyth up->intwait = 0; /* clear it to let proc continue in osleave */
17537da2899SCharles.Forsyth
17637da2899SCharles.Forsyth if(up->type != Interp) /* Used to unblock pending I/O */
17737da2899SCharles.Forsyth return;
17837da2899SCharles.Forsyth
17937da2899SCharles.Forsyth if(intwait == 0) /* Not posted so it's a sync error */
18037da2899SCharles.Forsyth disfault(nil, Eintr); /* Should never happen */
18137da2899SCharles.Forsyth }
18237da2899SCharles.Forsyth
18337da2899SCharles.Forsyth void
trapILL(void)18437da2899SCharles.Forsyth trapILL(void)
18537da2899SCharles.Forsyth {
18637da2899SCharles.Forsyth disfault(nil, "Illegal instruction");
18737da2899SCharles.Forsyth }
18837da2899SCharles.Forsyth
18937da2899SCharles.Forsyth void
trapBUS(void)19037da2899SCharles.Forsyth trapBUS(void)
19137da2899SCharles.Forsyth {
19237da2899SCharles.Forsyth disfault(nil, "Bus error");
19337da2899SCharles.Forsyth }
19437da2899SCharles.Forsyth
19537da2899SCharles.Forsyth void
trapSEGV(void)19637da2899SCharles.Forsyth trapSEGV(void)
19737da2899SCharles.Forsyth {
19837da2899SCharles.Forsyth disfault(nil, "Segmentation violation");
19937da2899SCharles.Forsyth }
20037da2899SCharles.Forsyth
20137da2899SCharles.Forsyth /*
20237da2899SCharles.Forsyth * This is not a signal handler but rather a vector from real/FPcontrol-Irix.c
20337da2899SCharles.Forsyth */
20437da2899SCharles.Forsyth void
trapFPE(unsigned exception[5],int value[2])20537da2899SCharles.Forsyth trapFPE(unsigned exception[5], int value[2])
20637da2899SCharles.Forsyth {
20737da2899SCharles.Forsyth disfault(nil, "Floating point exception");
20837da2899SCharles.Forsyth }
20937da2899SCharles.Forsyth
21037da2899SCharles.Forsyth void
oshostintr(Proc * p)21137da2899SCharles.Forsyth oshostintr(Proc *p)
21237da2899SCharles.Forsyth {
21337da2899SCharles.Forsyth kill(p->sigid, SIGUSR1);
21437da2899SCharles.Forsyth }
21537da2899SCharles.Forsyth
21637da2899SCharles.Forsyth void
oslongjmp(void * regs,osjmpbuf env,int val)21737da2899SCharles.Forsyth oslongjmp(void *regs, osjmpbuf env, int val)
21837da2899SCharles.Forsyth {
21937da2899SCharles.Forsyth USED(regs);
22037da2899SCharles.Forsyth siglongjmp(env, val);
22137da2899SCharles.Forsyth }
22237da2899SCharles.Forsyth
22337da2899SCharles.Forsyth static struct termios tinit;
22437da2899SCharles.Forsyth
22537da2899SCharles.Forsyth static void
termset(void)22637da2899SCharles.Forsyth termset(void)
22737da2899SCharles.Forsyth {
22837da2899SCharles.Forsyth struct termios t;
22937da2899SCharles.Forsyth
23037da2899SCharles.Forsyth tcgetattr(0, &t);
23137da2899SCharles.Forsyth tinit = t;
23237da2899SCharles.Forsyth t.c_lflag &= ~(ICANON|ECHO|ISIG);
23337da2899SCharles.Forsyth t.c_cc[VMIN] = 1;
23437da2899SCharles.Forsyth t.c_cc[VTIME] = 0;
23537da2899SCharles.Forsyth tcsetattr(0, TCSANOW, &t);
23637da2899SCharles.Forsyth }
23737da2899SCharles.Forsyth
23837da2899SCharles.Forsyth static void
termrestore(void)23937da2899SCharles.Forsyth termrestore(void)
24037da2899SCharles.Forsyth {
24137da2899SCharles.Forsyth tcsetattr(0, TCSANOW, &tinit);
24237da2899SCharles.Forsyth
24337da2899SCharles.Forsyth /* if(sproctbl[0] < 0)
24437da2899SCharles.Forsyth panic("corrupt sproc tbl");
24537da2899SCharles.Forsyth
24637da2899SCharles.Forsyth kill(sproctbl[0], SIGUSR2);
24737da2899SCharles.Forsyth sginap(10000); */
24837da2899SCharles.Forsyth }
24937da2899SCharles.Forsyth
25037da2899SCharles.Forsyth void
trapUSR2(void)25137da2899SCharles.Forsyth trapUSR2(void)
25237da2899SCharles.Forsyth {
25337da2899SCharles.Forsyth int i;
25437da2899SCharles.Forsyth
25537da2899SCharles.Forsyth for(i = MAXSPROC - 1; i > 0; i--) {
25637da2899SCharles.Forsyth if(sproctbl[i] != -1)
25737da2899SCharles.Forsyth kill(sproctbl[i], SIGKILL);
25837da2899SCharles.Forsyth sproctbl[i] = -1;
25937da2899SCharles.Forsyth }
26037da2899SCharles.Forsyth
26137da2899SCharles.Forsyth execvp(rebootargv[0], rebootargv);
26237da2899SCharles.Forsyth panic("reboot failure");
26337da2899SCharles.Forsyth }
26437da2899SCharles.Forsyth
26537da2899SCharles.Forsyth void
cleanexit(int x)26637da2899SCharles.Forsyth cleanexit(int x)
26737da2899SCharles.Forsyth {
26837da2899SCharles.Forsyth USED(x);
26937da2899SCharles.Forsyth
27037da2899SCharles.Forsyth if(up->intwait) {
27137da2899SCharles.Forsyth up->intwait = 0;
27237da2899SCharles.Forsyth return;
27337da2899SCharles.Forsyth }
27437da2899SCharles.Forsyth
27537da2899SCharles.Forsyth if(dflag == 0)
27637da2899SCharles.Forsyth termrestore();
27737da2899SCharles.Forsyth kill(0, SIGKILL);
27837da2899SCharles.Forsyth exit(0);
27937da2899SCharles.Forsyth }
28037da2899SCharles.Forsyth
28137da2899SCharles.Forsyth void
getnobody(void)28237da2899SCharles.Forsyth getnobody(void)
28337da2899SCharles.Forsyth {
28437da2899SCharles.Forsyth struct passwd *pwd;
28537da2899SCharles.Forsyth
28637da2899SCharles.Forsyth pwd = getpwnam("nobody");
28737da2899SCharles.Forsyth if(pwd != nil) {
28837da2899SCharles.Forsyth uidnobody = pwd->pw_uid;
28937da2899SCharles.Forsyth gidnobody = pwd->pw_gid;
29037da2899SCharles.Forsyth }
29137da2899SCharles.Forsyth }
29237da2899SCharles.Forsyth
29337da2899SCharles.Forsyth void
osreboot(char * file,char ** argv)29437da2899SCharles.Forsyth osreboot(char *file, char **argv)
29537da2899SCharles.Forsyth {
29637da2899SCharles.Forsyth if(dflag == 0)
29737da2899SCharles.Forsyth termrestore();
29837da2899SCharles.Forsyth execvp(file, argv);
29937da2899SCharles.Forsyth panic("reboot failure");
30037da2899SCharles.Forsyth }
30137da2899SCharles.Forsyth
30237da2899SCharles.Forsyth void
libinit(char * imod)30337da2899SCharles.Forsyth libinit(char *imod)
30437da2899SCharles.Forsyth {
30537da2899SCharles.Forsyth struct sigaction act;
30637da2899SCharles.Forsyth struct passwd *pw;
30737da2899SCharles.Forsyth int i;
30837da2899SCharles.Forsyth char sys[64];
30937da2899SCharles.Forsyth
31037da2899SCharles.Forsyth setsid();
31137da2899SCharles.Forsyth
31237da2899SCharles.Forsyth for(i=0; i<MAXSPROC; i++)
31337da2899SCharles.Forsyth sproctbl[i] = -1;
31437da2899SCharles.Forsyth
31537da2899SCharles.Forsyth sproctbl[0] = getpid();
31637da2899SCharles.Forsyth
31737da2899SCharles.Forsyth gethostname(sys, sizeof(sys));
31837da2899SCharles.Forsyth kstrdup(&ossysname, sys);
31937da2899SCharles.Forsyth
32037da2899SCharles.Forsyth if(dflag == 0)
32137da2899SCharles.Forsyth termset();
32237da2899SCharles.Forsyth
32337da2899SCharles.Forsyth if(signal(SIGTERM, SIG_IGN) != SIG_IGN)
32437da2899SCharles.Forsyth signal(SIGTERM, cleanexit);
32537da2899SCharles.Forsyth if(signal(SIGINT, SIG_IGN) != SIG_IGN)
32637da2899SCharles.Forsyth signal(SIGINT, cleanexit);
32737da2899SCharles.Forsyth signal(SIGUSR2, trapUSR2);
32837da2899SCharles.Forsyth /* For the correct functioning of devcmd in the
32937da2899SCharles.Forsyth * face of exiting slaves
33037da2899SCharles.Forsyth */
33137da2899SCharles.Forsyth signal(SIGCLD, SIG_IGN);
33237da2899SCharles.Forsyth signal(SIGPIPE, SIG_IGN);
33337da2899SCharles.Forsyth memset(&act, 0 , sizeof(act));
33437da2899SCharles.Forsyth act.sa_handler=trapUSR1;
33537da2899SCharles.Forsyth sigaction(SIGUSR1, &act, nil);
33637da2899SCharles.Forsyth if(sflag == 0) {
33737da2899SCharles.Forsyth act.sa_handler=trapBUS;
33837da2899SCharles.Forsyth sigaction(SIGBUS, &act, nil);
33937da2899SCharles.Forsyth act.sa_handler=trapILL;
34037da2899SCharles.Forsyth sigaction(SIGILL, &act, nil);
34137da2899SCharles.Forsyth act.sa_handler=trapSEGV;
34237da2899SCharles.Forsyth sigaction(SIGSEGV, &act, nil);
34337da2899SCharles.Forsyth }
34437da2899SCharles.Forsyth
34537da2899SCharles.Forsyth if(usconfig(CONF_INITUSERS, 1000) < 0)
34637da2899SCharles.Forsyth panic("usconfig");
34737da2899SCharles.Forsyth
34837da2899SCharles.Forsyth Xup = (Proc**)PRDA->usr_prda.fill;
34937da2899SCharles.Forsyth up = newproc();
35037da2899SCharles.Forsyth
35137da2899SCharles.Forsyth pw = getpwuid(getuid());
35237da2899SCharles.Forsyth if(pw != nil) {
35337da2899SCharles.Forsyth if (strlen(pw->pw_name) + 1 <= KNAMELEN)
35437da2899SCharles.Forsyth strcpy(eve, pw->pw_name);
35537da2899SCharles.Forsyth else
35637da2899SCharles.Forsyth print("pw_name too long\n");
35737da2899SCharles.Forsyth }
35837da2899SCharles.Forsyth else
35937da2899SCharles.Forsyth print("cannot getpwuid\n");
36037da2899SCharles.Forsyth
36137da2899SCharles.Forsyth /* after setting up, since this takes locks */
36237da2899SCharles.Forsyth getnobody();
36337da2899SCharles.Forsyth up->env->uid = getuid();
36437da2899SCharles.Forsyth up->env->gid = getgid();
36537da2899SCharles.Forsyth emuinit(imod);
36637da2899SCharles.Forsyth }
36737da2899SCharles.Forsyth
36837da2899SCharles.Forsyth int
readkbd(void)36937da2899SCharles.Forsyth readkbd(void)
37037da2899SCharles.Forsyth {
37137da2899SCharles.Forsyth int n;
37237da2899SCharles.Forsyth char buf[1];
37337da2899SCharles.Forsyth
37437da2899SCharles.Forsyth n = read(0, buf, sizeof(buf));
37537da2899SCharles.Forsyth if(n < 0)
37637da2899SCharles.Forsyth fprint(2, "keyboard read error: %s\n", strerror(errno));
37737da2899SCharles.Forsyth if(n <= 0)
37837da2899SCharles.Forsyth pexit("keyboard thread", 0);
37937da2899SCharles.Forsyth switch(buf[0]) {
38037da2899SCharles.Forsyth case '\r':
38137da2899SCharles.Forsyth buf[0] = '\n';
38237da2899SCharles.Forsyth break;
38337da2899SCharles.Forsyth case DELETE:
38437da2899SCharles.Forsyth cleanexit(0);
38537da2899SCharles.Forsyth break;
38637da2899SCharles.Forsyth }
38737da2899SCharles.Forsyth return buf[0];
38837da2899SCharles.Forsyth }
38937da2899SCharles.Forsyth
39037da2899SCharles.Forsyth int
segflush(void * a,ulong n)39137da2899SCharles.Forsyth segflush(void *a, ulong n)
39237da2899SCharles.Forsyth {
39337da2899SCharles.Forsyth cacheflush(a, n, BCACHE);
39437da2899SCharles.Forsyth return 0;
39537da2899SCharles.Forsyth }
39637da2899SCharles.Forsyth
39737da2899SCharles.Forsyth /*
39837da2899SCharles.Forsyth * Return an abitrary millisecond clock time
39937da2899SCharles.Forsyth */
40037da2899SCharles.Forsyth long
osmillisec(void)40137da2899SCharles.Forsyth osmillisec(void)
40237da2899SCharles.Forsyth {
40337da2899SCharles.Forsyth static long sec0 = 0, usec0;
40437da2899SCharles.Forsyth struct timeval t;
40537da2899SCharles.Forsyth
40637da2899SCharles.Forsyth if(gettimeofday(&t,(struct timezone*)0)<0)
40737da2899SCharles.Forsyth return(0);
40837da2899SCharles.Forsyth if(sec0==0){
40937da2899SCharles.Forsyth sec0 = t.tv_sec;
41037da2899SCharles.Forsyth usec0 = t.tv_usec;
41137da2899SCharles.Forsyth }
41237da2899SCharles.Forsyth return((t.tv_sec-sec0)*1000+(t.tv_usec-usec0+500)/1000);
41337da2899SCharles.Forsyth }
41437da2899SCharles.Forsyth
41537da2899SCharles.Forsyth /*
41637da2899SCharles.Forsyth * Return the time since the epoch in nanoseconds and microseconds
41737da2899SCharles.Forsyth * The epoch is defined at 1 Jan 1970
41837da2899SCharles.Forsyth */
41937da2899SCharles.Forsyth vlong
osnsec(void)42037da2899SCharles.Forsyth osnsec(void)
42137da2899SCharles.Forsyth {
42237da2899SCharles.Forsyth struct timeval t;
42337da2899SCharles.Forsyth
42437da2899SCharles.Forsyth gettimeofday(&t, nil);
42537da2899SCharles.Forsyth return (vlong)t.tv_sec*1000000000L + t.tv_usec*1000;
42637da2899SCharles.Forsyth }
42737da2899SCharles.Forsyth
42837da2899SCharles.Forsyth vlong
osusectime(void)42937da2899SCharles.Forsyth osusectime(void)
43037da2899SCharles.Forsyth {
43137da2899SCharles.Forsyth struct timeval t;
43237da2899SCharles.Forsyth
43337da2899SCharles.Forsyth gettimeofday(&t, nil);
43437da2899SCharles.Forsyth return (vlong)t.tv_sec * 1000000 + t.tv_usec;
43537da2899SCharles.Forsyth }
43637da2899SCharles.Forsyth
43737da2899SCharles.Forsyth int
osmillisleep(ulong milsec)43837da2899SCharles.Forsyth osmillisleep(ulong milsec)
43937da2899SCharles.Forsyth {
44037da2899SCharles.Forsyth static int tick;
44137da2899SCharles.Forsyth
44237da2899SCharles.Forsyth /*
44337da2899SCharles.Forsyth * Posix-conforming CLK_TCK implementations tend to call sysconf,
44437da2899SCharles.Forsyth * and we don't need the overhead.
44537da2899SCharles.Forsyth */
44637da2899SCharles.Forsyth if(tick == 0)
44737da2899SCharles.Forsyth tick = CLK_TCK;
44837da2899SCharles.Forsyth sginap((tick*milsec)/1000);
44937da2899SCharles.Forsyth return 0;
45037da2899SCharles.Forsyth }
45137da2899SCharles.Forsyth
45237da2899SCharles.Forsyth int
limbosleep(ulong milsec)45337da2899SCharles.Forsyth limbosleep(ulong milsec)
45437da2899SCharles.Forsyth {
45537da2899SCharles.Forsyth return osmillisleep(milsec);
45637da2899SCharles.Forsyth }
45737da2899SCharles.Forsyth
45837da2899SCharles.Forsyth void
osyield(void)45937da2899SCharles.Forsyth osyield(void)
46037da2899SCharles.Forsyth {
46137da2899SCharles.Forsyth sginap(0);
46237da2899SCharles.Forsyth }
46337da2899SCharles.Forsyth
46437da2899SCharles.Forsyth void
ospause(void)46537da2899SCharles.Forsyth ospause(void)
46637da2899SCharles.Forsyth {
46737da2899SCharles.Forsyth for(;;)
46837da2899SCharles.Forsyth pause();
46937da2899SCharles.Forsyth }
47037da2899SCharles.Forsyth
47137da2899SCharles.Forsyth void
oslopri(void)47237da2899SCharles.Forsyth oslopri(void)
47337da2899SCharles.Forsyth {
47437da2899SCharles.Forsyth nice(2);
47537da2899SCharles.Forsyth }
476