You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@guacamole.apache.org by vn...@apache.org on 2017/07/03 21:52:09 UTC
[1/3] incubator-guacamole-server git commit: GUACAMOLE-303: Extend
common SFTP filesystem such that arbitrary directories can be used as the
root of the filesystem.
Repository: incubator-guacamole-server
Updated Branches:
refs/heads/master 836fc3eaa -> 07db9808a
GUACAMOLE-303: Extend common SFTP filesystem such that arbitrary directories can be used as the root of the filesystem.
Project: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/commit/0474f86c
Tree: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/tree/0474f86c
Diff: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/diff/0474f86c
Branch: refs/heads/master
Commit: 0474f86c46309ddae785359c92374820cc768525
Parents: 836fc3e
Author: Michael Jumper <mj...@apache.org>
Authored: Thu Jun 29 15:28:21 2017 -0700
Committer: Michael Jumper <mj...@apache.org>
Committed: Thu Jun 29 15:36:10 2017 -0700
----------------------------------------------------------------------
src/common-ssh/common-ssh/sftp.h | 21 ++-
src/common-ssh/sftp.c | 259 ++++++++++++++++++++++++++++++++--
src/protocols/rdp/rdp.c | 2 +-
src/protocols/ssh/ssh.c | 2 +-
src/protocols/vnc/vnc.c | 2 +-
5 files changed, 270 insertions(+), 16 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/0474f86c/src/common-ssh/common-ssh/sftp.h
----------------------------------------------------------------------
diff --git a/src/common-ssh/common-ssh/sftp.h b/src/common-ssh/common-ssh/sftp.h
index 038a577..0ec2d12 100644
--- a/src/common-ssh/common-ssh/sftp.h
+++ b/src/common-ssh/common-ssh/sftp.h
@@ -34,6 +34,11 @@
#define GUAC_COMMON_SSH_SFTP_MAX_PATH 2048
/**
+ * Maximum number of path components per path.
+ */
+#define GUAC_COMMON_SSH_SFTP_MAX_DEPTH 1024
+
+/**
* Representation of an SFTP-driven filesystem object. Unlike guac_object, this
* structure is not tied to any particular user.
*/
@@ -55,6 +60,11 @@ typedef struct guac_common_ssh_sftp_filesystem {
LIBSSH2_SFTP* sftp_session;
/**
+ * The path to the directory to expose to the user as a filesystem object.
+ */
+ char root_path[GUAC_COMMON_SSH_SFTP_MAX_PATH];
+
+ /**
* The path files will be sent to, if uploaded directly via a "file"
* instruction.
*/
@@ -103,15 +113,22 @@ typedef struct guac_common_ssh_sftp_ls_state {
* The session to use to provide SFTP. This session will automatically be
* destroyed when this filesystem is destroyed.
*
+ * @param root_path
+ * The path accessible via SFTP to consider the root path of the filesystem
+ * exposed to the user. Only the contents of this path will be available
+ * via the filesystem object.
+ *
* @param name
* The name to send as the name of the filesystem whenever it is exposed
- * to a user.
+ * to a user, or NULL to automatically generate a name from the provided
+ * root_path.
*
* @return
* A new SFTP filesystem object, not yet exposed to users.
*/
guac_common_ssh_sftp_filesystem* guac_common_ssh_create_sftp_filesystem(
- guac_common_ssh_session* session, const char* name);
+ guac_common_ssh_session* session, const char* root_path,
+ const char* name);
/**
* Destroys the given filesystem object, disconnecting from SFTP and freeing
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/0474f86c/src/common-ssh/sftp.c
----------------------------------------------------------------------
diff --git a/src/common-ssh/sftp.c b/src/common-ssh/sftp.c
index 4be1568..e0e029f 100644
--- a/src/common-ssh/sftp.c
+++ b/src/common-ssh/sftp.c
@@ -33,6 +33,111 @@
#include <string.h>
/**
+ * Given an arbitrary absolute path, which may contain "..", ".", and
+ * backslashes, creates an equivalent absolute path which does NOT contain
+ * relative path components (".." or "."), backslashes, or empty path
+ * components. With the exception of paths referring to the root directory, the
+ * resulting path is guaranteed to not contain trailing slashes.
+ *
+ * Normalization will fail if the given path is not absolute, is too long, or
+ * contains more than GUAC_COMMON_SSH_SFTP_MAX_DEPTH path components.
+ *
+ * @param fullpath
+ * The buffer to populate with the normalized path. The normalized path
+ * will not contain relative path components like ".." or ".", nor will it
+ * contain backslashes. This buffer MUST be at least
+ * GUAC_COMMON_SSH_SFTP_MAX_PATH bytes in size.
+ *
+ * @param path
+ * The absolute path to normalize.
+ *
+ * @return
+ * Non-zero if normalization succeeded, zero otherwise.
+ */
+static int guac_common_ssh_sftp_normalize_path(char* fullpath,
+ const char* path) {
+
+ int i;
+
+ int path_depth = 0;
+ char path_component_data[GUAC_COMMON_SSH_SFTP_MAX_PATH];
+ const char* path_components[GUAC_COMMON_SSH_SFTP_MAX_DEPTH];
+
+ const char** current_path_component = &(path_components[0]);
+ const char* current_path_component_data = &(path_component_data[0]);
+
+ /* If original path is not absolute, normalization fails */
+ if (path[0] != '\\' && path[0] != '/')
+ return 1;
+
+ /* Skip past leading slash */
+ path++;
+
+ /* Copy path into component data for parsing */
+ strncpy(path_component_data, path, sizeof(path_component_data) - 1);
+
+ /* Find path components within path */
+ for (i = 0; i < sizeof(path_component_data); i++) {
+
+ /* If current character is a path separator, parse as component */
+ char c = path_component_data[i];
+ if (c == '/' || c == '\\' || c == '\0') {
+
+ /* Terminate current component */
+ path_component_data[i] = '\0';
+
+ /* If component refers to parent, just move up in depth */
+ if (strcmp(current_path_component_data, "..") == 0) {
+ if (path_depth > 0)
+ path_depth--;
+ }
+
+ /* Otherwise, if component not current directory, add to list */
+ else if (strcmp(current_path_component_data, ".") != 0
+ && strcmp(current_path_component_data, "") != 0)
+ path_components[path_depth++] = current_path_component_data;
+
+ /* If end of string, stop */
+ if (c == '\0')
+ break;
+
+ /* Update start of next component */
+ current_path_component_data = &(path_component_data[i+1]);
+
+ } /* end if separator */
+
+ } /* end for each character */
+
+ /* If no components, the path is simply root */
+ if (path_depth == 0) {
+ strcpy(fullpath, "/");
+ return 1;
+ }
+
+ /* Ensure last component is null-terminated */
+ path_component_data[i] = 0;
+
+ /* Convert components back into path */
+ for (; path_depth > 0; path_depth--) {
+
+ const char* filename = *(current_path_component++);
+
+ /* Add separator */
+ *(fullpath++) = '/';
+
+ /* Copy string */
+ while (*filename != 0)
+ *(fullpath++) = *(filename++);
+
+ }
+
+ /* Terminate absolute path */
+ *(fullpath++) = 0;
+ return 1;
+
+}
+
+/**
* Translates the last error message received by the SFTP layer of an SSH
* session into a Guacamole protocol status code.
*
@@ -184,6 +289,73 @@ static int guac_ssh_append_filename(char* fullpath, const char* path,
}
/**
+ * Concatenates the given paths, separating the two with a single forward
+ * slash. The full result must be no more than GUAC_COMMON_SSH_SFTP_MAX_PATH
+ * bytes long, counting null terminator.
+ *
+ * @param fullpath
+ * The buffer to store the result within. This buffer must be at least
+ * GUAC_COMMON_SSH_SFTP_MAX_PATH bytes long.
+ *
+ * @param path_a
+ * The path to place at the beginning of the resulting path.
+ *
+ * @param path_b
+ * The path to append after path_a within the resulting path.
+ *
+ * @return
+ * Non-zero if the paths were successfully concatenated together, zero
+ * otherwise.
+ */
+static int guac_ssh_append_path(char* fullpath, const char* path_a,
+ const char* path_b) {
+
+ int i;
+
+ /* Copy path, appending a trailing slash */
+ for (i = 0; i < GUAC_COMMON_SSH_SFTP_MAX_PATH; i++) {
+
+ char c = path_a[i];
+ if (c == '\0') {
+ if (i > 0 && path_a[i-1] != '/')
+ fullpath[i++] = '/';
+ break;
+ }
+
+ /* Copy character if not end of string */
+ fullpath[i] = c;
+
+ }
+
+ /* Skip past leading slashes in second path */
+ while (*path_b == '/')
+ path_b++;
+
+ /* Append path */
+ for (; i < GUAC_COMMON_SSH_SFTP_MAX_PATH; i++) {
+
+ char c = *(path_b++);
+ if (c == '\0')
+ break;
+
+ /* Append each character within path */
+ fullpath[i] = c;
+
+ }
+
+ /* Verify path length is within maximum */
+ if (i == GUAC_COMMON_SSH_SFTP_MAX_PATH)
+ return 0;
+
+ /* Terminate path string */
+ fullpath[i] = '\0';
+
+ /* Append was successful */
+ return 1;
+
+}
+
+/**
* Handler for blob messages which continue an inbound SFTP data transfer
* (upload). The data associated with the given stream is expected to be a
* pointer to an open LIBSSH2_SFTP_HANDLE for the file to which the data
@@ -568,6 +740,38 @@ static int guac_common_ssh_sftp_ls_ack_handler(guac_user* user,
}
/**
+ * Translates a stream name for the given SFTP filesystem object into the
+ * absolute path corresponding to the actual file it represents.
+ *
+ * @param fullpath
+ * The buffer to populate with the translated path. This buffer MUST be at
+ * least GUAC_COMMON_SSH_SFTP_MAX_PATH bytes in size.
+ *
+ * @param object
+ * The Guacamole protocol object associated with the SFTP filesystem.
+ *
+ * @param name
+ * The name of the stream (file) to translate into an absolute path.
+ *
+ * @return
+ * Non-zero if translation succeeded, zero otherwise.
+ */
+static int guac_common_ssh_sftp_translate_name(char* fullpath,
+ guac_object* object, char* name) {
+
+ char normalized_name[GUAC_COMMON_SSH_SFTP_MAX_PATH];
+
+ guac_common_ssh_sftp_filesystem* filesystem =
+ (guac_common_ssh_sftp_filesystem*) object->data;
+
+ /* Normalize stream name into a path, and append to the root path */
+ return guac_common_ssh_sftp_normalize_path(normalized_name, name)
+ && guac_ssh_append_path(fullpath, filesystem->root_path,
+ normalized_name);
+
+}
+
+/**
* Handler for get messages. In context of SFTP and the filesystem exposed via
* the Guacamole protocol, get messages request the body of a file within the
* filesystem.
@@ -587,16 +791,25 @@ static int guac_common_ssh_sftp_ls_ack_handler(guac_user* user,
static int guac_common_ssh_sftp_get_handler(guac_user* user,
guac_object* object, char* name) {
+ char fullpath[GUAC_COMMON_SSH_SFTP_MAX_PATH];
+
guac_common_ssh_sftp_filesystem* filesystem =
(guac_common_ssh_sftp_filesystem*) object->data;
LIBSSH2_SFTP* sftp = filesystem->sftp_session;
LIBSSH2_SFTP_ATTRIBUTES attributes;
+ /* Translate stream name into filesystem path */
+ if (!guac_common_ssh_sftp_translate_name(fullpath, object, name)) {
+ guac_user_log(user, GUAC_LOG_INFO, "Unable to generate real path "
+ "for stream \"%s\"", name);
+ return 0;
+ }
+
/* Attempt to read file information */
- if (libssh2_sftp_stat(sftp, name, &attributes)) {
+ if (libssh2_sftp_stat(sftp, fullpath, &attributes)) {
guac_user_log(user, GUAC_LOG_INFO, "Unable to read file \"%s\"",
- name);
+ fullpath);
return 0;
}
@@ -604,10 +817,10 @@ static int guac_common_ssh_sftp_get_handler(guac_user* user,
if (LIBSSH2_SFTP_S_ISDIR(attributes.permissions)) {
/* Open as directory */
- LIBSSH2_SFTP_HANDLE* dir = libssh2_sftp_opendir(sftp, name);
+ LIBSSH2_SFTP_HANDLE* dir = libssh2_sftp_opendir(sftp, fullpath);
if (dir == NULL) {
guac_user_log(user, GUAC_LOG_INFO,
- "Unable to read directory \"%s\"", name);
+ "Unable to read directory \"%s\"", fullpath);
return 0;
}
@@ -638,11 +851,11 @@ static int guac_common_ssh_sftp_get_handler(guac_user* user,
else {
/* Open as normal file */
- LIBSSH2_SFTP_HANDLE* file = libssh2_sftp_open(sftp, name,
+ LIBSSH2_SFTP_HANDLE* file = libssh2_sftp_open(sftp, fullpath,
LIBSSH2_FXF_READ, 0);
if (file == NULL) {
guac_user_log(user, GUAC_LOG_INFO,
- "Unable to read file \"%s\"", name);
+ "Unable to read file \"%s\"", fullpath);
return 0;
}
@@ -688,19 +901,28 @@ static int guac_common_ssh_sftp_get_handler(guac_user* user,
static int guac_common_ssh_sftp_put_handler(guac_user* user,
guac_object* object, guac_stream* stream, char* mimetype, char* name) {
+ char fullpath[GUAC_COMMON_SSH_SFTP_MAX_PATH];
+
guac_common_ssh_sftp_filesystem* filesystem =
(guac_common_ssh_sftp_filesystem*) object->data;
LIBSSH2_SFTP* sftp = filesystem->sftp_session;
+ /* Translate stream name into filesystem path */
+ if (!guac_common_ssh_sftp_translate_name(fullpath, object, name)) {
+ guac_user_log(user, GUAC_LOG_INFO, "Unable to generate real path "
+ "for stream \"%s\"", name);
+ return 0;
+ }
+
/* Open file via SFTP */
- LIBSSH2_SFTP_HANDLE* file = libssh2_sftp_open(sftp, name,
+ LIBSSH2_SFTP_HANDLE* file = libssh2_sftp_open(sftp, fullpath,
LIBSSH2_FXF_WRITE | LIBSSH2_FXF_CREAT | LIBSSH2_FXF_TRUNC,
S_IRUSR | S_IWUSR);
/* Acknowledge stream if successful */
if (file != NULL) {
- guac_user_log(user, GUAC_LOG_DEBUG, "File \"%s\" opened", name);
+ guac_user_log(user, GUAC_LOG_DEBUG, "File \"%s\" opened", fullpath);
guac_protocol_send_ack(user->socket, stream, "SFTP: File opened",
GUAC_PROTOCOL_STATUS_SUCCESS);
}
@@ -708,7 +930,7 @@ static int guac_common_ssh_sftp_put_handler(guac_user* user,
/* Abort on failure */
else {
guac_user_log(user, GUAC_LOG_INFO,
- "Unable to open file \"%s\"", name);
+ "Unable to open file \"%s\"", fullpath);
guac_protocol_send_ack(user->socket, stream, "SFTP: Open failed",
guac_sftp_get_status(filesystem));
}
@@ -756,7 +978,8 @@ guac_object* guac_common_ssh_alloc_sftp_filesystem_object(
}
guac_common_ssh_sftp_filesystem* guac_common_ssh_create_sftp_filesystem(
- guac_common_ssh_session* session, const char* name) {
+ guac_common_ssh_session* session, const char* root_path,
+ const char* name) {
/* Request SFTP */
LIBSSH2_SFTP* sftp_session = libssh2_sftp_init(session->session);
@@ -768,10 +991,24 @@ guac_common_ssh_sftp_filesystem* guac_common_ssh_create_sftp_filesystem(
malloc(sizeof(guac_common_ssh_sftp_filesystem));
/* Associate SSH session with SFTP data and user */
- filesystem->name = strdup(name);
filesystem->ssh_session = session;
filesystem->sftp_session = sftp_session;
+ /* Normalize and store the provided root path */
+ if (!guac_common_ssh_sftp_normalize_path(filesystem->root_path,
+ root_path)) {
+ guac_client_log(session->client, GUAC_LOG_WARNING, "Cannot create "
+ "SFTP filesystem - \"%s\" is not a valid path.", root_path);
+ free(filesystem);
+ return NULL;
+ }
+
+ /* Generate filesystem name from root path if no name is provided */
+ if (name != NULL)
+ filesystem->name = strdup(name);
+ else
+ filesystem->name = strdup(filesystem->root_path);
+
/* Initially upload files to current directory */
strcpy(filesystem->upload_path, ".");
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/0474f86c/src/protocols/rdp/rdp.c
----------------------------------------------------------------------
diff --git a/src/protocols/rdp/rdp.c b/src/protocols/rdp/rdp.c
index d06fad3..c1be71e 100644
--- a/src/protocols/rdp/rdp.c
+++ b/src/protocols/rdp/rdp.c
@@ -988,7 +988,7 @@ void* guac_rdp_client_thread(void* data) {
/* Load and expose filesystem */
rdp_client->sftp_filesystem =
guac_common_ssh_create_sftp_filesystem(
- rdp_client->sftp_session, "/");
+ rdp_client->sftp_session, "/", NULL);
/* Expose filesystem to connection owner */
guac_client_for_owner(client,
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/0474f86c/src/protocols/ssh/ssh.c
----------------------------------------------------------------------
diff --git a/src/protocols/ssh/ssh.c b/src/protocols/ssh/ssh.c
index aa9fdae..18a0dcb 100644
--- a/src/protocols/ssh/ssh.c
+++ b/src/protocols/ssh/ssh.c
@@ -266,7 +266,7 @@ void* ssh_client_thread(void* data) {
/* Request SFTP */
ssh_client->sftp_filesystem = guac_common_ssh_create_sftp_filesystem(
- ssh_client->sftp_session, "/");
+ ssh_client->sftp_session, "/", NULL);
/* Expose filesystem to connection owner */
guac_client_for_owner(client,
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/0474f86c/src/protocols/vnc/vnc.c
----------------------------------------------------------------------
diff --git a/src/protocols/vnc/vnc.c b/src/protocols/vnc/vnc.c
index 81d46f1..2b7263a 100644
--- a/src/protocols/vnc/vnc.c
+++ b/src/protocols/vnc/vnc.c
@@ -272,7 +272,7 @@ void* guac_vnc_client_thread(void* data) {
/* Load filesystem */
vnc_client->sftp_filesystem =
guac_common_ssh_create_sftp_filesystem(
- vnc_client->sftp_session, "/");
+ vnc_client->sftp_session, "/", NULL);
/* Expose filesystem to connection owner */
guac_client_for_owner(client,
[2/3] incubator-guacamole-server git commit: GUACAMOLE-303: Add
"sftp-root-directory" parameter to VNC, RDP, and SSH.
Posted by vn...@apache.org.
GUACAMOLE-303: Add "sftp-root-directory" parameter to VNC, RDP, and SSH.
Project: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/commit/d51e92eb
Tree: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/tree/d51e92eb
Diff: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/diff/d51e92eb
Branch: refs/heads/master
Commit: d51e92eb312735ec857e7ede0a202728ae9dcb26
Parents: 0474f86
Author: Michael Jumper <mj...@apache.org>
Authored: Thu Jun 29 15:48:23 2017 -0700
Committer: Michael Jumper <mj...@apache.org>
Committed: Thu Jun 29 15:48:23 2017 -0700
----------------------------------------------------------------------
src/protocols/rdp/rdp.c | 4 ++--
src/protocols/rdp/rdp_settings.c | 13 +++++++++++++
src/protocols/rdp/rdp_settings.h | 6 ++++++
src/protocols/ssh/settings.c | 15 +++++++++++++++
src/protocols/ssh/settings.h | 6 ++++++
src/protocols/ssh/ssh.c | 3 ++-
src/protocols/vnc/settings.c | 13 +++++++++++++
src/protocols/vnc/settings.h | 6 ++++++
src/protocols/vnc/vnc.c | 4 ++--
9 files changed, 65 insertions(+), 5 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/rdp/rdp.c
----------------------------------------------------------------------
diff --git a/src/protocols/rdp/rdp.c b/src/protocols/rdp/rdp.c
index c1be71e..0b15d05 100644
--- a/src/protocols/rdp/rdp.c
+++ b/src/protocols/rdp/rdp.c
@@ -987,8 +987,8 @@ void* guac_rdp_client_thread(void* data) {
/* Load and expose filesystem */
rdp_client->sftp_filesystem =
- guac_common_ssh_create_sftp_filesystem(
- rdp_client->sftp_session, "/", NULL);
+ guac_common_ssh_create_sftp_filesystem(rdp_client->sftp_session,
+ settings->sftp_root_directory, NULL);
/* Expose filesystem to connection owner */
guac_client_for_owner(client,
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/rdp/rdp_settings.c
----------------------------------------------------------------------
diff --git a/src/protocols/rdp/rdp_settings.c b/src/protocols/rdp/rdp_settings.c
index f73ef9d..57e6016 100644
--- a/src/protocols/rdp/rdp_settings.c
+++ b/src/protocols/rdp/rdp_settings.c
@@ -84,6 +84,7 @@ const char* GUAC_RDP_CLIENT_ARGS[] = {
"sftp-private-key",
"sftp-passphrase",
"sftp-directory",
+ "sftp-root-directory",
"sftp-server-alive-interval",
#endif
@@ -368,6 +369,12 @@ enum RDP_ARGS_IDX {
IDX_SFTP_DIRECTORY,
/**
+ * The path of the directory within the SSH server to expose as a
+ * filesystem guac_object. If omitted, "/" will be used by default.
+ */
+ IDX_SFTP_ROOT_DIRECTORY,
+
+ /**
* The interval at which SSH keepalive messages are sent to the server for
* SFTP connections. The default is 0 (disabling keepalives), and a value
* of 1 is automatically increased to 2 by libssh2 to avoid busy loop corner
@@ -784,6 +791,11 @@ guac_rdp_settings* guac_rdp_parse_args(guac_user* user,
guac_user_parse_args_string(user, GUAC_RDP_CLIENT_ARGS, argv,
IDX_SFTP_DIRECTORY, NULL);
+ /* SFTP root directory */
+ settings->sftp_root_directory =
+ guac_user_parse_args_string(user, GUAC_RDP_CLIENT_ARGS, argv,
+ IDX_SFTP_ROOT_DIRECTORY, "/");
+
/* Default keepalive value */
settings->sftp_server_alive_interval =
guac_user_parse_args_int(user, GUAC_RDP_CLIENT_ARGS, argv,
@@ -909,6 +921,7 @@ void guac_rdp_settings_free(guac_rdp_settings* settings) {
#ifdef ENABLE_COMMON_SSH
/* Free SFTP settings */
free(settings->sftp_directory);
+ free(settings->sftp_root_directory);
free(settings->sftp_hostname);
free(settings->sftp_passphrase);
free(settings->sftp_password);
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/rdp/rdp_settings.h
----------------------------------------------------------------------
diff --git a/src/protocols/rdp/rdp_settings.h b/src/protocols/rdp/rdp_settings.h
index 8edb79e..ec540ef 100644
--- a/src/protocols/rdp/rdp_settings.h
+++ b/src/protocols/rdp/rdp_settings.h
@@ -361,6 +361,12 @@ typedef struct guac_rdp_settings {
char* sftp_directory;
/**
+ * The path of the directory within the SSH server to expose as a
+ * filesystem guac_object.
+ */
+ char* sftp_root_directory;
+
+ /**
* The interval at which SSH keepalive messages are sent to the server for
* SFTP connections. The default is 0 (disabling keepalives), and a value
* of 1 is automatically increased to 2 by libssh2 to avoid busy loop corner
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/ssh/settings.c
----------------------------------------------------------------------
diff --git a/src/protocols/ssh/settings.c b/src/protocols/ssh/settings.c
index 8843923..832dcfa 100644
--- a/src/protocols/ssh/settings.c
+++ b/src/protocols/ssh/settings.c
@@ -37,6 +37,7 @@ const char* GUAC_SSH_CLIENT_ARGS[] = {
"font-name",
"font-size",
"enable-sftp",
+ "sftp-root-directory",
"private-key",
"passphrase",
#ifdef ENABLE_SSH_AGENT
@@ -93,6 +94,12 @@ enum SSH_ARGS_IDX {
IDX_ENABLE_SFTP,
/**
+ * The path of the directory within the SSH server to expose as a
+ * filesystem guac_object. If omitted, "/" will be used by default.
+ */
+ IDX_SFTP_ROOT_DIRECTORY,
+
+ /**
* The private key to use for authentication, if any.
*/
IDX_PRIVATE_KEY,
@@ -236,6 +243,11 @@ guac_ssh_settings* guac_ssh_parse_args(guac_user* user,
guac_user_parse_args_boolean(user, GUAC_SSH_CLIENT_ARGS, argv,
IDX_ENABLE_SFTP, false);
+ /* SFTP root directory */
+ settings->sftp_root_directory =
+ guac_user_parse_args_string(user, GUAC_SSH_CLIENT_ARGS, argv,
+ IDX_SFTP_ROOT_DIRECTORY, "/");
+
#ifdef ENABLE_SSH_AGENT
settings->enable_agent =
guac_user_parse_args_boolean(user, GUAC_SSH_CLIENT_ARGS, argv,
@@ -316,6 +328,9 @@ void guac_ssh_settings_free(guac_ssh_settings* settings) {
/* Free requested command */
free(settings->command);
+ /* Free SFTP settings */
+ free(settings->sftp_root_directory);
+
/* Free typescript settings */
free(settings->typescript_name);
free(settings->typescript_path);
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/ssh/settings.h
----------------------------------------------------------------------
diff --git a/src/protocols/ssh/settings.h b/src/protocols/ssh/settings.h
index f49d054..f093023 100644
--- a/src/protocols/ssh/settings.h
+++ b/src/protocols/ssh/settings.h
@@ -145,6 +145,12 @@ typedef struct guac_ssh_settings {
*/
bool enable_sftp;
+ /**
+ * The path of the directory within the SSH server to expose as a
+ * filesystem guac_object.
+ */
+ char* sftp_root_directory;
+
#ifdef ENABLE_SSH_AGENT
/**
* Whether the SSH agent is enabled.
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/ssh/ssh.c
----------------------------------------------------------------------
diff --git a/src/protocols/ssh/ssh.c b/src/protocols/ssh/ssh.c
index 18a0dcb..b9bb59b 100644
--- a/src/protocols/ssh/ssh.c
+++ b/src/protocols/ssh/ssh.c
@@ -266,7 +266,8 @@ void* ssh_client_thread(void* data) {
/* Request SFTP */
ssh_client->sftp_filesystem = guac_common_ssh_create_sftp_filesystem(
- ssh_client->sftp_session, "/", NULL);
+ ssh_client->sftp_session, settings->sftp_root_directory,
+ NULL);
/* Expose filesystem to connection owner */
guac_client_for_owner(client,
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/vnc/settings.c
----------------------------------------------------------------------
diff --git a/src/protocols/vnc/settings.c b/src/protocols/vnc/settings.c
index 697466d..0bcd5ab 100644
--- a/src/protocols/vnc/settings.c
+++ b/src/protocols/vnc/settings.c
@@ -66,6 +66,7 @@ const char* GUAC_VNC_CLIENT_ARGS[] = {
"sftp-private-key",
"sftp-passphrase",
"sftp-directory",
+ "sftp-root-directory",
"sftp-server-alive-interval",
#endif
@@ -230,6 +231,12 @@ enum VNC_ARGS_IDX {
IDX_SFTP_DIRECTORY,
/**
+ * The path of the directory within the SSH server to expose as a
+ * filesystem guac_object. If omitted, "/" will be used by default.
+ */
+ IDX_SFTP_ROOT_DIRECTORY,
+
+ /**
* The interval at which SSH keepalive messages are sent to the server for
* SFTP connections. The default is 0 (disabling keepalives), and a value
* of 1 is automatically incremented to 2 by libssh2 to avoid busy loop corner
@@ -405,6 +412,11 @@ guac_vnc_settings* guac_vnc_parse_args(guac_user* user,
guac_user_parse_args_string(user, GUAC_VNC_CLIENT_ARGS, argv,
IDX_SFTP_DIRECTORY, NULL);
+ /* SFTP root directory */
+ settings->sftp_root_directory =
+ guac_user_parse_args_string(user, GUAC_VNC_CLIENT_ARGS, argv,
+ IDX_SFTP_ROOT_DIRECTORY, "/");
+
/* Default keepalive value */
settings->sftp_server_alive_interval =
guac_user_parse_args_int(user, GUAC_VNC_CLIENT_ARGS, argv,
@@ -447,6 +459,7 @@ void guac_vnc_settings_free(guac_vnc_settings* settings) {
#ifdef ENABLE_COMMON_SSH
/* Free SFTP settings */
free(settings->sftp_directory);
+ free(settings->sftp_root_directory);
free(settings->sftp_hostname);
free(settings->sftp_passphrase);
free(settings->sftp_password);
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/vnc/settings.h
----------------------------------------------------------------------
diff --git a/src/protocols/vnc/settings.h b/src/protocols/vnc/settings.h
index 3c7b258..4fa8eb4 100644
--- a/src/protocols/vnc/settings.h
+++ b/src/protocols/vnc/settings.h
@@ -175,6 +175,12 @@ typedef struct guac_vnc_settings {
char* sftp_directory;
/**
+ * The path of the directory within the SSH server to expose as a
+ * filesystem guac_object.
+ */
+ char* sftp_root_directory;
+
+ /**
* The interval at which SSH keepalive messages are sent to the server for
* SFTP connections. The default is 0 (disabling keepalives), and a value
* of 1 is automatically increased to 2 by libssh2 to avoid busy loop corner
http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/blob/d51e92eb/src/protocols/vnc/vnc.c
----------------------------------------------------------------------
diff --git a/src/protocols/vnc/vnc.c b/src/protocols/vnc/vnc.c
index 2b7263a..38c7cd6 100644
--- a/src/protocols/vnc/vnc.c
+++ b/src/protocols/vnc/vnc.c
@@ -271,8 +271,8 @@ void* guac_vnc_client_thread(void* data) {
/* Load filesystem */
vnc_client->sftp_filesystem =
- guac_common_ssh_create_sftp_filesystem(
- vnc_client->sftp_session, "/", NULL);
+ guac_common_ssh_create_sftp_filesystem(vnc_client->sftp_session,
+ settings->sftp_root_directory, NULL);
/* Expose filesystem to connection owner */
guac_client_for_owner(client,
[3/3] incubator-guacamole-server git commit: GUACAMOLE-303: Merge
Allow root directory of SFTP filesystem to be configured.
Posted by vn...@apache.org.
GUACAMOLE-303: Merge Allow root directory of SFTP filesystem to be configured.
Project: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/commit/07db9808
Tree: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/tree/07db9808
Diff: http://git-wip-us.apache.org/repos/asf/incubator-guacamole-server/diff/07db9808
Branch: refs/heads/master
Commit: 07db9808a09d40d4a4e38fe605ae2c9b453afa84
Parents: 836fc3e d51e92e
Author: Nick Couchman <vn...@apache.org>
Authored: Mon Jul 3 17:47:05 2017 -0400
Committer: Nick Couchman <vn...@apache.org>
Committed: Mon Jul 3 17:47:05 2017 -0400
----------------------------------------------------------------------
src/common-ssh/common-ssh/sftp.h | 21 ++-
src/common-ssh/sftp.c | 259 ++++++++++++++++++++++++++++++++--
src/protocols/rdp/rdp.c | 4 +-
src/protocols/rdp/rdp_settings.c | 13 ++
src/protocols/rdp/rdp_settings.h | 6 +
src/protocols/ssh/settings.c | 15 ++
src/protocols/ssh/settings.h | 6 +
src/protocols/ssh/ssh.c | 3 +-
src/protocols/vnc/settings.c | 13 ++
src/protocols/vnc/settings.h | 6 +
src/protocols/vnc/vnc.c | 4 +-
11 files changed, 332 insertions(+), 18 deletions(-)
----------------------------------------------------------------------