// File: /workspace/github_c_makefile_star2_O0/vtereshkov[P]umka-lang/src/umka_decl.c
// Function: parseMapType
static const Type *parseMapType(Compiler *comp)
{
    lexEat(&comp->lex, TOK_MAP);
    lexEat(&comp->lex, TOK_LBRACKET);

    Type *type = typeAdd(&comp->types, &comp->blocks, TYPE_MAP);

    const Type *keyType = parseType(comp, NULL);
    if (!typeValidOperator(keyType, TOK_EQEQ))
        comp->error.handler(comp->error.context, "Map key type is not comparable");

    const Type *ptrKeyType = typeAddPtrTo(&comp->types, &comp->blocks, keyType);

    lexEat(&comp->lex, TOK_RBRACKET);

    const Type *itemType = parseTypeOrForwardType(comp);
    if (itemType->kind == TYPE_VOID)
        comp->error.handler(comp->error.context, "Map items cannot be void");

    const Type *ptrItemType = typeAddPtrTo(&comp->types, &comp->blocks, itemType);

    // The map base type is the Umka equivalent of MapNode
    Type *nodeType = typeAdd(&comp->types, &comp->blocks, TYPE_STRUCT);
    const Type *ptrNodeType = typeAddPtrTo(&comp->types, &comp->blocks, nodeType);

    typeAddField(&comp->types, nodeType, comp->intType, "#len");
    typeAddField(&comp->types, nodeType, ptrKeyType,    "#key");
    typeAddField(&comp->types, nodeType, ptrItemType,   "#data");
    typeAddField(&comp->types, nodeType, ptrNodeType,   "#left");
    typeAddField(&comp->types, nodeType, ptrNodeType,   "#right");

    type->base = nodeType;
    return type;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x40, %rsp
movq %rdi, -0x8(%rbp)
movq -0x8(%rbp), %rdi
addq $0x4ba8, %rdi           # imm = 0x4BA8
movl $0xe, %esi
callq 0x1b150
movq -0x8(%rbp), %rdi
addq $0x4ba8, %rdi           # imm = 0x4BA8
movl $0x3a, %esi
callq 0x1b150
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x8(%rbp), %rsi
addq $0x4220, %rsi           # imm = 0x4220
movl $0x15, %edx
callq 0x21950
movq %rax, -0x10(%rbp)
movq -0x8(%rbp), %rdi
xorl %eax, %eax
movl %eax, %esi
callq 0x9b80
movq %rax, -0x18(%rbp)
movq -0x18(%rbp), %rdi
movl $0x2e, %esi
callq 0x22a80
testb $0x1, %al
jne 0xa19e
movq -0x8(%rbp), %rax
movq 0x50f8(%rax), %rcx
movq -0x8(%rbp), %rax
movq 0x5118(%rax), %rdi
leaq 0x1ce0f5(%rip), %rsi    # 0x1d828f
movb $0x0, %al
callq *%rcx
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x8(%rbp), %rsi
addq $0x4220, %rsi           # imm = 0x4220
movq -0x18(%rbp), %rdx
callq 0x21fa0
movq %rax, -0x20(%rbp)
movq -0x8(%rbp), %rdi
addq $0x4ba8, %rdi           # imm = 0x4BA8
movl $0x3b, %esi
callq 0x1b150
movq -0x8(%rbp), %rdi
callq 0xb140
movq %rax, -0x28(%rbp)
movq -0x28(%rbp), %rax
cmpl $0x2, (%rax)
jne 0xa20d
movq -0x8(%rbp), %rax
movq 0x50f8(%rax), %rcx
movq -0x8(%rbp), %rax
movq 0x5118(%rax), %rdi
leaq 0x1ce0a5(%rip), %rsi    # 0x1d82ae
movb $0x0, %al
callq *%rcx
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x8(%rbp), %rsi
addq $0x4220, %rsi           # imm = 0x4220
movq -0x28(%rbp), %rdx
callq 0x21fa0
movq %rax, -0x30(%rbp)
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x8(%rbp), %rsi
addq $0x4220, %rsi           # imm = 0x4220
movl $0x16, %edx
callq 0x21950
movq %rax, -0x38(%rbp)
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x8(%rbp), %rsi
addq $0x4220, %rsi           # imm = 0x4220
movq -0x38(%rbp), %rdx
callq 0x21fa0
movq %rax, -0x40(%rbp)
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x38(%rbp), %rsi
movq -0x8(%rbp), %rax
movq 0x5240(%rax), %rdx
leaq 0x1ce02f(%rip), %rcx    # 0x1d82c7
callq 0x23070
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x38(%rbp), %rsi
movq -0x20(%rbp), %rdx
leaq 0x1ce015(%rip), %rcx    # 0x1d82cc
callq 0x23070
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x38(%rbp), %rsi
movq -0x30(%rbp), %rdx
leaq 0x1ca120(%rip), %rcx    # 0x1d43f6
callq 0x23070
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x38(%rbp), %rsi
movq -0x40(%rbp), %rdx
leaq 0x1cdfdc(%rip), %rcx    # 0x1d82d1
callq 0x23070
movq -0x8(%rbp), %rdi
addq $0x4e18, %rdi           # imm = 0x4E18
movq -0x38(%rbp), %rsi
movq -0x40(%rbp), %rdx
leaq 0x1cdfc3(%rip), %rcx    # 0x1d82d7
callq 0x23070
movq -0x38(%rbp), %rcx
movq -0x10(%rbp), %rax
movq %rcx, 0x8(%rax)
movq -0x10(%rbp), %rax
addq $0x40, %rsp
popq %rbp
retq
nop