// File: /workspace/github_c_makefile_star2_O1/orangeduck[P]mpc/mpc.c
// Function: mpc_optimise_unretained
static void mpc_optimise_unretained(mpc_parser_t *p, int force) {

  int i, n, m;
  mpc_parser_t *t;

  if (p->retained && !force) { return; }

  /* Optimise Subexpressions */

  if (p->type == MPC_TYPE_EXPECT)     { mpc_optimise_unretained(p->data.expect.x, 0); }
  if (p->type == MPC_TYPE_APPLY)      { mpc_optimise_unretained(p->data.apply.x, 0); }
  if (p->type == MPC_TYPE_APPLY_TO)   { mpc_optimise_unretained(p->data.apply_to.x, 0); }
  if (p->type == MPC_TYPE_CHECK)      { mpc_optimise_unretained(p->data.check.x, 0); }
  if (p->type == MPC_TYPE_CHECK_WITH) { mpc_optimise_unretained(p->data.check_with.x, 0); }
  if (p->type == MPC_TYPE_PREDICT)    { mpc_optimise_unretained(p->data.predict.x, 0); }
  if (p->type == MPC_TYPE_NOT)        { mpc_optimise_unretained(p->data.not.x, 0); }
  if (p->type == MPC_TYPE_MAYBE)      { mpc_optimise_unretained(p->data.not.x, 0); }
  if (p->type == MPC_TYPE_MANY)       { mpc_optimise_unretained(p->data.repeat.x, 0); }
  if (p->type == MPC_TYPE_MANY1)      { mpc_optimise_unretained(p->data.repeat.x, 0); }
  if (p->type == MPC_TYPE_COUNT)      { mpc_optimise_unretained(p->data.repeat.x, 0); }
  if (p->type == MPC_TYPE_SEPBY1)     {
    mpc_optimise_unretained(p->data.sepby1.x, 0);
    mpc_optimise_unretained(p->data.sepby1.sep, 0);
  }

  if (p->type == MPC_TYPE_OR) {
    for(i = 0; i < p->data.or.n; i++) {
      mpc_optimise_unretained(p->data.or.xs[i], 0);
    }
  }

  if (p->type == MPC_TYPE_AND) {
    for(i = 0; i < p->data.and.n; i++) {
      mpc_optimise_unretained(p->data.and.xs[i], 0);
    }
  }

  /* Perform optimisations */

  while (1) {

    /* Merge rhs `or` */
    if (p->type == MPC_TYPE_OR
    &&  p->data.or.xs[p->data.or.n-1]->type == MPC_TYPE_OR
    && !p->data.or.xs[p->data.or.n-1]->retained) {
      t = p->data.or.xs[p->data.or.n-1];
      n = p->data.or.n; m = t->data.or.n;
      p->data.or.n = n + m - 1;
      p->data.or.xs = realloc(p->data.or.xs, sizeof(mpc_parser_t*) * (n + m -1));
      memmove(p->data.or.xs + n - 1, t->data.or.xs, m * sizeof(mpc_parser_t*));
      free(t->data.or.xs); free(t->name); free(t);
      continue;
    }

    /* Merge lhs `or` */
    if (p->type == MPC_TYPE_OR
    &&  p->data.or.xs[0]->type == MPC_TYPE_OR
    && !p->data.or.xs[0]->retained) {
      t = p->data.or.xs[0];
      n = p->data.or.n; m = t->data.or.n;
      p->data.or.n = n + m - 1;
      p->data.or.xs = realloc(p->data.or.xs, sizeof(mpc_parser_t*) * (n + m -1));
      memmove(p->data.or.xs + m, p->data.or.xs + 1, (n - 1) * sizeof(mpc_parser_t*));
      memmove(p->data.or.xs, t->data.or.xs, m * sizeof(mpc_parser_t*));
      free(t->data.or.xs); free(t->name); free(t);
      continue;
    }

    /* Remove ast `pass` */
    if (p->type == MPC_TYPE_AND
    &&  p->data.and.n == 2
    &&  p->data.and.xs[0]->type == MPC_TYPE_PASS
    && !p->data.and.xs[0]->retained
    &&  p->data.and.f == mpcf_fold_ast) {
      t = p->data.and.xs[1];
      mpc_delete(p->data.and.xs[0]);
      free(p->data.and.xs); free(p->data.and.dxs); free(p->name);
      memcpy(p, t, sizeof(mpc_parser_t));
      free(t);
      continue;
    }

    /* Merge ast lhs `and` */
    if (p->type == MPC_TYPE_AND
    &&  p->data.and.f == mpcf_fold_ast
    &&  p->data.and.xs[0]->type == MPC_TYPE_AND
    && !p->data.and.xs[0]->retained
    &&  p->data.and.xs[0]->data.and.f == mpcf_fold_ast) {
      t = p->data.and.xs[0];
      n = p->data.and.n; m = t->data.and.n;
      p->data.and.n = n + m - 1;
      p->data.and.xs = realloc(p->data.and.xs, sizeof(mpc_parser_t*) * (n + m - 1));
      p->data.and.dxs = realloc(p->data.and.dxs, sizeof(mpc_dtor_t) * (n + m - 1 - 1));
      memmove(p->data.and.xs + m, p->data.and.xs + 1, (n - 1) * sizeof(mpc_parser_t*));
      memmove(p->data.and.xs, t->data.and.xs, m * sizeof(mpc_parser_t*));
      for (i = 0; i < p->data.and.n-1; i++) { p->data.and.dxs[i] = (mpc_dtor_t)mpc_ast_delete; }
      free(t->data.and.xs); free(t->data.and.dxs); free(t->name); free(t);
      continue;
    }

    /* Merge ast rhs `and` */
    if (p->type == MPC_TYPE_AND
    &&  p->data.and.f == mpcf_fold_ast
    &&  p->data.and.xs[p->data.and.n-1]->type == MPC_TYPE_AND
    && !p->data.and.xs[p->data.and.n-1]->retained
    &&  p->data.and.xs[p->data.and.n-1]->data.and.f == mpcf_fold_ast) {
      t = p->data.and.xs[p->data.and.n-1];
      n = p->data.and.n; m = t->data.and.n;
      p->data.and.n = n + m - 1;
      p->data.and.xs = realloc(p->data.and.xs, sizeof(mpc_parser_t*) * (n + m -1));
      p->data.and.dxs = realloc(p->data.and.dxs, sizeof(mpc_dtor_t) * (n + m - 1 - 1));
      memmove(p->data.and.xs + n - 1, t->data.and.xs, m * sizeof(mpc_parser_t*));
      for (i = 0; i < p->data.and.n-1; i++) { p->data.and.dxs[i] = (mpc_dtor_t)mpc_ast_delete; }
      free(t->data.and.xs); free(t->data.and.dxs); free(t->name); free(t);
      continue;
    }

    /* Remove re `lift` */
    if (p->type == MPC_TYPE_AND
    &&  p->data.and.n == 2
    &&  p->data.and.xs[0]->type == MPC_TYPE_LIFT
    &&  p->data.and.xs[0]->data.lift.lf == mpcf_ctor_str
    && !p->data.and.xs[0]->retained
    &&  p->data.and.f == mpcf_strfold) {
      t = p->data.and.xs[1];
      mpc_delete(p->data.and.xs[0]);
      free(p->data.and.xs); free(p->data.and.dxs); free(p->name);
      memcpy(p, t, sizeof(mpc_parser_t));
      free(t);
      continue;
    }

    /* Merge re lhs `and` */
    if (p->type == MPC_TYPE_AND
    &&  p->data.and.f == mpcf_strfold
    &&  p->data.and.xs[0]->type == MPC_TYPE_AND
    && !p->data.and.xs[0]->retained
    &&  p->data.and.xs[0]->data.and.f == mpcf_strfold) {
      t = p->data.and.xs[0];
      n = p->data.and.n; m = t->data.and.n;
      p->data.and.n = n + m - 1;
      p->data.and.xs = realloc(p->data.and.xs, sizeof(mpc_parser_t*) * (n + m - 1));
      p->data.and.dxs = realloc(p->data.and.dxs, sizeof(mpc_dtor_t) * (n + m - 1 - 1));
      memmove(p->data.and.xs + m, p->data.and.xs + 1, (n - 1) * sizeof(mpc_parser_t*));
      memmove(p->data.and.xs, t->data.and.xs, m * sizeof(mpc_parser_t*));
      for (i = 0; i < p->data.and.n-1; i++) { p->data.and.dxs[i] = free; }
      free(t->data.and.xs); free(t->data.and.dxs); free(t->name); free(t);
      continue;
    }

    /* Merge re rhs `and` */
    if (p->type == MPC_TYPE_AND
    &&  p->data.and.f == mpcf_strfold
    &&  p->data.and.xs[p->data.and.n-1]->type == MPC_TYPE_AND
    && !p->data.and.xs[p->data.and.n-1]->retained
    &&  p->data.and.xs[p->data.and.n-1]->data.and.f == mpcf_strfold) {
      t = p->data.and.xs[p->data.and.n-1];
      n = p->data.and.n; m = t->data.and.n;
      p->data.and.n = n + m - 1;
      p->data.and.xs = realloc(p->data.and.xs, sizeof(mpc_parser_t*) * (n + m -1));
      p->data.and.dxs = realloc(p->data.and.dxs, sizeof(mpc_dtor_t) * (n + m - 1 - 1));
      memmove(p->data.and.xs + n - 1, t->data.and.xs, m * sizeof(mpc_parser_t*));
      for (i = 0; i < p->data.and.n-1; i++) { p->data.and.dxs[i] = free; }
      free(t->data.and.xs); free(t->data.and.dxs); free(t->name); free(t);
      continue;
    }

    return;

  }

}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
pushq %rax
movq %rdi, %rbx
testl %esi, %esi
jne 0xc0dd
cmpb $0x0, 0x31(%rbx)
je 0xc0dd
addq $0x8, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
cmpb $0x5, 0x30(%rbx)
jne 0xc0ee
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0xf, 0x30(%rbx)
jne 0xc0ff
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x10, 0x30(%rbx)
jne 0xc110
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x19, 0x30(%rbx)
jne 0xc121
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x1a, 0x30(%rbx)
jne 0xc132
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x11, 0x30(%rbx)
jne 0xc143
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x12, 0x30(%rbx)
jne 0xc154
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x13, 0x30(%rbx)
jne 0xc165
movq 0x8(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x14, 0x30(%rbx)
jne 0xc176
movq 0x18(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x15, 0x30(%rbx)
jne 0xc187
movq 0x18(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x16, 0x30(%rbx)
jne 0xc198
movq 0x18(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x1d, 0x30(%rbx)
jne 0xc1b4
movq 0x18(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
movq 0x20(%rbx), %rdi
xorl %esi, %esi
callq 0xc0b6
cmpb $0x17, 0x30(%rbx)
jne 0xc1de
cmpl $0x0, 0x8(%rbx)
jle 0xc1de
xorl %r14d, %r14d
movq 0x10(%rbx), %rax
movq (%rax,%r14,8), %rdi
xorl %esi, %esi
callq 0xc0b6
incq %r14
movslq 0x8(%rbx), %rax
cmpq %rax, %r14
jl 0xc1c3
cmpb $0x18, 0x30(%rbx)
jne 0xc208
cmpl $0x0, 0x8(%rbx)
jle 0xc208
xorl %r14d, %r14d
movq 0x18(%rbx), %rax
movq (%rax,%r14,8), %rdi
xorl %esi, %esi
callq 0xc0b6
incq %r14
movslq 0x8(%rbx), %rax
cmpq %rax, %r14
jl 0xc1ed
movq 0x6d99(%rip), %rbp      # 0x12fa8
movq 0x6daa(%rip), %r13      # 0x12fc0
movb 0x30(%rbx), %al
cmpb $0x17, %al
jne 0xc259
movq 0x10(%rbx), %rdi
movslq 0x8(%rbx), %r12
movq -0x8(%rdi,%r12,8), %r14
cmpb $0x17, 0x30(%r14)
jne 0xc23c
cmpb $0x0, 0x31(%r14)
je 0xc439
cmpb $0x17, %al
jne 0xc259
movq 0x10(%rbx), %rdi
movq (%rdi), %r14
cmpb $0x17, 0x30(%r14)
jne 0xc259
cmpb $0x0, 0x31(%r14)
je 0xc4b4
cmpb $0x18, %al
jne 0xc0ce
cmpl $0x2, 0x8(%rbx)
jne 0xc284
movq 0x18(%rbx), %rcx
movq (%rcx), %rdi
cmpb $0x1, 0x30(%rdi)
jne 0xc284
cmpb $0x0, 0x31(%rdi)
jne 0xc284
cmpq %rbp, 0x10(%rbx)
je 0xc46b
cmpb $0x18, %al
jne 0xc0ce
cmpq %rbp, 0x10(%rbx)
jne 0xc2b1
movq 0x18(%rbx), %rdi
movq (%rdi), %r14
cmpb $0x18, 0x30(%r14)
jne 0xc2b1
cmpb $0x0, 0x31(%r14)
jne 0xc2b1
cmpq %rbp, 0x10(%r14)
je 0xc523
cmpb $0x18, %al
jne 0xc0ce
cmpq %rbp, 0x10(%rbx)
jne 0xc2e4
movq 0x18(%rbx), %rdi
movslq 0x8(%rbx), %r12
movq -0x8(%rdi,%r12,8), %r14
cmpb $0x18, 0x30(%r14)
jne 0xc2e4
cmpb $0x0, 0x31(%r14)
jne 0xc2e4
cmpq %rbp, 0x10(%r14)
je 0xc5be
cmpb $0x18, %al
jne 0xc0ce
cmpl $0x2, 0x8(%rbx)
jne 0xc31c
movq 0x18(%rbx), %rcx
movq (%rcx), %rdi
cmpb $0x3, 0x30(%rdi)
jne 0xc31c
movq 0x6c72(%rip), %rdx      # 0x12f78
cmpq %rdx, 0x8(%rdi)
jne 0xc31c
cmpb $0x0, 0x31(%rdi)
jne 0xc31c
cmpq %r13, 0x10(%rbx)
je 0xc46b
cmpb $0x18, %al
jne 0xc0ce
cmpq %r13, 0x10(%rbx)
jne 0xc349
movq 0x18(%rbx), %rdi
movq (%rdi), %r14
cmpb $0x18, 0x30(%r14)
jne 0xc349
cmpb $0x0, 0x31(%r14)
jne 0xc349
cmpq %r13, 0x10(%r14)
je 0xc644
cmpb $0x18, %al
jne 0xc0ce
cmpq %r13, 0x10(%rbx)
jne 0xc0ce
movq 0x18(%rbx), %rdi
movslq 0x8(%rbx), %r12
movq -0x8(%rdi,%r12,8), %r14
cmpb $0x18, 0x30(%r14)
jne 0xc0ce
cmpb $0x0, 0x31(%r14)
jne 0xc0ce
cmpq %r13, 0x10(%r14)
jne 0xc0ce
movq %rbp, %r13
movslq 0x8(%r14), %r15
leaq (%r15,%r12), %rbp
leaq (%r15,%r12), %rax
decq %rax
movl %eax, 0x8(%rbx)
leaq -0x8(,%rbp,8), %rsi
callq 0x4400
movq %rax, 0x18(%rbx)
movq 0x20(%rbx), %rdi
movslq %ebp, %rax
leaq -0x10(,%rax,8), %rsi
callq 0x4400
movq %rax, 0x20(%rbx)
movq 0x18(%rbx), %rax
leaq (%rax,%r12,8), %rdi
addq $-0x8, %rdi
movq 0x18(%r14), %rsi
shlq $0x3, %r15
movq %r15, %rdx
callq 0x4440
cmpl $0x2, 0x8(%rbx)
movq 0x6b33(%rip), %rdx      # 0x12f20
jl 0xc408
xorl %eax, %eax
movq 0x20(%rbx), %rcx
movq %rdx, (%rcx,%rax,8)
incq %rax
movslq 0x8(%rbx), %rcx
decq %rcx
cmpq %rcx, %rax
jl 0xc3f1
movq 0x18(%r14), %rdi
callq 0x4580
movq 0x20(%r14), %rdi
callq 0x4580
movq (%r14), %rdi
callq 0x4580
movq %r13, %rbp
movq 0x6b94(%rip), %r13      # 0x12fc0
movq %r14, %rdi
callq 0x4580
jmp 0xc216
movslq 0x8(%r14), %r15
leal (%r12,%r15), %eax
decl %eax
movl %eax, 0x8(%rbx)
movslq %eax, %rsi
shlq $0x3, %rsi
callq 0x4400
movq %rax, 0x10(%rbx)
leaq (%rax,%r12,8), %rdi
addq $-0x8, %rdi
movq 0x10(%r14), %rsi
shlq $0x3, %r15
jmp 0xc505
movq 0x8(%rcx), %r14
callq 0x4588
movq 0x18(%rbx), %rdi
callq 0x4580
movq 0x20(%rbx), %rdi
callq 0x4580
movq (%rbx), %rdi
callq 0x4580
movq 0x30(%r14), %rax
movq %rax, 0x30(%rbx)
movups (%r14), %xmm0
movups 0x10(%r14), %xmm1
movups 0x20(%r14), %xmm2
movups %xmm2, 0x20(%rbx)
movups %xmm1, 0x10(%rbx)
movups %xmm0, (%rbx)
jmp 0xc42c
movq %rbp, %r13
movslq 0x8(%rbx), %rbp
movslq 0x8(%r14), %r15
leal (%r15,%rbp), %eax
decl %eax
movl %eax, 0x8(%rbx)
movslq %eax, %rsi
shlq $0x3, %rsi
callq 0x4400
movq %rax, %r12
movq %rax, 0x10(%rbx)
leaq (%rax,%r15,8), %rdi
leaq 0x8(%rax), %rsi
leaq -0x8(,%rbp,8), %rdx
movq %r13, %rbp
movq 0x6acb(%rip), %r13      # 0x12fc0
callq 0x4440
movq 0x10(%r14), %rsi
shlq $0x3, %r15
movq %r12, %rdi
movq %r15, %rdx
callq 0x4440
movq 0x10(%r14), %rdi
callq 0x4580
movq (%r14), %rdi
callq 0x4580
jmp 0xc42c
movslq 0x8(%rbx), %r12
movslq 0x8(%r14), %r15
leaq (%r15,%r12), %rbp
leaq (%r15,%r12), %rax
decq %rax
movl %eax, 0x8(%rbx)
leaq -0x8(,%rbp,8), %rsi
callq 0x4400
movq %rax, 0x18(%rbx)
movq 0x20(%rbx), %rdi
movslq %ebp, %rax
leaq -0x10(,%rax,8), %rsi
callq 0x4400
movq %rax, 0x20(%rbx)
movq 0x18(%rbx), %rsi
leaq (%rsi,%r15,8), %rdi
addq $0x8, %rsi
leaq -0x8(,%r12,8), %rdx
callq 0x4440
movq 0x18(%rbx), %rdi
movq 0x18(%r14), %rsi
shlq $0x3, %r15
movq %r15, %rdx
callq 0x4440
cmpl $0x2, 0x8(%rbx)
movq 0x6a36(%rip), %rdx      # 0x12fd0
jl 0xc6d6
xorl %eax, %eax
movq 0x20(%rbx), %rcx
movq %rdx, (%rcx,%rax,8)
incq %rax
movslq 0x8(%rbx), %rcx
decq %rcx
cmpq %rcx, %rax
jl 0xc5a2
jmp 0xc6d6
movslq 0x8(%r14), %r15
leaq (%r15,%r12), %rbp
leaq (%r15,%r12), %rax
decq %rax
movl %eax, 0x8(%rbx)
leaq -0x8(,%rbp,8), %rsi
callq 0x4400
movq %rax, 0x18(%rbx)
movq 0x20(%rbx), %rdi
movslq %ebp, %rax
leaq -0x10(,%rax,8), %rsi
callq 0x4400
movq %rax, 0x20(%rbx)
movq 0x18(%rbx), %rax
leaq (%rax,%r12,8), %rdi
addq $-0x8, %rdi
movq 0x18(%r14), %rsi
shlq $0x3, %r15
movq %r15, %rdx
callq 0x4440
cmpl $0x2, 0x8(%rbx)
movq 0x69b0(%rip), %rdx      # 0x12fd0
jl 0xc6d6
xorl %eax, %eax
movq 0x20(%rbx), %rcx
movq %rdx, (%rcx,%rax,8)
incq %rax
movslq 0x8(%rbx), %rcx
decq %rcx
cmpq %rcx, %rax
jl 0xc628
jmp 0xc6d6
movslq 0x8(%rbx), %r12
movslq 0x8(%r14), %r15
leaq (%r15,%r12), %rbp
leaq (%r15,%r12), %rax
decq %rax
movl %eax, 0x8(%rbx)
leaq -0x8(,%rbp,8), %rsi
callq 0x4400
movq %rax, 0x18(%rbx)
movq 0x20(%rbx), %rdi
movslq %ebp, %rax
leaq -0x10(,%rax,8), %rsi
callq 0x4400
movq %rax, 0x20(%rbx)
movq 0x18(%rbx), %rsi
leaq (%rsi,%r15,8), %rdi
addq $0x8, %rsi
leaq -0x8(,%r12,8), %rdx
callq 0x4440
movq 0x18(%rbx), %rdi
movq 0x18(%r14), %rsi
shlq $0x3, %r15
movq %r15, %rdx
callq 0x4440
cmpl $0x2, 0x8(%rbx)
movq 0x6865(%rip), %rdx      # 0x12f20
jl 0xc6d6
xorl %eax, %eax
movq 0x20(%rbx), %rcx
movq %rdx, (%rcx,%rax,8)
incq %rax
movslq 0x8(%rbx), %rcx
decq %rcx
cmpq %rcx, %rax
jl 0xc6bf
movq 0x18(%r14), %rdi
callq 0x4580
movq 0x20(%r14), %rdi
callq 0x4580
movq (%r14), %rdi
callq 0x4580
movq 0x68b1(%rip), %rbp      # 0x12fa8
jmp 0xc42c