All of lore.kernel.org
 help / color / mirror / Atom feed
From: Andrew Morton <akpm@zip.com.au>
To: Robert Love <rml@tech9.net>
Cc: Linus Torvalds <torvalds@transmeta.com>,
	Dave Hansen <haveblue@us.ibm.com>,
	"Adam J. Richter" <adam@yggdrasil.com>,
	linux-kernel@vger.kernel.org
Subject: Re: Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() atboot  time
Date: Thu, 04 Apr 2002 12:54:12 -0800	[thread overview]
Message-ID: <3CACBD74.FAED4B72@zip.com.au> (raw)
In-Reply-To: <Pine.LNX.4.33.0204041113410.12895-100000@penguin.transmeta.com> <1017948383.22303.537.camel@phantasy>

Robert Love wrote:
> 
> ...
> Do you think it is better to deny preemption if state==TASK_ZOMBIE (note
> this requires code in preempt_schedule and the interrupt return path,
> since Ingo decoupled the two) or just disable preemption around critical
> regions caused by setting state to TASK_ZOMBIE ?
> 
> I suspect this is the first occurrence of a problem of this kind ... and
> the attached patch handles it.
> 

No, the problem goes deeper than this.

I have code which does, effectively:

sleeper()
{
	spin_lock(&some_lock);
	set_current_state(TASK_UNINTERRUPTIBLE);
	some_flag = 0;
	spin_unlock(&lock);
	schedule();
	if (some_flag == 0)
		i_am_horribly_confused();
}

waker()
{
	spin_lock(&some_lock);
	some_flag = 1;
	wake_up_process(sleeper);
	spin_unlock(&some_lock);
}

or something like that.  See __pdflush() and 
pdflush_operation() in http://www.zip.com.au/~akpm/linux/patches/2.5/2.5.8-pre1/delalloc/dallocbase-60-pdflush.patch

The above code work fine, is nice and I want to keep
it that way.  But it fails on preempt.

The spin_unlock() in sleeper() can sometimes set
task->state to TASK_RUNNING(), so my schedule() call
just falls straight through.

Probably nobody has noticed this in other places because
most sleep/wakeup stuff tends to be done inside a loop;
the bogus "wakeup" is ignored.

Although it can be worked around at the call site, I
think this needs fixing.  Otherwise we have the rule
"spin_unlock will flip you into TASK_RUNNING 0.0001%
of the time if CONFIG_PREEMPT=y".  ug.

I have thought deeply about this, and I then promptly
forgot everything I thought about, but I ended up
concluding that the sanest way of resolving this is
inside __set_current_state().  If the new state is
TASK_RUNNING and the old state is not TASK_RUNNING
then enable preemption, call schedule() if necessary, etc.

It is not acceptable to just say "don't preempt a task
which is not in state TASK_RUNNING", because if an
interrupt happens against a CPU which is running a task
which is in state TASK_INTERRUPTIBLE (say), then that
wakeup won't be serviced until the task exits the kernel.

-

  parent reply	other threads:[~2002-04-04 20:55 UTC|newest]

Thread overview: 30+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2002-04-04 11:59 Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() at boot time Adam J. Richter
2002-04-04 12:56 ` Stelian Pop
2002-04-04 13:40   ` Alessandro Suardi
2002-04-04 16:23 ` David C. Hansen
2002-04-04 18:28   ` Dave Hansen
2002-04-04 18:51     ` Robert Love
2002-04-04 19:14       ` Linus Torvalds
2002-04-04 19:26         ` Robert Love
2002-04-04 19:41           ` Dave Hansen
2002-04-04 20:02             ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() atboot time george anzinger
2002-04-04 20:54           ` Andrew Morton [this message]
2002-04-04 21:34           ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() at boot time Roger Larsson
2002-04-04 22:38             ` Andrew Morton
2002-04-04 22:42               ` Linus Torvalds
2002-04-04 22:54                 ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() atboot time Andrew Morton
2002-04-04 23:07                 ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() at boot time Robert Love
2002-04-04 23:42                   ` Linus Torvalds
2002-04-04 23:47                     ` Robert Love
2002-04-04 23:55                       ` Linus Torvalds
2002-04-05  0:03                         ` [PATCH] preemptive kernel behavior change: don't be rude Robert Love
2002-04-05  1:51                           ` george anzinger
2002-04-05  2:06                             ` Robert Love
2002-04-04 22:55               ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() at boot time Robert Love
2002-04-04 23:10                 ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() atboot time Andrew Morton
2002-04-04 23:16                   ` Robert Love
2002-04-04 19:13     ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() at boot time Linus Torvalds
2002-04-04 19:16       ` Robert Love
2002-04-04 19:45         ` Linus Torvalds
2002-04-04 20:09           ` Patch: linux-2.5.8-pre1/kernel/exit.c change caused BUG() atboot time george anzinger
2002-04-04 19:48       ` george anzinger

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=3CACBD74.FAED4B72@zip.com.au \
    --to=akpm@zip.com.au \
    --cc=adam@yggdrasil.com \
    --cc=haveblue@us.ibm.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=rml@tech9.net \
    --cc=torvalds@transmeta.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
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.