这篇文章中先讲讲NFSv4中的READ。客户端发起READ请求时需要提供三个信息:一个stateid、数据在文件中的起始位置、请求的数据量。服务器会根据客户端提供的stateid查找到对应的文件,然后读取文件中的数据返回给客户端。客户端包含三种stateid:delegation stateid、lock stateid、open stateid。我们还没有讲到文件锁,因此假设文件没有加锁,先去掉lock stateid。OPEN操作过程中一定会返回一个open stateid,可能还会返回一个delegation stateid。
上一篇文章中我们提到了这样一种情况:用户user1以只读权限打开了文件file1,服务器返回了一个open stateid和一个delegation stateid。接着用户user2以只读权限打开文件file1,这种情况下不会向服务器发送OPEN请求,user2直接拷贝了user1中的delegation stateid。现在假设另一个客户端上的用户以只写权限打开了文件file1,这时会出现什么情况呢?这种情况下服务器向客户端发送RECALL请求,收回客户端中的delegation,我们会在后面的文章中讲解delegation的回收过程,这篇文章中我们想讨论这样一个问题:服务器回收delegation后,user1还可以通过open stateid发起READ请求,那么user2如何发起READ请求呢?由于user2打开文件时根本没有发起OPEN请求,因此根本没有open stateid。现在delegation stateid也被服务器回收了,user2怎么办?
事实上,客户端在返还delegation前会先向服务器发起OPEN请求,更新这个文件中关联的nfs4_state结构中的信息,这样user2就获取了新的open stateid,以后user2就可以使用这个open stateid继续发起READ请求了。但是这个OPEN请求的参数跟前面介绍的OPEN请求有所差别,这篇文章中我们就来讲解这种情况下OPEN操作的执行过程,处理函数如下:
参数ctx:保存了用户的信息
参数state:这是用户使用的nfs4_state结构,OPEN操作执行完毕后会更行这个结构中的信息
参数stateid:这是用户使用的delegation的stateid
static int _nfs4_open_delegation_recal(struct nfs_open_context *ctx, struct nfs4_state *state, const nfs4_stateid *