void proc2(int *param1, char *param2);
void proc3(void *param1);
void proc5(void *param1, char param2[]);
void proc6(void *param1);
void proc7(void *param1);
void proc9(char *param1, int param2);
int proc10(FILE *param1);

// address: 0x4012e0
int main(int argc, char argv[][], char envp[][]) {
    unsigned int dl; 		// r10
    void *eax; 		// r24
    unsigned int edx; 		// r26
    int *esp; 		// r28
    int local0; 		// m[r28 - 44]
    void *local1; 		// m[r28 - 40]
    int *local22; 		// r24{78}
    unsigned int local3; 		// m[r28 - 101]
    unsigned int local34; 		// r26{191}
    void *local36; 		// r24{51}
    unsigned int local4; 		// m[r28 - 102]
    unsigned int local5; 		// m[r28 - 103]

    if (argc > 1) {
        local3 = 0;
        local4 = 0;
        local5 = 0;
        edx = 1;
        dl = 1;
        if (1 >= argc) {
L9:
            eax = *(argv + 4);
            proc2(&local0, eax);
            if (local3 == 0) {
                if (local4 == 0) {
                    proc7(&local0);
                } else {
                    eax = *(argv + *(unsigned char*)(esp - 103) * 4);
                    proc5(&local0, eax);
                }
            } else {
                proc3(&local0);
            }
            if (local1 != NULL) {
                proc6(local1);
            }
            *(int*)(esp - 100) = 1;
        } else {
            do {
                local36 = *(argv + edx * 4);
                if (*local36 == 45) {
                    if (*(local36 + 1) != 111) {
                        local22 = *(argv + edx * 4);
                        if (*(local22 + 1) == 120) {
                            local3 = 1;
                            goto L10;
                        }
                        goto L10;
                    }
                    local4 = 1;
                    local5 = dl + 1;
                    if ((int)(dl + 1) >= argc) {
                        puts("you have to add a filename to option -o\nlike: unpackkyra A_E.PAK -o ALGAE.CPS");
                        *(int*)(esp - 100) = 0;
                        goto L0;
                    }
                    edx++;
                    goto L10;
                }
L10:
                local34 = edx;
                edx = local34 + 1;
                dl = (unsigned char) local34 + 1;
            } while (local34 + 1 < argc);
            goto L9;
        }
    } else {
        eax = argv;
        printf("Use:\n%s filename [OPTIONS]\nHere are the options, default is listing files to stdout\n-o xxx   Extract only file 'xxx'\n-x       Extract all files\n", eax);
        *(int*)(esp - 100) = 0;
    }
L0:
    return *(esp - 100);
}

// address: 0x401530
void proc2(int *param1, char *param2) {
    FILE *eax; 		// r24
    void *esp; 		// r28
    char *local10; 		// r24{39}
    int local9; 		// r24{33}

    eax = fopen(param2, "rb");
    if (eax == NULL) {
        proc9("couldn't open file '%s'", param2);
    }
    *param1 = 1;
    local9 = proc10(eax);
    *(int*)(param1 + 8) = local9;
    local10 = malloc(local9);
    *(char **)(param1 + 4) = local10;
    if (local10 == NULL) {
        _assert("_buffer", "extract_kyra.cpp", 83);
    }
    fread(local10, local9, 1, eax);
    fclose(eax);
    return;
}

