コード例 #1
0
ファイル: sysfile.c プロジェクト: Akheon23/nix-os
static int
dirfixed(uchar *p, uchar *e, Dir *d)
{
	int len;

	len = GBIT16(p)+BIT16SZ;
	if(p + len > e)
		return -1;

	p += BIT16SZ;	/* ignore size */
	d->type = devno(GBIT16(p), 1);
	p += BIT16SZ;
	d->dev = GBIT32(p);
	p += BIT32SZ;
	d->qid.type = GBIT8(p);
	p += BIT8SZ;
	d->qid.vers = GBIT32(p);
	p += BIT32SZ;
	d->qid.path = GBIT64(p);
	p += BIT64SZ;
	d->mode = GBIT32(p);
	p += BIT32SZ;
	d->atime = GBIT32(p);
	p += BIT32SZ;
	d->mtime = GBIT32(p);
	p += BIT32SZ;
	d->length = GBIT64(p);

	return len;
}
コード例 #2
0
ファイル: convM2S.c プロジェクト: BackupTheBerlios/estyx-svn
static u8* gqid(u8 *p, u8 *ep, Qid *q)
{
	if(p+QIDSZ > ep)
		return nil;
	q->type = GBIT8(p);
	p += BIT8SZ;
	q->vers = GBIT32(p);
	p += BIT32SZ;
	q->path = GBIT32(p);
	p += BIT64SZ;
	return p;
}
コード例 #3
0
ファイル: convM2kdirent.c プロジェクト: 7perl/akaros
unsigned int convM2kstat(uint8_t * buf, unsigned int nbuf, struct kstat *ks)
{
	uint8_t *p, *ebuf;
	char *sv[4];
	int i, ns;
	uint32_t junk;

	if (nbuf < STATFIXLEN)
		return 0;

	p = buf;
	ebuf = buf + nbuf;

	p += BIT16SZ;	/* ignore size */
	junk /*kd->d_type */  = GBIT16(p);
	p += BIT16SZ;
	ks->st_rdev = ks->st_dev = GBIT32(p);
	p += BIT32SZ;
	junk /*qid.type */  = GBIT8(p);
	p += BIT8SZ;
	junk /*qid.vers */  = GBIT32(p);
	p += BIT32SZ;
	ks->st_ino = GBIT64(p);
	p += BIT64SZ;
	ks->st_mode = GBIT32(p);
	if (ks->st_mode & DMDIR) {
		ks->st_mode &= ~DMDIR;
		ks->st_mode |= __S_IFDIR;
	} else if (ks->st_mode & DMSYMLINK) {
		ks->st_mode &= ~DMSYMLINK;
		ks->st_mode |= __S_IFLNK;
	} else {
		ks->st_mode |= __S_IFREG;
	}
	p += BIT32SZ;
	ks->st_atime.tv_sec = GBIT32(p);
	p += BIT32SZ;
	ks->st_mtime.tv_sec = GBIT32(p);
	p += BIT32SZ;
	ks->st_size = GBIT64(p);
	p += BIT64SZ;
	ks->st_blksize = 512;
	ks->st_blocks = ROUNDUP(ks->st_size, ks->st_blksize) / ks->st_blksize;

	ks->st_nlink = 2;	// links make no sense any more. 
	ks->st_uid = ks->st_gid = 0;

	return p - buf;
}
コード例 #4
0
ファイル: 9pserve.c プロジェクト: 00001/plan9port
uchar*
read9ppkt(Ioproc *io, int fd)
{
	uchar buf[4], *pkt;
	int n, nn;

	n = ioreadn(io, fd, buf, 4);
	if(n != 4)
		return nil;
	n = GBIT32(buf);
	if(n > MAXMSGSIZE)
		return nil;
	pkt = emalloc(n);
	PBIT32(pkt, n);
	nn = ioreadn(io, fd, pkt+4, n-4);
	if(nn != n-4){
		free(pkt);
		return nil;
	}
/* would do this if we ever got one of these, but we only generate them
	if(pkt[4] == Ropenfd){
		newfd = iorecvfd(io, fd);
		PBIT32(pkt+n-4, newfd);
	}
*/
	return pkt;
}
コード例 #5
0
ファイル: 9pserve.c プロジェクト: 00001/plan9port
int
xopenfd(Msg *m)
{
	char errs[ERRMAX];
	int n, p[2];
	Conn *nc;

	if(pipe(p) < 0){
		rerrstr(errs, sizeof errs);
		err(m, errs);
		/* XXX return here? */
	}
	if(verbose) fprint(2, "%T xopen pipe %d %d...", p[0], p[1]);

	/* now we're committed. */

	/* a new connection for this fid */
	nc = emalloc(sizeof(Conn));
	nc->internal = chancreate(sizeof(void*), 0);

	/* a ref for us */
	nc->fdfid = m->fid;
	m->fid->ref++;
	nc->fdfid->openfd++;
	nc->fdmode = m->tx.mode;
	nc->fd = p[0];

	/* a thread to tend the pipe */
	threadcreate(openfdthread, nc, STACK);

	/* if mode is ORDWR, that openfdthread will write; start a reader */
	if((m->tx.mode&3) == ORDWR){
		nc = emalloc(sizeof(Conn));
		nc->internal = chancreate(sizeof(void*), 0);
		nc->fdfid = m->fid;
		m->fid->ref++;
		nc->fdfid->openfd++;
		nc->fdmode = OREAD;
		nc->fd = dup(p[0], -1);
		threadcreate(openfdthread, nc, STACK);
	}

	/* steal fid from other connection */
	if(delhash(m->c->fid, m->fid->cfid, m->fid) == 0)
		fidput(m->fid);

	/* rewrite as Ropenfd */
	m->rx.type = Ropenfd;
	n = GBIT32(m->rpkt);
	m->rpkt = erealloc(m->rpkt, n+4);
	PBIT32(m->rpkt+n, p[1]);
	n += 4;
	PBIT32(m->rpkt, n);
	m->rpkt[4] = Ropenfd;
	m->rx.unixfd = p[1];
	return 0;
}
コード例 #6
0
ファイル: 9pserve.c プロジェクト: 00001/plan9port
void
rewritehdr(Fcall *f, uchar *pkt)
{
	int i, n;

	n = GBIT32(pkt);
	PBIT16(pkt+5, f->tag);
	switch(f->type){
	case Tversion:
	case Rversion:
		restring(pkt, n, f->version);
		break;
	case Tauth:
		PBIT32(pkt+7, f->afid);
		restring(pkt, n, f->uname);
		restring(pkt, n, f->aname);
		break;
	case Tflush:
		PBIT16(pkt+7, f->oldtag);
		break;
	case Tattach:
		restring(pkt, n, f->uname);
		restring(pkt, n, f->aname);
		PBIT32(pkt+7, f->fid);
		PBIT32(pkt+11, f->afid);
		break;
	case Twalk:
		PBIT32(pkt+7, f->fid);
		PBIT32(pkt+11, f->newfid);
		for(i=0; i<f->nwname; i++)
			restring(pkt, n, f->wname[i]);
		break;
	case Tcreate:
		restring(pkt, n, f->name);
		/* fall through */
	case Topen:
	case Tclunk:
	case Tremove:
	case Tstat:
	case Twstat:
	case Twrite:
		PBIT32(pkt+7, f->fid);
		break;
	case Tread:
		PBIT32(pkt+7, f->fid);
		PBIT64(pkt+11, f->offset);
		break;
	case Rerror:
		restring(pkt, n, f->ename);
		break;
	}
}
コード例 #7
0
ファイル: convM2S.c プロジェクト: 7perl/akaros
static
uint8_t *gqid(uint8_t * p, uint8_t * ep, struct qid *q)
{
	if (p + QIDSZ > ep)
		return NULL;
	q->type = GBIT8(p);
	p += BIT8SZ;
	q->vers = GBIT32(p);
	p += BIT32SZ;
	q->path = GBIT64(p);
	p += BIT64SZ;
	return p;
}
コード例 #8
0
ファイル: 9pserve.c プロジェクト: 00001/plan9port
int
mwrite9p(Ioproc *io, int fd, uchar *pkt)
{
	int n, nfd;

	n = GBIT32(pkt);
	if(verbose > 2) fprint(2, "%T write %d %d %.*H\n", fd, n, n, pkt);
if(verbose > 1) fprint(2, "%T before iowrite\n");
	if(iowrite(io, fd, pkt, n) != n){
		fprint(2, "%T write error: %r\n");
		return -1;
	}
if(verbose > 1) fprint(2, "%T after iowrite\n");
	if(pkt[4] == Ropenfd){
		nfd = GBIT32(pkt+n-4);
		if(iosendfd(io, fd, nfd) < 0){
			fprint(2, "%T send fd error: %r\n");
			return -1;
		}
	}
	return 0;
}
コード例 #9
0
ファイル: sysfile.c プロジェクト: Shamar/harvey
static usize
dirfixed(uint8_t *p, uint8_t *e, Dir *d)
{
	int len;
	Dev *dev;

	len = GBIT16(p)+BIT16SZ;
	if(p + len > e)
		return 0;

	p += BIT16SZ;	/* ignore size */
	dev = devtabget(GBIT16(p), 1);			//XDYNX
	if(dev != nil){
		d->type = dev->dc;
		//devtabdecr(dev);
	}
	else
		d->type = -1;
	p += BIT16SZ;
	d->dev = GBIT32(p);
	p += BIT32SZ;
	d->qid.type = GBIT8(p);
	p += BIT8SZ;
	d->qid.vers = GBIT32(p);
	p += BIT32SZ;
	d->qid.path = GBIT64(p);
	p += BIT64SZ;
	d->mode = GBIT32(p);
	p += BIT32SZ;
	d->atime = GBIT32(p);
	p += BIT32SZ;
	d->mtime = GBIT32(p);
	p += BIT32SZ;
	d->length = GBIT64(p);

	return len;
}
コード例 #10
0
ファイル: 9pserve.c プロジェクト: 00001/plan9port
void
inputthread(void *arg)
{
	uchar *pkt;
	int n, nn, tag;
	Msg *m;
	Ioproc *io;

	threadsetname("input");
	if(verbose) fprint(2, "%T input thread\n");
	io = ioproc();
	USED(arg);
	while((pkt = read9ppkt(io, 0)) != nil){
		n = GBIT32(pkt);
		if(n < 7){
			fprint(2, "%T short 9P packet from server\n");
			free(pkt);
			continue;
		}
		if(verbose > 2) fprint(2, "%T read %.*H\n", n, pkt);
		tag = GBIT16(pkt+5);
		if((m = msgget(tag)) == nil){
			fprint(2, "%T unexpected 9P response tag %d\n", tag);
			free(pkt);
			continue;
		}
		if((nn = convM2S(pkt, n, &m->rx)) != n){
			fprint(2, "%T bad packet - convM2S %d but %d\n", nn, n);
			free(pkt);
			msgput(m);
			continue;
		}
		if(verbose > 1) fprint(2, "%T * -> %F%s\n", &m->rx,
			m->internal ? " (internal)" : "");
		m->rpkt = pkt;
		m->rx.tag = m->ctag;
		if(m->internal)
			sendp(m->c->internal, m);
		else if(m->c->outq)
			sendq(m->c->outq, m);
		else
			msgput(m);
	}
	closeioproc(io);
	/*fprint(2, "%T input eof\n"); */
	threadexitsall(0);
}
コード例 #11
0
ファイル: 9p12.c プロジェクト: Requaos/harvey
static int
readmsg(Chan *c, void *abuf, int n, int *ninep)
{
	int fd, len;
	uint8_t *buf;

	buf = abuf;
	fd = c->chan;
	qlock(&c->rlock);
	if(readn(fd, buf, 3) != 3){
		qunlock(&c->rlock);
		print("readn(3) fails: %r\n");
		return -1;
	}
	if((50 <= buf[0] && buf[0] <= 87 && (buf[0]&1)==0 && GBIT16(buf+1) == 0xFFFF)
	|| buf[0] == 86	/* Tattach */){
		*ninep = 1;
		/* assume message boundaries */
		n = read(fd, buf+3, n-3);
		if(n < 0){
			qunlock(&c->rlock);
			return -1;
		}
		return n+3;
	}

	*ninep = 2;
	if(read(fd, buf+3, 1) != 1){
		qunlock(&c->rlock);
		print("read(1) fails: %r\n");
		return -1;
	}
	len = GBIT32(buf);
	if(len > n){
		print("msg too large\n");
		qunlock(&c->rlock);
		return -1;
	}
	if(readn(fd, buf+4, len-4) != len-4){
		print("readn(%d) fails: %r\n", len-4);
		qunlock(&c->rlock);
		return -1;
	}
	qunlock(&c->rlock);
	return len;
}
コード例 #12
0
ファイル: 9pserve.c プロジェクト: 00001/plan9port
void
repack(Fcall *f, uchar **ppkt)
{
	uint n, nn;
	uchar *pkt;
	
	pkt = *ppkt;
	n = GBIT32(pkt);
	nn = sizeS2M(f);
	if(nn > n){
		free(pkt);
		pkt = emalloc(nn);
		*ppkt = pkt;
	}
	n = convS2M(f, pkt, nn);	
	if(n <= BIT16SZ)
		sysfatal("convS2M conversion error");
	if(n != nn)
		sysfatal("convS2M and sizeS2M disagree");
}
コード例 #13
0
ファイル: 9pserve.c プロジェクト: 00001/plan9port
Msg*
mread9p(Ioproc *io, int fd)
{
	int n, nn;
	uchar *pkt;
	Msg *m;

	if((pkt = read9ppkt(io, fd)) == nil)
		return nil;

	m = msgnew(0);
	m->tpkt = pkt;
	n = GBIT32(pkt);
	nn = convM2S(pkt, n, &m->tx);
	if(nn != n){
		fprint(2, "%T read bad packet from %d\n", fd);
		return nil;
	}
	return m;
}
コード例 #14
0
ファイル: pci.c プロジェクト: vrthra/9front-tmp
static int
pcicfgrw(Pcidev *pcidev, int rno, int data, int len, int read)
{
	uchar buf[4];

	if(read){
		memset(buf, 0, sizeof(buf));
		if(pread(pcidev->rawfd, buf, len, rno) != len)
			return -1;
		switch(len){
		case 1:
			return GBIT8(buf);
		case 2:
			return GBIT16(buf);
		case 4:
			return GBIT32(buf);
		default:
			abort();
		}
	} else {
		switch(len){
		case 1:
			PBIT8(buf, data);
			break;
		case 2:
			PBIT16(buf, data);
			break;
		case 4:
			PBIT32(buf, data);
			break;
		default:
			abort();
		}
		if(pwrite(pcidev->rawfd, buf, len, rno) != len)
			return -1;
	}
	return 0;
}
コード例 #15
0
ファイル: convM2S.c プロジェクト: 0intro/drawterm
/*
 * no syntactic checks.
 * three causes for error:
 *  1. message size field is incorrect
 *  2. input buffer too short for its own data (counts too long, etc.)
 *  3. too many names or qids
 * gqid() and gstring() return nil if they would reach beyond buffer.
 * main switch statement checks range and also can fall through
 * to test at end of routine.
 */
