ifconfig.c revision 54a1eb7677a10c1591ba48562ae480cd71721bf6
1dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 2dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <stdio.h> 3dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <stdlib.h> 4dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <unistd.h> 5dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 6dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <errno.h> 7dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <string.h> 8dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <ctype.h> 9dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 10dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <sys/socket.h> 11dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <netinet/in.h> 12dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <linux/if.h> 13dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <linux/sockios.h> 14dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <arpa/inet.h> 15dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 16dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic void die(const char *s) 17dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 18dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr,"error: %s (%s)\n", s, strerror(errno)); 19dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project exit(-1); 20dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 21dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 22dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic void setflags(int s, struct ifreq *ifr, int set, int clr) 23dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 24dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if(ioctl(s, SIOCGIFFLAGS, ifr) < 0) die("SIOCGIFFLAGS"); 25dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ifr->ifr_flags = (ifr->ifr_flags & (~clr)) | set; 26dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if(ioctl(s, SIOCSIFFLAGS, ifr) < 0) die("SIOCSIFFLAGS"); 27dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 28dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 29dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic inline void init_sockaddr_in(struct sockaddr_in *sin, const char *addr) 30dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 3154a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat sin->sin_family = AF_INET; 3254a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat sin->sin_port = 0; 3354a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat sin->sin_addr.s_addr = inet_addr(addr); 34dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 35dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 3654a1eb7677a10c1591ba48562ae480cd71721bf6San Mehatstatic void setmtu(int s, struct ifreq *ifr, const char *mtu) 3754a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat{ 3854a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat int m = atoi(mtu); 3954a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat ifr->ifr_mtu = m; 4054a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat if(ioctl(s, SIOCSIFMTU, ifr) < 0) die("SIOCSIFMTU"); 4154a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat} 42fa49e2860bebe6bb2a26194c58992e5d5aed0b0dSan Mehatstatic void setdstaddr(int s, struct ifreq *ifr, const char *addr) 43fa49e2860bebe6bb2a26194c58992e5d5aed0b0dSan Mehat{ 4454a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat init_sockaddr_in((struct sockaddr_in *) &ifr->ifr_dstaddr, addr); 45fa49e2860bebe6bb2a26194c58992e5d5aed0b0dSan Mehat if(ioctl(s, SIOCSIFDSTADDR, ifr) < 0) die("SIOCSIFDSTADDR"); 46fa49e2860bebe6bb2a26194c58992e5d5aed0b0dSan Mehat} 47fa49e2860bebe6bb2a26194c58992e5d5aed0b0dSan Mehat 48dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic void setnetmask(int s, struct ifreq *ifr, const char *addr) 49dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 5054a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat init_sockaddr_in((struct sockaddr_in *) &ifr->ifr_netmask, addr); 51dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if(ioctl(s, SIOCSIFNETMASK, ifr) < 0) die("SIOCSIFNETMASK"); 52dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 53dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 54dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic void setaddr(int s, struct ifreq *ifr, const char *addr) 55dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 5654a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat init_sockaddr_in((struct sockaddr_in *) &ifr->ifr_addr, addr); 57dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if(ioctl(s, SIOCSIFADDR, ifr) < 0) die("SIOCSIFADDR"); 58dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 59dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 60dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectint ifconfig_main(int argc, char *argv[]) 61dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 62dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project struct ifreq ifr; 63dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int s; 64dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project unsigned int addr, mask, flags; 65dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char astring[20]; 66dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char mstring[20]; 67dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char *updown, *brdcst, *loopbk, *ppp, *running, *multi; 68dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 69dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project argc--; 70dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project argv++; 71dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 72dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if(argc == 0) return 0; 73dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 74dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project memset(&ifr, 0, sizeof(struct ifreq)); 75dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project strncpy(ifr.ifr_name, argv[0], IFNAMSIZ); 76dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ifr.ifr_name[IFNAMSIZ-1] = 0; 77dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project argc--, argv++; 78dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 79dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) { 80dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project die("cannot open control socket\n"); 81dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 82dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 83dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (argc == 0) { 84dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (ioctl(s, SIOCGIFADDR, &ifr) < 0) { 85dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project perror(ifr.ifr_name); 86dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 87dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else 88dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project addr = ((struct sockaddr_in *)&ifr.ifr_addr)->sin_addr.s_addr; 89dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 90dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (ioctl(s, SIOCGIFNETMASK, &ifr) < 0) { 91dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project perror(ifr.ifr_name); 92dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 93dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else 94dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project mask = ((struct sockaddr_in *)&ifr.ifr_addr)->sin_addr.s_addr; 95dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 96dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (ioctl(s, SIOCGIFFLAGS, &ifr) < 0) { 97dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project perror(ifr.ifr_name); 98dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 99dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else 100dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project flags = ifr.ifr_flags; 101dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 102dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project sprintf(astring, "%d.%d.%d.%d", 103dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project addr & 0xff, 104dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ((addr >> 8) & 0xff), 105dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ((addr >> 16) & 0xff), 106dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ((addr >> 24) & 0xff)); 107dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project sprintf(mstring, "%d.%d.%d.%d", 108dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project mask & 0xff, 109dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ((mask >> 8) & 0xff), 110dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ((mask >> 16) & 0xff), 111dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ((mask >> 24) & 0xff)); 112dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project printf("%s: ip %s mask %s flags [", ifr.ifr_name, 113dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project astring, 114dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project mstring 115dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ); 116dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 117dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project updown = (flags & IFF_UP) ? "up" : "down"; 118dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project brdcst = (flags & IFF_BROADCAST) ? " broadcast" : ""; 119dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project loopbk = (flags & IFF_LOOPBACK) ? " loopback" : ""; 120dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ppp = (flags & IFF_POINTOPOINT) ? " point-to-point" : ""; 121dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project running = (flags & IFF_RUNNING) ? " running" : ""; 122dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project multi = (flags & IFF_MULTICAST) ? " multicast" : ""; 123dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project printf("%s%s%s%s%s%s]\n", updown, brdcst, loopbk, ppp, running, multi); 124dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return 0; 125dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 126dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 12754a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat while(argc > 0) { 12854a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat if (!strcmp(argv[0], "up")) { 129dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project setflags(s, &ifr, IFF_UP, 0); 13054a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } else if (!strcmp(argv[0], "mtu")) { 13154a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat argc--, argv++; 13254a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat if (!argc) { 13354a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat errno = EINVAL; 13454a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat die("expecting a value for parameter \"mtu\""); 13554a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } 13654a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat setmtu(s, &ifr, argv[0]); 13754a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } else if (!strcmp(argv[0], "-pointopoint")) { 138fa49e2860bebe6bb2a26194c58992e5d5aed0b0dSan Mehat setflags(s, &ifr, IFF_POINTOPOINT, 1); 13954a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } else if (!strcmp(argv[0], "pointopoint")) { 14054a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat argc--, argv++; 14154a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat if (!argc) { 14254a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat errno = EINVAL; 14354a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat die("expecting an IP address for parameter \"pointtopoint\""); 14454a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } 14554a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat setdstaddr(s, &ifr, argv[0]); 14654a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat setflags(s, &ifr, IFF_POINTOPOINT, 0); 14754a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } else if (!strcmp(argv[0], "down")) { 148dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project setflags(s, &ifr, 0, IFF_UP); 14954a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } else if (!strcmp(argv[0], "netmask")) { 15054a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat argc--, argv++; 15154a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat if (!argc) { 15254a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat errno = EINVAL; 15354a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat die("expecting an IP address for parameter \"netmask\""); 15454a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } 15554a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat setnetmask(s, &ifr, argv[0]); 15654a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat } else if (isdigit(argv[0][0])) { 157dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project setaddr(s, &ifr, argv[0]); 15854a1eb7677a10c1591ba48562ae480cd71721bf6San Mehat setflags(s, &ifr, IFF_UP, 0); 159dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 160dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project argc--, argv++; 161dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 162dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return 0; 163dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 164