summaryrefslogtreecommitdiffstats
path: root/libssh/socket.c
diff options
context:
space:
mode:
Diffstat (limited to 'libssh/socket.c')
-rw-r--r--libssh/socket.c50
1 files changed, 50 insertions, 0 deletions
diff --git a/libssh/socket.c b/libssh/socket.c
index 933119f7..3ac91caf 100644
--- a/libssh/socket.c
+++ b/libssh/socket.c
@@ -32,6 +32,7 @@
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/un.h>
+extern const char **environ;
#endif
#include "libssh/priv.h"
#include "libssh/socket.h"
@@ -39,6 +40,7 @@
#include "libssh/poll.h"
#include "libssh/session.h"
+
/** \defgroup ssh_socket SSH Sockets
* \addtogroup ssh_socket
* @{
@@ -658,6 +660,54 @@ int ssh_socket_get_status(struct socket *s) {
return r;
}
+#ifndef _WIN32
+/**
+ * @internal
+ * @brief executes a command and redirect input and outputs
+ * @param command command to execute
+ * @param in input file descriptor
+ * @param out output file descriptor
+ */
+void ssh_execute_command(const char *command, socket_t in, socket_t out){
+ const char *args[]={"/bin/sh","-c",command,NULL};
+ /* redirect in and out to stdin, stdout and stderr */
+ dup2(in, 0);
+ dup2(out,1);
+ dup2(out,2);
+ close(in);
+ close(out);
+ execve(args[0],(char * const *)args,(char * const *)environ);
+ exit(1);
+}
+
+/**
+ * @internal
+ * @brief Open a socket on a ProxyCommand
+ * This call will always be nonblocking.
+ * @param s socket to connect.
+ * @param command Command to execute.
+ * @returns SSH_OK socket is being connected.
+ * @returns SSH_ERROR error while executing the command.
+ */
+
+socket_t ssh_socket_connect_proxycommand(ssh_session session,
+ const char *command){
+ socket_t fd[2];
+ int pid;
+ enter_function();
+ socketpair(AF_UNIX,SOCK_STREAM,0,fd);
+ pid = fork();
+ if(pid == 0){
+ ssh_execute_command(command,fd[1],fd[1]);
+ }
+ close(fd[1]);
+ ssh_log(session,SSH_LOG_PROTOCOL,"ProxyCommand connection pipe: [%d,%d]",fd[0],fd[1]);
+ return fd[0];
+}
+
+#endif /* _WIN32 */
+
+
/** @}
*/
/* vim: set ts=2 sw=2 et cindent: */