mirror of
https://review.haiku-os.org/haiku
synced 2025-02-07 06:16:11 +01:00
nfs4: Add per server NFS4 objects
RPC::Server is now able to store RPC programs data. NFS4Server objects are currently used mainly for managing client id.
This commit is contained in:
parent
96e3dbc2d0
commit
6ee3ed0f6f
@ -11,7 +11,7 @@
|
||||
|
||||
#include "InodeIdMap.h"
|
||||
#include "NFS4Defs.h"
|
||||
#include "RPCServer.h"
|
||||
#include "NFS4Server.h"
|
||||
|
||||
|
||||
class Inode;
|
||||
@ -27,7 +27,10 @@ public:
|
||||
Inode* CreateRootInode();
|
||||
|
||||
inline uint32 FHExpiryType() const;
|
||||
|
||||
inline RPC::Server* Server();
|
||||
inline NFS4Server* NFSServer();
|
||||
|
||||
inline uint64 AllocFileId();
|
||||
|
||||
inline dev_t DevId() const;
|
||||
@ -55,6 +58,13 @@ Filesystem::Server()
|
||||
}
|
||||
|
||||
|
||||
inline NFS4Server*
|
||||
Filesystem::NFSServer()
|
||||
{
|
||||
return reinterpret_cast<NFS4Server*>(fServer->PrivateData());
|
||||
}
|
||||
|
||||
|
||||
inline uint64
|
||||
Filesystem::AllocFileId()
|
||||
{
|
||||
|
@ -83,9 +83,6 @@ Inode::~Inode()
|
||||
}
|
||||
|
||||
|
||||
// filesystems that do not provide fileid are currently unsupported
|
||||
// client will have to be able to create its own mapping between file names
|
||||
// and made up IDs
|
||||
status_t
|
||||
Inode::LookUp(const char* name, ino_t* id)
|
||||
{
|
||||
@ -309,39 +306,16 @@ Inode::Stat(struct stat* st)
|
||||
status_t
|
||||
Inode::Open(int mode, OpenFileCookie* cookie)
|
||||
{
|
||||
cookie->fSeq = 0;
|
||||
cookie->fClientId = fFilesystem->NFSServer()->ClientId();
|
||||
|
||||
Request request(fFilesystem->Server());
|
||||
request.Builder().SetClientID(fFilesystem->Server());
|
||||
|
||||
status_t result = request.Send();
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
uint64 id, ver;
|
||||
result = request.Reply().SetClientID(&id, &ver);
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
request.Reset();
|
||||
request.Builder().SetClientIDConfirm(id, ver);
|
||||
|
||||
result = request.Send();
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
result = request.Reply().SetClientIDConfirm();
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
request.Reset();
|
||||
RequestBuilder& req = request.Builder();
|
||||
|
||||
req.PutFH(fParentFH);
|
||||
req.Open(cookie->fSeq, OPEN4_SHARE_ACCESS_READ, id, OPEN4_NOCREATE, fName);
|
||||
cookie->fSeq++;
|
||||
req.Open(fFilesystem->NFSServer()->SequenceId(), OPEN4_SHARE_ACCESS_READ,
|
||||
cookie->fClientId, OPEN4_NOCREATE, fName);
|
||||
|
||||
result = request.Send();
|
||||
status_t result = request.Send();
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
@ -359,8 +333,8 @@ Inode::Open(int mode, OpenFileCookie* cookie)
|
||||
if (confirm) {
|
||||
request.Reset();
|
||||
req.PutFH(fHandle);
|
||||
req.OpenConfirm(cookie->fSeq, cookie->fStateId, cookie->fStateSeq);
|
||||
cookie->fSeq++;
|
||||
req.OpenConfirm(fFilesystem->NFSServer()->SequenceId(),
|
||||
cookie->fStateId, cookie->fStateSeq);
|
||||
|
||||
result = request.Send();
|
||||
if (result != B_OK)
|
||||
@ -386,7 +360,8 @@ Inode::Close(OpenFileCookie* cookie)
|
||||
RequestBuilder& req = request.Builder();
|
||||
|
||||
req.PutFH(fHandle);
|
||||
req.Close(cookie->fSeq, cookie->fStateId, cookie->fStateSeq);
|
||||
req.Close(fFilesystem->NFSServer()->SequenceId(), cookie->fStateId,
|
||||
cookie->fStateSeq);
|
||||
|
||||
status_t result = request.Send();
|
||||
if (result != B_OK)
|
||||
@ -402,6 +377,8 @@ Inode::Close(OpenFileCookie* cookie)
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
fFilesystem->NFSServer()->ReleaseCID(cookie->fClientId);
|
||||
|
||||
return B_OK;
|
||||
}
|
||||
|
||||
|
@ -19,9 +19,9 @@
|
||||
|
||||
|
||||
struct OpenFileCookie {
|
||||
uint64 fClientId;
|
||||
uint32 fStateId[3];
|
||||
uint32 fStateSeq;
|
||||
uint32 fSeq;
|
||||
};
|
||||
|
||||
class Inode {
|
||||
|
@ -7,6 +7,7 @@ KernelAddon nfs4 :
|
||||
Filesystem.cpp
|
||||
Inode.cpp
|
||||
kernel_interface.cpp
|
||||
NFS4Server.cpp
|
||||
ReplyInterpreter.cpp
|
||||
Request.cpp
|
||||
RequestBuilder.cpp
|
||||
|
74
src/add-ons/kernel/file_systems/nfs4/NFS4Server.cpp
Normal file
74
src/add-ons/kernel/file_systems/nfs4/NFS4Server.cpp
Normal file
@ -0,0 +1,74 @@
|
||||
/*
|
||||
* Copyright 2012 Haiku, Inc. All rights reserved.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Authors:
|
||||
* Paweł Dziepak, pdziepak@quarnos.org
|
||||
*/
|
||||
|
||||
|
||||
#include "NFS4Server.h"
|
||||
#include "Request.h"
|
||||
|
||||
|
||||
NFS4Server::NFS4Server(RPC::Server* serv)
|
||||
:
|
||||
fCIDUseCount(0),
|
||||
fSequenceId(0),
|
||||
fServer(serv)
|
||||
{
|
||||
mutex_init(&fLock, NULL);
|
||||
}
|
||||
|
||||
|
||||
NFS4Server::~NFS4Server()
|
||||
{
|
||||
mutex_destroy(&fLock);
|
||||
}
|
||||
|
||||
|
||||
uint64
|
||||
NFS4Server::ClientId(uint64 prevId, bool forceNew)
|
||||
{
|
||||
mutex_lock(&fLock);
|
||||
if ((forceNew && fClientId == prevId) || fCIDUseCount == 0) {
|
||||
Request request(fServer);
|
||||
request.Builder().SetClientID(fServer);
|
||||
|
||||
status_t result = request.Send();
|
||||
if (result != B_OK)
|
||||
goto out_unlock;
|
||||
|
||||
uint64 ver;
|
||||
result = request.Reply().SetClientID(&fClientId, &ver);
|
||||
if (result != B_OK)
|
||||
goto out_unlock;
|
||||
|
||||
request.Reset();
|
||||
request.Builder().SetClientIDConfirm(fClientId, ver);
|
||||
|
||||
result = request.Send();
|
||||
if (result != B_OK)
|
||||
goto out_unlock;
|
||||
|
||||
result = request.Reply().SetClientIDConfirm();
|
||||
if (result != B_OK)
|
||||
goto out_unlock;
|
||||
}
|
||||
|
||||
fCIDUseCount++;
|
||||
|
||||
out_unlock:
|
||||
mutex_unlock(&fLock);
|
||||
return fClientId;
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
NFS4Server::ReleaseCID(uint64 cid)
|
||||
{
|
||||
mutex_lock(&fLock);
|
||||
fCIDUseCount--;
|
||||
mutex_unlock(&fLock);
|
||||
}
|
||||
|
44
src/add-ons/kernel/file_systems/nfs4/NFS4Server.h
Normal file
44
src/add-ons/kernel/file_systems/nfs4/NFS4Server.h
Normal file
@ -0,0 +1,44 @@
|
||||
/*
|
||||
* Copyright 2012 Haiku, Inc. All rights reserved.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Authors:
|
||||
* Paweł Dziepak, pdziepak@quarnos.org
|
||||
*/
|
||||
#ifndef NFS4SERVER_H
|
||||
#define NFS4SERVER_H
|
||||
|
||||
|
||||
#include <lock.h>
|
||||
|
||||
#include "RPCServer.h"
|
||||
|
||||
|
||||
class NFS4Server : public RPC::ProgramData {
|
||||
public:
|
||||
NFS4Server(RPC::Server* serv);
|
||||
virtual ~NFS4Server();
|
||||
|
||||
uint64 ClientId(uint64 prevId = 0, bool forceNew = false);
|
||||
void ReleaseCID(uint64 cid);
|
||||
|
||||
inline uint32 SequenceId();
|
||||
private:
|
||||
uint64 fClientId;
|
||||
uint32 fCIDUseCount;
|
||||
mutex fLock;
|
||||
|
||||
vint32 fSequenceId;
|
||||
|
||||
RPC::Server* fServer;
|
||||
};
|
||||
|
||||
uint32
|
||||
NFS4Server::SequenceId()
|
||||
{
|
||||
return static_cast<uint32>(atomic_add(&fSequenceId, 1));
|
||||
}
|
||||
|
||||
|
||||
#endif // NFS4SERVER_H
|
||||
|
@ -77,6 +77,7 @@ Server::Server(Connection* conn, ServerAddress* addr)
|
||||
:
|
||||
fConnection(conn),
|
||||
fAddress(addr),
|
||||
fPrivateData(NULL),
|
||||
fXID(rand() << 1)
|
||||
{
|
||||
_StartListening();
|
||||
@ -85,6 +86,8 @@ Server::Server(Connection* conn, ServerAddress* addr)
|
||||
|
||||
Server::~Server()
|
||||
{
|
||||
delete fPrivateData;
|
||||
|
||||
fThreadCancel = true;
|
||||
fConnection->Disconnect();
|
||||
interrupt_thread(fThread);
|
||||
@ -200,7 +203,7 @@ Server::Repair()
|
||||
uint32
|
||||
Server::_GetXID()
|
||||
{
|
||||
return (uint32)atomic_add(&fXID, 1);
|
||||
return static_cast<uint32>(atomic_add(&fXID, 1));
|
||||
}
|
||||
|
||||
|
||||
@ -262,7 +265,8 @@ ServerManager::~ServerManager()
|
||||
|
||||
|
||||
status_t
|
||||
ServerManager::Acquire(Server** pserv, uint32 ip, uint16 port, Transport proto)
|
||||
ServerManager::Acquire(Server** pserv, uint32 ip, uint16 port, Transport proto,
|
||||
ProgramData* (*createPriv)(Server*))
|
||||
{
|
||||
status_t result;
|
||||
|
||||
@ -301,6 +305,7 @@ ServerManager::Acquire(Server** pserv, uint32 ip, uint16 port, Transport proto)
|
||||
delete conn;
|
||||
return B_NO_MEMORY;
|
||||
}
|
||||
node->fServer->SetPrivateData(createPriv(node->fServer));
|
||||
|
||||
node->fRefCount = 1;
|
||||
node->fLeft = node->fRight = NULL;
|
||||
|
@ -43,6 +43,11 @@ private:
|
||||
|
||||
};
|
||||
|
||||
class ProgramData {
|
||||
public:
|
||||
virtual ~ProgramData() { }
|
||||
};
|
||||
|
||||
class Server {
|
||||
public:
|
||||
Server(Connection* conn,
|
||||
@ -63,6 +68,9 @@ public:
|
||||
inline const ServerAddress& ID() const;
|
||||
inline ServerAddress LocalID() const;
|
||||
|
||||
inline ProgramData* PrivateData();
|
||||
inline void SetPrivateData(ProgramData* priv);
|
||||
|
||||
private:
|
||||
inline uint32 _GetXID();
|
||||
|
||||
@ -79,6 +87,8 @@ private:
|
||||
Connection* fConnection;
|
||||
const ServerAddress* fAddress;
|
||||
|
||||
ProgramData* fPrivateData;
|
||||
|
||||
vint32 fXID;
|
||||
static const bigtime_t kWaitTime = 1000000;
|
||||
};
|
||||
@ -118,6 +128,21 @@ Server::LocalID() const
|
||||
}
|
||||
|
||||
|
||||
inline ProgramData*
|
||||
Server::PrivateData()
|
||||
{
|
||||
return fPrivateData;
|
||||
}
|
||||
|
||||
|
||||
inline void
|
||||
Server::SetPrivateData(ProgramData* priv)
|
||||
{
|
||||
delete fPrivateData;
|
||||
fPrivateData = priv;
|
||||
}
|
||||
|
||||
|
||||
struct ServerNode {
|
||||
ServerAddress fID;
|
||||
Server* fServer;
|
||||
@ -133,7 +158,8 @@ public:
|
||||
~ServerManager();
|
||||
|
||||
status_t Acquire(Server** pserv, uint32 ip, uint16 port,
|
||||
Transport proto);
|
||||
Transport proto,
|
||||
ProgramData* (*createPriv)(Server*));
|
||||
void Release(Server* serv);
|
||||
|
||||
private:
|
||||
|
@ -28,6 +28,13 @@ dprintf(const char* format, ...);
|
||||
RPC::ServerManager* gRPCServerManager;
|
||||
|
||||
|
||||
static RPC::ProgramData*
|
||||
sCreateNFS4Server(RPC::Server* serv)
|
||||
{
|
||||
return new NFS4Server(serv);
|
||||
}
|
||||
|
||||
|
||||
static status_t
|
||||
nfs4_mount(fs_volume* volume, const char* device, uint32 flags,
|
||||
const char* args, ino_t* _rootVnodeID)
|
||||
@ -36,7 +43,8 @@ nfs4_mount(fs_volume* volume, const char* device, uint32 flags,
|
||||
|
||||
RPC::Server *server;
|
||||
// hardcoded ip 192.168.1.70
|
||||
result = gRPCServerManager->Acquire(&server, 0xc0a80146, 2049, ProtocolUDP);
|
||||
result = gRPCServerManager->Acquire(&server, 0xc0a80146, 2049, ProtocolUDP,
|
||||
sCreateNFS4Server);
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user