Import 1.3.291.3.29
authorLinus Torvalds<torvalds@linuxfoundation.org>
Fri, 23 Nov 2007 20:10:15 +0000 (23 15:10 -0500)
committerLinus Torvalds<torvalds@linuxfoundation.org>
Fri, 23 Nov 2007 20:10:15 +0000 (23 15:10 -0500)
48 files changed:
Documentation/devices.tex
Documentation/devices.txt
Documentation/modules.txt
Documentation/scsi.txt[new file with mode: 0644]
Makefile
Rules.make
arch/alpha/Makefile
arch/alpha/boot/Makefile
arch/alpha/config.in
arch/alpha/kernel/traps.c
arch/alpha/mm/init.c
arch/i386/config.in
arch/i386/kernel/setup.c
arch/i386/mm/init.c
drivers/block/genhd.c
drivers/net/slip.c
drivers/pci/pci.c
drivers/scsi/53c7,8xx.c
drivers/scsi/Makefile
drivers/scsi/eata_dma.c
drivers/scsi/eata_dma.h
drivers/scsi/eata_dma_proc.c
drivers/scsi/eata_pio.c
drivers/scsi/hosts.c
drivers/scsi/qlogic.c
drivers/scsi/scsi.h
drivers/scsi/st.c
drivers/scsi/st.h
drivers/scsi/st_options.h
drivers/sound/soundcard.c
fs/binfmt_elf.c
fs/buffer.c
fs/proc/array.c
fs/proc/link.c
fs/proc/mem.c
fs/proc/root.c
include/asm-alpha/page.h
include/asm-alpha/pgtable.h
include/asm-i386/page.h
include/asm-i386/pgtable.h
include/linux/kdev_t.h
include/linux/pci.h
include/linux/proc_fs.h
ipc/shm.c
kernel/ksyms.c
mm/filemap.c
mm/memory.c
mm/swap.c

index 32ceb90..ab0e1eb 100644 (file)
@@ -42,7+42,7 @@ foo \kill}%
 %
 \title{{\bf Linux Allocated Devices}}
 \author{Maintained by H. Peter Anvin $<$Peter.Anvin@linux.org$>$}
-\date{Last revised: September 6, 1995}
+\date{Last revised: September 20, 1995}
 \maketitle
 %
 \noindent
@@ -138,8+138,10 @@ an unreasonable effort.
 \major{  }{}{block}{Third IDE hard disk/CD-ROM interface}
 \major{34}{}{char }{Z8530 HDLC driver}
 \major{  }{}{block}{Fourth IDE hard disk/CD-ROM interface}
-\major{35}{}{block}{Modular RAM disk}
-\major{36--223}{}{}{Unallocated}
+\major{35}{}{char }{tclmidi MIDI driver}
+\major{  }{}{block}{Modular RAM disk}
+\major{36}{}{block}{MCA ESDI hard disk}
+\major{37--223}{}{}{Unallocated}
 \major{224--254}{}{}{Local use}
 \major{255}{}{}{Reserved}
 \end{devicelist}
@@ -318,9+320,9 @@ NOTE: These devices permit both read and write access.
 \end{devicelist}
 
 \noindent
-Partitions are handled in the same way as for IDE
-disks (see major number 3) except that the limit on
-logical partitions is 11 rather than 59 per disk.
+Partitions are handled in the same way as for IDE disks (see major
+number 3) except that the limit on logical partitions is 11 rather
+than 59 per disk.
 
 \begin{devicelist}
 \major{ 9}{}{char }{SCSI tape devices}
@@ -401,8+403,8 @@ names for these devices, please let me know.
 \end{devicelist}
 
 \noindent
-Partitions are handled in the same way as IDE disks
-(see major number 3).
+Partitions are handled in the same way as for IDE disks (see major
+number 3).
 
 \begin{devicelist}
 \major{14}{}{char }{Sound card}
@@ -430,8+432,8 @@ Partitions are handled in the same way as IDE disks
 \end{devicelist}
 
 \noindent
-Partitions are handled in the same way as IDE disks
-(see major number 3).
+Partitions are handled in the same way as for IDE disks (see major
+number 3).
 
 \begin{devicelist}
 \major{15}{}{char }{Joystick}
@@ -517,8+519,8 @@ See the Double documentation for an explanation of the ``mirror'' devices.
 \end{devicelist}
 
 \noindent
-Partitions are handled the same way as for the first
-interface (see major number 3).
+Partitions are handled the same way as for the first interface (see
+major number 3).
 
 \begin{devicelist}
 \major{23}{}{char }{Digiboard serial card -- alternate devices}
@@ -621,9+623,9 @@ interface (see major number 3).
 \end{devicelist}
 
 \noindent
-Partitions are handled in the same way as for IDE
-disks (see major number 3) except that the limit on
-logical partitions is 11 rather than 59 per disk.
+Partitions are handled in the same way as for IDE disks (see major
+number 3) except that the limit on logical partitions is 11 rather
+than 59 per disk.
 
 \begin{devicelist}
 \major{29}{}{char }{Universal frame buffer}
@@ -702,6+704,7 @@ support reading only.
        \minor{0}{/dev/ttyX0}{First Specialix port}
        \minor{1}{/dev/ttyX1}{Second Specialix port}
        \minordots
+\\
 \major{  }{}{block}{Philips LMS CM-206 CD-ROM}
        \minor{0}{/dev/cm206cd}{Philips LMS CM-206 CD-ROM}
 \end{devicelist}
@@ -711,6+714,7 @@ support reading only.
        \minor{0}{/dev/cux0}{Callout device corresponding to {\file ttyX0}}
        \minor{1}{/dev/cux1}{Callout device corresponding to {\file ttyX1}}
        \minordots
+\\
 \major{  }{}{block}{Third IDE hard disk/CD-ROM interface}
        \minor{0}{/dev/hde}{Master: whole disk (or CD-ROM)}
        \minor{64}{/dev/hdf}{Slave: whole disk (or CD-ROM)}
@@ -727,6+731,13 @@ major number 3).
        \minor{2}{/dev/sc3}{Second Z8530, first port}
        \minor{3}{/dev/sc4}{Second Z8530, second port}
        \minordots
+\end{devicelist}
+
+\noindent
+The author has indicated that the device names will change in a
+subsequent version; {\file /dev/sc1} will become {\file /dev/scc0} etc.
+
+\begin{devicelist}
 \major{  }{}{block}{Fourth IDE hard disk/CD-ROM interface}
        \minor{0}{/dev/hdg}{Master: whole disk (or CD-ROM)}
        \minor{64}{/dev/hdh}{Slave: whole disk (or CD-ROM)}
@@ -737,7+748,21 @@ Partitions are handled the same way as for the first interface (see
 major number 3).
 
 \begin{devicelist}
-\major{35}{}{block}{Modular RAM disk}
+\major{35}{}{char }{tclmidi MIDI driver}
+       \minor{0}{/dev/midi0}{First MIDI port, kernel timed}
+       \minor{1}{/dev/midi1}{Second MIDI port, kernel timed}
+       \minor{2}{/dev/midi2}{Third MIDI port, kernel timed}
+       \minor{3}{/dev/midi3}{Fourth MIDI port, kernel timed}
+       \minor{64}{/dev/rmidi0}{First MIDI port, untimed}
+       \minor{65}{/dev/rmidi1}{Second MIDI port, untimed}
+       \minor{66}{/dev/rmidi2}{Third MIDI port, untimed}
+       \minor{67}{/dev/rmidi3}{Fourth MIDI port, untimed}
+       \minor{128}{/dev/smpte0}{First MIDI port, SMPTE timed}
+       \minor{129}{/dev/smpte1}{Second MIDI port, SMPTE timed}
+       \minor{130}{/dev/smpte2}{Third MIDI port, SMPTE timed}
+       \minor{131}{/dev/smpte3}{Fourth MIDI port, SMPTE timed}
+\\
+\major{  }{}{block}{Modular RAM disk}
        \minor{0}{/dev/ram0}{First modular RAM disk}
        \minor{1}{/dev/ram1}{Second modular RAM disk}
        \minordots
@@ -745,7+770,18 @@ major number 3).
 \end{devicelist}
 
 \begin{devicelist}
-\major{36}{--223}{}{Unallocated}
+\major{36}{}{block}{MCA ESDI hard disk}
+       \minor{0}{/dev/eda}{First ESDI disk whole disk}
+       \minor{64}{/dev/edb}{Second ESDI disk whole disk}
+       \minordots
+\end{devicelist}
+
+\noindent
+Partitions are handled the same way as for IDE disks (see major number
+3).
+
+\begin{devicelist}
+\major{37}{--223}{}{Unallocated}
 \end{devicelist}
 
 \begin{devicelist}
index cad73fa..0200ff3 100644 (file)
@@ -2,7+2,7 @@
 
         Maintained by H. Peter Anvin <Peter.Anvin@linux.org>
 
-                  Last revised: September 6, 1995
+                  Last revised: September 20, 1995
 
 This list is the successor to Rick Miller's Linux Device List, which
 he stopped maintaining when he lost network access in 1993.  It is a
@@ -503,13+503,34 @@ an unreasonable effort.
                Partitions are handled the same way as for the first
                interface (see major number 3).
 
- 35 block      Modular RAM disk device
+ 35 char       tclmidi MIDI driver
+                 0 = /dev/midi0        First MIDI port, kernel timed
+                 1 = /dev/midi1        Second MIDI port, kernel timed
+                 2 = /dev/midi2        Third MIDI port, kernel timed
+                 3 = /dev/midi3        Fourth MIDI port, kernel timed
+                64 = /dev/rmidi0       First MIDI port, untimed
+                65 = /dev/rmidi1       Second MIDI port, untimed
+                66 = /dev/rmidi2       Third MIDI port, untimed
+                67 = /dev/rmidi3       Fourth MIDI port, untimed
+               128 = /dev/smpte0       First MIDI port, SMPTE timed
+               129 = /dev/smpte1       Second MIDI port, SMPTE timed
+               130 = /dev/smpte2       Third MIDI port, SMPTE timed
+               131 = /dev/smpte3       Fourth MIDI port, SMPTE timed
+    block      Modular RAM disk device
                  0 = /dev/ram0         First modular RAM disk
                  1 = /dev/ram1         Second modular RAM disk
                      ...
                255 = /dev/ram255       256th modular RAM disk
 
- 36-223                UNALLOCATED
+ 36 block      MCA ESDI hard disk
+                 0 = /dev/eda          First ESDI disk whole disk
+                64 = /dev/edb          Second ESDI disk whole disk
+                     ...
+
+               Partitions are handled in the same way as IDE disks
+               (see major number 3).
+
+ 37-223                UNALLOCATED
 
 224-254                LOCAL USE
                Allocated for local/experimental use
index c7b976c..21c41d8 100644 (file)
@@ -34,7+34,9 @@ The set of modules is rapidly increasing, but so far these are known:
        Most filesystems: minix, xiafs, msdos, umsdos, sysv, isofs, hpfs,
                          smbfs, nfs
 
-       Some SCSI drivers: aha1542, in2000
+       Mid-level SCSI support (required by top and low level scsi drivers).
+       Most low-level SCSI drivers: (i.e. aha1542, in2000)
+       All SCSI high-level drivers: disk, tape, cdrom, generic.
 
        Some ethernet drivers:
                plip, slip, dummy,
diff --git a/Documentation/scsi.txt b/Documentation/scsi.txt
new file mode 100644 (file)
index 0000000..1ce285f
--- /dev/null
@@ -0,0 +1,30 @@
+
+       The scsi support in the linux kernel can be modularized in a
+number of different ways depending upon the needs of the end user.  To
+understand  your options, we should first define a few terms.
+
+       The scsi-core contains the core of scsi support.  Without it
+you can do nothing with any of the other scsi drivers.  The scsi core
+support can be a module (scsi_mod.o), or it can be build into the kernel.
+If the core is a module, it must be the first scsi module loaded, and
+if you unload the modules, it will have to be the last one unloaded.
+
+       The individual upper and lower level drivers can be loaded in any
+order once the scsi core is present in the kernel (either compiled in
+or loaded as a module).  The disk driver (sd_mod.o), cdrom driver (sr_mod.o),
+tape driver (st.o) and scsi generics driver (sg.o) represent the upper level
+drivers to support the various assorted devices which can be controlled.
+You can for example load the tape driver to use the tape drive, and then
+unload it once you have no further need for the driver (and release the
+associated memory).
+
+       The lower level drivers are the ones that support the
+individual cards that are supported for the hardware platform that you
+are running under.  Examples are aha1542.o to drive Adaptec 1542
+cards.  Rather than list the drivers which *can* be modularized, it is
+easier to list the ones which cannot, since the list only contains a
+few entries.  The drivers which have NOT been modularized are:
+
+       NCR5380 boards of one kind or another including PAS16,
+               Trantor T128/128F/228, 
+
index 86a265a..6eea7dd 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,6+1,6 @@
 VERSION = 1
 PATCHLEVEL = 3
-SUBLEVEL = 28
+SUBLEVEL = 29
 
 ARCH = i386
 
