Ich benötige eine plattformübergreifende Methode zur Ermittlung der MAC-Adresse eines Computers zur Laufzeit. Für Windows kann das 'wmi' -Modul verwendet werden. Die einzige Methode, die ich unter Linux finden konnte, bestand darin, ifconfig auszuführen und eine Regex in der gesamten Ausgabe auszuführen. Ich mag es nicht, ein Paket zu verwenden, das nur auf einem Betriebssystem funktioniert, und das Parsen der Ausgabe eines anderen Programms scheint nicht sehr elegant zu sein, ganz zu schweigen von Fehler.
Kennt jemand eine plattformübergreifende Methode (Windows und Linux), um die MAC-Adresse zu erhalten? Wenn nicht, kennt jemand elegantere Methoden als die oben aufgeführten?
Python 2.5 enthält eine Uuid-Implementierung, die (in mindestens einer Version) die MAC-Adresse benötigt. Sie können die Mac-Suchfunktion einfach in Ihren eigenen Code importieren:
from uuid import getnode as get_mac
mac = get_mac()
Der Rückgabewert ist die MAC-Adresse als 48-Bit-Ganzzahl.
Die reine Python-Lösung für dieses Problem unter Linux, um den MAC für eine bestimmte lokale Schnittstelle zu erhalten, ursprünglich als Kommentar von vishnubob veröffentlicht und von Ben Mackey in diesem Aktivitätsrezept verbessert
#!/usr/bin/python
import fcntl, socket, struct
def getHwAddr(ifname):
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
info = fcntl.ioctl(s.fileno(), 0x8927, struct.pack('256s', ifname[:15]))
return ':'.join(['%02x' % ord(char) for char in info[18:24]])
print getHwAddr('eth0')
netifaces ist ein gutes Modul, um die MAC-Adresse (und andere Adressen) zu erhalten. Es ist crossplatform und macht ein bisschen mehr Sinn als Socket oder Uuid.
>>> import netifaces
>>> netifaces.interfaces()
['lo', 'eth0', 'tun2']
>>> netifaces.ifaddresses('eth0')[netifaces.AF_LINK]
[{'addr': '08:00:27:50:f2:51', 'broadcast': 'ff:ff:ff:ff:ff:ff'}]
Eine andere Sache, die Sie beachten sollten, ist, dass uuid.getnode()
die MAC-Adresse fälschen kann, indem Sie eine zufällige 48-Bit-Zahl zurückgeben, die möglicherweise nicht Ihren Erwartungen entspricht. Es gibt auch keinen expliziten Hinweis, dass die MAC-Adresse gefälscht wurde. Sie können sie jedoch erkennen, indem Sie getnode()
zweimal aufrufen und sehen, ob das Ergebnis variiert. Wenn derselbe Wert von beiden Anrufen zurückgegeben wird, haben Sie die MAC-Adresse, andernfalls erhalten Sie eine falsche Adresse.
>>> print uuid.getnode.__doc__
Get the hardware address as a 48-bit positive integer.
The first time this runs, it may launch a separate program, which could
be quite slow. If all attempts to obtain the hardware address fail, we
choose a random 48-bit number with its eighth bit set to 1 as recommended
in RFC 4122.
Manchmal haben wir mehr als eine Netzschnittstelle.
Eine einfache Methode, um die MAC-Adresse einer bestimmten Schnittstelle herauszufinden, ist:
def getmac(interface):
try:
mac = open('/sys/class/net/'+interface+'/address').readline()
except:
mac = "00:00:00:00:00:00"
return mac[0:17]
die Methode aufzurufen ist einfach
myMAC = getmac("wlan0")
Meine Antwort hier verwenden: https://stackoverflow.com/a/18031868/2362361
Es ist wichtig zu wissen, für welchen iface Sie den MAC benötigen, da viele vorhanden sein können (Bluetooth, mehrere Netzwerkgeräte usw.).
Dies erledigt den Job, wenn Sie die IP des iface kennen, für den Sie den MAC benötigen, und zwar mit netifaces
(verfügbar in PyPI):
import netifaces as nif
def mac_for_ip(ip):
'Returns a list of MACs for interfaces that have given IP, returns None if not found'
for i in nif.interfaces():
addrs = nif.ifaddresses(i)
try:
if_mac = addrs[nif.AF_LINK][0]['addr']
if_ip = addrs[nif.AF_INET][0]['addr']
except IndexError, KeyError: #ignore ifaces that dont have MAC or IP
if_mac = if_ip = None
if if_ip == ip:
return if_mac
return None
Testen:
>>> mac_for_ip('169.254.90.191')
'2c:41:38:0a:94:8b'
Beachten Sie, dass Sie Ihre eigene plattformübergreifende Bibliothek in Python mithilfe von bedingten Importen erstellen können. z.B.
import platform
if platform.system() == 'Linux':
import LinuxMac
mac_address = LinuxMac.get_mac_address()
Elif platform.system() == 'Windows':
# etc
Dadurch können Sie os.system-Aufrufe oder plattformspezifische Bibliotheken verwenden.
Sie können dies mit psutil tun, das plattformübergreifend ist:
import psutil
mac_addresses = []
nics = psutil.net_if_addrs()
nics.pop('lo') # remove loopback since it doesnt have a real mac address
for i in nics:
for j in nics[i]:
if j.family == 17: # AF_LINK
mac_addresses.append(j.address)
Lassen Sie mich unter Linux ein Shell-Skript einführen, das die MAC-Adresse anzeigt und deren Änderung zulässt (MAC-Sniffing).
ifconfig eth0 | grep HWaddr |cut -dH -f2|cut -d\ -f2
00:26:6c:df:c3:95
Kürzere Argumente können dffer (ich bin kein Experte) versuchen:
ifconfig etho | grep HWaddr
eth0 Link encap:Ethernet HWaddr 00:26:6c:df:c3:95
Um den MAC zu ändern, können wir Folgendes tun:
ifconfig eth0 down
ifconfig eth0 hw ether 00:80:48:BA:d1:30
ifconfig eth0 up
ändert die MAC-Adresse in 00: 80: 48: BA: d1: 30 (wird vorübergehend beim Neustart auf den aktuellen Wert zurückgesetzt).
Das plattformübergreifende getmac - Paket wird dafür funktionieren, wenn Sie nichts dagegen haben, eine Abhängigkeit zu übernehmen. Es funktioniert mit Python 2.7+ und 3.4+. Es werden viele verschiedene Methoden ausprobiert, bis entweder eine Adresse abgerufen oder keine zurückgegeben wird.
from getmac import get_mac_address
eth_mac = get_mac_address(interface="eth0")
win_mac = get_mac_address(interface="Ethernet 3")
ip_mac = get_mac_address(ip="192.168.0.1")
ip6_mac = get_mac_address(ip6="::1")
Host_mac = get_mac_address(hostname="localhost")
updated_mac = get_mac_address(ip="10.0.0.1", network_request=True)
Haftungsausschluss: Ich bin der Autor des Pakets.
Update (14. Januar 2019): Das Paket unterstützt jetzt nur Python 2.7+ und 3.4+. Sie können immer noch eine ältere Version des Pakets verwenden, wenn Sie mit einem älteren Python (2.5, 2.6, 3.2, 3.3) arbeiten müssen.
Alternative,
import uuid
mac_id=(':'.join(['{:02x}'.format((uuid.getnode() >> ele) & 0xff)
Ich kenne keinen einheitlichen Weg, aber hier ist etwas, das Sie nützlich finden könnten:
http://www.codeguru.com/Cpp/I-N/network/networkinformation/article.php/c5451
Was ich in diesem Fall tun würde, wäre, diese in eine Funktion zu packen, und je nach Betriebssystem würde sie den richtigen Befehl ausführen, nach Bedarf analysieren und nur die MAC-Adresse zurückgeben, die Sie wie gewünscht formatiert haben. Natürlich ist es natürlich, außer dass Sie es nur einmal tun müssen und es sieht sauberer aus dem Hauptcode.