summaryrefslogtreecommitdiff
path: root/module/9p.m
blob: 8389aa6a9e5b86c1e9691091321c7f20af46357f (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
Ninep: module
{
	PATH:	con "/dis/lib/ninep.dis";

	VERSION:	con "9P2000";
	MAXWELEM:	con 16;

	NOTAG:	con 16rFFFF;
	NOFID:	con int ~0;	# 32 bits in this version of 9P

	BIT8SZ:	con 1;
	BIT16SZ:	con 2;
	BIT32SZ:	con 4;
	BIT64SZ:	con 8;
	QIDSZ:	con BIT8SZ+BIT32SZ+BIT64SZ;

	STATFIXLEN:	con BIT16SZ+QIDSZ+5*BIT16SZ+4*BIT32SZ+BIT64SZ;	# amount of fixed length data in a stat buffer
	IOHDRSZ:	con 24;	# room for Twrite/Rread header
	DEFIOUNIT: con 8192;	# `reasonable' iounit
	DEFMSIZE:	con IOHDRSZ+DEFIOUNIT;	# usable default for fversion and iounit

	Tversion,		# 100
	Rversion,
	Tauth,		# 102
	Rauth,
	Tattach,		# 104
	Rattach,
	Terror,		# 106, illegal
	Rerror,
	Tflush,		#108
	Rflush,
	Twalk,		# 110
	Rwalk,
	Topen,		# 112
	Ropen,
	Tcreate,		# 114
	Rcreate,
	Tread,		# 116
	Rread,
	Twrite,		# 118
	Rwrite,
	Tclunk,		# 120
	Rclunk,
	Tremove,		# 122
	Rremove,
	Tstat,		# 124
	Rstat,
	Twstat,		#126
	Rwstat,
	Tmax: con 100+iota;

	ERRMAX:	con 128;

	OREAD:	con 0; 		# open for read
	OWRITE:	con 1; 		# write
	ORDWR:	con 2; 		# read and write
	OEXEC:	con 3; 		# execute, == read but check execute permission
	OTRUNC:	con 16; 		# or'ed in (except for exec), truncate file first
	ORCLOSE: con 64; 		# or'ed in, remove on close

	# mode bits in Dir.mode used by the protocol
	DMDIR:		con int 1<<31;		# mode bit for directory
	DMAPPEND:	con int 1<<30;		# mode bit for append-only files
	DMEXCL:		con int 1<<29;		# mode bit for exclusive use files
	DMAUTH:		con int 1<<27;		# mode bit for authentication files

	# Qid.qtype
	QTDIR:	con 16r80;
	QTAPPEND:	con 16r40;
	QTEXCL:	con 16r20;
	QTAUTH:	con 16r08;
	QTFILE:	con 16r00;

	Tmsg: adt {
		tag: int;
		pick {
		Readerror =>
			error: string;		# tag is unused in this case
		Version =>
			msize: int;
			version: string;
		Auth =>
			afid: int;
			uname, aname: string;
		Attach =>
			fid, afid: int;
			uname, aname: string;
		Flush =>
			oldtag: int;
		Walk =>
			fid, newfid: int;
			names: array of string;
		Open =>
			fid, mode: int;
		Create =>
			fid: int;
			name: string;
			perm, mode: int;
		Read =>
			fid: int;
			offset: big;
			count: int;
		Write =>
			fid: int;
			offset: big;
			data: array of byte;
		Clunk or
		Stat or
		Remove => 
			fid: int;
		Wstat =>
			fid: int;
			stat: Sys->Dir;
		}

		read:	fn(fd: ref Sys->FD, msize: int): ref Tmsg;
		unpack:	fn(a: array of byte): (int, ref Tmsg);
		pack:	fn(nil: self ref Tmsg): array of byte;
		packedsize:	fn(nil: self ref Tmsg): int;
		text:	fn(nil: self ref Tmsg): string;
		mtype: fn(nil: self ref Tmsg): int;
	};

	Rmsg: adt {
		tag: int;
		pick {
		Readerror =>
			error: string;		# tag is unused in this case
		Version =>
			msize: int;
			version: string;
		Auth =>
			aqid: Sys->Qid;
		Attach =>
			qid: Sys->Qid;
		Flush =>
		Error =>
			ename: string;
		Clunk or
		Remove or
		Wstat =>
		Walk =>
			qids: array of Sys->Qid;
		Create or
		Open =>
			qid: Sys->Qid;
			iounit: int;
		Read =>
			data: array of byte;
		Write =>
			count: int;
		Stat =>
			stat: Sys->Dir;
		}

		read:	fn(fd: ref Sys->FD, msize: int): ref Rmsg;
		unpack:	fn(a: array of byte): (int, ref Rmsg);
		pack:	fn(nil: self ref Rmsg): array of byte;
		packedsize:	fn(nil: self ref Rmsg): int;
		text:	fn(nil: self ref Rmsg): string;
		mtype: fn(nil: self ref Rmsg): int;
		write: fn(nil: self ref Rmsg, fd: ref Sys->FD, msize: int): int;
	};

	init:	fn();

	readmsg:	fn(fd: ref Sys->FD, msize: int): (array of byte, string);
	istmsg:	fn(f: array of byte): int;

	compatible:	fn(t: ref Tmsg.Version, msize: int, version: string): (int, string);

	packdirsize:	fn(d: Sys->Dir): int;
	packdir:	fn(d: Sys->Dir): array of byte;
	unpackdir: fn(f: array of byte): (int, Sys->Dir);
	dir2text:	fn(d: Sys->Dir): string;
	qid2text:	fn(q: Sys->Qid): string;

	utflen:	fn(s: string): int;
};