Last active
April 16, 2017 15:39
-
-
Save dfukunaga/c3ca70c26d121e97c390243cd58571c9 to your computer and use it in GitHub Desktop.
get route source address
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <arpa/inet.h> | |
#include <netinet/in.h> | |
#include <stdio.h> | |
#include <string.h> | |
#include <sys/socket.h> | |
#include <string> | |
std::string get_src_addr_popen(const std::string& addr) { | |
// assemble command string | |
char command[64]; | |
snprintf(command, 64, "ip route get %s", addr.c_str()); | |
// execute command | |
FILE* fp = popen(command, "r"); | |
if (fp == NULL) { | |
return ""; // error | |
} | |
// get stdout of command | |
char buffer[64]; | |
if (fgets(buffer, 64, fp) == NULL) { | |
return ""; // error | |
} | |
buffer[strlen(buffer) - 1] = '\0'; // chomp '\n' | |
// get source address | |
char* pos = strstr(buffer, "src "); | |
if (pos == NULL) { | |
return ""; // error | |
} | |
pclose(fp); // close file pointer | |
return std::string(pos + 4); | |
} | |
std::string get_src_addr_socket(const std::string& addr) { | |
// create address structure | |
struct sockaddr_in sin; | |
socklen_t len = sizeof(sin); | |
// set address configurations | |
sin.sin_family = AF_INET; | |
inet_aton(addr.c_str(), &sin.sin_addr); | |
sin.sin_port = htons(0); | |
// create socket | |
int sockfd = socket(AF_INET, SOCK_DGRAM, 0); | |
if (sockfd == -1) { | |
return ""; // error | |
} | |
// connect socket | |
int rc_conn = connect(sockfd, (struct sockaddr*)&sin, sizeof(sin)); | |
if (rc_conn == -1) { | |
return ""; // error | |
} | |
// get local address | |
int rc_get = getsockname(sockfd, (struct sockaddr*)&sin, &len); | |
if (rc_get == -1) { | |
return ""; // error | |
} | |
return std::string(inet_ntoa(sin.sin_addr)); | |
} | |
#include <iostream> | |
int main(int argc, char** argv) { | |
std::cout << get_src_addr_popen(argv[1]) << std::endl; | |
std::cout << get_src_addr_socket(argv[1]) << std::endl; | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment