user1809923
user1809923

Reputation: 1255

Getting sockaddr_in from CFDataRef

I have a CFDataRef (I am not even sure, why I use CFData and Socket anymore..) which contains a clients address (a struct sockaddr_in) and I need to get the IP and port. Unfortunately there are no direct methods to get them.

Hence I have tried the following:

CFDataRef clientAddress = ...; //defined somewhere else, contains a sockaddr_in
struct sockaddr_in clientAddress2;
clientAddress2 = *(struct sockaddr_in*)CFDataGetBytePtr(clientAddress);

(don't take the names to seriously, they are just for the purpose of this example). Unfortuantely the execution of CFDataGetBytePtr seems to crash, since I get a "EXC_BAD_ACCESS (code=2,address=0x0)" error, when running my app.

What is the best way to get the IP and Port from a CFDataRef containing a sockaddr_in?

Thank you!

Upvotes: 1

Views: 1903

Answers (1)

Francesco Germinara
Francesco Germinara

Reputation: 508

You can convert CFDataRef to NSData, than assign BYTES to structure sockaddr.

If the address could be IP6 or IP4 you check the INET FAMILY and than assign the BYTES to the correct structure (sockaddr_in for IP4 or sockaddr_in6 for IP6)

For example, assume that address is value of type CFDataRef address

    NSString *addressString;
    int port=0;
    struct sockaddr *addressGeneric;
    struct sockaddr_in addressClient;

    NSData *myData = (__bridge NSData *)address;
    addressGeneric = (struct sockaddr *) [myData bytes];

    switch( addressGeneric->sa_family ) {
        case AF_INET: {
          struct sockaddr_in *ip4;
          char dest[INET_ADDRSTRLEN];
          ip4 = (struct sockaddr_in *) [myData bytes];
          port = ntohs(ip4->sin_port);
          addressString = [NSString stringWithFormat: @"IP4: %s Port: %d", inet_ntop(AF_INET, &ip4->sin_addr, dest, sizeof dest),port];
         }
         break;

        case AF_INET6: {
            struct sockaddr_in6 *ip6;
            char dest[INET6_ADDRSTRLEN];
            ip6 = (struct sockaddr_in6 *) [myData bytes];
            port = ntohs(ip6->sin6_port);
            addressString = [NSString stringWithFormat: @"IP6: %s Port: %d",  inet_ntop(AF_INET6, &ip6->sin6_addr, dest, sizeof dest),port];
         }
         break;
       default:
         addressString=@"Error on get family type.";
         break;
     }

     NSLog(@"Client Address: %@",addressString);

This is the output

2013-08-25 12:22:35.308 FGWakeService[9283:303] Client Address: IP4: 192.168.69.38 Port: 58614

Upvotes: 3

Related Questions