Museum

Home

Lab Overview

Retrotechnology Articles

⇒ Online Manual

Media Vault

Software Library

Restoration Projects

Artifacts Sought

Related Articles

intro(2)

9p(2)

stat(2)

intro(5)

FCALL(2)

NAME

Fcall, convS2M, convD2M, convM2S, convM2D, fcallfmt, dirfmt, dirmodefmt, read9pmsg, statcheck, sizeS2M, sizeD2M − interface to Plan 9 File protocol

SYNOPSIS

­#include <u.h>
­#include <libc.h>
­#include <fcall.h>

uint convS2M(Fcall ∗f, uchar ∗ap, uint nap)

uint convD2M(Dir ∗d, uchar ∗ap, uint nap)

uint convM2S(uchar ∗ap, uint nap, Fcall ∗f)

uint convM2D(uchar ∗ap, uint nap, Dir ∗d, char ∗strs)

int dirfmt(Fmt∗)

int fcallfmt(Fmt∗)

int dirmodefmt(Fmt∗)

int read9pmsg(int fd, uchar ∗buf, uint nbuf)

int statcheck(uchar ∗buf, uint nbuf)

uint sizeS2M(Fcall ∗f)

uint sizeD2M(Dir ∗d)

DESCRIPTION

These routines convert messages in the machine-independent format of the Plan 9 file protocol, 9P, to and from a more convenient form, an ­Fcall structure:

#define MAXWELEM 16
 typedef
struct Fcall
{
uchartype;
u32intfid;
ushorttag;
union {
struct {
u32intmsize; /∗ Tversion, Rversion ∗/
char∗version;/∗ Tversion, Rversion ∗/
};
struct {
ushortoldtag; /∗ Tflush ∗/
};
struct {
char∗ename;/∗ Rerror ∗/
};
struct {
Qidqid;/∗ Rattach, Ropen, Rcreate ∗/
u32intiounit; /∗ Ropen, Rcreate ∗/
};
struct {
Qidaqid;/∗ Rauth ∗/
};
struct {
u32intafid; /∗ Tauth, Tattach ∗/
char∗uname;/∗ Tauth, Tattach ∗/
char∗aname;/∗ Tauth, Tattach ∗/
};
struct {
u32intperm; /∗ Tcreate ∗/
char∗name;/∗ Tcreate ∗/
ucharmode; /∗ Tcreate, Topen ∗/
};
struct {
u32intnewfid; /∗ Twalk ∗/
ushortnwname; /∗ Twalk ∗/
char∗wname[MAXWELEM];/∗ Twalk ∗/
};
struct {
ushortnwqid; /∗ Rwalk ∗/
Qidwqid[MAXWELEM];/∗ Rwalk ∗/
};
struct {
vlongoffset; /∗ Tread, Twrite ∗/
u32intcount; /∗ Tread, Twrite, Rread ∗/
char∗data;/∗ Twrite, Rread ∗/
};
struct {
ushortnstat; /∗ Twstat, Rstat ∗/
uchar∗stat; /∗ Twstat, Rstat ∗/
};
};
} Fcall;

 /∗ these are implemented as macros ∗/
 ucharGBIT8(uchar∗)
ushortGBIT16(uchar∗)
ulongGBIT32(uchar∗)
vlongGBIT64(uchar∗)
 voidPBIT8(uchar∗, uchar)
voidPBIT16(uchar∗, ushort)
voidPBIT32(uchar∗, ulong)
voidPBIT64(uchar∗, vlong)
 #defineBIT8SZ1
#defineBIT16SZ2
#defineBIT32SZ4
#defineBIT64SZ8

This structure is defined in <fcall.h>.  See section 5 for a full description of 9P messages and their encoding.  For all message types, the ­type field of an ­Fcall holds one of Tversion, Rversion, Tattach, Rattach, etc. (defined in an enumerated type in <fcall.h>).  ­Fid is used by most messages, and ­tag is used by all messages.  The other fields are used selectively by the message types given in comments. 

­ConvM2S takes a 9P message at ­ap of length nap, and uses it to fill in ­Fcall structure f. If the passed message including any data for ­Twrite and ­Rread messages is formatted properly, the return value is the number of bytes the message occupied in the buffer ap, which will always be less than or equal to nap; otherwise it is 0. For ­Twrite and ­Tread messages, ­data is set to a pointer into the argument message, not a copy. 

­ConvS2M does the reverse conversion, turning ­f into a message starting at ap. The length of the resulting message is returned. For ­Twrite and ­Rread messages, ­count bytes starting at ­data are copied into the message. 

The constant ­IOHDRSZ is a suitable amount of buffer to reserve for storing the 9P header; the data portion of a ­Twrite or ­Rread will be no more than the buffer size negotiated in the Tversion/Rversion exchange, minus IOHDRSZ. 

The routine ­sizeS2M returns the number of bytes required to store the machine-independent representation of the ­Fcall structure f, including its initial 32-bit size field. In other words, it reports the number of bytes produced by a successful call to convS2M.

Another structure is Dir, used by the routines described in stat(2). ­ConvM2D converts the machine-independent form starting at ­ap into d and returns the length of the machine-independent encoding.  The strings in the returned ­Dir structure are stored at successive locations starting at strs.  Usually ­strs will point to storage immediately after the ­Dir itself.  It can also be a ­nil pointer, in which case the string pointers in the returned ­Dir are all nil; however, the return value still includes their length. 

­ConvD2M does the reverse translation, also returning the length of the encoding.  If the buffer is too short, the return value will be ­BIT16SZ and the correct size will be returned in the first ­BIT16SZ bytes.  (If the buffer is less that BIT16SZ, the return value is zero; therefore a correct test for complete packing of the message is that the return value is greater than BIT16SZ).  The macro ­GBIT16 can be used to extract the correct value.  The related macros with different sizes retrieve the corresponding-sized quantities.  ­PBIT16 and its brethren place values in messages.  With the exception of handling short buffers in convD2M, these macros are not usually needed except by internal routines.

Analogous to sizeS2M, ­sizeD2M returns the number of bytes required to store the machine-independent representation of the ­Dir structure d, including its initial 16-bit size field.

The routine ­statcheck checks whether the ­nbuf bytes of ­buf contain a validly formatted machine-independent ­Dir entry suitable as an argument, for example, for the ­wstat (see stat(2)) system call. It checks that the sizes of all the elements of the the entry sum to exactly nbuf, which is a simple but effective test of validity. ­Nbuf and ­buf should include the second two-byte (16-bit) length field that precedes the entry when formatted in a 9P message (see stat(5)); in other words, ­nbuf is 2 plus the sum of the sizes of the entry itself.  ­Statcheck also verifies that the length field has the correct value (that is, nbuf-2).  It returns ­0 for a valid entry and ­-1 for an incorrectly formatted entry. 

Dirfmt, fcallfmt, and ­dirmodefmt are formatting routines, suitable for fmtinstall(2). They convert Dir∗, Fcall∗, and long values into string representations of the directory buffer, ­Fcall buffer, or file mode value.  ­Fcallfmt assumes that ­dirfmt has been installed with format letter ­D and ­dirmodefmt with format letter M. 

­Read9pmsg calls read(2) multiple times, if necessary, to read an entire 9P message into buf.  The return value is 0 for end of file, or -1 for error; it does not return partial messages. 

SOURCE

­/sys/src/libc/9sys

SEE ALSO

intro(2), 9p(2), stat(2), intro(5)

Plan 9  —  May 27, 2002

Typewritten Software • bear@typewritten.org • Edmonds, WA 98026