// address: 0x4017b0
void proc3(void *param1) {
    unsigned int eax; 		// r24
    unsigned int ebx; 		// r27
    unsigned char *ecx; 		// r25
    int *edi; 		// r31
    unsigned int edx; 		// r26
    int *esi; 		// r30
    int *esp; 		// r28
    unsigned int local11; 		// m[r28 - 24]
    int local12; 		// r25{49}
    int local13; 		// r25{177}
    int local14; 		// r25{54}
    int local15; 		// r25{183}
    FILE *local16; 		// r24{110}
    char *local17; 		// r24{128}
    int local21; 		// %pc{109}
    int *local23; 		// r30{168}
    unsigned int local24; 		// r24{78}
    int *local25; 		// r31{178}
    unsigned char *local26; 		// r25{16}
    int local27; 		// local13{177}
    int local28; 		// local15{183}
    int local29; 		// %pc{202}

    local26 = *(param1 + 4);
    edx = *(unsigned char*)(local26 + 3);
    eax = *(unsigned char*)(local26 + 2);
    edx = edx * 0x1000000 + eax * 0x10000;
    eax = *(unsigned char*)(local26 + 1);
    eax = edx + eax * 256 + *local26;
    local11 = eax;
    esi = local26 + 4;
    for(;;) {
        local23 = esi;
        edi = local23;
        local12 = -1;
        local27 = local12;
        do {
            local13 = local27;
            local25 = edi;
            local28 = local13;
            if (local13 == 0) {
                goto L11;
            }
            edi = local25 + 1;
            local14 = local13 - 1;
            local27 = local14;
            local28 = local14;
        } while (*local25 != 0);
L11:
        local15 = local28;
        if (*local23 == 0) {
            goto L0;
        }
        ecx = local23 +  !local15 - 1;
        edx = *(unsigned char*)(ecx + 4);
        eax = *(unsigned char*)(ecx + 3);
        edx = edx * 0x1000000 + eax * 0x10000;
        local24 = *(unsigned char*)(ecx + 2);
        eax = *(unsigned char*)(ecx + 1);
        ebx = edx + local24 * 256 + eax;
        if (*(param1 + 8) >= ebx) {
            if (ebx == 0) {
                ebx = *(param1 + 8);
                goto L6;
            }
        } else {
            ebx = *(param1 + 8);
        }
L6:
        esi = ecx + 5;
        local16 = fopen(local23, "wb");
        local29 = local21;
        if (local16 != NULL) {
            local17 = local11 + *(param1 + 4);
            fwrite(local17, ebx - local11, 1, local16);
            fclose(local16);
        }
        if (*(param1 + 8) == ebx) {
L0:
            return;
        }
        local11 = ebx;
    }
}

// address: 0x401696
void proc5(void *param1, char param2[]) {
    unsigned int eax; 		// r24
    int *ebx; 		// r27
    unsigned char *ecx; 		// r25
    int *edi; 		// r31
    unsigned int edx; 		// r26
    int *esi; 		// r30
    int *esp; 		// r28
    unsigned int local11; 		// m[r28 - 24]
    int local12; 		// r25{49}
    int local13; 		// r25{197}
    int local14; 		// r25{54}
    int local15; 		// r25{203}
    unsigned int local16; 		// r31{89}
    unsigned int local17; 		// r31{94}
    unsigned int local18; 		// r31{101}
    unsigned int local19; 		// r31{211}
    FILE *local20; 		// r24{122}
    char *local21; 		// r24{140}
    int *local25; 		// r27{186}
    unsigned int local26; 		// r24{78}
    int *local27; 		// r31{198}
    unsigned char *local28; 		// r25{16}
    int local29; 		// local13{197}
    int local30; 		// local15{203}
    unsigned int local31; 		// local19{211}

    local28 = *(param1 + 4);
    edx = *(unsigned char*)(local28 + 3);
    eax = *(unsigned char*)(local28 + 2);
    edx = edx * 0x1000000 + eax * 0x10000;
    eax = *(unsigned char*)(local28 + 1);
    eax = edx + eax * 256 + *local28;
    local11 = eax;
    ebx = local28 + 4;
    for(;;) {
        local25 = ebx;
        edi = local25;
        local12 = -1;
        local29 = local12;
        do {
            local13 = local29;
            local27 = edi;
            local30 = local13;
            if (local13 == 0) {
                goto L14;
            }
            edi = local27 + 1;
            local14 = local13 - 1;
            local29 = local14;
            local30 = local14;
        } while (*local27 != 0);
L14:
        local15 = local30;
        if (*local25 == 0) {
L1:
            printf("File '%s' not found in this pakfile\n", param2);
            goto L0;
        }
        ecx = local25 +  !local15 - 1;
        edx = *(unsigned char*)(ecx + 4);
        eax = *(unsigned char*)(ecx + 3);
        edx = edx * 0x1000000 + eax * 0x10000;
        local26 = *(unsigned char*)(ecx + 2);
        eax = *(unsigned char*)(ecx + 1);
        local16 = edx + local26 * 256 + eax;
        local31 = local16;
        if (*(param1 + 8) >= local16) {
            if (local16 == 0) {
                local18 = *(param1 + 8);
                local31 = local18;
                goto L9;
            }
        } else {
            local17 = *(param1 + 8);
            local31 = local17;
        }
L9:
        local19 = local31;
        ebx = ecx + 5;
        eax = strcmp(local25, param2);
        if (eax == 0) {
            break;
        }
        if (*(param1 + 8) == local19) {
            goto L1;
        }
        local11 = local19;
    }
    local20 = fopen(param2, "wb");
    if (local20 != NULL) {
        local21 = local11 + *(param1 + 4);
        fwrite(local21, local19 - local11, 1, local20);
        fclose(local20);
    }
L0:
    return;
}