index e596ccd..f9af348 100644 (file)
@@ -92,12+92,13 @@ ifdef MOD_SUB_DIRS
        set -e; for i in $(MOD_SUB_DIRS); do $(MAKE) -C $$i modules; done
 endif
 ifneq "$(strip $(MOD_LIST_NAME))" ""
-ifndef M_OBJS # Hack for fs subdirectories
        rm -f $$TOPDIR/modules/$(MOD_LIST_NAME)
+ifdef MOD_SUB_DIRS
        for i in $(MOD_SUB_DIRS); do \
            echo `basename $$i`.o >> $$TOPDIR/modules/$(MOD_LIST_NAME); done
-else
-       echo $(M_OBJS) > $$TOPDIR/modules/$(MOD_LIST_NAME)
+endif
+ifdef M_OBJS
+       echo $(M_OBJS) >> $$TOPDIR/modules/$(MOD_LIST_NAME)
 endif
 endif
 ifdef M_OBJS
index a09d02b..d7783d7 100644 (file)
 NM := nm -B
 
 # enable this for linking under OSF/1:
-LINKFLAGS = -non_shared -T 0xfffffc0000310000 -N
+#LINKFLAGS = -non_shared -T 0xfffffc0000310000 -N
 # enable this for linking under Linux:
-#LINKFLAGS = -static -T arch/alpha/vmlinux.lds -N
+LINKFLAGS = -static -T arch/alpha/vmlinux.lds -N
 
 CFLAGS := $(CFLAGS) -mno-fp-regs
 
index 6fc2535..4f0ed68 100644 (file)
@@ -9,9+9,9 @@
 #
 
 # enable this for linking under OSF/1:
-LINKFLAGS = -non_shared -T 0x20000000 -N
+#LINKFLAGS = -non_shared -T 0x20000000 -N
 # enable this for linking under Linux:
-#LINKFLAGS = -static -T bootloader.lds -N 
+LINKFLAGS = -static -T bootloader.lds -N 
 
 .S.s:
        $(CC) -D__ASSEMBLY__ -traditional -E -o $*.o $<
@@ -32,9+32,9 @@ vmlinux.gz: vmlinux
        gzip -fv vmlinux
 
 vmlinux: tools/build $(TOPDIR)/vmlinux
-       tools/build -v $(TOPDIR)/vmlinux > vmlinux
-#      cp $(TOPDIR)/vmlinux vmlinux
-#      quickstrip vmlinux
+#      tools/build -v $(TOPDIR)/vmlinux > vmlinux
+       cp $(TOPDIR)/vmlinux vmlinux
+       quickstrip vmlinux
 
 tools/lxboot: tools/build
        tools/build > tools/lxboot
index 87b77f0..1e7b253 100644 (file)
@@ -6,7+6,7 @@
 comment 'General setup'
 
 tristate 'Normal floppy disk support' CONFIG_BLK_DEV_FD y
-bool 'Normal (MFM/RLL) disk and IDE disk/cdrom support' CONFIG_ST506 n
+bool 'Normal (MFM/RLL) disk and IDE disk/cdrom support' CONFIG_ST506 y
 if [ "$CONFIG_ST506" = "y" ]; then
   comment 'Please see drivers/block/README.ide for help/info on IDE drives'
   bool '   Use old disk-only driver for primary i/f' CONFIG_BLK_DEV_HD n
@@ -29,7+29,7 @@ choice 'Alpha system type' \
         EB66           CONFIG_ALPHA_EB66               \
         EB66+          CONFIG_ALPHA_EB66P              \
         EB64           CONFIG_ALPHA_EB64               \
-        EB64+          CONFIG_ALPHA_EB64P" Jensen
+        EB64+          CONFIG_ALPHA_EB64P" Cabriolet
 if [ "$CONFIG_ALPHA_NONAME" = "y" ]; then
        define_bool CONFIG_PCI y
        define_bool CONFIG_ALPHA_LCA y
@@ -110,7+110,7 @@ comment 'SCSI low-level drivers'
 
 dep_tristate 'Adaptec AHA152X support' CONFIG_SCSI_AHA152X n $CONFIG_SCSI
 dep_tristate 'Adaptec AHA1542 support' CONFIG_SCSI_AHA1542 n $CONFIG_SCSI
-dep_tristate 'Adaptec AHA1740 support' CONFIG_SCSI_AHA1740 y $CONFIG_SCSI
+dep_tristate 'Adaptec AHA1740 support' CONFIG_SCSI_AHA1740 n $CONFIG_SCSI
 dep_tristate 'Adaptec AHA274X/284X/294X support' CONFIG_SCSI_AIC7XXX n $CONFIG_SCSI
 dep_tristate 'BusLogic SCSI support' CONFIG_SCSI_BUSLOGIC n $CONFIG_SCSI
 dep_tristate 'EATA-DMA (DPT, NEC, ATT, Olivetti) support' CONFIG_SCSI_EATA_DMA n $CONFIG_SCSI
@@ -119,7+119,7 @@ dep_tristate 'UltraStor 14F/34F support' CONFIG_SCSI_U14_34F n $CONFIG_SCSI
 dep_tristate 'Future Domain 16xx SCSI support' CONFIG_SCSI_FUTURE_DOMAIN n $CONFIG_SCSI
 bool 'Generic NCR5380 SCSI support' CONFIG_SCSI_GENERIC_NCR5380 n
 if [ "$CONFIG_PCI" = "y" ]; then
-  dep_tristate 'NCR53c7,8xx SCSI support'  CONFIG_SCSI_NCR53C7xx n $CONFIG_SCSI
+  dep_tristate 'NCR53c7,8xx SCSI support'  CONFIG_SCSI_NCR53C7xx y $CONFIG_SCSI
 fi
 dep_tristate 'Always IN2000 SCSI support (test release)' CONFIG_SCSI_IN2000 n $CONFIG_SCSI
 bool 'PAS16 SCSI support' CONFIG_SCSI_PAS16 n
@@ -176,7+176,7 @@ if [ "$CONFIG_NET_VENDOR_3COM" = "y" ]; then
        fi
        tristate '3c509/3c579 support' CONFIG_EL3 y
 fi
-bool 'Other ISA cards' CONFIG_NET_ISA y
+bool 'Other ISA cards' CONFIG_NET_ISA n
 if [ "$CONFIG_NET_ISA" = "y" ]; then
        tristate 'Cabletron E21xx support' CONFIG_E2100 n
        tristate 'DEPCA support' CONFIG_DEPCA y
@@ -199,17+199,17 @@ if [ "$CONFIG_NET_ISA" = "y" ]; then
        tristate 'NE2000/NE1000 support' CONFIG_NE2000 n
        bool 'SK_G16 support' CONFIG_SK_G16 n
 fi
-bool 'EISA, VLB, PCI and on board controllers' CONFIG_NET_EISA n
+bool 'EISA, VLB, PCI and on board controllers' CONFIG_NET_EISA y
 if [ "$CONFIG_NET_EISA" = "y" ]; then
        if [ "$CONFIG_NET_ALPHA" = "y" ]; then
                tristate 'Ansel Communications EISA 3200 support' CONFIG_AC3200 n
        fi
        tristate 'Apricot Xen-II on board ethernet' CONFIG_APRICOT n
-       tristate 'DE425, DE434, DE435, DE500 support' CONFIG_DE4X5 n
+       tristate 'DE425, DE434, DE435, DE500 support' CONFIG_DE4X5 y
 #      tristate 'DEC 21040 PCI support' CONFIG_DEC_ELCP n
 #      bool 'LPL T100V 100Mbs support' CONFIG_LPL_T100 n
 #      bool 'PCnet32 (32 bit VLB and PCI LANCE) support' CONFIG_PCNET32 n
-       bool 'Zenith Z-Note support' CONFIG_ZNET y
+       bool 'Zenith Z-Note support' CONFIG_ZNET n
 fi
 bool 'Pocket and portable adaptors' CONFIG_NET_POCKET n
 if [ "$CONFIG_NET_POCKET" = "y" ]; then
index 2a29b02..055a933 100644 (file)
@@ -42,9+42,7 @@ void die_if_kernel(char * str, struct pt_regs * regs, long err)
        for (i = -3; i < 6; i++)
                printk("%c%08x%c",i?' ':'<',pc[i],i?' ':'>');
        printk("\n");
-       for (i = 0 ; i < 5000000000 ; i++)
-               /* pause */;
-       halt();
+       do_exit(SIGSEGV);
 }
 
 asmlinkage void do_entArith(unsigned long summary, unsigned long write_mask,
index 62203ef..6ab5a18 100644 (file)
@@ -68,12+68,12 @@ void show_mem(void)
        i = MAP_NR(high_memory);
        while (i-- > 0) {
                total++;
-               if (mem_map[i] & MAP_PAGE_RESERVED)
+               if (mem_map[i].reserved)
                        reserved++;
-               else if (!mem_map[i])
+               else if (!mem_map[i].count)
                        free++;
                else
-                       shared += mem_map[i]-1;
+                       shared += mem_map[i].count-1;
        }
        printk("%d pages of RAM\n",total);
        printk("%d free pages\n",free);
@@ -127,7+127,7 @@ unsigned long paging_init(unsigned long start_mem, unsigned long end_mem)
                        continue;
 
                while (nr--)
-                       mem_map[pfn++] = 0;
+                       mem_map[pfn++].reserved = 0;
        }
 
        /* unmap the console stuff: we don't need it, and we don't want it */
@@ -158,7+158,7 @@ void mem_init(unsigned long start_mem, unsigned long end_mem)
         */
        tmp = KERNEL_START;
        while (tmp < start_mem) {
-               mem_map[MAP_NR(tmp)] = MAP_PAGE_RESERVED;
+               mem_map[MAP_NR(tmp)].reserved = 1;
                tmp += PAGE_SIZE;
        }
 
@@ -171,9+171,9 @@ void mem_init(unsigned long start_mem, unsigned long end_mem)
 #endif
 
        for (tmp = PAGE_OFFSET ; tmp < high_memory ; tmp += PAGE_SIZE) {
-               if (mem_map[MAP_NR(tmp)])
+               if (mem_map[MAP_NR(tmp)].reserved)
                        continue;
-               mem_map[MAP_NR(tmp)] = 1;
+               mem_map[MAP_NR(tmp)].count = 1;
                free_page(tmp);
        }
        tmp = nr_free_pages << PAGE_SHIFT;
@@ -191,12+191,12 @@ void si_meminfo(struct sysinfo *val)
        val->freeram = nr_free_pages << PAGE_SHIFT;
        val->bufferram = buffermem;
        while (i-- > 0)  {
-               if (mem_map[i] & MAP_PAGE_RESERVED)
+               if (mem_map[i].reserved)
                        continue;
                val->totalram++;
-               if (!mem_map[i])
+               if (!mem_map[i].count)
                        continue;
-               val->sharedram += mem_map[i]-1;
+               val->sharedram += mem_map[i].count-1;
        }
        val->totalram <<= PAGE_SHIFT;
        val->sharedram <<= PAGE_SHIFT;
index 8662c5c..0784f36 100644 (file)
@@ -34,7+34,7 @@ fi
 bool 'System V IPC' CONFIG_SYSVIPC y
 tristate 'Kernel support for ELF binaries' CONFIG_BINFMT_ELF y
 if [ "$CONFIG_BINFMT_ELF" = "y" ]; then
-bool 'Compile kernel as ELF - if your GCC is ELF-GCC' CONFIG_KERNEL_ELF n
+bool 'Compile kernel as ELF - if your GCC is ELF-GCC' CONFIG_KERNEL_ELF y
 fi
 #bool 'Use -mpentium flag for Pentium-specific optimizations' CONFIG_M586 n
 #if [ "$CONFIG_M586" = "n" ]; then
index a463716..727df0c 100644 (file)
 #include <linux/tty.h>
 #include <linux/ioport.h>
 #include <linux/delay.h>
+#include <linux/config.h>
 
 #include <asm/segment.h>
 #include <asm/system.h>
index 2a5f4f5..7ba06cf 100644 (file)
@@ -73,12+73,12 @@ void show_mem(void)
        i = high_memory >> PAGE_SHIFT;
        while (i-- > 0) {
                total++;
-               if (mem_map[i] & MAP_PAGE_RESERVED)
+               if (mem_map[i].reserved)
                        reserved++;
-               else if (!mem_map[i])
+               else if (!mem_map[i].count)
                        free++;
                else
-                       shared += mem_map[i]-1;
+                       shared += mem_map[i].count-1;
        }
        printk("%d pages of RAM\n",total);
        printk("%d free pages\n",free);
@@ -192,12+192,12 @@ void mem_init(unsigned long start_mem, unsigned long end_mem)
         * controller as well..
         */
        while (start_low_mem < 0x9f000) {
-               mem_map[MAP_NR(start_low_mem)] = 0;
+               mem_map[MAP_NR(start_low_mem)].reserved = 0;
                start_low_mem += PAGE_SIZE;
        }
 
        while (start_mem < high_memory) {
-               mem_map[MAP_NR(start_mem)] = 0;
+               mem_map[MAP_NR(start_mem)].reserved = 0;
                start_mem += PAGE_SIZE;
        }
 #ifdef CONFIG_SCSI
