diff options
author | SeungBeom Kim <sbcrux.kim@samsung.com> | 2010-09-14 21:16:51 -0700 |
---|---|---|
committer | Simon Wilson <simonwilson@google.com> | 2010-09-21 10:05:49 -0700 |
commit | 57450df3b0953a095ff6955680f7dc7e8600ad89 (patch) | |
tree | 758d5ab8baa47b93608f19c720e1bf9aa6059ca8 /sec_mm/sec_omx/sec_codecs | |
parent | 62cfa7ab18ad26d95568167d29216d7954a6760c (diff) | |
download | device_samsung_crespo-57450df3b0953a095ff6955680f7dc7e8600ad89.zip device_samsung_crespo-57450df3b0953a095ff6955680f7dc7e8600ad89.tar.gz device_samsung_crespo-57450df3b0953a095ff6955680f7dc7e8600ad89.tar.bz2 |
S5PC11X: OMX: Added SEC_OMX(OpenMAX IL)
Component name
1. OMX.SEC.AVC.Decoder
2. OMX.SEC.MPEG4.Decoder
3. OMX.SEC.H263.Decoder
4. OMX.SEC.AVC.Encoder
5. OMX.SEC.MPEG4.Encoder
6. OMX.SEC.H263.Encoder
Change-Id: I4ae562c6d44fac8c376a8f60fd376c46bd1e721d
Signed-off-by: SeungBeom Kim <sbcrux.kim@samsung.com>
Diffstat (limited to 'sec_mm/sec_omx/sec_codecs')
7 files changed, 1924 insertions, 0 deletions
diff --git a/sec_mm/sec_omx/sec_codecs/Android.mk b/sec_mm/sec_omx/sec_codecs/Android.mk new file mode 100644 index 0000000..a51a075 --- /dev/null +++ b/sec_mm/sec_omx/sec_codecs/Android.mk @@ -0,0 +1,7 @@ +LOCAL_PATH := $(call my-dir) + +include $(CLEAR_VARS) + +include $(SEC_CODECS)/video/mfc_c110/dec/Android.mk +include $(SEC_CODECS)/video/mfc_c110/enc/Android.mk + diff --git a/sec_mm/sec_omx/sec_codecs/video/mfc_c110/dec/Android.mk b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/dec/Android.mk new file mode 100644 index 0000000..7d1f027 --- /dev/null +++ b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/dec/Android.mk @@ -0,0 +1,26 @@ + +LOCAL_PATH := $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_MODULE_TAGS := optional + +LOCAL_SRC_FILES := \ + src/SsbSipMfcDecAPI.c + +LOCAL_MODULE := libsecmfcdecapi + +LOCAL_PRELINK_MODULE := false + +LOCAL_CFLAGS := + +LOCAL_ARM_MODE := arm + +LOCAL_STATIC_LIBRARIES := + +LOCAL_SHARED_LIBRARIES := liblog + +LOCAL_C_INCLUDES := \ + $(SEC_CODECS)/video/mfc_c110/include + +include $(BUILD_STATIC_LIBRARY) + diff --git a/sec_mm/sec_omx/sec_codecs/video/mfc_c110/dec/src/SsbSipMfcDecAPI.c b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/dec/src/SsbSipMfcDecAPI.c new file mode 100644 index 0000000..abcc020 --- /dev/null +++ b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/dec/src/SsbSipMfcDecAPI.c @@ -0,0 +1,584 @@ +/* + * Copyright 2010 Samsung Electronics Co. LTD + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include <stdlib.h> +#include <unistd.h> +#include <string.h> +#include <fcntl.h> + +#include <sys/types.h> +#include <sys/stat.h> +#include <sys/ioctl.h> +#include <sys/mman.h> +#include <utils/Log.h> + +#include "mfc_interface.h" +#include "SsbSipMfcApi.h" + +#define _MFCLIB_MAGIC_NUMBER 0x92241000 + +#define USR_DATA_START_CODE (0x000001B2) +#define VOP_START_CODE (0x000001B6) +#define MP4_START_CODE (0x000001) + +static void getAByte(char *buff, int *code) +{ + int byte; + + *code = (*code << 8); + byte = (int)*buff; + byte &= 0xFF; + *code |= byte; +} + +static mfc_packed_mode isPBPacked(_MFCLIB *pCtx, int length) +{ + char *strmBuffer = NULL; + char *strmBufferEnd = NULL; + int startCode = 0xFFFFFFFF; + + strmBuffer = (char *)pCtx->virStrmBuf; + strmBufferEnd = (char *)pCtx->virStrmBuf + length; + + while (1) { + while (startCode != USR_DATA_START_CODE) { + if (startCode == VOP_START_CODE) { + LOGV("isPBPacked: VOP START Found !!.....return\n"); + LOGV("isPBPacked: Non Packed PB\n"); + return MFC_UNPACKED_PB; + } + getAByte(strmBuffer, &startCode); + strmBuffer++; + if (strmBuffer >= strmBufferEnd) + goto out; + } + LOGV("isPBPacked: User Data Found !!\n"); + + do { + if (*strmBuffer == 'p') { + LOGI("isPBPacked: Packed PB\n"); + return MFC_PACKED_PB; + } + getAByte(strmBuffer, &startCode); + strmBuffer++; + if (strmBuffer >= strmBufferEnd) + goto out; + } while ((startCode >> 8) != MP4_START_CODE); + } + +out: + LOGV("isPBPacked: Non Packed PB\n"); + return MFC_UNPACKED_PB; +} + +void *SsbSipMfcDecOpen(void) +{ + int hMFCOpen; + unsigned int mapped_addr; + _MFCLIB *pCTX; + + pCTX = (_MFCLIB *)malloc(sizeof(_MFCLIB)); + if (pCTX == NULL) { + LOGE("SsbSipMfcDecOpen: malloc failed.\n"); + return NULL; + } + memset(pCTX, 0, sizeof(_MFCLIB)); + + hMFCOpen = open(S5PC110_MFC_DEV_NAME, O_RDWR | O_NDELAY); + if (hMFCOpen < 0) { + LOGE("SsbSipMfcDecOpen: MFC Open failure\n"); + return NULL; + } + + mapped_addr = (unsigned int)mmap(0, MMAP_BUFFER_SIZE_MMAP, PROT_READ | PROT_WRITE, MAP_SHARED, hMFCOpen, 0); + if (!mapped_addr) { + LOGE("SsbSipMfcDecOpen: FIMV5.0 driver address mapping failed\n"); + return NULL; + } + + pCTX->magic = _MFCLIB_MAGIC_NUMBER; + pCTX->hMFC = hMFCOpen; + pCTX->mapped_addr = mapped_addr; + pCTX->inter_buff_status = MFC_USE_NONE; + + return (void *)pCTX; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecInit(void *openHandle, SSBSIP_MFC_CODEC_TYPE codec_type, int Frameleng) +{ + int ret_code; + int packedPB = MFC_UNPACKED_PB; + mfc_common_args DecArg; + _MFCLIB *pCTX; + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecSetConfig: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + memset(&DecArg, 0x00, sizeof(DecArg)); + + if ((codec_type != MPEG4_DEC) && + (codec_type != H264_DEC) && + (codec_type != H263_DEC) && + (codec_type != MPEG1_DEC) && + (codec_type != MPEG2_DEC) && + (codec_type != FIMV1_DEC) && + (codec_type != FIMV2_DEC) && + (codec_type != FIMV3_DEC) && + (codec_type != FIMV4_DEC) && + (codec_type != XVID_DEC) && + (codec_type != VC1RCV_DEC) && + (codec_type != VC1_DEC)) { + LOGE("SsbSipMfcDecOpen: Undefined codec type.\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX->codec_type = codec_type; + + if ((pCTX->codec_type == MPEG4_DEC) || + (pCTX->codec_type == FIMV1_DEC) || + (pCTX->codec_type == FIMV2_DEC) || + (pCTX->codec_type == FIMV3_DEC) || + (pCTX->codec_type == FIMV4_DEC) || + (pCTX->codec_type == XVID_DEC)) + packedPB = isPBPacked(pCTX, Frameleng); + + /* init args */ + DecArg.args.dec_init.in_codec_type = pCTX->codec_type; + DecArg.args.dec_init.in_strm_size = Frameleng; + DecArg.args.dec_init.in_strm_buf = pCTX->phyStrmBuf; + DecArg.args.dec_init.in_packed_PB = packedPB; + + /* mem alloc args */ + DecArg.args.dec_init.in_mapped_addr = pCTX->mapped_addr; + + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_DEC_INIT, &DecArg); + if (DecArg.ret_code != MFC_RET_OK) { + LOGE("SsbSipMfcDecInit: IOCTL_MFC_DEC_INIT (%d) failed\n", DecArg.ret_code); + return MFC_RET_DEC_INIT_FAIL; + } + + pCTX->decOutInfo.img_width = DecArg.args.dec_init.out_img_width; + pCTX->decOutInfo.img_height = DecArg.args.dec_init.out_img_height; + pCTX->decOutInfo.buf_width = DecArg.args.dec_init.out_buf_width; + pCTX->decOutInfo.buf_height = DecArg.args.dec_init.out_buf_height; + + pCTX->virFrmBuf.luma = DecArg.args.dec_init.out_u_addr.luma; + pCTX->virFrmBuf.chroma = DecArg.args.dec_init.out_u_addr.chroma; + + pCTX->phyFrmBuf.luma = DecArg.args.dec_init.out_p_addr.luma; + pCTX->phyFrmBuf.chroma = DecArg.args.dec_init.out_p_addr.chroma; + pCTX->sizeFrmBuf.luma = DecArg.args.dec_init.out_frame_buf_size.luma; + pCTX->sizeFrmBuf.chroma = DecArg.args.dec_init.out_frame_buf_size.chroma; + pCTX->inter_buff_status |= MFC_USE_YUV_BUFF; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecExe(void *openHandle, int lengthBufFill) +{ + int ret_code; + int Yoffset; + int Coffset; + _MFCLIB *pCTX; + mfc_common_args DecArg; + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecExe: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + if ((lengthBufFill < 0) || (lengthBufFill > MAX_DECODER_INPUT_BUFFER_SIZE)) { + LOGE("SsbSipMfcDecExe: lengthBufFill is invalid. (lengthBufFill=%d)\n", lengthBufFill); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + memset(&DecArg, 0x00, sizeof(DecArg)); + + DecArg.args.dec_exe.in_codec_type = pCTX->codec_type; + DecArg.args.dec_exe.in_strm_buf = pCTX->phyStrmBuf; + DecArg.args.dec_exe.in_strm_size = lengthBufFill; + DecArg.args.dec_exe.in_frm_buf.luma = pCTX->phyFrmBuf.luma; + DecArg.args.dec_exe.in_frm_buf.chroma = pCTX->phyFrmBuf.chroma; + DecArg.args.dec_exe.in_frm_size.luma = pCTX->sizeFrmBuf.luma; + DecArg.args.dec_exe.in_frm_size.chroma = pCTX->sizeFrmBuf.chroma; + DecArg.args.dec_exe.in_frametag = pCTX->in_frametag; + + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_DEC_EXE, &DecArg); + if (DecArg.ret_code != MFC_RET_OK) { + LOGE("SsbSipMfcDecExe: IOCTL_MFC_DEC_EXE failed(ret : %d)\n", DecArg.ret_code); + return MFC_RET_DEC_EXE_ERR; + } + + Yoffset = DecArg.args.dec_exe.out_display_Y_addr - DecArg.args.dec_exe.in_frm_buf.luma; + Coffset = DecArg.args.dec_exe.out_display_C_addr - DecArg.args.dec_exe.in_frm_buf.chroma; + + pCTX->decOutInfo.YPhyAddr = (void *)(DecArg.args.dec_exe.out_display_Y_addr); + pCTX->decOutInfo.CPhyAddr = (void *)(DecArg.args.dec_exe.out_display_C_addr); + pCTX->decOutInfo.YVirAddr = (void *)(pCTX->virFrmBuf.luma + Yoffset); + pCTX->decOutInfo.CVirAddr = (void *)(pCTX->virFrmBuf.chroma + Coffset); + pCTX->decOutInfo.timestamp_top = DecArg.args.dec_exe.out_timestamp_top; + pCTX->decOutInfo.timestamp_bottom = DecArg.args.dec_exe.out_timestamp_bottom; + pCTX->decOutInfo.consumedByte = DecArg.args.dec_exe.out_consume_bytes; + pCTX->decOutInfo.res_change = DecArg.args.dec_exe.out_res_change; + pCTX->decOutInfo.crop_top_offset = DecArg.args.dec_exe.out_crop_top_offset; + pCTX->decOutInfo.crop_bottom_offset = DecArg.args.dec_exe.out_crop_bottom_offset; + pCTX->decOutInfo.crop_left_offset = DecArg.args.dec_exe.out_crop_left_offset; + pCTX->decOutInfo.crop_right_offset = DecArg.args.dec_exe.out_crop_right_offset; + pCTX->out_frametag_top = DecArg.args.dec_exe.out_frametag_top; + pCTX->out_frametag_bottom = DecArg.args.dec_exe.out_frametag_bottom; + pCTX->displayStatus = DecArg.args.dec_exe.out_display_status; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecClose(void *openHandle) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args free_arg; + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecClose: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + + if (pCTX->inter_buff_status & MFC_USE_YUV_BUFF) { + free_arg.args.mem_free.u_addr = pCTX->virFrmBuf.luma; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_FREE_BUF, &free_arg); + free_arg.args.mem_free.u_addr = pCTX->virFrmBuf.chroma; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_FREE_BUF, &free_arg); + } + + if (pCTX->inter_buff_status & MFC_USE_STRM_BUFF) { + free_arg.args.mem_free.u_addr = pCTX->virStrmBuf; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_FREE_BUF, &free_arg); + } + + pCTX->inter_buff_status = MFC_USE_NONE; + + munmap((void *)pCTX->mapped_addr, MMAP_BUFFER_SIZE_MMAP); + close(pCTX->hMFC); + free(pCTX); + + return MFC_RET_OK; +} + +void *SsbSipMfcDecGetInBuf(void *openHandle, void **phyInBuf, int inputBufferSize) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args user_addr_arg, phys_addr_arg; + + if (inputBufferSize < 0) { + LOGE("SsbSipMfcDecGetInBuf: inputBufferSize = %d is invalid\n", inputBufferSize); + return NULL; + } + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecGetInBuf: openHandle is NULL\n"); + return NULL; + } + + pCTX = (_MFCLIB *)openHandle; + + user_addr_arg.args.mem_alloc.codec_type = pCTX->codec_type; + user_addr_arg.args.mem_alloc.buff_size = inputBufferSize; + user_addr_arg.args.mem_alloc.mapped_addr = pCTX->mapped_addr; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_GET_IN_BUF, &user_addr_arg); + if (ret_code < 0) { + LOGE("SsbSipMfcDecGetInBuf: IOCTL_MFC_GET_IN_BUF failed\n"); + return NULL; + } + pCTX->virStrmBuf = user_addr_arg.args.mem_alloc.out_uaddr; + pCTX->phyStrmBuf = user_addr_arg.args.mem_alloc.out_paddr; + pCTX->sizeStrmBuf = inputBufferSize; + pCTX->inter_buff_status |= MFC_USE_STRM_BUFF; + + *phyInBuf = (void *)pCTX->phyStrmBuf; + + return (void *)pCTX->virStrmBuf; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecSetInBuf(void *openHandle, void *phyInBuf, void *virInBuf, int inputBufferSize) +{ + _MFCLIB *pCTX; + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecSetInBuf: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + + pCTX->phyStrmBuf = (int)phyInBuf; + pCTX->virStrmBuf = (int)virInBuf; + pCTX->sizeStrmBuf = inputBufferSize; + return MFC_RET_OK; +} + +SSBSIP_MFC_DEC_OUTBUF_STATUS SsbSipMfcDecGetOutBuf(void *openHandle, SSBSIP_MFC_DEC_OUTPUT_INFO *output_info) +{ + _MFCLIB *pCTX; + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecGetOutBuf: openHandle is NULL\n"); + return MFC_GETOUTBUF_DISPLAY_END; + } + + pCTX = (_MFCLIB *)openHandle; + + output_info->YPhyAddr = pCTX->decOutInfo.YPhyAddr; + output_info->CPhyAddr = pCTX->decOutInfo.CPhyAddr; + + output_info->YVirAddr = pCTX->decOutInfo.YVirAddr; + output_info->CVirAddr = pCTX->decOutInfo.CVirAddr; + + output_info->img_width = pCTX->decOutInfo.img_width; + output_info->img_height= pCTX->decOutInfo.img_height; + + output_info->buf_width = pCTX->decOutInfo.buf_width; + output_info->buf_height= pCTX->decOutInfo.buf_height; + + if (pCTX->displayStatus == 0) + return MFC_GETOUTBUF_DISPLAY_END; + else if (pCTX->displayStatus == 1) + return MFC_GETOUTBUF_DISPLAY_DECODING; + else if (pCTX->displayStatus == 2) + return MFC_GETOUTBUF_DISPLAY_ONLY; + else + return MFC_GETOUTBUF_DECODING_ONLY; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecSetConfig(void *openHandle, SSBSIP_MFC_DEC_CONF conf_type, void *value) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args DecArg; + SSBSIP_MFC_IMG_RESOLUTION *img_resolution; + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecSetConfig: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + if (value == NULL) { + LOGE("SsbSipMfcDecSetConfig: value is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + memset(&DecArg, 0x00, sizeof(DecArg)); + + switch (conf_type) { + case MFC_DEC_SETCONF_POST_ENABLE: + case MFC_DEC_SETCONF_EXTRA_BUFFER_NUM: + case MFC_DEC_SETCONF_DISPLAY_DELAY: + case MFC_DEC_SETCONF_IS_LAST_FRAME: + case MFC_DEC_SETCONF_SLICE_ENABLE: + case MFC_DEC_SETCONF_CRC_ENABLE: + DecArg.args.set_config.in_config_param = conf_type; + DecArg.args.set_config.in_config_value[0] = *((unsigned int *)value); + DecArg.args.set_config.in_config_value[1] = 0; + break; + + case MFC_DEC_SETCONF_FIMV1_WIDTH_HEIGHT: + img_resolution = (SSBSIP_MFC_IMG_RESOLUTION *)value; + DecArg.args.set_config.in_config_param = conf_type; + DecArg.args.set_config.in_config_value[0] = img_resolution->width; + DecArg.args.set_config.in_config_value[1] = img_resolution->height; + break; + + case MFC_DEC_SETCONF_FRAME_TAG: + pCTX->in_frametag = *((int *)value); + return MFC_RET_OK; + + default: + LOGE("SsbSipMfcDecSetConfig: No such conf_type is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_SET_CONFIG, &DecArg); + if (DecArg.ret_code != MFC_RET_OK) { + LOGE("SsbSipMfcDecSetConfig: IOCTL_MFC_SET_CONFIG failed(ret : %d, conf_type: %d)\n", DecArg.ret_code, conf_type); + return MFC_RET_DEC_SET_CONF_FAIL; + } + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecGetConfig(void *openHandle, SSBSIP_MFC_DEC_CONF conf_type, void *value) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args DecArg; + + SSBSIP_MFC_IMG_RESOLUTION *img_resolution; + MFC_CRC_DATA *crc_data; + + if (openHandle == NULL) { + LOGE("SsbSipMfcDecGetConfig: openHandle is NULL\n"); + return MFC_RET_FAIL; + } + + if (value == NULL) { + LOGE("SsbSipMfcDecGetConfig: value is NULL\n"); + return MFC_RET_FAIL; + } + + pCTX = (_MFCLIB *)openHandle; + memset(&DecArg, 0x00, sizeof(DecArg)); + + switch (conf_type) { + case MFC_DEC_GETCONF_BUF_WIDTH_HEIGHT: + img_resolution = (SSBSIP_MFC_IMG_RESOLUTION *)value; + img_resolution->width = pCTX->decOutInfo.img_width; + img_resolution->height = pCTX->decOutInfo.img_height; + img_resolution->buf_width = pCTX->decOutInfo.buf_width; + img_resolution->buf_height = pCTX->decOutInfo.buf_height; + break; + + case MFC_DEC_GETCONF_CRC_DATA: + crc_data = (MFC_CRC_DATA *)value; + + DecArg.args.get_config.in_config_param = conf_type; + + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_GET_CONFIG, &DecArg); + if (DecArg.ret_code != MFC_RET_OK) { + LOGE("SsbSipMfcDecGetConfig: IOCTL_MFC_GET_CONFIG failed(ret : %d, conf_type: %d)\n", DecArg.ret_code, conf_type); + return MFC_RET_DEC_GET_CONF_FAIL; + } + crc_data->luma0 = DecArg.args.get_config.out_config_value[0]; + crc_data->chroma0 = DecArg.args.get_config.out_config_value[1]; + break; + + case MFC_DEC_GETCONF_FRAME_TAG: + *((unsigned int *)value) = pCTX->out_frametag_top; + break; + + default: + LOGE("SsbSipMfcDecGetConfig: No such conf_type is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + + return MFC_RET_OK; +} + +int tile_4x2_read(int x_size, int y_size, int x_pos, int y_pos) +{ + int pixel_x_m1, pixel_y_m1; + int roundup_x, roundup_y; + int linear_addr0, linear_addr1, bank_addr ; + int x_addr; + int trans_addr; + + pixel_x_m1 = x_size -1; + pixel_y_m1 = y_size -1; + + roundup_x = ((pixel_x_m1 >> 7) + 1); + roundup_y = ((pixel_x_m1 >> 6) + 1); + + x_addr = x_pos >> 2; + + if ((y_size <= y_pos+32) && ( y_pos < y_size) && + (((pixel_y_m1 >> 5) & 0x1) == 0) && (((y_pos >> 5) & 0x1) == 0)) { + linear_addr0 = (((y_pos & 0x1f) <<4) | (x_addr & 0xf)); + linear_addr1 = (((y_pos >> 6) & 0xff) * roundup_x + ((x_addr >> 6) & 0x3f)); + + if (((x_addr >> 5) & 0x1) == ((y_pos >> 5) & 0x1)) + bank_addr = ((x_addr >> 4) & 0x1); + else + bank_addr = 0x2 | ((x_addr >> 4) & 0x1); + } else { + linear_addr0 = (((y_pos & 0x1f) << 4) | (x_addr & 0xf)); + linear_addr1 = (((y_pos >> 6) & 0xff) * roundup_x + ((x_addr >> 5) & 0x7f)); + + if (((x_addr >> 5) & 0x1) == ((y_pos >> 5) & 0x1)) + bank_addr = ((x_addr >> 4) & 0x1); + else + bank_addr = 0x2 | ((x_addr >> 4) & 0x1); + } + + linear_addr0 = linear_addr0 << 2; + trans_addr = (linear_addr1 <<13) | (bank_addr << 11) | linear_addr0; + + return trans_addr; +} + +void tile_to_linear_4x2(unsigned char *p_linear_addr, unsigned char *p_tiled_addr, unsigned int x_size, unsigned int y_size) +{ + int trans_addr; + unsigned int i, j, k, index; + unsigned char data8[4]; + unsigned int max_index = x_size * y_size; + + for (i = 0; i < y_size; i = i + 16) { + for (j = 0; j < x_size; j = j + 16) { + trans_addr = tile_4x2_read(x_size, y_size, j, i); + for (k = 0; k < 16; k++) { + /* limit check - prohibit segmentation fault */ + index = (i * x_size) + (x_size * k) + j; + /* remove equal condition to solve thumbnail bug */ + if (index + 16 > max_index) { + continue; + } + + data8[0] = p_tiled_addr[trans_addr + 64 * k + 0]; + data8[1] = p_tiled_addr[trans_addr + 64 * k + 1]; + data8[2] = p_tiled_addr[trans_addr + 64 * k + 2]; + data8[3] = p_tiled_addr[trans_addr + 64 * k + 3]; + + p_linear_addr[i * x_size + x_size * k + j] = data8[0]; + p_linear_addr[i * x_size + x_size * k + j + 1] = data8[1]; + p_linear_addr[i * x_size + x_size * k + j + 2] = data8[2]; + p_linear_addr[i * x_size + x_size * k + j + 3] = data8[3]; + + data8[0] = p_tiled_addr[trans_addr + 64 * k + 4]; + data8[1] = p_tiled_addr[trans_addr + 64 * k + 5]; + data8[2] = p_tiled_addr[trans_addr + 64 * k + 6]; + data8[3] = p_tiled_addr[trans_addr + 64 * k + 7]; + + p_linear_addr[i * x_size + x_size * k + j + 4] = data8[0]; + p_linear_addr[i * x_size + x_size * k + j + 5] = data8[1]; + p_linear_addr[i * x_size + x_size * k + j + 6] = data8[2]; + p_linear_addr[i * x_size + x_size * k + j + 7] = data8[3]; + + data8[0] = p_tiled_addr[trans_addr + 64 * k + 8]; + data8[1] = p_tiled_addr[trans_addr + 64 * k + 9]; + data8[2] = p_tiled_addr[trans_addr + 64 * k + 10]; + data8[3] = p_tiled_addr[trans_addr + 64 * k + 11]; + p_linear_addr[i*x_size + x_size * k + j + 8] = data8[0]; + p_linear_addr[i*x_size + x_size * k + j + 9] = data8[1]; + p_linear_addr[i*x_size + x_size * k + j + 10] = data8[2]; + p_linear_addr[i*x_size + x_size * k + j + 11] = data8[3]; + + data8[0] = p_tiled_addr[trans_addr + 64 * k + 12]; + data8[1] = p_tiled_addr[trans_addr + 64 * k + 13]; + data8[2] = p_tiled_addr[trans_addr + 64 * k + 14]; + data8[3] = p_tiled_addr[trans_addr + 64 * k + 15]; + p_linear_addr[i*x_size + x_size * k + j + 12] = data8[0]; + p_linear_addr[i*x_size + x_size * k + j + 13] = data8[1]; + p_linear_addr[i*x_size + x_size * k + j + 14] = data8[2]; + p_linear_addr[i*x_size + x_size * k + j + 15] = data8[3]; + } + } + } +} diff --git a/sec_mm/sec_omx/sec_codecs/video/mfc_c110/enc/Android.mk b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/enc/Android.mk new file mode 100644 index 0000000..735da6b --- /dev/null +++ b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/enc/Android.mk @@ -0,0 +1,26 @@ + +LOCAL_PATH := $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_MODULE_TAGS := optional + +LOCAL_SRC_FILES := \ + src/SsbSipMfcEncAPI.c + +LOCAL_MODULE := libsecmfcencapi + +LOCAL_PRELINK_MODULE := false + +LOCAL_CFLAGS := -DUSE_FIMC_FRAME_BUFFER + +LOCAL_ARM_MODE := arm + +LOCAL_STATIC_LIBRARIES := + +LOCAL_SHARED_LIBRARIES := liblog + +LOCAL_C_INCLUDES := \ + $(SEC_CODECS)/video/mfc_c110/include + +include $(BUILD_STATIC_LIBRARY) + diff --git a/sec_mm/sec_omx/sec_codecs/video/mfc_c110/enc/src/SsbSipMfcEncAPI.c b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/enc/src/SsbSipMfcEncAPI.c new file mode 100644 index 0000000..2c33c5b --- /dev/null +++ b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/enc/src/SsbSipMfcEncAPI.c @@ -0,0 +1,630 @@ +/* + * Copyright 2010 Samsung Electronics Co. LTD + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include <stdlib.h> +#include <unistd.h> +#include <string.h> +#include <fcntl.h> + +#include <sys/types.h> +#include <sys/stat.h> +#include <sys/ioctl.h> +#include <sys/mman.h> +#include <utils/Log.h> + +#include "SsbSipMfcApi.h" +#include "mfc_interface.h" + +#define _MFCLIB_MAGIC_NUMBER 0x92241001 + +void *SsbSipMfcEncOpen(void) +{ + int hMFCOpen; + _MFCLIB *pCTX; + unsigned int mapped_addr; + + hMFCOpen = open(S5PC110_MFC_DEV_NAME, O_RDWR | O_NDELAY); + if (hMFCOpen < 0) { + LOGE("SsbSipMfcEncOpen: MFC Open failure\n"); + return NULL; + } + + pCTX = (_MFCLIB *)malloc(sizeof(_MFCLIB)); + if (pCTX == NULL) { + LOGE("SsbSipMfcEncOpen: malloc failed.\n"); + close(hMFCOpen); + return NULL; + } + + mapped_addr = (unsigned int)mmap(0, MMAP_BUFFER_SIZE_MMAP, PROT_READ | PROT_WRITE, MAP_SHARED, hMFCOpen, 0); + if (!mapped_addr) { + LOGE("SsbSipMfcEncOpen: FIMV5.0 driver address mapping failed\n"); + return NULL; + } + + memset(pCTX, 0, sizeof(_MFCLIB)); + + pCTX->magic = _MFCLIB_MAGIC_NUMBER; + pCTX->hMFC = hMFCOpen; + pCTX->mapped_addr = mapped_addr; + pCTX->inter_buff_status = MFC_USE_NONE; + + return (void *)pCTX; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncInit(void *openHandle, void *param) +{ + int ret_code; + int dpbBufSize; + + _MFCLIB *pCTX; + mfc_common_args EncArg; + mfc_common_args user_addr_arg, phys_addr_arg; + SSBSIP_MFC_ENC_H264_PARAM *h264_arg; + SSBSIP_MFC_ENC_MPEG4_PARAM *mpeg4_arg; + SSBSIP_MFC_ENC_H263_PARAM *h263_arg; + SSBSIP_MFC_CODEC_TYPE codec_type; + + pCTX = (_MFCLIB *)openHandle; + memset(&EncArg, 0, sizeof(mfc_common_args)); + + LOGV("SsbSipMfcEncInit: Encode Init start\n"); + + mpeg4_arg = (SSBSIP_MFC_ENC_MPEG4_PARAM *)param; + codec_type = mpeg4_arg->codecType; + + if ((codec_type != MPEG4_ENC) && + (codec_type != H264_ENC) && + (codec_type != H263_ENC)) { + LOGE("SsbSipMfcEncOpen: Undefined codec type.\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX->codec_type = codec_type; + + switch (pCTX->codec_type) { + case MPEG4_ENC: + LOGV("SsbSipMfcEncInit: MPEG4 Encode\n"); + mpeg4_arg = (SSBSIP_MFC_ENC_MPEG4_PARAM *)param; + + pCTX->width = mpeg4_arg->SourceWidth; + pCTX->height = mpeg4_arg->SourceHeight; + break; + + case H263_ENC: + LOGV("SsbSipMfcEncInit: H263 Encode\n"); + h263_arg = (SSBSIP_MFC_ENC_H263_PARAM *)param; + + pCTX->width = h263_arg->SourceWidth; + pCTX->height = h263_arg->SourceHeight; + break; + + case H264_ENC: + LOGV("SsbSipMfcEncInit: H264 Encode\n"); + h264_arg = (SSBSIP_MFC_ENC_H264_PARAM *)param; + + pCTX->width = h264_arg->SourceWidth; + pCTX->height = h264_arg->SourceHeight; + break; + + default: + break; + } + + switch (pCTX->codec_type) { + case MPEG4_ENC: + mpeg4_arg = (SSBSIP_MFC_ENC_MPEG4_PARAM*)param; + + EncArg.args.enc_init_mpeg4.in_codec_type = pCTX->codec_type; + EncArg.args.enc_init_mpeg4.in_profile_level = ENC_PROFILE_LEVEL(mpeg4_arg->ProfileIDC, mpeg4_arg->LevelIDC); + + EncArg.args.enc_init_mpeg4.in_width = mpeg4_arg->SourceWidth; + EncArg.args.enc_init_mpeg4.in_height = mpeg4_arg->SourceHeight; + EncArg.args.enc_init_mpeg4.in_gop_num = mpeg4_arg->IDRPeriod; + if (mpeg4_arg->DisableQpelME) + EncArg.args.enc_init_mpeg4.in_qpelME_enable = 0; + else + EncArg.args.enc_init_mpeg4.in_qpelME_enable = 1; + + EncArg.args.enc_init_mpeg4.in_MS_mode = mpeg4_arg->SliceMode; + EncArg.args.enc_init_mpeg4.in_MS_size = mpeg4_arg->SliceArgument; + + if (mpeg4_arg->NumberBFrames > 2) { + LOGE("SsbSipMfcEncInit: No such BframeNum is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_mpeg4.in_BframeNum = mpeg4_arg->NumberBFrames; + EncArg.args.enc_init_mpeg4.in_mb_refresh = mpeg4_arg->RandomIntraMBRefresh; + + /* rate control*/ + EncArg.args.enc_init_mpeg4.in_RC_frm_enable = mpeg4_arg->EnableFRMRateControl; + if ((mpeg4_arg->QSCodeMin > 51) || (mpeg4_arg->QSCodeMax > 51)) { + LOGE("SsbSipMfcEncInit: No such Min/Max QP is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_mpeg4.in_RC_qbound = ENC_RC_QBOUND(mpeg4_arg->QSCodeMin, mpeg4_arg->QSCodeMax); + EncArg.args.enc_init_mpeg4.in_RC_rpara = mpeg4_arg->CBRPeriodRf; + + /* pad control */ + EncArg.args.enc_init_mpeg4.in_pad_ctrl_on = mpeg4_arg->PadControlOn; + if ((mpeg4_arg->LumaPadVal > 255) || (mpeg4_arg->CbPadVal > 255) || (mpeg4_arg->CrPadVal > 255)) { + LOGE("SsbSipMfcEncInit: No such Pad value is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_mpeg4.in_luma_pad_val = mpeg4_arg->LumaPadVal; + EncArg.args.enc_init_mpeg4.in_cb_pad_val = mpeg4_arg->CbPadVal; + EncArg.args.enc_init_mpeg4.in_cr_pad_val = mpeg4_arg->CrPadVal; + + EncArg.args.enc_init_mpeg4.in_time_increament_res = mpeg4_arg->TimeIncreamentRes; + EncArg.args.enc_init_mpeg4.in_time_vop_time_increament = mpeg4_arg->VopTimeIncreament; + EncArg.args.enc_init_mpeg4.in_RC_framerate = (mpeg4_arg->TimeIncreamentRes / mpeg4_arg->VopTimeIncreament); + EncArg.args.enc_init_mpeg4.in_RC_bitrate = mpeg4_arg->Bitrate; + if ((mpeg4_arg->FrameQp > 51) || (mpeg4_arg->FrameQp_P) > 51 || (mpeg4_arg->FrameQp_B > 51)) { + LOGE("SsbSipMfcEncInit: No such FrameQp is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_mpeg4.in_frame_qp = mpeg4_arg->FrameQp; + if (mpeg4_arg->FrameQp_P) + EncArg.args.enc_init_mpeg4.in_frame_P_qp = mpeg4_arg->FrameQp_P; + else + EncArg.args.enc_init_mpeg4.in_frame_P_qp = mpeg4_arg->FrameQp; + if (mpeg4_arg->FrameQp_B) + EncArg.args.enc_init_mpeg4.in_frame_B_qp = mpeg4_arg->FrameQp_B; + else + EncArg.args.enc_init_mpeg4.in_frame_B_qp = mpeg4_arg->FrameQp; + + break; + + case H263_ENC: + h263_arg = (SSBSIP_MFC_ENC_H263_PARAM *)param; + + EncArg.args.enc_init_mpeg4.in_codec_type = pCTX->codec_type; + EncArg.args.enc_init_mpeg4.in_profile_level = ENC_PROFILE_LEVEL(66, 40); + EncArg.args.enc_init_mpeg4.in_width = h263_arg->SourceWidth; + EncArg.args.enc_init_mpeg4.in_height = h263_arg->SourceHeight; + EncArg.args.enc_init_mpeg4.in_gop_num = h263_arg->IDRPeriod; + EncArg.args.enc_init_mpeg4.in_mb_refresh = h263_arg->RandomIntraMBRefresh; + EncArg.args.enc_init_mpeg4.in_MS_mode = h263_arg->SliceMode; + EncArg.args.enc_init_mpeg4.in_MS_size = 0; + + /* rate control*/ + EncArg.args.enc_init_mpeg4.in_RC_frm_enable = h263_arg->EnableFRMRateControl; + if ((h263_arg->QSCodeMin > 51) || (h263_arg->QSCodeMax > 51)) { + LOGE("SsbSipMfcEncInit: No such Min/Max QP is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_mpeg4.in_RC_qbound = ENC_RC_QBOUND(h263_arg->QSCodeMin, h263_arg->QSCodeMax); + EncArg.args.enc_init_mpeg4.in_RC_rpara = h263_arg->CBRPeriodRf; + + /* pad control */ + EncArg.args.enc_init_mpeg4.in_pad_ctrl_on = h263_arg->PadControlOn; + if ((h263_arg->LumaPadVal > 255) || (h263_arg->CbPadVal > 255) || (h263_arg->CrPadVal > 255)) { + LOGE("SsbSipMfcEncInit: No such Pad value is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_mpeg4.in_luma_pad_val = h263_arg->LumaPadVal; + EncArg.args.enc_init_mpeg4.in_cb_pad_val = h263_arg->CbPadVal; + EncArg.args.enc_init_mpeg4.in_cr_pad_val = h263_arg->CrPadVal; + + EncArg.args.enc_init_mpeg4.in_RC_framerate = h263_arg->FrameRate; + EncArg.args.enc_init_mpeg4.in_RC_bitrate = h263_arg->Bitrate; + if (h263_arg->FrameQp > 51) { + LOGE("SsbSipMfcEncInit: No such FrameQp is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_mpeg4.in_frame_qp = h263_arg->FrameQp; + if (h263_arg->FrameQp_P) + EncArg.args.enc_init_mpeg4.in_frame_P_qp = h263_arg->FrameQp_P; + else + EncArg.args.enc_init_mpeg4.in_frame_P_qp = h263_arg->FrameQp; + + break; + + case H264_ENC: + h264_arg = (SSBSIP_MFC_ENC_H264_PARAM *)param; + + EncArg.args.enc_init_h264.in_codec_type = H264_ENC; + EncArg.args.enc_init_h264.in_profile_level = ENC_PROFILE_LEVEL(h264_arg->ProfileIDC, h264_arg->LevelIDC); + + EncArg.args.enc_init_h264.in_width = h264_arg->SourceWidth; + EncArg.args.enc_init_h264.in_height = h264_arg->SourceHeight; + EncArg.args.enc_init_h264.in_gop_num = h264_arg->IDRPeriod; + + if ((h264_arg->NumberRefForPframes > 2) || (h264_arg->NumberReferenceFrames > 2)) { + LOGE("SsbSipMfcEncInit: No such ref Num is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_h264.in_reference_num = h264_arg->NumberReferenceFrames; + EncArg.args.enc_init_h264.in_ref_num_p = h264_arg->NumberRefForPframes; + + if ((h264_arg->SliceMode == 0) || (h264_arg->SliceMode == 1) || + (h264_arg->SliceMode == 2) || (h264_arg->SliceMode == 4)) { + EncArg.args.enc_init_h264.in_MS_mode = h264_arg->SliceMode; + } else { + LOGE("SsbSipMfcEncInit: No such slice mode is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_h264.in_MS_size = h264_arg->SliceArgument; + + if (h264_arg->NumberBFrames > 2) { + LOGE("SsbSipMfcEncInit: No such BframeNum is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_h264.in_BframeNum = h264_arg->NumberBFrames; + + EncArg.args.enc_init_h264.in_deblock_filt = h264_arg->LoopFilterDisable; + if ((abs(h264_arg->LoopFilterAlphaC0Offset) > 6) || (abs(h264_arg->LoopFilterBetaOffset) > 6)) { + LOGE("SsbSipMfcEncInit: No such AlphaC0Offset or BetaOffset is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_h264.in_deblock_alpha_C0 = h264_arg->LoopFilterAlphaC0Offset; + EncArg.args.enc_init_h264.in_deblock_beta = h264_arg->LoopFilterBetaOffset; + + EncArg.args.enc_init_h264.in_symbolmode = h264_arg->SymbolMode; + EncArg.args.enc_init_h264.in_interlace_mode = h264_arg->PictureInterlace; + EncArg.args.enc_init_h264.in_transform8x8_mode = h264_arg->Transform8x8Mode; + + EncArg.args.enc_init_h264.in_mb_refresh = h264_arg->RandomIntraMBRefresh; + + /* pad control */ + EncArg.args.enc_init_h264.in_pad_ctrl_on = h264_arg->PadControlOn; + if ((h264_arg->LumaPadVal > 255) || (h264_arg->CbPadVal > 255) || (h264_arg->CrPadVal > 255)) { + LOGE("SsbSipMfcEncInit: No such Pad value is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_h264.in_luma_pad_val = h264_arg->LumaPadVal; + EncArg.args.enc_init_h264.in_cb_pad_val = h264_arg->CbPadVal; + EncArg.args.enc_init_h264.in_cr_pad_val = h264_arg->CrPadVal; + + /* rate control*/ + EncArg.args.enc_init_h264.in_RC_frm_enable = h264_arg->EnableFRMRateControl; + EncArg.args.enc_init_h264.in_RC_mb_enable = h264_arg->EnableMBRateControl; + EncArg.args.enc_init_h264.in_RC_framerate = h264_arg->FrameRate; + EncArg.args.enc_init_h264.in_RC_bitrate = h264_arg->Bitrate; + if (h264_arg->FrameQp > 51) { + LOGE("SsbSipMfcEncInit: No such FrameQp is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_h264.in_frame_qp = h264_arg->FrameQp; + if (h264_arg->FrameQp_P) + EncArg.args.enc_init_h264.in_frame_P_qp = h264_arg->FrameQp_P; + else + EncArg.args.enc_init_h264.in_frame_P_qp = h264_arg->FrameQp; + if (h264_arg->FrameQp_B) + EncArg.args.enc_init_h264.in_frame_B_qp = h264_arg->FrameQp_B; + else + EncArg.args.enc_init_h264.in_frame_B_qp = h264_arg->FrameQp; + + if ((h264_arg->QSCodeMin > 51) || (h264_arg->QSCodeMax > 51)) { + LOGE("SsbSipMfcEncInit: No such Min/Max QP is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + EncArg.args.enc_init_h264.in_RC_qbound = ENC_RC_QBOUND(h264_arg->QSCodeMin, h264_arg->QSCodeMax); + EncArg.args.enc_init_h264.in_RC_rpara = h264_arg->CBRPeriodRf; + EncArg.args.enc_init_h264.in_RC_mb_dark_disable = h264_arg->DarkDisable; + EncArg.args.enc_init_h264.in_RC_mb_smooth_disable = h264_arg->SmoothDisable; + EncArg.args.enc_init_h264.in_RC_mb_static_disable = h264_arg->StaticDisable; + EncArg.args.enc_init_h264.in_RC_mb_activity_disable = h264_arg->ActivityDisable; + + /* default setting */ + EncArg.args.enc_init_h264.in_md_interweight_pps = 0; + EncArg.args.enc_init_h264.in_md_intraweight_pps = 0; + break; + + default: + break; + } + + EncArg.args.enc_init_mpeg4.in_mapped_addr = pCTX->mapped_addr; + + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_ENC_INIT, &EncArg); + if (EncArg.ret_code != MFC_RET_OK) { + LOGE("SsbSipMfcEncInit: IOCTL_MFC_ENC_INIT (%d) failed\n", EncArg.ret_code); + return MFC_RET_ENC_INIT_FAIL; + } + + pCTX->virStrmBuf = EncArg.args.enc_init_mpeg4.out_u_addr.strm_ref_y; + pCTX->phyStrmBuf = EncArg.args.enc_init_mpeg4.out_p_addr.strm_ref_y; + pCTX->sizeStrmBuf = MAX_ENCODER_OUTPUT_BUFFER_SIZE; + pCTX->encodedHeaderSize = EncArg.args.enc_init_mpeg4.out_header_size; + + pCTX->virMvRefYC = EncArg.args.enc_init_mpeg4.out_u_addr.mv_ref_yc; + + pCTX->inter_buff_status |= MFC_USE_STRM_BUFF; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncExe(void *openHandle) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args EncArg; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncExe: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + + memset(&EncArg, 0x00, sizeof(mfc_common_args)); + + EncArg.args.enc_exe.in_codec_type = pCTX->codec_type; + EncArg.args.enc_exe.in_Y_addr = (unsigned int)pCTX->phyFrmBuf.luma; + EncArg.args.enc_exe.in_CbCr_addr = (unsigned int)pCTX->phyFrmBuf.chroma; + EncArg.args.enc_exe.in_Y_addr_vir = (unsigned int)pCTX->virFrmBuf.luma; + EncArg.args.enc_exe.in_CbCr_addr_vir = (unsigned int)pCTX->virFrmBuf.chroma; + EncArg.args.enc_exe.in_strm_st = (unsigned int)pCTX->phyStrmBuf; + EncArg.args.enc_exe.in_strm_end = (unsigned int)pCTX->phyStrmBuf + pCTX->sizeStrmBuf; + EncArg.args.enc_exe.in_frametag = pCTX->in_frametag; + + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_ENC_EXE, &EncArg); + if (EncArg.ret_code != MFC_RET_OK) { + LOGE("SsbSipMfcDecExe: IOCTL_MFC_ENC_EXE failed(ret : %d)\n", EncArg.ret_code); + return MFC_RET_ENC_EXE_ERR; + } + + pCTX->encodedDataSize = EncArg.args.enc_exe.out_encoded_size; + pCTX->encodedframeType = EncArg.args.enc_exe.out_frame_type; + pCTX->encoded_Y_paddr = EncArg.args.enc_exe.out_encoded_Y_paddr; + pCTX->encoded_C_paddr = EncArg.args.enc_exe.out_encoded_C_paddr; + pCTX->out_frametag_top = EncArg.args.enc_exe.out_frametag_top; + pCTX->out_frametag_bottom = EncArg.args.enc_exe.out_frametag_bottom; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncClose(void *openHandle) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args free_arg; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncClose: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + + if (pCTX->inter_buff_status & MFC_USE_YUV_BUFF) { + free_arg.args.mem_free.u_addr = pCTX->virFrmBuf.luma; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_FREE_BUF, &free_arg); + } + + if (pCTX->inter_buff_status & MFC_USE_STRM_BUFF) { + free_arg.args.mem_free.u_addr = pCTX->virStrmBuf; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_FREE_BUF, &free_arg); + free_arg.args.mem_free.u_addr = pCTX->virMvRefYC; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_FREE_BUF, &free_arg); + } + + pCTX->inter_buff_status = MFC_USE_NONE; + + munmap((void *)pCTX->mapped_addr, MMAP_BUFFER_SIZE_MMAP); + close(pCTX->hMFC); + free(pCTX); + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncGetInBuf(void *openHandle, SSBSIP_MFC_ENC_INPUT_INFO *input_info) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args user_addr_arg, phys_addr_arg; + int y_size, c_size; + int aligned_y_size, aligned_c_size; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncGetInBuf: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + + user_addr_arg.args.mem_alloc.codec_type = pCTX->codec_type; + + y_size = pCTX->width * pCTX->height; + c_size = (pCTX->width * pCTX->height) >> 1; + + aligned_y_size = ALIGN_TO_8KB(ALIGN_TO_128B(pCTX->width) * ALIGN_TO_32B(pCTX->height)); + aligned_c_size = ALIGN_TO_8KB(ALIGN_TO_128B(pCTX->width) * ALIGN_TO_32B(pCTX->height/2)); + + /* Allocate luma & chroma buf */ + user_addr_arg.args.mem_alloc.buff_size = aligned_y_size + aligned_c_size; + user_addr_arg.args.mem_alloc.mapped_addr = pCTX->mapped_addr; + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_GET_IN_BUF, &user_addr_arg); + if (ret_code < 0) { + LOGE("SsbSipMfcEncGetInBuf: IOCTL_MFC_GET_IN_BUF failed\n"); + return MFC_RET_ENC_GET_INBUF_FAIL; + } + pCTX->virFrmBuf.luma = user_addr_arg.args.mem_alloc.out_uaddr; + pCTX->virFrmBuf.chroma = user_addr_arg.args.mem_alloc.out_uaddr + (unsigned int)aligned_y_size; + pCTX->phyFrmBuf.luma = user_addr_arg.args.mem_alloc.out_paddr; + pCTX->phyFrmBuf.chroma = user_addr_arg.args.mem_alloc.out_paddr + (unsigned int)aligned_y_size; + + pCTX->sizeFrmBuf.luma = (unsigned int)y_size; + pCTX->sizeFrmBuf.chroma = (unsigned int)c_size; + pCTX->inter_buff_status |= MFC_USE_YUV_BUFF; + + input_info->YPhyAddr = (void*)pCTX->phyFrmBuf.luma; + input_info->CPhyAddr = (void*)pCTX->phyFrmBuf.chroma; + input_info->YVirAddr = (void*)pCTX->virFrmBuf.luma; + input_info->CVirAddr = (void*)pCTX->virFrmBuf.chroma; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncSetInBuf(void *openHandle, SSBSIP_MFC_ENC_INPUT_INFO *input_info) +{ + _MFCLIB *pCTX; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncSetInBuf: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + LOGV("SsbSipMfcEncSetInBuf: input_info->YPhyAddr & input_info->CPhyAddr should be 64KB aligned\n"); + + pCTX = (_MFCLIB *)openHandle; + + pCTX->phyFrmBuf.luma = (unsigned int)input_info->YPhyAddr; + pCTX->phyFrmBuf.chroma = (unsigned int)input_info->CPhyAddr; + pCTX->virFrmBuf.luma = (unsigned int)input_info->YVirAddr; + pCTX->virFrmBuf.chroma = (unsigned int)input_info->CVirAddr; + + pCTX->sizeFrmBuf.luma = (unsigned int)input_info->YSize; + pCTX->sizeFrmBuf.chroma = (unsigned int)input_info->CSize; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncGetOutBuf(void *openHandle, SSBSIP_MFC_ENC_OUTPUT_INFO *output_info) +{ + _MFCLIB *pCTX; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncGetOutBuf: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + + output_info->headerSize = pCTX->encodedHeaderSize; + output_info->dataSize = pCTX->encodedDataSize; + output_info->StrmPhyAddr = (void *)pCTX->phyStrmBuf; + output_info->StrmVirAddr = (void *)pCTX->virStrmBuf; + + if (pCTX->encodedframeType == 0) + output_info->frameType = MFC_FRAME_TYPE_NOT_CODED; + else if (pCTX->encodedframeType == 1) + output_info->frameType = MFC_FRAME_TYPE_I_FRAME; + else if (pCTX->encodedframeType == 2) + output_info->frameType = MFC_FRAME_TYPE_P_FRAME; + else if (pCTX->encodedframeType == 3) + output_info->frameType = MFC_FRAME_TYPE_B_FRAME; + else if (pCTX->encodedframeType == 4) + output_info->frameType = MFC_FRAME_TYPE_OTHERS; + else { + LOGE("Strange encoded frame type = %d\n", pCTX->encodedframeType); + return MFC_RET_INVALID_PARAM; + } + + output_info->encodedYPhyAddr = (void *)pCTX->encoded_Y_paddr; + output_info->encodedCPhyAddr = (void *)pCTX->encoded_C_paddr; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncSetOutBuf(void *openHandle, void *phyOutbuf, void *virOutbuf, int outputBufferSize) +{ + _MFCLIB *pCTX; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncSetOutBuf: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + + pCTX->phyStrmBuf = (int)phyOutbuf; + pCTX->virStrmBuf = (int)virOutbuf; + pCTX->sizeStrmBuf = outputBufferSize; + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncSetConfig(void *openHandle, SSBSIP_MFC_ENC_CONF conf_type, void *value) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args EncArg; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncSetConfig: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + if (value == NULL) { + LOGE("SsbSipMfcEncSetConfig: value is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + memset(&EncArg, 0x00, sizeof(mfc_common_args)); + + switch (conf_type) { + case MFC_ENC_SETCONF_FRAME_TYPE: + case MFC_ENC_SETCONF_CHANGE_FRAME_RATE: + case MFC_ENC_SETCONF_CHANGE_BIT_RATE: + case MFC_ENC_SETCONF_ALLOW_FRAME_SKIP: + EncArg.args.set_config.in_config_param = conf_type; + EncArg.args.set_config.in_config_value[0] = *((unsigned int *) value); + EncArg.args.set_config.in_config_value[1] = 0; + break; + + case MFC_ENC_SETCONF_FRAME_TAG: + pCTX->in_frametag = *((int *)value); + return MFC_RET_OK; + + default: + LOGE("SsbSipMfcEncSetConfig: No such conf_type is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + + ret_code = ioctl(pCTX->hMFC, IOCTL_MFC_SET_CONFIG, &EncArg); + if (EncArg.ret_code != MFC_RET_OK) { + LOGE("SsbSipMfcEncSetConfig: IOCTL_MFC_SET_CONFIG failed(ret : %d)\n", EncArg.ret_code); + return MFC_RET_ENC_SET_CONF_FAIL; + } + + return MFC_RET_OK; +} + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncGetConfig(void *openHandle, SSBSIP_MFC_ENC_CONF conf_type, void *value) +{ + int ret_code; + _MFCLIB *pCTX; + mfc_common_args EncArg; + + pCTX = (_MFCLIB *)openHandle; + + if (openHandle == NULL) { + LOGE("SsbSipMfcEncGetConfig: openHandle is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + if (value == NULL) { + LOGE("SsbSipMfcEncGetConfig: value is NULL\n"); + return MFC_RET_INVALID_PARAM; + } + + pCTX = (_MFCLIB *)openHandle; + memset(&EncArg, 0x00, sizeof(mfc_common_args)); + + switch (conf_type) { + case MFC_ENC_GETCONF_FRAME_TAG: + *((unsigned int *)value) = pCTX->out_frametag_top; + break; + + default: + LOGE("SsbSipMfcEncGetConfig: No such conf_type is supported.\n"); + return MFC_RET_INVALID_PARAM; + } + + return MFC_RET_OK; +} diff --git a/sec_mm/sec_omx/sec_codecs/video/mfc_c110/include/SsbSipMfcApi.h b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/include/SsbSipMfcApi.h new file mode 100644 index 0000000..f8aaddc --- /dev/null +++ b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/include/SsbSipMfcApi.h @@ -0,0 +1,323 @@ +/* + * Copyright 2010 Samsung Electronics Co. LTD + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef _SSBSIP_MFC_API_H_ +#define _SSBSIP_MFC_API_H_ + +/*--------------------------------------------------------------------------------*/ +/* Definition */ +/*--------------------------------------------------------------------------------*/ +#define MAX_DECODER_INPUT_BUFFER_SIZE (1024 * 3072) +#define MAX_ENCODER_OUTPUT_BUFFER_SIZE (1024 * 3072) + +#define SUPPORT_1080P 1 + +#if SUPPORT_1080P +#define MMAP_BUFFER_SIZE_MMAP (63*1024*1024) +#else +#define MMAP_BUFFER_SIZE_MMAP (49*1024*1024) +#endif + +#define S5PC110_MFC_DEV_NAME "/dev/s3c-mfc" + +/*--------------------------------------------------------------------------------*/ +/* Structure and Type */ +/*--------------------------------------------------------------------------------*/ +typedef enum { + H264_DEC, + VC1_DEC, /* VC1 advaced Profile decoding */ + MPEG4_DEC, + XVID_DEC, + MPEG1_DEC, + MPEG2_DEC, + H263_DEC, + VC1RCV_DEC, /* VC1 simple/main profile decoding */ + FIMV1_DEC, + FIMV2_DEC, + FIMV3_DEC, + FIMV4_DEC, + H264_ENC, + MPEG4_ENC, + H263_ENC, + UNKNOWN_TYPE +} SSBSIP_MFC_CODEC_TYPE; + +typedef enum { + DONT_CARE = 0, + I_FRAME = 1, + NOT_CODED = 2 +} SSBSIP_MFC_FORCE_SET_FRAME_TYPE; + +typedef enum { + MFC_DEC_SETCONF_POST_ENABLE = 1, + MFC_DEC_SETCONF_EXTRA_BUFFER_NUM, + MFC_DEC_SETCONF_DISPLAY_DELAY, + MFC_DEC_SETCONF_IS_LAST_FRAME, + MFC_DEC_SETCONF_SLICE_ENABLE, + MFC_DEC_SETCONF_CRC_ENABLE, + MFC_DEC_SETCONF_FIMV1_WIDTH_HEIGHT, + MFC_DEC_SETCONF_FRAME_TAG, + MFC_DEC_GETCONF_CRC_DATA, + MFC_DEC_GETCONF_BUF_WIDTH_HEIGHT, + MFC_DEC_GETCONF_FRAME_TAG +} SSBSIP_MFC_DEC_CONF; + +typedef enum { + MFC_ENC_SETCONF_FRAME_TYPE = 100, + MFC_ENC_SETCONF_CHANGE_FRAME_RATE, + MFC_ENC_SETCONF_CHANGE_BIT_RATE, + MFC_ENC_SETCONF_FRAME_TAG, + MFC_ENC_SETCONF_ALLOW_FRAME_SKIP, + MFC_ENC_GETCONF_FRAME_TAG +} SSBSIP_MFC_ENC_CONF; + +typedef enum { + MFC_GETOUTBUF_STATUS_NULL = 0, + MFC_GETOUTBUF_DECODING_ONLY = 1, + MFC_GETOUTBUF_DISPLAY_DECODING, + MFC_GETOUTBUF_DISPLAY_ONLY, + MFC_GETOUTBUF_DISPLAY_END +} SSBSIP_MFC_DEC_OUTBUF_STATUS; + +typedef enum { + MFC_FRAME_TYPE_NOT_CODED, + MFC_FRAME_TYPE_I_FRAME, + MFC_FRAME_TYPE_P_FRAME, + MFC_FRAME_TYPE_B_FRAME, + MFC_FRAME_TYPE_OTHERS +} SSBSIP_MFC_FRAME_TYPE; + +typedef enum { + MFC_RET_OK = 1, + MFC_RET_FAIL = -1000, + MFC_RET_OPEN_FAIL = -1001, + MFC_RET_CLOSE_FAIL = -1002, + + MFC_RET_DEC_INIT_FAIL = -2000, + MFC_RET_DEC_EXE_TIME_OUT = -2001, + MFC_RET_DEC_EXE_ERR = -2002, + MFC_RET_DEC_GET_INBUF_FAIL = -2003, + MFC_RET_DEC_SET_INBUF_FAIL = -2004, + MFC_RET_DEC_GET_OUTBUF_FAIL = -2005, + MFC_RET_DEC_GET_CONF_FAIL = -2006, + MFC_RET_DEC_SET_CONF_FAIL = -2007, + + MFC_RET_ENC_INIT_FAIL = -3000, + MFC_RET_ENC_EXE_TIME_OUT = -3001, + MFC_RET_ENC_EXE_ERR = -3002, + MFC_RET_ENC_GET_INBUF_FAIL = -3003, + MFC_RET_ENC_SET_INBUF_FAIL = -3004, + MFC_RET_ENC_GET_OUTBUF_FAIL = -3005, + MFC_RET_ENC_SET_OUTBUF_FAIL = -3006, + MFC_RET_ENC_GET_CONF_FAIL = -3007, + MFC_RET_ENC_SET_CONF_FAIL = -3008, + + MFC_RET_INVALID_PARAM = -4000 +} SSBSIP_MFC_ERROR_CODE; + +typedef struct { + void *YPhyAddr; // [OUT] physical address of Y + void *CPhyAddr; // [OUT] physical address of CbCr + void *YVirAddr; // [OUT] virtual address of Y + void *CVirAddr; // [OUT] virtual address of CbCr + + int img_width; // [OUT] width of real image + int img_height; // [OUT] height of real image + int buf_width; // [OUT] width aligned to 16 + int buf_height; // [OUT] height alighed to 16 + + int timestamp_top; // [OUT] timestamp of top filed(This is used for interlaced stream) + int timestamp_bottom; // [OUT] timestamp of bottom filed(This is used for interlaced stream) + int consumedByte; // [OUT] the number of byte consumed during decoding + int res_change; // [OUT] whether resolution is changed or not. 0: not change, 1: increased, 2: decreased + int crop_top_offset; // [OUT] crop information, top_offset + int crop_bottom_offset; // [OUT] crop information, bottom_offset + int crop_left_offset; // [OUT] crop information, left_offset + int crop_right_offset; // [OUT] crop information, right_offset +} SSBSIP_MFC_DEC_OUTPUT_INFO; + +typedef struct { + void *YPhyAddr; // [IN/OUT] physical address of Y + void *CPhyAddr; // [IN/OUT] physical address of CbCr + void *YVirAddr; // [IN/OUT] virtual address of Y + void *CVirAddr; // [IN/OUT] virtual address of CbCr + int YSize; // [IN/OUT] input size of Y data + int CSize; // [IN/OUT] input size of CbCr data +} SSBSIP_MFC_ENC_INPUT_INFO; + +typedef struct { + unsigned int dataSize; // [OUT] encoded data size(without header) + unsigned int headerSize; // [OUT] encoded header size + unsigned int frameType; // [OUT] frame type of encoded stream + void *StrmPhyAddr; // [OUT] physical address of Y + void *StrmVirAddr; // [OUT] virtual address of Y + void *encodedYPhyAddr; // [OUT] physical address of Y which is flushed + void *encodedCPhyAddr; // [OUT] physical address of C which is flushed +} SSBSIP_MFC_ENC_OUTPUT_INFO; + +typedef struct { + // common parameters + SSBSIP_MFC_CODEC_TYPE codecType; // [IN] codec type + int SourceWidth; // [IN] width of video to be encoded + int SourceHeight; // [IN] height of video to be encoded + int IDRPeriod; // [IN] GOP number(interval of I-frame) + int SliceMode; // [IN] Multi slice mode + int RandomIntraMBRefresh; // [IN] cyclic intra refresh + int EnableFRMRateControl; // [IN] frame based rate control enable + int Bitrate; // [IN] rate control parameter(bit rate) + int FrameQp; // [IN] The quantization parameter of the frame + int FrameQp_P; // [IN] The quantization parameter of the P frame + int QSCodeMax; // [IN] Maximum Quantization value + int QSCodeMin; // [IN] Minimum Quantization value + int CBRPeriodRf; // [IN] Reaction coefficient parameter for rate control + int PadControlOn; // [IN] Enable padding control + int LumaPadVal; // [IN] Luma pel value used to fill padding area + int CbPadVal; // [IN] CB pel value used to fill padding area + int CrPadVal; // [IN] CR pel value used to fill padding area + + // H.264 specific parameters + int ProfileIDC; // [IN] profile + int LevelIDC; // [IN] level + int FrameQp_B; // [IN] The quantization parameter of the B frame + int FrameRate; // [IN] rate control parameter(frame rate) + int SliceArgument; // [IN] MB number or byte number + int NumberBFrames; // [IN] The number of consecutive B frame inserted + int NumberReferenceFrames; // [IN] The number of reference pictures used + int NumberRefForPframes; // [IN] The number of reference pictures used for encoding P pictures + int LoopFilterDisable; // [IN] disable the loop filter + int LoopFilterAlphaC0Offset; // [IN] Alpha & C0 offset for H.264 loop filter + int LoopFilterBetaOffset; // [IN] Beta offset for H.264 loop filter + int SymbolMode; // [IN] The mode of entropy coding(CABAC, CAVLC) + int PictureInterlace; // [IN] Enables the interlace mode + int Transform8x8Mode; // [IN] Allow 8x8 transform(This is allowed only for high profile) + int EnableMBRateControl; // [IN] Enable macroblock-level rate control + int DarkDisable; // [IN] Disable adaptive rate control on dark region + int SmoothDisable; // [IN] Disable adaptive rate control on smooth region + int StaticDisable; // [IN] Disable adaptive rate control on static region + int ActivityDisable; // [IN] Disable adaptive rate control on high activity region +} SSBSIP_MFC_ENC_H264_PARAM; + +typedef struct { + // common parameters + SSBSIP_MFC_CODEC_TYPE codecType; // [IN] codec type + int SourceWidth; // [IN] width of video to be encoded + int SourceHeight; // [IN] height of video to be encoded + int IDRPeriod; // [IN] GOP number(interval of I-frame) + int SliceMode; // [IN] Multi slice mode + int RandomIntraMBRefresh; // [IN] cyclic intra refresh + int EnableFRMRateControl; // [IN] frame based rate control enable + int Bitrate; // [IN] rate control parameter(bit rate) + int FrameQp; // [IN] The quantization parameter of the frame + int FrameQp_P; // [IN] The quantization parameter of the P frame + int QSCodeMax; // [IN] Maximum Quantization value + int QSCodeMin; // [IN] Minimum Quantization value + int CBRPeriodRf; // [IN] Reaction coefficient parameter for rate control + int PadControlOn; // [IN] Enable padding control + int LumaPadVal; // [IN] Luma pel value used to fill padding area + int CbPadVal; // [IN] CB pel value used to fill padding area + int CrPadVal; // [IN] CR pel value used to fill padding area + + // MPEG4 specific parameters + int ProfileIDC; // [IN] profile + int LevelIDC; // [IN] level + int FrameQp_B; // [IN] The quantization parameter of the B frame + int TimeIncreamentRes; // [IN] frame rate + int VopTimeIncreament; // [IN] frame rate + int SliceArgument; // [IN] MB number or byte number + int NumberBFrames; // [IN] The number of consecutive B frame inserted + int DisableQpelME; // [IN] disable quarter-pixel motion estimation +} SSBSIP_MFC_ENC_MPEG4_PARAM; + +typedef struct { + // common parameters + SSBSIP_MFC_CODEC_TYPE codecType; // [IN] codec type + int SourceWidth; // [IN] width of video to be encoded + int SourceHeight; // [IN] height of video to be encoded + int IDRPeriod; // [IN] GOP number(interval of I-frame) + int SliceMode; // [IN] Multi slice mode + int RandomIntraMBRefresh; // [IN] cyclic intra refresh + int EnableFRMRateControl; // [IN] frame based rate control enable + int Bitrate; // [IN] rate control parameter(bit rate) + int FrameQp; // [IN] The quantization parameter of the frame + int FrameQp_P; // [IN] The quantization parameter of the P frame + int QSCodeMax; // [IN] Maximum Quantization value + int QSCodeMin; // [IN] Minimum Quantization value + int CBRPeriodRf; // [IN] Reaction coefficient parameter for rate control + int PadControlOn; // [IN] Enable padding control + int LumaPadVal; // [IN] Luma pel value used to fill padding area + int CbPadVal; // [IN] CB pel value used to fill padding area + int CrPadVal; // [IN] CR pel value used to fill padding area + + // H.263 specific parameters + int FrameRate; // [IN] rate control parameter(frame rate) +} SSBSIP_MFC_ENC_H263_PARAM; + +typedef struct { + int width; + int height; + int buf_width; + int buf_height; +} SSBSIP_MFC_IMG_RESOLUTION; + +#ifdef __cplusplus +extern "C" { +#endif + +/*--------------------------------------------------------------------------------*/ +/* Format Conversion API */ +/*--------------------------------------------------------------------------------*/ + +void tile_to_linear_4x2(unsigned char *p_linear_addr, unsigned char *p_tiled_addr, unsigned int x_size, unsigned int y_size); +void tile_to_linear_NEON_NEW(unsigned char *p_linear_addr, unsigned char *p_tiled_addr, unsigned int x_size, unsigned int y_size); + +/*--------------------------------------------------------------------------------*/ +/* Decoding APIs */ +/*--------------------------------------------------------------------------------*/ +void *SsbSipMfcDecOpen(void); +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecInit(void *openHandle, SSBSIP_MFC_CODEC_TYPE codec_type, int Frameleng); +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecExe(void *openHandle, int lengthBufFill); +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecClose(void *openHandle); + +void *SsbSipMfcDecGetInBuf(void *openHandle, void **phyInBuf, int inputBufferSize); +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecSetInBuf(void *openHandle, void *phyInBuf, void *virInBuf, int inputBufferSize); + +SSBSIP_MFC_DEC_OUTBUF_STATUS SsbSipMfcDecGetOutBuf(void *openHandle, SSBSIP_MFC_DEC_OUTPUT_INFO *output_info); + +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecSetConfig(void *openHandle, SSBSIP_MFC_DEC_CONF conf_type, void *value); +SSBSIP_MFC_ERROR_CODE SsbSipMfcDecGetConfig(void *openHandle, SSBSIP_MFC_DEC_CONF conf_type, void *value); + +/*--------------------------------------------------------------------------------*/ +/* Encoding APIs */ +/*--------------------------------------------------------------------------------*/ +void *SsbSipMfcEncOpen(void); +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncInit(void *openHandle, void *param); +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncExe(void *openHandle); +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncClose(void *openHandle); + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncGetInBuf(void *openHandle, SSBSIP_MFC_ENC_INPUT_INFO *input_info); +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncSetInBuf(void *openHandle, SSBSIP_MFC_ENC_INPUT_INFO *input_info); + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncGetOutBuf(void *openHandle, SSBSIP_MFC_ENC_OUTPUT_INFO *output_info); +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncSetOutBuf (void *openHandle, void *phyOutbuf, void *virOutbuf, int outputBufferSize); + +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncSetConfig(void *openHandle, SSBSIP_MFC_ENC_CONF conf_type, void *value); +SSBSIP_MFC_ERROR_CODE SsbSipMfcEncGetConfig(void *openHandle, SSBSIP_MFC_ENC_CONF conf_type, void *value); + +#ifdef __cplusplus +} +#endif + +#endif /* _SSBSIP_MFC_API_H_ */ diff --git a/sec_mm/sec_omx/sec_codecs/video/mfc_c110/include/mfc_interface.h b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/include/mfc_interface.h new file mode 100644 index 0000000..ba7f537 --- /dev/null +++ b/sec_mm/sec_omx/sec_codecs/video/mfc_c110/include/mfc_interface.h @@ -0,0 +1,328 @@ +/* + * Copyright 2010 Samsung Electronics Co. LTD + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef _MFC_INTERFACE_H_ +#define _MFC_INTERFACE_H_ + +#include "SsbSipMfcApi.h" + +#define IOCTL_MFC_DEC_INIT 0x00800001 +#define IOCTL_MFC_ENC_INIT 0x00800002 +#define IOCTL_MFC_DEC_EXE 0x00800003 +#define IOCTL_MFC_ENC_EXE 0x00800004 + +#define IOCTL_MFC_GET_IN_BUF 0x00800010 +#define IOCTL_MFC_FREE_BUF 0x00800011 +#define IOCTL_MFC_GET_PHYS_ADDR 0x00800012 + +#define IOCTL_MFC_SET_CONFIG 0x00800101 +#define IOCTL_MFC_GET_CONFIG 0x00800102 + +/* MFC H/W support maximum 32 extra DPB */ +#define MFC_MAX_EXTRA_DPB 5 + +#define ENC_PROFILE_LEVEL(profile, level) ((profile) | ((level) << 8)) + +#define ENC_PROFILE_MPEG4_SP 0 +#define ENC_PROFILE_MPEG4_ASP 1 +#define ENC_PROFILE_H264_BP 0 +#define ENC_PROFILE_H264_MAIN 1 +#define ENC_PROFILE_H264_HIGH 2 + +#define ENC_RC_DISABLE 0 +#define ENC_RC_ENABLE_MACROBLOCK 1 +#define ENC_RC_ENABLE_FRAME 2 + +#define ENC_RC_QBOUND(min_qp, max_qp) ((min_qp) | ((max_qp) << 8)) +#define ENC_RC_MB_CTRL_DARK_DISABLE (1 << 3) +#define ENC_RC_MB_CTRL_SMOOTH_DISABLE (1 << 2) +#define ENC_RC_MB_CTRL_STATIC_DISABLE (1 << 1) +#define ENC_RC_MB_CTRL_ACTIVITY_DISABLE (1 << 0) + +#define ALIGN_TO_16B(x) ((((x) + (1 << 4) - 1) >> 4) << 4) +#define ALIGN_TO_32B(x) ((((x) + (1 << 5) - 1) >> 5) << 5) +#define ALIGN_TO_64B(x) ((((x) + (1 << 6) - 1) >> 6) << 6) +#define ALIGN_TO_128B(x) ((((x) + (1 << 7) - 1) >> 7) << 7) +#define ALIGN_TO_2KB(x) ((((x) + (1 << 11) - 1) >> 11) << 11) +#define ALIGN_TO_4KB(x) ((((x) + (1 << 12) - 1) >> 12) << 12) +#define ALIGN_TO_8KB(x) ((((x) + (1 << 13) - 1) >> 13) << 13) +#define ALIGN_TO_64KB(x) ((((x) + (1 << 16) - 1) >> 16) << 16) +#define ALIGN_TO_128KB(x) ((((x) + (1 << 17) - 1) >> 17) << 17) + +typedef struct { + int luma0; // per frame (or top field) + int chroma0; // per frame (or top field) + int luma1; // per frame (or bottom field) + int chroma1; // per frame (or bottom field) +} MFC_CRC_DATA; + +typedef enum { + MFC_USE_NONE = 0x00, + MFC_USE_YUV_BUFF = 0x01, + MFC_USE_STRM_BUFF = 0x10 +} mfc_interbuff_status; + +typedef enum { + MFC_UNPACKED_PB = 0, + MFC_PACKED_PB = 1 +} mfc_packed_mode; + +typedef struct tag_strm_ref_buf_arg { + unsigned int strm_ref_y; + unsigned int mv_ref_yc; +} mfc_strm_ref_buf_arg_t; + +typedef struct tag_frame_buf_arg { + unsigned int luma; + unsigned int chroma; +} mfc_frame_buf_arg_t; + +typedef struct { + SSBSIP_MFC_CODEC_TYPE in_codec_type; /* [IN] codec type */ + int in_width; /* [IN] width of YUV420 frame to be encoded */ + int in_height; /* [IN] height of YUV420 frame to be encoded */ + int in_profile_level; /* [IN] profile & level */ + int in_gop_num; /* [IN] GOP Number (interval of I-frame) */ + int in_frame_qp; /* [IN] the quantization parameter of the frame */ + int in_frame_P_qp; /* [IN] the quantization parameter of the P frame */ + int in_frame_B_qp; /* [IN] the quantization parameter of the B frame */ + + int in_RC_frm_enable; /* [IN] RC enable (0:disable, 1:frame level RC) */ + int in_RC_framerate; /* [IN] RC parameter (framerate) */ + int in_RC_bitrate; /* [IN] RC parameter (bitrate in kbps) */ + int in_RC_qbound; /* [IN] RC parameter (Q bound) */ + int in_RC_rpara; /* [IN] RC parameter (Reaction Coefficient) */ + + int in_MS_mode; /* [IN] Multi-slice mode (0:single, 1:multiple) */ + int in_MS_size; /* [IN] Multi-slice size (in num. of mb or byte) */ + int in_mb_refresh; /* [IN] Macroblock refresh */ + int in_interlace_mode; /* [IN] interlace mode(0:progressive, 1:interlace) */ + int in_BframeNum; /* [IN] B frame number */ + + int in_pad_ctrl_on; /* [IN] Enable (1) / Disable (0) padding */ + int in_luma_pad_val; /* [IN] pad value if pad_ctrl_on is Enable */ + int in_cb_pad_val; + int in_cr_pad_val; + + unsigned int in_mapped_addr; + mfc_strm_ref_buf_arg_t out_u_addr; + mfc_strm_ref_buf_arg_t out_p_addr; + mfc_strm_ref_buf_arg_t out_buf_size; + unsigned int out_header_size; + + /* MPEG4 Only */ + int in_qpelME_enable; /* [IN] Quarter-pel MC enable(1:enable, 0:disable) */ + int in_time_increament_res; /* [IN] time increment resolution */ + int in_time_vop_time_increament; /* [IN] time increment */ +} mfc_enc_init_mpeg4_arg_t; + +typedef mfc_enc_init_mpeg4_arg_t mfc_enc_init_h263_arg_t; + +typedef struct { + SSBSIP_MFC_CODEC_TYPE in_codec_type; /* [IN] codec type */ + int in_width; /* [IN] width of YUV420 frame to be encoded */ + int in_height; /* [IN] height of YUV420 frame to be encoded */ + int in_profile_level; /* [IN] profile & level */ + int in_gop_num; /* [IN] GOP Number (interval of I-frame) */ + int in_frame_qp; /* [IN] the quantization parameter of the frame */ + int in_frame_P_qp; /* [IN] the quantization parameter of the P frame */ + int in_frame_B_qp; /* [IN] the quantization parameter of the B frame */ + + int in_RC_frm_enable; /* [IN] RC enable (0:disable, 1:frame level RC) */ + int in_RC_framerate; /* [IN] RC parameter (framerate) */ + int in_RC_bitrate; /* [IN] RC parameter (bitrate in kbps) */ + int in_RC_qbound; /* [IN] RC parameter (Q bound) */ + int in_RC_rpara; /* [IN] RC parameter (Reaction Coefficient) */ + + int in_MS_mode; /* [IN] Multi-slice mode (0:single, 1:multiple) */ + int in_MS_size; /* [IN] Multi-slice size (in num. of mb or byte) */ + int in_mb_refresh; /* [IN] Macroblock refresh */ + int in_interlace_mode; /* [IN] interlace mode(0:progressive, 1:interlace) */ + int in_BframeNum; + + int in_pad_ctrl_on; /* [IN] Enable padding control */ + int in_luma_pad_val; /* [IN] Luma pel value used to fill padding area */ + int in_cb_pad_val; /* [IN] CB pel value used to fill padding area */ + int in_cr_pad_val; /* [IN] CR pel value used to fill padding area */ + + unsigned int in_mapped_addr; + mfc_strm_ref_buf_arg_t out_u_addr; + mfc_strm_ref_buf_arg_t out_p_addr; + mfc_strm_ref_buf_arg_t out_buf_size; + unsigned int out_header_size; + + /* H264 Only */ + int in_RC_mb_enable; /* [IN] RC enable (0:disable, 1:MB level RC) */ + int in_reference_num; /* [IN] The number of reference pictures used */ + int in_ref_num_p; /* [IN] The number of reference pictures used for P pictures */ + int in_RC_mb_dark_disable; /* [IN] Disable adaptive rate control on dark region */ + int in_RC_mb_smooth_disable; /* [IN] Disable adaptive rate control on smooth region */ + int in_RC_mb_static_disable; /* [IN] Disable adaptive rate control on static region */ + int in_RC_mb_activity_disable; /* [IN] Disable adaptive rate control on static region */ + int in_deblock_filt; /* [IN] disable the loop filter */ + int in_deblock_alpha_C0; /* [IN] Alpha & C0 offset for H.264 loop filter */ + int in_deblock_beta; /* [IN] Beta offset for H.264 loop filter */ + int in_symbolmode; /* [IN] The mode of entropy coding(CABAC, CAVLC) */ + int in_transform8x8_mode; /* [IN] Allow 8x8 transform(only for high profile) */ + int in_md_interweight_pps; /* [IN] Inter weighted parameter for mode decision */ + int in_md_intraweight_pps; /* [IN] Intra weighted parameter for mode decision */ +} mfc_enc_init_h264_arg_t; + +typedef struct { + SSBSIP_MFC_CODEC_TYPE in_codec_type; /* [IN] codec type */ + unsigned int in_Y_addr; /* [IN] In-buffer addr of Y component */ + unsigned int in_CbCr_addr; /* [IN] In-buffer addr of CbCr component */ + unsigned int in_Y_addr_vir; /* [IN] In-buffer addr of Y component */ + unsigned int in_CbCr_addr_vir; /* [IN] In-buffer addr of CbCr component */ + unsigned int in_strm_st; /* [IN] Out-buffer start addr of encoded strm */ + unsigned int in_strm_end; /* [IN] Out-buffer end addr of encoded strm */ + int in_frametag; /* [IN] unique frame ID */ + + unsigned int out_frame_type; /* [OUT] frame type */ + int out_encoded_size; /* [OUT] Length of Encoded video stream */ + unsigned int out_encoded_Y_paddr; /* [OUT] physical Y address which is flushed */ + unsigned int out_encoded_C_paddr; /* [OUT] physical C address which is flushed */ + int out_frametag_top; /* [OUT] unique frame ID of an output frame or top field */ + int out_frametag_bottom; /* [OUT] unique frame ID of bottom field */ +} mfc_enc_exe_arg; + +typedef struct { + SSBSIP_MFC_CODEC_TYPE in_codec_type; /* [IN] codec type */ + unsigned int in_strm_buf; /* [IN] the physical address of STRM_BUF */ + int in_strm_size; /* [IN] size of video stream filled in STRM_BUF */ + int in_packed_PB; /* [IN] Is packed PB frame or not, 1: packedPB 0: unpacked */ + + int out_img_width; /* [OUT] width of YUV420 frame */ + int out_img_height; /* [OUT] height of YUV420 frame */ + int out_buf_width; /* [OUT] width of YUV420 frame */ + int out_buf_height; /* [OUT] height of YUV420 frame */ + int out_dpb_cnt; /* [OUT] the number of buffers which is nessary during decoding */ + + mfc_frame_buf_arg_t in_frm_buf; /* [IN] the address of dpb FRAME_BUF */ + mfc_frame_buf_arg_t in_frm_size; /* [IN] size of dpb FRAME_BUF */ + unsigned int in_mapped_addr; + + mfc_frame_buf_arg_t out_u_addr; + mfc_frame_buf_arg_t out_p_addr; + mfc_frame_buf_arg_t out_frame_buf_size; +} mfc_dec_init_arg_t; + +typedef struct { + SSBSIP_MFC_CODEC_TYPE in_codec_type; /* [IN] codec type */ + unsigned int in_strm_buf; /* [IN] the physical address of STRM_BUF */ + int in_strm_size; /* [IN] Size of video stream filled in STRM_BUF */ + mfc_frame_buf_arg_t in_frm_buf; /* [IN] the address of dpb FRAME_BUF */ + mfc_frame_buf_arg_t in_frm_size; /* [IN] size of dpb FRAME_BUF */ + int in_frametag; /* [IN] unique frame ID */ + + unsigned int out_display_Y_addr; /* [OUT] the physical address of display buf */ + unsigned int out_display_C_addr; /* [OUT] the physical address of display buf */ + int out_display_status; /* [OUT] whether display frame exist or not. */ + int out_timestamp_top; /* [OUT] presentation time of an output frame or top field */ + int out_timestamp_bottom; /* [OUT] presentation time of bottom field */ + int out_consume_bytes; /* [OUT] consumed bytes when decoding finished */ + int out_frametag_top; /* [OUT] unique frame ID of an output frame or top field */ + int out_frametag_bottom; /* [OUT] unique frame ID of bottom field */ + int out_res_change; /* [OUT] whether resolution is changed or not (0, 1, 2) */ + int out_crop_top_offset; /* [OUT] crop information, top offset */ + int out_crop_bottom_offset; /* [OUT] crop information, bottom offset */ + int out_crop_left_offset; /* [OUT] crop information, left offset */ + int out_crop_right_offset; /* [OUT] crop information, right offset */ +} mfc_dec_exe_arg_t; + +typedef struct { + int in_config_param; /* [IN] Configurable parameter type */ + int out_config_value[4]; /* [IN] Values to get for the configurable parameter. */ +} mfc_get_config_arg_t; + +typedef struct { + int in_config_param; /* [IN] Configurable parameter type */ + int in_config_value[2]; /* [IN] Values to be set for the configurable parameter. */ + int out_config_value_old[2]; /* [OUT] Old values of the configurable parameters */ +} mfc_set_config_arg_t; + +typedef struct tag_get_phys_addr_arg +{ + unsigned int u_addr; + unsigned int p_addr; +} mfc_get_phys_addr_arg_t; + +typedef struct tag_mem_alloc_arg +{ + SSBSIP_MFC_CODEC_TYPE codec_type; + int buff_size; + unsigned int mapped_addr; + unsigned int out_uaddr; + unsigned int out_paddr; +} mfc_mem_alloc_arg_t; + +typedef struct tag_mem_free_arg_t +{ + unsigned int u_addr; +} mfc_mem_free_arg_t; + +typedef union { + mfc_enc_init_mpeg4_arg_t enc_init_mpeg4; + mfc_enc_init_h263_arg_t enc_init_h263; + mfc_enc_init_h264_arg_t enc_init_h264; + mfc_enc_exe_arg enc_exe; + + mfc_dec_init_arg_t dec_init; + mfc_dec_exe_arg_t dec_exe; + + mfc_get_config_arg_t get_config; + mfc_set_config_arg_t set_config; + + mfc_mem_alloc_arg_t mem_alloc; + mfc_mem_free_arg_t mem_free; + mfc_get_phys_addr_arg_t get_phys_addr; +} mfc_args; + +typedef struct tag_mfc_args { + SSBSIP_MFC_ERROR_CODE ret_code; /* [OUT] error code */ + mfc_args args; +} mfc_common_args; + +typedef struct { + int magic; + int hMFC; + int width; + int height; + int sizeStrmBuf; + mfc_frame_buf_arg_t sizeFrmBuf; + int displayStatus; + int inter_buff_status; + unsigned int virFreeStrmAddr; + unsigned int phyStrmBuf; + unsigned int virStrmBuf; + unsigned int virMvRefYC; + mfc_frame_buf_arg_t phyFrmBuf; + mfc_frame_buf_arg_t virFrmBuf; + unsigned int mapped_addr; + mfc_common_args MfcArg; + SSBSIP_MFC_CODEC_TYPE codec_type; + SSBSIP_MFC_DEC_OUTPUT_INFO decOutInfo; + unsigned int encodedHeaderSize; + int encodedDataSize; + unsigned int encodedframeType; + int in_frametag; + int out_frametag_top; + int out_frametag_bottom; + unsigned int encoded_Y_paddr; + unsigned int encoded_C_paddr; +} _MFCLIB; + +#endif /* _MFC_INTERFACE_H_ */ |