All of lore.kernel.org
 help / color / mirror / Atom feed
* [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+
@ 2009-09-16 14:37 Ursula Braun
  2009-09-16 14:37 ` [patch 1/7] [PATCH] iucv: suspend/resume error msg for left over pathes Ursula Braun
                   ` (7 more replies)
  0 siblings, 8 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390; +Cc: schwidefsky, heiko.carstens

Dave,

here are bugfixes for iucv and af_iucv for the next possible 2.6.31 follow-on.
They apply to linux-2.6 and net-2.6.

Summary:

Ursula Braun (1)
iucv: suspend/resume error msg for left over pathes

Hendrik Brueckner (6)
iucv: fix iucv_buffer_cpumask check when calling IUCV functions
iucv: use correct output register in iucv_query_maxconn()
af_iucv: fix race in __iucv_sock_wait()
af_iucv: handle non-accepted sockets after resuming from suspend
af_iucv: do not call iucv_sock_kill() twice
af_iucv: fix race when queueing skbs on the backlog queue

Thanks,
        Ursula


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [patch 1/7] [PATCH] iucv: suspend/resume error msg for left over pathes
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
@ 2009-09-16 14:37 ` Ursula Braun
  2009-09-16 14:37 ` [patch 2/7] [PATCH] iucv: fix iucv_buffer_cpumask check when calling IUCV functions Ursula Braun
                   ` (6 subsequent siblings)
  7 siblings, 0 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390; +Cc: schwidefsky, heiko.carstens, Ursula Braun

[-- Attachment #1: 600-iucv-pm-leftover.diff --]
[-- Type: text/plain, Size: 2102 bytes --]

From: Ursula Braun <ursula.braun@de.ibm.com>

During suspend IUCV exploiters have to close their IUCV connections.
When restoring an image, it can be checked if all IUCV pathes had
been closed before the Linux instance was suspended. If not, an
error message is issued to indicate a problem in one of the
used programs exploiting IUCV communication.

Signed-off-by: Ursula Braun <ursula.braun@de.ibm.com>
---

 net/iucv/iucv.c |   14 ++++++++++++++
 1 file changed, 14 insertions(+)

diff -urpN linux-2.6/net/iucv/iucv.c linux-2.6-patched/net/iucv/iucv.c
--- linux-2.6/net/iucv/iucv.c	2009-09-10 00:13:59.000000000 +0200
+++ linux-2.6-patched/net/iucv/iucv.c	2009-09-15 12:25:31.000000000 +0200
@@ -79,6 +79,14 @@ static int iucv_bus_match(struct device 
 	return 0;
 }
 
+enum iucv_pm_states {
+	IUCV_PM_INITIAL = 0,
+	IUCV_PM_FREEZING = 1,
+	IUCV_PM_THAWING = 2,
+	IUCV_PM_RESTORING = 3,
+};
+static enum iucv_pm_states iucv_pm_state;
+
 static int iucv_pm_prepare(struct device *);
 static void iucv_pm_complete(struct device *);
 static int iucv_pm_freeze(struct device *);
@@ -1875,6 +1883,7 @@ static int iucv_pm_freeze(struct device 
 #ifdef CONFIG_PM_DEBUG
 	printk(KERN_WARNING "iucv_pm_freeze\n");
 #endif
+	iucv_pm_state = IUCV_PM_FREEZING;
 	for_each_cpu_mask_nr(cpu, iucv_irq_cpumask)
 		smp_call_function_single(cpu, iucv_block_cpu_almost, NULL, 1);
 	if (dev->driver && dev->driver->pm && dev->driver->pm->freeze)
@@ -1899,6 +1908,7 @@ static int iucv_pm_thaw(struct device *d
 #ifdef CONFIG_PM_DEBUG
 	printk(KERN_WARNING "iucv_pm_thaw\n");
 #endif
+	iucv_pm_state = IUCV_PM_THAWING;
 	if (!iucv_path_table) {
 		rc = iucv_enable();
 		if (rc)
@@ -1933,6 +1943,10 @@ static int iucv_pm_restore(struct device
 #ifdef CONFIG_PM_DEBUG
 	printk(KERN_WARNING "iucv_pm_restore %p\n", iucv_path_table);
 #endif
+	if ((iucv_pm_state != IUCV_PM_RESTORING) && iucv_path_table)
+		pr_warning("Suspending Linux did not completely close all IUCV "
+			"connections\n");
+	iucv_pm_state = IUCV_PM_RESTORING;
 	if (cpus_empty(iucv_irq_cpumask)) {
 		rc = iucv_query_maxconn();
 		rc = iucv_enable();


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [patch 2/7] [PATCH] iucv: fix iucv_buffer_cpumask check when calling IUCV functions
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
  2009-09-16 14:37 ` [patch 1/7] [PATCH] iucv: suspend/resume error msg for left over pathes Ursula Braun
@ 2009-09-16 14:37 ` Ursula Braun
  2009-09-16 14:37 ` [patch 3/7] [PATCH] iucv: use correct output register in iucv_query_maxconn() Ursula Braun
                   ` (5 subsequent siblings)
  7 siblings, 0 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390
  Cc: schwidefsky, heiko.carstens, Hendrik Brueckner, Ursula Braun

[-- Attachment #1: 601-iucv-cpumask.diff --]
[-- Type: text/plain, Size: 4004 bytes --]

From: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>

Prior to calling IUCV functions, the DECLARE BUFFER function must have been
called for at least one CPU to receive IUCV interrupts.

With commit "iucv: establish reboot notifier" (6c005961), a check has been
introduced to avoid calling IUCV functions if the current CPU does not have
an interrupt buffer declared.
Because one interrupt buffer is sufficient, change the condition to ensure
that one interrupt buffer is available.

In addition, checking the buffer on the current CPU creates a race with
CPU up/down notifications: before checking the buffer, the IUCV function
might be interrupted by an smp_call_function() that retrieves the interrupt
buffer for the current CPU.
When the IUCV function continues, the check fails and -EIO is returned. If a
buffer is available on any other CPU, the IUCV function call must be invoked
(instead of failing with -EIO).

Signed-off-by: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>
Signed-off-by: Ursula Braun <ursula.braun@de.ibm.com>
---

 net/iucv/iucv.c |   22 +++++++++++-----------
 1 file changed, 11 insertions(+), 11 deletions(-)

diff -urpN linux-2.6/net/iucv/iucv.c linux-2.6-patched/net/iucv/iucv.c
--- linux-2.6/net/iucv/iucv.c	2009-09-15 12:25:32.000000000 +0200
+++ linux-2.6-patched/net/iucv/iucv.c	2009-09-15 12:25:32.000000000 +0200
@@ -864,7 +864,7 @@ int iucv_path_accept(struct iucv_path *p
 	int rc;
 
 	local_bh_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -913,7 +913,7 @@ int iucv_path_connect(struct iucv_path *
 
 	spin_lock_bh(&iucv_table_lock);
 	iucv_cleanup_queue();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -973,7 +973,7 @@ int iucv_path_quiesce(struct iucv_path *
 	int rc;
 
 	local_bh_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1005,7 +1005,7 @@ int iucv_path_resume(struct iucv_path *p
 	int rc;
 
 	local_bh_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1034,7 +1034,7 @@ int iucv_path_sever(struct iucv_path *pa
 	int rc;
 
 	preempt_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1068,7 +1068,7 @@ int iucv_message_purge(struct iucv_path 
 	int rc;
 
 	local_bh_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1160,7 +1160,7 @@ int __iucv_message_receive(struct iucv_p
 	if (msg->flags & IUCV_IPRMDATA)
 		return iucv_message_receive_iprmdata(path, msg, flags,
 						     buffer, size, residual);
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1233,7 +1233,7 @@ int iucv_message_reject(struct iucv_path
 	int rc;
 
 	local_bh_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1272,7 +1272,7 @@ int iucv_message_reply(struct iucv_path 
 	int rc;
 
 	local_bh_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1322,7 +1322,7 @@ int __iucv_message_send(struct iucv_path
 	union iucv_param *parm;
 	int rc;
 
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}
@@ -1409,7 +1409,7 @@ int iucv_message_send2way(struct iucv_pa
 	int rc;
 
 	local_bh_disable();
-	if (!cpu_isset(smp_processor_id(), iucv_buffer_cpumask)) {
+	if (cpus_empty(iucv_buffer_cpumask)) {
 		rc = -EIO;
 		goto out;
 	}


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [patch 3/7] [PATCH] iucv: use correct output register in iucv_query_maxconn()
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
  2009-09-16 14:37 ` [patch 1/7] [PATCH] iucv: suspend/resume error msg for left over pathes Ursula Braun
  2009-09-16 14:37 ` [patch 2/7] [PATCH] iucv: fix iucv_buffer_cpumask check when calling IUCV functions Ursula Braun
@ 2009-09-16 14:37 ` Ursula Braun
  2009-09-16 14:37 ` [patch 4/7] [PATCH] af_iucv: fix race in __iucv_sock_wait() Ursula Braun
                   ` (4 subsequent siblings)
  7 siblings, 0 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390
  Cc: schwidefsky, heiko.carstens, Hendrik Brueckner, Ursula Braun

[-- Attachment #1: 602-iucv-query-maxconn.diff --]
[-- Type: text/plain, Size: 2794 bytes --]

From: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>

The iucv_query_maxconn() function uses the wrong output register and
stores the size of the interrupt buffer instead of the maximum number
of connections.

According to the QUERY IUCV function, general register 1 contains the
maximum number of connections.

If the maximum number of connections is not set properly, the following
warning is displayed:

Badness at /usr/src/kernel-source/2.6.30-39.x.20090806/net/iucv/iucv.c:1808
Modules linked in: netiucv fsm af_iucv sunrpc qeth_l3 dm_multipath dm_mod vmur qeth ccwgroup
CPU: 0 Tainted: G        W  2.6.30 #4
Process seq (pid: 16925, task: 0000000030e24a40, ksp: 000000003033bd98)
Krnl PSW : 0404200180000000 000000000053b270 (iucv_external_interrupt+0x64/0x224)
           R:0 T:1 IO:0 EX:0 Key:0 M:1 W:0 P:0 AS:0 CC:2 PM:0 EA:3
Krnl GPRS: 00000000011279c2 00000000014bdb70 0029000000000000 0000000000000029
           000000000053b236 000000000001dba4 0000000000000000 0000000000859210
           0000000000a67f68 00000000008a6100 000000003f83fb90 0000000000004000
           000000003f8c7bc8 00000000005a2250 000000000053b236 000000003fc2fe08
Krnl Code: 000000000053b262: e33010000021	clg	%r3,0(%r1)
           000000000053b268: a7440010		brc	4,53b288
           000000000053b26c: a7f40001		brc	15,53b26e
          >000000000053b270: c03000184134	larl	%r3,8434d8
           000000000053b276: eb220030000c	srlg	%r2,%r2,48
           000000000053b27c: eb6ff0a00004	lmg	%r6,%r15,160(%r15)
           000000000053b282: c0f4fffff6a7	brcl	15,539fd0
           000000000053b288: 4310a003		ic	%r1,3(%r10)
Call Trace:
([<000000000053b236>] iucv_external_interrupt+0x2a/0x224)
 [<000000000010e09e>] do_extint+0x132/0x190
 [<00000000001184b6>] ext_no_vtime+0x1e/0x22
 [<0000000000549f7a>] _spin_unlock_irqrestore+0x96/0xa4
([<0000000000549f70>] _spin_unlock_irqrestore+0x8c/0xa4)
 [<00000000002101d6>] pipe_write+0x3da/0x5bc
 [<0000000000205d14>] do_sync_write+0xe4/0x13c
 [<0000000000206a7e>] vfs_write+0xae/0x15c
 [<0000000000206c24>] SyS_write+0x54/0xac
 [<0000000000117c8e>] sysc_noemu+0x10/0x16
 [<00000042ff8defcc>] 0x42ff8defcc

Signed-off-by: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>
Signed-off-by: Ursula Braun <ursula.braun@de.ibm.com>
---

 net/iucv/iucv.c |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff -urpN linux-2.6/net/iucv/iucv.c linux-2.6-patched/net/iucv/iucv.c
--- linux-2.6/net/iucv/iucv.c	2009-09-15 12:25:32.000000000 +0200
+++ linux-2.6-patched/net/iucv/iucv.c	2009-09-15 12:25:32.000000000 +0200
@@ -362,7 +362,7 @@ static int iucv_query_maxconn(void)
 		"	srl	%0,28\n"
 		: "=d" (ccode), "+d" (reg0), "+d" (reg1) : : "cc");
 	if (ccode == 0)
-		iucv_max_pathid = reg0;
+		iucv_max_pathid = reg1;
 	kfree(param);
 	return ccode ? -EPERM : 0;
 }


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [patch 4/7] [PATCH] af_iucv: fix race in __iucv_sock_wait()
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
                   ` (2 preceding siblings ...)
  2009-09-16 14:37 ` [patch 3/7] [PATCH] iucv: use correct output register in iucv_query_maxconn() Ursula Braun
