如何在Python中调用SIOCSIFHWADDR ioctl来更改MAC地址?
我有一段Python代码,它用来创建一个Linux的TAP接口,但每次创建时,系统都会自动生成一个随机的MAC地址。为了方便测试,我想在接口初始化后手动指定一个MAC地址。我知道可以通过
这里是C语言中的结构体:
struct ifreq
{
# define IFHWADDRLEN 6
# define IFNAMSIZ IF_NAMESIZE
union
{
char ifrn_name[IFNAMSIZ]; /* Interface name, e.g. "en0". */
} ifr_ifrn;
union
{
struct sockaddr ifru_addr;
struct sockaddr ifru_dstaddr;
struct sockaddr ifru_broadaddr;
struct sockaddr ifru_netmask;
struct sockaddr ifru_hwaddr;
short int ifru_flags;
int ifru_ivalue;
int ifru_mtu;
struct ifmap ifru_map;
char ifru_slave[IFNAMSIZ]; /* Just fits the size */
char ifru_newname[IFNAMSIZ];
__caddr_t ifru_data;
} ifr_ifru;
};
我觉得我只需要填写
在Python中,调用
谢谢!
3 个回答
0
你可以把/sbin/ip当作一个子进程来启动,比如这样:
/sbin/ip link set dev dummy0 address 02:23:45:67:89:ab
这样做可以省去很多麻烦。
0
一个 union
的意思就是可以用多种方式来理解里面的内容。你只需要关注其中一种,这种:
struct ifreq_set_hwaddr
{
# define IFHWADDRLEN 6
# define IFNAMSIZ IF_NAMESIZE
char ifrn_name[IFNAMSIZ]; /* Interface name, e.g. "en0". */
struct sockaddr ifru_hwaddr;
};
注意,我假设 struct sockaddr
的对齐要求和其他的 union 成员是一样的(或者是最严格的)。如果不是,你可能需要添加一些填充。
6
来自: http://nullege.com/codes/show/src@p@y@pynetlinux-1.0@pynetlinux@ifconfig.py
def set_mac(self, newmac):
''' Set the device's mac address. Device must be down for this to
succeed. '''
macbytes = [int(i, 16) for i in newmac.split(':')]
ifreq = struct.pack('16sH6B8x', self.name, AF_UNIX, *macbytes)
fcntl.ioctl(sockfd, SIOCSIFHWADDR, ifreq)
我用过这个模块里的很多网络方法,真的很有用!