^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-or-later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) // Copyright (C) IBM Corporation 2018
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) // FSI master driver for AST2600
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) #include <linux/clk.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) #include <linux/delay.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #include <linux/fsi.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <linux/io.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <linux/mfd/syscon.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/mutex.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/of.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/platform_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/regmap.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <linux/iopoll.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <linux/gpio/consumer.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include "fsi-master.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) struct fsi_master_aspeed {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) struct fsi_master master;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) struct mutex lock; /* protect HW access */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) struct device *dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) void __iomem *base;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) struct clk *clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) struct gpio_desc *cfam_reset_gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #define to_fsi_master_aspeed(m) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) container_of(m, struct fsi_master_aspeed, master)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) /* Control register (size 0x400) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) static const u32 ctrl_base = 0x80000000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) static const u32 fsi_base = 0xa0000000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) #define OPB_FSI_VER 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) #define OPB_TRIGGER 0x04
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) #define OPB_CTRL_BASE 0x08
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) #define OPB_FSI_BASE 0x0c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) #define OPB_CLK_SYNC 0x3c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) #define OPB_IRQ_CLEAR 0x40
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) #define OPB_IRQ_MASK 0x44
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) #define OPB_IRQ_STATUS 0x48
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) #define OPB0_SELECT 0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) #define OPB0_RW 0x14
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) #define OPB0_XFER_SIZE 0x18
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) #define OPB0_FSI_ADDR 0x1c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) #define OPB0_FSI_DATA_W 0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) #define OPB0_STATUS 0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) #define OPB0_FSI_DATA_R 0x84
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) #define OPB0_WRITE_ORDER1 0x4c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) #define OPB0_WRITE_ORDER2 0x50
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) #define OPB1_WRITE_ORDER1 0x54
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) #define OPB1_WRITE_ORDER2 0x58
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) #define OPB0_READ_ORDER1 0x5c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) #define OPB1_READ_ORDER2 0x60
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) #define OPB_RETRY_COUNTER 0x64
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) /* OPBn_STATUS */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) #define STATUS_HALFWORD_ACK BIT(0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) #define STATUS_FULLWORD_ACK BIT(1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) #define STATUS_ERR_ACK BIT(2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) #define STATUS_RETRY BIT(3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) #define STATUS_TIMEOUT BIT(4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) /* OPB_IRQ_MASK */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) #define OPB1_XFER_ACK_EN BIT(17)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) #define OPB0_XFER_ACK_EN BIT(16)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) /* OPB_RW */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) #define CMD_READ BIT(0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) #define CMD_WRITE 0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) /* OPBx_XFER_SIZE */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) #define XFER_FULLWORD (BIT(1) | BIT(0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) #define XFER_HALFWORD (BIT(0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) #define XFER_BYTE (0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) #define CREATE_TRACE_POINTS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) #include <trace/events/fsi_master_aspeed.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) #define FSI_LINK_ENABLE_SETUP_TIME 10 /* in mS */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) /* Run the bus at maximum speed by default */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) #define FSI_DIVISOR_DEFAULT 1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) #define FSI_DIVISOR_CABLED 2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) static u16 aspeed_fsi_divisor = FSI_DIVISOR_DEFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) module_param_named(bus_div,aspeed_fsi_divisor, ushort, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) #define OPB_POLL_TIMEOUT 10000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) static int __opb_write(struct fsi_master_aspeed *aspeed, u32 addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) u32 val, u32 transfer_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) void __iomem *base = aspeed->base;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) u32 reg, status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) writel(CMD_WRITE, base + OPB0_RW);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) writel(transfer_size, base + OPB0_XFER_SIZE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) writel(addr, base + OPB0_FSI_ADDR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) writel(val, base + OPB0_FSI_DATA_W);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) writel(0x1, base + OPB_IRQ_CLEAR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) writel(0x1, base + OPB_TRIGGER);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) ret = readl_poll_timeout(base + OPB_IRQ_STATUS, reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) (reg & OPB0_XFER_ACK_EN) != 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 0, OPB_POLL_TIMEOUT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) status = readl(base + OPB0_STATUS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) trace_fsi_master_aspeed_opb_write(addr, val, transfer_size, status, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) /* Return error when poll timed out */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) /* Command failed, master will reset */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) if (status & STATUS_ERR_ACK)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) return -EIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) static int opb_writeb(struct fsi_master_aspeed *aspeed, u32 addr, u8 val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) return __opb_write(aspeed, addr, val, XFER_BYTE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) static int opb_writew(struct fsi_master_aspeed *aspeed, u32 addr, __be16 val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) return __opb_write(aspeed, addr, (__force u16)val, XFER_HALFWORD);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) static int opb_writel(struct fsi_master_aspeed *aspeed, u32 addr, __be32 val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) return __opb_write(aspeed, addr, (__force u32)val, XFER_FULLWORD);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) static int __opb_read(struct fsi_master_aspeed *aspeed, uint32_t addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) u32 transfer_size, void *out)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) void __iomem *base = aspeed->base;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) u32 result, reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) int status, ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) writel(CMD_READ, base + OPB0_RW);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) writel(transfer_size, base + OPB0_XFER_SIZE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) writel(addr, base + OPB0_FSI_ADDR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) writel(0x1, base + OPB_IRQ_CLEAR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) writel(0x1, base + OPB_TRIGGER);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) ret = readl_poll_timeout(base + OPB_IRQ_STATUS, reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) (reg & OPB0_XFER_ACK_EN) != 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 0, OPB_POLL_TIMEOUT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) status = readl(base + OPB0_STATUS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) result = readl(base + OPB0_FSI_DATA_R);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) trace_fsi_master_aspeed_opb_read(addr, transfer_size, result,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) readl(base + OPB0_STATUS),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) /* Return error when poll timed out */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) /* Command failed, master will reset */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) if (status & STATUS_ERR_ACK)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) return -EIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) if (out) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) switch (transfer_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) case XFER_BYTE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) *(u8 *)out = result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) case XFER_HALFWORD:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) *(u16 *)out = result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) case XFER_FULLWORD:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) *(u32 *)out = result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) static int opb_readl(struct fsi_master_aspeed *aspeed, uint32_t addr, __be32 *out)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) return __opb_read(aspeed, addr, XFER_FULLWORD, out);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) static int opb_readw(struct fsi_master_aspeed *aspeed, uint32_t addr, __be16 *out)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) return __opb_read(aspeed, addr, XFER_HALFWORD, (void *)out);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) static int opb_readb(struct fsi_master_aspeed *aspeed, uint32_t addr, u8 *out)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) return __opb_read(aspeed, addr, XFER_BYTE, (void *)out);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) static int check_errors(struct fsi_master_aspeed *aspeed, int err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) if (trace_fsi_master_aspeed_opb_error_enabled()) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) __be32 mresp0, mstap0, mesrb0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) opb_readl(aspeed, ctrl_base + FSI_MRESP0, &mresp0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) opb_readl(aspeed, ctrl_base + FSI_MSTAP0, &mstap0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) opb_readl(aspeed, ctrl_base + FSI_MESRB0, &mesrb0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) trace_fsi_master_aspeed_opb_error(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) be32_to_cpu(mresp0),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) be32_to_cpu(mstap0),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) be32_to_cpu(mesrb0));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) if (err == -EIO) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) /* Check MAEB (0x70) ? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) /* Then clear errors in master */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) ret = opb_writel(aspeed, ctrl_base + FSI_MRESP0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) cpu_to_be32(FSI_MRESP_RST_ALL_MASTER));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) /* TODO: log? return different code? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) /* TODO: confirm that 0x70 was okay */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) /* This will pass through timeout errors */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) static int aspeed_master_read(struct fsi_master *master, int link,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) uint8_t id, uint32_t addr, void *val, size_t size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) struct fsi_master_aspeed *aspeed = to_fsi_master_aspeed(master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) if (id > 0x3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) addr |= id << 21;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) addr += link * FSI_HUB_LINK_SIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) mutex_lock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) switch (size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) case 1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) ret = opb_readb(aspeed, fsi_base + addr, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) case 2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) ret = opb_readw(aspeed, fsi_base + addr, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) case 4:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) ret = opb_readl(aspeed, fsi_base + addr, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) goto done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) ret = check_errors(aspeed, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) done:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) mutex_unlock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) static int aspeed_master_write(struct fsi_master *master, int link,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) uint8_t id, uint32_t addr, const void *val, size_t size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) struct fsi_master_aspeed *aspeed = to_fsi_master_aspeed(master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) if (id > 0x3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) addr |= id << 21;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) addr += link * FSI_HUB_LINK_SIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) mutex_lock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) switch (size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) case 1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) ret = opb_writeb(aspeed, fsi_base + addr, *(u8 *)val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) case 2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) ret = opb_writew(aspeed, fsi_base + addr, *(__be16 *)val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) case 4:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) ret = opb_writel(aspeed, fsi_base + addr, *(__be32 *)val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) goto done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) ret = check_errors(aspeed, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) done:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) mutex_unlock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) static int aspeed_master_link_enable(struct fsi_master *master, int link,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) bool enable)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) struct fsi_master_aspeed *aspeed = to_fsi_master_aspeed(master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) int idx, bit, ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) __be32 reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) idx = link / 32;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) bit = link % 32;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) reg = cpu_to_be32(0x80000000 >> bit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) mutex_lock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) if (!enable) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) ret = opb_writel(aspeed, ctrl_base + FSI_MCENP0 + (4 * idx), reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) goto done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) ret = opb_writel(aspeed, ctrl_base + FSI_MSENP0 + (4 * idx), reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) goto done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) mdelay(FSI_LINK_ENABLE_SETUP_TIME);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) done:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) mutex_unlock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) static int aspeed_master_term(struct fsi_master *master, int link, uint8_t id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) uint32_t addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) __be32 cmd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) addr = 0x4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) cmd = cpu_to_be32(0xecc00000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) return aspeed_master_write(master, link, id, addr, &cmd, 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) static int aspeed_master_break(struct fsi_master *master, int link)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) uint32_t addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) __be32 cmd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) addr = 0x0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) cmd = cpu_to_be32(0xc0de0000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) return aspeed_master_write(master, link, 0, addr, &cmd, 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) static void aspeed_master_release(struct device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) struct fsi_master_aspeed *aspeed =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) to_fsi_master_aspeed(dev_to_fsi_master(dev));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) kfree(aspeed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) /* mmode encoders */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) static inline u32 fsi_mmode_crs0(u32 x)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) return (x & FSI_MMODE_CRS0MASK) << FSI_MMODE_CRS0SHFT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) static inline u32 fsi_mmode_crs1(u32 x)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) return (x & FSI_MMODE_CRS1MASK) << FSI_MMODE_CRS1SHFT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) static int aspeed_master_init(struct fsi_master_aspeed *aspeed)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) __be32 reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) reg = cpu_to_be32(FSI_MRESP_RST_ALL_MASTER | FSI_MRESP_RST_ALL_LINK
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) | FSI_MRESP_RST_MCR | FSI_MRESP_RST_PYE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) opb_writel(aspeed, ctrl_base + FSI_MRESP0, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) /* Initialize the MFSI (hub master) engine */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) reg = cpu_to_be32(FSI_MRESP_RST_ALL_MASTER | FSI_MRESP_RST_ALL_LINK
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) | FSI_MRESP_RST_MCR | FSI_MRESP_RST_PYE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) opb_writel(aspeed, ctrl_base + FSI_MRESP0, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) reg = cpu_to_be32(FSI_MECTRL_EOAE | FSI_MECTRL_P8_AUTO_TERM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) opb_writel(aspeed, ctrl_base + FSI_MECTRL, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) reg = cpu_to_be32(FSI_MMODE_ECRC | FSI_MMODE_EPC | FSI_MMODE_RELA
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) | fsi_mmode_crs0(aspeed_fsi_divisor)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) | fsi_mmode_crs1(aspeed_fsi_divisor)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) | FSI_MMODE_P8_TO_LSB);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) dev_info(aspeed->dev, "mmode set to %08x (divisor %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) be32_to_cpu(reg), aspeed_fsi_divisor);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) opb_writel(aspeed, ctrl_base + FSI_MMODE, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) reg = cpu_to_be32(0xffff0000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) opb_writel(aspeed, ctrl_base + FSI_MDLYR, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) reg = cpu_to_be32(~0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) opb_writel(aspeed, ctrl_base + FSI_MSENP0, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) /* Leave enabled long enough for master logic to set up */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) mdelay(FSI_LINK_ENABLE_SETUP_TIME);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) opb_writel(aspeed, ctrl_base + FSI_MCENP0, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) opb_readl(aspeed, ctrl_base + FSI_MAEB, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) reg = cpu_to_be32(FSI_MRESP_RST_ALL_MASTER | FSI_MRESP_RST_ALL_LINK);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) opb_writel(aspeed, ctrl_base + FSI_MRESP0, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) opb_readl(aspeed, ctrl_base + FSI_MLEVP0, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) /* Reset the master bridge */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) reg = cpu_to_be32(FSI_MRESB_RST_GEN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) opb_writel(aspeed, ctrl_base + FSI_MRESB0, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) reg = cpu_to_be32(FSI_MRESB_RST_ERR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) opb_writel(aspeed, ctrl_base + FSI_MRESB0, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) static ssize_t cfam_reset_store(struct device *dev, struct device_attribute *attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) const char *buf, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) struct fsi_master_aspeed *aspeed = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) mutex_lock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) gpiod_set_value(aspeed->cfam_reset_gpio, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) usleep_range(900, 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) gpiod_set_value(aspeed->cfam_reset_gpio, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) mutex_unlock(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) static DEVICE_ATTR(cfam_reset, 0200, NULL, cfam_reset_store);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) static int setup_cfam_reset(struct fsi_master_aspeed *aspeed)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) struct device *dev = aspeed->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) struct gpio_desc *gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) gpio = devm_gpiod_get_optional(dev, "cfam-reset", GPIOD_OUT_LOW);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) if (IS_ERR(gpio))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) return PTR_ERR(gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) if (!gpio)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) aspeed->cfam_reset_gpio = gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) rc = device_create_file(dev, &dev_attr_cfam_reset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) devm_gpiod_put(dev, gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) static int tacoma_cabled_fsi_fixup(struct device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) struct gpio_desc *routing_gpio, *mux_gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) int gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) * The routing GPIO is a jumper indicating we should mux for the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) * externally connected FSI cable.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) routing_gpio = devm_gpiod_get_optional(dev, "fsi-routing",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) GPIOD_IN | GPIOD_FLAGS_BIT_NONEXCLUSIVE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) if (IS_ERR(routing_gpio))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) return PTR_ERR(routing_gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) if (!routing_gpio)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) mux_gpio = devm_gpiod_get_optional(dev, "fsi-mux", GPIOD_ASIS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) if (IS_ERR(mux_gpio))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) return PTR_ERR(mux_gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) if (!mux_gpio)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) gpio = gpiod_get_value(routing_gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) if (gpio < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) return gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) /* If the routing GPIO is high we should set the mux to low. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) if (gpio) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) * Cable signal integrity means we should run the bus
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) * slightly slower. Do not override if a kernel param
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) * has already overridden.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) if (aspeed_fsi_divisor == FSI_DIVISOR_DEFAULT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) aspeed_fsi_divisor = FSI_DIVISOR_CABLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) gpiod_direction_output(mux_gpio, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) dev_info(dev, "FSI configured for external cable\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) gpiod_direction_output(mux_gpio, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) devm_gpiod_put(dev, routing_gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) static int fsi_master_aspeed_probe(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) struct fsi_master_aspeed *aspeed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) int rc, links, reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) __be32 raw;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) rc = tacoma_cabled_fsi_fixup(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) dev_err(&pdev->dev, "Tacoma FSI cable fixup failed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) aspeed = kzalloc(sizeof(*aspeed), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) if (!aspeed)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) aspeed->dev = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) aspeed->base = devm_platform_ioremap_resource(pdev, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) if (IS_ERR(aspeed->base)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) rc = PTR_ERR(aspeed->base);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) goto err_free_aspeed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) aspeed->clk = devm_clk_get(aspeed->dev, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) if (IS_ERR(aspeed->clk)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) dev_err(aspeed->dev, "couldn't get clock\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) rc = PTR_ERR(aspeed->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) goto err_free_aspeed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) rc = clk_prepare_enable(aspeed->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) dev_err(aspeed->dev, "couldn't enable clock\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) goto err_free_aspeed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) rc = setup_cfam_reset(aspeed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) dev_err(&pdev->dev, "CFAM reset GPIO setup failed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) writel(0x1, aspeed->base + OPB_CLK_SYNC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) writel(OPB1_XFER_ACK_EN | OPB0_XFER_ACK_EN,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) aspeed->base + OPB_IRQ_MASK);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) /* TODO: determine an appropriate value */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) writel(0x10, aspeed->base + OPB_RETRY_COUNTER);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) writel(ctrl_base, aspeed->base + OPB_CTRL_BASE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) writel(fsi_base, aspeed->base + OPB_FSI_BASE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) /* Set read data order */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) writel(0x00030b1b, aspeed->base + OPB0_READ_ORDER1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) /* Set write data order */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) writel(0x0011101b, aspeed->base + OPB0_WRITE_ORDER1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) writel(0x0c330f3f, aspeed->base + OPB0_WRITE_ORDER2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) * Select OPB0 for all operations.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) * Will need to be reworked when enabling DMA or anything that uses
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) * OPB1.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) writel(0x1, aspeed->base + OPB0_SELECT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) rc = opb_readl(aspeed, ctrl_base + FSI_MVER, &raw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) dev_err(&pdev->dev, "failed to read hub version\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) goto err_release;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) reg = be32_to_cpu(raw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) links = (reg >> 8) & 0xff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) dev_info(&pdev->dev, "hub version %08x (%d links)\n", reg, links);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) aspeed->master.dev.parent = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) aspeed->master.dev.release = aspeed_master_release;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) aspeed->master.dev.of_node = of_node_get(dev_of_node(&pdev->dev));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) aspeed->master.n_links = links;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) aspeed->master.read = aspeed_master_read;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) aspeed->master.write = aspeed_master_write;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) aspeed->master.send_break = aspeed_master_break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) aspeed->master.term = aspeed_master_term;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) aspeed->master.link_enable = aspeed_master_link_enable;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) dev_set_drvdata(&pdev->dev, aspeed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) mutex_init(&aspeed->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) aspeed_master_init(aspeed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) rc = fsi_master_register(&aspeed->master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) if (rc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) goto err_release;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) /* At this point, fsi_master_register performs the device_initialize(),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) * and holds the sole reference on master.dev. This means the device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) * will be freed (via ->release) during any subsequent call to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) * fsi_master_unregister. We add our own reference to it here, so we
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) * can perform cleanup (in _remove()) without it being freed before
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) * we're ready.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) get_device(&aspeed->master.dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) err_release:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) clk_disable_unprepare(aspeed->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) err_free_aspeed:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) kfree(aspeed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) static int fsi_master_aspeed_remove(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) struct fsi_master_aspeed *aspeed = platform_get_drvdata(pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) fsi_master_unregister(&aspeed->master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) clk_disable_unprepare(aspeed->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) static const struct of_device_id fsi_master_aspeed_match[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) { .compatible = "aspeed,ast2600-fsi-master" },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) { },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) MODULE_DEVICE_TABLE(of, fsi_master_aspeed_match);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) static struct platform_driver fsi_master_aspeed_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) .driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) .name = "fsi-master-aspeed",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) .of_match_table = fsi_master_aspeed_match,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) .probe = fsi_master_aspeed_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) .remove = fsi_master_aspeed_remove,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) module_platform_driver(fsi_master_aspeed_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) MODULE_LICENSE("GPL");