Commit ac995a26 authored by Linus Torvalds's avatar Linus Torvalds

Linux 2.1.116

I just released Linux-2.1.116. I've tested it fairly extensively on my SMP
box, both with little memory and much, and I cannot make it lock up any
more.

Special thanks to Dean Gaudet who helped me set up a apache configuration
that finally made me able to repeat the lockup, and made me able to debug
the thing.

Most of the 2.1.116 patches are "just" alpha and m68k updates, and can be
ignored by most people. The bugfixes are, roughly:

 - fixed serious low-memory situation problem, where a critical resource
   allocation problem could result in nasy behaviour. Notably, doing TCP
   under low memory could result in TCP trying to allocate memory in a
   tight loop and locking out kswapd completely so that the situation
   would never be rectified. In short, the machine hung.
   This problem has been there forever, the only reason it doesn't show up
   under 2.0.x seems to be because under 2.0.x the TCP allocation was
   always for a single page, for which this situation never arises. Under
   2.1.x the slab code forced multi-page allocations.
   If you've seen lockups with 2.1.x, this may be the cause. This was what
   held up 2.1.116 for so long.
 - various minor driver updates. Networking, radio, bttv.
 - NFS over TCP still doesn't work, but at least it fails due to new
   reasons.

Alan, try your squid thing under 2.1.116. I suspect it will hold up now,

                Linus
