|
From: <sv...@va...> - 2014-07-31 19:21:17
|
Author: florian
Date: Thu Jul 31 19:21:07 2014
New Revision: 14220
Log:
Fix VG_(percentify) to some extent.
- for m == 0, the computed format string was incorrect
- ULong value requires %llu format, UInt needs %u
The function has other issues:
- The computation of p1 and p2 will overflow for certain value
combinations e.g. n = ULONG_MAX and m = 1.
- It is unsafe to use sprintf.
- The width of the result into which the numbers will be right justified
is coupled to the size of the buffer. That is not always desirable.
- The size of the buffer should be at least 20 + 1 + d + 1 + 1 so no
overrun will ever occur for all possible input values.
I'm not going to tackle this. The proper fix is to add light-weight
support for writing floating point numbers to the printf machinery.
Modified:
branches/BUF_REMOVAL/coregrind/m_libcprint.c
Modified: branches/BUF_REMOVAL/coregrind/m_libcprint.c
==============================================================================
--- branches/BUF_REMOVAL/coregrind/m_libcprint.c (original)
+++ branches/BUF_REMOVAL/coregrind/m_libcprint.c Thu Jul 31 19:21:07 2014
@@ -293,12 +293,12 @@
{
Int i, len, space;
ULong p1;
- HChar fmt[32];
+ HChar fmt[32]; // large enough
if (m == 0) {
// Have to generate the format string in order to be flexible about
// the width of the field.
- VG_(sprintf)(fmt, "%%-%ds", n_buf);
+ VG_(sprintf)(fmt, "%%%ds", n_buf);
// fmt is now "%<n_buf>s" where <d> is 1,2,3...
VG_(sprintf)(buf, fmt, "--%");
return;
@@ -307,7 +307,7 @@
p1 = (100*n) / m;
if (d == 0) {
- VG_(sprintf)(buf, "%lld%%", p1);
+ VG_(sprintf)(buf, "%lld%%", p1); // FIXME: unsafe
} else {
ULong p2;
UInt ex;
@@ -320,9 +320,9 @@
p2 = ((100*n*ex) / m) % ex;
// Have to generate the format string in order to be flexible about
// the width of the post-decimal-point part.
- VG_(sprintf)(fmt, "%%lld.%%0%dlld%%%%", d);
+ VG_(sprintf)(fmt, "%%llu.%%0%ullu%%%%", d);
// fmt is now "%lld.%0<d>lld%%" where <d> is 1,2,3...
- VG_(sprintf)(buf, fmt, p1, p2);
+ VG_(sprintf)(buf, fmt, p1, p2); // FIXME: unsafe
}
len = VG_(strlen)(buf);
|