arnaucube
arnaucube/poulpyPublic Self-hosted repository
poulpy/poulpy-backend/src/cpu_spqlios/spqlios-arithmetic/spqlios/arithmetic/zn_api.c
poulpy-backend/src/cpu_spqlios/spqlios-arithmetic/spqlios/arithmetic/zn_api.cRaw
  1#include <string.h>
  2
  3#include "zn_arithmetic_private.h"
  4
  5void default_init_z_module_precomp(MOD_Z* module) {
  6  // Add here initialization of items that are in the precomp
  7}
  8
  9void default_finalize_z_module_precomp(MOD_Z* module) {
 10  // Add here deleters for items that are in the precomp
 11}
 12
 13void default_init_z_module_vtable(MOD_Z* module) {
 14  // Add function pointers here
 15  module->vtable.i8_approxdecomp_from_tndbl = default_i8_approxdecomp_from_tndbl_ref;
 16  module->vtable.i16_approxdecomp_from_tndbl = default_i16_approxdecomp_from_tndbl_ref;
 17  module->vtable.i32_approxdecomp_from_tndbl = default_i32_approxdecomp_from_tndbl_ref;
 18  module->vtable.zn32_vmp_prepare_contiguous = default_zn32_vmp_prepare_contiguous_ref;
 19  module->vtable.zn32_vmp_prepare_dblptr = default_zn32_vmp_prepare_dblptr_ref;
 20  module->vtable.zn32_vmp_prepare_row = default_zn32_vmp_prepare_row_ref;
 21  module->vtable.zn32_vmp_apply_i8 = default_zn32_vmp_apply_i8_ref;
 22  module->vtable.zn32_vmp_apply_i16 = default_zn32_vmp_apply_i16_ref;
 23  module->vtable.zn32_vmp_apply_i32 = default_zn32_vmp_apply_i32_ref;
 24  module->vtable.dbl_to_tn32 = dbl_to_tn32_ref;
 25  module->vtable.tn32_to_dbl = tn32_to_dbl_ref;
 26  module->vtable.dbl_round_to_i32 = dbl_round_to_i32_ref;
 27  module->vtable.i32_to_dbl = i32_to_dbl_ref;
 28  module->vtable.dbl_round_to_i64 = dbl_round_to_i64_ref;
 29  module->vtable.i64_to_dbl = i64_to_dbl_ref;
 30
 31  // Add optimized function pointers here
 32  if (CPU_SUPPORTS("avx")) {
 33    module->vtable.zn32_vmp_apply_i8 = default_zn32_vmp_apply_i8_avx;
 34    module->vtable.zn32_vmp_apply_i16 = default_zn32_vmp_apply_i16_avx;
 35    module->vtable.zn32_vmp_apply_i32 = default_zn32_vmp_apply_i32_avx;
 36  }
 37}
 38
 39void init_z_module_info(MOD_Z* module,  //
 40                        Z_MODULE_TYPE mtype) {
 41  memset(module, 0, sizeof(MOD_Z));
 42  module->mtype = mtype;
 43  switch (mtype) {
 44    case DEFAULT:
 45      default_init_z_module_precomp(module);
 46      default_init_z_module_vtable(module);
 47      break;
 48    default:
 49      NOT_SUPPORTED();  // unknown mtype
 50  }
 51}
 52
 53void finalize_z_module_info(MOD_Z* module) {
 54  if (module->custom) module->custom_deleter(module->custom);
 55  switch (module->mtype) {
 56    case DEFAULT:
 57      default_finalize_z_module_precomp(module);
 58      // fft64_finalize_rnx_module_vtable(module); // nothing to finalize
 59      break;
 60    default:
 61      NOT_SUPPORTED();  // unknown mtype
 62  }
 63}
 64
 65EXPORT MOD_Z* new_z_module_info(Z_MODULE_TYPE mtype) {
 66  MOD_Z* res = (MOD_Z*)malloc(sizeof(MOD_Z));
 67  init_z_module_info(res, mtype);
 68  return res;
 69}
 70
 71EXPORT void delete_z_module_info(MOD_Z* module_info) {
 72  finalize_z_module_info(module_info);
 73  free(module_info);
 74}
 75
 76//////////////// wrappers //////////////////
 77
 78/** @brief sets res = gadget_decompose(a) (int8_t* output) */
 79EXPORT void i8_approxdecomp_from_tndbl(const MOD_Z* module,                      // N
 80                                       const TNDBL_APPROXDECOMP_GADGET* gadget,  // gadget
 81                                       int8_t* res, uint64_t res_size,           // res (in general, size ell.a_size)
 82                                       const double* a, uint64_t a_size) {       // a
 83  module->vtable.i8_approxdecomp_from_tndbl(module, gadget, res, res_size, a, a_size);
 84}
 85
 86/** @brief sets res = gadget_decompose(a) (int16_t* output) */
 87EXPORT void i16_approxdecomp_from_tndbl(const MOD_Z* module,                      // N
 88                                        const TNDBL_APPROXDECOMP_GADGET* gadget,  // gadget
 89                                        int16_t* res, uint64_t res_size,          // res (in general, size ell.a_size)
 90                                        const double* a, uint64_t a_size) {       // a
 91  module->vtable.i16_approxdecomp_from_tndbl(module, gadget, res, res_size, a, a_size);
 92}
 93/** @brief sets res = gadget_decompose(a) (int32_t* output) */
 94EXPORT void i32_approxdecomp_from_tndbl(const MOD_Z* module,                      // N
 95                                        const TNDBL_APPROXDECOMP_GADGET* gadget,  // gadget
 96                                        int32_t* res, uint64_t res_size,          // res (in general, size ell.a_size)
 97                                        const double* a, uint64_t a_size) {       // a
 98  module->vtable.i32_approxdecomp_from_tndbl(module, gadget, res, res_size, a, a_size);
 99}
100
101/** @brief prepares a vmp matrix (contiguous row-major version) */
102EXPORT void zn32_vmp_prepare_contiguous(const MOD_Z* module,
103                                        ZN32_VMP_PMAT* pmat,                                   // output
104                                        const int32_t* mat, uint64_t nrows, uint64_t ncols) {  // a
105  module->vtable.zn32_vmp_prepare_contiguous(module, pmat, mat, nrows, ncols);
106}
107
108/** @brief prepares a vmp matrix (mat[row]+col*N points to the item) */
109EXPORT void zn32_vmp_prepare_dblptr(const MOD_Z* module,
110                                    ZN32_VMP_PMAT* pmat,                                    // output
111                                    const int32_t** mat, uint64_t nrows, uint64_t ncols) {  // a
112  module->vtable.zn32_vmp_prepare_dblptr(module, pmat, mat, nrows, ncols);
113}
114
115/** @brief prepares the ith-row of a vmp matrix with nrows and ncols */
116EXPORT void zn32_vmp_prepare_row(const MOD_Z* module,
117                                 ZN32_VMP_PMAT* pmat,                                                   // output
118                                 const int32_t* row, uint64_t row_i, uint64_t nrows, uint64_t ncols) {  // a
119  module->vtable.zn32_vmp_prepare_row(module, pmat, row, row_i, nrows, ncols);
120}
121
122/** @brief applies a vmp product (int32_t* input) */
123EXPORT void zn32_vmp_apply_i32(const MOD_Z* module, int32_t* res, uint64_t res_size, const int32_t* a, uint64_t a_size,
124                               const ZN32_VMP_PMAT* pmat, uint64_t nrows, uint64_t ncols) {
125  module->vtable.zn32_vmp_apply_i32(module, res, res_size, a, a_size, pmat, nrows, ncols);
126}
127/** @brief applies a vmp product (int16_t* input) */
128EXPORT void zn32_vmp_apply_i16(const MOD_Z* module, int32_t* res, uint64_t res_size, const int16_t* a, uint64_t a_size,
129                               const ZN32_VMP_PMAT* pmat, uint64_t nrows, uint64_t ncols) {
130  module->vtable.zn32_vmp_apply_i16(module, res, res_size, a, a_size, pmat, nrows, ncols);
131}
132
133/** @brief applies a vmp product (int8_t* input) */
134EXPORT void zn32_vmp_apply_i8(const MOD_Z* module, int32_t* res, uint64_t res_size, const int8_t* a, uint64_t a_size,
135                              const ZN32_VMP_PMAT* pmat, uint64_t nrows, uint64_t ncols) {
136  module->vtable.zn32_vmp_apply_i8(module, res, res_size, a, a_size, pmat, nrows, ncols);
137}
138
139/** reduction mod 1, output in torus32 space */
140EXPORT void dbl_to_tn32(const MOD_Z* module,              //
141                        int32_t* res, uint64_t res_size,  // res
142                        const double* a, uint64_t a_size  // a
143) {
144  module->vtable.dbl_to_tn32(module, res, res_size, a, a_size);
145}
146
147/** real centerlift mod 1, output in double space */
148EXPORT void tn32_to_dbl(const MOD_Z* module,               //
149                        double* res, uint64_t res_size,    // res
150                        const int32_t* a, uint64_t a_size  // a
151) {
152  module->vtable.tn32_to_dbl(module, res, res_size, a, a_size);
153}
154
155/** round to the nearest int, output in i32 space */
156EXPORT void dbl_round_to_i32(const MOD_Z* module,              //
157                             int32_t* res, uint64_t res_size,  // res
158                             const double* a, uint64_t a_size  // a
159) {
160  module->vtable.dbl_round_to_i32(module, res, res_size, a, a_size);
161}
162
163/** small int (int32 space) to double */
164EXPORT void i32_to_dbl(const MOD_Z* module,               //
165                       double* res, uint64_t res_size,    // res
166                       const int32_t* a, uint64_t a_size  // a
167) {
168  module->vtable.i32_to_dbl(module, res, res_size, a, a_size);
169}
170
171/** round to the nearest int, output in int64 space */
172EXPORT void dbl_round_to_i64(const MOD_Z* module,              //
173                             int64_t* res, uint64_t res_size,  // res
174                             const double* a, uint64_t a_size  // a
175) {
176  module->vtable.dbl_round_to_i64(module, res, res_size, a, a_size);
177}
178
179/** small int (int64 space, <= 2^50) to double */
180EXPORT void i64_to_dbl(const MOD_Z* module,               //
181                       double* res, uint64_t res_size,    // res
182                       const int64_t* a, uint64_t a_size  // a
183) {
184  module->vtable.i64_to_dbl(module, res, res_size, a, a_size);
185}