~ft/c9

8a2251728f02f436b3f841f59f2086a4ecbea135 — Sigrid Solveig Haflínudóttir 3 years ago 3c6d044
optional client/server compilation
2 files changed, 78 insertions(+), 60 deletions(-)

M c9.c
M c9.h
M c9.c => c9.c +68 -60
@@ 93,6 93,8 @@ r64(uint8_t **p)
	return r32(p) | (uint64_t)r32(p)<<32;
}

#ifndef C9_NO_CLIENT

static C9error
newtag(C9ctx *c, C9ttype type, C9tag *tag)
{


@@ 174,66 176,6 @@ T(C9ctx *c, uint32_t size, C9ttype type, C9tag *tag, C9error *err)
	return p;
}

static uint8_t *
R(C9ctx *c, uint32_t size, C9rtype type, C9tag tag, C9error *err)
{
	uint8_t *p = NULL;

	if(size > c->msize-4-1-2){
		c->error("R: invalid size");
		*err = C9Esize;
	}else{
		size += 4+1+2;
		if((p = c->begin(c, size)) == NULL){
			c->error("R: no buffer");
			*err = C9Ebuf;
		}else{
			*err = 0;
			w32(&p, size);
			w08(&p, type);
			w16(&p, tag);
		}
	}
	return p;
}

C9error
c9parsedir(C9ctx *c, C9stat *stat, uint8_t **t, uint32_t *size)
{
	uint8_t *b;
	uint32_t cnt, sz;

	if(*size < 49 || (sz = r16(t)) < 47 || *size < 2+sz)
		goto error;
	*size -= 2+sz;
	*t += 6; /* skip type(2) and dev(4) */
	stat->qid.type = r08(t);
	stat->qid.version = r32(t);
	stat->qid.path = r64(t);
	stat->mode = r32(t);
	stat->atime = r32(t);
	stat->mtime = r32(t);
	stat->size = r64(t);
	sz -= 39;
	if((cnt = r16(t)) > sz-2)
		goto error;
	stat->name = (char*)*t; b = *t = *t+cnt; sz -= 2+cnt;
	if(sz < 2 || (cnt = r16(t)) > sz-2)
		goto error;
	stat->uid = (char*)*t; *b = 0; b = *t = *t+cnt; sz -= 2+cnt;
	if(sz < 2 || (cnt = r16(t)) > sz-2)
		goto error;
	stat->gid = (char*)*t; *b = 0; b = *t = *t+cnt; sz -= 2+cnt;
	if(sz < 2 || (cnt = r16(t)) > sz-2)
		goto error;
	stat->muid = memmove(*t-1, *t, cnt); *b = stat->muid[cnt] = 0; *t = *t+cnt; sz -= 2+cnt;
	*t += sz;
	return 0;
error:
	c->error("c9parsedir: invalid size");
	return C9Epkt;
}

C9error
c9version(C9ctx *c, C9tag *tag, uint32_t msize)
{


@@ 647,6 589,70 @@ error:
	return C9Epkt;
}

#endif /* C9_NO_CLIENT */

C9error
c9parsedir(C9ctx *c, C9stat *stat, uint8_t **t, uint32_t *size)
{
	uint8_t *b;
	uint32_t cnt, sz;

	if(*size < 49 || (sz = r16(t)) < 47 || *size < 2+sz)
		goto error;
	*size -= 2+sz;
	*t += 6; /* skip type(2) and dev(4) */
	stat->qid.type = r08(t);
	stat->qid.version = r32(t);
	stat->qid.path = r64(t);
	stat->mode = r32(t);
	stat->atime = r32(t);
	stat->mtime = r32(t);
	stat->size = r64(t);
	sz -= 39;
	if((cnt = r16(t)) > sz-2)
		goto error;
	stat->name = (char*)*t; b = *t = *t+cnt; sz -= 2+cnt;
	if(sz < 2 || (cnt = r16(t)) > sz-2)
		goto error;
	stat->uid = (char*)*t; *b = 0; b = *t = *t+cnt; sz -= 2+cnt;
	if(sz < 2 || (cnt = r16(t)) > sz-2)
		goto error;
	stat->gid = (char*)*t; *b = 0; b = *t = *t+cnt; sz -= 2+cnt;
	if(sz < 2 || (cnt = r16(t)) > sz-2)
		goto error;
	stat->muid = memmove(*t-1, *t, cnt); *b = stat->muid[cnt] = 0; *t = *t+cnt; sz -= 2+cnt;
	*t += sz;
	return 0;
error:
	c->error("c9parsedir: invalid size");
	return C9Epkt;
}

#ifndef C9_NO_SERVER

static uint8_t *
R(C9ctx *c, uint32_t size, C9rtype type, C9tag tag, C9error *err)
{
	uint8_t *p = NULL;

	if(size > c->msize-4-1-2){
		c->error("R: invalid size");
		*err = C9Esize;
	}else{
		size += 4+1+2;
		if((p = c->begin(c, size)) == NULL){
			c->error("R: no buffer");
			*err = C9Ebuf;
		}else{
			*err = 0;
			w32(&p, size);
			w08(&p, type);
			w16(&p, tag);
		}
	}
	return p;
}

C9error
s9version(C9ctx *c)
{


@@ 1157,3 1163,5 @@ error:
	c->error("s9proc: invalid packet (type=%d)", t.type);
	return C9Epkt;
}

#endif /* C9_NO_SERVER */

M c9.h => c9.h +10 -0
@@ 297,8 297,10 @@ struct C9ctx

	/* private stuff */
	uint32_t msize;
#ifndef C9_NO_CLIENT
	uint32_t flush[C9maxflush];
	uint32_t tags[C9maxtags/C9tagsbits];
#endif
	union
	{
		C9tag lowfreetag;


@@ 309,6 311,8 @@ struct C9ctx
/* Parse one directory entry. */
extern C9error c9parsedir(C9ctx *c, C9stat *stat, uint8_t **data, uint32_t *size) __attribute__((nonnull(1, 2, 3)));

#ifndef C9_NO_CLIENT

extern C9error c9version(C9ctx *c, C9tag *tag, uint32_t msize) __attribute__((nonnull(1, 2)));
extern C9error c9auth(C9ctx *c, C9tag *tag, C9fid afid, const char *uname, const char *aname) __attribute__((nonnull(1, 2)));
extern C9error c9flush(C9ctx *c, C9tag *tag, C9tag oldtag) __attribute__((nonnull(1, 2)));


@@ 331,6 335,10 @@ extern C9error c9wstat(C9ctx *c, C9tag *tag, C9fid fid, const C9stat *s) __attri
 */
extern C9error c9proc(C9ctx *c) __attribute__((nonnull(1)));

#endif /* C9_NO_CLIENT */

#ifndef C9_NO_SERVER

extern C9error s9version(C9ctx *c) __attribute__((nonnull(1)));
extern C9error s9auth(C9ctx *c, C9tag tag, const C9qid *aqid) __attribute__((nonnull(1, 3)));
extern C9error s9error(C9ctx *c, C9tag tag, const char *err) __attribute__((nonnull(1)));


@@ 348,3 356,5 @@ extern C9error s9stat(C9ctx *c, C9tag tag, const C9stat *s) __attribute__((nonnu
extern C9error s9wstat(C9ctx *c, C9tag tag) __attribute__((nonnull(1)));

extern C9error s9proc(C9ctx *c) __attribute__((nonnull(1)));

#endif /* C9_NO_SERVER */