2

*(Socket programming)*C-code for client (passing messages through UDP) is given below. We can automatically assign port number to socket by

  1. not calling bind() before sendto() (related post)
  2. binding with port 0 (only provided in windows and solaris documentation for bind) that makes the kernel do automatic assignment.realted post

However doing the same with getaddrinfo() function,passing "0"(port number) as 2nd argument assigns port 0 to socket and not any USER_RESERVED port.

How to achieve automatic port assignment using getaddrinfo()?

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<arpa/inet.h>
#include<netdb.h>

int main(int argc,char *argv[])
{
    struct addrinfo client,*cl;
    int status;


    memset(&client,0,sizeof(client));//stucture should be empty

    client.ai_family=AF_INET;
    client.ai_socktype=SOCK_DGRAM;
    client.ai_flags=AI_PASSIVE;

    if(getaddrinfo(INADDR_ANY,"0",&client,&cl)!=0)
    {
        fprintf(stderr,"getaddrinfo: %s\n",gai_strerror(status));
        return 2;
    }

    int s;
    //printf("Port:: %d\n",((struct sockaddr_in*)(cl->ai_addr))->sin_port); //checking protocol number
    s=socket(cl->ai_family,cl->ai_socktype,cl->ai_protocol);
    //printf("Port:: %d\n",((struct sockaddr_in*)(cl->ai_addr))->sin_port); //checking protocol number

    //bind(s,cl->ai_addr,cl->ai_addrlen);
    //printf("Port:: %d\n",((struct sockaddr_in*)(cl->ai_addr))->sin_port); //checking protocol number

    struct sockaddr_in server;
    server.sin_family=AF_INET;
    inet_pton(AF_INET,argv[1],&(server.sin_addr));
    server.sin_port=htons(4169);
    char str[100];
    for(int i=2;i<argc;i++)
    {
        strncat(str,argv[i],strlen(argv[i]));
        str[strlen(str)]=' ';
    }

    sendto(s,str,strlen(str),0,(struct sockaddr *)&server,(socklen_t)sizeof(server));
    //printf("Port:: %d\n",((struct sockaddr_in*)(cl->ai_addr))->sin_port); //checking protocol number

    close(s);
}
onk101
  • 21
  • 4
  • `getaddrinfo` provides information about the intended destination, specified by the first two arguments. It plays absolutely no part in any local port assignment. – ottomeister Oct 14 '18 at 08:11
  • getaddrinfo provides information not just about the intended destination, but can also be used to populate struct addr_info for creating and binding sockets to ports. I have added link to the two methods i have mentioned in the question,none of them uses getaddrinfo(). @ottomeister – onk101 Oct 14 '18 at 15:01
  • When passing a numeric value in the `service` parameter, including `"0"`, you should be including the `AI_NUMERICSERV` flag. Also, the `node` parameter expects a null-terminated string. Passing `INADDR_ANY` works only because it is defined as `0` and `0` can be passed to a `char*` pointer. Documented behavior is to pass in `NULL` if you want the returned addresses to use `INADDR_ANY`. Don't use macros for purposes they are not intended for, and `INADDR_ANY` is not intended to be passed into `getaddrinfo()` like this – Remy Lebeau Oct 14 '18 at 18:14
  • The question says it's about client-side use. On the client side you typically only use `getaddrinfo` to obtain the server address, to be passed to a `sendto` or `connect` call. In any case, the reason you're getting a port value of zero in the `sockaddr` result is that that's what you're telling `getaddrinfo` to construct by passing it `"0"` as the second argument. The actual assignment of a port is made only by a later call (`bind`, `connect`, ...) that operates on the socket. That's the point when a port value of 0 is interpreted as "pick a port for me". – ottomeister Oct 15 '18 at 17:38
  • BTW, if the reason you're asking this question is that you want to know which port has been assigned, you can use `getsockname` to obtain that information after you've made the call that causes the port assignment to happen. – ottomeister Oct 15 '18 at 18:54

0 Answers0