⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ifconf.c

📁 实现linux的网卡的ip地址、掩码、默认路由的查询和修改程序
💻 C
字号:
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <netinet/in.h>
#include <unistd.h>
#include <string.h>
#include <arpa/inet.h>
#include <net/if.h>
#include <errno.h>
#include <features.h>
#include <netpacket/packet.h>
#include <net/ethernet.h>
#include <net/route.h>
#include <stdio.h>

#define   FAILURE   0
#define   SUCCESS   1
typedef unsigned char           UNS8; /* 8-bit */
typedef unsigned short          UNS16;  /* 16-bit */
typedef unsigned int            UNS32;  /* 32-bit */ 
typedef unsigned long long int  UNS64;  /* 64-bit */
typedef char                    S8;   /* 8-bit */
typedef short                   S16;  /* 16-bit */
typedef int                     S32;  /* 32-bit */ 
typedef long long int           S64;  /* 64-bit */
typedef enum {
    FALSE,
    TRUE
} BOOL;
#define m_MSG(format, args...)  printf(format, ## args)
#define m_ERROR(terminal,format, args...)  fprintf(terminal,format, ## args)
#define m_DEBUG(format, args...)  printf(format, ## args)


typedef struct _rt {
    UNS32 dst;
    UNS32 mask;
    UNS32 gw;
    S32   flags;
}RT;
S32 setDefaultRoute( S32 fd, S8 *interface, UNS32 *route_addr )
{
    struct  rtentry     rtent;
    struct  sockaddr_in *p;

    memset( &rtent,0,sizeof( struct rtentry ) );
    p = ( struct sockaddr_in * ) &rtent.rt_dst;
    p->sin_family = AF_INET;
    p->sin_addr.s_addr = 0;
    p = ( struct sockaddr_in * ) &rtent.rt_gateway;
    p->sin_family = AF_INET;
    p->sin_addr.s_addr = *route_addr;
    p = ( struct sockaddr_in * ) &rtent.rt_genmask;
    p->sin_family = AF_INET;
    p->sin_addr.s_addr = 0;

    rtent.rt_dev = interface;

    rtent.rt_metric = 1;
    rtent.rt_window = 0;
    rtent.rt_flags = RTF_UP | RTF_GATEWAY;
    if ( ioctl( fd,SIOCADDRT,&rtent ) == -1 ) {
        if ( errno == ENETUNREACH )    /* possibly gateway is over the bridge */ {
            /* try adding a route to gateway first */
            memset( &rtent,0,sizeof( struct rtentry ) );
            p = ( struct sockaddr_in * ) &rtent.rt_dst;
            p->sin_family = AF_INET;
            p->sin_addr.s_addr = *route_addr;
            p = ( struct sockaddr_in * ) &rtent.rt_gateway;
            p->sin_family = AF_INET;
            p->sin_addr.s_addr = 0;
            p = ( struct sockaddr_in * ) &rtent.rt_genmask;
            p->sin_family = AF_INET;
            p->sin_addr.s_addr = 0xffffffff;


            rtent.rt_dev = interface;
            rtent.rt_metric = 0;
            rtent.rt_flags = RTF_UP | RTF_HOST;
            if ( ioctl( fd,SIOCADDRT,&rtent ) == 0 ) {
                memset( &rtent,0,sizeof( struct rtentry ) );
                p = ( struct sockaddr_in * ) &rtent.rt_dst;
                p->sin_family = AF_INET;
                p->sin_addr.s_addr = 0;
                p = ( struct sockaddr_in * ) &rtent.rt_gateway;
                p->sin_family = AF_INET;
                p->sin_addr.s_addr = *route_addr;
                p = ( struct sockaddr_in * ) &rtent.rt_genmask;
                p->sin_family = AF_INET;
                p->sin_addr.s_addr = 0;


                rtent.rt_dev = interface;

                rtent.rt_metric = 1;
                rtent.rt_window = 0;
                rtent.rt_flags = RTF_UP | RTF_GATEWAY ;
                if ( ioctl( fd,SIOCADDRT,&rtent ) == -1 ) {
                    m_ERROR(stderr,"ioctl SIOCADDRT: %m\n");
                    return FAILURE;
                }
            }
        } else {
            m_ERROR(stderr,"ioctl SIOCADDRT: %m\n" );
            return FAILURE;
        }
    }
    return SUCCESS;
}
//通过读取 /proc/net/route获取路由表
S32 get_route( FILE *fp,RT *rt )
{
    S8          devname[64] ;
    UNS32       d, g, m;
    S32         flgs,ref,use,metric,mtu,win,ir;
    S32         r;

    if ( fp == NULL ) {
		m_DEBUG("I am here 1\n\n");
		return FAILURE;
    }
    r = fscanf( fp,"%63s%lx%lx%X%d%d%d%lx%d%d%d\n",devname,&d,&g,&flgs,&ref,&use,&metric,&m,&mtu,&win,&ir );
    if ( r != 11 ) {
        if ( ( r < 0 ) && feof( fp ) ) {
            /* EOF with no (nonspace) chars read. */
			m_DEBUG("I am here 3\n\n");
            return FAILURE;
        }
		m_DEBUG("I am here 4\n\n");
        return FAILURE;
    }

    if ( !( flgs & RTF_UP ) ) {
        /* Skip interfaces that are down. */
		m_DEBUG("I am here 5\n\n");
        return get_route( fp,rt );
    }

    rt->dst = d;
    rt->mask = m;
    rt->gw = g;
    rt->flags = flgs;

    return SUCCESS;
}
S32 read_interface( S8 *interface, UNS32 *ipaddr, UNS32 *netmaskaddr, UNS32 *gwaddr )
{
    S32               fd;
    struct ifreq      ifr;
    struct sockaddr_in*our_ip;
    RT                rt;
    S32               fret;
	FILE			  *fp = NULL;

    *ipaddr = 0;
    *netmaskaddr = 0;
    *gwaddr = 0;
    memset( &ifr,0,sizeof( struct ifreq ) );
    if ( ( fd = socket( AF_INET,SOCK_RAW,IPPROTO_RAW ) ) >= 0 ) {
        ifr.ifr_addr.sa_family = AF_INET;
        strcpy( ifr.ifr_name,interface );

        if ( ipaddr ) {
        		bzero(ipaddr,sizeof(UNS32));
            if ( ioctl( fd,SIOCGIFADDR,&ifr ) == 0 ) {
                our_ip = ( struct sockaddr_in * ) &ifr.ifr_addr;
                *ipaddr = our_ip->sin_addr.s_addr;
            } else {
                m_ERROR(stderr, "SIOCGIFADDR failed, is the interface up and configured?: %m" );
                close( fd );
                return FAILURE;
            }
        }
        if ( netmaskaddr ) {
        		bzero(netmaskaddr,sizeof(UNS32));
            if ( ioctl( fd,SIOCGIFNETMASK,&ifr ) == 0 ) {
                our_ip = ( struct sockaddr_in * ) &ifr.ifr_netmask;
                *netmaskaddr = our_ip->sin_addr.s_addr;
            } else {
                m_ERROR(stderr,"SIOCGIFHWADDR failed!: %m" );
                close( fd );
                return FAILURE;
            }
        }
    } else {
        m_ERROR(stderr,"socket failed!: %m" );
        return FAILURE;
    }
    close( fd );
    if ( gwaddr ) {
    	bzero(gwaddr,sizeof(UNS32));
		fp = fopen( "/proc/net/route","r" );
		if ( fp == NULL ) {
			return FAILURE;
		}else{
			if ( fscanf( fp,"%*[^\n]\n" ) < 0 ) {/* Skip the first line. */        
				/* Empty or missing line, or read error. */        
				m_DEBUG("I am here 2\n\n");
				return FAILURE;
			}
		}
        while ( ( fret = get_route( fp,&rt ) ) == SUCCESS ) {
			m_DEBUG("DST:0x%08x,FLAGS:0x%08x,GW:0x%08x,MASK:0x%08x\n",rt.dst,rt.flags,rt.gw,rt.mask);
            if ( rt.flags & RTF_GATEWAY ) {
                *gwaddr = rt.gw;
                break;
            }
        }
		fclose(fp);
        if ( fret != SUCCESS ) {
            return FAILURE;
        }
    }

    return SUCCESS;
}

