From: Rasmus Villemoes <linux@rasmusvillemoes.dk>
To: Ingo Molnar <mingo@kernel.org>
Cc: Linus Torvalds <torvalds@linux-foundation.org>,
Chris Metcalf <cmetcalf@ezchip.com>,
open list <linux-kernel@vger.kernel.org>,
Peter Zijlstra <a.p.zijlstra@chello.nl>,
Thomas Gleixner <tglx@linutronix.de>,
"H. Peter Anvin" <hpa@zytor.com>, Borislav Petkov <bp@alien8.de>
Subject: Re: [PATCH] string: Improve the generic strlcpy() implementation
Date: Wed, 07 Oct 2015 11:04:36 +0200 [thread overview]
Message-ID: <87y4ffuk0r.fsf@rasmusvillemoes.dk> (raw)
In-Reply-To: <20151007071821.GD7837@gmail.com> (Ingo Molnar's message of "Wed, 7 Oct 2015 09:18:21 +0200")
On Wed, Oct 07 2015, Ingo Molnar <mingo@kernel.org> wrote:
> We have procfs and sysfs as well, where format strings are indeed dominant, but
> are you sure this race exists in snprintf() in that form? I.e. can the return
> value of snprintf() be different from the true length of the output string, if the
> source string is modified in parallel?
Well, if truncation has happened the return value is different
(larger). But assuming the output buffer is large enough, the 'compute
strlen, then do copying, potentially copying a nul byte which wasn't
there moments before' is pretty obvious:
lib/vsprintf.c:
static noinline_for_stack
char *string(char *buf, char *end, const char *s, struct printf_spec spec)
{
int len, i;
if ((unsigned long)s < PAGE_SIZE)
s = "(null)";
len = strnlen(s, spec.precision);
if (!(spec.flags & LEFT)) {
while (len < spec.field_width--) {
if (buf < end)
*buf = ' ';
++buf;
}
}
for (i = 0; i < len; ++i) {
if (buf < end)
*buf = *s;
++buf; ++s;
}
while (len < spec.field_width--) {
if (buf < end)
*buf = ' ';
++buf;
}
return buf;
}
(spec.precision is an s16 which by default is set to -1, so for the
usual case of plain %s the upper bound in strnlen is (size_t)-1,
effectively infinity). If it wasn't for the field width padding it would
probably not be that hard to fix.
But, to rephrase an earlier question: Can anyone point to an instance
where the strlcpy source or a %s argument to a printf function can
actually change under us? I'd like to see if one can intentionally
trigger the potential race, but I suspect that the vast majority cannot
have a problem - maybe someone has an idea of specific places that are
worth looking at.
>> > So I'd improve it all in the following order:
>> >
>> > - fix the strscpy() uninitialized use
>> >
>> > - base strlcpy() on strscpy() via the patch I sent. This makes all users faster
>> > and eliminates the theoretical race.
>>
>> I'm not so sure about that part. I'd strongly suspect that the vast
>> majority of strings handled by strlcpy (and in the future strscpy) are
>> shorter than 32 bytes, so is all the word_at_a_time and pre/post
>> alignment yoga really worth it?
>
> That's a good question, I'll measure it.
Here's a few pseudo-datapoints. About half the strlcpy instances (just
from lazy grepping) has a string literal as src, and those only have
about 1/8th chance of being aligned. A quick skim through a small
vmlinux showed 34 calls of strlcpy where %rsi was easily seen to be a
literal address, of which 7 were aligned. That's 1/5, but the sample
size is rather small (also, the 1/8 is admittedly an underestimate,
since gcc seems to put long enough literals in rodata.str1.8).
Rasmus
next prev parent reply other threads:[~2015-10-07 9:04 UTC|newest]
Thread overview: 34+ messages / expand[flat|nested] mbox.gz Atom feed top
2015-09-10 19:43 [GIT PULL] strscpy string copy function Chris Metcalf
2015-10-04 15:55 ` Linus Torvalds
2015-10-05 11:27 ` [PATCH] string: Improve the generic strlcpy() implementation Ingo Molnar
2015-10-05 11:53 ` Ingo Molnar
2015-10-05 13:15 ` Ingo Molnar
2015-10-05 14:04 ` Ingo Molnar
[not found] ` <CA+55aFx2McOeEiB7fJ-BV=vBsH=i2cC-qW8_EBEnScfQhugD_w@mail.gmail.com>
2015-10-05 14:07 ` Ingo Molnar
2015-10-05 14:33 ` Ingo Molnar
2015-10-05 15:32 ` Linus Torvalds
2015-10-05 16:03 ` Ingo Molnar
2015-10-05 12:28 ` Linus Torvalds
2015-10-05 13:10 ` Ingo Molnar
2015-10-05 22:28 ` Rasmus Villemoes
2015-10-06 7:54 ` Ingo Molnar
2015-10-06 8:03 ` Ingo Molnar
2015-10-06 22:00 ` Rasmus Villemoes
2015-10-07 7:18 ` Ingo Molnar
2015-10-07 9:04 ` Rasmus Villemoes [this message]
2015-10-07 9:22 ` Linus Torvalds
2015-10-08 8:48 ` Ingo Molnar
2015-10-09 8:10 ` Rasmus Villemoes
2015-10-09 9:10 ` [RFC 0/3] eliminate potential race in string() (was: [PATCH] string: Improve the generic strlcpy() implementation) Rasmus Villemoes
2015-10-09 9:14 ` [RFC 1/3] lib/vsprintf.c: pull out padding code from dentry_name() Rasmus Villemoes
2015-10-09 9:14 ` [RFC 2/3] lib/vsprintf.c: move string() below widen_string() Rasmus Villemoes
2015-10-09 9:14 ` [RFC 3/3] lib/vsprintf.c: eliminate potential race in string() Rasmus Villemoes
2015-10-10 7:47 ` [RFC 0/3] eliminate potential race in string() (was: [PATCH] string: Improve the generic strlcpy() implementation) Ingo Molnar
2015-10-19 12:42 ` [PATCH] string: Improve the generic strlcpy() implementation Rasmus Villemoes
2015-10-19 16:24 ` Chris Metcalf
2015-10-05 15:38 Alexey Dobriyan
2015-10-05 16:11 ` Ingo Molnar
2015-10-05 16:13 ` Ingo Molnar
[not found] ` <CA+55aFyTVJfCt00gYJpiQW5kqPaRGJ93JmfRRni-73zCf5ivqg@mail.gmail.com>
2015-10-05 16:22 ` Ingo Molnar
2015-10-05 16:28 ` Ingo Molnar
2015-10-05 20:40 ` Linus Torvalds
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=87y4ffuk0r.fsf@rasmusvillemoes.dk \
--to=linux@rasmusvillemoes.dk \
--cc=a.p.zijlstra@chello.nl \
--cc=bp@alien8.de \
--cc=cmetcalf@ezchip.com \
--cc=hpa@zytor.com \
--cc=linux-kernel@vger.kernel.org \
--cc=mingo@kernel.org \
--cc=tglx@linutronix.de \
--cc=torvalds@linux-foundation.org \
/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