• Skip to content
  • Skip to link menu
Trinity API Reference
  • Trinity API Reference
  • tdesu
 

tdesu

  • tdesu
ssh.cpp
1 /*
2 *
3 * $Id$
4 *
5 * This file is part of the KDE project, module tdesu.
6 * Copyright (C) 2000 Geert Jansen <jansen@kde.org>
7 *
8 * This is free software; you can use this library under the GNU Library
9 * General Public License, version 2. See the file "COPYING.LIB" for the
10 * exact licensing terms.
11 *
12 * ssh.cpp: Execute a program on a remote machine using ssh.
13 */
14 
15 #include <config.h>
16 
17 #include <stdio.h>
18 #include <stdlib.h>
19 #include <unistd.h>
20 #include <fcntl.h>
21 #include <signal.h>
22 #include <errno.h>
23 #include <string.h>
24 #include <ctype.h>
25 #include <signal.h>
26 #include <time.h>
27 
28 #include <sys/types.h>
29 #include <sys/stat.h>
30 
31 #include <tqglobal.h>
32 #include <tqcstring.h>
33 
34 #include <kdebug.h>
35 #include <tdelocale.h>
36 #include <kstandarddirs.h>
37 
38 #include "ssh.h"
39 #include "kcookie.h"
40 
41 
42 SshProcess::SshProcess(const TQCString &host, const TQCString &user, const TQCString &command)
43 {
44  m_Host = host;
45  m_User = user;
46  m_Command = command;
47  m_Stub = "tdesu_stub";
48  srand(time(0L));
49 }
50 
51 
52 SshProcess::~SshProcess()
53 {
54 }
55 
56 
57 void SshProcess::setStub(const TQCString &stub)
58 {
59  m_Stub = stub;
60 }
61 
62 
63 int SshProcess::checkInstall(const char *password)
64 {
65  return exec(password, 1);
66 }
67 
68 
69 int SshProcess::checkNeedPassword()
70 {
71  return exec(0L, 2);
72 }
73 
74 
75 int SshProcess::exec(const char *password, int check)
76 {
77  if (check)
78  setTerminal(true);
79 
80  QCStringList args;
81  args += "-l"; args += m_User;
82  args += "-o"; args += "StrictHostKeyChecking=no";
83  args += m_Host; args += m_Stub;
84 
85  if (StubProcess::exec("ssh", args) < 0)
86  {
87  return check ? SshNotFound : -1;
88  }
89 
90  int ret = ConverseSsh(password, check);
91  if (ret < 0)
92  {
93  if (!check)
94  kdError(900) << k_lineinfo << "Conversation with ssh failed\n";
95  return ret;
96  }
97  if (check == 2)
98  {
99  if (ret == 1)
100  {
101  kill(m_Pid, SIGTERM);
102  waitForChild();
103  }
104  return ret;
105  }
106 
107  if (m_bErase && password)
108  {
109  char *ptr = const_cast<char *>(password);
110  const uint plen = strlen(password);
111  for (unsigned i=0; i < plen; i++)
112  ptr[i] = '\000';
113  }
114 
115  ret = ConverseStub(check);
116  if (ret < 0)
117  {
118  if (!check)
119  kdError(900) << k_lineinfo << "Converstation with tdesu_stub failed\n";
120  return ret;
121  }
122  else if (ret == 1)
123  {
124  kill(m_Pid, SIGTERM);
125  waitForChild();
126  ret = SshIncorrectPassword;
127  }
128 
129  if (check == 1)
130  {
131  waitForChild();
132  return 0;
133  }
134 
135  setExitString("Waiting for forwarded connections to terminate");
136  ret = waitForChild();
137  return ret;
138 }
139 
140 /*
141 * Create a port forwarding for DCOP. For the remote port, we take a pseudo
142 * random number between 10k and 50k. This is not ok, of course, but I see
143 * no other way. There is, afaik, no security issue involved here. If the port
144 * happens to be occupied, ssh will refuse to start.
145 *
146 * 14/SEP/2000: DCOP forwarding is not used anymore.
147 */
148 
149 TQCString SshProcess::dcopForward()
150 {
151  TQCString result;
152 
153  setDcopTransport("tcp");
154 
155  TQCString srv = StubProcess::dcopServer();
156  if (srv.isEmpty())
157  return result;
158 
159  int i = srv.find('/');
160  if (i == -1)
161  return result;
162  if (srv.left(i) != "tcp")
163  return result;
164  int j = srv.find(':', ++i);
165  if (j == -1)
166  return result;
167  TQCString host = srv.mid(i, j-i);
168  bool ok;
169  int port = srv.mid(++j).toInt(&ok);
170  if (!ok)
171  return result;
172 
173  m_dcopPort = 10000 + (int) ((40000.0 * rand()) / (1.0 + RAND_MAX));
174  result.sprintf("%d:%s:%d", m_dcopPort, host.data(), port);
175  return result;
176 }
177 
178 
179 /*
180 * Conversation with ssh.
181 * If check is 0, this waits for either a "Password: " prompt,
182 * or the header of the stub. If a prompt is received, the password is
183 * written back. Used for running a command.
184 * If check is 1, operation is the same as 0 except that if a stub header is
185 * received, the stub is stopped with the "stop" command. This is used for
186 * checking a password.
187 * If check is 2, operation is the same as 1, except that no password is
188 * written. The prompt is saved to m_Prompt. Used for checking the need for
189 * a password.
190 */
191 
192 int SshProcess::ConverseSsh(const char *password, int check)
193 {
194  unsigned i, j, colon;
195 
196  TQCString line;
197  int state = 0;
198 
199  while (state < 2)
200  {
201  line = readLine();
202  const uint len = line.length();
203  if (line.isNull())
204  return -1;
205 
206  switch (state) {
207  case 0:
208  // Check for "tdesu_stub" header.
209  if (line == "tdesu_stub")
210  {
211  unreadLine(line);
212  return 0;
213  }
214 
215  // Match "Password: " with the regex ^[^:]+:[\w]*$.
216  for (i=0,j=0,colon=0; i<len; i++)
217  {
218  if (line[i] == ':')
219  {
220  j = i; colon++;
221  continue;
222  }
223  if (!isspace(line[i]))
224  j++;
225  }
226  if ((colon == 1) && (line[j] == ':'))
227  {
228  if (check == 2)
229  {
230  m_Prompt = line;
231  return SshNeedsPassword;
232  }
233  WaitSlave();
234  write(m_Fd, password, strlen(password));
235  write(m_Fd, "\n", 1);
236  state++;
237  break;
238  }
239 
240  // Warning/error message.
241  m_Error += line; m_Error += "\n";
242  if (m_bTerminal)
243  fprintf(stderr, "ssh: %s\n", line.data());
244  break;
245 
246  case 1:
247  if (line.isEmpty())
248  {
249  state++;
250  break;
251  }
252  return -1;
253  }
254  }
255  return 0;
256 }
257 
258 
259 // Display redirection is handled by ssh natively.
260 TQCString SshProcess::display()
261 {
262  return "no";
263 }
264 
265 
266 TQCString SshProcess::displayAuth()
267 {
268  return "no";
269 }
270 
271 
272 // Return the remote end of the forwarded connection.
273 TQCString SshProcess::dcopServer()
274 {
275  return TQCString().sprintf("tcp/localhost:%d", m_dcopPort);
276 }
277 
278 void SshProcess::virtual_hook( int id, void* data )
279 { StubProcess::virtual_hook( id, data ); }
SshProcess::dcopServer
virtual TQCString dcopServer()
See display.
Definition: ssh.cpp:273
SshProcess::display
virtual TQCString display()
This virtual function can be overloaded when special behavior is desired.
Definition: ssh.cpp:260
PtyProcess::waitForChild
int waitForChild()
Waits for the child to exit.
Definition: process.cpp:486
PtyProcess::WaitSlave
int WaitSlave()
Waits until the pty has cleared the ECHO flag.
Definition: process.cpp:412
PtyProcess::exec
int exec(const TQCString &command, const QCStringList &args)
Forks off and execute a command.
Definition: process.cpp:324
PtyProcess::unreadLine
void unreadLine(const TQCString &line, bool addNewline=true)
Puts back a line of input.
Definition: process.cpp:311
PtyProcess::readLine
TQCString readLine(bool block=true)
Reads a line from the program's standard out.
Definition: process.cpp:175
SshProcess::exec
int exec(const char *password, int check=0)
Executes the command.
Definition: ssh.cpp:75
PtyProcess::setExitString
void setExitString(const TQCString &exit)
Sets the exit string.
Definition: process.h:83
StubProcess::dcopServer
virtual TQCString dcopServer()
See display.
Definition: stub.h:110
SshProcess::setStub
void setStub(const TQCString &stub)
Sets the localtion of the remote stub.
Definition: ssh.cpp:57
StubProcess::setDcopTransport
void setDcopTransport(const TQCString &dcopTransport)
Specify dcop transport.
Definition: stub.h:41
PtyProcess::setTerminal
void setTerminal(bool terminal)
Enables/disables terminal output.
Definition: process.h:105
SshProcess::checkNeedPassword
int checkNeedPassword()
Checks if the current user@host needs a password.
Definition: ssh.cpp:69
SshProcess::checkInstall
int checkInstall(const char *password)
Checks if the stub is installed and if the password is correct.
Definition: ssh.cpp:63
StubProcess::ConverseStub
int ConverseStub(int check)
Exchange all parameters with tdesu_stub.
Definition: stub.cpp:80

tdesu

Skip menu "tdesu"
  • Main Page
  • Class Hierarchy
  • Alphabetical List
  • Class List
  • File List
  • Class Members
  • Related Pages

tdesu

Skip menu "tdesu"
  • arts
  • dcop
  • dnssd
  • interfaces
  •   kspeech
  •     interface
  •     library
  •   tdetexteditor
  • kate
  • kded
  • kdoctools
  • kimgio
  • kjs
  • libtdemid
  • libtdescreensaver
  •     tdecore
  • tdeabc
  • tdecmshell
  • tdecore
  • tdefx
  • tdehtml
  • tdeinit
  • tdeio
  •   bookmarks
  •   httpfilter
  •   kpasswdserver
  •   kssl
  • tdeioslave
  •   http
  •   tdefile
  •   tdeio
  •   tdeioexec
  • tdemdi
  •   tdemdi
  • tdenewstuff
  • tdeparts
  • tdeprint
  • tderandr
  • tderesources
  • tdespell2
  • tdesu
  • tdeui
  • tdeunittest
  • tdeutils
  • tdewallet
Generated for tdesu by doxygen 1.8.8
This website is maintained by Timothy Pearson.