⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sub.c

📁 这是一个同样来自贝尔实验室的和UNIX有着渊源的操作系统, 其简洁的设计和实现易于我们学习和理解
💻 C
📖 第 1 页 / 共 2 页
字号:
	lock(&rabuflock);	unlock(&rabuflock);	rabuffree = 0;	for(i=0; i<1000; i++) {		rb = ialloc(sizeof(*rb), 0);		rb->link = rabuffree;		rabuffree = rb;	}}Msgbuf*mballoc(int count, Chan *cp, int category){	Msgbuf *mb;	ilock(&msgalloc);	if(count > SMALLBUF) {		if(count > LARGEBUF)			panic("msgbuf count");		mb = msgalloc.lmsgbuf;		if(mb == 0) {			mb = ialloc(sizeof(Msgbuf), 0);			if(1)				mb->xdata = ialloc(LARGEBUF+256, 256);			else				mb->xdata = ialloc(LARGEBUF+OFFMSG, LINESIZE);			mb->free = 0;			cons.nlarge++;		} else			msgalloc.lmsgbuf = mb->next;		mb->flags = LARGE;	} else {		mb = msgalloc.smsgbuf;		if(mb == 0) {			mb = ialloc(sizeof(Msgbuf), 0);			if(1)				mb->xdata = ialloc(SMALLBUF+256, 256);			else				mb->xdata = ialloc(SMALLBUF+OFFMSG, LINESIZE);			mb->free = 0;			cons.nsmall++;		} else			msgalloc.smsgbuf = mb->next;		mb->flags = 0;	}	mballocs[category]++;	iunlock(&msgalloc);	mb->count = count;	mb->chan = cp;	mb->next = 0;	mb->param = 0;	mb->category = category;	if(1)		mb->data = mb->xdata+256;	else		mb->data = mb->xdata+OFFMSG;	mb->free = 0;	return mb;}voidmbfree(Msgbuf *mb){	if(mb == nil)		return;	if(mb->flags & BTRACE)		print("mbfree: BTRACE cat=%d flags=%ux, caller 0x%lux\n",			mb->category, mb->flags, getcallerpc(&mb));	/*	 * drivers which perform non cache coherent DMA manage their own buffer	 * pool of uncached buffers and provide their own free routine.	 * this is provided mainly for ethernet drivers ported from cpu kernel.	 */	if(mb->flags&Mbrcvbuf) {		if (mb->free == nil)			panic("freeb: nil mb->free");		(*mb->free)(mb);		return;	}	if(mb->flags & FREE)		panic("mbfree already free");	ilock(&msgalloc);	mballocs[mb->category]--;	mb->flags |= FREE;	if(mb->flags & LARGE) {		mb->next = msgalloc.lmsgbuf;		msgalloc.lmsgbuf = mb;	} else {		mb->next = msgalloc.smsgbuf;		msgalloc.smsgbuf = mb;	}	mb->data = 0;	mb->free = 0;	iunlock(&msgalloc);}/* * returns 1 if n is prime * used for adjusting lengths * of hashing things. * there is no need to be clever */intprime(vlong n){	long i;	if((n%2) == 0)		return 0;	for(i=3;; i+=2) {		if((n%i) == 0)			return 0;		if((vlong)i*i >= n)			return 1;	}}char*getwd(char *word, char *line){	int c, n;	while(*line == ' ')		line++;	for(n=0; n<Maxword; n++) {		c = *line;		if(c == ' ' || c == 0 || c == '\n')			break;		line++;		*word++ = c;	}	*word = 0;	return line;}voidhexdump(void *a, int n){	char s1[30], s2[4];	uchar *p;	int i;	p = a;	s1[0] = 0;	for(i=0; i<n; i++) {		sprint(s2, " %.2ux", p[i]);		strcat(s1, s2);		if((i&7) == 7) {			print("%s\n", s1);			s1[0] = 0;		}	}	if(s1[0])		print("%s\n", s1);}void*recv(Queue *q, int){	User *p;	void *a;	int i, c;	long s;	if(q == 0)		panic("recv null q");	for(;;) {		lock(q);		c = q->count;		if(c > 0) {			i = q->loc;			a = q->args[i];			i++;			if(i >= q->size)				i = 0;			q->loc = i;			q->count = c-1;			p = q->whead;			if(p) {				q->whead = p->qnext;				if(q->whead == 0)					q->wtail = 0;				ready(p);			}			unlock(q);			return a;		}		p = q->rtail;		if(p == 0)			q->rhead = u;		else			p->qnext = u;		q->rtail = u;		u->qnext = 0;		s = splhi();		u->state = Recving;		unlock(q);		sched();		splx(s);	}}voidsend(Queue *q, void *a){	User *p;	int i, c;	long s;	if(q == 0)		panic("send null q");	for(;;) {		lock(q);		c = q->count;		if(c < q->size) {			i = q->loc + c;			if(i >= q->size)				i -= q->size;			q->args[i] = a;			q->count = c+1;			p = q->rhead;			if(p) {				q->rhead = p->qnext;				if(q->rhead == 0)					q->rtail = 0;				ready(p);			}			unlock(q);			return;		}		p = q->wtail;		if(p == 0)			q->whead = u;		else			p->qnext = u;		q->wtail = u;		u->qnext = 0;		s = splhi();		u->state = Sending;		unlock(q);		sched();		splx(s);	}}Queue*newqueue(int size){	Queue *q;	q = ialloc(sizeof(Queue) + (size-1)*sizeof(void*), 0);	q->size = size;	lock(q);	unlock(q);	return q;}no(void*){	return 0;}intdevread(Device *d, Off b, void *c){	int e;	for (;;)		switch(d->type)		{		case Devcw:			return cwread(d, b, c);		case Devjuke:			d = d->j.m;			break;		case Devro:			return roread(d, b, c);		case Devwren:			return wrenread(d, b, c);		case Devide:			return ideread(d, b, c);		case Devmarvsata:			return mvideread(d, b, c);		case Devworm:		case Devlworm:			return wormread(d, b, c);		case Devfworm:			return fwormread(d, b, c);		case Devmcat:			return mcatread(d, b, c);		case Devmlev:			return mlevread(d, b, c);		case Devmirr:			return mirrread(d, b, c);		case Devpart:			return partread(d, b, c);		case Devswab:			e = devread(d->swab.d, b, c);			if(e == 0)				swab(c, 0);			return e;		case Devnone:			print("read from device none(%lld)\n", (Wideoff)b);			return 1;		default:			panic("illegal device in read: %Z %lld", d, (Wideoff)b);			return 1;		}}intdevwrite(Device *d, Off b, void *c){	int e;	/*	 * set readonly to non-0 to prevent all writes;	 * mainly for trying dangerous experiments.	 */	if (readonly)		return 0;	for (;;)		switch(d->type)		{		case Devcw:			return cwwrite(d, b, c);		case Devjuke:			d = d->j.m;			break;		case Devro:			print("write to ro device %Z(%lld)\n", d, (Wideoff)b);			return 1;		case Devwren:			return wrenwrite(d, b, c);		case Devide:			return idewrite(d, b, c);		case Devmarvsata:			return mvidewrite(d, b, c);		case Devworm:		case Devlworm:			return wormwrite(d, b, c);		case Devfworm:			return fwormwrite(d, b, c);		case Devmcat:			return mcatwrite(d, b, c);		case Devmlev:			return mlevwrite(d, b, c);		case Devmirr:			return mirrwrite(d, b, c);		case Devpart:			return partwrite(d, b, c);		case Devswab:			swab(c, 1);			e = devwrite(d->swab.d, b, c);			swab(c, 0);			return e;		case Devnone:			/* checktag() can generate blocks with type devnone */			return 0;		default:			panic("illegal device in write: %Z %ld", d, b);			return 1;		}}Devsizedevsize(Device *d){	for (;;)		switch(d->type)		{		case Devcw:		case Devro:			return cwsize(d);		case Devjuke:			d = d->j.m;			break;		case Devwren:			return wrensize(d);		case Devide:			return idesize(d);		case Devmarvsata:			return mvidesize(d);		case Devworm:		case Devlworm:			return wormsize(d);		case Devfworm:			return fwormsize(d);		case Devmcat:			return mcatsize(d);		case Devmlev:			return mlevsize(d);		case Devmirr:			return mirrsize(d);		case Devpart:			return partsize(d);		case Devswab:			d = d->swab.d;			break;		default:			panic("illegal device in dev_size: %Z", d);			return 0;		}}Offsuperaddr(Device *d){	for (;;)		switch(d->type) {		default:			return SUPER_ADDR;		case Devcw:		case Devro:			return cwsaddr(d);		case Devswab:			d = d->swab.d;			break;		}}Offgetraddr(Device *d){	for (;;)		switch(d->type) {		default:			return ROOT_ADDR;		case Devcw:		case Devro:			return cwraddr(d);		case Devswab:			d = d->swab.d;			break;		}}voiddevream(Device *d, int top){	Device *l;loop:	print("	devream: %Z %d\n", d, top);	switch(d->type) {	default:		print("ream: unknown dev type %Z\n", d);		return;	case Devcw:		devream(d->cw.w, 0);		devream(d->cw.c, 0);		if(top) {			wlock(&mainlock);			cwream(d);			wunlock(&mainlock);		}		devinit(d);		return;	case Devfworm:		devream(d->fw.fw, 0);		fwormream(d);		break;	case Devpart:		devream(d->part.d, 0);		break;	case Devmlev:	case Devmcat:	case Devmirr:		for(l=d->cat.first; l; l=l->link)			devream(l, 0);		break;	case Devjuke:	case Devworm:	case Devlworm:	case Devwren:	case Devide:	case Devmarvsata:		break;	case Devswab:		d = d->swab.d;		goto loop;	}	devinit(d);	if(top) {		wlock(&mainlock);		rootream(d, ROOT_ADDR);		superream(d, SUPER_ADDR);		wunlock(&mainlock);	}}voiddevrecover(Device *d){	for (;;) {		print("recover: %Z\n", d);		switch(d->type) {		default:			print("recover: unknown dev type %Z\n", d);			return;		case Devcw:			wlock(&mainlock);	/* recover */			cwrecover(d);			wunlock(&mainlock);			return;		case Devswab:			d = d->swab.d;			break;		}	}}voiddevinit(Device *d){	for (;;) {		if(d->init)			return;		d->init = 1;		print("	devinit %Z\n", d);		switch(d->type) {		default:			print("devinit unknown device %Z\n", d);			return;		case Devro:			cwinit(d->ro.parent);			return;		case Devcw:			cwinit(d);			return;		case Devjuke:			jukeinit(d);			return;		case Devwren:			wreninit(d);			return;		case Devide:			ideinit(d);			return;		case Devmarvsata:			mvideinit(d);			return;		case Devworm:		case Devlworm:			return;		case Devfworm:			fworminit(d);			return;		case Devmcat:			mcatinit(d);			return;		case Devmlev:			mlevinit(d);			return;		case Devmirr:			mirrinit(d);			return;		case Devpart:			partinit(d);			return;		case Devswab:			d = d->swab.d;			break;		case Devnone:			print("devinit of Devnone\n");			return;		}	}}voidswab2(void *c){	uchar *p;	int t;	p = c;	t = p[0];	p[0] = p[1];	p[1] = t;}voidswab4(void *c){	uchar *p;	int t;	p = c;	t = p[0];	p[0] = p[3];	p[3] = t;	t = p[1];	p[1] = p[2];	p[2] = t;}voidswab8(void *c){	uchar *p;	int t;	p = c;	t = p[0];	p[0] = p[7];	p[7] = t;	t = p[1];	p[1] = p[6];	p[6] = t;	t = p[2];	p[2] = p[5];	p[5] = t;	t = p[3];	p[3] = p[4];	p[4] = t;}/* * swab a block *	flag = 0 -- convert from foreign to native *	flag = 1 -- convert from native to foreign */voidswab(void *c, int flag){	uchar *p;	Tag *t;	int i, j;	Dentry *d;	Cache *h;	Bucket *b;	Superb *s;	Fbuf *f;	Off *l;	/* swab the tag */	p = (uchar*)c;	t = (Tag*)(p + BUFSIZE);	if(!flag) {		swab2(&t->pad);		swab2(&t->tag);		swaboff(&t->path);	}	/* swab each block type */	switch(t->tag) {	default:		print("no swab for tag=%G rw=%d\n", t->tag, flag);		for(j=0; j<16; j++)			print(" %.2x", p[BUFSIZE+j]);		print("\n");		for(i=0; i<16; i++) {			print("%.4x", i*16);			for(j=0; j<16; j++)				print(" %.2x", p[i*16+j]);			print("\n");		}		panic("swab");		break;	case Tsuper:		s = (Superb*)p;		swaboff(&s->fbuf.nfree);		for(i=0; i<FEPERBUF; i++)			swaboff(&s->fbuf.free[i]);#ifdef AUTOSWAB		swaboff(&s->magic);#endif		swaboff(&s->fstart);		swaboff(&s->fsize);		swaboff(&s->tfree);		swaboff(&s->qidgen);		swaboff(&s->cwraddr);		swaboff(&s->roraddr);		swaboff(&s->last);		swaboff(&s->next);		break;	case Tdir:		for(i=0; i<DIRPERBUF; i++) {			d = (Dentry*)p + i;			swab2(&d->uid);			swab2(&d->gid);			swab2(&d->mode);			swab2(&d->muid);			swaboff(&d->qid.path);			swab4(&d->qid.version);			swaboff(&d->size);			for(j=0; j<NDBLOCK; j++)				swaboff(&d->dblock[j]);			for (j = 0; j < NIBLOCK; j++)				swaboff(&d->iblocks[j]);			swab4(&d->atime);			swab4(&d->mtime);		}		break;	case Tind1:	case Tind2:#ifndef OLD	case Tind3:	case Tind4:	/* add more Tind tags here ... */#endif		l = (Off *)p;		for(i=0; i<INDPERBUF; i++) {			swaboff(l);			l++;		}		break;	case Tfree:		f = (Fbuf*)p;		swaboff(&f->nfree);		for(i=0; i<FEPERBUF; i++)			swaboff(&f->free[i]);		break;	case Tbuck:		for(i=0; i<BKPERBLK; i++) {			b = (Bucket*)p + i;			swab4(&b->agegen);			for(j=0; j<CEPERBK; j++) {				swab2(&b->entry[j].age);				swab2(&b->entry[j].state);				swaboff(&b->entry[j].waddr);			}		}		break;	case Tcache:		h = (Cache*)p;		swaboff(&h->maddr);		swaboff(&h->msize);		swaboff(&h->caddr);		swaboff(&h->csize);		swaboff(&h->fsize);		swaboff(&h->wsize);		swaboff(&h->wmax);		swaboff(&h->sbaddr);		swaboff(&h->cwraddr);		swaboff(&h->roraddr);		swab4(&h->toytime);		swab4(&h->time);		break;	case Tnone:	// unitialized	case Tfile:	// someone elses problem	case Tvirgo:	// bit map -- all bytes	case Tconfig:	// configuration string -- all bytes		break;	}	/* swab the tag */	if(flag) {		swab2(&t->pad);		swab2(&t->tag);		swaboff(&t->path);	}}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -