Linux下获得本机ip

21 篇文章 0 订阅
18 篇文章 1 订阅
java版

private InetAddress getLocalIp() throws SocketException{
    Enumeration<NetworkInterface> e = NetworkInterface.getNetworkInterfaces();
    while(e.hasMoreElements()){
        NetworkInterface ni = e.nextElement();
        if("eth0".equals(ni.getName())){
            Enumeration<InetAddress> e2 = ni.getInetAddresses();
            while (e2.hasMoreElements()) {
                InetAddress ia = e2.nextElement();
                if (ia instanceof Inet4Address){
                    return ia;
                }
            }
        }
    }
    return null;
}

python版:

import socket
import fcntl
import struct
 
def get_ip_address(ifname):
    s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    return socket.inet_ntoa(fcntl.ioctl(
        s.fileno(),
        0x8915,  # SIOCGIFADDR
        struct.pack('256s', ifname[:15])
    )[20:24])

print get_ip_address('eth0')

c版:

#include <stdio.h>  
#include <netdb.h>  
#include <arpa/inet.h>  
#include <sys/ioctl.h>  
#include <net/if.h>  

// 根据传入的网卡名,查询相应的ip,比如eth0,wlan0
char* get_ip(const char *inter_name){
    int s;
    struct ifconf conf;
    struct ifreq *ifr;
    char buff[BUFSIZ];
    int num, i;
    size_t l;

    s = socket(PF_INET, SOCK_DGRAM, 0); 
    conf.ifc_len = BUFSIZ;
    conf.ifc_buf = buff;

    ioctl(s, SIOCGIFCONF, &conf);
    num = conf.ifc_len / sizeof(struct ifreq);
    ifr = conf.ifc_req;

    for(i=0; i<num; i++){
        struct sockaddr_in *sin = (struct sockaddr_in *)(&ifr->ifr_addr);
        ioctl(s, SIOCGIFFLAGS, ifr);
        if( 
            ((ifr->ifr_flags & IFF_LOOPBACK) == 0)
                && (ifr->ifr_flags & IFF_UP)
        ){  
            if(strcmp(ifr->ifr_name, inter_name) == 0){ 
                return inet_ntoa(sin->sin_addr);
            }   
        }   
        ifr++;
    }   

    // 没有查询到相应的网卡的ip
    return NULL;
}


int main(int argc, char **argv){
    const char *s = get_ip(argv[1]);
    if(s != NULL)
        printf("%s\n", s);
    else
        printf("the interface doesn't exist\n");
}

lua版:

采用c模块实现,使用上面c版的代码。

#include <stdio.h>  
#include <netdb.h>  
#include <arpa/inet.h>  
#include <sys/ioctl.h>  
#include <net/if.h>  
#include <lua.h>
#include <lauxlib.h>
#include <lualib.h>
  
static int get_ip(lua_State *L){
	int s;
	struct ifconf conf;
	struct ifreq *ifr;
	char buff[BUFSIZ];
	int num, i;
	size_t l;
	const char *inter_name;

	s = socket(PF_INET, SOCK_DGRAM, 0);
	conf.ifc_len = BUFSIZ;
	conf.ifc_buf = buff;

	ioctl(s, SIOCGIFCONF, &conf);
	num = conf.ifc_len / sizeof(struct ifreq);
	ifr = conf.ifc_req;

	inter_name = lua_tolstring(L, -1, &l);
	for(i=0; i<num; i++){
		struct sockaddr_in *sin = (struct sockaddr_in *)(&ifr->ifr_addr);
		ioctl(s, SIOCGIFFLAGS, ifr);
		if(
			((ifr->ifr_flags & IFF_LOOPBACK) == 0)
				&& (ifr->ifr_flags & IFF_UP)
		){
			if(strcmp(ifr->ifr_name, inter_name) == 0){
				lua_pushstring(L, inet_ntoa(sin->sin_addr));	
				return 1;
			} 
		}
		ifr++;
	}

	// 没有查询到相应的网卡的ip
	lua_pushstring(L, "null");
	return 1;
}

static const struct luaL_Reg iplib[] = {
	{"get_ip", get_ip},
	{NULL, NULL}
};

int luaopen_iplib(lua_State *L){
	luaL_register(L, "iplib", iplib);
	return 1;
}
        然后编译成动态链接库:

gcc -fpic -shared -I <path-to-lua-include> -o iplib.so iplib.c 

        指定iplib.so在LUA_CPATH下,在lua中可以这样使用:

local ip = require('iplib')

ip_addr = ip.get_ip('eth0')
print(ip_addr)


在C++中,尤其是在Linux环境下,你可以通过读取网络接口文件或使用套接字API来获取本地IP地址。以下是一个简单的方法,通过读取`/etc/hostname`和`/etc/hosts`文件来获得主机名和IP地址,以及使用`getifaddrs`函数来获取所有网络接口的详细信息。 ```cpp #include <iostream> #include <fstream> #include <ifaddrs.h> #include <netinet/in.h> #include <arpa/inet.h> #include <netdb.h> #include <unistd.h> int main() { // 从 /etc/hostname 获取主机名 std::ifstream hostnameFile("/etc/hostname"); std::string hostname; if (hostnameFile.is_open()) { std::getline(hostnameFile, hostname); hostnameFile.close(); } // 从 /etc/hosts 获取与主机名对应的IP地址 std::ifstream hostsFile("/etc/hosts"); std::string line; std::string ip; bool found = false; if (hostsFile.is_open()) { while (std::getline(hostsFile, line)) { std::istringstream iss(line); std::string currentHostname; if (std::getline(iss, currentHostname, ' ') && currentHostname == hostname) { if (std::getline(iss, ip, ' ')) { found = true; break; } } } hostsFile.close(); } if (found) { std::cout << "Hostname: " << hostname << std::endl; std::cout << "IP Address: " << ip << std::endl; } else { std::cout << "Hostname not found in /etc/hosts" << std::endl; } // 使用 getifaddrs 获取所有网络接口的IP地址 struct ifaddrs *ifaddr, *ifa; if (getifaddrs(&ifaddr) == -1) { perror("getifaddrs"); return -1; } for (ifa = ifaddr; ifa != NULL; ifa = ifa->ifa_next) { if (ifa->ifa_addr == NULL) continue; if (ifa->ifa_addr->sa_family == AF_INET) { // IPv4 // 获取网络接口名称 std::string interfaceName = ifa->ifa_name; // 将套接字地址转换为IPv4地址 struct sockaddr_in *s = (struct sockaddr_in *)ifa->ifa_addr; char ip[INET_ADDRSTRLEN]; inet_ntop(AF_INET, &s->sin_addr, ip, INET_ADDRSTRLEN); std::cout << "Interface: " << interfaceName << " IP: " << ip << std::endl; } } // 释放 getifaddrs 的资源 freeifaddrs(ifaddr); return 0; } ``` 注意,这段代码仅供参考,实际情况中可能需要更复杂的错误处理和网络接口筛选逻辑。此外,直接从`/etc/hosts`中查找IP地址并不总是可靠,因为管理员可能不会在该文件中维护所有主机名到IP的映射,或者有多个IP对应同一个主机名。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值