introduce frame()
This commit is contained in:
parent
a876064718
commit
331eec77e6
1 changed files with 210 additions and 211 deletions
421
src/hover.cpp
421
src/hover.cpp
|
@ -273,38 +273,26 @@ struct Sec_Hover_Fn {
|
||||||
u32 version = bswap(version_be);
|
u32 version = bswap(version_be);
|
||||||
b8 is_big = version > 1000;
|
b8 is_big = version > 1000;
|
||||||
|
|
||||||
|
field_be<u32>("NBytes: %u");
|
||||||
|
field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
||||||
|
x = bswap(x);
|
||||||
|
x -= (x > 1000) * 1000;
|
||||||
|
return push_str8_node_child(arena, prev, fmt, x);
|
||||||
|
});
|
||||||
|
field_be<u32>("Obj Len: %u");
|
||||||
|
field<u32>("Datetime: ", hover_display_datetime_str);
|
||||||
|
field_be<u16>("Key Len: %u");
|
||||||
|
field_be<u16>("Cycle: %u");
|
||||||
if (is_big) {
|
if (is_big) {
|
||||||
field_be<u32>("NBytes: %u");
|
|
||||||
field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
|
||||||
x = bswap(x);
|
|
||||||
x -= 1000;
|
|
||||||
return push_str8_node_child(arena, prev, fmt, x);
|
|
||||||
});
|
|
||||||
field_be<u32>("Obj Len: %u");
|
|
||||||
field<u32>("Datetime: ", hover_display_datetime_str);
|
|
||||||
field_be<u16>("Key Len: %u");
|
|
||||||
field_be<u16>("Cycle: %u");
|
|
||||||
field_be<u64>("Seek Key: 0x%" PRIX64);
|
field_be<u64>("Seek Key: 0x%" PRIX64);
|
||||||
field_be<u64>("Seek Pdir: 0x%" PRIX64);
|
field_be<u64>("Seek Pdir: 0x%" PRIX64);
|
||||||
field_str8<u8>("Class Name: %s");
|
|
||||||
field_str8<u8>("Obj Name: %s");
|
|
||||||
field_str8<u8>("Obj Title: %s");
|
|
||||||
} else {
|
} else {
|
||||||
field_be<u32>("NBytes: %u");
|
|
||||||
field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
|
||||||
x = bswap(x);
|
|
||||||
return push_str8_node_child(arena, prev, fmt, x);
|
|
||||||
});
|
|
||||||
field_be<u32>("Obj Len: %u");
|
|
||||||
field<u32>("Datetime: ", hover_display_datetime_str);
|
|
||||||
field_be<u16>("Key Len: %u");
|
|
||||||
field_be<u16>("Cycle: %u");
|
|
||||||
field_be<u32>("Seek Key: 0x%" PRIX64);
|
field_be<u32>("Seek Key: 0x%" PRIX64);
|
||||||
field_be<u32>("Seek Pdir: 0x%" PRIX64);
|
field_be<u32>("Seek Pdir: 0x%" PRIX64);
|
||||||
field_str8<u8>("Class Name: %s");
|
|
||||||
field_str8<u8>("Obj Name: %s");
|
|
||||||
field_str8<u8>("Obj Title: %s");
|
|
||||||
}
|
}
|
||||||
|
field_str8<u8>("Class Name: %s");
|
||||||
|
field_str8<u8>("Obj Name: %s");
|
||||||
|
field_str8<u8>("Obj Title: %s");
|
||||||
}, HoverSec_HideIfNotHovered);
|
}, HoverSec_HideIfNotHovered);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -334,47 +322,40 @@ struct Sec_Hover_Fn {
|
||||||
{
|
{
|
||||||
String8 titlestr = title ? push_str8f(arena, "Frame Header: %s", title) : str8("Frame Header");
|
String8 titlestr = title ? push_str8f(arena, "Frame Header: %s", title) : str8("Frame Header");
|
||||||
Frame_Type frame_type = Frame_INVALID;
|
Frame_Type frame_type = Frame_INVALID;
|
||||||
titled_section(titlestr.c(), [this, &frame_type, &frame_size = size, n_items, titlestr] {
|
titled_section(titlestr.c(), [this, &frame_type, &frame_size = size, n_items] {
|
||||||
i64 size;
|
i64 size;
|
||||||
memcpy(&size, data + start + cur_field_off, sizeof(size));
|
memcpy(&size, data + start + cur_field_off, sizeof(size));
|
||||||
if (size >= 0) {
|
if (size >= 0) {
|
||||||
frame_type = Frame_Record;
|
frame_type = Frame_Record;
|
||||||
field<i64>("Record frame size: %" PRIi64 " B", hover_display_val_le_abs<i64>);
|
field<i64>("Record frame size: %" PRIi64 " B", hover_display_val_le_abs<i64>);
|
||||||
} else {
|
} else {
|
||||||
frame_type = Frame_List;
|
if (!n_items) {
|
||||||
assert(n_items);
|
// Since the caller didn't pass us a pointer to n_items, they think we're supposed
|
||||||
memcpy(n_items, data + start + cur_field_off + sizeof(i64), sizeof(*n_items));
|
// to be parsing a record frame. But it turns out this is actually a frame list!
|
||||||
titled_section("List Frame", [this] {
|
// Something fishy is going on, so just bail out.
|
||||||
field<i64>("Size: %" PRIi64 " B", hover_display_val_le_abs<i64>);
|
frame_type = Frame_INVALID;
|
||||||
field_le<u32>("N Items: %u");
|
} else {
|
||||||
});
|
frame_type = Frame_List;
|
||||||
|
memcpy(n_items, data + start + cur_field_off + sizeof(i64), sizeof(u32));
|
||||||
|
titled_section("List Frame", [this] {
|
||||||
|
field<i64>("Size: %" PRIi64 " B", hover_display_val_le_abs<i64>);
|
||||||
|
field_le<u32>("N Items: %u");
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
frame_size = std::abs(size);
|
frame_size = std::abs(size);
|
||||||
});
|
});
|
||||||
assert(frame_type == Frame_Record || frame_type == Frame_List);
|
|
||||||
return frame_type;
|
return frame_type;
|
||||||
}
|
}
|
||||||
|
|
||||||
void field_desc()
|
void field_desc(const char *title)
|
||||||
{
|
{
|
||||||
static const char *const field_struct_names[] = {
|
static const char *const field_struct_names[] = {
|
||||||
"Leaf", "Collection", "Record", "Variant", "Unsplit"
|
"Leaf", "Collection", "Record", "Variant", "Unsplit"
|
||||||
};
|
};
|
||||||
|
|
||||||
titled_section("Field", [this] {
|
frame<Frame_Record>(title, [this] {
|
||||||
u64 start_off = cur_field_off;
|
|
||||||
u64 size;
|
|
||||||
Frame_Type ftype = frame_header(size);
|
|
||||||
if (ftype != Frame_Record)
|
|
||||||
return;
|
|
||||||
|
|
||||||
// DEBUG
|
|
||||||
if (size > 100000) {
|
|
||||||
printf("read field_frame_size = %lu at offset 0x%lX!\n", size, start + cur_field_off);
|
|
||||||
// ended = true;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
field_le<u32>("Field version: %u");
|
field_le<u32>("Field version: %u");
|
||||||
field_le<u32>("Type version: %u");
|
field_le<u32>("Type version: %u");
|
||||||
field_le<u32>("On-disk parent id: %u");
|
field_le<u32>("On-disk parent id: %u");
|
||||||
|
@ -398,29 +379,12 @@ struct Sec_Hover_Fn {
|
||||||
field_str8<u32>("Type Name: %s");
|
field_str8<u32>("Type Name: %s");
|
||||||
field_str8<u32>("Type Alias: %s");
|
field_str8<u32>("Type Alias: %s");
|
||||||
field_str8<u32>("Description: %s");
|
field_str8<u32>("Description: %s");
|
||||||
|
|
||||||
u64 extra_size = size - (cur_field_off - start_off);
|
|
||||||
if (extra_size > 0)
|
|
||||||
range("Unknown", extra_size);
|
|
||||||
}, HoverSec_HideIfNotHovered);
|
}, HoverSec_HideIfNotHovered);
|
||||||
}
|
}
|
||||||
|
|
||||||
void column_desc(const char *title)
|
void column_desc(const char *title)
|
||||||
{
|
{
|
||||||
titled_section(title, [this, title] {
|
frame<Frame_Record>(title, [this] {
|
||||||
u64 start_off = cur_field_off;
|
|
||||||
u64 size;
|
|
||||||
Frame_Type ftype = frame_header(size);
|
|
||||||
if (ftype != Frame_Record)
|
|
||||||
return;
|
|
||||||
|
|
||||||
// DEBUG
|
|
||||||
if (size > 100000) {
|
|
||||||
printf("read column_desc_size = %lu at offset 0x%lX!\n", size, start + cur_field_off);
|
|
||||||
// ended = true;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
field<u16>("Column type: %s", [](Arena *arena, String8_Node *prev, const char *fmt, u16 val) {
|
field<u16>("Column type: %s", [](Arena *arena, String8_Node *prev, const char *fmt, u16 val) {
|
||||||
const char *readable_col_type = get_column_type_name(val);
|
const char *readable_col_type = get_column_type_name(val);
|
||||||
return push_str8_node_child(arena, prev, fmt, readable_col_type);
|
return push_str8_node_child(arena, prev, fmt, readable_col_type);
|
||||||
|
@ -436,56 +400,21 @@ struct Sec_Hover_Fn {
|
||||||
if (flags & RNTupleSerializer::kFlagDeferredColumn) {
|
if (flags & RNTupleSerializer::kFlagDeferredColumn) {
|
||||||
field_le<u64>("First element: %" PRIu64);
|
field_le<u64>("First element: %" PRIu64);
|
||||||
}
|
}
|
||||||
if (flags & RNTupleSerializer::kFlagHasValueRange) {
|
// if (flags & RNTupleSerializer::kFlagHasValueRange) {
|
||||||
field_le<double>("Value Min: %f");
|
// field_le<double>("Value Min: %f");
|
||||||
field_le<double>("Value Max: %f");
|
// field_le<double>("Value Max: %f");
|
||||||
}
|
// }
|
||||||
|
|
||||||
assert(cur_field_off >= start_off);
|
|
||||||
if (size < cur_field_off - start_off) {
|
|
||||||
printf("column_desc(%s) should be of size %lu but we allocated %lu bytes for it?\n", title, size, cur_field_off - start_off);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
u64 extra_size = size - (cur_field_off - start_off);
|
|
||||||
printf("extra size: %lu - %lu = %lu\n", size, cur_field_off - start_off, extra_size);
|
|
||||||
if (extra_size > 0)
|
|
||||||
range("Unknown", extra_size);
|
|
||||||
}, HoverSec_HideIfNotHovered);
|
}, HoverSec_HideIfNotHovered);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename F>
|
|
||||||
void list_frame(const char *title, F &&per_elem_fn)
|
|
||||||
{
|
|
||||||
if (ended)
|
|
||||||
return;
|
|
||||||
|
|
||||||
u64 size;
|
|
||||||
u32 n_elems;
|
|
||||||
Frame_Type ftype = frame_header(size, &n_elems, title);
|
|
||||||
if (ftype != Frame_List)
|
|
||||||
return;
|
|
||||||
|
|
||||||
// DEBUG
|
|
||||||
if (n_elems > 100000) {
|
|
||||||
printf("read n_elems = %u at offset 0x%lX!\n", n_elems, start + cur_field_off);
|
|
||||||
// ended = true;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
for (u32 i = 0; i < n_elems; ++i) {
|
|
||||||
per_elem_fn();
|
|
||||||
if (ended)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void schema_description(const char *title)
|
void schema_description(const char *title)
|
||||||
{
|
{
|
||||||
titled_section(title, [this] {
|
titled_section(title, [this] {
|
||||||
// TODO: Columns and alias columns are not the same
|
// TODO: Columns and alias columns are not the same
|
||||||
list_frame("Fields", [this] { field_desc(); });
|
frame<Frame_List>("Fields", [this] (u32 idx) { field_desc(push_str8f(arena, "Field %u", idx).c()); });
|
||||||
list_frame("Columns", [this] { column_desc("Column"); });
|
frame<Frame_List>("Columns", [this] (u32 idx) { column_desc(push_str8f(arena, "Column %u", idx).c()); });
|
||||||
list_frame("Alias Columns", [this] { column_desc("Alias Column"); });
|
frame<Frame_List>("Alias Columns", [this] (u32 idx) { column_desc(push_str8f(arena, "Alias Column %u", idx).c()); });
|
||||||
list_frame("Extra Type Infos", [this] {
|
frame<Frame_List>("Extra Type Infos", [this] (u32) {
|
||||||
field_le<u32>("Content identifier: %lu");
|
field_le<u32>("Content identifier: %lu");
|
||||||
field_le<u32>("Type version from: %lu");
|
field_le<u32>("Type version from: %lu");
|
||||||
field_le<u32>("Type version to: %lu");
|
field_le<u32>("Type version to: %lu");
|
||||||
|
@ -503,18 +432,12 @@ struct Sec_Hover_Fn {
|
||||||
|
|
||||||
void cluster_group()
|
void cluster_group()
|
||||||
{
|
{
|
||||||
titled_section("Cluster Group", [this] {
|
frame<Frame_List>("Cluster Group", [this] (u32) {
|
||||||
u64 size;
|
field_le<u64>("Min Entry: %" PRIu64);
|
||||||
u32 n_items;
|
field_le<u64>("Entry Span: %" PRIu64);
|
||||||
Frame_Type ftype = frame_header(size, &n_items);
|
field_le<u32>("N Clusters: %u");
|
||||||
assert(ftype == Frame_List);
|
field_le<u64>("Env.Link Len: %" PRIu64);
|
||||||
for (u32 i = 0; i < n_items; ++i) {
|
locator("Env.Link Locator");
|
||||||
field_le<u64>("Min Entry: %" PRIu64);
|
|
||||||
field_le<u64>("Entry Span: %" PRIu64);
|
|
||||||
field_le<u32>("N Clusters: %u");
|
|
||||||
field_le<u64>("Env.Link Len: %" PRIu64);
|
|
||||||
locator("Env.Link Locator");
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -592,9 +515,6 @@ struct Sec_Hover_Fn {
|
||||||
// so they're always occupying only 8 bytes.
|
// so they're always occupying only 8 bytes.
|
||||||
field_le<u64>("Flags: 0x%" PRIX64);
|
field_le<u64>("Flags: 0x%" PRIX64);
|
||||||
field_le<u64>("Header checksum: 0x%" PRIX64);
|
field_le<u64>("Header checksum: 0x%" PRIX64);
|
||||||
u64 size;
|
|
||||||
Frame_Type ftype = frame_header(size);
|
|
||||||
assert(ftype == Frame_Record);
|
|
||||||
schema_description("Schema Extension");
|
schema_description("Schema Extension");
|
||||||
// - list of column group record frames (TODO)
|
// - list of column group record frames (TODO)
|
||||||
//frame_header("Column Groups");
|
//frame_header("Column Groups");
|
||||||
|
@ -607,6 +527,84 @@ struct Sec_Hover_Fn {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cluster_summary()
|
||||||
|
{
|
||||||
|
frame<Frame_Record>("Cluster Summary", [this] {
|
||||||
|
field_le<u64>("First Entry: %" PRIu64);
|
||||||
|
field<u64>("", [] (Arena *arena, String8_Node *prev, const char *, u64 x) {
|
||||||
|
u64 entries = (x << 8) >> 8;
|
||||||
|
u8 flags = x >> 56;
|
||||||
|
String8_Node *sn = push_str8_node_child(arena, prev, "Entries: %" PRIu64, entries);
|
||||||
|
return push_str8_node(arena, sn, "Flags: 0b%b", flags);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void cluster()
|
||||||
|
{
|
||||||
|
frame<Frame_List>("Cluster", [this] (u32 col_idx) {
|
||||||
|
titled_section(push_str8f(arena, "Column %u", col_idx).c(), [this] {
|
||||||
|
frame<Frame_List>("Pages", [this] (u32 page_idx) {
|
||||||
|
titled_section(push_str8f(arena, "Page %u", page_idx).c(), [this] {
|
||||||
|
field<i32>("", [] (Arena *arena, String8_Node *prev, const char *, i32 n_elems) {
|
||||||
|
b8 has_checksum = n_elems < 0;
|
||||||
|
String8_Node *sn = push_str8_node_child(arena, prev, "N Elements: %u", std::abs(n_elems));
|
||||||
|
return push_str8_node(arena, sn, "Has Checksum: %s", has_checksum ? "yes" : "no");
|
||||||
|
});
|
||||||
|
locator("Element Locator");
|
||||||
|
}, HoverSec_HideIfNotHovered);
|
||||||
|
});
|
||||||
|
|
||||||
|
i64 n_cols;
|
||||||
|
if (!field<i64>("", [] (Arena *arena, String8_Node *prev, const char *, i64 n_cols) {
|
||||||
|
if (n_cols < 0) {
|
||||||
|
return push_str8_node_child(arena, prev, "Element Offset: <suppressed>");
|
||||||
|
}
|
||||||
|
return push_str8_node_child(arena, prev, "Element Offset: %" PRIi64, n_cols);
|
||||||
|
}, &n_cols))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (n_cols >= 0)
|
||||||
|
field_le<i32>("Compression Settings: %d");
|
||||||
|
}, HoverSec_HideIfNotHovered);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
template <Frame_Type FType, typename F>
|
||||||
|
void frame(const char *title, F &&frame_body_fn, u64 sec_flags = 0)
|
||||||
|
{
|
||||||
|
u64 start_off = cur_field_off;
|
||||||
|
u64 size;
|
||||||
|
|
||||||
|
titled_section(title, [this, title, start_off, &size, &frame_body_fn] {
|
||||||
|
u32 n_items = 0;
|
||||||
|
Frame_Type ftype = frame_header(size, &n_items);
|
||||||
|
if (ftype != FType)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if constexpr (FType == Frame_List) {
|
||||||
|
for (u32 i = 0; i < n_items; ++i)
|
||||||
|
frame_body_fn(i);
|
||||||
|
} else {
|
||||||
|
frame_body_fn();
|
||||||
|
}
|
||||||
|
|
||||||
|
assert(cur_field_off >= start_off);
|
||||||
|
u64 allocated_size = cur_field_off - start_off;
|
||||||
|
if (size < allocated_size) {
|
||||||
|
fprintf(stderr, "Frame %s told us its size was %" PRIu64 " but we accounted for %" PRIu64 " bytes!\n",
|
||||||
|
title, size, allocated_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
u64 extra_size = size - allocated_size;
|
||||||
|
if (extra_size > 0)
|
||||||
|
range("Unknown", extra_size);
|
||||||
|
}, sec_flags);
|
||||||
|
|
||||||
|
cur_field_off = start_off + size;
|
||||||
|
}
|
||||||
|
|
||||||
void page_list()
|
void page_list()
|
||||||
{
|
{
|
||||||
titled_section("Page List", [this] {
|
titled_section("Page List", [this] {
|
||||||
|
@ -620,7 +618,10 @@ struct Sec_Hover_Fn {
|
||||||
range("Payload", section.range.len - section.post_size - sizeof(u64) - 1);
|
range("Payload", section.range.len - section.post_size - sizeof(u64) - 1);
|
||||||
field_le<u64>("Checksum: 0x%" PRIX64);
|
field_le<u64>("Checksum: 0x%" PRIX64);
|
||||||
} else {
|
} else {
|
||||||
// TODO
|
envelope_preamble();
|
||||||
|
field_le<u64>("Header checksum: 0x%" PRIX64);
|
||||||
|
frame<Frame_List>("Cluster Summaries", [this] (u32) { cluster_summary(); });
|
||||||
|
frame<Frame_List>("Clusters", [this] (u32) { cluster(); });
|
||||||
}
|
}
|
||||||
}, HoverSec_HideIfNotHovered);
|
}, HoverSec_HideIfNotHovered);
|
||||||
});
|
});
|
||||||
|
@ -632,41 +633,33 @@ struct Sec_Hover_Fn {
|
||||||
u32 root_version_be;
|
u32 root_version_be;
|
||||||
memcpy(&root_version_be, data + start + 4, sizeof(u32));
|
memcpy(&root_version_be, data + start + 4, sizeof(u32));
|
||||||
u32 root_version = bswap(root_version_be);
|
u32 root_version = bswap(root_version_be);
|
||||||
b8 is_big = root_version > 1000000;
|
b8 is_big = root_version > 1000'000;
|
||||||
|
|
||||||
|
field_be<u32>("ROOT magic number");
|
||||||
|
field<u32>("ROOT version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u32 x) {
|
||||||
|
x = bswap(x);
|
||||||
|
x -= (x > 1000'000) * 1000'000;
|
||||||
|
return push_str8_node_child(arena, prev, fmt, x);
|
||||||
|
});
|
||||||
|
field_be<u32>("fBEGIN: 0x%" PRIX64);
|
||||||
if (is_big) {
|
if (is_big) {
|
||||||
field_be<u32>("ROOT magic number");
|
|
||||||
field<u32>("ROOT version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u32 x) {
|
|
||||||
x = bswap(x);
|
|
||||||
x -= 1000000;
|
|
||||||
return push_str8_node_child(arena, prev, fmt, x);
|
|
||||||
});
|
|
||||||
field_be<u32>("fBEGIN: 0x%" PRIX64);
|
|
||||||
field_be<u64>("fEND: 0x%" PRIX64);
|
field_be<u64>("fEND: 0x%" PRIX64);
|
||||||
field_be<u64>("Seek Free: 0x%" PRIX64);
|
field_be<u64>("Seek Free: 0x%" PRIX64);
|
||||||
field_be<u32>("NBytes Free: %u");
|
|
||||||
field_be<u32>("N Free: %u");
|
|
||||||
field_be<u32>("NBytes Name: %u");
|
|
||||||
field_be<u8>("Units: %u");
|
|
||||||
field_be<u32>("Compression: %u");
|
|
||||||
field_be<u64>("Seek Info: 0x%" PRIX64);
|
|
||||||
field_be<u32>("NBytes Info: %u");
|
|
||||||
range("Padding", section.post_size);
|
|
||||||
} else {
|
} else {
|
||||||
field_be<u32>("ROOT magic number");
|
|
||||||
field_be<u32>("ROOT version: %u");
|
|
||||||
field_be<u32>("fBEGIN: 0x%" PRIX64);
|
|
||||||
field_be<u32>("fEND: 0x%" PRIX64);
|
field_be<u32>("fEND: 0x%" PRIX64);
|
||||||
field_be<u32>("Seek Free: 0x%" PRIX64);
|
field_be<u32>("Seek Free: 0x%" PRIX64);
|
||||||
field_be<u32>("NBytes Free: %u");
|
|
||||||
field_be<u32>("N Free: %u");
|
|
||||||
field_be<u32>("NBytes Name: %u");
|
|
||||||
field_be<u8>("Units: %u");
|
|
||||||
field_be<u32>("Compression: %u");
|
|
||||||
field_be<u32>("Seek Info: 0x%" PRIX64);
|
|
||||||
field_be<u32>("NBytes Info: %u");
|
|
||||||
range("Padding", section.post_size);
|
|
||||||
}
|
}
|
||||||
|
field_be<u32>("NBytes Free: %u");
|
||||||
|
field_be<u32>("N Free: %u");
|
||||||
|
field_be<u32>("NBytes Name: %u");
|
||||||
|
field_be<u8>("Units: %u");
|
||||||
|
field_be<u32>("Compression: %u");
|
||||||
|
if (is_big)
|
||||||
|
field_be<u64>("Seek Info: 0x%" PRIX64);
|
||||||
|
else
|
||||||
|
field_be<u32>("Seek Info: 0x%" PRIX64);
|
||||||
|
field_be<u32>("NBytes Info: %u");
|
||||||
|
range("Padding", section.post_size);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -682,33 +675,75 @@ struct Sec_Hover_Fn {
|
||||||
u16 version = bswap(version_be);
|
u16 version = bswap(version_be);
|
||||||
b8 is_big = version > 1000;
|
b8 is_big = version > 1000;
|
||||||
|
|
||||||
|
field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
||||||
|
x = bswap(x);
|
||||||
|
x -= (x > 1000) * 1000;
|
||||||
|
return push_str8_node_child(arena, prev, fmt, x);
|
||||||
|
});
|
||||||
|
field<u32>("Created: ", hover_display_datetime_str);
|
||||||
|
field<u32>("Modified: ", hover_display_datetime_str);
|
||||||
|
field_be<u32>("NBytes Key: %u");
|
||||||
|
field_be<u32>("NBytes Name: %u");
|
||||||
if (is_big) {
|
if (is_big) {
|
||||||
field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
|
||||||
x = bswap(x);
|
|
||||||
x -= 1000;
|
|
||||||
return push_str8_node_child(arena, prev, fmt, x);
|
|
||||||
});
|
|
||||||
field<u32>("Created: ", hover_display_datetime_str);
|
|
||||||
field<u32>("Modified: ", hover_display_datetime_str);
|
|
||||||
field_be<u32>("NBytes Key: %u");
|
|
||||||
field_be<u32>("NBytes Name: %u");
|
|
||||||
field_be<u64>("Seek Dir: 0x%" PRIX64) ;
|
field_be<u64>("Seek Dir: 0x%" PRIX64) ;
|
||||||
field_be<u64>("Seek Parent: 0x%" PRIX64) ;
|
field_be<u64>("Seek Parent: 0x%" PRIX64) ;
|
||||||
field_be<u64>("Seek Keys: 0x%" PRIX64) ;
|
field_be<u64>("Seek Keys: 0x%" PRIX64) ;
|
||||||
field_be<u16>("UUID Vers.Class: %u");
|
|
||||||
field_le<u16>("UUID: %u");
|
|
||||||
} else {
|
} else {
|
||||||
field_be<u16>("Version: %u");
|
|
||||||
field<u32>("Created: ", hover_display_datetime_str);
|
|
||||||
field<u32>("Modified: ", hover_display_datetime_str);
|
|
||||||
field_be<u32>("NBytes Key: %u");
|
|
||||||
field_be<u32>("NBytes Name: %u");
|
|
||||||
field_be<u32>("Seek Dir: 0x%" PRIX64) ;
|
field_be<u32>("Seek Dir: 0x%" PRIX64) ;
|
||||||
field_be<u32>("Seek Parent: 0x%" PRIX64) ;
|
field_be<u32>("Seek Parent: 0x%" PRIX64) ;
|
||||||
field_be<u32>("Seek Keys: 0x%" PRIX64) ;
|
field_be<u32>("Seek Keys: 0x%" PRIX64) ;
|
||||||
field_be<u16>("UUID Vers.Class: %u");
|
}
|
||||||
field_le<u16>("UUID: %u");
|
field_be<u16>("UUID Vers.Class: %u");
|
||||||
|
field_le<u16>("UUID: %u");
|
||||||
|
if (!is_big)
|
||||||
range("Padding", 3 * sizeof(u32));
|
range("Padding", 3 * sizeof(u32));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void tfile_info()
|
||||||
|
{
|
||||||
|
titled_section("TFile Info", [this] {
|
||||||
|
tkey();
|
||||||
|
b8 zipped;
|
||||||
|
if (!maybe_rootzip(&zipped))
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (zipped) {
|
||||||
|
range("Compressed Payload", section.range.len);
|
||||||
|
} else {
|
||||||
|
field<u32>("Byte Count: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u32 x) {
|
||||||
|
x = bswap(x);
|
||||||
|
x -= 0x400000000;
|
||||||
|
return push_str8_node_child(arena, prev, fmt, x);
|
||||||
|
});
|
||||||
|
field_be<u16>("Version: %u");
|
||||||
|
// hover_try_object(hover)
|
||||||
|
field_be<u8>("Name: %u");
|
||||||
|
field_be<u32>("N Objects: %u");;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void tfile_freelist()
|
||||||
|
{
|
||||||
|
titled_section("TFile FreeList", [this] {
|
||||||
|
tkey();
|
||||||
|
u16 version_be;
|
||||||
|
memcpy(&version_be, data + start + cur_field_off, sizeof(u16));
|
||||||
|
u32 version = bswap(version_be);
|
||||||
|
b8 is_big = version > 1000;
|
||||||
|
|
||||||
|
field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
||||||
|
x = bswap(x);
|
||||||
|
x -= (x > 1000) * 1000;
|
||||||
|
return push_str8_node_child(arena, prev, fmt, x);
|
||||||
|
});
|
||||||
|
if (is_big) {
|
||||||
|
field_be<u64>("First: 0x%" PRIX64);
|
||||||
|
field_be<u64>("Last: 0x%" PRIX64);
|
||||||
|
} else {
|
||||||
|
field_be<u32>("First: 0x%X");
|
||||||
|
field_be<u32>("Last: 0x%X");
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -778,50 +813,14 @@ Sec_Hover_Info get_section_hover_info(Arena *arena, Section section, u64 off, co
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case Sec_TFile_Info: {
|
case Sec_TFile_Info: {
|
||||||
hover.tkey()
|
hover.tfile_info();
|
||||||
hover.maybe_rootzip()
|
|
||||||
// || hover.field<u32>("Byte Count: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u32 x) {
|
|
||||||
// x = bswap(x);
|
|
||||||
// x -= 0x400000000;
|
|
||||||
// return push_str8_node_child(arena, prev, fmt, x);
|
|
||||||
// })
|
|
||||||
// || hover.field_be<u16>("Version: %u")
|
|
||||||
// || hover_try_object(hover)
|
|
||||||
// || hover.field_be<u8>("Name: %u")
|
|
||||||
// || hover.field_be<u32>("N Objects: %u")
|
|
||||||
|| hover.range("Payload", section.range.len) // TODO: improve
|
|
||||||
;
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case Sec_TFile_FreeList: {
|
|
||||||
if (!hover.tkey()) {
|
|
||||||
u16 version_be;
|
|
||||||
memcpy(&version_be, data + start + hover.cur_field_off, sizeof(u16));
|
|
||||||
u32 version = bswap(version_be);
|
|
||||||
b8 is_big = version > 1000;
|
|
||||||
|
|
||||||
if (is_big) {
|
|
||||||
hover.field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
|
||||||
x = bswap(x);
|
|
||||||
x -= 1000;
|
|
||||||
return push_str8_node_child(arena, prev, fmt, x);
|
|
||||||
})
|
|
||||||
|| hover.field_be<u64>("First: 0x%" PRIX64)
|
|
||||||
|| hover.field_be<u64>("Last: 0x%" PRIX64)
|
|
||||||
;
|
|
||||||
} else {
|
|
||||||
hover.field<u16>("Version: %u", [] (Arena *arena, String8_Node *prev, const char *fmt, u16 x) {
|
|
||||||
x = bswap(x);
|
|
||||||
return push_str8_node_child(arena, prev, fmt, x);
|
|
||||||
})
|
|
||||||
|| hover.field_be<u32>("First: 0x%X")
|
|
||||||
|| hover.field_be<u32>("Last: 0x%X")
|
|
||||||
;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} break;
|
} break;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
case Sec_TFile_FreeList: {
|
||||||
|
hover.tfile_freelist();
|
||||||
|
} break;
|
||||||
|
|
||||||
default:;
|
default:;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue