// This method is cloned from Operator, just resetting sign and exception bits // (because we don't have any exception support in this toy example) TestCase* FPSumOf3Squares::buildRandomTestCase(int i){ TestCase *tc; /* Generate test cases using random input numbers */ tc = new TestCase(this); // TODO free all this memory when exiting TestBench /* Fill inputs */ for (unsigned int j = 0; j < ioList_.size(); j++) { Signal* s = ioList_[j]; if (s->type() == Signal::in) { // ****** Modification: positive normal numbers with small exponents mpz_class m = getLargeRandom(wF); mpz_class bias = (mpz_class(1)<<(wE-1)) - 1; mpz_class e = getLargeRandom(wE-2) - (mpz_class(1)<<(wE-3)) + bias; // ensure no overflow mpz_class a = (mpz_class(1)<<(wE+wF+1)) // 01 to denote a normal number + (e<<wF) + m; tc->addInput(s->getName(), a); } } /* Get correct outputs */ emulate(tc); // cout << tc->getInputVHDL(); // cout << tc->getExpectedOutputVHDL(); return tc; }
int main() { mpz_class m = mpz_class(20); mpz_class n = mpz_class(20); mpz_class result = latticePaths(m, n); std::cout << result << std::endl; return 0; }
RCP<const Integer> iabs(const Integer &n) { mpz_class m; mpz_t m_t; mpz_init(m_t); mpz_abs(m_t, n.as_mpz().get_mpz_t()); m = mpz_class(m_t); mpz_clear(m_t); return integer(mpz_class(m)); }
ShiftAddOp::ShiftAddOp(ShiftAddDag* impl, ShiftAddOpType op, ShiftAddOp* i, int s, ShiftAddOp* j) : impl(impl), op(op), i(i), j(j), s(s) { n=impl->computeConstant(op, i, s, j); // now compute the size according to this constant, as the log2 of the max value the result can take if (n >= 0) size = intlog2(n * ((mpz_class(1)<<impl->icm->xsize)-1)); else size = 1 + intlog2(-n* ((mpz_class(1)<<impl->icm->xsize)-1)); // we need a sign bit if(n==1) size=impl->icm->xsize; // compute the cost in terms of full adders of this node switch(op) { case X: cost_in_full_adders = 0; break; case Add: if (s >= j->size) // no overlap of bits of Vi<<s and Vj cost_in_full_adders = 0; else cost_in_full_adders = size - s - 1; // -1 because the cout bit is for free break; case Sub: cost_in_full_adders = size - 1; // -1 because the cout bit is for free break; case RSub: if (s >= j->size) // no overlap of bits of Vi<<s and Vj cost_in_full_adders = i->size - 1; // still need to negate i else cost_in_full_adders = size - s - 1; // -1 because the cout bit is for free break; case Shift: cost_in_full_adders = 0; break; case Neg: cost_in_full_adders = size -1; // -1 because the cout bit is for free break; } // build the variable name ostringstream o; if(n==1) o <<"X"; else if(n>=0) o<<"P"<<mpz2string(n)<<"X"; else o<<"M"<<mpz2string(-n)<<"X"; name = o.str(); // and add this object to the dictionary of the implementation if (op!=X) impl->saolist.push_back(this); }
mpz_class to_mpz_class(char c){ switch(c){ case '1': return mpz_class("1"); case '2': return mpz_class("2"); case '3': return mpz_class("3"); case '4': return mpz_class("4"); case '5': return mpz_class("5"); case '6': return mpz_class("6"); case '7': return mpz_class("7"); case '8': return mpz_class("8"); case '9': return mpz_class("9"); } return mpz_class("0"); }
void mul(mpz_class& z, const mpz_class& x, const mpz_class& y) const { #if 1 const size_t ySize = mcl::gmp::getUnitSize(y); mpz_class c = y == 0 ? mpz_class(0) : x * mcl::gmp::getUnit(y, 0); Unit q = c == 0 ? 0 : mcl::gmp::getUnit(c, 0) * r_; c += p_ * q; c >>= sizeof(Unit) * 8; for (size_t i = 1; i < n_; i++) { if (i < ySize) { c += x * mcl::gmp::getUnit(y, i); } Unit q = c == 0 ? 0 : mcl::gmp::getUnit(c, 0) * r_; c += p_ * q; c >>= sizeof(Unit) * 8; } if (c >= p_) { c -= p_; } z = c; #else z = x * y; const size_t zSize = mcl::gmp::getUnitSize(z); for (size_t i = 0; i < n_; i++) { if (i < zSize) { Unit q = mcl::gmp::getUnit(z, 0) * r_; z += p_ * (mp_limb_t)q; } z >>= sizeof(Unit) * 8; } if (z >= p_) { z -= p_; } #endif }
static bool is_mersenne_prime(mpz_class p) { if( 2 == p ) return true; else { mpz_class s(4); mpz_class div( (mpz_class(1) << p.get_ui()) - 1 ); for( mpz_class i(3); i <= p; ++i ) { s = (s * s - mpz_class(2)) % div ; } return ( s == mpz_class(0) ); } }
void lucas2(const Ptr<RCP<const Integer>> &g, const Ptr<RCP<const Integer>> &s, unsigned long n) { mpz_t g_t; mpz_t s_t; mpz_init(g_t); mpz_init(s_t); mpz_lucnum2_ui(g_t, s_t, n); *g = integer(mpz_class(g_t)); *s = integer(mpz_class(s_t)); mpz_clear(g_t); mpz_clear(s_t); }
void fibonacci2(const Ptr<RCP<const Integer>> &g, const Ptr<RCP<const Integer>> &s, unsigned long n) { mpz_t g_t; mpz_t s_t; mpz_init(g_t); mpz_init(s_t); mpz_fib2_ui(g_t, s_t, n); *g = integer(mpz_class(g_t)); *s = integer(mpz_class(s_t)); mpz_clear(g_t); mpz_clear(s_t); }
std::vector<mpz_class> renf_elem_class::num_vector() const noexcept { mpz_class x; std::vector<mpz_class> res; if (nf == nullptr) { fmpz_get_mpz(x.__get_mp(), fmpq_numref(b)); res.push_back(x); } else { fmpq_poly_t f; fmpq_poly_init(f); nf_elem_get_fmpq_poly(f, a->elem, nf->renf_t()->nf); for (size_t i = 0; i < fmpq_poly_length(f); i++) { fmpz_get_mpz(x.__get_mp(), fmpq_poly_numref(f) + i); res.push_back(x); } size_t deg = fmpq_poly_degree(nf->renf_t()->nf->pol); for (size_t i = fmpq_poly_length(f); i < deg; i++) res.push_back(mpz_class(0)); fmpq_poly_clear(f); } return res; }
nBinEqvCod::nBinEqvCod(int n, int w, int q) : n(n), w(w), q(q) { omp_set_dynamic(1); omp_set_num_threads(8); mpz_ui_pow_ui(qw.get_mpz_t(), (q - 1), w); //qw = qPow((q - 1), w); //qw = Bigint(q-1).pow(w); M = mpz_class(qw) * comb(n, w); // factorial(n) / (factorial(w) * factorial(n - w)); //code = new nBinEqvVec[M]; code = nullptr; qDebug() << "Creating non_binary equivalent codes"; qDebug() << "n:" << n << "\tw: " << w << "\tq:" << q << "\tM: " << M.get_str().c_str(); //#pragma omp parallel for //for (int i = 0; i < M; ++i) //{ // calc_eVec(i, &code[i]); // mapNBEV.insert(code[i].Ca, &code[i]); //} //-------------------------------------------------- //QTime midnight(0, 0, 0); //qsrand(midnight.secsTo(QTime::currentTime())); //code = new nBinEqvVec[3]; //calc_eVec(qrand() % M, code[0]); //calc_eVec(qrand() % M, code[1]); //calc_eVec(qrand() % M, code[2]); }
real_l_t floor(real_l_t const & x) { #if USE_GMPLIB return real_l_t(mpz_class(x._data)); #else return real_l_t(floor(x._data)); #endif }
void mod(const Ptr<RCP<const Number>> &r, const Integer &n, const Integer &d) { mpz_t inv_t; mpz_init(inv_t); mpz_mod(inv_t, n.as_mpz().get_mpz_t(), d.as_mpz().get_mpz_t()); *r = integer(mpz_class(inv_t)); }
void fdiv_q(const Ptr<RCP<const Integer>> &q, const Integer &n, const Integer &d) { mpz_t q_; mpz_init(q_); mpz_fdiv_q (q_, n.as_mpz().get_mpz_t(), d.as_mpz().get_mpz_t()); *q = integer(mpz_class(q_)); mpz_clear(q_); }
mpz_class FirstLogTable::function(int x) { mpz_class result; double apprinv; mpfr_t i,l; mpz_t r; mpfr_init(i); mpfr_init2(l,wOut); mpz_init2(r,400); apprinv = fit->output2double(fit->function(x));; // result = double2output(log(apprinv)); mpfr_set_d(i, apprinv, GMP_RNDN); mpfr_log(l, i, GMP_RNDN); mpfr_neg(l, l, GMP_RNDN); // Remove the sum of small offsets that are added to the other log tables for(int j=1; j<=op->stages; j++){ mpfr_set_d(i, 1.0, GMP_RNDN); int pi=op->p[j]; mpfr_mul_2si(i, i, -2*pi, GMP_RNDN); mpfr_sub(l, l, i, GMP_RNDN); } // code the log in 2's compliment mpfr_mul_2si(l, l, wOut, GMP_RNDN); mpfr_get_z(r, l, GMP_RNDN); result = mpz_class(r); // signed // This is a very inefficient way of converting mpz_class t = mpz_class(1) << wOut; result = t+result; if(result>t) result-=t; // cout << "x="<<x<<" apprinv="<<apprinv<<" logapprinv="<<log(apprinv)<<" result="<<result<<endl; mpfr_clear(i); mpfr_clear(l); mpz_clear(r); return result; }
int main() { mpz_class num = factorial(mpz_class(100)); mpz_class sum = 0; const mpz_class base = 10; while (num > 0) { sum += num % base; num /= base; } std::cout << sum.get_str() << std::endl; return 0; }
void gcd_ext(const Ptr<RCP<const Integer>> &g, const Ptr<RCP<const Integer>> &s, const Ptr<RCP<const Integer>> &t, const Integer &a, const Integer &b) { mpz_t g_t; mpz_t s_t; mpz_t t_t; mpz_init(g_t); mpz_init(s_t); mpz_init(t_t); mpz_gcdext(g_t, s_t, t_t, a.as_mpz().get_mpz_t(), b.as_mpz().get_mpz_t()); *g = integer(mpz_class(g_t)); *s = integer(mpz_class(s_t)); *t = integer(mpz_class(t_t)); mpz_clear(g_t); mpz_clear(s_t); mpz_clear(t_t); }
std::vector< share_t > share(const mpz_class& secret, unsigned int t, unsigned int n, const mpz_class& p, gmp_randclass& randomGenerator, unsigned int security) { std::vector<mpz_class> coefficients = getRandomPolynomial(t - 1, p, randomGenerator, security); coefficients[0] = secret; std::vector< share_t > shares; shares.resize(n); for (size_t i = 0; i < shares.size(); ++i) { shares[i].first = mpz_class(i + 1); shares[i].second = evaluatePolynomial(i + 1, coefficients, p); } return shares; }
void MathUtils::GetRandomPrime(mpz_class& rand_prime, unsigned int num_bits) { gmp_randclass r1 (gmp_randinit_default); r1.seed(GetTimeStamp()); mpz_class rand = r1.get_z_bits(num_bits); mpz_t p; mpz_init(p); mpz_nextprime(p, rand.get_mpz_t()); rand_prime = mpz_class(p); mpz_clear(p); }
void Portfolio::processSellEvent( Event* e ) { SellEvent * event = (SellEvent*) e; event->lock(); std::string company = event->getCompany(); mpz_class amount = event->getAmount(); mpf_class shareprice = event->getSharePrice(); event->unlock(); action( company, mpz_class(-1) * amount, shareprice ); } /* end Portfolio::processSellEvent() */
mpz_class binomialCoefficient(mpz_class top, mpz_class bottom) { mpz_class i = top - bottom + 1; mpz_class numerator = mpz_class(1); while (i <= top) { numerator *= i; i += 1; } i = mpz_class(2); mpz_class denominator = mpz_class(1); while (i <= bottom) { denominator *= i; i += 1; } return numerator / denominator; }
int mod_inverse(const Ptr<RCP<const Integer>> &b, const Integer &a, const Integer &m) { int ret_val; mpz_t inv_t; mpz_init(inv_t); ret_val = mpz_invert(inv_t, a.as_mpz().get_mpz_t(), m.as_mpz().get_mpz_t()); *b = integer(mpz_class(inv_t)); mpz_clear(inv_t); return ret_val; }
int i_nth_root(const Ptr<RCP<const Integer>> &r, const Integer &a, unsigned long int n) { if (n == 0) throw std::runtime_error("i_nth_root: Can not find Zeroth root"); int ret_val; mpz_t t; mpz_init(t); ret_val = mpz_root(t, a.as_mpz().get_mpz_t(), n); *r = integer(mpz_class(t)); mpz_clear(t); return ret_val; }
void constructK1ProblemStandard_1(ulong nBits, int nPartitions, FileRawBuffer * frwb, char * fileName){ RandomNumberGenerator rng(frwb); mpz_class max; mpz_pow_ui(max.get_mpz_t(),mpz_class(2).get_mpz_t(),nBits); max--; double log1=(nPartitions-1)*(log(max)/log(nPartitions)); int nElem=ceil(log1); ofstream filestr(fileName); filestr << 3600 << endl; filestr << "~" << endl; filestr << nElem<< endl; filestr << "~" << endl; filestr << nPartitions << endl; filestr << "~" << endl; for (int i = 0; i < nElem; i++) { filestr << rng.getNumberWithMaxBits(nBits) << endl; } filestr.close(); }
void MathUtils::GetSmoothnessBase(mpz_class& ret_base, mpz_class& N) { mpfr_t f_N, log_N, log_log_N; mpz_t base_mpz; mpz_init(base_mpz); mpfr_init(f_N); mpfr_init(log_N); mpfr_init(log_log_N); mpfr_set_z(f_N, N.get_mpz_t(), MPFR_RNDU); //f_N = N mpfr_log(log_N, f_N, MPFR_RNDU); //log_N = log(N) mpfr_log(log_log_N, log_N, MPFR_RNDU); //log_log_N = log(log(N)) mpfr_mul(f_N, log_N, log_log_N, MPFR_RNDU); //f_N = log(N) * log(log(N)) mpfr_sqrt(f_N, f_N, MPFR_RNDU); //f_N = sqrt(f_N) mpfr_div_ui(f_N, f_N, 2, MPFR_RNDU); //f_N = f_N/2 mpfr_exp(f_N, f_N, MPFR_RNDU); //f_N = e^f_N mpfr_get_z(base_mpz, f_N, MPFR_RNDU); ret_base = mpz_class(base_mpz); mpfr_clears(f_N, log_N, log_log_N, NULL); }
bool Test::largeNumber(bool verbose) { bool passed = true; std::array<std::pair<mpz_class, mpz_class>, 3> pairs = {{ {mpz_class("985763284578345834"), mpz_class("298498582277498400")}, {mpz_class("98576328457834581423412342334"), mpz_class("45827308937045311626868162560")}, {mpz_class("958324857389475983274569823476558973245"), mpz_class( "644667608743795154660944983332241662208")} }}; for (const std::pair<mpz_class, mpz_class> &v: pairs) { // XXX: Better way to do this? if (Test::numeric(v.first, v.second, 1, verbose)) { } else { passed = false; } } return passed; }
expression_tree Power(const expression_tree::operands_t& ops_to_copy, enviroment& env) { expression_tree::operands_t ops(ops_to_copy); if ( ops.size() == 0 ) { return expression_tree::make_exact_number( mpq_class(1) ); } if ( ops.size() == 1 ) { return expression_tree( ops[0] ); } assert( ops.size() == 2 ); assert( ops[0].get_type() != expression_tree::APPROXIMATE_NUMBER ); assert( ops[1].get_type() != expression_tree::APPROXIMATE_NUMBER ); //if exponent is an integer, then there are possible simplifications if ( ops[1].is_integer() ) { //(a^b)^c == a^(bc) if c is an integer if ( ops[0].is_operator("Power") ) { const expression_tree::operands_t& power_ops = ops[0].get_operands(); assert( power_ops.size() == 2 ); ops[1] = expression_tree::make_operator("Times", power_ops[1], ops[1]).evaluate(env); ops[0] = power_ops[0]; } } //x^0 == 0 //x^1 == x //But 0^0 is Indeterminate, TODO!!?? DEBUG : Expand[Det[{{n,n,n},{n+1,n+1,n+2},{n+3,n+2,n+1}}]] if ( ops[1].get_type() == expression_tree::EXACT_NUMBER ) { if ( ops[1].get_exact_number() == 0 ) { if ( ops[0].get_type() == expression_tree::EXACT_NUMBER ) { env.raise_error( "Power", "Indeterminate expression 0^0 encountered." ); return expression_tree::make_symbol( "Indeterminate" ); } else { return expression_tree::make_exact_number( 1 ); } } else if ( ops[1].get_exact_number() == 1 ) { return ops[0]; } } if ( ops[0].get_type() != expression_tree::EXACT_NUMBER || ops[1].get_type() != expression_tree::EXACT_NUMBER ) { return expression_tree::make_operator( "Power", ops ); //nonnumber nonpowering } //TODO check if fits //If the don't fit into these, then why bother calculating? long exponent = 0; unsigned long inverse_exponent = 0; bool exponent_conversion_success = mpz_get_si_checked(exponent, ops[1].get_exact_number().get_num()); bool inverse_exponent_conversion_success = mpz_get_ui_checked(inverse_exponent, ops[1].get_exact_number().get_den()); if ( !exponent_conversion_success || !inverse_exponent_conversion_success ) { env.raise_error( "Power", "exponent overflow" ); return expression_tree::make_operator( "Power", ops ); } if ( ops[0].get_exact_number() < 0 ) { if ( inverse_exponent != 1 ) { env.raise_error( "Power", "can't raise a negative base to a rational exponent" ); return expression_tree::make_symbol( "Indeterminate" ); } } else if ( ops[0].get_exact_number() == 0 ) { if ( exponent > 0 ) { return expression_tree( ops[0] ); // mpq_class(0) why reconstruct? } else if ( exponent == 0 ) { env.raise_error( "Power", "Indeterminate 0^0" ); return expression_tree::make_symbol( "Indeterminate" ); } else { //exponent < 0 env.raise_error( "Power", "Infinite expression 0^-exp" ); return expression_tree::make_symbol( "Infinity" ); } } else { //ops[0].get_exact_number() > 0 //everything is mathOK here } //shortcut for Power[a, -1] if ( exponent == -1 && inverse_exponent == 1 ) { mpq_class result = mpq_class(1) / ops[0].get_exact_number(); return expression_tree::make_exact_number( result ); } bool negative_exponent = false; if ( exponent < 0 ) { negative_exponent = true; exponent = -exponent; } mpq_class resultq = mpq_pow_ui_class( ops[0].get_exact_number(), exponent ); if (negative_exponent) { resultq = mpq_class(1) / resultq; } if ( inverse_exponent == 1 ) { return expression_tree::make_exact_number( resultq ); } else { //ops[1] is now equals 1/d. We did the numerator's job above. //ops[1] = mpq_class( mpz_class(1), ops[1].get_exact_number().get_den() ); //implicit constructor //TODO check if fits //unsigned long inverse_exponent = ops[1].get_exact_number().get_den().get_ui(); mpz_class numerator_result; mpz_class denominator_result; bool numerator_success = mpz_root_class( numerator_result, resultq.get_num(), inverse_exponent); bool denominator_success = mpz_root_class( denominator_result, resultq.get_den(), inverse_exponent); if ( numerator_success && denominator_success ) { mpq_class result( numerator_result, denominator_result ); return expression_tree::make_exact_number( result ); } else if ( numerator_success ) { //&& !denominator_success /* Creating : Times[numerator_result, Power[resultq.get_den(), -1/inverse_exponent]] */ expression_tree::operands_t ops_power; expression_tree::operands_t ops_times; mpq_class negated_exponent( mpq_class(-1)*mpq_class(1, inverse_exponent) ); ops_power.push_back( expression_tree::make_exact_number( mpq_class(resultq.get_den()) ) ); ops_power.push_back( expression_tree::make_exact_number( negated_exponent ) ); //could use 1/inverse_exponent also expression_tree power_expr = expression_tree::make_operator( "Power", ops_power ); //don't have to evaulate, can't do anything anyway if ( numerator_result == 1 ) { return power_expr; } else { ops_times.push_back( expression_tree::make_exact_number( mpq_class(numerator_result) ) ); ops_times.push_back( power_expr ); return expression_tree::make_operator("Times", ops_times)/*.evaluate()*/; } } else if ( denominator_success ) { //&& !numerator_success /* Creating : Times[Power[resultq.get_num(), 1/inverse_exponent], 1/denominator_result] */ expression_tree::operands_t ops_powerlhs; expression_tree::operands_t ops_times; ops_powerlhs.push_back( expression_tree::make_exact_number( mpq_class(resultq.get_num()) ) ); ops_powerlhs.push_back( expression_tree::make_exact_number( mpq_class(1, inverse_exponent) ) ); expression_tree powerlhs_tree = expression_tree::make_operator("Power", ops_powerlhs); if ( denominator_result == 1 ) { return powerlhs_tree; } else { ops_times.push_back( powerlhs_tree ); ops_times.push_back( expression_tree::make_exact_number(mpq_class( mpz_class(1), denominator_result )) ); return expression_tree::make_operator("Times", ops_times)/*.evaluate()*/; //FIXME might evaulate this? no... } } else { //!denominator_success && !numerator_success /* Creating : Power[resultq, exponent/inverse_exponent] */ expression_tree::operands_t ops_power; ops_power.push_back( expression_tree::make_exact_number( resultq ) ); ops_power.push_back( expression_tree::make_exact_number( mpq_class(1, inverse_exponent) ) ); return expression_tree::make_operator("Power", ops_power); } } }
void FixComplexKCM::emulate(TestCase * tc) { /* first we are going to format the entries */ mpz_class reIn = tc->getInputValue("ReIN"); mpz_class imIn = tc->getInputValue("ImIN"); /* Sign handling */ // Msb index counting from one bool reInNeg = ( signedInput && (mpz_tstbit(reIn.get_mpz_t(), input_width - 1) == 1) ); bool imInNeg = ( signedInput && (mpz_tstbit(imIn.get_mpz_t(), input_width - 1) == 1) ); // 2's complement -> absolute value unsigned representation if(reInNeg) { reIn = (mpz_class(1) << input_width) - reIn; } if(imInNeg) { imIn = (mpz_class(1) << input_width) - imIn; } //Cast to mp floating point number mpfr_t reIn_mpfr, imIn_mpfr; mpfr_init2(reIn_mpfr, input_width + 1); mpfr_init2(imIn_mpfr, input_width + 1); //Exact mpfr_set_z(reIn_mpfr, reIn.get_mpz_t(), GMP_RNDN); mpfr_set_z(imIn_mpfr, imIn.get_mpz_t(), GMP_RNDN); //Scaling : Exact mpfr_mul_2si(reIn_mpfr, reIn_mpfr, lsb_in, GMP_RNDN); mpfr_mul_2si(imIn_mpfr, imIn_mpfr, lsb_in, GMP_RNDN); mpfr_t re_prod, im_prod, crexim_prod, xrecim_prod; mpfr_t reOut, imOut; mpfr_inits2( 2 * input_width + 1, re_prod, im_prod, crexim_prod, xrecim_prod, NULL ); mpfr_inits2(5 * max(outputim_width, outputre_width) + 1, reOut, imOut, NULL); // c_r * x_r -> re_prod mpfr_mul(re_prod, reIn_mpfr, mpfr_constant_re, GMP_RNDN); // c_i * x_i -> im_prod mpfr_mul(im_prod, imIn_mpfr, mpfr_constant_im, GMP_RNDN); // c_r * x_i -> crexim_prod mpfr_mul(crexim_prod, mpfr_constant_re, imIn_mpfr, GMP_RNDN); // x_r * c_im -> xrecim_prod mpfr_mul(xrecim_prod, reIn_mpfr, mpfr_constant_im, GMP_RNDN); /* Input sign correction */ if(reInNeg) { //Exact mpfr_neg(re_prod, re_prod, GMP_RNDN); mpfr_neg(xrecim_prod, xrecim_prod, GMP_RNDN); } if(imInNeg) { //Exact mpfr_neg(im_prod, im_prod, GMP_RNDN); mpfr_neg(crexim_prod, crexim_prod, GMP_RNDN); } mpfr_sub(reOut, re_prod, im_prod, GMP_RNDN); mpfr_add(imOut, crexim_prod, xrecim_prod, GMP_RNDN); bool reOutNeg = (mpfr_sgn(reOut) < 0); bool imOutNeg = (mpfr_sgn(imOut) < 0); if(reOutNeg) { //Exact mpfr_abs(reOut, reOut, GMP_RNDN); } if(imOutNeg) { //Exact mpfr_abs(imOut, imOut, GMP_RNDN); } //Scale back (Exact) mpfr_mul_2si(reOut, reOut, -lsb_out, GMP_RNDN); mpfr_mul_2si(imOut, imOut, -lsb_out, GMP_RNDN); //Get bits vector mpz_class reUp, reDown, imUp, imDown, carry; mpfr_get_z(reUp.get_mpz_t(), reOut, GMP_RNDU); mpfr_get_z(reDown.get_mpz_t(), reOut, GMP_RNDD); mpfr_get_z(imDown.get_mpz_t(), imOut, GMP_RNDD); mpfr_get_z(imUp.get_mpz_t(), imOut, GMP_RNDU); carry = 0; //If result was negative, compute 2's complement if(reOutNeg) { reUp = (mpz_class(1) << outputre_width) - reUp; reDown = (mpz_class(1) << outputre_width) - reDown; } if(imOutNeg) { imUp = (mpz_class(1) << outputim_width) - imUp; imDown = (mpz_class(1) << outputim_width) - imDown; } //Handle border cases if(imUp > (mpz_class(1) << outputim_width) - 1 ) { imUp = 0; } if(reUp > (mpz_class(1) << outputre_width) - 1) { reUp = 0; } if(imDown > (mpz_class(1) << outputim_width) - 1 ) { imDown = 0; } if(reDown > (mpz_class(1) << outputre_width) - 1) { reDown = 0; } //Add expected results to corresponding outputs tc->addExpectedOutput("ReOut", reUp); tc->addExpectedOutput("ReOut", reDown); tc->addExpectedOutput("ImOut", imUp); tc->addExpectedOutput("ImOut", imDown); mpfr_clears( reOut, imOut, re_prod, im_prod, crexim_prod, xrecim_prod, reIn_mpfr, imIn_mpfr, NULL ); }
TEST(String, FromMPZ) { ASSERT_EQ("0", util::str(mpz_class("0"))); ASSERT_EQ("123456", util::str(mpz_class("123456"))); ASSERT_EQ("1234567890123456789012345", util::str(mpz_class("1234567890123456789012345"))); }
void Fp::init(const char *prime) { p = mpz_class(prime); if (p <= 1) { throw std::runtime_error("not positive"); } }