Brian
Brian

Reputation: 7316

UDP Socket - Server hanging on recvfrom

I am attempting to implement a client-server network. I am following Beej's Guide to Network Programming

My program scans an input from the keyboard, looks up the associated value in an array then sends a GET request to my server via UDP. However, it appears that my server is not receiving my request.

This is my client code excerpt:

    // loop through all the results and make a socket
for(p = servinfo; p != NULL; p = p->ai_next) {
    if ((sockfd = socket(p->ai_family, p->ai_socktype,
            p->ai_protocol)) == -1) {
        perror("talker: socket");
        continue;
    }

    break;
}

if (p == NULL) {
    fprintf(stderr, "talker: failed to bind socket\n");
    return 2;
}

printf("Please Enter Your Search (USC, UCLA etc.):");
char searchKey[5];
fgets(searchKey, sizeof(searchKey), stdin);
int len, bytes_sent;
char value[8];
len = strlen(value);
char request[10];
for(int i = 0; i < sizeof(clientMap) / sizeof(struct Mapping); i++) {
  if (strcmp(clientMap[i].key, searchKey) == 0) {
    //value = clientMap[i].value;
    memcpy(value, clientMap[i].value, sizeof(char) * 6);
    strcat(request, "GET ");
    strcat(request, value);
    break;
  }
}
printf("The Client 1 has received a request with search word %s, which maps to key %s\n", searchKey, value);
printf("The Client 1 sends the request %s to the Server 1 with port number %s and IP address %s\n", request, SERVERPORT, argv[1]);
printf("The Client1's port number is TODO and the IP address is TODO\n");
if ((numbytes = sendto(sockfd, request, strlen(request), 0,
         p->ai_addr, p->ai_addrlen)) == -1) {
    perror("talker: sendto");
    exit(1);
}

freeaddrinfo(servinfo);

printf("talker: sent %d bytes to %s\n", numbytes, argv[1]);

This is my server excerpt:

// loop through all the results and bind to the first we can
for(p = servinfo; p != NULL; p = p->ai_next) {
    if ((sockfd = socket(p->ai_family, p->ai_socktype,
            p->ai_protocol)) == -1) {
        perror("listener: socket");
        continue;
    }

    if (bind(sockfd, p->ai_addr, p->ai_addrlen) == -1) {
        close(sockfd);
        perror("listener: bind");
        continue;
    }

    break;
}

if (p == NULL) {
    fprintf(stderr, "listener: failed to bind socket\n");
    return 2;
}

freeaddrinfo(servinfo);

printf("listener: waiting to recvfrom...\n");

addr_len = sizeof their_addr;
if ((numbytes = recvfrom(sockfd, buf, MAXBUFLEN-1 , 0,
    (struct sockaddr *)&their_addr, &addr_len)) == -1) {
    perror("recvfrom");
    exit(1);
}

buf[numbytes] = '\0';
printf("The Server 1 has received a request with key %s\n", buf);
for(int i = 0; i < sizeof(serverMap) / sizeof(struct Mapping); i++) {
  if (strcmp(serverMap[i].key, buf) == 0) {
    char post[13];
    strcpy(post, "POST ");
    strcat(post, serverMap[i].value);
    printf("The Server 1 sends the reply %s to TODO: Finish this!", post);
    sendto(sockfd, post, strlen(post), 0, (struct sockaddr *)&their_addr, addr_len);
    break;
  }
}
close(sockfd);

I know that the problem is that my server is not receiving the datagram. I imagine I am making some obviously easy mistake, but my understanding of C and Networks is not so strong.

On a side note, you may notice that my print statements contain TODOs. I am unsure how to grab these IP addresses and port numbers. Can someone also help with this?

Upvotes: 0

Views: 2256

Answers (1)

Philip Stuyck
Philip Stuyck

Reputation: 7447

Your server needs anyhow a fixed port to listen on. How are you going to expect your client to know to which port it is supposed to send ? Just use an arbitrary port on both the server and the client.

Since you are new at this, try everything locally at first. The server should listen to INADDR_ANY and the arbitrary port that you choose.

Upvotes: 1

Related Questions