[patch] client/client.c: commands reget and reput

Simo Sorce simo.sorce at xsec.it
Tue Aug 27 05:10:30 GMT 2002


Thanks, I've committed a patch that adds these commands to smbclient.
I made it a bit different tough.
(Also added a patch for xfile.c)

Simo.

On Tue, 2002-08-20 at 11:48, Josef Zlomek wrote:
> Hello!
> 
> I have written the commands reget and reput for smbclient.
> When user gets/puts a large file and the connection brokes
> the user is unhappy (s)he has to transfer the file from the beginning.
> So with this patch (s)he can use command reget/reput that
> will continue in the transfer, i.e. it will seek both in local and remote file
> to position of the end of target file and continue with the transfer from this position.
> Although the local networks are fast, it takes several minutes to tranfer
> a 650 MB large file (e.g. ISO image) so I think these commands are useful.
> 
> Patch for the main branch (HEAD) follows, it needs my patch
> "[patch] basic seeking support for XFILE" to be installed before this patch.
> 
> Josef
> 
> 
> diff -ur samba.cvs/source/client/client.c samba.reget_reput/source/client/client.c
> --- samba.cvs/source/client/client.c	Sat Jul 13 05:51:27 2002
> +++ samba.reget_reput/source/client/client.c	Tue Aug 20 10:13:38 2002
> @@ -60,6 +60,7 @@
>  /* value for unused fid field in trans2 secondary request */
>  #define FID_UNUSED (0xFFFF)
>  
> +BOOL restart_at_file_end = False;
>  time_t newer_than = 0;
>  static int archive_level = 0;
>  
> @@ -651,7 +652,7 @@
>    ****************************************************************************/
>  static int do_get(char *rname,char *lname)
>  {  
> -	int handle=0,fnum;
> +	int handle = -1, fnum;
>  	BOOL newhandle = False;
>  	char *data;
>  	struct timeval tp_start;
> @@ -659,6 +660,7 @@
>  	uint16 attr;
>  	size_t size;
>  	off_t nread = 0;
> +	off_t start = 0;
>  	int rc = 0;
>  
>  	GetTimeOfDay(&tp_start);
> @@ -677,7 +679,18 @@
>  	if(!strcmp(lname,"-")) {
>  		handle = fileno(stdout);
>  	} else {
> -		handle = sys_open(lname,O_WRONLY|O_CREAT|O_TRUNC,0644);
> +		if (restart_at_file_end) {
> +			handle = sys_open(lname,O_WRONLY|O_CREAT,0644);
> +			if (handle >= 0) {
> +				start = sys_lseek(handle, 0, SEEK_END);
> +				if (start == -1) {
> +					d_printf("Error seeking local file\n");
> +					return 1;
> +				}
> +			}
> +		}
> +		if (handle < 0)
> +			handle = sys_open(lname,O_WRONLY|O_CREAT|O_TRUNC,0644);
>  		newhandle = True;
>  	}
>  	if (handle < 0) {
> @@ -704,7 +717,7 @@
>  	}
>  
>  	while (1) {
> -		int n = cli_read(cli, fnum, data, nread, read_size);
> +		int n = cli_read(cli, fnum, data, nread + start, read_size);
>  
>  		if (n <= 0) break;
>   
> @@ -717,7 +730,7 @@
>  		nread += n;
>  	}
>  
> -	if (nread < size) {
> +	if (nread + start < size) {
>  		DEBUG (0, ("Short read when getting file %s. Only got %ld bytes.\n",
>  			    rname, (long)nread));
>  
> @@ -787,6 +800,21 @@
>  
>  
>  /****************************************************************************
> +  get a file restarting at end of local file
> +  ****************************************************************************/
> +static int cmd_reget(void)
> +{
> +	int rc;
> +
> +	restart_at_file_end = True;
> +	rc = cmd_get();
> +	restart_at_file_end = False;
> +
> +	return rc;
> +}
> +
> +
> +/****************************************************************************
>    do a mget operation on one file
>    ****************************************************************************/
>  static void do_mget(file_info *finfo)
> @@ -1048,9 +1076,10 @@
>    ****************************************************************************/
>  static int do_put(char *rname,char *lname)
>  {
> -	int fnum;
> +	int fnum = -1;
>  	XFILE *f;
> -	int nread=0;
> +	size_t nread = 0;
> +	size_t start = 0;
>  	char *buf=NULL;
>  	int maxwrite=io_bufsize;
>  	int rc = 0;
> @@ -1058,7 +1087,21 @@
>  	struct timeval tp_start;
>  	GetTimeOfDay(&tp_start);
>  
> -	fnum = cli_open(cli, rname, O_RDWR|O_CREAT|O_TRUNC, DENY_NONE);
> +	if (restart_at_file_end) {
> +		fnum = cli_open(cli, rname, O_RDWR|O_CREAT, DENY_NONE);
> +		if (fnum >= 0) {
> +			if (!cli_qfileinfo(cli, fnum, NULL, &start,
> +					   NULL, NULL, NULL, NULL, NULL) &&
> +			    !cli_getattrE(cli, fnum, NULL, &start,
> +					  NULL, NULL, NULL)) {
> +				d_printf("getattrib: %s\n",cli_errstr(cli));
> +				return 1;
> +			}
> +		}
> +	}
> +	if (fnum == -1) {
> +		fnum = cli_open(cli, rname, O_RDWR|O_CREAT|O_TRUNC, DENY_NONE);
> +	}
>    
>  	if (fnum == -1) {
>  		d_printf("%s opening remote file %s\n",cli_errstr(cli),rname);
> @@ -1075,6 +1118,12 @@
>  		/* size of file is not known */
>  	} else {
>  		f = x_fopen(lname,O_RDONLY, 0);
> +		if (f != NULL && restart_at_file_end) {
> +			if (x_lseek(f, start, SEEK_SET) == -1) {
> +				d_printf("Error seeking local file\n");
> +				return 1;
> +			}
> +		}
>  	}
>  
>  	if (!f) {
> @@ -1104,7 +1153,7 @@
>  			break;
>  		}
>  
> -		ret = cli_write(cli, fnum, 0, buf, nread, n);
> +		ret = cli_write(cli, fnum, 0, buf, nread + start, n);
>  
>  		if (n != ret) {
>  			d_printf("Error writing file: %s\n", cli_errstr(cli));
> @@ -1195,6 +1244,22 @@
>  	return do_put(rname,lname);
>  }
>  
> +
> +/****************************************************************************
> +  put a file restarting at end of local file
> +  ****************************************************************************/
> +static int cmd_reput(void)
> +{
> +	int rc;
> +
> +	restart_at_file_end = True;
> +	rc = cmd_put();
> +	restart_at_file_end = False;
> +
> +	return rc;
> +}
> +
> +
>  /*************************************
>    File list structure
>  *************************************/
> @@ -2009,7 +2074,9 @@
>    {"quit",cmd_quit,"logoff the server",{COMPL_NONE,COMPL_NONE}},
>    {"rd",cmd_rmdir,"<directory> remove a directory",{COMPL_NONE,COMPL_NONE}},
>    {"recurse",cmd_recurse,"toggle directory recursion for mget and mput",{COMPL_NONE,COMPL_NONE}},  
> +  {"reget",cmd_reget,"<remote name> [local name] get a file restarting at end of local file",{COMPL_REMOTE,COMPL_LOCAL}},
>    {"rename",cmd_rename,"<src> <dest> rename some files",{COMPL_REMOTE,COMPL_REMOTE}},
> +  {"reput",cmd_reput,"<local name> [remote name] put a file restarting at end of remote file",{COMPL_LOCAL,COMPL_REMOTE}},
>    {"rm",cmd_del,"<mask> delete all matching files",{COMPL_REMOTE,COMPL_NONE}},
>    {"rmdir",cmd_rmdir,"<directory> remove a directory",{COMPL_NONE,COMPL_NONE}},
>    {"setmode",cmd_setmode,"filename <setmode string> change modes of file",{COMPL_REMOTE,COMPL_NONE}},
-- 
Simo Sorce - simo.sorce at xsec.it
Xsec s.r.l.
via Durando 10 Ed. G - 20158 - Milano
tel. +39 02 2399 7130 - fax: +39 02 700 442 399
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 232 bytes
Desc: This is a digitally signed message part
Url : http://lists.samba.org/archive/samba-technical/attachments/20020827/0ab64575/attachment.bin


More information about the samba-technical mailing list