| Index: gcc/gmp/mpn/generic/divexact.c
|
| diff --git a/gcc/gmp/mpn/generic/divexact.c b/gcc/gmp/mpn/generic/divexact.c
|
| deleted file mode 100644
|
| index a0e439cbee9884514bbe227d5e3be9ada9d9a923..0000000000000000000000000000000000000000
|
| --- a/gcc/gmp/mpn/generic/divexact.c
|
| +++ /dev/null
|
| @@ -1,234 +0,0 @@
|
| -/* mpn_divexact(qp,np,nn,dp,dn,tp) -- Divide N = {np,nn} by D = {dp,dn} storing
|
| - the result in Q = {qp,nn-dn+1} expecting no remainder. Overlap allowed
|
| - between Q and N; all other overlap disallowed.
|
| -
|
| - Contributed to the GNU project by Torbjorn Granlund.
|
| -
|
| - THE FUNCTIONS IN THIS FILE ARE INTERNAL WITH A MUTABLE INTERFACE. IT IS
|
| - ONLY SAFE TO REACH THEM THROUGH DOCUMENTED INTERFACES. IN FACT, IT IS
|
| - ALMOST GUARANTEED THAT THEY WILL CHANGE OR DISAPPEAR IN A FUTURE GMP
|
| - RELEASE.
|
| -
|
| -Copyright 2006, 2007 Free Software Foundation, Inc.
|
| -
|
| -This file is part of the GNU MP Library.
|
| -
|
| -The GNU MP Library is free software; you can redistribute it and/or modify
|
| -it under the terms of the GNU Lesser General Public License as published by
|
| -the Free Software Foundation; either version 3 of the License, or (at your
|
| -option) any later version.
|
| -
|
| -The GNU MP Library is distributed in the hope that it will be useful, but
|
| -WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
| -or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
|
| -License for more details.
|
| -
|
| -You should have received a copy of the GNU Lesser General Public License
|
| -along with the GNU MP Library. If not, see http://www.gnu.org/licenses/. */
|
| -
|
| -
|
| -/* We use the Jebelean's bidirectional exact division algorithm. This is
|
| - somewhat naively implemented, with equal quotient parts done by 2-adic
|
| - division and truncating division. Since 2-adic division is faster, it
|
| - should be used for a larger chunk.
|
| -
|
| - This code is horrendously ugly, in all sorts of ways.
|
| -
|
| - * It was hacked without much care or thought, but with a testing program.
|
| - * It handles scratch space frivolously, and furthermore the itch function
|
| - is broken.
|
| - * Doesn't provide any measures to deal with mu_divappr_q's +3 error. We
|
| - have yet to provoke an error due to this, though.
|
| - * Algorithm selection leaves a lot to be desired. In particular, the choice
|
| - between DC and MU isn't a point, but we treat it like one.
|
| - * It makes the msb part 1 or 2 limbs larger than the lsb part, in spite of
|
| - that the latter is faster. We should at least reverse this, but perhaps
|
| - we should make the lsb part considerably larger. (How do we tune this?)
|
| -
|
| - Perhaps we could somehow use 2-adic division for both parts, not as now
|
| - truncating division for the upper part and 2-adic for the lower part.
|
| -*/
|
| -
|
| -
|
| -#include "gmp.h"
|
| -#include "gmp-impl.h"
|
| -#include "longlong.h"
|
| -
|
| -
|
| -mp_size_t
|
| -mpn_divexact_itch (mp_size_t nn, mp_size_t dn)
|
| -{
|
| - return nn + dn; /* FIXME this is not right */
|
| -}
|
| -
|
| -void
|
| -mpn_divexact (mp_ptr qp,
|
| - mp_srcptr np, mp_size_t nn,
|
| - mp_srcptr dp, mp_size_t dn,
|
| - mp_ptr scratch)
|
| -{
|
| - mp_size_t qn;
|
| - mp_size_t nn0, qn0;
|
| - mp_size_t nn1, qn1;
|
| - mp_ptr tp;
|
| - mp_limb_t qml;
|
| - mp_limb_t qh;
|
| - int cnt;
|
| - mp_ptr xdp;
|
| - mp_limb_t di;
|
| - mp_limb_t dip[2], xp[2], cy;
|
| - TMP_DECL;
|
| -
|
| - TMP_MARK;
|
| -
|
| - qn = nn - dn + 1;
|
| -
|
| - /* For small divisors, and small quotients, don't use Jebelean's algorithm. */
|
| - if (dn < DIVEXACT_JEB_THRESHOLD || qn < DIVEXACT_JEB_THRESHOLD)
|
| - {
|
| - tp = scratch;
|
| - MPN_COPY (tp, np, qn);
|
| - binvert_limb (di, dp[0]); di = -di;
|
| - dn = MIN (dn, qn);
|
| - mpn_sb_bdiv_q (qp, tp, qn, dp, dn, di);
|
| - TMP_FREE;
|
| - return;
|
| - }
|
| -
|
| - qn0 = ((nn - dn) >> 1) + 1; /* low quotient size */
|
| -
|
| - /* If quotient is much larger than the divisor, the bidirectional algorithm
|
| - does not work as currently implemented. Fall back to plain bdiv. */
|
| - if (qn0 > dn)
|
| - {
|
| - if (BELOW_THRESHOLD (dn, DC_BDIV_Q_THRESHOLD))
|
| - {
|
| - tp = scratch;
|
| - MPN_COPY (tp, np, qn);
|
| - binvert_limb (di, dp[0]); di = -di;
|
| - dn = MIN (dn, qn);
|
| - mpn_sb_bdiv_q (qp, tp, qn, dp, dn, di);
|
| - }
|
| - else if (BELOW_THRESHOLD (dn, MU_BDIV_Q_THRESHOLD))
|
| - {
|
| - tp = scratch;
|
| - MPN_COPY (tp, np, qn);
|
| - binvert_limb (di, dp[0]); di = -di;
|
| - mpn_dc_bdiv_q (qp, tp, qn, dp, dn, di);
|
| - }
|
| - else
|
| - {
|
| - mpn_mu_bdiv_q (qp, np, qn, dp, dn, scratch);
|
| - }
|
| - TMP_FREE;
|
| - return;
|
| - }
|
| -
|
| - nn0 = qn0 + qn0;
|
| -
|
| - nn1 = nn0 - 1 + ((nn-dn) & 1);
|
| - qn1 = qn0;
|
| - if (LIKELY (qn0 != dn))
|
| - {
|
| - nn1 = nn1 + 1;
|
| - qn1 = qn1 + 1;
|
| - if (UNLIKELY (dp[dn - 1] == 1 && qn1 != dn))
|
| - {
|
| - /* If the leading divisor limb == 1, i.e. has just one bit, we have
|
| - to include an extra limb in order to get the needed overlap. */
|
| - /* FIXME: Now with the mu_divappr_q function, we should really need
|
| - more overlap. That indicates one of two things: (1) The test code
|
| - is not good. (2) We actually overlap too much by default. */
|
| - nn1 = nn1 + 1;
|
| - qn1 = qn1 + 1;
|
| - }
|
| - }
|
| -
|
| - tp = TMP_ALLOC_LIMBS (nn1 + 1);
|
| -
|
| - count_leading_zeros (cnt, dp[dn - 1]);
|
| -
|
| - /* Normalize divisor, store into tmp area. */
|
| - if (cnt != 0)
|
| - {
|
| - xdp = TMP_ALLOC_LIMBS (qn1);
|
| - mpn_lshift (xdp, dp + dn - qn1, qn1, cnt);
|
| - }
|
| - else
|
| - {
|
| - xdp = (mp_ptr) dp + dn - qn1;
|
| - }
|
| -
|
| - /* Shift dividend according to the divisor normalization. */
|
| - /* FIXME: We compute too much here for XX_divappr_q, but these functions'
|
| - interfaces want a pointer to the imaginative least significant limb, not
|
| - to the least significant *used* limb. Of course, we could leave nn1-qn1
|
| - rubbish limbs in the low part, to save some time. */
|
| - if (cnt != 0)
|
| - {
|
| - cy = mpn_lshift (tp, np + nn - nn1, nn1, cnt);
|
| - if (cy != 0)
|
| - {
|
| - tp[nn1] = cy;
|
| - nn1++;
|
| - }
|
| - }
|
| - else
|
| - {
|
| - /* FIXME: This copy is not needed for mpn_mu_divappr_q, except when the
|
| - mpn_sub_n right before is executed. */
|
| - MPN_COPY (tp, np + nn - nn1, nn1);
|
| - }
|
| -
|
| - if (BELOW_THRESHOLD (qn1, DC_DIVAPPR_Q_THRESHOLD))
|
| - {
|
| - /* Compute divisor inverse. */
|
| - cy = mpn_add_1 (xp, xdp + qn1 - 2, 2, 1);
|
| - if (cy != 0)
|
| - dip[0] = dip[1] = 0;
|
| - else
|
| - {
|
| - mp_limb_t scratch[10]; /* FIXME */
|
| - mpn_invert (dip, xp, 2, scratch);
|
| - }
|
| -
|
| - qp[qn0 - 1 + nn1 - qn1] = mpn_sb_divappr_q (qp + qn0 - 1, tp, nn1, xdp, qn1, dip);
|
| - }
|
| - else if (BELOW_THRESHOLD (qn1, MU_DIVAPPR_Q_THRESHOLD))
|
| - {
|
| - qp[qn0 - 1 + nn1 - qn1] = mpn_dc_divappr_q (qp + qn0 - 1, tp, nn1, xdp, qn1);
|
| - }
|
| - else
|
| - {
|
| - /* FIXME: mpn_mu_divappr_q doesn't handle qh != 0. Work around it with a
|
| - conditional subtraction here. */
|
| - qh = mpn_cmp (tp + nn1 - qn1, xdp, qn1) >= 0;
|
| - if (qh)
|
| - mpn_sub_n (tp + nn1 - qn1, tp + nn1 - qn1, xdp, qn1);
|
| - mpn_mu_divappr_q (qp + qn0 - 1, tp, nn1, xdp, qn1, scratch);
|
| - qp[qn0 - 1 + nn1 - qn1] = qh;
|
| - }
|
| - qml = qp[qn0 - 1];
|
| -
|
| - binvert_limb (di, dp[0]); di = -di;
|
| -
|
| - if (BELOW_THRESHOLD (qn0, DC_BDIV_Q_THRESHOLD))
|
| - {
|
| - MPN_COPY (tp, np, qn0);
|
| - mpn_sb_bdiv_q (qp, tp, qn0, dp, qn0, di);
|
| - }
|
| - else if (BELOW_THRESHOLD (qn0, MU_BDIV_Q_THRESHOLD))
|
| - {
|
| - MPN_COPY (tp, np, qn0);
|
| - mpn_dc_bdiv_q (qp, tp, qn0, dp, qn0, di);
|
| - }
|
| - else
|
| - {
|
| - mpn_mu_bdiv_q (qp, np, qn0, dp, qn0, scratch);
|
| - }
|
| -
|
| - if (qml < qp[qn0 - 1])
|
| - mpn_decr_u (qp + qn0, 1);
|
| -
|
| - TMP_FREE;
|
| -}
|
|
|