]> git.neil.brown.name Git - history.git/commitdiff
[PATCH] remove umsdos from tree
authorChristoph Hellwig <hch@lst.de>
Tue, 11 Jan 2005 01:21:11 +0000 (17:21 -0800)
committerLinus Torvalds <torvalds@ppc970.osdl.org>
Tue, 11 Jan 2005 01:21:11 +0000 (17:21 -0800)
UMSDOS has been non-function since early 2.5 and would need a major rewrite
to be resurrected (which I don't hope anyone plans as it's a really
horrible hack)

From: Adrian Bunk <bunk@stusta.de>

With umsdos gone, there's no longer a MAINTAINERS entry required.

Signed-off-by: Adrian Bunk <bunk@stusta.de>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
18 files changed:
Documentation/filesystems/00-INDEX
Documentation/filesystems/umsdos.txt [deleted file]
MAINTAINERS
fs/Kconfig
fs/Makefile
fs/umsdos/Makefile [deleted file]
fs/umsdos/README-WIP.txt [deleted file]
fs/umsdos/dir.c [deleted file]
fs/umsdos/emd.c [deleted file]
fs/umsdos/inode.c [deleted file]
fs/umsdos/ioctl.c [deleted file]
fs/umsdos/mangle.c [deleted file]
fs/umsdos/namei.c [deleted file]
fs/umsdos/rdir.c [deleted file]
fs/umsdos/specs [deleted file]
include/linux/umsdos_fs.h [deleted file]
include/linux/umsdos_fs.p [deleted file]
include/linux/umsdos_fs_i.h [deleted file]

index 6cf8082f605befa2e81f79ea9da75bb987695461..bcfbab899b370509175af4e9bca4f0cb68624324 100644 (file)
@@ -42,8 +42,6 @@ udf.txt
        - info and mount options for the UDF filesystem.
 ufs.txt
        - info on the ufs filesystem.
-umsdos.txt
-       - info on the umsdos extensions to the msdos filesystem.
 vfat.txt
        - info on using the VFAT filesystem used in Windows NT and Windows 95
 vfs.txt
diff --git a/Documentation/filesystems/umsdos.txt b/Documentation/filesystems/umsdos.txt
deleted file mode 100644 (file)
index c253708..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-Firstly, let me say that UMSDOS is going through some major code changes,
-and has some KNOWN BUGS (and quite a few unknown :-). Please read
-fs/umsdos/README-WIP.txt for more information on current status. Thanks.
-
-----------------------------------------------------------------------------
-Very short explanation for the impatient!
-
-Umsdos is a file system driver that run on top the MSDOS fs driver.
-It is written by Jacques Gelinas (jacques@solucorp.qc.ca)
-and is currently maintained by Matija Nalis (mnalis@jagor.srce.hr)
-
-Umsdos is not a file system per se, but a twist to make a boring
-one into a useful one.
-
-It gives you:
-
-       long file names
-       Permissions and owners
-       Links
-       Special files (devices, pipes...)
-       All that is needed to be a linux root fs.
-
-There is plenty of documentation on it in the source. A formatted document
-made from those comments is available from
-sunsite.unc.edu:/pub/Linux/system/Filesystems/umsdos.
-
-You mount a DOS partition like this:
-
-mount -t umsdos /dev/hda3 /mnt
-         ^
----------|
-
-All options are passed to the msdos drivers. Option like uid,gid etc are
-given to msdos.
-
-The default behavior of Umsdos is to do the same thing as the msdos driver
-mostly passing commands to it without much processing. Again, this is
-the default. After doing the mount on a DOS partition, nothing special
-happens. This is why all mount options are passed to the msdos fs driver.
-
-Umsdos uses a special DOS file --linux-.--- to store the information
-which can't be handled by the normal MS-DOS filesystem. This is the trick.
-
---linux-.--- is optional. There is one per directory.
-
-**** If --linux-.--- is missing, then Umsdos process the directory the
-     same way the msdos driver does. Short file names, no goodies, default
-     owner and permissions. So each directory may have or not this
-     --linux-.---
-
-Now, how to get those --linux-.---.
-
-\begin joke_section
-
-       Well send me a directory content
-       and I will send you one customised for you.
-       $5 per directory. Add any applicable taxes.
-\end joke_section
-
-A utility umssync creates those. The kernel maintains them. It is available
-from the same directory above (sunsite) in the file umsdos_progs-0.7.tar.gz.
-A compiled version is available in umsdos_progs-0.7.bin.tar.gz.
-
-So in our example, after mounting mnt, we do
-
-       umssync .
-
-This will promote this directory (a recursive option is available) to full
-umsdos capabilities (long name, etc.).  However, an "ls -l" before and after
-won't show much difference.  The files which were there are still there, but
-now you can do all this:
-
-       chmod 644 *
-       chown you.your_group *
-       ls >THIS_IS.A.VERY.LONG.NAME
-       ln -s toto tata
-       ls -l
-
-Once a directory is promoted, all subdirectories created will inherit that
-promotion.
-
-What happens if you boot DOS and create files in those promoted directories ?
-Umsdos won't notice new files, but will signal removed files (it won't crash).
-Using umssync in /etc/rc will make sure the DOS directory is in sync with
-the --linux-.---.
-
-It is a good idea to put the following command in your RC file just
-after the "mount -a":
-
-       mount -a
-       /sbin/umssync -i+ -c+ -r99 /umsdos_mount_point
-
-       (You put one for each umsdos mount point in the fstab)
-
-This will ensure nice operation.  A umsdos.fsck is in the making,
-so you will be allowed to manage umsdos partitions in the same way
-other filesystems are, using the generic fsck front end.
-
-Hope this helps!
-
index df0d9e0b30e4084b587c6222d11260f056518547..502b6bf95c5ec7f79589c4e7f4da3b3454967531 100644 (file)
@@ -2244,13 +2244,6 @@ L:       linux_udf@hpesjro.fc.hp.com
 W:     http://linux-udf.sourceforge.net
 S:     Maintained
 
-UMSDOS FILESYSTEM
-P:     Matija Nalis
-M:     Matija Nalis <mnalis-umsdos@voyager.hr>
-L:     linux-kernel@vger.kernel.org
-W:     http://linux.voyager.hr/umsdos/
-S:     Maintained
-
 UNIFORM CDROM DRIVER
 P:     Jens Axboe
 M:     axboe@suse.de
index e2661f504c5daaa4f88c04a42a365b221a295826..17e4eb1b97a8f3cd3fcb1b624bd369a460c304ca 100644 (file)
@@ -578,9 +578,8 @@ config FAT_FS
        tristate
        select NLS
        help
-         If you want to use one of the FAT-based file systems (the MS-DOS,
-         VFAT (Windows 95) and UMSDOS (used to run Linux on top of an
-         ordinary DOS partition) file systems), then you must say Y or M here
+         If you want to use one of the FAT-based file systems (the MS-DOS and
+         VFAT (Windows 95) file systems), then you must say Y or M here
          to include FAT support. You will then be able to mount partitions or
          diskettes with FAT-based file systems and transparently access the
          files on them, i.e. MSDOS files will look and behave just like all
@@ -612,9 +611,6 @@ config FAT_FS
          fat.  Note that if you compile the FAT support as a module, you
          cannot compile any of the FAT-based file systems into the kernel
          -- they will have to be modules as well.
-         The file system of your root partition (the one containing the
-         directory /) cannot be a module, so don't say M here if you intend
-         to use UMSDOS as your root file system.
 
 config MSDOS_FS
        tristate "MSDOS fs support"
@@ -631,10 +627,6 @@ config MSDOS_FS
          transparent, i.e. the MSDOS files look and behave just like all
          other Unix files.
 
