aboutsummaryrefslogtreecommitdiff
path: root/sshfs.c
diff options
context:
space:
mode:
Diffstat (limited to 'sshfs.c')
-rw-r--r--sshfs.c170
1 files changed, 37 insertions, 133 deletions
diff --git a/sshfs.c b/sshfs.c
index f116633..97eaf06 100644
--- a/sshfs.c
+++ b/sshfs.c
@@ -132,8 +132,6 @@
#define SFTP_SERVER_PATH "/usr/lib/sftp-server"
-#define SSHNODELAY_SO "sshnodelay.so"
-
/* Asynchronous readdir parameters */
#define READDIR_START 2
#define READDIR_MAX 32
@@ -216,8 +214,6 @@ struct sshfs {
struct fuse_args ssh_args;
char *workarounds;
int rename_workaround;
- int nodelay_workaround;
- int nodelaysrv_workaround;
int truncate_workaround;
int buflimit_workaround;
int fstat_workaround;
@@ -297,6 +293,7 @@ static const char *ssh_opts[] = {
"AddressFamily",
"BatchMode",
"BindAddress",
+ "CertificateFile",
"ChallengeResponseAuthentication",
"CheckHostIP",
"Cipher",
@@ -307,28 +304,40 @@ static const char *ssh_opts[] = {
"ConnectTimeout",
"ControlMaster",
"ControlPath",
+ "ControlPersist",
+ "FingerprintHash",
"GlobalKnownHostsFile",
"GSSAPIAuthentication",
"GSSAPIDelegateCredentials",
"HostbasedAuthentication",
+ "HostbasedKeyTypes",
"HostKeyAlgorithms",
"HostKeyAlias",
"HostName",
"IdentitiesOnly",
"IdentityFile",
+ "IdentityAgent",
+ "IPQoS",
"KbdInteractiveAuthentication",
"KbdInteractiveDevices",
+ "KexAlgorithms",
"LocalCommand",
"LogLevel",
"MACs",
"NoHostAuthenticationForLocalhost",
"NumberOfPasswordPrompts",
"PasswordAuthentication",
+ "PermitLocalCommand",
+ "PKCS11Provider",
"Port",
"PreferredAuthentications",
"ProxyCommand",
+ "ProxyJump",
+ "ProxyUseFdpass",
+ "PubkeyAcceptedKeyTypes"
"PubkeyAuthentication",
"RekeyLimit",
+ "RevokedHostKeys",
"RhostsRSAAuthentication",
"RSAAuthentication",
"ServerAliveCountMax",
@@ -336,9 +345,11 @@ static const char *ssh_opts[] = {
"SmartcardDevice",
"StrictHostKeyChecking",
"TCPKeepAlive",
+ "UpdateHostKeys",
"UsePrivilegedPort",
"UserKnownHostsFile",
"VerifyHostKeyDNS",
+ "VisualHostKey",
NULL,
};
@@ -408,23 +419,11 @@ static struct fuse_opt sshfs_opts[] = {
static struct fuse_opt workaround_opts[] = {
SSHFS_OPT("none", rename_workaround, 0),
- SSHFS_OPT("none", nodelay_workaround, 0),
- SSHFS_OPT("none", nodelaysrv_workaround, 0),
SSHFS_OPT("none", truncate_workaround, 0),
SSHFS_OPT("none", buflimit_workaround, 0),
SSHFS_OPT("none", fstat_workaround, 0),
- SSHFS_OPT("all", rename_workaround, 1),
- SSHFS_OPT("all", nodelay_workaround, 1),
- SSHFS_OPT("all", nodelaysrv_workaround, 1),
- SSHFS_OPT("all", truncate_workaround, 1),
- SSHFS_OPT("all", buflimit_workaround, 1),
- SSHFS_OPT("all", fstat_workaround, 1),
SSHFS_OPT("rename", rename_workaround, 1),
SSHFS_OPT("norename", rename_workaround, 0),
- SSHFS_OPT("nodelay", nodelay_workaround, 1),
- SSHFS_OPT("nonodelay", nodelay_workaround, 0),
- SSHFS_OPT("nodelaysrv", nodelaysrv_workaround, 1),
- SSHFS_OPT("nonodelaysrv", nodelaysrv_workaround, 0),
SSHFS_OPT("truncate", truncate_workaround, 1),
SSHFS_OPT("notruncate", truncate_workaround, 0),
SSHFS_OPT("buflimit", buflimit_workaround, 1),
@@ -877,85 +876,6 @@ static void ssh_add_arg(const char *arg)
_exit(1);
}
-#ifdef SSH_NODELAY_WORKAROUND
-static int do_ssh_nodelay_workaround(void)
-{
-#ifdef __APPLE__
- char *oldpreload = getenv("DYLD_INSERT_LIBRARIES");
-#else
- char *oldpreload = getenv("LD_PRELOAD");
-#endif
- char *newpreload;
- char sopath[PATH_MAX];
- int res;
-
-#ifdef __APPLE__
- char *sshfs_program_path_base = NULL;
- if (!sshfs_program_path[0]) {
- goto nobundle;
- }
- sshfs_program_path_base = dirname(sshfs_program_path);
- if (!sshfs_program_path_base) {
- goto nobundle;
- }
- snprintf(sopath, sizeof(sopath), "%s/%s", sshfs_program_path_base,
- SSHNODELAY_SO);
- res = access(sopath, R_OK);
- if (res == -1) {
- goto nobundle;
- }
- goto pathok;
-
-nobundle:
-#endif /* __APPLE__ */
-
- snprintf(sopath, sizeof(sopath), "%s/%s", LIBDIR, SSHNODELAY_SO);
- res = access(sopath, R_OK);
- if (res == -1) {
- char *s;
- if (!realpath(sshfs.progname, sopath))
- return -1;
-
- s = strrchr(sopath, '/');
- if (!s)
- s = sopath;
- else
- s++;
-
- if (s + strlen(SSHNODELAY_SO) >= sopath + sizeof(sopath))
- return -1;
-
- strcpy(s, SSHNODELAY_SO);
- res = access(sopath, R_OK);
- if (res == -1) {
- fprintf(stderr, "sshfs: cannot find %s\n",
- SSHNODELAY_SO);
- return -1;
- }
- }
-
-#ifdef __APPLE__
-pathok:
-#endif
-
- newpreload = g_strdup_printf("%s%s%s",
- oldpreload ? oldpreload : "",
- oldpreload ? " " : "",
- sopath);
-
-#ifdef __APPLE__
- if (!newpreload || setenv("DYLD_INSERT_LIBRARIES", newpreload, 1) == -1)
- fprintf(stderr, "warning: failed set DYLD_INSERT_LIBRARIES for ssh nodelay workaround\n");
-#else /* !__APPLE__ */
- if (!newpreload || setenv("LD_PRELOAD", newpreload, 1) == -1) {
- fprintf(stderr, "warning: failed set LD_PRELOAD "
- "for ssh nodelay workaround\n");
- }
-#endif /* __APPLE__ */
- g_free(newpreload);
- return 0;
-}
-#endif
static int pty_expect_loop(void)
{
@@ -1089,29 +1009,6 @@ static int start_ssh(void)
} else if (pid == 0) {
int devnull;
-#ifdef SSH_NODELAY_WORKAROUND
- if (sshfs.nodelay_workaround &&
- do_ssh_nodelay_workaround() == -1) {
- fprintf(stderr,
- "warning: ssh nodelay workaround disabled\n");
- }
-#endif
-
- if (sshfs.nodelaysrv_workaround) {
- int i;
- /*
- * Hack to work around missing TCP_NODELAY
- * setting in sshd
- */
- for (i = 1; i < sshfs.ssh_args.argc; i++) {
- if (strcmp(sshfs.ssh_args.argv[i], "-x") == 0) {
- replace_arg(&sshfs.ssh_args.argv[i],
- "-X");
- break;
- }
- }
- }
-
devnull = open("/dev/null", O_WRONLY);
if (dup2(sockpair[1], 0) == -1 || dup2(sockpair[1], 1) == -1) {
@@ -2178,11 +2075,16 @@ static int sftp_readdir_async(struct buffer *handle, fuse_cache_dirh_t h,
outstanding--;
if (done) {
+ /* We need to cache want_reply, since processing
+ thread may free req right after unlock() if
+ want_reply == 0 */
+ int want_reply;
pthread_mutex_lock(&sshfs.lock);
if (sshfs_req_pending(req))
req->want_reply = 0;
+ want_reply = req->want_reply;
pthread_mutex_unlock(&sshfs.lock);
- if (!req->want_reply)
+ if (!want_reply)
continue;
}
@@ -2645,7 +2547,8 @@ static int sshfs_fsync(const char *path, int isdatasync,
int err;
(void) isdatasync;
- if (err = sshfs_flush(path, fi))
+ err = sshfs_flush(path, fi);
+ if (err)
return err;
if (!sshfs.ext_fsync)
@@ -3422,14 +3325,10 @@ static void usage(const char *progname)
" cache if full (default: 5)\n"
" -o workaround=LIST colon separated list of workarounds\n"
" none no workarounds enabled\n"
-" all all workarounds enabled\n"
" [no]rename fix renaming to existing file (default: off)\n"
-#ifdef SSH_NODELAY_WORKAROUND
-" [no]nodelay set nodelay tcp flag in ssh (default: on)\n"
-#endif
-" [no]nodelaysrv set nodelay tcp flag in sshd (default: off)\n"
" [no]truncate fix truncate for old servers (default: off)\n"
" [no]buflimit fix buffer fillup bug in server (default: on)\n"
+" [no]fstat fix fstat for old servers (default: off)\n"
" -o idmap=TYPE user/group ID mapping (default: " IDMAP_DEFAULT ")\n"
" none no translation of the ID space\n"
" user only translate UID/GID of connecting user\n"
@@ -3549,10 +3448,14 @@ static int workaround_opt_proc(void *data, const char *arg, int key,
return -1;
}
-int parse_workarounds(void)
+static int parse_workarounds(void)
{
int res;
- char *argv[] = { "", "-o", sshfs.workarounds, NULL };
+ /* Need separate variables because literals are const
+ char */
+ char argv0[] = "";
+ char argv1[] = "-o";
+ char *argv[] = { argv0, argv1, sshfs.workarounds, NULL };
struct fuse_args args = FUSE_ARGS_INIT(3, argv);
char *s = sshfs.workarounds;
if (!s)
@@ -3958,14 +3861,11 @@ int main(int argc, char *argv[])
memset(sshfs_program_path, 0, PATH_MAX);
}
#endif /* __APPLE__ */
- g_thread_init(NULL);
sshfs.blksize = 4096;
/* SFTP spec says all servers should allow at least 32k I/O */
sshfs.max_read = 32768;
sshfs.max_write = 32768;
- sshfs.nodelay_workaround = 1;
- sshfs.nodelaysrv_workaround = 0;
#ifdef __APPLE__
sshfs.rename_workaround = 1;
#else
@@ -4164,6 +4064,13 @@ int main(int argc, char *argv[])
exit(1);
}
+ res = fuse_set_signal_handlers(fuse_get_session(fuse));
+ if (res == -1) {
+ fuse_unmount(mountpoint, ch);
+ fuse_destroy(fuse);
+ exit(1);
+ }
+
/*
* FIXME: trim $PATH so it doesn't contain anything inside the
* mountpoint, which would deadlock.
@@ -4176,9 +4083,6 @@ int main(int argc, char *argv[])
}
res = fuse_daemonize(foreground);
- if (res != -1)
- res = fuse_set_signal_handlers(fuse_get_session(fuse));
-
if (res == -1) {
fuse_unmount(mountpoint, ch);
fuse_destroy(fuse);