Glen Sanft wrote: > Hey folks, > > Just a heads-up. > > I fetched mc-4.6.0-2005-05-10-17.diff.bz2 in the hopes of getting a > current mc which would to an ftpfs "reget" for me. I haven't been able to > do that since I can't remember when. It's still appending (hence > destroying) the local partial file, so no joy there.
I use the attached quick-and-dirty fix, which makes reget work at least for me - I am using it for two years or so without problems. Feel free to apply it, but unfortunately there seems to be no chance to apply such hack to mainline mc. -- Jindrich Makovicka
diff -urN vanilla/mc/src/file.c mc/src/file.c --- vanilla/mc/src/file.c 2004-12-02 12:32:32.000000000 +0100 +++ mc/src/file.c 2004-12-30 15:09:52.000000000 +0100 @@ -578,21 +578,20 @@ gettimeofday (&tv_transfer_start, (struct timezone *) NULL); - while ((src_desc = mc_open (src_path, O_RDONLY | O_LINEAR)) < 0) { + while ((src_desc = mc_open (src_path, O_RDONLY | O_LINEAR, ctx->do_reget)) < 0) { return_status = file_error ( - _(" Cannot open source file \"%s\" \n %s "), src_path); - if (return_status == FILE_RETRY) - continue; - ctx->do_append = 0; - return return_status; - } + _(" Cannot open source file \"%s\" \n %s "), src_path); - if (ctx->do_reget) { - if (mc_lseek (src_desc, ctx->do_reget, SEEK_SET) != ctx->do_reget) { + if (ctx->do_reget) { message (1, _("Warning"), - _(" Reget failed, about to overwrite file ")); + _(" Reget failed, about to overwrite file ")); ctx->do_reget = ctx->do_append = 0; } + + if (return_status == FILE_RETRY) + continue; + ctx->do_append = 0; + return return_status; } while (mc_fstat (src_desc, &sb)) { @@ -738,10 +737,10 @@ file_progress_set_stalled_label (ctx, stalled_msg); return_status = file_progress_show_bytes (ctx, *progress_bytes + - n_read_total, ctx->progress_bytes); + n_read_total + ctx->do_reget, ctx->progress_bytes); if (return_status == FILE_CONT) { return_status = - file_progress_show (ctx, n_read_total, file_size); + file_progress_show (ctx, n_read_total + ctx->do_reget, file_size); } mc_refresh (); if (return_status != FILE_CONT) diff -urN vanilla/mc/vfs/direntry.c mc/vfs/direntry.c --- vanilla/mc/vfs/direntry.c 2004-11-30 13:38:48.000000000 +0100 +++ mc/vfs/direntry.c 2004-12-30 15:08:01.000000000 +0100 @@ -709,7 +709,7 @@ } static void * -vfs_s_open (struct vfs_class *me, const char *file, int flags, int mode) +vfs_s_open (struct vfs_class *me, const char *file, int flags, int mode, off_t offset) { int was_changed = 0; struct vfs_s_fh *fh; @@ -768,7 +768,7 @@ if (IS_LINEAR (flags)) { if (MEDATA->linear_start) { print_vfs_message (_("Starting linear transfer...")); - if (!MEDATA->linear_start (me, fh, 0)) { + if (!MEDATA->linear_start (me, fh, offset)) { g_free (fh); return NULL; } @@ -785,7 +785,15 @@ g_free (fh); ERRNOR (errno, NULL); } + if (IS_LINEAR(flags) && (offset > 0)) { + if (lseek(fh->handle, offset, SEEK_SET) != offset) { + close(fh->handle); + g_free(fh); + return NULL; + } } + } + /* i.e. we had no open files and now we have one */ vfs_rmstamp (me, (vfsid) super); @@ -1014,7 +1022,7 @@ struct vfs_s_fh *fh; char *local; - fh = vfs_s_open (me, path, O_RDONLY, 0); + fh = vfs_s_open (me, path, O_RDONLY, 0, 0); if (!fh || !fh->ino || !fh->ino->localname) return NULL; diff -urN vanilla/mc/vfs/extfs.c mc/vfs/extfs.c --- vanilla/mc/vfs/extfs.c 2004-12-29 12:31:31.000000000 +0100 +++ mc/vfs/extfs.c 2004-12-30 15:08:01.000000000 +0100 @@ -649,7 +649,7 @@ } static void * -extfs_open (struct vfs_class *me, const char *file, int flags, int mode) +extfs_open (struct vfs_class *me, const char *file, int flags, int mode, off_t offset) { struct pseudofile *extfs_info; struct archive *archive; @@ -700,6 +700,13 @@ if (local_handle == -1) ERRNOR (EIO, NULL); + if (IS_LINEAR(flags) && (offset > 0)) { + if (lseek(local_handle, offset, SEEK_SET) != offset) { + close(local_handle); + return 0; + } + } + extfs_info = g_new (struct pseudofile, 1); extfs_info->archive = archive; extfs_info->entry = entry; @@ -1232,7 +1239,7 @@ extfs_getlocalcopy (struct vfs_class *me, const char *path) { struct pseudofile *fp = - (struct pseudofile *) extfs_open (me, path, O_RDONLY, 0); + (struct pseudofile *) extfs_open (me, path, O_RDONLY, 0, 0); char *p; if (fp == NULL) @@ -1252,7 +1259,7 @@ const char *local, int has_changed) { struct pseudofile *fp = - (struct pseudofile *) extfs_open (me, path, O_RDONLY, 0); + (struct pseudofile *) extfs_open (me, path, O_RDONLY, 0, 0); if (fp == NULL) return 0; diff -urN vanilla/mc/vfs/ftpfs.c mc/vfs/ftpfs.c --- vanilla/mc/vfs/ftpfs.c 2004-11-05 13:05:48.000000000 +0100 +++ mc/vfs/ftpfs.c 2004-12-30 15:08:01.000000000 +0100 @@ -935,8 +935,14 @@ int s, j, data; socklen_t fromlen = sizeof(from); - if ((s = ftpfs_initconn (me, super)) == -1) + if ((s = ftpfs_initconn (me, super)) == -1) { + /* try issuing an empty command to force reconnect */ + j = ftpfs_command (me, super, WAIT_REPLY, "NOOP"); + if (j != COMPLETE) return -1; + if ((s = ftpfs_initconn (me, super)) == -1) { return -1; + } + } if (ftpfs_changetype (me, super, isbinary) == -1) return -1; if (reget > 0){ @@ -1261,6 +1267,12 @@ vfs_s_free_entry (me, ent); continue; } + if (S_ISDIR (ent->ino->st.st_mode)) { + /* fixup broken UNIX access rights */ + if (ent->ino->st.st_mode & S_IRUSR) ent->ino->st.st_mode |= S_IXUSR; + if (ent->ino->st.st_mode & S_IRGRP) ent->ino->st.st_mode |= S_IXGRP; + if (ent->ino->st.st_mode & S_IROTH) ent->ino->st.st_mode |= S_IXOTH; + } ent->ino->st.st_nlink = i; /* Ouch, we need to preserve our counts :-( */ num_entries++; vfs_s_insert_entry (me, dir, ent); diff -urN vanilla/mc/vfs/local.c mc/vfs/local.c --- vanilla/mc/vfs/local.c 2004-09-27 12:51:14.000000000 +0200 +++ mc/vfs/local.c 2004-12-30 15:08:01.000000000 +0100 @@ -19,7 +19,7 @@ static struct vfs_class vfs_local_ops; static void * -local_open (struct vfs_class *me, const char *file, int flags, int mode) +local_open (struct vfs_class *me, const char *file, int flags, int mode, off_t offset) { int *local_info; int fd; @@ -28,6 +28,13 @@ if (fd == -1) return 0; + if (IS_LINEAR(flags) && (offset > 0)) { + if (lseek(fd, offset, SEEK_SET) != offset) { + close(fd); + return 0; + } + } + local_info = g_new (int, 1); *local_info = fd; diff -urN vanilla/mc/vfs/mcfs.c mc/vfs/mcfs.c --- vanilla/mc/vfs/mcfs.c 2004-11-05 13:05:48.000000000 +0100 +++ mc/vfs/mcfs.c 2004-12-30 15:08:01.000000000 +0100 @@ -515,7 +515,7 @@ /* The callbacks */ static void * -mcfs_open (struct vfs_class *me, const char *file, int flags, int mode) +mcfs_open (struct vfs_class *me, const char *file, int flags, int mode, off_t offset) { char *remote_file; mcfs_connection *mc; @@ -540,6 +540,13 @@ remote_handle->handle = result; remote_handle->conn = mc; + if (IS_LINEAR(flags) && (offset > 0)) { + if (mcfs_lseek(remote_handle, offset, SEEK_SET) != offset) { + mcfs_close(remote_handle); + return 0; + } + } + return remote_handle; } diff -urN vanilla/mc/vfs/sfs.c mc/vfs/sfs.c --- vanilla/mc/vfs/sfs.c 2004-09-22 14:04:08.000000000 +0200 +++ mc/vfs/sfs.c 2004-12-30 15:08:01.000000000 +0100 @@ -185,7 +185,7 @@ } static void * -sfs_open (struct vfs_class *me, const char *path, int flags, int mode) +sfs_open (struct vfs_class *me, const char *path, int flags, int mode, off_t offset) { int *sfs_info; int fd; @@ -195,6 +195,13 @@ if (fd == -1) return 0; + if (IS_LINEAR(flags) && (offset > 0)) { + if (lseek(fd, offset, SEEK_SET) != offset) { + close(fd); + return 0; + } + } + sfs_info = g_new (int, 1); *sfs_info = fd; diff -urN vanilla/mc/vfs/smbfs.c mc/vfs/smbfs.c --- vanilla/mc/vfs/smbfs.c 2004-11-05 13:05:48.000000000 +0100 +++ mc/vfs/smbfs.c 2004-12-30 15:08:01.000000000 +0100 @@ -1796,7 +1796,7 @@ } static void * -smbfs_open (struct vfs_class *me, const char *file, int flags, int mode) +smbfs_open (struct vfs_class *me, const char *file, int flags, int mode, off_t offset) { char *remote_file; void *ret; @@ -1817,8 +1817,16 @@ ret = smbfs_open_readwrite (remote_handle, remote_file, flags, mode); g_free (remote_file); - if (!ret) + if (!ret) { g_free (remote_handle); + } else { + if (IS_LINEAR(flags) && (offset > 0)) { + if (smbfs_lseek(remote_handle, offset, SEEK_SET) != offset) { + smbfs_close(remote_handle); + return 0; + } + } + } return ret; } diff -urN vanilla/mc/vfs/undelfs.c mc/vfs/undelfs.c --- vanilla/mc/vfs/undelfs.c 2004-11-05 13:05:48.000000000 +0100 +++ mc/vfs/undelfs.c 2004-12-30 15:08:01.000000000 +0100 @@ -397,12 +397,16 @@ /* We do not support lseek */ static void * -undelfs_open (struct vfs_class *me, const char *fname, int flags, int mode) +undelfs_open (struct vfs_class *me, const char *fname, int flags, int mode, off_t offset) { char *file, *f; ext2_ino_t inode, i; undelfs_file *p = NULL; + if (offset > 0) { + return 0; + } + /* Only allow reads on this file system */ undelfs_get_path (fname, &file, &f); if (!file) diff -urN vanilla/mc/vfs/vfs.c mc/vfs/vfs.c --- vanilla/mc/vfs/vfs.c 2004-11-18 13:57:36.000000000 +0100 +++ mc/vfs/vfs.c 2004-12-30 15:08:01.000000000 +0100 @@ -314,7 +314,8 @@ int mc_open (const char *filename, int flags, ...) { - int mode; + int mode = 0; + off_t offset = 0; void *info; va_list ap; @@ -326,8 +327,14 @@ va_start (ap, flags); mode = va_arg (ap, int); va_end (ap); - } else - mode = 0; + } else { + if (flags & O_LINEAR) { + va_start (ap, flags); + offset = va_arg (ap, off_t); + va_end (ap); + } + mode = 0; + } if (!vfs->open) { g_free (file); @@ -335,7 +342,7 @@ return -1; } - info = (*vfs->open) (vfs, file, flags, mode); /* open must be supported */ + info = (*vfs->open) (vfs, file, flags, mode, offset); /* open must be supported */ g_free (file); if (!info){ errno = ferrno (vfs); diff -urN vanilla/mc/vfs/vfs-impl.h mc/vfs/vfs-impl.h --- vanilla/mc/vfs/vfs-impl.h 2004-09-22 14:04:08.000000000 +0200 +++ mc/vfs/vfs-impl.h 2004-12-30 15:08:01.000000000 +0100 @@ -27,7 +27,7 @@ int (*which) (struct vfs_class *me, const char *path); void *(*open) (struct vfs_class *me, const char *fname, int flags, - int mode); + int mode, off_t offset); int (*close) (void *vfs_info); int (*read) (void *vfs_info, char *buffer, int count); int (*write) (void *vfs_info, const char *buf, int count);
_______________________________________________ Mc-devel mailing list http://mail.gnome.org/mailman/listinfo/mc-devel