File indexing completed on 2024-04-06 12:21:25
0001 #ifndef CC_INVERSION_H__
0002 #define CC_INVERSION_H__
0003
0004 namespace l1ct {
0005
0006 constexpr int ceillog2(int x) { return (x <= 2) ? 1 : 1 + ceillog2((x + 1) / 2); }
0007
0008 template <class data_T, int N>
0009 inline float real_val_from_idx(unsigned i) {
0010
0011 static constexpr int NB = ceillog2(N);
0012 data_T x(0);
0013
0014 x[x.width - 1] = 1;
0015
0016 x(x.width - 2, x.width - NB - 1) = i;
0017 return (float)x;
0018 }
0019
0020 template <class data_T, int N>
0021 inline unsigned idx_from_real_val(data_T x) {
0022
0023 static constexpr int NB = ceillog2(N);
0024
0025
0026 ap_uint<NB> y = x(x.width - 2, x.width - NB - 1);
0027 return (unsigned)y(NB - 1, 0);
0028 }
0029
0030 template <class data_T, class table_T, int N>
0031 void init_invert_table(table_T table_out[N]) {
0032
0033 for (unsigned i = 0; i < N; i++) {
0034 float x = real_val_from_idx<data_T, N>(i);
0035 table_T inv_x = 1 / x;
0036 table_out[i] = inv_x;
0037 }
0038 }
0039
0040 template <class in_t, class table_t, int N>
0041 table_t invert_with_shift(in_t in) {
0042 table_t inv_table[N];
0043 init_invert_table<in_t, table_t, N>(inv_table);
0044
0045
0046 int msb = 0;
0047 for (int b = 0; b < in.width; b++) {
0048
0049 if (in[b])
0050 msb = b;
0051 }
0052
0053 in_t in_shifted = in << (in.width - msb - 1);
0054
0055 int idx = idx_from_real_val<in_t, N>(in_shifted);
0056 table_t inv_in = inv_table[idx];
0057
0058 table_t out = inv_in << (in.width - msb - 1);
0059 return out;
0060 }
0061
0062 }
0063 #endif