int icmp_select_best_ip(char ip_list[][16], int ip_num, char *best_ip) { int sockfd = 0; struct timeval time_delay, min_time; struct sockaddr_in from_addr; char *cur_ip = NULL, *best = NULL, ip_str[16] = {'\0'}; int ip_idx = 0; if(!ip_list || !best_ip || ip_num <= 1) return -1; sockfd = icmp_socket(); if(sockfd < 0){ perror("socket error"); return sockfd; } min_time.tv_sec = 0x0FFFFFFF; min_time.tv_usec = 0x0FFFFFFF; while(1) { if(ip_idx >= ip_num) break; cur_ip = ip_list[ip_idx]; if(!cur_ip) break; select_best_ip(sockfd, cur_ip, &time_delay, &from_addr); printf("%s %ld %ld \n", cur_ip, time_delay.tv_sec, time_delay.tv_usec); if(tv_min(&time_delay, &min_time)){ memset(ip_str,0,sizeof(ip_str)); strncpy(ip_str, inet_ntoa(from_addr.sin_addr), strlen(inet_ntoa(from_addr.sin_addr))); best = ip_str; } ++ip_idx; } close(sockfd); if(best) strcpy(best_ip, best); else return -1; return 0; }
int main(int argc, char **argv) { char *prgName = NULL; int c; char *iface = NULL; if ( (prgName=strrchr(argv[0],'/')) ) prgName++; else prgName = argv[0]; while( (c = getopt(argc, argv, "i:h")) > 0) { switch(c) { case 'i': iface = optarg; break; case 'h': usage(prgName); return 1; break; } } if ( iface == NULL ) { usage(prgName); return 1; } /* open socket */ int fd = icmp_socket(iface); if ( fd == -1 ) return 1; /* send a router solicitation */ unsigned char buf[2048]; if ((c = send_ra_solicit(fd, buf))< 0 ) return 1; /* listen for router advertisement */ struct pollfd pollfd; pollfd.fd = fd; pollfd.events = POLLIN; pollfd.revents = 0; int rp = poll(&pollfd, 1, 2000); /* wait max 2 sec. */ if ( rp > 0 ) { /* print prefix on stdout */ char ans_data[4096]; struct iovec iov; struct msghdr msg; int cc; iov.iov_len = sizeof(ans_data); iov.iov_base = ans_data; memset(&msg, 0, sizeof(msg)); msg.msg_name = NULL; msg.msg_namelen = 0; msg.msg_iov = &iov; msg.msg_iovlen = 1; msg.msg_control = ans_data; msg.msg_controllen = sizeof(ans_data); cc = recvmsg(fd, &msg, MSG_DONTWAIT); if (cc < 0) { perror("recvmsg:"); return 1; } else { parse_reply(&msg, cc); } } else { return 1; } return 0; }