From patchwork Wed Apr 2 15:50:16 2014 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Philipp Zabel X-Patchwork-Id: 336383 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 3DEF014010E for ; Thu, 3 Apr 2014 02:50:44 +1100 (EST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S932412AbaDBPuY (ORCPT ); Wed, 2 Apr 2014 11:50:24 -0400 Received: from metis.ext.pengutronix.de ([92.198.50.35]:48508 "EHLO metis.ext.pengutronix.de" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S932250AbaDBPuW (ORCPT ); Wed, 2 Apr 2014 11:50:22 -0400 Received: from dude.hi.pengutronix.de ([10.1.0.7] helo=dude.pengutronix.de) by metis.ext.pengutronix.de with esmtp (Exim 4.72) (envelope-from ) id 1WVNQh-0000vC-BH; Wed, 02 Apr 2014 17:50:19 +0200 From: Philipp Zabel To: netdev@vger.kernel.org Cc: linux-kernel@vger.kernel.org, "David S. Miller" , Frederic LAMBERT , kernel@pengutronix.de, Philipp Zabel Subject: [PATCH] net: Micrel KSZ8864RMN 4-port managed switch support Date: Wed, 2 Apr 2014 17:50:16 +0200 Message-Id: <1396453816-32348-1-git-send-email-p.zabel@pengutronix.de> X-Mailer: git-send-email 1.9.1 X-SA-Exim-Connect-IP: 10.1.0.7 X-SA-Exim-Mail-From: p.zabel@pengutronix.de X-SA-Exim-Scanned: No (on metis.ext.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: netdev@vger.kernel.org Sender: netdev-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org This patch adds support for the Micrel KSZ8864RMN switch to the spi_ks8995 driver. The KSZ8864RMN switch has a wider 256-byte register space. Signed-off-by: Philipp Zabel --- drivers/net/phy/spi_ks8995.c | 49 +++++++++++++++++++++++++++++++++++--------- 1 file changed, 39 insertions(+), 10 deletions(-) diff --git a/drivers/net/phy/spi_ks8995.c b/drivers/net/phy/spi_ks8995.c index 4cf5fb9..ad4e028 100644 --- a/drivers/net/phy/spi_ks8995.c +++ b/drivers/net/phy/spi_ks8995.c @@ -1,5 +1,5 @@ /* - * SPI driver for Micrel/Kendin KS8995M ethernet switch + * SPI driver for Micrel/Kendin KS8995M and KSZ8864RMN ethernet switches * * Copyright (C) 2008 Gabor Juhos * @@ -70,7 +70,10 @@ #define KS8995_REG_IAD1 0x76 /* Indirect Access Data 1 */ #define KS8995_REG_IAD0 0x77 /* Indirect Access Data 0 */ +#define KSZ8864_REG_ID1 0xfe /* Chip ID in bit 7 */ + #define KS8995_REGS_SIZE 0x80 +#define KSZ8864_REGS_SIZE 0x100 #define ID1_CHIPID_M 0xf #define ID1_CHIPID_S 4 @@ -94,6 +97,7 @@ struct ks8995_switch { struct spi_device *spi; struct mutex lock; struct ks8995_pdata *pdata; + unsigned int regs_size; }; static inline u8 get_chip_id(u8 val) @@ -216,11 +220,11 @@ static ssize_t ks8995_registers_read(struct file *filp, struct kobject *kobj, dev = container_of(kobj, struct device, kobj); ks8995 = dev_get_drvdata(dev); - if (unlikely(off > KS8995_REGS_SIZE)) + if (unlikely(off > ks8995->regs_size)) return 0; - if ((off + count) > KS8995_REGS_SIZE) - count = KS8995_REGS_SIZE - off; + if ((off + count) > ks8995->regs_size) + count = ks8995->regs_size - off; if (unlikely(!count)) return count; @@ -238,11 +242,11 @@ static ssize_t ks8995_registers_write(struct file *filp, struct kobject *kobj, dev = container_of(kobj, struct device, kobj); ks8995 = dev_get_drvdata(dev); - if (unlikely(off >= KS8995_REGS_SIZE)) + if (unlikely(off >= ks8995->regs_size)) return -EFBIG; - if ((off + count) > KS8995_REGS_SIZE) - count = KS8995_REGS_SIZE - off; + if ((off + count) > ks8995->regs_size) + count = ks8995->regs_size - off; if (unlikely(!count)) return count; @@ -306,6 +310,26 @@ static int ks8995_probe(struct spi_device *spi) goto err_drvdata; } + ks->regs_size = KS8995_REGS_SIZE; + if (get_chip_id(ids[1]) != CHIPID_M) { + u8 val; + + /* Check if this is a KSZ8864RMN */ + err = ks8995_read(ks, &val, KSZ8864_REG_ID1, sizeof(val)); + if (err < 0) { + dev_err(&spi->dev, + "unable to read chip id register, err=%d\n", + err); + goto err_drvdata; + } + if ((val & 0x80) == 0) { + dev_err(&spi->dev, "unknown chip:%02x,0\n", ids[1]); + goto err_drvdata; + } + ks->regs_size = KSZ8864_REGS_SIZE; + ks8995_registers_attr.size = KSZ8864_REGS_SIZE; + } + err = ks8995_reset(ks); if (err) goto err_drvdata; @@ -317,9 +341,14 @@ static int ks8995_probe(struct spi_device *spi) goto err_drvdata; } - dev_info(&spi->dev, "KS89%02X device found, Chip ID:%01x, " - "Revision:%01x\n", ids[0], - get_chip_id(ids[1]), get_chip_rev(ids[1])); + if (get_chip_id(ids[1]) == CHIPID_M) { + dev_info(&spi->dev, + "KS8995 device found, Chip ID:%01x, Revision:%01x\n", + get_chip_id(ids[1]), get_chip_rev(ids[1])); + } else { + dev_info(&spi->dev, "KSZ8864 device found, Revision:%01x\n", + get_chip_rev(ids[1])); + } return 0;