mirror of
https://github.com/facebook/sapling.git
synced 2024-10-05 14:28:17 +03:00
fix issues when checking EdenFS status on windows
Summary: - Catch the Windows-specific exceptions types thrown when attempting to open the socket if EdenFS is not running, and convert this to an EdenNotRunning exception. - Update EdenFS to write its pid to a separate file, in addition to the normal lock file, and have `edenfsctl` read this file instead of the lock file on Windows. Other processes cannot read the lock file while EdenFS is running and holding the lock, so it is nice to have the pid written in an alternate location. Reviewed By: pkaush Differential Revision: D20854615 fbshipit-source-id: 1c8e8f402eb17dd012d03e11fbb662f493d9362d
This commit is contained in:
parent
b1a35b8252
commit
104ae880db
@ -30,6 +30,7 @@ if sys.platform != "win32":
|
||||
|
||||
# These paths are relative to the user's client directory.
|
||||
LOCK_FILE = "lock"
|
||||
PID_FILE = "pid"
|
||||
|
||||
|
||||
class EdenStartError(Exception):
|
||||
@ -102,7 +103,16 @@ def poll_until(
|
||||
def get_pid_using_lockfile(config_dir: Path) -> int:
|
||||
"""Read the pid from the Eden lockfile, throwing an exception upon failure.
|
||||
"""
|
||||
lockfile = config_dir / LOCK_FILE
|
||||
if sys.platform == "win32":
|
||||
# On Windows read the separate pid file. We will not be able to read the
|
||||
# lock file if EdenFS is running and holding the lock.
|
||||
lockfile = config_dir / PID_FILE
|
||||
else:
|
||||
# On other platforms we still prefer reading the pid from the lock file,
|
||||
# just to support older instances of EdenFS that only wrote the pid to the lock
|
||||
# file.
|
||||
lockfile = config_dir / LOCK_FILE
|
||||
|
||||
with lockfile.open("r") as f:
|
||||
lockfile_contents = f.read()
|
||||
return int(lockfile_contents.rstrip())
|
||||
|
@ -18,10 +18,13 @@ from thrift.transport.TTransport import TTransportException
|
||||
|
||||
|
||||
if sys.platform == "win32":
|
||||
from eden.thrift.windows_thrift import WinTSocket # @manual
|
||||
from eden.thrift.windows_thrift import WinTSocket, WindowsSocketException # @manual
|
||||
else:
|
||||
from thrift.transport.TSocket import TSocket
|
||||
|
||||
class WindowsSocketException(Exception):
|
||||
pass
|
||||
|
||||
|
||||
SOCKET_PATH = "socket"
|
||||
|
||||
@ -91,15 +94,18 @@ class EdenClient(EdenService.Client):
|
||||
|
||||
def open(self):
|
||||
# type: () -> None
|
||||
transport = self._transport
|
||||
assert transport is not None
|
||||
try:
|
||||
assert self._transport is not None
|
||||
# pyre-fixme[16]: `Optional` has no attribute `open`.
|
||||
self._transport.open()
|
||||
transport.open()
|
||||
except TTransportException as ex:
|
||||
self.close()
|
||||
if ex.type == TTransportException.NOT_OPEN:
|
||||
raise EdenNotRunningError(self._socket_path)
|
||||
raise
|
||||
except WindowsSocketException:
|
||||
self.close()
|
||||
raise EdenNotRunningError(self._socket_path)
|
||||
|
||||
def close(self):
|
||||
# type: () -> None
|
||||
|
@ -14,6 +14,7 @@ using folly::StringPiece;
|
||||
|
||||
namespace {
|
||||
constexpr StringPiece kLockFileName{"lock"};
|
||||
constexpr StringPiece kPidFileName{"pid"};
|
||||
constexpr StringPiece kTakeoverSocketName{"takeover"};
|
||||
constexpr StringPiece kThriftSocketName{"socket"};
|
||||
} // namespace
|
||||
@ -42,6 +43,13 @@ void EdenStateDir::takeoverLock(folly::File lockFile) {
|
||||
int rc = fstat(lockFile.fd(), &lockFileStat_);
|
||||
folly::checkUnixError(rc, "error getting lock file attributes");
|
||||
lockFile_ = std::move(lockFile);
|
||||
|
||||
// On Windows, also write the pid to a separate file.
|
||||
// Other processes cannot read the lock file while we are holding the lock,
|
||||
// so we store it in a separate file too.
|
||||
auto pidFilePath = path_ + PathComponentPiece(kPidFileName);
|
||||
folly::File pidFile(pidFilePath.c_str(), O_WRONLY | O_CREAT, 0644);
|
||||
writePidToLockFile(pidFile);
|
||||
}
|
||||
|
||||
folly::File EdenStateDir::extractLock() {
|
||||
|
Loading…
Reference in New Issue
Block a user