From patchwork Thu Jun 2 16:58:07 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mario Limonciello X-Patchwork-Id: 629376 X-Patchwork-Delegate: davem@davemloft.net Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 3rLD2F0qjdz9t8J for ; Fri, 3 Jun 2016 02:58:29 +1000 (AEST) Authentication-Results: ozlabs.org; dkim=fail reason="signature verification failed" (1024-bit key; unprotected) header.d=dell.com header.i=@dell.com header.b=f/q6vde6; dkim-atps=neutral Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1161299AbcFBQ60 (ORCPT ); Thu, 2 Jun 2016 12:58:26 -0400 Received: from AUSXIPPS310.us.dell.com ([143.166.148.211]:36740 "EHLO ausxipps310.us.dell.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1161332AbcFBQ6X (ORCPT ); Thu, 2 Jun 2016 12:58:23 -0400 DomainKey-Signature: s=smtpout; d=dell.com; c=nofws; q=dns; h=X-LoopCount0:X-IronPort-AV:From:To:Cc:Subject:Date: Message-Id:X-Mailer:In-Reply-To:References; b=Tc5HwuMjduTyx6DaNBlTAoF9K0h3QM4O8XUehaznr9WIfOV/p/LI3Ljq IkTFjitlkNgkSdIQFw7Nie8ir9fuGQF6uWEaqs2VDroBmMRlEcn/YThLH QunnQ/qZcgpAkhfJ6Zc2mNj40OCGXztODc9s1/emx+zg2S4QgTw/YriUR M=; DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=dell.com; i=@dell.com; q=dns/txt; s=smtpout; t=1464886703; x=1496422703; h=from:to:cc:subject:date:message-id:in-reply-to: references; bh=6PhILBwsOe7TPWOZ6B3WOQh0i4T3zgK/5HTBe1B6Eeg=; b=f/q6vde6QATU7nS1DhleYmfDDM1/dnn3ZWqs193RY3lDfWhZnzOOjYW3 JaFQRt4A3pTZHQN4ejST7kLcuDvOMW7Azcf1nHZE5JLwwR5utTUMM+/aD EQGkdAFkGUwaV2kbJPc0mkx61Zpl59DtzucFaX/rAXVbB93CYLUPAIL1l s=; X-LoopCount0: from 10.209.151.17 X-IronPort-AV: E=Sophos;i="5.26,407,1459832400"; d="scan'208";a="323070677" From: Mario Limonciello To: hayeswang@realtek.com Cc: LKML , Netdev , Linux USB , pali.rohar@gmail.com, anthony.wong@canonical.com, Greg KH , Mario Limonciello Subject: [PATCH v2] r8152: Add support for setting MAC to system's Auxiliary MAC address Date: Thu, 2 Jun 2016 11:58:07 -0500 Message-Id: <1464886687-16284-2-git-send-email-mario_limonciello@dell.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1464886687-16284-1-git-send-email-mario_limonciello@dell.com> References: <1464886687-16284-1-git-send-email-mario_limonciello@dell.com> Sender: netdev-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org Dell systems with Type-C ports have support for a persistent system specific MAC address when used with Dell Type-C docks and dongles. This means a dock plugged into two different systems will show different (but persistent) MAC addresses. Dell Type-C docks and dongles use the r8152 driver. This information for the system's persistent MAC address is burned in when the HW is built and available under _SB\AMAC in the DSDT at runtime. More information about the technology is available here: http://www.dell.com/support/article/us/en/04/SLN301147 Signed-off-by: Mario Limonciello --- drivers/net/usb/r8152.c | 53 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 53 insertions(+) diff --git a/drivers/net/usb/r8152.c b/drivers/net/usb/r8152.c index 3f9f6ed..6dea542 100644 --- a/drivers/net/usb/r8152.c +++ b/drivers/net/usb/r8152.c @@ -26,6 +26,8 @@ #include #include #include +#include +#include /* Information for net-next */ #define NETNEXT_VERSION "08" @@ -500,6 +502,7 @@ enum rtl8152_flags { SELECTIVE_SUSPEND, PHY_RESET, SCHEDULE_NAPI, + MAC_PASSTHRU = 0, }; /* Define these values to match your device */ @@ -653,6 +656,7 @@ enum tx_csum_stat { */ static const int multicast_filter_limit = 32; static unsigned int agg_buf_sz = 16384; +static bool mac_passthru_active; #define RTL_LIMITED_TSO_SIZE (agg_buf_sz - sizeof(struct tx_desc) - \ VLAN_ETH_HLEN - VLAN_HLEN) @@ -1030,6 +1034,49 @@ out1: return ret; } +static int get_auxiliary_addr(struct r8152 *tp, struct sockaddr *sa) +{ + acpi_status status; + struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; + union acpi_object *obj; + int ret = -1; + unsigned char buf[6]; + + if (!dmi_name_in_vendors("Dell Inc.") || mac_passthru_active) + return -1; + + /* returns _AUXMAC_#AABBCCDDEEFF# */ + status = acpi_evaluate_object(NULL, "\\_SB.AMAC", NULL, &buffer); + obj = (union acpi_object *)buffer.pointer; + if (ACPI_SUCCESS(status)) { + if (obj->type != ACPI_TYPE_BUFFER || + obj->string.length != 0x17) { + pr_warn("r8152: get_auxiliary_addr: Invalid buffer"); + goto amacout; + } + if (strncmp(obj->string.pointer, "_AUXMAC_#", 9) != 0) { + pr_warn("r8152: get_auxiliary_addr: Invalid header"); + goto amacout; + } + ret = hex2bin(buf, obj->string.pointer + 9, 6); + if (ret < 0) { + pr_warn("r8152: get_auxiliary_addr: Invalid MAC"); + goto amacout; + } + memcpy(sa->sa_data, buf, 6); + ether_addr_copy(tp->netdev->dev_addr, sa->sa_data); + netdev_info(tp->netdev, "Using system MAC address %pM\n", + sa->sa_data); + set_bit(MAC_PASSTHRU, &tp->flags); + mac_passthru_active = true; + ret = 1; + } + +amacout: + kfree(obj); + return ret; +} + static int set_ethernet_addr(struct r8152 *tp) { struct net_device *dev = tp->netdev; @@ -1041,6 +1088,10 @@ static int set_ethernet_addr(struct r8152 *tp) else ret = pla_ocp_read(tp, PLA_BACKUP, 8, sa.sa_data); + /* if system provides auxiliary MAC address */ + if (get_auxiliary_addr(tp, &sa)) + ret = 0; + if (ret < 0) { netif_err(tp, probe, dev, "Get ether addr fail\n"); } else if (!is_valid_ether_addr(sa.sa_data)) { @@ -4268,6 +4319,8 @@ static void rtl8152_disconnect(struct usb_interface *intf) if (udev->state == USB_STATE_NOTATTACHED) set_bit(RTL8152_UNPLUG, &tp->flags); + if (test_bit(MAC_PASSTHRU, &tp->flags)) + mac_passthru_active = false; netif_napi_del(&tp->napi); unregister_netdev(tp->netdev); tp->rtl_ops.unload(tp);