da4ml 0.2.0__py3-none-any.whl → 0.3.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of da4ml might be problematic. Click here for more details.
- da4ml/_version.py +2 -2
- da4ml/cmvm/api.py +2 -6
- da4ml/cmvm/core/__init__.py +0 -1
- da4ml/cmvm/types.py +99 -19
- da4ml/codegen/__init__.py +5 -4
- da4ml/codegen/cpp/__init__.py +2 -1
- da4ml/codegen/cpp/cpp_codegen.py +58 -25
- da4ml/codegen/cpp/hls_model.py +252 -0
- da4ml/codegen/cpp/source/ap_types/ap_binary.h +78 -0
- da4ml/codegen/cpp/source/ap_types/ap_common.h +376 -0
- da4ml/codegen/cpp/source/ap_types/ap_decl.h +212 -0
- da4ml/codegen/cpp/source/ap_types/ap_fixed.h +360 -0
- da4ml/codegen/cpp/source/ap_types/ap_fixed_base.h +2354 -0
- da4ml/codegen/cpp/source/ap_types/ap_fixed_ref.h +718 -0
- da4ml/codegen/cpp/source/ap_types/ap_fixed_special.h +230 -0
- da4ml/codegen/cpp/source/ap_types/ap_int.h +330 -0
- da4ml/codegen/cpp/source/ap_types/ap_int_base.h +1885 -0
- da4ml/codegen/cpp/source/ap_types/ap_int_ref.h +1346 -0
- da4ml/codegen/cpp/source/ap_types/ap_int_special.h +223 -0
- da4ml/codegen/cpp/source/ap_types/ap_shift_reg.h +138 -0
- da4ml/codegen/cpp/source/ap_types/etc/ap_private.h +7199 -0
- da4ml/codegen/cpp/source/ap_types/hls_math.h +27 -0
- da4ml/codegen/cpp/source/ap_types/hls_stream.h +263 -0
- da4ml/codegen/cpp/source/ap_types/utils/x_hls_utils.h +80 -0
- da4ml/codegen/cpp/source/binder_util.hh +56 -0
- da4ml/codegen/cpp/source/build_binder.mk +24 -0
- da4ml/codegen/cpp/source/{vitis.h → vitis_bitshift.hh} +1 -1
- da4ml/codegen/verilog/__init__.py +2 -3
- da4ml/codegen/verilog/comb.py +65 -24
- da4ml/codegen/verilog/io_wrapper.py +36 -141
- da4ml/codegen/verilog/pipeline.py +21 -3
- da4ml/codegen/verilog/source/binder_util.hh +72 -0
- da4ml/codegen/verilog/source/build_prj.tcl +0 -1
- da4ml/codegen/verilog/source/mux.v +58 -0
- da4ml/codegen/verilog/source/negative.v +28 -0
- da4ml/codegen/verilog/source/shift_adder.v +4 -1
- da4ml/codegen/verilog/source/template.xdc +3 -0
- da4ml/codegen/verilog/verilog_model.py +42 -15
- da4ml/converter/__init__.py +0 -0
- da4ml/converter/hgq2/parser.py +105 -0
- da4ml/converter/hgq2/replica.py +383 -0
- da4ml/trace/__init__.py +2 -2
- da4ml/trace/fixed_variable.py +177 -18
- da4ml/trace/fixed_variable_array.py +124 -9
- da4ml/trace/ops/__init__.py +22 -6
- da4ml/trace/ops/conv_utils.py +146 -14
- da4ml/trace/ops/einsum_utils.py +9 -6
- da4ml/trace/ops/reduce_utils.py +103 -0
- da4ml/trace/pipeline.py +36 -34
- da4ml/trace/tracer.py +37 -5
- da4ml-0.3.0.dist-info/METADATA +107 -0
- da4ml-0.3.0.dist-info/RECORD +64 -0
- da4ml/codegen/cpp/source/vitis_bridge.h +0 -17
- da4ml-0.2.0.dist-info/METADATA +0 -65
- da4ml-0.2.0.dist-info/RECORD +0 -39
- /da4ml/codegen/verilog/source/{ioutils.hh → ioutil.hh} +0 -0
- {da4ml-0.2.0.dist-info → da4ml-0.3.0.dist-info}/WHEEL +0 -0
- {da4ml-0.2.0.dist-info → da4ml-0.3.0.dist-info}/licenses/LICENSE +0 -0
- {da4ml-0.2.0.dist-info → da4ml-0.3.0.dist-info}/top_level.txt +0 -0
|
@@ -0,0 +1,1346 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2011-2019 Xilinx, Inc.
|
|
3
|
+
*
|
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
5
|
+
* you may not use this file except in compliance with the License.
|
|
6
|
+
* You may obtain a copy of the License at
|
|
7
|
+
*
|
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
9
|
+
*
|
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13
|
+
* See the License for the specific language governing permissions and
|
|
14
|
+
* limitations under the License.
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
#ifndef __AP_INT_REF_H__
|
|
18
|
+
#define __AP_INT_REF_H__
|
|
19
|
+
|
|
20
|
+
#ifndef __AP_INT_H__
|
|
21
|
+
#error "Only ap_fixed.h and ap_int.h can be included directly in user code."
|
|
22
|
+
#endif
|
|
23
|
+
|
|
24
|
+
#ifndef __cplusplus
|
|
25
|
+
#error "C++ is required to include this header file"
|
|
26
|
+
|
|
27
|
+
#else
|
|
28
|
+
|
|
29
|
+
#ifndef __SYNTHESIS__
|
|
30
|
+
#include <iostream>
|
|
31
|
+
#endif
|
|
32
|
+
|
|
33
|
+
/* Concatination reference.
|
|
34
|
+
----------------------------------------------------------------
|
|
35
|
+
*/
|
|
36
|
+
template <int _AP_W1, typename _AP_T1, int _AP_W2, typename _AP_T2>
|
|
37
|
+
struct ap_concat_ref {
|
|
38
|
+
enum {
|
|
39
|
+
_AP_WR = _AP_W1 + _AP_W2,
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
_AP_T1& mbv1;
|
|
43
|
+
_AP_T2& mbv2;
|
|
44
|
+
|
|
45
|
+
INLINE ap_concat_ref(const ap_concat_ref<_AP_W1, _AP_T1, _AP_W2, _AP_T2>& ref)
|
|
46
|
+
: mbv1(ref.mbv1), mbv2(ref.mbv2) {}
|
|
47
|
+
|
|
48
|
+
INLINE ap_concat_ref(_AP_T1& bv1, _AP_T2& bv2) : mbv1(bv1), mbv2(bv2) {}
|
|
49
|
+
|
|
50
|
+
template <int _AP_W3, bool _AP_S3>
|
|
51
|
+
INLINE ap_concat_ref& operator=(const ap_int_base<_AP_W3, _AP_S3>& val) {
|
|
52
|
+
ap_int_base<_AP_W1 + _AP_W2, false> vval(val);
|
|
53
|
+
int W_ref1 = mbv1.length();
|
|
54
|
+
int W_ref2 = mbv2.length();
|
|
55
|
+
ap_int_base<_AP_W1, false> Part1;
|
|
56
|
+
Part1.V = _AP_ROOT_op_get_range(vval.V, W_ref2, W_ref1 + W_ref2 - 1);
|
|
57
|
+
mbv1.set(Part1);
|
|
58
|
+
ap_int_base<_AP_W2, false> Part2;
|
|
59
|
+
Part2.V = _AP_ROOT_op_get_range(vval.V, 0, W_ref2 - 1);
|
|
60
|
+
mbv2.set(Part2);
|
|
61
|
+
return *this;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
// assign op from hls supported C integral types.
|
|
65
|
+
// FIXME disabled to support legacy code directly assign from sc_signal<T>
|
|
66
|
+
//template <typename T>
|
|
67
|
+
//INLINE typename _ap_type::enable_if<_ap_type::is_integral<T>::value,
|
|
68
|
+
// ap_concat_ref&>::type
|
|
69
|
+
//operator=(T val) {
|
|
70
|
+
// ap_int_base<_AP_W1 + _AP_W2, false> tmpVal(val);
|
|
71
|
+
// return operator=(tmpVal);
|
|
72
|
+
//}
|
|
73
|
+
#define ASSIGN_WITH_CTYPE(_Tp) \
|
|
74
|
+
INLINE ap_concat_ref& operator=(_Tp val) { \
|
|
75
|
+
ap_int_base<_AP_W1 + _AP_W2, false> tmpVal(val); \
|
|
76
|
+
return operator=(tmpVal); \
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
ASSIGN_WITH_CTYPE(bool)
|
|
80
|
+
ASSIGN_WITH_CTYPE(char)
|
|
81
|
+
ASSIGN_WITH_CTYPE(signed char)
|
|
82
|
+
ASSIGN_WITH_CTYPE(unsigned char)
|
|
83
|
+
ASSIGN_WITH_CTYPE(short)
|
|
84
|
+
ASSIGN_WITH_CTYPE(unsigned short)
|
|
85
|
+
ASSIGN_WITH_CTYPE(int)
|
|
86
|
+
ASSIGN_WITH_CTYPE(unsigned int)
|
|
87
|
+
ASSIGN_WITH_CTYPE(long)
|
|
88
|
+
ASSIGN_WITH_CTYPE(unsigned long)
|
|
89
|
+
ASSIGN_WITH_CTYPE(ap_slong)
|
|
90
|
+
ASSIGN_WITH_CTYPE(ap_ulong)
|
|
91
|
+
#if _AP_ENABLE_HALF_ == 1
|
|
92
|
+
ASSIGN_WITH_CTYPE(half)
|
|
93
|
+
#endif
|
|
94
|
+
ASSIGN_WITH_CTYPE(float)
|
|
95
|
+
ASSIGN_WITH_CTYPE(double)
|
|
96
|
+
|
|
97
|
+
#undef ASSIGN_WITH_CTYPE
|
|
98
|
+
|
|
99
|
+
// Be explicit to prevent it from being deleted, as field d_bv
|
|
100
|
+
// is of reference type.
|
|
101
|
+
INLINE ap_concat_ref& operator=(
|
|
102
|
+
const ap_concat_ref<_AP_W1, _AP_T1, _AP_W2, _AP_T2>& val) {
|
|
103
|
+
ap_int_base<_AP_W1 + _AP_W2, false> tmpVal(val);
|
|
104
|
+
return operator=(tmpVal);
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
template <int _AP_W3, typename _AP_T3, int _AP_W4, typename _AP_T4>
|
|
108
|
+
INLINE ap_concat_ref& operator=(
|
|
109
|
+
const ap_concat_ref<_AP_W3, _AP_T3, _AP_W4, _AP_T4>& val) {
|
|
110
|
+
ap_int_base<_AP_W1 + _AP_W2, false> tmpVal(val);
|
|
111
|
+
return operator=(tmpVal);
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
template <int _AP_W3, bool _AP_S3>
|
|
115
|
+
INLINE ap_concat_ref& operator=(const ap_bit_ref<_AP_W3, _AP_S3>& val) {
|
|
116
|
+
ap_int_base<_AP_W1 + _AP_W2, false> tmpVal(val);
|
|
117
|
+
return operator=(tmpVal);
|
|
118
|
+
}
|
|
119
|
+
template <int _AP_W3, bool _AP_S3>
|
|
120
|
+
INLINE ap_concat_ref& operator=(const ap_range_ref<_AP_W3, _AP_S3>& val) {
|
|
121
|
+
ap_int_base<_AP_W1 + _AP_W2, false> tmpVal(val);
|
|
122
|
+
return operator=(tmpVal);
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
template <int _AP_W3, int _AP_I3, bool _AP_S3, ap_q_mode _AP_Q3,
|
|
126
|
+
ap_o_mode _AP_O3, int _AP_N3>
|
|
127
|
+
INLINE ap_concat_ref& operator=(
|
|
128
|
+
const af_range_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3>& val) {
|
|
129
|
+
return operator=((const ap_int_base<_AP_W3, false>)(val));
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
template <int _AP_W3, int _AP_I3, bool _AP_S3, ap_q_mode _AP_Q3,
|
|
133
|
+
ap_o_mode _AP_O3, int _AP_N3>
|
|
134
|
+
INLINE ap_concat_ref& operator=(
|
|
135
|
+
const ap_fixed_base<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3>&
|
|
136
|
+
val) {
|
|
137
|
+
return operator=(val.to_ap_int_base());
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
template <int _AP_W3, int _AP_I3, bool _AP_S3, ap_q_mode _AP_Q3,
|
|
141
|
+
ap_o_mode _AP_O3, int _AP_N3>
|
|
142
|
+
INLINE ap_concat_ref& operator=(
|
|
143
|
+
const af_bit_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3>& val) {
|
|
144
|
+
return operator=((ap_ulong)(bool)(val));
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
INLINE operator ap_int_base<_AP_WR, false>() const { return get(); }
|
|
148
|
+
|
|
149
|
+
INLINE operator ap_ulong() const { return get().to_uint64(); }
|
|
150
|
+
|
|
151
|
+
template <int _AP_W3, bool _AP_S3>
|
|
152
|
+
INLINE ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3,
|
|
153
|
+
ap_range_ref<_AP_W3, _AP_S3> >
|
|
154
|
+
operator,(const ap_range_ref<_AP_W3, _AP_S3> &a2) {
|
|
155
|
+
return ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3,
|
|
156
|
+
ap_range_ref<_AP_W3, _AP_S3> >(
|
|
157
|
+
*this, const_cast<ap_range_ref<_AP_W3, _AP_S3>&>(a2));
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
template <int _AP_W3, bool _AP_S3>
|
|
161
|
+
INLINE
|
|
162
|
+
ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3, ap_int_base<_AP_W3, _AP_S3> >
|
|
163
|
+
operator,(ap_int_base<_AP_W3, _AP_S3> &a2) {
|
|
164
|
+
return ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3,
|
|
165
|
+
ap_int_base<_AP_W3, _AP_S3> >(*this, a2);
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
template <int _AP_W3, bool _AP_S3>
|
|
169
|
+
INLINE
|
|
170
|
+
ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3, ap_int_base<_AP_W3, _AP_S3> >
|
|
171
|
+
operator,(volatile ap_int_base<_AP_W3, _AP_S3> &a2) {
|
|
172
|
+
return ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3,
|
|
173
|
+
ap_int_base<_AP_W3, _AP_S3> >(
|
|
174
|
+
*this, const_cast<ap_int_base<_AP_W3, _AP_S3>&>(a2));
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
template <int _AP_W3, bool _AP_S3>
|
|
178
|
+
INLINE
|
|
179
|
+
ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3, ap_int_base<_AP_W3, _AP_S3> >
|
|
180
|
+
operator,(const ap_int_base<_AP_W3, _AP_S3> &a2) {
|
|
181
|
+
return ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3,
|
|
182
|
+
ap_int_base<_AP_W3, _AP_S3> >(
|
|
183
|
+
*this, const_cast<ap_int_base<_AP_W3, _AP_S3>&>(a2));
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
template <int _AP_W3, bool _AP_S3>
|
|
187
|
+
INLINE
|
|
188
|
+
ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3, ap_int_base<_AP_W3, _AP_S3> >
|
|
189
|
+
operator,(const volatile ap_int_base<_AP_W3, _AP_S3> &a2) {
|
|
190
|
+
// FIXME op's life does not seem long enough
|
|
191
|
+
ap_int_base<_AP_W3, _AP_S3> op(a2);
|
|
192
|
+
return ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3,
|
|
193
|
+
ap_int_base<_AP_W3, _AP_S3> >(
|
|
194
|
+
*this, const_cast<ap_int_base<_AP_W3, _AP_S3>&>(op));
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
template <int _AP_W3, bool _AP_S3>
|
|
198
|
+
INLINE ap_concat_ref<_AP_WR, ap_concat_ref, 1, ap_bit_ref<_AP_W3, _AP_S3> >
|
|
199
|
+
operator,(const ap_bit_ref<_AP_W3, _AP_S3> &a2) {
|
|
200
|
+
return ap_concat_ref<_AP_WR, ap_concat_ref, 1, ap_bit_ref<_AP_W3, _AP_S3> >(
|
|
201
|
+
*this, const_cast<ap_bit_ref<_AP_W3, _AP_S3>&>(a2));
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
template <int _AP_W3, typename _AP_T3, int _AP_W4, typename _AP_T4>
|
|
205
|
+
INLINE ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3 + _AP_W4,
|
|
206
|
+
ap_concat_ref<_AP_W3, _AP_T3, _AP_W4, _AP_T4> >
|
|
207
|
+
operator,(const ap_concat_ref<_AP_W3, _AP_T3, _AP_W4, _AP_T4> &a2) {
|
|
208
|
+
return ap_concat_ref<_AP_WR, ap_concat_ref, _AP_W3 + _AP_W4,
|
|
209
|
+
ap_concat_ref<_AP_W3, _AP_T3, _AP_W4, _AP_T4> >(
|
|
210
|
+
*this, const_cast<ap_concat_ref<_AP_W3, _AP_T3, _AP_W4, _AP_T4>&>(a2));
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
template <int _AP_W3, int _AP_I3, bool _AP_S3, ap_q_mode _AP_Q3,
|
|
214
|
+
ap_o_mode _AP_O3, int _AP_N3>
|
|
215
|
+
INLINE ap_concat_ref<
|
|
216
|
+
_AP_WR, ap_concat_ref, _AP_W3,
|
|
217
|
+
af_range_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3> >
|
|
218
|
+
operator,(
|
|
219
|
+
const af_range_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3> &a2) {
|
|
220
|
+
return ap_concat_ref<
|
|
221
|
+
_AP_WR, ap_concat_ref, _AP_W3,
|
|
222
|
+
af_range_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3> >(
|
|
223
|
+
*this,
|
|
224
|
+
const_cast<
|
|
225
|
+
af_range_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3>&>(a2));
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
template <int _AP_W3, int _AP_I3, bool _AP_S3, ap_q_mode _AP_Q3,
|
|
229
|
+
ap_o_mode _AP_O3, int _AP_N3>
|
|
230
|
+
INLINE
|
|
231
|
+
ap_concat_ref<_AP_WR, ap_concat_ref, 1,
|
|
232
|
+
af_bit_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3> >
|
|
233
|
+
operator,(const af_bit_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3>
|
|
234
|
+
&a2) {
|
|
235
|
+
return ap_concat_ref<
|
|
236
|
+
_AP_WR, ap_concat_ref, 1,
|
|
237
|
+
af_bit_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3> >(
|
|
238
|
+
*this,
|
|
239
|
+
const_cast<af_bit_ref<_AP_W3, _AP_I3, _AP_S3, _AP_Q3, _AP_O3, _AP_N3>&>(
|
|
240
|
+
a2));
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
template <int _AP_W3, bool _AP_S3>
|
|
244
|
+
INLINE ap_int_base<AP_MAX(_AP_WR, _AP_W3), _AP_S3> operator&(
|
|
245
|
+
const ap_int_base<_AP_W3, _AP_S3>& a2) {
|
|
246
|
+
return get() & a2;
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
template <int _AP_W3, bool _AP_S3>
|
|
250
|
+
INLINE ap_int_base<AP_MAX(_AP_WR, _AP_W3), _AP_S3> operator|(
|
|
251
|
+
const ap_int_base<_AP_W3, _AP_S3>& a2) {
|
|
252
|
+
return get() | a2;
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
template <int _AP_W3, bool _AP_S3>
|
|
256
|
+
INLINE ap_int_base<AP_MAX(_AP_WR, _AP_W3), _AP_S3> operator^(
|
|
257
|
+
const ap_int_base<_AP_W3, _AP_S3>& a2) {
|
|
258
|
+
return get() ^ a2;
|
|
259
|
+
}
|
|
260
|
+
|
|
261
|
+
#if 0
|
|
262
|
+
template<int Hi, int Lo>
|
|
263
|
+
INLINE ap_int_base<Hi-Lo+1, false> slice() {
|
|
264
|
+
ap_int_base<_AP_WR, false> bv = get();
|
|
265
|
+
return bv.slice<Hi,Lo>();
|
|
266
|
+
}
|
|
267
|
+
#endif
|
|
268
|
+
|
|
269
|
+
INLINE ap_int_base<_AP_WR, false> get() const {
|
|
270
|
+
ap_int_base<_AP_WR, false> tmpVal(0);
|
|
271
|
+
int W_ref1 = mbv1.length();
|
|
272
|
+
int W_ref2 = mbv2.length();
|
|
273
|
+
ap_int_base<_AP_W2, false> v2(mbv2);
|
|
274
|
+
ap_int_base<_AP_W1, false> v1(mbv1);
|
|
275
|
+
tmpVal.V = _AP_ROOT_op_set_range(tmpVal.V, 0, W_ref2 - 1, v2.V);
|
|
276
|
+
tmpVal.V =
|
|
277
|
+
_AP_ROOT_op_set_range(tmpVal.V, W_ref2, W_ref1 + W_ref2 - 1, v1.V);
|
|
278
|
+
return tmpVal;
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
template <int _AP_W3>
|
|
282
|
+
INLINE void set(const ap_int_base<_AP_W3, false>& val) {
|
|
283
|
+
ap_int_base<_AP_W1 + _AP_W2, false> vval(val);
|
|
284
|
+
int W_ref1 = mbv1.length();
|
|
285
|
+
int W_ref2 = mbv2.length();
|
|
286
|
+
ap_int_base<_AP_W1, false> tmpVal1;
|
|
287
|
+
tmpVal1.V = _AP_ROOT_op_get_range(vval.V, W_ref2, W_ref1 + W_ref2 - 1);
|
|
288
|
+
mbv1.set(tmpVal1);
|
|
289
|
+
ap_int_base<_AP_W2, false> tmpVal2;
|
|
290
|
+
tmpVal2.V = _AP_ROOT_op_get_range(vval.V, 0, W_ref2 - 1);
|
|
291
|
+
mbv2.set(tmpVal2);
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
INLINE int length() const { return mbv1.length() + mbv2.length(); }
|
|
295
|
+
}; // struct ap_concat_ref
|
|
296
|
+
|
|
297
|
+
/* Range (slice) reference.
|
|
298
|
+
----------------------------------------------------------------
|
|
299
|
+
*/
|
|
300
|
+
template <int _AP_W, bool _AP_S>
|
|
301
|
+
struct ap_range_ref {
|
|
302
|
+
// struct ssdm_int or its sim model.
|
|
303
|
+
// TODO make it possible to reference to ap_fixed_base/ap_fixed/ap_ufixed
|
|
304
|
+
// and then we can retire af_range_ref.
|
|
305
|
+
typedef ap_int_base<_AP_W, _AP_S> ref_type;
|
|
306
|
+
ref_type& d_bv;
|
|
307
|
+
int l_index;
|
|
308
|
+
int h_index;
|
|
309
|
+
|
|
310
|
+
public:
|
|
311
|
+
INLINE ap_range_ref(const ap_range_ref<_AP_W, _AP_S>& ref)
|
|
312
|
+
: d_bv(ref.d_bv), l_index(ref.l_index), h_index(ref.h_index) {}
|
|
313
|
+
|
|
314
|
+
INLINE ap_range_ref(ref_type* bv, int h, int l)
|
|
315
|
+
: d_bv(*bv), l_index(l), h_index(h) {}
|
|
316
|
+
|
|
317
|
+
INLINE ap_range_ref(const ref_type* bv, int h, int l)
|
|
318
|
+
: d_bv(*const_cast<ref_type*>(bv)), l_index(l), h_index(h) {}
|
|
319
|
+
|
|
320
|
+
INLINE operator ap_int_base<_AP_W, false>() const {
|
|
321
|
+
ap_int_base<_AP_W, false> ret;
|
|
322
|
+
ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
|
|
323
|
+
return ret;
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
INLINE operator ap_ulong() const { return to_uint64(); }
|
|
327
|
+
|
|
328
|
+
/// @name assign operators
|
|
329
|
+
// @{
|
|
330
|
+
|
|
331
|
+
// FIXME disabled to work-around lagacy code assigning from sc_signal<T>,
|
|
332
|
+
// which dependes on implicit type conversion.
|
|
333
|
+
//
|
|
334
|
+
// /// assign from hls supported C integral types.
|
|
335
|
+
// template <typename T>
|
|
336
|
+
// INLINE typename _ap_type::enable_if<_ap_type::is_integral<T>::value,
|
|
337
|
+
// ap_range_ref&>::type
|
|
338
|
+
// operator=(T val) {
|
|
339
|
+
// ap_int_base<_AP_W, false> tmp(val);
|
|
340
|
+
// d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, tmp.V);
|
|
341
|
+
// return *this;
|
|
342
|
+
// }
|
|
343
|
+
#define ASSIGN_WITH_CTYPE(_Tp) \
|
|
344
|
+
INLINE ap_range_ref& operator=(_Tp val) { \
|
|
345
|
+
ap_int_base<_AP_W, false> tmp(val); \
|
|
346
|
+
d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, tmp.V); \
|
|
347
|
+
return *this; \
|
|
348
|
+
}
|
|
349
|
+
|
|
350
|
+
ASSIGN_WITH_CTYPE(bool)
|
|
351
|
+
ASSIGN_WITH_CTYPE(char)
|
|
352
|
+
ASSIGN_WITH_CTYPE(signed char)
|
|
353
|
+
ASSIGN_WITH_CTYPE(unsigned char)
|
|
354
|
+
ASSIGN_WITH_CTYPE(short)
|
|
355
|
+
ASSIGN_WITH_CTYPE(unsigned short)
|
|
356
|
+
ASSIGN_WITH_CTYPE(int)
|
|
357
|
+
ASSIGN_WITH_CTYPE(unsigned int)
|
|
358
|
+
ASSIGN_WITH_CTYPE(long)
|
|
359
|
+
ASSIGN_WITH_CTYPE(unsigned long)
|
|
360
|
+
ASSIGN_WITH_CTYPE(ap_slong)
|
|
361
|
+
ASSIGN_WITH_CTYPE(ap_ulong)
|
|
362
|
+
#if _AP_ENABLE_HALF_ == 1
|
|
363
|
+
ASSIGN_WITH_CTYPE(half)
|
|
364
|
+
#endif
|
|
365
|
+
ASSIGN_WITH_CTYPE(float)
|
|
366
|
+
ASSIGN_WITH_CTYPE(double)
|
|
367
|
+
|
|
368
|
+
#undef ASSIGN_WITH_CTYPE
|
|
369
|
+
|
|
370
|
+
/// assign using string. XXX crucial for cosim.
|
|
371
|
+
INLINE ap_range_ref& operator=(const char* val) {
|
|
372
|
+
const ap_int_base<_AP_W, false> tmp(val); // XXX figure out radix
|
|
373
|
+
d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, tmp.V);
|
|
374
|
+
return *this;
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
/// assign from ap_int_base.
|
|
378
|
+
template <int _AP_W2, bool _AP_S2>
|
|
379
|
+
INLINE ap_range_ref& operator=(const ap_int_base<_AP_W2, _AP_S2>& val) {
|
|
380
|
+
ap_int_base<_AP_W, false> tmp(val);
|
|
381
|
+
d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, tmp.V);
|
|
382
|
+
return *this;
|
|
383
|
+
}
|
|
384
|
+
|
|
385
|
+
/// copy assign operator
|
|
386
|
+
// XXX Be explicit to prevent it from being deleted, as field d_bv
|
|
387
|
+
// is of reference type.
|
|
388
|
+
INLINE ap_range_ref& operator=(const ap_range_ref& val) {
|
|
389
|
+
return operator=((const ap_int_base<_AP_W, false>)val);
|
|
390
|
+
}
|
|
391
|
+
|
|
392
|
+
/// assign from range reference to ap_int_base.
|
|
393
|
+
template <int _AP_W2, bool _AP_S2>
|
|
394
|
+
INLINE ap_range_ref& operator=(const ap_range_ref<_AP_W2, _AP_S2>& val) {
|
|
395
|
+
return operator=((const ap_int_base<_AP_W2, false>)val);
|
|
396
|
+
}
|
|
397
|
+
|
|
398
|
+
/// assign from bit reference to ap_int_base.
|
|
399
|
+
template <int _AP_W2, bool _AP_S2>
|
|
400
|
+
INLINE ap_range_ref& operator=(const ap_bit_ref<_AP_W2, _AP_S2>& val) {
|
|
401
|
+
return operator=((ap_ulong)(bool)(val));
|
|
402
|
+
}
|
|
403
|
+
|
|
404
|
+
/// assign from ap_fixed_base.
|
|
405
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
406
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
407
|
+
INLINE ap_range_ref& operator=(
|
|
408
|
+
const ap_fixed_base<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>&
|
|
409
|
+
val) {
|
|
410
|
+
return operator=(val.to_ap_int_base());
|
|
411
|
+
}
|
|
412
|
+
|
|
413
|
+
/// assign from range reference to ap_fixed_base.
|
|
414
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
415
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
416
|
+
INLINE ap_range_ref& operator=(
|
|
417
|
+
const af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>& val) {
|
|
418
|
+
return operator=((const ap_int_base<_AP_W2, false>)val);
|
|
419
|
+
}
|
|
420
|
+
|
|
421
|
+
/// assign from bit reference to ap_fixed_base.
|
|
422
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
423
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
424
|
+
INLINE ap_range_ref& operator=(
|
|
425
|
+
const af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>& val) {
|
|
426
|
+
return operator=((ap_ulong)(bool)(val));
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
/// assign from compound reference.
|
|
430
|
+
template <int _AP_W2, typename _AP_T2, int _AP_W3, typename _AP_T3>
|
|
431
|
+
INLINE ap_range_ref& operator=(
|
|
432
|
+
const ap_concat_ref<_AP_W2, _AP_T3, _AP_W3, _AP_T3>& val) {
|
|
433
|
+
return operator=((const ap_int_base<_AP_W2 + _AP_W3, false>)(val));
|
|
434
|
+
}
|
|
435
|
+
// @}
|
|
436
|
+
|
|
437
|
+
template <int _AP_W2, bool _AP_S2>
|
|
438
|
+
INLINE
|
|
439
|
+
ap_concat_ref<_AP_W, ap_range_ref, _AP_W2, ap_range_ref<_AP_W2, _AP_S2> >
|
|
440
|
+
operator,(const ap_range_ref<_AP_W2, _AP_S2> &a2) {
|
|
441
|
+
return ap_concat_ref<_AP_W, ap_range_ref, _AP_W2,
|
|
442
|
+
ap_range_ref<_AP_W2, _AP_S2> >(
|
|
443
|
+
*this, const_cast<ap_range_ref<_AP_W2, _AP_S2>&>(a2));
|
|
444
|
+
}
|
|
445
|
+
|
|
446
|
+
template <int _AP_W2, bool _AP_S2>
|
|
447
|
+
INLINE
|
|
448
|
+
ap_concat_ref<_AP_W, ap_range_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
449
|
+
operator,(ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
450
|
+
return ap_concat_ref<_AP_W, ap_range_ref, _AP_W2,
|
|
451
|
+
ap_int_base<_AP_W2, _AP_S2> >(*this, a2);
|
|
452
|
+
}
|
|
453
|
+
|
|
454
|
+
INLINE
|
|
455
|
+
ap_concat_ref<_AP_W, ap_range_ref, _AP_W, ap_int_base<_AP_W, _AP_S> >
|
|
456
|
+
operator,(ap_int_base<_AP_W, _AP_S>& a2) {
|
|
457
|
+
return ap_concat_ref<_AP_W, ap_range_ref, _AP_W,
|
|
458
|
+
ap_int_base<_AP_W, _AP_S> >(*this, a2);
|
|
459
|
+
}
|
|
460
|
+
|
|
461
|
+
template <int _AP_W2, bool _AP_S2>
|
|
462
|
+
INLINE
|
|
463
|
+
ap_concat_ref<_AP_W, ap_range_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
464
|
+
operator,(volatile ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
465
|
+
return ap_concat_ref<_AP_W, ap_range_ref, _AP_W2,
|
|
466
|
+
ap_int_base<_AP_W2, _AP_S2> >(
|
|
467
|
+
*this, const_cast<ap_int_base<_AP_W2, _AP_S2>&>(a2));
|
|
468
|
+
}
|
|
469
|
+
|
|
470
|
+
template <int _AP_W2, bool _AP_S2>
|
|
471
|
+
INLINE
|
|
472
|
+
ap_concat_ref<_AP_W, ap_range_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
473
|
+
operator,(const ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
474
|
+
return ap_concat_ref<_AP_W, ap_range_ref, _AP_W2,
|
|
475
|
+
ap_int_base<_AP_W2, _AP_S2> >(
|
|
476
|
+
*this, const_cast<ap_int_base<_AP_W2, _AP_S2>&>(a2));
|
|
477
|
+
}
|
|
478
|
+
|
|
479
|
+
template <int _AP_W2, bool _AP_S2>
|
|
480
|
+
INLINE
|
|
481
|
+
ap_concat_ref<_AP_W, ap_range_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
482
|
+
operator,(const volatile ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
483
|
+
return ap_concat_ref<_AP_W, ap_range_ref, _AP_W2,
|
|
484
|
+
ap_int_base<_AP_W2, _AP_S2> >(
|
|
485
|
+
*this, const_cast<ap_int_base<_AP_W2, _AP_S2>&>(a2));
|
|
486
|
+
}
|
|
487
|
+
|
|
488
|
+
template <int _AP_W2, bool _AP_S2>
|
|
489
|
+
INLINE ap_concat_ref<_AP_W, ap_range_ref, 1, ap_bit_ref<_AP_W2, _AP_S2> >
|
|
490
|
+
operator,(const ap_bit_ref<_AP_W2, _AP_S2> &a2) {
|
|
491
|
+
return ap_concat_ref<_AP_W, ap_range_ref, 1, ap_bit_ref<_AP_W2, _AP_S2> >(
|
|
492
|
+
*this, const_cast<ap_bit_ref<_AP_W2, _AP_S2>&>(a2));
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
template <int _AP_W2, typename _AP_T2, int _AP_W3, typename _AP_T3>
|
|
496
|
+
INLINE ap_concat_ref<_AP_W, ap_range_ref, _AP_W2 + _AP_W3,
|
|
497
|
+
ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3> >
|
|
498
|
+
operator,(const ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3> &a2) {
|
|
499
|
+
return ap_concat_ref<_AP_W, ap_range_ref, _AP_W2 + _AP_W3,
|
|
500
|
+
ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3> >(
|
|
501
|
+
*this, const_cast<ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3>&>(a2));
|
|
502
|
+
}
|
|
503
|
+
|
|
504
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
505
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
506
|
+
INLINE ap_concat_ref<
|
|
507
|
+
_AP_W, ap_range_ref, _AP_W2,
|
|
508
|
+
af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> >
|
|
509
|
+
operator,(
|
|
510
|
+
const af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> a2) {
|
|
511
|
+
return ap_concat_ref<
|
|
512
|
+
_AP_W, ap_range_ref, _AP_W2,
|
|
513
|
+
af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> >(
|
|
514
|
+
*this,
|
|
515
|
+
const_cast<
|
|
516
|
+
af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>&>(a2));
|
|
517
|
+
}
|
|
518
|
+
|
|
519
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
520
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
521
|
+
INLINE
|
|
522
|
+
ap_concat_ref<_AP_W, ap_range_ref, 1,
|
|
523
|
+
af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> >
|
|
524
|
+
operator,(const af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>
|
|
525
|
+
&a2) {
|
|
526
|
+
return ap_concat_ref<
|
|
527
|
+
_AP_W, ap_range_ref, 1,
|
|
528
|
+
af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> >(
|
|
529
|
+
*this,
|
|
530
|
+
const_cast<af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>&>(
|
|
531
|
+
a2));
|
|
532
|
+
}
|
|
533
|
+
|
|
534
|
+
template <int _AP_W2, bool _AP_S2>
|
|
535
|
+
INLINE bool operator==(const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
536
|
+
ap_int_base<_AP_W, false> lop(*this);
|
|
537
|
+
ap_int_base<_AP_W2, false> hop(op2);
|
|
538
|
+
return lop == hop;
|
|
539
|
+
}
|
|
540
|
+
|
|
541
|
+
template <int _AP_W2, bool _AP_S2>
|
|
542
|
+
INLINE bool operator!=(const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
543
|
+
return !(operator==(op2));
|
|
544
|
+
}
|
|
545
|
+
|
|
546
|
+
template <int _AP_W2, bool _AP_S2>
|
|
547
|
+
INLINE bool operator<(const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
548
|
+
ap_int_base<_AP_W, false> lop(*this);
|
|
549
|
+
ap_int_base<_AP_W2, false> hop(op2);
|
|
550
|
+
return lop < hop;
|
|
551
|
+
}
|
|
552
|
+
|
|
553
|
+
template <int _AP_W2, bool _AP_S2>
|
|
554
|
+
INLINE bool operator<=(const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
555
|
+
ap_int_base<_AP_W, false> lop(*this);
|
|
556
|
+
ap_int_base<_AP_W2, false> hop(op2);
|
|
557
|
+
return lop <= hop;
|
|
558
|
+
}
|
|
559
|
+
|
|
560
|
+
template <int _AP_W2, bool _AP_S2>
|
|
561
|
+
INLINE bool operator>(const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
562
|
+
return !(operator<=(op2));
|
|
563
|
+
}
|
|
564
|
+
|
|
565
|
+
template <int _AP_W2, bool _AP_S2>
|
|
566
|
+
INLINE bool operator>=(const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
567
|
+
return !(operator<(op2));
|
|
568
|
+
}
|
|
569
|
+
|
|
570
|
+
template <int _AP_W2, bool _AP_S2>
|
|
571
|
+
INLINE ap_range_ref<_AP_W, _AP_S>& operator|=(
|
|
572
|
+
const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
573
|
+
(this->d_bv).V |= (op2.d_bv).V;
|
|
574
|
+
return *this;
|
|
575
|
+
};
|
|
576
|
+
|
|
577
|
+
template <int _AP_W2, bool _AP_S2>
|
|
578
|
+
INLINE ap_range_ref<_AP_W, _AP_S>& operator|=(
|
|
579
|
+
const ap_int_base<_AP_W2, _AP_S2>& op2) {
|
|
580
|
+
(this->d_bv).V |= op2.V;
|
|
581
|
+
return *this;
|
|
582
|
+
};
|
|
583
|
+
|
|
584
|
+
template <int _AP_W2, bool _AP_S2>
|
|
585
|
+
INLINE ap_range_ref<_AP_W, _AP_S>& operator&=(
|
|
586
|
+
const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
587
|
+
(this->d_bv).V &= (op2.d_bv).V;
|
|
588
|
+
return *this;
|
|
589
|
+
};
|
|
590
|
+
|
|
591
|
+
template <int _AP_W2, bool _AP_S2>
|
|
592
|
+
INLINE ap_range_ref<_AP_W, _AP_S>& operator&=(
|
|
593
|
+
const ap_int_base<_AP_W2, _AP_S2>& op2) {
|
|
594
|
+
(this->d_bv).V &= op2.V;
|
|
595
|
+
return *this;
|
|
596
|
+
};
|
|
597
|
+
|
|
598
|
+
template <int _AP_W2, bool _AP_S2>
|
|
599
|
+
INLINE ap_range_ref<_AP_W, _AP_S>& operator^=(
|
|
600
|
+
const ap_range_ref<_AP_W2, _AP_S2>& op2) {
|
|
601
|
+
(this->d_bv).V ^= (op2.d_bv).V;
|
|
602
|
+
return *this;
|
|
603
|
+
};
|
|
604
|
+
|
|
605
|
+
template <int _AP_W2, bool _AP_S2>
|
|
606
|
+
INLINE ap_range_ref<_AP_W, _AP_S>& operator^=(
|
|
607
|
+
const ap_int_base<_AP_W2, _AP_S2>& op2) {
|
|
608
|
+
(this->d_bv).V ^= op2.V;
|
|
609
|
+
return *this;
|
|
610
|
+
};
|
|
611
|
+
|
|
612
|
+
INLINE ap_int_base<_AP_W, false> get() const {
|
|
613
|
+
ap_int_base<_AP_W, false> ret;
|
|
614
|
+
ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
|
|
615
|
+
return ret;
|
|
616
|
+
}
|
|
617
|
+
|
|
618
|
+
template <int _AP_W2>
|
|
619
|
+
INLINE void set(const ap_int_base<_AP_W2, false>& val) {
|
|
620
|
+
d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, val.V);
|
|
621
|
+
}
|
|
622
|
+
|
|
623
|
+
INLINE int length() const {
|
|
624
|
+
return h_index >= l_index ? h_index - l_index + 1 : l_index - h_index + 1;
|
|
625
|
+
}
|
|
626
|
+
|
|
627
|
+
INLINE int to_int() const {
|
|
628
|
+
return (int)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
|
|
629
|
+
}
|
|
630
|
+
|
|
631
|
+
INLINE unsigned to_uint() const {
|
|
632
|
+
return (unsigned)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
|
|
633
|
+
}
|
|
634
|
+
|
|
635
|
+
INLINE long to_long() const {
|
|
636
|
+
return (long)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
|
|
637
|
+
}
|
|
638
|
+
|
|
639
|
+
INLINE unsigned long to_ulong() const {
|
|
640
|
+
return (unsigned long)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
|
|
641
|
+
}
|
|
642
|
+
|
|
643
|
+
INLINE ap_slong to_int64() const {
|
|
644
|
+
return (ap_slong)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
|
|
645
|
+
}
|
|
646
|
+
|
|
647
|
+
INLINE ap_ulong to_uint64() const {
|
|
648
|
+
return (ap_ulong)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
|
|
649
|
+
}
|
|
650
|
+
|
|
651
|
+
INLINE bool and_reduce() const {
|
|
652
|
+
bool ret = true;
|
|
653
|
+
bool reverse = l_index > h_index;
|
|
654
|
+
unsigned low = reverse ? h_index : l_index;
|
|
655
|
+
unsigned high = reverse ? l_index : h_index;
|
|
656
|
+
for (unsigned i = low; i != high; ++i) {
|
|
657
|
+
#ifdef __SYNTHESIS__
|
|
658
|
+
#pragma HLS unroll
|
|
659
|
+
#endif
|
|
660
|
+
ret &= _AP_ROOT_op_get_bit(d_bv.V, i);
|
|
661
|
+
}
|
|
662
|
+
return ret;
|
|
663
|
+
}
|
|
664
|
+
|
|
665
|
+
INLINE bool or_reduce() const {
|
|
666
|
+
bool ret = false;
|
|
667
|
+
bool reverse = l_index > h_index;
|
|
668
|
+
unsigned low = reverse ? h_index : l_index;
|
|
669
|
+
unsigned high = reverse ? l_index : h_index;
|
|
670
|
+
for (unsigned i = low; i != high; ++i) {
|
|
671
|
+
#ifdef __SYNTHESIS__
|
|
672
|
+
#pragma HLS unroll
|
|
673
|
+
#endif
|
|
674
|
+
ret |= _AP_ROOT_op_get_bit(d_bv.V, i);
|
|
675
|
+
}
|
|
676
|
+
return ret;
|
|
677
|
+
}
|
|
678
|
+
|
|
679
|
+
INLINE bool xor_reduce() const {
|
|
680
|
+
bool ret = false;
|
|
681
|
+
bool reverse = l_index > h_index;
|
|
682
|
+
unsigned low = reverse ? h_index : l_index;
|
|
683
|
+
unsigned high = reverse ? l_index : h_index;
|
|
684
|
+
for (unsigned i = low; i != high; ++i) {
|
|
685
|
+
#ifdef __SYNTHESIS__
|
|
686
|
+
#pragma HLS unroll
|
|
687
|
+
#endif
|
|
688
|
+
ret ^= _AP_ROOT_op_get_bit(d_bv.V, i);
|
|
689
|
+
}
|
|
690
|
+
return ret;
|
|
691
|
+
}
|
|
692
|
+
#ifndef __SYNTHESIS__
|
|
693
|
+
std::string to_string(signed char radix = 2) const {
|
|
694
|
+
ap_int_base<_AP_W, false> ret;
|
|
695
|
+
ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
|
|
696
|
+
return ret.to_string(radix);
|
|
697
|
+
}
|
|
698
|
+
#else
|
|
699
|
+
// XXX HLS will delete this in synthesis
|
|
700
|
+
INLINE char* to_string(signed char radix = 2) const {
|
|
701
|
+
return 0;
|
|
702
|
+
}
|
|
703
|
+
#endif
|
|
704
|
+
}; // struct ap_range_ref
|
|
705
|
+
|
|
706
|
+
// XXX apcc cannot handle global std::ios_base::Init() brought in by <iostream>
|
|
707
|
+
#ifndef AP_AUTOCC
|
|
708
|
+
#ifndef __SYNTHESIS__
|
|
709
|
+
template <int _AP_W, bool _AP_S>
|
|
710
|
+
INLINE std::ostream& operator<<(std::ostream& os,
|
|
711
|
+
const ap_range_ref<_AP_W, _AP_S>& x) {
|
|
712
|
+
std::ios_base::fmtflags ff = std::cout.flags();
|
|
713
|
+
if (ff & std::cout.hex) {
|
|
714
|
+
os << x.to_string(16); // don't print sign
|
|
715
|
+
} else if (ff & std::cout.oct) {
|
|
716
|
+
os << x.to_string(8); // don't print sign
|
|
717
|
+
} else {
|
|
718
|
+
os << x.to_string(10);
|
|
719
|
+
}
|
|
720
|
+
return os;
|
|
721
|
+
}
|
|
722
|
+
#endif // ifndef __SYNTHESIS__
|
|
723
|
+
|
|
724
|
+
#ifndef __SYNTHESIS__
|
|
725
|
+
template <int _AP_W, bool _AP_S>
|
|
726
|
+
INLINE std::istream& operator>>(std::istream& in,
|
|
727
|
+
ap_range_ref<_AP_W, _AP_S>& op) {
|
|
728
|
+
std::string str;
|
|
729
|
+
in >> str;
|
|
730
|
+
op = ap_int_base<_AP_W, _AP_S>(str.c_str());
|
|
731
|
+
return in;
|
|
732
|
+
}
|
|
733
|
+
#endif // ifndef __SYNTHESIS__
|
|
734
|
+
#endif // ifndef AP_AUTOCC
|
|
735
|
+
|
|
736
|
+
/* Bit reference.
|
|
737
|
+
----------------------------------------------------------------
|
|
738
|
+
*/
|
|
739
|
+
template <int _AP_W, bool _AP_S>
|
|
740
|
+
struct ap_bit_ref {
|
|
741
|
+
// struct ssdm_int or its sim model.
|
|
742
|
+
// TODO make it possible to reference to ap_fixed_base/ap_fixed/ap_ufixed
|
|
743
|
+
// and then we can retire af_bit_ref.
|
|
744
|
+
typedef ap_int_base<_AP_W, _AP_S> ref_type;
|
|
745
|
+
ref_type& d_bv;
|
|
746
|
+
int d_index;
|
|
747
|
+
|
|
748
|
+
public:
|
|
749
|
+
// copy ctor
|
|
750
|
+
INLINE ap_bit_ref(const ap_bit_ref<_AP_W, _AP_S>& ref)
|
|
751
|
+
: d_bv(ref.d_bv), d_index(ref.d_index) {}
|
|
752
|
+
|
|
753
|
+
INLINE ap_bit_ref(ref_type* bv, int index = 0) : d_bv(*bv), d_index(index) {}
|
|
754
|
+
|
|
755
|
+
INLINE ap_bit_ref(const ref_type* bv, int index = 0)
|
|
756
|
+
: d_bv(*const_cast<ref_type*>(bv)), d_index(index) {}
|
|
757
|
+
|
|
758
|
+
INLINE operator bool() const { return _AP_ROOT_op_get_bit(d_bv.V, d_index); }
|
|
759
|
+
INLINE bool to_bool() const { return _AP_ROOT_op_get_bit(d_bv.V, d_index); }
|
|
760
|
+
|
|
761
|
+
// assign op from hls supported C integral types.
|
|
762
|
+
// FIXME disabled to support sc_signal<bool>.
|
|
763
|
+
// NOTE this used to be unsigned long long.
|
|
764
|
+
//template <typename T>
|
|
765
|
+
//INLINE typename _ap_type::enable_if<_ap_type::is_integral<T>::value,
|
|
766
|
+
// ap_bit_ref&>::type
|
|
767
|
+
//operator=(T val) {
|
|
768
|
+
// d_bv.V = _AP_ROOT_op_set_bit(d_bv.V, d_index, val);
|
|
769
|
+
// return *this;
|
|
770
|
+
//}
|
|
771
|
+
#define ASSIGN_WITH_CTYPE(_Tp) \
|
|
772
|
+
INLINE ap_bit_ref& operator=(_Tp val) { \
|
|
773
|
+
d_bv.V = _AP_ROOT_op_set_bit(d_bv.V, d_index, val); \
|
|
774
|
+
return *this; \
|
|
775
|
+
}
|
|
776
|
+
|
|
777
|
+
ASSIGN_WITH_CTYPE(bool)
|
|
778
|
+
ASSIGN_WITH_CTYPE(char)
|
|
779
|
+
ASSIGN_WITH_CTYPE(signed char)
|
|
780
|
+
ASSIGN_WITH_CTYPE(unsigned char)
|
|
781
|
+
ASSIGN_WITH_CTYPE(short)
|
|
782
|
+
ASSIGN_WITH_CTYPE(unsigned short)
|
|
783
|
+
ASSIGN_WITH_CTYPE(int)
|
|
784
|
+
ASSIGN_WITH_CTYPE(unsigned int)
|
|
785
|
+
ASSIGN_WITH_CTYPE(long)
|
|
786
|
+
ASSIGN_WITH_CTYPE(unsigned long)
|
|
787
|
+
ASSIGN_WITH_CTYPE(ap_slong)
|
|
788
|
+
ASSIGN_WITH_CTYPE(ap_ulong)
|
|
789
|
+
|
|
790
|
+
#undef ASSIGN_WITH_CTYPE
|
|
791
|
+
|
|
792
|
+
#define ASSIGN_WITH_CTYPE_FP(_Tp) \
|
|
793
|
+
INLINE ap_bit_ref& operator=(_Tp val) { \
|
|
794
|
+
bool tmp_val = val; \
|
|
795
|
+
d_bv.V = _AP_ROOT_op_set_bit(d_bv.V, d_index,tmp_val); \
|
|
796
|
+
return *this; \
|
|
797
|
+
}
|
|
798
|
+
|
|
799
|
+
#if _AP_ENABLE_HALF_ == 1
|
|
800
|
+
ASSIGN_WITH_CTYPE_FP(half)
|
|
801
|
+
#endif
|
|
802
|
+
ASSIGN_WITH_CTYPE_FP(float)
|
|
803
|
+
ASSIGN_WITH_CTYPE_FP(double)
|
|
804
|
+
|
|
805
|
+
#undef ASSIGN_WITH_CTYPE_FP
|
|
806
|
+
|
|
807
|
+
|
|
808
|
+
template <int _AP_W2, bool _AP_S2>
|
|
809
|
+
INLINE ap_bit_ref& operator=(const ap_int_base<_AP_W2, _AP_S2>& val) {
|
|
810
|
+
return operator=((ap_ulong)(val.V != 0));
|
|
811
|
+
}
|
|
812
|
+
|
|
813
|
+
template <int _AP_W2, bool _AP_S2>
|
|
814
|
+
INLINE ap_bit_ref& operator=(const ap_range_ref<_AP_W2, _AP_S2>& val) {
|
|
815
|
+
return operator=((ap_int_base<_AP_W2, false>)val);
|
|
816
|
+
}
|
|
817
|
+
|
|
818
|
+
// Be explicit to prevent it from being deleted, as field d_bv
|
|
819
|
+
// is of reference type.
|
|
820
|
+
INLINE ap_bit_ref& operator=(const ap_bit_ref& val) {
|
|
821
|
+
return operator=((ap_ulong)(bool)val);
|
|
822
|
+
}
|
|
823
|
+
|
|
824
|
+
template <int _AP_W2, bool _AP_S2>
|
|
825
|
+
INLINE ap_bit_ref& operator=(const ap_bit_ref<_AP_W2, _AP_S2>& val) {
|
|
826
|
+
return operator=((ap_ulong)(bool)val);
|
|
827
|
+
}
|
|
828
|
+
|
|
829
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
830
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
831
|
+
INLINE ap_bit_ref& operator=(
|
|
832
|
+
const af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>& val) {
|
|
833
|
+
return operator=((const ap_int_base<_AP_W2, false>)val);
|
|
834
|
+
}
|
|
835
|
+
|
|
836
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
837
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
838
|
+
INLINE ap_bit_ref& operator=(
|
|
839
|
+
const af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>& val) {
|
|
840
|
+
return operator=((ap_ulong)(bool)val);
|
|
841
|
+
}
|
|
842
|
+
|
|
843
|
+
template <int _AP_W2, typename _AP_T2, int _AP_W3, typename _AP_T3>
|
|
844
|
+
INLINE ap_bit_ref& operator=(
|
|
845
|
+
const ap_concat_ref<_AP_W2, _AP_T3, _AP_W3, _AP_T3>& val) {
|
|
846
|
+
return operator=((const ap_int_base<_AP_W2 + _AP_W3, false>)val);
|
|
847
|
+
}
|
|
848
|
+
|
|
849
|
+
template <int _AP_W2, bool _AP_S2>
|
|
850
|
+
INLINE ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
851
|
+
operator,(ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
852
|
+
return ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >(
|
|
853
|
+
*this, a2);
|
|
854
|
+
}
|
|
855
|
+
|
|
856
|
+
template <int _AP_W2, bool _AP_S2>
|
|
857
|
+
INLINE ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
858
|
+
operator,(volatile ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
859
|
+
return ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >(
|
|
860
|
+
*this, const_cast<ap_int_base<_AP_W2, _AP_S2>&>(a2));
|
|
861
|
+
}
|
|
862
|
+
|
|
863
|
+
template <int _AP_W2, bool _AP_S2>
|
|
864
|
+
INLINE ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
865
|
+
operator,(const ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
866
|
+
ap_int_base<_AP_W2, _AP_S2> op(a2);
|
|
867
|
+
return ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >(
|
|
868
|
+
*this, const_cast<ap_int_base<_AP_W2, _AP_S2>&>(op));
|
|
869
|
+
}
|
|
870
|
+
|
|
871
|
+
template <int _AP_W2, bool _AP_S2>
|
|
872
|
+
INLINE ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >
|
|
873
|
+
operator,(const volatile ap_int_base<_AP_W2, _AP_S2> &a2) {
|
|
874
|
+
ap_int_base<_AP_W2, _AP_S2> op(a2);
|
|
875
|
+
return ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_int_base<_AP_W2, _AP_S2> >(
|
|
876
|
+
*this, const_cast<ap_int_base<_AP_W2, _AP_S2>&>(op));
|
|
877
|
+
}
|
|
878
|
+
|
|
879
|
+
template <int _AP_W2, bool _AP_S2>
|
|
880
|
+
INLINE ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_range_ref<_AP_W2, _AP_S2> >
|
|
881
|
+
operator,(const ap_range_ref<_AP_W2, _AP_S2> &a2) {
|
|
882
|
+
return ap_concat_ref<1, ap_bit_ref, _AP_W2, ap_range_ref<_AP_W2, _AP_S2> >(
|
|
883
|
+
*this, const_cast<ap_range_ref<_AP_W2, _AP_S2>&>(a2));
|
|
884
|
+
}
|
|
885
|
+
|
|
886
|
+
template <int _AP_W2, bool _AP_S2>
|
|
887
|
+
INLINE ap_concat_ref<1, ap_bit_ref, 1, ap_bit_ref<_AP_W2, _AP_S2> > operator,(
|
|
888
|
+
const ap_bit_ref<_AP_W2, _AP_S2> &a2) {
|
|
889
|
+
return ap_concat_ref<1, ap_bit_ref, 1, ap_bit_ref<_AP_W2, _AP_S2> >(
|
|
890
|
+
*this, const_cast<ap_bit_ref<_AP_W2, _AP_S2>&>(a2));
|
|
891
|
+
}
|
|
892
|
+
|
|
893
|
+
template <int _AP_W2, typename _AP_T2, int _AP_W3, typename _AP_T3>
|
|
894
|
+
INLINE ap_concat_ref<1, ap_bit_ref, _AP_W2 + _AP_W3,
|
|
895
|
+
ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3> >
|
|
896
|
+
operator,(const ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3> &a2) {
|
|
897
|
+
return ap_concat_ref<1, ap_bit_ref, _AP_W2 + _AP_W3,
|
|
898
|
+
ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3> >(
|
|
899
|
+
*this, const_cast<ap_concat_ref<_AP_W2, _AP_T2, _AP_W3, _AP_T3>&>(a2));
|
|
900
|
+
}
|
|
901
|
+
|
|
902
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
903
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
904
|
+
INLINE ap_concat_ref<
|
|
905
|
+
1, ap_bit_ref, _AP_W2,
|
|
906
|
+
af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> >
|
|
907
|
+
operator,(
|
|
908
|
+
const af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> &a2) {
|
|
909
|
+
return ap_concat_ref<
|
|
910
|
+
1, ap_bit_ref, _AP_W2,
|
|
911
|
+
af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> >(
|
|
912
|
+
*this,
|
|
913
|
+
const_cast<
|
|
914
|
+
af_range_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>&>(a2));
|
|
915
|
+
}
|
|
916
|
+
|
|
917
|
+
template <int _AP_W2, int _AP_I2, bool _AP_S2, ap_q_mode _AP_Q2,
|
|
918
|
+
ap_o_mode _AP_O2, int _AP_N2>
|
|
919
|
+
INLINE ap_concat_ref<1, ap_bit_ref, 1, af_bit_ref<_AP_W2, _AP_I2, _AP_S2,
|
|
920
|
+
_AP_Q2, _AP_O2, _AP_N2> >
|
|
921
|
+
operator,(
|
|
922
|
+
const af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2> &a2) {
|
|
923
|
+
return ap_concat_ref<1, ap_bit_ref, 1, af_bit_ref<_AP_W2, _AP_I2, _AP_S2,
|
|
924
|
+
_AP_Q2, _AP_O2, _AP_N2> >(
|
|
925
|
+
*this,
|
|
926
|
+
const_cast<af_bit_ref<_AP_W2, _AP_I2, _AP_S2, _AP_Q2, _AP_O2, _AP_N2>&>(
|
|
927
|
+
a2));
|
|
928
|
+
}
|
|
929
|
+
|
|
930
|
+
template <int _AP_W2, bool _AP_S2>
|
|
931
|
+
INLINE bool operator==(const ap_bit_ref<_AP_W2, _AP_S2>& op) {
|
|
932
|
+
return get() == op.get();
|
|
933
|
+
}
|
|
934
|
+
|
|
935
|
+
template <int _AP_W2, bool _AP_S2>
|
|
936
|
+
INLINE bool operator!=(const ap_bit_ref<_AP_W2, _AP_S2>& op) {
|
|
937
|
+
return get() != op.get();
|
|
938
|
+
}
|
|
939
|
+
|
|
940
|
+
INLINE bool get() const { return _AP_ROOT_op_get_bit(d_bv.V, d_index); }
|
|
941
|
+
|
|
942
|
+
INLINE bool get() { return _AP_ROOT_op_get_bit(d_bv.V, d_index); }
|
|
943
|
+
|
|
944
|
+
template <int _AP_W3>
|
|
945
|
+
INLINE void set(const ap_int_base<_AP_W3, false>& val) {
|
|
946
|
+
operator=(val);
|
|
947
|
+
}
|
|
948
|
+
|
|
949
|
+
INLINE bool operator~() const {
|
|
950
|
+
bool bit = _AP_ROOT_op_get_bit(d_bv.V, d_index);
|
|
951
|
+
return bit ? false : true;
|
|
952
|
+
}
|
|
953
|
+
|
|
954
|
+
INLINE int length() const { return 1; }
|
|
955
|
+
|
|
956
|
+
#ifndef __SYNTHESIS__
|
|
957
|
+
std::string to_string() const { return get() ? "1" : "0"; }
|
|
958
|
+
#else
|
|
959
|
+
// XXX HLS will delete this in synthesis
|
|
960
|
+
INLINE char* to_string() const { return 0; }
|
|
961
|
+
#endif
|
|
962
|
+
}; // struct ap_bit_ref
|
|
963
|
+
|
|
964
|
+
/* ap_range_ref with int.
|
|
965
|
+
* ------------------------------------------------------------
|
|
966
|
+
*/
|
|
967
|
+
// equality and relational operators.
|
|
968
|
+
#define REF_REL_OP_WITH_INT(REL_OP, C_TYPE, _AP_W2, _AP_S2) \
|
|
969
|
+
template <int _AP_W, bool _AP_S> \
|
|
970
|
+
INLINE bool operator REL_OP(const ap_range_ref<_AP_W, _AP_S>& op, \
|
|
971
|
+
C_TYPE op2) { \
|
|
972
|
+
return ap_int_base<_AP_W, false>(op) \
|
|
973
|
+
REL_OP ap_int_base<_AP_W2, _AP_S2>(op2); \
|
|
974
|
+
} \
|
|
975
|
+
template <int _AP_W, bool _AP_S> \
|
|
976
|
+
INLINE bool operator REL_OP(const ap_bit_ref<_AP_W, _AP_S>& op, \
|
|
977
|
+
C_TYPE op2) { \
|
|
978
|
+
return bool(op) REL_OP op2; \
|
|
979
|
+
} \
|
|
980
|
+
template <int _AP_W, bool _AP_S> \
|
|
981
|
+
INLINE bool operator REL_OP(C_TYPE op2, \
|
|
982
|
+
const ap_bit_ref<_AP_W, _AP_S>& op) { \
|
|
983
|
+
return op2 REL_OP bool(op); \
|
|
984
|
+
} \
|
|
985
|
+
template <int _AP_W, typename _AP_T, int _AP_W1, typename _AP_T1> \
|
|
986
|
+
INLINE bool operator REL_OP( \
|
|
987
|
+
const ap_concat_ref<_AP_W, _AP_T, _AP_W1, _AP_T1>& op, C_TYPE op2) { \
|
|
988
|
+
return ap_int_base<_AP_W + _AP_W1, false>(op) \
|
|
989
|
+
REL_OP ap_int_base<_AP_W2, _AP_S2>(op2); \
|
|
990
|
+
}
|
|
991
|
+
|
|
992
|
+
// Make the line shorter than 5000 chars
|
|
993
|
+
#define REF_REL_WITH_INT_1(C_TYPE, _AP_WI, _AP_SI) \
|
|
994
|
+
REF_REL_OP_WITH_INT(>, C_TYPE, _AP_WI, _AP_SI) \
|
|
995
|
+
REF_REL_OP_WITH_INT(<, C_TYPE, _AP_WI, _AP_SI) \
|
|
996
|
+
REF_REL_OP_WITH_INT(>=, C_TYPE, _AP_WI, _AP_SI) \
|
|
997
|
+
REF_REL_OP_WITH_INT(<=, C_TYPE, _AP_WI, _AP_SI)
|
|
998
|
+
|
|
999
|
+
REF_REL_WITH_INT_1(bool, 1, false)
|
|
1000
|
+
REF_REL_WITH_INT_1(char, 8, CHAR_IS_SIGNED)
|
|
1001
|
+
REF_REL_WITH_INT_1(signed char, 8, true)
|
|
1002
|
+
REF_REL_WITH_INT_1(unsigned char, 8, false)
|
|
1003
|
+
REF_REL_WITH_INT_1(short, _AP_SIZE_short, true)
|
|
1004
|
+
REF_REL_WITH_INT_1(unsigned short, _AP_SIZE_short, false)
|
|
1005
|
+
REF_REL_WITH_INT_1(int, _AP_SIZE_int, true)
|
|
1006
|
+
REF_REL_WITH_INT_1(unsigned int, _AP_SIZE_int, false)
|
|
1007
|
+
REF_REL_WITH_INT_1(long, _AP_SIZE_long, true)
|
|
1008
|
+
REF_REL_WITH_INT_1(unsigned long, _AP_SIZE_long, false)
|
|
1009
|
+
REF_REL_WITH_INT_1(ap_slong, _AP_SIZE_ap_slong, true)
|
|
1010
|
+
REF_REL_WITH_INT_1(ap_ulong, _AP_SIZE_ap_slong, false)
|
|
1011
|
+
|
|
1012
|
+
// Make the line shorter than 5000 chars
|
|
1013
|
+
#define REF_REL_WITH_INT_2(C_TYPE, _AP_WI, _AP_SI) \
|
|
1014
|
+
REF_REL_OP_WITH_INT(==, C_TYPE, _AP_WI, _AP_SI) \
|
|
1015
|
+
REF_REL_OP_WITH_INT(!=, C_TYPE, _AP_WI, _AP_SI)
|
|
1016
|
+
|
|
1017
|
+
REF_REL_WITH_INT_2(bool, 1, false)
|
|
1018
|
+
REF_REL_WITH_INT_2(char, 8, CHAR_IS_SIGNED)
|
|
1019
|
+
REF_REL_WITH_INT_2(signed char, 8, true)
|
|
1020
|
+
REF_REL_WITH_INT_2(unsigned char, 8, false)
|
|
1021
|
+
REF_REL_WITH_INT_2(short, _AP_SIZE_short, true)
|
|
1022
|
+
REF_REL_WITH_INT_2(unsigned short, _AP_SIZE_short, false)
|
|
1023
|
+
REF_REL_WITH_INT_2(int, _AP_SIZE_int, true)
|
|
1024
|
+
REF_REL_WITH_INT_2(unsigned int, _AP_SIZE_int, false)
|
|
1025
|
+
REF_REL_WITH_INT_2(long, _AP_SIZE_long, true)
|
|
1026
|
+
REF_REL_WITH_INT_2(unsigned long, _AP_SIZE_long, false)
|
|
1027
|
+
REF_REL_WITH_INT_2(ap_slong, _AP_SIZE_ap_slong, true)
|
|
1028
|
+
REF_REL_WITH_INT_2(ap_ulong, _AP_SIZE_ap_slong, false)
|
|
1029
|
+
|
|
1030
|
+
#undef REF_REL_OP_WITH_INT
|
|
1031
|
+
#undef REF_REL_WITH_INT_1
|
|
1032
|
+
#undef REF_REL_WITH_INT_2
|
|
1033
|
+
|
|
1034
|
+
#define REF_BIN_OP_WITH_INT(BIN_OP, RTYPE, C_TYPE, _AP_W2, _AP_S2) \
|
|
1035
|
+
template <int _AP_W, bool _AP_S> \
|
|
1036
|
+
INLINE typename ap_int_base<_AP_W, false>::template RType<_AP_W2, \
|
|
1037
|
+
_AP_S2>::RTYPE \
|
|
1038
|
+
operator BIN_OP(const ap_range_ref<_AP_W, _AP_S>& op, C_TYPE op2) { \
|
|
1039
|
+
return ap_int_base<_AP_W, false>(op) \
|
|
1040
|
+
BIN_OP ap_int_base<_AP_W2, _AP_S2>(op2); \
|
|
1041
|
+
} \
|
|
1042
|
+
template <int _AP_W, bool _AP_S> \
|
|
1043
|
+
INLINE typename ap_int_base<_AP_W2, _AP_S2>::template RType<_AP_W, \
|
|
1044
|
+
false>::RTYPE \
|
|
1045
|
+
operator BIN_OP(C_TYPE op2, const ap_range_ref<_AP_W, _AP_S>& op) { \
|
|
1046
|
+
return ap_int_base<_AP_W2, _AP_S2>(op2) \
|
|
1047
|
+
BIN_OP ap_int_base<_AP_W, false>(op); \
|
|
1048
|
+
}
|
|
1049
|
+
|
|
1050
|
+
// arithmetic operators.
|
|
1051
|
+
#define REF_BIN_OP_WITH_INT_ARITH(C_TYPE, _AP_W2, _AP_S2) \
|
|
1052
|
+
REF_BIN_OP_WITH_INT(+, plus, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1053
|
+
REF_BIN_OP_WITH_INT(-, minus, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1054
|
+
REF_BIN_OP_WITH_INT(*, mult, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1055
|
+
REF_BIN_OP_WITH_INT(/, div, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1056
|
+
REF_BIN_OP_WITH_INT(%, mod, C_TYPE, (_AP_W2), (_AP_S2))
|
|
1057
|
+
|
|
1058
|
+
REF_BIN_OP_WITH_INT_ARITH(bool, 1, false)
|
|
1059
|
+
REF_BIN_OP_WITH_INT_ARITH(char, 8, CHAR_IS_SIGNED)
|
|
1060
|
+
REF_BIN_OP_WITH_INT_ARITH(signed char, 8, true)
|
|
1061
|
+
REF_BIN_OP_WITH_INT_ARITH(unsigned char, 8, false)
|
|
1062
|
+
REF_BIN_OP_WITH_INT_ARITH(short, _AP_SIZE_short, true)
|
|
1063
|
+
REF_BIN_OP_WITH_INT_ARITH(unsigned short, _AP_SIZE_short, false)
|
|
1064
|
+
REF_BIN_OP_WITH_INT_ARITH(int, _AP_SIZE_int, true)
|
|
1065
|
+
REF_BIN_OP_WITH_INT_ARITH(unsigned int, _AP_SIZE_int, false)
|
|
1066
|
+
REF_BIN_OP_WITH_INT_ARITH(long, _AP_SIZE_long, true)
|
|
1067
|
+
REF_BIN_OP_WITH_INT_ARITH(unsigned long, _AP_SIZE_long, false)
|
|
1068
|
+
REF_BIN_OP_WITH_INT_ARITH(ap_slong, _AP_SIZE_ap_slong, true)
|
|
1069
|
+
REF_BIN_OP_WITH_INT_ARITH(ap_ulong, _AP_SIZE_ap_slong, false)
|
|
1070
|
+
|
|
1071
|
+
#undef REF_BIN_OP_WITH_INT_ARITH
|
|
1072
|
+
|
|
1073
|
+
// bitwise and shift operators
|
|
1074
|
+
#define REF_BIN_OP_WITH_INT_BITS(C_TYPE, _AP_W2, _AP_S2) \
|
|
1075
|
+
REF_BIN_OP_WITH_INT(&, logic, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1076
|
+
REF_BIN_OP_WITH_INT(|, logic, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1077
|
+
REF_BIN_OP_WITH_INT(^, logic, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1078
|
+
REF_BIN_OP_WITH_INT(>>, arg1, C_TYPE, (_AP_W2), (_AP_S2)) \
|
|
1079
|
+
REF_BIN_OP_WITH_INT(<<, arg1, C_TYPE, (_AP_W2), (_AP_S2))
|
|
1080
|
+
|
|
1081
|
+
REF_BIN_OP_WITH_INT_BITS(bool, 1, false)
|
|
1082
|
+
REF_BIN_OP_WITH_INT_BITS(char, 8, CHAR_IS_SIGNED)
|
|
1083
|
+
REF_BIN_OP_WITH_INT_BITS(signed char, 8, true)
|
|
1084
|
+
REF_BIN_OP_WITH_INT_BITS(unsigned char, 8, false)
|
|
1085
|
+
REF_BIN_OP_WITH_INT_BITS(short, _AP_SIZE_short, true)
|
|
1086
|
+
REF_BIN_OP_WITH_INT_BITS(unsigned short, _AP_SIZE_short, false)
|
|
1087
|
+
REF_BIN_OP_WITH_INT_BITS(int, _AP_SIZE_int, true)
|
|
1088
|
+
REF_BIN_OP_WITH_INT_BITS(unsigned int, _AP_SIZE_int, false)
|
|
1089
|
+
REF_BIN_OP_WITH_INT_BITS(long, _AP_SIZE_long, true)
|
|
1090
|
+
REF_BIN_OP_WITH_INT_BITS(unsigned long, _AP_SIZE_long, false)
|
|
1091
|
+
REF_BIN_OP_WITH_INT_BITS(ap_slong, _AP_SIZE_ap_slong, true)
|
|
1092
|
+
REF_BIN_OP_WITH_INT_BITS(ap_ulong, _AP_SIZE_ap_slong, false)
|
|
1093
|
+
|
|
1094
|
+
#undef REF_BIN_OP_WITH_INT_BITS
|
|
1095
|
+
|
|
1096
|
+
/* ap_range_ref with ap_range_ref
|
|
1097
|
+
* ------------------------------------------------------------
|
|
1098
|
+
*/
|
|
1099
|
+
#define REF_BIN_OP(BIN_OP, RTYPE) \
|
|
1100
|
+
template <int _AP_W, bool _AP_S, int _AP_W2, bool _AP_S2> \
|
|
1101
|
+
INLINE \
|
|
1102
|
+
typename ap_int_base<_AP_W, false>::template RType<_AP_W2, false>::RTYPE \
|
|
1103
|
+
operator BIN_OP(const ap_range_ref<_AP_W, _AP_S>& lhs, \
|
|
1104
|
+
const ap_range_ref<_AP_W2, _AP_S2>& rhs) { \
|
|
1105
|
+
return (lhs.operator ap_int_base<_AP_W, false>())BIN_OP( \
|
|
1106
|
+
rhs.operator ap_int_base<_AP_W2, false>()); \
|
|
1107
|
+
}
|
|
1108
|
+
|
|
1109
|
+
REF_BIN_OP(+, plus)
|
|
1110
|
+
REF_BIN_OP(-, minus)
|
|
1111
|
+
REF_BIN_OP(*, mult)
|
|
1112
|
+
REF_BIN_OP(/, div)
|
|
1113
|
+
REF_BIN_OP(%, mod)
|
|
1114
|
+
REF_BIN_OP(&, logic)
|
|
1115
|
+
REF_BIN_OP(|, logic)
|
|
1116
|
+
REF_BIN_OP(^, logic)
|
|
1117
|
+
REF_BIN_OP(>>, arg1)
|
|
1118
|
+
REF_BIN_OP(<<, arg1)
|
|
1119
|
+
|
|
1120
|
+
/* ap_concat_ref with ap_concat_ref.
|
|
1121
|
+
* ------------------------------------------------------------
|
|
1122
|
+
*/
|
|
1123
|
+
|
|
1124
|
+
//************************************************************************
|
|
1125
|
+
// Implement
|
|
1126
|
+
// ap_int_base<M+N> = ap_concat_ref<M> OP ap_concat_ref<N>
|
|
1127
|
+
// for operators +, -, *, /, %, >>, <<, &, |, ^
|
|
1128
|
+
// Without these operators the operands are converted to int64 and
|
|
1129
|
+
// larger results lose informations (higher order bits).
|
|
1130
|
+
//
|
|
1131
|
+
// operand OP
|
|
1132
|
+
// / |
|
|
1133
|
+
// left-concat right-concat
|
|
1134
|
+
// / | / |
|
|
1135
|
+
// <LW1,LT1> <LW2,LT2> <RW1,RT1> <RW2,RT2>
|
|
1136
|
+
//
|
|
1137
|
+
// _AP_LW1, _AP_LT1 (width and type of left-concat's left side)
|
|
1138
|
+
// _AP_LW2, _AP_LT2 (width and type of left-concat's right side)
|
|
1139
|
+
// Similarly for RHS of operand OP: _AP_RW1, AP_RW2, _AP_RT1, _AP_RT2
|
|
1140
|
+
//
|
|
1141
|
+
// In Verilog 2001 result of concatenation is always unsigned even
|
|
1142
|
+
// when both sides are signed.
|
|
1143
|
+
//************************************************************************
|
|
1144
|
+
|
|
1145
|
+
#undef SYN_CONCAT_REF_BIN_OP
|
|
1146
|
+
|
|
1147
|
+
#define SYN_CONCAT_REF_BIN_OP(BIN_OP, RTYPE) \
|
|
1148
|
+
template <int _AP_LW1, typename _AP_LT1, int _AP_LW2, typename _AP_LT2, \
|
|
1149
|
+
int _AP_RW1, typename _AP_RT1, int _AP_RW2, typename _AP_RT2> \
|
|
1150
|
+
INLINE typename ap_int_base<_AP_LW1 + _AP_LW2, false>::template RType< \
|
|
1151
|
+
_AP_RW1 + _AP_RW2, false>::RTYPE \
|
|
1152
|
+
operator BIN_OP( \
|
|
1153
|
+
const ap_concat_ref<_AP_LW1, _AP_LT1, _AP_LW2, _AP_LT2>& lhs, \
|
|
1154
|
+
const ap_concat_ref<_AP_RW1, _AP_RT1, _AP_RW2, _AP_RT2>& rhs) { \
|
|
1155
|
+
return lhs.get() BIN_OP rhs.get(); \
|
|
1156
|
+
}
|
|
1157
|
+
|
|
1158
|
+
SYN_CONCAT_REF_BIN_OP(+, plus)
|
|
1159
|
+
SYN_CONCAT_REF_BIN_OP(-, minus)
|
|
1160
|
+
SYN_CONCAT_REF_BIN_OP(*, mult)
|
|
1161
|
+
SYN_CONCAT_REF_BIN_OP(/, div)
|
|
1162
|
+
SYN_CONCAT_REF_BIN_OP(%, mod)
|
|
1163
|
+
SYN_CONCAT_REF_BIN_OP(&, logic)
|
|
1164
|
+
SYN_CONCAT_REF_BIN_OP(|, logic)
|
|
1165
|
+
SYN_CONCAT_REF_BIN_OP(^, logic)
|
|
1166
|
+
SYN_CONCAT_REF_BIN_OP(>>, arg1)
|
|
1167
|
+
SYN_CONCAT_REF_BIN_OP(<<, arg1)
|
|
1168
|
+
|
|
1169
|
+
#undef SYN_CONCAT_REF_BIN_OP
|
|
1170
|
+
|
|
1171
|
+
#define CONCAT_OP_WITH_INT(C_TYPE, _AP_WI, _AP_SI) \
|
|
1172
|
+
template <int _AP_W, bool _AP_S> \
|
|
1173
|
+
INLINE ap_int_base<_AP_W + _AP_WI, false> operator,( \
|
|
1174
|
+
const ap_int_base<_AP_W, _AP_S> &op1, C_TYPE op2) { \
|
|
1175
|
+
ap_int_base<_AP_WI + _AP_W, false> val(op2); \
|
|
1176
|
+
ap_int_base<_AP_WI + _AP_W, false> ret(op1); \
|
|
1177
|
+
ret <<= _AP_WI; \
|
|
1178
|
+
if (_AP_SI) { \
|
|
1179
|
+
val <<= _AP_W; \
|
|
1180
|
+
val >>= _AP_W; \
|
|
1181
|
+
} \
|
|
1182
|
+
ret |= val; \
|
|
1183
|
+
return ret; \
|
|
1184
|
+
} \
|
|
1185
|
+
template <int _AP_W, bool _AP_S> \
|
|
1186
|
+
INLINE ap_int_base<_AP_W + _AP_WI, false> operator,( \
|
|
1187
|
+
C_TYPE op1, const ap_int_base<_AP_W, _AP_S> &op2) { \
|
|
1188
|
+
ap_int_base<_AP_WI + _AP_W, false> val(op1); \
|
|
1189
|
+
ap_int_base<_AP_WI + _AP_W, false> ret(op2); \
|
|
1190
|
+
if (_AP_S) { \
|
|
1191
|
+
ret <<= _AP_WI; \
|
|
1192
|
+
ret >>= _AP_WI; \
|
|
1193
|
+
} \
|
|
1194
|
+
ret |= val << _AP_W; \
|
|
1195
|
+
return ret; \
|
|
1196
|
+
} \
|
|
1197
|
+
template <int _AP_W, bool _AP_S> \
|
|
1198
|
+
INLINE ap_int_base<_AP_W + _AP_WI, false> operator,( \
|
|
1199
|
+
const ap_range_ref<_AP_W, _AP_S> &op1, C_TYPE op2) { \
|
|
1200
|
+
ap_int_base<_AP_WI + _AP_W, false> val(op2); \
|
|
1201
|
+
ap_int_base<_AP_WI + _AP_W, false> ret(op1); \
|
|
1202
|
+
ret <<= _AP_WI; \
|
|
1203
|
+
if (_AP_SI) { \
|
|
1204
|
+
val <<= _AP_W; \
|
|
1205
|
+
val >>= _AP_W; \
|
|
1206
|
+
} \
|
|
1207
|
+
ret |= val; \
|
|
1208
|
+
return ret; \
|
|
1209
|
+
} \
|
|
1210
|
+
template <int _AP_W, bool _AP_S> \
|
|
1211
|
+
INLINE ap_int_base<_AP_W + _AP_WI, false> operator,( \
|
|
1212
|
+
C_TYPE op1, const ap_range_ref<_AP_W, _AP_S> &op2) { \
|
|
1213
|
+
ap_int_base<_AP_WI + _AP_W, false> val(op1); \
|
|
1214
|
+
ap_int_base<_AP_WI + _AP_W, false> ret(op2); \
|
|
1215
|
+
int len = op2.length(); \
|
|
1216
|
+
val <<= len; \
|
|
1217
|
+
ret |= val; \
|
|
1218
|
+
return ret; \
|
|
1219
|
+
} \
|
|
1220
|
+
template <int _AP_W, bool _AP_S> \
|
|
1221
|
+
INLINE ap_int_base<_AP_WI + 1, false> operator,( \
|
|
1222
|
+
const ap_bit_ref<_AP_W, _AP_S> &op1, C_TYPE op2) { \
|
|
1223
|
+
ap_int_base<_AP_WI + 1, false> val(op2); \
|
|
1224
|
+
val[_AP_WI] = op1; \
|
|
1225
|
+
return val; \
|
|
1226
|
+
} \
|
|
1227
|
+
template <int _AP_W, bool _AP_S> \
|
|
1228
|
+
INLINE ap_int_base<_AP_WI + 1, false> operator,( \
|
|
1229
|
+
C_TYPE op1, const ap_bit_ref<_AP_W, _AP_S> &op2) { \
|
|
1230
|
+
ap_int_base<_AP_WI + 1, false> val(op1); \
|
|
1231
|
+
val <<= 1; \
|
|
1232
|
+
val[0] = op2; \
|
|
1233
|
+
return val; \
|
|
1234
|
+
} \
|
|
1235
|
+
template <int _AP_W, typename _AP_T, int _AP_W2, typename _AP_T2> \
|
|
1236
|
+
INLINE ap_int_base<_AP_W + _AP_W2 + _AP_WI, false> operator,( \
|
|
1237
|
+
const ap_concat_ref<_AP_W, _AP_T, _AP_W2, _AP_T2> &op1, C_TYPE op2) { \
|
|
1238
|
+
ap_int_base<_AP_WI + _AP_W + _AP_W2, _AP_SI> val(op2); \
|
|
1239
|
+
ap_int_base<_AP_WI + _AP_W + _AP_W2, _AP_SI> ret(op1); \
|
|
1240
|
+
if (_AP_SI) { \
|
|
1241
|
+
val <<= _AP_W + _AP_W2; \
|
|
1242
|
+
val >>= _AP_W + _AP_W2; \
|
|
1243
|
+
} \
|
|
1244
|
+
ret <<= _AP_WI; \
|
|
1245
|
+
ret |= val; \
|
|
1246
|
+
return ret; \
|
|
1247
|
+
} \
|
|
1248
|
+
template <int _AP_W, typename _AP_T, int _AP_W2, typename _AP_T2> \
|
|
1249
|
+
INLINE ap_int_base<_AP_W + _AP_W2 + _AP_WI, false> operator,( \
|
|
1250
|
+
C_TYPE op1, const ap_concat_ref<_AP_W, _AP_T, _AP_W2, _AP_T2> &op2) { \
|
|
1251
|
+
ap_int_base<_AP_WI + _AP_W + _AP_W2, _AP_SI> val(op1); \
|
|
1252
|
+
ap_int_base<_AP_WI + _AP_W + _AP_W2, _AP_SI> ret(op2); \
|
|
1253
|
+
int len = op2.length(); \
|
|
1254
|
+
val <<= len; \
|
|
1255
|
+
ret |= val; \
|
|
1256
|
+
return ret; \
|
|
1257
|
+
} \
|
|
1258
|
+
template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
|
|
1259
|
+
ap_o_mode _AP_O, int _AP_N> \
|
|
1260
|
+
INLINE ap_int_base<_AP_W + _AP_WI, false> operator,( \
|
|
1261
|
+
const af_range_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N> &op1, \
|
|
1262
|
+
C_TYPE op2) { \
|
|
1263
|
+
ap_int_base<_AP_WI + _AP_W, false> val(op2); \
|
|
1264
|
+
ap_int_base<_AP_WI + _AP_W, false> ret(op1); \
|
|
1265
|
+
if (_AP_SI) { \
|
|
1266
|
+
val <<= _AP_W; \
|
|
1267
|
+
val >>= _AP_W; \
|
|
1268
|
+
} \
|
|
1269
|
+
ret <<= _AP_WI; \
|
|
1270
|
+
ret |= val; \
|
|
1271
|
+
return ret; \
|
|
1272
|
+
} \
|
|
1273
|
+
template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
|
|
1274
|
+
ap_o_mode _AP_O, int _AP_N> \
|
|
1275
|
+
INLINE ap_int_base<_AP_W + _AP_WI, false> operator,( \
|
|
1276
|
+
C_TYPE op1, \
|
|
1277
|
+
const af_range_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N> &op2) { \
|
|
1278
|
+
ap_int_base<_AP_WI + _AP_W, false> val(op1); \
|
|
1279
|
+
ap_int_base<_AP_WI + _AP_W, false> ret(op2); \
|
|
1280
|
+
int len = op2.length(); \
|
|
1281
|
+
val <<= len; \
|
|
1282
|
+
ret |= val; \
|
|
1283
|
+
return ret; \
|
|
1284
|
+
} \
|
|
1285
|
+
template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
|
|
1286
|
+
ap_o_mode _AP_O, int _AP_N> \
|
|
1287
|
+
INLINE ap_int_base<1 + _AP_WI, false> operator,( \
|
|
1288
|
+
const af_bit_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N> &op1, \
|
|
1289
|
+
C_TYPE op2) { \
|
|
1290
|
+
ap_int_base<_AP_WI + 1, _AP_SI> val(op2); \
|
|
1291
|
+
val[_AP_WI] = op1; \
|
|
1292
|
+
return val; \
|
|
1293
|
+
} \
|
|
1294
|
+
template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
|
|
1295
|
+
ap_o_mode _AP_O, int _AP_N> \
|
|
1296
|
+
INLINE ap_int_base<1 + _AP_WI, false> operator,( \
|
|
1297
|
+
C_TYPE op1, \
|
|
1298
|
+
const af_bit_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N> &op2) { \
|
|
1299
|
+
ap_int_base<_AP_WI + 1, _AP_SI> val(op1); \
|
|
1300
|
+
val <<= 1; \
|
|
1301
|
+
val[0] = op2; \
|
|
1302
|
+
return val; \
|
|
1303
|
+
}
|
|
1304
|
+
|
|
1305
|
+
CONCAT_OP_WITH_INT(bool, 1, false)
|
|
1306
|
+
CONCAT_OP_WITH_INT(char, 8, CHAR_IS_SIGNED)
|
|
1307
|
+
CONCAT_OP_WITH_INT(signed char, 8, true)
|
|
1308
|
+
CONCAT_OP_WITH_INT(unsigned char, 8, false)
|
|
1309
|
+
CONCAT_OP_WITH_INT(short, _AP_SIZE_short, true)
|
|
1310
|
+
CONCAT_OP_WITH_INT(unsigned short, _AP_SIZE_short, false)
|
|
1311
|
+
CONCAT_OP_WITH_INT(int, _AP_SIZE_int, true)
|
|
1312
|
+
CONCAT_OP_WITH_INT(unsigned int, _AP_SIZE_int, false)
|
|
1313
|
+
CONCAT_OP_WITH_INT(long, _AP_SIZE_long, true)
|
|
1314
|
+
CONCAT_OP_WITH_INT(unsigned long, _AP_SIZE_long, false)
|
|
1315
|
+
CONCAT_OP_WITH_INT(ap_slong, _AP_SIZE_ap_slong, true)
|
|
1316
|
+
CONCAT_OP_WITH_INT(ap_ulong, _AP_SIZE_ap_slong, false)
|
|
1317
|
+
|
|
1318
|
+
#undef CONCAT_OP_WITH_INT
|
|
1319
|
+
|
|
1320
|
+
#define CONCAT_SHIFT_WITH_INT(C_TYPE, OP) \
|
|
1321
|
+
template <int _AP_W, typename _AP_T, int _AP_W1, typename _AP_T1> \
|
|
1322
|
+
INLINE ap_uint<_AP_W + _AP_W1> operator OP( \
|
|
1323
|
+
const ap_concat_ref<_AP_W, _AP_T, _AP_W1, _AP_T1> lhs, C_TYPE rhs) { \
|
|
1324
|
+
return ap_uint<_AP_W + _AP_W1>(lhs).get() OP int(rhs); \
|
|
1325
|
+
}
|
|
1326
|
+
|
|
1327
|
+
// FIXME int(rhs) may loose precision.
|
|
1328
|
+
|
|
1329
|
+
CONCAT_SHIFT_WITH_INT(int, <<)
|
|
1330
|
+
CONCAT_SHIFT_WITH_INT(unsigned int, <<)
|
|
1331
|
+
CONCAT_SHIFT_WITH_INT(long, <<)
|
|
1332
|
+
CONCAT_SHIFT_WITH_INT(unsigned long, <<)
|
|
1333
|
+
CONCAT_SHIFT_WITH_INT(ap_slong, <<)
|
|
1334
|
+
CONCAT_SHIFT_WITH_INT(ap_ulong, <<)
|
|
1335
|
+
|
|
1336
|
+
CONCAT_SHIFT_WITH_INT(int, >>)
|
|
1337
|
+
CONCAT_SHIFT_WITH_INT(unsigned int, >>)
|
|
1338
|
+
CONCAT_SHIFT_WITH_INT(long, >>)
|
|
1339
|
+
CONCAT_SHIFT_WITH_INT(unsigned long, >>)
|
|
1340
|
+
CONCAT_SHIFT_WITH_INT(ap_slong, >>)
|
|
1341
|
+
CONCAT_SHIFT_WITH_INT(ap_ulong, >>)
|
|
1342
|
+
|
|
1343
|
+
#endif // ifndef __cplusplus
|
|
1344
|
+
#endif // ifndef __AP_INT_REF_H__
|
|
1345
|
+
|
|
1346
|
+
// -*- cpp -*-
|