Re: Performance improvements for src/port/snprintf.c
Tom Lane <tgl@sss.pgh.pa.us>
From: Tom Lane <tgl@sss.pgh.pa.us>
To: Andres Freund <andres@anarazel.de>
Cc: pgsql-hackers@lists.postgresql.org,
Thomas Munro <thomas.munro@enterprisedb.com>,
Andrew Gierth <andrew@tao11.riddles.org.uk>,
Alexander Kuzmenkov <a.kuzmenkov@postgrespro.ru>
Date: 2018-10-03T16:43:26Z
Lists: pgsql-hackers
Andres Freund <andres@anarazel.de> writes: > On 2018-10-03 11:59:27 -0400, Tom Lane wrote: >> I experimented with adding an initial check for "format is exactly %s" >> at the top of dopr(), and couldn't get excited about that. Instrumenting >> things showed that the optimization fired in only 1.8% of the calls >> during a run of our core regression tests. Now, that might not count >> as a really representative workload, but it doesn't make me think that >> the case is worth optimizing for us. > Seems right. I also have a hard time to believe that any of those "%s" > printfs are performance critical - we'd hopefully just have avoided the > sprintf in that case. Yup, that's probably a good chunk of the reason why there aren't very many. But we *do* use %s a lot to assemble multiple strings or combine them with fixed text, which is why the other form of the optimization is useful. >> But then it occurred to me that there's more than one way to skin this >> cat. We could, for an even cheaper extra test, detect that any one >> format specifier is just "%s", and use the same kind of fast-path >> within the loop. With the same sort of instrumentation, I found that >> a full 45% of the format specs executed in the core regression tests >> are just %s. That makes me think that a patch along the lines of the >> attached is a good win for our use-cases. Comparing to Fedora 28's >> glibc, this gets us to > Hm, especially if we special case the float->string conversions directly > at the hot callsites, that seems reasonable. I kinda wish we could just > easily move the format string processing to compile-time, but given > translatability that won't be widely possible even if it were otherwise > feasible. Yeah, there's a mighty big pile of infrastructure that depends on the way *printf works. I agree that one way or another we're going to be special-casing float8out and float4out. BTW, I poked around in the related glibc sources the other day, and it seemed like they are doing some sort of quasi-compilation of format strings. I couldn't figure out how they made it pay, though --- without some way to avoid re-compiling the same format string over and over, seems like it couldn't net out as a win. But if they are avoiding that, I didn't find where. regards, tom lane
Commits
-
Improve snprintf.c's handling of NaN, Infinity, and minus zero.
- 6eb3eb577d76 12.0 landed
-
Rationalize snprintf.c's handling of "ll" formats.
- 595a0eab7f42 12.0 landed
-
Provide fast path in snprintf.c for conversion specs that are just "%s".
- 6d842be6c118 12.0 landed
-
Make assorted performance improvements in snprintf.c.
- abd9ca377d66 12.0 landed
-
Set snprintf.c's maximum number of NL arguments to be 31.
- 625b38ea0e98 12.0 cited
-
Always use our own versions of *printf().
- 96bf88d52711 12.0 cited