smtp: use the upload buffer size for scratch buffer malloc
[platform/upstream/curl.git] / lib / ssh.c
1 /***************************************************************************
2  *                                  _   _ ____  _
3  *  Project                     ___| | | |  _ \| |
4  *                             / __| | | | |_) | |
5  *                            | (__| |_| |  _ <| |___
6  *                             \___|\___/|_| \_\_____|
7  *
8  * Copyright (C) 1998 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
9  *
10  * This software is licensed as described in the file COPYING, which
11  * you should have received as part of this distribution. The terms
12  * are also available at https://curl.haxx.se/docs/copyright.html.
13  *
14  * You may opt to use, copy, modify, merge, publish, distribute and/or sell
15  * copies of the Software, and permit persons to whom the Software is
16  * furnished to do so, under the terms of the COPYING file.
17  *
18  * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
19  * KIND, either express or implied.
20  *
21  ***************************************************************************/
22
23 /* #define CURL_LIBSSH2_DEBUG */
24
25 #include "curl_setup.h"
26
27 #ifdef USE_LIBSSH2
28
29 #include <limits.h>
30
31 #include <libssh2.h>
32 #include <libssh2_sftp.h>
33
34 #ifdef HAVE_FCNTL_H
35 #include <fcntl.h>
36 #endif
37
38 #ifdef HAVE_NETINET_IN_H
39 #include <netinet/in.h>
40 #endif
41 #ifdef HAVE_ARPA_INET_H
42 #include <arpa/inet.h>
43 #endif
44 #ifdef HAVE_UTSNAME_H
45 #include <sys/utsname.h>
46 #endif
47 #ifdef HAVE_NETDB_H
48 #include <netdb.h>
49 #endif
50 #ifdef __VMS
51 #include <in.h>
52 #include <inet.h>
53 #endif
54
55 #if (defined(NETWARE) && defined(__NOVELL_LIBC__))
56 #undef in_addr_t
57 #define in_addr_t unsigned long
58 #endif
59
60 #include <curl/curl.h>
61 #include "urldata.h"
62 #include "sendf.h"
63 #include "hostip.h"
64 #include "progress.h"
65 #include "transfer.h"
66 #include "escape.h"
67 #include "http.h" /* for HTTP proxy tunnel stuff */
68 #include "ssh.h"
69 #include "url.h"
70 #include "speedcheck.h"
71 #include "getinfo.h"
72 #include "strdup.h"
73 #include "strcase.h"
74 #include "vtls/vtls.h"
75 #include "connect.h"
76 #include "strerror.h"
77 #include "inet_ntop.h"
78 #include "parsedate.h" /* for the week day and month names */
79 #include "sockaddr.h" /* required for Curl_sockaddr_storage */
80 #include "strtoofft.h"
81 #include "multiif.h"
82 #include "select.h"
83 #include "warnless.h"
84
85 /* The last 3 #include files should be in this order */
86 #include "curl_printf.h"
87 #include "curl_memory.h"
88 #include "curl_path.h"
89 #include "memdebug.h"
90
91 #if LIBSSH2_VERSION_NUM >= 0x010206
92 /* libssh2_sftp_statvfs and friends were added in 1.2.6 */
93 #define HAS_STATVFS_SUPPORT 1
94 #endif
95
96 #define sftp_libssh2_last_error(s) curlx_ultosi(libssh2_sftp_last_error(s))
97
98 #define sftp_libssh2_realpath(s,p,t,m) \
99         libssh2_sftp_symlink_ex((s), (p), curlx_uztoui(strlen(p)), \
100                                 (t), (m), LIBSSH2_SFTP_REALPATH)
101
102
103 /* Local functions: */
104 static const char *sftp_libssh2_strerror(int err);
105 static LIBSSH2_ALLOC_FUNC(my_libssh2_malloc);
106 static LIBSSH2_REALLOC_FUNC(my_libssh2_realloc);
107 static LIBSSH2_FREE_FUNC(my_libssh2_free);
108
109 static CURLcode ssh_connect(struct connectdata *conn, bool *done);
110 static CURLcode ssh_multi_statemach(struct connectdata *conn, bool *done);
111 static CURLcode ssh_do(struct connectdata *conn, bool *done);
112
113 static CURLcode scp_done(struct connectdata *conn,
114                          CURLcode, bool premature);
115 static CURLcode scp_doing(struct connectdata *conn,
116                           bool *dophase_done);
117 static CURLcode scp_disconnect(struct connectdata *conn, bool dead_connection);
118
119 static CURLcode sftp_done(struct connectdata *conn,
120                           CURLcode, bool premature);
121 static CURLcode sftp_doing(struct connectdata *conn,
122                            bool *dophase_done);
123 static CURLcode sftp_disconnect(struct connectdata *conn, bool dead);
124 static
125 CURLcode sftp_perform(struct connectdata *conn,
126                       bool *connected,
127                       bool *dophase_done);
128
129 static int ssh_getsock(struct connectdata *conn,
130                        curl_socket_t *sock, /* points to numsocks number
131                                                of sockets */
132                        int numsocks);
133
134 static int ssh_perform_getsock(const struct connectdata *conn,
135                                curl_socket_t *sock, /* points to numsocks
136                                                        number of sockets */
137                                int numsocks);
138
139 static CURLcode ssh_setup_connection(struct connectdata *conn);
140
141 /*
142  * SCP protocol handler.
143  */
144
145 const struct Curl_handler Curl_handler_scp = {
146   "SCP",                                /* scheme */
147   ssh_setup_connection,                 /* setup_connection */
148   ssh_do,                               /* do_it */
149   scp_done,                             /* done */
150   ZERO_NULL,                            /* do_more */
151   ssh_connect,                          /* connect_it */
152   ssh_multi_statemach,                  /* connecting */
153   scp_doing,                            /* doing */
154   ssh_getsock,                          /* proto_getsock */
155   ssh_getsock,                          /* doing_getsock */
156   ZERO_NULL,                            /* domore_getsock */
157   ssh_perform_getsock,                  /* perform_getsock */
158   scp_disconnect,                       /* disconnect */
159   ZERO_NULL,                            /* readwrite */
160   ZERO_NULL,                            /* connection_check */
161   PORT_SSH,                             /* defport */
162   CURLPROTO_SCP,                        /* protocol */
163   PROTOPT_DIRLOCK | PROTOPT_CLOSEACTION
164   | PROTOPT_NOURLQUERY                  /* flags */
165 };
166
167
168 /*
169  * SFTP protocol handler.
170  */
171
172 const struct Curl_handler Curl_handler_sftp = {
173   "SFTP",                               /* scheme */
174   ssh_setup_connection,                 /* setup_connection */
175   ssh_do,                               /* do_it */
176   sftp_done,                            /* done */
177   ZERO_NULL,                            /* do_more */
178   ssh_connect,                          /* connect_it */
179   ssh_multi_statemach,                  /* connecting */
180   sftp_doing,                           /* doing */
181   ssh_getsock,                          /* proto_getsock */
182   ssh_getsock,                          /* doing_getsock */
183   ZERO_NULL,                            /* domore_getsock */
184   ssh_perform_getsock,                  /* perform_getsock */
185   sftp_disconnect,                      /* disconnect */
186   ZERO_NULL,                            /* readwrite */
187   ZERO_NULL,                            /* connection_check */
188   PORT_SSH,                             /* defport */
189   CURLPROTO_SFTP,                       /* protocol */
190   PROTOPT_DIRLOCK | PROTOPT_CLOSEACTION
191   | PROTOPT_NOURLQUERY                  /* flags */
192 };
193
194 static void
195 kbd_callback(const char *name, int name_len, const char *instruction,
196              int instruction_len, int num_prompts,
197              const LIBSSH2_USERAUTH_KBDINT_PROMPT *prompts,
198              LIBSSH2_USERAUTH_KBDINT_RESPONSE *responses,
199              void **abstract)
200 {
201   struct connectdata *conn = (struct connectdata *)*abstract;
202
203 #ifdef CURL_LIBSSH2_DEBUG
204   fprintf(stderr, "name=%s\n", name);
205   fprintf(stderr, "name_len=%d\n", name_len);
206   fprintf(stderr, "instruction=%s\n", instruction);
207   fprintf(stderr, "instruction_len=%d\n", instruction_len);
208   fprintf(stderr, "num_prompts=%d\n", num_prompts);
209 #else
210   (void)name;
211   (void)name_len;
212   (void)instruction;
213   (void)instruction_len;
214 #endif  /* CURL_LIBSSH2_DEBUG */
215   if(num_prompts == 1) {
216     responses[0].text = strdup(conn->passwd);
217     responses[0].length = curlx_uztoui(strlen(conn->passwd));
218   }
219   (void)prompts;
220   (void)abstract;
221 } /* kbd_callback */
222
223 static CURLcode sftp_libssh2_error_to_CURLE(int err)
224 {
225   switch(err) {
226     case LIBSSH2_FX_OK:
227       return CURLE_OK;
228
229     case LIBSSH2_FX_NO_SUCH_FILE:
230     case LIBSSH2_FX_NO_SUCH_PATH:
231       return CURLE_REMOTE_FILE_NOT_FOUND;
232
233     case LIBSSH2_FX_PERMISSION_DENIED:
234     case LIBSSH2_FX_WRITE_PROTECT:
235     case LIBSSH2_FX_LOCK_CONFlICT:
236       return CURLE_REMOTE_ACCESS_DENIED;
237
238     case LIBSSH2_FX_NO_SPACE_ON_FILESYSTEM:
239     case LIBSSH2_FX_QUOTA_EXCEEDED:
240       return CURLE_REMOTE_DISK_FULL;
241
242     case LIBSSH2_FX_FILE_ALREADY_EXISTS:
243       return CURLE_REMOTE_FILE_EXISTS;
244
245     case LIBSSH2_FX_DIR_NOT_EMPTY:
246       return CURLE_QUOTE_ERROR;
247
248     default:
249       break;
250   }
251
252   return CURLE_SSH;
253 }
254
255 static CURLcode libssh2_session_error_to_CURLE(int err)
256 {
257   switch(err) {
258     /* Ordered by order of appearance in libssh2.h */
259     case LIBSSH2_ERROR_NONE:
260       return CURLE_OK;
261
262     /* This is the error returned by libssh2_scp_recv2
263      * on unknown file */
264     case LIBSSH2_ERROR_SCP_PROTOCOL:
265       return CURLE_REMOTE_FILE_NOT_FOUND;
266
267     case LIBSSH2_ERROR_SOCKET_NONE:
268       return CURLE_COULDNT_CONNECT;
269
270     case LIBSSH2_ERROR_ALLOC:
271       return CURLE_OUT_OF_MEMORY;
272
273     case LIBSSH2_ERROR_SOCKET_SEND:
274       return CURLE_SEND_ERROR;
275
276     case LIBSSH2_ERROR_HOSTKEY_INIT:
277     case LIBSSH2_ERROR_HOSTKEY_SIGN:
278     case LIBSSH2_ERROR_PUBLICKEY_UNRECOGNIZED:
279     case LIBSSH2_ERROR_PUBLICKEY_UNVERIFIED:
280       return CURLE_PEER_FAILED_VERIFICATION;
281
282     case LIBSSH2_ERROR_PASSWORD_EXPIRED:
283       return CURLE_LOGIN_DENIED;
284
285     case LIBSSH2_ERROR_SOCKET_TIMEOUT:
286     case LIBSSH2_ERROR_TIMEOUT:
287       return CURLE_OPERATION_TIMEDOUT;
288
289     case LIBSSH2_ERROR_EAGAIN:
290       return CURLE_AGAIN;
291   }
292
293   /* TODO: map some more of the libssh2 errors to the more appropriate CURLcode
294      error code, and possibly add a few new SSH-related one. We must however
295      not return or even depend on libssh2 errors in the public libcurl API */
296
297   return CURLE_SSH;
298 }
299
300 static LIBSSH2_ALLOC_FUNC(my_libssh2_malloc)
301 {
302   (void)abstract; /* arg not used */
303   return malloc(count);
304 }
305
306 static LIBSSH2_REALLOC_FUNC(my_libssh2_realloc)
307 {
308   (void)abstract; /* arg not used */
309   return realloc(ptr, count);
310 }
311
312 static LIBSSH2_FREE_FUNC(my_libssh2_free)
313 {
314   (void)abstract; /* arg not used */
315   if(ptr) /* ssh2 agent sometimes call free with null ptr */
316     free(ptr);
317 }
318
319 /*
320  * SSH State machine related code
321  */
322 /* This is the ONLY way to change SSH state! */
323 static void state(struct connectdata *conn, sshstate nowstate)
324 {
325   struct ssh_conn *sshc = &conn->proto.sshc;
326 #if defined(DEBUGBUILD) && !defined(CURL_DISABLE_VERBOSE_STRINGS)
327   /* for debug purposes */
328   static const char * const names[] = {
329     "SSH_STOP",
330     "SSH_INIT",
331     "SSH_S_STARTUP",
332     "SSH_HOSTKEY",
333     "SSH_AUTHLIST",
334     "SSH_AUTH_PKEY_INIT",
335     "SSH_AUTH_PKEY",
336     "SSH_AUTH_PASS_INIT",
337     "SSH_AUTH_PASS",
338     "SSH_AUTH_AGENT_INIT",
339     "SSH_AUTH_AGENT_LIST",
340     "SSH_AUTH_AGENT",
341     "SSH_AUTH_HOST_INIT",
342     "SSH_AUTH_HOST",
343     "SSH_AUTH_KEY_INIT",
344     "SSH_AUTH_KEY",
345     "SSH_AUTH_GSSAPI",
346     "SSH_AUTH_DONE",
347     "SSH_SFTP_INIT",
348     "SSH_SFTP_REALPATH",
349     "SSH_SFTP_QUOTE_INIT",
350     "SSH_SFTP_POSTQUOTE_INIT",
351     "SSH_SFTP_QUOTE",
352     "SSH_SFTP_NEXT_QUOTE",
353     "SSH_SFTP_QUOTE_STAT",
354     "SSH_SFTP_QUOTE_SETSTAT",
355     "SSH_SFTP_QUOTE_SYMLINK",
356     "SSH_SFTP_QUOTE_MKDIR",
357     "SSH_SFTP_QUOTE_RENAME",
358     "SSH_SFTP_QUOTE_RMDIR",
359     "SSH_SFTP_QUOTE_UNLINK",
360     "SSH_SFTP_QUOTE_STATVFS",
361     "SSH_SFTP_GETINFO",
362     "SSH_SFTP_FILETIME",
363     "SSH_SFTP_TRANS_INIT",
364     "SSH_SFTP_UPLOAD_INIT",
365     "SSH_SFTP_CREATE_DIRS_INIT",
366     "SSH_SFTP_CREATE_DIRS",
367     "SSH_SFTP_CREATE_DIRS_MKDIR",
368     "SSH_SFTP_READDIR_INIT",
369     "SSH_SFTP_READDIR",
370     "SSH_SFTP_READDIR_LINK",
371     "SSH_SFTP_READDIR_BOTTOM",
372     "SSH_SFTP_READDIR_DONE",
373     "SSH_SFTP_DOWNLOAD_INIT",
374     "SSH_SFTP_DOWNLOAD_STAT",
375     "SSH_SFTP_CLOSE",
376     "SSH_SFTP_SHUTDOWN",
377     "SSH_SCP_TRANS_INIT",
378     "SSH_SCP_UPLOAD_INIT",
379     "SSH_SCP_DOWNLOAD_INIT",
380     "SSH_SCP_DOWNLOAD",
381     "SSH_SCP_DONE",
382     "SSH_SCP_SEND_EOF",
383     "SSH_SCP_WAIT_EOF",
384     "SSH_SCP_WAIT_CLOSE",
385     "SSH_SCP_CHANNEL_FREE",
386     "SSH_SESSION_DISCONNECT",
387     "SSH_SESSION_FREE",
388     "QUIT"
389   };
390
391   /* a precaution to make sure the lists are in sync */
392   DEBUGASSERT(sizeof(names)/sizeof(names[0]) == SSH_LAST);
393
394   if(sshc->state != nowstate) {
395     infof(conn->data, "SFTP %p state change from %s to %s\n",
396           (void *)sshc, names[sshc->state], names[nowstate]);
397   }
398 #endif
399
400   sshc->state = nowstate;
401 }
402
403
404 #ifdef HAVE_LIBSSH2_KNOWNHOST_API
405 static int sshkeycallback(struct Curl_easy *easy,
406                           const struct curl_khkey *knownkey, /* known */
407                           const struct curl_khkey *foundkey, /* found */
408                           enum curl_khmatch match,
409                           void *clientp)
410 {
411   (void)easy;
412   (void)knownkey;
413   (void)foundkey;
414   (void)clientp;
415
416   /* we only allow perfect matches, and we reject everything else */
417   return (match != CURLKHMATCH_OK)?CURLKHSTAT_REJECT:CURLKHSTAT_FINE;
418 }
419 #endif
420
421 /*
422  * Earlier libssh2 versions didn't have the ability to seek to 64bit positions
423  * with 32bit size_t.
424  */
425 #ifdef HAVE_LIBSSH2_SFTP_SEEK64
426 #define SFTP_SEEK(x,y) libssh2_sftp_seek64(x, (libssh2_uint64_t)y)
427 #else
428 #define SFTP_SEEK(x,y) libssh2_sftp_seek(x, (size_t)y)
429 #endif
430
431 /*
432  * Earlier libssh2 versions didn't do SCP properly beyond 32bit sizes on 32bit
433  * architectures so we check of the necessary function is present.
434  */
435 #ifndef HAVE_LIBSSH2_SCP_SEND64
436 #define SCP_SEND(a,b,c,d) libssh2_scp_send_ex(a, b, (int)(c), (size_t)d, 0, 0)
437 #else
438 #define SCP_SEND(a,b,c,d) libssh2_scp_send64(a, b, (int)(c),            \
439                                              (libssh2_uint64_t)d, 0, 0)
440 #endif
441
442 /*
443  * libssh2 1.2.8 fixed the problem with 32bit ints used for sockets on win64.
444  */
445 #ifdef HAVE_LIBSSH2_SESSION_HANDSHAKE
446 #define libssh2_session_startup(x,y) libssh2_session_handshake(x,y)
447 #endif
448
449 static CURLcode ssh_knownhost(struct connectdata *conn)
450 {
451   CURLcode result = CURLE_OK;
452
453 #ifdef HAVE_LIBSSH2_KNOWNHOST_API
454   struct Curl_easy *data = conn->data;
455
456   if(data->set.str[STRING_SSH_KNOWNHOSTS]) {
457     /* we're asked to verify the host against a file */
458     struct ssh_conn *sshc = &conn->proto.sshc;
459     int rc;
460     int keytype;
461     size_t keylen;
462     const char *remotekey = libssh2_session_hostkey(sshc->ssh_session,
463                                                     &keylen, &keytype);
464     int keycheck = LIBSSH2_KNOWNHOST_CHECK_FAILURE;
465     int keybit = 0;
466
467     if(remotekey) {
468       /*
469        * A subject to figure out is what host name we need to pass in here.
470        * What host name does OpenSSH store in its file if an IDN name is
471        * used?
472        */
473       struct libssh2_knownhost *host;
474       enum curl_khmatch keymatch;
475       curl_sshkeycallback func =
476         data->set.ssh_keyfunc?data->set.ssh_keyfunc:sshkeycallback;
477       struct curl_khkey knownkey;
478       struct curl_khkey *knownkeyp = NULL;
479       struct curl_khkey foundkey;
480
481       keybit = (keytype == LIBSSH2_HOSTKEY_TYPE_RSA)?
482         LIBSSH2_KNOWNHOST_KEY_SSHRSA:LIBSSH2_KNOWNHOST_KEY_SSHDSS;
483
484 #ifdef HAVE_LIBSSH2_KNOWNHOST_CHECKP
485       keycheck = libssh2_knownhost_checkp(sshc->kh,
486                                           conn->host.name,
487                                           (conn->remote_port != PORT_SSH)?
488                                           conn->remote_port:-1,
489                                           remotekey, keylen,
490                                           LIBSSH2_KNOWNHOST_TYPE_PLAIN|
491                                           LIBSSH2_KNOWNHOST_KEYENC_RAW|
492                                           keybit,
493                                           &host);
494 #else
495       keycheck = libssh2_knownhost_check(sshc->kh,
496                                          conn->host.name,
497                                          remotekey, keylen,
498                                          LIBSSH2_KNOWNHOST_TYPE_PLAIN|
499                                          LIBSSH2_KNOWNHOST_KEYENC_RAW|
500                                          keybit,
501                                          &host);
502 #endif
503
504       infof(data, "SSH host check: %d, key: %s\n", keycheck,
505             (keycheck <= LIBSSH2_KNOWNHOST_CHECK_MISMATCH)?
506             host->key:"<none>");
507
508       /* setup 'knownkey' */
509       if(keycheck <= LIBSSH2_KNOWNHOST_CHECK_MISMATCH) {
510         knownkey.key = host->key;
511         knownkey.len = 0;
512         knownkey.keytype = (keytype == LIBSSH2_HOSTKEY_TYPE_RSA)?
513           CURLKHTYPE_RSA : CURLKHTYPE_DSS;
514         knownkeyp = &knownkey;
515       }
516
517       /* setup 'foundkey' */
518       foundkey.key = remotekey;
519       foundkey.len = keylen;
520       foundkey.keytype = (keytype == LIBSSH2_HOSTKEY_TYPE_RSA)?
521         CURLKHTYPE_RSA : CURLKHTYPE_DSS;
522
523       /*
524        * if any of the LIBSSH2_KNOWNHOST_CHECK_* defines and the
525        * curl_khmatch enum are ever modified, we need to introduce a
526        * translation table here!
527        */
528       keymatch = (enum curl_khmatch)keycheck;
529
530       /* Ask the callback how to behave */
531       Curl_set_in_callback(data, true);
532       rc = func(data, knownkeyp, /* from the knownhosts file */
533                 &foundkey, /* from the remote host */
534                 keymatch, data->set.ssh_keyfunc_userp);
535       Curl_set_in_callback(data, false);
536     }
537     else
538       /* no remotekey means failure! */
539       rc = CURLKHSTAT_REJECT;
540
541     switch(rc) {
542     default: /* unknown return codes will equal reject */
543       /* FALLTHROUGH */
544     case CURLKHSTAT_REJECT:
545       state(conn, SSH_SESSION_FREE);
546       /* FALLTHROUGH */
547     case CURLKHSTAT_DEFER:
548       /* DEFER means bail out but keep the SSH_HOSTKEY state */
549       result = sshc->actualcode = CURLE_PEER_FAILED_VERIFICATION;
550       break;
551     case CURLKHSTAT_FINE:
552     case CURLKHSTAT_FINE_ADD_TO_FILE:
553       /* proceed */
554       if(keycheck != LIBSSH2_KNOWNHOST_CHECK_MATCH) {
555         /* the found host+key didn't match but has been told to be fine
556            anyway so we add it in memory */
557         int addrc = libssh2_knownhost_add(sshc->kh,
558                                           conn->host.name, NULL,
559                                           remotekey, keylen,
560                                           LIBSSH2_KNOWNHOST_TYPE_PLAIN|
561                                           LIBSSH2_KNOWNHOST_KEYENC_RAW|
562                                           keybit, NULL);
563         if(addrc)
564           infof(data, "Warning adding the known host %s failed!\n",
565                 conn->host.name);
566         else if(rc == CURLKHSTAT_FINE_ADD_TO_FILE) {
567           /* now we write the entire in-memory list of known hosts to the
568              known_hosts file */
569           int wrc =
570             libssh2_knownhost_writefile(sshc->kh,
571                                         data->set.str[STRING_SSH_KNOWNHOSTS],
572                                         LIBSSH2_KNOWNHOST_FILE_OPENSSH);
573           if(wrc) {
574             infof(data, "Warning, writing %s failed!\n",
575                   data->set.str[STRING_SSH_KNOWNHOSTS]);
576           }
577         }
578       }
579       break;
580     }
581   }
582 #else /* HAVE_LIBSSH2_KNOWNHOST_API */
583   (void)conn;
584 #endif
585   return result;
586 }
587
588 static CURLcode ssh_check_fingerprint(struct connectdata *conn)
589 {
590   struct ssh_conn *sshc = &conn->proto.sshc;
591   struct Curl_easy *data = conn->data;
592   const char *pubkey_md5 = data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5];
593   char md5buffer[33];
594   int i;
595
596   const char *fingerprint = libssh2_hostkey_hash(sshc->ssh_session,
597       LIBSSH2_HOSTKEY_HASH_MD5);
598
599   if(fingerprint) {
600     /* The fingerprint points to static storage (!), don't free() it. */
601     for(i = 0; i < 16; i++)
602       snprintf(&md5buffer[i*2], 3, "%02x", (unsigned char) fingerprint[i]);
603     infof(data, "SSH MD5 fingerprint: %s\n", md5buffer);
604   }
605
606   /* Before we authenticate we check the hostkey's MD5 fingerprint
607    * against a known fingerprint, if available.
608    */
609   if(pubkey_md5 && strlen(pubkey_md5) == 32) {
610     if(!fingerprint || !strcasecompare(md5buffer, pubkey_md5)) {
611       if(fingerprint)
612         failf(data,
613             "Denied establishing ssh session: mismatch md5 fingerprint. "
614             "Remote %s is not equal to %s", md5buffer, pubkey_md5);
615       else
616         failf(data,
617             "Denied establishing ssh session: md5 fingerprint not available");
618       state(conn, SSH_SESSION_FREE);
619       sshc->actualcode = CURLE_PEER_FAILED_VERIFICATION;
620       return sshc->actualcode;
621     }
622     infof(data, "MD5 checksum match!\n");
623     /* as we already matched, we skip the check for known hosts */
624     return CURLE_OK;
625   }
626   return ssh_knownhost(conn);
627 }
628
629 /*
630  * ssh_statemach_act() runs the SSH state machine as far as it can without
631  * blocking and without reaching the end.  The data the pointer 'block' points
632  * to will be set to TRUE if the libssh2 function returns LIBSSH2_ERROR_EAGAIN
633  * meaning it wants to be called again when the socket is ready
634  */
635
636 static CURLcode ssh_statemach_act(struct connectdata *conn, bool *block)
637 {
638   CURLcode result = CURLE_OK;
639   struct Curl_easy *data = conn->data;
640   struct SSHPROTO *sftp_scp = data->req.protop;
641   struct ssh_conn *sshc = &conn->proto.sshc;
642   curl_socket_t sock = conn->sock[FIRSTSOCKET];
643   char *new_readdir_line;
644   int rc = LIBSSH2_ERROR_NONE;
645   int err;
646   int seekerr = CURL_SEEKFUNC_OK;
647   *block = 0; /* we're not blocking by default */
648
649   do {
650
651     switch(sshc->state) {
652     case SSH_INIT:
653       sshc->secondCreateDirs = 0;
654       sshc->nextstate = SSH_NO_STATE;
655       sshc->actualcode = CURLE_OK;
656
657       /* Set libssh2 to non-blocking, since everything internally is
658          non-blocking */
659       libssh2_session_set_blocking(sshc->ssh_session, 0);
660
661       state(conn, SSH_S_STARTUP);
662       /* fall-through */
663
664     case SSH_S_STARTUP:
665       rc = libssh2_session_startup(sshc->ssh_session, (int)sock);
666       if(rc == LIBSSH2_ERROR_EAGAIN) {
667         break;
668       }
669       if(rc) {
670         failf(data, "Failure establishing ssh session");
671         state(conn, SSH_SESSION_FREE);
672         sshc->actualcode = CURLE_FAILED_INIT;
673         break;
674       }
675
676       state(conn, SSH_HOSTKEY);
677
678       /* fall-through */
679     case SSH_HOSTKEY:
680       /*
681        * Before we authenticate we should check the hostkey's fingerprint
682        * against our known hosts. How that is handled (reading from file,
683        * whatever) is up to us.
684        */
685       result = ssh_check_fingerprint(conn);
686       if(!result)
687         state(conn, SSH_AUTHLIST);
688       /* ssh_check_fingerprint sets state appropriately on error */
689       break;
690
691     case SSH_AUTHLIST:
692       /*
693        * Figure out authentication methods
694        * NB: As soon as we have provided a username to an openssh server we
695        * must never change it later. Thus, always specify the correct username
696        * here, even though the libssh2 docs kind of indicate that it should be
697        * possible to get a 'generic' list (not user-specific) of authentication
698        * methods, presumably with a blank username. That won't work in my
699        * experience.
700        * So always specify it here.
701        */
702       sshc->authlist = libssh2_userauth_list(sshc->ssh_session,
703                                              conn->user,
704                                              curlx_uztoui(strlen(conn->user)));
705
706       if(!sshc->authlist) {
707         if(libssh2_userauth_authenticated(sshc->ssh_session)) {
708           sshc->authed = TRUE;
709           infof(data, "SSH user accepted with no authentication\n");
710           state(conn, SSH_AUTH_DONE);
711           break;
712         }
713         err = libssh2_session_last_errno(sshc->ssh_session);
714         if(err == LIBSSH2_ERROR_EAGAIN)
715           rc = LIBSSH2_ERROR_EAGAIN;
716         else {
717           state(conn, SSH_SESSION_FREE);
718           sshc->actualcode = libssh2_session_error_to_CURLE(err);
719         }
720         break;
721       }
722       infof(data, "SSH authentication methods available: %s\n",
723             sshc->authlist);
724
725       state(conn, SSH_AUTH_PKEY_INIT);
726       break;
727
728     case SSH_AUTH_PKEY_INIT:
729       /*
730        * Check the supported auth types in the order I feel is most secure
731        * with the requested type of authentication
732        */
733       sshc->authed = FALSE;
734
735       if((data->set.ssh_auth_types & CURLSSH_AUTH_PUBLICKEY) &&
736          (strstr(sshc->authlist, "publickey") != NULL)) {
737         char *home = NULL;
738         bool out_of_memory = FALSE;
739
740         sshc->rsa_pub = sshc->rsa = NULL;
741
742         /* To ponder about: should really the lib be messing about with the
743            HOME environment variable etc? */
744         home = curl_getenv("HOME");
745
746         if(data->set.str[STRING_SSH_PRIVATE_KEY])
747           sshc->rsa = strdup(data->set.str[STRING_SSH_PRIVATE_KEY]);
748         else {
749           /* If no private key file is specified, try some common paths. */
750           if(home) {
751             /* Try ~/.ssh first. */
752             sshc->rsa = aprintf("%s/.ssh/id_rsa", home);
753             if(!sshc->rsa)
754               out_of_memory = TRUE;
755             else if(access(sshc->rsa, R_OK) != 0) {
756               Curl_safefree(sshc->rsa);
757               sshc->rsa = aprintf("%s/.ssh/id_dsa", home);
758               if(!sshc->rsa)
759                 out_of_memory = TRUE;
760               else if(access(sshc->rsa, R_OK) != 0) {
761                 Curl_safefree(sshc->rsa);
762               }
763             }
764           }
765           if(!out_of_memory && !sshc->rsa) {
766             /* Nothing found; try the current dir. */
767             sshc->rsa = strdup("id_rsa");
768             if(sshc->rsa && access(sshc->rsa, R_OK) != 0) {
769               Curl_safefree(sshc->rsa);
770               sshc->rsa = strdup("id_dsa");
771               if(sshc->rsa && access(sshc->rsa, R_OK) != 0) {
772                 Curl_safefree(sshc->rsa);
773                 /* Out of guesses. Set to the empty string to avoid
774                  * surprising info messages. */
775                 sshc->rsa = strdup("");
776               }
777             }
778           }
779         }
780
781         /*
782          * Unless the user explicitly specifies a public key file, let
783          * libssh2 extract the public key from the private key file.
784          * This is done by simply passing sshc->rsa_pub = NULL.
785          */
786         if(data->set.str[STRING_SSH_PUBLIC_KEY]
787             /* treat empty string the same way as NULL */
788             && data->set.str[STRING_SSH_PUBLIC_KEY][0]) {
789           sshc->rsa_pub = strdup(data->set.str[STRING_SSH_PUBLIC_KEY]);
790           if(!sshc->rsa_pub)
791             out_of_memory = TRUE;
792         }
793
794         if(out_of_memory || sshc->rsa == NULL) {
795           free(home);
796           Curl_safefree(sshc->rsa);
797           Curl_safefree(sshc->rsa_pub);
798           state(conn, SSH_SESSION_FREE);
799           sshc->actualcode = CURLE_OUT_OF_MEMORY;
800           break;
801         }
802
803         sshc->passphrase = data->set.ssl.key_passwd;
804         if(!sshc->passphrase)
805           sshc->passphrase = "";
806
807         free(home);
808
809         if(sshc->rsa_pub)
810           infof(data, "Using SSH public key file '%s'\n", sshc->rsa_pub);
811         infof(data, "Using SSH private key file '%s'\n", sshc->rsa);
812
813         state(conn, SSH_AUTH_PKEY);
814       }
815       else {
816         state(conn, SSH_AUTH_PASS_INIT);
817       }
818       break;
819
820     case SSH_AUTH_PKEY:
821       /* The function below checks if the files exists, no need to stat() here.
822        */
823       rc = libssh2_userauth_publickey_fromfile_ex(sshc->ssh_session,
824                                                   conn->user,
825                                                   curlx_uztoui(
826                                                     strlen(conn->user)),
827                                                   sshc->rsa_pub,
828                                                   sshc->rsa, sshc->passphrase);
829       if(rc == LIBSSH2_ERROR_EAGAIN) {
830         break;
831       }
832
833       Curl_safefree(sshc->rsa_pub);
834       Curl_safefree(sshc->rsa);
835
836       if(rc == 0) {
837         sshc->authed = TRUE;
838         infof(data, "Initialized SSH public key authentication\n");
839         state(conn, SSH_AUTH_DONE);
840       }
841       else {
842         char *err_msg;
843         (void)libssh2_session_last_error(sshc->ssh_session,
844                                          &err_msg, NULL, 0);
845         infof(data, "SSH public key authentication failed: %s\n", err_msg);
846         state(conn, SSH_AUTH_PASS_INIT);
847         rc = 0; /* clear rc and continue */
848       }
849       break;
850
851     case SSH_AUTH_PASS_INIT:
852       if((data->set.ssh_auth_types & CURLSSH_AUTH_PASSWORD) &&
853          (strstr(sshc->authlist, "password") != NULL)) {
854         state(conn, SSH_AUTH_PASS);
855       }
856       else {
857         state(conn, SSH_AUTH_HOST_INIT);
858         rc = 0; /* clear rc and continue */
859       }
860       break;
861
862     case SSH_AUTH_PASS:
863       rc = libssh2_userauth_password_ex(sshc->ssh_session, conn->user,
864                                         curlx_uztoui(strlen(conn->user)),
865                                         conn->passwd,
866                                         curlx_uztoui(strlen(conn->passwd)),
867                                         NULL);
868       if(rc == LIBSSH2_ERROR_EAGAIN) {
869         break;
870       }
871       if(rc == 0) {
872         sshc->authed = TRUE;
873         infof(data, "Initialized password authentication\n");
874         state(conn, SSH_AUTH_DONE);
875       }
876       else {
877         state(conn, SSH_AUTH_HOST_INIT);
878         rc = 0; /* clear rc and continue */
879       }
880       break;
881
882     case SSH_AUTH_HOST_INIT:
883       if((data->set.ssh_auth_types & CURLSSH_AUTH_HOST) &&
884          (strstr(sshc->authlist, "hostbased") != NULL)) {
885         state(conn, SSH_AUTH_HOST);
886       }
887       else {
888         state(conn, SSH_AUTH_AGENT_INIT);
889       }
890       break;
891
892     case SSH_AUTH_HOST:
893       state(conn, SSH_AUTH_AGENT_INIT);
894       break;
895
896     case SSH_AUTH_AGENT_INIT:
897 #ifdef HAVE_LIBSSH2_AGENT_API
898       if((data->set.ssh_auth_types & CURLSSH_AUTH_AGENT)
899          && (strstr(sshc->authlist, "publickey") != NULL)) {
900
901         /* Connect to the ssh-agent */
902         /* The agent could be shared by a curl thread i believe
903            but nothing obvious as keys can be added/removed at any time */
904         if(!sshc->ssh_agent) {
905           sshc->ssh_agent = libssh2_agent_init(sshc->ssh_session);
906           if(!sshc->ssh_agent) {
907             infof(data, "Could not create agent object\n");
908
909             state(conn, SSH_AUTH_KEY_INIT);
910             break;
911           }
912         }
913
914         rc = libssh2_agent_connect(sshc->ssh_agent);
915         if(rc == LIBSSH2_ERROR_EAGAIN)
916           break;
917         if(rc < 0) {
918           infof(data, "Failure connecting to agent\n");
919           state(conn, SSH_AUTH_KEY_INIT);
920           rc = 0; /* clear rc and continue */
921         }
922         else {
923           state(conn, SSH_AUTH_AGENT_LIST);
924         }
925       }
926       else
927 #endif /* HAVE_LIBSSH2_AGENT_API */
928         state(conn, SSH_AUTH_KEY_INIT);
929       break;
930
931     case SSH_AUTH_AGENT_LIST:
932 #ifdef HAVE_LIBSSH2_AGENT_API
933       rc = libssh2_agent_list_identities(sshc->ssh_agent);
934
935       if(rc == LIBSSH2_ERROR_EAGAIN)
936         break;
937       if(rc < 0) {
938         infof(data, "Failure requesting identities to agent\n");
939         state(conn, SSH_AUTH_KEY_INIT);
940         rc = 0; /* clear rc and continue */
941       }
942       else {
943         state(conn, SSH_AUTH_AGENT);
944         sshc->sshagent_prev_identity = NULL;
945       }
946 #endif
947       break;
948
949     case SSH_AUTH_AGENT:
950 #ifdef HAVE_LIBSSH2_AGENT_API
951       /* as prev_identity evolves only after an identity user auth finished we
952          can safely request it again as long as EAGAIN is returned here or by
953          libssh2_agent_userauth */
954       rc = libssh2_agent_get_identity(sshc->ssh_agent,
955                                       &sshc->sshagent_identity,
956                                       sshc->sshagent_prev_identity);
957       if(rc == LIBSSH2_ERROR_EAGAIN)
958         break;
959
960       if(rc == 0) {
961         rc = libssh2_agent_userauth(sshc->ssh_agent, conn->user,
962                                     sshc->sshagent_identity);
963
964         if(rc < 0) {
965           if(rc != LIBSSH2_ERROR_EAGAIN) {
966             /* tried and failed? go to next identity */
967             sshc->sshagent_prev_identity = sshc->sshagent_identity;
968           }
969           break;
970         }
971       }
972
973       if(rc < 0)
974         infof(data, "Failure requesting identities to agent\n");
975       else if(rc == 1)
976         infof(data, "No identity would match\n");
977
978       if(rc == LIBSSH2_ERROR_NONE) {
979         sshc->authed = TRUE;
980         infof(data, "Agent based authentication successful\n");
981         state(conn, SSH_AUTH_DONE);
982       }
983       else {
984         state(conn, SSH_AUTH_KEY_INIT);
985         rc = 0; /* clear rc and continue */
986       }
987 #endif
988       break;
989
990     case SSH_AUTH_KEY_INIT:
991       if((data->set.ssh_auth_types & CURLSSH_AUTH_KEYBOARD)
992          && (strstr(sshc->authlist, "keyboard-interactive") != NULL)) {
993         state(conn, SSH_AUTH_KEY);
994       }
995       else {
996         state(conn, SSH_AUTH_DONE);
997       }
998       break;
999
1000     case SSH_AUTH_KEY:
1001       /* Authentication failed. Continue with keyboard-interactive now. */
1002       rc = libssh2_userauth_keyboard_interactive_ex(sshc->ssh_session,
1003                                                     conn->user,
1004                                                     curlx_uztoui(
1005                                                       strlen(conn->user)),
1006                                                     &kbd_callback);
1007       if(rc == LIBSSH2_ERROR_EAGAIN) {
1008         break;
1009       }
1010       if(rc == 0) {
1011         sshc->authed = TRUE;
1012         infof(data, "Initialized keyboard interactive authentication\n");
1013       }
1014       state(conn, SSH_AUTH_DONE);
1015       break;
1016
1017     case SSH_AUTH_DONE:
1018       if(!sshc->authed) {
1019         failf(data, "Authentication failure");
1020         state(conn, SSH_SESSION_FREE);
1021         sshc->actualcode = CURLE_LOGIN_DENIED;
1022         break;
1023       }
1024
1025       /*
1026        * At this point we have an authenticated ssh session.
1027        */
1028       infof(data, "Authentication complete\n");
1029
1030       Curl_pgrsTime(conn->data, TIMER_APPCONNECT); /* SSH is connected */
1031
1032       conn->sockfd = sock;
1033       conn->writesockfd = CURL_SOCKET_BAD;
1034
1035       if(conn->handler->protocol == CURLPROTO_SFTP) {
1036         state(conn, SSH_SFTP_INIT);
1037         break;
1038       }
1039       infof(data, "SSH CONNECT phase done\n");
1040       state(conn, SSH_STOP);
1041       break;
1042
1043     case SSH_SFTP_INIT:
1044       /*
1045        * Start the libssh2 sftp session
1046        */
1047       sshc->sftp_session = libssh2_sftp_init(sshc->ssh_session);
1048       if(!sshc->sftp_session) {
1049         char *err_msg;
1050         if(libssh2_session_last_errno(sshc->ssh_session) ==
1051            LIBSSH2_ERROR_EAGAIN) {
1052           rc = LIBSSH2_ERROR_EAGAIN;
1053           break;
1054         }
1055
1056         (void)libssh2_session_last_error(sshc->ssh_session,
1057                                          &err_msg, NULL, 0);
1058         failf(data, "Failure initializing sftp session: %s", err_msg);
1059         state(conn, SSH_SESSION_FREE);
1060         sshc->actualcode = CURLE_FAILED_INIT;
1061         break;
1062       }
1063       state(conn, SSH_SFTP_REALPATH);
1064       break;
1065
1066     case SSH_SFTP_REALPATH:
1067     {
1068       char tempHome[PATH_MAX];
1069
1070       /*
1071        * Get the "home" directory
1072        */
1073       rc = sftp_libssh2_realpath(sshc->sftp_session, ".",
1074                                  tempHome, PATH_MAX-1);
1075       if(rc == LIBSSH2_ERROR_EAGAIN) {
1076         break;
1077       }
1078       if(rc > 0) {
1079         /* It seems that this string is not always NULL terminated */
1080         tempHome[rc] = '\0';
1081         sshc->homedir = strdup(tempHome);
1082         if(!sshc->homedir) {
1083           state(conn, SSH_SFTP_CLOSE);
1084           sshc->actualcode = CURLE_OUT_OF_MEMORY;
1085           break;
1086         }
1087         conn->data->state.most_recent_ftp_entrypath = sshc->homedir;
1088       }
1089       else {
1090         /* Return the error type */
1091         err = sftp_libssh2_last_error(sshc->sftp_session);
1092         if(err)
1093           result = sftp_libssh2_error_to_CURLE(err);
1094         else
1095           /* in this case, the error wasn't in the SFTP level but for example
1096              a time-out or similar */
1097           result = CURLE_SSH;
1098         sshc->actualcode = result;
1099         DEBUGF(infof(data, "error = %d makes libcurl = %d\n",
1100                      err, (int)result));
1101         state(conn, SSH_STOP);
1102         break;
1103       }
1104     }
1105     /* This is the last step in the SFTP connect phase. Do note that while
1106        we get the homedir here, we get the "workingpath" in the DO action
1107        since the homedir will remain the same between request but the
1108        working path will not. */
1109     DEBUGF(infof(data, "SSH CONNECT phase done\n"));
1110     state(conn, SSH_STOP);
1111     break;
1112
1113     case SSH_SFTP_QUOTE_INIT:
1114
1115       result = Curl_getworkingpath(conn, sshc->homedir, &sftp_scp->path);
1116       if(result) {
1117         sshc->actualcode = result;
1118         state(conn, SSH_STOP);
1119         break;
1120       }
1121
1122       if(data->set.quote) {
1123         infof(data, "Sending quote commands\n");
1124         sshc->quote_item = data->set.quote;
1125         state(conn, SSH_SFTP_QUOTE);
1126       }
1127       else {
1128         state(conn, SSH_SFTP_GETINFO);
1129       }
1130       break;
1131
1132     case SSH_SFTP_POSTQUOTE_INIT:
1133       if(data->set.postquote) {
1134         infof(data, "Sending quote commands\n");
1135         sshc->quote_item = data->set.postquote;
1136         state(conn, SSH_SFTP_QUOTE);
1137       }
1138       else {
1139         state(conn, SSH_STOP);
1140       }
1141       break;
1142
1143     case SSH_SFTP_QUOTE:
1144       /* Send any quote commands */
1145     {
1146       const char *cp;
1147
1148       /*
1149        * Support some of the "FTP" commands
1150        *
1151        * 'sshc->quote_item' is already verified to be non-NULL before it
1152        * switched to this state.
1153        */
1154       char *cmd = sshc->quote_item->data;
1155       sshc->acceptfail = FALSE;
1156
1157       /* if a command starts with an asterisk, which a legal SFTP command never
1158          can, the command will be allowed to fail without it causing any
1159          aborts or cancels etc. It will cause libcurl to act as if the command
1160          is successful, whatever the server reponds. */
1161
1162       if(cmd[0] == '*') {
1163         cmd++;
1164         sshc->acceptfail = TRUE;
1165       }
1166
1167       if(strcasecompare("pwd", cmd)) {
1168         /* output debug output if that is requested */
1169         char *tmp = aprintf("257 \"%s\" is current directory.\n",
1170                             sftp_scp->path);
1171         if(!tmp) {
1172           result = CURLE_OUT_OF_MEMORY;
1173           state(conn, SSH_SFTP_CLOSE);
1174           sshc->nextstate = SSH_NO_STATE;
1175           break;
1176         }
1177         if(data->set.verbose) {
1178           Curl_debug(data, CURLINFO_HEADER_OUT, (char *)"PWD\n", 4, conn);
1179           Curl_debug(data, CURLINFO_HEADER_IN, tmp, strlen(tmp), conn);
1180         }
1181         /* this sends an FTP-like "header" to the header callback so that the
1182            current directory can be read very similar to how it is read when
1183            using ordinary FTP. */
1184         result = Curl_client_write(conn, CLIENTWRITE_HEADER, tmp, strlen(tmp));
1185         free(tmp);
1186         if(result) {
1187           state(conn, SSH_SFTP_CLOSE);
1188           sshc->nextstate = SSH_NO_STATE;
1189           sshc->actualcode = result;
1190         }
1191         else
1192           state(conn, SSH_SFTP_NEXT_QUOTE);
1193         break;
1194       }
1195       {
1196         /*
1197          * the arguments following the command must be separated from the
1198          * command with a space so we can check for it unconditionally
1199          */
1200         cp = strchr(cmd, ' ');
1201         if(cp == NULL) {
1202           failf(data, "Syntax error in SFTP command. Supply parameter(s)!");
1203           state(conn, SSH_SFTP_CLOSE);
1204           sshc->nextstate = SSH_NO_STATE;
1205           sshc->actualcode = CURLE_QUOTE_ERROR;
1206           break;
1207         }
1208
1209         /*
1210          * also, every command takes at least one argument so we get that
1211          * first argument right now
1212          */
1213         result = Curl_get_pathname(&cp, &sshc->quote_path1, sshc->homedir);
1214         if(result) {
1215           if(result == CURLE_OUT_OF_MEMORY)
1216             failf(data, "Out of memory");
1217           else
1218             failf(data, "Syntax error: Bad first parameter");
1219           state(conn, SSH_SFTP_CLOSE);
1220           sshc->nextstate = SSH_NO_STATE;
1221           sshc->actualcode = result;
1222           break;
1223         }
1224
1225         /*
1226          * SFTP is a binary protocol, so we don't send text commands
1227          * to the server. Instead, we scan for commands used by
1228          * OpenSSH's sftp program and call the appropriate libssh2
1229          * functions.
1230          */
1231         if(strncasecompare(cmd, "chgrp ", 6) ||
1232            strncasecompare(cmd, "chmod ", 6) ||
1233            strncasecompare(cmd, "chown ", 6) ) {
1234           /* attribute change */
1235
1236           /* sshc->quote_path1 contains the mode to set */
1237           /* get the destination */
1238           result = Curl_get_pathname(&cp, &sshc->quote_path2, sshc->homedir);
1239           if(result) {
1240             if(result == CURLE_OUT_OF_MEMORY)
1241               failf(data, "Out of memory");
1242             else
1243               failf(data, "Syntax error in chgrp/chmod/chown: "
1244                     "Bad second parameter");
1245             Curl_safefree(sshc->quote_path1);
1246             state(conn, SSH_SFTP_CLOSE);
1247             sshc->nextstate = SSH_NO_STATE;
1248             sshc->actualcode = result;
1249             break;
1250           }
1251           memset(&sshc->quote_attrs, 0, sizeof(LIBSSH2_SFTP_ATTRIBUTES));
1252           state(conn, SSH_SFTP_QUOTE_STAT);
1253           break;
1254         }
1255         if(strncasecompare(cmd, "ln ", 3) ||
1256                 strncasecompare(cmd, "symlink ", 8)) {
1257           /* symbolic linking */
1258           /* sshc->quote_path1 is the source */
1259           /* get the destination */
1260           result = Curl_get_pathname(&cp, &sshc->quote_path2, sshc->homedir);
1261           if(result) {
1262             if(result == CURLE_OUT_OF_MEMORY)
1263               failf(data, "Out of memory");
1264             else
1265               failf(data,
1266                     "Syntax error in ln/symlink: Bad second parameter");
1267             Curl_safefree(sshc->quote_path1);
1268             state(conn, SSH_SFTP_CLOSE);
1269             sshc->nextstate = SSH_NO_STATE;
1270             sshc->actualcode = result;
1271             break;
1272           }
1273           state(conn, SSH_SFTP_QUOTE_SYMLINK);
1274           break;
1275         }
1276         else if(strncasecompare(cmd, "mkdir ", 6)) {
1277           /* create dir */
1278           state(conn, SSH_SFTP_QUOTE_MKDIR);
1279           break;
1280         }
1281         else if(strncasecompare(cmd, "rename ", 7)) {
1282           /* rename file */
1283           /* first param is the source path */
1284           /* second param is the dest. path */
1285           result = Curl_get_pathname(&cp, &sshc->quote_path2, sshc->homedir);
1286           if(result) {
1287             if(result == CURLE_OUT_OF_MEMORY)
1288               failf(data, "Out of memory");
1289             else
1290               failf(data, "Syntax error in rename: Bad second parameter");
1291             Curl_safefree(sshc->quote_path1);
1292             state(conn, SSH_SFTP_CLOSE);
1293             sshc->nextstate = SSH_NO_STATE;
1294             sshc->actualcode = result;
1295             break;
1296           }
1297           state(conn, SSH_SFTP_QUOTE_RENAME);
1298           break;
1299         }
1300         else if(strncasecompare(cmd, "rmdir ", 6)) {
1301           /* delete dir */
1302           state(conn, SSH_SFTP_QUOTE_RMDIR);
1303           break;
1304         }
1305         else if(strncasecompare(cmd, "rm ", 3)) {
1306           state(conn, SSH_SFTP_QUOTE_UNLINK);
1307           break;
1308         }
1309 #ifdef HAS_STATVFS_SUPPORT
1310         else if(strncasecompare(cmd, "statvfs ", 8)) {
1311           state(conn, SSH_SFTP_QUOTE_STATVFS);
1312           break;
1313         }
1314 #endif
1315
1316         failf(data, "Unknown SFTP command");
1317         Curl_safefree(sshc->quote_path1);
1318         Curl_safefree(sshc->quote_path2);
1319         state(conn, SSH_SFTP_CLOSE);
1320         sshc->nextstate = SSH_NO_STATE;
1321         sshc->actualcode = CURLE_QUOTE_ERROR;
1322         break;
1323       }
1324     }
1325     break;
1326
1327     case SSH_SFTP_NEXT_QUOTE:
1328       Curl_safefree(sshc->quote_path1);
1329       Curl_safefree(sshc->quote_path2);
1330
1331       sshc->quote_item = sshc->quote_item->next;
1332
1333       if(sshc->quote_item) {
1334         state(conn, SSH_SFTP_QUOTE);
1335       }
1336       else {
1337         if(sshc->nextstate != SSH_NO_STATE) {
1338           state(conn, sshc->nextstate);
1339           sshc->nextstate = SSH_NO_STATE;
1340         }
1341         else {
1342           state(conn, SSH_SFTP_GETINFO);
1343         }
1344       }
1345       break;
1346
1347     case SSH_SFTP_QUOTE_STAT:
1348     {
1349       char *cmd = sshc->quote_item->data;
1350       sshc->acceptfail = FALSE;
1351
1352       /* if a command starts with an asterisk, which a legal SFTP command never
1353          can, the command will be allowed to fail without it causing any
1354          aborts or cancels etc. It will cause libcurl to act as if the command
1355          is successful, whatever the server reponds. */
1356
1357       if(cmd[0] == '*') {
1358         cmd++;
1359         sshc->acceptfail = TRUE;
1360       }
1361
1362       if(!strncasecompare(cmd, "chmod", 5)) {
1363         /* Since chown and chgrp only set owner OR group but libssh2 wants to
1364          * set them both at once, we need to obtain the current ownership
1365          * first.  This takes an extra protocol round trip.
1366          */
1367         rc = libssh2_sftp_stat_ex(sshc->sftp_session, sshc->quote_path2,
1368                                   curlx_uztoui(strlen(sshc->quote_path2)),
1369                                   LIBSSH2_SFTP_STAT,
1370                                   &sshc->quote_attrs);
1371         if(rc == LIBSSH2_ERROR_EAGAIN) {
1372           break;
1373         }
1374         if(rc != 0 && !sshc->acceptfail) { /* get those attributes */
1375           err = sftp_libssh2_last_error(sshc->sftp_session);
1376           Curl_safefree(sshc->quote_path1);
1377           Curl_safefree(sshc->quote_path2);
1378           failf(data, "Attempt to get SFTP stats failed: %s",
1379                 sftp_libssh2_strerror(err));
1380           state(conn, SSH_SFTP_CLOSE);
1381           sshc->nextstate = SSH_NO_STATE;
1382           sshc->actualcode = CURLE_QUOTE_ERROR;
1383           break;
1384         }
1385       }
1386
1387       /* Now set the new attributes... */
1388       if(strncasecompare(cmd, "chgrp", 5)) {
1389         sshc->quote_attrs.gid = strtoul(sshc->quote_path1, NULL, 10);
1390         sshc->quote_attrs.flags = LIBSSH2_SFTP_ATTR_UIDGID;
1391         if(sshc->quote_attrs.gid == 0 && !ISDIGIT(sshc->quote_path1[0]) &&
1392            !sshc->acceptfail) {
1393           Curl_safefree(sshc->quote_path1);
1394           Curl_safefree(sshc->quote_path2);
1395           failf(data, "Syntax error: chgrp gid not a number");
1396           state(conn, SSH_SFTP_CLOSE);
1397           sshc->nextstate = SSH_NO_STATE;
1398           sshc->actualcode = CURLE_QUOTE_ERROR;
1399           break;
1400         }
1401       }
1402       else if(strncasecompare(cmd, "chmod", 5)) {
1403         sshc->quote_attrs.permissions = strtoul(sshc->quote_path1, NULL, 8);
1404         sshc->quote_attrs.flags = LIBSSH2_SFTP_ATTR_PERMISSIONS;
1405         /* permissions are octal */
1406         if(sshc->quote_attrs.permissions == 0 &&
1407            !ISDIGIT(sshc->quote_path1[0])) {
1408           Curl_safefree(sshc->quote_path1);
1409           Curl_safefree(sshc->quote_path2);
1410           failf(data, "Syntax error: chmod permissions not a number");
1411           state(conn, SSH_SFTP_CLOSE);
1412           sshc->nextstate = SSH_NO_STATE;
1413           sshc->actualcode = CURLE_QUOTE_ERROR;
1414           break;
1415         }
1416       }
1417       else if(strncasecompare(cmd, "chown", 5)) {
1418         sshc->quote_attrs.uid = strtoul(sshc->quote_path1, NULL, 10);
1419         sshc->quote_attrs.flags = LIBSSH2_SFTP_ATTR_UIDGID;
1420         if(sshc->quote_attrs.uid == 0 && !ISDIGIT(sshc->quote_path1[0]) &&
1421            !sshc->acceptfail) {
1422           Curl_safefree(sshc->quote_path1);
1423           Curl_safefree(sshc->quote_path2);
1424           failf(data, "Syntax error: chown uid not a number");
1425           state(conn, SSH_SFTP_CLOSE);
1426           sshc->nextstate = SSH_NO_STATE;
1427           sshc->actualcode = CURLE_QUOTE_ERROR;
1428           break;
1429         }
1430       }
1431
1432       /* Now send the completed structure... */
1433       state(conn, SSH_SFTP_QUOTE_SETSTAT);
1434       break;
1435     }
1436
1437     case SSH_SFTP_QUOTE_SETSTAT:
1438       rc = libssh2_sftp_stat_ex(sshc->sftp_session, sshc->quote_path2,
1439                                 curlx_uztoui(strlen(sshc->quote_path2)),
1440                                 LIBSSH2_SFTP_SETSTAT,
1441                                 &sshc->quote_attrs);
1442       if(rc == LIBSSH2_ERROR_EAGAIN) {
1443         break;
1444       }
1445       if(rc != 0 && !sshc->acceptfail) {
1446         err = sftp_libssh2_last_error(sshc->sftp_session);
1447         Curl_safefree(sshc->quote_path1);
1448         Curl_safefree(sshc->quote_path2);
1449         failf(data, "Attempt to set SFTP stats failed: %s",
1450               sftp_libssh2_strerror(err));
1451         state(conn, SSH_SFTP_CLOSE);
1452         sshc->nextstate = SSH_NO_STATE;
1453         sshc->actualcode = CURLE_QUOTE_ERROR;
1454         break;
1455       }
1456       state(conn, SSH_SFTP_NEXT_QUOTE);
1457       break;
1458
1459     case SSH_SFTP_QUOTE_SYMLINK:
1460       rc = libssh2_sftp_symlink_ex(sshc->sftp_session, sshc->quote_path1,
1461                                    curlx_uztoui(strlen(sshc->quote_path1)),
1462                                    sshc->quote_path2,
1463                                    curlx_uztoui(strlen(sshc->quote_path2)),
1464                                    LIBSSH2_SFTP_SYMLINK);
1465       if(rc == LIBSSH2_ERROR_EAGAIN) {
1466         break;
1467       }
1468       if(rc != 0 && !sshc->acceptfail) {
1469         err = sftp_libssh2_last_error(sshc->sftp_session);
1470         Curl_safefree(sshc->quote_path1);
1471         Curl_safefree(sshc->quote_path2);
1472         failf(data, "symlink command failed: %s",
1473               sftp_libssh2_strerror(err));
1474         state(conn, SSH_SFTP_CLOSE);
1475         sshc->nextstate = SSH_NO_STATE;
1476         sshc->actualcode = CURLE_QUOTE_ERROR;
1477         break;
1478       }
1479       state(conn, SSH_SFTP_NEXT_QUOTE);
1480       break;
1481
1482     case SSH_SFTP_QUOTE_MKDIR:
1483       rc = libssh2_sftp_mkdir_ex(sshc->sftp_session, sshc->quote_path1,
1484                                  curlx_uztoui(strlen(sshc->quote_path1)),
1485                                  data->set.new_directory_perms);
1486       if(rc == LIBSSH2_ERROR_EAGAIN) {
1487         break;
1488       }
1489       if(rc != 0 && !sshc->acceptfail) {
1490         err = sftp_libssh2_last_error(sshc->sftp_session);
1491         Curl_safefree(sshc->quote_path1);
1492         failf(data, "mkdir command failed: %s", sftp_libssh2_strerror(err));
1493         state(conn, SSH_SFTP_CLOSE);
1494         sshc->nextstate = SSH_NO_STATE;
1495         sshc->actualcode = CURLE_QUOTE_ERROR;
1496         break;
1497       }
1498       state(conn, SSH_SFTP_NEXT_QUOTE);
1499       break;
1500
1501     case SSH_SFTP_QUOTE_RENAME:
1502       rc = libssh2_sftp_rename_ex(sshc->sftp_session, sshc->quote_path1,
1503                                   curlx_uztoui(strlen(sshc->quote_path1)),
1504                                   sshc->quote_path2,
1505                                   curlx_uztoui(strlen(sshc->quote_path2)),
1506                                   LIBSSH2_SFTP_RENAME_OVERWRITE |
1507                                   LIBSSH2_SFTP_RENAME_ATOMIC |
1508                                   LIBSSH2_SFTP_RENAME_NATIVE);
1509
1510       if(rc == LIBSSH2_ERROR_EAGAIN) {
1511         break;
1512       }
1513       if(rc != 0 && !sshc->acceptfail) {
1514         err = sftp_libssh2_last_error(sshc->sftp_session);
1515         Curl_safefree(sshc->quote_path1);
1516         Curl_safefree(sshc->quote_path2);
1517         failf(data, "rename command failed: %s", sftp_libssh2_strerror(err));
1518         state(conn, SSH_SFTP_CLOSE);
1519         sshc->nextstate = SSH_NO_STATE;
1520         sshc->actualcode = CURLE_QUOTE_ERROR;
1521         break;
1522       }
1523       state(conn, SSH_SFTP_NEXT_QUOTE);
1524       break;
1525
1526     case SSH_SFTP_QUOTE_RMDIR:
1527       rc = libssh2_sftp_rmdir_ex(sshc->sftp_session, sshc->quote_path1,
1528                                  curlx_uztoui(strlen(sshc->quote_path1)));
1529       if(rc == LIBSSH2_ERROR_EAGAIN) {
1530         break;
1531       }
1532       if(rc != 0 && !sshc->acceptfail) {
1533         err = sftp_libssh2_last_error(sshc->sftp_session);
1534         Curl_safefree(sshc->quote_path1);
1535         failf(data, "rmdir command failed: %s", sftp_libssh2_strerror(err));
1536         state(conn, SSH_SFTP_CLOSE);
1537         sshc->nextstate = SSH_NO_STATE;
1538         sshc->actualcode = CURLE_QUOTE_ERROR;
1539         break;
1540       }
1541       state(conn, SSH_SFTP_NEXT_QUOTE);
1542       break;
1543
1544     case SSH_SFTP_QUOTE_UNLINK:
1545       rc = libssh2_sftp_unlink_ex(sshc->sftp_session, sshc->quote_path1,
1546                                   curlx_uztoui(strlen(sshc->quote_path1)));
1547       if(rc == LIBSSH2_ERROR_EAGAIN) {
1548         break;
1549       }
1550       if(rc != 0 && !sshc->acceptfail) {
1551         err = sftp_libssh2_last_error(sshc->sftp_session);
1552         Curl_safefree(sshc->quote_path1);
1553         failf(data, "rm command failed: %s", sftp_libssh2_strerror(err));
1554         state(conn, SSH_SFTP_CLOSE);
1555         sshc->nextstate = SSH_NO_STATE;
1556         sshc->actualcode = CURLE_QUOTE_ERROR;
1557         break;
1558       }
1559       state(conn, SSH_SFTP_NEXT_QUOTE);
1560       break;
1561
1562 #ifdef HAS_STATVFS_SUPPORT
1563     case SSH_SFTP_QUOTE_STATVFS:
1564     {
1565       LIBSSH2_SFTP_STATVFS statvfs;
1566       rc = libssh2_sftp_statvfs(sshc->sftp_session, sshc->quote_path1,
1567                                 curlx_uztoui(strlen(sshc->quote_path1)),
1568                                 &statvfs);
1569
1570       if(rc == LIBSSH2_ERROR_EAGAIN) {
1571         break;
1572       }
1573       if(rc != 0 && !sshc->acceptfail) {
1574         err = sftp_libssh2_last_error(sshc->sftp_session);
1575         Curl_safefree(sshc->quote_path1);
1576         failf(data, "statvfs command failed: %s", sftp_libssh2_strerror(err));
1577         state(conn, SSH_SFTP_CLOSE);
1578         sshc->nextstate = SSH_NO_STATE;
1579         sshc->actualcode = CURLE_QUOTE_ERROR;
1580         break;
1581       }
1582       else if(rc == 0) {
1583         char *tmp = aprintf("statvfs:\n"
1584                             "f_bsize: %llu\n" "f_frsize: %llu\n"
1585                             "f_blocks: %llu\n" "f_bfree: %llu\n"
1586                             "f_bavail: %llu\n" "f_files: %llu\n"
1587                             "f_ffree: %llu\n" "f_favail: %llu\n"
1588                             "f_fsid: %llu\n" "f_flag: %llu\n"
1589                             "f_namemax: %llu\n",
1590                             statvfs.f_bsize, statvfs.f_frsize,
1591                             statvfs.f_blocks, statvfs.f_bfree,
1592                             statvfs.f_bavail, statvfs.f_files,
1593                             statvfs.f_ffree, statvfs.f_favail,
1594                             statvfs.f_fsid, statvfs.f_flag,
1595                             statvfs.f_namemax);
1596         if(!tmp) {
1597           result = CURLE_OUT_OF_MEMORY;
1598           state(conn, SSH_SFTP_CLOSE);
1599           sshc->nextstate = SSH_NO_STATE;
1600           break;
1601         }
1602
1603         result = Curl_client_write(conn, CLIENTWRITE_HEADER, tmp, strlen(tmp));
1604         free(tmp);
1605         if(result) {
1606           state(conn, SSH_SFTP_CLOSE);
1607           sshc->nextstate = SSH_NO_STATE;
1608           sshc->actualcode = result;
1609         }
1610       }
1611       state(conn, SSH_SFTP_NEXT_QUOTE);
1612       break;
1613     }
1614 #endif
1615     case SSH_SFTP_GETINFO:
1616     {
1617       if(data->set.get_filetime) {
1618         state(conn, SSH_SFTP_FILETIME);
1619       }
1620       else {
1621         state(conn, SSH_SFTP_TRANS_INIT);
1622       }
1623       break;
1624     }
1625
1626     case SSH_SFTP_FILETIME:
1627     {
1628       LIBSSH2_SFTP_ATTRIBUTES attrs;
1629
1630       rc = libssh2_sftp_stat_ex(sshc->sftp_session, sftp_scp->path,
1631                                 curlx_uztoui(strlen(sftp_scp->path)),
1632                                 LIBSSH2_SFTP_STAT, &attrs);
1633       if(rc == LIBSSH2_ERROR_EAGAIN) {
1634         break;
1635       }
1636       if(rc == 0) {
1637         data->info.filetime = attrs.mtime;
1638       }
1639
1640       state(conn, SSH_SFTP_TRANS_INIT);
1641       break;
1642     }
1643
1644     case SSH_SFTP_TRANS_INIT:
1645       if(data->set.upload)
1646         state(conn, SSH_SFTP_UPLOAD_INIT);
1647       else {
1648         if(sftp_scp->path[strlen(sftp_scp->path)-1] == '/')
1649           state(conn, SSH_SFTP_READDIR_INIT);
1650         else
1651           state(conn, SSH_SFTP_DOWNLOAD_INIT);
1652       }
1653       break;
1654
1655     case SSH_SFTP_UPLOAD_INIT:
1656     {
1657       unsigned long flags;
1658       /*
1659        * NOTE!!!  libssh2 requires that the destination path is a full path
1660        *          that includes the destination file and name OR ends in a "/"
1661        *          If this is not done the destination file will be named the
1662        *          same name as the last directory in the path.
1663        */
1664
1665       if(data->state.resume_from != 0) {
1666         LIBSSH2_SFTP_ATTRIBUTES attrs;
1667         if(data->state.resume_from < 0) {
1668           rc = libssh2_sftp_stat_ex(sshc->sftp_session, sftp_scp->path,
1669                                     curlx_uztoui(strlen(sftp_scp->path)),
1670                                     LIBSSH2_SFTP_STAT, &attrs);
1671           if(rc == LIBSSH2_ERROR_EAGAIN) {
1672             break;
1673           }
1674           if(rc) {
1675             data->state.resume_from = 0;
1676           }
1677           else {
1678             curl_off_t size = attrs.filesize;
1679             if(size < 0) {
1680               failf(data, "Bad file size (%" CURL_FORMAT_CURL_OFF_T ")", size);
1681               return CURLE_BAD_DOWNLOAD_RESUME;
1682             }
1683             data->state.resume_from = attrs.filesize;
1684           }
1685         }
1686       }
1687
1688       if(data->set.ftp_append)
1689         /* Try to open for append, but create if nonexisting */
1690         flags = LIBSSH2_FXF_WRITE|LIBSSH2_FXF_CREAT|LIBSSH2_FXF_APPEND;
1691       else if(data->state.resume_from > 0)
1692         /* If we have restart position then open for append */
1693         flags = LIBSSH2_FXF_WRITE|LIBSSH2_FXF_APPEND;
1694       else
1695         /* Clear file before writing (normal behaviour) */
1696         flags = LIBSSH2_FXF_WRITE|LIBSSH2_FXF_CREAT|LIBSSH2_FXF_TRUNC;
1697
1698       sshc->sftp_handle =
1699         libssh2_sftp_open_ex(sshc->sftp_session, sftp_scp->path,
1700                              curlx_uztoui(strlen(sftp_scp->path)),
1701                              flags, data->set.new_file_perms,
1702                              LIBSSH2_SFTP_OPENFILE);
1703
1704       if(!sshc->sftp_handle) {
1705         rc = libssh2_session_last_errno(sshc->ssh_session);
1706
1707         if(LIBSSH2_ERROR_EAGAIN == rc)
1708           break;
1709
1710         if(LIBSSH2_ERROR_SFTP_PROTOCOL == rc)
1711           /* only when there was an SFTP protocol error can we extract
1712              the sftp error! */
1713           err = sftp_libssh2_last_error(sshc->sftp_session);
1714         else
1715           err = -1; /* not an sftp error at all */
1716
1717         if(sshc->secondCreateDirs) {
1718           state(conn, SSH_SFTP_CLOSE);
1719           sshc->actualcode = err>= LIBSSH2_FX_OK?
1720             sftp_libssh2_error_to_CURLE(err):CURLE_SSH;
1721           failf(data, "Creating the dir/file failed: %s",
1722                 sftp_libssh2_strerror(err));
1723           break;
1724         }
1725         if(((err == LIBSSH2_FX_NO_SUCH_FILE) ||
1726             (err == LIBSSH2_FX_FAILURE) ||
1727             (err == LIBSSH2_FX_NO_SUCH_PATH)) &&
1728            (data->set.ftp_create_missing_dirs &&
1729             (strlen(sftp_scp->path) > 1))) {
1730           /* try to create the path remotely */
1731           rc = 0; /* clear rc and continue */
1732           sshc->secondCreateDirs = 1;
1733           state(conn, SSH_SFTP_CREATE_DIRS_INIT);
1734           break;
1735         }
1736         state(conn, SSH_SFTP_CLOSE);
1737         sshc->actualcode = err>= LIBSSH2_FX_OK?
1738           sftp_libssh2_error_to_CURLE(err):CURLE_SSH;
1739         if(!sshc->actualcode) {
1740           /* Sometimes, for some reason libssh2_sftp_last_error() returns
1741              zero even though libssh2_sftp_open() failed previously! We need
1742              to work around that! */
1743           sshc->actualcode = CURLE_SSH;
1744           err = -1;
1745         }
1746         failf(data, "Upload failed: %s (%d/%d)",
1747               err>= LIBSSH2_FX_OK?sftp_libssh2_strerror(err):"ssh error",
1748               err, rc);
1749         break;
1750       }
1751
1752       /* If we have a restart point then we need to seek to the correct
1753          position. */
1754       if(data->state.resume_from > 0) {
1755         /* Let's read off the proper amount of bytes from the input. */
1756         if(conn->seek_func) {
1757           Curl_set_in_callback(data, true);
1758           seekerr = conn->seek_func(conn->seek_client, data->state.resume_from,
1759                                     SEEK_SET);
1760           Curl_set_in_callback(data, false);
1761         }
1762
1763         if(seekerr != CURL_SEEKFUNC_OK) {
1764           curl_off_t passed = 0;
1765
1766           if(seekerr != CURL_SEEKFUNC_CANTSEEK) {
1767             failf(data, "Could not seek stream");
1768             return CURLE_FTP_COULDNT_USE_REST;
1769           }
1770           /* seekerr == CURL_SEEKFUNC_CANTSEEK (can't seek to offset) */
1771           do {
1772             size_t readthisamountnow =
1773               (data->state.resume_from - passed > data->set.buffer_size) ?
1774               (size_t)data->set.buffer_size :
1775               curlx_sotouz(data->state.resume_from - passed);
1776
1777             size_t actuallyread;
1778             Curl_set_in_callback(data, true);
1779             actuallyread = data->state.fread_func(data->state.buffer, 1,
1780                                                   readthisamountnow,
1781                                                   data->state.in);
1782             Curl_set_in_callback(data, false);
1783
1784             passed += actuallyread;
1785             if((actuallyread == 0) || (actuallyread > readthisamountnow)) {
1786               /* this checks for greater-than only to make sure that the
1787                  CURL_READFUNC_ABORT return code still aborts */
1788               failf(data, "Failed to read data");
1789               return CURLE_FTP_COULDNT_USE_REST;
1790             }
1791           } while(passed < data->state.resume_from);
1792         }
1793
1794         /* now, decrease the size of the read */
1795         if(data->state.infilesize > 0) {
1796           data->state.infilesize -= data->state.resume_from;
1797           data->req.size = data->state.infilesize;
1798           Curl_pgrsSetUploadSize(data, data->state.infilesize);
1799         }
1800
1801         SFTP_SEEK(sshc->sftp_handle, data->state.resume_from);
1802       }
1803       if(data->state.infilesize > 0) {
1804         data->req.size = data->state.infilesize;
1805         Curl_pgrsSetUploadSize(data, data->state.infilesize);
1806       }
1807       /* upload data */
1808       Curl_setup_transfer(conn, -1, -1, FALSE, NULL, FIRSTSOCKET, NULL);
1809
1810       /* not set by Curl_setup_transfer to preserve keepon bits */
1811       conn->sockfd = conn->writesockfd;
1812
1813       if(result) {
1814         state(conn, SSH_SFTP_CLOSE);
1815         sshc->actualcode = result;
1816       }
1817       else {
1818         /* store this original bitmask setup to use later on if we can't
1819            figure out a "real" bitmask */
1820         sshc->orig_waitfor = data->req.keepon;
1821
1822         /* we want to use the _sending_ function even when the socket turns
1823            out readable as the underlying libssh2 sftp send function will deal
1824            with both accordingly */
1825         conn->cselect_bits = CURL_CSELECT_OUT;
1826
1827         /* since we don't really wait for anything at this point, we want the
1828            state machine to move on as soon as possible so we set a very short
1829            timeout here */
1830         Curl_expire(data, 0, EXPIRE_RUN_NOW);
1831
1832         state(conn, SSH_STOP);
1833       }
1834       break;
1835     }
1836
1837     case SSH_SFTP_CREATE_DIRS_INIT:
1838       if(strlen(sftp_scp->path) > 1) {
1839         sshc->slash_pos = sftp_scp->path + 1; /* ignore the leading '/' */
1840         state(conn, SSH_SFTP_CREATE_DIRS);
1841       }
1842       else {
1843         state(conn, SSH_SFTP_UPLOAD_INIT);
1844       }
1845       break;
1846
1847     case SSH_SFTP_CREATE_DIRS:
1848       sshc->slash_pos = strchr(sshc->slash_pos, '/');
1849       if(sshc->slash_pos) {
1850         *sshc->slash_pos = 0;
1851
1852         infof(data, "Creating directory '%s'\n", sftp_scp->path);
1853         state(conn, SSH_SFTP_CREATE_DIRS_MKDIR);
1854         break;
1855       }
1856       state(conn, SSH_SFTP_UPLOAD_INIT);
1857       break;
1858
1859     case SSH_SFTP_CREATE_DIRS_MKDIR:
1860       /* 'mode' - parameter is preliminary - default to 0644 */
1861       rc = libssh2_sftp_mkdir_ex(sshc->sftp_session, sftp_scp->path,
1862                                  curlx_uztoui(strlen(sftp_scp->path)),
1863                                  data->set.new_directory_perms);
1864       if(rc == LIBSSH2_ERROR_EAGAIN) {
1865         break;
1866       }
1867       *sshc->slash_pos = '/';
1868       ++sshc->slash_pos;
1869       if(rc < 0) {
1870         /*
1871          * Abort if failure wasn't that the dir already exists or the
1872          * permission was denied (creation might succeed further down the
1873          * path) - retry on unspecific FAILURE also
1874          */
1875         err = sftp_libssh2_last_error(sshc->sftp_session);
1876         if((err != LIBSSH2_FX_FILE_ALREADY_EXISTS) &&
1877            (err != LIBSSH2_FX_FAILURE) &&
1878            (err != LIBSSH2_FX_PERMISSION_DENIED)) {
1879           result = sftp_libssh2_error_to_CURLE(err);
1880           state(conn, SSH_SFTP_CLOSE);
1881           sshc->actualcode = result?result:CURLE_SSH;
1882           break;
1883         }
1884         rc = 0; /* clear rc and continue */
1885       }
1886       state(conn, SSH_SFTP_CREATE_DIRS);
1887       break;
1888
1889     case SSH_SFTP_READDIR_INIT:
1890       Curl_pgrsSetDownloadSize(data, -1);
1891       if(data->set.opt_no_body) {
1892         state(conn, SSH_STOP);
1893         break;
1894       }
1895
1896       /*
1897        * This is a directory that we are trying to get, so produce a directory
1898        * listing
1899        */
1900       sshc->sftp_handle = libssh2_sftp_open_ex(sshc->sftp_session,
1901                                                sftp_scp->path,
1902                                                curlx_uztoui(
1903                                                  strlen(sftp_scp->path)),
1904                                                0, 0, LIBSSH2_SFTP_OPENDIR);
1905       if(!sshc->sftp_handle) {
1906         if(libssh2_session_last_errno(sshc->ssh_session) ==
1907            LIBSSH2_ERROR_EAGAIN) {
1908           rc = LIBSSH2_ERROR_EAGAIN;
1909           break;
1910         }
1911         err = sftp_libssh2_last_error(sshc->sftp_session);
1912         failf(data, "Could not open directory for reading: %s",
1913               sftp_libssh2_strerror(err));
1914         state(conn, SSH_SFTP_CLOSE);
1915         result = sftp_libssh2_error_to_CURLE(err);
1916         sshc->actualcode = result?result:CURLE_SSH;
1917         break;
1918       }
1919       sshc->readdir_filename = malloc(PATH_MAX + 1);
1920       if(!sshc->readdir_filename) {
1921         state(conn, SSH_SFTP_CLOSE);
1922         sshc->actualcode = CURLE_OUT_OF_MEMORY;
1923         break;
1924       }
1925       sshc->readdir_longentry = malloc(PATH_MAX + 1);
1926       if(!sshc->readdir_longentry) {
1927         Curl_safefree(sshc->readdir_filename);
1928         state(conn, SSH_SFTP_CLOSE);
1929         sshc->actualcode = CURLE_OUT_OF_MEMORY;
1930         break;
1931       }
1932       state(conn, SSH_SFTP_READDIR);
1933       break;
1934
1935     case SSH_SFTP_READDIR:
1936       sshc->readdir_len = libssh2_sftp_readdir_ex(sshc->sftp_handle,
1937                                                   sshc->readdir_filename,
1938                                                   PATH_MAX,
1939                                                   sshc->readdir_longentry,
1940                                                   PATH_MAX,
1941                                                   &sshc->readdir_attrs);
1942       if(sshc->readdir_len == LIBSSH2_ERROR_EAGAIN) {
1943         rc = LIBSSH2_ERROR_EAGAIN;
1944         break;
1945       }
1946       if(sshc->readdir_len > 0) {
1947         sshc->readdir_filename[sshc->readdir_len] = '\0';
1948
1949         if(data->set.ftp_list_only) {
1950           char *tmpLine;
1951
1952           tmpLine = aprintf("%s\n", sshc->readdir_filename);
1953           if(tmpLine == NULL) {
1954             state(conn, SSH_SFTP_CLOSE);
1955             sshc->actualcode = CURLE_OUT_OF_MEMORY;
1956             break;
1957           }
1958           result = Curl_client_write(conn, CLIENTWRITE_BODY,
1959                                      tmpLine, sshc->readdir_len + 1);
1960           free(tmpLine);
1961
1962           if(result) {
1963             state(conn, SSH_STOP);
1964             break;
1965           }
1966           /* since this counts what we send to the client, we include the
1967              newline in this counter */
1968           data->req.bytecount += sshc->readdir_len + 1;
1969
1970           /* output debug output if that is requested */
1971           if(data->set.verbose) {
1972             Curl_debug(data, CURLINFO_DATA_OUT, sshc->readdir_filename,
1973                        sshc->readdir_len, conn);
1974           }
1975         }
1976         else {
1977           sshc->readdir_currLen = (int)strlen(sshc->readdir_longentry);
1978           sshc->readdir_totalLen = 80 + sshc->readdir_currLen;
1979           sshc->readdir_line = calloc(sshc->readdir_totalLen, 1);
1980           if(!sshc->readdir_line) {
1981             Curl_safefree(sshc->readdir_filename);
1982             Curl_safefree(sshc->readdir_longentry);
1983             state(conn, SSH_SFTP_CLOSE);
1984             sshc->actualcode = CURLE_OUT_OF_MEMORY;
1985             break;
1986           }
1987
1988           memcpy(sshc->readdir_line, sshc->readdir_longentry,
1989                  sshc->readdir_currLen);
1990           if((sshc->readdir_attrs.flags & LIBSSH2_SFTP_ATTR_PERMISSIONS) &&
1991              ((sshc->readdir_attrs.permissions & LIBSSH2_SFTP_S_IFMT) ==
1992               LIBSSH2_SFTP_S_IFLNK)) {
1993             sshc->readdir_linkPath = malloc(PATH_MAX + 1);
1994             if(sshc->readdir_linkPath == NULL) {
1995               Curl_safefree(sshc->readdir_filename);
1996               Curl_safefree(sshc->readdir_longentry);
1997               state(conn, SSH_SFTP_CLOSE);
1998               sshc->actualcode = CURLE_OUT_OF_MEMORY;
1999               break;
2000             }
2001
2002             snprintf(sshc->readdir_linkPath, PATH_MAX, "%s%s", sftp_scp->path,
2003                      sshc->readdir_filename);
2004             state(conn, SSH_SFTP_READDIR_LINK);
2005             break;
2006           }
2007           state(conn, SSH_SFTP_READDIR_BOTTOM);
2008           break;
2009         }
2010       }
2011       else if(sshc->readdir_len == 0) {
2012         Curl_safefree(sshc->readdir_filename);
2013         Curl_safefree(sshc->readdir_longentry);
2014         state(conn, SSH_SFTP_READDIR_DONE);
2015         break;
2016       }
2017       else if(sshc->readdir_len <= 0) {
2018         err = sftp_libssh2_last_error(sshc->sftp_session);
2019         result = sftp_libssh2_error_to_CURLE(err);
2020         sshc->actualcode = result?result:CURLE_SSH;
2021         failf(data, "Could not open remote file for reading: %s :: %d",
2022               sftp_libssh2_strerror(err),
2023               libssh2_session_last_errno(sshc->ssh_session));
2024         Curl_safefree(sshc->readdir_filename);
2025         Curl_safefree(sshc->readdir_longentry);
2026         state(conn, SSH_SFTP_CLOSE);
2027         break;
2028       }
2029       break;
2030
2031     case SSH_SFTP_READDIR_LINK:
2032       sshc->readdir_len =
2033         libssh2_sftp_symlink_ex(sshc->sftp_session,
2034                                 sshc->readdir_linkPath,
2035                                 curlx_uztoui(strlen(sshc->readdir_linkPath)),
2036                                 sshc->readdir_filename,
2037                                 PATH_MAX, LIBSSH2_SFTP_READLINK);
2038       if(sshc->readdir_len == LIBSSH2_ERROR_EAGAIN) {
2039         rc = LIBSSH2_ERROR_EAGAIN;
2040         break;
2041       }
2042       Curl_safefree(sshc->readdir_linkPath);
2043
2044       /* get room for the filename and extra output */
2045       sshc->readdir_totalLen += 4 + sshc->readdir_len;
2046       new_readdir_line = Curl_saferealloc(sshc->readdir_line,
2047                                           sshc->readdir_totalLen);
2048       if(!new_readdir_line) {
2049         sshc->readdir_line = NULL;
2050         Curl_safefree(sshc->readdir_filename);
2051         Curl_safefree(sshc->readdir_longentry);
2052         state(conn, SSH_SFTP_CLOSE);
2053         sshc->actualcode = CURLE_OUT_OF_MEMORY;
2054         break;
2055       }
2056       sshc->readdir_line = new_readdir_line;
2057
2058       sshc->readdir_currLen += snprintf(sshc->readdir_line +
2059                                         sshc->readdir_currLen,
2060                                         sshc->readdir_totalLen -
2061                                         sshc->readdir_currLen,
2062                                         " -> %s",
2063                                         sshc->readdir_filename);
2064
2065       state(conn, SSH_SFTP_READDIR_BOTTOM);
2066       break;
2067
2068     case SSH_SFTP_READDIR_BOTTOM:
2069       sshc->readdir_currLen += snprintf(sshc->readdir_line +
2070                                         sshc->readdir_currLen,
2071                                         sshc->readdir_totalLen -
2072                                         sshc->readdir_currLen, "\n");
2073       result = Curl_client_write(conn, CLIENTWRITE_BODY,
2074                                  sshc->readdir_line,
2075                                  sshc->readdir_currLen);
2076
2077       if(!result) {
2078
2079         /* output debug output if that is requested */
2080         if(data->set.verbose) {
2081           Curl_debug(data, CURLINFO_DATA_OUT, sshc->readdir_line,
2082                      sshc->readdir_currLen, conn);
2083         }
2084         data->req.bytecount += sshc->readdir_currLen;
2085       }
2086       Curl_safefree(sshc->readdir_line);
2087       if(result) {
2088         state(conn, SSH_STOP);
2089       }
2090       else
2091         state(conn, SSH_SFTP_READDIR);
2092       break;
2093
2094     case SSH_SFTP_READDIR_DONE:
2095       if(libssh2_sftp_closedir(sshc->sftp_handle) ==
2096          LIBSSH2_ERROR_EAGAIN) {
2097         rc = LIBSSH2_ERROR_EAGAIN;
2098         break;
2099       }
2100       sshc->sftp_handle = NULL;
2101       Curl_safefree(sshc->readdir_filename);
2102       Curl_safefree(sshc->readdir_longentry);
2103
2104       /* no data to transfer */
2105       Curl_setup_transfer(conn, -1, -1, FALSE, NULL, -1, NULL);
2106       state(conn, SSH_STOP);
2107       break;
2108
2109     case SSH_SFTP_DOWNLOAD_INIT:
2110       /*
2111        * Work on getting the specified file
2112        */
2113       sshc->sftp_handle =
2114         libssh2_sftp_open_ex(sshc->sftp_session, sftp_scp->path,
2115                              curlx_uztoui(strlen(sftp_scp->path)),
2116                              LIBSSH2_FXF_READ, data->set.new_file_perms,
2117                              LIBSSH2_SFTP_OPENFILE);
2118       if(!sshc->sftp_handle) {
2119         if(libssh2_session_last_errno(sshc->ssh_session) ==
2120            LIBSSH2_ERROR_EAGAIN) {
2121           rc = LIBSSH2_ERROR_EAGAIN;
2122           break;
2123         }
2124         err = sftp_libssh2_last_error(sshc->sftp_session);
2125         failf(data, "Could not open remote file for reading: %s",
2126               sftp_libssh2_strerror(err));
2127         state(conn, SSH_SFTP_CLOSE);
2128         result = sftp_libssh2_error_to_CURLE(err);
2129         sshc->actualcode = result?result:CURLE_SSH;
2130         break;
2131       }
2132       state(conn, SSH_SFTP_DOWNLOAD_STAT);
2133       break;
2134
2135     case SSH_SFTP_DOWNLOAD_STAT:
2136     {
2137       LIBSSH2_SFTP_ATTRIBUTES attrs;
2138
2139       rc = libssh2_sftp_stat_ex(sshc->sftp_session, sftp_scp->path,
2140                                 curlx_uztoui(strlen(sftp_scp->path)),
2141                                 LIBSSH2_SFTP_STAT, &attrs);
2142       if(rc == LIBSSH2_ERROR_EAGAIN) {
2143         break;
2144       }
2145       if(rc ||
2146               !(attrs.flags & LIBSSH2_SFTP_ATTR_SIZE) ||
2147               (attrs.filesize == 0)) {
2148         /*
2149          * libssh2_sftp_open() didn't return an error, so maybe the server
2150          * just doesn't support stat()
2151          * OR the server doesn't return a file size with a stat()
2152          * OR file size is 0
2153          */
2154         data->req.size = -1;
2155         data->req.maxdownload = -1;
2156         Curl_pgrsSetDownloadSize(data, -1);
2157       }
2158       else {
2159         curl_off_t size = attrs.filesize;
2160
2161         if(size < 0) {
2162           failf(data, "Bad file size (%" CURL_FORMAT_CURL_OFF_T ")", size);
2163           return CURLE_BAD_DOWNLOAD_RESUME;
2164         }
2165         if(conn->data->state.use_range) {
2166           curl_off_t from, to;
2167           char *ptr;
2168           char *ptr2;
2169           CURLofft to_t;
2170           CURLofft from_t;
2171
2172           from_t = curlx_strtoofft(conn->data->state.range, &ptr, 0, &from);
2173           if(from_t == CURL_OFFT_FLOW)
2174             return CURLE_RANGE_ERROR;
2175           while(*ptr && (ISSPACE(*ptr) || (*ptr == '-')))
2176             ptr++;
2177           to_t = curlx_strtoofft(ptr, &ptr2, 0, &to);
2178           if(to_t == CURL_OFFT_FLOW)
2179             return CURLE_RANGE_ERROR;
2180           if((to_t == CURL_OFFT_INVAL) /* no "to" value given */
2181              || (to >= size)) {
2182             to = size - 1;
2183           }
2184           if(from_t) {
2185             /* from is relative to end of file */
2186             from = size - to;
2187             to = size - 1;
2188           }
2189           if(from > size) {
2190             failf(data, "Offset (%"
2191                   CURL_FORMAT_CURL_OFF_T ") was beyond file size (%"
2192                   CURL_FORMAT_CURL_OFF_T ")", from, attrs.filesize);
2193             return CURLE_BAD_DOWNLOAD_RESUME;
2194           }
2195           if(from > to) {
2196             from = to;
2197             size = 0;
2198           }
2199           else {
2200             size = to - from + 1;
2201           }
2202
2203           SFTP_SEEK(conn->proto.sshc.sftp_handle, from);
2204         }
2205         data->req.size = size;
2206         data->req.maxdownload = size;
2207         Curl_pgrsSetDownloadSize(data, size);
2208       }
2209
2210       /* We can resume if we can seek to the resume position */
2211       if(data->state.resume_from) {
2212         if(data->state.resume_from < 0) {
2213           /* We're supposed to download the last abs(from) bytes */
2214           if((curl_off_t)attrs.filesize < -data->state.resume_from) {
2215             failf(data, "Offset (%"
2216                   CURL_FORMAT_CURL_OFF_T ") was beyond file size (%"
2217                   CURL_FORMAT_CURL_OFF_T ")",
2218                   data->state.resume_from, attrs.filesize);
2219             return CURLE_BAD_DOWNLOAD_RESUME;
2220           }
2221           /* download from where? */
2222           data->state.resume_from += attrs.filesize;
2223         }
2224         else {
2225           if((curl_off_t)attrs.filesize < data->state.resume_from) {
2226             failf(data, "Offset (%" CURL_FORMAT_CURL_OFF_T
2227                   ") was beyond file size (%" CURL_FORMAT_CURL_OFF_T ")",
2228                   data->state.resume_from, attrs.filesize);
2229             return CURLE_BAD_DOWNLOAD_RESUME;
2230           }
2231         }
2232         /* Does a completed file need to be seeked and started or closed ? */
2233         /* Now store the number of bytes we are expected to download */
2234         data->req.size = attrs.filesize - data->state.resume_from;
2235         data->req.maxdownload = attrs.filesize - data->state.resume_from;
2236         Curl_pgrsSetDownloadSize(data,
2237                                  attrs.filesize - data->state.resume_from);
2238         SFTP_SEEK(sshc->sftp_handle, data->state.resume_from);
2239       }
2240     }
2241
2242     /* Setup the actual download */
2243     if(data->req.size == 0) {
2244       /* no data to transfer */
2245       Curl_setup_transfer(conn, -1, -1, FALSE, NULL, -1, NULL);
2246       infof(data, "File already completely downloaded\n");
2247       state(conn, SSH_STOP);
2248       break;
2249     }
2250     Curl_setup_transfer(conn, FIRSTSOCKET, data->req.size,
2251                         FALSE, NULL, -1, NULL);
2252
2253     /* not set by Curl_setup_transfer to preserve keepon bits */
2254     conn->writesockfd = conn->sockfd;
2255
2256     /* we want to use the _receiving_ function even when the socket turns
2257        out writableable as the underlying libssh2 recv function will deal
2258        with both accordingly */
2259     conn->cselect_bits = CURL_CSELECT_IN;
2260
2261     if(result) {
2262       /* this should never occur; the close state should be entered
2263          at the time the error occurs */
2264       state(conn, SSH_SFTP_CLOSE);
2265       sshc->actualcode = result;
2266     }
2267     else {
2268       state(conn, SSH_STOP);
2269     }
2270     break;
2271
2272     case SSH_SFTP_CLOSE:
2273       if(sshc->sftp_handle) {
2274         rc = libssh2_sftp_close(sshc->sftp_handle);
2275         if(rc == LIBSSH2_ERROR_EAGAIN) {
2276           break;
2277         }
2278         if(rc < 0) {
2279           infof(data, "Failed to close libssh2 file\n");
2280         }
2281         sshc->sftp_handle = NULL;
2282       }
2283
2284       Curl_safefree(sftp_scp->path);
2285
2286       DEBUGF(infof(data, "SFTP DONE done\n"));
2287
2288       /* Check if nextstate is set and move .nextstate could be POSTQUOTE_INIT
2289          After nextstate is executed, the control should come back to
2290          SSH_SFTP_CLOSE to pass the correct result back  */
2291       if(sshc->nextstate != SSH_NO_STATE &&
2292          sshc->nextstate != SSH_SFTP_CLOSE) {
2293         state(conn, sshc->nextstate);
2294         sshc->nextstate = SSH_SFTP_CLOSE;
2295       }
2296       else {
2297         state(conn, SSH_STOP);
2298         result = sshc->actualcode;
2299       }
2300       break;
2301
2302     case SSH_SFTP_SHUTDOWN:
2303       /* during times we get here due to a broken transfer and then the
2304          sftp_handle might not have been taken down so make sure that is done
2305          before we proceed */
2306
2307       if(sshc->sftp_handle) {
2308         rc = libssh2_sftp_close(sshc->sftp_handle);
2309         if(rc == LIBSSH2_ERROR_EAGAIN) {
2310           break;
2311         }
2312         if(rc < 0) {
2313           infof(data, "Failed to close libssh2 file\n");
2314         }
2315         sshc->sftp_handle = NULL;
2316       }
2317       if(sshc->sftp_session) {
2318         rc = libssh2_sftp_shutdown(sshc->sftp_session);
2319         if(rc == LIBSSH2_ERROR_EAGAIN) {
2320           break;
2321         }
2322         if(rc < 0) {
2323           infof(data, "Failed to stop libssh2 sftp subsystem\n");
2324         }
2325         sshc->sftp_session = NULL;
2326       }
2327
2328       Curl_safefree(sshc->homedir);
2329       conn->data->state.most_recent_ftp_entrypath = NULL;
2330
2331       state(conn, SSH_SESSION_DISCONNECT);
2332       break;
2333
2334     case SSH_SCP_TRANS_INIT:
2335       result = Curl_getworkingpath(conn, sshc->homedir, &sftp_scp->path);
2336       if(result) {
2337         sshc->actualcode = result;
2338         state(conn, SSH_STOP);
2339         break;
2340       }
2341
2342       if(data->set.upload) {
2343         if(data->state.infilesize < 0) {
2344           failf(data, "SCP requires a known file size for upload");
2345           sshc->actualcode = CURLE_UPLOAD_FAILED;
2346           state(conn, SSH_SCP_CHANNEL_FREE);
2347           break;
2348         }
2349         state(conn, SSH_SCP_UPLOAD_INIT);
2350       }
2351       else {
2352         state(conn, SSH_SCP_DOWNLOAD_INIT);
2353       }
2354       break;
2355
2356     case SSH_SCP_UPLOAD_INIT:
2357       /*
2358        * libssh2 requires that the destination path is a full path that
2359        * includes the destination file and name OR ends in a "/" .  If this is
2360        * not done the destination file will be named the same name as the last
2361        * directory in the path.
2362        */
2363       sshc->ssh_channel =
2364         SCP_SEND(sshc->ssh_session, sftp_scp->path, data->set.new_file_perms,
2365                  data->state.infilesize);
2366       if(!sshc->ssh_channel) {
2367         int ssh_err;
2368         char *err_msg;
2369
2370         if(libssh2_session_last_errno(sshc->ssh_session) ==
2371            LIBSSH2_ERROR_EAGAIN) {
2372           rc = LIBSSH2_ERROR_EAGAIN;
2373           break;
2374         }
2375
2376         ssh_err = (int)(libssh2_session_last_error(sshc->ssh_session,
2377                                                    &err_msg, NULL, 0));
2378         failf(conn->data, "%s", err_msg);
2379         state(conn, SSH_SCP_CHANNEL_FREE);
2380         sshc->actualcode = libssh2_session_error_to_CURLE(ssh_err);
2381         /* Map generic errors to upload failed */
2382         if(sshc->actualcode == CURLE_SSH ||
2383            sshc->actualcode == CURLE_REMOTE_FILE_NOT_FOUND)
2384           sshc->actualcode = CURLE_UPLOAD_FAILED;
2385         break;
2386       }
2387
2388       /* upload data */
2389       Curl_setup_transfer(conn, -1, data->req.size, FALSE, NULL,
2390                           FIRSTSOCKET, NULL);
2391
2392       /* not set by Curl_setup_transfer to preserve keepon bits */
2393       conn->sockfd = conn->writesockfd;
2394
2395       if(result) {
2396         state(conn, SSH_SCP_CHANNEL_FREE);
2397         sshc->actualcode = result;
2398       }
2399       else {
2400         /* store this original bitmask setup to use later on if we can't
2401            figure out a "real" bitmask */
2402         sshc->orig_waitfor = data->req.keepon;
2403
2404         /* we want to use the _sending_ function even when the socket turns
2405            out readable as the underlying libssh2 scp send function will deal
2406            with both accordingly */
2407         conn->cselect_bits = CURL_CSELECT_OUT;
2408
2409         state(conn, SSH_STOP);
2410       }
2411       break;
2412
2413     case SSH_SCP_DOWNLOAD_INIT:
2414     {
2415       curl_off_t bytecount;
2416
2417       /*
2418        * We must check the remote file; if it is a directory no values will
2419        * be set in sb
2420        */
2421
2422        /*
2423         * If support for >2GB files exists, use it.
2424         */
2425
2426       /* get a fresh new channel from the ssh layer */
2427 #if LIBSSH2_VERSION_NUM < 0x010700
2428       struct stat sb;
2429       memset(&sb, 0, sizeof(struct stat));
2430       sshc->ssh_channel = libssh2_scp_recv(sshc->ssh_session,
2431                                            sftp_scp->path, &sb);
2432 #else
2433       libssh2_struct_stat sb;
2434       memset(&sb, 0, sizeof(libssh2_struct_stat));
2435       sshc->ssh_channel = libssh2_scp_recv2(sshc->ssh_session,
2436                                             sftp_scp->path, &sb);
2437 #endif
2438
2439       if(!sshc->ssh_channel) {
2440         int ssh_err;
2441         char *err_msg;
2442
2443         if(libssh2_session_last_errno(sshc->ssh_session) ==
2444            LIBSSH2_ERROR_EAGAIN) {
2445           rc = LIBSSH2_ERROR_EAGAIN;
2446           break;
2447         }
2448
2449
2450         ssh_err = (int)(libssh2_session_last_error(sshc->ssh_session,
2451                                                    &err_msg, NULL, 0));
2452         failf(conn->data, "%s", err_msg);
2453         state(conn, SSH_SCP_CHANNEL_FREE);
2454         sshc->actualcode = libssh2_session_error_to_CURLE(ssh_err);
2455         break;
2456       }
2457
2458       /* download data */
2459       bytecount = (curl_off_t)sb.st_size;
2460       data->req.maxdownload =  (curl_off_t)sb.st_size;
2461       Curl_setup_transfer(conn, FIRSTSOCKET, bytecount, FALSE, NULL, -1, NULL);
2462
2463       /* not set by Curl_setup_transfer to preserve keepon bits */
2464       conn->writesockfd = conn->sockfd;
2465
2466       /* we want to use the _receiving_ function even when the socket turns
2467          out writableable as the underlying libssh2 recv function will deal
2468          with both accordingly */
2469       conn->cselect_bits = CURL_CSELECT_IN;
2470
2471       if(result) {
2472         state(conn, SSH_SCP_CHANNEL_FREE);
2473         sshc->actualcode = result;
2474       }
2475       else
2476         state(conn, SSH_STOP);
2477     }
2478     break;
2479
2480     case SSH_SCP_DONE:
2481       if(data->set.upload)
2482         state(conn, SSH_SCP_SEND_EOF);
2483       else
2484         state(conn, SSH_SCP_CHANNEL_FREE);
2485       break;
2486
2487     case SSH_SCP_SEND_EOF:
2488       if(sshc->ssh_channel) {
2489         rc = libssh2_channel_send_eof(sshc->ssh_channel);
2490         if(rc == LIBSSH2_ERROR_EAGAIN) {
2491           break;
2492         }
2493         if(rc) {
2494           infof(data, "Failed to send libssh2 channel EOF\n");
2495         }
2496       }
2497       state(conn, SSH_SCP_WAIT_EOF);
2498       break;
2499
2500     case SSH_SCP_WAIT_EOF:
2501       if(sshc->ssh_channel) {
2502         rc = libssh2_channel_wait_eof(sshc->ssh_channel);
2503         if(rc == LIBSSH2_ERROR_EAGAIN) {
2504           break;
2505         }
2506         if(rc) {
2507           infof(data, "Failed to get channel EOF: %d\n", rc);
2508         }
2509       }
2510       state(conn, SSH_SCP_WAIT_CLOSE);
2511       break;
2512
2513     case SSH_SCP_WAIT_CLOSE:
2514       if(sshc->ssh_channel) {
2515         rc = libssh2_channel_wait_closed(sshc->ssh_channel);
2516         if(rc == LIBSSH2_ERROR_EAGAIN) {
2517           break;
2518         }
2519         if(rc) {
2520           infof(data, "Channel failed to close: %d\n", rc);
2521         }
2522       }
2523       state(conn, SSH_SCP_CHANNEL_FREE);
2524       break;
2525
2526     case SSH_SCP_CHANNEL_FREE:
2527       if(sshc->ssh_channel) {
2528         rc = libssh2_channel_free(sshc->ssh_channel);
2529         if(rc == LIBSSH2_ERROR_EAGAIN) {
2530           break;
2531         }
2532         if(rc < 0) {
2533           infof(data, "Failed to free libssh2 scp subsystem\n");
2534         }
2535         sshc->ssh_channel = NULL;
2536       }
2537       DEBUGF(infof(data, "SCP DONE phase complete\n"));
2538 #if 0 /* PREV */
2539       state(conn, SSH_SESSION_DISCONNECT);
2540 #endif
2541       state(conn, SSH_STOP);
2542       result = sshc->actualcode;
2543       break;
2544
2545     case SSH_SESSION_DISCONNECT:
2546       /* during weird times when we've been prematurely aborted, the channel
2547          is still alive when we reach this state and we MUST kill the channel
2548          properly first */
2549       if(sshc->ssh_channel) {
2550         rc = libssh2_channel_free(sshc->ssh_channel);
2551         if(rc == LIBSSH2_ERROR_EAGAIN) {
2552           break;
2553         }
2554         if(rc < 0) {
2555           infof(data, "Failed to free libssh2 scp subsystem\n");
2556         }
2557         sshc->ssh_channel = NULL;
2558       }
2559
2560       if(sshc->ssh_session) {
2561         rc = libssh2_session_disconnect(sshc->ssh_session, "Shutdown");
2562         if(rc == LIBSSH2_ERROR_EAGAIN) {
2563           break;
2564         }
2565         if(rc < 0) {
2566           infof(data, "Failed to disconnect libssh2 session\n");
2567         }
2568       }
2569
2570       Curl_safefree(sshc->homedir);
2571       conn->data->state.most_recent_ftp_entrypath = NULL;
2572
2573       state(conn, SSH_SESSION_FREE);
2574       break;
2575
2576     case SSH_SESSION_FREE:
2577 #ifdef HAVE_LIBSSH2_KNOWNHOST_API
2578       if(sshc->kh) {
2579         libssh2_knownhost_free(sshc->kh);
2580         sshc->kh = NULL;
2581       }
2582 #endif
2583
2584 #ifdef HAVE_LIBSSH2_AGENT_API
2585       if(sshc->ssh_agent) {
2586         rc = libssh2_agent_disconnect(sshc->ssh_agent);
2587         if(rc == LIBSSH2_ERROR_EAGAIN) {
2588           break;
2589         }
2590         if(rc < 0) {
2591           infof(data, "Failed to disconnect from libssh2 agent\n");
2592         }
2593         libssh2_agent_free(sshc->ssh_agent);
2594         sshc->ssh_agent = NULL;
2595
2596         /* NB: there is no need to free identities, they are part of internal
2597            agent stuff */
2598         sshc->sshagent_identity = NULL;
2599         sshc->sshagent_prev_identity = NULL;
2600       }
2601 #endif
2602
2603       if(sshc->ssh_session) {
2604         rc = libssh2_session_free(sshc->ssh_session);
2605         if(rc == LIBSSH2_ERROR_EAGAIN) {
2606           break;
2607         }
2608         if(rc < 0) {
2609           infof(data, "Failed to free libssh2 session\n");
2610         }
2611         sshc->ssh_session = NULL;
2612       }
2613
2614       /* worst-case scenario cleanup */
2615
2616       DEBUGASSERT(sshc->ssh_session == NULL);
2617       DEBUGASSERT(sshc->ssh_channel == NULL);
2618       DEBUGASSERT(sshc->sftp_session == NULL);
2619       DEBUGASSERT(sshc->sftp_handle == NULL);
2620 #ifdef HAVE_LIBSSH2_KNOWNHOST_API
2621       DEBUGASSERT(sshc->kh == NULL);
2622 #endif
2623 #ifdef HAVE_LIBSSH2_AGENT_API
2624       DEBUGASSERT(sshc->ssh_agent == NULL);
2625 #endif
2626
2627       Curl_safefree(sshc->rsa_pub);
2628       Curl_safefree(sshc->rsa);
2629
2630       Curl_safefree(sshc->quote_path1);
2631       Curl_safefree(sshc->quote_path2);
2632
2633       Curl_safefree(sshc->homedir);
2634
2635       Curl_safefree(sshc->readdir_filename);
2636       Curl_safefree(sshc->readdir_longentry);
2637       Curl_safefree(sshc->readdir_line);
2638       Curl_safefree(sshc->readdir_linkPath);
2639
2640       /* the code we are about to return */
2641       result = sshc->actualcode;
2642
2643       memset(sshc, 0, sizeof(struct ssh_conn));
2644
2645       connclose(conn, "SSH session free");
2646       sshc->state = SSH_SESSION_FREE; /* current */
2647       sshc->nextstate = SSH_NO_STATE;
2648       state(conn, SSH_STOP);
2649       break;
2650
2651     case SSH_QUIT:
2652       /* fallthrough, just stop! */
2653     default:
2654       /* internal error */
2655       sshc->nextstate = SSH_NO_STATE;
2656       state(conn, SSH_STOP);
2657       break;
2658     }
2659
2660   } while(!rc && (sshc->state != SSH_STOP));
2661
2662   if(rc == LIBSSH2_ERROR_EAGAIN) {
2663     /* we would block, we need to wait for the socket to be ready (in the
2664        right direction too)! */
2665     *block = TRUE;
2666   }
2667
2668   return result;
2669 }
2670
2671 /* called by the multi interface to figure out what socket(s) to wait for and
2672    for what actions in the DO_DONE, PERFORM and WAITPERFORM states */
2673 static int ssh_perform_getsock(const struct connectdata *conn,
2674                                curl_socket_t *sock, /* points to numsocks
2675                                                        number of sockets */
2676                                int numsocks)
2677 {
2678 #ifdef HAVE_LIBSSH2_SESSION_BLOCK_DIRECTION
2679   int bitmap = GETSOCK_BLANK;
2680   (void)numsocks;
2681
2682   sock[0] = conn->sock[FIRSTSOCKET];
2683
2684   if(conn->waitfor & KEEP_RECV)
2685     bitmap |= GETSOCK_READSOCK(FIRSTSOCKET);
2686
2687   if(conn->waitfor & KEEP_SEND)
2688     bitmap |= GETSOCK_WRITESOCK(FIRSTSOCKET);
2689
2690   return bitmap;
2691 #else
2692   /* if we don't know the direction we can use the generic *_getsock()
2693      function even for the protocol_connect and doing states */
2694   return Curl_single_getsock(conn, sock, numsocks);
2695 #endif
2696 }
2697
2698 /* Generic function called by the multi interface to figure out what socket(s)
2699    to wait for and for what actions during the DOING and PROTOCONNECT states*/
2700 static int ssh_getsock(struct connectdata *conn,
2701                        curl_socket_t *sock, /* points to numsocks number
2702                                                of sockets */
2703                        int numsocks)
2704 {
2705 #ifndef HAVE_LIBSSH2_SESSION_BLOCK_DIRECTION
2706   (void)conn;
2707   (void)sock;
2708   (void)numsocks;
2709   /* if we don't know any direction we can just play along as we used to and
2710      not provide any sensible info */
2711   return GETSOCK_BLANK;
2712 #else
2713   /* if we know the direction we can use the generic *_getsock() function even
2714      for the protocol_connect and doing states */
2715   return ssh_perform_getsock(conn, sock, numsocks);
2716 #endif
2717 }
2718
2719 #ifdef HAVE_LIBSSH2_SESSION_BLOCK_DIRECTION
2720 /*
2721  * When one of the libssh2 functions has returned LIBSSH2_ERROR_EAGAIN this
2722  * function is used to figure out in what direction and stores this info so
2723  * that the multi interface can take advantage of it. Make sure to call this
2724  * function in all cases so that when it _doesn't_ return EAGAIN we can
2725  * restore the default wait bits.
2726  */
2727 static void ssh_block2waitfor(struct connectdata *conn, bool block)
2728 {
2729   struct ssh_conn *sshc = &conn->proto.sshc;
2730   int dir = 0;
2731   if(block) {
2732     dir = libssh2_session_block_directions(sshc->ssh_session);
2733     if(dir) {
2734       /* translate the libssh2 define bits into our own bit defines */
2735       conn->waitfor = ((dir&LIBSSH2_SESSION_BLOCK_INBOUND)?KEEP_RECV:0) |
2736         ((dir&LIBSSH2_SESSION_BLOCK_OUTBOUND)?KEEP_SEND:0);
2737     }
2738   }
2739   if(!dir)
2740     /* It didn't block or libssh2 didn't reveal in which direction, put back
2741        the original set */
2742     conn->waitfor = sshc->orig_waitfor;
2743 }
2744 #else
2745   /* no libssh2 directional support so we simply don't know */
2746 #define ssh_block2waitfor(x,y) Curl_nop_stmt
2747 #endif
2748
2749 /* called repeatedly until done from multi.c */
2750 static CURLcode ssh_multi_statemach(struct connectdata *conn, bool *done)
2751 {
2752   struct ssh_conn *sshc = &conn->proto.sshc;
2753   CURLcode result = CURLE_OK;
2754   bool block; /* we store the status and use that to provide a ssh_getsock()
2755                  implementation */
2756
2757   result = ssh_statemach_act(conn, &block);
2758   *done = (sshc->state == SSH_STOP) ? TRUE : FALSE;
2759   ssh_block2waitfor(conn, block);
2760
2761   return result;
2762 }
2763
2764 static CURLcode ssh_block_statemach(struct connectdata *conn,
2765                                     bool disconnect)
2766 {
2767   struct ssh_conn *sshc = &conn->proto.sshc;
2768   CURLcode result = CURLE_OK;
2769   struct Curl_easy *data = conn->data;
2770
2771   while((sshc->state != SSH_STOP) && !result) {
2772     bool block;
2773     timediff_t left = 1000;
2774     struct curltime now = Curl_now();
2775
2776     result = ssh_statemach_act(conn, &block);
2777     if(result)
2778       break;
2779
2780     if(!disconnect) {
2781       if(Curl_pgrsUpdate(conn))
2782         return CURLE_ABORTED_BY_CALLBACK;
2783
2784       result = Curl_speedcheck(data, now);
2785       if(result)
2786         break;
2787
2788       left = Curl_timeleft(data, NULL, FALSE);
2789       if(left < 0) {
2790         failf(data, "Operation timed out");
2791         return CURLE_OPERATION_TIMEDOUT;
2792       }
2793     }
2794
2795 #ifdef HAVE_LIBSSH2_SESSION_BLOCK_DIRECTION
2796     if(!result && block) {
2797       int dir = libssh2_session_block_directions(sshc->ssh_session);
2798       curl_socket_t sock = conn->sock[FIRSTSOCKET];
2799       curl_socket_t fd_read = CURL_SOCKET_BAD;
2800       curl_socket_t fd_write = CURL_SOCKET_BAD;
2801       if(LIBSSH2_SESSION_BLOCK_INBOUND & dir)
2802         fd_read = sock;
2803       if(LIBSSH2_SESSION_BLOCK_OUTBOUND & dir)
2804         fd_write = sock;
2805       /* wait for the socket to become ready */
2806       (void)Curl_socket_check(fd_read, CURL_SOCKET_BAD, fd_write,
2807                               left>1000?1000:left); /* ignore result */
2808     }
2809 #endif
2810
2811   }
2812
2813   return result;
2814 }
2815
2816 /*
2817  * SSH setup and connection
2818  */
2819 static CURLcode ssh_setup_connection(struct connectdata *conn)
2820 {
2821   struct SSHPROTO *ssh;
2822
2823   conn->data->req.protop = ssh = calloc(1, sizeof(struct SSHPROTO));
2824   if(!ssh)
2825     return CURLE_OUT_OF_MEMORY;
2826
2827   return CURLE_OK;
2828 }
2829
2830 static Curl_recv scp_recv, sftp_recv;
2831 static Curl_send scp_send, sftp_send;
2832
2833 /*
2834  * Curl_ssh_connect() gets called from Curl_protocol_connect() to allow us to
2835  * do protocol-specific actions at connect-time.
2836  */
2837 static CURLcode ssh_connect(struct connectdata *conn, bool *done)
2838 {
2839 #ifdef CURL_LIBSSH2_DEBUG
2840   curl_socket_t sock;
2841 #endif
2842   struct ssh_conn *ssh;
2843   CURLcode result;
2844   struct Curl_easy *data = conn->data;
2845
2846   /* initialize per-handle data if not already */
2847   if(!data->req.protop)
2848     ssh_setup_connection(conn);
2849
2850   /* We default to persistent connections. We set this already in this connect
2851      function to make the re-use checks properly be able to check this bit. */
2852   connkeep(conn, "SSH default");
2853
2854   if(conn->handler->protocol & CURLPROTO_SCP) {
2855     conn->recv[FIRSTSOCKET] = scp_recv;
2856     conn->send[FIRSTSOCKET] = scp_send;
2857   }
2858   else {
2859     conn->recv[FIRSTSOCKET] = sftp_recv;
2860     conn->send[FIRSTSOCKET] = sftp_send;
2861   }
2862   ssh = &conn->proto.sshc;
2863
2864 #ifdef CURL_LIBSSH2_DEBUG
2865   if(conn->user) {
2866     infof(data, "User: %s\n", conn->user);
2867   }
2868   if(conn->passwd) {
2869     infof(data, "Password: %s\n", conn->passwd);
2870   }
2871   sock = conn->sock[FIRSTSOCKET];
2872 #endif /* CURL_LIBSSH2_DEBUG */
2873
2874   ssh->ssh_session = libssh2_session_init_ex(my_libssh2_malloc,
2875                                              my_libssh2_free,
2876                                              my_libssh2_realloc, conn);
2877   if(ssh->ssh_session == NULL) {
2878     failf(data, "Failure initialising ssh session");
2879     return CURLE_FAILED_INIT;
2880   }
2881
2882   if(data->set.ssh_compression) {
2883 #if LIBSSH2_VERSION_NUM >= 0x010208
2884     if(libssh2_session_flag(ssh->ssh_session, LIBSSH2_FLAG_COMPRESS, 1) < 0)
2885 #endif
2886       infof(data, "Failed to enable compression for ssh session\n");
2887   }
2888
2889 #ifdef HAVE_LIBSSH2_KNOWNHOST_API
2890   if(data->set.str[STRING_SSH_KNOWNHOSTS]) {
2891     int rc;
2892     ssh->kh = libssh2_knownhost_init(ssh->ssh_session);
2893     if(!ssh->kh) {
2894       /* eeek. TODO: free the ssh_session! */
2895       return CURLE_FAILED_INIT;
2896     }
2897
2898     /* read all known hosts from there */
2899     rc = libssh2_knownhost_readfile(ssh->kh,
2900                                     data->set.str[STRING_SSH_KNOWNHOSTS],
2901                                     LIBSSH2_KNOWNHOST_FILE_OPENSSH);
2902     if(rc < 0)
2903       infof(data, "Failed to read known hosts from %s\n",
2904             data->set.str[STRING_SSH_KNOWNHOSTS]);
2905   }
2906 #endif /* HAVE_LIBSSH2_KNOWNHOST_API */
2907
2908 #ifdef CURL_LIBSSH2_DEBUG
2909   libssh2_trace(ssh->ssh_session, ~0);
2910   infof(data, "SSH socket: %d\n", (int)sock);
2911 #endif /* CURL_LIBSSH2_DEBUG */
2912
2913   state(conn, SSH_INIT);
2914
2915   result = ssh_multi_statemach(conn, done);
2916
2917   return result;
2918 }
2919
2920 /*
2921  ***********************************************************************
2922  *
2923  * scp_perform()
2924  *
2925  * This is the actual DO function for SCP. Get a file according to
2926  * the options previously setup.
2927  */
2928
2929 static
2930 CURLcode scp_perform(struct connectdata *conn,
2931                       bool *connected,
2932                       bool *dophase_done)
2933 {
2934   CURLcode result = CURLE_OK;
2935
2936   DEBUGF(infof(conn->data, "DO phase starts\n"));
2937
2938   *dophase_done = FALSE; /* not done yet */
2939
2940   /* start the first command in the DO phase */
2941   state(conn, SSH_SCP_TRANS_INIT);
2942
2943   /* run the state-machine */
2944   result = ssh_multi_statemach(conn, dophase_done);
2945
2946   *connected = conn->bits.tcpconnect[FIRSTSOCKET];
2947
2948   if(*dophase_done) {
2949     DEBUGF(infof(conn->data, "DO phase is complete\n"));
2950   }
2951
2952   return result;
2953 }
2954
2955 /* called from multi.c while DOing */
2956 static CURLcode scp_doing(struct connectdata *conn,
2957                                bool *dophase_done)
2958 {
2959   CURLcode result;
2960   result = ssh_multi_statemach(conn, dophase_done);
2961
2962   if(*dophase_done) {
2963     DEBUGF(infof(conn->data, "DO phase is complete\n"));
2964   }
2965   return result;
2966 }
2967
2968 /*
2969  * The DO function is generic for both protocols. There was previously two
2970  * separate ones but this way means less duplicated code.
2971  */
2972
2973 static CURLcode ssh_do(struct connectdata *conn, bool *done)
2974 {
2975   CURLcode result;
2976   bool connected = 0;
2977   struct Curl_easy *data = conn->data;
2978   struct ssh_conn *sshc = &conn->proto.sshc;
2979
2980   *done = FALSE; /* default to false */
2981
2982   data->req.size = -1; /* make sure this is unknown at this point */
2983
2984   sshc->actualcode = CURLE_OK; /* reset error code */
2985   sshc->secondCreateDirs = 0;   /* reset the create dir attempt state
2986                                    variable */
2987
2988   Curl_pgrsSetUploadCounter(data, 0);
2989   Curl_pgrsSetDownloadCounter(data, 0);
2990   Curl_pgrsSetUploadSize(data, -1);
2991   Curl_pgrsSetDownloadSize(data, -1);
2992
2993   if(conn->handler->protocol & CURLPROTO_SCP)
2994     result = scp_perform(conn, &connected,  done);
2995   else
2996     result = sftp_perform(conn, &connected,  done);
2997
2998   return result;
2999 }
3000
3001 /* BLOCKING, but the function is using the state machine so the only reason
3002    this is still blocking is that the multi interface code has no support for
3003    disconnecting operations that takes a while */
3004 static CURLcode scp_disconnect(struct connectdata *conn, bool dead_connection)
3005 {
3006   CURLcode result = CURLE_OK;
3007   struct ssh_conn *ssh = &conn->proto.sshc;
3008   (void) dead_connection;
3009
3010   if(ssh->ssh_session) {
3011     /* only if there's a session still around to use! */
3012
3013     state(conn, SSH_SESSION_DISCONNECT);
3014
3015     result = ssh_block_statemach(conn, TRUE);
3016   }
3017
3018   return result;
3019 }
3020
3021 /* generic done function for both SCP and SFTP called from their specific
3022    done functions */
3023 static CURLcode ssh_done(struct connectdata *conn, CURLcode status)
3024 {
3025   CURLcode result = CURLE_OK;
3026   struct SSHPROTO *sftp_scp = conn->data->req.protop;
3027
3028   if(!status) {
3029     /* run the state-machine
3030
3031        TODO: when the multi interface is used, this _really_ should be using
3032        the ssh_multi_statemach function but we have no general support for
3033        non-blocking DONE operations!
3034     */
3035     result = ssh_block_statemach(conn, FALSE);
3036   }
3037   else
3038     result = status;
3039
3040   if(sftp_scp)
3041     Curl_safefree(sftp_scp->path);
3042   if(Curl_pgrsDone(conn))
3043     return CURLE_ABORTED_BY_CALLBACK;
3044
3045   conn->data->req.keepon = 0; /* clear all bits */
3046   return result;
3047 }
3048
3049
3050 static CURLcode scp_done(struct connectdata *conn, CURLcode status,
3051                          bool premature)
3052 {
3053   (void)premature; /* not used */
3054
3055   if(!status)
3056     state(conn, SSH_SCP_DONE);
3057
3058   return ssh_done(conn, status);
3059
3060 }
3061
3062 static ssize_t scp_send(struct connectdata *conn, int sockindex,
3063                         const void *mem, size_t len, CURLcode *err)
3064 {
3065   ssize_t nwrite;
3066   (void)sockindex; /* we only support SCP on the fixed known primary socket */
3067
3068   /* libssh2_channel_write() returns int! */
3069   nwrite = (ssize_t)
3070     libssh2_channel_write(conn->proto.sshc.ssh_channel, mem, len);
3071
3072   ssh_block2waitfor(conn, (nwrite == LIBSSH2_ERROR_EAGAIN)?TRUE:FALSE);
3073
3074   if(nwrite == LIBSSH2_ERROR_EAGAIN) {
3075     *err = CURLE_AGAIN;
3076     nwrite = 0;
3077   }
3078   else if(nwrite < LIBSSH2_ERROR_NONE) {
3079     *err = libssh2_session_error_to_CURLE((int)nwrite);
3080     nwrite = -1;
3081   }
3082
3083   return nwrite;
3084 }
3085
3086 static ssize_t scp_recv(struct connectdata *conn, int sockindex,
3087                         char *mem, size_t len, CURLcode *err)
3088 {
3089   ssize_t nread;
3090   (void)sockindex; /* we only support SCP on the fixed known primary socket */
3091
3092   /* libssh2_channel_read() returns int */
3093   nread = (ssize_t)
3094     libssh2_channel_read(conn->proto.sshc.ssh_channel, mem, len);
3095
3096   ssh_block2waitfor(conn, (nread == LIBSSH2_ERROR_EAGAIN)?TRUE:FALSE);
3097   if(nread == LIBSSH2_ERROR_EAGAIN) {
3098     *err = CURLE_AGAIN;
3099     nread = -1;
3100   }
3101
3102   return nread;
3103 }
3104
3105 /*
3106  * =============== SFTP ===============
3107  */
3108
3109 /*
3110  ***********************************************************************
3111  *
3112  * sftp_perform()
3113  *
3114  * This is the actual DO function for SFTP. Get a file/directory according to
3115  * the options previously setup.
3116  */
3117
3118 static
3119 CURLcode sftp_perform(struct connectdata *conn,
3120                       bool *connected,
3121                       bool *dophase_done)
3122 {
3123   CURLcode result = CURLE_OK;
3124
3125   DEBUGF(infof(conn->data, "DO phase starts\n"));
3126
3127   *dophase_done = FALSE; /* not done yet */
3128
3129   /* start the first command in the DO phase */
3130   state(conn, SSH_SFTP_QUOTE_INIT);
3131
3132   /* run the state-machine */
3133   result = ssh_multi_statemach(conn, dophase_done);
3134
3135   *connected = conn->bits.tcpconnect[FIRSTSOCKET];
3136
3137   if(*dophase_done) {
3138     DEBUGF(infof(conn->data, "DO phase is complete\n"));
3139   }
3140
3141   return result;
3142 }
3143
3144 /* called from multi.c while DOing */
3145 static CURLcode sftp_doing(struct connectdata *conn,
3146                            bool *dophase_done)
3147 {
3148   CURLcode result = ssh_multi_statemach(conn, dophase_done);
3149
3150   if(*dophase_done) {
3151     DEBUGF(infof(conn->data, "DO phase is complete\n"));
3152   }
3153   return result;
3154 }
3155
3156 /* BLOCKING, but the function is using the state machine so the only reason
3157    this is still blocking is that the multi interface code has no support for
3158    disconnecting operations that takes a while */
3159 static CURLcode sftp_disconnect(struct connectdata *conn, bool dead_connection)
3160 {
3161   CURLcode result = CURLE_OK;
3162   (void) dead_connection;
3163
3164   DEBUGF(infof(conn->data, "SSH DISCONNECT starts now\n"));
3165
3166   if(conn->proto.sshc.ssh_session) {
3167     /* only if there's a session still around to use! */
3168     state(conn, SSH_SFTP_SHUTDOWN);
3169     result = ssh_block_statemach(conn, TRUE);
3170   }
3171
3172   DEBUGF(infof(conn->data, "SSH DISCONNECT is done\n"));
3173
3174   return result;
3175
3176 }
3177
3178 static CURLcode sftp_done(struct connectdata *conn, CURLcode status,
3179                                bool premature)
3180 {
3181   struct ssh_conn *sshc = &conn->proto.sshc;
3182
3183   if(!status) {
3184     /* Post quote commands are executed after the SFTP_CLOSE state to avoid
3185        errors that could happen due to open file handles during POSTQUOTE
3186        operation */
3187     if(!status && !premature && conn->data->set.postquote) {
3188       sshc->nextstate = SSH_SFTP_POSTQUOTE_INIT;
3189       state(conn, SSH_SFTP_CLOSE);
3190     }
3191     else
3192       state(conn, SSH_SFTP_CLOSE);
3193   }
3194   return ssh_done(conn, status);
3195 }
3196
3197 /* return number of sent bytes */
3198 static ssize_t sftp_send(struct connectdata *conn, int sockindex,
3199                          const void *mem, size_t len, CURLcode *err)
3200 {
3201   ssize_t nwrite;   /* libssh2_sftp_write() used to return size_t in 0.14
3202                        but is changed to ssize_t in 0.15. These days we don't
3203                        support libssh2 0.15*/
3204   (void)sockindex;
3205
3206   nwrite = libssh2_sftp_write(conn->proto.sshc.sftp_handle, mem, len);
3207
3208   ssh_block2waitfor(conn, (nwrite == LIBSSH2_ERROR_EAGAIN)?TRUE:FALSE);
3209
3210   if(nwrite == LIBSSH2_ERROR_EAGAIN) {
3211     *err = CURLE_AGAIN;
3212     nwrite = 0;
3213   }
3214   else if(nwrite < LIBSSH2_ERROR_NONE) {
3215     *err = libssh2_session_error_to_CURLE((int)nwrite);
3216     nwrite = -1;
3217   }
3218
3219   return nwrite;
3220 }
3221
3222 /*
3223  * Return number of received (decrypted) bytes
3224  * or <0 on error
3225  */
3226 static ssize_t sftp_recv(struct connectdata *conn, int sockindex,
3227                          char *mem, size_t len, CURLcode *err)
3228 {
3229   ssize_t nread;
3230   (void)sockindex;
3231
3232   nread = libssh2_sftp_read(conn->proto.sshc.sftp_handle, mem, len);
3233
3234   ssh_block2waitfor(conn, (nread == LIBSSH2_ERROR_EAGAIN)?TRUE:FALSE);
3235
3236   if(nread == LIBSSH2_ERROR_EAGAIN) {
3237     *err = CURLE_AGAIN;
3238     nread = -1;
3239
3240   }
3241   else if(nread < 0) {
3242     *err = libssh2_session_error_to_CURLE((int)nread);
3243   }
3244   return nread;
3245 }
3246
3247 static const char *sftp_libssh2_strerror(int err)
3248 {
3249   switch(err) {
3250     case LIBSSH2_FX_NO_SUCH_FILE:
3251       return "No such file or directory";
3252
3253     case LIBSSH2_FX_PERMISSION_DENIED:
3254       return "Permission denied";
3255
3256     case LIBSSH2_FX_FAILURE:
3257       return "Operation failed";
3258
3259     case LIBSSH2_FX_BAD_MESSAGE:
3260       return "Bad message from SFTP server";
3261
3262     case LIBSSH2_FX_NO_CONNECTION:
3263       return "Not connected to SFTP server";
3264
3265     case LIBSSH2_FX_CONNECTION_LOST:
3266       return "Connection to SFTP server lost";
3267
3268     case LIBSSH2_FX_OP_UNSUPPORTED:
3269       return "Operation not supported by SFTP server";
3270
3271     case LIBSSH2_FX_INVALID_HANDLE:
3272       return "Invalid handle";
3273
3274     case LIBSSH2_FX_NO_SUCH_PATH:
3275       return "No such file or directory";
3276
3277     case LIBSSH2_FX_FILE_ALREADY_EXISTS:
3278       return "File already exists";
3279
3280     case LIBSSH2_FX_WRITE_PROTECT:
3281       return "File is write protected";
3282
3283     case LIBSSH2_FX_NO_MEDIA:
3284       return "No media";
3285
3286     case LIBSSH2_FX_NO_SPACE_ON_FILESYSTEM:
3287       return "Disk full";
3288
3289     case LIBSSH2_FX_QUOTA_EXCEEDED:
3290       return "User quota exceeded";
3291
3292     case LIBSSH2_FX_UNKNOWN_PRINCIPLE:
3293       return "Unknown principle";
3294
3295     case LIBSSH2_FX_LOCK_CONFlICT:
3296       return "File lock conflict";
3297
3298     case LIBSSH2_FX_DIR_NOT_EMPTY:
3299       return "Directory not empty";
3300
3301     case LIBSSH2_FX_NOT_A_DIRECTORY:
3302       return "Not a directory";
3303
3304     case LIBSSH2_FX_INVALID_FILENAME:
3305       return "Invalid filename";
3306
3307     case LIBSSH2_FX_LINK_LOOP:
3308       return "Link points to itself";
3309   }
3310   return "Unknown error in libssh2";
3311 }
3312
3313 #endif /* USE_LIBSSH2 */