Nowe posty

Autor Wątek: I couldn't bind Xserver to the port: Address already in use  (Przeczytany 3747 razy)

  • Gość
Mój serwer (Xserver) już całkiem działa. Jednak po wyjściu z niego za pomocą control-c (mam obsłużony sygnał SIGINT), po ponownej próbie uruchomienia narzeka że port jest już zbindowany z czymś innym.

Cytuj
tomasz@tomasz-laptop:~/Dokumenty/c/xserver/bin/Debug$ ./xserver
Xserver is going up

Xserver is going to open socket
I couldn't bind Xserver to the port: Address already in use
Kod server'a:

#include 
#include
#include
#include
#include
#include
#include
#include

#define LINE_SIZE 256

ssize_t recv_line (int sockfd, void *buf, size_t len, int flags){
    int result = 0;
    int counter = 0;
    char ch = '\\0';
    do {

    result = recv (sockfd, &ch, 1, flags);
    strncpy (buf+counter, &ch, 1);
    counter += result;

    } while (result != 0 && ch != '\\x0A');
    memset (buf+counter, 0, 1);

    return (ssize_t)(counter-1);


}

    int sock = -1;
    int sock_peer = -1;

void signal_handler (int signum) {
    printf ("Kończę połączenie z klientem\\n\\n");
    close (sock_peer);
    printf ("Kończę zbindowanie z portem\\n\\n");
    close (sock);
    exit(EXIT_SUCCESS);
}

int main()
{

    /* char server_version[] = "0.0.1"; */
    int server_port = 7000;
    char banner[] = "Xserver 0.0.1\\n";
    struct sockaddr_in server;
    struct sockaddr_in peer;

    socklen_t sockaddr_len;
    int result = -1;
    char buffer[LINE_SIZE];

    signal (SIGINT, signal_handler);

    printf ("Xserver is going up\\n\\n");

    printf ("Xserver is going to open socket\\n");
    sock = socket (AF_INET, SOCK_STREAM, 0);

    if (sock == -1) {

        perror ("Xserver couldn't open socket\\n");
        printf ("Xserver is shut down\\n\\n");
        return 1;
        }

    memset (&server, 0, sizeof (server));
    server.sin_family = AF_INET;
    server.sin_port = htons(server_port);
    server.sin_addr.s_addr = htonl (INADDR_ANY);



    if (bind (sock, (struct sockaddr*)&server, sizeof (server)) == -1) {

        perror ("I couldn't bind Xserver to the port");
        return 2;

        }

    while (1) {

        if (listen (sock, 1) == -1) {

            perror ("I coulndn't listen to");
            return 3;

            }

        sockaddr_len = (socklen_t)sizeof (server);

        while (1) {

        if ((sock_peer = accept (sock, (struct sockaddr*)&peer, &sockaddr_len)) == -1) {

            perror ("I couldn't accept\\n");
            return 4;
            }

        printf ("I connected\\n");
        send (sock_peer, banner, strlen (banner), 0);

        while (1) {

        if ((result = recv_line (sock_peer, buffer, LINE_SIZE, 0)) == -1) {

            perror ("Nie mogę odczytać");
            break;
            }

        printf ("Oderbrano linię: %s", buffer);
        if (strcmp (buffer, "exit\\r\\n") == 0) {
            send (sock_peer, "Zamykam sesję\\n", 13, 0);
            close (sock_peer);
            break;
            } else {

            if (strcmp (buffer, "help") == 0) {
                send (sock_peer, "Bardzo użyteczna pomoc\\n", 23, 0);
                } else {

                /*
                Nic nie robie
                */

                }

            }

        }


        }



        }

    printf ("Xserver is going to close socket\\n");



    close (sock);

    printf ("Xserver is going down\\n\\n");
    return 0;
}
Co robię źle? Przecież zamknąłem wszystkie gniazda. Chyba nie ma jakiejś funkcji unbind?

jk33

  • Gość
I couldn't bind Xserver to the port: Address already in use
« Odpowiedź #1 dnia: 2010-09-18, 10:26:46 »
Słowa klucze:
1) TIME_WAIT
2) SO_REUSE

W skrócie: chodzi o to, że nie możesz się zbindować do gniazd protokołu tcp, na których niedawno były jakieś połączenia dopóki nie ma pewności, że wszystkie końce tych połączeń zostały zamknięte. Po odczekaniu kilku minut można swobodnie ponownie wykorzystać gniazda. Jeśli chcesz wcześniej -> wskazówka 2

pozdrawiam, Janek

  • Gość
I couldn't bind Xserver to the port: Address already in use
« Odpowiedź #2 dnia: 2010-09-18, 18:28:10 »
Chodzi o setsockopt?