CIRCT 23.0.0git
Loading...
Searching...
No Matches
Types.cpp
Go to the documentation of this file.
1//===- Types.cpp - ESI type system -----------------------------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// DO NOT EDIT!
10// This file is distributed as part of an ESI package. The source for this file
11// should always be modified within CIRCT.
12//
13//===----------------------------------------------------------------------===//
14
15#include "esi/Types.h"
16#include "esi/Values.h"
17#include <algorithm>
18#include <cstring>
19#include <format>
20#include <span>
21#include <sstream>
22
23namespace esi {
24
25// NOLINTNEXTLINE(misc-no-recursion)
26static void dumpType(std::ostream &os, const esi::Type *type, int level = 0,
27 bool oneLine = false) {
28 if (auto *uintType = dynamic_cast<const esi::UIntType *>(type)) {
29 os << "uint" << uintType->getBitWidth();
30 } else if (auto *sintType = dynamic_cast<const esi::SIntType *>(type)) {
31 os << "sint" << sintType->getBitWidth();
32 } else if (auto *bitsType = dynamic_cast<const esi::BitsType *>(type)) {
33 os << "bits" << bitsType->getBitWidth();
34 } else if (dynamic_cast<const esi::VoidType *>(type)) {
35 os << "void";
36 } else if (dynamic_cast<const esi::AnyType *>(type)) {
37 os << "any";
38 } else if (auto *aliasType = dynamic_cast<const esi::TypeAliasType *>(type)) {
39 os << aliasType->getName();
40 } else if (auto *structType = dynamic_cast<const esi::StructType *>(type)) {
41 os << "struct {";
42 const auto &fields = structType->getFields();
43 for (size_t i = 0; i < fields.size(); ++i) {
44 if (!oneLine)
45 os << std::endl << std::string(level + 2, ' ');
46 else if (i > 0)
47 os << " ";
48 const auto &[name, fieldType] = fields[i];
49 os << name << ": ";
50 dumpType(os, fieldType, level + 1, oneLine);
51 if (i < fields.size() - 1)
52 os << ",";
53 }
54 if (!oneLine)
55 os << std::endl << std::string(level, ' ');
56 os << "}";
57 } else if (auto *arrayType = dynamic_cast<const esi::ArrayType *>(type)) {
58 dumpType(os, arrayType->getElementType(), level + 1, oneLine);
59 os << "[" << arrayType->getSize() << "]";
60 } else if (auto *channelType = dynamic_cast<const esi::ChannelType *>(type)) {
61 os << "chan<";
62 dumpType(os, channelType->getInner(), level + 1, oneLine);
63 os << ">";
64 } else if (auto *bundleType = dynamic_cast<const esi::BundleType *>(type)) {
65 os << "bundle {";
66 const auto &channels = bundleType->getChannels();
67 for (size_t i = 0; i < channels.size(); ++i) {
68 if (!oneLine)
69 os << std::endl << std::string(level + 2, ' ');
70 else if (i > 0)
71 os << " ";
72 const auto &[name, direction, fieldType] = channels[i];
73 os << std::format(
74 "{} [{}]: ", direction == BundleType::To ? "to" : "from", name);
75 dumpType(os, fieldType, level + 1, oneLine);
76 if (i < channels.size() - 1)
77 os << ",";
78 }
79 if (!oneLine)
80 os << std::endl << std::string(level, ' ');
81 else
82 os << " ";
83 os << "}";
84 } else if (auto *windowType = dynamic_cast<const esi::WindowType *>(type)) {
85 os << "window[";
86 dumpType(os, windowType->getIntoType(), level + 1, oneLine);
87 os << "]";
88 } else if (auto *unionType = dynamic_cast<const esi::UnionType *>(type)) {
89 os << "union {";
90 const auto &fields = unionType->getFields();
91 for (size_t i = 0; i < fields.size(); ++i) {
92 if (!oneLine)
93 os << std::endl << std::string(level + 2, ' ');
94 else if (i > 0)
95 os << " ";
96 const auto &[name, fieldType] = fields[i];
97 os << name << ": ";
98 dumpType(os, fieldType, level + 1, oneLine);
99 if (i < fields.size() - 1)
100 os << ",";
101 }
102 if (!oneLine)
103 os << std::endl << std::string(level, ' ');
104 os << "}";
105 } else if (auto *listType = dynamic_cast<const esi::ListType *>(type)) {
106 os << "list<";
107 dumpType(os, listType->getElementType(), level + 1, oneLine);
108 os << ">";
109 } else {
110 // For unknown types, just print the type ID
111 os << type->getID();
112 }
113}
114
115void Type::dump(std::ostream &os, bool oneLine) const {
116 dumpType(os, this, oneLine ? 0 : 0, oneLine);
117}
118
119// Recurse through an ESI type and print an elaborated version of it.
120std::string Type::toString(bool oneLine) const {
121 std::stringstream ss;
122 dump(ss, oneLine);
123 return ss.str();
124}
125
126std::pair<const Type *, BundleType::Direction>
127BundleType::findChannel(std::string name) const {
128 for (auto [channelName, dir, type] : channels)
129 if (channelName == name)
130 return std::make_pair(type, dir);
131 throw std::runtime_error(
132 std::format("Channel '{}' not found in bundle", name));
133}
134
135void ChannelType::ensureValid(const std::any &obj) const {
136 return inner->ensureValid(obj);
137}
138
139MutableBitVector ChannelType::serialize(const std::any &obj) const {
140 return inner->serialize(obj);
141}
142
143std::any ChannelType::deserialize(BitVector &data) const {
144 return inner->deserialize(data);
145}
146
147void VoidType::ensureValid(const std::any &obj) const {
148 // Void type should be represented by an empty std::any or nullptr
149 if (!obj.has_value())
150 return;
151
152 try {
153 std::any_cast<std::nullptr_t>(obj);
154 return;
155 } catch (const std::bad_any_cast &) {
156 throw std::runtime_error(
157 std::format("void type must be represented by empty std::any or "
158 "nullptr, but got {}",
159 obj.type().name()));
160 }
161}
162
163std::any VoidType::deserialize(BitVector &data) const {
164 // Void carries no logical data. Transports that pad empty messages to one
165 // byte strip that byte before handing the BitVector to us, so we consume
166 // nothing here.
167 return std::any{};
168}
169
170MutableBitVector VoidType::serialize(const std::any &obj) const {
171 ensureValid(obj);
172 // Void carries no logical data. Transports that require a non-empty payload
173 // are responsible for adding their own placeholder byte.
174 return MutableBitVector(0);
175}
176
177void TypeAliasType::ensureValid(const std::any &obj) const {
179}
180
181MutableBitVector TypeAliasType::serialize(const std::any &obj) const {
182 return innerType->serialize(obj);
183}
184
186 return innerType->deserialize(data);
187}
188
189void BitsType::ensureValid(const std::any &obj) const {
190 try {
191 auto data = std::any_cast<std::vector<uint8_t>>(obj);
192 size_t expectedSize = (getWidth() + 7) / 8; // Round up to nearest byte
193 if (data.size() != expectedSize) {
194 throw std::runtime_error("wrong size: expected " +
195 std::to_string(expectedSize) + " bytes, got " +
196 std::to_string(data.size()));
197 }
198 } catch (const std::bad_any_cast &) {
199 throw std::runtime_error(std::format(
200 "must be std::vector<uint8_t>, but got {}", obj.type().name()));
201 }
202}
203
204MutableBitVector BitsType::serialize(const std::any &obj) const {
205 ensureValid(obj);
206 auto bytes = std::any_cast<std::vector<uint8_t>>(obj); // copy
207 return MutableBitVector(std::move(bytes), getWidth());
208}
209
210std::any BitsType::deserialize(BitVector &data) const {
211 uint64_t w = getWidth();
212 if (data.width() < w)
213 throw std::runtime_error(std::format("Insufficient data for bits type. "
214 " Expected {} bits, got {} bits",
215 w, data.width()));
216 BitVector view = data.slice(0, w);
217 // Materialize into byte vector sized to width. This can be shortcut by just
218 // casting the view to a mutable bit vector, and grabbing its storage.
219 MutableBitVector viewCopy(view);
220 data >>= w;
221 return std::any(viewCopy.takeStorage());
222}
223
224// Helper function to extract signed integer-like values from std::any.
225// We here support cstdint int's and esi::Int.
226static Int getIntLikeFromAny(const std::any &obj, unsigned widthHint) {
227 const std::type_info &type = obj.type();
228
229 if (type == typeid(int64_t))
230 return Int(std::any_cast<int64_t>(obj), widthHint);
231 if (type == typeid(int32_t))
232 return Int(static_cast<int64_t>(std::any_cast<int32_t>(obj)), widthHint);
233 if (type == typeid(int16_t))
234 return Int(static_cast<int64_t>(std::any_cast<int16_t>(obj)), widthHint);
235 if (type == typeid(int8_t))
236 return Int(static_cast<int64_t>(std::any_cast<int8_t>(obj)), widthHint);
237 if (type == typeid(esi::Int))
238 return std::any_cast<Int>(obj);
239
240 throw std::bad_any_cast();
241}
242
243// Helper function to extract unsigned integer-like values from std::any.
244// We here support cstdint uint's and esi::UInt.
245static UInt getUIntLikeFromAny(const std::any &obj, unsigned widthHint) {
246 const std::type_info &type = obj.type();
247
248 if (type == typeid(uint64_t))
249 return UInt(std::any_cast<uint64_t>(obj), widthHint);
250 if (type == typeid(uint32_t))
251 return UInt(static_cast<uint64_t>(std::any_cast<uint32_t>(obj)), widthHint);
252 if (type == typeid(uint16_t))
253 return UInt(static_cast<uint64_t>(std::any_cast<uint16_t>(obj)), widthHint);
254 if (type == typeid(uint8_t))
255 return UInt(static_cast<uint64_t>(std::any_cast<uint8_t>(obj)), widthHint);
256 if (type == typeid(esi::UInt))
257 return std::any_cast<UInt>(obj);
258
259 throw std::bad_any_cast();
260}
261
262void SIntType::ensureValid(const std::any &obj) const {
263 try {
264 Int value = getIntLikeFromAny(obj, getWidth());
265 } catch (const std::exception &e) {
266 throw std::runtime_error(std::format(
267 "Unable to convert provided object to a {}-bit wide Int: {}",
268 getWidth(), e.what()));
269 }
270}
271
272MutableBitVector SIntType::serialize(const std::any &obj) const {
273 Int ival = getIntLikeFromAny(obj, getWidth());
274 if (static_cast<uint64_t>(ival.width()) != getWidth())
275 throw std::runtime_error(
276 std::format("Int width mismatch for SIntType serialize. Expected {} "
277 "bits, got {} bits",
278 getWidth(), ival.width()));
279 // Move bits into MutableBitVector.
280 return MutableBitVector(std::move(ival));
281}
282
283std::any SIntType::deserialize(BitVector &data) const {
284 uint64_t w = getWidth();
285 if (data.width() < w)
286 throw std::runtime_error(std::format(
287 "Insufficient data for sint type. Expected {} bits, got {} bits", w,
288 data.width()));
289 Int val(data.slice(0, w));
290 data >>= w;
291 return std::any(val);
292}
293
294void UIntType::ensureValid(const std::any &obj) const {
295 try {
296 UInt value = getUIntLikeFromAny(obj, getWidth());
297 } catch (const std::exception &e) {
298 throw std::runtime_error(std::format(
299 "Unable to convert provided object to a {}-bit wide UInt: {}",
300 getWidth(), e.what()));
301 }
302}
303
304MutableBitVector UIntType::serialize(const std::any &obj) const {
305 UInt uval = getUIntLikeFromAny(obj, getWidth());
306 if (static_cast<uint64_t>(uval.width()) != getWidth())
307 throw std::runtime_error(std::format(
308 "UInt width mismatch for UIntType serialize. Expected {} bits, got {} "
309 "bits",
310 getWidth(), uval.width()));
311 return MutableBitVector(std::move(uval));
312}
313
314std::any UIntType::deserialize(BitVector &data) const {
315 uint64_t w = getWidth();
316 if (data.width() < w)
317 throw std::runtime_error(std::format(
318 "Insufficient data for uint type. Expected {} bits, got {} bits", w,
319 data.width()));
320 UInt val(data.slice(0, w));
321 data >>= w;
322 return std::any(val);
323}
324
325void StructType::ensureValid(const std::any &obj) const {
326 try {
327 auto structData = std::any_cast<std::map<std::string, std::any>>(obj);
328
329 if (structData.size() != fields.size()) {
330 throw std::runtime_error(std::format("struct has {} fields, expected {}",
331 structData.size(), fields.size()));
332 }
333
334 for (const auto &[fieldName, fieldType] : fields) {
335 auto it = structData.find(fieldName);
336 if (it == structData.end())
337 throw std::runtime_error(std::format("missing field '{}'", fieldName));
338
339 try {
340 fieldType->ensureValid(it->second);
341 } catch (const std::runtime_error &e) {
342 throw std::runtime_error(
343 std::format("invalid field '{}': {}", fieldName, e.what()));
344 }
345 }
346 } catch (const std::bad_any_cast &) {
347 throw std::runtime_error(
348 std::format("must be std::map<std::string, std::any>, but got {}",
349 obj.type().name()));
350 }
351}
352
353MutableBitVector StructType::serialize(const std::any &obj) const {
354 ensureValid(obj);
355 auto structData = std::any_cast<std::map<std::string, std::any>>(obj);
356 MutableBitVector out(0);
357 auto handleField = [&](const std::pair<std::string, const Type *> &f) {
358 const auto &name = f.first;
359 const Type *ty = f.second;
360 auto fieldData = ty->serialize(structData.at(name));
361 out <<= fieldData.width();
362 out |= fieldData;
363 };
364 if (isReverse()) {
365 for (const auto &f : fields)
366 handleField(f);
367 } else {
368 for (auto it = fields.rbegin(); it != fields.rend(); ++it)
369 handleField(*it);
370 }
371 return out;
372}
373
374std::any StructType::deserialize(BitVector &data) const {
375 std::map<std::string, std::any> result;
376 auto consumeField = [&](const std::pair<std::string, const Type *> &f) {
377 const auto &name = f.first;
378 const Type *ty = f.second;
379 result[name] = ty->deserialize(data);
380 };
381 if (isReverse()) {
382 for (auto it = fields.rbegin(); it != fields.rend(); ++it)
383 consumeField(*it);
384 } else {
385 for (const auto &f : fields)
386 consumeField(f);
387 }
388 return std::any(result);
389}
390
391void ArrayType::ensureValid(const std::any &obj) const {
392 try {
393 auto arrayData = std::any_cast<std::vector<std::any>>(obj);
394
395 if (arrayData.size() != size) {
396 throw std::runtime_error(std::format("array has {} elements, expected {}",
397 arrayData.size(), size));
398 }
399
400 for (size_t i = 0; i < arrayData.size(); ++i) {
401 try {
402 elementType->ensureValid(arrayData[i]);
403 } catch (const std::runtime_error &e) {
404 throw std::runtime_error(
405 std::format("invalid element {}: {}", i, e.what()));
406 }
407 }
408 } catch (const std::bad_any_cast &) {
409 throw std::runtime_error(std::format(
410 "must be std::vector<std::any>, but got {}", obj.type().name()));
411 }
412}
413
414MutableBitVector ArrayType::serialize(const std::any &obj) const {
415 ensureValid(obj);
416 auto arrayData = std::any_cast<std::vector<std::any>>(obj);
417 MutableBitVector out(0);
418 auto handleElem = [&](const std::any &elem) {
419 auto elemData = elementType->serialize(elem);
420 out <<= elemData.width();
421 out |= elemData;
422 };
423 if (isReverse()) {
424 for (const auto &e : arrayData)
425 handleElem(e);
426 } else {
427 for (auto it = arrayData.rbegin(); it != arrayData.rend(); ++it)
428 handleElem(*it);
429 }
430 return out;
431}
432
433std::any ArrayType::deserialize(BitVector &data) const {
434 std::vector<std::any> result;
435 result.reserve(size);
436 for (uint64_t i = 0; i < size; ++i) {
437 std::any value = elementType->deserialize(data);
438 result.push_back(value);
439 }
440 if (isReverse())
441 std::reverse(result.begin(), result.end());
442 return std::any(result);
443}
444
445void UnionType::ensureValid(const std::any &obj) const {
446 try {
447 auto unionData = std::any_cast<std::map<std::string, std::any>>(obj);
448
449 if (unionData.size() != 1) {
450 throw std::runtime_error(std::format(
451 "union must have exactly 1 active field, got {}", unionData.size()));
452 }
453
454 auto &[activeName, activeValue] = *unionData.begin();
455 for (const auto &[fieldName, fieldType] : fields) {
456 if (fieldName == activeName) {
457 try {
458 fieldType->ensureValid(activeValue);
459 } catch (const std::runtime_error &e) {
460 throw std::runtime_error(
461 std::format("invalid field '{}': {}", activeName, e.what()));
462 }
463 return;
464 }
465 }
466 throw std::runtime_error(
467 std::format("unknown field '{}' in union", activeName));
468 } catch (const std::bad_any_cast &) {
469 throw std::runtime_error(
470 std::format("must be std::map<std::string, std::any>, but got {}",
471 obj.type().name()));
472 }
473}
474
475MutableBitVector UnionType::serialize(const std::any &obj) const {
476 ensureValid(obj);
477 auto unionData = std::any_cast<std::map<std::string, std::any>>(obj);
478 auto &[activeName, activeValue] = *unionData.begin();
479
480 const Type *activeType = nullptr;
481 for (const auto &[fieldName, fieldType] : fields) {
482 if (fieldName == activeName) {
483 activeType = fieldType;
484 break;
485 }
486 }
487
488 MutableBitVector fieldBits = activeType->serialize(activeValue);
489 std::ptrdiff_t unionWidth = getBitWidth();
490 // In a packed union, field data occupies the MSBs and padding (zeros)
491 // occupies the LSBs. Shift field data up by the padding amount.
492 if (fieldBits.width() < static_cast<uint64_t>(unionWidth)) {
493 uint64_t padBits = unionWidth - fieldBits.width();
494 fieldBits <<= padBits;
495 return fieldBits;
496 }
497 return fieldBits;
498}
499
500std::any UnionType::deserialize(BitVector &data) const {
501 // Deserialize all fields from the same bit range, since we don't know
502 // which field is active in a packed union.
503 std::ptrdiff_t unionWidth = getBitWidth();
504 if (data.width() < static_cast<uint64_t>(unionWidth))
505 throw std::runtime_error(std::format("Insufficient data for union type. "
506 " Expected {} bits, got {} bits",
507 unionWidth, data.width()));
508
509 BitVector unionBits = data.slice(0, unionWidth);
510 std::map<std::string, std::any> result;
511 for (const auto &[fieldName, fieldType] : fields) {
512 // In a packed union, field data is at the MSBs. Skip the LSB padding
513 // to reach each field's data.
514 std::ptrdiff_t fieldWidth = fieldType->getBitWidth();
515 uint64_t padBits = unionWidth - fieldWidth;
516 BitVector fieldData(unionBits);
517 fieldData >>= padBits;
518 result[fieldName] = fieldType->deserialize(fieldData);
519 }
520 data >>= unionWidth;
521 return std::any(result);
522}
523} // namespace esi
The "any" type is a special type which can be used to represent any type, as identified by the type i...
Definition Types.h:159
Arrays have a compile time specified (static) size and an element type.
Definition Types.h:283
uint64_t size
Definition Types.h:306
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:414
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:391
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:433
const Type * elementType
Definition Types.h:305
bool isReverse() const
Definition Types.h:292
uint64_t getWidth() const
Definition Types.h:197
A lightweight, non-owning bit vector view backed by a byte array span.
Definition Values.h:51
size_t width() const
Definition Values.h:63
Bits are just an array of bits.
Definition Types.h:206
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:189
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:210
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:204
Bundles represent a collection of channels.
Definition Types.h:104
ChannelVector channels
Definition Types.h:120
std::pair< const Type *, Direction > findChannel(std::string name) const
Definition Types.cpp:127
Channels are the basic communication primitives.
Definition Types.h:125
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:135
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:139
const Type * inner
Definition Types.h:137
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:143
Lists represent variable-length sequences of elements of a single type.
Definition Types.h:386
A mutable bit vector that owns its underlying storage.
Definition Values.h:278
std::vector< uint8_t > takeStorage()
Return and transfer ownership of the underlying storage.
Definition Values.h:312
Signed integer.
Definition Types.h:224
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:283
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:272
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:262
Structs are an ordered collection of fields, each with a name and a type.
Definition Types.h:246
bool isReverse() const
Definition Types.h:275
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:325
FieldVector fields
Definition Types.h:278
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:353
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:374
Type aliases provide a named type which forwards to an inner type.
Definition Types.h:166
const Type * innerType
Definition Types.h:189
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:177
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:185
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:181
Root class of the ESI type system.
Definition Types.h:36
virtual void ensureValid(const std::any &obj) const
Ensure that a std::any object is valid for this type.
Definition Types.h:74
std::string toString(bool oneLine=false) const
Definition Types.cpp:120
virtual std::any deserialize(BitVector &data) const
Deserialize from a BitVector stream (LSB-first).
Definition Types.h:60
ID getID() const
Definition Types.h:42
virtual MutableBitVector serialize(const std::any &obj) const
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.h:53
void dump(std::ostream &os, bool oneLine=false) const
Definition Types.cpp:115
Unsigned integer.
Definition Types.h:235
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:314
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:304
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:294
Unions are a tagged collection of fields where only one field is active at a time.
Definition Types.h:356
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:475
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:445
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:500
std::ptrdiff_t getBitWidth() const override
Definition Types.h:365
FieldVector fields
Definition Types.h:381
The "void" type is a special type which can be used to represent no type.
Definition Types.h:141
std::any deserialize(BitVector &data) const override
Deserialize from a BitVector stream (LSB-first).
Definition Types.cpp:163
void ensureValid(const std::any &obj) const override
Ensure that a std::any object is valid for this type.
Definition Types.cpp:147
MutableBitVector serialize(const std::any &obj) const override
Serialize an object to a MutableBitVector (LSB-first stream).
Definition Types.cpp:170
Windows represent a fixed-size sliding window over a stream of data.
Definition Types.h:316
Definition esi.py:1
static UInt getUIntLikeFromAny(const std::any &obj, unsigned widthHint)
Definition Types.cpp:245
static Int getIntLikeFromAny(const std::any &obj, unsigned widthHint)
Definition Types.cpp:226
static void dumpType(std::ostream &os, const esi::Type *type, int level=0, bool oneLine=false)
Definition Types.cpp:26