@ 2009-09-16 14:37 ` Ursula Braun
  2009-09-16 14:37 ` [patch 5/7] [PATCH] af_iucv: handle non-accepted sockets after resuming from suspend Ursula Braun
                   ` (3 subsequent siblings)
  7 siblings, 0 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390
  Cc: schwidefsky, heiko.carstens, Hendrik Brueckner, Ursula Braun

[-- Attachment #1: 604-af_iucv-sock-wait-race.diff --]
[-- Type: text/plain, Size: 969 bytes --]

From: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>

Moving prepare_to_wait before the condition to avoid a race between
schedule_timeout and wake up.
The race can appear during iucv_sock_connect() and iucv_callback_connack().

Signed-off-by: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>
Signed-off-by: Ursula Braun <ursula.braun@de.ibm.com>
---

 net/iucv/af_iucv.c |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

Index: linux-2.6-uschi/net/iucv/af_iucv.c
===================================================================
--- linux-2.6-uschi.orig/net/iucv/af_iucv.c
+++ linux-2.6-uschi/net/iucv/af_iucv.c
@@ -59,8 +59,8 @@ do {									\
 	DEFINE_WAIT(__wait);						\
 	long __timeo = timeo;						\
 	ret = 0;							\
+	prepare_to_wait(sk->sk_sleep, &__wait, TASK_INTERRUPTIBLE);	\
 	while (!(condition)) {						\
-		prepare_to_wait(sk->sk_sleep, &__wait, TASK_INTERRUPTIBLE); \
 		if (!__timeo) {						\
 			ret = -EAGAIN;					\
 			break;						\


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [patch 5/7] [PATCH] af_iucv: handle non-accepted sockets after resuming from suspend
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
                   ` (3 preceding siblings ...)
  2009-09-16 14:37 ` [patch 4/7] [PATCH] af_iucv: fix race in __iucv_sock_wait() Ursula Braun
@ 2009-09-16 14:37 ` Ursula Braun
  2009-09-16 14:37 ` [patch 6/7] [PATCH] af_iucv: do not call iucv_sock_kill() twice Ursula Braun
                   ` (2 subsequent siblings)
  7 siblings, 0 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390
  Cc: schwidefsky, heiko.carstens, Hendrik Brueckner, Ursula Braun

[-- Attachment #1: 605-af_iucv-socket-discon.diff --]
[-- Type: text/plain, Size: 867 bytes --]

From: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>

After resuming from suspend, all af_iucv sockets are disconnected.
Ensure that iucv_accept_dequeue() can handle disconnected sockets
which are not yet accepted.

Signed-off-by: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>
Signed-off-by: Ursula Braun <ursula.braun@de.ibm.com>
---

 net/iucv/af_iucv.c |    1 +
 1 file changed, 1 insertion(+)

Index: linux-2.6-uschi/net/iucv/af_iucv.c
===================================================================
--- linux-2.6-uschi.orig/net/iucv/af_iucv.c
+++ linux-2.6-uschi/net/iucv/af_iucv.c
@@ -569,6 +569,7 @@ struct sock *iucv_accept_dequeue(struct 
 
 		if (sk->sk_state == IUCV_CONNECTED ||
 		    sk->sk_state == IUCV_SEVERED ||
+		    sk->sk_state == IUCV_DISCONN ||	/* due to PM restore */
 		    !newsock) {
 			iucv_accept_unlink(sk);
 			if (newsock)


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [patch 6/7] [PATCH] af_iucv: do not call iucv_sock_kill() twice
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
                   ` (4 preceding siblings ...)
  2009-09-16 14:37 ` [patch 5/7] [PATCH] af_iucv: handle non-accepted sockets after resuming from suspend Ursula Braun
@ 2009-09-16 14:37 ` Ursula Braun
  2009-09-16 14:37 ` [patch 7/7] [PATCH] af_iucv: fix race when queueing skbs on the backlog queue Ursula Braun
  2009-09-17  3:58 ` [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ David Miller
  7 siblings, 0 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390
  Cc: schwidefsky, heiko.carstens, Hendrik Brueckner, Ursula Braun

[-- Attachment #1: 606-af_iucv-sock-kill.diff --]
[-- Type: text/plain, Size: 3883 bytes --]

From: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>

For non-accepted sockets on the accept queue, iucv_sock_kill()
is called twice (in iucv_sock_close() and iucv_sock_cleanup_listen()).
This typically results in a kernel oops as shown below.

Remove the duplicate call to iucv_sock_kill() and set the SOCK_ZAPPED
flag in iucv_sock_close() only.

The iucv_sock_kill() function frees a socket only if the socket is zapped
and orphaned (sk->sk_socket == NULL):
  - Non-accepted sockets are always orphaned and, thus, iucv_sock_kill()
    frees the socket twice.
  - For accepted sockets or sockets created with iucv_sock_create(),
    sk->sk_socket is initialized. This caused the first call to
    iucv_sock_kill() to return immediately. To free these sockets,
    iucv_sock_release() uses sock_orphan() before calling iucv_sock_kill().

<1>Unable to handle kernel pointer dereference at virtual kernel address 000000003edd3000
<4>Oops: 0011 [#1] PREEMPT SMP DEBUG_PAGEALLOC
<4>Modules linked in: af_iucv sunrpc qeth_l3 dm_multipath dm_mod qeth vmur ccwgroup
<4>CPU: 0 Not tainted 2.6.30 #4
<4>Process iucv_sock_close (pid: 2486, task: 000000003aea4340, ksp: 000000003b75bc68)
<4>Krnl PSW : 0704200180000000 000003e00168e23a (iucv_sock_kill+0x2e/0xcc [af_iucv])
<4>           R:0 T:1 IO:1 EX:1 Key:0 M:1 W:0 P:0 AS:0 CC:2 PM:0 EA:3
<4>Krnl GPRS: 0000000000000000 000000003b75c000 000000003edd37f0 0000000000000001
<4>           000003e00168ec62 000000003988d960 0000000000000000 000003e0016b0608
<4>           000000003fe81b20 000000003839bb58 00000000399977f0 000000003edd37f0
<4>           000003e00168b000 000003e00168f138 000000003b75bcd0 000000003b75bc98
<4>Krnl Code: 000003e00168e22a: c0c0ffffe6eb	larl	%r12,3e00168b000
<4>           000003e00168e230: b90400b2		lgr	%r11,%r2
<4>           000003e00168e234: e3e0f0980024	stg	%r14,152(%r15)
<4>          >000003e00168e23a: e310225e0090	llgc	%r1,606(%r2)
<4>           000003e00168e240: a7110001		tmll	%r1,1
<4>           000003e00168e244: a7840007		brc	8,3e00168e252
<4>           000003e00168e248: d507d00023c8	clc	0(8,%r13),968(%r2)
<4>           000003e00168e24e: a7840009		brc	8,3e00168e260
<4>Call Trace:
<4>([<000003e0016b0608>] afiucv_dbf+0x0/0xfffffffffffdea20 [af_iucv])
<4> [<000003e00168ec6c>] iucv_sock_close+0x130/0x368 [af_iucv]
<4> [<000003e00168ef02>] iucv_sock_release+0x5e/0xe4 [af_iucv]
<4> [<0000000000438e6c>] sock_release+0x44/0x104
<4> [<0000000000438f5e>] sock_close+0x32/0x50
<4> [<0000000000207898>] __fput+0xf4/0x250
<4> [<00000000002038aa>] filp_close+0x7a/0xa8
<4> [<00000000002039ba>] SyS_close+0xe2/0x148
<4> [<0000000000117c8e>] sysc_noemu+0x10/0x16
<4> [<00000042ff8deeac>] 0x42ff8deeac

Signed-off-by: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>
Signed-off-by: Ursula Braun <ursula.braun@de.ibm.com>
---

 net/iucv/af_iucv.c |   10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

Index: linux-2.6-uschi/net/iucv/af_iucv.c
===================================================================
--- linux-2.6-uschi.orig/net/iucv/af_iucv.c
+++ linux-2.6-uschi/net/iucv/af_iucv.c
@@ -361,10 +361,9 @@ static void iucv_sock_cleanup_listen(str
 	}
 
 	parent->sk_state = IUCV_CLOSED;
-	sock_set_flag(parent, SOCK_ZAPPED);
 }
 
-/* Kill socket */
+/* Kill socket (only if zapped and orphaned) */
 static void iucv_sock_kill(struct sock *sk)
 {
 	if (!sock_flag(sk, SOCK_ZAPPED) || sk->sk_socket)
@@ -426,17 +425,18 @@ static void iucv_sock_close(struct sock 
 
 		skb_queue_purge(&iucv->send_skb_q);
 		skb_queue_purge(&iucv->backlog_skb_q);
-
-		sock_set_flag(sk, SOCK_ZAPPED);
 		break;
 
 	default:
 		sock_set_flag(sk, SOCK_ZAPPED);
+		/* nothing to do here */
 		break;
 	}
 
+	/* mark socket for deletion by iucv_sock_kill() */
+	sock_set_flag(sk, SOCK_ZAPPED);
+
 	release_sock(sk);
-	iucv_sock_kill(sk);
 }
 
 static void iucv_sock_init(struct sock *sk, struct sock *parent)


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [patch 7/7] [PATCH] af_iucv: fix race when queueing skbs on the backlog queue
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
                   ` (5 preceding siblings ...)
  2009-09-16 14:37 ` [patch 6/7] [PATCH] af_iucv: do not call iucv_sock_kill() twice Ursula Braun
@ 2009-09-16 14:37 ` Ursula Braun
  2009-09-17  3:58 ` [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ David Miller
  7 siblings, 0 replies; 9+ messages in thread
From: Ursula Braun @ 2009-09-16 14:37 UTC (permalink / raw)
  To: davem, netdev, linux-s390
  Cc: schwidefsky, heiko.carstens, Hendrik Brueckner, Ursula Braun

[-- Attachment #1: 607-af_iucv-backlog-queue.diff --]
[-- Type: text/plain, Size: 4785 bytes --]

From: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>

iucv_sock_recvmsg() and iucv_process_message()/iucv_fragment_skb race
for dequeuing an skb from the backlog queue.

If iucv_sock_recvmsg() dequeues first, iucv_process_message() calls
sock_queue_rcv_skb() with an skb that is NULL.

This results in the following kernel panic:

<1>Unable to handle kernel pointer dereference at virtual kernel address (null)
<4>Oops: 0004 [#1] PREEMPT SMP DEBUG_PAGEALLOC
<4>Modules linked in: af_iucv sunrpc qeth_l3 dm_multipath dm_mod vmur qeth ccwgroup
<4>CPU: 0 Not tainted 2.6.30 #4
<4>Process client-iucv (pid: 4787, task: 0000000034e75940, ksp: 00000000353e3710)
<4>Krnl PSW : 0704000180000000 000000000043ebca (sock_queue_rcv_skb+0x7a/0x138)
<4>           R:0 T:1 IO:1 EX:1 Key:0 M:1 W:0 P:0 AS:0 CC:0 PM:0 EA:3
<4>Krnl GPRS: 0052900000000000 000003e0016e0fe8 0000000000000000 0000000000000000
<4>           000000000043eba8 0000000000000002 0000000000000001 00000000341aa7f0
<4>           0000000000000000 0000000000007800 0000000000000000 0000000000000000
<4>           00000000341aa7f0 0000000000594650 000000000043eba8 000000003fc2fb28
<4>Krnl Code: 000000000043ebbe: a7840006            brc     8,43ebca
<4>           000000000043ebc2: 5930c23c            c       %r3,572(%r12)
<4>           000000000043ebc6: a724004c            brc     2,43ec5e
<4>          >000000000043ebca: e3c0b0100024        stg     %r12,16(%r11)
<4>           000000000043ebd0: a7190000            lghi    %r1,0
<4>           000000000043ebd4: e310b0200024        stg     %r1,32(%r11)
<4>           000000000043ebda: c010ffffdce9        larl    %r1,43a5ac
<4>           000000000043ebe0: e310b0800024        stg     %r1,128(%r11)
<4>Call Trace:
<4>([<000000000043eba8>] sock_queue_rcv_skb+0x58/0x138)
<4> [<000003e0016bcf2a>] iucv_process_message+0x112/0x3cc [af_iucv]
<4> [<000003e0016bd3d4>] iucv_callback_rx+0x1f0/0x274 [af_iucv]
<4> [<000000000053a21a>] iucv_message_pending+0xa2/0x120
<4> [<000000000053b5a6>] iucv_tasklet_fn+0x176/0x1b8
<4> [<000000000014fa82>] tasklet_action+0xfe/0x1f4
<4> [<0000000000150a56>] __do_softirq+0x116/0x284
<4> [<0000000000111058>] do_softirq+0xe4/0xe8
<4> [<00000000001504ba>] irq_exit+0xba/0xd8
<4> [<000000000010e0b2>] do_extint+0x146/0x190
<4> [<00000000001184b6>] ext_no_vtime+0x1e/0x22
<4> [<00000000001fbf4e>] kfree+0x202/0x28c
<4>([<00000000001fbf44>] kfree+0x1f8/0x28c)
<4> [<000000000044205a>] __kfree_skb+0x32/0x124
<4> [<000003e0016bd8b2>] iucv_sock_recvmsg+0x236/0x41c [af_iucv]
<4> [<0000000000437042>] sock_aio_read+0x136/0x160
<4> [<0000000000205e50>] do_sync_read+0xe4/0x13c
<4> [<0000000000206dce>] vfs_read+0x152/0x15c
<4> [<0000000000206ed0>] SyS_read+0x54/0xac
<4> [<0000000000117c8e>] sysc_noemu+0x10/0x16
<4> [<00000042ff8def3c>] 0x42ff8def3c

Signed-off-by: Hendrik Brueckner <brueckner@linux.vnet.ibm.com>
Signed-off-by: Ursula Braun <ursula.braun@de.ibm.com>
---

 net/iucv/af_iucv.c |   16 ++++++++++++++--
 1 file changed, 14 insertions(+), 2 deletions(-)

Index: linux-2.6-uschi/net/iucv/af_iucv.c
===================================================================
--- linux-2.6-uschi.orig/net/iucv/af_iucv.c
+++ linux-2.6-uschi/net/iucv/af_iucv.c
@@ -1036,6 +1036,10 @@ out:
 	return err;
 }
 
+/* iucv_fragment_skb() - Fragment a single IUCV message into multiple skb's
+ *
+ * Locking: must be called with message_q.lock held
+ */
 static int iucv_fragment_skb(struct sock *sk, struct sk_buff *skb, int len)
 {
 	int dataleft, size, copied = 0;
@@ -1070,6 +1074,10 @@ static int iucv_fragment_skb(struct sock
 	return 0;
 }
 
+/* iucv_process_message() - Receive a single outstanding IUCV message
+ *
+ * Locking: must be called with message_q.lock held
+ */
 static void iucv_process_message(struct sock *sk, struct sk_buff *skb,
 				 struct iucv_path *path,
 				 struct iucv_message *msg)
@@ -1120,6 +1128,10 @@ static void iucv_process_message(struct 
 		skb_queue_head(&iucv_sk(sk)->backlog_skb_q, skb);
 }
 
+/* iucv_process_message_q() - Process outstanding IUCV messages
+ *
+ * Locking: must be called with message_q.lock held
+ */
 static void iucv_process_message_q(struct sock *sk)
 {
 	struct iucv_sock *iucv = iucv_sk(sk);
@@ -1210,6 +1222,7 @@ static int iucv_sock_recvmsg(struct kioc
 		kfree_skb(skb);
 
 		/* Queue backlog skbs */
+		spin_lock_bh(&iucv->message_q.lock);
 		rskb = skb_dequeue(&iucv->backlog_skb_q);
 		while (rskb) {
 			if (sock_queue_rcv_skb(sk, rskb)) {
@@ -1221,11 +1234,10 @@ static int iucv_sock_recvmsg(struct kioc
 			}
 		}
 		if (skb_queue_empty(&iucv->backlog_skb_q)) {
-			spin_lock_bh(&iucv->message_q.lock);
 			if (!list_empty(&iucv->message_q.list))
 				iucv_process_message_q(sk);
-			spin_unlock_bh(&iucv->message_q.lock);
 		}
+		spin_unlock_bh(&iucv->message_q.lock);
 	}
 
 done:


^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+
  2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
                   ` (6 preceding siblings ...)
  2009-09-16 14:37 ` [patch 7/7] [PATCH] af_iucv: fix race when queueing skbs on the backlog queue Ursula Braun
@ 2009-09-17  3:58 ` David Miller
  7 siblings, 0 replies; 9+ messages in thread
From: David Miller @ 2009-09-17  3:58 UTC (permalink / raw)
  To: ursula.braun; +Cc: netdev, linux-s390, schwidefsky, heiko.carstens

From: Ursula Braun <ursula.braun@de.ibm.com>
Date: Wed, 16 Sep 2009 16:37:21 +0200

> Summary:
> 
> Ursula Braun (1)
> iucv: suspend/resume error msg for left over pathes
> 
> Hendrik Brueckner (6)
> iucv: fix iucv_buffer_cpumask check when calling IUCV functions
> iucv: use correct output register in iucv_query_maxconn()
> af_iucv: fix race in __iucv_sock_wait()
> af_iucv: handle non-accepted sockets after resuming from suspend
> af_iucv: do not call iucv_sock_kill() twice
> af_iucv: fix race when queueing skbs on the backlog queue

All applied, thank you.

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2009-09-17  3:57 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2009-09-16 14:37 [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ Ursula Braun
2009-09-16 14:37 ` [patch 1/7] [PATCH] iucv: suspend/resume error msg for left over pathes Ursula Braun
2009-09-16 14:37 ` [patch 2/7] [PATCH] iucv: fix iucv_buffer_cpumask check when calling IUCV functions Ursula Braun
2009-09-16 14:37 ` [patch 3/7] [PATCH] iucv: use correct output register in iucv_query_maxconn() Ursula Braun
2009-09-16 14:37 ` [patch 4/7] [PATCH] af_iucv: fix race in __iucv_sock_wait() Ursula Braun
2009-09-16 14:37 ` [patch 5/7] [PATCH] af_iucv: handle non-accepted sockets after resuming from suspend Ursula Braun
2009-09-16 14:37 ` [patch 6/7] [PATCH] af_iucv: do not call iucv_sock_kill() twice Ursula Braun
2009-09-16 14:37 ` [patch 7/7] [PATCH] af_iucv: fix race when queueing skbs on the backlog queue Ursula Braun
2009-09-17  3:58 ` [patch 0/7] s390: iucv / af_iucv fixes for 2.6.31+ David Miller

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.