@@ -805,9 +805,96 @@ int ssh_do_receive(const char *infile, FILE *fp, getmode_t mode,
805
805
return (r == 0 && !ftp -> ti .ioerror && !ftp -> ti .interrupted ) ? 0 : -1 ;
806
806
}
807
807
808
+ static int do_scp_write (ssh_scp scp , const char * path , FILE * fp ,
809
+ ftp_transfer_func hookf )
810
+ {
811
+ time_t then = time (NULL ) - 1 ;
812
+ ftp_set_close_handler ();
813
+
814
+ if (hookf )
815
+ hookf (& ftp -> ti );
816
+ ftp -> ti .begin = false;
817
+
818
+ struct stat sb ;
819
+ errno = 0 ;
820
+ if (fstat (fileno (fp ), & sb ) == -1 )
821
+ {
822
+ ftp_err (_ ("Couldn't fstat local file: %s\n" ), strerror (errno ));
823
+ ssh_scp_free (scp );
824
+ return -1 ;
825
+ }
826
+
827
+ int rc = ssh_scp_push_file (scp , path , sb .st_size , sb .st_mode & (S_IRWXU | S_IRWXG | S_IRWXO ));
828
+ if (rc != SSH_OK )
829
+ {
830
+ ftp_err (_ ("Failed to start scp upload: %s\n" ),
831
+ ssh_get_error (ftp -> session ));
832
+ ssh_scp_close (scp );
833
+ ssh_scp_free (scp );
834
+ return -1 ;
835
+ }
836
+
837
+ /* read file */
838
+ char buffer [SSH_BUFSIZ ];
839
+ ssize_t nbytes = 0 ;
840
+ errno = 0 ;
841
+ while ((nbytes = fread (buffer , sizeof (char ), sizeof (buffer ), fp )) > 0 )
842
+ {
843
+ if (ftp_sigints () > 0 )
844
+ {
845
+ ftp_trace ("break due to sigint\n" );
846
+ break ;
847
+ }
848
+
849
+ rc = ssh_scp_write (scp , buffer , nbytes );
850
+ if (rc != SSH_OK )
851
+ {
852
+ ftp_err (_ ("Error while writing to file: %s\n" ), ssh_get_error (ftp -> session ));
853
+ ssh_scp_close (scp );
854
+ ssh_scp_free (scp );
855
+ return -1 ;
856
+ }
857
+
858
+ ftp -> ti .size += nbytes ;
859
+ if (hookf )
860
+ {
861
+ time_t now = time (NULL );
862
+ if (now > then )
863
+ {
864
+ hookf (& ftp -> ti );
865
+ then = now ;
866
+ }
867
+ }
868
+ errno = 0 ;
869
+ }
870
+
871
+ if (ferror (fp ))
872
+ {
873
+ ftp_err (_ ("Failed to read from file: %s\n" ), strerror (errno ));
874
+ rc = -1 ;
875
+ }
876
+
877
+ ssh_scp_close (scp );
878
+ ssh_scp_free (scp );
879
+ return rc ;
880
+ }
881
+
808
882
static int do_write (const char * path , FILE * fp , ftp_transfer_func hookf ,
809
883
uint64_t offset )
810
884
{
885
+ /* try to set up a scp connection */
886
+ if (!offset )
887
+ {
888
+ ssh_scp scp = ssh_scp_new (ftp -> session , SSH_SCP_WRITE , path );
889
+ if (scp != NULL )
890
+ {
891
+ int rc = ssh_scp_init (scp );
892
+ if (rc == SSH_OK )
893
+ return do_scp_write (scp , path , fp , hookf );
894
+ ssh_scp_free (scp );
895
+ }
896
+ }
897
+
811
898
time_t then = time (NULL ) - 1 ;
812
899
ftp_set_close_handler ();
813
900
0 commit comments