// File: /workspace/github_cpp_makefile_star2_O2/marxn[P]pupp/3rdparty/gmp/mpn/mu_div_qr.c
// Function: _gmpn_preinv_mu_div_qr
mp_limb_t
mpn_preinv_mu_div_qr (mp_ptr qp,
		      mp_ptr rp,
		      mp_srcptr np,
		      mp_size_t nn,
		      mp_srcptr dp,
		      mp_size_t dn,
		      mp_srcptr ip,
		      mp_size_t in,
		      mp_ptr scratch)
{
  mp_size_t qn;
  mp_limb_t cy, cx, qh;
  mp_limb_t r;
  mp_size_t tn, wn;

#define tp           scratch
#define scratch_out  (scratch + tn)

  qn = nn - dn;

  np += qn;
  qp += qn;

  qh = mpn_cmp (np, dp, dn) >= 0;
  if (qh != 0)
    mpn_sub_n (rp, np, dp, dn);
  else
    MPN_COPY_INCR (rp, np, dn);

  /* if (qn == 0) */			/* The while below handles this case */
  /*   return qh; */			/* Degenerate use.  Should we allow this? */

  while (qn > 0)
    {
      if (qn < in)
	{
	  ip += in - qn;
	  in = qn;
	}
      np -= in;
      qp -= in;

      /* Compute the next block of quotient limbs by multiplying the inverse I
	 by the upper part of the partial remainder R.  */
      mpn_mul_n (tp, rp + dn - in, ip, in);		/* mulhi  */
      cy = mpn_add_n (qp, tp + in, rp + dn - in, in);	/* I's msb implicit */
      ASSERT_ALWAYS (cy == 0);

      qn -= in;

      /* Compute the product of the quotient block and the divisor D, to be
	 subtracted from the partial remainder combined with new limbs from the
	 dividend N.  We only really need the low dn+1 limbs.  */

      if (BELOW_THRESHOLD (in, MUL_TO_MULMOD_BNM1_FOR_2NXN_THRESHOLD))
	mpn_mul (tp, dp, dn, qp, in);		/* dn+in limbs, high 'in' cancels */
      else
	{
	  tn = mpn_mulmod_bnm1_next_size (dn + 1);
	  mpn_mulmod_bnm1 (tp, tn, dp, dn, qp, in, scratch_out);
	  wn = dn + in - tn;			/* number of wrapped limbs */
	  if (wn > 0)
	    {
	      cy = mpn_sub_n (tp, tp, rp + dn - wn, wn);
	      cy = mpn_sub_1 (tp + wn, tp + wn, tn - wn, cy);
	      cx = mpn_cmp (rp + dn - in, tp + dn, tn - dn) < 0;
	      ASSERT_ALWAYS (cx >= cy);
	      mpn_incr_u (tp, cx - cy);
	    }
	}

      r = rp[dn - in] - tp[dn];

      /* Subtract the product from the partial remainder combined with new
	 limbs from the dividend N, generating a new partial remainder R.  */
      if (dn != in)
	{
	  cy = mpn_sub_n (tp, np, tp, in);	/* get next 'in' limbs from N */
	  cy = mpn_sub_nc (tp + in, rp, tp + in, dn - in, cy);
	  MPN_COPY (rp, tp, dn);		/* FIXME: try to avoid this */
	}
      else
	{
	  cy = mpn_sub_n (rp, np, tp, in);	/* get next 'in' limbs from N */
	}

      STAT (int i; int err = 0;
	    static int errarr[5]; static int err_rec; static int tot);

      /* Check the remainder R and adjust the quotient as needed.  */
      r -= cy;
      while (r != 0)
	{
	  /* We loop 0 times with about 69% probability, 1 time with about 31%
	     probability, 2 times with about 0.6% probability, if inverse is
	     computed as recommended.  */
	  mpn_incr_u (qp, 1);
	  cy = mpn_sub_n (rp, rp, dp, dn);
	  r -= cy;
	  STAT (err++);
	}
      if (mpn_cmp (rp, dp, dn) >= 0)
	{
	  /* This is executed with about 76% probability.  */
	  mpn_incr_u (qp, 1);
	  cy = mpn_sub_n (rp, rp, dp, dn);
	  STAT (err++);
	}

      STAT (
	    tot++;
	    errarr[err]++;
	    if (err > err_rec)
	      err_rec = err;
	    if (tot % 0x10000 == 0)
	      {
		for (i = 0; i <= err_rec; i++)
		  printf ("  %d(%.1f%%)", errarr[i], 100.0*errarr[i]/tot);
		printf ("\n");
	      }
	    );
    }

  return qh;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x68, %rsp
movq %r9, %rbx
movq %r8, %r14
movq %rcx, %rbp
movq %rsi, %r12
movq %rdi, %r15
subq %r9, %rbp
leaq (%rdx,%rbp,8), %r13
movq %r13, %rdi
movq %r8, %rsi
movq %r9, %rdx
callq 0x1ac5c
movl %eax, 0x24(%rsp)
testl %eax, %eax
movq %r13, 0x40(%rsp)
movq %r12, %rdi
movq %r13, %rsi
js 0x28246
movq %r14, %rdx
movq %rbx, %rcx
callq 0x17ed0
jmp 0x2824e
movq %rbx, %rdx
callq 0x290c6
movq 0xa8(%rsp), %rcx
movq 0xa0(%rsp), %rax
movq %rax, 0x48(%rsp)
leaq (%r15,%rbp,8), %r13
leaq (%r12,%rbx,8), %rax
movq %rax, 0x38(%rsp)
leaq 0x1(%rbx), %rax
movq %rax, 0x50(%rsp)
movq 0xb0(%rsp), %r15
leaq (%r15,%rbx,8), %rax
movq %rax, 0x30(%rsp)
testq %rbp, %rbp
jle 0x2851f
movq %rbp, %rax
subq %rcx, %rax
movq %r15, %rdi
movq %rcx, %r15
cmovlq %rbp, %r15
negq %rax
movq %rbp, 0x60(%rsp)
cmpq %rbp, %rcx
movl $0x0, %ecx
cmovleq %rcx, %rax
movq 0x48(%rsp), %rdx
leaq (%rdx,%rax,8), %rdx
leaq (,%r15,8), %rax
subq %rax, %r13
movq 0x38(%rsp), %rbp
movq %rax, 0x18(%rsp)
subq %rax, %rbp
movq %rbp, %rsi
movq %rdx, 0x48(%rsp)
movq %r15, %rcx
callq 0x19500
movq 0xb0(%rsp), %rax
leaq (%rax,%r15,8), %rsi
movq %r13, %rdi
movq %rsi, 0x58(%rsp)
movq %rbp, %rdx
movq %r15, %rcx
callq 0x17cf0
testq %rax, %rax
jne 0x28538
cmpq $0x20, %r15
movq %r15, 0x10(%rsp)
jle 0x283ec
movq 0x50(%rsp), %rdi
callq 0x253ca
movq 0xb0(%rsp), %rdi
movq %rax, %r15
leaq (%rdi,%rax,8), %rax
movq %rax, (%rsp)
movq %r15, %rsi
movq %r14, %rdx
movq %rbx, %rcx
movq %r13, %r8
movq 0x10(%rsp), %r9
callq 0x24f3e
movq 0x10(%rsp), %r8
leaq (%r8,%rbx), %rcx
movq %r15, 0x28(%rsp)
subq %r15, %rcx
testq %rcx, %rcx
jle 0x2840c
leaq (,%rcx,8), %rax
movq 0x38(%rsp), %rdx
subq %rax, %rdx
movq 0xb0(%rsp), %rdi
movq %rdi, %rsi
movq %rcx, %r15
callq 0x17ed0
movq 0xb0(%rsp), %rcx
leaq (%rcx,%r15,8), %rdi
movq 0x28(%rsp), %rdx
subq %r15, %rdx
movq %rdi, %rsi
movq %rax, %rcx
callq 0x17e44
movq %rax, %r15
movq 0x28(%rsp), %rdx
subq %rbx, %rdx
movq %rbp, %rdi
movq 0x30(%rsp), %rsi
callq 0x1ac5c
shrl $0x1f, %eax
subq %r15, %rax
jb 0x28550
movq 0xb0(%rsp), %rcx
addq %rax, (%rcx)
jae 0x283ea
addq $0x1, 0x8(%rcx)
leaq 0x8(%rcx), %rcx
jb 0x283df
jmp 0x28407
movq 0xb0(%rsp), %rdi
movq %r14, %rsi
movq %rbx, %rdx
movq %r13, %rcx
movq 0x10(%rsp), %r8
callq 0x18a58
movq 0x10(%rsp), %r8
movq 0x40(%rsp), %rsi
subq 0x18(%rsp), %rsi
movq %rbx, %rbp
movq 0x30(%rsp), %rax
movq (%rax), %rax
movq %rax, 0x18(%rsp)
subq %r8, %rbp
movq (%r12,%rbp,8), %r15
movq %rsi, 0x40(%rsp)
jne 0x2844c
movq %r12, %rdi
movq 0xb0(%rsp), %rdx
movq %rbx, %rcx
callq 0x17ed0
movq %rax, %rbp
jmp 0x2848b
movq 0xb0(%rsp), %rdi
movq %rdi, %rdx
movq %r8, %rcx
callq 0x17ed0
movq 0x58(%rsp), %rdi
movq %r12, %rsi
movq %rdi, %rdx
movq %rbp, %rcx
movq %rax, %r8
callq 0x17eb0
movq %rax, %rbp
movq %r12, %rdi
movq 0xb0(%rsp), %rsi
movq %rbx, %rdx
callq 0x290c6
movq 0x18(%rsp), %rax
addq %rbp, %rax
subq %rax, %r15
movq 0x60(%rsp), %rbp
subq 0x10(%rsp), %rbp
testq %r15, %r15
je 0x284c8
movq %r13, %rax
addq $0x1, (%rax)
leaq 0x8(%rax), %rax
jb 0x284a8
movq %r12, %rdi
movq %r12, %rsi
movq %r14, %rdx
movq %rbx, %rcx
callq 0x17ed0
subq %rax, %r15
jmp 0x284a0
movq %r12, %rdi
movq %r14, %rsi
movq %rbx, %rdx
callq 0x1ac5c
movq 0x10(%rsp), %r8
movq %r8, %rcx
testl %eax, %eax
movq 0xb0(%rsp), %r15
js 0x2828a
movq %r13, %rax
addq $0x1, (%rax)
leaq 0x8(%rax), %rax
jb 0x284f1
movq %r12, %rdi
movq %r12, %rsi
movq %r14, %rdx
movq %rbx, %rcx
movq %r8, %r15
callq 0x17ed0
movq %r15, %rcx
movq 0xb0(%rsp), %r15
jmp 0x2828a
xorl %eax, %eax
cmpl $0x0, 0x24(%rsp)
setns %al
addq $0x68, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0xb4b8(%rip), %rdi      # 0x339f7
leaq 0xb497(%rip), %rdx      # 0x339dd
movl $0x118, %esi            # imm = 0x118
callq 0x29ce6
leaq 0xb4a0(%rip), %rdi      # 0x339f7
leaq 0xb4a5(%rip), %rdx      # 0x33a03
movl $0x12c, %esi            # imm = 0x12C
callq 0x29ce6