uint
convM2S(uchar *ap, uint nap, Fcall *f)
{
	uchar *p, *ep;
	uint i, size;

	p = ap;
	ep = p + nap;

	if(p+BIT32SZ+BIT8SZ+BIT16SZ > ep)
		return 0;
	size = GBIT32(p);
	p += BIT32SZ;

	if(size < BIT32SZ+BIT8SZ+BIT16SZ)
		return 0;

	f->type = GBIT8(p);
	p += BIT8SZ;
	f->tag = GBIT16(p);
	p += BIT16SZ;

	switch(f->type)
	{
	default:
		return 0;

	case Tversion:
		if(p+BIT32SZ > ep)
			return 0;
		f->msize = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->version);
		break;

	case Tflush:
		if(p+BIT16SZ > ep)
			return 0;
		f->oldtag = GBIT16(p);
		p += BIT16SZ;
		break;

	case Tauth:
		if(p+BIT32SZ > ep)
			return 0;
		f->afid = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->uname);
		if(p == nil)
			break;
		p = gstring(p, ep, &f->aname);
		if(p == nil)
			break;
		break;

	case Tattach:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		if(p+BIT32SZ > ep)
			return 0;
		f->afid = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->uname);
		if(p == nil)
			break;
		p = gstring(p, ep, &f->aname);
		if(p == nil)
			break;
		break;

	case Twalk:
		if(p+BIT32SZ+BIT32SZ+BIT16SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->newfid = GBIT32(p);
		p += BIT32SZ;
		f->nwname = GBIT16(p);
		p += BIT16SZ;
		if(f->nwname > MAXWELEM)
			return 0;
		for(i=0; i<f->nwname; i++){
			p = gstring(p, ep, &f->wname[i]);
			if(p == nil)
				break;
		}
		break;

	case Topen:
		if(p+BIT32SZ+BIT8SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->mode = GBIT8(p);
		p += BIT8SZ;
		break;

	case Tcreate:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->name);
		if(p == nil)
			break;
		if(p+BIT32SZ+BIT8SZ > ep)
			return 0;
		f->perm = GBIT32(p);
		p += BIT32SZ;
		f->mode = GBIT8(p);
		p += BIT8SZ;
		break;

	case Tread:
		if(p+BIT32SZ+BIT64SZ+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->offset = GBIT64(p);
		p += BIT64SZ;
		f->count = GBIT32(p);
		p += BIT32SZ;
		break;

	case Twrite:
		if(p+BIT32SZ+BIT64SZ+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->offset = GBIT64(p);
		p += BIT64SZ;
		f->count = GBIT32(p);
		p += BIT32SZ;
		if(p+f->count > ep)
			return 0;
		f->data = (char*)p;
		p += f->count;
		break;

	case Tclunk:
	case Tremove:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		break;

	case Tstat:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		break;

	case Twstat:
		if(p+BIT32SZ+BIT16SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->nstat = GBIT16(p);
		p += BIT16SZ;
		if(p+f->nstat > ep)
			return 0;
		f->stat = p;
		p += f->nstat;
		break;

/*
 */
	case Rversion:
		if(p+BIT32SZ > ep)
			return 0;
		f->msize = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->version);
		break;

	case Rerror:
		p = gstring(p, ep, &f->ename);
		break;

	case Rflush:
		break;

	case Rauth:
		p = gqid(p, ep, &f->aqid);
		if(p == nil)
			break;
		break;

	case Rattach:
		p = gqid(p, ep, &f->qid);
		if(p == nil)
			break;
		break;

	case Rwalk:
		if(p+BIT16SZ > ep)
			return 0;
		f->nwqid = GBIT16(p);
		p += BIT16SZ;
		if(f->nwqid > MAXWELEM)
			return 0;
		for(i=0; i<f->nwqid; i++){
			p = gqid(p, ep, &f->wqid[i]);
			if(p == nil)
				break;
		}
		break;

	case Ropen:
	case Rcreate:
		p = gqid(p, ep, &f->qid);
		if(p == nil)
			break;
		if(p+BIT32SZ > ep)
			return 0;
		f->iounit = GBIT32(p);
		p += BIT32SZ;
		break;

	case Rread:
		if(p+BIT32SZ > ep)
			return 0;
		f->count = GBIT32(p);
		p += BIT32SZ;
		if(p+f->count > ep)
			return 0;
		f->data = (char*)p;
		p += f->count;
		break;

	case Rwrite:
		if(p+BIT32SZ > ep)
			return 0;
		f->count = GBIT32(p);
		p += BIT32SZ;
		break;

	case Rclunk:
	case Rremove:
		break;

	case Rstat:
		if(p+BIT16SZ > ep)
			return 0;
		f->nstat = GBIT16(p);
		p += BIT16SZ;
		if(p+f->nstat > ep)
			return 0;
		f->stat = p;
		p += f->nstat;
		break;

	case Rwstat:
		break;
	}

	if(p==nil || p>ep)
		return 0;
	if(ap+size == p)
		return size;
	return 0;
}
コード例 #16
0
ファイル: convM2D.c プロジェクト: npe9/harvey
uint
_convM2D(uint8_t *buf, uint nbuf, Dir *d, char *strs)
{
	uint8_t *p, *ebuf;
	char *sv[4];
	int i, ns, nsv[4];

	p = buf;
	ebuf = buf + nbuf;

	p += BIT16SZ;	/* ignore size */
	d->type = GBIT16(p);
	p += BIT16SZ;
	d->dev = GBIT32(p);
	p += BIT32SZ;
	d->qid.type = GBIT8(p);
	p += BIT8SZ;
	d->qid.vers = GBIT32(p);
	p += BIT32SZ;
	d->qid.path = GBIT64(p);
	p += BIT64SZ;
	d->mode = GBIT32(p);
	p += BIT32SZ;
	d->atime = GBIT32(p);
	p += BIT32SZ;
	d->mtime = GBIT32(p);
	p += BIT32SZ;
	d->length = GBIT64(p);
	p += BIT64SZ;

	d->name = nil;
	d->uid = nil;
	d->gid = nil;
	d->muid = nil;

	for(i = 0; i < 4; i++){
		if(p + BIT16SZ > ebuf)
			return 0;
		ns = GBIT16(p);
		p += BIT16SZ;
		if(p + ns > ebuf)
			return 0;
		if(strs){
			nsv[i] = ns;
			sv[i] = strs;
			memmove(strs, p, ns);
			strs += ns;
			*strs++ = '\0';
		}
		p += ns;
	}

	if(strs){
		d->name = sv[0];
		d->uid = sv[1];
		d->gid = sv[2];
		d->muid = sv[3];
	}else{
		d->name = nullstring;
		d->uid = nullstring;
		d->gid = nullstring;
		d->muid = nullstring;
	}
	
	return p - buf;
}
コード例 #17
0
ファイル: convM2S.c プロジェクト: BackupTheBerlios/estyx-svn
u16 convM2S(u8 *ap, u16 nap, estyx_fcall_t *f)
{
	u8 *p, *ep;
	u16 i, size;

	p = ap;
	ep = p + nap;

	if(p+BIT32SZ+BIT8SZ+BIT16SZ > ep)
		return 0;
	size = GBIT32(p);
	p += BIT32SZ;

	if (size<BIT32SZ+BIT8SZ+BIT16SZ)
		return 0;

	f->type = GBIT8(p);
	p += BIT8SZ;
	f->tag = GBIT16(p);
	p += BIT16SZ;

	switch(f->type) {
	default:
		return 0;

	case Tversion:
		if(p+BIT32SZ > ep)
			return 0;
		f->u.version.msize = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->u.version.version);
		break;

	case Tflush:
		if(p+BIT16SZ > ep)
			return 0;
		f->u.oldtag = GBIT16(p);
		p += BIT16SZ;
		break;

	case Tauth:
		if(p+BIT32SZ > ep)
			return 0;
		f->u.attach.afid = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->u.attach.uname);
		if(p == nil)
			break;
		p = gstring(p, ep, &f->u.attach.aname);
		if(p == nil)
			break;
		break;

	case Tattach:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		if(p+BIT32SZ > ep)
			return 0;
		f->u.attach.afid = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->u.attach.uname);
		if(p == nil)
			break;
		p = gstring(p, ep, &f->u.attach.aname);
		if(p == nil)
			break;
		break;

	case Twalk:
		if(p+BIT32SZ+BIT32SZ+BIT16SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->u.twalk.newfid = GBIT32(p);
		p += BIT32SZ;
		f->u.twalk.nwname = GBIT16(p);
		p += BIT16SZ;
		if(f->u.twalk.nwname > MAXWELEM)
			return 0;
		for(i=0; i<f->u.twalk.nwname; i++){
			p = gstring(p, ep, &f->u.twalk.wname[i]);
			if(p == nil)
				break;
		}
		break;

	case Topen:
		if(p+BIT32SZ+BIT8SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->u.create.mode = GBIT8(p);
		p += BIT8SZ;
		break;

	case Tcreate:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->u.create.name);
		if(p == nil)
			break;
		if(p+BIT32SZ+BIT8SZ > ep)
			return 0;
		f->u.create.perm = GBIT32(p);
		p += BIT32SZ;
		f->u.create.mode = GBIT8(p);
		p += BIT8SZ;
		break;

	case Tread:
		if(p+BIT32SZ+BIT64SZ+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->u.rw.offset = GBIT32(p);
		p += BIT64SZ;
		f->u.rw.count = GBIT32(p);
		p += BIT32SZ;
		break;

	case Twrite:
		if(p+BIT32SZ+BIT64SZ+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->u.rw.offset = GBIT32(p);
		p += BIT64SZ;
		f->u.rw.count = GBIT32(p);
		p += BIT32SZ;
		if(p+f->u.rw.count > ep)
			return 0;
		f->u.rw.data = p;
		p += f->u.rw.count;
		break;

	case Tclunk:
	case Tremove:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		break;

	case Tstat:
		if(p+BIT32SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		break;

	case Twstat:
		if(p+BIT32SZ+BIT16SZ > ep)
			return 0;
		f->fid = GBIT32(p);
		p += BIT32SZ;
		f->u.stat.nstat = GBIT16(p);
		p += BIT16SZ;
		if(p+f->u.stat.nstat > ep)
			return 0;
		f->u.stat.stat = p;
		p += f->u.stat.nstat;
		break;
#if 0
// we never receive R packets so no need for this
/*
 */
	case Rversion:
		if(p+BIT32SZ > ep)
			return 0;
		f->u.version.msize = GBIT32(p);
		p += BIT32SZ;
		p = gstring(p, ep, &f->u.version.version);
		break;

	case Rerror:
		p = gstring(p, ep, &f->u.ename);
		break;

	case Rflush:
		break;

	case Rauth:
		p = gqid(p, ep, &f->u.aqid);
		if(p == nil)
			break;
		break;

	case Rattach:
		p = gqid(p, ep, &f->u.open.qid);
		if(p == nil)
			break;
		break;

	case Rwalk:
		if(p+BIT16SZ > ep)
			return 0;
		f->u.rwalk.nwqid = GBIT16(p);
		p += BIT16SZ;
		if(f->u.rwalk.nwqid > MAXWELEM)
			return 0;
		for(i=0; i<f->u.rwalk.nwqid; i++){
			p = gqid(p, ep, &f->u.rwalk.wqid[i]);
			if(p == nil)
				break;
		}
		break;

	case Ropen:
	case Rcreate:
		p = gqid(p, ep, &f->u.open.qid);
		if(p == nil)
			break;
		if(p+BIT32SZ > ep)
			return 0;
		f->u.open.iounit = GBIT32(p);
		p += BIT32SZ;
		break;

	case Rread:
		if(p+BIT32SZ > ep)			return 0;
		f->u.rw.count = GBIT32(p);
		p += BIT32SZ;
		if(p+f->u.rw.count > ep)
			return 0;
		f->u.rw.data = data;
		p += f->u.rw.count;
		break;

	case Rwrite:
		if(p+BIT32SZ > ep)
			return 0;
		f->u.rw.count = GBIT32(p);
		p += BIT32SZ;
		break;

	case Rclunk:
	case Rremove:
		break;

	case Rstat:
		if(p+BIT16SZ > ep)
			return 0;
		f->u.stat.nstat = GBIT16(p);
		p += BIT16SZ;
		if(p+f->u.stat.nstat > ep)
			return 0;
		f->u.stat.stat = p;
		p += f->u.stat.nstat;
		break;

	case Rwstat:
		break;
#endif
	}

	if(p==nil || p>ep)
		return 0;
	if(ap+size == p)
		return size;
	return 0;
}
コード例 #18
0
ファイル: convM2kdirent.c プロジェクト: 7perl/akaros
unsigned int convM2kdirent(uint8_t * buf, unsigned int nbuf, struct kdirent *kd,
						   char *strs)
{
	uint8_t *p, *ebuf;
	char *sv[4];
	int i, ns;
	uint32_t junk;
	printd("%s >>>>>>>>>nbuf %d STATFIXLEN %d\n", __func__, nbuf, STATFIXLEN);
	if (nbuf < STATFIXLEN)
		return 0;

	p = buf;
	ebuf = buf + nbuf;

	p += BIT16SZ;	/* ignore size */
	kd->d_type = GBIT16(p);
	p += BIT16SZ;
	junk = GBIT32(p);
	p += BIT32SZ;
	junk = GBIT8(p);
	p += BIT8SZ;
	junk = GBIT32(p);
	p += BIT32SZ;
	kd->d_ino = GBIT64(p);
	p += BIT64SZ;
	junk /* mode */  = GBIT32(p);
	p += BIT32SZ;
	junk /*d->atime */  = GBIT32(p);
	p += BIT32SZ;
	junk /*d->mtime */  = GBIT32(p);
	p += BIT32SZ;
	junk /*d->length */  = GBIT64(p);
	p += BIT64SZ;

	/* for now, uids in akaros are ints. Does not
	 * matter; kdirents are limited in what they tell you.
	 * get the name, ignore the rest. Maybe we can
	 * fix this later. 
	 */
	for (i = 0; i < 4; i++) {
		if (p + BIT16SZ > ebuf)
			return 0;
		ns = GBIT16(p);
		p += BIT16SZ;
		if (p + ns > ebuf)
			return 0;
		if (strs) {
			sv[i] = strs;
			memmove(strs, p, ns);
			strs += ns;
			*strs++ = '\0';
		}
		if (i == 0) {
			kd->d_reclen = ns;
			printd("memmove %p %p %d\n", kd->d_name, p, ns);
			memmove(kd->d_name, p, ns);
			kd->d_name[ns] = 0;
		}
		p += ns;
	}

	printd("%s returns %d %s\n", __func__, p - buf, kd->d_name);
	return p - buf;
}