myl7/fss 1.1.0
Function secret sharing (FSS) primitives including distributed point/comparison function (DPF/DCF)
Loading...
Searching...
No Matches
grotto_dcf.cuh
Go to the documentation of this file.
1// SPDX-License-Identifier: Apache-2.0
23#pragma once
24#include <cuda_runtime.h>
25#include <type_traits>
26#include <cstddef>
27#include <cassert>
28#include <omp.h>
29#include <fss/dpf.cuh>
30#include <fss/group/bytes.cuh>
31#include <fss/prg.cuh>
32#include <fss/util.cuh>
33
34namespace fss {
35
45template <int in_bits, typename Prg, typename In = uint, int par_depth = -1>
46 requires((std::is_unsigned_v<In> || std::is_same_v<In, __uint128_t>) && in_bits <= sizeof(In) * 8 && Prgable<Prg, 2>)
47class GrottoDcf {
49
50public:
51 using Cw = typename DpfType::Cw;
52 Prg prg;
53
63 __host__ __device__ void Gen(Cw cws[], const int4 s0s[2], In a) {
64 DpfType dpf{prg};
65 int4 beta = {0, 0, 0, 0};
66 dpf.Gen(cws, s0s, a, beta);
67 }
68
78 struct ParityTree {
79 bool *p;
80 bool b;
81 };
82
94 void Preprocess(ParityTree &pt, int4 s0, const Cw cws[]) {
95 constexpr size_t N = 1ULL << in_bits;
96
97 // Phase 1: expand tree, write leaf control bits to pt.p[N-1 .. 2N-2]
98 ExpandTree(pt.b, s0, cws, pt.p + (N - 1));
99
100 // Phase 2a: build parity segment tree bottom-up
101 for (size_t j = N - 2; j < N - 1; --j) {
102 pt.p[j] = pt.p[2 * j + 1] ^ pt.p[2 * j + 2];
103 }
104 }
105
116 __host__ __device__ static bool Eval(const ParityTree &pt, In x) {
117 constexpr size_t N = 1ULL << in_bits;
118 In e = static_cast<In>(x) + 1;
119
120 // e == 0 means x + 1 overflowed, i.e., e = N (entire domain)
121 if (e == 0 || e == N) return pt.p[0];
122
123 bool pi = false;
124 size_t cur = 0;
125 for (int i = 0; i < in_bits; ++i) {
126 bool e_bit = (e >> (in_bits - 1 - i)) & 1;
127 if (e_bit) {
128 pi ^= pt.p[2 * cur + 1];
129 cur = 2 * cur + 2;
130 } else {
131 cur = 2 * cur + 1;
132 }
133 }
134 return pi;
135 }
136
151 void EvalAll(bool b, int4 s0, const Cw cws[], bool ys[]) {
152 constexpr size_t N = 1ULL << in_bits;
153
154 // Phase 1: expand tree to get leaf control bits into ys[]
155 ExpandTree(b, s0, cws, ys);
156
157 // Phase 2b: prefix-sum scan (running XOR)
158 // ys[x] currently holds leaf x's control bit.
159 // Transform to: ys[x] = XOR of control bits [0..x] = share of 1[alpha <= x].
160 for (size_t x = 1; x < N; ++x) {
161 ys[x] = ys[x] ^ ys[x - 1];
162 }
163 }
164
165private:
174 void ExpandTree(bool b, int4 s0, const Cw cws[], bool t[]) {
175 int4 st = s0;
176 st = util::SetLsb(st, b);
177
178 assert(in_bits < sizeof(size_t) * 8);
179 size_t l = 0;
180 size_t r = 1ULL << in_bits;
181 int i = 0;
182
183 int par_depth_ = util::ResolveParDepth(par_depth);
184
185#pragma omp parallel
186#pragma omp single
187 ExpandTreeRec(st, cws, t, l, r, i, par_depth_);
188 }
189
190 void ExpandTreeRec(int4 st, const Cw cws[], bool t[], size_t l, size_t r, int i, int par_depth_) {
191 bool tc = util::GetLsb(st);
192 int4 s = st;
193 s = util::SetLsb(s, false);
194
195 if (i == in_bits) {
196 assert(l + 1 == r);
197 t[l] = tc;
198 return;
199 }
200
201 Cw cw = cws[i];
202 int4 s_cw = cw.s;
203 bool tl_cw = util::GetLsb(s_cw);
204 s_cw = util::SetLsb(s_cw, false);
205 bool tr_cw = cw.tr;
206
207 auto [sl, sr] = prg.Gen(s);
208
209 bool tl = util::GetLsb(sl);
210 sl = util::SetLsb(sl, false);
211 bool tr = util::GetLsb(sr);
212 sr = util::SetLsb(sr, false);
213
214 if (tc) {
215 sl = util::Xor(sl, s_cw);
216 sr = util::Xor(sr, s_cw);
217 tl = tl ^ tl_cw;
218 tr = tr ^ tr_cw;
219 }
220
221 int4 stl = sl;
222 stl = util::SetLsb(stl, tl);
223 int4 str = sr;
224 str = util::SetLsb(str, tr);
225
226 size_t mid = (l + r) / 2;
227
228 if (i < par_depth_) {
229#pragma omp task
230 ExpandTreeRec(stl, cws, t, l, mid, i + 1, par_depth_);
231#pragma omp task
232 ExpandTreeRec(str, cws, t, mid, r, i + 1, par_depth_);
233#pragma omp taskwait
234 } else {
235 ExpandTreeRec(stl, cws, t, l, mid, i + 1, par_depth_);
236 ExpandTreeRec(str, cws, t, mid, r, i + 1, par_depth_);
237 }
238 }
239};
240
241} // namespace fss
2-party DPF scheme.
Definition dpf.cuh:64
void Gen(Cw cws[], const int4 s0s[2], In a, int4 b_buf)
Key generation method.
Definition dpf.cuh:93
2-party DCF scheme over F2 from standard DPF (Grotto construction).
Definition grotto_dcf.cuh:47
void Gen(Cw cws[], const int4 s0s[2], In a)
Key generation method.
Definition grotto_dcf.cuh:63
static bool Eval(const ParityTree &pt, In x)
Prefix-parity query on the parity segment tree.
Definition grotto_dcf.cuh:116
void Preprocess(ParityTree &pt, int4 s0, const Cw cws[])
Preprocess: expand DPF tree and build parity segment tree.
Definition grotto_dcf.cuh:94
void EvalAll(bool b, int4 s0, const Cw cws[], bool ys[])
Full domain evaluation.
Definition grotto_dcf.cuh:151
Pseudorandom generator (PRG) interface.
Definition prg.cuh:21
2-party distributed point function (DPF).
Correction word.
Definition dpf.cuh:76
Parity segment tree over leaf control bits.
Definition grotto_dcf.cuh:78