@@ -207,7+207,7 @@ void mem_init(unsigned long start_mem, unsigned long end_mem)
        sound_mem_init();
 #endif
        for (tmp = 0 ; tmp < high_memory ; tmp += PAGE_SIZE) {
-               if (mem_map[MAP_NR(tmp)]) {
+               if (mem_map[MAP_NR(tmp)].reserved) {
                        if (tmp >= 0xA0000 && tmp < 0x100000)
                                reservedpages++;
                        else if (tmp < (unsigned long) &_etext)
@@ -216,7+216,7 @@ void mem_init(unsigned long start_mem, unsigned long end_mem)
                                datapages++;
                        continue;
                }
-               mem_map[MAP_NR(tmp)] = 1;
+               mem_map[MAP_NR(tmp)].count = 1;
                free_page(tmp);
        }
        tmp = nr_free_pages << PAGE_SHIFT;
@@ -249,12+249,12 @@ void si_meminfo(struct sysinfo *val)
        val->freeram = nr_free_pages << PAGE_SHIFT;
        val->bufferram = buffermem;
        while (i-- > 0)  {
-               if (mem_map[i] & MAP_PAGE_RESERVED)
+               if (mem_map[i].reserved)
                        continue;
                val->totalram++;
-               if (!mem_map[i])
+               if (!mem_map[i].count)
                        continue;
-               val->sharedram += mem_map[i]-1;
+               val->sharedram += mem_map[i].count-1;
        }
        val->totalram <<= PAGE_SHIFT;
        val->sharedram <<= PAGE_SHIFT;
index d99f675..5cfa298 100644 (file)
@@ -79,11+79,12 @@ static void extended_partition(struct gendisk *hd, kdev_t dev)
 {
        struct buffer_head *bh;
        struct partition *p;
-       unsigned long first_sector, this_sector, this_size;
+       unsigned long first_sector, first_size, this_sector, this_size;
        int mask = (1 << hd->minor_shift) - 1;
        int i;
 
        first_sector = hd->part[MINOR(dev)].start_sect;
+       first_size = hd->part[MINOR(dev)].nr_sects;
        this_sector = first_sector;
 
        while (1) {
@@ -122,7+123,13 @@ static void extended_partition(struct gendisk *hd, kdev_t dev)
                    if (!p->nr_sects || p->sys_ind == EXTENDED_PARTITION)
                      continue;
 
-                   if (p->start_sect + p->nr_sects > this_size)
+                   /* Check the 3rd and 4th entries -
+                      these sometimes contain random garbage */
+                   if (i >= 2
+                       && p->start_sect + p->nr_sects > this_size
+                       && (this_sector + p->start_sect < first_sector ||
+                           this_sector + p->start_sect + p->nr_sects >
+                            first_sector + first_size))
                      continue;
 
                    add_partition(hd, current_minor, this_sector+p->start_sect, p->nr_sects);
index 1cc6e3d..724e33c 100644 (file)
@@ -1163,15+1163,14 @@ slip_init_ctrl_dev(struct device *dummy)
        }
 
 
-       /* If not loadable module, a bootstrap Space.c slip_proto dev
-        *  now needs to be unregistered.
+#ifdef MODULE
+       return status;
+#else
+       /* Return "not found", so that dev_init() will unlink
+        * the placeholder device entry for us.
         */
-#ifndef MODULE
-/*     printk("SLIP: Unregistering bootstrap device "
-              "'slip_proto' - slip OK\n");*/
-       unregister_netdev(dummy);
+       return ENODEV;
 #endif
-       return status;
       }
 
 
index b8c9299..b76b8b0 100644 (file)
@@ -83,6+83,8 @@ struct pci_dev_info dev_info[] = {
        DEVICE( SI,             SI_501,         "85C501"),
        DEVICE( SI,             SI_496,         "85C496"),
        DEVICE( SI,             SI_601,         "85C601"),
+       DEVICE( SI,             SI_5511,                "85C5511"),
+       DEVICE( SI,             SI_5513,                "85C5513"),
        DEVICE( HP,             HP_J2585A,      "J2585A"),
 #if 0
        DEVICE( SMC,            SMC_37C665,     "FDC 37C665"),  /* 1042 ? */
@@ -110,6+112,7 @@ struct pci_dev_info dev_info[] = {
        DEVICE( LEADTEK,        LEADTEK_805,    "S3 805"),
        DEVICE( CONTAQ,         CONTAQ_82C599,  "82C599"),
        DEVICE( CMD,            CMD_640,        "640 (buggy)"),
+       DEVICE( CMD,            CMD_646,        "646"),
        DEVICE( VISION,         VISION_QD8500,  "QD-8500"),
        DEVICE( VISION,         VISION_QD8580,  "QD-8580"),
        DEVICE( WINBOND,        WINBOND_83769,  "W83769F"),
@@ -123,6+126,7 @@ struct pci_dev_info dev_info[] = {
        DEVICE( AL,             AL_M1461,       "M1461"),
        DEVICE( AL,             AL_M4803,       "M4803"),
        DEVICE( IMS,            IMS_8849,       "8849"),
+       DEVICE( REALTEK,        REALTEK_8300,   "ENW-8300C"),
        DEVICE( VIA,            VIA_82C505,     "VT 82C505"),
        DEVICE( VIA,            VIA_82C561,     "VT 82C561"),
        DEVICE( VIA,            VIA_82C576,     "VT 82C576 3V"),
index d8603ef..03f3624 100644 (file)
@@ -994,6+994,8 @@ int NCR53c7xx_detect(Scsi_Host_Template *tpnt) {
     unsigned char pci_bus, pci_device_fn;
     static short pci_index=0;  /* Device index to PCI BIOS calls */
 
+    tpnt->proc_dir = &proc_scsi_ncr53c7xx;
+
     for (current_override = count = 0; current_override < OVERRIDE_LIMIT; 
         ++current_override) {
         if (overrides[current_override].pci ? 
@@ -1120,7+1122,6 @@ NCR53c8x0_init_fixup (struct Scsi_Host *host) {
      * SCRIPTS.
      */
     
-    tpnt->proc_dir = &proc_scsi_ncr53c7xx;
 
     patch_abs_rwri_data (hostdata->script, 0, dmode_memory_to_memory, tmp);
     patch_abs_rwri_data (hostdata->script, 0, dmode_memory_to_ncr, memory_to_ncr);
index 140a979..c651fea 100644 (file)
@@ -38,7+38,6 @@ else
       # Create this before we build anything else.
       SCSI_MODULE_VER := scsi_syms.ver
       SYMTAB_OBJS := scsi_syms.o
-      include ../../versions.mk
       endif
     M_OBJS += scsi_mod.o
   endif
@@ -235,6+234,12 @@ endif
 
 include $(TOPDIR)/Rules.make
 
+ifeq ($(CONFIG_SCSI),m)
+  ifdef CONFIG_MODVERSIONS
+      include ../../versions.mk
+  endif
+endif
+
 aha152x.o: aha152x.c
        $(CC) $(CFLAGS) $(AHA152X) -c aha152x.c 
 
index 9c917bf..5bfbd89 100644 (file)
  * Thanks also to Greg Hosler who did a lot of testing and  *
  * found quite a number of bugs during the development.            *
  ************************************************************
- *  last change: 95/07/18                 OS: Linux 1.3.10  *
+ *  last change: 95/09/17                 OS: Linux 1.3.28  *
  ************************************************************/
 
 /* Look in eata_dma.h for configuration and revision information */
@@ -504,10+504,11 @@ int eata_queue(Scsi_Cmnd * cmd, void (* done) (Scsi_Cmnd *))
     cmd->host_scribble = (char *)&hd->ccb[y];  
     
     if(eata_send_command((u32) cp, (u32) sh->base, EATA_CMD_DMA_SEND_CP) == FALSE) {
-       cmd->result = DID_ERROR << 16;
-       printk("eata_queue target %d, pid %ld, HBA busy, returning DID_ERROR,"
-              " done.\n", cmd->target, cmd->pid);
+       cmd->result = DID_BUS_BUSY << 16;
+       printk("eata_queue target %d, pid %ld, HBA busy, returning DID_BUS_BUSY\n", 
+              cmd->target, cmd->pid);
        done(cmd);
+       cp->status = FREE;     /* Hmmm..... */
        restore_flags(flags);
        return(0);
     }
@@ -857,7+858,6 @@ short register_HBA(u32 base, struct get_conf *gc, Scsi_Host_Template * tpnt,
               "Please use the EATA-PIO driver.\n", base);
        return (FALSE);
     }
-
     if(gc->HAA_valid == FALSE || ntohl(gc->len) < 0x22) 
        gc->MAX_CHAN = 0;
     
@@ -1124,8+1124,8 @@ void find_EISA(struct get_conf *buf, Scsi_Host_Template * tpnt)
                                      (int)pal1, (int)pal2, (int)pal3));
 #endif
                if (get_conf_PIO(base, buf) == TRUE) {
-                   DBG(DBG_PROBE && DBG_EISA, print_config(buf));
                    if (buf->IRQ) {  
+                       DBG(DBG_EISA, printk("Registering EISA HBA\n"));
                        register_HBA(base, buf, tpnt, IS_EISA);
                    } else
                        printk("eata_dma: No valid IRQ. HBA removed from list\n");
@@ -1151,6+1151,7 @@ void find_ISA(struct get_conf *buf, Scsi_Host_Template * tpnt)
     for (i = 0; i < MAXISA; i++) {  
        if (ISAbases[i]) {  
            if (get_conf_PIO(ISAbases[i],buf) == TRUE){
+               DBG(DBG_ISA, printk("Registering ISA HBA\n"));
                register_HBA(ISAbases[i], buf, tpnt, IS_ISA);
            } else {
                if (check_blink_state(ISAbases[i])) 
@@ -1176,6+1177,7 @@ void find_PCI(struct get_conf *buf, Scsi_Host_Template * tpnt)
     u16 com_adr;
     u16 rev_device;
     u32 error, i, x;
+    u8 pal1, pal2, pal3;
 
     if (pcibios_present()) {
        for (i = 0; i <= MAXPCI; ++i, ++pci_index) {
@@ -1217,21+1219,26 @@ void find_PCI(struct get_conf *buf, Scsi_Host_Template * tpnt)
                /* Check if the address is valid */
                if (base & 0x01) {
                    base &= 0xfffffffe;
-                   /* EISA tag there ? */
-                   if ((inb(base) == 0x12) && (inb(base + 1) == 0x14))
-                       continue;   /* Jep, it's forced, so move on  */
-                   base += 0x10;   /* Now, THIS is the real address */
+                    /* EISA tag there ? */
+                   pal1 = inb(base);
+                   pal2 = inb(base + 1);
+                   pal3 = inb(base + 2);
+                   if (((pal1 == 0x12) && (pal2 == 0x14)) ||
+                       ((pal1 == 0x38) && (pal2 == 0xa3) && (pal3 == 0x82)) ||
+                       ((pal1 == 0x06) && (pal2 == 0x94) && (pal3 == 0x24)))
+                       base += 0x08;
+                   else
+                       base += 0x10;   /* Now, THIS is the real address */
+
                    if (base != 0x1f8) {
                        /* We didn't find it in the primary search */
                        if (get_conf_PIO(base, buf) == TRUE) {
-                           if (buf->FORCADR)   /* If the address is forced */
-                               continue;       /* we'll find it later      */
-                           
+
                            /* OK. We made it till here, so we can go now  
                             * and register it. We  only have to check and 
                             * eventually remove it from the EISA and ISA list 
                             */
-                           
+                           DBG(DBG_PCI, printk("Registering PCI HBA\n"));
                            register_HBA(base, buf, tpnt, IS_PCI);
                            
                            if (base < 0x1000) {
index dc31aac..dc15cfd 100644 (file)
 
 #define VER_MAJOR 2
 #define VER_MINOR 5
-#define VER_SUB   "7b"
+#define VER_SUB   "8"
 
 
 /************************************************************************
@@ -73,6+73,8 @@ int eata_release(struct Scsi_Host *);
 #define eata_release NULL  
 #endif
 
+#include <linux/scsicam.h>
+
 #define EATA_DMA {                   \
         NULL, NULL,                  \
         NULL,               /* proc_dir_entry */ \
index 83d2a72..5c486c5 100644 (file)
@@ -369,7+369,7 @@ int eata_proc_info(char *buffer, char **start, off_t offset, int length,
                       SD(HBA_ptr)->writes[11]);
        len += size; 
        pos = begin + len;
-       size = sprintf(buffer+len,"Sum   : %12u %12u\n",
+       size = sprintf(buffer+len,"Sum   :%12u %12u\n",
                       SD(HBA_ptr)->reads[12], 
                       SD(HBA_ptr)->writes[12]);
        len += size; 
index 473f361..dbb857c 100644 (file)
@@ -378,11+378,12 @@ int eata_pio_queue(Scsi_Cmnd * cmd, void (*done) (Scsi_Cmnd *))
     
     if (eata_pio_send_command(base, EATA_CMD_PIO_SEND_CP)) 
     {
-       cmd->result = DID_ERROR << 16;
+       cmd->result = DID_BUS_BUSY << 16;
        printk("eata_pio_queue target %d, pid %ld, HBA busy, returning "
-               "DID_ERROR, done.\n", cmd->target, cmd->pid);
-       restore_flags(flags);
+               "DID_BUS_BUSY, done.\n", cmd->target, cmd->pid);
         done(cmd);
+        cp->status = FREE;      
+        restore_flags(flags);
        return (0);
     }
     while (!(inb(base + HA_RSTATUS) & HA_SDRQ));
index 6549132..778fb75 100644 (file)
@@ -416,7+416,7 @@ void scsi_mem_init(unsigned long memory_end)
                     Low24 += PAGE_SIZE) {
                    unsigned long ForbiddenAddress = High8 + Low24;
                    if (ForbiddenAddress >= memory_end) goto next_host;
-                   mem_map[MAP_NR(ForbiddenAddress)] = MAP_PAGE_RESERVED;
+                   mem_map[MAP_NR(ForbiddenAddress)].reserved = 1;
                }
            }
        }
index d7b05e1..b6f762d 100644 (file)
@@ -543,7+543,7 @@ int qltyp;                  /* type of chip */
 struct Scsi_Host       *hreg;  /* registered host structure */
 unsigned long  flags;
 
-tpnt->proc_dir =  &proc_scsi_qlogic;
+host->proc_dir =  &proc_scsi_qlogic;
 
 /* Qlogic Cards only exist at 0x230 or 0x330 (the chip itself decodes the
    address - I check 230 first since MIDI cards are typically at 330
index 4687e19..0b46af1 100644 (file)
@@ -510,37+510,37 @@ static Scsi_Cmnd * end_scsi_request(Scsi_Cmnd * SCpnt, int uptodate, int sectors
  * that an interrupt may start another request, so we run this with interrupts
  * turned off 
  */
-#define INIT_SCSI_REQUEST \
-    if (!CURRENT) {\
-       CLEAR_INTR; \
+#define INIT_SCSI_REQUEST       \
+    if (!CURRENT) {             \
+       CLEAR_INTR;             \
        restore_flags(flags);   \
-       return; \
-    } \
-    if (MAJOR(CURRENT->rq_dev) != MAJOR_NR) \
-       panic(DEVICE_NAME ": request list destroyed"); \
-    if (CURRENT->bh) { \
-       if (!CURRENT->bh->b_lock) \
-           panic(DEVICE_NAME ": block not locked"); \
+       return;                 \
+    }                           \
+    if (MAJOR(CURRENT->rq_dev) != MAJOR_NR)           \
+       panic(DEVICE_NAME ": request list destroyed");\
+    if (CURRENT->bh) {                                \
+       if (!CURRENT->bh->b_lock)                     \
+           panic(DEVICE_NAME ": block not locked");  \
     }
 #endif
 
 #define SCSI_SLEEP(QUEUE, CONDITION) {             \
-    if (CONDITION) {                   \
+    if (CONDITION) {                               \
        struct wait_queue wait = { current, NULL};  \
-       add_wait_queue(QUEUE, &wait);           \
-       for(;;) {                           \
+       add_wait_queue(QUEUE, &wait);               \
+       for(;;) {                                   \
        current->state = TASK_UNINTERRUPTIBLE;      \
-       if (CONDITION) {                \
-                  if (intr_count)                              \
-                     panic("scsi: trying to call schedule() in interrupt" \
-                           ", file %s, line %d.\n", __FILE__, __LINE__);  \
-          schedule();                  \
-          }                            \
-           else                        \
-                  break;                                       \
-       }                       \
-       remove_wait_queue(QUEUE, &wait);        \
-       current->state = TASK_RUNNING;          \
+       if (CONDITION) {                            \
+            if (intr_count)                        \
+               panic("scsi: trying to call schedule() in interrupt" \
+                     ", file %s, line %d.\n", __FILE__, __LINE__);  \
+           schedule();                 \
+        }                              \
+       else                            \
+           break;                      \
+       }                               \
+       remove_wait_queue(QUEUE, &wait);\
+       current->state = TASK_RUNNING;  \
     }; }
 
 #endif
index 80cc412..6263134 100644 (file)
   Copyright 1992, 1993, 1994, 1995 Kai Makisara
                 email Kai.Makisara@metla.fi
 
-  Last modified: Sun Sep 10 20:33:24 1995 by makisara@kai.makisara.fi
+  Last modified: Tue Sep 19 21:51:41 1995 by root@kai.makisara.fi
   Some small formal changes - aeb, 950809
 */
 #ifdef MODULE
@@ -74,14+74,16 @@ static int debugging = 1;
 #define TAPE_NR(x) (MINOR(x) & 127)
 
 static int st_nbr_buffers;
-static int st_req_nbr_buffers;
 static ST_buffer **st_buffers;
 static int st_buffer_size = ST_BUFFER_SIZE;
 static int st_write_threshold = ST_WRITE_THRESHOLD;
 static int st_max_buffers = ST_MAX_BUFFERS;
 
+#define MAX_SCSI_TAPES 8
 Scsi_Tape * scsi_tapes = NULL;
 
+static ST_buffer *new_tape_buffer(int);
+
 static int st_init(void);
 static int st_attach(Scsi_Device *);
 static int st_detect(Scsi_Device *);
@@ -189,7+191,7 @@ st_sleep_done (Scsi_Cmnd * SCpnt)
     if ((STp->buffer)->writing)
       SCpnt->request.rq_status = RQ_INACTIVE;
     else
-      SCpnt->request.rq_status = RQ_SCSI_BUSY;
+      SCpnt->request.rq_status = RQ_SCSI_DONE;
     if (!(STp->buffer)->writing || STp->write_pending)
       wake_up( &(STp->waiting) );
     STp->write_pending = 0;
@@ -257,13+259,13 @@ back_over_eof(kdev_t devt)
   unsigned int flags;
 
   SCpnt = allocate_device(NULL, STp->device, 1);
+  SCpnt->request.rq_dev = devt;
   cmd[0] = SPACE;
   cmd[1] = ((SCpnt->lun << 5) & 0xe0) | 0x01; /* Space FileMarks */
   cmd[2] = cmd[3] = cmd[4] = 0xff;  /* -1 filemarks */
   cmd[5] = 0;
 
-  SCpnt->request.rq_status = RQ_ACTIVE;
-  SCpnt->request.rq_dev = devt;
+  SCpnt->request.rq_status = RQ_SCSI_BUSY;
   scsi_do_cmd(SCpnt,
              (void *) cmd, (void *) (STp->buffer)->b_data, 0,
              st_sleep_done, ST_TIMEOUT, MAX_RETRIES);
@@ -271,7+273,7 @@ back_over_eof(kdev_t devt)
   /* need to do the check with interrupts off. -RAB */
   save_flags(flags);
   cli();
-  if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+  if (SCpnt->request.rq_status != RQ_SCSI_DONE)
     sleep_on( &(STp->waiting) );
   restore_flags(flags);
   
@@ -336,7+338,7 @@ flush_write_buffer(kdev_t devt)
     cmd[2] = blks >> 16;
     cmd[3] = blks >> 8;
     cmd[4] = blks;
-    SCpnt->request.rq_status = RQ_ACTIVE;
+    SCpnt->request.rq_status = RQ_SCSI_BUSY;
     SCpnt->request.rq_dev = devt;
     scsi_do_cmd (SCpnt,
                 (void *) cmd, (STp->buffer)->b_data, transfer,
@@ -345,7+347,7 @@ flush_write_buffer(kdev_t devt)
     /* this must be done with interrupts off */
     save_flags (flags);
     cli();
-    if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+    if (SCpnt->request.rq_status != RQ_SCSI_DONE)
       sleep_on( &(STp->waiting) );
     restore_flags(flags);
  
@@ -388,7+390,6 @@ flush_buffer(struct inode * inode, struct file * filp, int seek_next)
   STp = &(scsi_tapes[dev]);
   STbuffer = STp->buffer;
 
-
   /*
    * If there was a bus reset, block further access
    * to this device.
@@ -455,10+456,14 @@ scsi_tape_open(struct inode * inode, struct file * filp)
       if (!st_buffers[i]->in_use)
        break;
     if (i >= st_nbr_buffers) {
-      printk("st%d: No free buffers.\n", dev);
-      return (-EBUSY);
+      STp->buffer = new_tape_buffer(FALSE);
+      if (STp->buffer == NULL) {
+       printk("st%d: No free buffers.\n", dev);
+       return (-EBUSY);
+      }
     }
-    STp->buffer = st_buffers[i];
+    else
+      STp->buffer = st_buffers[i];
     (STp->buffer)->in_use = 1;
     (STp->buffer)->writing = 0;
     STp->in_use = 1;
@@ -479,6+484,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
 #endif
 
     SCpnt = allocate_device(NULL, STp->device, 1);
+    SCpnt->request.rq_dev = devt;
     if (!SCpnt) {
       printk("st%d: Tape request not allocated", dev);
       return (-EBUSY);
@@ -487,8+493,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
     memset ((void *) &cmd[0], 0, 10);
     cmd[0] = TEST_UNIT_READY;
     cmd[1] = (SCpnt->lun << 5) & 0xe0;
-    SCpnt->request.rq_status = RQ_ACTIVE;
-    SCpnt->request.rq_dev = devt;
+    SCpnt->request.rq_status = RQ_SCSI_BUSY;
     scsi_do_cmd(SCpnt,
                (void *) cmd, (void *) (STp->buffer)->b_data,
                0, st_sleep_done, ST_LONG_TIMEOUT,
@@ -497,7+502,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
     /* this must be done with interrupts off */
     save_flags (processor_flags);
     cli();
-    if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+    if (SCpnt->request.rq_status != RQ_SCSI_DONE)
       sleep_on( &(STp->waiting) );
     restore_flags(processor_flags);
 
@@ -507,8+512,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
       memset ((void *) &cmd[0], 0, 10);
       cmd[0] = TEST_UNIT_READY;
       cmd[1] = (SCpnt->lun << 5) & 0xe0;
-      SCpnt->request.rq_status = RQ_ACTIVE;
-      SCpnt->request.rq_dev = devt;
+      SCpnt->request.rq_status = RQ_SCSI_BUSY;
       scsi_do_cmd(SCpnt,
                  (void *) cmd, (void *) (STp->buffer)->b_data,
                  0, st_sleep_done, ST_LONG_TIMEOUT,
@@ -517,7+521,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
       /* this must be done with interrupts off */
       save_flags (processor_flags);
       cli();
-      if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+      if (SCpnt->request.rq_status != RQ_SCSI_DONE)
        sleep_on( &(STp->waiting) );
       restore_flags(processor_flags);
 
@@ -551,8+555,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
     memset ((void *) &cmd[0], 0, 10);
     cmd[0] = READ_BLOCK_LIMITS;
     cmd[1] = (SCpnt->lun << 5) & 0xe0;
-    SCpnt->request.rq_status = RQ_ACTIVE;
-    SCpnt->request.rq_dev = devt;
+    SCpnt->request.rq_status = RQ_SCSI_BUSY;
     scsi_do_cmd(SCpnt,
                (void *) cmd, (void *) (STp->buffer)->b_data,
                6, st_sleep_done, ST_TIMEOUT, MAX_READY_RETRIES);
@@ -560,7+563,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
     /* this must be done with interrupts off */
     save_flags (processor_flags);
     cli();
-    if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+    if (SCpnt->request.rq_status != RQ_SCSI_DONE)
       sleep_on( &(STp->waiting) );
     restore_flags(processor_flags);
 
@@ -587,8+590,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
     cmd[0] = MODE_SENSE;
     cmd[1] = (SCpnt->lun << 5) & 0xe0;
     cmd[4] = 12;
-    SCpnt->request.rq_status = RQ_ACTIVE;
-    SCpnt->request.rq_dev = devt;
+    SCpnt->request.rq_status = RQ_SCSI_BUSY;
     scsi_do_cmd(SCpnt,
                (void *) cmd, (void *) (STp->buffer)->b_data,
                12, st_sleep_done, ST_TIMEOUT, MAX_READY_RETRIES);
@@ -596,7+598,7 @@ scsi_tape_open(struct inode * inode, struct file * filp)
     /* this must be done with interrupts off */
     save_flags (processor_flags);
     cli();
-    if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+    if (SCpnt->request.rq_status != RQ_SCSI_DONE)
       sleep_on( &(STp->waiting) );
     restore_flags(processor_flags);
 
@@ -714,13+716,13 @@ scsi_tape_close(struct inode * inode, struct file * filp)
 
       if (result == 0 || result == (-ENOSPC)) {
        SCpnt = allocate_device(NULL, STp->device, 1);
+       SCpnt->request.rq_dev = devt;
 
        memset(cmd, 0, 10);
        cmd[0] = WRITE_FILEMARKS;
        cmd[1] = (SCpnt->lun << 5) & 0xe0;
        cmd[4] = 1 + STp->two_fm;
-       SCpnt->request.rq_status = RQ_ACTIVE;
-       SCpnt->request.rq_dev = devt;
+       SCpnt->request.rq_status = RQ_SCSI_BUSY;
        scsi_do_cmd( SCpnt,
                    (void *) cmd, (void *) (STp->buffer)->b_data,
                    0, st_sleep_done, ST_TIMEOUT, MAX_WRITE_RETRIES);
@@ -728,7+730,7 @@ scsi_tape_close(struct inode * inode, struct file * filp)
        /* this must be done with interrupts off */
        save_flags (flags);
        cli();
-       if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+       if (SCpnt->request.rq_status != RQ_SCSI_DONE)
          sleep_on( &(STp->waiting) );
        restore_flags(flags);
 
@@ -867,6+869,7 @@ st_write(struct inode * inode, struct file * filp, const char * buf, int count)
       write_threshold--;
 
     SCpnt = allocate_device(NULL, STp->device, 1);
+    SCpnt->request.rq_dev = devt;
 
     total = count;
 
@@ -902,8+905,7 @@ st_write(struct inode * inode, struct file * filp, const char * buf, int count)
       cmd[2] = blks >> 16;
       cmd[3] = blks >> 8;
       cmd[4] = blks;
-      SCpnt->request.rq_status = RQ_ACTIVE;
-      SCpnt->request.rq_dev = devt;
+      SCpnt->request.rq_status = RQ_SCSI_BUSY;
       scsi_do_cmd (SCpnt,
                   (void *) cmd, (STp->buffer)->b_data, transfer,
                   st_sleep_done, ST_TIMEOUT, MAX_WRITE_RETRIES);
@@ -911,7+913,7 @@ st_write(struct inode * inode, struct file * filp, const char * buf, int count)
       /* this must be done with interrupts off */
       save_flags (flags);
       cli();
-      if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+      if (SCpnt->request.rq_status != RQ_SCSI_DONE)
        sleep_on( &(STp->waiting) );
       restore_flags(flags);
 
@@ -1018,8+1020,7 @@ st_write(struct inode * inode, struct file * filp, const char * buf, int count)
       cmd[2] = blks >> 16;
       cmd[3] = blks >> 8;
       cmd[4] = blks;
-      SCpnt->request.rq_status = RQ_ACTIVE;
-      SCpnt->request.rq_dev = devt;
+      SCpnt->request.rq_status = RQ_SCSI_BUSY;
       STp->write_pending = 1;
       scsi_do_cmd (SCpnt,
                   (void *) cmd, (STp->buffer)->b_data,
@@ -1090,6+1091,7 @@ st_read(struct inode * inode, struct file * filp, char * buf, int count)
     STp->rw = ST_READING;
 
     SCpnt = allocate_device(NULL, STp->device, 1);
+    SCpnt->request.rq_dev = devt;
 
     for (total = 0; total < count; ) {
 
@@ -1118,8+1120,7 @@ st_read(struct inode * inode, struct file * filp, char * buf, int count)
        cmd[3] = blks >> 8;
        cmd[4] = blks;
 
-       SCpnt->request.rq_status = RQ_ACTIVE;
-       SCpnt->request.rq_dev = devt;
+       SCpnt->request.rq_status = RQ_SCSI_BUSY;
        scsi_do_cmd (SCpnt,
                     (void *) cmd, (STp->buffer)->b_data,
                     bytes, st_sleep_done, ST_TIMEOUT, MAX_RETRIES);
@@ -1127,7+1128,7 @@ st_read(struct inode * inode, struct file * filp, char * buf, int count)
        /* this must be done with interrupts off */
        save_flags (flags);
        cli();
-       if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+       if (SCpnt->request.rq_status != RQ_SCSI_DONE)
          sleep_on( &(STp->waiting) );
        restore_flags(flags);
 
@@ -1687,9+1688,9 @@ st_int_ioctl(struct inode * inode,struct file * file,
      }
 
    SCpnt = allocate_device(NULL, STp->device, 1);
-   cmd[1] |= (SCpnt->lun << 5) & 0xe0;
-   SCpnt->request.rq_status = RQ_ACTIVE;
    SCpnt->request.rq_dev = devt;
+   cmd[1] |= (SCpnt->lun << 5) & 0xe0;
+   SCpnt->request.rq_status = RQ_SCSI_BUSY;
    scsi_do_cmd(SCpnt,
               (void *) cmd, (void *) (STp->buffer)->b_data, datalen,
               st_sleep_done, timeout, MAX_RETRIES);
@@ -1697,7+1698,7 @@ st_int_ioctl(struct inode * inode,struct file * file,
    /* this must be done with interrupts off */
    save_flags (flags);
    cli();
-   if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+   if (SCpnt->request.rq_status != RQ_SCSI_DONE)
      sleep_on( &(STp->waiting) );
    restore_flags(flags);
 
@@ -1860,30+1861,38 @@ st_ioctl(struct inode * inode,struct file * file,
      if (i)
        return i;
 
-     /*
-      * If there was a bus reset, block further access
-      * to this device.  If the user wants to rewind the tape,
-      * then reset the flag and allow access again.
-      */
-     if( STp->device->was_reset) 
-       {
-        if(mtc.mt_op != MTREW && 
-           mtc.mt_op != MTOFFL &&
-           mtc.mt_op != MTRESET && 
-           mtc.mt_op != MTRETEN && 
-           mtc.mt_op != MTEOM)
-          return (-EIO);
-        STp->device->was_reset = 0;
-       }
-
      memcpy_fromfs((char *) &mtc, (char *)arg, sizeof(struct mtop));
 
-     i = flush_buffer(inode, file, mtc.mt_op == MTSEEK ||
-                     mtc.mt_op == MTREW || mtc.mt_op == MTOFFL ||
-                     mtc.mt_op == MTRETEN || mtc.mt_op == MTEOM ||
-                     mtc.mt_op == MTLOCK || mtc.mt_op == MTLOAD);
-     if (i < 0)
-       return i;
+     if (!(STp->device)->was_reset) {
+       i = flush_buffer(inode, file, mtc.mt_op == MTSEEK ||
+                       mtc.mt_op == MTREW || mtc.mt_op == MTOFFL ||
+                       mtc.mt_op == MTRETEN || mtc.mt_op == MTEOM ||
+                       mtc.mt_op == MTLOCK || mtc.mt_op == MTLOAD);
+       if (i < 0)
+        return i;
+     }
+     else {
+       /*
+       * If there was a bus reset, block further access
+       * to this device.  If the user wants to rewind the tape,
+       * then reset the flag and allow access again.
+       */
+       if(mtc.mt_op != MTREW && 
+         mtc.mt_op != MTOFFL &&
+         mtc.mt_op != MTRETEN && 
+         mtc.mt_op != MTERASE &&
+         mtc.mt_op != MTSEEK &&
+         mtc.mt_op != MTEOM)
+        return (-EIO);
+       STp->device->was_reset = 0;
+       if (STp->door_locked != ST_UNLOCKED) {
+        if (st_int_ioctl(inode, file, MTLOCK, 0)) {
+          printk("st%d: Could not relock door after bus reset.\n", dev);
+          STp->door_locked = ST_UNLOCKED;
+        }
+       }
+     }
+
      if (mtc.mt_op != MTNOP && mtc.mt_op != MTSETBLK &&
         mtc.mt_op != MTSETDENSITY && mtc.mt_op != MTWSM &&
         mtc.mt_op != MTSETDRVBUFFER)
@@ -1970,6+1979,7 @@ st_ioctl(struct inode * inode,struct file * file,
        return i;
 
      SCpnt = allocate_device(NULL, STp->device, 1);
+     SCpnt->request.rq_dev = devt;
 
      memset (scmd, 0, 10);
      if ((STp->device)->scsi_level < SCSI_2) {
@@ -1980,8+1990,7 @@ st_ioctl(struct inode * inode,struct file * file,
        scmd[0] = READ_POSITION;
        scmd[1] = 1;
      }
-     SCpnt->request.rq_status = RQ_ACTIVE;
-     SCpnt->request.rq_dev = devt;
+     SCpnt->request.rq_status = RQ_SCSI_BUSY;
      scmd[1] |= (SCpnt->lun << 5) & 0xe0;
      scsi_do_cmd(SCpnt,
                 (void *) scmd, (void *) (STp->buffer)->b_data,
@@ -1990,7+1999,7 @@ st_ioctl(struct inode * inode,struct file * file,
      /* this must be done with interrupts off */
      save_flags (flags);
      cli();
-     if (TAPE_NR(SCpnt->request.rq_dev) == dev)
+     if (SCpnt->request.rq_status != RQ_SCSI_DONE)
        sleep_on( &(STp->waiting) );
      restore_flags(flags);
 
@@ -2026,6+2035,44 @@ st_ioctl(struct inode * inode,struct file * file,
 }
 
 \f
+/* Try to allocate a new tape buffer */
+       static ST_buffer *
+new_tape_buffer( int from_initialization )
+{
+  int priority;
+  ST_buffer *tb;
+
+  if (st_nbr_buffers >= st_template.dev_max)
+    return NULL;  /* Should never happen */
+
+  if (from_initialization)
+    priority = GFP_ATOMIC;
+  else
+    priority = GFP_KERNEL;
+  tb = (ST_buffer *)scsi_init_malloc(sizeof(ST_buffer), priority);
+  if (tb) {
+    tb->b_data = (unsigned char *)scsi_init_malloc(st_buffer_size,
+                                                  priority | GFP_DMA);
+    if (!tb->b_data) {
+      scsi_init_free((char *)tb, sizeof(ST_buffer));
+      tb = NULL;
+    }
+  }
+  if (!tb) {
+    printk("st: Can't allocate new tape buffer (nbr %d).\n", st_nbr_buffers);
+    return NULL;
+  }
+
+#if DEBUG
+  printk("st: Allocated tape buffer %d.\n", st_nbr_buffers);
+#endif
+  tb->in_use = 0;
+  tb->writing = 0;
+  st_buffers[st_nbr_buffers++] = tb;
+  return tb;
+}
+
+
 /* Set the boot options. Syntax: st=xxx,yyy
    where xxx is buffer size in 512 byte blocks and yyy is write threshold
    in 512 byte blocks. */
@@ -2120,6+2167,9 @@ static int st_init()
 {
   int i;
   Scsi_Tape * STp;
+#if !ST_RUNTIME_BUFFERS
+  int target_nbr;
+#endif
 
   if (st_template.dev_noticed == 0) return 0;
 
@@ -2132,15+2182,17 @@ static int st_init()
   }
 
   if (scsi_tapes) return 0;
-  scsi_tapes = (Scsi_Tape *) scsi_init_malloc(
-               (st_template.dev_noticed + ST_EXTRA_DEVS) * 
-                                             sizeof(Scsi_Tape), GFP_ATOMIC);
+  st_template.dev_max = st_template.dev_noticed + ST_EXTRA_DEVS;
+  if (st_template.dev_max < MAX_SCSI_TAPES)
+    st_template.dev_max = MAX_SCSI_TAPES;
+  scsi_tapes =
+    (Scsi_Tape *) scsi_init_malloc(st_template.dev_max * sizeof(Scsi_Tape),
+                                  GFP_ATOMIC);
   if (scsi_tapes == NULL) {
     printk("Unable to allocate descriptors for SCSI tapes.\n");
     unregister_chrdev(SCSI_TAPE_MAJOR, "st");
     return 1;
   }
-  st_template.dev_max = st_template.dev_noticed + ST_EXTRA_DEVS;
 
 #if DEBUG
   printk("st: Buffer size %d bytes, write threshold %d bytes.\n",
@@ -2168,62+2220,49 @@ static int st_init()
     STp->drv_block = 0;
     STp->moves_after_eof = 1;
     STp->at_sm = 0;
-    STp->mt_status = (struct mtget *) scsi_init_malloc(sizeof(struct mtget), GFP_ATOMIC);
+    STp->mt_status = (struct mtget *) scsi_init_malloc(sizeof(struct mtget),
+                                                      GFP_ATOMIC);
     /* Initialize status */
     memset((void *) scsi_tapes[i].mt_status, 0, sizeof(struct mtget));
   }
 
   /* Allocate the buffers */
-  st_nbr_buffers = st_template.dev_noticed;
-  if (st_nbr_buffers < ST_EXTRA_DEVS)
-    st_nbr_buffers = ST_EXTRA_DEVS;
-  if (st_nbr_buffers > st_max_buffers)
-    st_nbr_buffers = st_max_buffers;
-  st_req_nbr_buffers = st_nbr_buffers;
-  st_buffers = (ST_buffer **) scsi_init_malloc(st_nbr_buffers * 
-                                              sizeof(ST_buffer *),
-                                              GFP_ATOMIC);
+  st_buffers =
+    (ST_buffer **) scsi_init_malloc(st_template.dev_max * sizeof(ST_buffer *),
+                                   GFP_ATOMIC);
   if (st_buffers == NULL) {
     printk("Unable to allocate tape buffer pointers.\n");
     unregister_chrdev(SCSI_TAPE_MAJOR, "st");
     scsi_init_free((char *) scsi_tapes,
-                  (st_template.dev_noticed + ST_EXTRA_DEVS) 
-                  * sizeof(Scsi_Tape));
+                  st_template.dev_max * sizeof(Scsi_Tape));
     return 1;
   }
 
-  /* FIXME - if we are hitting this because we are loading a tape module
-  as a loadable driver, we should not use kmalloc - it will allocate
-  a 64Kb region in order to buffer about 32Kb.  Try using 31 blocks
-  instead. */
-  
-  for (i=0; i < st_nbr_buffers; i++) {
-    st_buffers[i] = (ST_buffer *) scsi_init_malloc(sizeof(ST_buffer) - 
-                                                  1 + st_buffer_size,
-                                                  GFP_ATOMIC | GFP_DMA);
-    if (st_buffers[i] == NULL) {
-      printk("Not enough memory for buffer %d.\n", i);
+#if ST_RUNTIME_BUFFERS
+  st_nbr_buffers = 0;
+#else
+  target_nbr = st_template.dev_noticed;
+  if (target_nbr < ST_EXTRA_DEVS)
+    target_nbr = ST_EXTRA_DEVS;
+  if (target_nbr > st_max_buffers)
+    target_nbr = st_max_buffers;
+
+  for (i=st_nbr_buffers=0; i < target_nbr; i++) {
+    if (!new_tape_buffer(TRUE)) {
       if (i == 0) {
+       printk("Can't continue without at least one tape buffer.\n");
        unregister_chrdev(SCSI_TAPE_MAJOR, "st");
-       scsi_init_free((char *) scsi_tapes,
-                      (st_template.dev_noticed + ST_EXTRA_DEVS) 
-                      * sizeof(Scsi_Tape));
        scsi_init_free((char *) st_buffers,
-                      st_nbr_buffers * sizeof(ST_buffer *));
+                      st_template.dev_max * sizeof(ST_buffer *));
+       scsi_init_free((char *) scsi_tapes,
+                      st_template.dev_max * sizeof(Scsi_Tape));
        return 1;
       }
-      st_nbr_buffers = i;
       printk("Number of tape buffers adjusted.\n");
       break;
     }
-    else {
-#if DEBUG
-/*    printk("st: Buffer address: %p\n", st_buffers[i]); */
-#endif
-      st_buffers[i]->in_use = 0;
-      st_buffers[i]->writing = 0;
-    }
   }
+#endif
   return 0;
 }
 
@@ -2265,18+2304,17 @@ void cleanup_module( void)
   st_registered--;
   if(scsi_tapes != NULL) {
     scsi_init_free((char *) scsi_tapes,
-                  (st_template.dev_noticed + ST_EXTRA_DEVS) 
-                  * sizeof(Scsi_Tape));
+                  st_template.dev_max * sizeof(Scsi_Tape));
 
     if (st_buffers != NULL) {
       for (i=0; i < st_nbr_buffers; i++)
        if (st_buffers[i] != NULL) {
-         scsi_init_free((char *) st_buffers[i],
-                        sizeof(ST_buffer) - 1 + st_buffer_size);
+         scsi_init_free((char *) st_buffers[i]->b_data, st_buffer_size);
+         scsi_init_free((char *) st_buffers[i], sizeof(ST_buffer));
        }
       
       scsi_init_free((char *) st_buffers,
-                    st_req_nbr_buffers * sizeof(ST_buffer *));
+                    st_template.dev_max * sizeof(ST_buffer *));
     }
   }
   st_template.dev_max = 0;
index bf0d688..3dfa428 100644 (file)
@@ -18,7+18,7 @@ typedef struct {
   int writing;
   int last_result;
   int last_result_fatal;
-  unsigned char b_data[1];
+  unsigned char *b_data;
 } ST_buffer;
 
 typedef struct {
index 5092707..7237600 100644 (file)
 
    Copyright 1995 Kai Makisara.
 
-   Last modified: Sun Sep 10 13:26:02 1995 by root@kai.makisara.fi
+   Last modified: Mon Sep 18 21:00:49 1995 by root@kai.makisara.fi
 */
 
 #ifndef _ST_OPTIONS_H
 #define _ST_OPTIONS_H
 
+/* The driver allocates the tape buffers when needed if ST_RUNTIME_BUFFERS
+   is nonzero. Otherwise a number of buffers are allocated at initialization.
+   The drawback of runtime allocation is that allocation may fail. In any
+   case the driver tries to allocate a new tape buffer when none is free. */
+#define ST_RUNTIME_BUFFERS 0
+
 /* The driver does not wait for some operations to finish before returning
    to the user program if ST_NOWAIT is non-zero. This helps if the SCSI
    adapter does not support multiple outstanding commands. However, the user
    SENSE. */
 #define ST_DEFAULT_BLOCK 0
 
-/* The tape driver buffer size in kilobytes. When loading as module, the
-   memory block being used is slightly less than a power of two, i.e.,
-   a 64 kB block is used for a 32 kB buffer => we may as well use what is
-   being allocated! */
-#ifdef MODULE
-#define ST_BUFFER_BLOCKS 63
-#else
+/* The tape driver buffer size in kilobytes. */
 #define ST_BUFFER_BLOCKS 32
-#endif
 
 /* The number of kilobytes of data in the buffer that triggers an
    asynchronous write in fixed block mode. See also ST_ASYNC_WRITES
index 04d5a20..979bddd 100644 (file)
@@ -618,10+618,10 @@ sound_mem_init (void)
 
            for (i = MAP_NR (start_addr); i <= MAP_NR (end_addr); i++)
              {
-               if (mem_map[i])
+               if (mem_map[i].reserved || mem_map[i].count)
                  panic ("sound_mem_init: Page not free (driver incompatible with kernel).\n");
 
-               mem_map[i] = MAP_PAGE_RESERVED;
+               mem_map[i].reserved = 1;
              }
          }
       }                                /* for dev */
index 16ffcb9..b491690 100644 (file)
@@ -590,7+590,7 @@ load_elf_binary(struct linux_binprm * bprm, struct pt_regs * regs)
                                        elf_ppnt->p_offset & 0xfffff000);
                        
 #ifdef LOW_ELF_STACK
-                       if(elf_ppnt->p_vaddr & 0xfffff000 < elf_stack) 
+                       if((elf_ppnt->p_vaddr & 0xfffff000) < elf_stack) 
                                elf_stack = elf_ppnt->p_vaddr & 0xfffff000;
 #endif
                        
index 757f188..e14c53b 100644 (file)
@@ -566,7+566,7 @@ repeat0:
                         tmp = bh->b_next_free;
                         if (!bh) break;
                         
-                        if (mem_map[MAP_NR((unsigned long) bh->b_data)] != 1 ||
+                        if (mem_map[MAP_NR((unsigned long) bh->b_data)].count != 1 ||
                             bh->b_dirt) {
                                 refile_buffer(bh);
                                 continue;
@@ -614,7+614,7 @@ repeat0:
                if(candidate[i] == bh) candidate[i] = NULL;  /* Got last one */
                if (bh->b_count || bh->b_size != size)
                         panic("Busy buffer in candidate list\n");
-               if (mem_map[MAP_NR((unsigned long) bh->b_data)] != 1)
+               if (mem_map[MAP_NR((unsigned long) bh->b_data)].count != 1)
                         panic("Shared buffer in candidate list\n");
                if (BADNESS(bh)) panic("Buffer in candidate list with BADNESS != 0\n");
                
@@ -638,7+638,7 @@ repeat0:
                                tmp = bh->b_next_free;
                                if (!bh) break;
                                
-                               if (mem_map[MAP_NR((unsigned long) bh->b_data)] != 1 ||
+                               if (mem_map[MAP_NR((unsigned long) bh->b_data)].count != 1 ||
                                    bh->b_dirt) {
                                        refile_buffer(bh);
                                        continue;
@@ -761,7+761,7 @@ void refile_buffer(struct buffer_head * buf){
                panic("Attempt to refile free buffer\n");
        if (buf->b_dirt)
                dispose = BUF_DIRTY;
-       else if (mem_map[MAP_NR((unsigned long) buf->b_data)] > 1)
+       else if (mem_map[MAP_NR((unsigned long) buf->b_data)].count > 1)
                dispose = BUF_SHARED;
        else if (buf->b_lock)
                dispose = BUF_LOCKED;
@@ -1048,7+1048,7 @@ static unsigned long check_aligned(struct buffer_head * first, unsigned long add
        }
        if (!aligned)
                return try_to_align(bh, nrbuf, address);
-       mem_map[MAP_NR(page)]++;
+       mem_map[MAP_NR(page)].count++;
        read_buffers(bh,nrbuf);         /* make sure they are actually read correctly */
        while (nrbuf-- > 0)
                brelse(bh[nrbuf]);
@@ -1106,7+1106,7 @@ static unsigned long try_to_load_aligned(unsigned long address,
        }
        buffermem += PAGE_SIZE;
        bh->b_this_page = tmp;
-       mem_map[MAP_NR(address)]++;
+       mem_map[MAP_NR(address)].count++;
        buffer_pages[MAP_NR(address)] = bh;
        read_buffers(arr,block);
        while (block-- > 0)
@@ -1308,7+1308,7 @@ static int try_to_free(struct buffer_head * bh, struct buffer_head ** bhp)
        buffermem -= PAGE_SIZE;
        buffer_pages[MAP_NR(page)] = NULL;
        free_page(page);
-       return !mem_map[MAP_NR(page)];
+       return !mem_map[MAP_NR(page)].count;
 }
 
 
@@ -1471,7+1471,7 @@ void show_buffers(void)
                        locked++;
                if (bh->b_dirt)
                        dirty++;
-               if(mem_map[MAP_NR(((unsigned long) bh->b_data))] !=1) shared++;
+               if(mem_map[MAP_NR(((unsigned long) bh->b_data))].count !=1) shared++;
                if (bh->b_count)
                        used++, lastused = found;
                bh = bh->b_next_free;
@@ -1505,7+1505,7 @@ static inline int try_to_reassign(struct buffer_head * bh, struct buffer_head **
        *bhp = bh;
        page = (unsigned long) bh->b_data;
        page &= PAGE_MASK;
-       if(mem_map[MAP_NR(page)] != 1) return 0;
+       if(mem_map[MAP_NR(page)].count != 1) return 0;
        tmp = bh;
        do {
                if (!tmp)
index 80bbb31..1ff9408 100644 (file)
@@ -512,7+512,7 @@ static inline void statm_pte_range(pmd_t * pmd, unsigned long address, unsigned
                        ++*dirty;
                if (pte_page(page) >= high_memory)
                        continue;
-               if (mem_map[MAP_NR(pte_page(page))] > 1)
+               if (mem_map[MAP_NR(pte_page(page))].count > 1)
                        ++*shared;
        } while (address < end);
 }
index 599ac1d..f7b3433 100644 (file)
@@ -61,7+61,7 @@ struct inode_operations proc_link_inode_operations = {
  * looking up the file structure of the newly opened proc fd file, and
  * replacing it with the actual file structure of the process's file
  * descriptor.  This allows plan 9 semantics, so that the returned
- * file descriptor is an dup of the target file descriptor.
+ * file descriptor is a dup of the target file descriptor.
  */
 static int proc_fd_dupf(struct inode * inode, struct file * f)
 {
index fa4cfed..20d14bd 100644 (file)
@@ -291,7+291,7 @@ int mem_mmap(struct inode * inode, struct file * file,
 
                set_pte(src_table, pte_mkdirty(*src_table));
                set_pte(dest_table, *src_table);
-               mem_map[MAP_NR(pte_page(*src_table))]++;
+               mem_map[MAP_NR(pte_page(*src_table))].count++;
 
                stmp += PAGE_SIZE;
                dtmp += PAGE_SIZE;
index 283eaae..9fa4cba 100644 (file)
@@ -328,8+328,10 @@ int proc_lookup(struct inode * dir,const char * name, int len,
        }
 
        de = (struct proc_dir_entry *) dir->u.generic_ip;
-       if (!de)
+       if (!de) {
+               iput(dir);
                return -EINVAL;
+       }
 
        /* Special case "." and "..": they aren't on the directory list */
        *result = dir;
@@ -354,8+356,10 @@ int proc_lookup(struct inode * dir,const char * name, int len,
                if (proc_match(len, name, de))
                        break;
        }
-       if (!de)
+       if (!de) {
+               iput(dir);
                return -ENOENT;
+       }
 
        ino = de->low_ino | (dir->i_ino & ~(0xffff));
 
@@ -371,11+375,14 @@ static int proc_root_lookup(struct inode * dir,const char * name, int len,
        struct inode ** result)
 {
        unsigned int pid, c;
-       int i, ino;
+       int i, ino, retval;
 
-       int retval = proc_lookup(dir, name, len, result);
-       if (retval != -ENOENT)
+       dir->i_count++;
+       retval = proc_lookup(dir, name, len, result);
+       if (retval != -ENOENT) {
+               iput(dir);
                return retval;
+       }
        
        pid = 0;
        while (len-- > 0) {
index 6ff3326..24244ee 100644 (file)
@@ -71,9+71,13 @@ __asm__ __volatile__( \
 
 #define PAGE_OFFSET            0xFFFFFC0000000000
 #define MAP_NR(addr)           ((((unsigned long) (addr)) - PAGE_OFFSET) >> PAGE_SHIFT)
-#define MAP_PAGE_RESERVED      (1<<31)
 
-typedef unsigned int mem_map_t;
+typedef struct {
+       unsigned count:30,
+                dirty:1,
+                reserved:1;
+} mem_map_t;
+
 
 #endif /* __KERNEL__ */
 
index e510513..7c0f9d0 100644 (file)
@@ -171,35+171,30 @@ extern inline unsigned long pgd_page(pgd_t pgd)
 
 extern inline int pte_none(pte_t pte)          { return !pte_val(pte); }
 extern inline int pte_present(pte_t pte)       { return pte_val(pte) & _PAGE_VALID; }
-extern inline int pte_inuse(pte_t *ptep)       { return mem_map[MAP_NR(ptep)] != 1; }
+extern inline int pte_inuse(pte_t *ptep)       { return mem_map[MAP_NR(ptep)].reserved || mem_map[MAP_NR(ptep)].count != 1; }
 extern inline void pte_clear(pte_t *ptep)      { pte_val(*ptep) = 0; }
 extern inline void pte_reuse(pte_t * ptep)
 {
-       if (!(mem_map[MAP_NR(ptep)] & MAP_PAGE_RESERVED))
-               mem_map[MAP_NR(ptep)]++;
+       if (!mem_map[MAP_NR(ptep)].reserved)
+               mem_map[MAP_NR(ptep)].count++;
 }
 
 extern inline int pmd_none(pmd_t pmd)          { return !pmd_val(pmd); }
 extern inline int pmd_bad(pmd_t pmd)           { return (pmd_val(pmd) & ~_PFN_MASK) != _PAGE_TABLE || pmd_page(pmd) > high_memory; }
 extern inline int pmd_present(pmd_t pmd)       { return pmd_val(pmd) & _PAGE_VALID; }
-extern inline int pmd_inuse(pmd_t *pmdp)       { return mem_map[MAP_NR(pmdp)] != 1; }
+extern inline int pmd_inuse(pmd_t *pmdp)       { return mem_map[MAP_NR(pmdp)].reserved || mem_map[MAP_NR(pmdp)].count != 1; }
 extern inline void pmd_clear(pmd_t * pmdp)     { pmd_val(*pmdp) = 0; }
 extern inline void pmd_reuse(pmd_t * pmdp)
 {
-       if (!(mem_map[MAP_NR(pmdp)] & MAP_PAGE_RESERVED))
-               mem_map[MAP_NR(pmdp)]++;
+       if (!mem_map[MAP_NR(pmdp)].reserved)
+               mem_map[MAP_NR(pmdp)].count++;
 }
 
 extern inline int pgd_none(pgd_t pgd)          { return !pgd_val(pgd); }
 extern inline int pgd_bad(pgd_t pgd)           { return (pgd_val(pgd) & ~_PFN_MASK) != _PAGE_TABLE || pgd_page(pgd) > high_memory; }
 extern inline int pgd_present(pgd_t pgd)       { return pgd_val(pgd) & _PAGE_VALID; }
-extern inline int pgd_inuse(pgd_t *pgdp)       { return mem_map[MAP_NR(pgdp)] != 1; }
+extern inline int pgd_inuse(pgd_t *pgdp)       { return mem_map[MAP_NR(pgdp)].reserved; }
 extern inline void pgd_clear(pgd_t * pgdp)     { pgd_val(*pgdp) = 0; }
-extern inline void pgd_reuse(pgd_t * pgdp)
-{
-       if (!(mem_map[MAP_NR(pgdp)] & MAP_PAGE_RESERVED))
-               mem_map[MAP_NR(pgdp)]++;
-}
 
 /*
  * The following only work if pte_present() is true.
@@ -273,7+268,7 @@ extern inline pte_t * pte_offset(pmd_t * dir, unsigned long address)
  */
 extern inline void pte_free_kernel(pte_t * pte)
 {
-       mem_map[MAP_NR(pte)] = 1;
+       mem_map[MAP_NR(pte)].reserved = 0;
        free_page((unsigned long) pte);
 }
 
@@ -285,7+280,7 @@ extern inline pte_t * pte_alloc_kernel(pmd_t *pmd, unsigned long address)
                if (pmd_none(*pmd)) {
                        if (page) {
                                pmd_set(pmd, page);
-                               mem_map[MAP_NR(page)] = MAP_PAGE_RESERVED;
+                               mem_map[MAP_NR(page)].reserved = 1;
                                return page + address;
                        }
                        pmd_set(pmd, (pte_t *) BAD_PAGETABLE);
@@ -303,7+298,7 @@ extern inline pte_t * pte_alloc_kernel(pmd_t *pmd, unsigned long address)
 
 extern inline void pmd_free_kernel(pmd_t * pmd)
 {
-       mem_map[MAP_NR(pmd)] = 1;
+       mem_map[MAP_NR(pmd)].reserved = 0;
        free_page((unsigned long) pmd);
 }
 
@@ -315,7+310,7 @@ extern inline pmd_t * pmd_alloc_kernel(pgd_t *pgd, unsigned long address)
                if (pgd_none(*pgd)) {
                        if (page) {
                                pgd_set(pgd, page);
-                               mem_map[MAP_NR(page)] = MAP_PAGE_RESERVED;
+                               mem_map[MAP_NR(page)].reserved = 1;
                                return page + address;
                        }
                        pgd_set(pgd, BAD_PAGETABLE);
index 285f3f6..88e548e 100644 (file)
@@ -81,9+81,12 @@ do { if ((task)->mm == current->mm) invalidate(); } while (0)
 /* This handles the memory map.. */
 #define PAGE_OFFSET            0
 #define MAP_NR(addr)           (((unsigned long)(addr)) >> PAGE_SHIFT)
-#define MAP_PAGE_RESERVED      (1<<15)
 
-typedef unsigned short mem_map_t;
+typedef struct {
+       unsigned count:30,
+                dirty:1,
+                reserved:1;
+} mem_map_t;
 
 #endif /* __KERNEL__ */
 
index ac23385..9edb5ce 100644 (file)
@@ -143,12+143,12 @@ do { \
 
 extern inline int pte_none(pte_t pte)          { return !pte_val(pte); }
 extern inline int pte_present(pte_t pte)       { return pte_val(pte) & _PAGE_PRESENT; }
-extern inline int pte_inuse(pte_t *ptep)       { return mem_map[MAP_NR(ptep)] != 1; }
+extern inline int pte_inuse(pte_t *ptep)       { return mem_map[MAP_NR(ptep)].reserved || mem_map[MAP_NR(ptep)].count != 1; }
 extern inline void pte_clear(pte_t *ptep)      { pte_val(*ptep) = 0; }
 extern inline void pte_reuse(pte_t * ptep)
 {
-       if (!(mem_map[MAP_NR(ptep)] & MAP_PAGE_RESERVED))
-               mem_map[MAP_NR(ptep)]++;
+       if (!mem_map[MAP_NR(ptep)].reserved)
+               mem_map[MAP_NR(ptep)].count++;
 }
 
 extern inline int pmd_none(pmd_t pmd)          { return !pmd_val(pmd); }
@@ -170,13+170,8 @@ extern inline void pmd_reuse(pmd_t * pmdp) { }
 extern inline int pgd_none(pgd_t pgd)          { return 0; }
 extern inline int pgd_bad(pgd_t pgd)           { return 0; }
 extern inline int pgd_present(pgd_t pgd)       { return 1; }
-extern inline int pgd_inuse(pgd_t * pgdp)      { return mem_map[MAP_NR(pgdp)] != 1; }
+extern inline int pgd_inuse(pgd_t * pgdp)      { return mem_map[MAP_NR(pgdp)].reserved; }
 extern inline void pgd_clear(pgd_t * pgdp)     { }
-extern inline void pgd_reuse(pgd_t * pgdp)
-{
-       if (!(mem_map[MAP_NR(pgdp)] & MAP_PAGE_RESERVED))
-               mem_map[MAP_NR(pgdp)]++;
-}
 
 /*
  * The following only work if pte_present() is true.
@@ -243,7+238,7 @@ extern inline pte_t * pte_offset(pmd_t * dir, unsigned long address)
  */
 extern inline void pte_free_kernel(pte_t * pte)
 {
-       mem_map[MAP_NR(pte)] = 1;
+       mem_map[MAP_NR(pte)].reserved = 0;
        free_page((unsigned long) pte);
 }
 
@@ -255,7+250,7 @@ extern inline pte_t * pte_alloc_kernel(pmd_t * pmd, unsigned long address)
                if (pmd_none(*pmd)) {
                        if (page) {
                                pmd_val(*pmd) = _PAGE_TABLE | (unsigned long) page;
-                               mem_map[MAP_NR(page)] = MAP_PAGE_RESERVED;
+                               mem_map[MAP_NR(page)].reserved = 1;
                                return page + address;
                        }
                        pmd_val(*pmd) = _PAGE_TABLE | (unsigned long) BAD_PAGETABLE;
index b08cd38..0497ea8 100644 (file)
@@ -104,11+104,11 @@ static inline kdev_t to_kdev_t(int dev)
 #else /* __KERNEL__ */
 
 /*
-Some unfortunate programs want their definitions of MAJOR and MINOR
-from the kernel sources.
+Some programs want their definitions of MAJOR and MINOR and MKDEV
+from the kernel sources. These must be the externally visible ones.
 */
 #define MAJOR(dev)     ((dev)>>8)
 #define MINOR(dev)     ((dev) & 0xff)
-
+#define MKDEV(ma,mi)   ((ma)<<8 | (mi))
 #endif /* __KERNEL__ */
 #endif
index 31c1b2f..fdcc6fa 100644 (file)
  *     - your exact hardware description. Try to find out
  *       which device is unknown. It may be you mainboard chipset.
  *       PCI-CPU bridge or PCI-ISA bridge.
- *     - Send all that to frederic@cao-vlsi.ibp.fr, and I'll add
- *       your device to the list as soon as possible
+ *     - If you can't find the actual information in your hardware
+ *       booklet, try to read the references of the chip on the board.
+ *     - Send all that, with the word PCIPROBE in the subject,
+ *       to frederic@cao-vlsi.ibp.fr, and I'll add your device to 
+ *       the list as soon as possible
  *             fred.
  */
 
 #define PCI_DEVICE_ID_SI_501           0x0406
 #define PCI_DEVICE_ID_SI_496           0x0496
 #define PCI_DEVICE_ID_SI_601           0x0601
+#define PCI_DEVICE_ID_SI_5511          0x5511
+#define PCI_DEVICE_ID_SI_5513          0x5513
 
 #define PCI_VENDOR_ID_HP               0x103c
 #define PCI_DEVICE_ID_HP_J2585A                0x1030
 
 #define PCI_VENDOR_ID_CMD              0x1095
 #define PCI_DEVICE_ID_CMD_640          0x0640
+#define PCI_DEVICE_ID_CMD_646          0x0646
 
 #define PCI_VENDOR_ID_VISION           0x1098
 #define PCI_DEVICE_ID_VISION_QD8500    0x0001
 #define PCI_VENDOR_ID_IMS              0x10e0
 #define PCI_DEVICE_ID_IMS_8849         0x8849
 
+#define PCI_VENDOR_ID_REALTEK          0x10ec
+#define PCI_DEVICE_ID_REALTEK_8300     0x8029
+
 #define PCI_VENDOR_ID_VIA              0x1106
 #define PCI_DEVICE_ID_VIA_82C505       0x0505
 #define PCI_DEVICE_ID_VIA_82C561       0x0561
index a5558b2..ec0e17f 100644 (file)
@@ -221,7+221,6 @@ extern int proc_match(int, const char *, struct proc_dir_entry *);
 extern int proc_readdir(struct inode *, struct file *, void *, filldir_t);
 extern int proc_lookup(struct inode *, const char *, int, struct inode **);
 
-extern struct inode_operations proc_base_inode_operations;
 extern struct inode_operations proc_net_inode_operations;
 extern struct inode_operations proc_netdir_inode_operations;
 extern struct inode_operations proc_scsi_inode_operations;
index e563966..7f5747c 100644 (file)
--- a/ipc/shm.c
+++ b/ipc/shm.c
@@ -664,7+664,7 @@ static pte_t shm_swap_in(struct vm_area_struct * shmd, unsigned long offset, uns
 
 done:  /* pte_val(pte) == shp->shm_pages[idx] */
        current->min_flt++;
-       mem_map[MAP_NR(pte_page(pte))]++;
+       mem_map[MAP_NR(pte_page(pte))].count++;
        return pte_modify(pte, shmd->vm_page_prot);
 }
 
@@ -764,7+764,7 @@ int shm_swap (int prio, unsigned long limit)
                        printk("shm_swap_out: page and pte mismatch\n");
                set_pte(page_table,
                  __pte(shmd->vm_pte + SWP_ENTRY(0, idx << SHM_IDX_SHIFT)));
-               mem_map[MAP_NR(pte_page(pte))]--;
+               mem_map[MAP_NR(pte_page(pte))].count--;
                if (shmd->vm_mm->rss > 0)
                        shmd->vm_mm->rss--;
                invalid++;
@@ -774,7+774,7 @@ int shm_swap (int prio, unsigned long limit)
                break;
        }
 
-       if (mem_map[MAP_NR(pte_page(page))] != 1)
+       if (mem_map[MAP_NR(pte_page(page))].count != 1)
                goto check_table;
        shp->shm_pages[idx] = swap_nr;
        if (invalid)
index 32faac0..b5a3ceb 100644 (file)
@@ -92,11+92,6 @@ int (* dispatch_scsi_info_ptr) (int ino, char *buffer, char **start,
                                off_t offset, int length, 
                                int inode, int func) = 0; /* Dirty hack */
 
-#if defined(CONFIG_PROC_FS)
-extern struct proc_dir_entry scsi_dir[]; 
-extern struct proc_dir_entry scsi_hba_dir[];
-#endif
-
 extern int sys_tz;
 extern int request_dma(unsigned int dmanr, char * deviceID);
 extern void free_dma(unsigned int dmanr);
@@ -290,6+285,7 @@ struct symbol_table symbol_table = {
        X(printk),
        X(sprintf),
        X(vsprintf),
+       X(kdevname),
        X(simple_strtoul),
        X(system_utsname),
        X(sys_call_table),
@@ -416,11+412,6 @@ struct symbol_table symbol_table = {
         */
        X(gendisk_head),
        X(resetup_one_dev),
-
-#if defined(CONFIG_PROC_FS)
-       X(scsi_dir),
-       X(scsi_hba_dir),
-#endif
        X(dispatch_scsi_info_ptr),
 #endif
        /* Added to make file system as module */
index 18860ac..a8f81da 100644 (file)
@@ -153,7+153,7 @@ static pte_t filemap_swapin(struct vm_area_struct * vma,
 {
        unsigned long page = SWP_OFFSET(entry);
 
-       mem_map[page]++;
+       mem_map[page].count++;
        page = (page << PAGE_SHIFT) + PAGE_OFFSET;
        return mk_pte(page,vma->vm_page_prot);
 }
@@ -173,7+173,7 @@ static inline int filemap_sync_pte(pte_t * ptep, struct vm_area_struct *vma,
                        return 0;
                set_pte(ptep, pte_mkclean(pte));
                page = pte_page(pte);
-               mem_map[MAP_NR(page)]++;
+               mem_map[MAP_NR(page)].count++;
        } else {
                if (pte_none(pte))
                        return 0;
index e150d1b..8fbd651 100644 (file)
@@ -207,7+207,7 @@ static inline void copy_one_pte(pte_t * old_pte, pte_t * new_pte)
                set_pte(new_pte, pte);
                return;
        }
-       if (pte_page(pte) > high_memory || (mem_map[MAP_NR(pte_page(pte))] & MAP_PAGE_RESERVED)) {
+       if (pte_page(pte) > high_memory || mem_map[MAP_NR(pte_page(pte))].reserved) {
                set_pte(new_pte, pte);
                return;
        }
@@ -217,7+217,7 @@ static inline void copy_one_pte(pte_t * old_pte, pte_t * new_pte)
                pte = pte_mkdirty(pte);
        set_pte(new_pte, pte_mkold(pte));
        set_pte(old_pte, pte);
-       mem_map[MAP_NR(pte_page(pte))]++;
+       mem_map[MAP_NR(pte_page(pte))].count++;
 }
 
 static inline int copy_pte_range(pmd_t *dst_pmd, pmd_t *src_pmd, unsigned long address, unsigned long size)
@@ -315,7+315,7 @@ static inline void forget_pte(pte_t page)
                return;
        if (pte_present(page)) {
                free_page(pte_page(page));
-               if (mem_map[MAP_NR(pte_page(page))] & MAP_PAGE_RESERVED)
+               if (mem_map[MAP_NR(pte_page(page))].reserved)
                        return;
                if (current->mm->rss <= 0)
                        return;
@@ -479,7+479,7 @@ static inline void remap_pte_range(pte_t * pte, unsigned long address, unsigned
        do {
                pte_t oldpage = *pte;
                pte_clear(pte);
-               if (offset >= high_memory || (mem_map[MAP_NR(offset)] & MAP_PAGE_RESERVED))
+               if (offset >= high_memory || mem_map[MAP_NR(offset)].reserved)
                        set_pte(pte, mk_pte(offset, prot));
                forget_pte(oldpage);
                address += PAGE_SIZE;
@@ -558,7+558,7 @@ unsigned long put_dirty_page(struct task_struct * tsk, unsigned long page, unsig
 
        if (page >= high_memory)
                printk("put_dirty_page: trying to put page %08lx at %08lx\n",page,address);
-       if (mem_map[MAP_NR(page)] != 1)
+       if (mem_map[MAP_NR(page)].count != 1)
                printk("mem_map disagrees with %08lx at %08lx\n",page,address);
        pgd = pgd_offset(tsk->mm,address);
        pmd = pmd_alloc(pgd, address);
@@ -632,9+632,9 @@ void do_wp_page(struct task_struct * tsk, struct vm_area_struct * vma,
        /*
         * Do we need to copy?
         */
-       if (mem_map[MAP_NR(old_page)] != 1) {
+       if (mem_map[MAP_NR(old_page)].count != 1) {
                if (new_page) {
-                       if (mem_map[MAP_NR(old_page)] & MAP_PAGE_RESERVED)
+                       if (mem_map[MAP_NR(old_page)].reserved)
                                ++vma->vm_mm->rss;
                        copy_page(old_page,new_page);
                        set_pte(page_table, pte_mkwrite(pte_mkdirty(mk_pte(new_page, vma->vm_page_prot))));
@@ -812,7+812,7 @@ static int try_to_share(unsigned long to_address, struct vm_area_struct * to_are
 /* is the page reasonable at all? */
        if (pte_page(from) >= high_memory)
                return 0;
-       if (mem_map[MAP_NR(pte_page(from))] & MAP_PAGE_RESERVED)
+       if (mem_map[MAP_NR(pte_page(from))].reserved)
                return 0;
 /* is the destination ok? */
        to_dir = pgd_offset(to_area->vm_mm,to_address);
@@ -862,7+862,7 @@ static int try_to_share(unsigned long to_address, struct vm_area_struct * to_are
                set_pte(from_table, pte_mkdirty(from));
                delete_from_swap_cache(pte_page(from));
        }
-       mem_map[MAP_NR(pte_page(from))]++;
+       mem_map[MAP_NR(pte_page(from))].count++;
        set_pte(to_table, mk_pte(pte_page(from), to_area->vm_page_prot));
 /* Check if we need to do anything at all to the 'from' field */
        if (!pte_write(from))
@@ -966,7+966,7 @@ static inline void do_swap_page(struct task_struct * tsk,
                free_page(pte_page(page));
                return;
        }
-       if (mem_map[MAP_NR(pte_page(page))] > 1 && !(vma->vm_flags & VM_SHARED))
+       if (mem_map[MAP_NR(pte_page(page))].count > 1 && !(vma->vm_flags & VM_SHARED))
                page = pte_wrprotect(page);
        ++vma->vm_mm->rss;
        ++tsk->maj_flt;
@@ -1041,7+1041,7 @@ void do_no_page(struct task_struct * tsk, struct vm_area_struct * vma,
        entry = mk_pte(page, vma->vm_page_prot);
        if (write_access) {
                entry = pte_mkwrite(pte_mkdirty(entry));
-       } else if (mem_map[MAP_NR(page)] > 1 && !(vma->vm_flags & VM_SHARED))
+       } else if (mem_map[MAP_NR(page)].count > 1 && !(vma->vm_flags & VM_SHARED))
                entry = pte_wrprotect(entry);
        put_page(page_table, entry);
 }
index c952bf1..de5df9b 100644 (file)
--- a/mm/swap.c
+++ b/mm/swap.c
@@ -367,7+367,7 @@ static inline int try_to_swap_out(struct task_struct * tsk, struct vm_area_struc
                return 0;
        if (page >= limit)
                return 0;
-       if (mem_map[MAP_NR(page)] & MAP_PAGE_RESERVED)
+       if (mem_map[MAP_NR(page)].reserved)
                return 0;
        if ((pte_dirty(pte) && delete_from_swap_cache(page)) || pte_young(pte))  {
                set_pte(page_table, pte_mkold(pte));
@@ -380,7+380,7 @@ static inline int try_to_swap_out(struct task_struct * tsk, struct vm_area_struc
                        if (vma->vm_ops->swapout(vma, address - vma->vm_start + vma->vm_offset, page_table))
                                kill_proc(pid, SIGBUS, 1);
                } else {
-                       if (mem_map[MAP_NR(page)] != 1)
+                       if (mem_map[MAP_NR(page)].count != 1)
                                return 0;
                        if (!(entry = get_swap_page()))
                                return 0;
@@ -393,7+393,7 @@ static inline int try_to_swap_out(struct task_struct * tsk, struct vm_area_struc
                return 1;       /* we slept: the process may not exist any more */
        }
         if ((entry = find_in_swap_cache(page)))  {
-               if (mem_map[MAP_NR(page)] != 1) {
+               if (mem_map[MAP_NR(page)].count != 1) {
                        set_pte(page_table, pte_mkdirty(pte));
                        printk("Aiee.. duplicated cached swap-cache entry\n");
                        return 0;
@@ -407,7+407,7 @@ static inline int try_to_swap_out(struct task_struct * tsk, struct vm_area_struc
        vma->vm_mm->rss--;
        pte_clear(page_table);
        invalidate();
-       entry = mem_map[MAP_NR(page)];
+       entry = mem_map[MAP_NR(page)].count;
        free_page(page);
        return entry;
 }
@@ -717,21+717,21 @@ static inline void check_free_buffers(unsigned long addr)
 
 void free_pages(unsigned long addr, unsigned long order)
 {
-       if (addr < high_memory) {
+       if (MAP_NR(addr) < MAP_NR(high_memory)) {
                unsigned long flag;
                mem_map_t * map = mem_map + MAP_NR(addr);
-               if (*map) {
-                       if (!(*map & MAP_PAGE_RESERVED)) {
-                               save_flags(flag);
-                               cli();
-                               if (!--*map)  {
-                                       free_pages_ok(addr, order);
-                                       delete_from_swap_cache(addr);
-                               }
-                               restore_flags(flag);
-                               if (*map == 1)
-                                       check_free_buffers(addr);
+               if (map->reserved)
+                       return;
+               if (map->count) {
+                       save_flags(flag);
+                       cli();
+                       if (!--map->count) {
+                               free_pages_ok(addr, order);
+                               delete_from_swap_cache(addr);
                        }
+                       restore_flags(flag);
+                       if (map->count == 1)
+                               check_free_buffers(addr);
                        return;
                }
                printk("Trying to free free memory (%08lx): memory probably corrupted\n",addr);
@@ -775,7+775,7 @@ do { unsigned long size = PAGE_SIZE << high; \
                mark_used((unsigned long) addr, high); \
                restore_flags(flags); \
                addr = (struct mem_list *) (size + (unsigned long) addr); \
-       } mem_map[MAP_NR((unsigned long) addr)] = 1; \
+       } mem_map[MAP_NR((unsigned long) addr)].count = 1; \
 } while (0)
 
 unsigned long __get_free_pages(int priority, unsigned long order, unsigned long limit)
@@ -956,6+956,8 @@ static int unuse_process(struct task_struct * p, unsigned int type, unsigned lon
        /*
         * Go through process' page directory.
         */
+       if (!p->mm || pgd_inuse(p->mm->pgd))
+               return 0;
        vma = p->mm->mmap;
        while (vma) {
                pgd_t * pgd = pgd_offset(p->mm, vma->vm_start);
@@ -1244,7+1246,7 @@ void si_swapinfo(struct sysinfo *val)
 
 /*
  * set up the free-area data structures:
- *   - mark all pages MAP_PAGE_RESERVED
+ *   - mark all pages reserved
  *   - mark all memory queues empty
  *   - clear the memory bitmaps
  */
@@ -1266,8+1268,12 @@ unsigned long free_area_init(unsigned long start_mem, unsigned long end_mem)
        mem_map = (mem_map_t *) start_mem;
        p = mem_map + MAP_NR(end_mem);
        start_mem = LONG_ALIGN((unsigned long) p);
-       while (p > mem_map)
-               *--p = MAP_PAGE_RESERVED;
+       while (p > mem_map) {
+               --p;
+               p->count = 0;
+               p->dirty = 0;
+               p->reserved = 1;
+       }
 
        for (i = 0 ; i < NR_MEM_LISTS ; i++) {
                unsigned long bitmap_size;
close