Back to home page

OSCL-LXR

 
 

    


0001 /* SPDX-License-Identifier: GPL-2.0-or-later */
0002 /*
0003  * DMA driver header for STMicroelectronics STi FDMA controller
0004  *
0005  * Copyright (C) 2014 STMicroelectronics
0006  *
0007  * Author: Ludovic Barre <Ludovic.barre@st.com>
0008  */
0009 #ifndef __DMA_ST_FDMA_H
0010 #define __DMA_ST_FDMA_H
0011 
0012 #include <linux/dmaengine.h>
0013 #include <linux/dmapool.h>
0014 #include <linux/io.h>
0015 #include <linux/remoteproc/st_slim_rproc.h>
0016 #include "virt-dma.h"
0017 
0018 #define ST_FDMA_NR_DREQS 32
0019 #define FW_NAME_SIZE 30
0020 #define DRIVER_NAME "st-fdma"
0021 
0022 /**
0023  * struct st_fdma_generic_node - Free running/paced generic node
0024  *
0025  * @length: Length in bytes of a line in a 2D mem to mem
0026  * @sstride: Stride, in bytes, between source lines in a 2D data move
0027  * @dstride: Stride, in bytes, between destination lines in a 2D data move
0028  */
0029 struct st_fdma_generic_node {
0030     u32 length;
0031     u32 sstride;
0032     u32 dstride;
0033 };
0034 
0035 /**
0036  * struct st_fdma_hw_node - Node structure used by fdma hw
0037  *
0038  * @next: Pointer to next node
0039  * @control: Transfer Control Parameters
0040  * @nbytes: Number of Bytes to read
0041  * @saddr: Source address
0042  * @daddr: Destination address
0043  *
0044  * @generic: generic node for free running/paced transfert type
0045  * 2 others transfert type are possible, but not yet implemented
0046  *
0047  * The NODE structures must be aligned to a 32 byte boundary
0048  */
0049 struct st_fdma_hw_node {
0050     u32 next;
0051     u32 control;
0052     u32 nbytes;
0053     u32 saddr;
0054     u32 daddr;
0055     union {
0056         struct st_fdma_generic_node generic;
0057     };
0058 } __aligned(32);
0059 
0060 /*
0061  * node control parameters
0062  */
0063 #define FDMA_NODE_CTRL_REQ_MAP_MASK GENMASK(4, 0)
0064 #define FDMA_NODE_CTRL_REQ_MAP_FREE_RUN 0x0
0065 #define FDMA_NODE_CTRL_REQ_MAP_DREQ(n)  ((n)&FDMA_NODE_CTRL_REQ_MAP_MASK)
0066 #define FDMA_NODE_CTRL_REQ_MAP_EXT      FDMA_NODE_CTRL_REQ_MAP_MASK
0067 #define FDMA_NODE_CTRL_SRC_MASK     GENMASK(6, 5)
0068 #define FDMA_NODE_CTRL_SRC_STATIC   BIT(5)
0069 #define FDMA_NODE_CTRL_SRC_INCR     BIT(6)
0070 #define FDMA_NODE_CTRL_DST_MASK     GENMASK(8, 7)
0071 #define FDMA_NODE_CTRL_DST_STATIC   BIT(7)
0072 #define FDMA_NODE_CTRL_DST_INCR     BIT(8)
0073 #define FDMA_NODE_CTRL_SECURE       BIT(15)
0074 #define FDMA_NODE_CTRL_PAUSE_EON    BIT(30)
0075 #define FDMA_NODE_CTRL_INT_EON      BIT(31)
0076 
0077 /**
0078  * struct st_fdma_sw_node - descriptor structure for link list
0079  *
0080  * @pdesc: Physical address of desc
0081  * @node: link used for putting this into a channel queue
0082  */
0083 struct st_fdma_sw_node {
0084     dma_addr_t pdesc;
0085     struct st_fdma_hw_node *desc;
0086 };
0087 
0088 #define NAME_SZ 10
0089 
0090 struct st_fdma_driverdata {
0091     u32 id;
0092     char name[NAME_SZ];
0093 };
0094 
0095 struct st_fdma_desc {
0096     struct virt_dma_desc vdesc;
0097     struct st_fdma_chan *fchan;
0098     bool iscyclic;
0099     unsigned int n_nodes;
0100     struct st_fdma_sw_node node[];
0101 };
0102 
0103 enum st_fdma_type {
0104     ST_FDMA_TYPE_FREE_RUN,
0105     ST_FDMA_TYPE_PACED,
0106 };
0107 
0108 struct st_fdma_cfg {
0109     struct device_node *of_node;
0110     enum st_fdma_type type;
0111     dma_addr_t dev_addr;
0112     enum dma_transfer_direction dir;
0113     int req_line; /* request line */
0114     long req_ctrl; /* Request control */
0115 };
0116 
0117 struct st_fdma_chan {
0118     struct st_fdma_dev *fdev;
0119     struct dma_pool *node_pool;
0120     struct dma_slave_config scfg;
0121     struct st_fdma_cfg cfg;
0122 
0123     int dreq_line;
0124 
0125     struct virt_dma_chan vchan;
0126     struct st_fdma_desc *fdesc;
0127     enum dma_status status;
0128 };
0129 
0130 struct st_fdma_dev {
0131     struct device *dev;
0132     const struct st_fdma_driverdata *drvdata;
0133     struct dma_device dma_device;
0134 
0135     struct st_slim_rproc *slim_rproc;
0136 
0137     int irq;
0138 
0139     struct st_fdma_chan *chans;
0140 
0141     spinlock_t dreq_lock;
0142     unsigned long dreq_mask;
0143 
0144     u32 nr_channels;
0145     char fw_name[FW_NAME_SIZE];
0146 };
0147 
0148 /* Peripheral Registers*/
0149 
0150 #define FDMA_CMD_STA_OFST   0xFC0
0151 #define FDMA_CMD_SET_OFST   0xFC4
0152 #define FDMA_CMD_CLR_OFST   0xFC8
0153 #define FDMA_CMD_MASK_OFST  0xFCC
0154 #define FDMA_CMD_START(ch)      (0x1 << (ch << 1))
0155 #define FDMA_CMD_PAUSE(ch)      (0x2 << (ch << 1))
0156 #define FDMA_CMD_FLUSH(ch)      (0x3 << (ch << 1))
0157 
0158 #define FDMA_INT_STA_OFST   0xFD0
0159 #define FDMA_INT_STA_CH         0x1
0160 #define FDMA_INT_STA_ERR        0x2
0161 
0162 #define FDMA_INT_SET_OFST   0xFD4
0163 #define FDMA_INT_CLR_OFST   0xFD8
0164 #define FDMA_INT_MASK_OFST  0xFDC
0165 
0166 #define fdma_read(fdev, name) \
0167     readl((fdev)->slim_rproc->peri + name)
0168 
0169 #define fdma_write(fdev, val, name) \
0170     writel((val), (fdev)->slim_rproc->peri + name)
0171 
0172 /* fchan interface (dmem) */
0173 #define FDMA_CH_CMD_OFST    0x200
0174 #define FDMA_CH_CMD_STA_MASK        GENMASK(1, 0)
0175 #define FDMA_CH_CMD_STA_IDLE        (0x0)
0176 #define FDMA_CH_CMD_STA_START       (0x1)
0177 #define FDMA_CH_CMD_STA_RUNNING     (0x2)
0178 #define FDMA_CH_CMD_STA_PAUSED      (0x3)
0179 #define FDMA_CH_CMD_ERR_MASK        GENMASK(4, 2)
0180 #define FDMA_CH_CMD_ERR_INT     (0x0 << 2)
0181 #define FDMA_CH_CMD_ERR_NAND        (0x1 << 2)
0182 #define FDMA_CH_CMD_ERR_MCHI        (0x2 << 2)
0183 #define FDMA_CH_CMD_DATA_MASK       GENMASK(31, 5)
0184 #define fchan_read(fchan, name) \
0185     readl((fchan)->fdev->slim_rproc->mem[ST_SLIM_DMEM].cpu_addr \
0186             + (fchan)->vchan.chan.chan_id * 0x4 \
0187             + name)
0188 
0189 #define fchan_write(fchan, val, name) \
0190     writel((val), (fchan)->fdev->slim_rproc->mem[ST_SLIM_DMEM].cpu_addr \
0191             + (fchan)->vchan.chan.chan_id * 0x4 \
0192             + name)
0193 
0194 /* req interface */
0195 #define FDMA_REQ_CTRL_OFST  0x240
0196 #define dreq_write(fchan, val, name) \
0197     writel((val), (fchan)->fdev->slim_rproc->mem[ST_SLIM_DMEM].cpu_addr \
0198             + fchan->dreq_line * 0x04 \
0199             + name)
0200 /* node interface */
0201 #define FDMA_NODE_SZ 128
0202 #define FDMA_PTRN_OFST      0x800
0203 #define FDMA_CNTN_OFST      0x808
0204 #define FDMA_SADDRN_OFST    0x80c
0205 #define FDMA_DADDRN_OFST    0x810
0206 #define fnode_read(fchan, name) \
0207     readl((fchan)->fdev->slim_rproc->mem[ST_SLIM_DMEM].cpu_addr \
0208             + (fchan)->vchan.chan.chan_id * FDMA_NODE_SZ \
0209             + name)
0210 
0211 #define fnode_write(fchan, val, name) \
0212     writel((val), (fchan)->fdev->slim_rproc->mem[ST_SLIM_DMEM].cpu_addr \
0213             + (fchan)->vchan.chan.chan_id * FDMA_NODE_SZ \
0214             + name)
0215 
0216 /*
0217  * request control bits
0218  */
0219 #define FDMA_REQ_CTRL_NUM_OPS_MASK  GENMASK(31, 24)
0220 #define FDMA_REQ_CTRL_NUM_OPS(n)    (FDMA_REQ_CTRL_NUM_OPS_MASK & \
0221                     ((n) << 24))
0222 #define FDMA_REQ_CTRL_INITIATOR_MASK    BIT(22)
0223 #define FDMA_REQ_CTRL_INIT0     (0x0 << 22)
0224 #define FDMA_REQ_CTRL_INIT1     (0x1 << 22)
0225 #define FDMA_REQ_CTRL_INC_ADDR_ON   BIT(21)
0226 #define FDMA_REQ_CTRL_DATA_SWAP_ON  BIT(17)
0227 #define FDMA_REQ_CTRL_WNR       BIT(14)
0228 #define FDMA_REQ_CTRL_OPCODE_MASK   GENMASK(7, 4)
0229 #define FDMA_REQ_CTRL_OPCODE_LD_ST1 (0x0 << 4)
0230 #define FDMA_REQ_CTRL_OPCODE_LD_ST2 (0x1 << 4)
0231 #define FDMA_REQ_CTRL_OPCODE_LD_ST4 (0x2 << 4)
0232 #define FDMA_REQ_CTRL_OPCODE_LD_ST8 (0x3 << 4)
0233 #define FDMA_REQ_CTRL_OPCODE_LD_ST16    (0x4 << 4)
0234 #define FDMA_REQ_CTRL_OPCODE_LD_ST32    (0x5 << 4)
0235 #define FDMA_REQ_CTRL_OPCODE_LD_ST64    (0x6 << 4)
0236 #define FDMA_REQ_CTRL_HOLDOFF_MASK  GENMASK(2, 0)
0237 #define FDMA_REQ_CTRL_HOLDOFF(n)    ((n) & FDMA_REQ_CTRL_HOLDOFF_MASK)
0238 
0239 /* bits used by client to configure request control */
0240 #define FDMA_REQ_CTRL_CFG_MASK (FDMA_REQ_CTRL_HOLDOFF_MASK | \
0241                 FDMA_REQ_CTRL_DATA_SWAP_ON | \
0242                 FDMA_REQ_CTRL_INC_ADDR_ON | \
0243                 FDMA_REQ_CTRL_INITIATOR_MASK)
0244 
0245 #endif  /* __DMA_ST_FDMA_H */