summaryrefslogtreecommitdiff
diff options
authorPMR <pmr@pmr-lander>2020-04-24 10:40:48 +0000
committerPMR <pmr@pmr-lander>2020-04-24 10:40:48 +0000
commit5a7e87e661aa962b989b462cf1b53194b4fd8280 (patch)
treef2f32203fb3c9b1a332a52f42a0de29d3e596890
parent4f7a6f7757c0e2f6c8d7013a503108917ba52ebf (diff)
parent16a5b5873e4df2e12170e3877355468885629197 (diff)
Merge #382897 from ~narahuang/plainbox-provider-checkbox/+git/plainbox-provider-checkbox:fix-missing-mac-passthrough-script
-rwxr-xr-xbin/mac_passthrough.py119
-rw-r--r--units/dock/jobs.pxu2
2 files changed, 120 insertions, 1 deletions
diff --git a/bin/mac_passthrough.py b/bin/mac_passthrough.py
new file mode 100755
index 0000000..92d2eb6
--- /dev/null
+++ b/bin/mac_passthrough.py
@@ -0,0 +1,119 @@
+#!/usr/bin/env python3
+# Copyright 2020 Canonical Ltd.
+# All rights reserved.
+#
+# Written by:
+# Nara Huang <nara.huang@canonical.com>
+#
+# Script to get system ethernet device MAC address, and from ACPI DSDT table,
+# grep "AUXMAC" to get pass-through MAC address,
+# then compare them to check if MAC address pass-through function is working
+import subprocess
+import glob
+import os
+import shutil
+MAC_PASS_SMBIOS_TOKEN = '0x49b'
+
+
+def get_system_mac():
+ """ Get mac addresses from ethernet devices
+ Returns:
+ List: Mac addresses of ethernet devices
+ """
+ mac_addresses = []
+ for interface in glob.glob("/sys/class/net/en*/address"):
+ try:
+ with open(interface, 'r') as iface:
+ mac = iface.read()
+ mac = mac.strip()
+ mac = mac.replace(':', '')
+ mac_addresses.append(mac)
+ except Exception as err:
+ raise SystemExit(err)
+ return mac_addresses
+ # Since system could have multiple ethernet interfaces,
+ # the return value is a list.
+
+
+def get_pass_through_mac():
+ """ Get pass-through mac address from BIOS ACPI DSDT table
+ iasl command is included in acpica-tools package
+ Returns:
+ String: Pass-through MAC address from DSDT table
+ """
+ tmp_path = os.environ.get("SNAP_USER_DATA", "/tmp")
+ aml_path = os.path.join(tmp_path, 'dsdt.aml')
+ dsl_path = os.path.join(tmp_path, 'dsdt.dsl')
+ try:
+ shutil.copy('/sys/firmware/acpi/tables/DSDT', aml_path)
+ subprocess.call(['iasl', '-d', aml_path], stdout=subprocess.DEVNULL,
+ stderr=subprocess.STDOUT)
+ with open(dsl_path, encoding='utf-8', errors='ignore') as dsl:
+ dsdt = dsl.readlines()
+ for line in dsdt:
+ if 'AUXMAC' in line:
+ bios_mac = line.split('#')[1]
+ print('Pass-through MAC address from DSDT table: '
+ + bios_mac.lower())
+ return bios_mac.lower()
+ raise SystemExit('No AUXMAC is found in DSDT table, '
+ 'MAC address pass-through is not working.')
+ except Exception as err:
+ raise SystemExit(err)
+
+
+def check_mac_passthrough(mac, bios_mac):
+ """ Compare pass-through MAC address from BIOS DSDT table
+ and system MAC address, to check if the pass-through function works.
+ Args:
+ mac: A list contains MAC addresses from system
+ bios_mac: A string of MAC address from BIOS DSDT table
+ """
+ if len(mac) == 2 and mac[0] == mac[1]:
+ print('AUXMAC in DSDT table is identical to onboard NIC MAC, which '
+ 'means in BIOS setting, it is set to '
+ '"Integrated NIC 1 MAC Address".')
+ return 0
+ if bios_mac in mac:
+ print('AUXMAC in DSDT table is passed to dock, MAC address '
+ 'pass-through is working.')
+ return 0
+ else:
+ raise SystemExit('MAC address pass-through is not working, '
+ 'maybe the dock is not connected?')
+ # If a system enables mac pass-through function,
+ # but not connected with a dock, it goes here.
+
+
+def check_smbios_token(index):
+ """ Check SMBIOS for BIOS MAC address pass-through setting.
+ If it shows "false", then the function is enabled in
+ BIOS setting.
+ This function requires command "smbios-token-ctl",
+ which comes with package "smbios-utils"
+ Args:
+ index: A string for SMBIOS token index
+ """
+ smbios_token_cmd = ['smbios-token-ctl', '--token-id=']
+ smbios_token_cmd[1] += index
+ try:
+ out = subprocess.check_output(smbios_token_cmd)
+ for line in out.decode("utf-8").splitlines():
+ if 'value: bool' in line:
+ if 'true' in line:
+ raise SystemExit('MAC address pass-through '
+ 'is disabled in BIOS setting.')
+ except Exception as err:
+ raise SystemExit(err)
+ print('MAC address pass-through is enabled in BIOS setting.')
+
+
+def main():
+ check_smbios_token(MAC_PASS_SMBIOS_TOKEN)
+ pasthrough_mac_addresses = get_pass_through_mac()
+ os_mac_addresses = get_system_mac()
+ check_mac_passthrough(os_mac_addresses, pasthrough_mac_addresses)
+
+
+if __name__ == '__main__':
+ raise SystemExit(main())
diff --git a/units/dock/jobs.pxu b/units/dock/jobs.pxu
index c457102..49876d8 100644
--- a/units/dock/jobs.pxu
+++ b/units/dock/jobs.pxu
@@ -2294,7 +2294,7 @@ id: dock/mac-address-passthrough
category_id: dock
plugin: shell
user: root
-command: mac-passthrough.py
+command: mac_passthrough.py
_description: Check dock MAC address pass-through function, please make sure following items before running this test:
1. Pass-through mac address is flashed in BIOS
2. MAC address pass-through is enabled in BIOS settings