patch-2.4.0-test3 linux/fs/umsdos/emd.c
Next file: linux/fs/umsdos/inode.c
Previous file: linux/fs/umsdos/dir.c
Back to the patch index
Back to the overall index
- Lines: 764
- Date:
Wed Jul 5 21:38:48 2000
- Orig file:
v2.4.0-test2/linux/fs/umsdos/emd.c
- Orig date:
Mon Aug 9 11:43:49 1999
diff -u --recursive --new-file v2.4.0-test2/linux/fs/umsdos/emd.c linux/fs/umsdos/emd.c
@@ -15,169 +15,25 @@
#include <linux/msdos_fs.h>
#include <linux/umsdos_fs.h>
#include <linux/dcache.h>
-
-#include <asm/uaccess.h>
+#include <linux/pagemap.h>
#include <asm/delay.h>
-
-/*
- * Read a file into kernel space memory
- * returns how many bytes read (from fat_file_read)
- */
-
-ssize_t umsdos_file_read_kmem ( struct file *filp,
- char *buf,
- size_t count)
-{
- ssize_t ret;
- mm_segment_t old_fs = get_fs ();
-
- set_fs (KERNEL_DS);
- ret = fat_file_read (filp, buf, count, &filp->f_pos);
- set_fs (old_fs);
- return ret;
-}
-
-
-/*
- * Write to file from kernel space.
- * Does the real job, assumes all structures are initialized!
- */
-
-
-ssize_t umsdos_file_write_kmem_real (struct file * filp,
- const char *buf,
- size_t count)
-{
- mm_segment_t old_fs = get_fs ();
- ssize_t ret;
-
- set_fs (KERNEL_DS);
- ret = fat_file_write (filp, buf, count, &filp->f_pos);
- set_fs (old_fs);
- if (ret < 0) {
- printk(KERN_WARNING "umsdos_file_write: ret=%d\n", ret);
- goto out;
- }
-#ifdef UMSDOS_PARANOIA
-if (ret != count)
-printk(KERN_WARNING "umsdos_file_write: count=%u, ret=%u\n", count, ret);
-#endif
-out:
- return ret;
-}
-
-
-/*
- * Write to a file from kernel space.
- */
-
-ssize_t umsdos_file_write_kmem (struct file *filp,
- const char *buf,
- size_t count)
+static void copy_entry(struct umsdos_dirent *p, struct umsdos_dirent *q)
{
- ssize_t ret;
-
- ret = umsdos_file_write_kmem_real (filp, buf, count);
- return ret;
+ p->name_len = q->name_len;
+ p->flags = q->flags;
+ p->nlink = le16_to_cpu (q->nlink);
+ /* FIXME -- 32bit UID/GID issues */
+ p->uid = le16_to_cpu (q->uid);
+ p->gid = le16_to_cpu (q->gid);
+ p->atime = le32_to_cpu (q->atime);
+ p->mtime = le32_to_cpu (q->mtime);
+ p->ctime = le32_to_cpu (q->ctime);
+ p->rdev = le16_to_cpu (q->rdev);
+ p->mode = le16_to_cpu (q->mode);
}
-
-
-/*
- * Write a block of bytes into one EMD file.
- * The block of data is NOT in user space.
- *
- * Return 0 if OK, a negative error code if not.
- *
- * Note: buffer is in kernel memory, not in user space.
- */
-
-ssize_t umsdos_emd_dir_write ( struct file *filp,
- char *buf,
- size_t count)
-{
- int written;
-
-#ifdef __BIG_ENDIAN
- struct umsdos_dirent *d = (struct umsdos_dirent *) buf;
-
- d->nlink = cpu_to_le16 (d->nlink);
- d->uid = cpu_to_le16 (d->uid);
- d->gid = cpu_to_le16 (d->gid);
- d->atime = cpu_to_le32 (d->atime);
- d->mtime = cpu_to_le32 (d->mtime);
- d->ctime = cpu_to_le32 (d->ctime);
- d->rdev = cpu_to_le16 (d->rdev);
- d->mode = cpu_to_le16 (d->mode);
-#endif
-
- filp->f_flags = 0;
-Printk (("umsdos_emd_dir_write /mn/: calling write_kmem with %p, %p, %d, %Ld\n",
-filp, buf, count, filp->f_pos));
- written = umsdos_file_write_kmem (filp, buf, count);
-
-#ifdef __BIG_ENDIAN
- d->nlink = le16_to_cpu (d->nlink);
- d->uid = le16_to_cpu (d->uid);
- d->gid = le16_to_cpu (d->gid);
- d->atime = le32_to_cpu (d->atime);
- d->mtime = le32_to_cpu (d->mtime);
- d->ctime = le32_to_cpu (d->ctime);
- d->rdev = le16_to_cpu (d->rdev);
- d->mode = le16_to_cpu (d->mode);
-#endif
-
-#ifdef UMSDOS_PARANOIA
-if (written != count)
-printk(KERN_ERR "umsdos_emd_dir_write: ERROR: written (%d) != count (%d)\n",
-written, count);
-#endif
-
- return (written != count) ? -EIO : 0;
-}
-
-
-
-/*
- * Read a block of bytes from one EMD file.
- * The block of data is NOT in user space.
- * Return 0 if OK, -EIO if any error.
- */
-/* buffer in kernel memory, not in user space */
-
-ssize_t umsdos_emd_dir_read (struct file *filp, char *buf, size_t count)
-{
- ssize_t sizeread, ret = 0;
-
-#ifdef __BIG_ENDIAN
- struct umsdos_dirent *d = (struct umsdos_dirent *) buf;
-
-#endif
-
- filp->f_flags = 0;
- sizeread = umsdos_file_read_kmem (filp, buf, count);
- if (sizeread != count) {
- printk (KERN_WARNING
- "UMSDOS: EMD problem, pos=%Ld, count=%d, read=%d\n",
- filp->f_pos, count, sizeread);
- ret = -EIO;
- }
-#ifdef __BIG_ENDIAN
- d->nlink = le16_to_cpu (d->nlink);
- d->uid = le16_to_cpu (d->uid);
- d->gid = le16_to_cpu (d->gid);
- d->atime = le32_to_cpu (d->atime);
- d->mtime = le32_to_cpu (d->mtime);
- d->ctime = le32_to_cpu (d->ctime);
- d->rdev = le16_to_cpu (d->rdev);
- d->mode = le16_to_cpu (d->mode);
-#endif
- return ret;
-}
-
-
/*
* Lookup the EMD dentry for a directory.
*
@@ -256,35 +112,60 @@
* does not change {d,i}_count
*/
-int umsdos_emd_dir_readentry (struct file *filp, struct umsdos_dirent *entry)
+int umsdos_emd_dir_readentry (struct dentry *demd, loff_t *pos, struct umsdos_dirent *entry)
{
- int ret;
-
- Printk ((KERN_DEBUG "umsdos_emd_dir_readentry /mn/: entering.\n"));
-
- ret = umsdos_emd_dir_read (filp, (char *) entry, UMSDOS_REC_SIZE);
- if (ret == 0) { /* if no error */
- /* Variable size record. Maybe, we have to read some more */
- int recsize = umsdos_evalrecsize (entry->name_len);
-
- if (recsize > UMSDOS_REC_SIZE) {
-Printk ((KERN_DEBUG "umsdos_emd_dir_readentry /mn/: %d > %d!\n",
-recsize, UMSDOS_REC_SIZE));
- ret = umsdos_emd_dir_read (filp,
- ((char *) entry) + UMSDOS_REC_SIZE,
- recsize - UMSDOS_REC_SIZE);
+ struct address_space *mapping = demd->d_inode->i_mapping;
+ struct page *page;
+ struct umsdos_dirent *p;
+ int offs = *pos & ~PAGE_CACHE_MASK;
+ int recsize;
+
+ page = read_cache_page(mapping, *pos>>PAGE_CACHE_SHIFT,
+ (filler_t*)mapping->a_ops->readpage, NULL);
+ if (IS_ERR(page))
+ goto sync_fail;
+ wait_on_page(page);
+ if (!Page_Uptodate(page))
+ goto async_fail;
+ p = (struct umsdos_dirent*)((char*)kmap(page)+offs);
+ recsize = umsdos_evalrecsize(p->name_len);
+ if (offs + recsize > PAGE_CACHE_SIZE) {
+ struct page *page2;
+ int part = ((char*)page_address(page)+PAGE_CACHE_SIZE)-p->spare;
+ page2 = read_cache_page(mapping, 1+(*pos>>PAGE_CACHE_SHIFT),
+ (filler_t*)mapping->a_ops->readpage, NULL);
+ if (IS_ERR(page2)) {
+ kunmap(page);
+ page_cache_release(page);
+ page = page2;
+ goto sync_fail;
}
- }
- Printk (("umsdos_emd_dir_readentry /mn/: ret=%d.\n", ret));
- if (entry && ret == 0) {
-Printk (("umsdos_emd_dir_readentry /mn/: returning len=%d,name=%.*s\n",
-(int) entry->name_len, (int) entry->name_len, entry->name));
- }
- return ret;
+ wait_on_page(page2);
+ if (!Page_Uptodate(page2)) {
+ kunmap(page);
+ page_cache_release(page2);
+ goto async_fail;
+ }
+ memcpy(entry->spare,p->spare,part);
+ memcpy(entry->spare+part,(char*)kmap(page2),
+ recsize+offs-PAGE_CACHE_SIZE);
+ kunmap(page2);
+ page_cache_release(page2);
+ } else
+ memcpy(entry->spare,p->spare,((char*)p+recsize)-p->spare);
+ copy_entry(entry, p);
+ kunmap(page);
+ page_cache_release(page);
+ *pos += recsize;
+ return 0;
+async_fail:
+ page_cache_release(page);
+ page = ERR_PTR(-EIO);
+sync_fail:
+ return PTR_ERR(page);
}
-
/*
* Write an entry in the EMD file.
* Return 0 if OK, -EIO if some error.
@@ -298,8 +179,10 @@
struct umsdos_dirent *entry = &info->entry;
struct dentry *emd_dentry;
int ret;
- struct umsdos_dirent entry0;
- struct file filp;
+ struct umsdos_dirent entry0,*p;
+ struct address_space *mapping;
+ struct page *page, *page2 = NULL;
+ int offs;
emd_dentry = umsdos_get_emd_dentry(parent);
ret = PTR_ERR(emd_dentry);
@@ -335,76 +218,97 @@
memset (entry->spare, 0, sizeof (entry->spare));
}
- fill_new_filp (&filp, emd_dentry);
- filp.f_pos = info->f_pos;
- filp.f_reada = 0;
- filp.f_flags = O_RDWR;
-
/* write the entry and update the parent timestamps */
- ret = umsdos_emd_dir_write (&filp, (char *) entry, info->recsize);
- if (!ret) {
- dir->i_ctime = dir->i_mtime = CURRENT_TIME;
- mark_inode_dirty(dir);
- } else
- printk ("UMSDOS: problem with EMD file: can't write\n");
+ mapping = emd_dentry->d_inode->i_mapping;
+ offs = info->f_pos & ~PAGE_CACHE_MASK;
+ ret = -ENOMEM;
+ page = grab_cache_page(mapping, info->f_pos>>PAGE_CACHE_SHIFT);
+ if (!page)
+ goto out_dput;
+ p = (struct umsdos_dirent*)((char*)page_address(page)+offs);
+ if (offs + info->recsize > PAGE_CACHE_SIZE) {
+ ret = mapping->a_ops->prepare_write(NULL,page,offs,
+ PAGE_CACHE_SIZE);
+ if (ret)
+ goto out_unlock;
+ page2 = grab_cache_page(mapping,
+ (info->f_pos>>PAGE_CACHE_SHIFT)+1);
+ if (!page2)
+ goto out_unlock2;
+ ret = mapping->a_ops->prepare_write(NULL,page2,0,
+ offs+info->recsize-PAGE_CACHE_SIZE);
+ if (ret)
+ goto out_unlock3;
+ p->name_len = entry->name_len;
+ p->flags = entry->flags;
+ p->nlink = cpu_to_le16(entry->nlink);
+ p->uid = cpu_to_le16(entry->uid);
+ p->gid = cpu_to_le16(entry->gid);
+ p->atime = cpu_to_le32(entry->atime);
+ p->mtime = cpu_to_le32(entry->mtime);
+ p->ctime = cpu_to_le32(entry->ctime);
+ p->rdev = cpu_to_le16(entry->rdev);
+ p->mode = cpu_to_le16(entry->mode);
+ memcpy(p->name,entry->name,
+ ((char*)page_address(page)+PAGE_CACHE_SIZE)-p->spare);
+ memcpy((char*)page_address(page2),
+ entry->spare+PAGE_CACHE_SIZE-offs,
+ offs+info->recsize-PAGE_CACHE_SIZE);
+ ret = mapping->a_ops->commit_write(NULL,page2,0,
+ offs+info->recsize-PAGE_CACHE_SIZE);
+ if (ret)
+ goto out_unlock3;
+ ret = mapping->a_ops->commit_write(NULL,page,offs,
+ PAGE_CACHE_SIZE);
+ UnlockPage(page2);
+ page_cache_release(page2);
+ if (ret)
+ goto out_unlock;
+ } else {
+ ret = mapping->a_ops->prepare_write(NULL,page,offs,
+ info->recsize);
+ if (ret)
+ goto out_unlock;
+ p->name_len = entry->name_len;
+ p->flags = entry->flags;
+ p->nlink = cpu_to_le16(entry->nlink);
+ p->uid = cpu_to_le16(entry->uid);
+ p->gid = cpu_to_le16(entry->gid);
+ p->atime = cpu_to_le32(entry->atime);
+ p->mtime = cpu_to_le32(entry->mtime);
+ p->ctime = cpu_to_le32(entry->ctime);
+ p->rdev = cpu_to_le16(entry->rdev);
+ p->mode = cpu_to_le16(entry->mode);
+ memcpy(p->spare,entry->spare,((char*)p+info->recsize)-p->spare);
+ ret = mapping->a_ops->commit_write(NULL,page,offs,
+ info->recsize);
+ if (ret)
+ goto out_unlock;
+ }
+ UnlockPage(page);
+ page_cache_release(page);
+
+ dir->i_ctime = dir->i_mtime = CURRENT_TIME;
+ mark_inode_dirty(dir);
out_dput:
dput(emd_dentry);
out:
Printk (("umsdos_writeentry /mn/: returning %d...\n", ret));
return ret;
+out_unlock3:
+ UnlockPage(page2);
+ page_cache_release(page2);
+out_unlock2:
+ ClearPageUptodate(page);
+ kunmap(page);
+out_unlock:
+ UnlockPage(page);
+ page_cache_release(page);
+ printk ("UMSDOS: problem with EMD file: can't write\n");
+ goto out_dput;
}
-
-
-#define CHUNK_SIZE (8*UMSDOS_REC_SIZE)
-struct find_buffer {
- char buffer[CHUNK_SIZE];
- int pos; /* read offset in buffer */
- int size; /* Current size of buffer */
- struct file filp;
-};
-
-
-
-/*
- * Fill the read buffer and take care of the bytes remaining inside.
- * Unread bytes are simply moved to the beginning.
- *
- * Return -ENOENT if EOF, 0 if OK, a negative error code if any problem.
- *
- * Note: the caller must hold a lock on the parent directory.
- */
-
-static int umsdos_fillbuf (struct find_buffer *buf)
-{
- struct inode *inode = buf->filp.f_dentry->d_inode;
- int mustmove = buf->size - buf->pos;
- int mustread, remain;
- int ret = -ENOENT;
-
- if (mustmove > 0) {
- memcpy (buf->buffer, buf->buffer + buf->pos, mustmove);
- }
- buf->pos = 0;
- mustread = CHUNK_SIZE - mustmove;
- remain = inode->i_size - buf->filp.f_pos;
- if (remain < mustread)
- mustread = remain;
- if (mustread > 0) {
- ret = umsdos_emd_dir_read (&buf->filp, buf->buffer + mustmove,
- mustread);
- if (ret == 0)
- buf->size = mustmove + mustread;
- } else if (mustmove) {
- buf->size = mustmove;
- ret = 0;
- }
- return ret;
-}
-
-
-
/*
* General search, locate a name in the EMD file or an empty slot to
* store it. if info->entry.name_len == 0, search the first empty
@@ -432,115 +336,144 @@
* record, multiple contiguous records are allocated.
*/
-static int umsdos_find (struct dentry *parent, struct umsdos_info *info)
+static int umsdos_find (struct dentry *demd, struct umsdos_info *info)
{
struct umsdos_dirent *entry = &info->entry;
int recsize = info->recsize;
- struct dentry *demd;
struct inode *emd_dir;
int ret = -ENOENT;
- struct find_buffer buf;
struct {
off_t posok; /* Position available to store the entry */
- int found; /* A valid empty position has been found. */
off_t one; /* One empty position -> maybe <- large enough */
- int onesize; /* size of empty region starting at one */
} empty;
+ int found = 0;
+ int empty_size = 0;
+ struct address_space *mapping;
+ filler_t *readpage;
+ struct page *page = NULL;
+ int index = -1;
+ int offs = PAGE_CACHE_SIZE,max_offs = PAGE_CACHE_SIZE;
+ char *p = NULL;
+ loff_t pos = 0;
-Printk (("umsdos_find: locating %s in %s/%s\n",
-entry->name, parent->d_parent->d_name.name, parent->d_name.name));
-
- /*
- * Lookup the EMD file in the parent directory.
- */
- demd = umsdos_get_emd_dentry(parent);
- ret = PTR_ERR(demd);
- if (IS_ERR(demd))
- goto out;
/* make sure there's an EMD file ... */
ret = -ENOENT;
emd_dir = demd->d_inode;
if (!emd_dir)
goto out_dput;
+ mapping = emd_dir->i_mapping;
+ readpage = (filler_t*)mapping->a_ops->readpage;
-Printk(("umsdos_find: found EMD file %s/%s, ino=%p\n",
-demd->d_parent->d_name.name, demd->d_name.name, emd_dir));
-
- fill_new_filp (&buf.filp, demd);
-
- buf.pos = 0;
- buf.size = 0;
-
- empty.found = 0;
empty.posok = emd_dir->i_size;
- empty.onesize = 0;
while (1) {
- struct umsdos_dirent *rentry = (struct umsdos_dirent *)
- (buf.buffer + buf.pos);
- int file_pos = buf.filp.f_pos - buf.size + buf.pos;
-
- if (buf.pos == buf.size) {
- ret = umsdos_fillbuf (&buf);
- if (ret < 0) {
- /* Not found, so note where it can be added */
+ struct umsdos_dirent *rentry;
+ int entry_size;
+
+ if (offs >= max_offs) {
+ if (page) {
+ kunmap(page);
+ page_cache_release(page);
+ }
+ if (pos >= emd_dir->i_size) {
info->f_pos = empty.posok;
break;
}
- } else if (rentry->name_len == 0) {
+ if (++index == (emd_dir->i_size>>PAGE_CACHE_SHIFT))
+ max_offs = emd_dir->i_size & ~PAGE_CACHE_MASK;
+ offs -= PAGE_CACHE_SIZE;
+ page = read_cache_page(mapping,index,readpage,NULL);
+ if (IS_ERR(page))
+ goto sync_fail;
+ wait_on_page(page);
+ if (!Page_Uptodate(page))
+ goto async_fail;
+ p = (char*)kmap(page);
+ }
+
+ rentry = (struct umsdos_dirent *)(p+offs);
+
+ if (rentry->name_len == 0) {
/* We are looking for an empty section at least */
/* as large as recsize. */
if (entry->name_len == 0) {
- info->f_pos = file_pos;
+ info->f_pos = pos;
ret = 0;
break;
- } else if (!empty.found) {
- if (empty.onesize == 0) {
- /* This is the first empty record of a section. */
- empty.one = file_pos;
- }
- /* grow the empty section */
- empty.onesize += UMSDOS_REC_SIZE;
- if (empty.onesize == recsize) {
- /* Here is a large enough section. */
- empty.posok = empty.one;
- empty.found = 1;
- }
}
- buf.pos += UMSDOS_REC_SIZE;
- } else {
- int entry_size = umsdos_evalrecsize (rentry->name_len);
-
- if (buf.pos + entry_size > buf.size) {
- ret = umsdos_fillbuf (&buf);
- if (ret < 0) {
- /* Not found, so note where it can be added */
- info->f_pos = empty.posok;
- break;
- }
- } else {
- empty.onesize = 0; /* Reset the free slot search. */
- if (entry->name_len == rentry->name_len
- && memcmp (entry->name, rentry->name, rentry->name_len) == 0) {
- info->f_pos = file_pos;
- *entry = *rentry;
- ret = 0;
- break;
- } else {
- buf.pos += entry_size;
- }
+ offs += UMSDOS_REC_SIZE;
+ pos += UMSDOS_REC_SIZE;
+ if (found)
+ continue;
+ if (!empty_size)
+ empty.one = pos-UMSDOS_REC_SIZE;
+ empty_size += UMSDOS_REC_SIZE;
+ if (empty_size == recsize) {
+ /* Here is a large enough section. */
+ empty.posok = empty.one;
+ found = 1;
}
+ continue;
}
+
+ entry_size = umsdos_evalrecsize(rentry->name_len);
+ if (entry_size > PAGE_CACHE_SIZE)
+ goto async_fail;
+ empty_size = 0;
+ if (entry->name_len != rentry->name_len)
+ goto skip_it;
+
+ if (entry_size + offs > PAGE_CACHE_SIZE) {
+ /* Sucker spans the page boundary */
+ int len = (p+PAGE_CACHE_SIZE)-rentry->name;
+ struct page *next_page;
+ char *q;
+ next_page = read_cache_page(mapping,index+1,readpage,NULL);
+ if (IS_ERR(next_page)) {
+ page_cache_release(page);
+ page = next_page;
+ goto sync_fail;
+ }
+ wait_on_page(next_page);
+ if (!Page_Uptodate(next_page)) {
+ page_cache_release(page);
+ page = next_page;
+ goto async_fail;
+ }
+ q = (char*)kmap(next_page);
+ if (memcmp(entry->name, rentry->name, len) ||
+ memcmp(entry->name+len, q, entry->name_len-len)) {
+ kunmap(next_page);
+ page_cache_release(next_page);
+ goto skip_it;
+ }
+ kunmap(next_page);
+ page_cache_release(next_page);
+ } else if (memcmp (entry->name, rentry->name, entry->name_len))
+ goto skip_it;
+
+ info->f_pos = pos;
+ copy_entry(entry, rentry);
+ ret = 0;
+ break;
+skip_it:
+ offs+=entry_size;
+ pos+=entry_size;
+ }
+ if (page) {
+ kunmap(page);
+ page_cache_release(page);
}
-Printk(("umsdos_find: ready to mangle %s, len=%d, pos=%ld\n",
-entry->name, entry->name_len, (long)info->f_pos));
umsdos_manglename (info);
out_dput:
dput(demd);
-
-out:
- Printk (("umsdos_find: returning %d\n", ret));
return ret;
+
+async_fail:
+ page_cache_release(page);
+ page = ERR_PTR(-EIO);
+sync_fail:
+ return PTR_ERR(page);
}
@@ -557,12 +490,17 @@
int umsdos_newentry (struct dentry *parent, struct umsdos_info *info)
{
int err, ret = -EEXIST;
+ struct dentry *demd = umsdos_get_emd_dentry(parent);
- err = umsdos_find (parent, info);
+ ret = PTR_ERR(demd);
+ if (IS_ERR(ret))
+ goto out;
+ err = umsdos_find (demd, info);
if (err && err == -ENOENT) {
ret = umsdos_writeentry (parent, info, 0);
Printk (("umsdos_writeentry EMD ret = %d\n", ret));
}
+out:
return ret;
}
@@ -580,15 +518,20 @@
int umsdos_newhidden (struct dentry *parent, struct umsdos_info *info)
{
int ret;
+ struct dentry *demd = umsdos_get_emd_dentry(parent);
+ ret = PTR_ERR(demd);
+ if (IS_ERR(ret))
+ goto out;
umsdos_parse ("..LINK", 6, info);
info->entry.name_len = 0;
- ret = umsdos_find (parent, info);
+ ret = umsdos_find (demd, info);
if (ret == -ENOENT || ret == 0) {
info->entry.name_len = sprintf (info->entry.name,
"..LINK%ld", info->f_pos);
ret = 0;
}
+out:
return ret;
}
@@ -603,8 +546,12 @@
int umsdos_delentry (struct dentry *parent, struct umsdos_info *info, int isdir)
{
int ret;
+ struct dentry *demd = umsdos_get_emd_dentry(parent);
- ret = umsdos_find (parent, info);
+ ret = PTR_ERR(demd);
+ if (IS_ERR(ret))
+ goto out;
+ ret = umsdos_find (demd, info);
if (ret)
goto out;
if (info->entry.name_len == 0)
@@ -637,7 +584,7 @@
{
struct dentry *demd;
int ret = 2;
- struct file filp;
+ loff_t pos = 0;
demd = umsdos_get_emd_dentry(dentry);
if (IS_ERR(demd))
@@ -646,14 +593,11 @@
if (!demd->d_inode)
goto out_dput;
- fill_new_filp (&filp, demd);
- filp.f_flags = O_RDONLY;
-
ret = 1;
- while (filp.f_pos < demd->d_inode->i_size) {
+ while (pos < demd->d_inode->i_size) {
struct umsdos_dirent entry;
- if (umsdos_emd_dir_readentry (&filp, &entry) != 0) {
+ if (umsdos_emd_dir_readentry (demd, &pos, &entry) != 0) {
ret = 0;
break;
}
@@ -666,9 +610,6 @@
out_dput:
dput(demd);
out:
-Printk(("umsdos_isempty: checked %s/%s, empty=%d\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, ret));
-
return ret;
}
@@ -686,8 +627,12 @@
int expect)
{
int ret;
+ struct dentry *demd = umsdos_get_emd_dentry(parent);
- ret = umsdos_find (parent, info);
+ ret = PTR_ERR(demd);
+ if (IS_ERR(ret))
+ goto out;
+ ret = umsdos_find (demd, info);
if (ret)
goto out;
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)