<PackageReference Include="BouncyCastle.Cryptography" Version="2.3.1" />

SamplerZ

class SamplerZ
namespace Org.BouncyCastle.Pqc.Crypto.Falcon { internal class SamplerZ { private FalconRNG p; private FalconFPR sigma_min; private FprEngine fpre; internal SamplerZ(FalconRNG p, FalconFPR sigma_min, FprEngine fpre) { this.p = p; this.sigma_min = sigma_min; this.fpre = fpre; } internal int Sample(FalconFPR mu, FalconFPR isigma) { return sampler(mu, isigma); } private int gaussian0_sampler(FalconRNG p) { uint[] array = new uint[54] { 10745844, 3068844, 3741698, 5559083, 1580863, 8248194, 2260429, 13669192, 2736639, 708981, 4421575, 10046180, 169348, 7122675, 4136815, 30538, 13063405, 7650655, 4132, 14505003, 7826148, 417, 16768101, 11363290, 31, 8444042, 8086568, 1, 12844466, 265321, 0, 1232676, 13644283, 0, 38047, 9111839, 0, 870, 6138264, 0, 14, 12545723, 0, 0, 3104126, 0, 0, 28824, 0, 0, 198, 0, 0, 1 }; ulong num = p.prng_get_u64(); uint num2 = p.prng_get_u8(); uint num3 = (uint)((int)num & 16777215); uint num4 = (uint)((int)(num >> 24) & 16777215); uint num5 = (uint)((int)(num >> 48) | (int)(num2 << 16)); int num6 = 0; for (int i = 0; i < array.Length; i += 3) { uint num7 = array[i + 2]; uint num8 = array[i + 1]; uint num9 = array[i]; uint num10 = num3 - num7 >> 31; num10 = num4 - num8 - num10 >> 31; num10 = num5 - num9 - num10 >> 31; num6 += (int)num10; } return num6; } private int BerExp(FalconRNG p, FalconFPR x, FalconFPR ccs) { int num = (int)fpre.fpr_trunc(fpre.fpr_mul(x, fpre.fpr_inv_log2)); FalconFPR x2 = fpre.fpr_sub(x, fpre.fpr_mul(fpre.fpr_of(num), fpre.fpr_log2)); uint num2 = (uint)num; num2 = (uint)((int)num2 ^ (int)((num2 ^ 63) & (0 - (63 - num2 >> 31)))); num = (int)num2; ulong num3 = (fpre.fpr_expm_p63(x2, ccs) << 1) - 1 >> num; int num4 = 64; uint num5; do { num4 -= 8; num5 = (uint)((int)p.prng_get_u8() - ((int)(num3 >> num4) & 255)); } while (num5 == 0 && num4 > 0); return (int)(num5 >> 31); } private int sampler(FalconFPR mu, FalconFPR isigma) { int num = (int)fpre.fpr_floor(mu); FalconFPR y = fpre.fpr_sub(mu, fpre.fpr_of(num)); FalconFPR y2 = fpre.fpr_half(fpre.fpr_sqr(isigma)); FalconFPR ccs = fpre.fpr_mul(isigma, sigma_min); int num4; FalconFPR x; do { int num2 = gaussian0_sampler(p); uint num3 = p.prng_get_u8() & 1; num4 = (int)num3 + (int)((num3 << 1) - 1) * num2; x = fpre.fpr_mul(fpre.fpr_sqr(fpre.fpr_sub(fpre.fpr_of(num4), y)), y2); x = fpre.fpr_sub(x, fpre.fpr_mul(fpre.fpr_of(num2 * num2), fpre.fpr_inv_2sqrsigma0)); } while (BerExp(p, x, ccs) == 0); return num + num4; } } }