A startup GUI for running TightVNC over SSH
Here's a little utility I put together to make it a little easier to startup TightVNC to run over SSH. Although TightVNC supports SSH itself, I wanted to be able to start it up without the need to always start it in a terminal window. So I got to thinking how I could use zenity with some scripts to do this. And here's what I came up with.
Essentially, what this utility does is use the ssh-agent utility to register your public SSH identities - using ssh-add - so that you can start up an SSH session without having to enter a password. The key piece to making this whole thing work as a GUI is by use of the gnome-ssh-askpass utility included with OpenSSH.
First off, set some passphrases -- So the first thing I would suggest is that you set a passphrase on all your SSH identities, otherwise someone could grab them, and gain entry to your account in various ways. The easiest way to do this is with ssh-keygen
ssh-keygen -p -f ~/.ssh/id_dsa ssh-keygen -p -f ~/.ssh/id_rsa ssh-keygen -p -f ~/.ssh/identity
Whew. I feel more secure already.
Up next, configure some authorized keys -- Ok, so now that you have some passphrases set, you need to tell SSH that they are authorized to allow connections with. The key here is that you want to do this on the system you are running the VNC server on. What you need to do is grab the id_dsa.pub and id_rsa.pub files and put them in the authorized_keys file on the target.
source% scp ~/.ssh/id_rsa.pub target:. source% scp ~/.ssh/id_dsa.pub target:. target% cat ~/id_rsa.pub >> ~/.ssh/authorized_keys target% cat ~/id_dsa.pub >> ~/.ssh/authorized_keys
This should be enough to enable to to ssh to the target machine without a passowrd, it will however require you to enter a passphrase instead. This is good.
Configuring a password popup -- One nice little feature of ssh-add is that it can defer to an optional (GUI) utility to ask for passphrases. And in fact if you look in the contrib/ folder of the OpenSSH source, you will see a couple utilities for GNOME, the most relevant one now days being gnome-ssh-askpass2.c.
You can get ssh-add to invoke this by setting the environment variable SSH_ASKPASS to the path of the utility and invoking a "ssh-add < /dev/null".
Now, this is all well and good, but I wanted to generalize this a little bit so I can use it to ask for passwords in other contexts. First and foremost, TightVNC requires a password. And the gnome-ssh-askpass utility spits out some verbage specific to OpenSSH. I wanted to remove that. So a quick hack a the source and gnome-ssh-askpass became gnome-askpass. Here's the diff, which you can use with patch to enable my mods.
33,35c33,35
< * "GNOME_SSH_ASKPASS_GRAB_SERVER=true" then gnome-ssh-askpass will grab
< * the X server. If you set "GNOME_SSH_ASKPASS_GRAB_POINTER=true", then the
< * pointer will be grabbed too. These may have some benefit to security if
---
> * "GNOME_ASKPASS_GRAB_SERVER=true" then gnome-ssh-askpass will grab
> * the X server. If you set "GNOME_ASKPASS_GRAB_POINTER=true", then the
> * pointer will be grabbed too. These may have some benefit to security if
88a89
> char *title;
95,96c96,97
< grab_server = (getenv("GNOME_SSH_ASKPASS_GRAB_SERVER") != NULL);
< grab_pointer = (getenv("GNOME_SSH_ASKPASS_GRAB_POINTER") != NULL);
---
> grab_server = (getenv("GNOME_ASKPASS_GRAB_SERVER") != NULL);
> grab_pointer = (getenv("GNOME_ASKPASS_GRAB_POINTER") != NULL);
111,112c112,115
<
< gtk_window_set_title(GTK_WINDOW(dialog), "OpenSSH");
---
>
> title = getenv("GNOME_ASKPASS_TITLE");
> if (title == NULL) title = "OpenSSH";
> gtk_window_set_title(GTK_WINDOW(dialog), title);
With these mods, you can set a GNOME_ASKPASS_TITLE environment variable to change the title.
Finally, putting it all together -- Are you still with me? Now here is the final script that I use to fire up TightVNC. When you use the script it prompts for three things
- First, it asks which VNC Server (host:port) to connect to
- Next, it will ask for the VNC Server password
- Next, it will prompt you to enter your SSH Identity passphrase(s)
And now, without further adieu...
#! /bin/sh
#
# Script to put a GUI front end around TightVNC over SSH
#
# Author: Joseph Mocker, Sun Microsystems.
#
# This script works only with TightVNC
#
# Prompt for VNC Server
server=`zenity --entry --title="VNC Server" --text="Connect to server (host:port):"`
if [ "x$server" = "x" ]; then
exit 0
fi
# Prompt for VNC Password
GNOME_ASKPASS_TITLE="VNC Server"
export GNOME_ASKPASS_TITLE
passwd=`gnome-askpass Password for server ${server}:"`
host=`echo $server | cut -d: -f1`
port=`echo $server | cut -d: -f2`
echo $passwd | vncpasswd -f > /tmp/tmpvnc.$$
# Start up a "private" SSH agent
eval `ssh-agent -s`
# Register SSH Identities with the agent
SSH_ASKPASS=gnome-askpass
export SSH_ASKPASS
unset GNOME_ASKPASS_TITLE
ssh-add < /dev/null
vncviewer -passwd /tmp/tmpvnc.$$ -encodings "hextile zlib raw" -via $host localhost:$port &
# Give it a little bit to make the connection
sleep 10
# Kill the "private" SSH Agent
eval `ssh-agent -k`
# Cleanup
rm /tmp/tmpvnc.$$

Posted by Shawn Holwegner on June 04, 2007 at 01:24 AM PDT #