Previous patch did not return correct device number for the backing file location on LOOP_GET_STATUS call. Updated patch is attached.

Igor

--- modules/cloop/compressed_loop.c.orig	2005-03-05 01:16:13.000000000 -0500
+++ modules/cloop/compressed_loop.c	2005-03-05 01:20:25.000000000 -0500
@@ -120,6 +120,7 @@
 
  struct file   *backing_file;  /* associated file */
  struct inode  *backing_inode; /* for bmap */
+ char           backing_file_name[LO_NAME_SIZE];
 
  unsigned int underlying_blksize;
  int refcnt;
@@ -448,6 +449,8 @@
   }
 
  clo->backing_file = file;
+ memcpy(clo->backing_file_name, filename, LO_NAME_SIZE);
+ clo->backing_file_name[LO_NAME_SIZE-1] = 0;
 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
  clo->dev = dev;
 #endif
@@ -625,6 +628,7 @@
 error_release:
  if(bbuf) vfree(bbuf);
  clo->backing_file=NULL;
+ memset(clo->backing_file_name, 0, LO_NAME_SIZE);
  return error;
 }
 
@@ -663,6 +667,7 @@
  else { filp_close(initial_file,0); initial_file=NULL; }
  clo->backing_file  = NULL;
  clo->backing_inode = NULL;
+ memset(clo->backing_file_name, 0, LO_NAME_SIZE);
 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
  cloop_sizes[cloop_num] = 0;
  cloop_blksizes[cloop_num] = 0;
@@ -678,6 +683,7 @@
 {
 	struct cloop_device *clo;
 	int cloop_num, err=0;
+	struct loop_info info;
 
 	if (!inode) return -EINVAL;
 	if (MAJOR(inode->i_rdev) != MAJOR_NR) {
@@ -700,8 +706,36 @@
 	 err = clo_clr_fd(cloop_num, inode->i_bdev);
 	 break;
         case LOOP_SET_STATUS:
+	  if(copy_from_user(&info,(struct loop_info __user *)arg,sizeof(info)))
+	    err = -EFAULT;
+	  else if (clo->backing_file) {
+	    memcpy(clo->backing_file_name, info.lo_name, LO_NAME_SIZE);
+	    clo->backing_file_name[LO_NAME_SIZE-1] = 0;
+	  } else
+	    err = -ENXIO;
+	  break;
         case LOOP_GET_STATUS:
-	 err=0; break;
+	  memset(&info, 0, sizeof(info));
+	  if (clo->backing_file) {
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
+	    info.lo_device = kdev_t_to_nr(clo->backing_inode->i_dev);
+	    info.lo_rdevice = kdev_t_to_nr(clo->dev);
+#else
+	    struct kstat stat;
+	    err = vfs_getattr(clo->backing_file->f_vfsmnt,
+			      clo->backing_file->f_dentry, &stat);
+	    if(err) return err;
+	    info.lo_device = new_encode_dev(stat.dev);
+	    info.lo_rdevice = new_encode_dev(clo->bdev ? stat.rdev : stat.dev);
+#endif
+	    info.lo_number = cloop_num;
+	    info.lo_inode = clo->backing_inode->i_ino;
+	    memcpy(info.lo_name, clo->backing_file_name, LO_NAME_SIZE);
+	    if(copy_to_user((struct loop_info __user *)arg,&info,sizeof(info)))
+	      err = -EFAULT;
+	  } else
+	    err = -ENXIO;
+	  break;
 	default:
 	 err = -EINVAL;
 	}
@@ -832,13 +866,19 @@
 
  if(file) /* global file name for first cloop-Device is a module option string. */
   {
-   initial_file=filp_open(file,0x00,0x00);
-   if(initial_file==NULL||IS_ERR(initial_file))
+    initial_file=filp_open(file, O_RDONLY | O_LARGEFILE, 0);
+    if(initial_file==NULL||IS_ERR(initial_file))
     {
      printk(KERN_ERR
-            "%s: Unable to get file %s for cloop device\n",
-            cloop_name, file);
-     return -EINVAL;
+            "%s: Unable to get file %s for cloop device (%ld)\n",
+            cloop_name, file, PTR_ERR(initial_file));
+     if (initial_file) {
+       error = PTR_ERR(initial_file);
+       initial_file = NULL;
+     } else
+       error = -EINVAL;
+     i=max_cloop;
+     goto out_mem;
     }
    error=clo_set_file(0,initial_file,file);
    if(error) { i=max_cloop; goto out_mem; }
@@ -857,6 +897,7 @@
 /* error_filp_close: */
  if(initial_file) filp_close(initial_file,0); initial_file=NULL;
  cloop_dev[0].backing_file=NULL;
+ memset(cloop_dev[0].backing_file_name, 0, LO_NAME_SIZE);
  return error;
 }
 

Reply via email to