user: Converte this assembly snippet into its equivalent C code:

```asm
<mpfr_as_mpz>:
  endbr64
  push   %r15
  push   %r14
  mov    %r8d,%r14d
  push   %r13
  mov    %edx,%r13d
  push   %r12
  mov    %edi,%r12d
  mov    %esi,%edi
  push   %rbp
  mov    %esi,%ebp
  push   %rbx
  sub    $0x18,%rsp
  mov    %ecx,0xc(%rsp)
  call   <mpfr_get_prec@plt>
  mov    %ebp,%edi
  mov    %eax,%ebx
  call   <mpfr_zero_p@plt>
  test   %rax,%rax
  jne    L11
  mov    %ebp,%edi
  lea    -0x1(%rbx),%r15d
  call   <mpfr_number_p@plt>
  mov    %ebp,%edi
  test   %rax,%rax
  je     L73
  call   <mpfr_get_exp@plt>
  mov    %ebp,%esi
  mov    %r12d,%edi
  mov    %eax,0xc(%rsp)
  call   <mpfr_get_z_2exp@plt>
  mov    %r12d,%esi
  mov    %r12d,%edi
  call   <mpz_abs@plt>
  mov    %r15d,%esi
  mov    %r12d,%edi
  call   <mpz_clrbit@plt>
  test   %r14d,%r14d
  mov    0xc(%rsp),%edx
  je     L57
  mov    %edx,%r14d
  lea    -0x1(%rbx,%r13,1),%eax
  sub    %r13d,%r14d
  cmp    %edx,%eax
  jg     L51
  sub    %ebx,%r14d
  add    $0x2,%r14d
  jmp    L95
  xchg   %ax,%ax
L73:
  call   <mpfr_inf_p@plt>
  mov    %eax,%edi
  call   <assert@plt>
  mov    0xc(%rsp),%eax
  sub    %r13d,%eax
  test   %r14d,%r14d
  je     L83
  sub    %ebx,%eax
  xor    %esi,%esi
  mov    %r12d,%edi
  mov    %eax,%r14d
  add    $0x3,%r14d
  call   <mpz_set_ui@plt>
L95:
  xor    %r13d,%r13d
  mov    %r14d,%esi
  mov    %r13d,%edi
  call   <mpz_init_set_ui@plt>
  mov    %r15d,%edx
  mov    %r13d,%esi
  mov    %r13d,%edi
  call   <mpz_mul_2exp@plt>
  mov    %r13d,%edx
  mov    %r12d,%esi
  mov    %r12d,%edi
  call   <mpz_add@plt>
  mov    %r13d,%edi
  call   <mpz_clear@plt>
  mov    %ebp,%edi
  call   <mpfr_sgn@plt>
  test   %rax,%rax
  js     L48
  add    $0x18,%rsp
  pop    %rbx
  pop    %rbp
  pop    %r12
  pop    %r13
  pop    %r14
  pop    %r15
  ret
  nopl   0x0(%rax)
L11:
  add    $0x18,%rsp
  mov    %r12d,%edi
  xor    %esi,%esi
  pop    %rbx
  pop    %rbp
  pop    %r12
  pop    %r13
  pop    %r14
  pop    %r15
  jmp    1270 <mpz_set_ui@plt>
  nopl   0x0(%rax,%rax,1)
L83:
  mov    $0x1,%esi
  mov    %r12d,%edi
  lea    0x1(%rax),%r14d
  call   <mpz_set_ui@plt>
  jmp    L95
  cs nopw 0x0(%rax,%rax,1)
L51:
  mov    %r15d,%edx
  mov    %r12d,%esi
  mov    %r12d,%edi
  mov    %r14d,%r15d
  sub    %r14d,%edx
  mov    $0x1,%r14d
  call   <mpz_tdiv_q_2exp@plt>
  jmp    L95
  nop
L48:
  add    $0x18,%rsp
  mov    %r12d,%esi
  mov    %r12d,%edi
  pop    %rbx
  pop    %rbp
  pop    %r12
  pop    %r13
  pop    %r14
  pop    %r15
  jmp    11c0 <mpz_neg@plt>
  nopl   0x0(%rax)
L57:
  sub    %r13d,%edx
  mov    %r12d,%esi
  mov    %r12d,%edi
  mov    %edx,%r14d
  mov    $0x1,%edx
  call   <mpz_add_ui@plt>
  jmp    L95
```

assistant: ```c
void mpfr_as_mpz(mpz_t m, mpfr_srcptr x, mpfr_exp_t emin, mpfr_exp_t emax, int subnormal) {
  mpfr_prec_t prec = mpfr_get_prec(x);
  if (mpfr_zero_p(x)) {
    mpz_set_ui(m, 0);
    return;
  }
  mpfr_uexp_t base_m;
  mp_bitcnt_t base_e = prec - 1;
  if (mpfr_number_p(x)) {
    mpfr_exp_t exp = mpfr_get_exp(x);
    mpfr_get_z_2exp(m, x);
    mpz_abs(m, m);
    mpz_clrbit(m, prec - 1);
    if (!subnormal) {
      base_m = exp - emin;
      mpz_add_ui(m, m, 1);
    } else if (exp >= emin + prec - 1) {
      base_m = exp - emin - prec + 2;
    } else {
      base_m = 1;
      base_e = exp - emin;
      mpz_tdiv_q_2exp(m, m, prec - 1 - base_e);
    }
  } else {
    assert(mpfr_inf_p(x));
    if (!subnormal) {
      base_m = emax - emin + 1;
      mpz_set_ui(m, 1);
    } else {
      base_m = emax - emin - prec + 3;
      mpz_set_ui(m, 0);
    }
  }
  mpz_t base;
  mpz_init_set_ui(base, base_m);
  mpz_mul_2exp(base, base, base_e);
  mpz_add(m, m, base);
  mpz_clear(base);
  if (mpfr_sgn(x) < 0) {
    mpz_neg(m, m);
  }
}
```