1
0
mirror of synced 2024-11-28 09:30:51 +01:00

Added big and little endian support to inspector

This commit is contained in:
WerWolv 2020-11-22 15:32:37 +01:00
parent cd4de2ff96
commit 989eade5d7
5 changed files with 72 additions and 28 deletions

View File

@ -53,7 +53,7 @@ add_executable(ImHex
)
if (WIN32)
target_link_libraries(ImHex libglfw3.a libgcc.a libstdc++.a libmagic.a libgnurx.a libtre.a libintl.a libiconv.a shlwapi.lib ws2_32.lib libcrypto.a libwinpthread.a)
target_link_libraries(ImHex libglfw3.a libgcc.a libstdc++.a libmagic.a libgnurx.a libtre.a libintl.a libiconv.a shlwapi.lib libcrypto.a libwinpthread.a)
endif (WIN32)
if (UNIX)

View File

@ -9,6 +9,12 @@
#include <string>
#include <vector>
#ifdef __MINGW32__
#include <winsock.h>
#else
#include <arpa/inet.h>
#endif
#include "lang/token.hpp"
namespace hex {
@ -80,6 +86,26 @@ namespace hex {
return (value & mask) >> to;
}
template<typename T>
struct always_false : std::false_type {};
template<typename T>
constexpr T changeEndianess(T value, std::endian endian) {
if (endian == std::endian::native)
return value;
if constexpr (sizeof(T) == 1)
return value;
else if constexpr (sizeof(T) == 2)
return __builtin_bswap16(value);
else if constexpr (sizeof(T) == 4)
return __builtin_bswap32(value);
else if constexpr (sizeof(T) == 8)
return __builtin_bswap64(value);
else
static_assert(always_false<T>::value, "Invalid type provided!");
}
class ScopeExit {
public:

View File

@ -2,6 +2,7 @@
#include "views/view.hpp"
#include <bit>
#include <cstdio>
#include <ctime>
#include <string>
@ -53,6 +54,8 @@ namespace hex {
bool m_windowOpen = true;
bool m_shouldInvalidate = true;
std::endian m_endianess = std::endian::native;
PreviewData m_previewData = { 0 };
size_t m_validBytes = 0;
std::vector<std::pair<std::string, std::string>> m_cachedData;

View File

@ -41,31 +41,36 @@ namespace hex {
this->m_cachedData.emplace_back("Binary (8 bit)", binary);
}
this->m_cachedData.emplace_back("uint8_t", hex::format("%u", this->m_previewData.unsigned8));
this->m_cachedData.emplace_back("int8_t", hex::format("%d", this->m_previewData.signed8));
this->m_cachedData.emplace_back("uint16_t", hex::format("%u", this->m_previewData.unsigned16));
this->m_cachedData.emplace_back("int16_t", hex::format("%d", this->m_previewData.signed16));
this->m_cachedData.emplace_back("uint32_t", hex::format("%lu", this->m_previewData.unsigned32));
this->m_cachedData.emplace_back("int32_t", hex::format("%ld", this->m_previewData.signed32));
this->m_cachedData.emplace_back("uint64_t", hex::format("%llu", this->m_previewData.unsigned64));
this->m_cachedData.emplace_back("int64_t", hex::format("%lld", this->m_previewData.signed64));
this->m_cachedData.emplace_back("uint8_t", hex::format("%u", hex::changeEndianess(this->m_previewData.unsigned8, this->m_endianess)));
this->m_cachedData.emplace_back("int8_t", hex::format("%d", hex::changeEndianess(this->m_previewData.signed8, this->m_endianess)));
this->m_cachedData.emplace_back("uint16_t", hex::format("%u", hex::changeEndianess(this->m_previewData.unsigned16, this->m_endianess)));
this->m_cachedData.emplace_back("int16_t", hex::format("%d", hex::changeEndianess(this->m_previewData.signed16, this->m_endianess)));
this->m_cachedData.emplace_back("uint32_t", hex::format("%lu", hex::changeEndianess(this->m_previewData.unsigned32, this->m_endianess)));
this->m_cachedData.emplace_back("int32_t", hex::format("%ld", hex::changeEndianess(this->m_previewData.signed32, this->m_endianess)));
this->m_cachedData.emplace_back("uint64_t", hex::format("%llu", hex::changeEndianess(this->m_previewData.unsigned64, this->m_endianess)));
this->m_cachedData.emplace_back("int64_t", hex::format("%lld", hex::changeEndianess(this->m_previewData.signed64, this->m_endianess)));
this->m_cachedData.emplace_back("ANSI Character / char8_t", hex::format("%c", this->m_previewData.ansiChar));
this->m_cachedData.emplace_back("Wide Character / char16_t", hex::format("%lc", this->m_previewData.wideChar));
this->m_cachedData.emplace_back("ANSI Character / char8_t", hex::format("%c", hex::changeEndianess(this->m_previewData.ansiChar, this->m_endianess)));
this->m_cachedData.emplace_back("Wide Character / char16_t", hex::format("%lc", hex::changeEndianess(this->m_previewData.wideChar, this->m_endianess)));
{
char buffer[5] = { 0 };
char codepointString[5] = { 0 };
u32 codepoint = 0;
u8 codepointSize = ImTextCharFromUtf8(&codepoint, buffer, buffer + 4);
std::memcpy(buffer, &this->m_previewData.utf8Char, 4);
u32 utf8 = 0;
ImTextCharFromUtf8(&utf8, buffer, buffer + 4);
this->m_cachedData.emplace_back("UTF-8 code point", hex::format("U+%08lx", utf8));
std::memcpy(codepointString, &codepoint, std::min(codepointSize, u8(4)));
this->m_cachedData.emplace_back("UTF-8 code point", hex::format("'%s' (U+%04lx)", codepoint == 0xFFFD ? "Invalid" : codepointString, codepoint));
}
this->m_cachedData.emplace_back("float (32 bit)", hex::format("%e", this->m_previewData.float32));
this->m_cachedData.emplace_back("double (64 bit)", hex::format("%e", this->m_previewData.float64));
this->m_cachedData.emplace_back("float (32 bit)", hex::format("%e", hex::changeEndianess(this->m_previewData.float32, this->m_endianess)));
this->m_cachedData.emplace_back("double (64 bit)", hex::format("%e", hex::changeEndianess(this->m_previewData.float64, this->m_endianess)));
#if defined(_WIN64)
{
std::tm * ptm = _localtime32(&this->m_previewData.time32);
auto endianAdjustedTime = hex::changeEndianess(this->m_previewData.time32, this->m_endianess);
std::tm * ptm = _localtime32(&endianAdjustedTime);
char buffer[32];
if (std::strftime(buffer, 32, "%a, %d.%m.%Y %H:%M:%S", ptm))
this->m_cachedData.emplace_back("__time32_t", buffer);
@ -74,7 +79,8 @@ namespace hex {
}
{
std::tm * ptm = _localtime64(&this->m_previewData.time64);
auto endianAdjustedTime = hex::changeEndianess(this->m_previewData.time64, this->m_endianess);
std::tm * ptm = _localtime64(&endianAdjustedTime);
char buffer[64];
if (std::strftime(buffer, 64, "%a, %d.%m.%Y %H:%M:%S", ptm) != 0)
this->m_cachedData.emplace_back("__time64_t", buffer);
@ -83,7 +89,8 @@ namespace hex {
}
#else
{
std::tm * ptm = localtime(&this->m_previewData.time);
auto endianAdjustedTime = hex::changeEndianess(this->m_previewData.time, this->m_endianess);
std::tm * ptm = localtime(&endianAdjustedTime);
char buffer[64];
if (std::strftime(buffer, 64, "%a, %d.%m.%Y %H:%M:%S", ptm) != 0)
this->m_cachedData.emplace_back("time_t", buffer);
@ -93,7 +100,9 @@ namespace hex {
#endif
this->m_cachedData.emplace_back("GUID", hex::format("{%08lX-%04hX-%04hX-%02hhX%02hhX-%02hhX%02hhX%02hhX%02hhX%02hhX%02hhX}",
this->m_previewData.guid.data1, this->m_previewData.guid.data2, this->m_previewData.guid.data3,
hex::changeEndianess(this->m_previewData.guid.data1, this->m_endianess),
hex::changeEndianess(this->m_previewData.guid.data2, this->m_endianess),
hex::changeEndianess(this->m_previewData.guid.data3, this->m_endianess),
this->m_previewData.guid.data4[0], this->m_previewData.guid.data4[1], this->m_previewData.guid.data4[2], this->m_previewData.guid.data4[3],
this->m_previewData.guid.data4[4], this->m_previewData.guid.data4[5], this->m_previewData.guid.data4[6], this->m_previewData.guid.data4[7]));
}
@ -101,7 +110,7 @@ namespace hex {
if (ImGui::Begin("Data Inspector", &this->m_windowOpen)) {
if (this->m_dataProvider != nullptr && this->m_dataProvider->isReadable()) {
if (ImGui::BeginChild("##scrolling")) {
if (ImGui::BeginChild("##scrolling", ImVec2(0, ImGui::GetWindowHeight() - 60))) {
if (ImGui::BeginTable("##datainspector", 2, ImGuiTableFlags_Borders | ImGuiTableFlags_Resizable | ImGuiTableFlags_RowBg)) {
ImGui::TableSetupColumn("Name");
ImGui::TableSetupColumn("Value");
@ -124,7 +133,7 @@ namespace hex {
ImGui::TableNextColumn();
ImGui::TextUnformatted("RGBA Color");
ImGui::TableNextColumn();
ImGui::ColorButton("##nolabel", ImColor(this->m_previewData.unsigned32),
ImGui::ColorButton("##nolabel", ImColor(hex::changeEndianess(this->m_previewData.unsigned32, this->m_endianess)),
ImGuiColorEditFlags_None, ImVec2(ImGui::GetColumnWidth(), 15));
ImGui::TableSetBgColor(ImGuiTableBgTarget_RowBg0,
((rowCount % 2) == 0) ? 0xFF101010 : 0xFF303030);
@ -136,6 +145,16 @@ namespace hex {
}
}
ImGui::EndChild();
if (ImGui::RadioButton("Little Endian", this->m_endianess == std::endian::little)) {
this->m_endianess = std::endian::little;
this->m_shouldInvalidate = true;
}
ImGui::SameLine();
if (ImGui::RadioButton("Big Endian", this->m_endianess == std::endian::big)) {
this->m_endianess = std::endian::big;
this->m_shouldInvalidate = true;
}
}
}
ImGui::End();

View File

@ -6,11 +6,7 @@
#include <vector>
#ifdef __MINGW32__
#include <winsock.h>
#else
#include <arpa/inet.h>
#endif
#include "utils.hpp"
namespace hex {
@ -27,7 +23,7 @@ namespace hex {
static void formatBigHexInt(auto dataArray, char *buffer, size_t bufferSize) {
for (int i = 0; i < dataArray.size(); i++)
snprintf(buffer + 8 * i, bufferSize - 8 * i, "%08X", htonl(dataArray[i]));
snprintf(buffer + 8 * i, bufferSize - 8 * i, "%08X", hex::changeEndianess(dataArray[i], std::endian::big));
}
void ViewHashes::createView() {