Coda File System

NFS -> Coda translator.

From: Peter J. Braam <braam_at_cs.cmu.edu>
Date: Mon, 9 Feb 1998 19:16:10 -0500 (EST)
Hi Wendy, Eric, Joshua,

Portability of Coda to other Unix systems requires access to kernel
code or the ability to build a file system kernel module.  It is 
possible to dramatically improve the portability -- at least as a 
first shot at it -- by modifying a user level NFS server to provide
a mountable file system on one end, and speak to the Coda cache 
manager running on the same machine on the other.

This would replace 
   Coda kernel module + Coda cache manager (Venus) 
with
   NFS kernel module + user level NFS Server + Coda cache manager (Venus)
all running on the same machine.  

Coda could then be ported to all Unix systems without writing kernel
code. 

To get you started here are some first steps.  The target will be to
modify a user level nfs server in such a way that it can talk to Venus and
arrange file service.  There are many challenges but our first aim is to
arrange that we have all the tools in place. 

You will need to understand something about the Coda Kernel <-> Venus
protocol and this is documented halfway reasonably.   You can find that
document in 

ftp:lesbos.odyssey.cs.cmu.edu//pub/yale/ck.ps.gz

You should also find the coda-4.3.13.tgz tarball on ftp.coda.cs.cmu.edu.
Unpack that on a Linux machine and type "./configure ; make coda". You may
have to type "make oldconfig ; make dep " in the kernel source tree on
that machine first.  If that stuff builds, then cd into utils-src and do
"make coda".  If all goes well you end up with a program called "potemkin"
in utils-src/potemkin/potemkin.   This is the fake Venus which you are
going to work with and minimally modify.  (DON"T be tempted to change this
a lot, just put the socket in, nothing else!). 

Install the RedHat packages for your kernel (we have them for RedHat 4.2
and 5.0 prebuilt):
coda-debug-kernel-2.0.30-module-4.3.13-3.i386.rpm
coda-debug-kernel-2.0.32-module-4.3.13-3.i386.rpm
Then do:
 insmod coda
 potemkin -rd /tmp -v 

This will mount /tmp on /coda and you have a baby version of Coda working
on your machine.  It is really important to get this all working. You will
see the requests that are made by the kernel to potemkin at every stage.
You should also look through the source of potemkin.

Next you need to learn a bit about NFS.  The three places I would use are:
sources for the rpc.mountd and rpc.nfsd package:
   nfs-server-2.2beta16-7.src.rpm
   The Linux kernel code in /usr/src/linux/fs/nfs
   the book: Unix Internals (author Uresh Vahalia).  pp. 301 -- 306.  
Send me a fax or mail address and I can send you a copy of these pages.

>From here our next target is to get mount to work.  Mount will probably
involve a getrootvol and getattr operation being sent to Venus (or
better potemkin Venus). 

We will mount coda with something like
mount -t nfs hostname:/nfscoda /coda

The mount request will go from the NFS kernel code and  reach the
rpc.mountd which will consult
/etc/exports
If it finds the export is permitted there it will return an NFS file
handle to the nfs client code in the kernel for the root /coda of the 
mount.  Here is where our fun starts.

For simplicity let's assume that we simply stuff the ViceFid into the file
handle (that's 12 bytes out of 32 available ones). A ViceFid identifies a
Coda file uniquely.

rpc.mountd should get the file handle from potemkin and NOT from the local
filesystem.  You can see this happening in the nfs-server code, mountd.c
where the routine which is relevant is mountproc_mnt_1.  Just before the
routine returns it calls fh_create.  It passes the pathname (in our case
/nfscoda) and the resulting res->fhstatus_u.fhs_fhandle will contain the
file handle.  (it would be really neat for you guys to build an nfs server
with debugging symbols, run gdb from emacs, run the rpc.mountd program
with the -d flag, so that it doesn't fork, and break on these two routines
while you try a mount).  Then look at what happens. 

What you would do in fh_create is to make some "upcalls" probably over a
UDP socket to potemkin..  The upcall would be like the one described in
the document we wrote.  It would essentially do:

venus_getrootvol(&fid);
memcpy(fh, &fid, sizeof(fid));
return success; 

and potemkin will return the fid of the root of Coda.  We could then
simply stuff that fid into the fh and return.  You find such code in the
Coda kernel module coda/kernel-src/vfs/linux21/upcall.c and super.c

The next thing that will happen is that NFS kernel code will come back to
rpc.nfsd and ask it for the inode number of the file handle we have just
received from rpc.mountd.  You can find the detail by exploring the code
in linux/fs/nfs/*c where nfs_read_super (or something like that)  is
called .  I'll let you find out what the rpc.nfsd code is doing here, but
at the end of the day it boils down to doing a venus_getattr upcall to
potemkin (over UDP) with the arguments

venus_getattr(&attrs, fh_to_fid(rootfh));

Now attr contains the inode number of /coda and we have an inode. 

One of the things you should arrange quite early on is that rpc.mountd and
rpc.nfsd talk to potemkin over a UDP socket with potemkin.  This is very
similar to the kernel/venus communication in Coda over /dev/cfs0. 

So potemkin will create a socket and wait for packets. Rpc.mountd and nfsd
will be linked with a file upcall.c very similar to the kernel file
upcall.c and write the upcall packets into the other end of this socket
after they were prepared in upcall.c as they are in the kernel.

I think this will give you quite a lot to absorb to get going, and when
this works it should be possible to mount Coda -- well potemkin Coda and
do "ls -l /coda" which should show the attributes of the directory given
in the -rd parameter to potemkin. 

We will deal with the remainder afterwards (there is quite a lot more to
say).

- Peter -
Received on 1998-02-09 19:19:16