s5p_mfc_opr_v5.c (51516B)
1// SPDX-License-Identifier: GPL-2.0-only 2/* 3 * drivers/media/platform/samsung/mfc5/s5p_mfc_opr_v5.c 4 * 5 * Samsung MFC (Multi Function Codec - FIMV) driver 6 * This file contains hw related functions. 7 * 8 * Kamil Debski, Copyright (c) 2011 Samsung Electronics 9 * http://www.samsung.com/ 10 */ 11 12#include "s5p_mfc_common.h" 13#include "s5p_mfc_cmd.h" 14#include "s5p_mfc_ctrl.h" 15#include "s5p_mfc_debug.h" 16#include "s5p_mfc_intr.h" 17#include "s5p_mfc_pm.h" 18#include "s5p_mfc_opr.h" 19#include "s5p_mfc_opr_v5.h" 20#include <asm/cacheflush.h> 21#include <linux/delay.h> 22#include <linux/dma-mapping.h> 23#include <linux/err.h> 24#include <linux/firmware.h> 25#include <linux/io.h> 26#include <linux/jiffies.h> 27#include <linux/mm.h> 28#include <linux/sched.h> 29 30#define OFFSETA(x) (((x) - dev->dma_base[BANK_L_CTX]) >> MFC_OFFSET_SHIFT) 31#define OFFSETB(x) (((x) - dev->dma_base[BANK_R_CTX]) >> MFC_OFFSET_SHIFT) 32 33/* Allocate temporary buffers for decoding */ 34static int s5p_mfc_alloc_dec_temp_buffers_v5(struct s5p_mfc_ctx *ctx) 35{ 36 struct s5p_mfc_dev *dev = ctx->dev; 37 struct s5p_mfc_buf_size_v5 *buf_size = dev->variant->buf_size->priv; 38 int ret; 39 40 ctx->dsc.size = buf_size->dsc; 41 ret = s5p_mfc_alloc_priv_buf(dev, BANK_L_CTX, &ctx->dsc); 42 if (ret) { 43 mfc_err("Failed to allocate temporary buffer\n"); 44 return ret; 45 } 46 47 BUG_ON(ctx->dsc.dma & ((1 << MFC_BANK1_ALIGN_ORDER) - 1)); 48 memset(ctx->dsc.virt, 0, ctx->dsc.size); 49 wmb(); 50 return 0; 51} 52 53 54/* Release temporary buffers for decoding */ 55static void s5p_mfc_release_dec_desc_buffer_v5(struct s5p_mfc_ctx *ctx) 56{ 57 s5p_mfc_release_priv_buf(ctx->dev, &ctx->dsc); 58} 59 60/* Allocate codec buffers */ 61static int s5p_mfc_alloc_codec_buffers_v5(struct s5p_mfc_ctx *ctx) 62{ 63 struct s5p_mfc_dev *dev = ctx->dev; 64 unsigned int enc_ref_y_size = 0; 65 unsigned int enc_ref_c_size = 0; 66 unsigned int guard_width, guard_height; 67 int ret; 68 69 if (ctx->type == MFCINST_DECODER) { 70 mfc_debug(2, "Luma size:%d Chroma size:%d MV size:%d\n", 71 ctx->luma_size, ctx->chroma_size, ctx->mv_size); 72 mfc_debug(2, "Totals bufs: %d\n", ctx->total_dpb_count); 73 } else if (ctx->type == MFCINST_ENCODER) { 74 enc_ref_y_size = ALIGN(ctx->img_width, S5P_FIMV_NV12MT_HALIGN) 75 * ALIGN(ctx->img_height, S5P_FIMV_NV12MT_VALIGN); 76 enc_ref_y_size = ALIGN(enc_ref_y_size, S5P_FIMV_NV12MT_SALIGN); 77 78 if (ctx->codec_mode == S5P_MFC_CODEC_H264_ENC) { 79 enc_ref_c_size = ALIGN(ctx->img_width, 80 S5P_FIMV_NV12MT_HALIGN) 81 * ALIGN(ctx->img_height >> 1, 82 S5P_FIMV_NV12MT_VALIGN); 83 enc_ref_c_size = ALIGN(enc_ref_c_size, 84 S5P_FIMV_NV12MT_SALIGN); 85 } else { 86 guard_width = ALIGN(ctx->img_width + 16, 87 S5P_FIMV_NV12MT_HALIGN); 88 guard_height = ALIGN((ctx->img_height >> 1) + 4, 89 S5P_FIMV_NV12MT_VALIGN); 90 enc_ref_c_size = ALIGN(guard_width * guard_height, 91 S5P_FIMV_NV12MT_SALIGN); 92 } 93 mfc_debug(2, "recon luma size: %d chroma size: %d\n", 94 enc_ref_y_size, enc_ref_c_size); 95 } else { 96 return -EINVAL; 97 } 98 /* Codecs have different memory requirements */ 99 switch (ctx->codec_mode) { 100 case S5P_MFC_CODEC_H264_DEC: 101 ctx->bank1.size = 102 ALIGN(S5P_FIMV_DEC_NB_IP_SIZE + 103 S5P_FIMV_DEC_VERT_NB_MV_SIZE, 104 S5P_FIMV_DEC_BUF_ALIGN); 105 ctx->bank2.size = ctx->total_dpb_count * ctx->mv_size; 106 break; 107 case S5P_MFC_CODEC_MPEG4_DEC: 108 ctx->bank1.size = 109 ALIGN(S5P_FIMV_DEC_NB_DCAC_SIZE + 110 S5P_FIMV_DEC_UPNB_MV_SIZE + 111 S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE + 112 S5P_FIMV_DEC_STX_PARSER_SIZE + 113 S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE, 114 S5P_FIMV_DEC_BUF_ALIGN); 115 ctx->bank2.size = 0; 116 break; 117 case S5P_MFC_CODEC_VC1RCV_DEC: 118 case S5P_MFC_CODEC_VC1_DEC: 119 ctx->bank1.size = 120 ALIGN(S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE + 121 S5P_FIMV_DEC_UPNB_MV_SIZE + 122 S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE + 123 S5P_FIMV_DEC_NB_DCAC_SIZE + 124 3 * S5P_FIMV_DEC_VC1_BITPLANE_SIZE, 125 S5P_FIMV_DEC_BUF_ALIGN); 126 ctx->bank2.size = 0; 127 break; 128 case S5P_MFC_CODEC_MPEG2_DEC: 129 ctx->bank1.size = 0; 130 ctx->bank2.size = 0; 131 break; 132 case S5P_MFC_CODEC_H263_DEC: 133 ctx->bank1.size = 134 ALIGN(S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE + 135 S5P_FIMV_DEC_UPNB_MV_SIZE + 136 S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE + 137 S5P_FIMV_DEC_NB_DCAC_SIZE, 138 S5P_FIMV_DEC_BUF_ALIGN); 139 ctx->bank2.size = 0; 140 break; 141 case S5P_MFC_CODEC_H264_ENC: 142 ctx->bank1.size = (enc_ref_y_size * 2) + 143 S5P_FIMV_ENC_UPMV_SIZE + 144 S5P_FIMV_ENC_COLFLG_SIZE + 145 S5P_FIMV_ENC_INTRAMD_SIZE + 146 S5P_FIMV_ENC_NBORINFO_SIZE; 147 ctx->bank2.size = (enc_ref_y_size * 2) + 148 (enc_ref_c_size * 4) + 149 S5P_FIMV_ENC_INTRAPRED_SIZE; 150 break; 151 case S5P_MFC_CODEC_MPEG4_ENC: 152 ctx->bank1.size = (enc_ref_y_size * 2) + 153 S5P_FIMV_ENC_UPMV_SIZE + 154 S5P_FIMV_ENC_COLFLG_SIZE + 155 S5P_FIMV_ENC_ACDCCOEF_SIZE; 156 ctx->bank2.size = (enc_ref_y_size * 2) + 157 (enc_ref_c_size * 4); 158 break; 159 case S5P_MFC_CODEC_H263_ENC: 160 ctx->bank1.size = (enc_ref_y_size * 2) + 161 S5P_FIMV_ENC_UPMV_SIZE + 162 S5P_FIMV_ENC_ACDCCOEF_SIZE; 163 ctx->bank2.size = (enc_ref_y_size * 2) + 164 (enc_ref_c_size * 4); 165 break; 166 default: 167 break; 168 } 169 /* Allocate only if memory from bank 1 is necessary */ 170 if (ctx->bank1.size > 0) { 171 172 ret = s5p_mfc_alloc_priv_buf(dev, BANK_L_CTX, &ctx->bank1); 173 if (ret) { 174 mfc_err("Failed to allocate Bank1 temporary buffer\n"); 175 return ret; 176 } 177 BUG_ON(ctx->bank1.dma & ((1 << MFC_BANK1_ALIGN_ORDER) - 1)); 178 } 179 /* Allocate only if memory from bank 2 is necessary */ 180 if (ctx->bank2.size > 0) { 181 ret = s5p_mfc_alloc_priv_buf(dev, BANK_R_CTX, &ctx->bank2); 182 if (ret) { 183 mfc_err("Failed to allocate Bank2 temporary buffer\n"); 184 s5p_mfc_release_priv_buf(ctx->dev, &ctx->bank1); 185 return ret; 186 } 187 BUG_ON(ctx->bank2.dma & ((1 << MFC_BANK2_ALIGN_ORDER) - 1)); 188 } 189 return 0; 190} 191 192/* Release buffers allocated for codec */ 193static void s5p_mfc_release_codec_buffers_v5(struct s5p_mfc_ctx *ctx) 194{ 195 s5p_mfc_release_priv_buf(ctx->dev, &ctx->bank1); 196 s5p_mfc_release_priv_buf(ctx->dev, &ctx->bank2); 197} 198 199/* Allocate memory for instance data buffer */ 200static int s5p_mfc_alloc_instance_buffer_v5(struct s5p_mfc_ctx *ctx) 201{ 202 struct s5p_mfc_dev *dev = ctx->dev; 203 struct s5p_mfc_buf_size_v5 *buf_size = dev->variant->buf_size->priv; 204 int ret; 205 206 if (ctx->codec_mode == S5P_MFC_CODEC_H264_DEC || 207 ctx->codec_mode == S5P_MFC_CODEC_H264_ENC) 208 ctx->ctx.size = buf_size->h264_ctx; 209 else 210 ctx->ctx.size = buf_size->non_h264_ctx; 211 212 ret = s5p_mfc_alloc_priv_buf(dev, BANK_L_CTX, &ctx->ctx); 213 if (ret) { 214 mfc_err("Failed to allocate instance buffer\n"); 215 return ret; 216 } 217 ctx->ctx.ofs = OFFSETA(ctx->ctx.dma); 218 219 /* Zero content of the allocated memory */ 220 memset(ctx->ctx.virt, 0, ctx->ctx.size); 221 wmb(); 222 223 /* Initialize shared memory */ 224 ctx->shm.size = buf_size->shm; 225 ret = s5p_mfc_alloc_priv_buf(dev, BANK_L_CTX, &ctx->shm); 226 if (ret) { 227 mfc_err("Failed to allocate shared memory buffer\n"); 228 s5p_mfc_release_priv_buf(dev, &ctx->ctx); 229 return ret; 230 } 231 232 /* shared memory offset only keeps the offset from base (port a) */ 233 ctx->shm.ofs = ctx->shm.dma - dev->dma_base[BANK_L_CTX]; 234 BUG_ON(ctx->shm.ofs & ((1 << MFC_BANK1_ALIGN_ORDER) - 1)); 235 236 memset(ctx->shm.virt, 0, buf_size->shm); 237 wmb(); 238 return 0; 239} 240 241/* Release instance buffer */ 242static void s5p_mfc_release_instance_buffer_v5(struct s5p_mfc_ctx *ctx) 243{ 244 s5p_mfc_release_priv_buf(ctx->dev, &ctx->ctx); 245 s5p_mfc_release_priv_buf(ctx->dev, &ctx->shm); 246} 247 248static int s5p_mfc_alloc_dev_context_buffer_v5(struct s5p_mfc_dev *dev) 249{ 250 /* NOP */ 251 252 return 0; 253} 254 255static void s5p_mfc_release_dev_context_buffer_v5(struct s5p_mfc_dev *dev) 256{ 257 /* NOP */ 258} 259 260static void s5p_mfc_write_info_v5(struct s5p_mfc_ctx *ctx, unsigned int data, 261 unsigned int ofs) 262{ 263 *(u32 *)(ctx->shm.virt + ofs) = data; 264 wmb(); 265} 266 267static unsigned int s5p_mfc_read_info_v5(struct s5p_mfc_ctx *ctx, 268 unsigned long ofs) 269{ 270 rmb(); 271 return *(u32 *)(ctx->shm.virt + ofs); 272} 273 274static void s5p_mfc_dec_calc_dpb_size_v5(struct s5p_mfc_ctx *ctx) 275{ 276 unsigned int guard_width, guard_height; 277 278 ctx->buf_width = ALIGN(ctx->img_width, S5P_FIMV_NV12MT_HALIGN); 279 ctx->buf_height = ALIGN(ctx->img_height, S5P_FIMV_NV12MT_VALIGN); 280 mfc_debug(2, 281 "SEQ Done: Movie dimensions %dx%d, buffer dimensions: %dx%d\n", 282 ctx->img_width, ctx->img_height, ctx->buf_width, 283 ctx->buf_height); 284 285 if (ctx->codec_mode == S5P_MFC_CODEC_H264_DEC) { 286 ctx->luma_size = ALIGN(ctx->buf_width * ctx->buf_height, 287 S5P_FIMV_DEC_BUF_ALIGN); 288 ctx->chroma_size = ALIGN(ctx->buf_width * 289 ALIGN((ctx->img_height >> 1), 290 S5P_FIMV_NV12MT_VALIGN), 291 S5P_FIMV_DEC_BUF_ALIGN); 292 ctx->mv_size = ALIGN(ctx->buf_width * 293 ALIGN((ctx->buf_height >> 2), 294 S5P_FIMV_NV12MT_VALIGN), 295 S5P_FIMV_DEC_BUF_ALIGN); 296 } else { 297 guard_width = 298 ALIGN(ctx->img_width + 24, S5P_FIMV_NV12MT_HALIGN); 299 guard_height = 300 ALIGN(ctx->img_height + 16, S5P_FIMV_NV12MT_VALIGN); 301 ctx->luma_size = ALIGN(guard_width * guard_height, 302 S5P_FIMV_DEC_BUF_ALIGN); 303 304 guard_width = 305 ALIGN(ctx->img_width + 16, S5P_FIMV_NV12MT_HALIGN); 306 guard_height = 307 ALIGN((ctx->img_height >> 1) + 4, 308 S5P_FIMV_NV12MT_VALIGN); 309 ctx->chroma_size = ALIGN(guard_width * guard_height, 310 S5P_FIMV_DEC_BUF_ALIGN); 311 312 ctx->mv_size = 0; 313 } 314} 315 316static void s5p_mfc_enc_calc_src_size_v5(struct s5p_mfc_ctx *ctx) 317{ 318 if (ctx->src_fmt->fourcc == V4L2_PIX_FMT_NV12M) { 319 ctx->buf_width = ALIGN(ctx->img_width, S5P_FIMV_NV12M_HALIGN); 320 321 ctx->luma_size = ALIGN(ctx->img_width, S5P_FIMV_NV12M_HALIGN) 322 * ALIGN(ctx->img_height, S5P_FIMV_NV12M_LVALIGN); 323 ctx->chroma_size = ALIGN(ctx->img_width, S5P_FIMV_NV12M_HALIGN) 324 * ALIGN((ctx->img_height >> 1), S5P_FIMV_NV12M_CVALIGN); 325 326 ctx->luma_size = ALIGN(ctx->luma_size, S5P_FIMV_NV12M_SALIGN); 327 ctx->chroma_size = 328 ALIGN(ctx->chroma_size, S5P_FIMV_NV12M_SALIGN); 329 } else if (ctx->src_fmt->fourcc == V4L2_PIX_FMT_NV12MT) { 330 ctx->buf_width = ALIGN(ctx->img_width, S5P_FIMV_NV12MT_HALIGN); 331 332 ctx->luma_size = ALIGN(ctx->img_width, S5P_FIMV_NV12MT_HALIGN) 333 * ALIGN(ctx->img_height, S5P_FIMV_NV12MT_VALIGN); 334 ctx->chroma_size = 335 ALIGN(ctx->img_width, S5P_FIMV_NV12MT_HALIGN) 336 * ALIGN((ctx->img_height >> 1), S5P_FIMV_NV12MT_VALIGN); 337 338 ctx->luma_size = ALIGN(ctx->luma_size, S5P_FIMV_NV12MT_SALIGN); 339 ctx->chroma_size = 340 ALIGN(ctx->chroma_size, S5P_FIMV_NV12MT_SALIGN); 341 } 342} 343 344/* Set registers for decoding temporary buffers */ 345static void s5p_mfc_set_dec_desc_buffer(struct s5p_mfc_ctx *ctx) 346{ 347 struct s5p_mfc_dev *dev = ctx->dev; 348 struct s5p_mfc_buf_size_v5 *buf_size = dev->variant->buf_size->priv; 349 350 mfc_write(dev, OFFSETA(ctx->dsc.dma), S5P_FIMV_SI_CH0_DESC_ADR); 351 mfc_write(dev, buf_size->dsc, S5P_FIMV_SI_CH0_DESC_SIZE); 352} 353 354/* Set registers for shared buffer */ 355static void s5p_mfc_set_shared_buffer(struct s5p_mfc_ctx *ctx) 356{ 357 struct s5p_mfc_dev *dev = ctx->dev; 358 mfc_write(dev, ctx->shm.ofs, S5P_FIMV_SI_CH0_HOST_WR_ADR); 359} 360 361/* Set registers for decoding stream buffer */ 362static int s5p_mfc_set_dec_stream_buffer_v5(struct s5p_mfc_ctx *ctx, 363 int buf_addr, unsigned int start_num_byte, 364 unsigned int buf_size) 365{ 366 struct s5p_mfc_dev *dev = ctx->dev; 367 368 mfc_write(dev, OFFSETA(buf_addr), S5P_FIMV_SI_CH0_SB_ST_ADR); 369 mfc_write(dev, ctx->dec_src_buf_size, S5P_FIMV_SI_CH0_CPB_SIZE); 370 mfc_write(dev, buf_size, S5P_FIMV_SI_CH0_SB_FRM_SIZE); 371 s5p_mfc_write_info_v5(ctx, start_num_byte, START_BYTE_NUM); 372 return 0; 373} 374 375/* Set decoding frame buffer */ 376static int s5p_mfc_set_dec_frame_buffer_v5(struct s5p_mfc_ctx *ctx) 377{ 378 unsigned int frame_size_lu, i; 379 unsigned int frame_size_ch, frame_size_mv; 380 struct s5p_mfc_dev *dev = ctx->dev; 381 unsigned int dpb; 382 size_t buf_addr1, buf_addr2; 383 int buf_size1, buf_size2; 384 385 buf_addr1 = ctx->bank1.dma; 386 buf_size1 = ctx->bank1.size; 387 buf_addr2 = ctx->bank2.dma; 388 buf_size2 = ctx->bank2.size; 389 dpb = mfc_read(dev, S5P_FIMV_SI_CH0_DPB_CONF_CTRL) & 390 ~S5P_FIMV_DPB_COUNT_MASK; 391 mfc_write(dev, ctx->total_dpb_count | dpb, 392 S5P_FIMV_SI_CH0_DPB_CONF_CTRL); 393 s5p_mfc_set_shared_buffer(ctx); 394 switch (ctx->codec_mode) { 395 case S5P_MFC_CODEC_H264_DEC: 396 mfc_write(dev, OFFSETA(buf_addr1), 397 S5P_FIMV_H264_VERT_NB_MV_ADR); 398 buf_addr1 += S5P_FIMV_DEC_VERT_NB_MV_SIZE; 399 buf_size1 -= S5P_FIMV_DEC_VERT_NB_MV_SIZE; 400 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H264_NB_IP_ADR); 401 buf_addr1 += S5P_FIMV_DEC_NB_IP_SIZE; 402 buf_size1 -= S5P_FIMV_DEC_NB_IP_SIZE; 403 break; 404 case S5P_MFC_CODEC_MPEG4_DEC: 405 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_MPEG4_NB_DCAC_ADR); 406 buf_addr1 += S5P_FIMV_DEC_NB_DCAC_SIZE; 407 buf_size1 -= S5P_FIMV_DEC_NB_DCAC_SIZE; 408 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_MPEG4_UP_NB_MV_ADR); 409 buf_addr1 += S5P_FIMV_DEC_UPNB_MV_SIZE; 410 buf_size1 -= S5P_FIMV_DEC_UPNB_MV_SIZE; 411 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_MPEG4_SA_MV_ADR); 412 buf_addr1 += S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE; 413 buf_size1 -= S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE; 414 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_MPEG4_SP_ADR); 415 buf_addr1 += S5P_FIMV_DEC_STX_PARSER_SIZE; 416 buf_size1 -= S5P_FIMV_DEC_STX_PARSER_SIZE; 417 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_MPEG4_OT_LINE_ADR); 418 buf_addr1 += S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE; 419 buf_size1 -= S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE; 420 break; 421 case S5P_MFC_CODEC_H263_DEC: 422 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H263_OT_LINE_ADR); 423 buf_addr1 += S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE; 424 buf_size1 -= S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE; 425 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H263_UP_NB_MV_ADR); 426 buf_addr1 += S5P_FIMV_DEC_UPNB_MV_SIZE; 427 buf_size1 -= S5P_FIMV_DEC_UPNB_MV_SIZE; 428 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H263_SA_MV_ADR); 429 buf_addr1 += S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE; 430 buf_size1 -= S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE; 431 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H263_NB_DCAC_ADR); 432 buf_addr1 += S5P_FIMV_DEC_NB_DCAC_SIZE; 433 buf_size1 -= S5P_FIMV_DEC_NB_DCAC_SIZE; 434 break; 435 case S5P_MFC_CODEC_VC1_DEC: 436 case S5P_MFC_CODEC_VC1RCV_DEC: 437 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_VC1_NB_DCAC_ADR); 438 buf_addr1 += S5P_FIMV_DEC_NB_DCAC_SIZE; 439 buf_size1 -= S5P_FIMV_DEC_NB_DCAC_SIZE; 440 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_VC1_OT_LINE_ADR); 441 buf_addr1 += S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE; 442 buf_size1 -= S5P_FIMV_DEC_OVERLAP_TRANSFORM_SIZE; 443 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_VC1_UP_NB_MV_ADR); 444 buf_addr1 += S5P_FIMV_DEC_UPNB_MV_SIZE; 445 buf_size1 -= S5P_FIMV_DEC_UPNB_MV_SIZE; 446 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_VC1_SA_MV_ADR); 447 buf_addr1 += S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE; 448 buf_size1 -= S5P_FIMV_DEC_SUB_ANCHOR_MV_SIZE; 449 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_VC1_BITPLANE3_ADR); 450 buf_addr1 += S5P_FIMV_DEC_VC1_BITPLANE_SIZE; 451 buf_size1 -= S5P_FIMV_DEC_VC1_BITPLANE_SIZE; 452 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_VC1_BITPLANE2_ADR); 453 buf_addr1 += S5P_FIMV_DEC_VC1_BITPLANE_SIZE; 454 buf_size1 -= S5P_FIMV_DEC_VC1_BITPLANE_SIZE; 455 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_VC1_BITPLANE1_ADR); 456 buf_addr1 += S5P_FIMV_DEC_VC1_BITPLANE_SIZE; 457 buf_size1 -= S5P_FIMV_DEC_VC1_BITPLANE_SIZE; 458 break; 459 case S5P_MFC_CODEC_MPEG2_DEC: 460 break; 461 default: 462 mfc_err("Unknown codec for decoding (%x)\n", 463 ctx->codec_mode); 464 return -EINVAL; 465 } 466 frame_size_lu = ctx->luma_size; 467 frame_size_ch = ctx->chroma_size; 468 frame_size_mv = ctx->mv_size; 469 mfc_debug(2, "Frm size: %d ch: %d mv: %d\n", frame_size_lu, frame_size_ch, 470 frame_size_mv); 471 for (i = 0; i < ctx->total_dpb_count; i++) { 472 /* Bank2 */ 473 mfc_debug(2, "Luma %d: %zx\n", i, 474 ctx->dst_bufs[i].cookie.raw.luma); 475 mfc_write(dev, OFFSETB(ctx->dst_bufs[i].cookie.raw.luma), 476 S5P_FIMV_DEC_LUMA_ADR + i * 4); 477 mfc_debug(2, "\tChroma %d: %zx\n", i, 478 ctx->dst_bufs[i].cookie.raw.chroma); 479 mfc_write(dev, OFFSETA(ctx->dst_bufs[i].cookie.raw.chroma), 480 S5P_FIMV_DEC_CHROMA_ADR + i * 4); 481 if (ctx->codec_mode == S5P_MFC_CODEC_H264_DEC) { 482 mfc_debug(2, "\tBuf2: %zx, size: %d\n", 483 buf_addr2, buf_size2); 484 mfc_write(dev, OFFSETB(buf_addr2), 485 S5P_FIMV_H264_MV_ADR + i * 4); 486 buf_addr2 += frame_size_mv; 487 buf_size2 -= frame_size_mv; 488 } 489 } 490 mfc_debug(2, "Buf1: %zu, buf_size1: %d\n", buf_addr1, buf_size1); 491 mfc_debug(2, "Buf 1/2 size after: %d/%d (frames %d)\n", 492 buf_size1, buf_size2, ctx->total_dpb_count); 493 if (buf_size1 < 0 || buf_size2 < 0) { 494 mfc_debug(2, "Not enough memory has been allocated\n"); 495 return -ENOMEM; 496 } 497 s5p_mfc_write_info_v5(ctx, frame_size_lu, ALLOC_LUMA_DPB_SIZE); 498 s5p_mfc_write_info_v5(ctx, frame_size_ch, ALLOC_CHROMA_DPB_SIZE); 499 if (ctx->codec_mode == S5P_MFC_CODEC_H264_DEC) 500 s5p_mfc_write_info_v5(ctx, frame_size_mv, ALLOC_MV_SIZE); 501 mfc_write(dev, ((S5P_FIMV_CH_INIT_BUFS & S5P_FIMV_CH_MASK) 502 << S5P_FIMV_CH_SHIFT) | (ctx->inst_no), 503 S5P_FIMV_SI_CH0_INST_ID); 504 return 0; 505} 506 507/* Set registers for encoding stream buffer */ 508static int s5p_mfc_set_enc_stream_buffer_v5(struct s5p_mfc_ctx *ctx, 509 unsigned long addr, unsigned int size) 510{ 511 struct s5p_mfc_dev *dev = ctx->dev; 512 513 mfc_write(dev, OFFSETA(addr), S5P_FIMV_ENC_SI_CH0_SB_ADR); 514 mfc_write(dev, size, S5P_FIMV_ENC_SI_CH0_SB_SIZE); 515 return 0; 516} 517 518static void s5p_mfc_set_enc_frame_buffer_v5(struct s5p_mfc_ctx *ctx, 519 unsigned long y_addr, unsigned long c_addr) 520{ 521 struct s5p_mfc_dev *dev = ctx->dev; 522 523 mfc_write(dev, OFFSETB(y_addr), S5P_FIMV_ENC_SI_CH0_CUR_Y_ADR); 524 mfc_write(dev, OFFSETB(c_addr), S5P_FIMV_ENC_SI_CH0_CUR_C_ADR); 525} 526 527static void s5p_mfc_get_enc_frame_buffer_v5(struct s5p_mfc_ctx *ctx, 528 unsigned long *y_addr, unsigned long *c_addr) 529{ 530 struct s5p_mfc_dev *dev = ctx->dev; 531 532 *y_addr = dev->dma_base[BANK_R_CTX] + 533 (mfc_read(dev, S5P_FIMV_ENCODED_Y_ADDR) << MFC_OFFSET_SHIFT); 534 *c_addr = dev->dma_base[BANK_R_CTX] + 535 (mfc_read(dev, S5P_FIMV_ENCODED_C_ADDR) << MFC_OFFSET_SHIFT); 536} 537 538/* Set encoding ref & codec buffer */ 539static int s5p_mfc_set_enc_ref_buffer_v5(struct s5p_mfc_ctx *ctx) 540{ 541 struct s5p_mfc_dev *dev = ctx->dev; 542 size_t buf_addr1, buf_addr2; 543 size_t buf_size1, buf_size2; 544 unsigned int enc_ref_y_size, enc_ref_c_size; 545 unsigned int guard_width, guard_height; 546 int i; 547 548 buf_addr1 = ctx->bank1.dma; 549 buf_size1 = ctx->bank1.size; 550 buf_addr2 = ctx->bank2.dma; 551 buf_size2 = ctx->bank2.size; 552 enc_ref_y_size = ALIGN(ctx->img_width, S5P_FIMV_NV12MT_HALIGN) 553 * ALIGN(ctx->img_height, S5P_FIMV_NV12MT_VALIGN); 554 enc_ref_y_size = ALIGN(enc_ref_y_size, S5P_FIMV_NV12MT_SALIGN); 555 if (ctx->codec_mode == S5P_MFC_CODEC_H264_ENC) { 556 enc_ref_c_size = ALIGN(ctx->img_width, S5P_FIMV_NV12MT_HALIGN) 557 * ALIGN((ctx->img_height >> 1), S5P_FIMV_NV12MT_VALIGN); 558 enc_ref_c_size = ALIGN(enc_ref_c_size, S5P_FIMV_NV12MT_SALIGN); 559 } else { 560 guard_width = ALIGN(ctx->img_width + 16, 561 S5P_FIMV_NV12MT_HALIGN); 562 guard_height = ALIGN((ctx->img_height >> 1) + 4, 563 S5P_FIMV_NV12MT_VALIGN); 564 enc_ref_c_size = ALIGN(guard_width * guard_height, 565 S5P_FIMV_NV12MT_SALIGN); 566 } 567 mfc_debug(2, "buf_size1: %zu, buf_size2: %zu\n", buf_size1, buf_size2); 568 switch (ctx->codec_mode) { 569 case S5P_MFC_CODEC_H264_ENC: 570 for (i = 0; i < 2; i++) { 571 mfc_write(dev, OFFSETA(buf_addr1), 572 S5P_FIMV_ENC_REF0_LUMA_ADR + (4 * i)); 573 buf_addr1 += enc_ref_y_size; 574 buf_size1 -= enc_ref_y_size; 575 576 mfc_write(dev, OFFSETB(buf_addr2), 577 S5P_FIMV_ENC_REF2_LUMA_ADR + (4 * i)); 578 buf_addr2 += enc_ref_y_size; 579 buf_size2 -= enc_ref_y_size; 580 } 581 for (i = 0; i < 4; i++) { 582 mfc_write(dev, OFFSETB(buf_addr2), 583 S5P_FIMV_ENC_REF0_CHROMA_ADR + (4 * i)); 584 buf_addr2 += enc_ref_c_size; 585 buf_size2 -= enc_ref_c_size; 586 } 587 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H264_UP_MV_ADR); 588 buf_addr1 += S5P_FIMV_ENC_UPMV_SIZE; 589 buf_size1 -= S5P_FIMV_ENC_UPMV_SIZE; 590 mfc_write(dev, OFFSETA(buf_addr1), 591 S5P_FIMV_H264_COZERO_FLAG_ADR); 592 buf_addr1 += S5P_FIMV_ENC_COLFLG_SIZE; 593 buf_size1 -= S5P_FIMV_ENC_COLFLG_SIZE; 594 mfc_write(dev, OFFSETA(buf_addr1), 595 S5P_FIMV_H264_UP_INTRA_MD_ADR); 596 buf_addr1 += S5P_FIMV_ENC_INTRAMD_SIZE; 597 buf_size1 -= S5P_FIMV_ENC_INTRAMD_SIZE; 598 mfc_write(dev, OFFSETB(buf_addr2), 599 S5P_FIMV_H264_UP_INTRA_PRED_ADR); 600 buf_addr2 += S5P_FIMV_ENC_INTRAPRED_SIZE; 601 buf_size2 -= S5P_FIMV_ENC_INTRAPRED_SIZE; 602 mfc_write(dev, OFFSETA(buf_addr1), 603 S5P_FIMV_H264_NBOR_INFO_ADR); 604 buf_addr1 += S5P_FIMV_ENC_NBORINFO_SIZE; 605 buf_size1 -= S5P_FIMV_ENC_NBORINFO_SIZE; 606 mfc_debug(2, "buf_size1: %zu, buf_size2: %zu\n", 607 buf_size1, buf_size2); 608 break; 609 case S5P_MFC_CODEC_MPEG4_ENC: 610 for (i = 0; i < 2; i++) { 611 mfc_write(dev, OFFSETA(buf_addr1), 612 S5P_FIMV_ENC_REF0_LUMA_ADR + (4 * i)); 613 buf_addr1 += enc_ref_y_size; 614 buf_size1 -= enc_ref_y_size; 615 mfc_write(dev, OFFSETB(buf_addr2), 616 S5P_FIMV_ENC_REF2_LUMA_ADR + (4 * i)); 617 buf_addr2 += enc_ref_y_size; 618 buf_size2 -= enc_ref_y_size; 619 } 620 for (i = 0; i < 4; i++) { 621 mfc_write(dev, OFFSETB(buf_addr2), 622 S5P_FIMV_ENC_REF0_CHROMA_ADR + (4 * i)); 623 buf_addr2 += enc_ref_c_size; 624 buf_size2 -= enc_ref_c_size; 625 } 626 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_MPEG4_UP_MV_ADR); 627 buf_addr1 += S5P_FIMV_ENC_UPMV_SIZE; 628 buf_size1 -= S5P_FIMV_ENC_UPMV_SIZE; 629 mfc_write(dev, OFFSETA(buf_addr1), 630 S5P_FIMV_MPEG4_COZERO_FLAG_ADR); 631 buf_addr1 += S5P_FIMV_ENC_COLFLG_SIZE; 632 buf_size1 -= S5P_FIMV_ENC_COLFLG_SIZE; 633 mfc_write(dev, OFFSETA(buf_addr1), 634 S5P_FIMV_MPEG4_ACDC_COEF_ADR); 635 buf_addr1 += S5P_FIMV_ENC_ACDCCOEF_SIZE; 636 buf_size1 -= S5P_FIMV_ENC_ACDCCOEF_SIZE; 637 mfc_debug(2, "buf_size1: %zu, buf_size2: %zu\n", 638 buf_size1, buf_size2); 639 break; 640 case S5P_MFC_CODEC_H263_ENC: 641 for (i = 0; i < 2; i++) { 642 mfc_write(dev, OFFSETA(buf_addr1), 643 S5P_FIMV_ENC_REF0_LUMA_ADR + (4 * i)); 644 buf_addr1 += enc_ref_y_size; 645 buf_size1 -= enc_ref_y_size; 646 mfc_write(dev, OFFSETB(buf_addr2), 647 S5P_FIMV_ENC_REF2_LUMA_ADR + (4 * i)); 648 buf_addr2 += enc_ref_y_size; 649 buf_size2 -= enc_ref_y_size; 650 } 651 for (i = 0; i < 4; i++) { 652 mfc_write(dev, OFFSETB(buf_addr2), 653 S5P_FIMV_ENC_REF0_CHROMA_ADR + (4 * i)); 654 buf_addr2 += enc_ref_c_size; 655 buf_size2 -= enc_ref_c_size; 656 } 657 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H263_UP_MV_ADR); 658 buf_addr1 += S5P_FIMV_ENC_UPMV_SIZE; 659 buf_size1 -= S5P_FIMV_ENC_UPMV_SIZE; 660 mfc_write(dev, OFFSETA(buf_addr1), S5P_FIMV_H263_ACDC_COEF_ADR); 661 buf_addr1 += S5P_FIMV_ENC_ACDCCOEF_SIZE; 662 buf_size1 -= S5P_FIMV_ENC_ACDCCOEF_SIZE; 663 mfc_debug(2, "buf_size1: %zu, buf_size2: %zu\n", 664 buf_size1, buf_size2); 665 break; 666 default: 667 mfc_err("Unknown codec set for encoding: %d\n", 668 ctx->codec_mode); 669 return -EINVAL; 670 } 671 return 0; 672} 673 674static int s5p_mfc_set_enc_params(struct s5p_mfc_ctx *ctx) 675{ 676 struct s5p_mfc_dev *dev = ctx->dev; 677 struct s5p_mfc_enc_params *p = &ctx->enc_params; 678 unsigned int reg; 679 unsigned int shm; 680 681 /* width */ 682 mfc_write(dev, ctx->img_width, S5P_FIMV_ENC_HSIZE_PX); 683 /* height */ 684 mfc_write(dev, ctx->img_height, S5P_FIMV_ENC_VSIZE_PX); 685 /* pictype : enable, IDR period */ 686 reg = mfc_read(dev, S5P_FIMV_ENC_PIC_TYPE_CTRL); 687 reg |= (1 << 18); 688 reg &= ~(0xFFFF); 689 reg |= p->gop_size; 690 mfc_write(dev, reg, S5P_FIMV_ENC_PIC_TYPE_CTRL); 691 mfc_write(dev, 0, S5P_FIMV_ENC_B_RECON_WRITE_ON); 692 /* multi-slice control */ 693 /* multi-slice MB number or bit size */ 694 mfc_write(dev, p->slice_mode, S5P_FIMV_ENC_MSLICE_CTRL); 695 if (p->slice_mode == V4L2_MPEG_VIDEO_MULTI_SLICE_MODE_MAX_MB) { 696 mfc_write(dev, p->slice_mb, S5P_FIMV_ENC_MSLICE_MB); 697 } else if (p->slice_mode == V4L2_MPEG_VIDEO_MULTI_SLICE_MODE_MAX_BYTES) { 698 mfc_write(dev, p->slice_bit, S5P_FIMV_ENC_MSLICE_BIT); 699 } else { 700 mfc_write(dev, 0, S5P_FIMV_ENC_MSLICE_MB); 701 mfc_write(dev, 0, S5P_FIMV_ENC_MSLICE_BIT); 702 } 703 /* cyclic intra refresh */ 704 mfc_write(dev, p->intra_refresh_mb, S5P_FIMV_ENC_CIR_CTRL); 705 /* memory structure cur. frame */ 706 if (ctx->src_fmt->fourcc == V4L2_PIX_FMT_NV12M) 707 mfc_write(dev, 0, S5P_FIMV_ENC_MAP_FOR_CUR); 708 else if (ctx->src_fmt->fourcc == V4L2_PIX_FMT_NV12MT) 709 mfc_write(dev, 3, S5P_FIMV_ENC_MAP_FOR_CUR); 710 /* padding control & value */ 711 reg = mfc_read(dev, S5P_FIMV_ENC_PADDING_CTRL); 712 if (p->pad) { 713 /** enable */ 714 reg |= (1UL << 31); 715 /** cr value */ 716 reg &= ~(0xFF << 16); 717 reg |= (p->pad_cr << 16); 718 /** cb value */ 719 reg &= ~(0xFF << 8); 720 reg |= (p->pad_cb << 8); 721 /** y value */ 722 reg &= ~(0xFF); 723 reg |= (p->pad_luma); 724 } else { 725 /** disable & all value clear */ 726 reg = 0; 727 } 728 mfc_write(dev, reg, S5P_FIMV_ENC_PADDING_CTRL); 729 /* rate control config. */ 730 reg = mfc_read(dev, S5P_FIMV_ENC_RC_CONFIG); 731 /** frame-level rate control */ 732 reg &= ~(0x1 << 9); 733 reg |= (p->rc_frame << 9); 734 mfc_write(dev, reg, S5P_FIMV_ENC_RC_CONFIG); 735 /* bit rate */ 736 if (p->rc_frame) 737 mfc_write(dev, p->rc_bitrate, 738 S5P_FIMV_ENC_RC_BIT_RATE); 739 else 740 mfc_write(dev, 0, S5P_FIMV_ENC_RC_BIT_RATE); 741 /* reaction coefficient */ 742 if (p->rc_frame) 743 mfc_write(dev, p->rc_reaction_coeff, S5P_FIMV_ENC_RC_RPARA); 744 shm = s5p_mfc_read_info_v5(ctx, EXT_ENC_CONTROL); 745 /* seq header ctrl */ 746 shm &= ~(0x1 << 3); 747 shm |= (p->seq_hdr_mode << 3); 748 /* frame skip mode */ 749 shm &= ~(0x3 << 1); 750 shm |= (p->frame_skip_mode << 1); 751 s5p_mfc_write_info_v5(ctx, shm, EXT_ENC_CONTROL); 752 /* fixed target bit */ 753 s5p_mfc_write_info_v5(ctx, p->fixed_target_bit, RC_CONTROL_CONFIG); 754 return 0; 755} 756 757static int s5p_mfc_set_enc_params_h264(struct s5p_mfc_ctx *ctx) 758{ 759 struct s5p_mfc_dev *dev = ctx->dev; 760 struct s5p_mfc_enc_params *p = &ctx->enc_params; 761 struct s5p_mfc_h264_enc_params *p_264 = &p->codec.h264; 762 unsigned int reg; 763 unsigned int shm; 764 765 s5p_mfc_set_enc_params(ctx); 766 /* pictype : number of B */ 767 reg = mfc_read(dev, S5P_FIMV_ENC_PIC_TYPE_CTRL); 768 /* num_b_frame - 0 ~ 2 */ 769 reg &= ~(0x3 << 16); 770 reg |= (p->num_b_frame << 16); 771 mfc_write(dev, reg, S5P_FIMV_ENC_PIC_TYPE_CTRL); 772 /* profile & level */ 773 reg = mfc_read(dev, S5P_FIMV_ENC_PROFILE); 774 /* level */ 775 reg &= ~(0xFF << 8); 776 reg |= (p_264->level << 8); 777 /* profile - 0 ~ 2 */ 778 reg &= ~(0x3F); 779 reg |= p_264->profile; 780 mfc_write(dev, reg, S5P_FIMV_ENC_PROFILE); 781 /* interlace */ 782 mfc_write(dev, p_264->interlace, S5P_FIMV_ENC_PIC_STRUCT); 783 /* height */ 784 if (p_264->interlace) 785 mfc_write(dev, ctx->img_height >> 1, S5P_FIMV_ENC_VSIZE_PX); 786 /* loopfilter ctrl */ 787 mfc_write(dev, p_264->loop_filter_mode, S5P_FIMV_ENC_LF_CTRL); 788 /* loopfilter alpha offset */ 789 if (p_264->loop_filter_alpha < 0) { 790 reg = 0x10; 791 reg |= (0xFF - p_264->loop_filter_alpha) + 1; 792 } else { 793 reg = 0x00; 794 reg |= (p_264->loop_filter_alpha & 0xF); 795 } 796 mfc_write(dev, reg, S5P_FIMV_ENC_ALPHA_OFF); 797 /* loopfilter beta offset */ 798 if (p_264->loop_filter_beta < 0) { 799 reg = 0x10; 800 reg |= (0xFF - p_264->loop_filter_beta) + 1; 801 } else { 802 reg = 0x00; 803 reg |= (p_264->loop_filter_beta & 0xF); 804 } 805 mfc_write(dev, reg, S5P_FIMV_ENC_BETA_OFF); 806 /* entropy coding mode */ 807 if (p_264->entropy_mode == V4L2_MPEG_VIDEO_H264_ENTROPY_MODE_CABAC) 808 mfc_write(dev, 1, S5P_FIMV_ENC_H264_ENTROPY_MODE); 809 else 810 mfc_write(dev, 0, S5P_FIMV_ENC_H264_ENTROPY_MODE); 811 /* number of ref. picture */ 812 reg = mfc_read(dev, S5P_FIMV_ENC_H264_NUM_OF_REF); 813 /* num of ref. pictures of P */ 814 reg &= ~(0x3 << 5); 815 reg |= (p_264->num_ref_pic_4p << 5); 816 /* max number of ref. pictures */ 817 reg &= ~(0x1F); 818 reg |= p_264->max_ref_pic; 819 mfc_write(dev, reg, S5P_FIMV_ENC_H264_NUM_OF_REF); 820 /* 8x8 transform enable */ 821 mfc_write(dev, p_264->_8x8_transform, S5P_FIMV_ENC_H264_TRANS_FLAG); 822 /* rate control config. */ 823 reg = mfc_read(dev, S5P_FIMV_ENC_RC_CONFIG); 824 /* macroblock level rate control */ 825 reg &= ~(0x1 << 8); 826 reg |= (p->rc_mb << 8); 827 /* frame QP */ 828 reg &= ~(0x3F); 829 reg |= p_264->rc_frame_qp; 830 mfc_write(dev, reg, S5P_FIMV_ENC_RC_CONFIG); 831 /* frame rate */ 832 if (p->rc_frame && p->rc_framerate_denom) 833 mfc_write(dev, p->rc_framerate_num * 1000 834 / p->rc_framerate_denom, S5P_FIMV_ENC_RC_FRAME_RATE); 835 else 836 mfc_write(dev, 0, S5P_FIMV_ENC_RC_FRAME_RATE); 837 /* max & min value of QP */ 838 reg = mfc_read(dev, S5P_FIMV_ENC_RC_QBOUND); 839 /* max QP */ 840 reg &= ~(0x3F << 8); 841 reg |= (p_264->rc_max_qp << 8); 842 /* min QP */ 843 reg &= ~(0x3F); 844 reg |= p_264->rc_min_qp; 845 mfc_write(dev, reg, S5P_FIMV_ENC_RC_QBOUND); 846 /* macroblock adaptive scaling features */ 847 if (p->rc_mb) { 848 reg = mfc_read(dev, S5P_FIMV_ENC_RC_MB_CTRL); 849 /* dark region */ 850 reg &= ~(0x1 << 3); 851 reg |= (p_264->rc_mb_dark << 3); 852 /* smooth region */ 853 reg &= ~(0x1 << 2); 854 reg |= (p_264->rc_mb_smooth << 2); 855 /* static region */ 856 reg &= ~(0x1 << 1); 857 reg |= (p_264->rc_mb_static << 1); 858 /* high activity region */ 859 reg &= ~(0x1); 860 reg |= p_264->rc_mb_activity; 861 mfc_write(dev, reg, S5P_FIMV_ENC_RC_MB_CTRL); 862 } 863 if (!p->rc_frame && !p->rc_mb) { 864 shm = s5p_mfc_read_info_v5(ctx, P_B_FRAME_QP); 865 shm &= ~(0xFFF); 866 shm |= ((p_264->rc_b_frame_qp & 0x3F) << 6); 867 shm |= (p_264->rc_p_frame_qp & 0x3F); 868 s5p_mfc_write_info_v5(ctx, shm, P_B_FRAME_QP); 869 } 870 /* extended encoder ctrl */ 871 shm = s5p_mfc_read_info_v5(ctx, EXT_ENC_CONTROL); 872 /* AR VUI control */ 873 shm &= ~(0x1 << 15); 874 shm |= (p_264->vui_sar << 1); 875 s5p_mfc_write_info_v5(ctx, shm, EXT_ENC_CONTROL); 876 if (p_264->vui_sar) { 877 /* aspect ration IDC */ 878 shm = s5p_mfc_read_info_v5(ctx, SAMPLE_ASPECT_RATIO_IDC); 879 shm &= ~(0xFF); 880 shm |= p_264->vui_sar_idc; 881 s5p_mfc_write_info_v5(ctx, shm, SAMPLE_ASPECT_RATIO_IDC); 882 if (p_264->vui_sar_idc == 0xFF) { 883 /* sample AR info */ 884 shm = s5p_mfc_read_info_v5(ctx, EXTENDED_SAR); 885 shm &= ~(0xFFFFFFFF); 886 shm |= p_264->vui_ext_sar_width << 16; 887 shm |= p_264->vui_ext_sar_height; 888 s5p_mfc_write_info_v5(ctx, shm, EXTENDED_SAR); 889 } 890 } 891 /* intra picture period for H.264 */ 892 shm = s5p_mfc_read_info_v5(ctx, H264_I_PERIOD); 893 /* control */ 894 shm &= ~(0x1 << 16); 895 shm |= (p_264->open_gop << 16); 896 /* value */ 897 if (p_264->open_gop) { 898 shm &= ~(0xFFFF); 899 shm |= p_264->open_gop_size; 900 } 901 s5p_mfc_write_info_v5(ctx, shm, H264_I_PERIOD); 902 /* extended encoder ctrl */ 903 shm = s5p_mfc_read_info_v5(ctx, EXT_ENC_CONTROL); 904 /* vbv buffer size */ 905 if (p->frame_skip_mode == 906 V4L2_MPEG_MFC51_VIDEO_FRAME_SKIP_MODE_BUF_LIMIT) { 907 shm &= ~(0xFFFF << 16); 908 shm |= (p_264->cpb_size << 16); 909 } 910 s5p_mfc_write_info_v5(ctx, shm, EXT_ENC_CONTROL); 911 return 0; 912} 913 914static int s5p_mfc_set_enc_params_mpeg4(struct s5p_mfc_ctx *ctx) 915{ 916 struct s5p_mfc_dev *dev = ctx->dev; 917 struct s5p_mfc_enc_params *p = &ctx->enc_params; 918 struct s5p_mfc_mpeg4_enc_params *p_mpeg4 = &p->codec.mpeg4; 919 unsigned int reg; 920 unsigned int shm; 921 unsigned int framerate; 922 923 s5p_mfc_set_enc_params(ctx); 924 /* pictype : number of B */ 925 reg = mfc_read(dev, S5P_FIMV_ENC_PIC_TYPE_CTRL); 926 /* num_b_frame - 0 ~ 2 */ 927 reg &= ~(0x3 << 16); 928 reg |= (p->num_b_frame << 16); 929 mfc_write(dev, reg, S5P_FIMV_ENC_PIC_TYPE_CTRL); 930 /* profile & level */ 931 reg = mfc_read(dev, S5P_FIMV_ENC_PROFILE); 932 /* level */ 933 reg &= ~(0xFF << 8); 934 reg |= (p_mpeg4->level << 8); 935 /* profile - 0 ~ 2 */ 936 reg &= ~(0x3F); 937 reg |= p_mpeg4->profile; 938 mfc_write(dev, reg, S5P_FIMV_ENC_PROFILE); 939 /* quarter_pixel */ 940 mfc_write(dev, p_mpeg4->quarter_pixel, S5P_FIMV_ENC_MPEG4_QUART_PXL); 941 /* qp */ 942 if (!p->rc_frame) { 943 shm = s5p_mfc_read_info_v5(ctx, P_B_FRAME_QP); 944 shm &= ~(0xFFF); 945 shm |= ((p_mpeg4->rc_b_frame_qp & 0x3F) << 6); 946 shm |= (p_mpeg4->rc_p_frame_qp & 0x3F); 947 s5p_mfc_write_info_v5(ctx, shm, P_B_FRAME_QP); 948 } 949 /* frame rate */ 950 if (p->rc_frame) { 951 if (p->rc_framerate_denom > 0) { 952 framerate = p->rc_framerate_num * 1000 / 953 p->rc_framerate_denom; 954 mfc_write(dev, framerate, 955 S5P_FIMV_ENC_RC_FRAME_RATE); 956 shm = s5p_mfc_read_info_v5(ctx, RC_VOP_TIMING); 957 shm &= ~(0xFFFFFFFF); 958 shm |= (1UL << 31); 959 shm |= ((p->rc_framerate_num & 0x7FFF) << 16); 960 shm |= (p->rc_framerate_denom & 0xFFFF); 961 s5p_mfc_write_info_v5(ctx, shm, RC_VOP_TIMING); 962 } 963 } else { 964 mfc_write(dev, 0, S5P_FIMV_ENC_RC_FRAME_RATE); 965 } 966 /* rate control config. */ 967 reg = mfc_read(dev, S5P_FIMV_ENC_RC_CONFIG); 968 /* frame QP */ 969 reg &= ~(0x3F); 970 reg |= p_mpeg4->rc_frame_qp; 971 mfc_write(dev, reg, S5P_FIMV_ENC_RC_CONFIG); 972 /* max & min value of QP */ 973 reg = mfc_read(dev, S5P_FIMV_ENC_RC_QBOUND); 974 /* max QP */ 975 reg &= ~(0x3F << 8); 976 reg |= (p_mpeg4->rc_max_qp << 8); 977 /* min QP */ 978 reg &= ~(0x3F); 979 reg |= p_mpeg4->rc_min_qp; 980 mfc_write(dev, reg, S5P_FIMV_ENC_RC_QBOUND); 981 /* extended encoder ctrl */ 982 shm = s5p_mfc_read_info_v5(ctx, EXT_ENC_CONTROL); 983 /* vbv buffer size */ 984 if (p->frame_skip_mode == 985 V4L2_MPEG_MFC51_VIDEO_FRAME_SKIP_MODE_BUF_LIMIT) { 986 shm &= ~(0xFFFF << 16); 987 shm |= (p->vbv_size << 16); 988 } 989 s5p_mfc_write_info_v5(ctx, shm, EXT_ENC_CONTROL); 990 return 0; 991} 992 993static int s5p_mfc_set_enc_params_h263(struct s5p_mfc_ctx *ctx) 994{ 995 struct s5p_mfc_dev *dev = ctx->dev; 996 struct s5p_mfc_enc_params *p = &ctx->enc_params; 997 struct s5p_mfc_mpeg4_enc_params *p_h263 = &p->codec.mpeg4; 998 unsigned int reg; 999 unsigned int shm; 1000 1001 s5p_mfc_set_enc_params(ctx); 1002 /* qp */ 1003 if (!p->rc_frame) { 1004 shm = s5p_mfc_read_info_v5(ctx, P_B_FRAME_QP); 1005 shm &= ~(0xFFF); 1006 shm |= (p_h263->rc_p_frame_qp & 0x3F); 1007 s5p_mfc_write_info_v5(ctx, shm, P_B_FRAME_QP); 1008 } 1009 /* frame rate */ 1010 if (p->rc_frame && p->rc_framerate_denom) 1011 mfc_write(dev, p->rc_framerate_num * 1000 1012 / p->rc_framerate_denom, S5P_FIMV_ENC_RC_FRAME_RATE); 1013 else 1014 mfc_write(dev, 0, S5P_FIMV_ENC_RC_FRAME_RATE); 1015 /* rate control config. */ 1016 reg = mfc_read(dev, S5P_FIMV_ENC_RC_CONFIG); 1017 /* frame QP */ 1018 reg &= ~(0x3F); 1019 reg |= p_h263->rc_frame_qp; 1020 mfc_write(dev, reg, S5P_FIMV_ENC_RC_CONFIG); 1021 /* max & min value of QP */ 1022 reg = mfc_read(dev, S5P_FIMV_ENC_RC_QBOUND); 1023 /* max QP */ 1024 reg &= ~(0x3F << 8); 1025 reg |= (p_h263->rc_max_qp << 8); 1026 /* min QP */ 1027 reg &= ~(0x3F); 1028 reg |= p_h263->rc_min_qp; 1029 mfc_write(dev, reg, S5P_FIMV_ENC_RC_QBOUND); 1030 /* extended encoder ctrl */ 1031 shm = s5p_mfc_read_info_v5(ctx, EXT_ENC_CONTROL); 1032 /* vbv buffer size */ 1033 if (p->frame_skip_mode == 1034 V4L2_MPEG_MFC51_VIDEO_FRAME_SKIP_MODE_BUF_LIMIT) { 1035 shm &= ~(0xFFFF << 16); 1036 shm |= (p->vbv_size << 16); 1037 } 1038 s5p_mfc_write_info_v5(ctx, shm, EXT_ENC_CONTROL); 1039 return 0; 1040} 1041 1042/* Initialize decoding */ 1043static int s5p_mfc_init_decode_v5(struct s5p_mfc_ctx *ctx) 1044{ 1045 struct s5p_mfc_dev *dev = ctx->dev; 1046 1047 s5p_mfc_set_shared_buffer(ctx); 1048 /* Setup loop filter, for decoding this is only valid for MPEG4 */ 1049 if (ctx->codec_mode == S5P_MFC_CODEC_MPEG4_DEC) 1050 mfc_write(dev, ctx->loop_filter_mpeg4, S5P_FIMV_ENC_LF_CTRL); 1051 else 1052 mfc_write(dev, 0, S5P_FIMV_ENC_LF_CTRL); 1053 mfc_write(dev, ((ctx->slice_interface & S5P_FIMV_SLICE_INT_MASK) << 1054 S5P_FIMV_SLICE_INT_SHIFT) | (ctx->display_delay_enable << 1055 S5P_FIMV_DDELAY_ENA_SHIFT) | ((ctx->display_delay & 1056 S5P_FIMV_DDELAY_VAL_MASK) << S5P_FIMV_DDELAY_VAL_SHIFT), 1057 S5P_FIMV_SI_CH0_DPB_CONF_CTRL); 1058 mfc_write(dev, 1059 ((S5P_FIMV_CH_SEQ_HEADER & S5P_FIMV_CH_MASK) << S5P_FIMV_CH_SHIFT) 1060 | (ctx->inst_no), S5P_FIMV_SI_CH0_INST_ID); 1061 return 0; 1062} 1063 1064static void s5p_mfc_set_flush(struct s5p_mfc_ctx *ctx, int flush) 1065{ 1066 struct s5p_mfc_dev *dev = ctx->dev; 1067 unsigned int dpb; 1068 1069 if (flush) 1070 dpb = mfc_read(dev, S5P_FIMV_SI_CH0_DPB_CONF_CTRL) | ( 1071 S5P_FIMV_DPB_FLUSH_MASK << S5P_FIMV_DPB_FLUSH_SHIFT); 1072 else 1073 dpb = mfc_read(dev, S5P_FIMV_SI_CH0_DPB_CONF_CTRL) & 1074 ~(S5P_FIMV_DPB_FLUSH_MASK << S5P_FIMV_DPB_FLUSH_SHIFT); 1075 mfc_write(dev, dpb, S5P_FIMV_SI_CH0_DPB_CONF_CTRL); 1076} 1077 1078/* Decode a single frame */ 1079static int s5p_mfc_decode_one_frame_v5(struct s5p_mfc_ctx *ctx, 1080 enum s5p_mfc_decode_arg last_frame) 1081{ 1082 struct s5p_mfc_dev *dev = ctx->dev; 1083 1084 mfc_write(dev, ctx->dec_dst_flag, S5P_FIMV_SI_CH0_RELEASE_BUF); 1085 s5p_mfc_set_shared_buffer(ctx); 1086 s5p_mfc_set_flush(ctx, ctx->dpb_flush_flag); 1087 /* Issue different commands to instance basing on whether it 1088 * is the last frame or not. */ 1089 switch (last_frame) { 1090 case MFC_DEC_FRAME: 1091 mfc_write(dev, ((S5P_FIMV_CH_FRAME_START & S5P_FIMV_CH_MASK) << 1092 S5P_FIMV_CH_SHIFT) | (ctx->inst_no), S5P_FIMV_SI_CH0_INST_ID); 1093 break; 1094 case MFC_DEC_LAST_FRAME: 1095 mfc_write(dev, ((S5P_FIMV_CH_LAST_FRAME & S5P_FIMV_CH_MASK) << 1096 S5P_FIMV_CH_SHIFT) | (ctx->inst_no), S5P_FIMV_SI_CH0_INST_ID); 1097 break; 1098 case MFC_DEC_RES_CHANGE: 1099 mfc_write(dev, ((S5P_FIMV_CH_FRAME_START_REALLOC & 1100 S5P_FIMV_CH_MASK) << S5P_FIMV_CH_SHIFT) | (ctx->inst_no), 1101 S5P_FIMV_SI_CH0_INST_ID); 1102 break; 1103 } 1104 mfc_debug(2, "Decoding a usual frame\n"); 1105 return 0; 1106} 1107 1108static int s5p_mfc_init_encode_v5(struct s5p_mfc_ctx *ctx) 1109{ 1110 struct s5p_mfc_dev *dev = ctx->dev; 1111 1112 if (ctx->codec_mode == S5P_MFC_CODEC_H264_ENC) 1113 s5p_mfc_set_enc_params_h264(ctx); 1114 else if (ctx->codec_mode == S5P_MFC_CODEC_MPEG4_ENC) 1115 s5p_mfc_set_enc_params_mpeg4(ctx); 1116 else if (ctx->codec_mode == S5P_MFC_CODEC_H263_ENC) 1117 s5p_mfc_set_enc_params_h263(ctx); 1118 else { 1119 mfc_err("Unknown codec for encoding (%x)\n", 1120 ctx->codec_mode); 1121 return -EINVAL; 1122 } 1123 s5p_mfc_set_shared_buffer(ctx); 1124 mfc_write(dev, ((S5P_FIMV_CH_SEQ_HEADER << 16) & 0x70000) | 1125 (ctx->inst_no), S5P_FIMV_SI_CH0_INST_ID); 1126 return 0; 1127} 1128 1129/* Encode a single frame */ 1130static int s5p_mfc_encode_one_frame_v5(struct s5p_mfc_ctx *ctx) 1131{ 1132 struct s5p_mfc_dev *dev = ctx->dev; 1133 int cmd; 1134 /* memory structure cur. frame */ 1135 if (ctx->src_fmt->fourcc == V4L2_PIX_FMT_NV12M) 1136 mfc_write(dev, 0, S5P_FIMV_ENC_MAP_FOR_CUR); 1137 else if (ctx->src_fmt->fourcc == V4L2_PIX_FMT_NV12MT) 1138 mfc_write(dev, 3, S5P_FIMV_ENC_MAP_FOR_CUR); 1139 s5p_mfc_set_shared_buffer(ctx); 1140 1141 if (ctx->state == MFCINST_FINISHING) 1142 cmd = S5P_FIMV_CH_LAST_FRAME; 1143 else 1144 cmd = S5P_FIMV_CH_FRAME_START; 1145 mfc_write(dev, ((cmd & S5P_FIMV_CH_MASK) << S5P_FIMV_CH_SHIFT) 1146 | (ctx->inst_no), S5P_FIMV_SI_CH0_INST_ID); 1147 1148 return 0; 1149} 1150 1151static void s5p_mfc_run_res_change(struct s5p_mfc_ctx *ctx) 1152{ 1153 struct s5p_mfc_dev *dev = ctx->dev; 1154 1155 s5p_mfc_set_dec_stream_buffer_v5(ctx, 0, 0, 0); 1156 dev->curr_ctx = ctx->num; 1157 s5p_mfc_decode_one_frame_v5(ctx, MFC_DEC_RES_CHANGE); 1158} 1159 1160static int s5p_mfc_run_dec_frame(struct s5p_mfc_ctx *ctx, int last_frame) 1161{ 1162 struct s5p_mfc_dev *dev = ctx->dev; 1163 struct s5p_mfc_buf *temp_vb; 1164 1165 if (ctx->state == MFCINST_FINISHING) { 1166 last_frame = MFC_DEC_LAST_FRAME; 1167 s5p_mfc_set_dec_stream_buffer_v5(ctx, 0, 0, 0); 1168 dev->curr_ctx = ctx->num; 1169 s5p_mfc_decode_one_frame_v5(ctx, last_frame); 1170 return 0; 1171 } 1172 1173 /* Frames are being decoded */ 1174 if (list_empty(&ctx->src_queue)) { 1175 mfc_debug(2, "No src buffers\n"); 1176 return -EAGAIN; 1177 } 1178 /* Get the next source buffer */ 1179 temp_vb = list_entry(ctx->src_queue.next, struct s5p_mfc_buf, list); 1180 temp_vb->flags |= MFC_BUF_FLAG_USED; 1181 s5p_mfc_set_dec_stream_buffer_v5(ctx, 1182 vb2_dma_contig_plane_dma_addr(&temp_vb->b->vb2_buf, 0), 1183 ctx->consumed_stream, temp_vb->b->vb2_buf.planes[0].bytesused); 1184 dev->curr_ctx = ctx->num; 1185 if (temp_vb->b->vb2_buf.planes[0].bytesused == 0) { 1186 last_frame = MFC_DEC_LAST_FRAME; 1187 mfc_debug(2, "Setting ctx->state to FINISHING\n"); 1188 ctx->state = MFCINST_FINISHING; 1189 } 1190 s5p_mfc_decode_one_frame_v5(ctx, last_frame); 1191 return 0; 1192} 1193 1194static int s5p_mfc_run_enc_frame(struct s5p_mfc_ctx *ctx) 1195{ 1196 struct s5p_mfc_dev *dev = ctx->dev; 1197 struct s5p_mfc_buf *dst_mb; 1198 struct s5p_mfc_buf *src_mb; 1199 unsigned long src_y_addr, src_c_addr, dst_addr; 1200 unsigned int dst_size; 1201 1202 if (list_empty(&ctx->src_queue) && ctx->state != MFCINST_FINISHING) { 1203 mfc_debug(2, "no src buffers\n"); 1204 return -EAGAIN; 1205 } 1206 if (list_empty(&ctx->dst_queue)) { 1207 mfc_debug(2, "no dst buffers\n"); 1208 return -EAGAIN; 1209 } 1210 if (list_empty(&ctx->src_queue)) { 1211 /* send null frame */ 1212 s5p_mfc_set_enc_frame_buffer_v5(ctx, dev->dma_base[BANK_R_CTX], 1213 dev->dma_base[BANK_R_CTX]); 1214 src_mb = NULL; 1215 } else { 1216 src_mb = list_entry(ctx->src_queue.next, struct s5p_mfc_buf, 1217 list); 1218 src_mb->flags |= MFC_BUF_FLAG_USED; 1219 if (src_mb->b->vb2_buf.planes[0].bytesused == 0) { 1220 /* send null frame */ 1221 s5p_mfc_set_enc_frame_buffer_v5(ctx, 1222 dev->dma_base[BANK_R_CTX], 1223 dev->dma_base[BANK_R_CTX]); 1224 ctx->state = MFCINST_FINISHING; 1225 } else { 1226 src_y_addr = vb2_dma_contig_plane_dma_addr( 1227 &src_mb->b->vb2_buf, 0); 1228 src_c_addr = vb2_dma_contig_plane_dma_addr( 1229 &src_mb->b->vb2_buf, 1); 1230 s5p_mfc_set_enc_frame_buffer_v5(ctx, src_y_addr, 1231 src_c_addr); 1232 if (src_mb->flags & MFC_BUF_FLAG_EOS) 1233 ctx->state = MFCINST_FINISHING; 1234 } 1235 } 1236 dst_mb = list_entry(ctx->dst_queue.next, struct s5p_mfc_buf, list); 1237 dst_mb->flags |= MFC_BUF_FLAG_USED; 1238 dst_addr = vb2_dma_contig_plane_dma_addr(&dst_mb->b->vb2_buf, 0); 1239 dst_size = vb2_plane_size(&dst_mb->b->vb2_buf, 0); 1240 s5p_mfc_set_enc_stream_buffer_v5(ctx, dst_addr, dst_size); 1241 dev->curr_ctx = ctx->num; 1242 mfc_debug(2, "encoding buffer with index=%d state=%d\n", 1243 src_mb ? src_mb->b->vb2_buf.index : -1, ctx->state); 1244 s5p_mfc_encode_one_frame_v5(ctx); 1245 return 0; 1246} 1247 1248static void s5p_mfc_run_init_dec(struct s5p_mfc_ctx *ctx) 1249{ 1250 struct s5p_mfc_dev *dev = ctx->dev; 1251 struct s5p_mfc_buf *temp_vb; 1252 1253 /* Initializing decoding - parsing header */ 1254 mfc_debug(2, "Preparing to init decoding\n"); 1255 temp_vb = list_entry(ctx->src_queue.next, struct s5p_mfc_buf, list); 1256 s5p_mfc_set_dec_desc_buffer(ctx); 1257 mfc_debug(2, "Header size: %d\n", 1258 temp_vb->b->vb2_buf.planes[0].bytesused); 1259 s5p_mfc_set_dec_stream_buffer_v5(ctx, 1260 vb2_dma_contig_plane_dma_addr(&temp_vb->b->vb2_buf, 0), 1261 0, temp_vb->b->vb2_buf.planes[0].bytesused); 1262 dev->curr_ctx = ctx->num; 1263 s5p_mfc_init_decode_v5(ctx); 1264} 1265 1266static void s5p_mfc_run_init_enc(struct s5p_mfc_ctx *ctx) 1267{ 1268 struct s5p_mfc_dev *dev = ctx->dev; 1269 struct s5p_mfc_buf *dst_mb; 1270 unsigned long dst_addr; 1271 unsigned int dst_size; 1272 1273 s5p_mfc_set_enc_ref_buffer_v5(ctx); 1274 dst_mb = list_entry(ctx->dst_queue.next, struct s5p_mfc_buf, list); 1275 dst_addr = vb2_dma_contig_plane_dma_addr(&dst_mb->b->vb2_buf, 0); 1276 dst_size = vb2_plane_size(&dst_mb->b->vb2_buf, 0); 1277 s5p_mfc_set_enc_stream_buffer_v5(ctx, dst_addr, dst_size); 1278 dev->curr_ctx = ctx->num; 1279 s5p_mfc_init_encode_v5(ctx); 1280} 1281 1282static int s5p_mfc_run_init_dec_buffers(struct s5p_mfc_ctx *ctx) 1283{ 1284 struct s5p_mfc_dev *dev = ctx->dev; 1285 struct s5p_mfc_buf *temp_vb; 1286 int ret; 1287 1288 /* 1289 * Header was parsed now starting processing 1290 * First set the output frame buffers 1291 */ 1292 if (ctx->capture_state != QUEUE_BUFS_MMAPED) { 1293 mfc_err("It seems that not all destination buffers were mmapped\nMFC requires that all destination are mmapped before starting processing\n"); 1294 return -EAGAIN; 1295 } 1296 if (list_empty(&ctx->src_queue)) { 1297 mfc_err("Header has been deallocated in the middle of initialization\n"); 1298 return -EIO; 1299 } 1300 temp_vb = list_entry(ctx->src_queue.next, struct s5p_mfc_buf, list); 1301 mfc_debug(2, "Header size: %d\n", 1302 temp_vb->b->vb2_buf.planes[0].bytesused); 1303 s5p_mfc_set_dec_stream_buffer_v5(ctx, 1304 vb2_dma_contig_plane_dma_addr(&temp_vb->b->vb2_buf, 0), 1305 0, temp_vb->b->vb2_buf.planes[0].bytesused); 1306 dev->curr_ctx = ctx->num; 1307 ret = s5p_mfc_set_dec_frame_buffer_v5(ctx); 1308 if (ret) { 1309 mfc_err("Failed to alloc frame mem\n"); 1310 ctx->state = MFCINST_ERROR; 1311 } 1312 return ret; 1313} 1314 1315/* Try running an operation on hardware */ 1316static void s5p_mfc_try_run_v5(struct s5p_mfc_dev *dev) 1317{ 1318 struct s5p_mfc_ctx *ctx; 1319 int new_ctx; 1320 unsigned int ret = 0; 1321 1322 if (test_bit(0, &dev->enter_suspend)) { 1323 mfc_debug(1, "Entering suspend so do not schedule any jobs\n"); 1324 return; 1325 } 1326 /* Check whether hardware is not running */ 1327 if (test_and_set_bit(0, &dev->hw_lock) != 0) { 1328 /* This is perfectly ok, the scheduled ctx should wait */ 1329 mfc_debug(1, "Couldn't lock HW\n"); 1330 return; 1331 } 1332 /* Choose the context to run */ 1333 new_ctx = s5p_mfc_get_new_ctx(dev); 1334 if (new_ctx < 0) { 1335 /* No contexts to run */ 1336 if (test_and_clear_bit(0, &dev->hw_lock) == 0) { 1337 mfc_err("Failed to unlock hardware\n"); 1338 return; 1339 } 1340 mfc_debug(1, "No ctx is scheduled to be run\n"); 1341 return; 1342 } 1343 ctx = dev->ctx[new_ctx]; 1344 /* Got context to run in ctx */ 1345 /* 1346 * Last frame has already been sent to MFC. 1347 * Now obtaining frames from MFC buffer 1348 */ 1349 s5p_mfc_clock_on(); 1350 s5p_mfc_clean_ctx_int_flags(ctx); 1351 1352 if (ctx->type == MFCINST_DECODER) { 1353 s5p_mfc_set_dec_desc_buffer(ctx); 1354 switch (ctx->state) { 1355 case MFCINST_FINISHING: 1356 s5p_mfc_run_dec_frame(ctx, MFC_DEC_LAST_FRAME); 1357 break; 1358 case MFCINST_RUNNING: 1359 ret = s5p_mfc_run_dec_frame(ctx, MFC_DEC_FRAME); 1360 break; 1361 case MFCINST_INIT: 1362 ret = s5p_mfc_hw_call(dev->mfc_cmds, open_inst_cmd, 1363 ctx); 1364 break; 1365 case MFCINST_RETURN_INST: 1366 ret = s5p_mfc_hw_call(dev->mfc_cmds, close_inst_cmd, 1367 ctx); 1368 break; 1369 case MFCINST_GOT_INST: 1370 s5p_mfc_run_init_dec(ctx); 1371 break; 1372 case MFCINST_HEAD_PARSED: 1373 ret = s5p_mfc_run_init_dec_buffers(ctx); 1374 mfc_debug(1, "head parsed\n"); 1375 break; 1376 case MFCINST_RES_CHANGE_INIT: 1377 s5p_mfc_run_res_change(ctx); 1378 break; 1379 case MFCINST_RES_CHANGE_FLUSH: 1380 s5p_mfc_run_dec_frame(ctx, MFC_DEC_FRAME); 1381 break; 1382 case MFCINST_RES_CHANGE_END: 1383 mfc_debug(2, "Finished remaining frames after resolution change\n"); 1384 ctx->capture_state = QUEUE_FREE; 1385 mfc_debug(2, "Will re-init the codec\n"); 1386 s5p_mfc_run_init_dec(ctx); 1387 break; 1388 default: 1389 ret = -EAGAIN; 1390 } 1391 } else if (ctx->type == MFCINST_ENCODER) { 1392 switch (ctx->state) { 1393 case MFCINST_FINISHING: 1394 case MFCINST_RUNNING: 1395 ret = s5p_mfc_run_enc_frame(ctx); 1396 break; 1397 case MFCINST_INIT: 1398 ret = s5p_mfc_hw_call(dev->mfc_cmds, open_inst_cmd, 1399 ctx); 1400 break; 1401 case MFCINST_RETURN_INST: 1402 ret = s5p_mfc_hw_call(dev->mfc_cmds, close_inst_cmd, 1403 ctx); 1404 break; 1405 case MFCINST_GOT_INST: 1406 s5p_mfc_run_init_enc(ctx); 1407 break; 1408 default: 1409 ret = -EAGAIN; 1410 } 1411 } else { 1412 mfc_err("Invalid context type: %d\n", ctx->type); 1413 ret = -EAGAIN; 1414 } 1415 1416 if (ret) { 1417 /* Free hardware lock */ 1418 if (test_and_clear_bit(0, &dev->hw_lock) == 0) 1419 mfc_err("Failed to unlock hardware\n"); 1420 1421 /* This is indeed important, as no operation has been 1422 * scheduled, reduce the clock count as no one will 1423 * ever do this, because no interrupt related to this try_run 1424 * will ever come from hardware. */ 1425 s5p_mfc_clock_off(); 1426 } 1427} 1428 1429static void s5p_mfc_clear_int_flags_v5(struct s5p_mfc_dev *dev) 1430{ 1431 mfc_write(dev, 0, S5P_FIMV_RISC_HOST_INT); 1432 mfc_write(dev, 0, S5P_FIMV_RISC2HOST_CMD); 1433 mfc_write(dev, 0xffff, S5P_FIMV_SI_RTN_CHID); 1434} 1435 1436static int s5p_mfc_get_dspl_y_adr_v5(struct s5p_mfc_dev *dev) 1437{ 1438 return mfc_read(dev, S5P_FIMV_SI_DISPLAY_Y_ADR) << MFC_OFFSET_SHIFT; 1439} 1440 1441static int s5p_mfc_get_dec_y_adr_v5(struct s5p_mfc_dev *dev) 1442{ 1443 return mfc_read(dev, S5P_FIMV_SI_DECODE_Y_ADR) << MFC_OFFSET_SHIFT; 1444} 1445 1446static int s5p_mfc_get_dspl_status_v5(struct s5p_mfc_dev *dev) 1447{ 1448 return mfc_read(dev, S5P_FIMV_SI_DISPLAY_STATUS); 1449} 1450 1451static int s5p_mfc_get_dec_status_v5(struct s5p_mfc_dev *dev) 1452{ 1453 return mfc_read(dev, S5P_FIMV_SI_DECODE_STATUS); 1454} 1455 1456static int s5p_mfc_get_dec_frame_type_v5(struct s5p_mfc_dev *dev) 1457{ 1458 return mfc_read(dev, S5P_FIMV_DECODE_FRAME_TYPE) & 1459 S5P_FIMV_DECODE_FRAME_MASK; 1460} 1461 1462static int s5p_mfc_get_disp_frame_type_v5(struct s5p_mfc_ctx *ctx) 1463{ 1464 return (s5p_mfc_read_info_v5(ctx, DISP_PIC_FRAME_TYPE) >> 1465 S5P_FIMV_SHARED_DISP_FRAME_TYPE_SHIFT) & 1466 S5P_FIMV_DECODE_FRAME_MASK; 1467} 1468 1469static int s5p_mfc_get_consumed_stream_v5(struct s5p_mfc_dev *dev) 1470{ 1471 return mfc_read(dev, S5P_FIMV_SI_CONSUMED_BYTES); 1472} 1473 1474static int s5p_mfc_get_int_reason_v5(struct s5p_mfc_dev *dev) 1475{ 1476 int reason; 1477 reason = mfc_read(dev, S5P_FIMV_RISC2HOST_CMD) & 1478 S5P_FIMV_RISC2HOST_CMD_MASK; 1479 switch (reason) { 1480 case S5P_FIMV_R2H_CMD_OPEN_INSTANCE_RET: 1481 reason = S5P_MFC_R2H_CMD_OPEN_INSTANCE_RET; 1482 break; 1483 case S5P_FIMV_R2H_CMD_CLOSE_INSTANCE_RET: 1484 reason = S5P_MFC_R2H_CMD_CLOSE_INSTANCE_RET; 1485 break; 1486 case S5P_FIMV_R2H_CMD_SEQ_DONE_RET: 1487 reason = S5P_MFC_R2H_CMD_SEQ_DONE_RET; 1488 break; 1489 case S5P_FIMV_R2H_CMD_FRAME_DONE_RET: 1490 reason = S5P_MFC_R2H_CMD_FRAME_DONE_RET; 1491 break; 1492 case S5P_FIMV_R2H_CMD_SLICE_DONE_RET: 1493 reason = S5P_MFC_R2H_CMD_SLICE_DONE_RET; 1494 break; 1495 case S5P_FIMV_R2H_CMD_SYS_INIT_RET: 1496 reason = S5P_MFC_R2H_CMD_SYS_INIT_RET; 1497 break; 1498 case S5P_FIMV_R2H_CMD_FW_STATUS_RET: 1499 reason = S5P_MFC_R2H_CMD_FW_STATUS_RET; 1500 break; 1501 case S5P_FIMV_R2H_CMD_SLEEP_RET: 1502 reason = S5P_MFC_R2H_CMD_SLEEP_RET; 1503 break; 1504 case S5P_FIMV_R2H_CMD_WAKEUP_RET: 1505 reason = S5P_MFC_R2H_CMD_WAKEUP_RET; 1506 break; 1507 case S5P_FIMV_R2H_CMD_INIT_BUFFERS_RET: 1508 reason = S5P_MFC_R2H_CMD_INIT_BUFFERS_RET; 1509 break; 1510 case S5P_FIMV_R2H_CMD_ENC_COMPLETE_RET: 1511 reason = S5P_MFC_R2H_CMD_COMPLETE_SEQ_RET; 1512 break; 1513 case S5P_FIMV_R2H_CMD_ERR_RET: 1514 reason = S5P_MFC_R2H_CMD_ERR_RET; 1515 break; 1516 default: 1517 reason = S5P_MFC_R2H_CMD_EMPTY; 1518 } 1519 return reason; 1520} 1521 1522static int s5p_mfc_get_int_err_v5(struct s5p_mfc_dev *dev) 1523{ 1524 return mfc_read(dev, S5P_FIMV_RISC2HOST_ARG2); 1525} 1526 1527static int s5p_mfc_err_dec_v5(unsigned int err) 1528{ 1529 return (err & S5P_FIMV_ERR_DEC_MASK) >> S5P_FIMV_ERR_DEC_SHIFT; 1530} 1531 1532static int s5p_mfc_get_img_width_v5(struct s5p_mfc_dev *dev) 1533{ 1534 return mfc_read(dev, S5P_FIMV_SI_HRESOL); 1535} 1536 1537static int s5p_mfc_get_img_height_v5(struct s5p_mfc_dev *dev) 1538{ 1539 return mfc_read(dev, S5P_FIMV_SI_VRESOL); 1540} 1541 1542static int s5p_mfc_get_dpb_count_v5(struct s5p_mfc_dev *dev) 1543{ 1544 return mfc_read(dev, S5P_FIMV_SI_BUF_NUMBER); 1545} 1546 1547static int s5p_mfc_get_mv_count_v5(struct s5p_mfc_dev *dev) 1548{ 1549 /* NOP */ 1550 return -1; 1551} 1552 1553static int s5p_mfc_get_inst_no_v5(struct s5p_mfc_dev *dev) 1554{ 1555 return mfc_read(dev, S5P_FIMV_RISC2HOST_ARG1); 1556} 1557 1558static int s5p_mfc_get_enc_strm_size_v5(struct s5p_mfc_dev *dev) 1559{ 1560 return mfc_read(dev, S5P_FIMV_ENC_SI_STRM_SIZE); 1561} 1562 1563static int s5p_mfc_get_enc_slice_type_v5(struct s5p_mfc_dev *dev) 1564{ 1565 return mfc_read(dev, S5P_FIMV_ENC_SI_SLICE_TYPE); 1566} 1567 1568static int s5p_mfc_get_enc_dpb_count_v5(struct s5p_mfc_dev *dev) 1569{ 1570 return -1; 1571} 1572 1573static unsigned int s5p_mfc_get_pic_type_top_v5(struct s5p_mfc_ctx *ctx) 1574{ 1575 return s5p_mfc_read_info_v5(ctx, PIC_TIME_TOP); 1576} 1577 1578static unsigned int s5p_mfc_get_pic_type_bot_v5(struct s5p_mfc_ctx *ctx) 1579{ 1580 return s5p_mfc_read_info_v5(ctx, PIC_TIME_BOT); 1581} 1582 1583static unsigned int s5p_mfc_get_crop_info_h_v5(struct s5p_mfc_ctx *ctx) 1584{ 1585 return s5p_mfc_read_info_v5(ctx, CROP_INFO_H); 1586} 1587 1588static unsigned int s5p_mfc_get_crop_info_v_v5(struct s5p_mfc_ctx *ctx) 1589{ 1590 return s5p_mfc_read_info_v5(ctx, CROP_INFO_V); 1591} 1592 1593/* Initialize opr function pointers for MFC v5 */ 1594static struct s5p_mfc_hw_ops s5p_mfc_ops_v5 = { 1595 .alloc_dec_temp_buffers = s5p_mfc_alloc_dec_temp_buffers_v5, 1596 .release_dec_desc_buffer = s5p_mfc_release_dec_desc_buffer_v5, 1597 .alloc_codec_buffers = s5p_mfc_alloc_codec_buffers_v5, 1598 .release_codec_buffers = s5p_mfc_release_codec_buffers_v5, 1599 .alloc_instance_buffer = s5p_mfc_alloc_instance_buffer_v5, 1600 .release_instance_buffer = s5p_mfc_release_instance_buffer_v5, 1601 .alloc_dev_context_buffer = s5p_mfc_alloc_dev_context_buffer_v5, 1602 .release_dev_context_buffer = s5p_mfc_release_dev_context_buffer_v5, 1603 .dec_calc_dpb_size = s5p_mfc_dec_calc_dpb_size_v5, 1604 .enc_calc_src_size = s5p_mfc_enc_calc_src_size_v5, 1605 .set_enc_stream_buffer = s5p_mfc_set_enc_stream_buffer_v5, 1606 .set_enc_frame_buffer = s5p_mfc_set_enc_frame_buffer_v5, 1607 .get_enc_frame_buffer = s5p_mfc_get_enc_frame_buffer_v5, 1608 .try_run = s5p_mfc_try_run_v5, 1609 .clear_int_flags = s5p_mfc_clear_int_flags_v5, 1610 .get_dspl_y_adr = s5p_mfc_get_dspl_y_adr_v5, 1611 .get_dec_y_adr = s5p_mfc_get_dec_y_adr_v5, 1612 .get_dspl_status = s5p_mfc_get_dspl_status_v5, 1613 .get_dec_status = s5p_mfc_get_dec_status_v5, 1614 .get_dec_frame_type = s5p_mfc_get_dec_frame_type_v5, 1615 .get_disp_frame_type = s5p_mfc_get_disp_frame_type_v5, 1616 .get_consumed_stream = s5p_mfc_get_consumed_stream_v5, 1617 .get_int_reason = s5p_mfc_get_int_reason_v5, 1618 .get_int_err = s5p_mfc_get_int_err_v5, 1619 .err_dec = s5p_mfc_err_dec_v5, 1620 .get_img_width = s5p_mfc_get_img_width_v5, 1621 .get_img_height = s5p_mfc_get_img_height_v5, 1622 .get_dpb_count = s5p_mfc_get_dpb_count_v5, 1623 .get_mv_count = s5p_mfc_get_mv_count_v5, 1624 .get_inst_no = s5p_mfc_get_inst_no_v5, 1625 .get_enc_strm_size = s5p_mfc_get_enc_strm_size_v5, 1626 .get_enc_slice_type = s5p_mfc_get_enc_slice_type_v5, 1627 .get_enc_dpb_count = s5p_mfc_get_enc_dpb_count_v5, 1628 .get_pic_type_top = s5p_mfc_get_pic_type_top_v5, 1629 .get_pic_type_bot = s5p_mfc_get_pic_type_bot_v5, 1630 .get_crop_info_h = s5p_mfc_get_crop_info_h_v5, 1631 .get_crop_info_v = s5p_mfc_get_crop_info_v_v5, 1632}; 1633 1634struct s5p_mfc_hw_ops *s5p_mfc_init_hw_ops_v5(void) 1635{ 1636 return &s5p_mfc_ops_v5; 1637}