HElib: src/SingleCRT.h Source File

HElib 1.0 Implementing Homomorphic Encryption

- Main Page
- Classes
- Files

- File List
- File Members

All Classes Files Functions Variables Friends Pages
SingleCRT.h
Go to the documentation of this file.
1 /* Copyright (C) 2012,2013 IBM Corp.
2 * This program is free software; you can redistribute it and/or modify
3 * it under the terms of the GNU General Public License as published by
4 * the Free Software Foundation; either version 2 of the License, or
5 * (at your option) any later version.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
10 * See the GNU General Public License for more details.
11 *
12 * You should have received a copy of the GNU General Public License along
13 * with this program; if not, write to the Free Software Foundation, Inc.,
14 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
15 */
20 #ifndef _SingleCRT_H_
21 #define _SingleCRT_H_
22
37 #include <vector>
38 #include <iostream>
39 #include <NTL/ZZX.h>
40
41 #include "FHEContext.h"
42 #include "IndexMap.h"
43 #include "DoubleCRT.h"
44
45 class SingleCRT {
46 const FHEcontext& context;
47 IndexMap<ZZX> map; // the SingleCRT data
48
49 friend class DoubleCRT;
50
51 // a "sanity check" function, verifies consistency of polys with current
52 // moduli chain an error is raised if they are not consistent
53 void verify();
54
55 // Generic operators, Fnc is either AddMod, SubMod, or MulMod. (This should
56 // have been a template, but gcc refuses to cooperate.)
57
58 // The behavior when the *this and other have different index sets depends
59 // on the matchIndexSets flag. When it is set to true then the union of the
60 // two index sets is used; if false, then the index set of *this is used.
61 SingleCRT& Op(const SingleCRT &other,
62 void (*Fnc)(ZZ&, const ZZ&, const ZZ&, const ZZ&),
63 bool matchIndexSets=true);
64
65 SingleCRT& Op(const ZZX &poly,
66 void (*Fnc)(ZZ&, const ZZ&, const ZZ&, const ZZ&));
67 SingleCRT& Op(const ZZ &num, void (*Fnc)(ZZX&, const ZZX&, const ZZ&));
68
69
70 public:
71
72
73 // Constructors and assignment operators
74
75 // representing an integer polynomial as SingleCRT. If the index set
76 // is not specified, then all the primes from the context are used.
77 // If the coefficients of poly are larger than the product of
78 // the used moduli, they are effectively reduced modulo that product
79
80 SingleCRT(const ZZX& poly, const FHEcontext& _context, const IndexSet& s);
81 SingleCRT(const ZZX& poly, const FHEcontext& _context);
82 SingleCRT(const ZZX& poly); // uses active context
83
84
85 // Without specifying a ZZX, we get the zero polynomial
86
87 SingleCRT(const FHEcontext& _context, const IndexSet& s);
88 SingleCRT(const FHEcontext& _context);
89
90 SingleCRT(); // uses the "active context", run-time error if it is NULL
91
92 // Assignment operators
93
94 SingleCRT& operator=(const SingleCRT& other);
95 SingleCRT& operator=(const DoubleCRT& dcrt);
96 SingleCRT& operator=(const ZZX& poly);
97 SingleCRT& operator=(const ZZ& num) { *this = to_ZZX(num); return *this; }
98 SingleCRT& operator=(const long num) { *this = to_ZZX(num); return *this; }
99
100 bool operator==(const SingleCRT& other) const {
101 return &context == &other.context && map == other.map;
102 }
103
104 bool operator!=(const SingleCRT& other) const {
105 return !(*this==other);
106 }
107
108 // Set to zero, one
109
110 SingleCRT& setZero() { *this = ZZX::zero(); return *this; }
111 SingleCRT& setOne() { *this = 1; return *this; }
112
113
114 // expand the index set by s1.
115 // it is assumed that s1 is disjoint from the current index set.
116 void addPrimes(const IndexSet& s1);
117
118
119 // remove s1 from the index set
120 void removePrimes(const IndexSet& s1) {
121 map.remove(s1);
122 }
123
124 // Arithmetic operations. Only the "destructive" versions are used,
125 // i.e., a += b is implemented but not a + b.
126
127 // Addition, negation, subtraction
128 SingleCRT& operator+=(const SingleCRT &other){ return Op(other,NTL::AddMod);}
129 SingleCRT& operator+=(const ZZX &poly) { return Op(poly, NTL::AddMod);}
130 SingleCRT& operator+=(const ZZ &num) { return Op(num, NTL::add); }
131 SingleCRT& operator+=(long num) { return Op(to_ZZ(num), NTL::add); }
132
133 SingleCRT& operator-=(const SingleCRT &other){ return Op(other,NTL::SubMod);}
134 SingleCRT& operator-=(const ZZX &poly) { return Op(poly, NTL::SubMod); }
135 SingleCRT& operator-=(const ZZ &num) { return Op(num, NTL::sub); }
136 SingleCRT& operator-=(long num) { return Op(to_ZZ(num), NTL::sub); }
137
138 // Procedural equivalents, supporting also the matchIndexSets flag
139 void Add(const SingleCRT &other, bool matchIndexSet=true)
140 { Op(other, NTL::AddMod, matchIndexSet); }
141 void Sub(const SingleCRT &other, bool matchIndexSet=true)
142 { Op(other, NTL::SubMod, matchIndexSet); }
143
144 // These are the prefix versions, ++dcrt and --dcrt.
145 SingleCRT& operator++() { return (*this += 1); };
146 SingleCRT& operator--() { return (*this -= 1); };
147
148 // Postfix version...no return value...just for style
149 void operator++(int) { *this += 1; };
150 void operator--(int) { *this -= 1; };
151
152 // Multiplication by constant
153 SingleCRT& operator*=(const ZZ &num) { return Op(num,NTL::mul); }
154 SingleCRT& operator*=(long num) { return Op(to_ZZ(num),NTL::mul); }
155
156 // Division by constant
157 SingleCRT& operator/=(const ZZ &num);
158 SingleCRT& operator/=(long num) { return (*this /= to_ZZ(num)); }
159
160 // Recovering the polynomial in coefficient representation. This yields an
161 // integer polynomial with coefficients in [-P/2,P/2] (P is the product of
162 // all moduli used). The polynomial is reduced modulo the product of only
163 // the primes in the IndexSet parameter.
164
165 void toPoly(ZZX& p, const IndexSet& s) const;
166 void toPoly(ZZX& p) const;
167
168 #if 0
169 // I/O: ONLY the ZZX vector is outputted/recovered, not the moduli chain!! An
170 // error is raised on input if this is not consistent with the current chain
171
172 friend ostream& operator<<(ostream &s, const SingleCRT &scrt)
173 { s << scrt.polys; return s; }
174
175 friend istream& operator>> (istream &s, SingleCRT &scrt)
176 { s >> scrt.polys; scrt.verify(); return s; }
177 #endif
178
179 // Access methods
180 const IndexMap<ZZX>& getMap() const { return map; }
181 const FHEcontext& getContext() const { return context; }
182 };
183 inline void conv(SingleCRT &s, const ZZX &p) { s=p; }
184 // Cannot implement to_SingleCRT(p), since modChain is not defined
185
186 inline void conv(ZZX &p, const SingleCRT &s) { s.toPoly(p); }
187 inline ZZX to_ZZX(const SingleCRT &s) { ZZX p; s.toPoly(p); return p; }
188
189 inline void conv(SingleCRT &s, const DoubleCRT &d) { s=d; }
190 #endif // #ifndef _SingleCRT_H_