aboutsummaryrefslogtreecommitdiffstats
path: root/vncviewer
diff options
context:
space:
mode:
Diffstat (limited to 'vncviewer')
-rw-r--r--vncviewer/ServerDialog.cxx15
-rw-r--r--vncviewer/ServerDialog.h2
-rw-r--r--vncviewer/parameters.cxx4
-rw-r--r--vncviewer/parameters.h4
-rw-r--r--vncviewer/vncviewer.cxx94
-rw-r--r--vncviewer/vncviewer.h2
6 files changed, 107 insertions, 14 deletions
diff --git a/vncviewer/ServerDialog.cxx b/vncviewer/ServerDialog.cxx
index 25a010a1..4cf35353 100644
--- a/vncviewer/ServerDialog.cxx
+++ b/vncviewer/ServerDialog.cxx
@@ -107,23 +107,22 @@ ServerDialog::~ServerDialog()
}
-const char *ServerDialog::run(const char* servername)
+void ServerDialog::run(const char* servername, char *newservername)
{
ServerDialog dialog;
- static char buffer[256];
dialog.serverName->value(servername);
dialog.show();
while (dialog.shown()) Fl::wait();
- if (dialog.serverName->value() == NULL)
- return NULL;
-
- strncpy(buffer, dialog.serverName->value(), sizeof(buffer));
- buffer[sizeof(buffer)-1] = '\0';
+ if (dialog.serverName->value() == NULL) {
+ newservername[0] = '\0';
+ return;
+ }
- return buffer;
+ strncpy(newservername, dialog.serverName->value(), VNCSERVERNAMELEN);
+ newservername[VNCSERVERNAMELEN - 1] = '\0';
}
void ServerDialog::handleOptions(Fl_Widget *widget, void *data)
diff --git a/vncviewer/ServerDialog.h b/vncviewer/ServerDialog.h
index 402d8ba8..e023659c 100644
--- a/vncviewer/ServerDialog.h
+++ b/vncviewer/ServerDialog.h
@@ -29,7 +29,7 @@ protected:
~ServerDialog();
public:
- static const char *run(const char* servername);
+ static void run(const char* servername, char *newservername);
protected:
static void handleOptions(Fl_Widget *widget, void *data);
diff --git a/vncviewer/parameters.cxx b/vncviewer/parameters.cxx
index 9a3bcd25..d386bd45 100644
--- a/vncviewer/parameters.cxx
+++ b/vncviewer/parameters.cxx
@@ -133,6 +133,10 @@ BoolParameter fullscreenSystemKeys("FullscreenSystemKeys",
"to the server when in full screen mode.",
true);
+#ifndef WIN32
+StringParameter via("via", "Gateway to tunnel via", "");
+#endif
+
const char* IDENTIFIER_STRING = "TigerVNC Configuration file Version 1.0";
VoidParameter* parameterArray[] = {
diff --git a/vncviewer/parameters.h b/vncviewer/parameters.h
index d7144a4b..2b4c0390 100644
--- a/vncviewer/parameters.h
+++ b/vncviewer/parameters.h
@@ -60,6 +60,10 @@ extern rfb::StringParameter menuKey;
extern rfb::BoolParameter fullscreenSystemKeys;
+#ifndef WIN32
+extern rfb::StringParameter via;
+#endif
+
void saveViewerParameters(const char *filename, const char *servername=NULL);
char* loadViewerParameters(const char *filename);
diff --git a/vncviewer/vncviewer.cxx b/vncviewer/vncviewer.cxx
index a512213b..ace1ce62 100644
--- a/vncviewer/vncviewer.cxx
+++ b/vncviewer/vncviewer.cxx
@@ -58,6 +58,7 @@
#include "CConn.h"
#include "ServerDialog.h"
#include "UserDialog.h"
+#include "vncviewer.h"
#ifdef WIN32
#include "resource.h"
@@ -76,6 +77,8 @@ static const char aboutText[] = N_("TigerVNC Viewer %d-bit v%s (%s)\n"
"See http://www.tigervnc.org for information on TigerVNC.");
extern const char* buildTime;
+char vncServerName[VNCSERVERNAMELEN] = { '\0' };
+
static bool exitMainloop = false;
static const char *exitError = NULL;
@@ -267,9 +270,84 @@ static void usage(const char *programName)
exit(1);
}
+#ifndef WIN32
+static int
+interpretViaParam(char *remoteHost, int *remotePort, int localPort)
+{
+ const int SERVER_PORT_OFFSET = 5900;
+ char *pos = strchr(vncServerName, ':');
+ if (pos == NULL)
+ *remotePort = SERVER_PORT_OFFSET;
+ else {
+ int portOffset = SERVER_PORT_OFFSET;
+ size_t len;
+ *pos++ = '\0';
+ len = strlen(pos);
+ if (*pos == ':') {
+ /* Two colons is an absolute port number, not an offset. */
+ pos++;
+ len--;
+ portOffset = 0;
+ }
+ if (!len || strspn (pos, "-0123456789") != len )
+ return 1;
+ *remotePort = atoi(pos) + portOffset;
+ }
+
+ if (*vncServerName != '\0')
+ strncpy(remoteHost, vncServerName, VNCSERVERNAMELEN);
+ else
+ strncpy(remoteHost, "localhost", VNCSERVERNAMELEN);
+
+ remoteHost[VNCSERVERNAMELEN - 1] = '\0';
+
+ snprintf(vncServerName, VNCSERVERNAMELEN, "localhost::%d", localPort);
+ vncServerName[VNCSERVERNAMELEN - 1] = '\0';
+ vlog.error(vncServerName);
+
+ return 0;
+}
+
+static void
+createTunnel(const char *gatewayHost, const char *remoteHost,
+ int remotePort, int localPort)
+{
+ char *cmd = getenv("VNC_VIA_CMD");
+ char *percent;
+ char lport[10], rport[10];
+ sprintf(lport, "%d", localPort);
+ sprintf(rport, "%d", remotePort);
+ setenv("G", gatewayHost, 1);
+ setenv("H", remoteHost, 1);
+ setenv("R", rport, 1);
+ setenv("L", lport, 1);
+ vlog.error("%s, %s, %d, %d", gatewayHost, remoteHost, rport, lport);
+ if (!cmd)
+ cmd = "/usr/bin/ssh -f -L \"$L\":\"$H\":\"$R\" \"$G\" sleep 20";
+ /* Compatibility with TigerVNC's method. */
+ while ((percent = strchr(cmd, '%')) != NULL)
+ *percent = '$';
+ system(cmd);
+}
+
+static int mktunnel()
+{
+ const char *gatewayHost;
+ char remoteHost[VNCSERVERNAMELEN];
+ int localPort = findFreeTcpPort();
+ int remotePort;
+
+ gatewayHost = strDup(via.getValueStr());
+ if (interpretViaParam(remoteHost, &remotePort, localPort) != 0)
+ return 1;
+ createTunnel(gatewayHost, remoteHost, remotePort, localPort);
+
+ return 0;
+}
+#endif /* !WIN32 */
+
int main(int argc, char** argv)
{
- const char* vncServerName = NULL;
UserDialog dlg;
setlocale(LC_ALL, "");
@@ -332,7 +410,8 @@ int main(int argc, char** argv)
usage(argv[0]);
}
- vncServerName = argv[i];
+ strncpy(vncServerName, argv[i], VNCSERVERNAMELEN);
+ vncServerName[VNCSERVERNAMELEN - 1] = '\0';
}
if (!::autoSelect.hasBeenSet()) {
@@ -363,12 +442,17 @@ int main(int argc, char** argv)
CSecurityTLS::msg = &dlg;
#endif
- if (vncServerName == NULL) {
- vncServerName = ServerDialog::run(defaultServerName);
- if ((vncServerName == NULL) || (vncServerName[0] == '\0'))
+ if (vncServerName[0] == '\0') {
+ ServerDialog::run(defaultServerName, vncServerName);
+ if (vncServerName[0] == '\0')
return 1;
}
+#ifndef WIN32
+ if (strlen (via.getValueStr()) > 0 && mktunnel() != 0)
+ usage(argv[0]);
+#endif
+
CConn *cc = new CConn(vncServerName);
while (!exitMainloop) {
diff --git a/vncviewer/vncviewer.h b/vncviewer/vncviewer.h
index 443dbea3..089fb270 100644
--- a/vncviewer/vncviewer.h
+++ b/vncviewer/vncviewer.h
@@ -19,6 +19,8 @@
#ifndef __VNCVIEWER_H__
#define __VNCVIEWER_H__
+#define VNCSERVERNAMELEN 64
+
void exit_vncviewer(const char *error = NULL);
void about_vncviewer();