sapling/eden/fs/takeover/TakeoverData.h
Wez Furlong ef214c6c4f serialize the InodeMap
Summary:
this isn't how we really want to do this long term, it's
just the most expedient short term implementation.

This diff provides an implementation of the `InodeMap::save()` which
was previously a stub method; the new implementation returns a thrift
structure that encompasses the unloaded inodes in the map, and adds
a corresponding load() method that performs the reverse transformation.

The struct is serialized into the Takeover data.

This diff doesn't hook up the real serialized data to EdenServer; that will happen
in a follow-on diff.

The way that we actually want to handle this longer term is to store the
`numFuseReferences` field into the overlay file on disk, but to do so we
will need to add a mountGeneration field alongside it and ensure that we
always write out the correct information at the correct times.  In addition,
we'd need to add equivalent data to TreeInode::Entry and add accessors that
safely return the correct values in the correct situations.

In the interest of getting something working, I've just dumped this code in
here.

I've also placed the thrift structure for this in `fuse/handlemap.thrift`;
this is a slight layering violation but one that feels "OK" in light of
the imminent refactor of the Takeover data struct to be its own thrift
struct anyway.

Reviewed By: simpkins

Differential Revision: D6670904

fbshipit-source-id: 11a0918954c741935c587e46fcb0e38849010de1
2018-01-09 22:23:10 -08:00

125 lines
3.1 KiB
C++

/*
* Copyright (c) 2004-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*
*/
#pragma once
#include <folly/File.h>
#include <folly/futures/Promise.h>
#include <memory>
#include <vector>
#include "eden/fs/fuse/FuseTypes.h"
#include "eden/fs/fuse/gen-cpp2/handlemap_types.h"
#include "eden/fs/utils/PathFuncs.h"
namespace folly {
class IOBuf;
class exception_wrapper;
} // namespace folly
namespace facebook {
namespace eden {
class SerializedFileHandleMap;
/**
* TakeoverData contains the data exchanged between processes during
* graceful mount point takeover.
*/
class TakeoverData {
public:
struct MountInfo {
MountInfo(
AbsolutePathPiece mountPath,
AbsolutePathPiece stateDirectory,
const std::vector<AbsolutePath>& bindMountPaths,
folly::File fd,
fuse_init_out connInfo,
SerializedFileHandleMap&& fileHandleMap,
SerializedInodeMap&& inodeMap)
: mountPath{mountPath},
stateDirectory{stateDirectory},
bindMounts{bindMountPaths},
fuseFD{std::move(fd)},
connInfo{connInfo},
fileHandleMap{std::move(fileHandleMap)},
inodeMap{std::move(inodeMap)} {}
AbsolutePath mountPath;
AbsolutePath stateDirectory;
std::vector<AbsolutePath> bindMounts;
folly::File fuseFD;
fuse_init_out connInfo;
SerializedFileHandleMap fileHandleMap;
SerializedInodeMap inodeMap;
};
/**
* Serialize the TakeoverData into a buffer that can be sent to a remote
* process.
*
* This includes all data except for file descriptors. The file descriptors
* must be sent separately.
*/
folly::IOBuf serialize();
/**
* Serialize an exception.
*/
static folly::IOBuf serializeError(const folly::exception_wrapper& ew);
/**
* Deserialize the TakeoverData from a buffer.
*/
static TakeoverData deserialize(const folly::IOBuf* buf);
/**
* The main eden lock file that prevents two edenfs processes from running at
* the same time.
*/
folly::File lockFile;
/**
* The thrift server socket.
*/
folly::File thriftSocket;
/**
* The list of mount points.
*/
std::vector<MountInfo> mountPoints;
/**
* The takeoverComplete promise will be fulfilled by the TakeoverServer code
* once the TakeoverData has been sent to the remote process.
*/
folly::Promise<folly::Unit> takeoverComplete;
private:
/**
* Message type values.
* If we ever need to include more information in the takeover data in the
* future we can do so by adding new message types here, and deprecating the
* older formats once we have upgraded all servers to use the new format.
*/
enum MessageType : uint32_t {
ERROR = 1,
MOUNTS = 2,
};
/**
* The length of the serialized header.
* This is just a 4-byte message type field.
*/
static constexpr uint32_t kHeaderLength = sizeof(uint32_t);
};
} // namespace eden
} // namespace facebook