-         If you want to use UMSDOS, the Unix-like file system on top of a
-         DOS file system, which allows you to run Linux from within a DOS
-         partition without repartitioning, you'll have to say Y or M here.
-
          If you have Windows 95 or Windows NT installed on your MSDOS
          partitions, you should use the VFAT file system (say Y to "VFAT fs
          support" below), or you will not be able to see the long filenames
@@ -654,11 +646,6 @@ config VFAT_FS
          used by Windows 95, Windows 98, Windows NT 4.0, and the Unix
          programs from the mtools package.
 
-         You cannot use the VFAT file system for your Linux root partition
-         (the one containing the directory /); use UMSDOS instead if you
-         want to run Linux from within a DOS partition (i.e. say Y to
-         "Unix like fs on top of std MSDOS fs", below).
-
          The VFAT support enlarges your kernel by about 10 KB and it only
          works if you said Y to the "DOS FAT fs support" above.  Please read
          the file <file:Documentation/filesystems/vfat.txt> for details.  If
@@ -689,35 +676,6 @@ config FAT_DEFAULT_IOCHARSET
          If unsure, you shouldn't set "utf8" here.
          See <file:Documentation/filesystems/vfat.txt> for more information.
 
-config UMSDOS_FS
-#dep_tristate '    UMSDOS: Unix-like file system on top of standard MSDOS fs' CONFIG_UMSDOS_FS $CONFIG_MSDOS_FS
-# UMSDOS is temprory broken
-       bool
-       help
-         Say Y here if you want to run Linux from within an existing DOS
-         partition of your hard drive. The advantage of this is that you can
-         get away without repartitioning your hard drive (which often implies
-         backing everything up and restoring afterwards) and hence you're
-         able to quickly try out Linux or show it to your friends; the
-         disadvantage is that Linux becomes susceptible to DOS viruses and
-         that UMSDOS is somewhat slower than ext2fs.  Another use of UMSDOS
-         is to write files with long unix filenames to MSDOS floppies; it
-         also allows Unix-style soft-links and owner/permissions of files on
-         MSDOS floppies.  You will need a program called umssync in order to
-         make use of UMSDOS; read
-         <file:Documentation/filesystems/umsdos.txt>.
-
-         To get utilities for initializing/checking UMSDOS file system, or
-         latest patches and/or information, visit the UMSDOS home page at
-         <http://www.voyager.hr/~mnalis/umsdos/>.
-
-         This option enlarges your kernel by about 28 KB and it only works if
-         you said Y to both "DOS FAT fs support" and "MSDOS fs support"
-         above.  To compile this as a module, choose M here: the module will be
-         called umsdos.  Note that the file system of your root partition
-         (the one containing the directory /) cannot be a module, so saying M
-         could be dangerous.  If unsure, say N.
-
 config NTFS_FS
        tristate "NTFS file system support"
        select NLS
index 82dbf96892fa422227215a806edcec6991b99162..443f2bc56ccfd99b7f0fa96cc895dea496825ac2 100644 (file)
@@ -57,7 +57,6 @@ obj-$(CONFIG_HUGETLBFS)               += hugetlbfs/
 obj-$(CONFIG_CODA_FS)          += coda/
 obj-$(CONFIG_MINIX_FS)         += minix/
 obj-$(CONFIG_FAT_FS)           += fat/
-obj-$(CONFIG_UMSDOS_FS)                += umsdos/
 obj-$(CONFIG_MSDOS_FS)         += msdos/
 obj-$(CONFIG_VFAT_FS)          += vfat/
 obj-$(CONFIG_BFS_FS)           += bfs/
diff --git a/fs/umsdos/Makefile b/fs/umsdos/Makefile
deleted file mode 100644 (file)
index 7de2612..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-#
-# Makefile for the umsdos Unix-like filesystem routines.
-#
-
-obj-$(CONFIG_UMSDOS) += umsdos.o
-
-umsdos-objs := dir.o  inode.o ioctl.o mangle.o namei.o rdir.o emd.o
-
-p:
-       proto *.c >/usr/include/linux/umsdos_fs.p
-
-doc:
-       nadoc -i -p umsdos.doc - /tmp/umsdos.mpg
diff --git a/fs/umsdos/README-WIP.txt b/fs/umsdos/README-WIP.txt
deleted file mode 100644 (file)
index 14643c7..0000000
+++ /dev/null
@@ -1,114 +0,0 @@
-Changes by Matija Nalis (mnalis@jagor.srce.hr) on umsdos dentry fixing
-(started by Peter T. Waltenberg <peterw@karaka.chch.cri.nz>)
-(Final conversion to dentries Bill Hawes <whawes@star.net>)
-
-There is no warning any more.
-Both read-only and read-write stuff is fixed, both in
-msdos-compatibile mode, and in umsdos EMD mode, and it seems stable.
-
-Userland NOTE: new umsdos_progs (umssync, umssetup, udosctl & friends) that
-will compile and work on 2.2.x+ kernels and glibc based systems, as well as
-kernel patches and other umsdos related information may be found at
-http://linux.voyager.hr/umsdos/
-
-Information below is getting outdated slowly -- I'll fix it one day when I
-get enough time - there are more important things to fix right now.
-
-Legend: those lines marked with '+' on the beggining of line indicates it
-passed all of my tests, and performed perfect in all of them.
-
-Current status (010125) - UMSDOS 0.86j:
-
-(1) pure MSDOS (no --linux-.--- EMD file):
-
-READ:
-+ readdir                      - works
-+ lookup                       - works
-+ read file                    - works
-
-WRITE:
-+ creat file                   - works
-+ unlink file                  - works
-+ write file                   - works
-+ rename file (same dir)       - works
-+ rename file (dif. dir)       - works
-+ rename dir (same dir)                - works
-+ rename dir (dif. dir)                - works
-+ mkdir                                - works
-+ rmdir                        - works
-
-
-(2) umsdos (with --linux-.--- EMD file):
-
-READ:
-+ readdir                      - works
-+ lookup                       - works
-+ permissions/owners stuff     - works
-+ long file names              - works
-+ read file                    - works
-+ switching MSDOS/UMSDOS       - works
-+ switching UMSDOS/MSDOS       - works
-- pseudo root things           - works mostly. See notes below.
-+ resolve symlink              - works
-+ dereference symlink          - works
-+ dangling symlink             - works
-+ hard links                   - works
-+ special files (block/char devices, FIFOs, sockets...)        - works
-+ various umsdos ioctls                - works
-
-
-WRITE:
-+ create symlink               - works
-+ create hardlink              - works
-+ create file                  - works
-+ create special file          - works
-+ write to file                        - works
-+ rename file (same dir)       - works
-+ rename file (dif. dir)       - works
-+ rename hardlink (same dir)   - works
-- rename hardlink (dif. dir)   - works, but see notes below.
-+ rename symlink (same dir)    - works
-+ rename symlink (dif. dir)    - works
-+ rename dir (same dir)                - works
-+ rename dir (dif. dir)                - works
-+ unlink file                  - works
-+ notify_change (chown,perms)  - works
-+ notify_change for hardlinks  - works
-+ unlink hardlink              - works
-+ mkdir                                - works
-+ rmdir                        - works
-+ umssyncing (many ioctls)     - works
-
-
-- CVF-FAT stuff (compressed DOS filesystem) - there is some support from Frank
-  Gockel <gockel@sent13.uni-duisburg.de> to use it even under umsdosfs, but I
-  have no way of testing it -- please let me know if there are problems specific
-  to umsdos (for instance, it works under msdosfs, but not under umsdosfs).
-
-
-Some current notes:
-
-Note: creating and using pseudo-hardlinks is always non-perfect, especially
-in filesystems that might be externally modified like umsdos. There is
-example is specs file about it. Specifically, moving directory which
-contains hardlinks will break them.
-
-Note: (about creating hardlinks in pseudoroot mode) - hardlinks created in
-pseudoroot mode are now again compatibile with 'normal' hardlinks, and vice
-versa. Thanks to Sorin Iordachescu <sorin@rodae.ro> for providing fix.
-See http://linux.voyager.hr/umsdos/hlbug.html for more info and upgrade
-procedure if you used broken versions...
-
-------------------------------------------------------------------------------
-
-Some general notes:
-
-Good idea when running development kernels is to have SysRq support compiled
-in kernel, and use Sync/Emergency-remount-RO if you bump into problems (like
-not being able to umount(2) umsdosfs, and because of it root partition also,
-or panics which force you to reboot etc.)
-
-I'm unfortunately somewhat out of time to read linux-kernel@vger, but I do
-check for messages having "UMSDOS" in the subject, and read them.  I might
-miss some in all that volume, though.  I should reply to any direct e-mail
-in few days.  If I don't, probably I never got your message.
diff --git a/fs/umsdos/dir.c b/fs/umsdos/dir.c
deleted file mode 100644 (file)
index 775f020..0000000
+++ /dev/null
@@ -1,810 +0,0 @@
-/*
- *  linux/fs/umsdos/dir.c
- *
- *  Written 1993 by Jacques Gelinas
- *      Inspired from linux/fs/msdos/... : Werner Almesberger
- *
- *  Extended MS-DOS directory handling functions
- */
-
-#include <linux/time.h>
-#include <linux/string.h>
-#include <linux/fs.h>
-#include <linux/msdos_fs.h>
-#include <linux/errno.h>
-#include <linux/stat.h>
-#include <linux/limits.h>
-#include <linux/umsdos_fs.h>
-#include <linux/slab.h>
-#include <linux/pagemap.h>
-#include <linux/smp_lock.h>
-
-#define UMSDOS_SPECIAL_DIRFPOS 3
-extern struct dentry *saved_root;
-extern struct inode *pseudo_root;
-
-/* #define UMSDOS_DEBUG_VERBOSE 1 */
-
-/*
- * Dentry operations routines
- */
-
-/* nothing for now ... */
-static int umsdos_dentry_validate(struct dentry *dentry, struct nameidata *nd)
-{
-       return 1;
-}
-
-/* for now, drop everything to force lookups ... */
-/* ITYM s/everything/& positive/... */
-static int umsdos_dentry_dput(struct dentry *dentry)
-{
-       struct inode *inode = dentry->d_inode;
-       if (inode) {
-               return 1;
-       }
-       return 0;
-}
-
-struct dentry_operations umsdos_dentry_operations =
-{
-       .d_revalidate   = umsdos_dentry_validate,
-       .d_delete       = umsdos_dentry_dput,
-};
-
-struct UMSDOS_DIR_ONCE {
-       void *dirbuf;
-       filldir_t filldir;
-       int count;
-       int stop;
-};
-
-/*
- * Record a single entry the first call.
- * Return -EINVAL the next one.
- * NOTE: filldir DOES NOT use a dentry
- */
-
-static int umsdos_dir_once (   void *buf,
-                               const char *name,
-                               int len,
-                               loff_t offset,
-                               ino_t ino,
-                               unsigned type)
-{
-       int ret = -EINVAL;
-       struct UMSDOS_DIR_ONCE *d = (struct UMSDOS_DIR_ONCE *) buf;
-
-       if (d->count == 0) {
-               PRINTK ((KERN_DEBUG "dir_once :%.*s: offset %Ld\n", 
-                       len, name, offset));
-               ret = d->filldir (d->dirbuf, name, len, offset, ino, DT_UNKNOWN);
-               d->stop = ret < 0;
-               d->count = 1;
-       }
-       return ret;
-}
-
-
-/*
- * Read count directory entries from directory filp
- * Return a negative value from linux/errno.h.
- * Return > 0 if success (the number of bytes written by filldir).
- * 
- * This function is used by the normal readdir VFS entry point,
- * and in order to get the directory entry from a file's dentry.
- * See umsdos_dentry_to_entry() below.
- */
-static int umsdos_readdir_x (struct inode *dir, struct file *filp,
-                               void *dirbuf, struct umsdos_dirent *u_entry,
-                               filldir_t filldir)
-{
-       struct dentry *demd;
-       off_t start_fpos;
-       int ret = 0;
-       loff_t pos;
-
-       umsdos_startlookup (dir);
-
-       if (filp->f_pos == UMSDOS_SPECIAL_DIRFPOS && dir == pseudo_root) {
-
-               /*
-                * We don't need to simulate this pseudo directory
-                * when umsdos_readdir_x is called for internal operation
-                * of umsdos. This is why dirent_in_fs is tested
-                */
-               /* #Specification: pseudo root / directory /DOS
-                * When umsdos operates in pseudo root mode (C:\linux is the
-                * linux root), it simulate a directory /DOS which points to
-                * the real root of the file system.
-                */
-
-               Printk ((KERN_WARNING "umsdos_readdir_x: pseudo_root thing UMSDOS_SPECIAL_DIRFPOS\n"));
-               if (filldir (dirbuf, "DOS", 3, 
-                               UMSDOS_SPECIAL_DIRFPOS, UMSDOS_ROOT_INO, DT_DIR) == 0) {
-                       filp->f_pos++;
-               }
-               goto out_end;
-       }
-
-       if (filp->f_pos < 2 || 
-           (dir->i_ino != UMSDOS_ROOT_INO && filp->f_pos == 32)) {
-       
-               int last_f_pos = filp->f_pos;
-               struct UMSDOS_DIR_ONCE bufk;
-
-               Printk (("umsdos_readdir_x: . or .. /mn/?\n"));
-
-               bufk.dirbuf = dirbuf;
-               bufk.filldir = filldir;
-               bufk.count = 0;
-
-               ret = fat_readdir (filp, &bufk, umsdos_dir_once);
-               if (last_f_pos > 0 && filp->f_pos > last_f_pos)
-                       filp->f_pos = UMSDOS_SPECIAL_DIRFPOS;
-               if (u_entry != NULL)
-                       u_entry->flags = 0;
-               goto out_end;
-       }
-
-       Printk (("umsdos_readdir_x: normal file /mn/?\n"));
-
-       /* get the EMD dentry */
-       demd = umsdos_get_emd_dentry(filp->f_dentry);
-       ret = PTR_ERR(demd);
-       if (IS_ERR(demd))
-               goto out_end;
-       ret = -EIO;
-       if (!demd->d_inode) {
-               printk(KERN_WARNING 
-                       "umsdos_readir_x: EMD file %s/%s not found\n",
-                       demd->d_parent->d_name.name, demd->d_name.name);
-               goto out_dput;
-       }
-
-       pos = filp->f_pos;
-       start_fpos = filp->f_pos;
-
-       if (pos <= UMSDOS_SPECIAL_DIRFPOS + 1)
-               pos = 0;
-       ret = 0;
-       while (pos < demd->d_inode->i_size) {
-               off_t cur_f_pos = pos;
-               struct dentry *dret;
-               struct inode *inode;
-               struct umsdos_dirent entry;
-               struct umsdos_info info;
-
-               ret = -EIO;
-               if (umsdos_emd_dir_readentry (demd, &pos, &entry) != 0)
-                       break;
-               if (entry.name_len == 0)
-                       continue;
-#ifdef UMSDOS_DEBUG_VERBOSE
-if (entry.flags & UMSDOS_HLINK)
-printk("umsdos_readdir_x: %s/%s is hardlink\n",
-filp->f_dentry->d_name.name, entry.name);
-#endif
-
-               umsdos_parse (entry.name, entry.name_len, &info);
-               info.f_pos = cur_f_pos;
-               umsdos_manglename (&info);
-               /*
-                * Do a real lookup on the short name.
-                */
-               dret = umsdos_covered(filp->f_dentry, info.fake.fname,
-                                                info.fake.len);
-               ret = PTR_ERR(dret);
-               if (IS_ERR(dret))
-                       break;
-               /*
-                * If the file wasn't found, remove it from the EMD.
-                */
-               inode = dret->d_inode;
-               if (!inode)
-                       goto remove_name;
-#ifdef UMSDOS_DEBUG_VERBOSE
-if (UMSDOS_I(inode)->i_is_hlink)
-printk("umsdos_readdir_x: %s/%s already resolved, ino=%ld\n",
-dret->d_parent->d_name.name, dret->d_name.name, inode->i_ino);
-#endif
-
-Printk (("Found %s/%s, ino=%ld, flags=%x\n",
-dret->d_parent->d_name.name, info.fake.fname, dret->d_inode->i_ino,
-entry.flags));
-               /* check whether to resolve a hard-link */
-               if ((entry.flags & UMSDOS_HLINK) &&
-                   !UMSDOS_I(inode)->i_is_hlink) {
-                       dret = umsdos_solve_hlink (dret);
-                       ret = PTR_ERR(dret);
-                       if (IS_ERR(dret))
-                               break;
-                       inode = dret->d_inode;
-                       if (!inode) {
-printk("umsdos_readdir_x: %s/%s negative after link\n",
-dret->d_parent->d_name.name, dret->d_name.name);
-                               goto clean_up;
-                       }
-               }
-
-               /* #Specification:  pseudo root / reading real root
-                * The pseudo root (/linux) is logically
-                * erased from the real root.  This means that
-                * ls /DOS, won't show "linux". This avoids
-                * infinite recursion (/DOS/linux/DOS/linux/...) while
-                * walking the file system.
-                */
-               if (inode != pseudo_root && !(entry.flags & UMSDOS_HIDDEN)) {
-                       if (filldir (dirbuf, entry.name, entry.name_len,
-                                cur_f_pos, inode->i_ino, DT_UNKNOWN) < 0) {
-                               pos = cur_f_pos;
-                       }
-Printk(("umsdos_readdir_x: got %s/%s, ino=%ld\n",
-dret->d_parent->d_name.name, dret->d_name.name, inode->i_ino));
-                       if (u_entry != NULL)
-                               *u_entry = entry;
-                       dput(dret);
-                       ret = 0;
-                       break;
-               }
-       clean_up:
-               dput(dret);
-               continue;
-
-       remove_name:
-               /* #Specification:  umsdos / readdir / not in MSDOS
-                * During a readdir operation, if the file is not
-                * in the MS-DOS directory any more, the entry is
-                * removed from the EMD file silently.
-                */
-#ifdef UMSDOS_PARANOIA
-printk("umsdos_readdir_x: %s/%s out of sync, erasing\n",
-filp->f_dentry->d_name.name, info.entry.name);
-#endif
-               ret = umsdos_delentry(filp->f_dentry, &info, 
-                                       S_ISDIR(info.entry.mode));
-               if (ret)
-                       printk(KERN_WARNING 
-                               "umsdos_readdir_x: delentry %s, err=%d\n",
-                               info.entry.name, ret);
-               goto clean_up;
-       }
-       /*
-        * If the fillbuf has failed, f_pos is back to 0.
-        * To avoid getting back into the . and .. state
-        * (see comments at the beginning), we put back
-        * the special offset.
-        */
-       filp->f_pos = pos;
-       if (filp->f_pos == 0)
-               filp->f_pos = start_fpos;
-out_dput:
-       dput(demd);
-
-out_end:
-       umsdos_endlookup (dir);
-       
-       Printk ((KERN_DEBUG "read dir %p pos %Ld ret %d\n",
-               dir, filp->f_pos, ret));
-       return ret;
-}
-
-
-/*
- * Read count directory entries from directory filp.
- * Return a negative value from linux/errno.h.
- * Return 0 or positive if successful.
- */
-static int UMSDOS_readdir (struct file *filp, void *dirbuf, filldir_t filldir)
-{
-       struct inode *dir = filp->f_dentry->d_inode;
-       int ret = 0, count = 0;
-       struct UMSDOS_DIR_ONCE bufk;
-
-       lock_kernel();
-
-       bufk.dirbuf = dirbuf;
-       bufk.filldir = filldir;
-       bufk.stop = 0;
-
-       Printk (("UMSDOS_readdir in\n"));
-       while (ret == 0 && bufk.stop == 0) {
-               struct umsdos_dirent entry;
-
-               bufk.count = 0;
-               ret = umsdos_readdir_x (dir, filp, &bufk, &entry, 
-                                       umsdos_dir_once);
-               if (bufk.count == 0)
-                       break;
-               count += bufk.count;
-       }
-       unlock_kernel();
-       Printk (("UMSDOS_readdir out %d count %d pos %Ld\n", 
-               ret, count, filp->f_pos));
-       return count ? : ret;
-}
-
-
-/*
- * Complete the inode content with info from the EMD file.
- *
- * This function modifies the state of a dir inode.  It decides
- * whether the dir is a UMSDOS or DOS directory.  This is done
- * deeper in umsdos_patch_inode() called at the end of this function.
- * 
- * Because it is does disk access, umsdos_patch_inode() may block.
- * At the same time, another process may get here to initialise
- * the same directory inode. There are three cases.
- * 
- * 1) The inode is already initialised.  We do nothing.
- * 2) The inode is not initialised.  We lock access and do it.
- * 3) Like 2 but another process has locked the inode, so we try
- * to lock it and check right afterward check whether
- * initialisation is still needed.
- * 
- * 
- * Thanks to the "mem" option of the kernel command line, it was
- * possible to consistently reproduce this problem by limiting
- * my memory to 4 MB and running X.
- *
- * Do this only if the inode is freshly read, because we will lose
- * the current (updated) content.
- *
- * A lookup of a mount point directory yield the inode into
- * the other fs, so we don't care about initialising it. iget()
- * does this automatically.
- */
-
-void umsdos_lookup_patch_new(struct dentry *dentry, struct umsdos_info *info)
-{
-       struct inode *inode = dentry->d_inode;
-       struct umsdos_dirent *entry = &info->entry;
-
-       /*
-        * This part of the initialization depends only on i_patched.
-        */
-       if (UMSDOS_I(inode)->i_patched)
-               goto out;
-       UMSDOS_I(inode)->i_patched = 1;
-       if (S_ISREG (entry->mode))
-               entry->mtime = inode->i_mtime;
-       inode->i_mode = entry->mode;
-       inode->i_rdev = to_kdev_t (entry->rdev);
-       inode->i_atime = entry->atime;
-       inode->i_ctime = entry->ctime;
-       inode->i_mtime = entry->mtime;
-       inode->i_uid = entry->uid;
-       inode->i_gid = entry->gid;
-
-       /* #Specification: umsdos / i_nlink
-        * The nlink field of an inode is maintained by the MSDOS file system
-        * for directory and by UMSDOS for other files.  The logic is that
-        * MSDOS is already figuring out what to do for directories and
-        * does nothing for other files.  For MSDOS, there are no hard links
-        * so all file carry nlink==1.  UMSDOS use some info in the
-        * EMD file to plug the correct value.
-        */
-       if (!S_ISDIR (entry->mode)) {
-               if (entry->nlink > 0) {
-                       inode->i_nlink = entry->nlink;
-               } else {
-                       printk (KERN_ERR 
-                               "UMSDOS:  lookup_patch entry->nlink < 1 ???\n");
-               }
-       }
-       /*
-        * The mode may have changed, so patch the inode again.
-        */
-       umsdos_patch_dentry_inode(dentry, info->f_pos);
-       umsdos_set_dirinfo_new(dentry, info->f_pos);
-
-out:
-       return;
-}
-
-
-/*
- * Return != 0 if an entry is the pseudo DOS entry in the pseudo root.
- */
-
-int umsdos_is_pseudodos (struct inode *dir, struct dentry *dentry)
-{
-       /* #Specification: pseudo root / DOS hard coded
-        * The pseudo sub-directory DOS in the pseudo root is hard coded.
-        * The name is DOS. This is done this way to help standardised
-        * the umsdos layout. The idea is that from now on /DOS is
-        * a reserved path and nobody will think of using such a path
-        * for a package.
-        */
-       return dir == pseudo_root
-           && dentry->d_name.len == 3
-           && dentry->d_name.name[0] == 'D'
-           && dentry->d_name.name[1] == 'O'
-           && dentry->d_name.name[2] == 'S';
-}
-
-
-/*
- * Check whether a file exists in the current directory.
- * Return 0 if OK, negative error code if not (ex: -ENOENT).
- *
- * fills dentry->d_inode with found inode, and increments its count.
- * if not found, return -ENOENT.
- */
-/* #Specification: umsdos / lookup
- * A lookup for a file is done in two steps.  First, we
- * locate the file in the EMD file.  If not present, we
- * return an error code (-ENOENT).  If it is there, we
- * repeat the operation on the msdos file system. If
- * this fails, it means that the file system is not in
- * sync with the EMD file.   We silently remove this
- * entry from the EMD file, and return ENOENT.
- */
-
-struct dentry *umsdos_lookup_x (struct inode *dir, struct dentry *dentry, int nopseudo)
-{                              
-       struct dentry *dret = NULL;
-       struct inode *inode;
-       int ret = -ENOENT;
-       struct umsdos_info info;
-
-#ifdef UMSDOS_DEBUG_VERBOSE
-printk("umsdos_lookup_x: looking for %s/%s\n", 
-dentry->d_parent->d_name.name, dentry->d_name.name);
-#endif
-
-       umsdos_startlookup (dir);
-       if (umsdos_is_pseudodos (dir, dentry)) {
-               /* #Specification: pseudo root / lookup(DOS)
-                * A lookup of DOS in the pseudo root will always succeed
-                * and return the inode of the real root.
-                */
-               Printk ((KERN_DEBUG "umsdos_lookup_x: following /DOS\n"));
-               inode = saved_root->d_inode;
-               goto out_add;
-       }
-
-       ret = umsdos_parse (dentry->d_name.name, dentry->d_name.len, &info);
-       if (ret) {
-printk("umsdos_lookup_x: %s/%s parse failed, ret=%d\n", 
-dentry->d_parent->d_name.name, dentry->d_name.name, ret);
-               goto out;
-       }
-
-       ret = umsdos_findentry (dentry->d_parent, &info, 0);
-       if (ret) {
-if (ret != -ENOENT)
-printk("umsdos_lookup_x: %s/%s findentry failed, ret=%d\n", 
-dentry->d_parent->d_name.name, dentry->d_name.name, ret);
-               goto out;
-       }
-Printk (("lookup %.*s pos %lu ret %d len %d ", 
-info.fake.len, info.fake.fname, info.f_pos, ret, info.fake.len));
-
-       /* do a real lookup to get the short name ... */
-       dret = umsdos_covered(dentry->d_parent, info.fake.fname, info.fake.len);
-       ret = PTR_ERR(dret);
-       if (IS_ERR(dret)) {
-printk("umsdos_lookup_x: %s/%s real lookup failed, ret=%d\n", 
-dentry->d_parent->d_name.name, dentry->d_name.name, ret);
-               goto out;
-       }
-       inode = dret->d_inode;
-       if (!inode)
-               goto out_remove;
-       umsdos_lookup_patch_new(dret, &info);
-#ifdef UMSDOS_DEBUG_VERBOSE
-printk("umsdos_lookup_x: found %s/%s, ino=%ld\n", 
-dret->d_parent->d_name.name, dret->d_name.name, dret->d_inode->i_ino);
-#endif
-
-       /* Check for a hard link */
-       if ((info.entry.flags & UMSDOS_HLINK) &&
-           !UMSDOS_I(inode)->i_is_hlink) {
-               dret = umsdos_solve_hlink (dret);
-               ret = PTR_ERR(dret);
-               if (IS_ERR(dret))
-                       goto out;
-               ret = -ENOENT;
-               inode = dret->d_inode;
-               if (!inode) {
-printk("umsdos_lookup_x: %s/%s negative after link\n", 
-dret->d_parent->d_name.name, dret->d_name.name);
-                       goto out_dput;
-               }
-       }
-
-       if (inode == pseudo_root && !nopseudo) {
-               /* #Specification: pseudo root / dir lookup
-                * For the same reason as readdir, a lookup in /DOS for
-                * the pseudo root directory (linux) will fail.
-                */
-               /*
-                * This has to be allowed for resolving hard links
-                * which are recorded independently of the pseudo-root
-                * mode.
-                */
-printk("umsdos_lookup_x: skipping DOS/linux\n");
-               ret = -ENOENT;
-               goto out_dput;
-       }
-
-       /*
-        * We've found it OK.  Now hash the dentry with the inode.
-        */
-out_add:
-       atomic_inc(&inode->i_count);
-       d_add (dentry, inode);
-       dentry->d_op = &umsdos_dentry_operations;
-       ret = 0;
-
-out_dput:
-       if (dret && dret != dentry)
-               d_drop(dret);
-       dput(dret);
-out:
-       umsdos_endlookup (dir);
-       return ERR_PTR(ret);
-
-out_remove:
-       printk(KERN_WARNING "UMSDOS:  entry %s/%s out of sync, erased\n",
-               dentry->d_parent->d_name.name, dentry->d_name.name);
-       umsdos_delentry (dentry->d_parent, &info, S_ISDIR (info.entry.mode));
-       ret = -ENOENT;
-       goto out_dput;
-}
-
-
-/*
- * Check whether a file exists in the current directory.
- * Return 0 if OK, negative error code if not (ex: -ENOENT).
- * 
- * Called by VFS; should fill dentry->d_inode via d_add.
- */
-
-struct dentry *UMSDOS_lookup (struct inode *dir, struct dentry *dentry, struct nameidata *nd)
-{
-       struct dentry *ret;
-
-       ret = umsdos_lookup_x (dir, dentry, 0);
-
-       /* Create negative dentry if not found. */
-       if (ret == ERR_PTR(-ENOENT)) {
-               Printk ((KERN_DEBUG 
-                       "UMSDOS_lookup: converting -ENOENT to negative\n"));
-               d_add (dentry, NULL);
-               dentry->d_op = &umsdos_dentry_operations;
-               ret = NULL;
-       }
-       return ret;
-}
-
-struct dentry *umsdos_covered(struct dentry *parent, char *name, int len)
-{
-       struct dentry *result, *dentry;
-       struct qstr qstr;
-
-       qstr.name = name;
-       qstr.len  = len;
-       qstr.hash = full_name_hash(name, len);
-       result = ERR_PTR(-ENOMEM);
-       dentry = d_alloc(parent, &qstr);
-       if (dentry) {
-               /* XXXXXXXXXXXXXXXXXXX Race alert! */
-               result = UMSDOS_rlookup(parent->d_inode, dentry);
-               d_drop(dentry);
-               if (result)
-                       goto out_fail;
-               return dentry;
-       }
-out:
-       return result;
-
-out_fail:
-       dput(dentry);
-       goto out;
-}
-
-/*
- * Lookup or create a dentry from within the filesystem.
- *
- * We need to use this instead of lookup_dentry, as the 
- * directory semaphore lock is already held.
- */
-struct dentry *umsdos_lookup_dentry(struct dentry *parent, char *name, int len,
-                                       int real)
-{
-       struct dentry *result, *dentry;
-       struct qstr qstr;
-
-       qstr.name = name;
-       qstr.len  = len;
-       qstr.hash = full_name_hash(name, len);
-       result = d_lookup(parent, &qstr);
-       if (!result) {
-               result = ERR_PTR(-ENOMEM);
-               dentry = d_alloc(parent, &qstr);
-               if (dentry) {
-                       result = real ?
-                               UMSDOS_rlookup(parent->d_inode, dentry) :
-                               UMSDOS_lookup(parent->d_inode, dentry);
-                       if (result)
-                               goto out_fail;
-                       return dentry;
-               }
-       }
-out:
-       return result;
-
-out_fail:
-       dput(dentry);
-       goto out;
-}
-
-/*
- * Return a path relative to our root.
- */
-char * umsdos_d_path(struct dentry *dentry, char * buffer, int len)
-{
-       struct dentry * old_root;
-       char * path;
-
-       read_lock(&current->fs->lock);
-       old_root = dget(current->fs->root);
-       read_unlock(&current->fs->lock);
-       spin_lock(&dcache_lock);
-       path = __d_path(dentry, current->fs->rootmnt, dentry->d_sb->s_root, current->fs->rootmnt, buffer, len); /* FIXME: current->fs->rootmnt */
-       spin_unlock(&dcache_lock);
-
-       if (*path == '/')
-               path++; /* skip leading '/' */
-
-       if (current->fs->root->d_inode == pseudo_root)
-       {
-               *(path-1) = '/';
-               path -= (UMSDOS_PSDROOT_LEN+1);
-               memcpy(path, UMSDOS_PSDROOT_NAME, UMSDOS_PSDROOT_LEN);
-       }
-       dput(old_root);
-
-       return path;
-}
-
-/*
- * Return the dentry which points to a pseudo-hardlink.
- *
- * it should try to find file it points to
- * if file is found, return new dentry/inode
- * The resolved inode will have i_is_hlink set.
- *
- * Note: the original dentry is always dput(), even if an error occurs.
- */
-
-struct dentry *umsdos_solve_hlink (struct dentry *hlink)
-{
-       /* root is our root for resolving pseudo-hardlink */
-       struct dentry *base = hlink->d_sb->s_root;
-       struct dentry *dentry_dst;
-       char *path, *pt;
-       int len;
-       struct address_space *mapping = hlink->d_inode->i_mapping;
-       struct page *page;
-
-       page=read_cache_page(mapping,0,(filler_t *)mapping->a_ops->readpage,NULL);
-       dentry_dst=(struct dentry *)page;
-       if (IS_ERR(page))
-               goto out;
-       wait_on_page_locked(page);
-       if (!PageUptodate(page))
-               goto async_fail;
-
-       dentry_dst = ERR_PTR(-ENOMEM);
-       path = (char *) kmalloc (PATH_MAX, GFP_KERNEL);
-       if (path == NULL)
-               goto out_release;
-       memcpy(path, kmap(page), hlink->d_inode->i_size);
-       kunmap(page);
-       page_cache_release(page);
-
-       len = hlink->d_inode->i_size;
-
-       /* start at root dentry */
-       dentry_dst = dget(base);
-       path[len] = '\0';
-       
-       pt = path;
-       if (*path == '/')
-               pt++; /* skip leading '/' */
-       
-       if (base->d_inode == pseudo_root)
-               pt += (UMSDOS_PSDROOT_LEN + 1);
-       
-       while (1) {
-               struct dentry *dir = dentry_dst, *demd;
-               char *start = pt;
-               int real;
-
-               while (*pt != '\0' && *pt != '/') pt++;
-               len = (int) (pt - start);
-               if (*pt == '/') *pt++ = '\0';
-
-               real = 1;
-               demd = umsdos_get_emd_dentry(dir);
-               if (!IS_ERR(demd)) {
-                       if (demd->d_inode)
-                               real = 0;
-                       dput(demd);
-               }
-
-#ifdef UMSDOS_DEBUG_VERBOSE
-printk ("umsdos_solve_hlink: dir %s/%s, name=%s, real=%d\n",
-dir->d_parent->d_name.name, dir->d_name.name, start, real);
-#endif
-               dentry_dst = umsdos_lookup_dentry(dir, start, len, real);
-/* XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX */
-               if (real)
-                       d_drop(dir);
-               dput (dir);
-               if (IS_ERR(dentry_dst))
-                       break;
-               /* not found? stop search ... */
-               if (!dentry_dst->d_inode) {
-                       break;
-               }
-               if (*pt == '\0')        /* we're finished! */
-                       break;
-       } /* end while */
-
-       if (!IS_ERR(dentry_dst)) {
-               struct inode *inode = dentry_dst->d_inode;
-               if (inode) {
-                       UMSDOS_I(inode)->i_is_hlink = 1;
-#ifdef UMSDOS_DEBUG_VERBOSE
-printk ("umsdos_solve_hlink: resolved link %s/%s, ino=%ld\n",
-dentry_dst->d_parent->d_name.name, dentry_dst->d_name.name, inode->i_ino);
-#endif
-               } else {
-#ifdef UMSDOS_DEBUG_VERBOSE
-printk ("umsdos_solve_hlink: resolved link %s/%s negative!\n",
-dentry_dst->d_parent->d_name.name, dentry_dst->d_name.name);
-#endif
-               }
-       } else
-               printk(KERN_WARNING
-                       "umsdos_solve_hlink: err=%ld\n", PTR_ERR(dentry_dst));
-       kfree (path);
-
-out:
-       dput(hlink);    /* original hlink no longer needed */
-       return dentry_dst;
-
-async_fail:
-       dentry_dst = ERR_PTR(-EIO);
-out_release:
-       page_cache_release(page);
-       goto out;
-}      
-
-
-struct file_operations umsdos_dir_operations =
-{
-       .read           = generic_read_dir,
-       .readdir        = UMSDOS_readdir,
-       .ioctl          = UMSDOS_ioctl_dir,
-};
-
-struct inode_operations umsdos_dir_inode_operations =
-{
-       .create         = UMSDOS_create,
-       .lookup         = UMSDOS_lookup,
-       .link           = UMSDOS_link,
-       .unlink         = UMSDOS_unlink,
-       .symlink        = UMSDOS_symlink,
-       .mkdir          = UMSDOS_mkdir,
-       .rmdir          = UMSDOS_rmdir,
-       .mknod          = UMSDOS_mknod,
-       .rename         = UMSDOS_rename,
-       .setattr        = UMSDOS_notify_change,
-};
diff --git a/fs/umsdos/emd.c b/fs/umsdos/emd.c
deleted file mode 100644 (file)
index 16a15d7..0000000
+++ /dev/null
@@ -1,660 +0,0 @@
-/*
- *  linux/fs/umsdos/emd.c
- *
- *  Written 1993 by Jacques Gelinas
- *
- *  Extended MS-DOS directory handling functions
- */
-
-#include <linux/types.h>
-#include <linux/fcntl.h>
-#include <linux/kernel.h>
-#include <linux/time.h>
-#include <linux/errno.h>
-#include <linux/string.h>
-#include <linux/msdos_fs.h>
-#include <linux/umsdos_fs.h>
-#include <linux/dcache.h>
-#include <linux/pagemap.h>
-#include <linux/delay.h>
-
-void put_entry (struct umsdos_dirent *p, struct umsdos_dirent *q)
-{
-       p->name_len = q->name_len;
-       p->flags = q->flags;
-       p->nlink = cpu_to_le16(q->nlink);
-       p->uid = cpu_to_le16(q->uid);
-       p->gid = cpu_to_le16(q->gid);
-       p->atime = cpu_to_le32(q->atime);
-       p->mtime = cpu_to_le32(q->mtime);
-       p->ctime = cpu_to_le32(q->ctime);
-       p->rdev = cpu_to_le16(q->rdev);
-       p->mode = cpu_to_le16(q->mode);
-}
-
-static void get_entry(struct umsdos_dirent *p, struct umsdos_dirent *q)
-{
-       p->name_len = q->name_len;
-       p->name[p->name_len]='\0';
-       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);
-}
-
-/*
- * Lookup the EMD dentry for a directory.
- *
- * Note: the caller must hold a lock on the parent directory.
- */
-struct dentry *umsdos_get_emd_dentry(struct dentry *parent)
-{
-       struct dentry *demd;
-
-       demd = umsdos_lookup_dentry(parent, UMSDOS_EMD_FILE, 
-                                       UMSDOS_EMD_NAMELEN, 1);
-       return demd;
-}
-
-/*
- * Check whether a directory has an EMD file.
- *
- * Note: the caller must hold a lock on the parent directory.
- */
-int umsdos_have_emd(struct dentry *dir)
-{
-       struct dentry *demd = umsdos_get_emd_dentry (dir);
-       int found = 0;
-
-       if (!IS_ERR(demd)) {
-               if (demd->d_inode)
-                       found = 1;
-               dput(demd);
-       }
-       return found;
-}
-
-/*
- * Create the EMD file for a directory if it doesn't
- * already exist. Returns 0 or an error code.
- *
- * Note: the caller must hold a lock on the parent directory.
- */
-int umsdos_make_emd(struct dentry *parent)
-{
-       struct dentry *demd = umsdos_get_emd_dentry(parent);
-       int err = PTR_ERR(demd);
-
-       if (IS_ERR(demd)) {
-               printk("umsdos_make_emd: can't get dentry in %s, err=%d\n",
-                       parent->d_name.name, err);
-               goto out;
-       }
-
-       /* already created? */
-       err = 0;
-       if (demd->d_inode)
-               goto out_set;
-
-Printk(("umsdos_make_emd: creating EMD %s/%s\n",
-parent->d_name.name, demd->d_name.name));
-
-       err = msdos_create(parent->d_inode, demd, S_IFREG | 0777, NULL);
-       if (err) {
-               printk (KERN_WARNING
-                       "umsdos_make_emd: create %s/%s failed, err=%d\n",
-                       parent->d_name.name, demd->d_name.name, err);
-       }
-out_set:
-       dput(demd);
-out:
-       return err;
-}
-
-
-/*
- * Read an entry from the EMD file.
- * Support variable length record.
- * Return -EIO if error, 0 if OK.
- *
- * does not change {d,i}_count
- */
-
-int umsdos_emd_dir_readentry (struct dentry *demd, loff_t *pos, struct umsdos_dirent *entry)
-{
-       struct address_space *mapping = demd->d_inode->i_mapping;
-       struct page *page;
-       struct umsdos_dirent *p;
-       int offs = *pos & ~PAGE_CACHE_MASK;
-       int recsize;
-       int ret = 0;
-
-       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_locked(page);
-       if (!PageUptodate(page))
-               goto async_fail;
-       p = (struct umsdos_dirent*)(kmap(page)+offs);
-
-       /* if this is an invalid entry (invalid name length), ignore it */
-       if( p->name_len > UMSDOS_MAXNAME )
-       {
-               printk (KERN_WARNING "Ignoring invalid EMD entry with size %d\n", entry->name_len);
-               p->name_len = 0; 
-               ret = -ENAMETOOLONG; /* notify umssync(8) code that something is wrong */
-               /* FIXME: does not work if we did 'ls -l' before 'udosctl uls' ?! */
-       }
-
-       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;
-               }
-               wait_on_page_locked(page2);
-               if (!PageUptodate(page2)) {
-                       kunmap(page);
-                       page_cache_release(page2);
-                       goto async_fail;
-               }
-               memcpy(entry->spare,p->spare,part);
-               memcpy(entry->spare+part,kmap(page2),
-                               recsize+offs-PAGE_CACHE_SIZE);
-               kunmap(page2);
-               page_cache_release(page2);
-       } else
-               memcpy(entry->spare,p->spare,((char*)p+recsize)-p->spare);
-       get_entry(entry, p);
-       kunmap(page);
-       page_cache_release(page);
-       *pos += recsize;
-       return ret;
-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.
- *
- * Note: the caller must hold a lock on the parent directory.
- */
-int umsdos_writeentry (struct dentry *parent, struct umsdos_info *info,
-                               int free_entry)
-{
-       struct inode *dir = parent->d_inode;
-       struct umsdos_dirent *entry = &info->entry;
-       struct dentry *emd_dentry;
-       int ret;
-       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);
-       if (IS_ERR(emd_dentry))
-               goto out;
-       /* make sure there's an EMD file */
-       ret = -EIO;
-       if (!emd_dentry->d_inode) {
-               printk(KERN_WARNING
-                       "umsdos_writeentry: no EMD file in %s/%s\n",
-                       parent->d_parent->d_name.name, parent->d_name.name);
-               goto out_dput;
-       }
-
-       if (free_entry) {
-               /* #Specification: EMD file / empty entries
-                * Unused entries in the EMD file are identified
-                * by the name_len field equal to 0. However to
-                * help future extension (or bug correction :-( ),
-                * empty entries are filled with 0.
-                */
-               memset (&entry0, 0, sizeof (entry0));
-               entry = &entry0;
-       } else if (entry->name_len > 0) {
-               memset (entry->name + entry->name_len, '\0', 
-                       sizeof (entry->name) - entry->name_len);
-               /* #Specification: EMD file / spare bytes
-                * 10 bytes are unused in each record of the EMD. They
-                * are set to 0 all the time, so it will be possible
-                * to do new stuff and rely on the state of those
-                * bytes in old EMD files.
-                */
-               memset (entry->spare, 0, sizeof (entry->spare));
-       }
-
-       /* write the entry and update the parent timestamps */
-       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 *) (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;
-               put_entry (p, entry);
-               memcpy(p->spare,entry->spare,
-                       (char *)(page_address(page) + PAGE_CACHE_SIZE) - p->spare);
-               memcpy(page_address(page2),
-                               ((char*)entry)+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);
-               unlock_page(page2);
-               page_cache_release(page2);
-               if (ret)
-                       goto out_unlock;
-       } else {
-               ret = mapping->a_ops->prepare_write(NULL,page,offs,
-                                       offs + info->recsize);
-               if (ret)
-                       goto out_unlock;
-               put_entry (p, entry);
-               memcpy(p->spare,entry->spare,((char*)p+info->recsize)-p->spare);
-               ret = mapping->a_ops->commit_write(NULL,page,offs,
-                                       offs + info->recsize);
-               if (ret)
-                       goto out_unlock;
-       }
-       unlock_page(page);
-       page_cache_release(page);
-               
-       dir->i_ctime = dir->i_mtime = CURRENT_TIME_SEC;
-       mark_inode_dirty(dir);
-
-out_dput:
-       dput(emd_dentry);
-out:
-       Printk (("umsdos_writeentry /mn/: returning %d...\n", ret));
-       return ret;
-out_unlock3:
-       unlock_page(page2);
-       page_cache_release(page2);
-out_unlock2:
-       ClearPageUptodate(page);
-       kunmap(page);
-out_unlock:
-       unlock_page(page);
-       page_cache_release(page);
-       printk ("UMSDOS:  problem with EMD file:  can't write\n");
-       goto out_dput;
-}
-
-/*
- * 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
- * slot (of the proper size).
- * 
- * Return 0 if found, -ENOENT if not found, another error code if
- * other problem.
- * 
- * So this routine is used to either find an existing entry or to
- * create a new one, while making sure it is a new one. After you
- * get -ENOENT, you make sure the entry is stuffed correctly and
- * call umsdos_writeentry().
- * 
- * To delete an entry, you find it, zero out the entry (memset)
- * and call umsdos_writeentry().
- * 
- * All this to say that umsdos_writeentry must be called after this
- * function since it relies on the f_pos field of info.
- *
- * Note: the caller must hold a lock on the parent directory.
- */
-/* #Specification: EMD file structure
- * The EMD file uses a fairly simple layout.  It is made of records
- * (UMSDOS_REC_SIZE == 64).  When a name can't be written in a single
- * record, multiple contiguous records are allocated.
- */
-
-static int umsdos_find (struct dentry *demd, struct umsdos_info *info)
-{
-       struct umsdos_dirent *entry = &info->entry;
-       int recsize = info->recsize;
-       struct inode *emd_dir;
-       int ret = -ENOENT;
-       struct {
-               off_t posok;    /* Position available to store the entry */
-               off_t one;      /* One empty position -> maybe <- large enough */
-       } 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;
-
-       /* 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;
-
-       empty.posok = emd_dir->i_size;
-       while (1) {
-               struct umsdos_dirent *rentry;
-               int entry_size;
-
-               if (offs >= max_offs) {
-                       if (page) {
-                               kunmap(page);
-                               page_cache_release(page);
-                               page = NULL;
-                       }
-                       if (pos >= emd_dir->i_size) {
-                               info->f_pos = empty.posok;
-                               break;
-                       }
-                       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_locked(page);
-                       if (!PageUptodate(page))
-                               goto async_fail;
-                       p = 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 = pos;
-                               ret = 0;
-                               break;
-                       }
-                       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_locked(next_page);
-                       if (!PageUptodate(next_page)) {
-                               page_cache_release(page);
-                               page = next_page;
-                               goto async_fail;
-                       }
-                       q = 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;
-               get_entry(entry, rentry);
-               ret = 0;
-               break;
-skip_it:
-               offs+=entry_size;
-               pos+=entry_size;
-       }
-       if (page) {
-               kunmap(page);
-               page_cache_release(page);
-       }
-       umsdos_manglename (info);
-
-out_dput:
-       dput(demd);
-       return ret;
-
-async_fail:
-       page_cache_release(page);
-       page = ERR_PTR(-EIO);
-sync_fail:
-       return PTR_ERR(page);
-}
-
-
-/*
- * Add a new entry in the EMD file.
- * Return 0 if OK or a negative error code.
- * Return -EEXIST if the entry already exists.
- *
- * Complete the information missing in info.
- * 
- * N.B. What if the EMD file doesn't exist?
- */
-
-int umsdos_newentry (struct dentry *parent, struct umsdos_info *info)
-{
-       int err, ret = -EEXIST;
-       struct dentry *demd = umsdos_get_emd_dentry(parent);
-
-       ret = PTR_ERR(demd);
-       if (IS_ERR(demd))
-               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;
-}
-
-
-/*
- * Create a new hidden link.
- * Return 0 if OK, an error code if not.
- */
-
-/* #Specification: hard link / hidden name
- * When a hard link is created, the original file is renamed
- * to a hidden name. The name is "..LINKNNN" where NNN is a
- * number define from the entry offset in the EMD file.
- */
-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(demd))
-               goto out;
-
-       umsdos_parse ("..LINK", 6, info);
-       info->entry.name_len = 0;
-       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;
-}
-
-
-/*
- * Remove an entry from the EMD file.
- * Return 0 if OK, a negative error code otherwise.
- * 
- * Complete the information missing in info.
- */
-
-int umsdos_delentry (struct dentry *parent, struct umsdos_info *info, int isdir)
-{
-       int ret;
-       struct dentry *demd = umsdos_get_emd_dentry(parent);
-
-       ret = PTR_ERR(demd);
-       if (IS_ERR(demd))
-               goto out;
-       ret = umsdos_find (demd, info);
-       if (ret)
-               goto out;
-       if (info->entry.name_len == 0)
-               goto out;
-
-       if ((isdir != 0) != (S_ISDIR (info->entry.mode) != 0)) {
-               if (S_ISDIR (info->entry.mode)) {
-                       ret = -EISDIR;
-               } else {
-                       ret = -ENOTDIR;
-               }
-               goto out;
-       }
-       ret = umsdos_writeentry (parent, info, 1);
-
-out:
-       return ret;
-}
-
-
-/*
- * Verify that an EMD directory is empty.
- * Return: 
- * 0 if not empty,
- * 1 if empty (except for EMD file),
- * 2 if empty or no EMD file.
- */
-
-int umsdos_isempty (struct dentry *dentry)
-{
-       struct dentry *demd;
-       int ret = 2;
-       loff_t pos = 0;
-
-       demd = umsdos_get_emd_dentry(dentry);
-       if (IS_ERR(demd))
-               goto out;
-       /* If the EMD file does not exist, it is certainly empty. :-) */
-       if (!demd->d_inode)
-               goto out_dput;
-
-       ret = 1;
-       while (pos < demd->d_inode->i_size) {
-               struct umsdos_dirent entry;
-
-               if (umsdos_emd_dir_readentry (demd, &pos, &entry) != 0) {
-                       ret = 0;
-                       break;
-               }
-               if (entry.name_len != 0) {
-                       ret = 0;
-                       break;
-               }
-       }
-
-out_dput:
-       dput(demd);
-out:
-       return ret;
-}
-
-/*
- * Locate an entry in a EMD directory.
- * Return 0 if OK, error code if not, generally -ENOENT.
- *
- * expect argument:
- *     0: anything
- *     1: file
- *     2: directory
- */
-
-int umsdos_findentry (struct dentry *parent, struct umsdos_info *info,
-                       int expect)
-{              
-       int ret;
-       struct dentry *demd = umsdos_get_emd_dentry(parent);
-
-       ret = PTR_ERR(demd);
-       if (IS_ERR(demd))
-               goto out;
-       ret = umsdos_find (demd, info);
-       if (ret)
-               goto out;
-
-       switch (expect) {
-       case 1:
-               if (S_ISDIR (info->entry.mode))
-                       ret = -EISDIR;
-               break;
-       case 2:
-               if (!S_ISDIR (info->entry.mode))
-                       ret = -ENOTDIR;
-       }
-
-out:
-       Printk (("umsdos_findentry: returning %d\n", ret));
-       return ret;
-}
diff --git a/fs/umsdos/inode.c b/fs/umsdos/inode.c
deleted file mode 100644 (file)
index 778feed..0000000
+++ /dev/null
@@ -1,483 +0,0 @@
-/*
- *  linux/fs/umsdos/inode.c
- *
- *      Written 1993 by Jacques Gelinas
- *      Inspired from linux/fs/msdos/... by Werner Almesberger
- */
-
-#include <linux/module.h>
-
-#include <linux/init.h>
-#include <linux/fs.h>
-#include <linux/msdos_fs.h>
-#include <linux/kernel.h>
-#include <linux/time.h>
-#include <linux/errno.h>
-#include <asm/uaccess.h>
-#include <linux/string.h>
-#include <linux/stat.h>
-#include <linux/umsdos_fs.h>
-#include <linux/list.h>
-#include <linux/pagemap.h>
-
-extern struct dentry_operations umsdos_dentry_operations;
-
-struct dentry *saved_root;     /* Original root if changed */
-struct inode *pseudo_root;     /* Useful to simulate the pseudo DOS */
-                                       /* directory. See UMSDOS_readdir_x() */
-
-static struct dentry *check_pseudo_root(struct super_block *);
-
-
-void UMSDOS_put_inode (struct inode *inode)
-{
-       PRINTK ((KERN_DEBUG 
-               "put inode %p (%lu) pos %lu count=%d\n"
-                ,inode, inode->i_ino
-                ,UMSDOS_I(inode)->pos
-                ,atomic_read(&inode->i_count)));
-
-       if (inode == pseudo_root) {
-               Printk ((KERN_ERR "Umsdos: debug: releasing pseudo_root - ino=%lu count=%d\n", inode->i_ino, atomic_read(&inode->i_count)));
-       }
-
-       if (atomic_read(&inode->i_count) == 1)
-               UMSDOS_I(inode)->i_patched = 0;
-}
-
-
-void UMSDOS_put_super (struct super_block *sb)
-{
-       Printk ((KERN_DEBUG "UMSDOS_put_super: entering\n"));
-       if (saved_root && pseudo_root && kdev_same(sb->s_dev, ROOT_DEV)) {
-               shrink_dcache_parent(saved_root);
-               dput(saved_root);
-               saved_root = NULL;
-               pseudo_root = NULL;
-       }
-       fat_put_super (sb);
-}
-
-
-/*
- * Complete the setup of a directory dentry based on its
- * EMD/non-EMD status.  If it has an EMD, then plug the
- * umsdos function table. If not, use the msdos one.
- */
-void umsdos_setup_dir(struct dentry *dir)
-{
-       struct inode *inode = dir->d_inode;
-       struct umsdos_inode_info *ui = UMSDOS_I(inode);
-
-       if (!S_ISDIR(inode->i_mode))
-               printk(KERN_ERR "umsdos_setup_dir: %s/%s not a dir!\n",
-                       dir->d_parent->d_name.name, dir->d_name.name);
-
-       init_waitqueue_head (&ui->dir_info.p);
-       ui->dir_info.looking = 0;
-       ui->dir_info.creating = 0;
-       ui->dir_info.pid = 0;
-
-       inode->i_op = &umsdos_rdir_inode_operations;
-       inode->i_fop = &umsdos_rdir_operations;
-       if (umsdos_have_emd(dir)) {
-Printk((KERN_DEBUG "umsdos_setup_dir: %s/%s using EMD\n",
-dir->d_parent->d_name.name, dir->d_name.name));
-               inode->i_op = &umsdos_dir_inode_operations;
-               inode->i_fop = &umsdos_dir_operations;
-       }
-}
-
-
-/*
- * Add some info into an inode so it can find its owner quickly
- */
-void umsdos_set_dirinfo_new (struct dentry *dentry, off_t f_pos)
-{
-       struct inode *inode = dentry->d_inode;
-       struct dentry *demd;
-
-       UMSDOS_I(inode)->pos = f_pos;
-
-       /* now check the EMD file */
-       demd = umsdos_get_emd_dentry(dentry->d_parent);
-       if (!IS_ERR(demd)) {
-               dput(demd);
-       }
-       return;
-}
-
-static struct inode_operations umsdos_file_inode_operations = {
-       .truncate       = fat_truncate,
-       .setattr        = UMSDOS_notify_change,
-};
-
-static struct inode_operations umsdos_symlink_inode_operations = {
-       .readlink       = page_readlink,
-       .follow_link    = page_follow_link,
-       .setattr        = UMSDOS_notify_change,
-};
-
-/*
- * Connect the proper tables in the inode and add some info.
- */
-/* #Specification: inode / umsdos info
- * The first time an inode is seen (inode->i_count == 1),
- * the inode number of the EMD file which controls this inode
- * is tagged to this inode. It allows operations such as
- * notify_change to be handled.
- */
-void umsdos_patch_dentry_inode(struct dentry *dentry, off_t f_pos)
-{
-       struct inode *inode = dentry->d_inode;
-
-PRINTK (("umsdos_patch_dentry_inode: inode=%lu\n", inode->i_ino));
-
-       /*
-        * Classify the inode based on EMD/non-EMD status.
-        */
-PRINTK (("umsdos_patch_inode: call umsdos_set_dirinfo_new(%p,%lu)\n",
-dentry, f_pos));
-       umsdos_set_dirinfo_new(dentry, f_pos);
-
-       inode->i_op = &umsdos_file_inode_operations;
-       if (S_ISREG (inode->i_mode)) {
-               /* address_space operations already set */
-       } else if (S_ISDIR (inode->i_mode)) {
-               umsdos_setup_dir(dentry);
-       } else if (S_ISLNK (inode->i_mode)) {
-               /* address_space operations already set */
-               inode->i_op = &umsdos_symlink_inode_operations;
-       } else
-               init_special_inode(inode, inode->i_mode,
-                                       kdev_t_to_nr(inode->i_rdev));
-}
-
-
-/*
- * lock the parent dir before starting ...
- * also handles hardlink converting
- */
-int UMSDOS_notify_change (struct dentry *dentry, struct iattr *attr)
-{
-       struct inode *dir, *inode;
-       struct umsdos_info info;
-       struct dentry *temp, *old_dentry = NULL;
-       int ret;
-
-       lock_kernel();
-
-       ret = umsdos_parse (dentry->d_name.name, dentry->d_name.len,
-                               &info);
-       if (ret)
-               goto out;
-       ret = umsdos_findentry (dentry->d_parent, &info, 0);
-       if (ret) {
-printk("UMSDOS_notify_change: %s/%s not in EMD, ret=%d\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, ret);
-               goto out;
-       }
-
-       if (info.entry.flags & UMSDOS_HLINK) {
-               /*
-                * In order to get the correct (real) inode, we just drop
-                * the original dentry.
-                */ 
-               d_drop(dentry);
-Printk(("UMSDOS_notify_change: hard link %s/%s, fake=%s\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, info.fake.fname));
-       
-               /* Do a real lookup to get the short name dentry */
-               temp = umsdos_covered(dentry->d_parent, info.fake.fname,
-                                               info.fake.len);
-               ret = PTR_ERR(temp);
-               if (IS_ERR(temp))
-                       goto out;
-       
-               /* now resolve the link ... */
-               temp = umsdos_solve_hlink(temp);
-               ret = PTR_ERR(temp);
-               if (IS_ERR(temp))
-                       goto out;
-               old_dentry = dentry;
-               dentry = temp;  /* so umsdos_notify_change_locked will operate on that */
-       }
-
-       dir = dentry->d_parent->d_inode;
-       inode = dentry->d_inode;
-
-       ret = inode_change_ok (inode, attr);
-       if (ret)
-               goto out;
-
-       ret = umsdos_notify_change_locked(dentry, attr);
-       if (ret == 0)
-               ret = inode_setattr (inode, attr);
-out:
-       if (old_dentry)
-               dput (dentry);  /* if we had to use fake dentry for hardlinks, dput() it now */
-       unlock_kernel();
-       return ret;
-}
-
-
-/*
- * Must be called with the parent lock held.
- */
-int umsdos_notify_change_locked(struct dentry *dentry, struct iattr *attr)
-{
-       struct inode *inode = dentry->d_inode;
-       struct dentry *demd;
-       struct address_space *mapping;
-       struct page *page;
-       int ret = 0;
-       struct umsdos_dirent *entry;
-       int offs;
-
-Printk(("UMSDOS_notify_change: entering for %s/%s (%d)\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, UMSDOS_I(inode)->i_patched));
-
-       if (inode->i_nlink == 0)
-               goto out;
-       if (inode->i_ino == UMSDOS_ROOT_INO)
-               goto out;
-
-       /* get the EMD file dentry */
-       demd = umsdos_get_emd_dentry(dentry->d_parent);
-       ret = PTR_ERR(demd);
-       if (IS_ERR(demd))
-               goto out;
-       ret = 0;
-       /* don't do anything if directory is not promoted to umsdos yet */
-       if (!demd->d_inode) { 
-               Printk((KERN_DEBUG
-                       "UMSDOS_notify_change: no EMD file %s/%s\n",
-                       demd->d_parent->d_name.name, demd->d_name.name));
-               goto out_dput;
-       }
-
-       /* don't do anything if this is the EMD itself */
-       if (inode == demd->d_inode)
-               goto out_dput;
-
-       /* This inode is not a EMD file nor an inode used internally
-        * by MSDOS, so we can update its status.
-        * See emd.c
-        */
-
-       /* Read only the start of the entry since we don't touch the name */
-       mapping = demd->d_inode->i_mapping;
-       offs = UMSDOS_I(inode)->pos & ~PAGE_CACHE_MASK;
-       ret = -ENOMEM;
-       page=grab_cache_page(mapping,UMSDOS_I(inode)->pos>>PAGE_CACHE_SHIFT);
-       if (!page)
-               goto out_dput;
-       ret=mapping->a_ops->prepare_write(NULL,page,offs,offs+UMSDOS_REC_SIZE);
-       if (ret)
-               goto out_unlock;
-       entry = (struct umsdos_dirent *) (page_address(page) + offs);
-       if (attr->ia_valid & ATTR_UID)
-               entry->uid = cpu_to_le16(attr->ia_uid);
-       if (attr->ia_valid & ATTR_GID)
-               entry->gid = cpu_to_le16(attr->ia_gid);
-       if (attr->ia_valid & ATTR_MODE)
-               entry->mode = cpu_to_le16(attr->ia_mode);
-       if (attr->ia_valid & ATTR_ATIME)
-               entry->atime = cpu_to_le32(attr->ia_atime);
-       if (attr->ia_valid & ATTR_MTIME)
-               entry->mtime = cpu_to_le32(attr->ia_mtime);
-       if (attr->ia_valid & ATTR_CTIME)
-               entry->ctime = cpu_to_le32(attr->ia_ctime);
-       entry->nlink = cpu_to_le16(inode->i_nlink);
-       ret=mapping->a_ops->commit_write(NULL,page,offs,offs+UMSDOS_REC_SIZE);
-       if (ret)
-               printk(KERN_WARNING
-                       "umsdos_notify_change: %s/%s EMD write error, ret=%d\n",
-                       dentry->d_parent->d_name.name, dentry->d_name.name,ret);
-
-       /* #Specification: notify_change / msdos fs
-        * notify_change operation are done only on the
-        * EMD file. The msdos fs is not even called.
-        */
-out_unlock:
-       unlock_page(page);
-       page_cache_release(page);
-out_dput:
-       dput(demd);
-out:
-       return ret;
-}
-
-
-/*
- * Update the disk with the inode content
- */
-int UMSDOS_write_inode (struct inode *inode, int wait)
-{
-       struct iattr newattrs;
-       int ret;
-
-       ret = fat_write_inode (inode, wait);
-       newattrs.ia_mtime = inode->i_mtime;
-       newattrs.ia_atime = inode->i_atime;
-       newattrs.ia_ctime = inode->i_ctime;
-       newattrs.ia_valid = ATTR_MTIME | ATTR_ATIME | ATTR_CTIME;
-       /*
-        * UMSDOS_notify_change is convenient to call here
-        * to update the EMD entry associated with this inode.
-        * But it has the side effect to re"dirt" the inode.
-        */
-/*      
- * UMSDOS_notify_change (inode, &newattrs);
-
- * inode->i_state &= ~I_DIRTY; / * FIXME: this doesn't work.  We need to remove ourselves from list on dirty inodes. /mn/ */
-       return ret;
-}
-
-
-static struct super_operations umsdos_sops =
-{
-       .write_inode    = UMSDOS_write_inode,
-       .put_inode      = UMSDOS_put_inode,
-       .delete_inode   = fat_delete_inode,
-       .put_super      = UMSDOS_put_super,
-       .statfs         = UMSDOS_statfs,
-       .clear_inode    = fat_clear_inode,
-};
-
-int UMSDOS_statfs(struct super_block *sb,struct statfs *buf)
-{
-       int ret;
-       ret = fat_statfs (sb, buf);
-       if (!ret)       
-               buf->f_namelen = UMSDOS_MAXNAME;
-       return ret;
-}
-
-/*
- * Read the super block of an Extended MS-DOS FS.
- */
-struct super_block *UMSDOS_read_super (struct super_block *sb, void *data,
-                                     int silent)
-{
-       struct super_block *res;
-       struct dentry *new_root;
-
-       /*
-        * Call msdos-fs to mount the disk.
-        * Note: this returns res == sb or NULL
-        */
-       MSDOS_SB(sb)->options.isvfat = 0;
-       res = fat_read_super(sb, data, silent, &umsdos_rdir_inode_operations);
-
-       if (IS_ERR(res))
-               return NULL;
-       if (res == NULL) {
-               if (!silent)
-                       printk(KERN_INFO "VFS: Can't find a valid "
-                              "UMSDOS filesystem on dev %s.\n", sb->s_id);
-               return NULL;
-       }
-
-       printk (KERN_INFO "UMSDOS 0.86k "
-               "(compatibility level %d.%d, fast msdos)\n", 
-               UMSDOS_VERSION, UMSDOS_RELEASE);
-
-       sb->s_op = &umsdos_sops;
-       MSDOS_SB(sb)->options.dotsOK = 0;       /* disable hidden==dotfile */
-
-       /* install our dentry operations ... */
-       sb->s_root->d_op = &umsdos_dentry_operations;
-
-       umsdos_patch_dentry_inode(sb->s_root, 0);
-
-       /* Check whether to change to the /linux root */
-       new_root = check_pseudo_root(sb);
-
-       if (new_root) {
-               /* sanity check */
-               if (new_root->d_op != &umsdos_dentry_operations)
-                       printk("umsdos_read_super: pseudo-root wrong ops!\n");
-
-               pseudo_root = new_root->d_inode;
-               saved_root = sb->s_root;
-               printk(KERN_INFO "UMSDOS: changed to alternate root\n");
-               dget (sb->s_root); sb->s_root = dget(new_root);
-       }
-       return sb;
-}
-
-/*
- * Check for an alternate root if we're the root device.
- */
-
-extern kdev_t ROOT_DEV;
-static struct dentry *check_pseudo_root(struct super_block *sb)
-{
-       struct dentry *root, *sbin, *init;
-
-       /*
-        * Check whether we're mounted as the root device.
-        * must check like this, because we can be used with initrd
-        */
-               
-       if (!kdev_same(sb->s_dev, ROOT_DEV))
-               goto out_noroot;
-
-       /* 
-        * lookup_dentry needs a (so far non-existent) root. 
-        */
-       printk(KERN_INFO "check_pseudo_root: mounted as root\n");
-       root = lookup_one_len(UMSDOS_PSDROOT_NAME, sb->s_root,UMSDOS_PSDROOT_LEN); 
-       if (IS_ERR(root))
-               goto out_noroot;
-               
-       if (!root->d_inode || !S_ISDIR(root->d_inode->i_mode))
-               goto out_dput;
-
-printk(KERN_INFO "check_pseudo_root: found %s/%s\n",
-root->d_parent->d_name.name, root->d_name.name);
-
-       /* look for /sbin/init */
-       sbin = lookup_one_len("sbin", root, 4);
-       if (IS_ERR(sbin))
-               goto out_dput;
-       if (!sbin->d_inode || !S_ISDIR(sbin->d_inode->i_mode))
-               goto out_dput_sbin;
-       init = lookup_one_len("init", sbin, 4);
-       if (IS_ERR(init))
-               goto out_dput_sbin;
-       if (!init->d_inode)
-               goto out_dput_init;
-       printk(KERN_INFO "check_pseudo_root: found %s/%s, enabling pseudo-root\n", init->d_parent->d_name.name, init->d_name.name);
-       dput(sbin);
-       dput(init);
-       return root;
-
-       /* Alternate root not found ... */
-out_dput_init:
-       dput(init);
-out_dput_sbin:
-       dput(sbin);
-out_dput:
-       dput(root);
-out_noroot:
-       return NULL;
-}
-
-
-static DECLARE_FSTYPE_DEV(umsdos_fs_type, "umsdos", UMSDOS_read_super);
-
-static int __init init_umsdos_fs (void)
-{
-       return register_filesystem (&umsdos_fs_type);
-}
-
-static void __exit exit_umsdos_fs (void)
-{
-       unregister_filesystem (&umsdos_fs_type);
-}
-
-module_init(init_umsdos_fs)
-module_exit(exit_umsdos_fs)
-MODULE_LICENSE("GPL");
diff --git a/fs/umsdos/ioctl.c b/fs/umsdos/ioctl.c
deleted file mode 100644 (file)
index fc30003..0000000
+++ /dev/null
@@ -1,446 +0,0 @@
-/*
- *  linux/fs/umsdos/ioctl.c
- *
- *  Written 1993 by Jacques Gelinas
- *
- *  Extended MS-DOS ioctl directory handling functions
- *
- *  Changes:
- *  11/07/2003      Daniele Bellucci <bellucda@tiscali.it>
- *                  - audit copy_to_user/put_user in umsdos_ioctl_fill.
- */
-
-#include <asm/uaccess.h>
-#include <linux/errno.h>
-#include <linux/mm.h>
-#include <linux/kernel.h>
-#include <linux/time.h>
-#include <linux/fs.h>
-#include <linux/msdos_fs.h>
-#include <linux/umsdos_fs.h>
-
-struct UMSDOS_DIR_ONCE {
-       struct dirent *ent;
-       int count;
-};
-
-/*
- * Record a single entry the first call.
- * Return -EINVAL the next one.
- */
-static int umsdos_ioctl_fill (
-                                    void *buf,
-                                    const char *name,
-                                    int name_len,
-                                    loff_t offset,
-                                    ino_t ino,
-                                    unsigned type)
-{
-       int ret = -EINVAL;
-       struct UMSDOS_DIR_ONCE *d = (struct UMSDOS_DIR_ONCE *) buf;
-
-       if (d->count == 0) {
-               if (copy_to_user (d->ent->d_name, name, name_len) ||
-                   put_user ('\0', d->ent->d_name + name_len) ||
-                   put_user (name_len, &d->ent->d_reclen) ||
-                   put_user (ino, &d->ent->d_ino) ||
-                   put_user (offset, &d->ent->d_off))
-                       return -EFAULT;
-               d->count = 1;
-               ret = 0;
-       }
-       return ret;
-}
-
-
-/*
- * Perform special function on a directory
- */
-/* #Specification: ioctl / prototypes
- * The official prototype for the umsdos ioctl on directory
- * is:
- * 
- * int ioctl (
- * int fd,          // File handle of the directory
- * int cmd, // command
- * struct umsdos_ioctl *data)
- * 
- * The struct and the commands are defined in linux/umsdos_fs.h.
- * 
- * umsdos_progs/umsdosio.c provide an interface in C++ to all
- * these ioctl. umsdos_progs/udosctl is a small utility showing
- * all this.
- * 
- * These ioctl generally allow one to work on the EMD or the
- * DOS directory independently. These are essential to implement
- * the synchronise.
- */
-int UMSDOS_ioctl_dir(struct inode *dir, struct file *filp, unsigned int cmd,
-                       unsigned long data_ptr)
-{
-       struct dentry *dentry = filp->f_dentry;
-       struct umsdos_ioctl *idata = (struct umsdos_ioctl *) data_ptr;
-       int ret;
-       struct umsdos_ioctl data;
-
-Printk(("UMSDOS_ioctl_dir: %s/%s, cmd=%d, data=%08lx\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, cmd, data_ptr));
-
-       /* forward non-umsdos ioctls - this hopefully doesn't cause conflicts */
-       if (cmd != UMSDOS_GETVERSION
-           && cmd != UMSDOS_READDIR_DOS
-           && cmd != UMSDOS_READDIR_EMD
-           && cmd != UMSDOS_INIT_EMD
-           && cmd != UMSDOS_CREAT_EMD
-           && cmd != UMSDOS_RENAME_DOS
-           && cmd != UMSDOS_UNLINK_EMD
-           && cmd != UMSDOS_UNLINK_DOS
-           && cmd != UMSDOS_RMDIR_DOS
-           && cmd != UMSDOS_STAT_DOS
-           && cmd != UMSDOS_DOS_SETUP)
-               return fat_dir_ioctl (dir, filp, cmd, data_ptr);
-
-       /* #Specification: ioctl / access
-        * Only root (effective id) is allowed to do IOCTL on directory
-        * in UMSDOS. EPERM is returned for other user.
-        */
-       /*
-        * Well, not all cases require write access, but it simplifies
-        * the code, and let's face it, there is only one client (umssync)
-        * for all this.
-        */
-       ret = verify_area (VERIFY_WRITE, (void *) data_ptr, 
-                               sizeof (struct umsdos_ioctl));
-       if (ret < 0)
-               goto out;
-
-       ret = -EPERM;
-       if (current->euid != 0 && cmd != UMSDOS_GETVERSION)
-               goto out;
-
-       ret = -EINVAL;
-       if (cmd == UMSDOS_GETVERSION) {
-               /* #Specification: ioctl / UMSDOS_GETVERSION
-                * The field version and release of the structure
-                * umsdos_ioctl are filled with the version and release
-                * number of the fs code in the kernel. This will allow
-                * some form of checking. Users won't be able to run
-                * incompatible utility such as the synchroniser (umssync).
-                * umsdos_progs/umsdosio.c enforce this checking.
-                * 
-                * Return always 0.
-                */
-               put_user (UMSDOS_VERSION, &idata->version);
-               put_user (UMSDOS_RELEASE, &idata->release);
-               ret = 0;
-               goto out;
-       }
-       if (cmd == UMSDOS_READDIR_DOS) {
-               /* #Specification: ioctl / UMSDOS_READDIR_DOS
-                * One entry is read from the DOS directory at the current
-                * file position. The entry is put as is in the dos_dirent
-                * field of struct umsdos_ioctl.
-                * 
-                * Return > 0 if success.
-                */
-               struct UMSDOS_DIR_ONCE bufk;
-
-               bufk.count = 0;
-               bufk.ent = &idata->dos_dirent;
-
-               fat_readdir (filp, &bufk, umsdos_ioctl_fill);
-
-               ret = bufk.count == 1 ? 1 : 0;
-               goto out;
-       }
-       if (cmd == UMSDOS_READDIR_EMD) {
-               /* #Specification: ioctl / UMSDOS_READDIR_EMD
-                * One entry is read from the EMD at the current
-                * file position. The entry is put as is in the umsdos_dirent
-                * field of struct umsdos_ioctl. The corresponding mangled
-                * DOS entry name is put in the dos_dirent field.
-                * 
-                * All entries are read including hidden links. Blank
-                * entries are skipped.
-                * 
-                * Return > 0 if success.
-                */
-               struct dentry *demd;
-               loff_t pos = filp->f_pos;
-
-               /* The absence of the EMD is simply seen as an EOF */
-               demd = umsdos_get_emd_dentry(dentry);
-               ret = PTR_ERR(demd);
-               if (IS_ERR(demd))
-                       goto out;
-               ret = 0;
-               if (!demd->d_inode)
-                       goto read_dput;
-
-               while (pos < demd->d_inode->i_size) {
-                       off_t f_pos = pos;
-                       struct umsdos_dirent entry;
-                       struct umsdos_info info;
-
-                       ret = umsdos_emd_dir_readentry (demd, &pos, &entry);
-
-                       if (ret == -ENAMETOOLONG) {
-                               printk (KERN_INFO "Fixing EMD entry with invalid size -- zeroing out\n");
-                               memset (&info, 0, sizeof (info));
-                               info.f_pos = f_pos;
-                               info.recsize = UMSDOS_REC_SIZE;
-                               ret = umsdos_writeentry (dentry, &info, 1);
-                               continue;
-                       }
-
-                       if (ret)
-                               break;
-                       if (entry.name_len <= 0)
-                               continue;
-
-                       umsdos_parse (entry.name, entry.name_len, &info);
-                       info.f_pos = f_pos;
-                       umsdos_manglename (&info);
-                       ret = -EFAULT;
-                       if (copy_to_user (&idata->umsdos_dirent, &entry,
-                                                       sizeof (entry)))
-                               break;
-                       if (copy_to_user (&idata->dos_dirent.d_name,
-                                                       info.fake.fname,
-                                                       info.fake.len + 1))
-                               break;
-                       ret = entry.name_len;
-                       break;
-               }
-               /* update the original f_pos */
-               filp->f_pos = pos;
-       read_dput:
-               d_drop(demd);
-               dput(demd);
-               goto out;
-       }
-       if (cmd == UMSDOS_INIT_EMD) {
-               /* #Specification: ioctl / UMSDOS_INIT_EMD
-                * The UMSDOS_INIT_EMD command makes sure the EMD
-                * exists for a directory. If it does not, it is
-                * created. Also, it makes sure the directory function
-                * table (struct inode_operations) is set to the UMSDOS
-                * semantic. This mean that umssync may be applied to
-                * an "opened" msdos directory, and it will change behavior
-                * on the fly.
-                * 
-                * Return 0 if success.
-                */
-
-               ret = umsdos_make_emd(dentry);
-Printk(("UMSDOS_ioctl_dir: INIT_EMD %s/%s, ret=%d\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, ret));
-               umsdos_setup_dir (dentry);
-               goto out;
-       }
-
-       ret = -EFAULT;
-       if (copy_from_user (&data, idata, sizeof (data)))
-               goto out;
-
-       if (cmd == UMSDOS_CREAT_EMD) {
-               /* #Specification: ioctl / UMSDOS_CREAT_EMD
-                * The umsdos_dirent field of the struct umsdos_ioctl is used
-                * as is to create a new entry in the EMD of the directory.
-                * The DOS directory is not modified.
-                * No validation is done (yet).
-                * 
-                * Return 0 if success.
-                */
-               struct umsdos_info info;
-
-               /* This makes sure info.entry and info in general
-                * is correctly initialised
-                */
-               memcpy (&info.entry, &data.umsdos_dirent,
-                       sizeof (data.umsdos_dirent));
-               umsdos_parse (data.umsdos_dirent.name
-                   ,data.umsdos_dirent.name_len, &info);
-               ret = umsdos_newentry (dentry, &info);
-               goto out;
-       }
-       else if (cmd == UMSDOS_RENAME_DOS) {
-               struct dentry *old_dentry, *new_dentry;         /* FIXME */
-
-               /* #Specification: ioctl / UMSDOS_RENAME_DOS
-                * A file or directory is renamed in a DOS directory
-                * (not moved across directory). The source name
-                * is in the dos_dirent.name field and the destination
-                * is in umsdos_dirent.name field.
-                * 
-                * This ioctl allows umssync to rename a mangled file
-                * name before syncing it back in the EMD.
-                */
-               old_dentry = umsdos_lookup_dentry (dentry, 
-                                               data.dos_dirent.d_name,
-                                               data.dos_dirent.d_reclen ,1);
-               ret = PTR_ERR(old_dentry);
-               if (IS_ERR(old_dentry))
-                       goto out;
-               new_dentry = umsdos_lookup_dentry (dentry,
-                                               data.umsdos_dirent.name,
-                                               data.umsdos_dirent.name_len, 1);
-               ret = PTR_ERR(new_dentry);
-               if (!IS_ERR(new_dentry)) {
-printk("umsdos_ioctl: renaming %s/%s to %s/%s\n",
-old_dentry->d_parent->d_name.name, old_dentry->d_name.name,
-new_dentry->d_parent->d_name.name, new_dentry->d_name.name);
-                       ret = msdos_rename (dir, old_dentry, dir, new_dentry);
-                       d_drop(new_dentry);
-                       d_drop(old_dentry);
-                       dput(new_dentry);
-               }
-               dput(old_dentry);
-               goto out;
-       }
-       else if (cmd == UMSDOS_UNLINK_EMD) {
-               /* #Specification: ioctl / UMSDOS_UNLINK_EMD
-                * The umsdos_dirent field of the struct umsdos_ioctl is used
-                * as is to remove an entry from the EMD of the directory.
-                * No validation is done (yet). The mode field is used
-                * to validate S_ISDIR or S_ISREG.
-                * 
-                * Return 0 if success.
-                */
-               struct umsdos_info info;
-
-               /* This makes sure info.entry and info in general
-                * is correctly initialised
-                */
-               memcpy (&info.entry, &data.umsdos_dirent,
-                       sizeof (data.umsdos_dirent));
-               umsdos_parse (data.umsdos_dirent.name,
-                               data.umsdos_dirent.name_len, &info);
-               ret = umsdos_delentry (dentry, &info,
-                               S_ISDIR (data.umsdos_dirent.mode));
-               if (ret) {
-                       printk(KERN_WARNING
-                               "umsdos_ioctl: delentry %s/%s failed, ret=%d\n",
-                               dentry->d_name.name, info.entry.name, ret);
-               }
-               goto out;
-       }
-       else if (cmd == UMSDOS_UNLINK_DOS) {
-               struct dentry *temp;
-
-               /* #Specification: ioctl / UMSDOS_UNLINK_DOS
-                * The dos_dirent field of the struct umsdos_ioctl is used to
-                * execute a msdos_unlink operation. The d_name and d_reclen
-                * fields are used.
-                * 
-                * Return 0 if success.
-                */
-               temp = umsdos_lookup_dentry(dentry, data.dos_dirent.d_name,
-                                               data.dos_dirent.d_reclen, 1);
-               ret = PTR_ERR(temp);
-               if (IS_ERR(temp))
-                       goto out;
-               ret = -ENOENT;
-               if (temp->d_inode) {
-                       ret = -EISDIR;
-                       if (!S_ISDIR(temp->d_inode->i_mode))
-                               ret = msdos_unlink (dir, temp);
-                       if (!ret)
-                               d_delete(temp);
-               }
-               dput (temp);
-               goto out;
-       }
-       else if (cmd == UMSDOS_RMDIR_DOS) {
-               struct dentry *temp;
-
-               /* #Specification: ioctl / UMSDOS_RMDIR_DOS
-                * The dos_dirent field of the struct umsdos_ioctl is used to
-                * execute a msdos_rmdir operation. The d_name and d_reclen
-                * fields are used.
-                * 
-                * Return 0 if success.
-                */
-               temp = umsdos_lookup_dentry(dentry, data.dos_dirent.d_name,
-                                           data.dos_dirent.d_reclen, 1);
-               ret = PTR_ERR(temp);
-               if (IS_ERR(temp))
-                       goto out;
-               ret = -ENOENT;
-               if (temp->d_inode) {
-                       ret = -ENOTDIR;
-                       if (S_ISDIR(temp->d_inode->i_mode))
-                               ret = msdos_rmdir (dir, temp);
-                       if (!ret)
-                               d_delete(temp);
-               }
-               dput (temp);
-               goto out;
-
-       } else if (cmd == UMSDOS_STAT_DOS) {
-               /* #Specification: ioctl / UMSDOS_STAT_DOS
-                * The dos_dirent field of the struct umsdos_ioctl is
-                * used to execute a stat operation in the DOS directory.
-                * The d_name and d_reclen fields are used.
-                * 
-                * The following field of umsdos_ioctl.stat are filled.
-                * 
-                * st_ino,st_mode,st_size,st_atime,st_mtime,st_ctime,
-                * Return 0 if success.
-                */
-               struct dentry *dret;
-               struct inode *inode;
-
-               dret = umsdos_lookup_dentry(dentry, data.dos_dirent.d_name,
-                                           data.dos_dirent.d_reclen, 1);
-               ret = PTR_ERR(dret);
-               if (IS_ERR(dret))
-                       goto out;
-               ret = -ENOENT;
-               inode = dret->d_inode;
-               if (inode) {
-                       data.stat.st_ino = inode->i_ino;
-                       data.stat.st_mode = inode->i_mode;
-                       data.stat.st_size = inode->i_size;
-                       data.stat.st_atime = inode->i_atime;
-                       data.stat.st_ctime = inode->i_ctime;
-                       data.stat.st_mtime = inode->i_mtime;
-                       ret = -EFAULT;
-                       if (!copy_to_user (&idata->stat, &data.stat, 
-                                               sizeof (data.stat)))
-                               ret = 0;
-               }
-               dput(dret);
-               goto out;
-       }
-       else if (cmd == UMSDOS_DOS_SETUP) {
-               /* #Specification: ioctl / UMSDOS_DOS_SETUP
-                * The UMSDOS_DOS_SETUP ioctl allow changing the
-                * default permission of the MS-DOS filesystem driver
-                * on the fly.  The MS-DOS driver applies global permissions
-                * to every file and directory. Normally these permissions
-                * are controlled by a mount option. This is not
-                * available for root partition, so a special utility
-                * (umssetup) is provided to do this, normally in
-                * /etc/rc.local.
-                * 
-                * Be aware that this applies ONLY to MS-DOS directories
-                * (those without EMD --linux-.---). Umsdos directory
-                * have independent (standard) permission for each
-                * and every file.
-                * 
-                * The field umsdos_dirent provide the information needed.
-                * umsdos_dirent.uid and gid sets the owner and group.
-                * umsdos_dirent.mode set the permissions flags.
-                */
-               dir->i_sb->u.msdos_sb.options.fs_uid = data.umsdos_dirent.uid;
-               dir->i_sb->u.msdos_sb.options.fs_gid = data.umsdos_dirent.gid;
-               dir->i_sb->u.msdos_sb.options.fs_fmask =
-                       dir->i_sb->u.msdos_sb.options.fs_dmask =
-                               data.umsdos_dirent.mode;
-               ret = 0;
-       }
-out:
-       Printk (("ioctl %d, returning %d\n", cmd, ret));
-       return ret;
-}
diff --git a/fs/umsdos/mangle.c b/fs/umsdos/mangle.c
deleted file mode 100644 (file)
index 0451123..0000000
+++ /dev/null
@@ -1,522 +0,0 @@
-/*
- *  linux/fs/umsdos/mangle.c
- *
- *      Written 1993 by Jacques Gelinas 
- *
- * Control the mangling of file name to fit msdos name space.
- * Many optimisations by GLU == dglaude@is1.vub.ac.be (Glaude David)
- */
-
-#include <linux/errno.h>
-#include <linux/string.h>
-#include <linux/kernel.h>
-#include <linux/umsdos_fs.h>
-
-/* (This file is used outside of the kernel) */
-#ifndef __KERNEL__
-#define KERN_WARNING
-#endif
-
-/*
- * Complete the mangling of the MSDOS fake name
- * based on the position of the entry in the EMD file.
- * 
- * Simply complete the job of umsdos_parse; fill the extension.
- * 
- * Beware that info->f_pos must be set.
- */
-void umsdos_manglename (struct umsdos_info *info)
-{
-       if (info->msdos_reject) {
-               /* #Specification: file name / non MSDOS conforming / mangling
-                * Each non MSDOS conforming file has a special extension
-                * build from the entry position in the EMD file.
-                * 
-                * This number is then transform in a base 32 number, where
-                * each digit is expressed like hexadecimal number, using
-                * digit and letter, except it uses 22 letters from 'a' to 'v'.
-                * The number 32 comes from 2**5. It is faster to split a binary
-                * number using a base which is a power of two. And I was 32
-                * when I started this project. Pick your answer :-) .
-                * 
-                * If the result is '0', it is replace with '_', simply
-                * to make it odd.
-                * 
-                * This is true for the first two character of the extension.
-                * The last one is taken from a list of odd character, which
-                * are:
-                * 
-                * { } ( ) ! ` ^ & @
-                * 
-                * With this scheme, we can produce 9216 ( 9* 32 * 32)
-                * different extensions which should not clash with any useful
-                * extension already popular or meaningful. Since most directory
-                * have much less than 32 * 32 files in it, the first character
-                * of the extension of any mangled name will be {.
-                * 
-                * Here are the reason to do this (this kind of mangling).
-                * 
-                * -The mangling is deterministic. Just by the extension, we
-                * are able to locate the entry in the EMD file.
-                * 
-                * -By keeping to beginning of the file name almost unchanged,
-                * we are helping the MSDOS user.
-                * 
-                * -The mangling produces names not too ugly, so an msdos user
-                * may live with it (remember it, type it, etc...).
-                * 
-                * -The mangling produces names ugly enough so no one will
-                * ever think of using such a name in real life. This is not
-                * fool proof. I don't think there is a total solution to this.
-                */
-               int entry_num;
-               char *pt = info->fake.fname + info->fake.len;
-               /* lookup for encoding the last character of the extension 
-                * It contains valid character after the ugly one to make sure 
-                * even if someone overflows the 32 * 32 * 9 limit, it still 
-                * does something 
-                */
-#define SPECIAL_MANGLING '{','}','(',')','!','`','^','&','@'
-               static char lookup3[] =
-               {
-                       SPECIAL_MANGLING,
-               /* This is the start of lookup12 */
-                       '_', '1', '2', '3', '4', '5', '6', '7', '8', '9',
-                       'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o',
-                       'p', 'q', 'r', 's', 't', 'u', 'v'
-               };
-
-#define lookup12 (lookup3+9)
-               entry_num = info->f_pos / UMSDOS_REC_SIZE;
-               if (entry_num > (9* 32 * 32)){
-                       printk (KERN_WARNING "UMSDOS: more than 9216 files in a directory.\n"
-                               "This may break the mangling strategy.\n"
-                               "Not a killer problem. See doc.\n");
-               }
-               *pt++ = '.';
-               *pt++ = lookup3 [(entry_num >> 10) & 31];
-               *pt++ = lookup12[(entry_num >> 5) & 31];
-               *pt++ = lookup12[entry_num & 31];
-               *pt = '\0';             /* help doing printk */ 
-               info->fake.len += 4;
-               info->msdos_reject = 0;         /* Avoid mangling twice */
-       }
-}
-
-/*
- * Evaluate the record size needed to store of name of len character.
- * The value returned is a multiple of UMSDOS_REC_SIZE.
- */
-int umsdos_evalrecsize (int len)
-{
-       struct umsdos_dirent dirent;
-       int nbrec = 1 + ((len - 1 + (dirent.name - (char *) &dirent))
-                        / UMSDOS_REC_SIZE);
-
-       return nbrec * UMSDOS_REC_SIZE;
-       /*
-        * GLU        This should be inlined or something to speed it up to the max.
-        * GLU        nbrec is absolutely not needed to return the value.
-        */
-}
-#ifdef TEST
-int umsdos_evalrecsize_old (int len)
-{
-       struct umsdos_dirent dirent;
-       int size = len + (dirent.name - (char *) &dirent);
-       int nbrec = size / UMSDOS_REC_SIZE;
-       int extra = size % UMSDOS_REC_SIZE;
-
-       if (extra > 0)
-               nbrec++;
-       return nbrec * UMSDOS_REC_SIZE;
-}
-#endif
-
-
-/*
- * Fill the struct info with the full and msdos name of a file
- * Return 0 if all is OK, a negative error code otherwise.
- */
-int umsdos_parse (
-                        const char *fname,
-                        int len,
-                        struct umsdos_info *info)
-{
-       int ret = -ENAMETOOLONG;
-
-       /* #Specification: file name / too long
-        * If a file name exceed UMSDOS maxima, the file name is silently
-        * truncated. This makes it conformant with the other file system
-        * of Linux (minix and ext2 at least).
-        */
-       if (len > UMSDOS_MAXNAME)
-               len = UMSDOS_MAXNAME;
-       {
-               const char *firstpt = NULL;     /* First place we saw a "." in fname */
-
-               /* #Specification: file name / non MSDOS conforming / base length 0
-                * file names beginning with a period '.' are invalid for MS-DOS.
-                * It needs absolutely a base name. So the file name is mangled
-                */
-               int ivldchar = fname[0] == '.';         /* At least one invalid character */
-               int msdos_len = len;
-               int base_len;
-
-               /*
-                * cardinal_per_size tells if there exists at least one
-                * DOS pseudo device on length n.  See the test below.
-                */
-               static const char cardinal_per_size[9] =
-               {
-                       0, 0, 0, 1, 1, 0, 1, 0, 1
-               };
-
-               /*
-                * lkp translate all character to acceptable character (for DOS).
-                * When lkp[n] == n, it means also it is an acceptable one.
-                * So it serves both as a flag and as a translator.
-                */
-               static char lkp[256];
-               static char is_init;
-
-               if (!is_init) {
-                       /*
-                        * Initialisation of the array is easier and less error
-                         * prone like this.
-                        */
-                       int i;
-                       static const char *spc = "\"*+,/:;<=>?[\\]|~";
-
-                       is_init = 1;
-                       for (i = 0; i <= 32; i++)
-                               lkp[i] = '#';
-                       for (i = 33; i < 'A'; i++)
-                               lkp[i] = (char) i;
-                       for (i = 'A'; i <= 'Z'; i++)
-                               lkp[i] = (char) (i + ('a' - 'A'));
-                       for (i = 'Z' + 1; i < 127; i++)
-                               lkp[i] = (char) i;
-                       for (i = 128; i < 256; i++)
-                               lkp[i] = '#';
-
-                       lkp['.'] = '_';
-                       while (*spc != '\0')
-                               lkp[(unsigned char) (*spc++)] = '#';
-               }
-               /*  GLU
-                * File names longer than 8+'.'+3 are invalid for MS-DOS,
-                * so the file name is to be mangled--no further test is needed.
-                * This speeds up handling of long names.
-                * The position of the last point is no more necessary anyway.
-                */
-               if (len <= (8 + 1 + 3)) {
-                       const char *pt = fname;
-                       const char *endpt = fname + len;
-
-                       while (pt < endpt) {
-                               if (*pt == '.') {
-                                       if (firstpt != NULL) {
-                                               /* 2 . in a file name. Reject */
-                                               ivldchar = 1;
-                                               break;
-                                       } else {
-                                               int extlen = (int) (endpt - pt);
-
-                                               firstpt = pt;
-                                               if (firstpt - fname > 8) {
-                                                       /* base name longer than 8: reject */
-                                                       ivldchar = 1;
-                                                       break;
-                                               } else if (extlen > 4) {
-                                                       /* Extension longer than 4 (including .): reject */
-                                                       ivldchar = 1;
-                                                       break;
-                                               } else if (extlen == 1) {
-                                                       /* #Specification: file name / non MSDOS conforming / last char == .
-                                                        * If the last character of a file name is
-                                                        * a period, mangling is applied. MS-DOS does
-                                                        * not support those file names.
-                                                        */
-                                                       ivldchar = 1;
-                                                       break;
-                                               } else if (extlen == 4) {
-                                                       /* #Specification: file name / non MSDOS conforming / mangling clash
-                                                        * To avoid clash with    the umsdos mangling, any file
-                                                        * with a special character as the first character
-                                                        * of the extension will be mangled. This solves the
-                                                        * following problem:
-                                                        * 
-                                                        * #
-                                                        * touch FILE
-                                                        * # FILE is invalid for DOS, so mangling is applied
-                                                        * # file.{_1 is created in the DOS directory
-                                                        * touch file.{_1
-                                                        * # To UMSDOS file point to a single DOS entry.
-                                                        * # So file.{_1 has to be mangled.
-                                                        * #
-                                                        */
-                                                       static char special[] =
-                                                       {
-                                                               SPECIAL_MANGLING, '\0'
-                                                       };
-
-                                                       if (strchr (special, firstpt[1]) != NULL) {
-                                                               ivldchar = 1;
-                                                               break;
-                                                       }
-                                               }
-                                       }
-                               } else if (lkp[(unsigned char) (*pt)] != *pt) {
-                                       ivldchar = 1;
-                                       break;
-                               }
-                               pt++;
-                       }
-               } else {
-                       ivldchar = 1;
-               }
-               if (ivldchar
-                   || (firstpt == NULL && len > 8)
-                   || (len == UMSDOS_EMD_NAMELEN
-                       && memcmp (fname, UMSDOS_EMD_FILE, UMSDOS_EMD_NAMELEN) == 0)) {
-                       /* #Specification: file name / --linux-.---
-                        * The name of the EMD file --linux-.--- is map to a mangled
-                        * name. So UMSDOS does not restrict its use.
-                        */
-                       /* #Specification: file name / non MSDOS conforming / mangling
-                        * Non MSDOS conforming file names must use some alias to fit
-                        * in the MSDOS name space.
-                        * 
-                        * The strategy is simple. The name is simply truncated to
-                        * 8 char. points are replace with underscore and a
-                        * number is given as an extension. This number correspond
-                        * to the entry number in the EMD file. The EMD file
-                        * only need to carry the real name.
-                        * 
-                        * Upper case is also converted to lower case.
-                        * Control character are converted to #.
-                        * Spaces are converted to #.
-                        * The following characters are also converted to #.
-                        * #
-                        * " * + , / : ; < = > ? [ \ ] | ~
-                        * #
-                        * 
-                        * Sometimes the problem is not in MS-DOS itself but in
-                        * command.com.
-                        */
-                       int i;
-                       char *pt = info->fake.fname;
-
-                       base_len = msdos_len = (msdos_len > 8) ? 8 : msdos_len;
-                       /*
-                        * There is no '.' any more so we know for a fact that
-                        * the base length is the length.
-                        */
-                       memcpy (info->fake.fname, fname, msdos_len);
-                       for (i = 0; i < msdos_len; i++, pt++)
-                               *pt = lkp[(unsigned char) (*pt)];
-                       *pt = '\0';     /* GLU  We force null termination. */
-                       info->msdos_reject = 1;
-                       /*
-                        * The numeric extension is added only when we know
-                        * the position in the EMD file, in umsdos_newentry(),
-                        * umsdos_delentry(), and umsdos_findentry().
-                        * See umsdos_manglename().
-                        */
-               } else {
-                       /* Conforming MSDOS file name */
-                       strncpy (info->fake.fname, fname, len);
-                       info->msdos_reject = 0;
-                       base_len = firstpt != NULL ? (int) (firstpt - fname) : len;
-               }
-               if (cardinal_per_size[base_len]) {
-                       /* #Specification: file name / MSDOS devices / mangling
-                        * To avoid unreachable file from MS-DOS, any MS-DOS conforming
-                        * file with a basename equal to one of the MS-DOS pseudo
-                        * devices will be mangled.
-                        * 
-                        * If a file such as "prn" was created, it would be unreachable
-                        * under MS-DOS because "prn" is assumed to be the printer, even
-                        * if the file does have an extension.
-                        * 
-                        * Since the extension is unimportant to MS-DOS, we must patch
-                        * the basename also. We simply insert a minus '-'. To avoid
-                        * conflict with valid file with a minus in front (such as
-                        * "-prn"), we add an mangled extension like any other
-                        * mangled file name.
-                        * 
-                        * Here is the list of DOS pseudo devices:
-                        * 
-                        * #
-                        * "prn","con","aux","nul",
-                        * "lpt1","lpt2","lpt3","lpt4",
-                        * "com1","com2","com3","com4",
-                        * "clock$"
-                        * #
-                        * 
-                        * and some standard ones for common DOS programs
-                        * 
-                        * "emmxxxx0","xmsxxxx0","setverxx"
-                        * 
-                        * (Thanks to Chris Hall <cah17@phoenix.cambridge.ac.uk>
-                        * for pointing these out to me).
-                        * 
-                        * Is there one missing?
-                        */
-                       /* This table must be ordered by length */
-                       static const char *tbdev[] =
-                       {
-                               "prn", "con", "aux", "nul",
-                               "lpt1", "lpt2", "lpt3", "lpt4",
-                               "com1", "com2", "com3", "com4",
-                               "clock$",
-                               "emmxxxx0", "xmsxxxx0", "setverxx"
-                       };
-
-                       /* Tell where to find in tbdev[], the first name of */
-                       /* a certain length */
-                       static const char start_ind_dev[9] =
-                       {
-                               0, 0, 0, 4, 12, 12, 13, 13, 16
-                       };
-                       char basen[9];
-                       int i;
-
-                       for (i = start_ind_dev[base_len - 1]; i < start_ind_dev[base_len]; i++) {
-                               if (memcmp (info->fake.fname, tbdev[i], base_len) == 0) {
-                                       memcpy (basen, info->fake.fname, base_len);
-                                       basen[base_len] = '\0';         /* GLU  We force null termination. */
-                                       /*
-                                        * GLU        We do that only if necessary; we try to do the
-                                        * GLU        simple thing in the usual circumstance. 
-                                        */
-                                       info->fake.fname[0] = '-';
-                                       strcpy (info->fake.fname + 1, basen);   /* GLU  We already guaranteed a null would be at the end. */
-                                       msdos_len = (base_len == 8) ? 8 : base_len + 1;
-                                       info->msdos_reject = 1;
-                                       break;
-                               }
-                       }
-               }
-               info->fake.fname[msdos_len] = '\0';     /* Help doing printk */
-               /* GLU      This zero should (always?) be there already. */
-               info->fake.len = msdos_len;
-               /* Why not use info->fake.len everywhere? Is it longer?
-                 */
-               memcpy (info->entry.name, fname, len);
-               info->entry.name[len] = '\0';   /* for printk */
-               info->entry.name_len = len;
-               ret = 0;
-       }
-       /*
-        * Evaluate how many records are needed to store this entry.
-        */
-       info->recsize = umsdos_evalrecsize (len);
-       return ret;
-}
-
-#ifdef TEST
-
-struct MANG_TEST {
-       char *fname;            /* Name to validate */
-       int msdos_reject;       /* Expected msdos_reject flag */
-       char *msname;           /* Expected msdos name */
-};
-
-struct MANG_TEST tb[] =
-{
-       "hello", 0, "hello",
-       "hello.1", 0, "hello.1",
-       "hello.1_", 0, "hello.1_",
-       "prm", 0, "prm",
-
-#ifdef PROPOSITION
-       "HELLO", 1, "hello",
-       "Hello.1", 1, "hello.1",
-       "Hello.c", 1, "hello.c",
-#else
-/*
- * I find the three examples below very unfortunate.  I propose to
- * convert them to lower case in a quick preliminary pass, then test
- * whether there are other troublesome characters.  I have not made
- * this change, because it is not easy, but I wanted to mention the 
- * principle.  Obviously something like that would increase the chance
- * of collisions, for example between "HELLO" and "Hello", but these
- * can be treated elsewhere along with the other collisions.
- */
-
-       "HELLO", 1, "hello",
-       "Hello.1", 1, "hello_1",
-       "Hello.c", 1, "hello_c",
-#endif
-
-       "hello.{_1", 1, "hello_{_",
-       "hello\t", 1, "hello#",
-       "hello.1.1", 1, "hello_1_",
-       "hel,lo", 1, "hel#lo",
-       "Salut.Tu.vas.bien?", 1, "salut_tu",
-       ".profile", 1, "_profile",
-       ".xv", 1, "_xv",
-       "toto.", 1, "toto_",
-       "clock$.x", 1, "-clock$",
-       "emmxxxx0", 1, "-emmxxxx",
-       "emmxxxx0.abcd", 1, "-emmxxxx",
-       "aux", 1, "-aux",
-       "prn", 1, "-prn",
-       "prn.abc", 1, "-prn",
-       "PRN", 1, "-prn",
-  /* 
-   * GLU        WARNING:  the results of these are different with my version
-   * GLU        of mangling compared to the original one.
-   * GLU        CAUSE:  the manner of calculating the baselen variable.
-   * GLU                For you they are always 3.
-   * GLU                For me they are respectively 7, 8, and 8.
-
-   */
-       "PRN.abc", 1, "prn_abc",
-       "Prn.abcd", 1, "prn_abcd",
-       "prn.abcd", 1, "prn_abcd",
-       "Prn.abcdefghij", 1, "prn_abcd"
-};
-
-int main (int argc, char *argv[])
-{
-       int i, rold, rnew;
-
-       printf ("Testing the umsdos_parse.\n");
-       for (i = 0; i < sizeof (tb) / sizeof (tb[0]); i++) {
-               struct MANG_TEST *pttb = tb + i;
-               struct umsdos_info info;
-               int ok = umsdos_parse (pttb->fname, strlen (pttb->fname), &info);
-
-               if (strcmp (info.fake.fname, pttb->msname) != 0) {
-                       printf ("**** %s -> ", pttb->fname);
-                       printf ("%s <> %s\n", info.fake.fname, pttb->msname);
-               } else if (info.msdos_reject != pttb->msdos_reject) {
-                       printf ("**** %s -> %s ", pttb->fname, pttb->msname);
-                       printf ("%d <> %d\n", info.msdos_reject, pttb->msdos_reject);
-               } else {
-                       printf ("     %s -> %s %d\n", pttb->fname, pttb->msname
-                               ,pttb->msdos_reject);
-               }
-       }
-       printf ("Testing the new umsdos_evalrecsize.");
-       for (i = 0; i < UMSDOS_MAXNAME; i++) {
-               rnew = umsdos_evalrecsize (i);
-               rold = umsdos_evalrecsize_old (i);
-               if (!(i % UMSDOS_REC_SIZE)) {
-                       printf ("\n%d:\t", i);
-               }
-               if (rnew != rold) {
-                       printf ("**** %d newres: %d != %d \n", i, rnew, rold);
-               } else {
-                       printf (".");
-               }
-       }
-       printf ("\nEnd of Testing.\n");
-
-       return 0;
-}
-
-#endif
diff --git a/fs/umsdos/namei.c b/fs/umsdos/namei.c
deleted file mode 100644 (file)
index 2d8a64a..0000000
+++ /dev/null
@@ -1,1124 +0,0 @@
-/*
- *  linux/fs/umsdos/namei.c
- *
- *      Written 1993 by Jacques Gelinas 
- *      Inspired from linux/fs/msdos/... by Werner Almesberger
- *
- * Maintain and access the --linux alternate directory file.
- */
- /*
-  * You are in the maze of twisted functions - half of them shouldn't
-  * be here...
-  */
-
-#include <linux/errno.h>
-#include <linux/kernel.h>
-#include <linux/time.h>
-#include <linux/types.h>
-#include <linux/fcntl.h>
-#include <linux/stat.h>
-#include <linux/string.h>
-#include <linux/msdos_fs.h>
-#include <linux/umsdos_fs.h>
-#include <linux/slab.h>
-
-#define UMSDOS_DIR_LOCK
-
-#ifdef UMSDOS_DIR_LOCK
-
-static inline void u_sleep_on (struct inode *dir)
-{
-       sleep_on (&UMSDOS_I(dir)->dir_info.p);
-}
-
-static inline void u_wake_up (struct inode *dir)
-{
-       wake_up (&UMSDOS_I(dir)->dir_info.p);
-}
-
-/*
- * Wait for creation exclusivity.
- * Return 0 if the dir was already available.
- * Return 1 if a wait was necessary.
- * When 1 is return, it means a wait was done. It does not
- * mean the directory is available.
- */
-static int umsdos_waitcreate (struct inode *dir)
-{
-       int ret = 0;
-
-       if (UMSDOS_I(dir)->dir_info.creating
-           && UMSDOS_I(dir)->dir_info.pid != current->pid) {
-               PRINTK (("creating && dir_info.pid=%lu, current->pid=%u\n", UMSDOS_I(dir)->dir_info.pid, current->pid));
-               u_sleep_on (dir);
-               ret = 1;
-       }
-       return ret;
-}
-
-/*
- * Wait for any lookup process to finish
- */
-static void umsdos_waitlookup (struct inode *dir)
-{
-       while (UMSDOS_I(dir)->dir_info.looking) {
-               u_sleep_on (dir);
-       }
-}
-
-/*
- * Lock all other process out of this directory.
- */
-/* #Specification: file creation / not atomic
- * File creation is a two step process. First we create (allocate)
- * an entry in the EMD file and then (using the entry offset) we
- * build a unique name for MSDOS. We create this name in the msdos
- * space.
- * 
- * We have to use semaphore (sleep_on/wake_up) to prevent lookup
- * into a directory when we create a file or directory and to
- * prevent creation while a lookup is going on. Since many lookup
- * may happen at the same time, the semaphore is a counter.
- * 
- * Only one creation is allowed at the same time. This protection
- * may not be necessary. The problem arise mainly when a lookup
- * or a readdir is done while a file is partially created. The
- * lookup process see that as a "normal" problem and silently
- * erase the file from the EMD file. Normal because a file
- * may be erased during a MSDOS session, but not removed from
- * the EMD file.
- * 
- * The locking is done on a directory per directory basis. Each
- * directory inode has its wait_queue.
- * 
- * For some operation like hard link, things even get worse. Many
- * creation must occur at once (atomic). To simplify the design
- * a process is allowed to recursively lock the directory for
- * creation. The pid of the locking process is kept along with
- * a counter so a second level of locking is granted or not.
- */
-void umsdos_lockcreate (struct inode *dir)
-{
-       /*
-        * Wait for any creation process to finish except
-        * if we (the process) own the lock
-        */
-       while (umsdos_waitcreate (dir) != 0);
-       UMSDOS_I(dir)->dir_info.creating++;
-       UMSDOS_I(dir)->dir_info.pid = current->pid;
-       umsdos_waitlookup (dir);
-}
-
-/*
- * Lock all other process out of those two directories.
- */
-static void umsdos_lockcreate2 (struct inode *dir1, struct inode *dir2)
-{
-       /*
-        * We must check that both directory are available before
-        * locking anyone of them. This is to avoid some deadlock.
-        * Thanks to dglaude@is1.vub.ac.be (GLAUDE DAVID) for pointing
-        * this to me.
-        */
-       while (1) {
-               if (umsdos_waitcreate (dir1) == 0
-                   && umsdos_waitcreate (dir2) == 0) {
-                       /* We own both now */
-                       UMSDOS_I(dir1)->dir_info.creating++;
-                       UMSDOS_I(dir1)->dir_info.pid = current->pid;
-                       UMSDOS_I(dir2)->dir_info.creating++;
-                       UMSDOS_I(dir2)->dir_info.pid = current->pid;
-                       break;
-               }
-       }
-       umsdos_waitlookup (dir1);
-       umsdos_waitlookup (dir2);
-}
-
-/*
- * Wait until creation is finish in this directory.
- */
-void umsdos_startlookup (struct inode *dir)
-{
-       while (umsdos_waitcreate (dir) != 0);
-       UMSDOS_I(dir)->dir_info.looking++;
-}
-
-/*
- * Unlock the directory.
- */
-void umsdos_unlockcreate (struct inode *dir)
-{
-       UMSDOS_I(dir)->dir_info.creating--;
-       if (UMSDOS_I(dir)->dir_info.creating < 0) {
-               printk ("UMSDOS: UMSDOS_I(dir)->dir_info.creating < 0: %d"
-                       ,UMSDOS_I(dir)->dir_info.creating);
-       }
-       u_wake_up (dir);
-}
-
-/*
- * Tell directory lookup is over.
- */
-void umsdos_endlookup (struct inode *dir)
-{
-       UMSDOS_I(dir)->dir_info.looking--;
-       if (UMSDOS_I(dir)->dir_info.looking < 0) {
-               printk ("UMSDOS: UMSDOS_I(dir)->dir_info.looking < 0: %d"
-                       ,UMSDOS_I(dir)->dir_info.looking);
-       }
-       u_wake_up (dir);
-}
-
-#else
-static void umsdos_lockcreate (struct inode *dir)
-{
-}
-static void umsdos_lockcreate2 (struct inode *dir1, struct inode *dir2)
-{
-}
-void umsdos_startlookup (struct inode *dir)
-{
-}
-static void umsdos_unlockcreate (struct inode *dir)
-{
-}
-void umsdos_endlookup (struct inode *dir)
-{
-}
-
-#endif
-
-static int umsdos_nevercreat (struct inode *dir, struct dentry *dentry,
-                               int errcod)
-{
-       int ret = 0;
-
-       if (umsdos_is_pseudodos (dir, dentry)) {
-               /* #Specification: pseudo root / any file creation /DOS
-                * The pseudo sub-directory /DOS can't be created!
-                * EEXIST is returned.
-                * 
-                * The pseudo sub-directory /DOS can't be removed!
-                * EPERM is returned.
-                */
-               ret = errcod;
-       }
-       return ret;
-}
-
-/*
- * Add a new file (ordinary or special) into the alternate directory.
- * The file is added to the real MSDOS directory. If successful, it
- * is then added to the EMD file.
- * 
- * Return the status of the operation. 0 mean success.
- *
- * #Specification: create / file exists in DOS
- * Here is a situation: we are trying to create a file with
- * UMSDOS. The file is unknown to UMSDOS but already
- * exists in the DOS directory.
- * 
- * Here is what we are NOT doing:
- * 
- * We could silently assume that everything is fine
- * and allows the creation to succeed.
- * 
- * It is possible not all files in the partition
- * are meant to be visible from linux. By trying to create
- * those file in some directory, one user may get access
- * to those file without proper permissions. Looks like
- * a security hole to me. Off course sharing a file system
- * with DOS is some kind of security hole :-)
- * 
- * So ?
- * 
- * We return EEXIST in this case.
- * The same is true for directory creation.
- */
-static int umsdos_create_any (struct inode *dir, struct dentry *dentry,
-                               int mode, dev_t rdev, char flags)
-{
-       struct dentry *fake;
-       struct inode *inode;
-       int ret;
-       struct umsdos_info info;
-
-       ret = umsdos_nevercreat (dir, dentry, -EEXIST);
-       if (ret)
-               goto out;
-
-       ret = umsdos_parse (dentry->d_name.name, dentry->d_name.len, &info);
-       if (ret)
-               goto out;
-
-       info.entry.mode = mode;
-       info.entry.rdev = rdev;
-       info.entry.flags = flags;
-       info.entry.uid = current->fsuid;
-       info.entry.gid = (dir->i_mode & S_ISGID) ? dir->i_gid : current->fsgid;
-       info.entry.ctime = info.entry.atime = info.entry.mtime = get_seconds();
-       info.entry.nlink = 1;
-       ret = umsdos_newentry (dentry->d_parent, &info);
-       if (ret)
-               goto out;
-
-       /* do a real lookup to get the short name dentry */
-       fake = umsdos_covered(dentry->d_parent, info.fake.fname, info.fake.len);
-       ret = PTR_ERR(fake);
-       if (IS_ERR(fake))
-               goto out_remove;
-
-       /* should not exist yet ... */
-       ret = -EEXIST;
-       if (fake->d_inode)
-               goto out_remove_dput;
-
-       ret = msdos_create (dir, fake, S_IFREG | 0777, NULL);
-       if (ret)
-               goto out_remove_dput;
-
-       inode = fake->d_inode;
-       atomic_inc(&inode->i_count);
-       d_instantiate (dentry, inode);
-       dput(fake);
-       if (atomic_read(&inode->i_count) > 1) {
-               printk(KERN_WARNING
-                       "umsdos_create_any: %s/%s, ino=%ld, icount=%d??\n",
-                       dentry->d_parent->d_name.name, dentry->d_name.name,
-                       inode->i_ino, atomic_read(&inode->i_count));
-       }
-       umsdos_lookup_patch_new(dentry, &info);
-
-out:
-       return ret;
-
-       /* Creation failed ... remove the EMD entry */
-out_remove_dput:
-       dput(fake);
-out_remove:
-       if (ret == -EEXIST)
-               printk(KERN_WARNING "UMSDOS: out of sync, deleting %s/%s\n",
-                       dentry->d_parent->d_name.name, info.fake.fname);
-       umsdos_delentry (dentry->d_parent, &info, S_ISDIR (info.entry.mode));
-       goto out;
-}
-
-/*
- * Add a new file into the alternate directory.
- * The file is added to the real MSDOS directory. If successful, it
- * is then added to the EMD file.
- * 
- * Return the status of the operation. 0 mean success.
- */
-int UMSDOS_create (struct inode *dir, struct dentry *dentry, int mode, struct nameidata *nd)
-{
-       return umsdos_create_any (dir, dentry, mode, 0, 0);
-}
-
-
-/*
- * Initialise the new_entry from the old for a rename operation.
- * (Only useful for umsdos_rename_f() below).
- */
-static void umsdos_ren_init (struct umsdos_info *new_info,
-                            struct umsdos_info *old_info)
-{
-       new_info->entry.mode = old_info->entry.mode;
-       new_info->entry.rdev = old_info->entry.rdev;
-       new_info->entry.uid = old_info->entry.uid;
-       new_info->entry.gid = old_info->entry.gid;
-       new_info->entry.ctime = old_info->entry.ctime;
-       new_info->entry.atime = old_info->entry.atime;
-       new_info->entry.mtime = old_info->entry.mtime;
-       new_info->entry.flags = old_info->entry.flags;
-       new_info->entry.nlink = old_info->entry.nlink;
-}
-
-/*
- * Rename a file (move) in the file system.
- */
-static int umsdos_rename_f (struct inode *old_dir, struct dentry *old_dentry,
-                           struct inode *new_dir, struct dentry *new_dentry,
-                           int flags)
-{
-       struct inode *old_inode = old_dentry->d_inode;
-       struct dentry *old, *new, *old_emd;
-       int err, ret;
-       struct umsdos_info old_info;
-       struct umsdos_info new_info;
-
-       ret = -EPERM;
-       err = umsdos_parse (old_dentry->d_name.name,
-                               old_dentry->d_name.len, &old_info);
-       if (err)
-               goto out;
-       err = umsdos_parse (new_dentry->d_name.name,
-                               new_dentry->d_name.len, &new_info);
-       if (err)
-               goto out;
-
-       /* Get the EMD dentry for the old parent */
-       old_emd = umsdos_get_emd_dentry(old_dentry->d_parent);
-       ret = PTR_ERR(old_emd);
-       if (IS_ERR(old_emd))
-               goto out;
-
-       umsdos_lockcreate2 (old_dir, new_dir);
-
-       ret = umsdos_findentry(old_emd->d_parent, &old_info, 0);
-       if (ret)
-               goto out_unlock;
-
-       err = umsdos_findentry(new_dentry->d_parent, &new_info, 0);
-       if (err == 0) {
-               /* check whether it _really_ exists ... */
-               ret = -EEXIST;
-               if (new_dentry->d_inode)
-                       goto out_unlock;
-
-               /* bogus lookup? complain and fix up the EMD ... */
-               printk(KERN_WARNING
-                       "umsdos_rename_f: entry %s/%s exists, inode NULL??\n",
-                       new_dentry->d_parent->d_name.name, new_info.entry.name);
-               err = umsdos_delentry(new_dentry->d_parent, &new_info,
-                                       S_ISDIR(new_info.entry.mode));
-       }
-
-       umsdos_ren_init (&new_info, &old_info);
-       if (flags)
-               new_info.entry.flags = flags;
-       ret = umsdos_newentry (new_dentry->d_parent, &new_info);
-       if (ret)
-               goto out_unlock;
-
-       /* If we're moving a hardlink, drop it first */
-       if (old_info.entry.flags & UMSDOS_HLINK) {
-               d_drop(old_dentry);
-       }
-
-       old = umsdos_covered(old_dentry->d_parent, old_info.fake.fname, 
-                                       old_info.fake.len);
-       ret = PTR_ERR(old);
-       if (IS_ERR(old))
-               goto out_unlock;
-       /* make sure it's the same inode! */
-       ret = -ENOENT;
-       /*
-        * note: for hardlinks they will be different!
-        *  old_inode will contain inode of .LINKxxx file containing data, and
-        *  old->d_inode will contain inode of file containing path to .LINKxxx file
-        */
-       if (!(old_info.entry.flags & UMSDOS_HLINK)) {
-               if (old->d_inode != old_inode)
-                       goto out_dput;
-       }
-
-       new = umsdos_covered(new_dentry->d_parent, new_info.fake.fname, 
-                                       new_info.fake.len);
-       ret = PTR_ERR(new);
-       if (IS_ERR(new))
-               goto out_dput;
-
-       /* Do the msdos-level rename */
-       ret = msdos_rename (old_dir, old, new_dir, new);
-
-       dput(new);
-
-       /* If the rename failed, remove the new EMD entry */
-       if (ret != 0) {
-               umsdos_delentry (new_dentry->d_parent, &new_info,
-                                S_ISDIR (new_info.entry.mode));
-               goto out_dput;
-       }
-
-       /*
-        * Rename successful ... remove the old name from the EMD.
-        * Note that we use the EMD parent here, as the old dentry
-        * may have moved to a new parent ...
-        */
-       err = umsdos_delentry (old_emd->d_parent, &old_info,
-                               S_ISDIR (old_info.entry.mode));
-       if (err) {
-               /* Failed? Complain a bit, but don't fail the operation */
-               printk(KERN_WARNING 
-                       "umsdos_rename_f: delentry %s/%s failed, error=%d\n",
-                       old_emd->d_parent->d_name.name, old_info.entry.name,
-                       err);
-       }
-
-       /*
-        * Update f_pos so notify_change will succeed
-        * if the file was already in use.
-        */
-       umsdos_set_dirinfo_new(old_dentry, new_info.f_pos);
-
-       /* dput() the dentry if we haven't already */
-out_dput:
-       dput(old);
-
-out_unlock:
-       dput(old_emd);
-       umsdos_unlockcreate (old_dir);
-       umsdos_unlockcreate (new_dir);
-
-out:
-       Printk ((" _ret=%d\n", ret));
-       return ret;
-}
-
-/*
- * Setup a Symbolic link or a (pseudo) hard link
- * Return a negative error code or 0 if OK.
- */
-/* #Specification: symbolic links / strategy
- * A symbolic link is simply a file which holds a path. It is
- * implemented as a normal MSDOS file (not very space efficient :-()
- * 
- * I see two different ways to do this: One is to place the link data
- * in unused entries of the EMD file; the other is to have a separate
- * file dedicated to hold all symbolic links data.
- * 
- * Let's go for simplicity...
- */
-
-/*
- * AV. Should be called with dir->i_sem down.
- */
-static int umsdos_symlink_x (struct inode *dir, struct dentry *dentry,
-                       const char *symname, int mode, char flags)
-{
-       int ret, len;
-
-       ret = umsdos_create_any (dir, dentry, mode, 0, flags);
-       if (ret) {
-               printk(KERN_WARNING
-                       "umsdos_symlink: create failed, ret=%d\n", ret);
-               goto out;
-       }
-
-       len = strlen (symname) + 1;
-       ret = page_symlink(dentry->d_inode, symname, len);
-       if (ret < 0)
-               goto out_unlink;
-out:
-       return ret;
-
-out_unlink:
-       printk(KERN_WARNING "umsdos_symlink: write failed, unlinking\n");
-       UMSDOS_unlink (dir, dentry);
-       d_drop(dentry);
-       goto out;
-}
-
-/*
- * Setup a Symbolic link.
- * Return a negative error code or 0 if OK.
- */
-int UMSDOS_symlink ( struct inode *dir, struct dentry *dentry,
-                const char *symname)
-{
-       return umsdos_symlink_x (dir, dentry, symname, S_IFLNK | 0777, 0);
-}
-
-/*
- * Add a link to an inode in a directory
- */
-int UMSDOS_link (struct dentry *olddentry, struct inode *dir,
-                struct dentry *dentry)
-{
-       struct inode *oldinode = olddentry->d_inode;
-       struct inode *olddir = olddentry->d_parent->d_inode;
-       struct dentry *temp;
-       char *path;
-       unsigned long buffer;
-       int ret;
-       struct umsdos_info old_info;
-       struct umsdos_info hid_info;
-
-#ifdef UMSDOS_DEBUG_VERBOSE
-printk("umsdos_link: new %s/%s -> %s/%s\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, 
-olddentry->d_parent->d_name.name, olddentry->d_name.name);
-#endif
-       ret = -EPERM;
-       if (S_ISDIR (oldinode->i_mode))
-               goto out;
-
-       ret = umsdos_nevercreat (dir, dentry, -EPERM);
-       if (ret)
-               goto out;
-
-       ret = -ENOMEM;
-       buffer = get_zeroed_page(GFP_KERNEL);
-       if (!buffer)
-               goto out;
-
-       /*
-        * Lock the link parent if it's not the same directory.
-        */
-       ret = -EDEADLOCK;
-       if (olddir != dir) {
-               if (atomic_read(&olddir->i_sem.count) < 1)
-                       goto out_free;
-               down(&olddir->i_sem);
-       }
-
-       /*
-        * Parse the name and get the visible directory entry.
-        */
-       ret = umsdos_parse (olddentry->d_name.name, olddentry->d_name.len,
-                               &old_info);
-       if (ret)
-               goto out_unlock;
-       ret = umsdos_findentry (olddentry->d_parent, &old_info, 1);
-       if (ret) {
-printk("UMSDOS_link: %s/%s not in EMD, ret=%d\n",
-olddentry->d_parent->d_name.name, olddentry->d_name.name, ret);
-               goto out_unlock;
-       }
-
-       /*
-        * If the visible dentry is a pseudo-hardlink, the original
-        * file must be already hidden.
-        */
-       if (!(old_info.entry.flags & UMSDOS_HLINK)) {
-               int err;
-
-               /* create a hidden link name */
-               ret = umsdos_newhidden (olddentry->d_parent, &hid_info);
-               if (ret) {
-printk("umsdos_link: can't make hidden %s/%s, ret=%d\n",
-olddentry->d_parent->d_name.name, hid_info.entry.name, ret);
-                       goto out_unlock;
-               }
-
-               /*
-                * Make a dentry and rename the original file ...
-                */
-               temp = umsdos_lookup_dentry(olddentry->d_parent,
-                                               hid_info.entry.name,
-                                               hid_info.entry.name_len, 0); 
-               ret = PTR_ERR(temp);
-               if (IS_ERR(temp)) {
-printk("umsdos_link: lookup %s/%s failed, ret=%d\n",
-dentry->d_parent->d_name.name, hid_info.entry.name, ret);
-                       goto cleanup;
-               }
-               /* rename the link to the hidden location ... */
-               ret = umsdos_rename_f(olddir, olddentry, olddir, temp,
-                                       UMSDOS_HIDDEN);
-               d_move(olddentry, temp);
-               dput(temp);
-               if (ret) {
-printk("umsdos_link: rename to %s/%s failed, ret=%d\n",
-temp->d_parent->d_name.name, temp->d_name.name, ret);
-                       goto cleanup;
-               }
-               /* mark the inode as a hardlink */
-               UMSDOS_I(oldinode)->i_is_hlink = 1;
-
-               /*
-                * Capture the path to the hidden link.
-                */
-               path = umsdos_d_path(olddentry, (char *) buffer, PAGE_SIZE);
-Printk(("umsdos_link: hidden link path=%s\n", path));
-
-               /*
-                * Recreate a dentry for the original name and symlink it,
-                * then symlink the new dentry. Don't give up if one fails,
-                * or we'll lose the file completely!
-                *
-                * Note: this counts as the "original" reference, so we 
-                * don't increment i_nlink for this one.
-                */ 
-               temp = umsdos_lookup_dentry(olddentry->d_parent,
-                                               old_info.entry.name,
-                                               old_info.entry.name_len, 0); 
-               ret = PTR_ERR(temp);
-               if (!IS_ERR(temp)) {
-                       ret = umsdos_symlink_x (olddir, temp, path, 
-                                               S_IFREG | 0777, UMSDOS_HLINK);
-                       dput(temp);
-               }
-
-               /* This symlink increments i_nlink (see below.) */
-               err = umsdos_symlink_x (dir, dentry, path,
-                                       S_IFREG | 0777, UMSDOS_HLINK);
-               /* fold the two errors */
-               if (!ret)
-                       ret = err;
-               goto out_unlock;
-
-               /* creation failed ... remove the link entry */
-       cleanup:
-printk("umsdos_link: link failed, ret=%d, removing %s/%s\n",
-ret, olddentry->d_parent->d_name.name, hid_info.entry.name);
-               err = umsdos_delentry(olddentry->d_parent, &hid_info, 0);
-               goto out_unlock;
-       }
-
-Printk(("UMSDOS_link: %s/%s already hidden\n",
-olddentry->d_parent->d_name.name, olddentry->d_name.name));
-       /*
-        * The original file is already hidden, and we need to get 
-        * the dentry for its real name, not the visible name.
-        * N.B. make sure it's the hidden inode ...
-        */
-       if (!UMSDOS_I(oldinode)->i_is_hlink)
-               printk("UMSDOS_link: %s/%s hidden, ino=%ld not hlink??\n",
-                       olddentry->d_parent->d_name.name,
-                       olddentry->d_name.name, oldinode->i_ino);
-
-       /*
-        * In order to get the correct (real) inode, we just drop
-        * the original dentry.
-        */ 
-       d_drop(olddentry);
-Printk(("UMSDOS_link: hard link %s/%s, fake=%s\n",
-olddentry->d_parent->d_name.name, olddentry->d_name.name, old_info.fake.fname));
-
-       /* Do a real lookup to get the short name dentry */
-       temp = umsdos_covered(olddentry->d_parent, old_info.fake.fname, 
-                                       old_info.fake.len);
-       ret = PTR_ERR(temp);
-       if (IS_ERR(temp))
-               goto out_unlock;
-
-       /* now resolve the link ... */
-       temp = umsdos_solve_hlink(temp);
-       ret = PTR_ERR(temp);
-       if (IS_ERR(temp))
-               goto out_unlock;
-       path = umsdos_d_path(temp, (char *) buffer, PAGE_SIZE);
-       dput(temp);
-Printk(("umsdos_link: %s/%s already hidden, path=%s\n",
-olddentry->d_parent->d_name.name, olddentry->d_name.name, path));
-
-       /* finally we can symlink it ... */
-       ret = umsdos_symlink_x (dir, dentry, path, S_IFREG | 0777,UMSDOS_HLINK);
-
-out_unlock:
-       /* remain locked for the call to notify_change ... */
-       if (ret == 0) {
-               struct iattr newattrs;
-
-               /* Do a real lookup to get the short name dentry */
-               temp = umsdos_covered(olddentry->d_parent,
-                                       old_info.fake.fname,
-                                       old_info.fake.len);
-               ret = PTR_ERR(temp);
-               if (IS_ERR(temp))
-                       goto out_unlock2;
-
-               /* now resolve the link ... */
-               temp = umsdos_solve_hlink(temp);
-               ret = PTR_ERR(temp);
-               if (IS_ERR(temp))
-                       goto out_unlock2;
-
-
-#ifdef UMSDOS_PARANOIA
-if (!UMSDOS_I(oldinode)->i_is_hlink)
-printk("UMSDOS_link: %s/%s, ino=%ld, not marked as hlink!\n",
-olddentry->d_parent->d_name.name, olddentry->d_name.name, oldinode->i_ino);
-#endif
-               temp->d_inode->i_nlink++;
-Printk(("UMSDOS_link: linked %s/%s, ino=%ld, nlink=%d\n",
-olddentry->d_parent->d_name.name, olddentry->d_name.name,
-oldinode->i_ino, oldinode->i_nlink));
-               newattrs.ia_valid = 0;
-               ret = umsdos_notify_change_locked(temp, &newattrs);
-               if (ret == 0)
-                       mark_inode_dirty(temp->d_inode);
-               dput(temp);
-out_unlock2:   
-               if (ret == 0)
-                       mark_inode_dirty(olddentry->d_inode);
-       }
-       if (olddir != dir)
-               up(&olddir->i_sem);
-
-out_free:
-       free_page(buffer);
-out:
-       Printk (("umsdos_link %d\n", ret));
-       return ret;
-}
-
-
-/*
- * Add a sub-directory in a directory
- */
-/* #Specification: mkdir / Directory already exist in DOS
- * We do the same thing as for file creation.
- * For all user it is an error.
- */
-/* #Specification: mkdir / umsdos directory / create EMD
- * When we created a new sub-directory in a UMSDOS
- * directory (one with full UMSDOS semantics), we
- * create immediately an EMD file in the new
- * sub-directory so it inherits UMSDOS semantics.
- */
-int UMSDOS_mkdir (struct inode *dir, struct dentry *dentry, int mode)
-{
-       struct dentry *temp;
-       struct inode *inode;
-       int ret, err;
-       struct umsdos_info info;
-
-       ret = umsdos_nevercreat (dir, dentry, -EEXIST);
-       if (ret)
-               goto out;
-
-       ret = umsdos_parse (dentry->d_name.name, dentry->d_name.len, &info);
-       if (ret)
-               goto out;
-
-       info.entry.mode = mode | S_IFDIR;
-       info.entry.rdev = 0;
-       info.entry.uid = current->fsuid;
-       info.entry.gid = (dir->i_mode & S_ISGID) ? dir->i_gid : current->fsgid;
-       info.entry.ctime = info.entry.atime = info.entry.mtime = get_seconds();
-       info.entry.flags = 0;
-       info.entry.nlink = 1;
-       ret = umsdos_newentry (dentry->d_parent, &info);
-       if (ret)
-               goto out;
-
-       /* lookup the short name dentry */
-       temp = umsdos_covered(dentry->d_parent, info.fake.fname, info.fake.len);
-       ret = PTR_ERR(temp);
-       if (IS_ERR(temp))
-               goto out_remove;
-
-       /* Make sure the short name doesn't exist */
-       ret = -EEXIST;
-       if (temp->d_inode) {
-printk("umsdos_mkdir: short name %s/%s exists\n",
-dentry->d_parent->d_name.name, info.fake.fname);
-               goto out_remove_dput;
-       }
-
-       ret = msdos_mkdir (dir, temp, mode);
-       if (ret)
-               goto out_remove_dput;
-
-       /*
-        * Lock the inode to protect the EMD creation ...
-        */
-       inode = temp->d_inode;
-       down(&inode->i_sem);
-
-       atomic_inc(&inode->i_count);
-       d_instantiate(dentry, inode);
-
-       /* N.B. this should have an option to create the EMD ... */
-       umsdos_lookup_patch_new(dentry, &info);
-
-       /* 
-        * Create the EMD file, and set up the dir so it is
-        * promoted to EMD with the EMD file invisible.
-        *
-        * N.B. error return if EMD fails?
-        */
-       err = umsdos_make_emd(dentry);
-       umsdos_setup_dir(dentry);
-
-       up(&inode->i_sem);
-       dput(temp);
-
-out:
-       Printk(("umsdos_mkdir: %s/%s, ret=%d\n",
-               dentry->d_parent->d_name.name, dentry->d_name.name, ret));
-       return ret;
-
-       /* an error occurred ... remove EMD entry. */
-out_remove_dput:
-       dput(temp);
-out_remove:
-       umsdos_delentry (dentry->d_parent, &info, 1);
-       goto out;
-}
-
-/*
- * Add a new device special file into a directory.
- *
- * #Specification: Special files / strategy
- * Device special file, pipes, etc ... are created like normal
- * file in the msdos file system. Of course they remain empty.
- * 
- * One strategy was to create those files only in the EMD file
- * since they were not important for MSDOS. The problem with
- * that, is that there were not getting inode number allocated.
- * The MSDOS filesystems is playing a nice game to fake inode
- * number, so why not use it.
- * 
- * The absence of inode number compatible with those allocated
- * for ordinary files was causing major trouble with hard link
- * in particular and other parts of the kernel I guess.
- */
-int UMSDOS_mknod (struct inode *dir, struct dentry *dentry,
-                int mode, dev_t rdev)
-{
-       return umsdos_create_any (dir, dentry, mode, rdev, 0);
-}
-
-/*
- * Remove a sub-directory.
- */
-int UMSDOS_rmdir (struct inode *dir, struct dentry *dentry)
-{
-       struct dentry *temp;
-       int ret, err, empty;
-       struct umsdos_info info;
-
-       ret = umsdos_nevercreat (dir, dentry, -EPERM);
-       if (ret)
-               goto out;
-
-       ret = -EBUSY;
-       if (!d_unhashed(dentry))
-               goto out;
-
-       /* check whether the EMD is empty */
-       ret = -ENOTEMPTY;
-       empty = umsdos_isempty (dentry);
-
-       /* Have to remove the EMD file? */
-       if (empty == 1) {
-               struct dentry *demd;
-
-               demd = umsdos_get_emd_dentry(dentry);
-               if (!IS_ERR(demd)) {
-                       err = -ENOENT;
-                       if (demd->d_inode)
-                               err = msdos_unlink (dentry->d_inode, demd);
-Printk (("UMSDOS_rmdir: unlinking empty EMD err=%d", err));
-#ifdef UMSDOS_PARANOIA
-if (err)
-printk("umsdos_rmdir: EMD %s/%s unlink failed, err=%d\n",
-demd->d_parent->d_name.name, demd->d_name.name, err);
-#endif
-                       if (!err) {
-                               d_delete(demd);
-                               ret = 0;
-                       }
-                       dput(demd);
-               }
-       } else if (empty == 2)
-               ret = 0;
-       if (ret)
-               goto out;
-
-       umsdos_parse (dentry->d_name.name, dentry->d_name.len, &info);
-       /* Call findentry to complete the mangling */
-       umsdos_findentry (dentry->d_parent, &info, 2);
-       temp = umsdos_covered(dentry->d_parent, info.fake.fname, info.fake.len);
-       ret = PTR_ERR(temp);
-       if (IS_ERR(temp))
-               goto out;
-       /*
-        * Attempt to remove the msdos name.
-        */
-       ret = msdos_rmdir (dir, temp);
-       if (ret && ret != -ENOENT)
-               goto out_dput;
-
-       d_delete(temp);
-       /* OK so far ... remove the name from the EMD */
-       ret = umsdos_delentry (dentry->d_parent, &info, 1);
-#ifdef UMSDOS_PARANOIA
-if (ret)
-printk("umsdos_rmdir: delentry %s failed, ret=%d\n", info.entry.name, ret);
-#endif
-
-       /* dput() temp if we didn't do it above */
-out_dput:
-       dput(temp);
-
-out:
-       Printk (("umsdos_rmdir %d\n", ret));
-       return ret;
-}
-
-
-/*
- * Remove a file from the directory.
- *
- * #Specification: hard link / deleting a link
- * When we delete a file and this file is a link,
- * we must subtract 1 from the nlink field of the
- * hidden link.
- * 
- * If the count goes to 0, we delete this hidden
- * link too.
- */
-int UMSDOS_unlink (struct inode *dir, struct dentry *dentry)
-{
-       struct dentry *temp, *link = NULL;
-       struct inode *inode;
-       int ret;
-       struct umsdos_info info;
-
-Printk(("UMSDOS_unlink: entering %s/%s\n",
-dentry->d_parent->d_name.name, dentry->d_name.name));
-
-       ret = umsdos_nevercreat (dir, dentry, -EPERM);
-       if (ret)
-               goto out;
-
-       ret = umsdos_parse (dentry->d_name.name, dentry->d_name.len, &info);
-       if (ret)
-               goto out;
-
-       umsdos_lockcreate (dir);
-       ret = umsdos_findentry (dentry->d_parent, &info, 1);
-       if (ret) {
-printk("UMSDOS_unlink: %s/%s not in EMD, ret=%d\n",
-dentry->d_parent->d_name.name, dentry->d_name.name, ret);
-               goto out_unlock;
-       }
-
-Printk (("UMSDOS_unlink %.*s ", info.fake.len, info.fake.fname));
-
-       /*
-        * Note! If this is a hardlink and the names are aliased,
-        * the short-name lookup will return the hardlink dentry.
-        * In order to get the correct (real) inode, we just drop
-        * the original dentry.
-        */ 
-       if (info.entry.flags & UMSDOS_HLINK) {
-               d_drop(dentry);
-       }
-
-       /* Do a real lookup to get the short name dentry */
-       temp = umsdos_covered(dentry->d_parent, info.fake.fname, info.fake.len);
-       ret = PTR_ERR(temp);
-       if (IS_ERR(temp))
-               goto out_unlock;
-
-       /*
-        * Resolve hardlinks now, but defer processing until later.
-        */
-       if (info.entry.flags & UMSDOS_HLINK) {
-               link = umsdos_solve_hlink(dget(temp));
-       }
-
-       /* Delete the EMD entry */
-       ret = umsdos_delentry (dentry->d_parent, &info, 0);
-       if (ret && ret != -ENOENT) {
-               printk(KERN_WARNING "UMSDOS_unlink: delentry %s, error=%d\n",
-                       info.entry.name, ret);
-               goto out_dput;
-       }
-
-       ret = msdos_unlink(dir, temp);
-       if (!ret)
-               d_delete(temp);
-#ifdef UMSDOS_PARANOIA
-if (ret)
-printk("umsdos_unlink: %s/%s unlink failed, ret=%d\n",
-temp->d_parent->d_name.name, temp->d_name.name, ret);
-#endif
-
-       /* dput() temp if we didn't do it above */
-out_dput:
-       dput(temp);
-
-out_unlock:
-       umsdos_unlockcreate (dir);
-
-       /*
-        * Now check for deferred handling of a hardlink.
-        */
-       if (!link)
-               goto out;
-
-       if (IS_ERR(link)) {
-printk("umsdos_unlink: failed to resolve %s/%s\n",
-dentry->d_parent->d_name.name, dentry->d_name.name);
-               if (!ret)
-                       ret = PTR_ERR(link);
-               goto out;
-       }
-
-Printk(("umsdos_unlink: link %s/%s deferred, pending ret=%d\n",
-link->d_parent->d_name.name, link->d_name.name, ret));
-
-       /* already have an error? */
-       if (ret)
-               goto out_cleanup;
-
-       /* make sure the link exists ... */
-       inode = link->d_inode;
-       if (!inode) {
-               printk(KERN_WARNING "umsdos_unlink: hard link not found\n");
-               goto out_cleanup;
-       }
-
-       /*
-        * If this was the last linked reference, delete it now.
-        *
-        * N.B. Deadlock problem? We should be holding the lock
-        * for the hardlink's parent, but another process might
-        * be holding that lock waiting for us to finish ...
-        */
-       if (inode->i_nlink <= 1) {
-               ret = UMSDOS_unlink (link->d_parent->d_inode, link);
-               if (ret) {
-                       printk(KERN_WARNING
-                               "umsdos_unlink: link removal failed, ret=%d\n",
-                                ret);
-               } else
-                       d_delete(link);
-       } else {
-               struct iattr newattrs;
-               inode->i_nlink--;
-               newattrs.ia_valid = 0;
-               ret = umsdos_notify_change_locked(link, &newattrs);
-               if (!ret)
-                       mark_inode_dirty(link->d_inode);
-       }
-
-out_cleanup:
-       d_drop(link);
-       dput(link);
-
-out:
-       Printk (("umsdos_unlink %d\n", ret));
-       return ret;
-}
-
-/*
- * Rename (move) a file.
- */
-int UMSDOS_rename (struct inode *old_dir, struct dentry *old_dentry,
-                  struct inode *new_dir, struct dentry *new_dentry)
-{
-       int ret;
-
-       ret = umsdos_nevercreat (new_dir, new_dentry, -EEXIST);
-       if (ret)
-               return ret;
-
-               /*
-                * If the target already exists, delete it first.
-                */
-       if (new_dentry->d_inode) {
-               dget(new_dentry);
-               if (S_ISDIR(old_dentry->d_inode->i_mode))
-                       ret = UMSDOS_rmdir (new_dir, new_dentry);
-               else
-                       ret = UMSDOS_unlink (new_dir, new_dentry);
-               if (!ret)
-                       d_drop(new_dentry);
-               dput(new_dentry);
-               if (ret)
-                       return ret;
-       }
-       ret = umsdos_rename_f(old_dir, old_dentry, new_dir, new_dentry, 0);
-       return ret;
-}
diff --git a/fs/umsdos/rdir.c b/fs/umsdos/rdir.c
deleted file mode 100644 (file)
index 2f32539..0000000
+++ /dev/null
@@ -1,248 +0,0 @@
-/*
- *  linux/fs/umsdos/rdir.c
- *
- *  Written 1994 by Jacques Gelinas
- *
- *  Extended MS-DOS directory pure MS-DOS handling functions
- *  (For directory without EMD file).
- */
-
-#include <linux/time.h>
-#include <linux/fs.h>
-#include <linux/msdos_fs.h>
-#include <linux/errno.h>
-#include <linux/stat.h>
-#include <linux/limits.h>
-#include <linux/umsdos_fs.h>
-#include <linux/slab.h>
-#include <linux/smp_lock.h>
-
-#include <asm/uaccess.h>
-
-
-extern struct dentry *saved_root;
-extern struct inode *pseudo_root;
-extern struct dentry_operations umsdos_dentry_operations;
-
-struct RDIR_FILLDIR {
-       void *dirbuf;
-       filldir_t filldir;
-       int real_root;
-};
-
-static int rdir_filldir (      void *buf,
-                               const char *name,
-                               int name_len,
-                               loff_t offset,
-                               ino_t ino,
-                               unsigned int d_type)
-{
-       int ret = 0;
-       struct RDIR_FILLDIR *d = (struct RDIR_FILLDIR *) buf;
-
-       if (d->real_root) {
-               PRINTK ((KERN_DEBUG "rdir_filldir /mn/: real root!\n"));
-               /* real root of a pseudo_rooted partition */
-               if (name_len != UMSDOS_PSDROOT_LEN
-                   || memcmp (name, UMSDOS_PSDROOT_NAME, UMSDOS_PSDROOT_LEN) != 0) {
-                       /* So it is not the /linux directory */
-                       if (name_len == 2 && name[0] == '.' && name[1] == '.') {
-                               /* Make sure the .. entry points back to the pseudo_root */
-                               ino = pseudo_root->i_ino;
-                       }
-                       ret = d->filldir (d->dirbuf, name, name_len, offset, ino, DT_UNKNOWN);
-               }
-       } else {
-               /* Any DOS directory */
-               ret = d->filldir (d->dirbuf, name, name_len, offset, ino, DT_UNKNOWN);
-       }
-       return ret;
-}
-
-
-static int UMSDOS_rreaddir (struct file *filp, void *dirbuf, filldir_t filldir)
-{
-       struct inode *dir = filp->f_dentry->d_inode;
-       struct RDIR_FILLDIR bufk;
-       int ret;
-
-       lock_kernel();
-       bufk.filldir = filldir;
-       bufk.dirbuf = dirbuf;
-       bufk.real_root = pseudo_root && (dir == saved_root->d_inode);
-       ret = fat_readdir (filp, &bufk, rdir_filldir);
-       unlock_kernel();
-       return ret;
-}
-
-
-/*
- * Lookup into a non promoted directory.
- * If the result is a directory, make sure we find out if it is
- * a promoted one or not (calling umsdos_setup_dir_inode(inode)).
- */
-/* #Specification: pseudo root / DOS/..
- * In the real root directory (c:\), the directory ..
- * is the pseudo root (c:\linux).
- */
-struct dentry *umsdos_rlookup_x ( struct inode *dir, struct dentry *dentry, int nopseudo)
-{
-       struct dentry *ret;
-
-       if (saved_root && dir == saved_root->d_inode && !nopseudo &&
-           dentry->d_name.len == UMSDOS_PSDROOT_LEN &&
-           memcmp (dentry->d_name.name, UMSDOS_PSDROOT_NAME, UMSDOS_PSDROOT_LEN) == 0) {
-               /* #Specification: pseudo root / DOS/linux
-                * Even in the real root directory (c:\), the directory
-                * /linux won't show
-                */
-                
-               ret = ERR_PTR(-ENOENT);
-               goto out;
-       }
-
-       ret = msdos_lookup (dir, dentry, NULL);
-       if (ret) {
-               printk(KERN_WARNING
-                       "umsdos_rlookup_x: %s/%s failed, ret=%ld\n",
-                       dentry->d_parent->d_name.name, dentry->d_name.name,
-                       PTR_ERR(ret));
-               goto out;
-       }
-       if (dentry->d_inode) {
-               /* We must install the proper function table
-                * depending on whether this is an MS-DOS or 
-                * a UMSDOS directory
-                */
-Printk ((KERN_DEBUG "umsdos_rlookup_x: patch_dentry_inode %s/%s\n",
-dentry->d_parent->d_name.name, dentry->d_name.name));
-/* only patch if needed (because we get called even for lookup
-   (not only rlookup) stuff sometimes, like in umsdos_covered() */
-               if (UMSDOS_I(dentry->d_inode)->i_patched == 0)  
-               umsdos_patch_dentry_inode(dentry, 0);
-
-       }
-out:
-       /* always install our dentry ops ... */
-       dentry->d_op = &umsdos_dentry_operations;
-       return ret;
-}
-
-
-struct dentry *UMSDOS_rlookup ( struct inode *dir, struct dentry *dentry, struct nameidata *nd)
-{
-       return umsdos_rlookup_x (dir, dentry, 0);
-}
-
-
-/* #Specification: dual mode / rmdir in a DOS directory
- * In a DOS (not EMD in it) directory, we use a reverse strategy
- * compared with a UMSDOS directory. We assume that a subdirectory
- * of a DOS directory is also a DOS directory. This is not always
- * true (umssync may be used anywhere), but makes sense.
- * 
- * So we call msdos_rmdir() directly. If it failed with a -ENOTEMPTY
- * then we check if it is a Umsdos directory. We check if it is
- * really empty (only . .. and --linux-.--- in it). If it is true
- * we remove the EMD and do a msdos_rmdir() again.
- * 
- * In a Umsdos directory, we assume all subdirectories are also
- * Umsdos directories, so we check the EMD file first.
- */
-/* #Specification: pseudo root / rmdir /DOS
- * The pseudo sub-directory /DOS can't be removed!
- * This is done even if the pseudo root is not a Umsdos
- * directory anymore (very unlikely), but an accident (under
- * MS-DOS) is always possible.
- * 
- * EPERM is returned.
- */
-static int UMSDOS_rrmdir ( struct inode *dir, struct dentry *dentry)
-{
-       int ret, empty;
-
-       ret = -EPERM;
-       if (umsdos_is_pseudodos (dir, dentry))
-               goto out;
-
-       ret = -EBUSY;
-       if (!d_unhashed(dentry))
-               goto out;
-
-       ret = msdos_rmdir (dir, dentry);
-       if (ret != -ENOTEMPTY)
-               goto out;
-
-       empty = umsdos_isempty (dentry);
-       if (empty == 1) {
-               struct dentry *demd;
-               /* We have to remove the EMD file. */
-               demd = umsdos_get_emd_dentry(dentry);
-               ret = PTR_ERR(demd);
-               if (!IS_ERR(demd)) {
-                       ret = 0;
-                       if (demd->d_inode)
-                               ret = msdos_unlink (dentry->d_inode, demd);
-                       if (!ret)
-                               d_delete(demd);
-                       dput(demd);
-               }
-       }
-       if (ret)
-               goto out;
-
-       /* now retry the original ... */
-       ret = msdos_rmdir (dir, dentry);
-
-out:
-       return ret;
-}
-
-/* #Specification: dual mode / introduction
- * One goal of UMSDOS is to allow a practical and simple coexistence
- * between MS-DOS and Linux in a single partition. Using the EMD file
- * in each directory, UMSDOS adds Unix semantics and capabilities to
- * a normal DOS filesystem. To help and simplify coexistence, here is
- * the logic related to the EMD file.
- * 
- * If it is missing, then the directory is managed by the MS-DOS driver.
- * The names are limited to DOS limits (8.3). No links, no device special
- * and pipe and so on.
- * 
- * If it is there, it is the directory. If it is there but empty, then
- * the directory looks empty. The utility umssync allows synchronisation
- * of the real DOS directory and the EMD.
- * 
- * Whenever umssync is applied to a directory without EMD, one is
- * created on the fly.  The directory is promoted to full Unix semantics.
- * Of course, the ls command will show exactly the same content as before
- * the umssync session.
- * 
- * It is believed that the user/admin will promote directories to Unix
- * semantics as needed.
- * 
- * The strategy to implement this is to use two function table (struct
- * inode_operations). One for true UMSDOS directory and one for directory
- * with missing EMD.
- * 
- * Functions related to the DOS semantic (but aware of UMSDOS) generally
- * have a "r" prefix (r for real) such as UMSDOS_rlookup, to differentiate
- * from the one with full UMSDOS semantics.
- */
-struct file_operations umsdos_rdir_operations =
-{
-       .read           = generic_read_dir,
-       .readdir        = UMSDOS_rreaddir,
-       .ioctl          = UMSDOS_ioctl_dir,
-};
-
-struct inode_operations umsdos_rdir_inode_operations =
-{
-       .create         = msdos_create,
-       .lookup         = UMSDOS_rlookup,
-       .unlink         = msdos_unlink,
-       .mkdir          = msdos_mkdir,
-       .rmdir          = UMSDOS_rrmdir,
-       .rename         = msdos_rename,
-       .setattr        = UMSDOS_notify_change,
-};
diff --git a/fs/umsdos/specs b/fs/umsdos/specs
deleted file mode 100644 (file)
index 0f7d68c..0000000
+++ /dev/null
@@ -1,289 +0,0 @@
-/* #Specification: umsdos / readdir
- * umsdos_readdir() should fill a struct dirent with
- * an inode number. The cheap way to get it is to
- * do a lookup in the MSDOS directory for each
- * entry processed by the readdir() function.
- * This is not very efficient, but very simple. The
- * other way around is to maintain a copy of the inode
- * number in the EMD file. This is a problem because
- * this has to be maintained in sync using tricks.
- * Remember that MSDOS (the OS) does not update the
- * modification time (mtime) of a directory. There is
- * no easy way to tell that a directory was modified
- * during a DOS session and synchronise the EMD file.
- */
-               /* #Specification: readdir / . and ..
-                * The msdos filesystem manages the . and .. entry properly
-                * so the EMD file won't hold any info about it.
-                * 
-                * In readdir, we assume that for the root directory
-                * the read position will be 0 for ".", 1 for "..". For
-                * a non root directory, the read position will be 0 for "."
-                * and 32 for "..".
-                */
-               /*
-                * This is a trick used by the msdos file system (fs/msdos/dir.c)
-                * to manage . and .. for the root directory of a file system.
-                * Since there is no such entry in the root, fs/msdos/dir.c
-                * use the following:
-                * 
-                * if f_pos == 0, return ".".
-                * if f_pos == 1, return "..".
-                * 
-                * So let msdos handle it
-                * 
-                * Since umsdos entries are much larger, we share the same f_pos.
-                * if f_pos is 0 or 1 or 32, we are clearly looking at . and
-                * ..
-                * 
-                * As soon as we get f_pos == 2 or f_pos == 64, then back to
-                * 0, but this time we are reading the EMD file.
-                * 
-                * Well, not so true. The problem, is that UMSDOS_REC_SIZE is
-                * also 64, so as soon as we read the first record in the
-                * EMD, we are back at offset 64. So we set the offset
-                * to UMSDOS_SPECIAL_DIRFPOS(3) as soon as we have read the
-                * .. entry from msdos.
-                * 
-                * Now (linux 1.3), umsdos_readdir can read more than one
-                * entry even if we limit (umsdos_dir_once) to only one:
-                * It skips over hidden file. So we switch to
-                * UMSDOS_SPECIAL_DIRFPOS as soon as we have read successfully
-                * the .. entry.
-                */
-                       /* #Specification: umsdos / lookup / inode info
-                        * After successfully reading an inode from the MSDOS
-                        * filesystem, we use the EMD file to complete it.
-                        * We update the following field.
-                        * 
-                        * uid, gid, atime, ctime, mtime, mode.
-                        * 
-                        * We rely on MSDOS for mtime. If the file
-                        * was modified during an MSDOS session, at least
-                        * mtime will be meaningful. We do this only for regular
-                        * file.
-                        * 
-                        * We don't rely on MS-DOS for mtime for directories
-                        * because the MS-DOS date on a directory is its
-                        * creation time (strange MSDOS behavior) which
-                        * corresponds to none of the three Unix time stamps.
-                        */
-       /* #Specification: umsdos / conversion mode
-        * The msdos filesystem can do some inline conversion
-        * of the data of a file.  It can translate silently
-        * from the MS-DOS text file format to the Unix one
-        * (CRLF -> LF) while reading, and the reverse
-        * while writing. This is activated using the mount
-        * option conv=....
-        * 
-        * This is not useful for Linux files in a promoted
-        * directory.  It can even be harmful.  For this
-        * reason, the binary (no conversion) mode is
-        * always activated.
-        */
-       /* #Specification: umsdos / conversion mode / todo
-        * A flag could be added to file and directories
-        * forcing an automatic conversion mode (as
-        * done with the msdos filesystem).
-        * 
-        * This flag could be setup on a directory basis
-        * (instead of file) and all files in it would
-        * logically inherit it.  If the conversion mode
-        * is active (conv=) then the i_binary flag would
-        * be left untouched in those directories.
-        * 
-        * It was proposed that the sticky bit be used to set
-        * this.  A problem with that is that new files would
-        * be written incorrectly.  The other problem is that
-        * the sticky bit has a meaning for directories. So
-        * another bit should be used (there is some space
-        * in the EMD file for it) and a special utility
-        * would be used to assign the flag to a directory).
-        * I don't think it is useful to assign this flag
-        * on a single file.
-        */
- * #Specification: weakness / rename
- * There is a case where UMSDOS rename has a different behavior
- * than a normal Unix file system.  Renaming an open file across
- * directory boundary does not work.  Renaming an open file within
- * a directory does work, however.
- * 
- * The problem may is in Linux VFS driver for msdos.
- * I believe this is not a bug but a design feature, because
- * an inode number represents some sort of directory address
- * in the MSDOS directory structure, so moving the file into
- * another directory does not preserve the inode number.
- */
-/* #Specification: rename / new name exist
- * If the destination name already exists, it will
- * silently be removed.  EXT2 does it this way
- * and this is the spec of SunOS.  So does UMSDOS.
- * 
- * If the destination is an empty directory it will
- * also be removed.
- */
-/* #Specification: rename / new name exist / possible flaw
- * The code to handle the deletion of the target (file
- * and directory) use to be in umsdos_rename_f, surrounded
- * by proper directory locking.  This was ensuring that only
- * one process could achieve a rename (modification) operation
- * in the source and destination directory.  This was also
- * ensuring the operation was "atomic".
- * 
- * This has been changed because this was creating a
- * stack overflow (the stack is only 4 kB) in the kernel.  To avoid
- * the code doing the deletion of the target (if exist) has
- * been moved to a upper layer. umsdos_rename_f is tried
- * once and if it fails with EEXIST, the target is removed
- * and umsdos_rename_f is done again.
- * 
- * This makes the code cleaner and may solve a
- * deadlock problem one tester was experiencing.
- * 
- * The point is to mention that possibly, the semantic of
- * "rename" may be wrong. Anyone dare to check that :-)
- * Be aware that IF it is wrong, to produce the problem you
- * will need two process trying to rename a file to the
- * same target at the same time. Again, I am not sure it
- * is a problem at all.
- */
-
-/* #Specification: hard link / strategy
- * Hard links are difficult to implement on top of an MS-DOS FAT file
- * system. Unlike Unix file systems, there are no inodes. A directory
- * entry holds the functionality of the inode and the entry.
- * 
- * We will used the same strategy as a normal Unix file system
- * (with inodes) except we will do it symbolically (using paths).
- * 
- * Because anything can happen during a DOS session (defragment,
- * directory sorting, etc.), we can't rely on an MS-DOS pseudo
- * inode number to record the link. For this reason, the link
- * will be done using hidden symbolic links. The following
- * scenario illustrates how it works.
- * 
- * Given a file /foo/file
- * 
- * #
- * ln /foo/file /tmp/file2
- * 
- * become internally
- * 
- * mv /foo/file /foo/-LINK1
- * ln -s /foo/-LINK1 /foo/file
- * ln -s /foo/-LINK1 /tmp/file2
- * #
- * 
- * Using this strategy, we can operate on /foo/file or /foo/file2.
- * We can remove one and keep the other, like a normal Unix hard link.
- * We can rename /foo/file or /tmp/file2 independently.
- * 
- * The entry -LINK1 will be hidden. It will hold a link count.
- * When all link are erased, the hidden file is erased too.
- */
-
-/* #Specification: weakness / hard link
- * The strategy for hard link introduces a side effect that
- * may or may not be acceptable. Here is the sequence
- * 
- * #
- * mkdir subdir1
- * touch subdir1/file
- * mkdir subdir2
- * ln    subdir1/file subdir2/file
- * rm    subdir1/file
- * rmdir subdir1
- * rmdir: subdir1: Directory not empty
- * #
- * 
- * This happen because there is an invisible file (--link) in
- * subdir1 which is referenced by subdir2/file.
- * 
- * Any idea ?
- */
-/* #Specification: weakness / hard link / rename directory
- * Another weakness of hard link come from the fact that
- * it is based on hidden symbolic links. Here is an example.
- * 
- * #
- * mkdir /subdir1
- * touch /subdir1/file
- * mkdir /subdir2
- * ln    /subdir1/file subdir2/file
- * mv    /subdir1 subdir3
- * ls -l /subdir2/file
- * #
- * 
- * Since /subdir2/file is a hidden symbolic link
- * to /subdir1/..hlinkNNN, accessing it will fail since
- * /subdir1 does not exist anymore (has been renamed).
- */
-/* #Specification: hard link / directory
- * A hard link can't be made on a directory. EPERM is returned
- * in this case.
- */
-/* #Specification: hard link / first hard link
- * The first time a hard link is done on a file, this
- * file must be renamed and hidden. Then an internal
- * symbolic link must be done on the hidden file.
- * 
- * The second link is done after on this hidden file.
- * 
- * It is expected that the Linux MSDOS file system
- * keeps the same pseudo inode when a rename operation
- * is done on a file in the same directory.
- */
-/* #Specification: function name / convention
- * A simple convention for function names has been used in
- * the UMSDOS filesystem. First, all functions use the prefix
- * umsdos_ to avoid name clashes with other parts of the kernel.
- * 
- * Standard VFS entry points use the prefix UMSDOS (upper case)
- * so it's easier to tell them apart.
- * N.B. (FIXME) PTW, the order and contents of this struct changed.
- */
-
-/* #Specification: mount / options
- * Umsdos run on top of msdos. Currently, it supports no
- * mount option, but happily pass all option received to
- * the msdos driver. I am not sure if all msdos mount option
- * make sense with Umsdos. Here are at least those who
- * are useful.
- * uid=
- * gid=
- * 
- * These options affect the operation of umsdos in directories
- * which do not have an EMD file. They behave like normal
- * msdos directory, with all limitation of msdos.
- */
-
-/* #Specification: pseudo root / mount
- * When a umsdos fs is mounted, a special handling is done
- * if it is the root partition. We check for the presence
- * of the file /linux/etc/init or /linux/etc/rc or
- * /linux/sbin/init. If one is there, we do a chroot("/linux").
- * 
- * We check both because (see init/main.c) the kernel
- * try to exec init at different place and if it fails
- * it tries /bin/sh /etc/rc. To be consistent with
- * init/main.c, many more test would have to be done
- * to locate init. Any complain ?
- * 
- * The chroot is done manually in init/main.c but the
- * info (the inode) is located at mount time and store
- * in a global variable (pseudo_root) which is used at
- * different place in the umsdos driver. There is no
- * need to store this variable elsewhere because it
- * will always be one, not one per mount.
- * 
- * This feature allows the installation
- * of a linux system within a DOS system in a subdirectory.
- * 
- * A user may install its linux stuff in c:\linux
- * avoiding any clash with existing DOS file and subdirectory.
- * When linux boots, it hides this fact, showing a normal
- * root directory with /etc /bin /tmp ...
- * 
- * The word "linux" is hardcoded in /usr/include/linux/umsdos_fs.h
- * in the macro UMSDOS_PSDROOT_NAME.
- */
diff --git a/include/linux/umsdos_fs.h b/include/linux/umsdos_fs.h
deleted file mode 100644 (file)
index 67c2569..0000000
+++ /dev/null
@@ -1,182 +0,0 @@
-#ifndef LINUX_UMSDOS_FS_H
-#define LINUX_UMSDOS_FS_H
-
-
-/*#define UMS_DEBUG 1  // define for check_* functions */
-/*#define UMSDOS_DEBUG 1*/
-#define UMSDOS_PARANOIA 1
-
-#define UMSDOS_VERSION 0
-#define UMSDOS_RELEASE 4
-
-#define UMSDOS_ROOT_INO 1
-
-/* This is the file acting as a directory extension */
-#define UMSDOS_EMD_FILE                "--linux-.---"
-#define UMSDOS_EMD_NAMELEN     12
-#define UMSDOS_PSDROOT_NAME    "linux"
-#define UMSDOS_PSDROOT_LEN     5
-
-#ifndef _LINUX_TYPES_H
-#include <linux/types.h>
-#endif
-#ifndef _LINUX_LIMITS_H
-#include <linux/limits.h>
-#endif
-#ifndef _LINUX_DIRENT_H
-#include <linux/dirent.h>
-#endif
-#ifndef _LINUX_IOCTL_H
-#include <linux/ioctl.h>
-#endif
-
-
-#ifdef __KERNEL__
-/* #Specification: convention / PRINTK Printk and printk
- * Here is the convention for the use of printk inside fs/umsdos
- * 
- * printk carry important message (error or status).
- * Printk is for debugging (it is a macro defined at the beginning of
- * most source.
- * PRINTK is a nulled Printk macro.
- * 
- * This convention makes the source easier to read, and Printk easier
- * to shut off.
- */
-#      define PRINTK(x)
-#      ifdef UMSDOS_DEBUG
-#              define Printk(x) printk x
-#      else
-#              define Printk(x)
-#      endif
-#endif /* __KERNEL__ */
-
-
-struct umsdos_fake_info {
-       char fname[13];
-       int len;
-};
-
-#define UMSDOS_MAXNAME 220
-/* This structure is 256 bytes large, depending on the name, only part */
-/* of it is written to disk */
-/* nice though it would be, I can't change this and preserve backward compatibility */
-struct umsdos_dirent {
-       unsigned char name_len; /* if == 0, then this entry is not used */
-       unsigned char flags;    /* UMSDOS_xxxx */
-       unsigned short nlink;   /* How many hard links point to this entry */
-       __kernel_uid_t uid;     /* Owner user id */
-       __kernel_gid_t gid;     /* Group id */
-       time_t atime;           /* Access time */
-       time_t mtime;           /* Last modification time */
-       time_t ctime;           /* Creation time */
-       unsigned short rdev;    /* major and minor of a device special file */
-       umode_t mode;           /* Standard UNIX permissions bits + type of */
-       char spare[12];         /* unused bytes for future extensions */
-                               /* file, see linux/stat.h */
-       char name[UMSDOS_MAXNAME];      /* Not '\0' terminated */
-                               /* but '\0' padded, so it will allow */
-                               /* for adding news fields in this record */
-                               /* by reducing the size of name[] */
-};
-
-#define UMSDOS_HIDDEN  1       /* Never show this entry in directory search */
-#define UMSDOS_HLINK   2       /* It is a (pseudo) hard link */
-
-/* #Specification: EMD file / record size
- * Entry are 64 bytes wide in the EMD file. It allows for a 30 characters
- * name. If a name is longer, contiguous entries are allocated. So a
- * umsdos_dirent may span multiple records.
- */
-#define UMSDOS_REC_SIZE                64
-
-/* Translation between MSDOS name and UMSDOS name */
-
-struct umsdos_info {
-       int msdos_reject;       /* Tell if the file name is invalid for MSDOS */
-                               /* See umsdos_parse */
-       struct umsdos_fake_info fake;
-       struct umsdos_dirent entry;
-       off_t f_pos;            /* offset of the entry in the EMD file
-                                * or offset where the entry may be store
-                                * if it is a new entry
-                                */
-       int recsize;            /* Record size needed to store entry */
-};
-
-/* Definitions for ioctl (number randomly chosen)
- * The next ioctl commands operate only on the DOS directory
- * The file umsdos_progs/umsdosio.c contain a string table
- * based on the order of those definition. Keep it in sync
- */
-#define UMSDOS_READDIR_DOS _IO(0x04,210)       /* Do a readdir of the DOS directory */
-#define UMSDOS_UNLINK_DOS  _IO(0x04,211)       /* Erase in the DOS directory only */
-#define UMSDOS_RMDIR_DOS   _IO(0x04,212)       /* rmdir in the DOS directory only */
-#define UMSDOS_STAT_DOS    _IO(0x04,213)       /* Get info about a file */
-
-/* The next ioctl commands operate only on the EMD file */
-#define UMSDOS_CREAT_EMD   _IO(0x04,214)       /* Create a file */
-#define UMSDOS_UNLINK_EMD  _IO(0x04,215)       /* unlink (rmdir) a file */
-#define UMSDOS_READDIR_EMD _IO(0x04,216)       /* read the EMD file only. */
-#define UMSDOS_GETVERSION  _IO(0x04,217)       /* Get the release number of UMSDOS */
-#define UMSDOS_INIT_EMD    _IO(0x04,218)       /* Create the EMD file if not there */
-#define UMSDOS_DOS_SETUP   _IO(0x04,219)       /* Set the defaults of the MS-DOS driver. */
-
-#define UMSDOS_RENAME_DOS  _IO(0x04,220)       /* rename a file/directory in the DOS
-                                                * directory only */
-struct umsdos_ioctl {
-       struct dirent dos_dirent;
-       struct umsdos_dirent umsdos_dirent;
-       /* The following structure is used to exchange some data with
-        * utilities (umsdos_progs/util/umsdosio.c). The first releases
-        * were using struct stat from "sys/stat.h". This was causing
-        * some problem for cross compilation of the kernel.
-        * Since I am not really using the structure stat, but only
-        * some fields of it, I have decided to replicate the structure
-        * here for compatibility with the binaries out there.
-        * FIXME PTW 1998, this has probably changed
-        */
-       
-       struct {
-               unsigned long st_dev;
-               ino_t st_ino;                   /* used */
-               umode_t st_mode;                /* used */
-               nlink_t st_nlink;
-               __kernel_uid_t st_uid;
-               __kernel_gid_t st_gid;
-               unsigned long st_rdev;
-               off_t st_size;                  /* used */
-               unsigned long st_blksize;
-               unsigned long st_blocks;
-               time_t st_atime;                /* used */
-               unsigned long __unused1;
-               time_t st_mtime;                /* used */
-               unsigned long __unused2;
-               time_t st_ctime;                /* used */
-               unsigned long __unused3;
-               uid_t st_uid32;
-               gid_t st_gid32;
-       } stat;
-       char version, release;
-};
-
-/* Different macros to access struct umsdos_dirent */
-#define EDM_ENTRY_ISUSED(e) ((e)->name_len!=0)
-
-#ifdef __KERNEL__
-
-#ifndef LINUX_FS_H
-#include <linux/fs.h>
-#endif
-
-extern struct inode_operations umsdos_dir_inode_operations;
-extern struct inode_operations umsdos_rdir_inode_operations;
-extern struct file_operations umsdos_dir_operations;
-extern struct file_operations umsdos_rdir_operations;
-
-#include <linux/umsdos_fs.p>
-
-#endif                         /* __KERNEL__ */
-
-#endif
diff --git a/include/linux/umsdos_fs.p b/include/linux/umsdos_fs.p
deleted file mode 100644 (file)
index 1c284c5..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-/* check.c 23/01/95 03.38.30 */
-void check_page_tables (void);
-
-/* dir.c 22/06/95 00.22.12 */
-int  dummy_dir_read ( struct file *filp,
-        char *buf,
-        size_t size,
-        loff_t *count);
-char * umsdos_d_path(struct dentry *, char *, int);
-void umsdos_lookup_patch_new(struct dentry *, struct umsdos_info *);
-int umsdos_is_pseudodos (struct inode *dir, struct dentry *dentry);
-struct dentry *umsdos_lookup_x ( struct inode *dir, struct dentry *dentry, int nopseudo);
-struct dentry *UMSDOS_lookup(struct inode *, struct dentry *, struct nameidata *);
-struct dentry *umsdos_lookup_dentry(struct dentry *, char *, int, int);
-struct dentry *umsdos_covered(struct dentry *, char *, int);
-
-struct dentry *umsdos_solve_hlink (struct dentry *hlink);
-
-/* emd.c 22/06/95 00.22.04 */
-struct dentry *umsdos_get_emd_dentry(struct dentry *);
-int umsdos_have_emd(struct dentry *);
-int umsdos_make_emd(struct dentry *);
-int umsdos_emd_dir_readentry (struct dentry *, loff_t *, struct umsdos_dirent *);
-int umsdos_newentry (struct dentry *, struct umsdos_info *);
-int umsdos_newhidden (struct dentry *, struct umsdos_info *);
-int umsdos_delentry (struct dentry *, struct umsdos_info *, int);
-int umsdos_findentry (struct dentry *, struct umsdos_info *, int);
-int umsdos_isempty (struct dentry *);
-int umsdos_writeentry (struct dentry *, struct umsdos_info *, int);
-
-/* file.c 25/01/95 02.25.38 */
-
-/* inode.c 12/06/95 09.49.40 */
-void fill_new_filp (struct file *filp, struct dentry *dentry);
-void UMSDOS_read_inode (struct inode *);
-void UMSDOS_write_inode (struct inode *, int);
-int UMSDOS_notify_change (struct dentry *, struct iattr *attr);
-int umsdos_notify_change_locked(struct dentry *, struct iattr *attr);
-void UMSDOS_put_inode (struct inode *);
-int UMSDOS_statfs (struct super_block *, struct statfs *);
-struct super_block *UMSDOS_read_super (struct super_block *, void *, int);
-void UMSDOS_put_super (struct super_block *);
-
-void umsdos_setup_dir(struct dentry *);
-void umsdos_set_dirinfo_new(struct dentry *, off_t);
-void umsdos_patch_dentry_inode (struct dentry *, off_t);
-int umsdos_get_dirowner (struct inode *inode, struct inode **result);
-
-/* ioctl.c 22/06/95 00.22.08 */
-int UMSDOS_ioctl_dir (struct inode *dir,
-        struct file *filp,
-        unsigned int cmd,
-        unsigned long data);
-
-/* mangle.c 25/01/95 02.25.38 */
-void umsdos_manglename (struct umsdos_info *info);
-int umsdos_evalrecsize (int len);
-int umsdos_parse (const char *name,int len, struct umsdos_info *info);
-
-/* namei.c 25/01/95 02.25.38 */
-void umsdos_lockcreate (struct inode *dir);
-void umsdos_startlookup (struct inode *dir);
-void umsdos_unlockcreate (struct inode *dir);
-void umsdos_endlookup (struct inode *dir);
-
-int umsdos_readlink_x (             struct dentry *dentry,
-                            char *buffer,
-                            int bufsiz);
-int UMSDOS_symlink (struct inode *dir,
-                   struct dentry *dentry,
-                   const char *symname);
-int UMSDOS_link (struct dentry *olddentry,
-                struct inode *dir,
-                struct dentry *dentry);
-int UMSDOS_create (struct inode *dir,
-                  struct dentry *dentry,
-                  int mode);
-
-int UMSDOS_mkdir (struct inode *dir,
-                 struct dentry *dentry,
-                 int mode);
-int UMSDOS_mknod (struct inode *dir,
-                 struct dentry *dentry,
-                 int mode,
-                 dev_t rdev);
-int UMSDOS_rmdir (struct inode *dir,struct dentry *dentry);
-int UMSDOS_unlink (struct inode *dir, struct dentry *dentry);
-int UMSDOS_rename (struct inode *old_dir,
-                  struct dentry *old_dentry,
-                  struct inode *new_dir,
-                  struct dentry *new_dentry);
-
-/* rdir.c 22/03/95 03.31.42 */
-struct dentry *umsdos_rlookup_x (struct inode *dir, struct dentry *dentry, int nopseudo);
-struct dentry *UMSDOS_rlookup (struct inode *dir, struct dentry *dentry, struct nameidata *nd);
-
-static inline struct umsdos_inode_info *UMSDOS_I(struct inode *inode)
-{
-       return &inode->u.umsdos_i;
-}
diff --git a/include/linux/umsdos_fs_i.h b/include/linux/umsdos_fs_i.h
deleted file mode 100644 (file)
index f4c992b..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-#ifndef UMSDOS_FS_I_H
-#define UMSDOS_FS_I_H
-
-#ifndef _LINUX_TYPES_H
-#include <linux/types.h>
-#endif
-
-#include <linux/msdos_fs_i.h>
-#include <linux/pipe_fs_i.h>
-
-/* #Specification: strategy / in memory inode
- * Here is the information specific to the inode of the UMSDOS file
- * system. This information is added to the end of the standard struct
- * inode. Each file system has its own extension to struct inode,
- * so do the umsdos file system.
- * 
- * The strategy is to have the umsdos_inode_info as a superset of
- * the msdos_inode_info, since most of the time the job is done
- * by the msdos fs code.
- * 
- * So we duplicate the msdos_inode_info, and add our own info at the
- * end.
- * 
- * The offset in this EMD file of the entry: pos
- * 
- * For directory, we have dir_locking_info to help synchronise
- * file creation and file lookup. See also msdos_fs_i.h for more 
- * information about msdos_inode_info.
- * 
- * Special file and fifo do have an inode which correspond to an
- * empty MSDOS file.
- * 
- * symlink are processed mostly like regular file. The content is the
- * link.
- * 
- * The UMSDOS specific extension is placed after the union.
- */
-
-struct dir_locking_info {
-       wait_queue_head_t p;
-       short int looking;      /* How many process doing a lookup */
-       short int creating;     /* Is there any creation going on here
-                                *  Only one at a time, although one
-                                *  may recursively lock, so it is a counter
-                                */
-       long pid;               /* pid of the process owning the creation
-                                * lock */
-};
-
-struct umsdos_inode_info {
-       struct msdos_inode_info msdos_info;
-       struct dir_locking_info dir_info;
-       int i_patched;          /* Inode has been patched */
-       int i_is_hlink;         /* Resolved hardlink inode? */
-       off_t pos;              /* Entry offset in the emd_owner file */
-};
-
-#endif