blob: 0bc6ff96540ea36ebab5c5b201b0444f0af9e5a7 [file] [log] [blame]
// Copyright 2018 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "src/developer/debug/zxdb/console/string_formatters.h"
#include <float.h>
#include <limits>
#include "src/lib/fxl/strings/string_printf.h"
namespace zxdb {
std::string GetLittleEndianHexOutput(containers::array_view<uint8_t> data) {
if (data.empty())
return std::string();
// For now we print into chunks of 32-bits, shortening the ends.
auto cur = data.data();
auto end = cur + data.size();
std::vector<std::string> chunks;
size_t added_bytes = 0;
while (cur < end && added_bytes < data.size()) {
uint32_t val = 0;
auto diff = end - cur;
for (int i = 0; i < 4 && i < diff; i++) {
uint32_t tmp = cur[i] << (i * 8);
uint32_t mask = 0xFF << (i * 8);
val = (val & ~mask) | tmp;
}
chunks.push_back(fxl::StringPrintf("%.8x", val));
cur += 4;
added_bytes += 4;
}
// Though each particular chunk correctly keeps the endianness, the order is
// backwards, as the last bits of the register would be printed first.
// For that we append the chunks backwards.
std::string result;
auto cit = chunks.rbegin();
while (cit != chunks.rend()) {
result.append(*cit);
cit++;
if (cit != chunks.rend())
result.append(" ");
}
return result;
}
std::string GetFPString(containers::array_view<uint8_t> value, int precision) {
switch (value.size()) {
case 4:
precision = precision != 0 ? precision : FLT_DIG;
return fxl::StringPrintf("%.*e", precision, *(const float*)(value.data()));
case 8:
precision = precision != 0 ? precision : DBL_DIG;
return fxl::StringPrintf("%.*e", precision, *(const double*)(value.data()));
case 16:
if (sizeof(long double) == sizeof(double)) {
// On systems that don't have a longer "long double" type (ARM), printf won't format it
// properly.
return "Can't format a 'long double' on this system.";
} else {
precision = precision != 0 ? precision : LDBL_DIG;
return fxl::StringPrintf("%.*Le", precision, *(const long double*)(value.data()));
}
default:
return fxl::StringPrintf("Wrong size for floating point printing: %zu", value.size());
}
}
} // namespace zxdb