171e2f4ddSJiaxun Yang // SPDX-License-Identifier: GPL-2.0-or-later
271e2f4ddSJiaxun Yang /*
371e2f4ddSJiaxun Yang * read/write operation to the PCI config space of CS5536
471e2f4ddSJiaxun Yang *
571e2f4ddSJiaxun Yang * Copyright (C) 2007 Lemote, Inc.
671e2f4ddSJiaxun Yang * Author : jlliu, liujl@lemote.com
771e2f4ddSJiaxun Yang *
871e2f4ddSJiaxun Yang * Copyright (C) 2009 Lemote, Inc.
971e2f4ddSJiaxun Yang * Author: Wu Zhangjin, wuzhangjin@gmail.com
1071e2f4ddSJiaxun Yang *
1171e2f4ddSJiaxun Yang * the Virtual Support Module(VSM) for virtulizing the PCI
1271e2f4ddSJiaxun Yang * configure space are defined in cs5536_modulename.c respectively,
1371e2f4ddSJiaxun Yang *
1471e2f4ddSJiaxun Yang * after this virtulizing, user can access the PCI configure space
1571e2f4ddSJiaxun Yang * directly as a normal multi-function PCI device which follows
1671e2f4ddSJiaxun Yang * the PCI-2.2 spec.
1771e2f4ddSJiaxun Yang */
1871e2f4ddSJiaxun Yang
1971e2f4ddSJiaxun Yang #include <linux/types.h>
2071e2f4ddSJiaxun Yang #include <cs5536/cs5536_pci.h>
2171e2f4ddSJiaxun Yang #include <cs5536/cs5536_vsm.h>
2271e2f4ddSJiaxun Yang
2371e2f4ddSJiaxun Yang enum {
2471e2f4ddSJiaxun Yang CS5536_FUNC_START = -1,
2571e2f4ddSJiaxun Yang CS5536_ISA_FUNC,
2671e2f4ddSJiaxun Yang reserved_func,
2771e2f4ddSJiaxun Yang CS5536_IDE_FUNC,
2871e2f4ddSJiaxun Yang CS5536_ACC_FUNC,
2971e2f4ddSJiaxun Yang CS5536_OHCI_FUNC,
3071e2f4ddSJiaxun Yang CS5536_EHCI_FUNC,
3171e2f4ddSJiaxun Yang CS5536_FUNC_END,
3271e2f4ddSJiaxun Yang };
3371e2f4ddSJiaxun Yang
3471e2f4ddSJiaxun Yang static const cs5536_pci_vsm_write vsm_conf_write[] = {
3571e2f4ddSJiaxun Yang [CS5536_ISA_FUNC] = pci_isa_write_reg,
3671e2f4ddSJiaxun Yang [reserved_func] = NULL,
3771e2f4ddSJiaxun Yang [CS5536_IDE_FUNC] = pci_ide_write_reg,
3871e2f4ddSJiaxun Yang [CS5536_ACC_FUNC] = pci_acc_write_reg,
3971e2f4ddSJiaxun Yang [CS5536_OHCI_FUNC] = pci_ohci_write_reg,
4071e2f4ddSJiaxun Yang [CS5536_EHCI_FUNC] = pci_ehci_write_reg,
4171e2f4ddSJiaxun Yang };
4271e2f4ddSJiaxun Yang
4371e2f4ddSJiaxun Yang static const cs5536_pci_vsm_read vsm_conf_read[] = {
4471e2f4ddSJiaxun Yang [CS5536_ISA_FUNC] = pci_isa_read_reg,
4571e2f4ddSJiaxun Yang [reserved_func] = NULL,
4671e2f4ddSJiaxun Yang [CS5536_IDE_FUNC] = pci_ide_read_reg,
4771e2f4ddSJiaxun Yang [CS5536_ACC_FUNC] = pci_acc_read_reg,
4871e2f4ddSJiaxun Yang [CS5536_OHCI_FUNC] = pci_ohci_read_reg,
4971e2f4ddSJiaxun Yang [CS5536_EHCI_FUNC] = pci_ehci_read_reg,
5071e2f4ddSJiaxun Yang };
5171e2f4ddSJiaxun Yang
5271e2f4ddSJiaxun Yang /*
5371e2f4ddSJiaxun Yang * write to PCI config space and transfer it to MSR write.
5471e2f4ddSJiaxun Yang */
cs5536_pci_conf_write4(int function,int reg,u32 value)5571e2f4ddSJiaxun Yang void cs5536_pci_conf_write4(int function, int reg, u32 value)
5671e2f4ddSJiaxun Yang {
5771e2f4ddSJiaxun Yang if ((function <= CS5536_FUNC_START) || (function >= CS5536_FUNC_END))
5871e2f4ddSJiaxun Yang return;
5971e2f4ddSJiaxun Yang if ((reg < 0) || (reg > 0x100) || ((reg & 0x03) != 0))
6071e2f4ddSJiaxun Yang return;
6171e2f4ddSJiaxun Yang
6271e2f4ddSJiaxun Yang if (vsm_conf_write[function] != NULL)
6371e2f4ddSJiaxun Yang vsm_conf_write[function](reg, value);
6471e2f4ddSJiaxun Yang }
6571e2f4ddSJiaxun Yang
6671e2f4ddSJiaxun Yang /*
6771e2f4ddSJiaxun Yang * read PCI config space and transfer it to MSR access.
6871e2f4ddSJiaxun Yang */
cs5536_pci_conf_read4(int function,int reg)6971e2f4ddSJiaxun Yang u32 cs5536_pci_conf_read4(int function, int reg)
7071e2f4ddSJiaxun Yang {
7171e2f4ddSJiaxun Yang u32 data = 0;
7271e2f4ddSJiaxun Yang
7371e2f4ddSJiaxun Yang if ((function <= CS5536_FUNC_START) || (function >= CS5536_FUNC_END))
7471e2f4ddSJiaxun Yang return 0;
7571e2f4ddSJiaxun Yang if ((reg < 0) || ((reg & 0x03) != 0))
7671e2f4ddSJiaxun Yang return 0;
7771e2f4ddSJiaxun Yang if (reg > 0x100)
7871e2f4ddSJiaxun Yang return 0xffffffff;
7971e2f4ddSJiaxun Yang
8071e2f4ddSJiaxun Yang if (vsm_conf_read[function] != NULL)
8171e2f4ddSJiaxun Yang data = vsm_conf_read[function](reg);
8271e2f4ddSJiaxun Yang
8371e2f4ddSJiaxun Yang return data;
8471e2f4ddSJiaxun Yang }
85