// address: 0x4027e0
void proc6(void *param1) {
    void *esp; 		// r28

    if (param1 != NULL) {
        free(param1);
    }
    return;
}

// address: 0x4015d8
void proc7(void *param1) {
    unsigned int eax; 		// r24
    unsigned int ebx; 		// r27
    unsigned char *ecx; 		// r25
    int *edi; 		// r31
    unsigned int edx; 		// r26
    int *esi; 		// r30
    int *esp; 		// r28
    unsigned int local10; 		// m[r28 - 24]
    int local11; 		// r25{49}
    int local12; 		// r25{155}
    int local13; 		// r25{54}
    int local14; 		// r25{161}
    int *local16; 		// r30{146}
    unsigned int local17; 		// r24{87}
    int *local18; 		// r31{156}
    unsigned char *local19; 		// r25{16}
    int local20; 		// local12{155}
    int local21; 		// local14{161}

    local19 = *(param1 + 4);
    edx = *(unsigned char*)(local19 + 3);
    eax = *(unsigned char*)(local19 + 2);
    edx = edx * 0x1000000 + eax * 0x10000;
    eax = *(unsigned char*)(local19 + 1);
    eax = edx + eax * 256 + *local19;
    local10 = eax;
    esi = local19 + 4;
    for(;;) {
        local16 = esi;
        edi = local16;
        local11 = -1;
        local20 = local11;
        do {
            local12 = local20;
            local18 = edi;
            local21 = local12;
            if (local12 == 0) {
                goto L8;
            }
            edi = local18 + 1;
            local13 = local12 - 1;
            local20 = local13;
            local21 = local13;
        } while (*local18 != 0);
L8:
        local14 = local21;
        if (*local16 == 0) {
            break;
        }
        ecx = local16 +  !local14 - 1;
        edx = *(unsigned char*)(ecx + 4);
        eax = *(unsigned char*)(ecx + 3);
        edx = edx * 0x1000000 + eax * 0x10000;
        eax = *(unsigned char*)(ecx + 2);
        local17 = *(unsigned char*)(ecx + 1);
        ebx = edx + eax * 256 + local17;
        if (*(param1 + 8) >= ebx) {
            if (ebx == 0) {
                ebx = *(param1 + 8);
                goto L3;
            }
        } else {
            ebx = *(param1 + 8);
        }
L3:
        esi = ecx + 5;
        printf("Filename: %s size: %d\n", local16, ebx - local10);
        if (*(param1 + 8) == ebx) {
            break;
        }
        local10 = ebx;
    }
    return;
}

// address: 0x4018a0
void proc9(char *param1, int param2) {
    void *esp; 		// r28
    char local0[]; 		// m[r28 - 0x40c]

    _vsnprintf(&local0, 1024, param1, &param2);
    fprintf(*0x40d168 + 64, "ERROR: %s!\n", &local0);
    exit(1);
    return;
}

// address: 0x401bc1
int proc10(FILE *param1) {
    int eax; 		// r24
    void *esp; 		// r28
    int local9; 		// r24{15}

    local9 = ftell(param1);
    fseek(param1, 0, 2);
    eax = ftell(param1);
    fseek(param1, local9, 0);
    return eax;
}

