// File: /workspace/github_c_makefile_star2_O2/Ziddykins[P]Dawn/src/spells.c
// Function: cast_fireball
void cast_fireball(const char *username, const char *target) {
    int pindex = get_pindex(username);
    int tindex = get_pindex(target);
    char out[MAX_MESSAGE_BUFFER];

    if (tindex == -1) {
        snprintf(out, MAX_MESSAGE_BUFFER, "PRIVMSG %s :Invalid target\r\n", dawn->active_room);
        add_msg(out, strlen(out));
        return;
    }

    if (!dawn->players[pindex].spellbook.fireball.learned) {
        snprintf(out, MAX_MESSAGE_BUFFER, "PRIVMSG %s :%s, you do not know this spell\r\n",
                 dawn->active_room, username);
        add_msg(out, strlen(out));
        return;
    }

    if (dawn->players[tindex].health <= 0) {
        snprintf(out, MAX_MESSAGE_BUFFER, "PRIVMSG %s :%s, %s is dead\r\n",
                 dawn->active_room, username, target);
        add_msg(out, strlen(out));
        return;
    }

    if (dawn->players[pindex].level >= dawn->players[tindex].level * 3) {
        snprintf(out, MAX_MESSAGE_BUFFER, "PRIVMSG %s :%s, pick on someone your own size!\r\n",
                 dawn->active_room, username);
        add_msg(out, strlen(out));
        return;
    }

    if (strcmp(username, target) == 0) {
        snprintf(out, MAX_MESSAGE_BUFFER, "PRIVMSG %s :%s whips a fireball at a mirror; it bounces back"
                ", hitting themselves for 1 point of damage. Well done.\r\n", dawn->active_room, username);
        dawn->players[pindex].health--;
        add_msg(out, strlen(out));
        return;
    }

    int fireball_cost = 1 + dawn->players[pindex].spellbook.fireball.level * 7;
    int fireball_damage =
            1 + rand() % dawn->players[pindex].intelligence * dawn->players[pindex].spellbook.fireball.level;

    if (dawn->players[pindex].mana >= fireball_cost) {
        int target_save = 1 + rand() % dawn->players[tindex].m_def;
        char result[128];
        dawn->players[pindex].mana -= fireball_cost;
        snprintf(out, MAX_MESSAGE_BUFFER, "PRIVMSG %s :%s hurls a fireball at %s! ",
                 dawn->active_room, username, target);
        if (target_save == fireball_damage) {
            snprintf(result, 128, "%s's shields had just enough energy to absorb the entire fireball!\r\n", target);
        } else if (target_save < fireball_damage) {
            struct Message tmpmsg;
            strcpy(tmpmsg.sender_nick, target);
            strcpy(tmpmsg.receiver, dawn->active_room);
            snprintf(result, 128, "%s is hit for %d damage!\r\n", target, fireball_damage - target_save);
            dawn->players[tindex].health -= fireball_damage - target_save;
            check_alive(&tmpmsg);
        } else if (target_save > fireball_damage) {
            snprintf(result, 128, "%s swats the fireball out of the sky with ease\r\n", target);
        }
        strncat(out, result, MAX_MESSAGE_BUFFER - strlen(result));
    }
    add_msg(out, strlen(out));
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0xb28, %rsp            # imm = 0xB28
movq %rsi, %rbx
movq %rdi, %r14
callq 0xc860
movl %eax, %ebp
movq %rbx, %rdi
callq 0xc860
leaq 0x1215d(%rip), %rcx     # 0x1fa80
movq (%rcx), %r15
cmpl $-0x1, %eax
je 0xda4f
movslq %ebp, %rcx
imulq $0x26a8, %rcx, %rbp     # imm = 0x26A8
cmpl $0x0, 0x1320(%r15,%rbp)
je 0xda76
leaq 0x1a0(%r15), %rcx
cltq
imulq $0x26a8, %rax, %r13     # imm = 0x26A8
cmpq $0x0, 0x2650(%rcx,%r13)
jle 0xda86
leaq (%r15,%rbp), %r12
addq $0x1a0, %r12            # imm = 0x1A0
addq %r13, %rcx
imull $0x3, 0x2668(%rcx), %eax
cmpl %eax, 0x2668(%r12)
jge 0xdab3
movq %r14, %rdi
movq %rbx, %rsi
callq 0x22e0
testl %eax, %eax
je 0xdb08
imull $0x7, 0x1178(%r12), %r15d
callq 0x2080
leaq 0x120ce(%rip), %r12     # 0x1fa80
movq (%r12), %rcx
cltd
idivl 0x2828(%rcx,%rbp)
cmpl %r15d, 0x2820(%rcx,%rbp)
jle 0xdadb
imull 0x1318(%rcx,%rbp), %edx
movl %edx, 0xc(%rsp)
notl %r15d
callq 0x2080
movq (%r12), %rcx
cltd
idivl 0x2830(%rcx,%r13)
movl %edx, 0x8(%rsp)
addl %r15d, 0x2820(%rcx,%rbp)
addq $0x100, %rcx            # imm = 0x100
leaq 0x965d(%rip), %rdx      # 0x17064
leaq 0x90(%rsp), %rdi
movl $0x190, %esi            # imm = 0x190
movq %r14, %r8
movq %rbx, %r9
xorl %eax, %eax
callq 0x23a0
movl 0xc(%rsp), %ebp
subl 0x8(%rsp), %ebp
jne 0xdb44
leaq 0x9656(%rip), %rdx      # 0x1708c
leaq 0x10(%rsp), %rdi
movl $0x80, %esi
movq %rbx, %rcx
xorl %eax, %eax
callq 0x23a0
jmp 0xdbb9
addq $0x100, %r15            # imm = 0x100
leaq 0x932b(%rip), %rdx      # 0x16d88
leaq 0x90(%rsp), %rdi
movl $0x190, %esi            # imm = 0x190
movq %r15, %rcx
xorl %eax, %eax
callq 0x23a0
jmp 0xdadb
addq $0x100, %r15            # imm = 0x100
leaq 0x932f(%rip), %rdx      # 0x16db3
jmp 0xdac1
addq $0x100, %r15            # imm = 0x100
leaq 0x950d(%rip), %rdx      # 0x16fa1
leaq 0x90(%rsp), %rdi
movl $0x190, %esi            # imm = 0x190
movq %r15, %rcx
movq %r14, %r8
movq %rbx, %r9
xorl %eax, %eax
callq 0x23a0
jmp 0xdadb
addq $0x100, %r15            # imm = 0x100
leaq 0x94fd(%rip), %rdx      # 0x16fbe
leaq 0x90(%rsp), %rdi
movl $0x190, %esi            # imm = 0x190
movq %r15, %rcx
movq %r14, %r8
xorl %eax, %eax
callq 0x23a0
leaq 0x90(%rsp), %rbx
movq %rbx, %rdi
callq 0x20c0
movq %rbx, %rdi
movq %rax, %rsi
callq 0xbd04
addq $0xb28, %rsp            # imm = 0xB28
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
addq $0x100, %r15            # imm = 0x100
leaq 0x94d9(%rip), %rdx      # 0x16fef
leaq 0x90(%rsp), %rdi
movl $0x190, %esi            # imm = 0x190
movq %r15, %rcx
movq %r14, %r8
xorl %eax, %eax
callq 0x23a0
leaq 0x11f49(%rip), %rax     # 0x1fa80
movq (%rax), %rax
decq 0x27f0(%rax,%rbp)
jmp 0xdadb
jle 0xdbab
leaq 0x228(%rsp), %r14
movq %r14, %rdi
movq %rbx, %rsi
callq 0x21c0
leaq 0x2e8(%rsp), %rdi
movl $0x100, %esi            # imm = 0x100
leaq 0x11f13(%rip), %r15     # 0x1fa80
addq (%r15), %rsi
callq 0x21c0
leaq 0x9555(%rip), %rdx      # 0x170d1
leaq 0x10(%rsp), %rdi
movl $0x80, %esi
movq %rbx, %rcx
movl %ebp, %r8d
xorl %eax, %eax
callq 0x23a0
movslq %ebp, %rax
movq (%r15), %rcx
subq %rax, 0x27f0(%rcx,%r13)
movq %r14, %rdi
callq 0x3824
jmp 0xdbb9
jge 0xdbb9
leaq 0x9538(%rip), %rdx      # 0x170ec
jmp 0xda36
leaq 0x10(%rsp), %rbx
movq %rbx, %rdi
callq 0x20c0
movl $0x190, %edx            # imm = 0x190
subq %rax, %rdx
leaq 0x90(%rsp), %rdi
movq %rbx, %rsi
callq 0x2120
jmp 0xdadb