Spicy
bitfield.h
1 // Copyright (c) 2020-2021 by the Zeek Project. See LICENSE for details.
2 
3 #pragma once
4 
5 #include <utility>
6 #include <vector>
7 
8 #include <hilti/ast/attribute.h>
9 #include <hilti/ast/expression.h>
10 #include <hilti/ast/function.h>
11 #include <hilti/ast/id.h>
12 #include <hilti/ast/type.h>
13 #include <hilti/ast/types/function.h>
14 #include <hilti/ast/types/integer.h>
15 #include <hilti/ast/types/unknown.h>
16 
17 #include <spicy/ast/aliases.h>
18 
19 namespace spicy {
20 namespace type {
21 
22 namespace bitfield {
23 
25 class Bits : public hilti::NodeBase {
26 public:
27  Bits() : NodeBase({ID("<no id>"), hilti::node::none}, Meta()) {}
28  Bits(ID id, int lower, int upper, int field_width, std::optional<AttributeSet> attrs = {}, Meta m = Meta())
29  : hilti::NodeBase(nodes(std::move(id), std::move(attrs)), std::move(m)),
30  _lower(lower),
31  _upper(upper),
32  _field_width(field_width) {}
33 
34  const auto& id() const { return child<ID>(0); }
35  auto lower() const { return _lower; }
36  auto upper() const { return _upper; }
37  Type type() const;
38  auto attributes() const { return childs()[1].tryReferenceAs<AttributeSet>(); }
39 
41  auto properties() const {
42  return node::Properties{
43  {"lower", _lower},
44  {"upper", _upper},
45  {"field_width", _field_width},
46  };
47  }
48 
49  bool operator==(const Bits& other) const {
50  return id() == other.id() && _lower == other._lower && _upper == other._upper &&
51  _field_width == other._field_width && attributes() == other.attributes();
52  }
53 
61  static Bits setAttributes(const Bits& f, const AttributeSet& attrs) {
62  auto x = Bits(f);
63  x.childs()[1] = attrs;
64  return x;
65  }
66 
67 private:
68  int _lower{0};
69  int _upper{0};
70  int _field_width{0};
71 };
72 
73 inline hilti::Node to_node(Bits f) { return hilti::Node(std::move(f)); }
74 
75 } // namespace bitfield
76 
78 class Bitfield : public hilti::TypeBase,
82 public:
83  Bitfield(int width, std::vector<bitfield::Bits> bits, Meta m = Meta())
84  : TypeBase(nodes(std::move(bits)), std::move(m)), _width(width) {}
85  Bitfield(Wildcard /*unused*/, Meta m = Meta()) : TypeBase({}, std::move(m)), _wildcard(true) {}
86 
87  int width() const { return _width; }
88  auto bits() const { return childsOfType<bitfield::Bits>(); }
89  std::optional<bitfield::Bits> bits(const ID& id) const;
90  std::optional<int> bitsIndex(const ID& id) const;
91  Type type() const;
92 
93  bool operator==(const Bitfield& other) const { return width() == other.width() && bits() == other.bits(); }
94 
96  auto _bitsNodes() { return nodesOfType<bitfield::Bits>(); }
97 
99  auto isEqual(const Type& other) const { return node::isEqual(this, other); }
101  auto typeParameters() const { return hilti::util::slice(childs(), 1); }
103  auto isWildcard() const { return _wildcard; }
105  auto properties() const { return node::Properties{}; }
106 
114  static Bitfield addField(const Bitfield& s, bitfield::Bits f) {
115  auto x = Type(s)._clone().as<Bitfield>();
116  x.addChild(std::move(f));
117  return x;
118  }
119 
120 private:
121  int _width = 0;
122  bool _wildcard = false;
123 };
124 
125 } // namespace type
126 } // namespace spicy
auto isEqual(const Type &other) const
Definition: bitfield.h:99
NodeBase(Meta meta)
Definition: node.h:325
auto typeParameters() const
Definition: bitfield.h:101
auto & childs() const
Definition: node.h:445
Definition: bitfield.h:25
auto properties() const
Definition: bitfield.h:41
const Node none
Definition: node.cc:12
auto _bitsNodes()
Definition: bitfield.h:96
Definition: bitfield.h:78
void addChild(Node n)
Definition: node.h:434
Definition: type.h:27
Definition: meta.h:18
Definition: attribute.h:159
static Bitfield addField(const Bitfield &s, bitfield::Bits f)
Definition: bitfield.h:114
Definition: type.h:152
auto isWildcard() const
Definition: bitfield.h:103
Definition: node.h:97
auto properties() const
Definition: bitfield.h:105
Definition: type.h:23
Definition: type.h:249
static Bits setAttributes(const Bits &f, const AttributeSet &attrs)
Definition: bitfield.h:61
std::vector< T > slice(const std::vector< T > &v, int begin, int end=-1)
Definition: util.h:196
Definition: id.h:18
Definition: node.h:318