get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

GET /api/patches/52537/?format=api
HTTP 200 OK
Allow: GET, PUT, PATCH, HEAD, OPTIONS
Content-Type: application/json
Vary: Accept

{
    "id": 52537,
    "url": "http://patches.dpdk.org/api/patches/52537/?format=api",
    "web_url": "http://patches.dpdk.org/project/dpdk/patch/1554877672-19745-11-git-send-email-rosen.xu@intel.com/",
    "project": {
        "id": 1,
        "url": "http://patches.dpdk.org/api/projects/1/?format=api",
        "name": "DPDK",
        "link_name": "dpdk",
        "list_id": "dev.dpdk.org",
        "list_email": "dev@dpdk.org",
        "web_url": "http://core.dpdk.org",
        "scm_url": "git://dpdk.org/dpdk",
        "webscm_url": "http://git.dpdk.org/dpdk",
        "list_archive_url": "https://inbox.dpdk.org/dev",
        "list_archive_url_format": "https://inbox.dpdk.org/dev/{}",
        "commit_url_format": ""
    },
    "msgid": "<1554877672-19745-11-git-send-email-rosen.xu@intel.com>",
    "list_archive_url": "https://inbox.dpdk.org/dev/1554877672-19745-11-git-send-email-rosen.xu@intel.com",
    "date": "2019-04-10T06:27:48",
    "name": "[v7,10/14] raw/ifpga_rawdev: add I2C and at24 EEPROM driver",
    "commit_ref": null,
    "pull_url": null,
    "state": "changes-requested",
    "archived": true,
    "hash": "aca925013839c8c66a59f0004e52d93285fbb1f2",
    "submitter": {
        "id": 946,
        "url": "http://patches.dpdk.org/api/people/946/?format=api",
        "name": "Xu, Rosen",
        "email": "rosen.xu@intel.com"
    },
    "delegate": {
        "id": 319,
        "url": "http://patches.dpdk.org/api/users/319/?format=api",
        "username": "fyigit",
        "first_name": "Ferruh",
        "last_name": "Yigit",
        "email": "ferruh.yigit@amd.com"
    },
    "mbox": "http://patches.dpdk.org/project/dpdk/patch/1554877672-19745-11-git-send-email-rosen.xu@intel.com/mbox/",
    "series": [
        {
            "id": 4223,
            "url": "http://patches.dpdk.org/api/series/4223/?format=api",
            "web_url": "http://patches.dpdk.org/project/dpdk/list/?series=4223",
            "date": "2019-04-10T06:27:38",
            "name": "Add patch set for IPN3KE",
            "version": 7,
            "mbox": "http://patches.dpdk.org/series/4223/mbox/"
        }
    ],
    "comments": "http://patches.dpdk.org/api/patches/52537/comments/",
    "check": "success",
    "checks": "http://patches.dpdk.org/api/patches/52537/checks/",
    "tags": {},
    "related": [],
    "headers": {
        "Return-Path": "<dev-bounces@dpdk.org>",
        "X-Original-To": "patchwork@dpdk.org",
        "Delivered-To": "patchwork@dpdk.org",
        "Received": [
            "from [92.243.14.124] (localhost [127.0.0.1])\n\tby dpdk.org (Postfix) with ESMTP id 1027A1B107;\n\tWed, 10 Apr 2019 08:27:44 +0200 (CEST)",
            "from mga18.intel.com (mga18.intel.com [134.134.136.126])\n\tby dpdk.org (Postfix) with ESMTP id 4C5A454AE\n\tfor <dev@dpdk.org>; Wed, 10 Apr 2019 08:27:41 +0200 (CEST)",
            "from fmsmga003.fm.intel.com ([10.253.24.29])\n\tby orsmga106.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384;\n\t09 Apr 2019 23:27:40 -0700",
            "from dpdkx8602.sh.intel.com ([10.67.110.200])\n\tby FMSMGA003.fm.intel.com with ESMTP; 09 Apr 2019 23:27:35 -0700"
        ],
        "X-Amp-Result": "SKIPPED(no attachment in message)",
        "X-Amp-File-Uploaded": "False",
        "X-ExtLoop1": "1",
        "X-IronPort-AV": "E=Sophos;i=\"5.60,332,1549958400\"; d=\"scan'208\";a=\"147980995\"",
        "From": "Rosen Xu <rosen.xu@intel.com>",
        "To": "dev@dpdk.org",
        "Cc": "ferruh.yigit@intel.com, tianfei.zhang@intel.com, dan.wei@intel.com,\n\trosen.xu@intel.com, andy.pei@intel.com, qiming.yang@intel.com,\n\thaiyue.wang@intel.com, santos.chen@intel.com, zhang.zhang@intel.com, \n\tdavid.lomartire@intel.com, jia.hu@intel.com",
        "Date": "Wed, 10 Apr 2019 14:27:48 +0800",
        "Message-Id": "<1554877672-19745-11-git-send-email-rosen.xu@intel.com>",
        "X-Mailer": "git-send-email 1.8.3.1",
        "In-Reply-To": "<1554877672-19745-1-git-send-email-rosen.xu@intel.com>",
        "References": "<1551338000-120348-1-git-send-email-rosen.xu@intel.com>\n\t<1554877672-19745-1-git-send-email-rosen.xu@intel.com>",
        "Subject": "[dpdk-dev] [PATCH v7 10/14] raw/ifpga_rawdev: add I2C and at24\n\tEEPROM driver",
        "X-BeenThere": "dev@dpdk.org",
        "X-Mailman-Version": "2.1.15",
        "Precedence": "list",
        "List-Id": "DPDK patches and discussions <dev.dpdk.org>",
        "List-Unsubscribe": "<https://mails.dpdk.org/options/dev>,\n\t<mailto:dev-request@dpdk.org?subject=unsubscribe>",
        "List-Archive": "<http://mails.dpdk.org/archives/dev/>",
        "List-Post": "<mailto:dev@dpdk.org>",
        "List-Help": "<mailto:dev-request@dpdk.org?subject=help>",
        "List-Subscribe": "<https://mails.dpdk.org/listinfo/dev>,\n\t<mailto:dev-request@dpdk.org?subject=subscribe>",
        "Errors-To": "dev-bounces@dpdk.org",
        "Sender": "\"dev\" <dev-bounces@dpdk.org>"
    },
    "content": "From: Tianfei zhang <tianfei.zhang@intel.com>\n\n1. Add Altera I2C master device driver\n2. Add at24 eeprom driver which is i2c slave device\n3. Introducing a new ops for opae_manager: opae_manager_networking_ops.\nThis ops will include some networking operation by FPGA, like vBNG\noperation, MAC ROM operation and so on.\n\nSigned-off-by: Tianfei Zhang <tianfei.zhang@intel.com>\n---\n drivers/raw/ifpga_rawdev/base/Makefile            |   2 +\n drivers/raw/ifpga_rawdev/base/ifpga_api.c         |  22 +\n drivers/raw/ifpga_rawdev/base/ifpga_api.h         |   1 +\n drivers/raw/ifpga_rawdev/base/ifpga_defines.h     |   3 +\n drivers/raw/ifpga_rawdev/base/ifpga_enumerate.c   |   2 +-\n drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.c |   2 +\n drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.h |   7 +\n drivers/raw/ifpga_rawdev/base/ifpga_fme.c         |  90 ++++\n drivers/raw/ifpga_rawdev/base/ifpga_hw.h          |   1 +\n drivers/raw/ifpga_rawdev/base/meson.build         |   2 +\n drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.c  |  88 ++++\n drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.h  |  14 +\n drivers/raw/ifpga_rawdev/base/opae_hw_api.c       |  49 ++-\n drivers/raw/ifpga_rawdev/base/opae_hw_api.h       |  26 +-\n drivers/raw/ifpga_rawdev/base/opae_i2c.c          | 490 ++++++++++++++++++++++\n drivers/raw/ifpga_rawdev/base/opae_i2c.h          | 130 ++++++\n 16 files changed, 926 insertions(+), 3 deletions(-)\n create mode 100644 drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.c\n create mode 100644 drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.h\n create mode 100644 drivers/raw/ifpga_rawdev/base/opae_i2c.c\n create mode 100644 drivers/raw/ifpga_rawdev/base/opae_i2c.h",
    "diff": "diff --git a/drivers/raw/ifpga_rawdev/base/Makefile b/drivers/raw/ifpga_rawdev/base/Makefile\nindex c6f51a8..edb538f 100644\n--- a/drivers/raw/ifpga_rawdev/base/Makefile\n+++ b/drivers/raw/ifpga_rawdev/base/Makefile\n@@ -25,5 +25,7 @@ SRCS-y += ifpga_fme_pr.c\n SRCS-y += opae_spi.c\n SRCS-y += opae_spi_transaction.c\n SRCS-y += opae_intel_max10.c\n+SRCS-y += opae_i2c.c\n+SRCS-y += opae_at24_eeprom.c\n \n SRCS-y += $(wildcard $(SRCDIR)/base/$(OSDEP)/*.c)\ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_api.c b/drivers/raw/ifpga_rawdev/base/ifpga_api.c\nindex 77d9471..c447b3c 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_api.c\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_api.c\n@@ -196,6 +196,28 @@ struct opae_manager_ops ifpga_mgr_ops = {\n \t.flash = ifpga_mgr_flash,\n };\n \n+static int ifpga_mgr_read_mac_rom(struct opae_manager *mgr, int offset,\n+\t\tvoid *buf, int size)\n+{\n+\tstruct ifpga_fme_hw *fme = mgr->data;\n+\n+\treturn fme_mgr_read_mac_rom(fme, offset, buf, size);\n+}\n+\n+static int ifpga_mgr_write_mac_rom(struct opae_manager *mgr, int offset,\n+\t\tvoid *buf, int size)\n+{\n+\tstruct ifpga_fme_hw *fme = mgr->data;\n+\n+\treturn fme_mgr_write_mac_rom(fme, offset, buf, size);\n+}\n+\n+/* Network APIs in FME */\n+struct opae_manager_networking_ops ifpga_mgr_network_ops = {\n+\t.read_mac_rom = ifpga_mgr_read_mac_rom,\n+\t.write_mac_rom = ifpga_mgr_write_mac_rom,\n+};\n+\n /* Adapter APIs */\n static int ifpga_adapter_enumerate(struct opae_adapter *adapter)\n {\ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_api.h b/drivers/raw/ifpga_rawdev/base/ifpga_api.h\nindex dae7ca1..4a24769 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_api.h\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_api.h\n@@ -12,6 +12,7 @@\n extern struct opae_manager_ops ifpga_mgr_ops;\n extern struct opae_bridge_ops ifpga_br_ops;\n extern struct opae_accelerator_ops ifpga_acc_ops;\n+extern struct opae_manager_networking_ops ifpga_mgr_network_ops;\n \n /* common APIs */\n int ifpga_get_prop(struct ifpga_hw *hw, u32 fiu_id, u32 port_id,\ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_defines.h b/drivers/raw/ifpga_rawdev/base/ifpga_defines.h\nindex f5e22ae..62f71c7 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_defines.h\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_defines.h\n@@ -21,6 +21,7 @@\n #define FME_FEATURE_QSPI_FLASH\t    \"fme_qspi_flash\"\n #define FME_FEATURE_MAX10_SPI       \"fme_max10_spi\"\n #define FME_FEATURE_NIOS_SPI        \"fme_nios_spi\"\n+#define FME_FEATURE_I2C_MASTER      \"fme_i2c_master\"\n \n #define PORT_FEATURE_HEADER         \"port_hdr\"\n #define PORT_FEATURE_UAFU           \"port_uafu\"\n@@ -46,6 +47,7 @@\n #define FME_GLOBAL_DPERF_REVISION\t0\n #define FME_QSPI_REVISION\t\t0\n #define FME_MAX10_SPI                   0\n+#define FME_I2C_MASTER                  0\n \n #define PORT_HEADER_REVISION\t\t0\n /* UAFU's header info depends on the downloaded GBS */\n@@ -85,6 +87,7 @@ enum fpga_id_type {\n #define FME_FEATURE_ID_EMIF_MGMT  0x9\n #define FME_FEATURE_ID_MAX10_SPI  0xe\n #define FME_FEATURE_ID_NIOS_SPI 0xd\n+#define FME_FEATURE_ID_I2C_MASTER  0xf\n \n #define PORT_FEATURE_ID_HEADER FEATURE_ID_FIU_HEADER\n #define PORT_FEATURE_ID_ERROR 0x10\ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_enumerate.c b/drivers/raw/ifpga_rawdev/base/ifpga_enumerate.c\nindex c779e0c..666dae1 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_enumerate.c\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_enumerate.c\n@@ -270,7 +270,7 @@ static int build_info_commit_dev(struct build_feature_devs_info *binfo)\n \n \t} else if (binfo->current_type == FME_ID) {\n \t\tmgr = opae_manager_alloc(hw->adapter->name, &ifpga_mgr_ops,\n-\t\t\t\tbinfo->fiu);\n+\t\t\t\t&ifpga_mgr_network_ops, binfo->fiu);\n \t\tif (!mgr)\n \t\t\treturn -ENOMEM;\n \ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.c b/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.c\nindex 2a35c06..0454f80 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.c\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.c\n@@ -201,6 +201,8 @@ int port_clear_error(struct ifpga_port_hw *port)\n \t&fme_spi_master_ops),},\n \t{FEATURE_DRV(FME_FEATURE_ID_NIOS_SPI, FME_FEATURE_NIOS_SPI,\n \t&fme_nios_spi_master_ops),},\n+\t{FEATURE_DRV(FME_FEATURE_ID_I2C_MASTER, FME_FEATURE_I2C_MASTER,\n+\t&fme_i2c_master_ops),},\n \t{0, NULL, NULL}, /* end of arrary */\n };\n \ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.h b/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.h\nindex 72352ee..a398a98 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.h\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_feature_dev.h\n@@ -172,6 +172,7 @@ int do_pr(struct ifpga_hw *hw, u32 port_id, void *buffer, u32 size,\n extern struct feature_ops fme_hssi_eth_ops;\n extern struct feature_ops fme_emif_ops;\n extern struct feature_ops fme_spi_master_ops;\n+extern struct feature_ops fme_i2c_master_ops;\n extern struct feature_ops fme_nios_spi_master_ops;\n \n int port_get_prop(struct ifpga_port_hw *port, struct feature_prop *prop);\n@@ -197,4 +198,10 @@ struct fpga_uafu_irq_set {\n /* help functions for feature ops */\n int fpga_msix_set_block(struct feature *feature, unsigned int start,\n \t\t\tunsigned int count, s32 *fds);\n+\n+/* FME network function ops*/\n+int fme_mgr_read_mac_rom(struct ifpga_fme_hw *fme, int offset,\n+\t\tvoid *buf, int size);\n+int fme_mgr_write_mac_rom(struct ifpga_fme_hw *fme, int offset,\n+\t\tvoid *buf, int size);\n #endif /* _IFPGA_FEATURE_DEV_H_ */\ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_fme.c b/drivers/raw/ifpga_rawdev/base/ifpga_fme.c\nindex 28226f0..95e022e 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_fme.c\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_fme.c\n@@ -5,6 +5,8 @@\n #include \"ifpga_feature_dev.h\"\n #include \"opae_spi.h\"\n #include \"opae_intel_max10.h\"\n+#include \"opae_i2c.h\"\n+#include \"opae_at24_eeprom.h\"\n \n #define PWR_THRESHOLD_MAX       0x7F\n \n@@ -960,3 +962,91 @@ struct feature_ops fme_nios_spi_master_ops = {\n \t.init = fme_nios_spi_init,\n \t.uinit = fme_nios_spi_uinit,\n };\n+\n+static int i2c_mac_rom_test(struct altera_i2c_dev *dev)\n+{\n+\tchar buf[20];\n+\tint ret;\n+\tchar read_buf[20] = {0,};\n+\tconst char *string = \"1a2b3c4d5e\";\n+\n+\topae_memcpy(buf, string, strlen(string));\n+\n+\tret = at24_eeprom_write(dev, AT24512_SLAVE_ADDR, 0,\n+\t\t\t(u8 *)buf, strlen(string));\n+\tif (ret < 0) {\n+\t\tdev_err(NULL, \"write i2c error:%d\\n\", ret);\n+\t\treturn ret;\n+\t}\n+\n+\tret = at24_eeprom_read(dev, AT24512_SLAVE_ADDR, 0,\n+\t\t\t(u8 *)read_buf, strlen(string));\n+\tif (ret < 0) {\n+\t\tdev_err(NULL, \"read i2c error:%d\\n\", ret);\n+\t\treturn ret;\n+\t}\n+\n+\tif (memcmp(buf, read_buf, strlen(string))) {\n+\t\tdev_err(NULL, \"%s test fail!\\n\", __func__);\n+\t\treturn -EFAULT;\n+\t}\n+\n+\tdev_info(NULL, \"%s test successful\\n\", __func__);\n+\n+\treturn 0;\n+}\n+\n+static int fme_i2c_init(struct feature *feature)\n+{\n+\tstruct feature_fme_i2c *i2c;\n+\tstruct ifpga_fme_hw *fme = (struct ifpga_fme_hw *)feature->parent;\n+\n+\ti2c = (struct feature_fme_i2c *)feature->addr;\n+\n+\tdev_info(NULL, \"FME I2C Master Init.\\n\");\n+\n+\tfme->i2c_master = altera_i2c_probe(i2c);\n+\tif (!fme->i2c_master)\n+\t\treturn -ENODEV;\n+\n+\t/* MAC ROM self test */\n+\ti2c_mac_rom_test(fme->i2c_master);\n+\n+\treturn 0;\n+}\n+\n+static void fme_i2c_uninit(struct feature *feature)\n+{\n+\tstruct ifpga_fme_hw *fme = (struct ifpga_fme_hw *)feature->parent;\n+\n+\taltera_i2c_remove(fme->i2c_master);\n+}\n+\n+struct feature_ops fme_i2c_master_ops = {\n+\t.init = fme_i2c_init,\n+\t.uinit = fme_i2c_uninit,\n+};\n+\n+int fme_mgr_read_mac_rom(struct ifpga_fme_hw *fme, int offset,\n+\t\tvoid *buf, int size)\n+{\n+\tstruct altera_i2c_dev *dev;\n+\n+\tdev = fme->i2c_master;\n+\tif (!dev)\n+\t\treturn -ENODEV;\n+\n+\treturn at24_eeprom_read(dev, AT24512_SLAVE_ADDR, offset, buf, size);\n+}\n+\n+int fme_mgr_write_mac_rom(struct ifpga_fme_hw *fme, int offset,\n+\t\tvoid *buf, int size)\n+{\n+\tstruct altera_i2c_dev *dev;\n+\n+\tdev = fme->i2c_master;\n+\tif (!dev)\n+\t\treturn -ENODEV;\n+\n+\treturn at24_eeprom_write(dev, AT24512_SLAVE_ADDR, offset, buf, size);\n+}\ndiff --git a/drivers/raw/ifpga_rawdev/base/ifpga_hw.h b/drivers/raw/ifpga_rawdev/base/ifpga_hw.h\nindex a2f4776..e296dd2 100644\n--- a/drivers/raw/ifpga_rawdev/base/ifpga_hw.h\n+++ b/drivers/raw/ifpga_rawdev/base/ifpga_hw.h\n@@ -81,6 +81,7 @@ struct ifpga_fme_hw {\n \tu32 capability;\n \n \tvoid *max10_dev; /* MAX10 device */\n+\tvoid *i2c_master; /* I2C Master device */\n };\n \n enum ifpga_port_state {\ndiff --git a/drivers/raw/ifpga_rawdev/base/meson.build b/drivers/raw/ifpga_rawdev/base/meson.build\nindex 6bc762f..7655985 100644\n--- a/drivers/raw/ifpga_rawdev/base/meson.build\n+++ b/drivers/raw/ifpga_rawdev/base/meson.build\n@@ -18,6 +18,8 @@ sources = [\n \t'opae_spi.c',\n \t'opae_spi_transaction.c',\n \t'opae_intel_max10.c',\n+\t'opae_i2c.c',\n+\t'opae_at24_eeprom.c',\n ]\n \n error_cflags = ['-Wno-sign-compare', '-Wno-unused-value',\ndiff --git a/drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.c b/drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.c\nnew file mode 100644\nindex 0000000..d70f7af\n--- /dev/null\n+++ b/drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.c\n@@ -0,0 +1,88 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2010-2019 Intel Corporation\n+ */\n+\n+#include \"opae_osdep.h\"\n+#include \"opae_i2c.h\"\n+#include \"opae_at24_eeprom.h\"\n+\n+#define AT24_READ_RETRY 10\n+\n+static int at24_eeprom_read_and_try(struct altera_i2c_dev *dev,\n+\t\tunsigned int slave_addr,\n+\t\tu32 offset, u8 *buf, u32 len)\n+{\n+\tint i;\n+\tint ret = 0;\n+\n+\tfor (i = 0; i < AT24_READ_RETRY; i++) {\n+\t\tret = i2c_read16(dev, slave_addr, offset,\n+\t\t\t\tbuf, len);\n+\t\tif (ret == 0)\n+\t\t\tbreak;\n+\n+\t\topae_udelay(100);\n+\t}\n+\n+\treturn ret;\n+}\n+\n+int at24_eeprom_read(struct altera_i2c_dev *dev, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buf, int count)\n+{\n+\tint len;\n+\tint status;\n+\tint read_count = 0;\n+\n+\tif (!count)\n+\t\treturn count;\n+\n+\tif (count > AT24C512_IO_LIMIT)\n+\t\tlen = AT24C512_IO_LIMIT;\n+\telse\n+\t\tlen = count;\n+\n+\twhile (count) {\n+\t\tstatus = at24_eeprom_read_and_try(dev, slave_addr, offset,\n+\t\t\t\tbuf, len);\n+\t\tif (status)\n+\t\t\tbreak;\n+\n+\t\tbuf += len;\n+\t\toffset += len;\n+\t\tcount -= len;\n+\t\tread_count += len;\n+\t}\n+\n+\treturn read_count;\n+}\n+\n+int at24_eeprom_write(struct altera_i2c_dev *dev, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buf, int count)\n+{\n+\tint len;\n+\tint status;\n+\tint write_count = 0;\n+\n+\tif (!count)\n+\t\treturn count;\n+\n+\tif (count > AT24C512_PAGE_SIZE)\n+\t\tlen = AT24C512_PAGE_SIZE;\n+\telse\n+\t\tlen = count;\n+\n+\twhile (count) {\n+\t\tstatus = i2c_write16(dev, slave_addr, offset, buf, len);\n+\t\tif (status)\n+\t\t\tbreak;\n+\n+\t\tbuf += len;\n+\t\toffset += len;\n+\t\tcount -= len;\n+\t\twrite_count += len;\n+\t}\n+\n+\treturn write_count;\n+}\n+\ndiff --git a/drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.h b/drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.h\nnew file mode 100644\nindex 0000000..caae9a3\n--- /dev/null\n+++ b/drivers/raw/ifpga_rawdev/base/opae_at24_eeprom.h\n@@ -0,0 +1,14 @@\n+\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2010-2019 Intel Corporation\n+ */\n+\n+#define AT24C512_PAGE_SIZE 128\n+#define AT24C512_IO_LIMIT  128\n+\n+#define AT24512_SLAVE_ADDR 0x51\n+\n+int at24_eeprom_read(struct altera_i2c_dev *dev, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buf, int count);\n+int at24_eeprom_write(struct altera_i2c_dev *dev, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buf, int count);\ndiff --git a/drivers/raw/ifpga_rawdev/base/opae_hw_api.c b/drivers/raw/ifpga_rawdev/base/opae_hw_api.c\nindex 41c5903..ec2b4c7 100644\n--- a/drivers/raw/ifpga_rawdev/base/opae_hw_api.c\n+++ b/drivers/raw/ifpga_rawdev/base/opae_hw_api.c\n@@ -210,12 +210,14 @@ int opae_acc_get_uuid(struct opae_accelerator *acc,\n  * opae_manager_alloc - alloc opae_manager data structure\n  * @name: manager name.\n  * @ops: ops of this manager.\n+ * @network_ops: ops of network management.\n  * @data: private data of this manager.\n  *\n  * Return: opae_manager on success, otherwise NULL.\n  */\n struct opae_manager *\n-opae_manager_alloc(const char *name, struct opae_manager_ops *ops, void *data)\n+opae_manager_alloc(const char *name, struct opae_manager_ops *ops,\n+\t\tstruct opae_manager_networking_ops *network_ops, void *data)\n {\n \tstruct opae_manager *mgr = opae_zmalloc(sizeof(*mgr));\n \n@@ -224,6 +226,7 @@ struct opae_manager *\n \n \tmgr->name = name;\n \tmgr->ops = ops;\n+\tmgr->network_ops = network_ops;\n \tmgr->data = data;\n \n \topae_log(\"%s %p\\n\", __func__, mgr);\n@@ -379,3 +382,47 @@ struct opae_accelerator *\n \n \treturn NULL;\n }\n+\n+/**\n+ * opae_manager_read_mac_rom - read the content of the MAC ROM\n+ * @mgr: opae_manager for MAC ROM\n+ * @port: the port number of retimer\n+ * @addr: buffer of the MAC address\n+ *\n+ * Return: return the bytes of read successfully\n+ */\n+int opae_manager_read_mac_rom(struct opae_manager *mgr, int port,\n+\t\tstruct opae_ether_addr *addr)\n+{\n+\tif (!mgr || !mgr->network_ops)\n+\t\treturn -EINVAL;\n+\n+\tif (mgr->network_ops->read_mac_rom)\n+\t\treturn mgr->network_ops->read_mac_rom(mgr,\n+\t\t\t\tport * sizeof(struct opae_ether_addr),\n+\t\t\t\taddr, sizeof(struct opae_ether_addr));\n+\n+\treturn -ENOENT;\n+}\n+\n+/**\n+ * opae_manager_write_mac_rom - write data into MAC ROM\n+ * @mgr: opae_manager for MAC ROM\n+ * @port: the port number of the retimer\n+ * @addr: data of the MAC address\n+ *\n+ * Return: return written bytes\n+ */\n+int opae_manager_write_mac_rom(struct opae_manager *mgr, int port,\n+\t\tstruct opae_ether_addr *addr)\n+{\n+\tif (!mgr || !mgr->network_ops)\n+\t\treturn -EINVAL;\n+\n+\tif (mgr->network_ops && mgr->network_ops->write_mac_rom)\n+\t\treturn mgr->network_ops->write_mac_rom(mgr,\n+\t\t\t\tport * sizeof(struct opae_ether_addr),\n+\t\t\t\taddr, sizeof(struct opae_ether_addr));\n+\n+\treturn -ENOENT;\n+}\ndiff --git a/drivers/raw/ifpga_rawdev/base/opae_hw_api.h b/drivers/raw/ifpga_rawdev/base/opae_hw_api.h\nindex 76224b4..826da37 100644\n--- a/drivers/raw/ifpga_rawdev/base/opae_hw_api.h\n+++ b/drivers/raw/ifpga_rawdev/base/opae_hw_api.h\n@@ -26,6 +26,7 @@ enum opae_adapter_type {\n \n /* OPAE Manager Data Structure */\n struct opae_manager_ops;\n+struct opae_manager_networking_ops;\n \n /*\n  * opae_manager has pointer to its parent adapter, as it could be able to manage\n@@ -36,6 +37,7 @@ struct opae_manager {\n \tconst char *name;\n \tstruct opae_adapter *adapter;\n \tstruct opae_manager_ops *ops;\n+\tstruct opae_manager_networking_ops *network_ops;\n \tvoid *data;\n };\n \n@@ -45,9 +47,18 @@ struct opae_manager_ops {\n \t\t     u32 size, u64 *status);\n };\n \n+/* networking management ops in FME */\n+struct opae_manager_networking_ops {\n+\tint (*read_mac_rom)(struct opae_manager *mgr, int offset, void *buf,\n+\t\t\tint size);\n+\tint (*write_mac_rom)(struct opae_manager *mgr, int offset, void *buf,\n+\t\t\tint size);\n+};\n+\n /* OPAE Manager APIs */\n struct opae_manager *\n-opae_manager_alloc(const char *name, struct opae_manager_ops *ops, void *data);\n+opae_manager_alloc(const char *name, struct opae_manager_ops *ops,\n+\t\tstruct opae_manager_networking_ops *network_ops, void *data);\n #define opae_manager_free(mgr) opae_free(mgr)\n int opae_manager_flash(struct opae_manager *mgr, int acc_id, void *buf,\n \t\t       u32 size, u64 *status);\n@@ -252,4 +263,17 @@ static inline void opae_adapter_remove_acc(struct opae_adapter *adapter,\n {\n \tTAILQ_REMOVE(&adapter->acc_list, acc, node);\n }\n+\n+/* OPAE vBNG network datastruct */\n+#define OPAE_ETHER_ADDR_LEN 6\n+\n+struct opae_ether_addr {\n+\tunsigned char addr_bytes[OPAE_ETHER_ADDR_LEN];\n+} __attribute__((__packed__));\n+\n+/* OPAE vBNG network API*/\n+int opae_manager_read_mac_rom(struct opae_manager *mgr, int port,\n+\t\tstruct opae_ether_addr *addr);\n+int opae_manager_write_mac_rom(struct opae_manager *mgr, int port,\n+\t\tstruct opae_ether_addr *addr);\n #endif /* _OPAE_HW_API_H_*/\ndiff --git a/drivers/raw/ifpga_rawdev/base/opae_i2c.c b/drivers/raw/ifpga_rawdev/base/opae_i2c.c\nnew file mode 100644\nindex 0000000..f8bc247\n--- /dev/null\n+++ b/drivers/raw/ifpga_rawdev/base/opae_i2c.c\n@@ -0,0 +1,490 @@\n+\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2010-2019 Intel Corporation\n+ */\n+\n+#include \"opae_osdep.h\"\n+#include \"opae_i2c.h\"\n+\n+static int i2c_transfer(struct altera_i2c_dev *dev,\n+\t\tstruct i2c_msg *msg, int num)\n+{\n+\tint ret, try;\n+\n+\tfor (ret = 0, try = 0; try < I2C_XFER_RETRY; try++) {\n+\t\tret = dev->xfer(dev, msg, num);\n+\t\tif (ret != -EAGAIN)\n+\t\t\tbreak;\n+\t}\n+\n+\treturn ret;\n+}\n+\n+/**\n+ * i2c read function\n+ */\n+int i2c_read(struct altera_i2c_dev *dev, int flags, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buf, u32 count)\n+{\n+\tu8 msgbuf[2];\n+\tint i = 0;\n+\n+\tif (flags & I2C_FLAG_ADDR16)\n+\t\tmsgbuf[i++] = offset >> 8;\n+\n+\tmsgbuf[i++] = offset;\n+\n+\tstruct i2c_msg msg[2] = {\n+\t\t{\n+\t\t\t.addr = slave_addr,\n+\t\t\t.flags = 0,\n+\t\t\t.len = i,\n+\t\t\t.buf = msgbuf,\n+\t\t},\n+\t\t{\n+\t\t\t.addr = slave_addr,\n+\t\t\t.flags = I2C_M_RD,\n+\t\t\t.len = count,\n+\t\t\t.buf = buf,\n+\t\t},\n+\t};\n+\n+\tif (!dev->xfer)\n+\t\treturn -ENODEV;\n+\n+\treturn i2c_transfer(dev, msg, 2);\n+}\n+\n+int i2c_write(struct altera_i2c_dev *dev, int flags, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buffer, int len)\n+{\n+\tstruct i2c_msg msg;\n+\tu8 *buf;\n+\tint ret;\n+\tint i = 0;\n+\n+\tif (!dev->xfer)\n+\t\treturn -ENODEV;\n+\n+\tbuf = opae_malloc(I2C_MAX_OFFSET_LEN + len);\n+\tif (!buf)\n+\t\treturn -ENOMEM;\n+\n+\tmsg.addr = slave_addr;\n+\tmsg.flags = 0;\n+\tmsg.buf = buf;\n+\n+\tif (flags & I2C_FLAG_ADDR16)\n+\t\tmsg.buf[i++] = offset >> 8;\n+\n+\tmsg.buf[i++] = offset;\n+\topae_memcpy(&msg.buf[i], buffer, len);\n+\tmsg.len = i + len;\n+\n+\tret = i2c_transfer(dev, &msg, 1);\n+\n+\topae_free(buf);\n+\treturn ret;\n+}\n+\n+int i2c_read8(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count)\n+{\n+\treturn i2c_read(dev, 0, slave_addr, offset, buf, count);\n+}\n+\n+int i2c_read16(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count)\n+{\n+\treturn i2c_read(dev, I2C_FLAG_ADDR16, slave_addr, offset,\n+\t\t\tbuf, count);\n+}\n+\n+int i2c_write8(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count)\n+{\n+\treturn i2c_write(dev, 0, slave_addr, offset, buf, count);\n+}\n+\n+int i2c_write16(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count)\n+{\n+\treturn i2c_write(dev, I2C_FLAG_ADDR16, slave_addr, offset,\n+\t\t\tbuf, count);\n+}\n+\n+static void i2c_indirect_write(struct altera_i2c_dev *dev, u32 reg,\n+\t\tu32 value)\n+{\n+\tu64 ctrl;\n+\n+\tctrl = I2C_CTRL_W | (reg >> 2);\n+\n+\topae_writeq(value & I2C_WRITE_DATA_MASK, dev->base + I2C_WRITE);\n+\topae_writeq(ctrl, dev->base + I2C_CTRL);\n+}\n+\n+static u32 i2c_indirect_read(struct altera_i2c_dev *dev, u32 reg)\n+{\n+\tu64 tmp;\n+\tu64 ctrl;\n+\tu32 value;\n+\n+\tctrl = I2C_CTRL_R | (reg >> 2);\n+\topae_writeq(ctrl, dev->base + I2C_CTRL);\n+\n+\t/* FIXME: Read one more time to avoid HW timing issue. */\n+\ttmp = opae_readq(dev->base + I2C_READ);\n+\ttmp = opae_readq(dev->base + I2C_READ);\n+\n+\tvalue = tmp & I2C_READ_DATA_MASK;\n+\n+\treturn value;\n+}\n+\n+static void altera_i2c_transfer(struct altera_i2c_dev *dev, u32 data)\n+{\n+\t/*send STOP on last byte*/\n+\tif (dev->msg_len == 1)\n+\t\tdata |= ALTERA_I2C_TFR_CMD_STO;\n+\tif (dev->msg_len > 0)\n+\t\ti2c_indirect_write(dev, ALTERA_I2C_TFR_CMD, data);\n+}\n+\n+static void altera_i2c_disable(struct altera_i2c_dev *dev)\n+{\n+\tu32 val = i2c_indirect_read(dev, ALTERA_I2C_CTRL);\n+\n+\ti2c_indirect_write(dev, ALTERA_I2C_CTRL, val&~ALTERA_I2C_CTRL_EN);\n+}\n+\n+static void altera_i2c_enable(struct altera_i2c_dev *dev)\n+{\n+\tu32 val = i2c_indirect_read(dev, ALTERA_I2C_CTRL);\n+\n+\ti2c_indirect_write(dev, ALTERA_I2C_CTRL, val | ALTERA_I2C_CTRL_EN);\n+}\n+\n+static void altera_i2c_reset(struct altera_i2c_dev *dev)\n+{\n+\taltera_i2c_disable(dev);\n+\taltera_i2c_enable(dev);\n+}\n+\n+static int altera_i2c_wait_core_idle(struct altera_i2c_dev *dev)\n+{\n+\tint retry = 0;\n+\n+\twhile (i2c_indirect_read(dev, ALTERA_I2C_STATUS)\n+\t\t\t& ALTERA_I2C_STAT_CORE) {\n+\t\tif (retry++ > ALTERA_I2C_TIMEOUT_US) {\n+\t\t\tdev_err(dev, \"timeout: Core Status not IDLE...\\n\");\n+\t\t\treturn -EBUSY;\n+\t\t}\n+\t\tudelay(1);\n+\t}\n+\n+\treturn 0;\n+}\n+\n+static void altera_i2c_enable_interrupt(struct altera_i2c_dev *dev,\n+\t\tu32 mask, bool enable)\n+{\n+\tu32 status;\n+\n+\tstatus = i2c_indirect_read(dev, ALTERA_I2C_ISER);\n+\tif (enable)\n+\t\tdev->isr_mask = status | mask;\n+\telse\n+\t\tdev->isr_mask = status&~mask;\n+\n+\ti2c_indirect_write(dev, ALTERA_I2C_ISER, dev->isr_mask);\n+}\n+\n+static void altera_i2c_interrupt_clear(struct altera_i2c_dev *dev, u32 mask)\n+{\n+\tu32 int_en;\n+\n+\tint_en = i2c_indirect_read(dev, ALTERA_I2C_ISR);\n+\n+\ti2c_indirect_write(dev, ALTERA_I2C_ISR, int_en | mask);\n+}\n+\n+static void altera_i2c_read_rx_fifo(struct altera_i2c_dev *dev)\n+{\n+\tsize_t rx_avail;\n+\tsize_t bytes;\n+\n+\trx_avail = i2c_indirect_read(dev, ALTERA_I2C_RX_FIFO_LVL);\n+\tbytes = min(rx_avail, dev->msg_len);\n+\n+\twhile (bytes-- > 0) {\n+\t\t*dev->buf++ = i2c_indirect_read(dev, ALTERA_I2C_RX_DATA);\n+\t\tdev->msg_len--;\n+\t\taltera_i2c_transfer(dev, 0);\n+\t}\n+}\n+\n+static void altera_i2c_stop(struct altera_i2c_dev *dev)\n+{\n+\ti2c_indirect_write(dev, ALTERA_I2C_TFR_CMD, ALTERA_I2C_TFR_CMD_STO);\n+}\n+\n+static int altera_i2c_fill_tx_fifo(struct altera_i2c_dev *dev)\n+{\n+\tsize_t tx_avail;\n+\tint bytes;\n+\tint ret;\n+\n+\ttx_avail = dev->fifo_size -\n+\t\ti2c_indirect_read(dev, ALTERA_I2C_TC_FIFO_LVL);\n+\tbytes = min(tx_avail, dev->msg_len);\n+\tret = dev->msg_len - bytes;\n+\n+\twhile (bytes-- > 0) {\n+\t\taltera_i2c_transfer(dev, *dev->buf++);\n+\t\tdev->msg_len--;\n+\t}\n+\n+\treturn ret;\n+}\n+\n+static u8 i2c_8bit_addr_from_msg(const struct i2c_msg *msg)\n+{\n+\treturn (msg->addr << 1) | (msg->flags & I2C_M_RD ? 1 : 0);\n+}\n+\n+static int altera_i2c_wait_complete(struct altera_i2c_dev *dev,\n+\t\tu32 *status)\n+{\n+\tint retry = 0;\n+\n+\twhile (!((*status = i2c_indirect_read(dev, ALTERA_I2C_ISR))\n+\t\t\t\t& dev->isr_mask)) {\n+\t\tif (retry++ > ALTERA_I2C_TIMEOUT_US)\n+\t\t\treturn -EBUSY;\n+\n+\t\tudelay(1000);\n+\t}\n+\n+\treturn 0;\n+}\n+\n+static bool altera_handle_i2c_status(struct altera_i2c_dev *dev, u32 status)\n+{\n+\tbool read, finish = false;\n+\tint ret;\n+\n+\tread = (dev->msg->flags & I2C_M_RD) != 0;\n+\n+\tif (status & ALTERA_I2C_ISR_ARB) {\n+\t\taltera_i2c_interrupt_clear(dev, ALTERA_I2C_ISR_ARB);\n+\t\tdev->msg_err = -EAGAIN;\n+\t\tfinish = true;\n+\t} else if (status & ALTERA_I2C_ISR_NACK) {\n+\t\tdev_debug(dev, \"could not get ACK\\n\");\n+\t\tdev->msg_err = -ENXIO;\n+\t\taltera_i2c_interrupt_clear(dev, ALTERA_I2C_ISR_NACK);\n+\t\taltera_i2c_stop(dev);\n+\t\tfinish = true;\n+\t} else if (read && (status & ALTERA_I2C_ISR_RXOF)) {\n+\t\t/* RX FIFO Overflow */\n+\t\taltera_i2c_read_rx_fifo(dev);\n+\t\taltera_i2c_interrupt_clear(dev, ALTERA_I2C_ISER_RXOF_EN);\n+\t\taltera_i2c_stop(dev);\n+\t\tdev_err(dev, \"error: RX FIFO overflow\\n\");\n+\t\tfinish = true;\n+\t} else if (read && (status & ALTERA_I2C_ISR_RXRDY)) {\n+\t\taltera_i2c_read_rx_fifo(dev);\n+\t\taltera_i2c_interrupt_clear(dev, ALTERA_I2C_ISR_RXRDY);\n+\t\tif (!dev->msg_len)\n+\t\t\tfinish = true;\n+\t} else if (!read && (status & ALTERA_I2C_ISR_TXRDY)) {\n+\t\taltera_i2c_interrupt_clear(dev, ALTERA_I2C_ISR_TXRDY);\n+\t\tif (dev->msg_len > 0)\n+\t\t\taltera_i2c_fill_tx_fifo(dev);\n+\t\telse\n+\t\t\tfinish = true;\n+\t} else {\n+\t\tdev_err(dev, \"unexpected status:0x%x\\n\", status);\n+\t\taltera_i2c_interrupt_clear(dev, ALTERA_I2C_ALL_IRQ);\n+\t}\n+\n+\tif (finish) {\n+\t\tret = altera_i2c_wait_core_idle(dev);\n+\t\tif (ret)\n+\t\t\tdev_err(dev, \"message timeout\\n\");\n+\n+\t\taltera_i2c_enable_interrupt(dev, ALTERA_I2C_ALL_IRQ, false);\n+\t\taltera_i2c_interrupt_clear(dev, ALTERA_I2C_ALL_IRQ);\n+\t\tdev_debug(dev, \"message done\\n\");\n+\t}\n+\n+\treturn finish;\n+}\n+\n+static bool altera_i2c_poll_status(struct altera_i2c_dev *dev)\n+{\n+\tu32 status;\n+\tbool finish = false;\n+\tint i = 0;\n+\n+\tdo {\n+\t\tif (altera_i2c_wait_complete(dev, &status)) {\n+\t\t\tdev_err(dev, \"altera i2c wait complete timeout, status=0x%x\\n\",\n+\t\t\t\t\tstatus);\n+\t\t\treturn -EBUSY;\n+\t\t}\n+\n+\t\tfinish = altera_handle_i2c_status(dev, status);\n+\n+\t\tif (i++ > I2C_XFER_RETRY)\n+\t\t\tbreak;\n+\n+\t} while (!finish);\n+\n+\treturn finish;\n+}\n+\n+static int altera_i2c_xfer_msg(struct altera_i2c_dev *dev,\n+\t\tstruct i2c_msg *msg)\n+{\n+\tu32 int_mask = ALTERA_I2C_ISR_RXOF |\n+\t\tALTERA_I2C_ISR_ARB | ALTERA_I2C_ISR_NACK;\n+\tu8 addr = i2c_8bit_addr_from_msg(msg);\n+\tbool finish;\n+\n+\tdev->msg = msg;\n+\tdev->msg_len = msg->len;\n+\tdev->buf = msg->buf;\n+\tdev->msg_err = 0;\n+\taltera_i2c_enable(dev);\n+\n+\t/*make sure RX FIFO is emtry*/\n+\tdo {\n+\t\ti2c_indirect_read(dev, ALTERA_I2C_RX_DATA);\n+\t} while (i2c_indirect_read(dev, ALTERA_I2C_RX_FIFO_LVL));\n+\n+\ti2c_indirect_write(dev, ALTERA_I2C_TFR_CMD_RW_D,\n+\t\t\tALTERA_I2C_TFR_CMD_STA | addr);\n+\n+\t/*enable irq*/\n+\tif (msg->flags & I2C_M_RD) {\n+\t\tint_mask |= ALTERA_I2C_ISR_RXOF | ALTERA_I2C_ISR_RXRDY;\n+\t\t/* in polling mode, we should set this ISR register? */\n+\t\taltera_i2c_enable_interrupt(dev, int_mask, true);\n+\t\taltera_i2c_transfer(dev, 0);\n+\t} else {\n+\t\tint_mask |= ALTERA_I2C_ISR_TXRDY;\n+\t\taltera_i2c_enable_interrupt(dev, int_mask, true);\n+\t\taltera_i2c_fill_tx_fifo(dev);\n+\t}\n+\n+\tfinish = altera_i2c_poll_status(dev);\n+\tif (!finish) {\n+\t\tdev->msg_err = -ETIMEDOUT;\n+\t\tdev_err(dev, \"%s: i2c transfer error\\n\", __func__);\n+\t}\n+\n+\taltera_i2c_enable_interrupt(dev, int_mask, false);\n+\n+\tif (i2c_indirect_read(dev, ALTERA_I2C_STATUS) & ALTERA_I2C_STAT_CORE)\n+\t\tdev_info(dev, \"core not idle...\\n\");\n+\n+\taltera_i2c_disable(dev);\n+\n+\treturn dev->msg_err;\n+}\n+\n+static int altera_i2c_xfer(struct altera_i2c_dev *dev,\n+\t\tstruct i2c_msg *msg, int num)\n+{\n+\tint ret = 0;\n+\tint i;\n+\n+\tfor (i = 0; i < num; i++, msg++) {\n+\t\tret = altera_i2c_xfer_msg(dev, msg);\n+\t\tif (ret)\n+\t\t\tbreak;\n+\t}\n+\n+\treturn ret;\n+}\n+\n+static void altera_i2c_hardware_init(struct altera_i2c_dev *dev)\n+{\n+\tu32 divisor = dev->i2c_clk / dev->bus_clk_rate;\n+\tu32 clk_mhz = dev->i2c_clk / 1000000;\n+\tu32 tmp = (ALTERA_I2C_THRESHOLD << ALTERA_I2C_CTRL_RXT_SHFT) |\n+\t\t  (ALTERA_I2C_THRESHOLD << ALTERA_I2C_CTRL_TCT_SHFT);\n+\tu32 t_high, t_low;\n+\n+\tif (dev->bus_clk_rate <= 100000) {\n+\t\ttmp &= ~ALTERA_I2C_CTRL_BSPEED;\n+\t\t/*standard mode SCL 50/50*/\n+\t\tt_high = divisor*1/2;\n+\t\tt_low = divisor*1/2;\n+\t} else {\n+\t\ttmp |= ALTERA_I2C_CTRL_BSPEED;\n+\t\t/*Fast mode SCL 33/66*/\n+\t\tt_high = divisor*1/3;\n+\t\tt_low = divisor*2/3;\n+\t}\n+\n+\ti2c_indirect_write(dev, ALTERA_I2C_CTRL, tmp);\n+\n+\tdev_info(dev, \"%s: rate=%uHz per_clk=%uMHz -> ratio=1:%u\\n\",\n+\t\t__func__, dev->bus_clk_rate, clk_mhz, divisor);\n+\n+\t/*reset the i2c*/\n+\taltera_i2c_reset(dev);\n+\n+\t/*Set SCL high Time*/\n+\ti2c_indirect_write(dev, ALTERA_I2C_SCL_HIGH, t_high);\n+\t/*Set SCL low time*/\n+\ti2c_indirect_write(dev, ALTERA_I2C_SCL_LOW, t_low);\n+\t/*Set SDA Hold time, 300ms*/\n+\ti2c_indirect_write(dev, ALTERA_I2C_SDA_HOLD, (300*clk_mhz)/1000);\n+\n+\taltera_i2c_enable_interrupt(dev, ALTERA_I2C_ALL_IRQ, false);\n+}\n+\n+struct altera_i2c_dev *altera_i2c_probe(void *base)\n+{\n+\tstruct altera_i2c_dev *dev;\n+\n+\tdev = opae_malloc(sizeof(*dev));\n+\tif (!dev)\n+\t\treturn NULL;\n+\n+\tdev->base = (u8 *)base;\n+\tdev->i2c_param.info = opae_readq(dev->base + I2C_PARAM);\n+\n+\tif (dev->i2c_param.devid != 0xEE011) {\n+\t\tdev_err(dev, \"find a invalid i2c master\\n\");\n+\t\treturn NULL;\n+\t}\n+\n+\tdev->fifo_size = dev->i2c_param.fifo_depth;\n+\n+\tif (dev->i2c_param.max_req == ALTERA_I2C_100KHZ)\n+\t\tdev->bus_clk_rate = 100000;\n+\telse if (dev->i2c_param.max_req == ALTERA_I2C_400KHZ)\n+\t\t/* i2c bus clk 400KHz*/\n+\t\tdev->bus_clk_rate = 400000;\n+\n+\t/* i2c input clock for vista creek is 100MHz */\n+\tdev->i2c_clk = dev->i2c_param.ref_clk * 1000000;\n+\tdev->xfer = altera_i2c_xfer;\n+\n+\taltera_i2c_hardware_init(dev);\n+\n+\treturn dev;\n+}\n+\n+int altera_i2c_remove(struct altera_i2c_dev *dev)\n+{\n+\taltera_i2c_disable(dev);\n+\n+\treturn 0;\n+}\ndiff --git a/drivers/raw/ifpga_rawdev/base/opae_i2c.h b/drivers/raw/ifpga_rawdev/base/opae_i2c.h\nnew file mode 100644\nindex 0000000..8890c8f\n--- /dev/null\n+++ b/drivers/raw/ifpga_rawdev/base/opae_i2c.h\n@@ -0,0 +1,130 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2010-2019 Intel Corporation\n+ */\n+\n+#ifndef _OPAE_I2C_H\n+#define _OPAE_I2C_H\n+\n+#include \"opae_osdep.h\"\n+\n+#define ALTERA_I2C_TFR_CMD\t0x00\t/* Transfer Command register */\n+#define ALTERA_I2C_TFR_CMD_STA\tBIT(9)\t/* send START before byte */\n+#define ALTERA_I2C_TFR_CMD_STO\tBIT(8)\t/* send STOP after byte */\n+#define ALTERA_I2C_TFR_CMD_RW_D\tBIT(0)\t/* Direction of transfer */\n+#define ALTERA_I2C_RX_DATA\t0x04\t/* RX data FIFO register */\n+#define ALTERA_I2C_CTRL\t\t0x8\t/* Control register */\n+#define ALTERA_I2C_CTRL_RXT_SHFT\t4\t/* RX FIFO Threshold */\n+#define ALTERA_I2C_CTRL_TCT_SHFT\t2\t/* TFER CMD FIFO Threshold */\n+#define ALTERA_I2C_CTRL_BSPEED\tBIT(1)\t/* Bus Speed */\n+#define ALTERA_I2C_CTRL_EN\tBIT(0)\t/* Enable Core */\n+#define ALTERA_I2C_ISER\t\t0xc\t/* Interrupt Status Enable register */\n+#define ALTERA_I2C_ISER_RXOF_EN\tBIT(4)\t/* Enable RX OVERFLOW IRQ */\n+#define ALTERA_I2C_ISER_ARB_EN\tBIT(3)\t/* Enable ARB LOST IRQ */\n+#define ALTERA_I2C_ISER_NACK_EN\tBIT(2)\t/* Enable NACK DET IRQ */\n+#define ALTERA_I2C_ISER_RXRDY_EN\tBIT(1)\t/* Enable RX Ready IRQ */\n+#define ALTERA_I2C_ISER_TXRDY_EN\tBIT(0)\t/* Enable TX Ready IRQ */\n+#define ALTERA_I2C_ISR\t\t0x10\t/* Interrupt Status register */\n+#define ALTERA_I2C_ISR_RXOF\t\tBIT(4)\t/* RX OVERFLOW */\n+#define ALTERA_I2C_ISR_ARB\t\tBIT(3)\t/* ARB LOST */\n+#define ALTERA_I2C_ISR_NACK\t\tBIT(2)\t/* NACK DET */\n+#define ALTERA_I2C_ISR_RXRDY\t\tBIT(1)\t/* RX Ready */\n+#define ALTERA_I2C_ISR_TXRDY\t\tBIT(0)\t/* TX Ready */\n+#define ALTERA_I2C_STATUS\t0x14\t/* Status register */\n+#define ALTERA_I2C_STAT_CORE\t\tBIT(0)\t/* Core Status */\n+#define ALTERA_I2C_TC_FIFO_LVL\t0x18   /* Transfer FIFO LVL register */\n+#define ALTERA_I2C_RX_FIFO_LVL\t0x1c\t/* Receive FIFO LVL register */\n+#define ALTERA_I2C_SCL_LOW\t0x20\t/* SCL low count register */\n+#define ALTERA_I2C_SCL_HIGH\t0x24\t/* SCL high count register */\n+#define ALTERA_I2C_SDA_HOLD\t0x28\t/* SDA hold count register */\n+\n+#define ALTERA_I2C_ALL_IRQ\t(ALTERA_I2C_ISR_RXOF | ALTERA_I2C_ISR_ARB | \\\n+\t\t\t\t ALTERA_I2C_ISR_NACK | ALTERA_I2C_ISR_RXRDY | \\\n+\t\t\t\t ALTERA_I2C_ISR_TXRDY)\n+\n+#define ALTERA_I2C_THRESHOLD\t0\n+#define ALTERA_I2C_DFLT_FIFO_SZ\t8\n+#define ALTERA_I2C_TIMEOUT_US  250000 /* 250ms */\n+\n+#define I2C_PARAM 0x8\n+#define I2C_CTRL  0x10\n+#define I2C_CTRL_R    BIT_ULL(9)\n+#define I2C_CTRL_W    BIT_ULL(8)\n+#define I2C_CTRL_ADDR_MASK GENMASK_ULL(3, 0)\n+#define I2C_READ 0x18\n+#define I2C_READ_DATA_VALID BIT_ULL(32)\n+#define I2C_READ_DATA_MASK GENMASK_ULL(31, 0)\n+#define I2C_WRITE 0x20\n+#define I2C_WRITE_DATA_MASK GENMASK_ULL(31, 0)\n+\n+#define ALTERA_I2C_100KHZ  0\n+#define ALTERA_I2C_400KHZ  1\n+\n+/* i2c slave using 16bit address */\n+#define I2C_FLAG_ADDR16  1\n+\n+#define I2C_XFER_RETRY 10\n+\n+struct i2c_core_param {\n+\tunion {\n+\t\tu64 info;\n+\t\tstruct {\n+\t\t\tu16 fifo_depth:9;\n+\t\t\tu8 interface:1;\n+\t\t\t/*reference clock of I2C core in MHz*/\n+\t\t\tu32 ref_clk:10;\n+\t\t\t/*Max I2C interface freq*/\n+\t\t\tu8 max_req:4;\n+\t\t\tu64 devid:32;\n+\t\t\t/* number of MAC address*/\n+\t\t\tu8 nu_macs:8;\n+\t\t};\n+\t};\n+};\n+\n+struct altera_i2c_dev {\n+\tu8 *base;\n+\tstruct i2c_core_param i2c_param;\n+\tu32 fifo_size;\n+\tu32 bus_clk_rate; /* i2c bus clock */\n+\tu32 i2c_clk; /* i2c input clock */\n+\tstruct i2c_msg *msg;\n+\tsize_t msg_len;\n+\tint msg_err;\n+\tu32 isr_mask;\n+\tu8 *buf;\n+\tint (*xfer)(struct altera_i2c_dev *dev, struct i2c_msg *msg, int num);\n+};\n+\n+/**\n+ * struct i2c_msg: an I2C message\n+ */\n+struct i2c_msg {\n+\tunsigned int addr;\n+\tunsigned int flags;\n+\tunsigned int len;\n+\tu8 *buf;\n+};\n+\n+#define I2C_MAX_OFFSET_LEN 4\n+\n+enum i2c_msg_flags {\n+\tI2C_M_TEN = 0x0010, /*ten-bit chip address*/\n+\tI2C_M_RD  = 0x0001, /*read data*/\n+\tI2C_M_STOP = 0x8000, /*send stop after this message*/\n+};\n+\n+struct altera_i2c_dev *altera_i2c_probe(void *base);\n+int altera_i2c_remove(struct altera_i2c_dev *dev);\n+int i2c_read(struct altera_i2c_dev *dev, int flags, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buf, u32 count);\n+int i2c_write(struct altera_i2c_dev *dev, int flags, unsigned int slave_addr,\n+\t\tu32 offset, u8 *buffer, int len);\n+int i2c_read8(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count);\n+int i2c_read16(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count);\n+int i2c_write8(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count);\n+int i2c_write16(struct altera_i2c_dev *dev, unsigned int slave_addr, u32 offset,\n+\t\tu8 *buf, u32 count);\n+#endif\n",
    "prefixes": [
        "v7",
        "10/14"
    ]
}