0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013 #include <linux/module.h>
0014 #include <linux/dma-mapping.h>
0015 #include <linux/platform_device.h>
0016 #include <linux/of_platform.h>
0017
0018 #include <asm/octeon/octeon.h>
0019 #include <asm/bitfield.h>
0020
0021 #define CVMX_SATA_UCTL_SHIM_CFG 0xE8
0022
0023 #define SATA_UCTL_ENDIAN_MODE_BIG 1
0024 #define SATA_UCTL_ENDIAN_MODE_LITTLE 0
0025 #define SATA_UCTL_ENDIAN_MODE_MASK 3
0026
0027 #define SATA_UCTL_DMA_ENDIAN_MODE_SHIFT 8
0028 #define SATA_UCTL_CSR_ENDIAN_MODE_SHIFT 0
0029 #define SATA_UCTL_DMA_READ_CMD_SHIFT 12
0030
0031 static int ahci_octeon_probe(struct platform_device *pdev)
0032 {
0033 struct device *dev = &pdev->dev;
0034 struct device_node *node = dev->of_node;
0035 struct resource *res;
0036 void __iomem *base;
0037 u64 cfg;
0038 int ret;
0039
0040 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
0041 base = devm_ioremap_resource(&pdev->dev, res);
0042 if (IS_ERR(base))
0043 return PTR_ERR(base);
0044
0045 cfg = cvmx_readq_csr(base + CVMX_SATA_UCTL_SHIM_CFG);
0046
0047 cfg &= ~(SATA_UCTL_ENDIAN_MODE_MASK << SATA_UCTL_DMA_ENDIAN_MODE_SHIFT);
0048 cfg &= ~(SATA_UCTL_ENDIAN_MODE_MASK << SATA_UCTL_CSR_ENDIAN_MODE_SHIFT);
0049
0050 #ifdef __BIG_ENDIAN
0051 cfg |= SATA_UCTL_ENDIAN_MODE_BIG << SATA_UCTL_DMA_ENDIAN_MODE_SHIFT;
0052 cfg |= SATA_UCTL_ENDIAN_MODE_BIG << SATA_UCTL_CSR_ENDIAN_MODE_SHIFT;
0053 #else
0054 cfg |= SATA_UCTL_ENDIAN_MODE_LITTLE << SATA_UCTL_DMA_ENDIAN_MODE_SHIFT;
0055 cfg |= SATA_UCTL_ENDIAN_MODE_LITTLE << SATA_UCTL_CSR_ENDIAN_MODE_SHIFT;
0056 #endif
0057
0058 cfg |= 1 << SATA_UCTL_DMA_READ_CMD_SHIFT;
0059
0060 cvmx_writeq_csr(base + CVMX_SATA_UCTL_SHIM_CFG, cfg);
0061
0062 if (!node) {
0063 dev_err(dev, "no device node, failed to add octeon sata\n");
0064 return -ENODEV;
0065 }
0066
0067 ret = of_platform_populate(node, NULL, NULL, dev);
0068 if (ret) {
0069 dev_err(dev, "failed to add ahci-platform core\n");
0070 return ret;
0071 }
0072
0073 return 0;
0074 }
0075
0076 static int ahci_octeon_remove(struct platform_device *pdev)
0077 {
0078 return 0;
0079 }
0080
0081 static const struct of_device_id octeon_ahci_match[] = {
0082 { .compatible = "cavium,octeon-7130-sata-uctl", },
0083 { }
0084 };
0085 MODULE_DEVICE_TABLE(of, octeon_ahci_match);
0086
0087 static struct platform_driver ahci_octeon_driver = {
0088 .probe = ahci_octeon_probe,
0089 .remove = ahci_octeon_remove,
0090 .driver = {
0091 .name = "octeon-ahci",
0092 .of_match_table = octeon_ahci_match,
0093 },
0094 };
0095
0096 module_platform_driver(ahci_octeon_driver);
0097
0098 MODULE_LICENSE("GPL");
0099 MODULE_AUTHOR("Cavium, Inc. <support@cavium.com>");
0100 MODULE_DESCRIPTION("Cavium Inc. sata config.");