Extend IntegerFormatter to handle non-hexadecimal properly.

- When asking for signed/unsigned, IntegerFormatter was previously
  treating all value types as int64, which would result in much larger
  than expected values in the variable list in some cases. Inspect the actual
  integer type of the variable and adjust the format string accordingly in
  order to deal with that.
This commit is contained in:
Rene Gollent
2012-07-13 21:04:50 -04:00
parent f55410e169
commit 89149ce667
+95 -25
View File
@@ -1,5 +1,6 @@
/*
* Copyright 2009, Ingo Weinhold, [email protected].
* Copyright 2012, Rene Gollent, [email protected].
* Distributed under the terms of the MIT License.
*/
@@ -7,10 +8,88 @@
#include "IntegerFormatter.h"
#include <stdio.h>
#include <string.h>
#include <TypeConstants.h>
static integer_format
GetFormatForTypeAndFormat(type_code type, integer_format format,
char* _formatString, int formatSize)
{
integer_format result = format;
_formatString[0] = '%';
++_formatString;
formatSize -= 1;
switch (type) {
case B_INT8_TYPE:
switch (format) {
case INTEGER_FORMAT_HEX_DEFAULT:
result = INTEGER_FORMAT_HEX_8;
break;
case INTEGER_FORMAT_SIGNED:
strlcpy(_formatString, B_PRId8, formatSize);
break;
case INTEGER_FORMAT_UNSIGNED:
strlcpy(_formatString, B_PRIu8, formatSize);
break;
default:
break;
}
break;
case B_INT16_TYPE:
switch (format) {
case INTEGER_FORMAT_HEX_DEFAULT:
result = INTEGER_FORMAT_HEX_16;
break;
case INTEGER_FORMAT_SIGNED:
strlcpy(_formatString, B_PRId16, formatSize);
break;
case INTEGER_FORMAT_UNSIGNED:
strlcpy(_formatString, B_PRIu16, formatSize);
break;
default:
break;
}
break;
case B_INT32_TYPE:
switch (format) {
case INTEGER_FORMAT_HEX_DEFAULT:
result = INTEGER_FORMAT_HEX_32;
break;
case INTEGER_FORMAT_SIGNED:
strlcpy(_formatString, B_PRId32, formatSize);
break;
case INTEGER_FORMAT_UNSIGNED:
strlcpy(_formatString, B_PRIu32, formatSize);
break;
default:
break;
}
break;
case B_INT64_TYPE:
default:
switch (format) {
case INTEGER_FORMAT_HEX_DEFAULT:
result = INTEGER_FORMAT_HEX_64;
break;
case INTEGER_FORMAT_SIGNED:
strlcpy(_formatString, B_PRId64, formatSize);
break;
case INTEGER_FORMAT_UNSIGNED:
strlcpy(_formatString, B_PRIu64, formatSize);
break;
default:
break;
}
break;
}
return result;
}
/*static*/ bool
IntegerFormatter::FormatValue(const BVariant& value, integer_format format,
char* buffer, size_t bufferSize)
@@ -19,38 +98,30 @@ IntegerFormatter::FormatValue(const BVariant& value, integer_format format,
if (!value.IsInteger(&isSigned))
return false;
if (format == INTEGER_FORMAT_DEFAULT)
format = isSigned ? INTEGER_FORMAT_SIGNED : INTEGER_FORMAT_UNSIGNED;
char formatString[10];
if (format == INTEGER_FORMAT_HEX_DEFAULT) {
switch (value.Type()) {
case B_INT8_TYPE:
case B_UINT8_TYPE:
format = INTEGER_FORMAT_HEX_8;
break;
case B_INT16_TYPE:
case B_UINT16_TYPE:
format = INTEGER_FORMAT_HEX_16;
break;
case B_INT32_TYPE:
case B_UINT32_TYPE:
format = INTEGER_FORMAT_HEX_32;
break;
case B_INT64_TYPE:
case B_UINT64_TYPE:
default:
format = INTEGER_FORMAT_HEX_64;
break;
}
if (format == INTEGER_FORMAT_DEFAULT) {
format = isSigned ? INTEGER_FORMAT_SIGNED : INTEGER_FORMAT_UNSIGNED;
}
format = GetFormatForTypeAndFormat(value.Type(), format, formatString,
sizeof(formatString));
// format the value
switch (format) {
case INTEGER_FORMAT_SIGNED:
snprintf(buffer, bufferSize, "%lld", value.ToInt64());
snprintf(buffer, bufferSize, formatString,
value.Type() == B_INT8_TYPE ? value.ToInt8() :
value.Type() == B_INT16_TYPE ? value.ToInt16() :
value.Type() == B_INT32_TYPE ? value.ToInt32() :
value.ToInt64());
break;
case INTEGER_FORMAT_UNSIGNED:
snprintf(buffer, bufferSize, "%llu", value.ToUInt64());
snprintf(buffer, bufferSize, formatString,
value.Type() == B_INT8_TYPE ? value.ToUInt8() :
value.Type() == B_INT16_TYPE ? value.ToUInt16() :
value.Type() == B_INT32_TYPE ? value.ToUInt32() :
value.ToUInt64());
break;
case INTEGER_FORMAT_HEX_8:
snprintf(buffer, bufferSize, "%#x", (uint8)value.ToUInt64());
@@ -62,7 +133,6 @@ IntegerFormatter::FormatValue(const BVariant& value, integer_format format,
snprintf(buffer, bufferSize, "%#lx", (uint32)value.ToUInt64());
break;
case INTEGER_FORMAT_HEX_64:
case INTEGER_FORMAT_HEX_DEFAULT:
default:
snprintf(buffer, bufferSize, "%#llx", value.ToUInt64());
break;