extern int Bignum_GetDigits(int);
extern void Bignum_ShiftRight(int, int);

int Bignum_ShiftLeft(int ctx, int q, int n)
{
  register int cc __asm__("r10") = ctx;
  register int qq __asm__("r8") = q;
  register int nn __asm__("r5") = n;
  register int words __asm__("r6") = nn >> 5;
  int rneed;
  register int nres __asm__("r9");
  register int *dq __asm__("r4");
  register int *sp __asm__("r3");
  register int *end __asm__("r6");
  {
    register int nd __asm__("r1") = *(int *)((char *)q + 4);
    register int *qc __asm__("r2") = (int *)qq;
    int m = *(int *)((char *)qc + 16);
    int w = words + m;
    rneed = w + 1;
    qc = (int *)*(int *)((char *)qc + 8);
    if (rneed > (int)qc) {
      do {
        int cap = (int)qc;
        nd += 1;
        cap <<= 1;
        __asm__ volatile("" : "+r"(nd));
        qc = (int *)cap;
      } while (rneed > (int)qc);
    }
  }
  nres = Bignum_GetDigits(cc);
  dq = (int *)((char *)nres + 20);
  {
    register int *sqq __asm__("r0") = (int *)((char *)qq + 20);
    if (words > 0) {
      register int z __asm__("r1") = 0;
      register int c __asm__("r2") = words;
      do {
        *dq = z;
        dq++;
        c -= 1;
      } while (c != 0);
    }
    sp = sqq;
    {
      register int *qp __asm__("r1") = (int *)qq;
      register int cnt __asm__("r0") = qp[4];
      register int inv __asm__("r1");
      register unsigned carry __asm__("r2");
      register int v __asm__("r0");
      end = (int *)((char *)sp + (cnt << 2));
      nn &= 31;
      if (nn != 0) {
        register int t32 __asm__("r0") = 32;
        inv = t32 - nn;
        carry = 0;
        do {
          v = *sp;
          v <<= nn;
          v |= carry;
          *dq = v;
          dq++;
          carry = *sp++;
          carry >>= inv;
        } while (sp < end);
        *dq = carry;
        if (carry == 0)
          goto done;
        rneed += 1;
        goto done;
      } else {
        do {
          *dq++ = *sp++;
        } while (sp < end);
      }
    }
  }
done:;
  {
    register int nl __asm__("r0") = rneed - 1;
    register int *np __asm__("r2") = (int *)nres;
    np[4] = nl;
  }
  Bignum_ShiftRight(cc, qq);
  return nres;
}
