Skip to content

Commit 3bfa422

Browse files
committed
debug output util, closes #76
1 parent 450a00c commit 3bfa422

File tree

5 files changed

+306
-27
lines changed

5 files changed

+306
-27
lines changed

code/dynamix/dbg_dmp.cpp

+272-5
Original file line numberDiff line numberDiff line change
@@ -2,28 +2,295 @@
22
// SPDX-License-Identifier: MIT
33
//
44
#include "dbg_dmp.hpp"
5+
#include "domain.hpp"
56
#include "domain_traverse.hpp"
67
#include "feature_info.hpp"
78
#include "mixin_info.hpp"
9+
#include "mutation_rule_info.hpp"
810
#include "type.hpp"
911
#include "object.hpp"
1012

1113
#include <ostream>
1214

13-
namespace dynamix {
14-
void dbg_dmp(std::ostream& out, const domain& d, int flags) {
15+
namespace dynamix::util {
16+
namespace {
17+
struct p {
18+
p(const void* pp) : ptr(pp) {}
19+
const void* ptr;
20+
};
21+
std::ostream& operator<<(std::ostream& out, p pp) {
22+
if (pp.ptr) {
23+
out << pp.ptr;
24+
}
25+
else {
26+
out << "none";
27+
}
28+
return out;
29+
}
30+
31+
#define IND " "
32+
#define NIND "\n "
1533

34+
void output_mixins(std::ostream& out, const itlib::span<const mixin_info* const>& mixins) {
35+
out << '{';
36+
bool first = true;
37+
for (const auto& m : mixins) {
38+
if (first) {
39+
first = false;
40+
}
41+
else {
42+
out << ", ";
43+
}
44+
out << '\'' << m->name.to_std() << '\'';
45+
}
46+
out << '}';
1647
}
1748

18-
void dbg_dmp(std::ostream& out, const mixin_info& mi, int flags) {
49+
void dbg_dmp_l(std::ostream& out, const type& t, uint32_t flags, domain_traverse* tr) {
50+
out << "type: ";
51+
output_mixins(out, t.mixins);
52+
out << " (" << &t << ") ('" << t.dom.name() << "')";
53+
54+
int num_features = 0;
55+
itlib::span ftable(t.ftable, t.ftable_length);
56+
for (auto& f : ftable) num_features += !!f;
57+
58+
if (flags & dnmx_type_dmp_ex) {
59+
out << NIND "size: " << t.buf_size();
60+
out << NIND "obj buf size: " << t.object_buffer_size;
61+
out << NIND "obj buf align: " << t.object_buffer_alignment;
62+
out << NIND "num obj: " << t.num_objects();
63+
out << NIND "default_constructible: " << t.default_constructible();
64+
out << NIND "copy_constructible: " << t.copy_constructible();
65+
out << NIND "copy_assignable: " << t.copy_assignable();
66+
out << NIND "equality_comparable: " << t.equality_comparable();
67+
out << NIND "comparable: " << t.comparable();
68+
out << NIND "features: " << num_features << '/' << ftable.size();
69+
}
70+
if (flags & dnmx_type_dmp_ftable) {
71+
out << NIND << num_features << " features:";
72+
for (auto& f : ftable) {
73+
if (!f) continue;
74+
out << NIND IND "impl: '" << f.begin->data->info->name.to_std() << "' " << (f.top_bid_back - f.begin) + 1 << '/' << f.size();
75+
if (flags & dnmx_type_dmp_full_ftable) {
76+
for (auto e = f.begin; e != f.end; ++e) {
77+
out << NIND IND IND "'" << t.mixins[e->mixin_index]->name.to_std() << "': " << p(e->payload) << " with " << e->data->bid << "_bid " << e->data->priority << "_prio";
78+
}
79+
}
80+
}
81+
}
82+
if (tr && (flags & dnmx_type_dmp_matching_queries)) {
83+
int count = 0;
84+
tr->traverse_type_queries([&](itlib::span<const mixin_info* const>, const type& qt) {
85+
if (qt == t) count += 1;
86+
});
87+
out << NIND << count << " matching queries:";
88+
tr->traverse_type_queries([&](itlib::span<const mixin_info* const> mixins, const type& qt) {
89+
if (qt != t) return;
90+
out << NIND IND;
91+
output_mixins(out, mixins);
92+
});
93+
}
94+
if (tr && (flags & dnmx_type_dmp_matching_type_classes)) {
95+
out << NIND "matching type classes:";
96+
tr->traverse_type_classes([&](const type_class& tc) {
97+
if (!tc.matches(&t)) return;
98+
out << NIND IND << tc.name.to_std();
99+
});
100+
}
101+
}
19102

103+
void dbg_dmp_l(std::ostream& out, const type_class& tc, uint32_t flags, domain_traverse* tr) {
104+
out << "type class: '" << tc.name.to_std() << ", match: " << p(tc.matches);
105+
if (tc.matches && tr && (flags & dnmx_tc_dmp_matching_types)) {
106+
tr->traverse_types([&](const type& t) {
107+
if (!tc.matches(&t)) return;
108+
out << "match ";
109+
dbg_dmp(out, t, 0);
110+
});
111+
}
20112
}
113+
}
114+
115+
void dbg_dmp(std::ostream& out, const domain& d, uint32_t flags) {
116+
domain_traverse tr(d);
117+
out << std::boolalpha;
118+
out << "domain: '" << d.name() << "' (" << &d << "), ud: " << d.user_data << ", ctx : ";
119+
if (d.context) {
120+
out << d.context;
121+
}
122+
else {
123+
out << "<null>";
124+
}
125+
out << ", alloc: ";
126+
allocator check;
127+
{
128+
auto da = d.get_allocator();
129+
if (da == check) {
130+
out << "default";
131+
}
132+
else {
133+
out << "mr " << da.resource();
134+
}
135+
}
136+
out << '\n';
137+
if (flags & dnmx_dom_dmp_settings) {
138+
auto& s = d.settings();
139+
out << "## Settings";
140+
out << NIND "canonicalize_types: " << s.canonicalize_types;
141+
out << NIND "allow_duplicate_feature_names: " << s.allow_duplicate_feature_names;
142+
out << NIND "allow_duplicate_mixin_names: " << s.allow_duplicate_mixin_names;
143+
out << '\n';
144+
}
145+
if (flags & dnmx_dom_dmp_features) {
146+
int count = 0;
147+
tr.traverse_features([&](const feature_info&) { ++count; });
148+
149+
out << "## " << count << " Features\n";
150+
feature_id::int_t next_slot = 0;
151+
tr.traverse_features([&](const feature_info& fi) {
152+
if (fi.iid() != next_slot) {
153+
out << fi.iid() - next_slot << " empty slots\n";
154+
}
155+
156+
dbg_dmp(out, fi, flags);
157+
out << '\n';
158+
159+
next_slot = fi.iid() + 1;
160+
});
161+
}
162+
if (flags & dnmx_dom_dmp_mixins) {
163+
int count = 0;
164+
tr.traverse_mixins([&](const mixin_info&) { ++count; });
21165

22-
void dbg_dmp(std::ostream& out, const type& t, int flags) {
166+
out << "## " << count << " Mixins\n";
167+
mixin_id::int_t next_slot = 0;
168+
tr.traverse_mixins([&](const mixin_info& mi) {
169+
if (mi.iid() != next_slot) {
170+
out << mi.iid() - next_slot << " empty slots\n";
171+
}
23172

173+
dbg_dmp(out, mi, flags);
174+
out << '\n';
175+
176+
next_slot = mi.iid() + 1;
177+
});
178+
}
179+
if (flags & dnmx_dom_dmp_mutation_rules) {
180+
out << "## " << d.num_mutation_rules() << " Mutation Rules\n";
181+
tr.traverse_mutation_rules([&](const mutation_rule_info& mri, uint32_t refs) {
182+
dbg_dmp(out, mri, flags);
183+
out << ", " << refs << " refs\n";
184+
});
185+
}
186+
if (flags & dnmx_dom_dmp_types) {
187+
out << "## " << d.num_types() << " Types\n";
188+
tr.traverse_types([&](const type& t) {
189+
dbg_dmp_l(out, t, flags, &tr);
190+
out << '\n';
191+
});
192+
}
193+
if (flags & dnmx_dom_dmp_type_classes) {
194+
int count = 0;
195+
tr.traverse_type_classes([&](const type_class&) { ++count; });
196+
197+
out << "## " << count << " Type Classes\n";
198+
tr.traverse_type_classes([&](const type_class& tc) {
199+
dbg_dmp(out, tc, flags);
200+
out << '\n';
201+
});
202+
}
203+
if (flags & dnmx_dom_dmp_type_queries) {
204+
out << "## " << d.num_type_queries() << " Type Queries\n";
205+
tr.traverse_type_queries([&](itlib::span<const mixin_info* const> mixins, const type& qt) {
206+
out << "tq: ";
207+
output_mixins(out, mixins);
208+
out << " -> type: ";
209+
output_mixins(out, qt.mixins);
210+
out << '\n';
211+
});
212+
}
24213
}
25214

26-
void dbg_dmp(std::ostream& out, const type_class& tc, int flags) {
215+
void dbg_dmp(std::ostream& out, const mixin_info& mi, uint32_t flags) {
216+
out << std::boolalpha;
217+
if (mi.dependency) {
218+
out << "dep-";
219+
}
220+
out << "mixin: '" << mi.name.to_std() << "', ";
221+
if (mi.id == invalid_mixin_id) {
222+
out << "unregistered";
223+
}
224+
else {
225+
out << "id: " << mi.iid() << " ('" << mi.dom->m_name.to_std() << "')";
226+
}
227+
out << ", ";
228+
if (mi.external()) {
229+
out << "external";
230+
}
231+
else {
232+
out << "internal";
233+
}
234+
auto features = mi.features_span();
235+
out << ", " << features.size() << " features";
236+
if (flags & dnmx_mixin_dmp_ex) {
237+
out << NIND "size: " << mi.size;
238+
out << NIND "alignment: " << mi.alignment;
239+
out << NIND "obj_buf_size: " << mi.obj_buf_size;
240+
out << NIND "obj_buf_align: " << mi.obj_buf_alignment_and_mixin_offset;
241+
out << NIND "init: " << p(mi.init);
242+
out << NIND "copy_init: " << p(mi.copy_init);
243+
out << NIND "move_init: " << p(mi.move_init);
244+
out << NIND "copy_asgn: " << p(mi.copy_asgn);
245+
out << NIND "move_asgn: " << p(mi.move_asgn);
246+
out << NIND "destroy: " << p(mi.destroy);
247+
out << NIND "equals: " << p(mi.equals);
248+
out << NIND "compare: " << p(mi.compare);
249+
out << NIND "allocator: " << p(mi.allocator);
250+
out << NIND "class: " << mi.mixin_class;
251+
out << NIND "type_info_class: " << mi.type_info_class;
252+
out << NIND "user_data: " << mi.user_data;
253+
out << NIND "order_priority: " << mi.order_priority;
254+
out << NIND "force_external: " << mi.force_external;
255+
}
256+
if (flags & dnmx_mixin_dmp_features) {
257+
out << NIND << features.size() << " features:";
258+
for (auto& f : features) {
259+
out << NIND IND "'" << f.info->name.to_std() << "': " << p(f.payload) << ' '
260+
<< f.bid << "_bid " << f.priority << "_prio";
261+
}
262+
}
263+
}
264+
265+
void dbg_dmp(std::ostream& out, const feature_info& fi, uint32_t) {
266+
out << std::boolalpha;
267+
out << "feature: '" << fi.name.to_std() << "', ";
268+
if (fi.id == invalid_feature_id) {
269+
out << "unregistered";
270+
}
271+
else {
272+
out << "id: " << fi.iid();
273+
}
274+
out << ", allow clashes: " << fi.allow_clashes << ", class: "
275+
<< fi.feature_class << ", default payload: " << p(fi.default_payload);
276+
}
277+
278+
void dbg_dmp(std::ostream& out, const mutation_rule_info& mri, uint32_t) {
279+
out << "rule: '" << mri.name.to_std() << "', prio: " << mri.order_priority
280+
<< ", ud" << mri.user_data << ", apply: " << p(mri.apply);
281+
}
282+
283+
void dbg_dmp(std::ostream& out, const type& t, uint32_t flags) {
284+
if (flags & (dnmx_type_dmp_matching_type_classes | dnmx_type_dmp_matching_queries)) {
285+
domain_traverse tr(t.dom);
286+
dbg_dmp_l(out, t, flags, &tr);
287+
}
288+
else {
289+
dbg_dmp_l(out, t, flags, nullptr);
290+
}
291+
}
27292

293+
void dbg_dmp(std::ostream& out, const type_class& tc, uint32_t flags) {
294+
dbg_dmp_l(out, tc, flags, nullptr);
28295
}
29296
}

code/dynamix/dbg_dmp.hpp

+23-7
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,12 @@
44
#pragma once
55
#include "../dnmx/api.h"
66
#include "mixin_info_fwd.hpp"
7+
#include "feature_info_fwd.hpp"
8+
#include "mutation_rule_info_fwd.hpp"
79
#include "type_class.hpp"
10+
811
#include <iosfwd>
12+
#include <cstdint>
913

1014
enum dnmx_dbg_dmp_flags {
1115
dnmx_dom_dmp_features = 0x1,
@@ -25,11 +29,17 @@ enum dnmx_dbg_dmp_flags {
2529
dnmx_type_dmp_ftable = 0x2000,
2630
dnmx_type_dmp_full_ftable = 0x4000,
2731
dnmx_type_dmp_matching_type_classes = 0x8000,
28-
dnmx_type_dmp_all = 0xF000,
32+
dnmx_type_dmp_matching_queries = 0x10000,
33+
dnmx_type_dmp_all = 0xFF000,
34+
35+
dnmx_tc_dmp_matching_types = 0x100000,
36+
dnmx_tc_dmp_all = 0xF00000,
37+
38+
dnmx_feature_dmp_all = 0,
2939

30-
dnmx_tc_dmp_matching_types = 0x10000,
31-
dnmx_tc_dmp_all = 0xF0000,
40+
dnmx_mr_dmp_all = 0,
3241

42+
dnmx_dmp_min = 0,
3343
dnmx_dmp_all = 0xFFFFFFFF
3444
};
3545

@@ -38,10 +48,16 @@ class domain;
3848
class type;
3949
class object;
4050

41-
DYNAMIX_API void dbg_dmp(std::ostream& out, const domain& d, int flags = dnmx_dmp_all);
42-
DYNAMIX_API void dbg_dmp(std::ostream& out, const mixin_info& mi, int flags = dmnx_mixin_dmp_all);
43-
DYNAMIX_API void dbg_dmp(std::ostream& out, const type& t, int flags = dnmx_type_dmp_all);
44-
DYNAMIX_API void dbg_dmp(std::ostream& out, const type_class& tc, int flags = dnmx_tc_dmp_all);
51+
namespace util {
52+
DYNAMIX_API void dbg_dmp(std::ostream& out, const domain& d, uint32_t flags = dnmx_dmp_all);
53+
DYNAMIX_API void dbg_dmp(std::ostream& out, const feature_info& fi, uint32_t flags = dnmx_feature_dmp_all);
54+
DYNAMIX_API void dbg_dmp(std::ostream& out, const mutation_rule_info& mri, uint32_t flags = dnmx_mr_dmp_all);
55+
DYNAMIX_API void dbg_dmp(std::ostream& out, const mixin_info& mi, uint32_t flags = dmnx_mixin_dmp_all);
56+
DYNAMIX_API void dbg_dmp(std::ostream& out, const type& t, uint32_t flags = dnmx_type_dmp_all);
57+
58+
// does not support matching types
59+
DYNAMIX_API void dbg_dmp(std::ostream& out, const type_class& tc, uint32_t flags = dnmx_tc_dmp_all);
4560

4661
DYNAMIX_API void dbg_dmp(std::ostream& out, const object& o);
4762
}
63+
}

code/dynamix/type.hpp

+2
Original file line numberDiff line numberDiff line change
@@ -161,6 +161,8 @@ class DYNAMIX_API type : public dnmx_basic_type {
161161
void deallocate_object_buffer(allocator& alloc, void* ptr) const noexcept;
162162

163163
static const type* from_c_handle(dnmx_type_handle ht) noexcept { return static_cast<const type*>(ht); }
164+
165+
const byte_size_t buf_size() const noexcept { return m_buf_size; }
164166
private:
165167
// size of own associated buffer
166168
// the domain allocates a single buffer for a type and all of its members

scratch/CMakeLists.txt

+1-1
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
add_executable(dynamix-scratch
55
scratch.cpp
66
)
7-
target_link_libraries(dynamix-scratch dynamix::dynamix)
7+
target_link_libraries(dynamix-scratch dynamix::dynamix doctest::util doctest::doctest)
88
set_target_properties(dynamix-scratch PROPERTIES FOLDER scratch)
99

1010
add_executable(dynamix-c-scratch

0 commit comments

Comments
 (0)