上一篇文章中我们讲解了NFS中文件句柄的作用以及组装过程,文件句柄由函数fh_compose()组装,这个函数的声明如下:
__be32 fh_compose(struct svc_fh *fhp, struct svc_export *exp, struct dentry *dentry, struct svc_fh *ref_fh)
fhp是输出参数,生成的文件句柄就保存在这个变量中了
exp是文件所在的文件系统
dentry是文件的目录项结构
ref_fh是创建文件句柄时使用的一个参考值,一般是父目录的文件句柄,这个值可以为NULL.
但是有一个问题没有说明白,就是这个函数中的参数是怎么设置的,谁赋的值呢?其实所有的文件句柄都是由根节点的文件句柄推导出来的,根节点的文件句柄是客户端获取的第一个文件句柄,客户端可以根据根节点的文件句柄发起READDIR调用获取第1层文件和子目录的文件句柄,然后根据子目录的文件句柄再次发起READDIR调用获取第2层文件和子目录的文件句柄。依次类推,可以获取文件系统中所有文件的文件句柄。
NFS中有两种获取根节点文件句柄的方式,NFSv2和NFSv3通过MOUNT协议获取根节点的文件句柄,NFSv4通过PUTROOTFH请求获取根节点的文件句柄,但是最终的处理过程是一样的,就是想办法设置fh_compose()中的参数,然后调用fh_compose()。
1.NFSv3中根节点文件句柄 组装过程
NFSv2和NFSv3通过MOUNT协议请求根节点的文件句柄,MOUNT协议的处理函数在nfs-uitls中,处理函数是mount_mnt_3_svc()。这个函数将客户端请求的路径与全局变量exportlist中保存的文件系统进行比较,将结果写入文件/proc/fs/nfsd/filehandle中。内核中的函数write_filehandle()解析filehandle文件中的内容,
2.N