V.0.2 If there are any questions or comments, please direct them to walt@erudition.net. The newest copy of this HowTo can always be retrieved from www.freebsd-howto.com. All rights for the reproduction of this document are reserved. Summary. This HowTo deals with the theory behind and configuration of NFS (Network FileSystem) on FreeBSD. 1. Background - What is NFS? 2. Deployment 2.1. Configuring NFS Server 2.1.1. portmap(8) 2.1.2. mountd(8) 2.1.3. nfsd(8), Reserved Ports, rpc.lockd(8) 2.1.4. exports(5) 2.2. NFS Clients, nfsiod(8) 2.3. Mount NFS exported Filesystems or Directories 3. Appendix 1. Background NFS, an acronym for 'Network FileSystem', is a method for distributing a filesystem across multiple hosts on a local or wide area network. Instead of other methods for exchaging files between hosts, such as ftp and scp, NFS allows one to treat moving files between multiple hosts as if the move was being made on a single filesystem. On Windows systems this is accomplished through Windows 'shares' (shared Windows partitions). Because of this, NFS allows for a very convenient method in manipulating files between multiple, trusted, hosts. Because of security considerations resulting from the NFS protocol, it is strongly recommended that NFS not be deployed across wide area networks, especially not between untrusted hosts or across untrusted network channels, such as the internet. For local area network purposes, NFS supplies a convenient and relatively safe method for file exchange between hosts using all of the convenience and power of regular shell commands such as mv(1) and cp(1). For a clearer understanding of what NFS is, let us take two example hosts: A and B. Host A will serve out one of its filesystems to host B so that host B will be able to view all files on the host A filesystem as if they were located locally on host B. The host that serves out the filesystem(s) is termed the "NFS Server", while the host accesses the served filesystem(s) is termed the "NFS Client." It is possible for a particular host to be both an NFS server and client; in our example, each host will only perform one of the actions. Our NFS server (host A) will serve out the filesystem mounted locally on its mount point /serve/data/. Our NFS client will mount this served out filesystem on its local mount point /nfs/A/data/. On the NFS client, when it runs 'ls /nfs/A/data/' the following output displays: data.1 data.2 data.3 INDEX To copy the data to one of its local filesystems, the command 'cp data.* /tmp/data' is issued in the directory /nfs/A/data/ on the NFS client, and the data files are copied from the NFS server's filesystem to a directory in the /tmp filesystem on the NFS client. If the command mv(1) were attempted instead of cp(1), then the following error would have shown: mv: Operation not permitted This is because when accessing NFS mounted filesystems, one does not operate with the same user ID as one does on the local host. The user ID with which NFS clients can access a served filesystem (hereafter known as an 'exported filesystem) is determined by the NFS server, thus restricting operations on the exported files according to the administrator's discretion. One can, although it is rarely recommended, allow access to NFS exported filesystems as root, or other high level user IDs, so that, in the case of the root user ID, NFS clients can perform operations on the NFS exported filesystem as if they were local root. Although, NFS is usually deployed by serving entire filesystems, a presumption dominating the previous discussion, directory structures not constituting an entire filesystem can be exported as well. This allows for an even greater amount of flexibility. 2. Deployment NFS can be deployed without too much difficulty. First, determine which hosts will be exporting filesystems/directories and with what permissions one wishes to export them (that is, as what user ID as discussed above). We will use the example filesystems used to illustrate NFS functionality from above. In our following discussion we are presuming that each of the hosts is on a local network and already configured for communication via TCP/IP across that network. 2.1. Configuring NFS Server. 2.1.1. portmap(8) The first task at hand is to configure the NFS server. Because NFS operates as an RPC service, it requires that portmap(8) be running on both the NFS server and client. RPC (Remote Procedure Call) services allow programs to make procedure calls across a network to other hosts. Portmap converts RPC program numbers into DARPA protocol port numbers, hence, it is vital for RPC service operation. By default the portmap daemon is set to start during bootup. If this had been disabled in /etc/rc.conf with the line 'portmap_enable="NO"' at some previous time, remove this line accordingly from both the NFS server and client hosts, and then start the portmap service by typing (remember, you must be root): (root@A)/># /usr/sbin/portmap Verify that the daemon is running: (root@A)/># ps aux | grep portmap daemon 105 0.0 0.3 884 496 ?? Is Thu07PM 0:00.01 /usr/sbin/portmap (root@A)/># 2.1.2. mountd(8) The mountd(8) daemon is vital for NFS operation. It services NFS mount requests of NFS exported filesystems by NFS clients. By default it is started during bootup if an /etc/exports file exists. On a clean FreeBSD installation the /etc/exports file does NOT exist, therefore, you will need to manually start the mountd(8) daemon, along with create an /etc/exports file, whose configuration will be explained later. to start the mountd(8) daemon, simply type: (root@A)/># /sbin/mountd -rl Verify that the daemon is running: (root@erudition)/># ps aux | grep mountd root 110 0.0 0.2 500 304 ?? Is Thu07PM 0:00.04 mountd -rl (root@A)/># The -r flag will allow the mounting of directories which are exported instead of the entire filesystem, and the -l flag will log NFS mount requests. 2.1.3. nfsd(8), Reserved Ports, rpc.lockd(8) Next, one must enable the NFS server daemon. Usually four instances of the server daemon are initiated. To make sure that the daemon instances are started during host bootup, enter the following lines into /etc/rc.conf: nfs_server_enable="YES" nfs_reserved_port_only="YES" rpc_lockd_enable="YES" The first line is self-explanatory. By default the NFS server daemon (nfsd) is started with four instances of itself. The second line allows NFS to only travel across a reserved port. Reserved ports are ports < 1024, which processes that are owned by regular system users can not bind to. This allows an extra element of security by preventing regular users from starting NFS clients and mounting NFS exported filesystems or directory structures. The last line enables file/record locking across NFS by starting the rpc.lockd(8) daemon. It is necessary for proper NFS functioning. Next, lest one wish to have to reboot to enable the above options, type the follow command at the prompt: (root@A)/># nfsd -n 4 (root@A)/># Verify that the NFS server daemons have been started: (root@A)/># ps x | grep nfsd 113 ?? Is 0:00.01 nfsd: master (nfsd) 115 ?? I 0:00.00 nfsd: server (nfsd) 116 ?? I 0:00.00 nfsd: server (nfsd) 117 ?? I 0:00.00 nfsd: server (nfsd) 118 ?? I 0:00.00 nfsd: server (nfsd) (root@A)/># Then, specify that NFS only be done over reserved ports: (root@A)/># sysctl -w vfs.nfs.nfs_privport=1 (root@A)/># 2.1.4. exports(5) Finally, we must configure the /etc/exports file to set up which filesystems and directory structures will be exported, and to which NFS clients we will allow that exportations along with their corresponding permissions. Open the /etc/exports file in your favourite text editor. The format of the entries is simple: Or alternatively, if one wishes to allow permission for an entire network easily: -network= -mask= The first column contains the filesystem or directory structure being exported. The second column contains the UIDs as which NFS clients will be able to read exported files, whether the exported mounts will be read/write or read-only, and some additional miscellaneous options which we will not concern ourselves with in this HowTo. The final column(s) contains a list of one or more hosts which will be allowed to NFS mount the exported filesystems or directories or the network and its mask that will be allowed to NFS mount the exported filesystems or directories. For instance, if we use our original example, one of our /etc/exports entries may look like this: /serv/data -maproot=nobody -ro B The filesystem that the NFS server will export is mounted on /serv/data, it will export it as read only (-ro) and such that when root processes on NFS client A accesses it, it will access it as user 'nobody' (UID 65534), and only host named 'B' will be able to NFS mount this filesystem. The most common permission options available are: -maproot=. This maps remote accesses to the NFS exported filesystem or directory with the specified user or UID, thus preventing root processes on NFS clients from being able to perform with root privileges on the NFS server. -mapall=. This maps all remote accesses to the NFS exported filesystem or directory with the specified user or UID, thus preventing any processes on NFS clients from being able to perform with the privileges of any users with the same UID on the NFS server; it allows for a very restricted control of what UIDs will be accessing the exported mounts. -ro. This only allows read-only access to the NFS exported filesystem or directory. Hosts which will be allowed to NFS mount the exported filesystem or directory can be specified by name or IP. Specification by IP is safer in case DNS information is spoofed thus inadvertently allowing exports to unintended hosts. Once the /etc/exports file is completed, a Hangup signal must be sent to the mountd(8) daemon so it will reread /etc/exports: (root@A)/># killall -HUP mountd (root@A)/># Your NFS server configuration is complete. 2.2. NFS Clients, nfsiod(8) Next, each NFS client must be configured. Portmap(8) is required on the NFS clients as well; the previous explanations about portmap(8) in the NFS server section apply wholly to NFS clients as well. Mountd(8) is not required on NFS client hosts unless they are also acting as NFS servers. NFS client daemons, however, are required. To ensure that the NFS client daemons start during bootup, enter the following lines into /etc/rc.conf: nfs_client_enable="YES" nfs_reserved_port_only="YES" Finally, lest you wish to reboot to have these options enabled, type the following on your NFS client host to start the NFS client daemon instances: (root@B)/># nfsiod -n 4 (root@B)/># Verify that the NFS client daemons have been started: (root@B)/># ps x | grep nfsiod 125 ?? I 0:00.00 nfsiod -n 4 126 ?? I 0:00.00 nfsiod -n 4 127 ?? I 0:00.00 nfsiod -n 4 128 ?? I 0:00.00 nfsiod -n 4 (root@B)/># And, finally, enable NFS over private ports with: (root@B)/># sysctl -w vfs.nfs.nfs_privport=1 (root@B)/># Your NFS client configuration is complete. 2.3. Mount NFS exported Filesystems or Directories Once the NFS server and client have been configured, we must mount the NFS exported filesystems or directories on the NFS client. Create the mount points at which you would like to mount the NFS exports, just as you would for regular, local, HD filesystems. In our original example we used the directory /nfs/A/data/ on which we mounted the NFS export. Continuing with this example, let us supposed we have the filesystem /serve/data/ on host A that we wish to mount on /nfs/A/data/. To accomplish this, we will use the mount(8) command at the NFS client command prompt (as root): (root@B)/># mount -t nfs A:/serve/data /nfs/A/data (root@B)/># To Verify that the mount took hold, we can simply use df(1). To simplify the mounting process, we can use /etc/fstab entries to both simplify the mounting syntax and allow NFS mounts to take hold during boot-time. An /etc/fstab entry for the above command would look like thus: A:/serve/data /nfs/A/data nfs rw 0 0 It is strongly recommended that the 'soft' option be used also: A:/serve/data /nfs/A/data nfs rw,soft 0 0 The 'soft' option allows bad NFS RPC requests to timeout, otherwise, the process that made the RPC request will hang and will NOT be able to be killed. Bad NFS RPC requests usually occur when the NFS server has shut down or is experiencing network conneectivity problems. In such cases, the RPC call from the NFS client will not succeed. Because NFS RPC requests can potentially, permanently hang the process that called made them, this is an ugly shortcoming of the NFS implementation. The 'soft' option allows for NFS RPC requests to timeout and thus avoid this shortcoming if the NFS server is unable to respond. Once the /etc/fstab entry is completed, the NFS mount will be done during boot up, and/or can be easily done at the command prompt with: (root@B)/># mount /nfs/A/data (root@B)/># If one does not wish to have the NFS export(s) mounted during bootup, but still have the /etc/fstab entry for the convenient manual mounting, then simply add the 'noauto' option in the /etc/fstab entry. 3. Appendix Manual Page Resources: 8 portmap 8 mountd 8 nfsd 8 rpc.lockd 5 exports 8 nfsiod 5 fstab 8 sysctl