• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

tudasc / TypeART / 24397737785

14 Apr 2026 12:00PM UTC coverage: 90.264% (+1.3%) from 88.924%
24397737785

Pull #187

github

web-flow
Merge 278119205 into de3bc148a
Pull Request #187: Release v2.2

880 of 935 new or added lines in 31 files covered. (94.12%)

17 existing lines in 3 files now uncovered.

4886 of 5413 relevant lines covered (90.26%)

38873.79 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

95.69
/lib/runtime/GlobalTypeDefCallbacks.cpp
1
#include "GlobalTypeDefCallbacks.h"
2

3
#include "CallbackInterface.h"
4
#include "Runtime.h"
5
#include "RuntimeData.h"
6
#include "TypeInterface.h"
7
#include "support/Logger.h"
8
#include "typelib/TypeDatabase.h"
9

10
#include <cassert>
11
#include <cstddef>
12
#include <cstdint>
13
#include <sys/types.h>
14
#include <vector>
15

16
namespace typeart {
17

18
namespace global_types {
19
struct GlobalTypeInfoData {
20
 private:
21
  const char* name_;
22
  // Layout : [ num_member, flag, offsets...[num_member], array_sizes...[num_member] ]
23
  const std::uint16_t* data_;
24
  const GlobalTypeInfo** member_types_;
25

26
 public:
27
  [[nodiscard]] const char* name() const {
4,530 ✔
28
    assert(name_ != nullptr && "Name should not be NULL");
9,060 ✔
29
    return name_;
4,530 ✔
30
  }
31

32
  [[nodiscard]] const GlobalTypeInfo** member_types() const {
5,050 ✔
33
    return member_types_;
5,050 ✔
34
  }
35

36
  [[nodiscard]] uint16_t num_member() const {
7,315 ✔
37
    assert(data_ != nullptr && "Data should not be NULL");
14,630 ✔
38
    return data_[0];
7,315 ✔
39
  }
40

41
  [[nodiscard]] uint16_t flag() const {
2,265 ✔
42
    assert(data_ != nullptr && "Data should not be NULL");
4,530 ✔
43
    return data_[1];
2,265 ✔
44
  }
45

46
  [[nodiscard]] const uint16_t* offsets() const {
5,050 ✔
47
    return &data_[2];
5,050 ✔
48
  }
49

50
  [[nodiscard]] const uint16_t* array_sizes() const {
5,050 ✔
51
    return &data_[2 + num_member()];
5,050 ✔
52
  }
53
};
54
}  // namespace global_types
55

56
using namespace typeart::global_types;
57

58
class TypeInfoHandle {
59
 public:
60
  explicit TypeInfoHandle(const GlobalTypeInfo* info) : info_(info) {
8,605 ✔
61
  }
8,605 ✔
62

63
  [[nodiscard]] bool is_valid() const {
8,605 ✔
64
    return info_ != nullptr;
8,605 ✔
65
  }
66

67
  [[nodiscard]] const GlobalTypeInfo* handle() const {
14,395 ✔
68
    return info_;
14,395 ✔
69
  }
70

71
  [[nodiscard]] std::int32_t type_id() const {
6,045 ✔
72
    return info_->type_id;
6,045 ✔
73
  }
74

408 ✔
75
  [[nodiscard]] std::uint32_t extent() const {
2,265 ✔
76
    return info_->extent;
2,265 ✔
77
  }
78

79
  [[nodiscard]] bool is_builtin() const {
3,525 ✔
80
    return builtins::BuiltInQuery::is_builtin_type(type_id());
3,525 ✔
81
  }
82

83
  [[nodiscard]] bool has_metadata() const {
2,265 ✔
84
    return info_->data != nullptr;
2,265 ✔
85
  }
86

87
  [[nodiscard]] const char* name() const {
2,265 ✔
88
    return info_->data->name();
2,265 ✔
89
  }
90

91
  [[nodiscard]] std::uint16_t num_members() const {
2,265 ✔
92
    return info_->data->num_member();
2,265 ✔
93
  }
94

95
  [[nodiscard]] std::uint16_t flags() const {
2,265 ✔
96
    return info_->data->flag();
2,265 ✔
97
  }
98

99
  [[nodiscard]] TypeInfoHandle get_member_type(size_t index) const {
5,050 ✔
100
    return TypeInfoHandle(info_->data->member_types()[index]);
5,050 ✔
101
  }
102

103
  [[nodiscard]] std::uint16_t get_offset(size_t index) const {
5,050 ✔
104
    return info_->data->offsets()[index];
5,050 ✔
105
  }
106

107
  [[nodiscard]] std::uint16_t get_array_size(size_t index) const {
5,050 ✔
108
    return info_->data->array_sizes()[index];
5,050 ✔
109
  }
110

111
 private:
112
  const GlobalTypeInfo* info_;
113
};
114

115
#define unlikely(x)   __builtin_expect(!!(x), 0)
116
#define CONCAT_(x, y) x##y
117
#define CONCAT(x, y)  CONCAT_(x, y)
118
#define GUARDNAME     CONCAT(typeart_guard_, __LINE__)
119
#define TYPEART_RUNTIME_GUARD     \
120
  typeart::RTGuard GUARDNAME;     \
121
  if (!GUARDNAME.shouldTrack()) { \
122
    return;                       \
123
  }
124

125
class GlobalTypeTranslator::Impl {
126
  TypeDatabase& type_db_;
127
  RuntimeT::TypeLookupMapT& translator_map_;
128
  int struct_count{0};
1,421 ✔
129

130
 public:
131
  explicit Impl(TypeDatabase& db, RuntimeT::TypeLookupMapT& translator_map)
1,421 ✔
132
      : type_db_(db), translator_map_(translator_map) {
1,421 ✔
133
  }
1,421 ✔
134

135
  int next_type_id(const GlobalTypeInfo* type) {
2,265 ✔
136
    // a fwd_decl and the decl must have the same type_id:
137
    {
138
      const auto& struct_list            = type_db_.getStructList();
2,265 ✔
139
      const auto* const global_type_name = type->data->name();
2,265 ✔
140
      for (const auto& type_in_db : struct_list) {
22,890 ✔
141
        if (type_in_db.name == global_type_name) {
20,625 ✔
NEW
142
          return type_in_db.type_id;
×
143
        }
144
      }
20,625 ✔
145
    }
2,265 ✔
146
    const int id = static_cast<int>(TYPEART_NUM_RESERVED_IDS) + struct_count;
2,265 ✔
147
    ++struct_count;
2,265 ✔
148
    return id;
2,265 ✔
149
  }
2,265 ✔
150

151
  int register_t(TypeInfoHandle type_handle) {
8,605 ✔
152
    if (unlikely(!type_handle.is_valid())) {
8,605 ✔
NEW
153
      LOG_ERROR("Type descriptor is NULL, is it a weak extern global due to fwd decl?");
×
NEW
154
      return TYPEART_UNKNOWN_TYPE;
×
155
    }
156

157
    if (auto element = translator_map_.find(type_handle.handle()); element != translator_map_.end()) {
13,685 ✔
158
      return element->second;
5,080 ✔
159
    }
160

161
    if (type_handle.is_builtin()) {
3,525 ✔
162
      translator_map_.try_emplace(type_handle.handle(), type_handle.type_id());
1,260 ✔
163
      return type_handle.type_id();
1,260 ✔
164
    }
165

166
    assert(type_handle.has_metadata() && "Required metadata is NULL");
4,530 ✔
167

168
    StructTypeInfo type_descriptor;
2,265 ✔
169
    type_descriptor.type_id     = next_type_id(type_handle.handle());
2,265 ✔
170
    type_descriptor.name        = type_handle.name();
2,265 ✔
171
    type_descriptor.extent      = type_handle.extent();
2,265 ✔
172
    type_descriptor.num_members = type_handle.num_members();
2,265 ✔
173
    type_descriptor.flag        = static_cast<StructTypeFlag>(type_handle.flags());
2,265 ✔
174

175
    const auto member_count = type_descriptor.num_members;
2,265 ✔
176
    type_descriptor.array_sizes.reserve(member_count);
2,265 ✔
177
    type_descriptor.offsets.reserve(member_count);
2,265 ✔
178
    type_descriptor.member_types.reserve(member_count);
2,265 ✔
179

180
    for (size_t i = 0; i < member_count; ++i) {
7,315 ✔
181
      const auto member_id  = register_t(type_handle.get_member_type(i));
5,050 ✔
182
      const auto array_size = type_handle.get_array_size(i);
5,050 ✔
183
      const auto offset     = type_handle.get_offset(i);
5,050 ✔
184

185
      type_descriptor.array_sizes.emplace_back(array_size);
5,050 ✔
186
      type_descriptor.offsets.emplace_back(offset);
5,050 ✔
187
      type_descriptor.member_types.emplace_back(member_id);
5,050 ✔
188
    }
5,050 ✔
189

190
    const bool fwd_decl = type_descriptor.flag == StructTypeFlag::FWD_DECL;
2,265 ✔
191
    {
192
      LOG_DEBUG("StructTypeInfo Dump " << (fwd_decl ? "FWD" : "") << type_descriptor.name);
2,265 ✔
193
      LOG_DEBUG("  Type_id: " << type_descriptor.type_id);
2,265 ✔
194
      LOG_DEBUG("  Extent: " << type_descriptor.extent);
2,265 ✔
195
      LOG_DEBUG("  Num Members: " << type_descriptor.num_members);
2,265 ✔
196
      LOG_DEBUG("  Flag: " << static_cast<int>(type_descriptor.flag));
2,265 ✔
197
      for (uint32_t i = 0; i < type_descriptor.num_members; ++i) {
7,315 ✔
198
        LOG_DEBUG("  Member[" << i << "]: "
6,060 ✔
199
                              << "ID=" << type_db_.getTypeName(type_descriptor.member_types[i]) << ", Offset="
1,010 ✔
200
                              << type_descriptor.offsets[i] << ", ArraySize=" << type_descriptor.array_sizes[i]);
1,010 ✔
201
      }
5,050 ✔
202
    }
203

204
    type_db_.registerStruct(type_descriptor, not fwd_decl);
2,265 ✔
205
    translator_map_.try_emplace(type_handle.handle(), type_descriptor.type_id);
2,265 ✔
206

207
    return type_descriptor.type_id;
2,265 ✔
208
  }
8,605 ✔
209
};
210

211
GlobalTypeTranslator::GlobalTypeTranslator(TypeDatabase& db) : pImpl(std::make_unique<Impl>(db, translator_map)) {
1,421 ✔
212
}
1,421 ✔
213

214
GlobalTypeTranslator::~GlobalTypeTranslator() = default;
1,421 ✔
215

216
void GlobalTypeTranslator::register_type(const void* type) {
3,555 ✔
217
  const auto* info_struct                           = reinterpret_cast<const GlobalTypeInfo*>(type);
3,555 ✔
218
  const auto type_id                                = pImpl->register_t(TypeInfoHandle{info_struct});
3,555 ✔
219
  const_cast<GlobalTypeInfo*>(info_struct)->type_id = type_id;
3,555 ✔
220
}
3,555 ✔
221

222
}  // namespace typeart
223

224
void __typeart_register_type(const void* type_ptr) {
3,555 ✔
225
  TYPEART_RUNTIME_GUARD;
3,555 ✔
226
  if (unlikely(type_ptr == nullptr)) {
3,555 ✔
NEW
227
    LOG_FATAL("type_ptr is NULL\n");
×
NEW
228
    return;
×
229
  }
230
  typeart::RuntimeSystem::get().type_translator().register_type(type_ptr);
3,555 ✔
231
}
3,555 ✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc