17#ifndef __AP_FIXED_REF_H__
18#define __AP_FIXED_REF_H__
21#error "Only ap_fixed.h and ap_int.h can be included directly in user code."
25#error "C++ is required to include this header file"
33template <
int _AP_W,
int _AP_I,
bool _AP_S, ap_q_mode _AP_Q, ap_o_mode _AP_O,
37#pragma warning(disable : 4521 4522)
46 : d_bv(ref.d_bv), d_index(ref.d_index) {
48 _AP_WARNING(d_index < 0,
"Index of bit vector (%d) cannot be negative.",
50 _AP_WARNING(d_index >= _AP_W,
"Index of bit vector (%d) out of range (%d).",
55 INLINE
af_bit_ref(ref_type* bv,
int index = 0) : d_bv(*bv), d_index(index) {}
57 INLINE
af_bit_ref(
const ref_type* bv,
int index = 0)
58 : d_bv(*const_cast<ref_type*>(bv)), d_index(index) {}
61 INLINE
operator bool()
const {
return _AP_ROOT_op_get_bit(d_bv.V, d_index); }
66 d_bv.V = _AP_ROOT_op_set_bit(d_bv.V, d_index, val);
73 return operator=(
bool(val));
76 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
77 ap_o_mode _AP_O2,
int _AP_N2>
80 return operator=(
bool(val));
83 template <
int _AP_W2,
bool _AP_S2>
85 return operator=(
bool(val));
88 template <
int _AP_W2,
bool _AP_S2>
90 return operator=(val != 0);
93 template <
int _AP_W2,
bool _AP_S2>
98 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
99 ap_o_mode _AP_O2,
int _AP_N2>
105 template <
int _AP_W2,
typename _AP_T2,
int _AP_W3,
typename _AP_T3>
114 template <
int _AP_W2,
int _AP_S2>
121 template <
int _AP_W2,
int _AP_S2>
128 template <
int _AP_W2,
int _AP_S2>
135 template <
int _AP_W2,
typename _AP_T2,
int _AP_W3,
typename _AP_T3>
144 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
145 ap_o_mode _AP_O2,
int _AP_N2>
157 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
158 ap_o_mode _AP_O2,
int _AP_N2>
175 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
176 ap_o_mode _AP_O2,
int _AP_N2>
177 INLINE
bool operator==(
179 return get() == op.get();
182 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
183 ap_o_mode _AP_O2,
int _AP_N2>
184 INLINE
bool operator!=(
186 return get() != op.get();
190 INLINE
bool operator~()
const {
191 bool bit = _AP_ROOT_op_get_bit(d_bv.V, d_index);
192 return bit ? false :
true;
195 INLINE
bool get()
const {
return _AP_ROOT_op_get_bit(d_bv.V, d_index); }
197 INLINE
int length()
const {
return 1; }
200 std::string to_string()
const {
return get() ?
"1" :
"0"; }
203 INLINE
char* to_string()
const {
return 0; }
210template <
int _AP_W,
int _AP_I,
bool _AP_S, ap_q_mode _AP_Q, ap_o_mode _AP_O,
212INLINE std::ostream& operator<<(
222template <
int _AP_W,
int _AP_I,
bool _AP_S, ap_q_mode _AP_Q, ap_o_mode _AP_O,
226#pragma warning(disable : 4521 4522)
237 : d_bv(ref.d_bv), l_index(ref.l_index), h_index(ref.h_index) {}
243 : d_bv(*bv), l_index(l), h_index(h) {
245 _AP_WARNING(h < 0 || l < 0,
246 "Higher bound(%d) and lower(%d) bound cannot be negative.", h,
248 _AP_WARNING(h >= _AP_W || l >= _AP_W,
249 "Higher bound(%d) or lower(%d) bound out of range.", h, l);
250 _AP_WARNING(h < l,
"The bits selected will be returned in reverse order.");
255 : d_bv(*const_cast<ref_type*>(bv)), l_index(l), h_index(h) {
257 _AP_WARNING(h < 0 || l < 0,
258 "Higher bound(%d) and lower(%d) bound cannot be negative.", h,
260 _AP_WARNING(h >= _AP_W || l >= _AP_W,
261 "Higher bound(%d) or lower(%d) bound out of range.", h, l);
262 _AP_WARNING(h < l,
"The bits selected will be returned in reverse order.");
269#define ASSIGN_CTYPE_TO_AF_RANGE(DATA_TYPE) \
270 INLINE af_range_ref& operator=(const DATA_TYPE val) { \
271 ap_int_base<_AP_W, false> loc(val); \
272 d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, loc.V); \
276 ASSIGN_CTYPE_TO_AF_RANGE(
bool)
277 ASSIGN_CTYPE_TO_AF_RANGE(
char)
278 ASSIGN_CTYPE_TO_AF_RANGE(
signed char)
279 ASSIGN_CTYPE_TO_AF_RANGE(
unsigned char)
280 ASSIGN_CTYPE_TO_AF_RANGE(
short)
281 ASSIGN_CTYPE_TO_AF_RANGE(
unsigned short)
282 ASSIGN_CTYPE_TO_AF_RANGE(
int)
283 ASSIGN_CTYPE_TO_AF_RANGE(
unsigned int)
284 ASSIGN_CTYPE_TO_AF_RANGE(
long)
285 ASSIGN_CTYPE_TO_AF_RANGE(
unsigned long)
286 ASSIGN_CTYPE_TO_AF_RANGE(ap_slong)
287 ASSIGN_CTYPE_TO_AF_RANGE(ap_ulong)
288#if _AP_ENABLE_HALF_ == 1
289 ASSIGN_CTYPE_TO_AF_RANGE(half)
291 ASSIGN_CTYPE_TO_AF_RANGE(
float)
292 ASSIGN_CTYPE_TO_AF_RANGE(
double)
293#undef ASSIGN_CTYPE_TO_AF_RANGE
298 d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, tmp.V);
304 template <
int _AP_W3,
bool _AP_S3>
306 d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, val.V);
311 template <
int _AP_W2,
bool _AP_S2>
314 return operator=(tmp);
318 template <
int _AP_W2,
bool _AP_S2>
321 return operator=(tmp);
325 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
326 ap_o_mode _AP_O2,
int _AP_N2>
330 d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, val.V);
339 return operator=(tmp);
343 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
344 ap_o_mode _AP_O2,
int _AP_N2>
348 return operator=(tmp);
352 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
353 ap_o_mode _AP_O2,
int _AP_N2>
357 return operator=(tmp);
361 template <
int _AP_W2,
typename _AP_T2,
int _AP_W3,
typename _AP_T3>
365 return operator=(tmp);
371 template <
int _AP_W2,
bool _AP_S2>
378 template <
int _AP_W2,
bool _AP_S2>
380 return !(operator==(op2));
383 template <
int _AP_W2,
bool _AP_S2>
390 template <
int _AP_W2,
bool _AP_S2>
397 template <
int _AP_W2,
bool _AP_S2>
399 return !(operator>(op2));
402 template <
int _AP_W2,
bool _AP_S2>
404 return !(operator<(op2));
410 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
411 ap_o_mode _AP_O2,
int _AP_N2>
412 INLINE
bool operator==(
419 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
420 ap_o_mode _AP_O2,
int _AP_N2>
421 INLINE
bool operator!=(
423 return !(operator==(op2));
426 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
427 ap_o_mode _AP_O2,
int _AP_N2>
428 INLINE
bool operator<(
435 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
436 ap_o_mode _AP_O2,
int _AP_N2>
437 INLINE
bool operator>(
444 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
445 ap_o_mode _AP_O2,
int _AP_N2>
446 INLINE
bool operator<=(
448 return !(operator>(op2));
451 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
452 ap_o_mode _AP_O2,
int _AP_N2>
453 INLINE
bool operator>=(
455 return !(operator<(op2));
462 template <
int _AP_W2,
int _AP_S2>
471 template <
int _AP_W2,
int _AP_S2>
479 template <
int _AP_W2,
int _AP_S2>
489 template <
int _AP_W2,
typename _AP_T2,
int _AP_W3,
typename _AP_T3>
499 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
500 ap_o_mode _AP_O2,
int _AP_N2>
515 template <
int _AP_W2,
int _AP_I2,
bool _AP_S2, ap_q_mode _AP_Q2,
516 ap_o_mode _AP_O2,
int _AP_N2>
531 INLINE
operator ap_ulong()
const {
533 ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
534 return ret.to_uint64();
539 ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
545 ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
550 INLINE
char to_char()
const {
551 return (
char)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
554 INLINE
int to_int()
const {
555 return (
int)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
558 INLINE
unsigned to_uint()
const {
559 return (
unsigned)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
562 INLINE
long to_long()
const {
563 return (
long)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
566 INLINE
unsigned long to_ulong()
const {
567 return (
unsigned long)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
570 INLINE ap_slong to_int64()
const {
571 return (ap_slong)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
574 INLINE ap_ulong to_uint64()
const {
575 return (ap_ulong)(_AP_ROOT_op_get_range(d_bv.V, l_index, h_index));
580 ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
584 template <
int _AP_W2>
586 d_bv.V = _AP_ROOT_op_set_range(d_bv.V, l_index, h_index, val.V);
589 INLINE
int length()
const {
590 return h_index >= l_index ? h_index - l_index + 1 : l_index - h_index + 1;
594 std::string to_string(
signed char rd = 2)
const {
596 ret.V = _AP_ROOT_op_get_range(d_bv.V, l_index, h_index);
597 return ret.to_string(rd);
601 INLINE
char* to_string(
signed char rd = 2)
const {
return 0; }
608template <
int _AP_W,
int _AP_I,
bool _AP_S, ap_q_mode _AP_Q, ap_o_mode _AP_O,
610INLINE std::ostream& operator<<(
619#define AF_REF_REL_OP_WITH_INT(REL_OP, C_TYPE, _AP_W2, _AP_S2) \
620 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
621 ap_o_mode _AP_O, int _AP_N> \
622 INLINE bool operator REL_OP( \
623 const af_range_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op, \
625 return ap_int_base<_AP_W, false>(op) \
626 REL_OP ap_int_base<_AP_W2, _AP_S2>(op2); \
629 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
630 ap_o_mode _AP_O, int _AP_N> \
631 INLINE bool operator REL_OP( \
633 const af_range_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op) { \
634 return ap_int_base<_AP_W2, _AP_S2>(op2) \
635 REL_OP ap_int_base<_AP_W, false>(op); \
638 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
639 ap_o_mode _AP_O, int _AP_N> \
640 INLINE bool operator REL_OP( \
641 const af_bit_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op, \
643 return bool(op) REL_OP op2; \
646 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
647 ap_o_mode _AP_O, int _AP_N> \
648 INLINE bool operator REL_OP( \
650 const af_bit_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op) { \
651 return op2 REL_OP bool(op); \
654#define AF_REF_REL_OPS_WITH_INT(C_TYPE, _AP_W2, _AP_S2) \
655 AF_REF_REL_OP_WITH_INT(>, C_TYPE, (_AP_W2), (_AP_S2)) \
656 AF_REF_REL_OP_WITH_INT(<, C_TYPE, (_AP_W2), (_AP_S2)) \
657 AF_REF_REL_OP_WITH_INT(>=, C_TYPE, (_AP_W2), (_AP_S2)) \
658 AF_REF_REL_OP_WITH_INT(<=, C_TYPE, (_AP_W2), (_AP_S2)) \
659 AF_REF_REL_OP_WITH_INT(==, C_TYPE, (_AP_W2), (_AP_S2)) \
660 AF_REF_REL_OP_WITH_INT(!=, C_TYPE, (_AP_W2), (_AP_S2))
662AF_REF_REL_OPS_WITH_INT(
bool, 1,
false)
663AF_REF_REL_OPS_WITH_INT(
char, 8, CHAR_IS_SIGNED)
664AF_REF_REL_OPS_WITH_INT(
signed char, 8, true)
665AF_REF_REL_OPS_WITH_INT(
unsigned char, 8, false)
666AF_REF_REL_OPS_WITH_INT(
short, _AP_SIZE_short, true)
667AF_REF_REL_OPS_WITH_INT(
unsigned short, _AP_SIZE_short, false)
668AF_REF_REL_OPS_WITH_INT(
int, _AP_SIZE_int, true)
669AF_REF_REL_OPS_WITH_INT(
unsigned int, _AP_SIZE_int, false)
670AF_REF_REL_OPS_WITH_INT(
long, _AP_SIZE_long, true)
671AF_REF_REL_OPS_WITH_INT(
unsigned long, _AP_SIZE_long, false)
672AF_REF_REL_OPS_WITH_INT(ap_slong, _AP_SIZE_ap_slong, true)
673AF_REF_REL_OPS_WITH_INT(ap_ulong, _AP_SIZE_ap_slong, false)
675#undef AF_REF_REL_OP_INT
676#undef AF_REF_REL_OPS_WITH_INT
678#define AF_REF_REL_OP_WITH_AP_INT(REL_OP) \
679 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
680 ap_o_mode _AP_O, int _AP_N, int _AP_W2, bool _AP_S2> \
681 INLINE bool operator REL_OP( \
682 const af_range_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op, \
683 const ap_int_base<_AP_W2, _AP_S>& op2) { \
684 return ap_int_base<_AP_W, false>(op) REL_OP op2; \
686 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
687 ap_o_mode _AP_O, int _AP_N, int _AP_W2, bool _AP_S2> \
688 INLINE bool operator REL_OP( \
689 const ap_int_base<_AP_W2, _AP_S2>& op2, \
690 const af_range_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op) { \
691 return op2 REL_OP ap_int_base<_AP_W, false>(op); \
693 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
694 ap_o_mode _AP_O, int _AP_N, int _AP_W2, bool _AP_S2> \
695 INLINE bool operator REL_OP( \
696 const af_bit_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op, \
697 const ap_int_base<_AP_W2, _AP_S2>& op2) { \
698 return ap_int_base<1, false>(op) REL_OP op2; \
700 template <int _AP_W, int _AP_I, bool _AP_S, ap_q_mode _AP_Q, \
701 ap_o_mode _AP_O, int _AP_N, int _AP_W2, bool _AP_S2> \
702 INLINE bool operator REL_OP( \
703 const ap_int_base<_AP_W2, _AP_S2>& op2, \
704 const af_bit_ref<_AP_W, _AP_I, _AP_S, _AP_Q, _AP_O, _AP_N>& op) { \
705 return op2 REL_OP ap_int_base<1, false>(op); \
708AF_REF_REL_OP_WITH_AP_INT(>)
709AF_REF_REL_OP_WITH_AP_INT(<)
710AF_REF_REL_OP_WITH_AP_INT(>=)
711AF_REF_REL_OP_WITH_AP_INT(<=)
712AF_REF_REL_OP_WITH_AP_INT(==)
713AF_REF_REL_OP_WITH_AP_INT(!=)