barretenberg
Loading...
Searching...
No Matches
uint.hpp
1#pragma once
2#include "../bool/bool.hpp"
3#include "../byte_array/byte_array.hpp"
4#include "../circuit_builders/circuit_builders_fwd.hpp"
5#include "../field/field.hpp"
6#include "../plookup/plookup.hpp"
7
8#include "./plookup/uint.hpp"
9
10namespace proof_system::plonk {
11namespace stdlib {
12
24template <typename Builder, typename Native> class uint {
25 // We only instantiate for widths 8, 16, 32 and 64, and only those widths were audited.
26 static_assert((sizeof(Native) == 1) || (sizeof(Native) == 2) || (sizeof(Native) == 4) || (sizeof(Native) == 8));
27
28 public:
29 static constexpr size_t width = sizeof(Native) * 8;
30
31 uint(const witness_t<Builder>& other);
32 uint(const field_t<Builder>& other);
33 uint(const uint256_t& value = 0);
34 uint(Builder* builder, const uint256_t& value = 0);
35 uint(const byte_array<Builder>& other);
36 // constructors used for bit arrays
37 uint(Builder* parent_context, const std::vector<bool_t<Builder>>& wires);
38 uint(Builder* parent_context, const std::array<bool_t<Builder>, width>& wires);
39
40 uint(const Native v)
41 : uint(static_cast<uint256_t>(v))
42 {}
43
44 std::vector<uint32_t> constrain_accumulators(Builder* ctx,
45 const uint32_t witness_index,
46 const size_t num_bits,
47 std::string const& msg) const;
48
49 static constexpr size_t num_accumulators()
50 {
51 return (width + Builder::UINT_LOG2_BASE - 1) / Builder::UINT_LOG2_BASE;
52 }
53
54 uint(const uint& other);
55 uint(uint&& other);
56
57 uint& operator=(const uint& other);
58 uint& operator=(uint&& other);
59
60 explicit operator byte_array<Builder>() const;
61 explicit operator field_t<Builder>() const;
62
63 uint operator+(const uint& other) const;
64 uint operator-(const uint& other) const;
65 uint operator*(const uint& other) const;
66 uint operator/(const uint& other) const;
67 uint operator%(const uint& other) const;
68
69 uint operator&(const uint& other) const;
70 uint operator^(const uint& other) const;
71 uint operator|(const uint& other) const;
72 uint operator~() const;
73
74 uint operator>>(const size_t shift) const;
75 uint operator<<(const size_t shift) const;
76
77 uint ror(const size_t target_rotation) const;
78 uint rol(const size_t target_rotation) const;
79 uint ror(const uint256_t target_rotation) const { return ror(static_cast<size_t>(target_rotation.data[0])); }
80 uint rol(const uint256_t target_rotation) const { return rol(static_cast<size_t>(target_rotation.data[0])); }
81
82 bool_t<Builder> operator>(const uint& other) const;
83 bool_t<Builder> operator<(const uint& other) const;
84 bool_t<Builder> operator>=(const uint& other) const;
85 bool_t<Builder> operator<=(const uint& other) const;
86 bool_t<Builder> operator==(const uint& other) const;
87 bool_t<Builder> operator!=(const uint& other) const;
88 bool_t<Builder> operator!() const;
89
90 uint operator+=(const uint& other)
91 {
92 *this = operator+(other);
93 return *this;
94 }
95 uint operator-=(const uint& other)
96 {
97 *this = operator-(other);
98 return *this;
99 }
100 uint operator*=(const uint& other)
101 {
102 *this = operator*(other);
103 return *this;
104 }
105 uint operator/=(const uint& other)
106 {
107 *this = operator/(other);
108 return *this;
109 }
110 uint operator%=(const uint& other)
111 {
112 *this = operator%(other);
113 return *this;
114 }
115
116 uint operator&=(const uint& other)
117 {
118 *this = operator&(other);
119 return *this;
120 }
121 uint operator^=(const uint& other)
122 {
123 *this = operator^(other);
124 return *this;
125 }
126 uint operator|=(const uint& other)
127 {
128 *this = operator|(other);
129 return *this;
130 }
131
132 uint operator>>=(const size_t shift)
133 {
134 *this = operator>>(shift);
135 return *this;
136 }
137 uint operator<<=(const size_t shift)
138 {
139 *this = operator<<(shift);
140 return *this;
141 }
142
143 uint256_t get_mask() const { return MASK; };
144
145 uint normalize() const;
146
147 uint256_t get_value() const;
148
149 bool is_constant() const { return witness_index == IS_CONSTANT; }
150 Builder* get_context() const { return context; }
151
152 bool_t<Builder> at(const size_t bit_index) const;
153
154 size_t get_width() const { return width; }
155
156 uint32_t get_witness_index() const { return witness_index; }
157
158 uint256_t get_additive_constant() const { return additive_constant; }
159
160 protected:
161 Builder* context;
162
163 enum WitnessStatus { OK, NOT_NORMALIZED, WEAK_NORMALIZED };
164
165 mutable uint256_t additive_constant;
166 mutable WitnessStatus witness_status;
167 mutable std::vector<uint32_t> accumulators;
168 mutable uint32_t witness_index;
169
170 static constexpr uint256_t CIRCUIT_UINT_MAX_PLUS_ONE = (uint256_t(1) << width);
171 static constexpr uint256_t MASK = CIRCUIT_UINT_MAX_PLUS_ONE - 1;
172
173 private:
174 enum LogicOp {
175 AND,
176 XOR,
177 };
178
179 std::pair<uint, uint> divmod(const uint& other) const;
180 uint logic_operator(const uint& other, const LogicOp op_type) const;
181 uint weak_normalize() const;
182
183 uint256_t get_unbounded_value() const;
184};
185
186template <typename T, typename w> inline std::ostream& operator<<(std::ostream& os, uint<T, w> const& v)
187{
188 return os << v.get_value();
189}
190
191template <typename Builder>
192using uint8 =
193 typename std::conditional<HasPlookup<Builder>, uint_plookup<Builder, uint8_t>, uint<Builder, uint8_t>>::type;
194template <typename Builder>
195using uint16 =
196 typename std::conditional<HasPlookup<Builder>, uint_plookup<Builder, uint16_t>, uint<Builder, uint16_t>>::type;
197template <typename Builder>
198using uint32 =
199 typename std::conditional<HasPlookup<Builder>, uint_plookup<Builder, uint32_t>, uint<Builder, uint32_t>>::type;
200template <typename Builder>
201using uint64 =
202 typename std::conditional<HasPlookup<Builder>, uint_plookup<Builder, uint64_t>, uint<Builder, uint64_t>>::type;
203
204EXTERN_STDLIB_BASIC_TYPE_VA(uint, uint8_t);
205EXTERN_STDLIB_BASIC_TYPE_VA(uint, uint16_t);
206EXTERN_STDLIB_BASIC_TYPE_VA(uint, uint32_t);
207EXTERN_STDLIB_BASIC_TYPE_VA(uint, uint64_t);
208
209} // namespace stdlib
210} // namespace proof_system::plonk
Definition: uint256.hpp:25
Definition: standard_circuit_builder.hpp:12
Definition: byte_array.hpp:9
Definition: field.hpp:10
A standard library fixed-width unsigned integer type. Useful, e.g., for hashing. Use safe_uint instea...
Definition: uint.hpp:24
uint operator+(const uint &other) const
Return a uint which, if range constrained, would be proven to be the sum of self and other.
Definition: arithmetic.cpp:40
uint ror(const size_t target_rotation) const
Definition: logic.cpp:295
bool_t< Builder > at(const size_t bit_index) const
Extract the bit value at a given position.
Definition: uint.cpp:285
uint operator<<(const size_t shift) const
Definition: logic.cpp:159
uint operator>>(const size_t shift) const
Right shift a uint.
Definition: logic.cpp:42
uint operator*(const uint &other) const
Multiply two uint_ct's, trucating overflowing bits.
Definition: arithmetic.cpp:191
bool_t< Builder > operator>(const uint &other) const
Determine whether this > other.
Definition: comparison.cpp:17
uint operator-(const uint &other) const
Return a uint which, if range constrained, would be proven to be the difference of self and other.
Definition: arithmetic.cpp:130
uint normalize() const
For non-constants, weakly normalize and constrain the updated witness to width-many bits.
Definition: uint.cpp:239
std::vector< uint32_t > constrain_accumulators(Builder *ctx, const uint32_t witness_index, const size_t num_bits, std::string const &msg) const
Constrain accumulators.
Definition: uint.cpp:14
Definition: witness.hpp:10
Definition: widget.bench.cpp:13