S32 write_interface( S8 *interface, UNS32 *ipaddr, UNS32 *netmaskaddr, UNS32 *gwaddr )
{
    S32               fd;
    struct ifreq      ifr;
    struct sockaddr_in*p  = ( struct sockaddr_in * ) &( ifr.ifr_addr );

    memset( &ifr,0,sizeof( struct ifreq ) );
    if ( interface ) {
        strcpy( ifr.ifr_name,interface );
    } else {
        return FAILURE;
    }


    if ( ( fd = socket( AF_INET,SOCK_STREAM,0 ) ) >= 0 ) {
        ifr.ifr_addr.sa_family = AF_INET;
        if ( ipaddr ) {
            p->sin_addr.s_addr = *ipaddr;
            if ( ioctl( fd,SIOCSIFADDR,&ifr ) == -1 ) { /* setting IP address */ 
                m_ERROR(stderr,"ioctl SIOCSIFADDR: %m\n" );
                return FAILURE;
            }
        }
        if ( netmaskaddr ) {
            p->sin_addr.s_addr = *netmaskaddr;
            if ( ioctl( fd,SIOCSIFNETMASK,&ifr ) == -1 ) { /* setting netmask */ 
                p->sin_addr.s_addr = 0xffffffff; /* try 255.255.255.255 */
                if ( ioctl( fd,SIOCSIFNETMASK,&ifr ) == -1 ) {
                    m_ERROR(stderr,"ioctl SIOCSIFNETMASK: %m\n" );
                    return FAILURE;
                }
            }
        }
		if (ipaddr && netmaskaddr){
			p->sin_addr.s_addr=*ipaddr|(~*netmaskaddr);
			if ( ioctl(fd,SIOCSIFBRDADDR,&ifr) == -1 ) {/* setting broadcast address */
				m_ERROR(stderr,"ioctl SIOCSIFBRDADDR: %m\n");
				return FAILURE;
			}
		}
		if ( gwaddr ) {
			return setDefaultRoute( fd,interface,gwaddr );
		}
		close( fd );
    } else {
        m_ERROR(stderr,"socket failed!: %m" );
        return FAILURE;
    }    	
	
    return SUCCESS;
}

int main(void)
{
	S8 *interface="eth0";

	struct in_addr ipaddr;
	struct in_addr netmaskaddr;
	struct in_addr gwaddr;

	inet_aton("192.168.2.18",&ipaddr);
	inet_aton("255.240.0.0",&netmaskaddr);
	inet_aton("192.168.2.3",&gwaddr);

//	write_interface(interface,(UNS32 *)&ipaddr,(UNS32 *)&netmaskaddr,(UNS32 *)&gwaddr);
	bzero(&ipaddr,sizeof(struct in_addr));
	bzero(&netmaskaddr,sizeof(struct in_addr));
	bzero(&gwaddr,sizeof(struct in_addr));
while(1){
	read_interface(interface,(UNS32 *)&ipaddr,(UNS32 *)&netmaskaddr,(UNS32 *)&gwaddr);
	m_DEBUG("ipaddr:%s\n",inet_ntoa(ipaddr));
	m_DEBUG("netmask:%s\n",inet_ntoa(netmaskaddr));
	m_DEBUG("gateway:%s\n",inet_ntoa(gwaddr));
	usleep(500000);
}
	return SUCCESS;
	
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -