mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: ebiederm@xmission.com (Eric W. Biederman)
To: Lucas De Marchi <lucas.demarchi@profusion.mobi>
Cc: Al Viro <viro@zeniv.linux.org.uk>,
	Linus Torvalds <torvalds@linux-foundation.org>,
	Dave Jones <davej@redhat.com>,
	Linux Kernel <linux-kernel@vger.kernel.org>,
	Andrew Morton <akpm@linux-foundation.org>
Subject: Re: [3.3-rc7] sys_poll use after free (hibernate)
Date: Thu, 22 Mar 2012 16:02:46 -0700	[thread overview]
Message-ID: <m1ehskxmqx.fsf@fess.ebiederm.org> (raw)
In-Reply-To: <CAMOw1v4gszzV7F3z1m+RWEe9UDgR2Jrp9wX_w9z_1UkXT=FL5Q@mail.gmail.com> (Lucas De Marchi's message of "Thu, 22 Mar 2012 19:12:26 -0300")

Lucas De Marchi <lucas.demarchi@profusion.mobi> writes:

> On Thu, Mar 22, 2012 at 6:31 PM, Eric W. Biederman

>> It looks like it was a combination of the fuzzer doing silly things
>> and a removed ctl_table entry being poisoned and having .poll set
>> to 6b6b6b6b6b6b6b6b so the guard against calling poll when it is
>> nonsense did not trigger.  So your patch should be sufficient
>> for now.
>
> What I understood afterwards was:
>
> 1. fuzzer calling poll() on files that did support poll
> 2. modules that created that sysctl entries were removed
> 3. 'table' was entirely removed (not ->poll).

I just grepped the kernel for ctl_table_poll and DEFINE_CTL_TABLE_POLL.
There are only the two original users of hostname and domainname.

The problem very much had to be that ctl_table was freed and poisoned
but we still pointed to it, and we were not using the grab_header idiom
to ensure we did not use an expired ctl_table entry.

Which means that it was any ctl_table being add/removed.  Probably in
this case the per cpu scheduler sysctl table entries that get
added/removed whenever we logically add/remove a cpu.

I expect what happened is that the fuzzer opened the sysctl file some
time before it was removed and then sometime after the entry was removed
(but before the memory was reused) called select/poll on that file
descriptor.  Since the ctl_table was poisoned ->poll was
6b6b6b6b6b6b6b6b and so we passed the checks for a non NULL ->poll and
we proceed to do nonsense things that caused the kernel oops in
proc_sys_poll.

>> Long term we still need a version of poll that is safe to use
>> with modules.
>
> I think the way it's now (with my patch taken by Andrew) is safe for
> having poll() with modules.

No it is not.

The problem is that proc_sys_poll is non-blocking.  It is called
primarily to place the system on a wait queue.  But notice that
if you place the caller on a wait_queue in proc_sys_poll and return
then we may call unregister_sysctl_table while and remove the sysctl
while someone still is on the wait queue.  Sleeping on a wait_queue
that has been freed is so bizarre I don't want to think about the
failure modes.

sysfs solves this problem by tracking openers and has it's wait_queue in
the per opener structure.  That same logic needs to be mirrored in
sysctl for poll to be safe on any sysctl table entry that can be
removed.

I believe a correct fix would remove the .poll field in struct ctl_table,
remove struct ctl_table_poll entirely and modify the signature of
proc_sys_poll_notify to be:
void proc_sys_poll_notify(struct ctl_table_header *head, struct ctl_table *table);

Eric

  reply	other threads:[~2012-03-22 22:59 UTC|newest]

Thread overview: 18+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2012-03-13  0:58 Dave Jones
2012-03-18 19:02 ` Linus Torvalds
2012-03-18 19:27   ` Al Viro
2012-03-19  8:17     ` Alexey Dobriyan
2012-03-20  6:08     ` Lucas De Marchi
2012-03-20 18:29       ` [PATCH] sysctl: protect poll() in entries that may go away Lucas De Marchi
2012-03-22 21:31       ` [3.3-rc7] sys_poll use after free (hibernate) Eric W. Biederman
2012-03-22 22:12         ` Lucas De Marchi
2012-03-22 23:02           ` Eric W. Biederman [this message]
2012-03-24  0:25           ` [REVIEW][PATCH] Making poll generally useful for sysctls Eric W. Biederman
2012-03-24  6:20             ` Lucas De Marchi
2012-03-24  7:58               ` Eric W. Biederman
2012-03-26 17:44                 ` Lucas De Marchi
2012-03-27  4:02                   ` Lucas De Marchi
2012-03-28  2:00                     ` Eric W. Biederman
2012-03-22 22:24     ` [3.3-rc7] sys_poll use after free (hibernate) Eric W. Biederman
2012-03-18 19:47 ` richard -rw- weinberger
2012-03-18 21:24   ` Dave Jones

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=m1ehskxmqx.fsf@fess.ebiederm.org \
    --to=ebiederm@xmission.com \
    --cc=akpm@linux-foundation.org \
    --cc=davej@redhat.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=lucas.demarchi@profusion.mobi \
    --cc=torvalds@linux-foundation.org \
    --cc=viro@zeniv.linux.org.uk \
    /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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

Powered by JetHome