1 /* SPDX-License-Identifier: GPL-2.0 */ 2 /* 3 * Cedrus VPU driver 4 * 5 * Copyright (C) 2016 Florent Revest <florent.revest@free-electrons.com> 6 * Copyright (C) 2018 Paul Kocialkowski <paul.kocialkowski@bootlin.com> 7 * Copyright (C) 2018 Bootlin 8 * 9 * Based on the vim2m driver, that is: 10 * 11 * Copyright (c) 2009-2010 Samsung Electronics Co., Ltd. 12 * Pawel Osciak, <pawel@osciak.com> 13 * Marek Szyprowski, <m.szyprowski@samsung.com> 14 */ 15 16 #ifndef _CEDRUS_H_ 17 #define _CEDRUS_H_ 18 19 #include <media/v4l2-ctrls.h> 20 #include <media/v4l2-device.h> 21 #include <media/v4l2-mem2mem.h> 22 #include <media/videobuf2-v4l2.h> 23 #include <media/videobuf2-dma-contig.h> 24 25 #include <linux/platform_device.h> 26 27 #define CEDRUS_NAME "cedrus" 28 29 #define CEDRUS_CAPABILITY_UNTILED BIT(0) 30 31 #define CEDRUS_QUIRK_NO_DMA_OFFSET BIT(0) 32 33 enum cedrus_codec { 34 CEDRUS_CODEC_MPEG2, 35 36 CEDRUS_CODEC_LAST, 37 }; 38 39 enum cedrus_irq_status { 40 CEDRUS_IRQ_NONE, 41 CEDRUS_IRQ_ERROR, 42 CEDRUS_IRQ_OK, 43 }; 44 45 struct cedrus_control { 46 u32 id; 47 u32 elem_size; 48 enum cedrus_codec codec; 49 unsigned char required:1; 50 }; 51 52 struct cedrus_mpeg2_run { 53 const struct v4l2_ctrl_mpeg2_slice_params *slice_params; 54 const struct v4l2_ctrl_mpeg2_quantization *quantization; 55 }; 56 57 struct cedrus_run { 58 struct vb2_v4l2_buffer *src; 59 struct vb2_v4l2_buffer *dst; 60 61 union { 62 struct cedrus_mpeg2_run mpeg2; 63 }; 64 }; 65 66 struct cedrus_buffer { 67 struct v4l2_m2m_buffer m2m_buf; 68 }; 69 70 struct cedrus_ctx { 71 struct v4l2_fh fh; 72 struct cedrus_dev *dev; 73 74 struct v4l2_pix_format src_fmt; 75 struct v4l2_pix_format dst_fmt; 76 enum cedrus_codec current_codec; 77 78 struct v4l2_ctrl_handler hdl; 79 struct v4l2_ctrl **ctrls; 80 81 struct vb2_buffer *dst_bufs[VIDEO_MAX_FRAME]; 82 }; 83 84 struct cedrus_dec_ops { 85 void (*irq_clear)(struct cedrus_ctx *ctx); 86 void (*irq_disable)(struct cedrus_ctx *ctx); 87 enum cedrus_irq_status (*irq_status)(struct cedrus_ctx *ctx); 88 void (*setup)(struct cedrus_ctx *ctx, struct cedrus_run *run); 89 int (*start)(struct cedrus_ctx *ctx); 90 void (*stop)(struct cedrus_ctx *ctx); 91 void (*trigger)(struct cedrus_ctx *ctx); 92 }; 93 94 struct cedrus_variant { 95 unsigned int capabilities; 96 unsigned int quirks; 97 }; 98 99 struct cedrus_dev { 100 struct v4l2_device v4l2_dev; 101 struct video_device vfd; 102 struct media_device mdev; 103 struct media_pad pad[2]; 104 struct platform_device *pdev; 105 struct device *dev; 106 struct v4l2_m2m_dev *m2m_dev; 107 struct cedrus_dec_ops *dec_ops[CEDRUS_CODEC_LAST]; 108 109 /* Device file mutex */ 110 struct mutex dev_mutex; 111 112 void __iomem *base; 113 114 struct clk *mod_clk; 115 struct clk *ahb_clk; 116 struct clk *ram_clk; 117 118 struct reset_control *rstc; 119 120 unsigned int capabilities; 121 }; 122 123 extern struct cedrus_dec_ops cedrus_dec_ops_mpeg2; 124 125 static inline void cedrus_write(struct cedrus_dev *dev, u32 reg, u32 val) 126 { 127 writel(val, dev->base + reg); 128 } 129 130 static inline u32 cedrus_read(struct cedrus_dev *dev, u32 reg) 131 { 132 return readl(dev->base + reg); 133 } 134 135 static inline dma_addr_t cedrus_buf_addr(struct vb2_buffer *buf, 136 struct v4l2_pix_format *pix_fmt, 137 unsigned int plane) 138 { 139 dma_addr_t addr = vb2_dma_contig_plane_dma_addr(buf, 0); 140 141 return addr + (pix_fmt ? (dma_addr_t)pix_fmt->bytesperline * 142 pix_fmt->height * plane : 0); 143 } 144 145 static inline dma_addr_t cedrus_dst_buf_addr(struct cedrus_ctx *ctx, 146 int index, unsigned int plane) 147 { 148 struct vb2_buffer *buf; 149 150 if (index < 0) 151 return 0; 152 153 buf = ctx->dst_bufs[index]; 154 return buf ? cedrus_buf_addr(buf, &ctx->dst_fmt, plane) : 0; 155 } 156 157 static inline struct cedrus_buffer * 158 vb2_v4l2_to_cedrus_buffer(const struct vb2_v4l2_buffer *p) 159 { 160 return container_of(p, struct cedrus_buffer, m2m_buf.vb); 161 } 162 163 static inline struct cedrus_buffer * 164 vb2_to_cedrus_buffer(const struct vb2_buffer *p) 165 { 166 return vb2_v4l2_to_cedrus_buffer(to_vb2_v4l2_buffer(p)); 167 } 168 169 void *cedrus_find_control_data(struct cedrus_ctx *ctx, u32 id); 170 171 #endif 172