9p man page on Plan9

Man page or keyword search:  
man Server   549 pages
apropos Keyword Search (all sections)
Output format
Plan9 logo
[printable version]

9P(2)									 9P(2)

       Srv,  dirread9p,	 emalloc9p,  erealloc9p, estrdup9p, listensrv, postfd,
       postmountsrv, readbuf, readstr, respond, responderror, threadlistensrv,
       threadpostmountsrv, srv - 9P file service

       #include <u.h>
       #include <libc.h>
       #include <fcall.h>
       #include <thread.h>
       #include <9p.h>

       typedef struct Srv {
	   Tree* tree;

	   void	 (*attach)(Req *r);
	   void	 (*auth)(Req *r);
	   void	 (*open)(Req *r);
	   void	 (*create)(Req *r);
	   void	 (*read)(Req *r);
	   void	 (*write)(Req *r);
	   void	 (*remove)(Req *r);
	   void	 (*flush)(Req *r);
	   void	 (*stat)(Req *r);
	   void	 (*wstat)(Req *r);
	   void	 (*walk)(Req *r);

	   char* (*walk1)(Fid *fid, char *name, Qid *qid);
	   char* (*clone)(Fid *oldfid, Fid *newfid);

	   void	 (*destroyfid)(Fid *fid);
	   void	 (*destroyreq)(Req *r);
	   void	 (*end)(Srv *s);
	   void* aux;

	   int	 infd;
	   int	 outfd;
	   int	 srvfd;
	   int	 nopipe;
       } Srv;

       int   srv(Srv *s)
       void  postmountsrv(Srv *s, char *name, char *mtpt, int flag)
       void  threadpostmountsrv(Srv *s, char *name, char *mtpt, int flag)
       void  listensrv(Srv *s, char *addr)
       void  threadlistensrv(Srv *s, char *addr)
       int   postfd(char *srvname, int fd)
       void  respond(Req *r, char *error)
       void  responderror(Req*)
       void  readstr(Req *r, char *src)
       void  readbuf(Req *r, void *src, long nsrc)
       typedef int Dirgen(int n, Dir *dir, void *aux)
       void  dirread9p(Req *r, Dirgen *gen, void *aux)
       void  walkandclone(Req *r, char *(*walk1)(Fid *old, char *name, void *v),
		 char *(*clone)(Fid *old, Fid *new, void *v), void *v)

       void* emalloc9p(ulong n)
       void* erealloc9p(void *v, ulong n)
       char* estrdup9p(char *s)

       extern int chatty9p;

       The  function srv serves a 9P session by reading requests from s->infd,
       dispatching them to the function pointers kept in Srv, and writing  the
       responses  to s->outfd.	(Typically, postmountsrv or threadpostmountsrv
       initializes the infd and outfd structure members.  See the  description

       Req  and	 Fid  structures  are  allocated  one-to-one  with uncompleted
       requests and active fids, and are described in 9pfid(2).

       The behavior of srv depends on  whether	there  is  a  file  tree  (see
       9pfile(2))  associated  with the server, that is, whether the tree ele‐
       ment is nonzero.	 The differences are made explicit in  the  discussion
       of the service loop below.  The aux element is the client's, to do with
       as it pleases.

       Srv does not return until the 9P conversation is finished.  Since it is
       usually run in a separate process so that the caller can exit, the ser‐
       vice loop has little chance to  return  gracefully  on  out  of	memory
       errors.	 It  calls  emalloc9p, erealloc9p, and estrdup9p to obtain its
       memory.	The default implementations of these functions act as  malloc,
       realloc,	 and  strdup  but abort the program if they run out of memory.
       If alternate behavior is desired, clients can  link  against  alternate
       implementations of these functions.

       Postmountsrv and threadpostmountsrv are wrappers that create a separate
       process in which to run srv.  They do the following:

	      If s->nopipe is zero (the common case), initialize  s->infd  and
	      s->outfd	to  be	one  end  of  a	 freshly  allocated pipe, with
	      s->srvfd initialized as the other end.

	      If name is non-nil, call postfd(s->srvfd, name) to post s->srvfd
	      as /srv/name.

	      Fork  a  child process via rfork (see fork(2)) or procrfork (see
	      thread(2)), using the RFFDG,  RFNAMEG,  and  RFMEM  flags.   The
	      child  process  calls  close(s->srvfd)  and then srv(s); it will
	      exit once srv returns.

	      If mtpt is non-nil, call amount(s->srvfd, mtpt, flag, "");  oth‐
	      erwise, close s->srvfd.

	      The parent returns to the caller.

       If  any	error occurs during this process, the entire process is termi‐
       nated by calling sysfatal (see perror(2)).

       Listensrv and threadlistensrv create a separate process to announce  as
       addr.   The  process  listens  for incoming connections, creating a new
       process to serve each.  Using these functions results in	 srv  and  the
       service	functions being run in multiple processes simultaneously.  The
       library locks its own data structures as necessary; the client may need
       to lock data it shares between the multiple connections.

   Service functions
       The functions in a Srv structure named after 9P transactions are called
       to satisfy requests as they arrive.  If a function is provided, it must
       arrange	for  respond  to be called when the request is satisfied.  The
       only parameter of each service function is a Req*  parameter  (say  r).
       The  incoming  request  parameters  are stored in r->ifcall; r->fid and
       r->newfid are pointers to Fid structures corresponding to  the  numeric
       fids  in	 r->ifcall;  similarly,	 r->oldreq is the Req structure corre‐
       sponding to r->ifcall.oldtag.  The outgoing  response  data  should  be
       stored  in  r->ofcall.	The  one  exception  to this rule is that stat
       should fill in r->d rather than r->ofcall.stat: the library  will  con‐
       vert  the  structure  into the machine-independent wire representation.
       Similarly, wstat may consult r->d rather than  decoding	r->ifcall.stat
       itself.	When a request has been handled, respond should be called with
       r and an error string.  If the request was satisfied successfully,  the
       error  string should be a nil pointer.  Note that it is permissible for
       a function to return without itself calling respond, as long as it  has
       arranged	 for  respond  to  be  called  at  some point in the future by
       another proc sharing its address space, but see the discussion of flush
       below.	Once respond has been called, the Req* as well as any pointers
       it once contained must be considered freed and not referenced.

       Responderror  calls  respond  with  the	system	 error	 string	  (see

       If  the service loop detects an error in a request (e.g., an attempt to
       reuse an extant fid, an open of an already open fid, a read from a  fid
       opened for write, etc.)	it will reply with an error without consulting
       the service functions.

       The service loop provided by srv (and indirectly	 by  postmountsrv  and
       threadpostmountsrv)  is	single-threaded.   If it is expected that some
       requests might block, arranging for alternate processes to handle  them
       is suggested.

       The  constraints	 on  the service functions are as follows.  These con‐
       straints are checked while the server executes.	If a service  function
       fails  to  do something it ought to have, srv will call endsrv and then

       Auth   If authentication is desired, the auth  function	should	record
	      that  r->afid is the new authentication fid and set r->afid->qid
	      and ofcall.qid.  Auth may be nil,	 in  which  case  it  will  be
	      treated  as having responded with the error ``argv0: authentica‐
	      tion not required,'' where argv0 is the program name variable as
	      set by ARGBEGIN (see arg(2)).

       Attach The  attach  function  should  check the authentication state of
	      afid if desired, and set r->fid->qid and ofcall.qid to  the  qid
	      of  the  file system root.  Attach may be nil only if file trees
	      are in use; in this case, the qid will be filled from  the  root
	      of the tree, and no authentication will be done.

       Walk   If  file	trees  are  in	use,  walk  is handled internally, and
	      srv->walk is never called.

	      If  file	trees  are   not   in	use,   walk   should   consult
	      r->ifcall.wname  and r->ifcall.nwname, filling in ofcall.qid and
	      ofcall.nqid, and also  copying  any  necessary  aux  state  from
	      r->fid to r->newfid when the two are different.  As long as walk
	      sets ofcall.nqid appropriately, it can respond with a nil	 error
	      string  even  when  9P  demands an error (e.g., in the case of a
	      short walk); the library detects error  conditions  and  handles
	      them appropriately.

	      Because  implementing  the  full	walk  message is intricate and
	      prone to error, the helper routine walkandclone will handle  the
	      request  given  pointers to two functions walk1 and (optionally)
	      clone .  Clone, if non-nil, is called to signal the creation  of
	      newfid  from  oldfid.   Typically	 a  clone routine will copy or
	      increment a reference count  in  oldfid's	 aux  element.	 Walk1
	      should walk fid to name, initializing fid->qid to the new path's
	      qid.  Both should return nil on success or an error  message  on
	      error.   Walkandclone  will  call	 respond  after	 handling  the

       Walk1, Clone
	      If the client provides  functions	 srv->walk1  and  (optionally)
	      srv->clone,  the	9P  service  loop  will call walkandclone with
	      these functions to handle the request.  Unlike the walk1	above,
	      srv->walk1  must fill in both fid->qid and *qid with the new qid
	      on a successful walk.

       Open   If file trees are in use, the file metadata will be consulted on
	      open,  create, remove, and wstat to see if the requester has the
	      appropriate permissions.	If not, an error  will	be  sent  back
	      without consulting a service function.

	      If  not using file trees or the user has the appropriate permis‐
	      sions, open is called with r->ofcall.qid already initialized  to
	      the  one	stored in the Fid structure (that is, the one returned
	      in the previous walk).  If  the  qid  changes,  both  should  be

       Create The   create   function	must  fill  in	both  r->fid->qid  and
	      r->ofcall.qid on success.	 When using file trees, create	should
	      allocate	a  new	File with createfile; note that createfile may
	      return nil (because, say, the file already exists).  If the cre‐
	      ate  function  is	 nil, srv behaves as though it were a function
	      that always responded with the error ``create prohibited''.

       Remove Remove should mark the  file  as	removed,  whether  by  calling
	      removefile  when	using  file  trees, or by updating an internal
	      data structure.  In general it is not a good idea	 to  clean  up
	      the  aux	information  associated with the corresponding File at
	      this time, to avoid memory errors if other fids have  references
	      to  that file.  Instead, it is suggested that remove simply mark
	      the file as removed (so that further operations on  it  know  to
	      fail)  and wait until the file tree's destroy function is called
	      to reclaim the aux pointer.  If not using file trees, it is pru‐
	      dent to take the analogous measures.  If remove is not provided,
	      all remove requests will draw ``remove prohibited'' errors.

       Read   The read function must be provided; it fills r->ofcall.data with
	      at most r->ifcall.count bytes of data from offset r->ifcall.off‐
	      set of the file.	It also sets r->ofcall.count to the number  of
	      bytes  being  returned.	If  using  file trees, srv will handle
	      reads of directories internally, only calling read for  requests
	      on  files.   Readstr  and readbuf are useful for satisfying read
	      requests on a string  or	buffer.	  Consulting  the  request  in
	      r->ifcall,  they	fill  r->ofcall.data  and set r->ofcall.count;
	      they do not call respond.	 Similarly, dirread9p can be  used  to
	      handle  directory	 reads	in  servers not using file trees.  The
	      passed gen function will be called as necessary to fill dir with
	      information  for	the  nth  entry	 in the directory.  The string
	      pointers	placed	in  dir	 should	 be  fresh  copies  made  with
	      estrdup9p; they will be freed by dirread9p after each successful
	      call to gen.  Gen should return zero if it  successfully	filled
	      dir, minus one on end of directory.

       Write  The  write  function is similar but need not be provided.	 If it
	      is not, all writes will draw ``write prohibited'' errors.	  Oth‐
	      erwise,  write should attempt to write the r->ifcall.count bytes
	      of r->ifcall.data to offset r->ifcall.offset of the  file,  set‐
	      ting  r->ofcall.count  to	 the number of bytes actually written.
	      Most programs consider it	 an  error  to	write  less  than  the
	      requested amount.

       Stat   Stat  should fill r->d with the stat information for r->fid.  If
	      using file trees, r->d will have been initialized with the  stat
	      info from the tree, and stat itself may be nil.

       Wstat  The  wstat  consults r->d in changing the metadata for r->fid as
	      described in stat(5).  When using file trees, srv will take care
	      to  check that the request satisfies the permissions outlined in
	      stat(5).	Otherwise wstat should take care  to  enforce  permis‐
	      sions where appropriate.

       Flush  Servers  that always call respond before returning from the ser‐
	      vice functions need not provide a flush implementation: flush is
	      only necessary in programs that arrange for respond to be called
	      asynchronously.  Flush should cause the request r->oldreq to  be
	      cancelled or hurried along.  If oldreq is cancelled, this should
	      be signalled by calling respond  on  oldreq  with	 error	string
	      `interrupted'.  Flush must respond to r with a nil error string.
	      Flush may respond to r before forcing a response	to  r->oldreq.
	      In  this case, the library will delay sending the Rflush message
	      until the response to r->oldreq has been sent.

       Destroyfid, destroyreq, and end are auxiliary functions, not called  in
       direct response to 9P requests.

	      When  a  Fid's  reference count drops to zero (i.e., it has been
	      clunked and there are no outstanding requests referring to  it),
	      destroyfid  is  called  to  allow	 the program to dispose of the
	      fid->aux pointer.

	      Similarly, when a Req's reference count drops to zero (i.e.,  it
	      has  been	 handled via respond and other outstanding pointers to
	      it have been closed), destroyreq is called to allow the  program
	      to dispose of the r->aux pointer.

       End    Once  the 9P service loop has finished (end of file been reached
	      on the service pipe or a bad message  has	 been  read),  end  is
	      called  (if  provided) to allow any final cleanup.  For example,
	      it was used by the Palm Pilot synchronization file system (never
	      finished)	 to  gracefully terminate the serial conversation once
	      the file system had been unmounted.  After calling end, the ser‐
	      vice  loop  (which  runs	in a separate process from its caller)
	      terminates using _exits (see exits(2)).

       If the chatty9p flag is at least one, a transcript of the 9P session is
       printed	on  standard error.  If the chatty9p flag is greater than one,
       additional unspecified debugging output is generated.   By  convention,
       servers	written	 using	this library accept the -D option to increment

       Archfs(4), cdfs(4), nntpfs(4), snap(4), and /sys/src/lib9p/ramfs.c  are
       good  examples  of  simple  single-threaded file servers.  Webfs(4) and
       sshnet (see ssh(1)) are good examples of multithreaded file servers.

       In general, the File interface is appropriate for maintaining arbitrary
       file  trees (as in ramfs).  The File interface is best avoided when the
       tree structure is easily generated as necessary; this is true when  the
       tree  is	 highly	 structured  (as  in cdfs and nntpfs) or is maintained


       9pfid(2), 9pfile(2), srv(3), intro(5)

       The switch to 9P2000 was taken as an opportunity to tidy	 much  of  the
       interface; we promise to avoid such gratuitous change in the future.

                             _         _         _ 
                            | |       | |       | |     
                            | |       | |       | |     
                         __ | | __ __ | | __ __ | | __  
                         \ \| |/ / \ \| |/ / \ \| |/ /  
                          \ \ / /   \ \ / /   \ \ / /   
                           \   /     \   /     \   /    
                            \_/       \_/       \_/ 
More information is available in HTML format for server Plan9

List of man pages available for Plan9

Copyright (c) for man pages and the logo by the respective OS vendor.

For those who want to learn more, the polarhome community provides shell access and support.

[legal] [privacy] [GNU] [policy] [cookies] [netiquette] [sponsors] [FAQ]
Polarhome, production since 1999.
Member of Polarhome portal.
Based on Fawad Halim's script.
Vote for polarhome
Free Shell Accounts :: the biggest list on the net