Hi,
The following code works on Linux, Windows, MacOS and Solaris, but on an Android device, it can only return 127.0.0.1 even when ifconfig shows the WIFI address is available:
static struct addrinfo hint = {
0, // int ai_flags;
AF_INET, // int ai_family;
SOCK_DGRAM, // int ai_socktype;
IPPROTO_UDP, // int ai_protocol;
0, // size_t ai_addrlen;
NULL, // char* ai_canonname;
NULL, // struct sockaddr* ai_addr;
NULL // struct addrinfo* ai_next;
};
struct addrinfo *_info;
if (getaddrinfo(addr, port, &hint, &_info) != 0) {
syslog(LOG_ERR, "Cannot reach %s", addr);
return 0;
}
The 'port' value is fixed (e.g. 6084). I have tried passing 'addr' with the value from gethostname(), but getaddrinfo() always return one and only one item, which is 127.0.0.1. I think the problem is gethostname() returns 'localhost'. Is there another way to get the host name so that getaddrinfo() can return all addresses, including WIFI address?
Please don't suggest getting WIFI address from Java. I only like to know if bionic fully supports getaddrinfo() and can return WIFI address.
I think you're confused as to what getaddrinfo() does...
Gus,
Like I said, that same piece of code works on 4 other platforms and reliably return all possible local address of 'addr', and 'addr' comes from a call to gethostname().
Why don't we concentrate on gethostname() instead of getaddrinfo().
I believe on all 4 other platforms, gethostname() returns the local host name, which will resolve to all possible addresses, including multiple network cards, WIFI, PPP, VPN, etc.
The problem with Android is that gethostname() returns "localhost" instead of the host name. As an result, 'localhost' can only resolve into 127.0.0.1 and nothing else. See a similar thread with no definitive answer:
http://comments.gmane.org/gmane.comp.handhelds.android.ndk/11967
Why gethostname() only Android cannot return a host name other than 'localhost'?
By the way, I am porting an ICE implementation to Android that works on all 4 platforms mentioned above. I know what I am doing:
http://tools.ietf.connectedorg/html/rfc5245
On Sunday, June 3, 2012 9:12:35 PM UTC-7, Angus Lees wrote:
I think you're confused as to what getaddrinfo() does...
On Mon, Jun 4, 2012 at 1:32 PM, technicware wrote:
Hi,
The following code works on Linux, Windows, MacOS and Solaris, but on an Android device, it can only return 127.0.0.1 even when ifconfig shows the WIFI address is available:
static struct addrinfo hint = {
0, // int ai_flags;
AF_INET, // int ai_family;
SOCK_DGRAM, // int ai_socktype;
IPPROTO_UDP, // int ai_protocol;
0, // size_t ai_addrlen;
NULL, // char* ai_canonname;
NULL, // struct sockaddr* ai_addr;(You have canonname and addr around the wrong way, although it's harmless here)NULL // struct addrinfo* ai_next;
};
struct addrinfo *_info;
if (getaddrinfo(addr, port, &hint, &_info) != 0) {
syslog(LOG_ERR, "Cannot reach %s", addr);
return 0;
}
The 'port' value is fixed (e.g. 6084). I have tried passing 'addr' with the value from gethostname(), but getaddrinfo() always return one and only one item, which is 127.0.0.1. I think the problem is gethostname() returns 'localhost'. Is there another way to get the host name so that getaddrinfo() can return all addresses, including WIFI address?
Please don't suggest getting WIFI address from Java. I only like to know if bionic fully supports getaddrinfo() and can return WIFI address.getaddrinfo() works on Android - but isn't meant to return a list of local addresses, which is what you seem to be wanting. getaddrinfo() is used for finding a suitable end point (either active or passive end) for a socket connection. Indeed, if you wanted to connect to using IPv4 UDP to localhost port 6084 (this is what you're asking in your example above) then there is almost certainly only a single sockaddr answer required.To get the list of local addresses you either need to use ioctl(SIOCGIFADDR) (IPv4-only), or netlink (IPv4+IPv6, but Linux-specific) - or call into the Java functions which will hide that rather unpleasant code from you.
--You may also find that you don't actually want a list of all addresses, since some will probably be private or otherwise unusable for whatever you're trying to do. If you want something in particular then there may be some other way of getting the answer you really want. We'd need more context to help you there.p;- GusYou received this message because you are subscribed to the Google Groups "android-ndk" group.To view this discussion on the web visit https://groups.google.com/d/msg/android-ndk/-/5nJhRZ_e1SkJ.
To post to this group, send email to andro...@googlegroups.com.
To unsubscribe from this group, send email to android-ndk...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/android-ndk?hl=en.
2. The local resolver code (getaddrinfo, getnameinfo and their
traditional
IPv4 cousins) special cases the name returned be gethostname and
returns the locally available addresses without bothering the name
servers (or /etc/hosts) or allowing them to spoof, confuse or
otherwise
override information the local machine knows first hand.
I have previously seen this brokenness on a few old Linux distributions and possibly on
some UNIX variant (not to be named as I am not certain).
Hi,
I write 1 application to extract the IP address of a m/c. The application is given below:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <netdb.h>
#define HAVE_GETADDRINFO 1
int main(int argc,char **argv)
{
int z;
char buf[1056];
z = gethostname(buf,sizeof buf);
if ( z == -1 )
{
fprintf(stderr, "%s: gethostname(2)\n",
strerror(errno));
exit(1);
}
struct addrinfo *result = NULL;
struct addrinfo *result1= NULL;
struct addrinfo *ptr = NULL;
struct addrinfo *rp = NULL;
struct addrinfo hints;
int sfd, s;
memset(&hints, 0, sizeof(struct addrinfo));
hints.ai_family = AF_UNSPEC; /* Allow IPv4 or IPv6 */
hints.ai_socktype = SOCK_STREAM; /* Datagram socket */
hints.ai_flags= AI_ADDRCONFIG;
s = getaddrinfo(buf, "2345\0", &hints, &result);
for (rp = result; rp != NULL; rp = rp->ai_next)
{
printf("Addr\n");
char ipstr[INET6_ADDRSTRLEN];
void *addr;
char *ipver;
// get the pointer to the address itself,
// different fields in IPv4 and IPv6:
if (rp->ai_family == AF_INET) { // IPv4
struct sockaddr_in *ipv4 = (struct sockaddr_in *)rp->ai_addr;
addr = &(ipv4->sin_addr);
ipver = "IPv4";
} else { // IPv6
struct sockaddr_in6 *ipv6 = (struct sockaddr_in6 *)rp->ai_addr;
addr = &(ipv6->sin6_addr);
ipver = "IPv6";
}
// convert the IP to a string and print it:
inet_ntop(rp->ai_family, addr, ipstr, sizeof ipstr);
printf("%s: %s\n", ipver, ipstr);
//std::cout << " Val : " << INET6_ADDRSTRLEN << std::endl;
}
printf("host name = '%s'\n",buf);
return 0;
}
By using the application, proper addresses are not returned in newer version of solaris. I am always getting the link local address like - ::1 and 127.0.0.1.
But in older version of solaris, the application is working fine..
Any one can suggest to solve this type of issue in solaris 10/11.
Regards,
Prasun.
Edited by: 972649 on Nov 21, 2012 11:15
I want to extract the IP address of a m/c. Is there any other way?
--
You received this message because you are subscribed to the Google Groups "android-ndk" group.
To view this discussion on the web visit https://groups.google.com/d/msg/android-ndk/-/IX-g3al8nQkJ.