filehande: 32 Bytes - inode number - file system ID - generation id: inc by 1 each time inode# is reused server creates fhandle; opaque to client Why Gen ID? - server gives client a fhandle with inode N - file N on server is deleted - a new file on server is created; os gives it inode N - client sends req to server with "old" version of N Problem: - fs ID, 32 bits: most likely few possible numbers (1, 2, 3,..) - gen id (32 bits): 1, 2, .. - inum (32 bits): thousands, max few million if client sent a "bad" fhadnle to server: get back an ESTALE - it was possible to easily guess fhandles and gain access to someone else's files. permission checking? - client encodes effective UID+GID of process into RPC msg - sends to server; server believed the client's credentials! - easy to fake your identity over NFS - one exception: root (UID 0) - maps uid 0 to uid -2 "nobody" - to protect against remote root exploits mount daemon authentication: - based on host IP addr, so easy to fake * more problems w/ v2 & v3: idempotency v2 was built on udp; v3 can use udp - implement reliability at RPC layer - simple timeout, retransmit, wait for response - abort after several retries Problem: 1. client sends msg (NFS_CREATE new file) 2. server gets msg, erxecutes successfully on local disk 3. server sends back reply 4. reply is lost 5. client never gets reply -- retransmits request 6. server receives request #2 to create file 7. server tries to create file, return err EEXIST Similar issues happen with delete file (REMOVE), RMDIR, etc. - non-repeatable optrations are called "idempotent" To solve, each RPC client includes a unique RPC identity per message, called the RPC "XID". - server is supposed to cache RPC XIDs (in RAM) per client (non-idempotent ops) - server also caches the original response sent to client (1st time) - if server sees repeated msg from same client w/ same XID, just return cached result. server needs heuristics to determine how long to keep cached entries * more problems w/ v2 & v3: open-unlink files Client Syscall Client NFS op Server Action -------------- ------------- ------------- unlink() NFS_REMOVE nfsd_remove, ext4_unlink -------------- ------------- ------------- open() NFS_LOOKUP nfsd_lookup, ext4_lookup NFS_GETATTR nfsd_getattr, ext4_getattr read() NFS_READ nfsd_read, ext4_read write() NFS_WRITE nfsd_write, ext4_write close() - - # problem: server has to open files on first read/write # server caches open files, and closes them periodically (timeout) -------------- ------------- ------------- open() NFS_LOOKUP nfsd_lookup, ext4_lookup NFS_GETATTR nfsd_getattr, ext4_getattr read() NFS_READ nfsd_read, ext4_read write() NFS_WRITE nfsd_write, ext4_write unlink() NFS_RENAME nfsd_rename, ext4_rename # client asks server to rename file F to new name (often .nfsXXXXXX) read() NFS_READ nfsd_read, ext4_read write() NFS_WRITE nfsd_write, ext4_write close() NFS_REMOVE nfsd_remove, ext4_unlink # client asks server to remove .nfsXXXXXX file