Skip to contentSkip to conversation

2.6.20-stable review

PATCH Applied Greg KH 11 participants 57 messages Mar 30, 2007 – Apr 4, 2007

Subsystems (11)
lore
Share & tools
lore

Greg KH

author
#0 lore raw

cover 2.6.20-stable review

This is the start of the stable review cycle for the 2.6.20.5 release. There are 37 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let us know. If anyone is a maintainer of the proper subsystem, and wants to add a Signed-off-by: line to the patch, please respond with it.

These patches are sent out with a number of different people on the Cc:
line. If you wish to be a reviewer, please email [email protected] to add your name to the list. If you want to be off the reviewer list, also email us.

Responses should be made by Tuesday, April 3, 00:00:00 UTC. Anything received after that time might be too late.

thanks,

greg k-h

author
#1 lore raw

PATCH 1/37 ide: clear bmdma status in ide_intr() for ICHx controllers (revised #4)

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Albert Lee <[email protected]>

ide: clear bmdma status in ide_intr() for ICHx controllers (revised #4)

patch 1/2 (revised):
- Fix drive->waiting_for_dma to work with CDB-intr devices.
- Do the dma status clearing in ide_intr() and add a new hwif->ide_dma_clear_irq for Intel ICHx controllers.

Revised per Alan, Sergei and Bart's advice.

Patch against 2.6.20-rc6. Tested ok on my ICH4 and pdc20275 adapters. Please review/apply, thanks.

---
 drivers/ide/ide-cd.c   |    8 ++++++
 drivers/ide/ide-io.c   |   11 ++++++++
 drivers/ide/ide.c      |    1 
 drivers/ide/pci/piix.c |   63 +++++++++++++++++++++++++++++++++++++------------
 include/linux/ide.h    |    1 
 5 files changed, 69 insertions(+), 15 deletions(-)
drivers/ide/ide-cd.c +8 -0
@@ -930,6 +930,10 @@ static ide_startstop_t cdrom_start_packe
 		HWIF(drive)->OUTB(drive->ctl, IDE_CONTROL_REG);
  
 	if (CDROM_CONFIG_FLAGS (drive)->drq_interrupt) {
+		/* waiting for CDB interrupt, not DMA yet. */
+		if (info->dma)
+			drive->waiting_for_dma = 0;
+
 		/* packet command */
 		ide_execute_command(drive, WIN_PACKETCMD, handler, ATAPI_WAIT_PC, cdrom_timer_expiry);
 		return ide_started;
@@ -972,6 +976,10 @@ static ide_startstop_t cdrom_transfer_pa
 		/* Check for errors. */
 		if (cdrom_decode_status(drive, DRQ_STAT, NULL))
 			return ide_stopped;
+
+		/* Ok, next interrupt will be DMA interrupt. */
+		if (info->dma)
+			drive->waiting_for_dma = 1;
 	} else {
 		/* Otherwise, we must wait for DRQ to get set. */
 		if (ide_wait_stat(&startstop, drive, DRQ_STAT,
drivers/ide/ide-io.c +11 -0
@@ -1646,6 +1646,17 @@ irqreturn_t ide_intr (int irq, void *dev
 	del_timer(&hwgroup->timer);
 	spin_unlock(&ide_lock);
 
+	/* Some controllers might set DMA INTR no matter DMA or PIO;
+	 * bmdma status might need to be cleared even for
+	 * PIO interrupts to prevent spurious/lost irq.
+	 */
+	if (hwif->ide_dma_clear_irq && !(drive->waiting_for_dma))
+		/* ide_dma_end() needs bmdma status for error checking.
+		 * So, skip clearing bmdma status here and leave it
+		 * to ide_dma_end() if this is dma interrupt.
+		 */
+		hwif->ide_dma_clear_irq(drive);
+
 	if (drive->unmask)
 		local_irq_enable_in_hardirq();
 	/* service this interrupt, may set handler for next interrupt */
drivers/ide/ide.c +1 -0
@@ -503,6 +503,7 @@ static void ide_hwif_restore(ide_hwif_t 
 	hwif->ide_dma_on		= tmp_hwif->ide_dma_on;
 	hwif->ide_dma_off_quietly	= tmp_hwif->ide_dma_off_quietly;
 	hwif->ide_dma_test_irq		= tmp_hwif->ide_dma_test_irq;
+	hwif->ide_dma_clear_irq		= tmp_hwif->ide_dma_clear_irq;
 	hwif->ide_dma_host_on		= tmp_hwif->ide_dma_host_on;
 	hwif->ide_dma_host_off		= tmp_hwif->ide_dma_host_off;
 	hwif->ide_dma_lostirq		= tmp_hwif->ide_dma_lostirq;
drivers/ide/pci/piix.c +48 -15

90 lines not on this page · raw message

include/linux/ide.h +1 -0
@@ -727,6 +727,7 @@ typedef struct hwif_s {
 	int (*ide_dma_on)(ide_drive_t *drive);
 	int (*ide_dma_off_quietly)(ide_drive_t *drive);
 	int (*ide_dma_test_irq)(ide_drive_t *drive);
+	void (*ide_dma_clear_irq)(ide_drive_t *drive);
 	int (*ide_dma_host_on)(ide_drive_t *drive);
 	int (*ide_dma_host_off)(ide_drive_t *drive);
 	int (*ide_dma_lostirq)(ide_drive_t *drive);
author
#2 lore raw

PATCH 2/37 ide: remove clearing bmdma status from cdrom_decode_status() (rev #4)

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Albert Lee <[email protected]>

ide: remove clearing bmdma status from cdrom_decode_status() (rev #4)

patch 2/2:
Remove clearing bmdma status from cdrom_decode_status() since ATA devices might need it as well.

(http://lkml.org/lkml/2006/12/4/201 and http://lkml.org/lkml/2006/11/15/94)

---
 drivers/ide/ide-cd.c   |    7 -------
 drivers/ide/pci/piix.c |    4 ----
 include/linux/ide.h    |    1 -
 3 files changed, 12 deletions(-)
drivers/ide/ide-cd.c +0 -7
@@ -687,15 +687,8 @@ static void ide_dump_status_no_sense(ide
 static int cdrom_decode_status(ide_drive_t *drive, int good_stat, int *stat_ret)
 {
 	struct request *rq = HWGROUP(drive)->rq;
-	ide_hwif_t *hwif = HWIF(drive);
 	int stat, err, sense_key;
 	
-	/* We may have bogus DMA interrupts in PIO state here */
-	if (HWIF(drive)->dma_status && hwif->atapi_irq_bogon) {
-		stat = hwif->INB(hwif->dma_status);
-		/* Should we force the bit as well ? */
-		hwif->OUTB(stat, hwif->dma_status);
-	}
 	/* Check for errors. */
 	stat = HWIF(drive)->INB(IDE_STATUS_REG);
 	if (stat_ret)
drivers/ide/pci/piix.c +0 -4
@@ -502,10 +502,6 @@ static void __devinit init_hwif_piix(ide
 		/* This is a painful system best to let it self tune for now */
 		return;
 	}
-	/* ESB2 appears to generate spurious DMA interrupts in PIO mode
-	   when in native mode */
-	if (hwif->pci_dev->device == PCI_DEVICE_ID_INTEL_ESB2_18)
-		hwif->atapi_irq_bogon = 1;
 
 	hwif->autodma = 0;
 	hwif->tuneproc = &piix_tune_drive;
include/linux/ide.h +0 -1
@@ -797,7 +797,6 @@ typedef struct hwif_s {
 	unsigned	sg_mapped  : 1;	/* sg_table and sg_nents are ready */
 	unsigned	no_io_32bit : 1; /* 1 = can not do 32-bit IO ops */
 	unsigned	err_stops_fifo : 1; /* 1=data FIFO is cleared by an error */
-	unsigned	atapi_irq_bogon : 1; /* Generates spurious DMA interrupts in PIO mode */
 
 	struct device	gendev;
 	struct completion gendev_rel_comp; /* To deal with device release() */
author
#3 lore raw

PATCH 3/37 sata_nv: delay on switching between NCQ and non-NCQ commands

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------

From: Robert Hancock <[email protected]>

sata_nv: delay on switching between NCQ and non-NCQ commands

This patch appears to solve some problems with commands timing out in cases where an NCQ command is immediately followed by a non-NCQ command (or possibly vice versa). This is a rather ugly solution, but until we know more about why this is needed, this is about all we can do.

[backport to 2.6.20 by Chuck Ebbert <[email protected]>]

---
 drivers/ata/sata_nv.c |   10 ++++++++++
 1 file changed, 10 insertions(+)
drivers/ata/sata_nv.c +10 -0
@@ -214,6 +214,7 @@ struct nv_adma_port_priv {
 	struct nv_adma_prd	*aprd;
 	dma_addr_t		aprd_dma;
 	u8			flags;
+	int			last_issue_ncq;
 };
 
 #define NV_ADMA_CHECK_INTR(GCTL, PORT) ((GCTL) & ( 1 << (19 + (12 * (PORT)))))
@@ -1151,6 +1152,7 @@ static unsigned int nv_adma_qc_issue(str
 {
 	struct nv_adma_port_priv *pp = qc->ap->private_data;
 	void __iomem *mmio = nv_adma_ctl_block(qc->ap);
+	int curr_ncq = (qc->tf.protocol == ATA_PROT_NCQ);
 
 	VPRINTK("ENTER\n");
 
@@ -1166,6 +1168,14 @@ static unsigned int nv_adma_qc_issue(str
 	/* write append register, command tag in lower 8 bits
 	   and (number of cpbs to append -1) in top 8 bits */
 	wmb();
+
+	if(curr_ncq != pp->last_issue_ncq) {
+	   	/* Seems to need some delay before switching between NCQ and non-NCQ
+		   commands, else we get command timeouts and such. */
+		udelay(20);
+		pp->last_issue_ncq = curr_ncq;
+	}
+
 	writew(qc->tag, mmio + NV_ADMA_APPEND);
 
 	DPRINTK("Issued tag %u\n",qc->tag);
author
#4 lore raw

PATCH 4/37 UML - fix epoll

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Jeff Dike <[email protected]>

UML/x86_64 needs the same packing of struct epoll_event as x86_64.

---
 include/linux/eventpoll.h |    7 +++++++
 1 file changed, 7 insertions(+)
include/linux/eventpoll.h +7 -0
@@ -31,12 +31,19 @@
 /* 
  * On x86-64 make the 64bit structure have the same alignment as the
  * 32bit structure. This makes 32bit emulation easier.
+ *
+ * UML/x86_64 needs the same packing as x86_64 - UML + UML_X86 +
+ * 64_BIT adds up to UML/x86_64.
  */
 #ifdef __x86_64__
 #define EPOLL_PACKED __attribute__((packed))
 #else
+#if defined(CONFIG_UML) && defined(CONFIG_UML_X86) && defined(CONFIG_64BIT)
+#define EPOLL_PACKED __attribute__((packed))
+#else
 #define EPOLL_PACKED
 #endif
+#endif
 
 struct epoll_event {
 	__u32 events;
author
#5 lore raw

PATCH 5/37 UML - host VDSO fix

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Jeff Dike <[email protected]>

This fixes a problem seen by a number of people running UML on newer host kernels. init would hang with an infinite segfault loop.

It turns out that the host kernel was providing a AT_SYSINFO_EHDR of 0xffffe000, which faked UML into believing that the host VDSO page could be reused. However, AT_SYSINFO pointed into the middle of the address space, and was unmapped as a result. Because UML was providing AT_SYSINFO_EHDR and AT_SYSINFO to its own processes, these would branch to nowhere when trying to use the VDSO.

The fix is to also check the location of AT_SYSINFO when deciding whether to use the host's VDSO.

---
 arch/um/os-Linux/elf_aux.c |    3 +++
 1 file changed, 3 insertions(+)
arch/um/os-Linux/elf_aux.c +3 -0
@@ -40,6 +40,9 @@ __init void scan_elf_aux( char **envp)
 		switch ( auxv->a_type ) {
 			case AT_SYSINFO:
 				__kernel_vsyscall = auxv->a_un.a_val;
+				/* See if the page is under TASK_SIZE */
+				if (__kernel_vsyscall < (unsigned long) envp)
+					__kernel_vsyscall = 0;
 				break;
 			case AT_SYSINFO_EHDR:
 				vsyscall_ehdr = auxv->a_un.a_val;
author
#6 lore raw

PATCH 6/37 UML - Fix static linking

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Jeff Dike <[email protected]>

During a static link, ld has started putting a .note section in the .uml.setup.init section. This has the result that the UML setups begin with 32 bytes of garbage and UML crashes immediately on boot.

This patch creates a specific .note section for ld to drop this stuff into.

---
 include/asm-um/common.lds.S |    1 +
 1 file changed, 1 insertion(+)
include/asm-um/common.lds.S +1 -0
@@ -15,6 +15,7 @@
   PROVIDE (_unprotected_end = .);
 
   . = ALIGN(4096);
+  .note : { *(note.*) }
   __start___ex_table = .;
   __ex_table : { *(__ex_table) }
   __stop___ex_table = .;
author
#7 lore raw

PATCH 6/37 UML - Fix static linking

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Jeff Dike <[email protected]>

During a static link, ld has started putting a .note section in the .uml.setup.init section. This has the result that the UML setups begin with 32 bytes of garbage and UML crashes immediately on boot.

This patch creates a specific .note section for ld to drop this stuff into.

---
 include/asm-um/common.lds.S |    1 +
 1 file changed, 1 insertion(+)
include/asm-um/common.lds.S +1 -0
@@ -15,6 +15,7 @@
   PROVIDE (_unprotected_end = .);
 
   . = ALIGN(4096);
+  .note : { *(note.*) }
   __start___ex_table = .;
   __ex_table : { *(__ex_table) }
   __stop___ex_table = .;
#8 lore raw

Re: [uml-devel] [patch 06/37] UML - Fix static linking

Quoted 1 line · Greg KH

-stable review patch. If anyone has any objections, please let us know.

I have one objection, the fix has a typo! This is the additional fix (note '.note' instead of 'note'):

include/asm-um/common.lds.S +1 -1
@@ -15,7 +15,7 @@
   PROVIDE (_unprotected_end = .);
 
   . = ALIGN(4096);
-  .note : { *(note.*) }
+  .note : { *(.note.*) }
   __start___ex_table = .;
   __ex_table : { *(__ex_table) }
   __stop___ex_table = .;

With this, the fix should be merged - I just re-hit this bug and rechecked everything, now it's ok.

Quoted 27 lines

------------------
From: Jeff Dike <[email protected]>

During a static link, ld has started putting a .note section in the .uml.setup.init section. This has the result that the UML setups begin with 32 bytes of garbage and UML crashes immediately on boot.

This patch creates a specific .note section for ld to drop this stuff into.

---
 include/asm-um/common.lds.S |    1 +
 1 file changed, 1 insertion(+)
include/asm-um/common.lds.S +1 -0
@@ -15,6 +15,7 @@
   PROVIDE (_unprotected_end = .);
 
   . = ALIGN(4096);
+  .note : { *(note.*) }
   __start___ex_table = .;
   __ex_table : { *(__ex_table) }
   __stop___ex_table = .;
Signature · 3 lines
Inform me of my mistakes, so I can add them to my list!
Paolo Giarrusso, aka Blaisorblade
http://www.user-mode-linux.org/~blaisorblade
author
#9 lore raw

PATCH 7/37 UML - use correct register file size everywhere

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Jeff Dike <[email protected]>

This patch uses MAX_REG_NR consistently to refer to the register file size. FRAME_SIZE isn't sufficient because on x86_64, it is smaller than the ptrace register file size. MAX_REG_NR was introduced as a consistent way to get the number of registers, but wasn't used everywhere it should be.

When this causes a problem, it makes PTRACE_SETREGS fail on x86_64 because of a corrupted segment register value in the known-good register file. The patch also adds a register dump at that point in case there are any future problems here.

---
 arch/um/include/sysdep-x86_64/ptrace.h  |    4 ----
 arch/um/os-Linux/skas/mem.c             |   10 +++++++---
 arch/um/os-Linux/skas/process.c         |    6 +++---
 arch/um/os-Linux/sys-i386/registers.c   |    5 +++--
 arch/um/os-Linux/sys-x86_64/registers.c |    4 ++--
 5 files changed, 15 insertions(+), 14 deletions(-)
arch/um/include/sysdep-x86_64/ptrace.h +0 -4
@@ -104,10 +104,6 @@ union uml_pt_regs {
 #endif
 #ifdef UML_CONFIG_MODE_SKAS
 	struct skas_regs {
-		/* x86_64 ptrace uses sizeof(user_regs_struct) as its register
-		 * file size, while i386 uses FRAME_SIZE.  Therefore, we need
-		 * to use UM_FRAME_SIZE here instead of HOST_FRAME_SIZE.
-		 */
 		unsigned long regs[MAX_REG_NR];
 		unsigned long fp[HOST_FP_SIZE];
                 struct faultinfo faultinfo;
arch/um/os-Linux/skas/mem.c +7 -3
@@ -48,7 +48,7 @@ int multi_op_count = 0;
 static inline long do_syscall_stub(struct mm_id * mm_idp, void **addr)
 {
 	unsigned long regs[MAX_REG_NR];
-	int n;
+	int n, i;
 	long ret, offset;
 	unsigned long * data;
 	unsigned long * syscall;
@@ -66,9 +66,13 @@ static inline long do_syscall_stub(struc
 		 (unsigned long) &__syscall_stub_start);
 
 	n = ptrace_setregs(pid, regs);
-	if(n < 0)
+	if(n < 0){
+		printk("Registers - \n");
+		for(i = 0; i < MAX_REG_NR; i++)
+			printk("\t%d\t0x%lx\n", i, regs[i]);
 		panic("do_syscall_stub : PTRACE_SETREGS failed, errno = %d\n",
-		      n);
+		      -n);
+	}
 
 	wait_stub_done(pid, 0, "do_syscall_stub");
 
arch/um/os-Linux/skas/process.c +3 -3
@@ -67,7 +67,7 @@ void wait_stub_done(int pid, int sig, ch
 
 	if((n < 0) || !WIFSTOPPED(status) ||
 	   (WSTOPSIG(status) != SIGUSR1 && WSTOPSIG(status) != SIGTRAP)){
-		unsigned long regs[HOST_FRAME_SIZE];
+		unsigned long regs[MAX_REG_NR];
 
 		if(ptrace(PTRACE_GETREGS, pid, 0, regs) < 0)
 			printk("Failed to get registers from stub, "
@@ -76,7 +76,7 @@ void wait_stub_done(int pid, int sig, ch
 			int i;
 
 			printk("Stub registers -\n");
-			for(i = 0; i < HOST_FRAME_SIZE; i++)
+			for(i = 0; i < ARRAY_SIZE(regs); i++)
 				printk("\t%d - %lx\n", i, regs[i]);
 		}
 		panic("%s : failed to wait for SIGUSR1/SIGTRAP, "
@@ -328,7 +328,7 @@ void userspace(union uml_pt_regs *regs)
 int copy_context_skas0(unsigned long new_stack, int pid)
 {
 	int err;
-	unsigned long regs[HOST_FRAME_SIZE];
+	unsigned long regs[MAX_REG_NR];
 	unsigned long fp_regs[HOST_FP_SIZE];
 	unsigned long current_stack = current_stub_stack();
 	struct stub_data *data = (struct stub_data *) current_stack;
arch/um/os-Linux/sys-i386/registers.c +3 -2
@@ -15,7 +15,7 @@
 
 /* These are set once at boot time and not changed thereafter */
 
-static unsigned long exec_regs[HOST_FRAME_SIZE];
+static unsigned long exec_regs[MAX_REG_NR];
 static unsigned long exec_fp_regs[HOST_FP_SIZE];
 static unsigned long exec_fpx_regs[HOST_XFP_SIZE];
 static int have_fpx_regs = 1;
@@ -101,6 +101,7 @@ void init_registers(int pid)
 {
 	int err;
 
+	memset(exec_regs, 0, sizeof(exec_regs));
 	err = ptrace(PTRACE_GETREGS, pid, 0, exec_regs);
 	if(err)
 		panic("check_ptrace : PTRACE_GETREGS failed, errno = %d",
@@ -124,7 +125,7 @@ void init_registers(int pid)
 
 void get_safe_registers(unsigned long *regs, unsigned long *fp_regs)
 {
-	memcpy(regs, exec_regs, HOST_FRAME_SIZE * sizeof(unsigned long));
+	memcpy(regs, exec_regs, sizeof(exec_regs));
 	if(fp_regs != NULL)
 		memcpy(fp_regs, exec_fp_regs,
 		       HOST_FP_SIZE * sizeof(unsigned long));
arch/um/os-Linux/sys-x86_64/registers.c +2 -2
@@ -14,7 +14,7 @@
 
 /* These are set once at boot time and not changed thereafter */
 
-static unsigned long exec_regs[HOST_FRAME_SIZE];
+static unsigned long exec_regs[MAX_REG_NR];
 static unsigned long exec_fp_regs[HOST_FP_SIZE];
 
 void init_thread_registers(union uml_pt_regs *to)
@@ -72,7 +72,7 @@ void init_registers(int pid)
 
 void get_safe_registers(unsigned long *regs, unsigned long *fp_regs)
 {
-	memcpy(regs, exec_regs, HOST_FRAME_SIZE * sizeof(unsigned long));
+	memcpy(regs, exec_regs, sizeof(exec_regs));
 	if(fp_regs != NULL)
 		memcpy(fp_regs, exec_fp_regs,
 		       HOST_FP_SIZE * sizeof(unsigned long));
author
#10 lore raw

PATCH 8/37 uml: fix unreasonably long udelay

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: "Paolo 'Blaisorblade' Giarrusso" <[email protected]>

Currently we have a confused udelay implementation.

* __const_udelay does not accept usecs but xloops in i386 and x86_64
* our implementation requires usecs as arg
* it gets a xloops count when called by asm/arch/delay.h

Bugs related to this (extremely long shutdown times) where reported by some x86_64 users, especially using Device Mapper.

To hit this bug, a compile-time constant time parameter must be passed - that's why UML seems to work most times.
Fix this with a simple udelay implementation.

---
 arch/um/sys-i386/delay.c   |   11 -----------
 arch/um/sys-x86_64/delay.c |   11 -----------
 include/asm-um/delay.h     |   17 ++++++++++++++---
 3 files changed, 14 insertions(+), 25 deletions(-)
arch/um/sys-i386/delay.c +0 -11
@@ -27,14 +27,3 @@ void __udelay(unsigned long usecs)
 }
 
 EXPORT_SYMBOL(__udelay);
-
-void __const_udelay(unsigned long usecs)
-{
-	int i, n;
-
-	n = (loops_per_jiffy * HZ * usecs) / MILLION;
-        for(i=0;i<n;i++)
-                cpu_relax();
-}
-
-EXPORT_SYMBOL(__const_udelay);
arch/um/sys-x86_64/delay.c +0 -11
@@ -28,14 +28,3 @@ void __udelay(unsigned long usecs)
 }
 
 EXPORT_SYMBOL(__udelay);
-
-void __const_udelay(unsigned long usecs)
-{
-	unsigned long i, n;
-
-	n = (loops_per_jiffy * HZ * usecs) / MILLION;
-        for(i=0;i<n;i++)
-                cpu_relax();
-}
-
-EXPORT_SYMBOL(__const_udelay);
include/asm-um/delay.h +14 -3
@@ -1,9 +1,20 @@
 #ifndef __UM_DELAY_H
 #define __UM_DELAY_H
 
-#include "asm/arch/delay.h"
-#include "asm/archparam.h"
-
 #define MILLION 1000000
 
+/* Undefined on purpose */
+extern void __bad_udelay(void);
+
+extern void __udelay(unsigned long usecs);
+extern void __delay(unsigned long loops);
+
+#define udelay(n) ((__builtin_constant_p(n) && (n) > 20000) ? \
+	__bad_udelay() : __udelay(n))
+
+/* It appears that ndelay is not used at all for UML, and has never been
+ * implemented. */
+extern void __unimplemented_ndelay(void);
+#define ndelay(n) __unimplemented_ndelay()
+
 #endif
author
#11 lore raw

PATCH 9/37 ieee1394: dv1394: fix CardBus card ejection

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Stefan Richter <[email protected]>

Fix NULL pointer dereference on hot ejection of a FireWire card while dv1394 was loaded. http://bugzilla.kernel.org/show_bug.cgi?id=7121
I did not test card ejection with open /dev/dv1394 files yet.

---
 drivers/ieee1394/dv1394.c |   12 +++++-------
 1 file changed, 5 insertions(+), 7 deletions(-)
drivers/ieee1394/dv1394.c +5 -7
@@ -2267,11 +2267,7 @@ static void dv1394_remove_host (struct h
 {
 	struct video_card *video;
 	unsigned long flags;
-	int id = host->id;
-
-	/* We only work with the OHCI-1394 driver */
-	if (strcmp(host->driver->name, OHCI1394_DRIVER_NAME))
-		return;
+	int id = host->id, found_ohci_card = 0;
 
 	/* find the corresponding video_cards */
 	do {
@@ -2284,6 +2280,7 @@ static void dv1394_remove_host (struct h
 			if ((tmp_vid->id >> 2) == id) {
 				list_del(&tmp_vid->list);
 				video = tmp_vid;
+				found_ohci_card = 1;
 				break;
 			}
 		}
@@ -2293,8 +2290,9 @@ static void dv1394_remove_host (struct h
 			dv1394_un_init(video);
 	} while (video != NULL);
 
-	class_device_destroy(hpsb_protocol_class,
-		MKDEV(IEEE1394_MAJOR, IEEE1394_MINOR_BLOCK_DV1394 * 16 + (id<<2)));
+	if (found_ohci_card)
+		class_device_destroy(hpsb_protocol_class, MKDEV(IEEE1394_MAJOR,
+				IEEE1394_MINOR_BLOCK_DV1394 * 16 + (id << 2)));
 }
 
 static void dv1394_add_host (struct hpsb_host *host)
author
#12 lore raw

PATCH 10/37 NET: Fix packet classidier NULL pointer OOPS

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Patrick McHardy <[email protected]>

[NET_SCHED]: cls_basic: fix NULL pointer dereference

cls_basic doesn't allocate tp->root before it is linked into the active classifier list, resulting in a NULL pointer dereference when packets hit the classifier before its ->change function is called.

Reported by Chris Madden <[email protected]>

---
 net/sched/cls_basic.c |   16 +++++++---------
 1 file changed, 7 insertions(+), 9 deletions(-)
net/sched/cls_basic.c +7 -9
@@ -82,6 +82,13 @@ static void basic_put(struct tcf_proto *
 
 static int basic_init(struct tcf_proto *tp)
 {
+	struct basic_head *head;
+
+	head = kzalloc(sizeof(*head), GFP_KERNEL);
+	if (head == NULL)
+		return -ENOBUFS;
+	INIT_LIST_HEAD(&head->flist);
+	tp->root = head;
 	return 0;
 }
 
@@ -177,15 +184,6 @@ static int basic_change(struct tcf_proto
 	}
 
 	err = -ENOBUFS;
-	if (head == NULL) {
-		head = kzalloc(sizeof(*head), GFP_KERNEL);
-		if (head == NULL)
-			goto errout;
-
-		INIT_LIST_HEAD(&head->flist);
-		tp->root = head;
-	}
-
 	f = kzalloc(sizeof(*f), GFP_KERNEL);
 	if (f == NULL)
 		goto errout;
author
#13 lore raw

PATCH 11/37 NET_SCHED: Fix ingress qdisc locking.

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Patrick McHardy <[email protected]>

[NET_SCHED]: Fix ingress locking

Ingress queueing uses a seperate lock for serializing enqueue operations, but fails to properly protect itself against concurrent changes to the qdisc tree. Use queue_lock for now since the real fix it quite intrusive.

---
 net/core/dev.c |    4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)
net/core/dev.c +2 -2
@@ -1750,10 +1750,10 @@ static int ing_filter(struct sk_buff *sk
 
 		skb->tc_verd = SET_TC_AT(skb->tc_verd,AT_INGRESS);
 
-		spin_lock(&dev->ingress_lock);
+		spin_lock(&dev->queue_lock);
 		if ((q = dev->qdisc_ingress) != NULL)
 			result = q->enqueue(skb, q);
-		spin_unlock(&dev->ingress_lock);
+		spin_unlock(&dev->queue_lock);
 
 	}
 
author
#14 lore raw

PATCH 12/37 IPV6: Fix ipv6 round-robin locking.

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: David Miller <[email protected]>

[IPV6]: Fix routing round-robin locking.

As per RFC2461, section 6.3.6, item #2, when no routers on the matching list are known to be reachable or probably reachable we do round robin on those available routes so that we make sure to probe as many of them as possible to detect when one becomes reachable faster.

Each routing table has a rwlock protecting the tree and the linked list of routes at each leaf. The round robin code executes during lookup and thus with the rwlock taken as a reader. A small local spinlock tries to provide protection but this does not work at all for two reasons:

1) The round-robin list manipulation, as coded, goes like this (with read lock held):

	walk routes finding head and tail

	spin_lock();
	rotate list using head and tail
	spin_unlock();

While one thread is rotating the list, another thread can end up with stale values of head and tail and then proceed to corrupt the list when it gets the lock. This ends up causing the OOPS in fib6_add() later onthat many people have been hitting.

2) All the other code paths that run with the rwlock held as a reader do not expect the list to change on them, they expect it to remain completely fixed while they hold the lock in that way.

So, simply stated, it is impossible to implement this correctly using a manipulation of the list without violating the rwlock locking semantics.

Reimplement using a per-fib6_node round-robin pointer. This way we don't need to manipulate the list at all, and since the round-robin pointer can only ever point to real existing entries we don't need to perform any locking on the changing of the round-robin pointer itself. We only need to reset the round-robin pointer to NULL when the entry it is pointing to is removed.

The idea is from Thomas Graf and it is very similar to how this was implemented before the advanced router selection code when in.

---
 include/net/ip6_fib.h |    1 
 net/ipv6/ip6_fib.c    |    8 ++++
 net/ipv6/route.c      |   97 ++++++++++++++++++++++++++++++--------------------
 3 files changed, 68 insertions(+), 38 deletions(-)
include/net/ip6_fib.h +1 -0
@@ -58,6 +58,7 @@ struct fib6_node
 	__u16			fn_bit;		/* bit key */
 	__u16			fn_flags;
 	__u32			fn_sernum;
+	struct rt6_info		*rr_ptr;
 };
 
 #ifndef CONFIG_IPV6_SUBTREES
net/ipv6/ip6_fib.c +8 -0
@@ -659,6 +659,10 @@ static int fib6_add_rt2node(struct fib6_
 		ins = &iter->u.next;
 	}
 
+	/* Reset round-robin state, if necessary */
+	if (ins == &fn->leaf)
+		fn->rr_ptr = NULL;
+
 	/*
 	 *	insert node
 	 */
@@ -1110,6 +1114,10 @@ static void fib6_del_route(struct fib6_n
 	rt6_stats.fib_rt_entries--;
 	rt6_stats.fib_discarded_routes++;
 
+	/* Reset round-robin state, if necessary */
+	if (fn->rr_ptr == rt)
+		fn->rr_ptr = NULL;
+
 	/* Adjust walkers */
 	read_lock(&fib6_walker_lock);
 	FOR_WALKERS(w) {
net/ipv6/route.c +59 -38

128 lines not on this page · raw message

author
#15 lore raw

PATCH 13/37 PPP: Fix PPP skb leak

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: G. Liakhovetski <[email protected]>

[PPP]: Don't leak an sk_buff on interface destruction.

---
 drivers/net/ppp_generic.c |    3 +++
 1 file changed, 3 insertions(+)
drivers/net/ppp_generic.c +3 -0
@@ -2544,6 +2544,9 @@ static void ppp_destroy_interface(struct
 	ppp->active_filter = NULL;
 #endif /* CONFIG_PPP_FILTER */
 
+	if (ppp->xmit_pending)
+		kfree_skb(ppp->xmit_pending);
+
 	kfree(ppp);
 }
 
author
#16 lore raw

PATCH 14/37 DCCP: Fix exploitable hole in DCCP socket options

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------

From: Arnaldo Carvalho de Melo <[email protected]>

[DCCP] getsockopt: Fix DCCP_SOCKOPT_[SEND,RECV]_CSCOV

We were only checking if there was enough space to put the int, but left len as specified by the (malicious) user, sigh, fix it by setting len to sizeof(val) and transfering just one int worth of data, the one asked for.

Also check for negative len values.

---
 net/dccp/proto.c |    4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)
net/dccp/proto.c +3 -1
@@ -575,7 +575,7 @@ static int do_dccp_getsockopt(struct soc
 	if (get_user(len, optlen))
 		return -EFAULT;
 
-	if (len < sizeof(int))
+	if (len < (int)sizeof(int))
 		return -EINVAL;
 
 	dp = dccp_sk(sk);
@@ -589,9 +589,11 @@ static int do_dccp_getsockopt(struct soc
 					       (__be32 __user *)optval, optlen);
 	case DCCP_SOCKOPT_SEND_CSCOV:
 		val = dp->dccps_pcslen;
+		len = sizeof(val);
 		break;
 	case DCCP_SOCKOPT_RECV_CSCOV:
 		val = dp->dccps_pcrlen;
+		len = sizeof(val);
 		break;
 	case 128 ... 191:
 		return ccid_hc_rx_getsockopt(dp->dccps_hc_rx_ccid, sk, optname,
author
#17 lore raw

PATCH 15/37 VIDEO: Fix FFB DAC revision probing

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: David Miller <[email protected]>

[VIDEO] ffb: Fix two DAC handling bugs.

The determination of whether the DAC has inverted cursor logic is broken, import the version checks the X.org driver uses to fix this.

Next, when we change the timing generator, borrow code from X.org that does 10 NOP reads of the timing generator register afterwards to make sure the video-enable transition occurs cleanly.

Finally, use macros for the DAC registers and fields in order to provide documentation for the next person who reads this code.

---
 drivers/video/ffb.c |   84 +++++++++++++++++++++++++++++++++++++---------------
 1 file changed, 60 insertions(+), 24 deletions(-)
drivers/video/ffb.c +60 -24
@@ -336,14 +336,30 @@ struct ffb_dac {
 	u32	value2;
 };
 
+#define FFB_DAC_UCTRL	0x1001 /* User Control */
+#define  FFB_DAC_UCTRL_MANREV	0x00000f00 /* 4-bit Manufacturing Revision */
+#define  FFB_DAC_UCTRL_MANREV_SHIFT 8
+#define FFB_DAC_TGEN	0x6000 /* Timing Generator */
+#define  FFB_DAC_TGEN_VIDE	0x00000001 /* Video Enable */
+#define FFB_DAC_DID	0x8000 /* Device Identification */
+#define  FFB_DAC_DID_PNUM	0x0ffff000 /* Device Part Number */
+#define  FFB_DAC_DID_PNUM_SHIFT 12
+#define  FFB_DAC_DID_REV	0xf0000000 /* Device Revision */
+#define  FFB_DAC_DID_REV_SHIFT 28
+
+#define FFB_DAC_CUR_CTRL	0x100
+#define  FFB_DAC_CUR_CTRL_P0	0x00000001
+#define  FFB_DAC_CUR_CTRL_P1	0x00000002
+
 struct ffb_par {
 	spinlock_t		lock;
 	struct ffb_fbc __iomem	*fbc;
 	struct ffb_dac __iomem	*dac;
 
 	u32			flags;
-#define FFB_FLAG_AFB		0x00000001
-#define FFB_FLAG_BLANKED	0x00000002
+#define FFB_FLAG_AFB		0x00000001 /* AFB m3 or m6 */
+#define FFB_FLAG_BLANKED	0x00000002 /* screen is blanked */
+#define FFB_FLAG_INVCURSOR	0x00000004 /* DAC has inverted cursor logic */
 
 	u32			fg_cache __attribute__((aligned (8)));
 	u32			bg_cache;
@@ -354,7 +370,6 @@ struct ffb_par {
 	unsigned long		physbase;
 	unsigned long		fbsize;
 
-	int			dac_rev;
 	int			board_type;
 };
 
@@ -426,11 +441,12 @@ static void ffb_switch_from_graph(struct
 	FFBWait(par);
 
 	/* Disable cursor.  */
-	upa_writel(0x100, &dac->type2);
-	if (par->dac_rev <= 2)
+	upa_writel(FFB_DAC_CUR_CTRL, &dac->type2);
+	if (par->flags & FFB_FLAG_INVCURSOR)
 		upa_writel(0, &dac->value2);
 	else
-		upa_writel(3, &dac->value2);
+		upa_writel((FFB_DAC_CUR_CTRL_P0 |
+			    FFB_DAC_CUR_CTRL_P1), &dac->value2);
 
 	spin_unlock_irqrestore(&par->lock, flags);
 }
@@ -664,18 +680,18 @@ ffb_blank(int blank, struct fb_info *inf
 	struct ffb_par *par = (struct ffb_par *) info->par;
 	struct ffb_dac __iomem *dac = par->dac;
 	unsigned long flags;
-	u32 tmp;
+	u32 val;
+	int i;
 
 	spin_lock_irqsave(&par->lock, flags);
 
 	FFBWait(par);
 
+	upa_writel(FFB_DAC_TGEN, &dac->type);
+	val = upa_readl(&dac->value);
 	switch (blank) {
 	case FB_BLANK_UNBLANK: /* Unblanking */
-		upa_writel(0x6000, &dac->type);
-		tmp = (upa_readl(&dac->value) | 0x1);
-		upa_writel(0x6000, &dac->type);
-		upa_writel(tmp, &dac->value);
+		val |= FFB_DAC_TGEN_VIDE;
 		par->flags &= ~FFB_FLAG_BLANKED;
 		break;
 
@@ -683,13 +699,16 @@ ffb_blank(int blank, struct fb_info *inf
 	case FB_BLANK_VSYNC_SUSPEND: /* VESA blank (vsync off) */
 	case FB_BLANK_HSYNC_SUSPEND: /* VESA blank (hsync off) */
 	case FB_BLANK_POWERDOWN: /* Poweroff */
-		upa_writel(0x6000, &dac->type);
-		tmp = (upa_readl(&dac->value) & ~0x1);
-		upa_writel(0x6000, &dac->type);
-		upa_writel(tmp, &dac->value);
+		val &= ~FFB_DAC_TGEN_VIDE;
 		par->flags |= FFB_FLAG_BLANKED;
 		break;
 	}
+	upa_writel(FFB_DAC_TGEN, &dac->type);
+	upa_writel(val, &dac->value);
+	for (i = 0; i < 10; i++) {
+		upa_writel(FFB_DAC_TGEN, &dac->type);
+		upa_readl(&dac->value);
+	}
 
 	spin_unlock_irqrestore(&par->lock, flags);
 
@@ -894,6 +913,7 @@ static int ffb_init_one(struct of_device
 	struct ffb_dac __iomem *dac;
 	struct all_info *all;
 	int err;
+	u32 dac_pnum, dac_rev, dac_mrev;
 
 	all = kzalloc(sizeof(*all), GFP_KERNEL);
 	if (!all)
@@ -948,17 +968,31 @@ static int ffb_init_one(struct of_device
 	if ((upa_readl(&fbc->ucsr) & FFB_UCSR_ALL_ERRORS) != 0)
 		upa_writel(FFB_UCSR_ALL_ERRORS, &fbc->ucsr);
 
-	ffb_switch_from_graph(&all->par);
-
 	dac = all->par.dac;
-	upa_writel(0x8000, &dac->type);
-	all->par.dac_rev = upa_readl(&dac->value) >> 0x1c;
+	upa_writel(FFB_DAC_DID, &dac->type);
+	dac_pnum = upa_readl(&dac->value);
+	dac_rev = (dac_pnum & FFB_DAC_DID_REV) >> FFB_DAC_DID_REV_SHIFT;
+	dac_pnum = (dac_pnum & FFB_DAC_DID_PNUM) >> FFB_DAC_DID_PNUM_SHIFT;
+
+	upa_writel(FFB_DAC_UCTRL, &dac->type);
+	dac_mrev = upa_readl(&dac->value);
+	dac_mrev = (dac_mrev & FFB_DAC_UCTRL_MANREV) >>
+		FFB_DAC_UCTRL_MANREV_SHIFT;
 
 	/* Elite3D has different DAC revision numbering, and no DAC revisions
-	 * have the reversed meaning of cursor enable.
+	 * have the reversed meaning of cursor enable.  Otherwise, Pacifica 1
+	 * ramdacs with manufacturing revision less than 3 have inverted
+	 * cursor logic.  We identify Pacifica 1 as not Pacifica 2, the
+	 * latter having a part number value of 0x236e.
 	 */
-	if (all->par.flags & FFB_FLAG_AFB)
-		all->par.dac_rev = 10;
+	if ((all->par.flags & FFB_FLAG_AFB) || dac_pnum == 0x236e) {
+		all->par.flags &= ~FFB_FLAG_INVCURSOR;
+	} else {
+		if (dac_mrev < 3)
+			all->par.flags |= FFB_FLAG_INVCURSOR;
+	}
+
+	ffb_switch_from_graph(&all->par);
 
 	/* Unblank it just to be sure.  When there are multiple
 	 * FFB/AFB cards in the system, or it is not the OBP
@@ -993,10 +1027,12 @@ static int ffb_init_one(struct of_device
 
 	dev_set_drvdata(&op->dev, all);
 
-	printk("%s: %s at %016lx, type %d, DAC revision %d\n",
+	printk("%s: %s at %016lx, type %d, "
+	       "DAC pnum[%x] rev[%d] manuf_rev[%d]\n",
 	       dp->full_name,
 	       ((all->par.flags & FFB_FLAG_AFB) ? "AFB" : "FFB"),
-	       all->par.physbase, all->par.board_type, all->par.dac_rev);
+	       all->par.physbase, all->par.board_type,
+	       dac_pnum, dac_rev, dac_mrev);
 
 	return 0;
 }
author
#18 lore raw

PATCH 16/37 NET: Fix sock_attach_fd() failure in sys_accept()

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------

From: Alexey Dobriyan <[email protected]>

[NET]: Correct accept(2) recovery after sock_attach_fd()

* d_alloc() in sock_attach_fd() fails leaving ->f_dentry of new file NULL
* bail out to out_fd label, doing fput()/__fput() on new file
* but __fput() assumes valid ->f_dentry and dereferences it

---
 net/socket.c |    7 ++++++-
 1 file changed, 6 insertions(+), 1 deletion(-)
net/socket.c +6 -1
@@ -1368,7 +1368,7 @@ asmlinkage long sys_accept(int fd, struc
 
 	err = sock_attach_fd(newsock, newfile);
 	if (err < 0)
-		goto out_fd;
+		goto out_fd_simple;
 
 	err = security_socket_accept(sock, newsock);
 	if (err)
@@ -1401,6 +1401,11 @@ out_put:
 	fput_light(sock->file, fput_needed);
 out:
 	return err;
+out_fd_simple:
+	sock_release(newsock);
+	put_filp(newfile);
+	put_unused_fd(newfd);
+	goto out_put;
 out_fd:
 	fput(newfile);
 	put_unused_fd(newfd);
author
#19 lore raw

PATCH 16/37 NET: Fix sock_attach_fd() failure in sys_accept()

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------

From: Alexey Dobriyan <[email protected]>

[NET]: Correct accept(2) recovery after sock_attach_fd()

* d_alloc() in sock_attach_fd() fails leaving ->f_dentry of new file NULL
* bail out to out_fd label, doing fput()/__fput() on new file
* but __fput() assumes valid ->f_dentry and dereferences it

---
 net/socket.c |    7 ++++++-
 1 file changed, 6 insertions(+), 1 deletion(-)
net/socket.c +6 -1
@@ -1368,7 +1368,7 @@ asmlinkage long sys_accept(int fd, struc
 
 	err = sock_attach_fd(newsock, newfile);
 	if (err < 0)
-		goto out_fd;
+		goto out_fd_simple;
 
 	err = security_socket_accept(sock, newsock);
 	if (err)
@@ -1401,6 +1401,11 @@ out_put:
 	fput_light(sock->file, fput_needed);
 out:
 	return err;
+out_fd_simple:
+	sock_release(newsock);
+	put_filp(newfile);
+	put_unused_fd(newfd);
+	goto out_put;
 out_fd:
 	fput(newfile);
 	put_unused_fd(newfd);
author
#20 lore raw

PATCH 17/37 SPARC: Fix sparc builds with gcc-4.2.x

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Mikael Pettersson <[email protected]>

[SPARC]: sparc64 gcc-4.2.0 20070317 -Werror failure

Compiling 2.6.21-rc5 with gcc-4.2.0 20070317 (prerelease) for sparc64 fails as follows:

gcc -Wp,-MD,arch/sparc64/kernel/.time.o.d -nostdinc -isystem /home/mikpe/pkgs/linux-sparc64/gcc-4.2.0/lib/gcc/sparc64-unknown-linux-gnu/4.2.0/include -D__KERNEL__ -Iinclude -include include/linux/autoconf.h -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -Os -m64 -pipe -mno-fpu -mcpu=ultrasparc -mcmodel=medlow -ffixed-g4 -ffixed-g5 -fcall-used-g7 -Wno-sign-compare -Wa,--undeclared-regs -fomit-frame-pointer -fno-stack-protector -Wdeclaration-after-statement -Wno-pointer-sign -Werror -D"KBUILD_STR(s)=#s" -D"KBUILD_BASENAME=KBUILD_STR(time)" -D"KBUILD_MODNAME=KBUILD_STR(time)" -c -o arch/sparc64/kernel/time.o arch/sparc64/kernel/time.c
cc1: warnings being treated as errors
arch/sparc64/kernel/time.c: In function 'kick_start_clock':
arch/sparc64/kernel/time.c:559: warning: overflow in implicit constant conversion make[1]: *** [arch/sparc64/kernel/time.o] Error 1
make: *** [arch/sparc64/kernel] Error 2

gcc gets unhappy when the MSTK_SET macro's u8 __val variable is updated with &= ~0xff (MSTK_YEAR_MASK). Making the constant unsigned fixes the problem.

[ I fixed up the sparc32 side as well -DaveM ]

---
 include/asm-sparc/mostek.h   |    2 +-
 include/asm-sparc64/mostek.h |    2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)
include/asm-sparc/mostek.h +1 -1
@@ -87,7 +87,7 @@ extern void __iomem *mstk48t02_regs;
 #define	MSTK_DOW_MASK	0x07
 #define	MSTK_DOM_MASK	0x3f
 #define	MSTK_MONTH_MASK	0x1f
-#define	MSTK_YEAR_MASK	0xff
+#define	MSTK_YEAR_MASK	0xffU
 
 /* Binary coded decimal conversion macros. */
 #define MSTK_REGVAL_TO_DECIMAL(x)  (((x) & 0x0F) + 0x0A * ((x) >> 0x04))
include/asm-sparc64/mostek.h +1 -1
@@ -89,7 +89,7 @@ extern void __iomem *mstk48t02_regs;
 #define	MSTK_DOW_MASK	0x07
 #define	MSTK_DOM_MASK	0x3f
 #define	MSTK_MONTH_MASK	0x1f
-#define	MSTK_YEAR_MASK	0xff
+#define	MSTK_YEAR_MASK	0xffU
 
 /* Binary coded decimal conversion macros. */
 #define MSTK_REGVAL_TO_DECIMAL(x)  (((x) & 0x0F) + 0x0A * ((x) >> 0x04))
author
#21 lore raw
In reply to Greg KH
Quoted 10 lines · Greg KH

This is the start of the stable review cycle for the 2.6.20.5 release. There are 37 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let us know. If anyone is a maintainer of the proper subsystem, and wants to add a Signed-off-by: line to the patch, please respond with it.

These patches are sent out with a number of different people on the Cc:
line. If you wish to be a reviewer, please email [email protected] to add your name to the list. If you want to be off the reviewer list, also email us.

Full patch is now also at:

	kernel.org/pub/linux/kernel/v2.6/testing/patch-2.6.20.5-rc1.gz

thanks,

greg k-h

author
#22 lore raw

PATCH 18/37 Fix decnet endianness

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------

From: Al Viro <[email protected]>

[PATCH] FRA_{DST,SRC} are le16 for decnet

---
 net/decnet/dn_rules.c |   12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)
net/decnet/dn_rules.c +6 -6
@@ -151,10 +151,10 @@ static int dn_fib_rule_configure(struct 
 	}
 
 	if (tb[FRA_SRC])
-		r->src = nla_get_u16(tb[FRA_SRC]);
+		r->src = nla_get_le16(tb[FRA_SRC]);
 
 	if (tb[FRA_DST])
-		r->dst = nla_get_u16(tb[FRA_DST]);
+		r->dst = nla_get_le16(tb[FRA_DST]);
 
 	r->src_len = frh->src_len;
 	r->srcmask = dnet_make_mask(r->src_len);
@@ -176,10 +176,10 @@ static int dn_fib_rule_compare(struct fi
 	if (frh->dst_len && (r->dst_len != frh->dst_len))
 		return 0;
 
-	if (tb[FRA_SRC] && (r->src != nla_get_u16(tb[FRA_SRC])))
+	if (tb[FRA_SRC] && (r->src != nla_get_le16(tb[FRA_SRC])))
 		return 0;
 
-	if (tb[FRA_DST] && (r->dst != nla_get_u16(tb[FRA_DST])))
+	if (tb[FRA_DST] && (r->dst != nla_get_le16(tb[FRA_DST])))
 		return 0;
 
 	return 1;
@@ -214,9 +214,9 @@ static int dn_fib_rule_fill(struct fib_r
 	frh->tos = 0;
 
 	if (r->dst_len)
-		NLA_PUT_U16(skb, FRA_DST, r->dst);
+		NLA_PUT_LE16(skb, FRA_DST, r->dst);
 	if (r->src_len)
-		NLA_PUT_U16(skb, FRA_SRC, r->src);
+		NLA_PUT_LE16(skb, FRA_SRC, r->src);
 
 	return 0;
 
author
#23 lore raw

PATCH 19/37 NET: Fix FIB rules compatability

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------

From: Thomas Graf <[email protected]>

[NET]: Fix fib_rules compatibility breakage

Based upon a patch from Patrick McHardy.

The fib_rules netlink attribute policy introduced in 2.6.19 broke userspace compatibilty. When specifying a rule with "from all" or "to all", iproute adds a zero byte long netlink attribute, but the policy requires all addresses to have a size equal to sizeof(struct in_addr)/sizeof(struct in6_addr), resulting in a validation error.

Check attribute length of FRA_SRC/FRA_DST in the generic framework by letting the family specific rules implementation provide the length of an address. Report an error if address length is non zero but no address attribute is provided. Fix actual bug by checking address length for non-zero instead of relying on availability of attribute.

---
 include/net/fib_rules.h |    1 +
 net/core/fib_rules.c    |   30 ++++++++++++++++++++++++++++++
 net/decnet/dn_rules.c   |   13 ++++++-------
 net/ipv4/fib_rules.c    |   14 ++++++--------
 net/ipv6/fib6_rules.c   |   14 +++++---------
 5 files changed, 48 insertions(+), 24 deletions(-)
include/net/fib_rules.h +1 -0
@@ -34,6 +34,7 @@ struct fib_rules_ops
 	int			family;
 	struct list_head	list;
 	int			rule_size;
+	int			addr_size;
 
 	int			(*action)(struct fib_rule *,
 					  struct flowi *, int,
net/core/fib_rules.c +30 -0
@@ -152,6 +152,28 @@ out:
 
 EXPORT_SYMBOL_GPL(fib_rules_lookup);
 
+static int validate_rulemsg(struct fib_rule_hdr *frh, struct nlattr **tb,
+			    struct fib_rules_ops *ops)
+{
+	int err = -EINVAL;
+
+	if (frh->src_len)
+		if (tb[FRA_SRC] == NULL ||
+		    frh->src_len > (ops->addr_size * 8) ||
+		    nla_len(tb[FRA_SRC]) != ops->addr_size)
+			goto errout;
+
+	if (frh->dst_len)
+		if (tb[FRA_DST] == NULL ||
+		    frh->dst_len > (ops->addr_size * 8) ||
+		    nla_len(tb[FRA_DST]) != ops->addr_size)
+			goto errout;
+
+	err = 0;
+errout:
+	return err;
+}
+
 int fib_nl_newrule(struct sk_buff *skb, struct nlmsghdr* nlh, void *arg)
 {
 	struct fib_rule_hdr *frh = nlmsg_data(nlh);
@@ -173,6 +195,10 @@ int fib_nl_newrule(struct sk_buff *skb, 
 	if (err < 0)
 		goto errout;
 
+	err = validate_rulemsg(frh, tb, ops);
+	if (err < 0)
+		goto errout;
+
 	rule = kzalloc(ops->rule_size, GFP_KERNEL);
 	if (rule == NULL) {
 		err = -ENOMEM;
@@ -260,6 +286,10 @@ int fib_nl_delrule(struct sk_buff *skb, 
 	if (err < 0)
 		goto errout;
 
+	err = validate_rulemsg(frh, tb, ops);
+	if (err < 0)
+		goto errout;
+
 	list_for_each_entry(rule, ops->rules_list, list) {
 		if (frh->action && (frh->action != rule->action))
 			continue;
net/decnet/dn_rules.c +6 -7
@@ -109,8 +109,6 @@ errout:
 
 static struct nla_policy dn_fib_rule_policy[FRA_MAX+1] __read_mostly = {
 	FRA_GENERIC_POLICY,
-	[FRA_SRC]	= { .type = NLA_U16 },
-	[FRA_DST]	= { .type = NLA_U16 },
 };
 
 static int dn_fib_rule_match(struct fib_rule *rule, struct flowi *fl, int flags)
@@ -133,7 +131,7 @@ static int dn_fib_rule_configure(struct 
 	int err = -EINVAL;
 	struct dn_fib_rule *r = (struct dn_fib_rule *)rule;
 
-	if (frh->src_len > 16 || frh->dst_len > 16 || frh->tos)
+	if (frh->tos)
 		goto  errout;
 
 	if (rule->table == RT_TABLE_UNSPEC) {
@@ -150,10 +148,10 @@ static int dn_fib_rule_configure(struct 
 		}
 	}
 
-	if (tb[FRA_SRC])
+	if (frh->src_len)
 		r->src = nla_get_le16(tb[FRA_SRC]);
 
-	if (tb[FRA_DST])
+	if (frh->dst_len)
 		r->dst = nla_get_le16(tb[FRA_DST]);
 
 	r->src_len = frh->src_len;
@@ -176,10 +174,10 @@ static int dn_fib_rule_compare(struct fi
 	if (frh->dst_len && (r->dst_len != frh->dst_len))
 		return 0;
 
-	if (tb[FRA_SRC] && (r->src != nla_get_le16(tb[FRA_SRC])))
+	if (frh->src_len && (r->src != nla_get_le16(tb[FRA_SRC])))
 		return 0;
 
-	if (tb[FRA_DST] && (r->dst != nla_get_le16(tb[FRA_DST])))
+	if (frh->dst_len && (r->dst != nla_get_le16(tb[FRA_DST])))
 		return 0;
 
 	return 1;
@@ -249,6 +247,7 @@ int dn_fib_dump_rules(struct sk_buff *sk
 static struct fib_rules_ops dn_fib_rules_ops = {
 	.family		= AF_DECnet,
 	.rule_size	= sizeof(struct dn_fib_rule),
+	.addr_size	= sizeof(u16),
 	.action		= dn_fib_rule_action,
 	.match		= dn_fib_rule_match,
 	.configure	= dn_fib_rule_configure,
net/ipv4/fib_rules.c +6 -8
@@ -171,8 +171,6 @@ static struct fib_table *fib_empty_table
 
 static struct nla_policy fib4_rule_policy[FRA_MAX+1] __read_mostly = {
 	FRA_GENERIC_POLICY,
-	[FRA_SRC]	= { .type = NLA_U32 },
-	[FRA_DST]	= { .type = NLA_U32 },
 	[FRA_FLOW]	= { .type = NLA_U32 },
 };
 
@@ -183,8 +181,7 @@ static int fib4_rule_configure(struct fi
 	int err = -EINVAL;
 	struct fib4_rule *rule4 = (struct fib4_rule *) rule;
 
-	if (frh->src_len > 32 || frh->dst_len > 32 ||
-	    (frh->tos & ~IPTOS_TOS_MASK))
+	if (frh->tos & ~IPTOS_TOS_MASK)
 		goto errout;
 
 	if (rule->table == RT_TABLE_UNSPEC) {
@@ -201,10 +198,10 @@ static int fib4_rule_configure(struct fi
 		}
 	}
 
-	if (tb[FRA_SRC])
+	if (frh->src_len)
 		rule4->src = nla_get_be32(tb[FRA_SRC]);
 
-	if (tb[FRA_DST])
+	if (frh->dst_len)
 		rule4->dst = nla_get_be32(tb[FRA_DST]);
 
 #ifdef CONFIG_NET_CLS_ROUTE
@@ -242,10 +239,10 @@ static int fib4_rule_compare(struct fib_
 		return 0;
 #endif
 
-	if (tb[FRA_SRC] && (rule4->src != nla_get_be32(tb[FRA_SRC])))
+	if (frh->src_len && (rule4->src != nla_get_be32(tb[FRA_SRC])))
 		return 0;
 
-	if (tb[FRA_DST] && (rule4->dst != nla_get_be32(tb[FRA_DST])))
+	if (frh->dst_len && (rule4->dst != nla_get_be32(tb[FRA_DST])))
 		return 0;
 
 	return 1;
@@ -309,6 +306,7 @@ static size_t fib4_rule_nlmsg_payload(st
 static struct fib_rules_ops fib4_rules_ops = {
 	.family		= AF_INET,
 	.rule_size	= sizeof(struct fib4_rule),
+	.addr_size	= sizeof(u32),
 	.action		= fib4_rule_action,
 	.match		= fib4_rule_match,
 	.configure	= fib4_rule_configure,
net/ipv6/fib6_rules.c +5 -9
@@ -131,8 +131,6 @@ static int fib6_rule_match(struct fib_ru
 
 static struct nla_policy fib6_rule_policy[FRA_MAX+1] __read_mostly = {
 	FRA_GENERIC_POLICY,
-	[FRA_SRC]	= { .len = sizeof(struct in6_addr) },
-	[FRA_DST]	= { .len = sizeof(struct in6_addr) },
 };
 
 static int fib6_rule_configure(struct fib_rule *rule, struct sk_buff *skb,
@@ -142,9 +140,6 @@ static int fib6_rule_configure(struct fi
 	int err = -EINVAL;
 	struct fib6_rule *rule6 = (struct fib6_rule *) rule;
 
-	if (frh->src_len > 128 || frh->dst_len > 128)
-		goto errout;
-
 	if (rule->action == FR_ACT_TO_TBL) {
 		if (rule->table == RT6_TABLE_UNSPEC)
 			goto errout;
@@ -155,11 +150,11 @@ static int fib6_rule_configure(struct fi
 		}
 	}
 
-	if (tb[FRA_SRC])
+	if (frh->src_len)
 		nla_memcpy(&rule6->src.addr, tb[FRA_SRC],
 			   sizeof(struct in6_addr));
 
-	if (tb[FRA_DST])
+	if (frh->dst_len)
 		nla_memcpy(&rule6->dst.addr, tb[FRA_DST],
 			   sizeof(struct in6_addr));
 
@@ -186,11 +181,11 @@ static int fib6_rule_compare(struct fib_
 	if (frh->tos && (rule6->tclass != frh->tos))
 		return 0;
 
-	if (tb[FRA_SRC] &&
+	if (frh->src_len &&
 	    nla_memcmp(tb[FRA_SRC], &rule6->src.addr, sizeof(struct in6_addr)))
 		return 0;
 
-	if (tb[FRA_DST] &&
+	if (frh->dst_len &&
 	    nla_memcmp(tb[FRA_DST], &rule6->dst.addr, sizeof(struct in6_addr)))
 		return 0;
 
@@ -240,6 +235,7 @@ static size_t fib6_rule_nlmsg_payload(st
 static struct fib_rules_ops fib6_rules_ops = {
 	.family			= AF_INET6,
 	.rule_size		= sizeof(struct fib6_rule),
+	.addr_size		= sizeof(struct in6_addr),
 	.action			= fib6_rule_action,
 	.match			= fib6_rule_match,
 	.configure		= fib6_rule_configure,
author
#24 lore raw

PATCH 20/37 DVB: fix nxt200x rf input switching

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Michael Krufky <[email protected]>

DVB: fix nxt200x rf input switching

After dvb tuner refactoring, the pll buffer has been altered such that the pll address is now stored in buf[0]. Instead of sending buf to set_pll_input, we should send buf+1.

(cherry picked from commit f5ae29e284b328e0976789d5c199bbbe80e4b005)

---
 drivers/media/dvb/frontends/nxt200x.c |    4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/media/dvb/frontends/nxt200x.c +2 -2
@@ -562,7 +562,7 @@ static int nxt200x_setup_frontend_parame
 
 			/* set input */
 			if (state->config->set_pll_input)
-				state->config->set_pll_input(buf, 1);
+				state->config->set_pll_input(buf+1, 1);
 			break;
 		case VSB_8:
 			/* Set non-punctured clock for VSB */
@@ -571,7 +571,7 @@ static int nxt200x_setup_frontend_parame
 
 			/* set input */
 			if (state->config->set_pll_input)
-				state->config->set_pll_input(buf, 0);
+				state->config->set_pll_input(buf+1, 0);
 			break;
 		default:
 			return -EINVAL;
author
#25 lore raw

PATCH 21/37 V4L: radio: Fix error in Kbuild file

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Trent Piepho <[email protected]>

V4L: radio: Fix error in Kbuild file

All the radio drivers need video_dev, but they were depending on VIDEO_DEV!=n. That meant that one could try to compile the driver into the kernel when VIDEO_DEV=m, which will not work. If video_dev is a module, then the radio drivers must be modules too.

(cherry picked from commit b10fece583fdfdb3d2f29b0da3896ec58b8fe122)

---
 drivers/media/radio/Kconfig |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/media/radio/Kconfig +1 -1
@@ -3,7 +3,7 @@
 #
 
 menu "Radio Adapters"
-	depends on VIDEO_DEV!=n
+	depends on VIDEO_DEV
 
 config RADIO_CADET
 	tristate "ADS Cadet AM/FM Tuner"
author
#26 lore raw

PATCH 22/37 V4L: Fix SECAM handling on saa7115

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------

From: Mauro Carvalho Chehab <[email protected]>

V4L: Fix SECAM handling on saa7115

(cherry picked from commit a9aaec4e83e687d23b78b38e331bbd6a10b96380)

---
 drivers/media/video/saa7115.c |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/media/video/saa7115.c +1 -1
@@ -960,7 +960,7 @@ static void saa711x_set_v4lstd(struct i2
 			reg |= 0x10;
 		} else if (std == V4L2_STD_NTSC_M_JP) {
 			reg |= 0x40;
-		} else if (std == V4L2_STD_SECAM) {
+		} else if (std & V4L2_STD_SECAM) {
 			reg |= 0x50;
 		}
 		saa711x_write(client, R_0E_CHROMA_CNTL_1, reg);
author
#27 lore raw

PATCH 23/37 V4L: msp_attach must return 0 if no msp3400 was found.

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Hans Verkuil <[email protected]>

V4L: msp_attach must return 0 if no msp3400 was found.

Returning -1 causes the probe to stop, but it should just continue instead. This patch fixes an annoying 'i2c_adapter i2c-7: Client creation failed at 0x44 (-1)' kernel message that appeared in 2.6.20

(cherry picked from commit 3284b4e077cb2322754ea7455b8f8af7ce3777b8)

---
 drivers/media/video/msp3400-driver.c |    4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/media/video/msp3400-driver.c +2 -2
@@ -825,7 +825,7 @@ static int msp_attach(struct i2c_adapter
 	if (msp_reset(client) == -1) {
 		v4l_dbg(1, msp_debug, client, "msp3400 not found\n");
 		kfree(client);
-		return -1;
+		return 0;
 	}
 
 	state = kmalloc(sizeof(*state), GFP_KERNEL);
@@ -859,7 +859,7 @@ static int msp_attach(struct i2c_adapter
 		v4l_dbg(1, msp_debug, client, "not an msp3400 (cannot read chip version)\n");
 		kfree(state);
 		kfree(client);
-		return -1;
+		return 0;
 	}
 
 	msp_set_audio(client);
author
#28 lore raw

PATCH 24/37 DVB: isl6421: dont reference freed memory

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Thomas Viehweger <[email protected]>

DVB: isl6421: don't reference freed memory

After freeing a block there should be no reference to this block.

(cherry picked from commit 09d4895488d4df5c58b739573846f514ceabc911)

---
 drivers/media/dvb/frontends/isl6421.c |    1 +
 1 file changed, 1 insertion(+)
drivers/media/dvb/frontends/isl6421.c +1 -0
@@ -122,6 +122,7 @@ struct dvb_frontend *isl6421_attach(stru
 	/* detect if it is present or not */
 	if (isl6421_set_voltage(fe, SEC_VOLTAGE_OFF)) {
 		kfree(isl6421);
+		fe->sec_priv = NULL;
 		return NULL;
 	}
 
author
#29 lore raw

PATCH 25/37 dvb-core: fix several locking related problems

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Simon Arlott <[email protected]>

dvb-core: fix several locking related problems

Fix several instances of dvb-core functions using mutex_lock_interruptible and returning -ERESTARTSYS where the calling function will either never retry or never check the return value.

These cause a race condition with dvb_dmxdev_filter_free and dvb_dvr_release, both of which are filesystem release functions whose return value is ignored and will never be retried. When this happens it becomes impossible to open dvr0 again (-EBUSY) since it has not been released properly.

(cherry picked from commit c278850206fd9df0bb62a72ca0b277fe20c5a452)

---
 drivers/media/dvb/dvb-core/dmxdev.c    |   12 +++---------
 drivers/media/dvb/dvb-core/dvb_demux.c |   21 +++++++--------------
 drivers/media/dvb/dvb-core/dvbdev.c    |    9 +++------
 3 files changed, 13 insertions(+), 29 deletions(-)
drivers/media/dvb/dvb-core/dmxdev.c +3 -9
@@ -181,8 +181,7 @@ static int dvb_dvr_release(struct inode 
 	struct dvb_device *dvbdev = file->private_data;
 	struct dmxdev *dmxdev = dvbdev->priv;
 
-	if (mutex_lock_interruptible(&dmxdev->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&dmxdev->mutex);
 
 	if ((file->f_flags & O_ACCMODE) == O_WRONLY) {
 		dmxdev->demux->disconnect_frontend(dmxdev->demux);
@@ -674,13 +673,8 @@ static int dvb_demux_open(struct inode *
 static int dvb_dmxdev_filter_free(struct dmxdev *dmxdev,
 				  struct dmxdev_filter *dmxdevfilter)
 {
-	if (mutex_lock_interruptible(&dmxdev->mutex))
-		return -ERESTARTSYS;
-
-	if (mutex_lock_interruptible(&dmxdevfilter->mutex)) {
-		mutex_unlock(&dmxdev->mutex);
-		return -ERESTARTSYS;
-	}
+	mutex_lock(&dmxdev->mutex);
+	mutex_lock(&dmxdevfilter->mutex);
 
 	dvb_dmxdev_filter_stop(dmxdevfilter);
 	dvb_dmxdev_filter_reset(dmxdevfilter);
drivers/media/dvb/dvb-core/dvb_demux.c +7 -14
@@ -673,8 +673,7 @@ static int dmx_ts_feed_stop_filtering(st
 	struct dvb_demux *demux = feed->demux;
 	int ret;
 
-	if (mutex_lock_interruptible(&demux->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&demux->mutex);
 
 	if (feed->state < DMX_STATE_GO) {
 		mutex_unlock(&demux->mutex);
@@ -748,8 +747,7 @@ static int dvbdmx_release_ts_feed(struct
 	struct dvb_demux *demux = (struct dvb_demux *)dmx;
 	struct dvb_demux_feed *feed = (struct dvb_demux_feed *)ts_feed;
 
-	if (mutex_lock_interruptible(&demux->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&demux->mutex);
 
 	if (feed->state == DMX_STATE_FREE) {
 		mutex_unlock(&demux->mutex);
@@ -916,8 +914,7 @@ static int dmx_section_feed_stop_filteri
 	struct dvb_demux *dvbdmx = dvbdmxfeed->demux;
 	int ret;
 
-	if (mutex_lock_interruptible(&dvbdmx->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdmx->mutex);
 
 	if (!dvbdmx->stop_feed) {
 		mutex_unlock(&dvbdmx->mutex);
@@ -942,8 +939,7 @@ static int dmx_section_feed_release_filt
 	struct dvb_demux_feed *dvbdmxfeed = (struct dvb_demux_feed *)feed;
 	struct dvb_demux *dvbdmx = dvbdmxfeed->demux;
 
-	if (mutex_lock_interruptible(&dvbdmx->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdmx->mutex);
 
 	if (dvbdmxfilter->feed != dvbdmxfeed) {
 		mutex_unlock(&dvbdmx->mutex);
@@ -1016,8 +1012,7 @@ static int dvbdmx_release_section_feed(s
 	struct dvb_demux_feed *dvbdmxfeed = (struct dvb_demux_feed *)feed;
 	struct dvb_demux *dvbdmx = (struct dvb_demux *)demux;
 
-	if (mutex_lock_interruptible(&dvbdmx->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdmx->mutex);
 
 	if (dvbdmxfeed->state == DMX_STATE_FREE) {
 		mutex_unlock(&dvbdmx->mutex);
@@ -1126,8 +1121,7 @@ static int dvbdmx_connect_frontend(struc
 	if (demux->frontend)
 		return -EINVAL;
 
-	if (mutex_lock_interruptible(&dvbdemux->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdemux->mutex);
 
 	demux->frontend = frontend;
 	mutex_unlock(&dvbdemux->mutex);
@@ -1138,8 +1132,7 @@ static int dvbdmx_disconnect_frontend(st
 {
 	struct dvb_demux *dvbdemux = (struct dvb_demux *)demux;
 
-	if (mutex_lock_interruptible(&dvbdemux->mutex))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdemux->mutex);
 
 	demux->frontend = NULL;
 	mutex_unlock(&dvbdemux->mutex);
drivers/media/dvb/dvb-core/dvbdev.c +3 -6
@@ -204,8 +204,7 @@ int dvb_register_device(struct dvb_adapt
 
 	int id;
 
-	if (mutex_lock_interruptible(&dvbdev_register_lock))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdev_register_lock);
 
 	if ((id = dvbdev_get_free_id (adap, type)) < 0) {
 		mutex_unlock(&dvbdev_register_lock);
@@ -295,8 +294,7 @@ int dvb_register_adapter(struct dvb_adap
 {
 	int num;
 
-	if (mutex_lock_interruptible(&dvbdev_register_lock))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdev_register_lock);
 
 	if ((num = dvbdev_get_free_adapter_num ()) < 0) {
 		mutex_unlock(&dvbdev_register_lock);
@@ -324,8 +322,7 @@ EXPORT_SYMBOL(dvb_register_adapter);
 
 int dvb_unregister_adapter(struct dvb_adapter *adap)
 {
-	if (mutex_lock_interruptible(&dvbdev_register_lock))
-		return -ERESTARTSYS;
+	mutex_lock(&dvbdev_register_lock);
 	list_del (&adap->list_head);
 	mutex_unlock(&dvbdev_register_lock);
 	return 0;
author
#30 lore raw

PATCH 26/37 V4L: saa7146: Fix allocation of clipping memory

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Oliver Endriss <[email protected]>

V4L: saa7146: Fix allocation of clipping memory

Olaf Hering pointed out that SAA7146_CLIPPING_MEM would become very large for PAGE_SIZE > 4K.

In fact, the number of clipping windows is limited to 16, and calculate_clipping_registers_rect() does not use more than 256 bytes. SAA7146_CLIPPING_MEM adjusted accordingly.

(cherry picked from commit 7a7cd1920969dd9da4e0d99aab573b3eba24c799)

Thanks-to: Olaf Hering <[email protected]>

---
 include/media/saa7146_vv.h |    3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)
include/media/saa7146_vv.h +2 -1
@@ -239,7 +239,8 @@ void saa7146_res_free(struct saa7146_fh 
 #define SAA7146_HPS_SYNC_PORT_B		0x01
 
 /* some memory sizes */
-#define SAA7146_CLIPPING_MEM	(14*PAGE_SIZE)
+/* max. 16 clipping rectangles */
+#define SAA7146_CLIPPING_MEM	(16 * 4 * sizeof(u32))
 
 /* some defines for the various clipping-modes */
 #define SAA7146_CLIPPING_RECT		0x4
author
#31 lore raw

PATCH 27/37 jmicron: make ide jmicron driver play nice with libata ones

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Tejun Heo <[email protected]>

jmicron: make ide jmicron driver play nice with libata ones

When libata is configured, the device is configured such that SATA and PATA ports live in separate functions with different programming interfaces. pata_jmicron and ide jmicron drivers can drive only the PATA part.

This patch makes jmicron match PCI class code such that it doesn't attach itself to the SATA part preventing the proper ahci driver from attaching.

This change is suggested by Bartlomiej.

---
 drivers/ide/pci/jmicron.c |   29 ++++++++++++++++++++++++-----
 1 file changed, 24 insertions(+), 5 deletions(-)
drivers/ide/pci/jmicron.c +24 -5
@@ -240,12 +240,31 @@ static int __devinit jmicron_init_one(st
 	return 0;
 }
 
+/* If libata is configured, jmicron PCI quirk will configure it such
+ * that the SATA ports are in AHCI function while the PATA ports are
+ * in a separate IDE function.  In such cases, match device class and
+ * attach only to IDE.  If libata isn't configured, keep the old
+ * behavior for backward compatibility.
+ */
+#if defined(CONFIG_ATA) || defined(CONFIG_ATA_MODULE)
+#define JMB_CLASS	PCI_CLASS_STORAGE_IDE << 8
+#define JMB_CLASS_MASK	0xffff00
+#else
+#define JMB_CLASS	0
+#define JMB_CLASS_MASK	0
+#endif
+
 static struct pci_device_id jmicron_pci_tbl[] = {
-	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB361, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
-	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB363, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 1},
-	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB365, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 2},
-	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB366, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 3},
-	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB368, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 4},
+	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB361,
+	  PCI_ANY_ID, PCI_ANY_ID, JMB_CLASS, JMB_CLASS_MASK, 0},
+	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB363,
+	  PCI_ANY_ID, PCI_ANY_ID, JMB_CLASS, JMB_CLASS_MASK, 1},
+	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB365,
+	  PCI_ANY_ID, PCI_ANY_ID, JMB_CLASS, JMB_CLASS_MASK, 2},
+	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB366,
+	  PCI_ANY_ID, PCI_ANY_ID, JMB_CLASS, JMB_CLASS_MASK, 3},
+	{ PCI_VENDOR_ID_JMICRON, PCI_DEVICE_ID_JMICRON_JMB368,
+	  PCI_ANY_ID, PCI_ANY_ID, JMB_CLASS, JMB_CLASS_MASK, 4},
 	{ 0, },
 };
 
author
#32 lore raw

PATCH 28/37 i2o: block IO errors on i2o disk

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Vasily Averin <[email protected]>

[PATCH] i2o: block IO errors on i2o disk

I2O subsystem has been broken in mainstream several months ago (after 2.6.18). Commit 4aff5e2333c9a1609662f2091f55c3f6fffdad36 from Jens Axboe split struct request ->flags into two parts: cmd_type and cmd_flags.

In i2o layer this patch has replaced flag REQ_SPECIAL by the according cmd_type. However i2o has used REQ_SPECIAL not as command type but as driver-specific flag for the debug purposes. As result all i2o requests have type "special" now, are not processed to the hardware and fail with I/O error:

i2o/hda:<3>Buffer I/O error on device i2o/hda, logical block 0
Buffer I/O error on device i2o/hda, logical block 0 Buffer I/O error on device i2o/hda, logical block 0
unable to read partition table
block-osm: device added (TID: 207): i2o/hda

The following patch removes the extra debug checks without any drawbacks and restores the normal driver's work.

From: Chuck Ebbert <[email protected]>

---
 drivers/message/i2o/i2o_block.c |   12 +-----------
 1 file changed, 1 insertion(+), 11 deletions(-)
drivers/message/i2o/i2o_block.c +1 -11
@@ -390,13 +390,6 @@ static int i2o_block_prep_req_fn(struct 
 		return BLKPREP_KILL;
 	}
 
-	/* request is already processed by us, so return */
-	if (blk_special_request(req)) {
-		osm_debug("REQ_SPECIAL already set!\n");
-		req->cmd_flags |= REQ_DONTPREP;
-		return BLKPREP_OK;
-	}
-
 	/* connect the i2o_block_request to the request */
 	if (!req->special) {
 		ireq = i2o_block_request_alloc();
@@ -408,11 +401,8 @@ static int i2o_block_prep_req_fn(struct 
 		ireq->i2o_blk_dev = i2o_blk_dev;
 		req->special = ireq;
 		ireq->req = req;
-	} else
-		ireq = req->special;
-
+	}
 	/* do not come back here */
-	req->cmd_type = REQ_TYPE_SPECIAL;
 	req->cmd_flags |= REQ_DONTPREP;
 
 	return BLKPREP_OK;
author
#33 lore raw

PATCH 29/37 ide: revert "ide: fix drive side 80c cable check, take 2" for now

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Bartlomiej Zolnierkiewicz <[email protected]>

[PATCH] ide: revert "ide: fix drive side 80c cable check, take 2" for now

"ide: fix drive side 80c cable check, take 2" patch from Tejun Heo (commit fab59375b9543f84d1714f7dd00f5d11e531bd3e) fixed 80c bit test (bit13 of word93) but we also need to fix master/slave IDENTIFY order (slave device should be probed first in order to make it release PDIAG- signal) and we should also check for pre-ATA3 slave devices (which may not release PDIAG- signal).

Unfortunately the fact that IDE driver doesn't reset devices itself helps only a bit as it seems that some BIOS-es reset ATA devices after programming the chipset, some BIOS-es can be set to not probe/configure selected devices, there may be no BIOS in case of add-on cards etc.

Since we are quite late in the release cycle and the required changes will affect a lot of systems just revert the fix for now.

[ Please also see libata commit f31f0cc2f0b7527072d94d02da332d9bb8d7d94c. ]

---
 drivers/ide/ide-iops.c |    9 +++++++++
 1 file changed, 9 insertions(+)
drivers/ide/ide-iops.c +9 -0
@@ -598,6 +598,9 @@ u8 eighty_ninty_three (ide_drive_t *driv
 	if(HWIF(drive)->udma_four == 0)
 		return 0;
 
+	printk(KERN_INFO "%s: hw_config=%04x\n",
+			 drive->name, drive->id->hw_config);
+
 	/* Check for SATA but only if we are ATA5 or higher */
 	if (drive->id->hw_config == 0 && (drive->id->major_rev_num & 0x7FE0))
 		return 1;
@@ -607,8 +610,14 @@ u8 eighty_ninty_three (ide_drive_t *driv
 	if(!(drive->id->hw_config & 0x4000))
 		return 0;
 #endif /* CONFIG_IDEDMA_IVB */
+/*
+ * FIXME: enable this after fixing master/slave IDENTIFY order,
+ *	  also ignore the result if the slave device is pre-ATA3 one
+ */
+#if 0
 	if (!(drive->id->hw_config & 0x2000))
 		return 0;
+#endif
 	return 1;
 }
 
author
#34 lore raw

PATCH 30/37 CIFS: Allow reset of file to ATTR_NORMAL when archive bit not set

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Steve French <[email protected]>

[CIFS] Allow reset of file to ATTR_NORMAL when archive bit not set

When a file had a dos attribute of 0x1 (readonly - but dos attribute of archive was not set) - doing chmod 0777 or equivalent would try to set a dos attribute of 0 (which some servers ignore) rather than ATTR_NORMAL (0x20) which most servers accept. Does not affect servers which support the CIFS Unix Extensions.

[<[email protected]>: removed changelog part of patch]

---
 fs/cifs/inode.c |   15 ++++++++++++---
 1 file changed, 12 insertions(+), 3 deletions(-)
fs/cifs/inode.c +12 -3
@@ -1133,6 +1133,7 @@ int cifs_setattr(struct dentry *direntry
 	struct cifsFileInfo *open_file = NULL;
 	FILE_BASIC_INFO time_buf;
 	int set_time = FALSE;
+	int set_dosattr = FALSE;
 	__u64 mode = 0xFFFFFFFFFFFFFFFFULL;
 	__u64 uid = 0xFFFFFFFFFFFFFFFFULL;
 	__u64 gid = 0xFFFFFFFFFFFFFFFFULL;
@@ -1269,15 +1270,23 @@ int cifs_setattr(struct dentry *direntry
 	else if (attrs->ia_valid & ATTR_MODE) {
 		rc = 0;
 		if ((mode & S_IWUGO) == 0) /* not writeable */ {
-			if ((cifsInode->cifsAttrs & ATTR_READONLY) == 0)
+			if ((cifsInode->cifsAttrs & ATTR_READONLY) == 0) {
+				set_dosattr = TRUE;
 				time_buf.Attributes =
 					cpu_to_le32(cifsInode->cifsAttrs |
 						    ATTR_READONLY);
+			}
 		} else if ((mode & S_IWUGO) == S_IWUGO) {
-			if (cifsInode->cifsAttrs & ATTR_READONLY)
+			if (cifsInode->cifsAttrs & ATTR_READONLY) {
+				set_dosattr = TRUE;
 				time_buf.Attributes =
 					cpu_to_le32(cifsInode->cifsAttrs &
 						    (~ATTR_READONLY));
+				/* Windows ignores set to zero */
+				if(time_buf.Attributes == 0)
+					time_buf.Attributes |=
+						cpu_to_le32(ATTR_NORMAL);
+			}
 		}
 		/* BB to be implemented -
 		   via Windows security descriptors or streams */
@@ -1315,7 +1324,7 @@ int cifs_setattr(struct dentry *direntry
 	} else
 		time_buf.ChangeTime = 0;
 
-	if (set_time || time_buf.Attributes) {
+	if (set_time || set_dosattr) {
 		time_buf.CreationTime = 0;	/* do not change */
 		/* In the future we should experiment - try setting timestamps
 		   via Handle (SetFileInfo) instead of by path */
author
#35 lore raw

PATCH 31/37 CIFS: reset mode when client notices that ATTR_READONLY is no longer set

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Alan Tyson <[email protected]>

[CIFS] reset mode when client notices that ATTR_READONLY is no longer set

[<[email protected]>: removed changelog part of patch]

---
 fs/cifs/inode.c   |    6 ++++++
 fs/cifs/readdir.c |    4 ++++
 2 files changed, 10 insertions(+)
fs/cifs/inode.c +6 -0
@@ -488,6 +488,12 @@ int cifs_get_inode_info(struct inode **p
 			   mode e.g. 555 */
 			if (cifsInfo->cifsAttrs & ATTR_READONLY)
 				inode->i_mode &= ~(S_IWUGO);
+			else if ((inode->i_mode & S_IWUGO) == 0)
+				/* the ATTR_READONLY flag may have been	*/
+				/* changed on server -- set any w bits	*/
+				/* allowed by mnt_file_mode		*/
+				inode->i_mode |= (S_IWUGO &
+						  cifs_sb->mnt_file_mode);
 		/* BB add code here -
 		   validate if device or weird share or device type? */
 		}
fs/cifs/readdir.c +4 -0
@@ -215,6 +215,10 @@ static void fill_in_inode(struct inode *
 		tmp_inode->i_mode |= S_IFREG;
 		if (attr & ATTR_READONLY)
 			tmp_inode->i_mode &= ~(S_IWUGO);
+		else if ((tmp_inode->i_mode & S_IWUGO) == 0)
+			/* the ATTR_READONLY flag may have been changed on   */
+		   	/* server -- set any w bits allowed by mnt_file_mode */
+			tmp_inode->i_mode |= (S_IWUGO & cifs_sb->mnt_file_mode);
 	} /* could add code here - to validate if device or weird share type? */
 
 	/* can not fill in nlink here as in qpathinfo version and Unx search */
author
#36 lore raw

PATCH 32/37 CRYPTO: api: scatterwalk_copychunks() fails to advance through scatterlist

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: J. Bruce Fields <[email protected]>

[CRYPTO] api: scatterwalk_copychunks() fails to advance through scatterlist

In the loop in scatterwalk_copychunks(), if walk->offset is zero, then scatterwalk_pagedone rounds that up to the nearest page boundary:

		walk->offset += PAGE_SIZE - 1;
		walk->offset &= PAGE_MASK;

which is a no-op in this case, so we don't advance to the next element of the scatterlist array:

		if (walk->offset >= walk->sg->offset + walk->sg->length)
			scatterwalk_start(walk, sg_next(walk->sg));

and we end up copying the same data twice.

It appears that other callers of scatterwalk_{page}done first advance walk->offset, so I believe that's the correct thing to do here.

This caused a bug in NFS when run with krb5p security, which would cause some writes to fail with permissions errors--for example, writes of less than 8 bytes (the des blocksize) at the start of a file.

A git-bisect shows the bug was originally introduced by 5c64097aa0f6dc4f27718ef47ca9a12538d62860, first in 2.6.19-rc1.

---
 crypto/scatterwalk.c |    4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)
crypto/scatterwalk.c +2 -2
@@ -91,6 +91,8 @@ void scatterwalk_copychunks(void *buf, s
 		memcpy_dir(buf, vaddr, len_this_page, out);
 		scatterwalk_unmap(vaddr, out);
 
+		scatterwalk_advance(walk, nbytes);
+
 		if (nbytes == len_this_page)
 			break;
 
@@ -99,7 +101,5 @@ void scatterwalk_copychunks(void *buf, s
 
 		scatterwalk_pagedone(walk, out, 1);
 	}
-
-	scatterwalk_advance(walk, nbytes);
 }
 EXPORT_SYMBOL_GPL(scatterwalk_copychunks);
#37 lore raw

Re: [patch 32/37] CRYPTO: api: scatterwalk_copychunks() fails to advance through scatterlist

Quoted 6 lines · Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: J. Bruce Fields <[email protected]>

[CRYPTO] api: scatterwalk_copychunks() fails to advance through scatterlist

This patch seems to cause some problems, I get reproducable freezes on the receiving system with net-2.6.22 when sending IPsec packets larger than the mtu (reproduced about 10 times). Reverting this patch seems to fix it. In a few cases the oops also occured on the sending system.

Backtrace from UML (sending system):

uml:~# ping 10.0.0.1 -s 20000
PING 10.0.0.1 (10.0.0.1) 20000(20028) bytes of data.
BUG: soft lockup detected on CPU#0!
Call Trace:
61787408:  [<602b346f>] _spin_lock+0x9/0xb
61787418:  [<6004f7b7>] softlockup_tick+0xa1/0xaf
61787438:  [<6003c9d3>] run_local_timers+0x13/0x15
61787448:  [<6003c7e8>] update_process_times+0x49/0x73
61787478:  [<6001926e>] timer_handler+0x21/0x4f
617874a8:  [<60029327>] sig_handler_common_skas+0xff/0x118
617874e8:  [<6002625f>] real_alarm_handler+0x37/0x3b
61787508:  [<600262b6>] alarm_handler+0x53/0x63
61787538:  [<60027e65>] hard_handler+0x15/0x18
617875f8:  [<6015bfd9>] scatterwalk_copychunks+0x6d/0xb4
617876d8:  [<6001adda>] maybe_map+0x32/0x9f
61787728:  [<6015d332>] blkcipher_walk_next+0x11d/0x30f
61787738:  [<6006b58c>] poison_obj+0x27/0x32
61787740:  [<6015d332>] blkcipher_walk_next+0x11d/0x30f
61787758:  [<6006cc92>] cache_alloc_debugcheck_after+0xe5/0x12e
61787780:  [<6015bfbf>] scatterwalk_copychunks+0x53/0xb4
61787788:  [<6006d14e>] __kmalloc+0xb7/0xc4
617877c8:  [<6015d3b6>] blkcipher_walk_next+0x1a1/0x30f
61787828:  [<6015d186>] blkcipher_walk_done+0x12e/0x1bd
61787838:  [<6002dae3>] aes_encrypt+0x0/0xb
61787850:  [<601643d8>] xor_128+0x0/0x1c
61787878:  [<6016416d>] crypto_cbc_encrypt+0x7a/0x8b
61787918:  [<60244183>] esp_output+0x32b/0x44c
61787948:  [<602b34dc>] _spin_unlock_bh+0x12/0x14
617879c8:  [<60257051>] xfrm4_output_one+0xaa/0x16a
61787a08:  [<60257234>] xfrm4_output_finish2+0x123/0x131
61787a28:  [<6025728f>] xfrm4_output_finish+0x3d/0xb9
61787a58:  [<60257366>] xfrm4_output+0x5b/0x5d
61787a78:  [<602183a9>] ip_push_pending_frames+0x374/0x442
61787ac8:  [<6023008d>] raw_sendmsg+0x2d0/0x396
61787b78:  [<60237edd>] inet_sendmsg+0x46/0x53
61787ba8:  [<601bb5ca>] sock_sendmsg+0xea/0x103
61787c18:  [<600473b9>] autoremove_wake_function+0x0/0x39
61787c38:  [<600192d3>] add_mmap+0x37/0x149
61787c98:  [<6001b10d>] buffer_op+0x2e/0x5f
61787cd8:  [<6001b1d5>] copy_from_user_skas+0x7a/0x7c
61787d08:  [<601c2747>] verify_iovec+0x4f/0x90
61787d38:  [<601bcc32>] sys_sendmsg+0x172/0x1db
61787d68:  [<602b34b5>] _spin_unlock_irqrestore+0x18/0x1d
61787d88:  [<601924bf>] __up_read+0x76/0x7f
61787db8:  [<60049ae1>] up_read+0x9/0xb
61787dc8:  [<60019d78>] handle_page_fault+0x1f4/0x224
61787e28:  [<60019f29>] segv+0xa7/0x27e
61787ef8:  [<6001ab91>] handle_syscall+0x65/0x80
61787f08:  [<60019e7c>] segv_handler+0x68/0x6e
61787f28:  [<600287ab>] handle_trap+0xd0/0xdb
61787f68:  [<60028c2d>] userspace+0x139/0x181
61787fc8:  [<6001a8ba>] fork_handler+0x86/0x8d
maintainer
#38 lore raw

Re: [patch 32/37] CRYPTO: api: scatterwalk_copychunks() fails to advance through scatterlist

Quoted 9 lines · Patrick McHardy
Quoted 2 lines

[CRYPTO] api: scatterwalk_copychunks() fails to advance through scatterlist

This patch seems to cause some problems, I get reproducable freezes on the receiving system with net-2.6.22 when sending IPsec packets larger than the mtu (reproduced about 10 times). Reverting this patch seems to fix it. In a few cases the oops also occured on the sending system.

Quoted 6 lines

Backtrace from UML (sending system):

uml:~# ping 10.0.0.1 -s 20000
PING 10.0.0.1 (10.0.0.1) 20000(20028) bytes of data.
BUG: soft lockup detected on CPU#0!
Call Trace:

Indeed. That patch was buggy. Sorry for not catching this earlier.

This should fix the problem.

[CRYPTO] api: Use the right value when advancing scatterwalk_copychunks

In the scatterwalk_copychunks loop, We should be advancing by len_this_page and not nbytes. The latter is the total length.

Cheers,

Signature · 5 lines
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <[email protected]>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt
--
crypto/scatterwalk.c +1 -1
index a664231..0f76175 100644
@@ -91,7 +91,7 @@ void scatterwalk_copychunks(void *buf, struct scatter_walk *walk,
 		memcpy_dir(buf, vaddr, len_this_page, out);
 		scatterwalk_unmap(vaddr, out);
 
-		scatterwalk_advance(walk, nbytes);
+		scatterwalk_advance(walk, len_this_page);
 
 		if (nbytes == len_this_page)
 			break;
#39 lore raw

Re: [patch 32/37] CRYPTO: api: scatterwalk_copychunks() fails to advance through scatterlist

Quoted 3 lines · Herbert Xu

Indeed. That patch was buggy. Sorry for not catching this earlier.

This should fix the problem.

Works fine, thanks Herbert.

author
#40 lore raw

Re: [patch 32/37] CRYPTO: api: scatterwalk_copychunks() fails to advance through scatterlist

In reply to Herbert Xu
Quoted 19 lines · Herbert Xu
Quoted 9 lines · Patrick McHardy
Quoted 2 lines

[CRYPTO] api: scatterwalk_copychunks() fails to advance through scatterlist

This patch seems to cause some problems, I get reproducable freezes on the receiving system with net-2.6.22 when sending IPsec packets larger than the mtu (reproduced about 10 times). Reverting this patch seems to fix it. In a few cases the oops also occured on the sending system.

Quoted 6 lines

Backtrace from UML (sending system):

uml:~# ping 10.0.0.1 -s 20000
PING 10.0.0.1 (10.0.0.1) 20000(20028) bytes of data.
BUG: soft lockup detected on CPU#0!
Call Trace:

Indeed. That patch was buggy. Sorry for not catching this earlier.

Quoted 8 lines

This should fix the problem.

[CRYPTO] api: Use the right value when advancing scatterwalk_copychunks

In the scatterwalk_copychunks loop, We should be advancing by len_this_page and not nbytes. The latter is the total length.

Is this an "add-on" patch, or a replacement one?

thanks,

greg k-h

maintainer
#41 lore raw

Re: [patch 32/37] CRYPTO: api: scatterwalk_copychunks() fails to advance through scatterlist

Quoted 2 lines · Greg KH

Is this an "add-on" patch, or a replacement one?

This is an add-on. In case you want a replacement, here it is:

Cheers,

Signature · 5 lines
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <[email protected]>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt
--
crypto/scatterwalk.c +2 -2
index 35172d3..0f76175 100644
@@ -91,6 +91,8 @@ void scatterwalk_copychunks(void *buf, struct scatter_walk *walk,
 		memcpy_dir(buf, vaddr, len_this_page, out);
 		scatterwalk_unmap(vaddr, out);
 
+		scatterwalk_advance(walk, len_this_page);
+
 		if (nbytes == len_this_page)
 			break;
 
@@ -99,7 +101,5 @@ void scatterwalk_copychunks(void *buf, struct scatter_walk *walk,
 
 		scatterwalk_pagedone(walk, out, 1);
 	}
-
-	scatterwalk_advance(walk, nbytes);
 }
 EXPORT_SYMBOL_GPL(scatterwalk_copychunks);
#42 lore raw

Re: [patch 32/37] CRYPTO: api: scatterwalk_copychunks() fails to advance through scatterlist

In reply to Herbert Xu
Quoted 1 line · Herbert Xu

Indeed. That patch was buggy. Sorry for not catching this earlier.

Yep, thanks for the fix. I used the wrong length, then tested with a case where nbytes would always be less than PAGE_SIZE, which doesn't hit this problem. Apologies!

--b.

author
#43 lore raw

PATCH 33/37 libata: clear TF before IDENTIFYing

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Tejun Heo <[email protected]>

libata: clear TF before IDENTIFYing

Some devices chock if Feature is not clear when IDENTIFY is issued. Set ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE for IDENTIFY such that whole TF is cleared when reading ID data.

Kudos to Art Haas for testing various futile patches over several months and Mark Lord for pointing out the fix.

---
 drivers/ata/libata-core.c |   11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)
drivers/ata/libata-core.c +10 -1
@@ -1478,7 +1478,16 @@ int ata_dev_read_id(struct ata_device *d
 	}
 
 	tf.protocol = ATA_PROT_PIO;
-	tf.flags |= ATA_TFLAG_POLLING; /* for polling presence detection */
+
+	/* Some devices choke if TF registers contain garbage.  Make
+	 * sure those are properly initialized.
+	 */
+	tf.flags |= ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE;
+
+	/* Device presence detection is unreliable on some
+	 * controllers.  Always poll IDENTIFY if available.
+	 */
+	tf.flags |= ATA_TFLAG_POLLING;
 
 	err_mask = ata_exec_internal(dev, &tf, NULL, DMA_FROM_DEVICE,
 				     id, sizeof(id[0]) * ATA_ID_WORDS);
author
#44 lore raw

PATCH 34/37 libata bugfix: HDIO_DRIVE_TASK

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Mark Lord <[email protected]>

libata bugfix: HDIO_DRIVE_TASK

I was trying to use HDIO_DRIVE_TASK for something today, and discovered that the libata implementation does not copy over the upper four LBA bits from args[6].

This is serious, as any tools using this ioctl would have their commands applied to the wrong sectors on the drive, possibly resulting in disk corruption.

Ideally, newer apps should use SG_IO/ATA_16 directly, avoiding this bug. But with libata poised to displace drivers/ide, better compatibility here is a must.

This patch fixes libata to use the upper four LBA bits passed in from the ioctl.

The original drivers/ide implementation copies over all bits except for the master/slave select bit. With this patch, libata will copy only the four high-order LBA bits, just in case there are assumptions elsewhere in libata (?).

---
 drivers/ata/libata-scsi.c |    1 +
 1 file changed, 1 insertion(+)
drivers/ata/libata-scsi.c +1 -0
@@ -295,6 +295,7 @@ int ata_task_ioctl(struct scsi_device *s
 	scsi_cmd[8]  = args[3];
 	scsi_cmd[10] = args[4];
 	scsi_cmd[12] = args[5];
+	scsi_cmd[13] = args[6] & 0x0f;
 	scsi_cmd[14] = args[0];
 
 	/* Good values for timeout and retries?  Values below
#45 lore raw

Re: [patch 34/37] libata bugfix: HDIO_DRIVE_TASK

Quoted 27 lines · Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Mark Lord <[email protected]>

libata bugfix: HDIO_DRIVE_TASK

I was trying to use HDIO_DRIVE_TASK for something today, and discovered that the libata implementation does not copy over the upper four LBA bits from args[6].

This is serious, as any tools using this ioctl would have their commands applied to the wrong sectors on the drive, possibly resulting in disk corruption.

Ideally, newer apps should use SG_IO/ATA_16 directly, avoiding this bug. But with libata poised to displace drivers/ide, better compatibility here is a must.

This patch fixes libata to use the upper four LBA bits passed in from the ioctl.

The original drivers/ide implementation copies over all bits except for the master/slave select bit. With this patch, libata will copy only the four high-order LBA bits, just in case there are assumptions elsewhere in libata (?).

Quoted 4 lines

..

Mmmm.. I've just noticed another bit we should be preserving there, both for *stable* and current mainline.

Instead of:

Review

Quoted 1 line
(quoted diff) +1 -0
+	scsi_cmd[13] = args[6] & 0x0f;

We should be doing:

Review

Quoted 1 line
(quoted diff) +1 -0
+	scsi_cmd[13] = args[6] & 0x4f;

As-is, the patch still helps, but it is not as useful as it could be. Here's the fixed version. I'm also sending out a 2.6.21 patch via Jeff.

---
drivers/ata/libata-scsi.c | 1 +

1 file changed, 1 insertion(+)
drivers/ata/libata-scsi.c +0 -0
@@ -295,6 +295,7 @@ int ata_task_ioctl(struct scsi_device *s
	scsi_cmd[8]  = args[3];
	scsi_cmd[10] = args[4];
	scsi_cmd[12] = args[5];
+	scsi_cmd[13] = args[6] & 0x4f;
	scsi_cmd[14] = args[0];

	/* Good values for timeout and retries?  Values below
Signature · 3 lines
Mark Lord
Real-Time Remedies Inc.
[email protected] 
author
#46 lore raw

Re: [patch 34/37] libata bugfix: HDIO_DRIVE_TASK

Quoted 43 lines · Mark Lord
Quoted 27 lines · Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Mark Lord <[email protected]>

libata bugfix: HDIO_DRIVE_TASK

I was trying to use HDIO_DRIVE_TASK for something today, and discovered that the libata implementation does not copy over the upper four LBA bits from args[6].

This is serious, as any tools using this ioctl would have their commands applied to the wrong sectors on the drive, possibly resulting in disk corruption.

Ideally, newer apps should use SG_IO/ATA_16 directly, avoiding this bug. But with libata poised to displace drivers/ide, better compatibility here is a must.

This patch fixes libata to use the upper four LBA bits passed in from the ioctl.

The original drivers/ide implementation copies over all bits except for the master/slave select bit. With this patch, libata will copy only the four high-order LBA bits, just in case there are assumptions elsewhere in libata (?).

Quoted 4 lines

..

Mmmm.. I've just noticed another bit we should be preserving there, both for *stable* and current mainline.

Instead of:

Review

Quoted 1 line
(quoted diff) +1 -0
+	scsi_cmd[13] = args[6] & 0x0f;

We should be doing:

Quoted 6 lines

Review

Quoted 1 line
(quoted diff) +1 -0
+	scsi_cmd[13] = args[6] & 0x4f;

As-is, the patch still helps, but it is not as useful as it could be. Here's the fixed version. I'm also sending out a 2.6.21 patch via Jeff.

Can you forward that one to the [email protected] address too, with the full changelog and Jeff's ack/signed-off-by so that I will remember to add it to the tree?

thanks,

greg k-h

#47 lore raw

libata bugfix: preserve LBA bit for HDIO_DRIVE_TASK

In reply to Greg KH

Ideally, this would go into linux-2.6.21.

Preserve the LBA bit in the DevSel/Head register for HDIO_DRIVE_TASK.

---

drivers/ata/libata-scsi.c renamed from drivers/ata/libata-scsi.c.orig +0 -0
@@ -333,7 +333,7 @@
	scsi_cmd[8]  = args[3];
	scsi_cmd[10] = args[4];
	scsi_cmd[12] = args[5];
-	scsi_cmd[13] = args[6] & 0x0f;
+	scsi_cmd[13] = args[6] & 0x4f;
	scsi_cmd[14] = args[0];

	/* Good values for timeout and retries?  Values below
Signature · 3 lines
Mark Lord
Real-Time Remedies Inc.
[email protected]
#48 lore raw

Re: libata bugfix: preserve LBA bit for HDIO_DRIVE_TASK

Quoted 10 lines · Mark Lord

Ideally, this would go into linux-2.6.21.

Preserve the LBA bit in the DevSel/Head register for HDIO_DRIVE_TASK.

---
--- linux/drivers/ata/libata-scsi.c.orig 2007-03-21
13:35:02.000000000 -0400
+++ linux/drivers/ata/libata-scsi.c 2007-03-30 17:40:58.000000000 -0400

Review line 339

Quoted 8 lines
(quoted diff) +1 -1
@@ -333,7 +333,7 @@
    scsi_cmd[8]  = args[3];
    scsi_cmd[10] = args[4];
    scsi_cmd[12] = args[5];
-    scsi_cmd[13] = args[6] & 0x0f;
+    scsi_cmd[13] = args[6] & 0x4f;
    scsi_cmd[14] = args[0];
 
    /* Good values for timeout and retries?  Values below

IDE seems to be just overriding devsel (0x10) and leaving the rest alone. Maybe we should do (args[6] & ~0x10) here? Or is it safer this way?

Thanks.

Signature · 1 line
tejun
#49 lore raw

Re: libata bugfix: preserve LBA bit for HDIO_DRIVE_TASK

Quoted 18 lines · Tejun Heo
Quoted 17 lines · Mark Lord

Ideally, this would go into linux-2.6.21.

Preserve the LBA bit in the DevSel/Head register for HDIO_DRIVE_TASK.

---
--- linux/drivers/ata/libata-scsi.c.orig 2007-03-21
13:35:02.000000000 -0400
+++ linux/drivers/ata/libata-scsi.c 2007-03-30 17:40:58.000000000 -0400

(quoted diff) +1 -1
@@ -333,7 +333,7 @@
    scsi_cmd[8]  = args[3];
    scsi_cmd[10] = args[4];
    scsi_cmd[12] = args[5];
-    scsi_cmd[13] = args[6] & 0x0f;
+    scsi_cmd[13] = args[6] & 0x4f;
    scsi_cmd[14] = args[0];
 
Quoted 4 lines

Review line 339

Quoted 1 line
(quoted diff) +0 -0
    /* Good values for timeout and retries?  Values below

IDE seems to be just overriding devsel (0x10) and leaving the rest alone. Maybe we should do (args[6] & ~0x10) here? Or is it safer this way?

Same thoughts here. I went "conservative" on this one, because the entire field has been all zeros until this patch, and I didn't want to trigger any possible latent bugs in libata.

Whatever.

Cheers

Acked-by
#50 lore raw

Re: libata bugfix: preserve LBA bit for HDIO_DRIVE_TASK

Quoted 25 lines · Mark Lord
Quoted 19 lines · Tejun Heo
Quoted 18 lines · Mark Lord

Ideally, this would go into linux-2.6.21.

Preserve the LBA bit in the DevSel/Head register for HDIO_DRIVE_TASK.

---
--- linux/drivers/ata/libata-scsi.c.orig 2007-03-21
13:35:02.000000000 -0400
+++ linux/drivers/ata/libata-scsi.c 2007-03-30 17:40:58.000000000
-0400

(quoted diff) +1 -1
@@ -333,7 +333,7 @@
    scsi_cmd[8]  = args[3];
    scsi_cmd[10] = args[4];
    scsi_cmd[12] = args[5];
-    scsi_cmd[13] = args[6] & 0x0f;
+    scsi_cmd[13] = args[6] & 0x4f;
    scsi_cmd[14] = args[0];
 
Quoted 4 lines

Review line 339

Quoted 1 line
(quoted diff) +0 -0
    /* Good values for timeout and retries?  Values below

IDE seems to be just overriding devsel (0x10) and leaving the rest alone. Maybe we should do (args[6] & ~0x10) here? Or is it safer this way?

Quoted 5 lines

Same thoughts here. I went "conservative" on this one, because the entire field has been all zeros until this patch, and I didn't want to trigger any possible latent bugs in libata.

Whatever.

Yeah, I agree 'whatever' should work here. :-)

Signature · 1 line
tejun
Applied
#51 lore raw

Re: libata bugfix: preserve LBA bit for HDIO_DRIVE_TASK

In reply to Mark Lord
Quoted 10 lines · Mark Lord

Ideally, this would go into linux-2.6.21.

Preserve the LBA bit in the DevSel/Head register for HDIO_DRIVE_TASK.

---
--- linux/drivers/ata/libata-scsi.c.orig 2007-03-21
13:35:02.000000000 -0400
+++ linux/drivers/ata/libata-scsi.c 2007-03-30 17:40:58.000000000 -0400

Review line 337

Quoted 6 lines
(quoted diff) +1 -1
@@ -333,7 +333,7 @@
    scsi_cmd[8]  = args[3];
    scsi_cmd[10] = args[4];
    scsi_cmd[12] = args[5];
-    scsi_cmd[13] = args[6] & 0x0f;
+    scsi_cmd[13] = args[6] & 0x4f;
    scsi_cmd[14] = args[0];

applied

author
#52 lore raw

PATCH 35/37 libata: sata_mv: dont touch reserved bits in EDMA config register

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Jeff Garzik <[email protected]>

[libata] sata_mv: don't touch reserved bits in EDMA config register

The code in mv_edma_cfg() reflected its 60xx origins, by doing things [slightly] incorrectly on the older 50xx and newer 6042/7042 chips.

Clean up the EDMA configuration setup such that, each chip family carefully initializes its own EDMA setup.

---
 drivers/ata/sata_mv.c |   20 ++++++++++++--------
 1 file changed, 12 insertions(+), 8 deletions(-)
drivers/ata/sata_mv.c +12 -8
@@ -843,23 +843,27 @@ static void mv_edma_cfg(struct mv_host_p
 	u32 cfg = readl(port_mmio + EDMA_CFG_OFS);
 
 	/* set up non-NCQ EDMA configuration */
-	cfg &= ~0x1f;		/* clear queue depth */
-	cfg &= ~EDMA_CFG_NCQ;	/* clear NCQ mode */
 	cfg &= ~(1 << 9);	/* disable equeue */
 
-	if (IS_GEN_I(hpriv))
+	if (IS_GEN_I(hpriv)) {
+		cfg &= ~0x1f;		/* clear queue depth */
 		cfg |= (1 << 8);	/* enab config burst size mask */
+	}
 
-	else if (IS_GEN_II(hpriv))
+	else if (IS_GEN_II(hpriv)) {
+		cfg &= ~0x1f;		/* clear queue depth */
 		cfg |= EDMA_CFG_RD_BRST_EXT | EDMA_CFG_WR_BUFF_LEN;
+		cfg &= ~(EDMA_CFG_NCQ | EDMA_CFG_NCQ_GO_ON_ERR); /* clear NCQ */
+	}
 
 	else if (IS_GEN_IIE(hpriv)) {
-		cfg |= (1 << 23);	/* dis RX PM port mask */
-		cfg &= ~(1 << 16);	/* dis FIS-based switching (for now) */
+		cfg |= (1 << 23);	/* do not mask PM field in rx'd FIS */
+		cfg |= (1 << 22);	/* enab 4-entry host queue cache */
 		cfg &= ~(1 << 19);	/* dis 128-entry queue (for now?) */
 		cfg |= (1 << 18);	/* enab early completion */
-		cfg |= (1 << 17);	/* enab host q cache */
-		cfg |= (1 << 22);	/* enab cutthrough */
+		cfg |= (1 << 17);	/* enab cut-through (dis stor&forwrd) */
+		cfg &= ~(1 << 16);	/* dis FIS-based switching (for now) */
+		cfg &= ~(EDMA_CFG_NCQ | EDMA_CFG_NCQ_GO_ON_ERR); /* clear NCQ */
 	}
 
 	writelfl(cfg, port_mmio + EDMA_CFG_OFS);
author
#53 lore raw

PATCH 36/37 libata: sata_mv: Fix 50xx irq mask

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Jeff Garzik <[email protected]>

[libata] sata_mv: Fix 50xx irq mask

IRQ mask bits assumed a 60xx or newer generation chip, which is very wrong for the 50xx series. Luckily both generations shared the per-port interrupt mask bits, leaving only the "misc chip features" bits to be completely mismatched.

Fix 50xx by ensuring we only program bits that exist.

---
 drivers/ata/sata_mv.c |   11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)
drivers/ata/sata_mv.c +10 -1
@@ -139,14 +139,19 @@ enum {
 	PCI_ERR			= (1 << 18),
 	TRAN_LO_DONE		= (1 << 19),	/* 6xxx: IRQ coalescing */
 	TRAN_HI_DONE		= (1 << 20),	/* 6xxx: IRQ coalescing */
+	PORTS_0_3_COAL_DONE	= (1 << 8),
+	PORTS_4_7_COAL_DONE	= (1 << 17),
 	PORTS_0_7_COAL_DONE	= (1 << 21),	/* 6xxx: IRQ coalescing */
 	GPIO_INT		= (1 << 22),
 	SELF_INT		= (1 << 23),
 	TWSI_INT		= (1 << 24),
 	HC_MAIN_RSVD		= (0x7f << 25),	/* bits 31-25 */
+	HC_MAIN_RSVD_5		= (0x1fff << 19), /* bits 31-19 */
 	HC_MAIN_MASKED_IRQS	= (TRAN_LO_DONE | TRAN_HI_DONE |
 				   PORTS_0_7_COAL_DONE | GPIO_INT | TWSI_INT |
 				   HC_MAIN_RSVD),
+	HC_MAIN_MASKED_IRQS_5	= (PORTS_0_3_COAL_DONE | PORTS_4_7_COAL_DONE |
+				   HC_MAIN_RSVD_5),
 
 	/* SATAHC registers */
 	HC_CFG_OFS		= 0,
@@ -2287,7 +2292,11 @@ static int mv_init_host(struct pci_dev *
 
 	/* and unmask interrupt generation for host regs */
 	writelfl(PCI_UNMASK_ALL_IRQS, mmio + PCI_IRQ_MASK_OFS);
-	writelfl(~HC_MAIN_MASKED_IRQS, mmio + HC_MAIN_IRQ_MASK_OFS);
+
+	if (IS_50XX(hpriv))
+		writelfl(~HC_MAIN_MASKED_IRQS_5, mmio + HC_MAIN_IRQ_MASK_OFS);
+	else
+		writelfl(~HC_MAIN_MASKED_IRQS, mmio + HC_MAIN_IRQ_MASK_OFS);
 
 	VPRINTK("HC MAIN IRQ cause/mask=0x%08x/0x%08x "
 		"PCI int cause/mask=0x%08x/0x%08x\n",
author
#54 lore raw

PATCH 37/37 generic_serial: fix decoding of baud rate

In reply to Greg KH

-stable review patch. If anyone has any objections, please let us know.

------------------
From: Daniel Drake <[email protected]>

Commit d720bc4b8fc5d6d179ef094908d4fbb5e436ffad partially removed a private implementation of baud speed decoding. However it doesn't seem to be
complete: after the speed is decoded, it is still being used as an index to a local speed table (array overrun, no doubt).

This was found by Graham Murray who noticed it caused a 2.6.19 regression with the SX driver: https://bugs.gentoo.org/170554

---
 drivers/char/generic_serial.c |    7 -------
 1 file changed, 7 deletions(-)
drivers/char/generic_serial.c +0 -7
@@ -711,12 +711,6 @@ void gs_close(struct tty_struct * tty, s
 }
 
 
-static unsigned int     gs_baudrates[] = {
-  0, 50, 75, 110, 134, 150, 200, 300, 600, 1200, 1800, 2400, 4800,
-  9600, 19200, 38400, 57600, 115200, 230400, 460800, 921600
-};
-
-
 void gs_set_termios (struct tty_struct * tty, 
                      struct ktermios * old_termios)
 {
@@ -772,7 +766,6 @@ void gs_set_termios (struct tty_struct *
 
 	baudrate = tty_get_baud_rate(tty);
 
-	baudrate = gs_baudrates[baudrate];
 	if ((tiosp->c_cflag & CBAUD) == B38400) {
 		if (     (port->flags & ASYNC_SPD_MASK) == ASYNC_SPD_HI)
 			baudrate = 57600;
#55 lore raw
In reply to Greg KH
Quoted 5 lines · Greg KH

This is the start of the stable review cycle for the 2.6.20.5 release. There are 37 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let us know. If anyone is a maintainer of the proper subsystem, and wants to add a Signed-off-by: line to the patch, please respond with it.

Will this be released anytime soon?

#56 lore raw
Quoted 8 lines · Chuck Ebbert
Quoted 5 lines · Greg KH

This is the start of the stable review cycle for the 2.6.20.5 release. There are 37 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let us know. If anyone is a maintainer of the proper subsystem, and wants to add a Signed-off-by: line to the patch, please respond with it.

Will this be released anytime soon?

Yes, sorry, I ended up having to travel over to germany on kind of a short notice, sorry. I'll push the release out tomorrow (.de timezone) when I get back to a better network connection...

thanks,

greg k-h