parent 45b31a0a
\documentstyle{article}
% $Id: devices.tex,v 1.12 1998/08/06 04:52:01 hpa Exp $
% $Id: devices.tex,v 1.14 1998/08/10 22:39:24 hpa Exp $
% ---------------------------------------------------------------------------
% Adopt somewhat reasonable margins, so it doesn't take a million
% pages to print... :-) If you're actually putting this in print, you
......@@ -48,7 +48,7 @@ foo \kill}%
%
\title{{\bf Linux Allocated Devices}}
\author{Maintained by H. Peter Anvin $<$hpa@zytor.com$>$}
\date{Last revised: August 5, 1998}
\date{Last revised: August 10, 1998}
\maketitle
%
\noindent
......@@ -246,7 +246,7 @@ Your cooperation is appreciated.
\major{78}{}{char }{PAM Software's multimodem boards}
\major{79}{}{char }{PAM Software's multimodem boards -- alternate devices}
\major{80}{}{char }{Photometrics AT200 CCD camera}
\major{81}{}{char }{Brooktree Bt848 frame grabbers}
\major{81}{}{char }{video4linux}
\major{82}{}{char }{WiNRADiO communications receiver card}
\major{83}{}{char }{Teletext/videotext interfaces}
\major{84}{}{char }{Ikon 1011[57] Versatec Greensheet Interface}
......@@ -275,7 +275,8 @@ Your cooperation is appreciated.
\major{107}{}{char }{3Dfx Voodoo Graphics device}
\major{108}{}{char }{Device independent PPP interface}
\major{109}{}{char }{Reserved for logical volume manager}
\major{110}{--119}{}{Unallocated}
\major{110}{}{char }{miroMEDIA Surround board}
\major{111}{--119}{}{Unallocated}
\major{120}{--127}{}{Local/experimental use}
\major{128}{--135}{char }{Unix98 PTY masters}
\major{136}{--143}{char }{Unix98 PTY slaves}
......@@ -438,19 +439,18 @@ schemes, the meaning of the numbers vary.
\minor{64}{/dev/ttyS0}{First serial port}
\minordots
\minor{127}{/dev/ttyS63}{64th serial port}
\minor{128}{/dev/ptyp0}{First old pseudo-tty master}
\minor{128}{/dev/ptyp0}{OBSOLETE}
\minordots
\minor{191}{/dev/ptysf}{64th old pseudo-tty master}
\minor{192}{/dev/ttyp0}{First old pseudo-tty slave}
\minor{191}{/dev/ptysf}{OBSOLETE}
\minor{192}{/dev/ttyp0}{OBSOLETE}
\minordots
\minor{255}{/dev/ttysf}{64th old pseudo-tty slave}
\minor{255}{/dev/ttysf}{OBSOLETE}
\end{devicelist}
\noindent
For compatibility with previous versions of Linux, the first 64 PTYs
are replicated under this device number. This use is deprecated with
the release of Linux 2.0 and may be removed in a future version of
Linux. To ensure proper operation, do not mix old and new PTY devices.
Older versions of the Linux kernel used this major number for BSD PTY
devices. As of Linux 2.1.115, this is no longer supported. Use major
numbers 2 and 3.
\begin{devicelist}
\major{ 5}{}{char }{Alternate TTY devices}
......@@ -583,9 +583,6 @@ physical disks.
\minor{133}{/dev/exttrp}{External device trap}
\minor{134}{/dev/apm\_bios}{Advanced Power Management BIOS}
\minor{135}{/dev/rtc}{Real Time Clock}
\minor{136}{/dev/qcam0}{QuickCam on {\file lp0}}
\minor{137}{/dev/qcam1}{QuickCam on {\file lp1}}
\minor{138}{/dev/qcam2}{QuickCam on {\file lp2}}
\minor{139}{/dev/openprom}{SPARC OpenBoot PROM}
\minor{140}{/dev/relay8}{Berkshire Products Octal relay card}
\minor{141}{/dev/relay16}{Berkshire Products ISO-16 relay card}
......@@ -599,8 +596,8 @@ physical disks.
\minor{149}{/dev/input/mouse}{Linux/SGI Irix emulation mouse}
\minor{150}{/dev/input/keyboard}{Linux/SGI Irix emulation keyboard}
\minor{151}{/dev/led}{Front panel LEDs}
\minor{152}{/dev/radio}{Radio card (type?)}
\minor{153}{/dev/mergemem}{Memory merge device}
\minor{154}{/dev/pmu}{Macintosh PowerBook power manager}
\end{devicelist}
\begin{devicelist}
......@@ -1677,16 +1674,19 @@ Currently for Dolphin Interconnect Solutions' PCI-SCI bridge.
\end{devicelist}
\begin{devicelist}
\major{81}{}{char }{Brooktree Bt848 frame grabbers}
\minor{0}{/dev/bttv0}{First Bt848 card}
\minor{0}{/dev/bttv1}{Second Bt848 card}
\minordots
\minor{16}{/dev/bttvc0}{Control for first Bt848 card}
\minor{17}{/dev/bttvc1}{Control for second Bt848 card}
\minordots
\minor{32}{/dev/bttv-vbi0}{VBI data of first Bt848 card}
\minor{33}{/dev/bttv-vbi1}{VBI data of second Bt848 card}
\minordots
\major{81}{}{char }{video4linux}
\minor{0}{/dev/video0}{Video capture/overlay device}
\minordots
\minor{63}{/dev/video63}{Video capture/overlay device}
\minor{64}{/dev/radio0}{Radio device}
\minordots
\minor{127}{/dev/radio63}{Radio device}
\minor{192}{/dev/vtx0}{Teletext device}
\minordots
\minor{223}{/dev/vtx31}{Teletext device}
\minor{224}{/dev/vbi0}{Vertical blank interupt}
\minordots
\minor{255}{/dev/vbi31}{Vertical blank interupt}
\end{devicelist}
\begin{devicelist}
......@@ -1910,7 +1910,14 @@ $<$arla-announce-request@stacken.kth.se$>$.
\end{devicelist}
\begin{devicelist}
\major{110}{--119}{}{Unallocated}
\major{110}{}{char }{miroMEDIA Surround board}
\minor{0}{/dev/srnd0}{First miroMEDIA Surround board}
\minor{1}{/dev/srnd1}{First miroMEDIA Surround board}
\minordots
\end{devicelist}
\begin{devicelist}
\major{111}{--119}{}{Unallocated}
\end{devicelist}
\begin{devicelist}
......@@ -1989,6 +1996,8 @@ It is recommended that these links exist on all systems:
\link{/dev/core}{/proc/kcore}{symbolic}{Backward compatibility}
\link{/dev/ramdisk}{ram0}{symbolic}{Backward compatibility}
\link{/dev/ftape}{qft0}{symbolic}{Backward compatibility}
\link{/dev/bttv0}{video0}{symbolic}{Backward compatibility}
\link{/dev/radio}{radio0}{symbolic}{Backward compatibility}
\link{/dev/scd?}{sr?}{hard}{Alternate name for CD-ROMs}
\end{nodelist}
......
LINUX ALLOCATED DEVICES
Maintained by H. Peter Anvin <hpa@zytor.com>
Last revised: August 5, 1998
Last revised: August 10, 1998
This list is the Linux Device List, the official registry of allocated
device numbers and /dev directory nodes for the Linux operating
......@@ -184,19 +184,16 @@ Your cooperation is appreciated.
64 = /dev/ttyS0 First serial port
...
127 = /dev/ttyS63 64th serial port
128 = /dev/ptyp0 First old pseudo-tty master
128 = /dev/ptyp0 OBSOLETE
...
191 = /dev/ptysf 64th old pseudo-tty master
192 = /dev/ttyp0 First old pseudo-tty slave
191 = /dev/ptysf OBSOLETE
192 = /dev/ttyp0 OBSOLETE
...
255 = /dev/ttysf 64th old pseudo-tty slave
255 = /dev/ttysf OBSOLETE
For compatibility with previous versions of Linux, the
first 64 PTYs are replicated under this device number.
This use is deprecated with the release of Linux 2.0
and may be removed in a future version of Linux. To
ensure proper operation, do not mix old and new PTY
devices.
Older versions of the Linux kernel used this major
number for BSD PTY devices. As of Linux 2.1.115, this
is no longer supported. Use major numbers 2 and 3.
5 char Alternate TTY devices
0 = /dev/tty Current TTY device
......@@ -310,9 +307,6 @@ Your cooperation is appreciated.
133 = /dev/exttrp External device trap
134 = /dev/apm_bios Advanced Power Management BIOS
135 = /dev/rtc Real Time Clock
136 = /dev/qcam0 QuickCam on lp0
137 = /dev/qcam1 QuickCam on lp1
138 = /dev/qcam2 QuickCam on lp2
139 = /dev/openprom SPARC OpenBoot PROM
140 = /dev/relay8 Berkshire Products Octal relay card
141 = /dev/relay16 Berkshire Products ISO-16 relay card
......@@ -326,8 +320,8 @@ Your cooperation is appreciated.
149 = /dev/input/mouse Linux/SGI Irix emulation mouse
150 = /dev/input/keyboard Linux/SGI Irix emulation keyboard
151 = /dev/led Front panel LEDs
152 = /dev/radio Radio card (type?)
153 = /dev/mergemem Memory merge device
154 = /dev/pmu Macintosh PowerBook power manager
11 char Raw keyboard device
0 = /dev/kbd Raw keyboard device
......@@ -1163,16 +1157,19 @@ Your cooperation is appreciated.
80 char Photometrics AT200 CCD camera
0 = /dev/at200 Photometrics AT200 CCD camera
81 char Brooktree Bt848 frame grabbers
0 = /dev/bttv0 First Bt848 card
1 = /dev/bttv1 Second Bt848 card
81 char video4linux
0 = /dev/video0 Video capture/overlay device
...
63 = /dev/video63 Video capture/overlay device
64 = /dev/radio0 Radio device
...
16 = /dev/bttvc0 Control for first Bt848 card
17 = /dev/bttvc1 Control for second Bt848 card
127 = /dev/radio63 Radio device
192 = /dev/vtx0 Teletext device
...
32 = /dev/bttv-vbi0 VBI data of first Bt848 card
33 = /dev/bttv-vbi1 VBI data of second Bt848 card
223 = /dev/vtx31 Teletext device
224 = /dev/vbi0 Vertical blank interrupt
...
255 = /dev/vbi31 Vertical blank interrupt
82 char WiNRADiO communications receiver card
0 = /dev/winradio0 First WiNRADiO card
......@@ -1330,7 +1327,12 @@ Your cooperation is appreciated.
109 char Reserved for logical volume manager
108-119 UNALLOCATED
110 char miroMEDIA Surround board
0 = /dev/srnd0 First miroMEDIA Surround board
1 = /dev/srnd1 Second miroMEDIA Surround board
...
111-119 UNALLOCATED
120-127 LOCAL/EXPERIMENTAL USE
......@@ -1388,6 +1390,8 @@ It is recommended that these links exist on all systems:
/dev/core /proc/kcore symbolic Backward compatibility
/dev/ramdisk ram0 symbolic Backward compatibility
/dev/ftape qft0 symbolic Backward compatibility
/dev/bttv0 video0 symbolic Backward compatibility
/dev/radio radio0 symbolic Backward compatibility
/dev/scd? sr? hard Alternate SCSI CD-ROM name
Locally defined links
......
......@@ -228,8 +228,10 @@ config: symlinks scripts/split-include
scripts/split-include include/linux/autoconf.h include/config; \
fi
linuxsubdirs: dummy
set -e; for i in $(SUBDIRS); do $(MAKE) -C $$i; done
linuxsubdirs: $(patsubst %, _dir_%, $(SUBDIRS))
$(patsubst %, _dir_%, $(SUBDIRS)) : dummy
$(MAKE) -C $(patsubst _dir_%, %, $@)
$(TOPDIR)/include/linux/version.h: include/linux/version.h
$(TOPDIR)/include/linux/compile.h: include/linux/compile.h
......@@ -271,26 +273,8 @@ init/version.o: init/version.c include/linux/compile.h
init/main.o: init/main.c
$(CC) $(CFLAGS) $(PROFILING) -c -o $*.o $<
fs: dummy
$(MAKE) linuxsubdirs SUBDIRS=fs
lib: dummy
$(MAKE) linuxsubdirs SUBDIRS=lib
mm: dummy
$(MAKE) linuxsubdirs SUBDIRS=mm
ipc: dummy
$(MAKE) linuxsubdirs SUBDIRS=ipc
kernel: dummy
$(MAKE) linuxsubdirs SUBDIRS=kernel
drivers: dummy
$(MAKE) linuxsubdirs SUBDIRS=drivers
net: dummy
$(MAKE) linuxsubdirs SUBDIRS=net
fs lib mm ipc kernel drivers net: dummy
$(MAKE) $(subst $@, _dir_$@, $@)
MODFLAGS = -DMODULE
ifdef CONFIG_MODULES
......@@ -298,11 +282,10 @@ ifdef CONFIG_MODVERSIONS
MODFLAGS += -DMODVERSIONS -include $(HPATH)/linux/modversions.h
endif
modules: include/linux/version.h
@set -e; \
for i in $(SUBDIRS); \
do $(MAKE) -C $$i CFLAGS="$(CFLAGS) $(MODFLAGS)" MAKING_MODULES=1 modules; \
done
modules: $(patsubst %, _mod_%, $(SUBDIRS))
$(patsubst %, _mod_%, $(SUBDIRS)) : include/linux/version.h
$(MAKE) -C $(patsubst _mod_%, %, $@) CFLAGS="$(CFLAGS) $(MODFLAGS)" MAKING_MODULES=1 modules
modules_install:
@( \
......@@ -396,7 +379,9 @@ sums:
dep-files: scripts/mkdep archdep include/linux/version.h
scripts/mkdep init/*.c > .depend
scripts/mkdep `find $(FINDHPATH) -follow -name \*.h ! -name modversions.h -print` > .hdepend
set -e; for i in $(SUBDIRS); do $(MAKE) -C $$i fastdep; done
# set -e; for i in $(SUBDIRS); do $(MAKE) -C $$i fastdep ;done
# let this be made through the fastdep rule in Rules.make
$(MAKE) $(patsubst %,_sfdep_%,$(SUBDIRS)) _FASTDEP_ALL_SUB_DIRS="$(SUBDIRS)"
MODVERFILE :=
......
......@@ -105,15 +105,23 @@ endif
fastdep: dummy
$(TOPDIR)/scripts/mkdep $(wildcard *.[chS] local.h.master) > .depend
ifdef ALL_SUB_DIRS
set -e; for i in $(ALL_SUB_DIRS); do $(MAKE) -C $$i fastdep; done
$(MAKE) $(patsubst %,_sfdep_%,$(ALL_SUB_DIRS)) _FASTDEP_ALL_SUB_DIRS="$(ALL_SUB_DIRS)"
endif
ifdef _FASTDEP_ALL_SUB_DIRS
$(patsubst %,_sfdep_%,$(_FASTDEP_ALL_SUB_DIRS)):
$(MAKE) -C $(patsubst _sfdep_%,%,$@) fastdep
endif
#
# A rule to make subdirectories
#
sub_dirs: dummy
sub_dirs: dummy $(patsubst %,_subdir_%,$(SUB_DIRS))
ifdef SUB_DIRS
set -e; for i in $(SUB_DIRS); do $(MAKE) -C $$i; done
$(patsubst %,_subdir_%,$(SUB_DIRS)) : dummy
$(MAKE) -C $(patsubst _subdir_%,%,$@)
endif
#
......@@ -123,13 +131,20 @@ ALL_MOBJS = $(MX_OBJS) $(M_OBJS)
ifneq "$(strip $(ALL_MOBJS))" ""
PDWN=$(shell $(CONFIG_SHELL) $(TOPDIR)/scripts/pathdown.sh)
endif
modules: $(ALL_MOBJS) $(MIX_OBJS) $(MI_OBJS) dummy
ifdef MOD_SUB_DIRS
set -e; for i in $(MOD_SUB_DIRS); do $(MAKE) -C $$i modules; done
$(patsubst %,_modsubdir_%,$(MOD_SUB_DIRS)) : dummy
$(MAKE) -C $(patsubst _modsubdir_%,%,$@) modules
endif
ifdef MOD_IN_SUB_DIRS
set -e; for i in $(MOD_IN_SUB_DIRS); do $(MAKE) -C $$i modules; done
$(patsubst %,_modinsubdir_%,$(MOD_IN_SUB_DIRS)) : dummy
$(MAKE) -C $(patsubst _modinsubdir_%,%,$@) modules
endif
modules: $(ALL_MOBJS) $(MIX_OBJS) $(MI_OBJS) dummy \
$(patsubst %,_modsubdir_%,$(MOD_SUB_DIRS)) \
$(patsubst %,_modinsubdir_%,$(MOD_IN_SUB_DIRS))
ifneq "$(strip $(MOD_LIST_NAME))" ""
rm -f $$TOPDIR/modules/$(MOD_LIST_NAME)
ifdef MOD_SUB_DIRS
......
......@@ -153,7 +153,6 @@ ENTRY(lcall7)
.globl ret_from_smpfork
ret_from_smpfork:
GET_CURRENT(%ebx)
call __putlock
btrl $0, SYMBOL_NAME(scheduler_lock)
jmp ret_from_sys_call
#endif /* __SMP__ */
......
......@@ -6,6 +6,6 @@
$(CC) -D__ASSEMBLY__ $(AFLAGS) -traditional -c $< -o $*.o
L_TARGET = lib.a
L_OBJS = checksum.o semaphore.o delay.o usercopy.o getuser.o putuser.o lock.o lock_check.o
L_OBJS = checksum.o semaphore.o delay.o usercopy.o getuser.o putuser.o
include $(TOPDIR)/Rules.make
.globl __getlock
__getlock:
pushl %eax
movl $-8192,%eax
andl %esp,%eax
movl 36(%eax),%eax
incl spinlocks(,%eax,4)
popl %eax
ret
.globl __putlock
__putlock:
pushl %eax
movl $-8192,%eax
andl %esp,%eax
movl 36(%eax),%eax
decl spinlocks(,%eax,4)
js __bad_put
popl %eax
ret
__bad_put:
pushl %edx
pushl %ecx
call __putlock_negative
popl %ecx
popl %edx
popl %eax
ret
#include <linux/sched.h>
#include <linux/interrupt.h>
unsigned int spinlocks[32];
static void show_stack(unsigned int *stack)
{
int i;
for (i = 0; i < 40; i++) {
extern int get_options, __start_fixup;
unsigned int p = stack[i];
if (p >= (unsigned int) &get_options && p < (unsigned int)&__start_fixup)
printk("[<%08x>] ", p);
}
}
void __putlock_negative(
unsigned int ecx,
unsigned int edx,
unsigned int eax,
unsigned int from_where)
{
static int count = 0;
spinlocks[current->processor] = 0;
if (count < 5) {
count++;
printk("negative putlock from %x\n", from_where);
show_stack(&ecx);
}
}
void __check_locks(unsigned int type)
{
static int warned = 0;
if (warned < 5) {
unsigned int from_where = (&type)[-1];
unsigned int this_cpu = current->processor;
int bad_irq = 0;
if (type) {
unsigned long flags;
__save_flags(flags);
if (!(flags & 0x200) || (global_irq_holder == this_cpu))
bad_irq = 1;
}
if (spinlocks[this_cpu] ||
local_irq_count[this_cpu] ||
local_bh_count[this_cpu] ||
bad_irq) {
warned++;
printk("scheduling with spinlocks=%d at %x\n", spinlocks[this_cpu], from_where);
show_stack(&type);
}
}
}
......@@ -10,8 +10,6 @@
inline unsigned long
__generic_copy_to_user(void *to, const void *from, unsigned long n)
{
if ((unsigned long) to < TASK_SIZE)
__check_locks(1);
if (access_ok(VERIFY_WRITE, to, n))
__copy_user(to,from,n);
return n;
......@@ -20,8 +18,6 @@ __generic_copy_to_user(void *to, const void *from, unsigned long n)
inline unsigned long
__generic_copy_from_user(void *to, const void *from, unsigned long n)
{
if ((unsigned long) from < TASK_SIZE)
__check_locks(1);
if (access_ok(VERIFY_READ, from, n))
__copy_user(to,from,n);
return n;
......@@ -60,7 +56,6 @@ long
__strncpy_from_user(char *dst, const char *src, long count)
{
long res;
__check_locks(1);
__do_strncpy_from_user(dst, src, count, res);
return res;
}
......@@ -69,7 +64,6 @@ long
strncpy_from_user(char *dst, const char *src, long count)
{
long res = -EFAULT;
__check_locks(1);
if (access_ok(VERIFY_READ, src, 1))
__do_strncpy_from_user(dst, src, count, res);
return res;
......@@ -102,7 +96,6 @@ strncpy_from_user(char *dst, const char *src, long count)
unsigned long
clear_user(void *to, unsigned long n)
{
__check_locks(1);
if (access_ok(VERIFY_WRITE, to, n))
__do_clear_user(to, n);
return n;
......@@ -111,7 +104,6 @@ clear_user(void *to, unsigned long n)
unsigned long
__clear_user(void *to, unsigned long n)
{
__check_locks(1);
__do_clear_user(to, n);
return n;
}
......@@ -126,7 +118,6 @@ long strlen_user(const char *s)
{
unsigned long res;
__check_locks(1);
__asm__ __volatile__(
"0: repne; scasb\n"
" notl %0\n"
......
......@@ -414,7 +414,8 @@ static int msdos_partition(struct gendisk *hd, kdev_t dev, unsigned long first_s
* This is necessary for drives for situations where
* the translated geometry is unavailable from the BIOS.
*/
for (i = 0; i < 4 ; i++) {
int xlate_done = 0;
for (i = 0; i < 4 && !xlate_done; i++) {
struct partition *q = &p[i];
if (NR_SECTS(q)
&& (q->sector & 63) == 1
......@@ -423,10 +424,16 @@ static int msdos_partition(struct gendisk *hd, kdev_t dev, unsigned long first_s
if (heads == 32 || heads == 64 || heads == 128 || heads == 255) {
(void) ide_xlate_1024(dev, heads, " [PTBL]");
break;
xlate_done = 1;
}
}
}
if (!xlate_done) {
/*
* Default translation is equivalent of "BIOS LBA":
*/
ide_xlate_1024(dev, -2, " [LBA]");
}
}
}
#endif /* CONFIG_BLK_DEV_IDE */
......
/*
* linux/drivers/block/ide.c Version 6.17 March 29, 1998
* linux/drivers/block/ide.c Version 6.18 August 16, 1998
*
* Copyright (C) 1994-1998 Linus Torvalds & authors (see below)
*/
......@@ -89,6 +89,7 @@
* Version 6.15 added SMP awareness to IDE drivers
* Version 6.16 fixed various bugs; even more SMP friendly
* Version 6.17 fix for newest EZ-Drive problem
* Version 6.18 default unpartitioned-disk translation now "BIOS LBA"
*
* Some additional driver compile-time options are in ide.h
*
......@@ -2562,7 +2563,7 @@ int ide_xlate_1024 (kdev_t i_rdev, int xparm, const char *msg)
printk("%s ", msg);
if (xparm == -1 && (drive->bios_cyl * drive->bios_head * drive->bios_sect) < (1024 * 16 * 63))
if (xparm < 0 && (drive->bios_cyl * drive->bios_head * drive->bios_sect) < (1024 * 16 * 63))
return 0; /* small disk: no translation needed */
if (drive->id) {
......@@ -2590,15 +2591,14 @@ int ide_xlate_1024 (kdev_t i_rdev, int xparm, const char *msg)
#if FAKE_FDISK_FOR_EZDRIVE
if (xparm == -1) {
drive->remap_0_to_1 = 1;
msg = "0->1";
printk("[remap 0->1] ");
} else
#endif /* FAKE_FDISK_FOR_EZDRIVE */
if (xparm == 1) {
drive->sect0 = 63;
drive->bios_cyl = (tracks - 1) / drive->bios_head;
msg = "+63";
printk("[remap +63] ");
}
printk("[remap %s] ", msg);
}
drive->part[0].nr_sects = current_capacity(drive);
printk("[%d/%d/%d]", drive->bios_cyl, drive->bios_head, drive->bios_sect);
......
......@@ -16,6 +16,7 @@
* once to be processed
* 97-4-11 Making protocol independent of endianity etc.
* 97-9-13 Cosmetic changes
* 98-5-13 Attempt to make 64-bit-clean on 64-bit machines
*
* possible FIXME: make set_sock / set_blksize / set_size / do_it one syscall
* why not: would need verify_area and friends, would share yet another
......@@ -24,18 +25,24 @@
#define PARANOIA
#include <linux/major.h>
#define MAJOR_NR NBD_MAJOR
#include <linux/nbd.h>
#include <linux/module.h>
#include <linux/sched.h>
#include <linux/fs.h>
#include <linux/stat.h>
#include <linux/errno.h>
#include <linux/file.h>
#include <linux/ioctl.h>
#include <asm/segment.h>
#include <asm/uaccess.h>
#include <asm/types.h>
#define MAJOR_NR NBD_MAJOR
#include <linux/nbd.h>
#define LO_MAGIC 0x68797548
static int nbd_blksizes[MAX_NBD] = {1024, 1024,};
static int nbd_sizes[MAX_NBD] = {0x7fffffff, 0x7fffffff,};
......@@ -68,8 +75,7 @@ static int nbd_open(struct inode *inode, struct file *file)
/*
* Send or receive packet.
*/
static
int nbd_xmit(int send, struct socket *sock, char *buf, int size)
static int nbd_xmit(int send, struct socket *sock, char *buf, int size)
{
mm_segment_t oldfs;
int result;
......@@ -132,7 +138,7 @@ void nbd_send_req(struct socket *sock, struct request *req)
DEBUG("NBD: sending control, ");
request.magic = htonl(NBD_REQUEST_MAGIC);
request.type = htonl(req->cmd);
request.from = htonl(req->sector * 512);
request.from = cpu_to_be64( (u64) req->sector * (u64) 512);
request.len = htonl(req->current_nr_sectors << 9);
memcpy(request.handle, &req, sizeof(req));
......@@ -153,8 +159,8 @@ void nbd_send_req(struct socket *sock, struct request *req)
}
#define HARDFAIL( s ) { printk( KERN_ERR "NBD: " s "(result %d)\n", result ); lo->harderror = result; return NULL; }
struct request * /* NULL returned = something went wrong, inform userspace */
nbd_read_stat(struct nbd_device *lo)
struct request *nbd_read_stat(struct nbd_device *lo)
/* NULL returned = something went wrong, inform userspace */
{
int result;
struct nbd_reply reply;
......@@ -425,8 +431,8 @@ int nbd_init(void)
{
int i;
if (sizeof(struct nbd_request) != 24) {
printk(KERN_CRIT "Sizeof nbd_request needs to be 24 in order to work!\n" );
if (sizeof(struct nbd_request) != 28) {
printk(KERN_CRIT "Sizeof nbd_request needs to be 28 in order to work!\n" );
return -EIO;
}
......
......@@ -86,7 +86,15 @@ static void pty_close(struct tty_struct * tty, struct file * filp)
if (tty->driver.subtype == PTY_TYPE_MASTER) {
tty_hangup(tty->link);
set_bit(TTY_OTHER_CLOSED, &tty->flags);
devpts_pty_kill(MINOR(tty->device) - tty->driver.minor_start);
#ifdef CONFIG_UNIX98_PTYS
{
unsigned int major = MAJOR(tty->device) - UNIX98_PTY_MASTER_MAJOR;
if ( major < UNIX98_NR_MAJORS ) {
devpts_pty_kill( MINOR(tty->device)
- tty->driver.minor_start + tty->driver.name_base );
}
}
#endif
}
}
......@@ -215,16 +223,20 @@ static int pty_chars_in_buffer(struct tty_struct *tty)
return ((count < N_TTY_BUF_SIZE/2) ? 0 : count);
}
/*
* Return the minor device number of a given pty. This lets us
* open a master pty with the multi-headed ptmx device, then
* find out which one we got after it is open, with an ioctl.
/*
* Return the device number of a Unix98 PTY (only!). This lets us open a
* master pty with the multi-headed ptmx device, then find out which
* one we got after it is open, with an ioctl.
*/
static int pty_get_device_minor(struct tty_struct *tty, unsigned int *value)
#ifdef CONFIG_UNIX98_PTYS
static int pty_get_device_number(struct tty_struct *tty, unsigned int *value)
{
unsigned int result = MINOR(tty->device);
unsigned int result = MINOR(tty->device)
- tty->driver.minor_start + tty->driver.name_base;
return put_user(result, value);
}
#endif
/* Set the lock flag on a pty */
static int pty_set_lock(struct tty_struct *tty, int * arg)
{
......@@ -238,22 +250,37 @@ static int pty_set_lock(struct tty_struct *tty, int * arg)
return 0;
}
static int pty_ioctl(struct tty_struct *tty, struct file *file,
unsigned int cmd, unsigned long arg)
static int pty_bsd_ioctl(struct tty_struct *tty, struct file *file,
unsigned int cmd, unsigned long arg)
{
if (!tty) {
printk("pty_ioctl called with NULL tty!\n");
return -EIO;
}
switch(cmd) {
case TIOCGPTN: /* Get PT Number */
return pty_get_device_minor(tty, (unsigned int *)arg);
case TIOCSPTLCK: /* Set PT Lock (disallow slave open) */
return pty_set_lock(tty, (int *) arg);
}
return -ENOIOCTLCMD;
}
#ifdef CONFIG_UNIX98_PTYS
static int pty_unix98_ioctl(struct tty_struct *tty, struct file *file,
unsigned int cmd, unsigned long arg)
{
if (!tty) {
printk("pty_unix98_ioctl called with NULL tty!\n");
return -EIO;
}
switch(cmd) {
case TIOCGPTN: /* Get PT Number */
return pty_get_device_number(tty, (unsigned int *)arg);
}
return pty_bsd_ioctl(tty,file,cmd,arg);
}
#endif
static void pty_flush_buffer(struct tty_struct *tty)
{
struct tty_struct *to = tty->link;
......@@ -370,7 +397,7 @@ __initfunc(int pty_init(void))
* assign it here, instead of up with the rest of the
* pty_driver initialization. <cananian@alumni.princeton.edu>
*/
pty_driver.ioctl = pty_ioctl;
pty_driver.ioctl = pty_bsd_ioctl;
/* Unix98 devices */
#ifdef CONFIG_UNIX98_PTYS
......@@ -381,6 +408,7 @@ __initfunc(int pty_init(void))
ptm_driver[i].proc_entry = 0;
ptm_driver[i].major = UNIX98_PTY_MASTER_MAJOR+i;
ptm_driver[i].minor_start = 0;
ptm_driver[i].name_base = i*NR_PTYS;
ptm_driver[i].num = NR_PTYS;
ptm_driver[i].other = &pts_driver[i];
ptm_driver[i].table = ptm_table[i];
......@@ -393,6 +421,7 @@ __initfunc(int pty_init(void))
pts_driver[i].proc_entry = 0;
pts_driver[i].major = UNIX98_PTY_SLAVE_MAJOR+i;
pts_driver[i].minor_start = 0;
pts_driver[i].name_base = i*NR_PTYS;
pts_driver[i].num = ptm_driver[i].num;
pts_driver[i].other = &ptm_driver[i];
pts_driver[i].table = pts_table[i];
......@@ -400,7 +429,7 @@ __initfunc(int pty_init(void))
pts_driver[i].termios_locked = pts_termios_locked[i];
pts_driver[i].driver_state = ptm_state[i];
ptm_driver[i].ioctl = pty_ioctl;
ptm_driver[i].ioctl = pty_unix98_ioctl;
if (tty_register_driver(&ptm_driver[i]))
panic("Couldn't register Unix98 ptm driver major %d",
......
......@@ -1238,7 +1238,7 @@ static int tty_open(struct inode * inode, struct file * filp)
#ifdef CONFIG_UNIX98_PTYS
if (device == PTMX_DEV) {
/* find a free pty. */
int major, minor, line;
int major, minor;
struct tty_driver *driver;
/* find a device that is not in use. */
......@@ -1255,9 +1255,8 @@ static int tty_open(struct inode * inode, struct file * filp)
return -EIO; /* no free ptys */
ptmx_found:
set_bit(TTY_PTY_LOCK, &tty->flags); /* LOCK THE SLAVE */
line = minor - driver->minor_start;
devpts_pty_new(line + major*NR_PTYS, MKDEV(driver->other->major,
line+driver->other->minor_start));
minor -= driver->minor_start;
devpts_pty_new(driver->other->name_base + minor, MKDEV(driver->other->major, minor + driver->other->minor_start));
noctty = 1;
goto init_dev_done;
}
......
......@@ -26,13 +26,14 @@
*/
#define BusLogic_DriverVersion "2.1.13"
#define BusLogic_DriverDate "17 April 1998"
#define BusLogic_DriverVersion "2.1.15"
#define BusLogic_DriverDate "17 August 1998"
#include <linux/version.h>
#include <linux/module.h>
#include <linux/config.h>
#include <linux/init.h>
#include <linux/types.h>
#include <linux/blk.h>
#include <linux/blkdev.h>
......@@ -1178,7 +1179,8 @@ static void BusLogic_InitializeProbeInfoList(BusLogic_HostAdapter_T
BusLogic_ProbeInfoCount - FlashPointCount;
memcpy(SavedProbeInfo,
BusLogic_ProbeInfoList,
sizeof(BusLogic_ProbeInfoList));
BusLogic_ProbeInfoCount
* sizeof(BusLogic_ProbeInfo_T));
memcpy(&BusLogic_ProbeInfoList[0],
&SavedProbeInfo[FlashPointCount],
MultiMasterCount * sizeof(BusLogic_ProbeInfo_T));
......@@ -3136,25 +3138,25 @@ static void BusLogic_ProcessCompletedCCBs(BusLogic_HostAdapter_T *HostAdapter)
HostAdapter->TargetStatistics[CCB->TargetID]
.CommandsCompleted++;
if (BusLogic_GlobalOptions.TraceErrors)
{
int i;
BusLogic_Notice("CCB #%ld Target %d: Result %X Host "
"Adapter Status %02X "
"Target Status %02X\n",
HostAdapter, CCB->SerialNumber,
CCB->TargetID, Command->result,
CCB->HostAdapterStatus,
CCB->TargetDeviceStatus);
BusLogic_Notice("CDB ", HostAdapter);
for (i = 0; i < CCB->CDB_Length; i++)
BusLogic_Notice(" %02X", HostAdapter, CCB->CDB[i]);
BusLogic_Notice("\n", HostAdapter);
BusLogic_Notice("Sense ", HostAdapter);
for (i = 0; i < CCB->SenseDataLength; i++)
BusLogic_Notice(" %02X", HostAdapter,
Command->sense_buffer[i]);
BusLogic_Notice("\n", HostAdapter);
}
{
int i;
BusLogic_Notice("CCB #%ld Target %d: Result %X Host "
"Adapter Status %02X "
"Target Status %02X\n",
HostAdapter, CCB->SerialNumber,
CCB->TargetID, Command->result,
CCB->HostAdapterStatus,
CCB->TargetDeviceStatus);
BusLogic_Notice("CDB ", HostAdapter);
for (i = 0; i < CCB->CDB_Length; i++)
BusLogic_Notice(" %02X", HostAdapter, CCB->CDB[i]);
BusLogic_Notice("\n", HostAdapter);
BusLogic_Notice("Sense ", HostAdapter);
for (i = 0; i < CCB->SenseDataLength; i++)
BusLogic_Notice(" %02X", HostAdapter,
Command->sense_buffer[i]);
BusLogic_Notice("\n", HostAdapter);
}
}
break;
}
......@@ -4206,7 +4208,6 @@ int BusLogic_ProcDirectoryInfo(char *ProcBuffer, char **StartPointer,
BusLogic_TargetStatistics_T *TargetStatistics;
int TargetID, Length;
char *Buffer;
if (WriteFlag) return 0;
for (HostAdapter = BusLogic_FirstRegisteredHostAdapter;
HostAdapter != NULL;
HostAdapter = HostAdapter->Next)
......@@ -4218,6 +4219,14 @@ int BusLogic_ProcDirectoryInfo(char *ProcBuffer, char **StartPointer,
return 0;
}
TargetStatistics = HostAdapter->TargetStatistics;
if (WriteFlag)
{
HostAdapter->ExternalHostAdapterResets = 0;
HostAdapter->HostAdapterInternalErrors = 0;
memset(TargetStatistics, 0,
BusLogic_MaxTargetDevices * sizeof(BusLogic_TargetStatistics_T));
return 0;
}
Buffer = HostAdapter->MessageBuffer;
Length = HostAdapter->MessageBufferLength;
Length += sprintf(&Buffer[Length], "\n\
......
......@@ -1772,4 +1772,43 @@ static void BusLogic_Message(BusLogic_MessageLevel_T, char *,
static void BusLogic_ParseDriverOptions(char *);
/*
Declare the Initialization Functions.
*/
static void BusLogic_AnnounceDriver(BusLogic_HostAdapter_T *) __init;
static void BusLogic_RegisterHostAdapter(BusLogic_HostAdapter_T *) __init;
static void BusLogic_UnregisterHostAdapter(BusLogic_HostAdapter_T *) __init;
static boolean BusLogic_CreateInitialCCBs(BusLogic_HostAdapter_T *) __init;
static void BusLogic_DestroyCCBs(BusLogic_HostAdapter_T *) __init;
static void BusLogic_AppendProbeAddressISA(BusLogic_IO_Address_T) __init;
static void
BusLogic_InitializeProbeInfoListISA(BusLogic_HostAdapter_T *) __init;
static void BusLogic_SortProbeInfo(BusLogic_ProbeInfo_T *, int) __init;
static int
BusLogic_InitializeMultiMasterProbeInfo(BusLogic_HostAdapter_T *) __init;
static int
BusLogic_InitializeFlashPointProbeInfo(BusLogic_HostAdapter_T *) __init;
static void BusLogic_InitializeProbeInfoList(BusLogic_HostAdapter_T *) __init;
static boolean BusLogic_Failure(BusLogic_HostAdapter_T *, char *) __init;
static boolean BusLogic_ProbeHostAdapter(BusLogic_HostAdapter_T *) __init;
static boolean BusLogic_CheckHostAdapter(BusLogic_HostAdapter_T *) __init;
static boolean
BusLogic_ReadHostAdapterConfiguration(BusLogic_HostAdapter_T *) __init;
static boolean
BusLogic_ReportHostAdapterConfiguration(BusLogic_HostAdapter_T *) __init;
static boolean BusLogic_AcquireResources(BusLogic_HostAdapter_T *) __init;
static void BusLogic_ReleaseResources(BusLogic_HostAdapter_T *) __init;
static boolean BusLogic_TargetDeviceInquiry(BusLogic_HostAdapter_T *) __init;
static void BusLogic_ReportTargetDeviceInfo(BusLogic_HostAdapter_T *) __init;
static void BusLogic_InitializeHostStructure(BusLogic_HostAdapter_T *,
SCSI_Host_T *) __init;
static void BusLogic_SelectQueueDepths(SCSI_Host_T *, SCSI_Device_T *) __init;
int BusLogic_DetectHostAdapter(SCSI_Host_Template_T *) __init;
int BusLogic_ReleaseHostAdapter(SCSI_Host_T *) __init;
static boolean BusLogic_ParseKeyword(char **, char *) __init;
static void BusLogic_ParseDriverOptions(char *) __init;
void BusLogic_Setup(char *, int *) __init;
#endif /* BusLogic_DriverVersion */
......@@ -3165,11 +3165,11 @@ STATIC s32bits probe_adapter(PADAPTER_INFO pAdapterInfo)
if(RD_HARPOON(ioport + hp_page_ctrl) & BIOS_SHADOW)
{
pAdapterInfo->ai_FlashRomSize = 64 * 1024; /* 64k Rom */
pAdapterInfo->ai_FlashRomSize = 64 * 1024; /* 64k ROM */
}
else
{
pAdapterInfo->ai_FlashRomSize = 32 * 1024; /* 32k Rom */
pAdapterInfo->ai_FlashRomSize = 32 * 1024; /* 32k ROM */
}
pAdapterInfo->ai_stateinfo |= (FAST20_ENA | TAG_QUEUE_ENA);
......@@ -4944,7 +4944,7 @@ int SccbMgr_isr(ULONG pCurrCard)
*
* Function: Sccb_bad_isr
*
* Description: Some type of interrupt has occured which is slightly
* Description: Some type of interrupt has occurred which is slightly
* out of the ordinary. We will now decode it fully, in
* this routine. This is broken up in an attempt to save
* processing time.
......@@ -7038,7 +7038,7 @@ void siwidr(ULONG port, UCHAR width)
*
* Function: sssyncv
*
* Description: Write the desired value to the Sync Regisiter for the
* Description: Write the desired value to the Sync Register for the
* ID specified.
*
*---------------------------------------------------------------------*/
......
BusLogic MultiMaster and FlashPoint SCSI Driver for Linux
Version 2.0.12 for Linux 2.0
Version 2.0.15 for Linux 2.0
Version 2.1.15 for Linux 2.1
PRODUCTION RELEASE
29 March 1998
17 August 1998
Leonard N. Zubkoff
Dandelion Digital
lnz@dandelion.com
Copyright 1995 by Leonard N. Zubkoff <lnz@dandelion.com>
Copyright 1995-1998 by Leonard N. Zubkoff <lnz@dandelion.com>
INTRODUCTION
......@@ -80,7 +81,7 @@ including: ... Linux ...".
Mylex Corporation is located at 34551 Ardenwood Blvd., Fremont, California
94555, USA and can be reached at 510/796-6100 or on the World Wide Web at
http://www.mylex.com. Mylex Technical Support can be reached by electronic
http://www.mylex.com. Mylex HBA Technical Support can be reached by electronic
mail at techsup@mylex.com, by Voice at 510/608-2400, or by FAX at 510/745-7715.
Contact information for offices in Europe and Japan is available on the Web
site.
......@@ -584,16 +585,16 @@ NOTE: Module Utilities 2.1.71 or later is required for correct parsing
DRIVER INSTALLATION
This distribution was prepared for Linux kernel version 2.0.33, but should be
This distribution was prepared for Linux kernel version 2.0.35, but should be
compatible with 2.0.4 or any later 2.0 series kernel.
To install the new BusLogic SCSI driver, you may use the following commands,
replacing "/usr/src" with wherever you keep your Linux kernel source tree:
cd /usr/src
tar -xvzf BusLogic-2.0.12.tar.gz
tar -xvzf BusLogic-2.0.15.tar.gz
mv README.* LICENSE.* BusLogic.[ch] FlashPoint.c linux/drivers/scsi
patch -p < BusLogic.patch
patch -p0 < BusLogic.patch (only for 2.0.33 and below)
cd linux
make config
make depend
......
Please see the file README.BusLogic for information about Linux support for
Mylex (formerly BusLogic) MultiMaster and FlashPoint SCSI Host Adapters.
The Mylex DAC960 PCI RAID Controllers are not supported at the present time,
but work on a Linux driver for the DAC960 is in progress. Please consult
The Mylex DAC960 PCI RAID Controllers are now supported. Please consult
http://www.dandelion.com/Linux/ for further information on the DAC960 driver.
......@@ -129,7 +129,7 @@ void autofs_hash_nuke(struct autofs_dirhash *);
/* Expiration-handling functions */
void autofs_update_usage(struct autofs_dirhash *,struct autofs_dir_ent *);
struct autofs_dir_ent *autofs_expire(struct autofs_dirhash *,unsigned long);
struct autofs_dir_ent *autofs_expire(struct super_block *,struct autofs_sb_info *);
/* Operations structures */
......
......@@ -37,15 +37,72 @@ void autofs_update_usage(struct autofs_dirhash *dh,
autofs_init_usage(dh,ent); /* Relink at queue tail */
}
struct autofs_dir_ent *autofs_expire(struct autofs_dirhash *dh,
unsigned long timeout)
struct autofs_dir_ent *autofs_expire(struct super_block *sb,
struct autofs_sb_info *sbi)
{
struct autofs_dirhash *dh = &sbi->dirhash;
struct autofs_dir_ent *ent;
struct dentry *dentry;
unsigned long timeout = sbi->exp_timeout;
ent = dh->expiry_head.exp_next;
if ( ent == &(dh->expiry_head) ) return NULL;
return (jiffies - ent->last_usage >= timeout) ? ent : NULL;
if ( ent == &(dh->expiry_head) )
return NULL; /* No entries */
while ( jiffies - ent->last_usage >= timeout ) {
/* Move to end of list in case expiry isn't desirable */
autofs_update_usage(dh, ent);
/* Check to see that entry is expirable */
if ( ent->ino < AUTOFS_FIRST_DIR_INO )
return ent; /* Symlinks are always expirable */
/* Get the dentry for the autofs subdirectory */
dentry = lookup_dentry(ent->name, dget(sb->s_root), 0);
if ( IS_ERR(dentry) ) {
printk("autofs: no such dentry on expiry queue: %s\n",
ent->name);
autofs_delete_usage(ent);
continue;
}
if ( !dentry->d_inode ) {
dput(dentry);
printk("autofs: negative dentry on expiry queue: %s\n",
ent->name);
autofs_delete_usage(ent);
continue;
}
/* Make sure entry is mounted and unused; note that dentry will
point to the mounted-on-top root. */
if ( !S_ISDIR(dentry->d_inode->i_mode)
|| dentry->d_covers == dentry ) {
dput(dentry);
DPRINTK(("autofs: not expirable (not a mounted directory): %s\n", ent->name));
continue;
}
/*
* Now, this is known to be a mount point; therefore the dentry
* will be held by the superblock. is_root_busy() will break if
* we hold a use count here, so we have to dput() it before calling
* is_root_busy(). However, since it is a mount point (already
* verified), dput() will be a nonblocking operation and the use
* count will not go to zero; therefore the call to is_root_busy()
* here is legal.
*/
dput(dentry);
if ( !is_root_busy(dentry) ) {
DPRINTK(("autofs: signaling expire on %s\n", ent->name));
return ent; /* Expirable! */
}
DPRINTK(("autofs: didn't expire due to is_root_busy: %s\n", ent->name));
}
return NULL; /* No expirable entries */
}
void autofs_initialize_hash(struct autofs_dirhash *dh) {
......
......@@ -289,7 +289,7 @@ static int autofs_root_symlink(struct inode *dir, struct dentry *dentry, const c
return -ENOSPC;
}
ent->name = kmalloc(dentry->d_name.len, GFP_KERNEL);
ent->name = kmalloc(dentry->d_name.len+1, GFP_KERNEL);
if ( !ent->name ) {
kfree(sl->data);
kfree(ent);
......@@ -302,7 +302,7 @@ static int autofs_root_symlink(struct inode *dir, struct dentry *dentry, const c
ent->ino = AUTOFS_FIRST_SYMLINK + n;
ent->hash = dentry->d_name.hash;
memcpy(ent->name, dentry->d_name.name,ent->len = dentry->d_name.len);
memcpy(ent->name, dentry->d_name.name, 1+(ent->len = dentry->d_name.len));
autofs_hash_insert(dh,ent);
d_instantiate(dentry, iget(dir->i_sb,ent->ino));
......@@ -392,14 +392,14 @@ static int autofs_root_mkdir(struct inode *dir, struct dentry *dentry, int mode)
if ( !ent )
return -ENOSPC;
ent->name = kmalloc(dentry->d_name.len, GFP_KERNEL);
ent->name = kmalloc(dentry->d_name.len+1, GFP_KERNEL);
if ( !ent->name ) {
kfree(ent);
return -ENOSPC;
}
ent->hash = dentry->d_name.hash;
memcpy(ent->name, dentry->d_name.name, ent->len = dentry->d_name.len);
memcpy(ent->name, dentry->d_name.name, 1+(ent->len = dentry->d_name.len));
ent->ino = sbi->next_dir_ino++;
autofs_hash_insert(dh,ent);
dir->i_nlink++;
......@@ -434,20 +434,20 @@ static inline int autofs_get_protover(int *p)
}
/* Perform an expiry operation */
static inline int autofs_expire_run(struct autofs_sb_info *sbi,
static inline int autofs_expire_run(struct super_block *sb,
struct autofs_sb_info *sbi,
struct autofs_packet_expire *pkt_p)
{
struct autofs_dir_ent *ent;
struct autofs_packet_expire pkt;
struct autofs_dirhash *dh = &(sbi->dirhash);
memset(&pkt,0,sizeof pkt);
pkt.hdr.proto_version = AUTOFS_PROTO_VERSION;
pkt.hdr.type = autofs_ptype_expire;
if ( !sbi->exp_timeout ||
!(ent = autofs_expire(dh,sbi->exp_timeout)) )
!(ent = autofs_expire(sb,sbi)) )
return -EAGAIN;
pkt.len = ent->len;
......@@ -456,8 +456,6 @@ static inline int autofs_expire_run(struct autofs_sb_info *sbi,
if ( copy_to_user(pkt_p, &pkt, sizeof(struct autofs_packet_expire)) )
return -EFAULT;
autofs_update_usage(dh,ent);
return 0;
}
......@@ -494,7 +492,8 @@ static int autofs_root_ioctl(struct inode *inode, struct file *filp,
case AUTOFS_IOC_SETTIMEOUT:
return autofs_get_set_timeout(sbi,(unsigned long *)arg);
case AUTOFS_IOC_EXPIRE:
return autofs_expire_run(sbi,(struct autofs_packet_expire *)arg);
return autofs_expire_run(inode->i_sb,sbi,
(struct autofs_packet_expire *)arg);
default:
return -ENOSYS;
}
......
......@@ -1054,7 +1054,7 @@ static int elf_core_dump(long signr, struct pt_regs * regs)
struct vm_area_struct *vma;
struct elfhdr elf;
off_t offset = 0, dataoff;
long limit = current->rlim[RLIMIT_CORE].rlim_cur;
unsigned long limit = current->rlim[RLIMIT_CORE].rlim_cur;
int numnote = 4;
struct memelfnote notes[4];
struct elf_prstatus prstatus; /* NT_PRSTATUS */
......@@ -1077,7 +1077,7 @@ static int elf_core_dump(long signr, struct pt_regs * regs)
for(vma = current->mm->mmap; vma != NULL; vma = vma->vm_next) {
if (maydump(vma))
{
int sz = vma->vm_end-vma->vm_start;
unsigned long sz = vma->vm_end-vma->vm_start;
if (size+sz >= limit)
break;
......
......@@ -402,7 +402,7 @@ int is_root_busy(struct dentry *root)
this_parent = this_parent->d_parent;
goto resume;
}
return (count == 1); /* one remaining use count? */
return (count > 1); /* remaining users? */
}
/*
......
......@@ -32,7 +32,7 @@
int ntfs_fixup_record(ntfs_volume *vol, char *record, char *magic, int size)
{
int start, count, offset;
short fixup;
unsigned short fixup;
if(!IS_MAGIC(record,magic))
return 0;
......
......@@ -3,12 +3,6 @@
#include <linux/linkage.h>
#ifdef __SMP__
extern void __check_locks(unsigned int);
#else
#define __check_locks(x) do { } while (0)
#endif
/*
* SMP- and interrupt-safe semaphores..
*
......@@ -90,7 +84,6 @@ static inline int waking_non_zero(struct semaphore *sem)
*/
extern inline void down(struct semaphore * sem)
{
__check_locks(0);
__asm__ __volatile__(
"# atomic down operation\n\t"
#ifdef __SMP__
......@@ -112,7 +105,6 @@ extern inline int down_interruptible(struct semaphore * sem)
{
int result;
__check_locks(0);
__asm__ __volatile__(
"# atomic interruptible down operation\n\t"
#ifdef __SMP__
......
......@@ -8,20 +8,13 @@
extern spinlock_t kernel_flag;
#ifdef __SMP__
extern void __check_locks(unsigned int);
#else
#define __check_locks(x) do { } while (0)
#endif
/*
* Release global kernel lock and global interrupt lock
*/
#define release_kernel_lock(task, cpu) \
do { \
if (task->lock_depth >= 0) \
__asm__ __volatile__(spin_unlock_string \
:"=m" (__dummy_lock(&kernel_flag))); \
spin_unlock(&kernel_flag); \
release_irqlock(cpu); \
__sti(); \
} while (0)
......@@ -32,8 +25,7 @@ do { \
#define reacquire_kernel_lock(task) \
do { \
if (task->lock_depth >= 0) \
__asm__ __volatile__(spin_lock_string \
:"=m" (__dummy_lock(&kernel_flag))); \
spin_lock(&kernel_flag); \
} while (0)
......@@ -46,7 +38,6 @@ do { \
*/
extern __inline__ void lock_kernel(void)
{
__check_locks(1);
__asm__ __volatile__(
"incl %1\n\t"
"jne 9f"
......
......@@ -152,12 +152,10 @@ typedef struct { unsigned long a[100]; } __dummy_lock_t;
#define spin_lock(lock) \
__asm__ __volatile__( \
spin_lock_string \
"\n\tcall __getlock" \
:"=m" (__dummy_lock(lock)))
#define spin_unlock(lock) \
__asm__ __volatile__( \
"call __putlock\n\t" \
spin_unlock_string \
:"=m" (__dummy_lock(lock)))
......@@ -202,7 +200,6 @@ typedef struct {
asm volatile("\n1:\t" \
"lock ; incl %0\n\t" \
"js 2f\n" \
"call __getlock\n" \
".section .text.lock,\"ax\"\n" \
"2:\tlock ; decl %0\n" \
"3:\tcmpl $0,%0\n\t" \
......@@ -212,9 +209,7 @@ typedef struct {
:"=m" (__dummy_lock(&(rw)->lock)))
#define read_unlock(rw) \
asm volatile( \
"call __putlock\n" \
"lock ; decl %0" \
asm volatile("lock ; decl %0" \
:"=m" (__dummy_lock(&(rw)->lock)))
#define write_lock(rw) \
......@@ -223,7 +218,6 @@ typedef struct {
"jc 4f\n" \
"2:\ttestl $0x7fffffff,%0\n\t" \
"jne 3f\n" \
"call __getlock\n" \
".section .text.lock,\"ax\"\n" \
"3:\tlock ; btrl $31,%0\n" \
"4:\tcmp $0,%0\n\t" \
......@@ -233,10 +227,7 @@ typedef struct {
:"=m" (__dummy_lock(&(rw)->lock)))
#define write_unlock(rw) \
asm volatile( \
"call __putlock\n" \
"lock ; btrl $31,%0": \
"=m" (__dummy_lock(&(rw)->lock)))
asm volatile("lock ; btrl $31,%0":"=m" (__dummy_lock(&(rw)->lock)))
#define read_lock_irq(lock) do { __cli(); read_lock(lock); } while (0)
#define read_unlock_irq(lock) do { read_unlock(lock); __sti(); } while (0)
......
......@@ -7,12 +7,6 @@
#include <linux/sched.h>
#include <asm/page.h>
#ifdef __SMP__
extern void __check_locks(unsigned int);
#else
#define __check_locks(x) do { } while (0)
#endif
#define VERIFY_READ 0
#define VERIFY_WRITE 1
......@@ -118,7 +112,6 @@ extern void __get_user_4(void);
/* Careful: we have to cast the result to the type of the pointer for sign reasons */
#define get_user(x,ptr) \
({ int __ret_gu,__val_gu; \
__check_locks(1); \
switch(sizeof (*(ptr))) { \
case 1: __get_user_x(1,__ret_gu,__val_gu,ptr); break; \
case 2: __get_user_x(2,__ret_gu,__val_gu,ptr); break; \
......@@ -143,7 +136,6 @@ extern void __put_user_bad(void);
#define put_user(x,ptr) \
({ int __ret_pu; \
__check_locks(1); \
switch(sizeof (*(ptr))) { \
case 1: __put_user_x(1,__ret_pu,(__typeof__(*(ptr)))(x),ptr); break; \
case 2: __put_user_x(2,__ret_pu,(__typeof__(*(ptr)))(x),ptr); break; \
......@@ -161,7 +153,6 @@ extern void __put_user_bad(void);
#define __put_user_nocheck(x,ptr,size) \
({ \
long __pu_err; \
__check_locks(1); \
__put_user_size((x),(ptr),(size),__pu_err); \
__pu_err; \
})
......@@ -204,7 +195,6 @@ struct __large_struct { unsigned long buf[100]; };
#define __get_user_nocheck(x,ptr,size) \
({ \
long __gu_err, __gu_val; \
__check_locks(1); \
__get_user_size(__gu_val,(ptr),(size),__gu_err); \
(x) = (__typeof__(*(ptr)))__gu_val; \
__gu_err; \
......@@ -284,7 +274,6 @@ do { \
static inline unsigned long
__generic_copy_from_user_nocheck(void *to, const void *from, unsigned long n)
{
__check_locks(1);
__copy_user(to,from,n);
return n;
}
......@@ -292,7 +281,6 @@ __generic_copy_from_user_nocheck(void *to, const void *from, unsigned long n)
static inline unsigned long
__generic_copy_to_user_nocheck(void *to, const void *from, unsigned long n)
{
__check_locks(1);
__copy_user(to,from,n);
return n;
}
......@@ -387,7 +375,6 @@ unsigned long __generic_copy_from_user(void *, const void *, unsigned long);
static inline unsigned long
__constant_copy_to_user(void *to, const void *from, unsigned long n)
{
__check_locks(1);
if (access_ok(VERIFY_WRITE, to, n))
__constant_copy_user(to,from,n);
return n;
......@@ -396,7 +383,6 @@ __constant_copy_to_user(void *to, const void *from, unsigned long n)
static inline unsigned long
__constant_copy_from_user(void *to, const void *from, unsigned long n)
{
__check_locks(1);
if (access_ok(VERIFY_READ, from, n))
__constant_copy_user(to,from,n);
return n;
......@@ -405,7 +391,6 @@ __constant_copy_from_user(void *to, const void *from, unsigned long n)
static inline unsigned long
__constant_copy_to_user_nocheck(void *to, const void *from, unsigned long n)
{
__check_locks(1);
__constant_copy_user(to,from,n);
return n;
}
......@@ -413,7 +398,6 @@ __constant_copy_to_user_nocheck(void *to, const void *from, unsigned long n)
static inline unsigned long
__constant_copy_from_user_nocheck(void *to, const void *from, unsigned long n)
{
__check_locks(1);
__constant_copy_user(to,from,n);
return n;
}
......
......@@ -258,6 +258,7 @@ extern inline unsigned long get_free_page(int gfp_mask)
* Decide if we should try to do some swapout..
*/
extern int free_memory_available(void);
extern struct wait_queue * kswapd_wait;
#define free_page(addr) free_pages((addr),0)
extern void FASTCALL(free_pages(unsigned long addr, unsigned long order));
......@@ -312,8 +313,7 @@ extern void put_cached_page(unsigned long);
* GFP bitmasks..
*/
#define __GFP_WAIT 0x01
#define __GFP_IO 0x02
#define __GFP_LOW 0x00
#define __GFP_LOW 0x02
#define __GFP_MED 0x04
#define __GFP_HIGH 0x08
......@@ -321,9 +321,9 @@ extern void put_cached_page(unsigned long);
#define GFP_BUFFER (__GFP_LOW | __GFP_WAIT)
#define GFP_ATOMIC (__GFP_HIGH)
#define GFP_USER (__GFP_LOW | __GFP_WAIT | __GFP_IO)
#define GFP_KERNEL (__GFP_MED | __GFP_WAIT | __GFP_IO)
#define GFP_NFS (__GFP_HIGH | __GFP_WAIT | __GFP_IO)
#define GFP_USER (__GFP_LOW | __GFP_WAIT)
#define GFP_KERNEL (__GFP_MED | __GFP_WAIT)
#define GFP_NFS (__GFP_HIGH | __GFP_WAIT)
/* Flag - indicates that the buffer will be suitable for DMA. Ignored on some
platforms, used as appropriate on others */
......
#ifndef LINUX_NBD_H
#define LINUX_NBD_H
#include <linux/ioctl.h>
#include <asm/types.h>
#define NBD_SET_SOCK _IO( 0xab, 0 )
#define NBD_SET_BLKSIZE _IO( 0xab, 1 )
#define NBD_SET_SIZE _IO( 0xab, 2 )
#define NBD_DO_IT _IO( 0xab, 3 )
#define NBD_CLEAR_SOCK _IO( 0xab, 4 )
#define NBD_CLEAR_QUE _IO( 0xab, 5 )
#define NBD_PRINT_DEBUG _IO( 0xab, 6 )
#define NBD_SET_SOCK _IO( 0xab, 0 )
#define NBD_SET_BLKSIZE _IO( 0xab, 1 )
#define NBD_SET_SIZE _IO( 0xab, 2 )
#define NBD_DO_IT _IO( 0xab, 3 )
#define NBD_CLEAR_SOCK _IO( 0xab, 4 )
#define NBD_CLEAR_QUE _IO( 0xab, 5 )
#define NBD_PRINT_DEBUG _IO( 0xab, 6 )
#ifdef MAJOR_NR
......@@ -54,21 +51,23 @@ struct nbd_device {
/* This now IS in some kind of include file... */
#define NBD_REQUEST_MAGIC 0x12560953
#define NBD_REPLY_MAGIC 0x96744668
#define LO_MAGIC 0x68797548
/* These are send over network in request/reply magic field */
#define NBD_REQUEST_MAGIC 0x25609513
#define NBD_REPLY_MAGIC 0x67446698
/* Do *not* use magics: 0x12560953 0x96744668. */
struct nbd_request {
__u32 magic;
__u32 from;
__u32 len;
u32 magic;
u32 type; /* == READ || == WRITE */
char handle[8];
__u32 type; /* == READ || == WRITE */
u64 from;
u32 len;
};
struct nbd_reply {
__u32 magic;
u32 magic;
u32 error; /* 0 = ok, else error */
char handle[8]; /* handle you got from request */
__u32 error; /* 0 = ok, else error */
};
#endif
......@@ -320,6 +320,7 @@ struct task_struct {
#define PF_SUPERPRIV 0x00000100 /* used super-user privileges */
#define PF_DUMPCORE 0x00000200 /* dumped core */
#define PF_SIGNALED 0x00000400 /* killed by a signal */
#define PF_MEMALLOC 0x00000800 /* Allocating memory */
#define PF_USEDFPU 0x00100000 /* task used FPU this quantum (SMP) */
#define PF_DTRACE 0x00200000 /* delayed trace (used on m68k) */
......
......@@ -68,7 +68,7 @@ asmlinkage int sys_capget(cap_user_header_t header, cap_user_data_t dataptr)
if (target != current)
read_unlock(&tasklist_lock);
spin_unlock(&task_capacibility_lock);
spin_unlock(&task_capability_lock);
if (!error) {
if (copy_to_user(dataptr, &data, sizeof data))
......
......@@ -51,9 +51,9 @@ spinlock_t taskslot_lock = SPIN_LOCK_UNLOCKED;
#define UIDHASH_SZ (PIDHASH_SZ >> 2)
static struct user_struct {
atomic_t count;
struct user_struct *next, **pprev;
unsigned int uid;
int task_count;
} *uidhash[UIDHASH_SZ];
spinlock_t uidhash_lock = SPIN_LOCK_UNLOCKED;
......@@ -98,12 +98,10 @@ void free_uid(struct task_struct *p)
if (up) {
p->user = NULL;
lock_kernel();
if (!--up->task_count) {
if (atomic_dec_and_test(&up->count)) {
uid_hash_remove(up);
kmem_cache_free(uid_cachep, up);
}
unlock_kernel();
}
}
......@@ -119,11 +117,11 @@ int alloc_uid(struct task_struct *p)
return -EAGAIN;
p->user = up;
up->uid = p->uid;
up->task_count = 0;
atomic_set(&up->count, 0);
uid_hash_insert(up, hashent);
}
up->task_count++;
atomic_inc(&up->count);
return 0;
}
......@@ -487,7 +485,7 @@ int do_fork(unsigned long clone_flags, unsigned long usp, struct pt_regs *regs)
lock_kernel();
if (p->user) {
if (p->user->task_count >= p->rlim[RLIMIT_NPROC].rlim_cur)
if (atomic_read(&p->user->count) >= p->rlim[RLIMIT_NPROC].rlim_cur)
goto bad_fork_free;
}
......@@ -567,7 +565,7 @@ int do_fork(unsigned long clone_flags, unsigned long usp, struct pt_regs *regs)
nr_tasks++;
if (p->user)
p->user->task_count++;
atomic_inc(&p->user->count);
retval = -ENOMEM;
/* copy all the process information */
......@@ -633,7 +631,7 @@ int do_fork(unsigned long clone_flags, unsigned long usp, struct pt_regs *regs)
}
if (p->user)
p->user->task_count++;
atomic_dec(&p->user->count);
nr_tasks--;
add_free_taskslot(p->tarray_ptr);
bad_fork_free:
......
......@@ -15,6 +15,7 @@
#include <linux/types.h>
#include <linux/unistd.h>
#include <linux/smp_lock.h>
#include <linux/signal.h>
#include <asm/uaccess.h>
......@@ -22,7 +23,6 @@
modprobe_path is set via /proc/sys.
*/
char modprobe_path[256] = "/sbin/modprobe";
static char * envp[] = { "HOME=/", "TERM=linux", "PATH=/sbin:/usr/sbin:/bin:/usr/bin", NULL };
/*
exec_modprobe is spawned from a kernel-mode user process,
......@@ -41,14 +41,15 @@ use_init_file_context(void)
/* don't use the user's root, use init's root instead */
exit_fs(current); /* current->fs->count--; */
current->fs = task_init->fs;
current->fs->count++;
atomic_inc(&current->fs->count);
unlock_kernel();
}
static int exec_modprobe(void * module_name)
{
char *argv[] = { modprobe_path, "-s", "-k", (char*)module_name, NULL};
static char * envp[] = { "HOME=/", "TERM=linux", "PATH=/sbin:/usr/sbin:/bin:/usr/bin", NULL };
char *argv[] = { modprobe_path, "-s", "-k", (char*)module_name, NULL };
int i;
use_init_file_context();
......@@ -97,6 +98,7 @@ int request_module(const char * module_name)
{
int pid;
int waitpid_result;
sigset_t tmpsig;
/* Don't allow request_module() before the root fs is mounted! */
if ( ! current->fs->root ) {
......@@ -107,10 +109,25 @@ int request_module(const char * module_name)
pid = kernel_thread(exec_modprobe, (void*) module_name, CLONE_FS);
if (pid < 0) {
printk(KERN_ERR "kmod: fork failed, errno %d\n", -pid);
printk(KERN_ERR "request_module[%s]: fork failed, errno %d\n", module_name, -pid);
return pid;
}
/* Block everything but SIGKILL/SIGSTOP */
spin_lock_irq(&current->sigmask_lock);
tmpsig = current->blocked;
siginitset(&current->blocked, ~(sigmask(SIGKILL)|sigmask(SIGSTOP)));
recalc_sigpending(current);
spin_unlock_irq(&current->sigmask_lock);
waitpid_result = waitpid(pid, NULL, __WCLONE);
/* Allow signals again.. */
spin_lock_irq(&current->sigmask_lock);
current->blocked = tmpsig;
recalc_sigpending(current);
spin_unlock_irq(&current->sigmask_lock);
if (waitpid_result != pid) {
printk (KERN_ERR "kmod: waitpid(%d,NULL,0) failed, returning %d.\n",
pid, waitpid_result);
......
......@@ -470,8 +470,6 @@ asmlinkage void schedule(void)
goto scheduling_in_interrupt;
release_kernel_lock(prev, this_cpu);
__check_locks(1);
/* Do "administrative" work here while we don't hold any locks */
if (bh_active & bh_mask)
do_bottom_half();
......
......@@ -172,10 +172,12 @@ static inline int shrink_one_page(struct page *page, int gfp_mask)
break;
}
age_page(page);
#if 0
if (page->age)
break;
if (page_cache_size * 100 < (page_cache.min_percent * num_physpages))
break;
#endif
if (PageSwapCache(page)) {
delete_from_swap_cache(page);
return 1;
......@@ -189,7 +191,7 @@ static inline int shrink_one_page(struct page *page, int gfp_mask)
break;
/* is it a buffer cache page? */
if ((gfp_mask & __GFP_IO) && bh && try_to_free_buffer(bh, &bh, 6))
if (bh && try_to_free_buffer(bh, &bh, 6))
return 1;
break;
......@@ -211,8 +213,8 @@ int shrink_mmap(int priority, int gfp_mask)
struct page * page;
int count_max, count_min;
count_max = (limit<<2) >> (priority>>1);
count_min = (limit<<2) >> (priority);
count_max = (limit<<1) >> (priority>>1);
count_min = (limit<<1) >> (priority);
page = mem_map + clock;
do {
......@@ -327,6 +329,7 @@ static unsigned long try_to_read_ahead(struct file * file,
*/
page = mem_map + MAP_NR(page_cache);
add_to_page_cache(page, inode, offset, hash);
set_bit(PG_referenced, &page->flags);
inode->i_op->readpage(file, page);
page_cache = 0;
}
......
......@@ -239,7 +239,6 @@ unsigned long __get_free_pages(int gfp_mask, unsigned long order)
goto nopage;
if (gfp_mask & __GFP_WAIT) {
__check_locks(1);
if (in_interrupt()) {
static int count = 0;
if (++count < 5) {
......@@ -264,6 +263,16 @@ unsigned long __get_free_pages(int gfp_mask, unsigned long order)
spin_lock_irqsave(&page_alloc_lock, flags);
RMQUEUE(order, (gfp_mask & GFP_DMA));
spin_unlock_irqrestore(&page_alloc_lock, flags);
/*
* If we failed to find anything, we'll return NULL, but we'll
* wake up kswapd _now_ ad even wait for it synchronously if
* we can.. This way we'll at least make some forward progress
* over time.
*/
wake_up(&kswapd_wait);
if (gfp_mask & __GFP_WAIT)
schedule();
nopage:
return 0;
}
......
......@@ -42,7 +42,7 @@ int swapout_interval = HZ / 4;
/*
* The wait queue for waking up the pageout daemon:
*/
static struct wait_queue * kswapd_wait = NULL;
struct wait_queue * kswapd_wait = NULL;
static void init_swap_timer(void);
......@@ -469,7 +469,7 @@ static int do_try_to_free_page(int gfp_mask)
return 1;
state = 1;
case 1:
if ((gfp_mask & __GFP_IO) && shm_swap(i, gfp_mask))
if (shm_swap(i, gfp_mask))
return 1;
state = 2;
case 2:
......@@ -525,7 +525,7 @@ int kswapd(void *unused)
/* Give kswapd a realtime priority. */
current->policy = SCHED_FIFO;
current->priority = 32; /* Fixme --- we need to standardise our
current->rt_priority = 32; /* Fixme --- we need to standardise our
namings for POSIX.4 realtime scheduling
priorities. */
......@@ -558,22 +558,18 @@ int kswapd(void *unused)
*/
tries = pager_daemon.tries_base;
tries >>= 4*free_memory_available();
while (tries--) {
int gfp_mask;
if (free_memory_available() > 1)
break;
gfp_mask = __GFP_IO;
do_try_to_free_page(gfp_mask);
do {
do_try_to_free_page(0);
/*
* Syncing large chunks is faster than swapping
* synchronously (less head movement). -- Rik.
*/
if (atomic_read(&nr_async_pages) >= pager_daemon.swap_cluster)
run_task_queue(&tq_disk);
}
if (free_memory_available() > 1)
break;
} while (--tries > 0);
}
/* As if we could ever get here - maybe we want to make this killable */
remove_wait_queue(&kswapd_wait, &wait);
......@@ -582,23 +578,30 @@ int kswapd(void *unused)
}
/*
* This is REALLY ugly.
*
* We need to make the locks finer granularity, but right
* now we need this so that we can do page allocations
* without holding the kernel lock etc.
*
* The "PF_MEMALLOC" flag protects us against recursion:
* if we need more memory as part of a swap-out effort we
* will just silently return "success" to tell the page
* allocator to accept the allocation.
*/
int try_to_free_pages(unsigned int gfp_mask, int count)
{
int retval;
int retval = 1;
lock_kernel();
do {
retval = do_try_to_free_page(gfp_mask);
if (!retval)
break;
count--;
} while (count > 0);
if (current->flags & PF_MEMALLOC) {
current->flags |= PF_MEMALLOC;
do {
retval = do_try_to_free_page(gfp_mask);
if (!retval)
break;
count--;
} while (count > 0);
current->flags &= PF_MEMALLOC;
}
unlock_kernel();
return retval;
}
......
......@@ -543,8 +543,8 @@ struct sk_buff *sock_wmalloc(struct sock *sk, unsigned long size, int force, int
atomic_add(skb->truesize, &sk->wmem_alloc);
skb->destructor = sock_wfree;
skb->sk = sk;
return skb;
}
return skb;
}
return NULL;
}
......@@ -557,8 +557,8 @@ struct sk_buff *sock_rmalloc(struct sock *sk, unsigned long size, int force, int
atomic_add(skb->truesize, &sk->rmem_alloc);
skb->destructor = sock_rfree;
skb->sk = sk;
return skb;
}
return skb;
}
return NULL;
}
......
......@@ -370,6 +370,16 @@ static struct sk_buff *ip_glue(struct ipq *qp)
skb->pkt_type = qp->fragments->skb->pkt_type;
skb->protocol = qp->fragments->skb->protocol;
/*
* Clearly bogus, because security markings of the individual
* fragments should have been checked for consistency before
* gluing, and intermediate coalescing of fragments may have
* taken place in ip_defrag() before ip_glue() ever got called.
* If we're not going to do the consistency checking, we might
* as well take the value associated with the first fragment.
* --rct
*/
skb->security = qp->fragments->skb->security;
/* Done with all fragments. Fixup the new IP header. */
iph = skb->nh.iph;
......
......@@ -25,6 +25,7 @@
* Oct 15, 1997 Farhan Thawar changed wan_encapsulate to add a pad byte of 0
* Apr 20, 1998 Alan Cox Fixed 2.1 symbols
* May 17, 1998 K. Baranowski Fixed SNAP encapsulation in wan_encapsulate
* Aug 15, 1998 Arnaldo C. Melo Fixed device_setup return value
*****************************************************************************/
#include <linux/stddef.h> /* offsetof(), etc. */
......@@ -466,7 +467,7 @@ static int device_setup (wan_device_t* wandev, wandev_conf_t* u_conf)
if(!copy_from_user(data, conf->data, conf->data_size))
{
conf->data=data;
wandev->setup(wandev,conf);
err = wandev->setup(wandev,conf);
}
else
err = -ENOBUFS;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment