M4RIE  0.0.20120415
 All Data Structures Files Functions Variables Macros Groups Pages
mzd_poly.h
1 #ifndef M4RIE_MZD_POLY_H
2 #define M4RIE_MZD_POLY_H
3 
4 /******************************************************************************
5 *
6 * M4RIE: Linear Algebra over GF(2^e)
7 *
8 * Copyright (C) 2011 Martin Albrecht <martinralbrecht@googlemail.com>
9 *
10 * Distributed under the terms of the GNU General Public License (GEL)
11 * version 2 or higher.
12 *
13 * This code is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * General Public License for more details.
17 *
18 * The full text of the GPL is available at:
19 *
20 * http://www.gnu.org/licenses/
21 ******************************************************************************/
22 
23 #include <m4ri/m4ri.h>
24 #include <stdarg.h>
25 
26 /********************************************************************
27  * Internal representation
28  *******************************************************************/
29 
30 static inline void _poly_add(mzd_t **c, const mzd_t **a, const mzd_t **b,const unsigned int length) {
31  switch(length) {
32  case 16: mzd_add(c[15], a[15], b[15]);
33  case 15: mzd_add(c[14], a[14], b[14]);
34  case 14: mzd_add(c[13], a[13], b[13]);
35  case 13: mzd_add(c[12], a[12], b[12]);
36  case 12: mzd_add(c[11], a[11], b[11]);
37  case 11: mzd_add(c[10], a[10], b[10]);
38  case 10: mzd_add(c[ 9], a[ 9], b[ 9]);
39  case 9: mzd_add(c[ 8], a[ 8], b[ 8]);
40  case 8: mzd_add(c[ 7], a[ 7], b[ 7]);
41  case 7: mzd_add(c[ 6], a[ 6], b[ 6]);
42  case 6: mzd_add(c[ 5], a[ 5], b[ 5]);
43  case 5: mzd_add(c[ 4], a[ 4], b[ 4]);
44  case 4: mzd_add(c[ 3], a[ 3], b[ 3]);
45  case 3: mzd_add(c[ 2], a[ 2], b[ 2]);
46  case 2: mzd_add(c[ 1], a[ 1], b[ 1]);
47  case 1: mzd_add(c[ 0], a[ 0], b[ 0]);
48  case 0:
49  break;
50  default:
51  for(unsigned int i=0; i<length; i++)
52  mzd_add(c[ i], a[ i], b[ i]);
53  }
54 }
55 
56 void _poly_addmul2(mzd_t **X, const mzd_t **a, const mzd_t **b);
57 void _poly_addmul4(mzd_t **X, const mzd_t **a, const mzd_t **b);
58 
59 /*********************************************************************
60  * mzd_poly_t will be the data type for matrices over GF(2)[x] in the
61  * future
62  *
63  * DO NOT USE YET.
64  *
65  *********************************************************************/
66 
67 typedef int deg_t;
68 
69 typedef struct {
70  mzd_t **x;
71  rci_t nrows;
72  rci_t ncols;
73  deg_t depth;
74 } mzd_poly_t;
75 
76 static inline mzd_poly_t *_mzd_poly_add(mzd_poly_t *C, const mzd_poly_t *A, const mzd_poly_t *B, unsigned int offset) {
77  _poly_add(C->x+offset, (const mzd_t**)A->x, (const mzd_t**)B->x, A->depth);
78  return C;
79 }
80 
81 static inline mzd_poly_t *mzd_poly_add(mzd_poly_t *C, const mzd_poly_t *A, const mzd_poly_t *B) {
82  assert(C->depth >= A->depth && A->depth == B->depth);
83  return _mzd_poly_add(C, A, B, 0);
84 }
85 
86 static inline mzd_poly_t *mzd_poly_init(const deg_t d, const rci_t m, const rci_t n) {
87  mzd_poly_t *A = (mzd_poly_t*)m4ri_mm_malloc(sizeof(mzd_poly_t));
88  A->x = (mzd_t**)m4ri_mm_malloc(sizeof(mzd_t*)*d);
89 
90  A->nrows = m;
91  A->ncols = n;
92  A->depth = d+1;
93 
94  for(int i=0; i<A->depth; i++)
95  A->x[i] = mzd_init(m,n);
96  return A;
97 }
98 
99 static inline void mzd_poly_free(mzd_poly_t *A) {
100  for(int i=0; i<A->depth; i++)
101  mzd_free(A->x[i]);
102 #if __M4RI_USE_MM_MALLOC
103  _mm_free(A);
104 #else
105  free(A);
106 #endif
107 }
108 
109 
110 static inline mzd_poly_t *_mzd_poly_adapt_depth(mzd_poly_t *A, const deg_t new_depth) {
111  if (new_depth < A->depth) {
112  for(int i=new_depth; i<A->depth; i++) {
113  mzd_free(A->x[i]);
114  A->x[i] = NULL;
115  }
116  } else {
117  for(int i=A->depth; i<new_depth; i++) {
118  A->x[i] = mzd_init(A->nrows,A->ncols);
119  }
120  }
121  A->depth = new_depth;
122  return A;
123 }
124 
125 #endif //M4RIE_MZD_POLY_H