// File: /workspace/github_c_makefile_star2_O0/oridb[P]mc/parse/infer.c
// Function: specialize
static void
specialize(void)
{
	Node *d, *n, *name;
	Type *ty, *it, *dt;
	size_t i;
	Trait *tr;

	for (i = 0; i < nimpldecl; i++) {
		d = impldecl[i];
		lappend(&file.stmts, &file.nstmts, d);
		typesub(d, 0);
	}

	for (i = 0; i < nspecializations; i++) {
		pushstab(specializationscope[i]);
		n = specializations[i];
		if (n->type == Nexpr && exprop(n) == Oauto) {
			tr = traittab[Tcdisp];
			assert(tr->nproto == 1);
			ty = exprtype(n);
			dt = mktyfunc(n->loc, NULL, 0, mktype(n->loc, Tyvoid));
			lappend(&dt->sub, &dt->nsub, ty);
			d = specializedcl(tr->proto[0], ty, dt, &name);
			htput(tr->proto[0]->decl.impls, ty, d);
		} else if (n->type == Nexpr && exprop(n) == Ovar) {
			d = specializedcl(genericdecls[i], n->expr.param, n->expr.type, &name);
			n->expr.args[0] = name;
			n->expr.did = d->decl.did;

			/* we need to sub in default types in the specialization, so call
			 * typesub on the specialized function */
			typesub(d, 0);
		} else if (n->type == Niterstmt) {
			tr = traittab[Tciter];
			assert(tr->nproto == 2);
			ty = exprtype(n->iterstmt.seq);
			if (ty->type == Typaram)
				goto enditer;

			it = itertype(n->iterstmt.seq, mktype(n->loc, Tybool));
			d = specializedcl(tr->proto[0], ty, it, &name);
			htput(tr->proto[0]->decl.impls, ty, d);

			it = itertype(n->iterstmt.seq, mktype(n->loc, Tyvoid));
			d = specializedcl(tr->proto[1], ty, it, &name);
			htput(tr->proto[1]->decl.impls, ty, d);
		} else {
			die("unknown node for specialization\n");
		}
enditer:
		popstab();
	}
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x60, %rsp
movq $0x0, -0x38(%rbp)
movq -0x38(%rbp), %rax
cmpq 0x56525(%rip), %rax     # 0x7d460
jae 0x26f84
movq 0x56514(%rip), %rax     # 0x7d458
movq -0x38(%rbp), %rcx
movq (%rax,%rcx,8), %rax
movq %rax, -0x8(%rbp)
movq -0x8(%rbp), %rdx
leaq 0x55e3d(%rip), %rsi     # 0x7cd98
movq %rsi, %rdi
addq $0x40, %rdi
addq $0x48, %rsi
callq 0x48290
movq -0x8(%rbp), %rdi
xorl %esi, %esi
callq 0x268f0
movq -0x38(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x38(%rbp)
jmp 0x26f30
movq $0x0, -0x38(%rbp)
movq -0x38(%rbp), %rax
cmpq 0x56499(%rip), %rax     # 0x7d430
jae 0x2729a
movq 0x56474(%rip), %rax     # 0x7d418
movq -0x38(%rbp), %rcx
movq (%rax,%rcx,8), %rdi
callq 0x32db0
movq 0x56470(%rip), %rax     # 0x7d428
movq -0x38(%rbp), %rcx
movq (%rax,%rcx,8), %rax
movq %rax, -0x10(%rbp)
movq -0x10(%rbp), %rax
cmpl $0x8, 0x8(%rax)
jne 0x270bc
movq -0x10(%rbp), %rdi
callq 0x2f210
cmpl $0x1, %eax
jne 0x270bc
leaq 0x56d25(%rip), %rax     # 0x7dd10
movq (%rax), %rax
movq 0x38(%rax), %rax
movq %rax, -0x40(%rbp)
movq -0x40(%rbp), %rax
cmpq $0x1, 0x38(%rax)
jne 0x27003
jmp 0x27022
leaq 0x2b971(%rip), %rdi     # 0x5297b
leaq 0x2b21f(%rip), %rsi     # 0x52230
movl $0xb06, %edx            # imm = 0xB06
leaq 0x2ba31(%rip), %rcx     # 0x52a4e
callq 0x6160
movq -0x10(%rbp), %rdi
callq 0x30340
movq %rax, -0x20(%rbp)
movq -0x10(%rbp), %rax
movq %rax, -0x48(%rbp)
movq -0x10(%rbp), %rax
movq (%rax), %rdi
movl $0x1, %esi
callq 0x36c10
movq %rax, %rcx
movq -0x48(%rbp), %rax
movq (%rax), %rdi
xorl %eax, %eax
movl %eax, %edx
movq %rdx, %rsi
callq 0x37520
movq %rax, -0x30(%rbp)
movq -0x30(%rbp), %rdi
addq $0x68, %rdi
movq -0x30(%rbp), %rsi
addq $0x70, %rsi
movq -0x20(%rbp), %rdx
callq 0x48290
movq -0x40(%rbp), %rax
movq 0x30(%rax), %rax
movq (%rax), %rdi
movq -0x20(%rbp), %rsi
movq -0x30(%rbp), %rdx
leaq -0x18(%rbp), %rcx
callq 0x31b80
movq %rax, -0x8(%rbp)
movq -0x40(%rbp), %rax
movq 0x30(%rax), %rax
movq (%rax), %rax
movq 0x48(%rax), %rdi
movq -0x20(%rbp), %rsi
movq -0x8(%rbp), %rdx
callq 0x49100
jmp 0x27282
movq -0x10(%rbp), %rax
cmpl $0x8, 0x8(%rax)
jne 0x2712f
movq -0x10(%rbp), %rdi
callq 0x2f210
cmpl $0x33, %eax
jne 0x2712f
movq 0x5635d(%rip), %rax     # 0x7d438
movq -0x38(%rbp), %rcx
movq (%rax,%rcx,8), %rdi
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rsi
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rdx
leaq -0x18(%rbp), %rcx
callq 0x31b80
movq %rax, -0x8(%rbp)
movq -0x18(%rbp), %rcx
movq -0x10(%rbp), %rax
movq 0x50(%rax), %rax
movq %rcx, (%rax)
movq -0x8(%rbp), %rax
movq 0x18(%rax), %rcx
movq -0x10(%rbp), %rax
movq %rcx, 0x38(%rax)
movq -0x8(%rbp), %rdi
xorl %esi, %esi
callq 0x268f0
jmp 0x27280
movq -0x10(%rbp), %rax
cmpl $0x4, 0x8(%rax)
jne 0x27270
leaq 0x56bcc(%rip), %rax     # 0x7dd10
movq (%rax), %rax
movq 0x30(%rax), %rax
movq %rax, -0x40(%rbp)
movq -0x40(%rbp), %rax
cmpq $0x2, 0x38(%rax)
jne 0x2715c
jmp 0x2717b
leaq 0x2b901(%rip), %rdi     # 0x52a64
leaq 0x2b0c6(%rip), %rsi     # 0x52230
movl $0xb16, %edx            # imm = 0xB16
leaq 0x2b8d8(%rip), %rcx     # 0x52a4e
callq 0x6160
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rdi
callq 0x30340
movq %rax, -0x20(%rbp)
movq -0x20(%rbp), %rax
cmpl $0x1a, (%rax)
jne 0x2719a
jmp 0x27284
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rax
movq %rax, -0x58(%rbp)
movq -0x10(%rbp), %rax
movq (%rax), %rdi
movl $0x2, %esi
callq 0x36c10
movq -0x58(%rbp), %rdi
movq %rax, %rsi
callq 0x2efc0
movq %rax, -0x28(%rbp)
movq -0x40(%rbp), %rax
movq 0x30(%rax), %rax
movq (%rax), %rdi
movq -0x20(%rbp), %rsi
movq -0x28(%rbp), %rdx
leaq -0x18(%rbp), %rcx
callq 0x31b80
movq %rax, -0x8(%rbp)
movq -0x40(%rbp), %rax
movq 0x30(%rax), %rax
movq (%rax), %rax
movq 0x48(%rax), %rdi
movq -0x20(%rbp), %rsi
movq -0x8(%rbp), %rdx
callq 0x49100
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rax
movq %rax, -0x50(%rbp)
movq -0x10(%rbp), %rax
movq (%rax), %rdi
movl $0x1, %esi
callq 0x36c10
movq -0x50(%rbp), %rdi
movq %rax, %rsi
callq 0x2efc0
movq %rax, -0x28(%rbp)
movq -0x40(%rbp), %rax
movq 0x30(%rax), %rax
movq 0x8(%rax), %rdi
movq -0x20(%rbp), %rsi
movq -0x28(%rbp), %rdx
leaq -0x18(%rbp), %rcx
callq 0x31b80
movq %rax, -0x8(%rbp)
movq -0x40(%rbp), %rax
movq 0x30(%rax), %rax
movq 0x8(%rax), %rax
movq 0x48(%rax), %rdi
movq -0x20(%rbp), %rsi
movq -0x8(%rbp), %rdx
callq 0x49100
jmp 0x2727e
leaq 0x2b7fd(%rip), %rdi     # 0x52a74
movb $0x0, %al
callq 0x1df20
jmp 0x27280
jmp 0x27282
jmp 0x27284
callq 0x32e20
movq -0x38(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x38(%rbp)
jmp 0x26f8c
addq $0x60, %rsp
popq %rbp
retq