// This is a personal academic project. Dear PVS-Studio, please check it.
// PVS-Studio Static Code Analyzer for C, C++ and C#: http://www.viva64.com
#include "include/server.h"

int main(int argc, char *argv[]) {
    int fd;
    if ((fd = socket(AF_INET, SOCK_STREAM, 0)) == 0)
        printSystemError("Server: socket()");
       
    int opt = 1;
    if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt)))
        printSystemError("Server: setsockopt()");

    struct sockaddr_in address;
    setSockAddress(argc, argv, &address);
       
    if (bind(fd, (struct sockaddr *) &address, sizeof(address)) < 0) 
        printSystemError("Server: bind()");

    if (listen(fd, MAX_PEND_REQ) < 0)
        printSystemError("Server: listen()");

    int addrlen = sizeof(address), fdAux;
    if ((fdAux = accept(fd, (struct sockaddr *) &address, (socklen_t *) &addrlen)) < 0)
        printSystemError("Server: accept()");

    if (setvbuf(stdout, NULL, _IONBF, 0) != 0)
        printSystemError("Server: setvbuf()");

    startChallenge(fdAux);

    close(fdAux);
    close(fd);

    return EXIT_SUCCESS;
}

void startChallenge(int fd) {
    FILE * stream;
    if ((stream = fdopen(fd, "r")) == NULL)
        printSystemError("Server: fdopen()");
    
    int challengeCount = 0;
    char * output = NULL;

    while (challengeCount < MAX_CHALLENGES) {
        challenge_t currentChallenge = challenges[challengeCount];
        printf("\033[1;1H\033[2J");
        if (genChallenge(stream, &output, currentChallenge)) {
            challengeCount++;
        }
        else {
            printf("Respuesta incorrecta: %s\n", output);
            sleep(TIME_SLEEP);
        }
        free(output);
    }

    printf("\033[1;1H\033[2J");
    printf("Felicitaciones, finalizaron el juego. Ahora deberán implementar el servidor que se comporte como el servidor provisto\n");

    if (stream != NULL)
        fclose(stream);

    return;
}