cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

ksz9477_i2c.c (2813B)


      1// SPDX-License-Identifier: GPL-2.0
      2/*
      3 * Microchip KSZ9477 series register access through I2C
      4 *
      5 * Copyright (C) 2018-2019 Microchip Technology Inc.
      6 */
      7
      8#include <linux/i2c.h>
      9#include <linux/kernel.h>
     10#include <linux/module.h>
     11#include <linux/regmap.h>
     12
     13#include "ksz_common.h"
     14
     15KSZ_REGMAP_TABLE(ksz9477, not_used, 16, 0, 0);
     16
     17static int ksz9477_i2c_probe(struct i2c_client *i2c,
     18			     const struct i2c_device_id *i2c_id)
     19{
     20	struct regmap_config rc;
     21	struct ksz_device *dev;
     22	int i, ret;
     23
     24	dev = ksz_switch_alloc(&i2c->dev, i2c);
     25	if (!dev)
     26		return -ENOMEM;
     27
     28	for (i = 0; i < ARRAY_SIZE(ksz9477_regmap_config); i++) {
     29		rc = ksz9477_regmap_config[i];
     30		rc.lock_arg = &dev->regmap_mutex;
     31		dev->regmap[i] = devm_regmap_init_i2c(i2c, &rc);
     32		if (IS_ERR(dev->regmap[i])) {
     33			ret = PTR_ERR(dev->regmap[i]);
     34			dev_err(&i2c->dev,
     35				"Failed to initialize regmap%i: %d\n",
     36				ksz9477_regmap_config[i].val_bits, ret);
     37			return ret;
     38		}
     39	}
     40
     41	if (i2c->dev.platform_data)
     42		dev->pdata = i2c->dev.platform_data;
     43
     44	ret = ksz9477_switch_register(dev);
     45
     46	/* Main DSA driver may not be started yet. */
     47	if (ret)
     48		return ret;
     49
     50	i2c_set_clientdata(i2c, dev);
     51
     52	return 0;
     53}
     54
     55static int ksz9477_i2c_remove(struct i2c_client *i2c)
     56{
     57	struct ksz_device *dev = i2c_get_clientdata(i2c);
     58
     59	if (dev)
     60		ksz_switch_remove(dev);
     61
     62	i2c_set_clientdata(i2c, NULL);
     63
     64	return 0;
     65}
     66
     67static void ksz9477_i2c_shutdown(struct i2c_client *i2c)
     68{
     69	struct ksz_device *dev = i2c_get_clientdata(i2c);
     70
     71	if (!dev)
     72		return;
     73
     74	if (dev->dev_ops->shutdown)
     75		dev->dev_ops->shutdown(dev);
     76
     77	dsa_switch_shutdown(dev->ds);
     78
     79	i2c_set_clientdata(i2c, NULL);
     80}
     81
     82static const struct i2c_device_id ksz9477_i2c_id[] = {
     83	{ "ksz9477-switch", 0 },
     84	{},
     85};
     86
     87MODULE_DEVICE_TABLE(i2c, ksz9477_i2c_id);
     88
     89static const struct of_device_id ksz9477_dt_ids[] = {
     90	{
     91		.compatible = "microchip,ksz9477",
     92		.data = &ksz_switch_chips[KSZ9477]
     93	},
     94	{
     95		.compatible = "microchip,ksz9897",
     96		.data = &ksz_switch_chips[KSZ9897]
     97	},
     98	{
     99		.compatible = "microchip,ksz9893",
    100		.data = &ksz_switch_chips[KSZ9893]
    101	},
    102	{
    103		.compatible = "microchip,ksz9563",
    104		.data = &ksz_switch_chips[KSZ9893]
    105	},
    106	{
    107		.compatible = "microchip,ksz8563",
    108		.data = &ksz_switch_chips[KSZ9893]
    109	},
    110	{
    111		.compatible = "microchip,ksz9567",
    112		.data = &ksz_switch_chips[KSZ9567]
    113	},
    114	{},
    115};
    116MODULE_DEVICE_TABLE(of, ksz9477_dt_ids);
    117
    118static struct i2c_driver ksz9477_i2c_driver = {
    119	.driver = {
    120		.name	= "ksz9477-switch",
    121		.of_match_table = of_match_ptr(ksz9477_dt_ids),
    122	},
    123	.probe	= ksz9477_i2c_probe,
    124	.remove	= ksz9477_i2c_remove,
    125	.shutdown = ksz9477_i2c_shutdown,
    126	.id_table = ksz9477_i2c_id,
    127};
    128
    129module_i2c_driver(ksz9477_i2c_driver);
    130
    131MODULE_AUTHOR("Tristram Ha <Tristram.Ha@microchip.com>");
    132MODULE_DESCRIPTION("Microchip KSZ9477 Series Switch I2C access Driver");
    133MODULE_LICENSE("GPL v2");