Line data Source code
1 : /* SPDX-License-Identifier: BSD-3-Clause 2 : * Copyright (C) 2021 Intel Corporation. All rights reserved. 3 : */ 4 : 5 : static int 6 28 : get_addr_str(struct sockaddr *sa, char *host, size_t hlen) 7 : { 8 28 : const char *result = NULL; 9 : 10 28 : if (sa == NULL || host == NULL) { 11 0 : return -1; 12 : } 13 : 14 28 : switch (sa->sa_family) { 15 28 : case AF_INET: 16 28 : result = inet_ntop(AF_INET, &(((struct sockaddr_in *)sa)->sin_addr), 17 : host, hlen); 18 28 : break; 19 0 : case AF_INET6: 20 0 : result = inet_ntop(AF_INET6, &(((struct sockaddr_in6 *)sa)->sin6_addr), 21 : host, hlen); 22 0 : break; 23 0 : default: 24 0 : break; 25 : } 26 : 27 28 : if (result != NULL) { 28 28 : return 0; 29 : } else { 30 0 : return -1; 31 : } 32 : } 33 : 34 : static bool 35 14 : sock_is_loopback(int fd) 36 : { 37 14 : struct ifaddrs *addrs, *tmp; 38 14 : struct sockaddr_storage sa = {}; 39 14 : socklen_t salen; 40 14 : struct ifreq ifr = {}; 41 14 : char ip_addr[256], ip_addr_tmp[256]; 42 : int rc; 43 14 : bool is_loopback = false; 44 : 45 14 : salen = sizeof(sa); 46 14 : rc = getsockname(fd, (struct sockaddr *)&sa, &salen); 47 14 : if (rc != 0) { 48 0 : return is_loopback; 49 : } 50 : 51 14 : memset(ip_addr, 0, sizeof(ip_addr)); 52 14 : rc = get_addr_str((struct sockaddr *)&sa, ip_addr, sizeof(ip_addr)); 53 14 : if (rc != 0) { 54 0 : return is_loopback; 55 : } 56 : 57 14 : getifaddrs(&addrs); 58 42 : for (tmp = addrs; tmp != NULL; tmp = tmp->ifa_next) { 59 42 : if (tmp->ifa_addr && (tmp->ifa_flags & IFF_UP) && 60 42 : (tmp->ifa_addr->sa_family == sa.ss_family)) { 61 14 : memset(ip_addr_tmp, 0, sizeof(ip_addr_tmp)); 62 14 : rc = get_addr_str(tmp->ifa_addr, ip_addr_tmp, sizeof(ip_addr_tmp)); 63 14 : if (rc != 0) { 64 0 : continue; 65 : } 66 : 67 14 : if (strncmp(ip_addr, ip_addr_tmp, sizeof(ip_addr)) == 0) { 68 14 : memcpy(ifr.ifr_name, tmp->ifa_name, sizeof(ifr.ifr_name)); 69 14 : ioctl(fd, SIOCGIFFLAGS, &ifr); 70 14 : if (ifr.ifr_flags & IFF_LOOPBACK) { 71 14 : is_loopback = true; 72 : } 73 14 : goto end; 74 : } 75 : } 76 : } 77 : 78 14 : end: 79 14 : freeifaddrs(addrs); 80 14 : return is_loopback; 81 : }