2 * GStreamer codec plugin for Tizen Emulator.
4 * Copyright (C) 2013 Samsung Electronics Co., Ltd. All rights reserved.
7 * KiTae Kim <kt920.kim@samsung.com>
8 * SeokYeon Hwang <syeon.hwang@samsung.com>
9 * YeongKyoon Lee <yeongkyoon.lee@samsung.com>
11 * This library is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU Library General Public
13 * License as published by the Free Software Foundation; either
14 * version 2 of the License, or (at your option) any later version.
16 * This library is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 * Library General Public License for more details.
21 * You should have received a copy of the GNU Library General Public
22 * License along with this library; if not, write to the
23 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
24 * Boston, MA 02111-1307, USA.
31 #include "gstemulcommon.h"
32 #include "gstemulapi.h"
33 #include "gstemulapi2.h"
34 #include "gstemuldev.h"
42 emul_avcodec_init (CodecContext *ctx, CodecElement *codec, CodecDevice *dev)
46 int size = 0, ret = 0;
50 CODEC_LOG (DEBUG, "enter: %s\n", __func__);
54 GST_ERROR ("failed to get %s fd.\n", CODEC_DEV);
58 mmapbuf = (uint8_t *)dev->buf;
60 GST_ERROR ("failed to get mmaped memory address.\n");
64 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
65 emul_avcodec_init_to (ctx, codec, mmapbuf);
67 copyback = CODEC_USER_FROM;
68 ioctl (fd, CODEC_CMD_ADD_TASK_QUEUE, ©back);
71 ioctl (fd, CODEC_CMD_COPY_TO_DEVICE_MEM, &usable);
73 CODEC_LOG (DEBUG, "[init][%d] failure.\n", __LINE__);
77 emul_avcodec_init_to (ctx, codec, mmapbuf);
80 CODEC_LOG (DEBUG, "[init] write data to qemu.\n");
82 memcpy (mmapbuf + size,
83 &codec->media_type, sizeof(codec->media_type));
84 size += sizeof(codec->media_type);
85 memcpy (mmapbuf + size, &codec->codec_type, sizeof(codec->codec_type));
86 size += sizeof(codec->codec_type);
87 memcpy (mmapbuf + size, codec->name, sizeof(codec->name));
88 size += sizeof(codec->name);
90 if (codec->media_type == AVMEDIA_TYPE_VIDEO) {
91 memcpy (mmapbuf + size, &ctx->video, sizeof(ctx->video));
92 size += sizeof(ctx->video);
93 } else if (codec->media_type == AVMEDIA_TYPE_AUDIO) {
94 memcpy (mmapbuf + size, &ctx->audio, sizeof(ctx->audio));
95 size += sizeof(ctx->audio);
97 GST_ERROR ("media type is unknown.\n");
102 memcpy (mmapbuf + size,
103 &ctx->codecdata_size, sizeof(ctx->codecdata_size));
104 size += sizeof(ctx->codecdata_size);
105 if (ctx->codecdata_size) {
106 memcpy (mmapbuf + size, ctx->codecdata, ctx->codecdata_size);
107 size += ctx->codecdata_size;
109 size -= sizeof(size);
110 memcpy (mmapbuf, &size, sizeof(size));
112 CODEC_LOG (DEBUG, "[init] write data: %d\n", size);
124 CODEC_PARAM_INIT (params);
125 params.api_index = CODEC_INIT;
126 params.mem_offset = dev->mem_info.offset;
127 CODEC_WRITE_TO_QEMU (fd, ¶ms, 1);
129 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
130 ret = emul_avcodec_init_from (ctx, codec, mmapbuf);
133 ioctl (fd, CODEC_CMD_COPY_FROM_DEVICE_MEM, &usable);
135 CODEC_LOG (DEBUG, "[init][%d] failure.\n", __LINE__);
139 ret = emul_avcodec_init_from (ctx, codec, mmapbuf);
141 CODEC_LOG (DEBUG, "[init] read data from qemu.\n");
142 if (codec->media_type == AVMEDIA_TYPE_AUDIO) {
143 memcpy (&ctx->audio.sample_fmt,
144 (uint8_t *)mmapbuf, sizeof(ctx->audio.sample_fmt));
145 size += sizeof(ctx->audio.sample_fmt);
146 CODEC_LOG (DEBUG, "[init] AUDIO sample_fmt: %d\n", ctx->audio.sample_fmt);
148 CODEC_LOG (DEBUG, "[init] %s\n", codec->media_type ? "AUDIO" : "VIDEO");
149 memcpy (&ret, (uint8_t *)mmapbuf + size, sizeof(ret));
151 memcpy (&ctx->index, (uint8_t *)mmapbuf + size, sizeof(ctx->index));
153 CODEC_LOG (DEBUG, "context index: %d\n", ctx->index);
157 ioctl (fd, CODEC_CMD_REMOVE_TASK_QUEUE, ©back);
160 CODEC_LOG (DEBUG, "leave: %s, ret: %d\n", __func__, ret);
165 emul_avcodec_deinit (CodecContext *ctx, CodecDevice *dev)
168 int copyback, usable;
169 void *mmapbuf = NULL;
170 CodecIOParams params;
172 CODEC_LOG (DEBUG, "enter: %s\n", __func__);
176 GST_ERROR ("failed to get %s fd.\n", CODEC_DEV);
182 GST_ERROR ("failed to get mmaped memory address.\n");
187 copyback = CODEC_USER_FROM;
188 ioctl (fd, CODEC_CMD_ADD_TASK_QUEUE, ©back);
191 ioctl (fd, CODEC_CMD_COPY_TO_DEVICE_MEM, &usable);
193 CODEC_LOG (DEBUG, "[deinit][%d] failure.\n", __LINE__);
199 CODEC_PARAM_INIT (params);
200 params.api_index = CODEC_DEINIT;
201 params.ctx_index = ctx->index;
202 params.mem_offset = dev->mem_info.offset;
203 CODEC_WRITE_TO_QEMU (fd, ¶ms, 1);
205 // ioctl (fd, CODEC_CMD_REMOVE_TASK_QUEUE, ©back);
207 CODEC_LOG (DEBUG, "leave: %s\n", __func__);
211 emul_avcodec_decode_video (CodecContext *ctx, uint8_t *in_buf, int in_size,
212 GstBuffer **out_buf, int *got_picture_ptr, CodecDevice *dev)
215 uint8_t *mmapbuf = NULL;
216 int len = 0, size = 0;
217 int copyback, usable;
218 CodecIOParams params;
220 CODEC_LOG (DEBUG, "enter: %s\n", __func__);
224 GST_ERROR ("failed to get %s fd\n", CODEC_DEV);
228 mmapbuf = (uint8_t *)dev->buf;
230 GST_ERROR ("failed to get mmaped memory address\n");
234 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
235 emul_avcodec_decode_video_to (in_buf, in_size, mmapbuf);
237 copyback = CODEC_USER_FROM;
238 ioctl (fd, CODEC_CMD_ADD_TASK_QUEUE, ©back);
241 ioctl (fd, CODEC_CMD_COPY_TO_DEVICE_MEM, &usable);
243 CODEC_LOG (DEBUG, "[decode_video] wait 1.\n");
247 emul_avcodec_decode_video_to (in_buf, in_size, mmapbuf);
249 CODEC_LOG (DEBUG, "[decode_video] write data to qemu\n");
251 memcpy (mmapbuf + size, &in_size, sizeof(in_size));
252 size += sizeof(in_size);
254 memcpy (mmapbuf + size, in_buf, in_size);
258 size -= sizeof(size);
259 CODEC_LOG (DEBUG, "[decode_video] total: %d, inbuf size: %d\n", size, in_size);
260 memcpy(mmapbuf, &size, sizeof(size));
266 /* provide raw image for decoding to qemu */
267 CODEC_PARAM_INIT (params);
268 params.api_index = CODEC_DECODE_VIDEO;
269 params.ctx_index = ctx->index;
270 params.mem_offset = dev->mem_info.offset;
271 CODEC_WRITE_TO_QEMU (fd, ¶ms, 1);
273 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
274 len = emul_avcodec_decode_video_from (ctx, got_picture_ptr, mmapbuf);
277 ioctl (fd, CODEC_CMD_COPY_FROM_DEVICE_MEM, &usable);
279 CODEC_LOG (DEBUG, "[decode_video] wait 2.\n");
283 len = emul_avcodec_decode_video_from (ctx, got_picture_ptr, mmapbuf);
285 CODEC_LOG (DEBUG, "[decode_video] read data from qemu.\n");
286 memcpy (&len, (uint8_t *)mmapbuf, sizeof(len));
288 memcpy (got_picture_ptr,
289 (uint8_t *)mmapbuf + size, sizeof(*got_picture_ptr));
290 size += sizeof(*got_picture_ptr);
291 memcpy (&ctx->video, (uint8_t *)mmapbuf + size, sizeof(ctx->video));
293 CODEC_LOG (DEBUG, "[decode_video] len: %d, have_date: %d\n", len, *got_picture_ptr);
297 ioctl (fd, CODEC_CMD_REMOVE_TASK_QUEUE, ©back);
300 CODEC_LOG (DEBUG, "leave: %s\n", __func__);
305 emul_av_picture_copy (CodecContext *ctx, uint8_t *pict, uint32_t pict_size, CodecDevice *dev)
308 void *mmapbuf = NULL;
309 int copyback, usable;
310 CodecIOParams params;
312 CODEC_LOG (DEBUG, "enter: %s\n", __func__);
316 GST_ERROR ("failed to get %s fd\n", CODEC_DEV);
322 GST_ERROR ("failed to get mmaped memory address\n");
326 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
329 copyback = CODEC_USER_FROM;
330 ioctl (fd, CODEC_CMD_ADD_TASK_QUEUE, ©back);
333 ioctl (fd, CODEC_CMD_COPY_TO_DEVICE_MEM, &usable);
335 CODEC_LOG (DEBUG, "[decode_video] wait 1.\n");
343 // printf("before av_picture_copy. ctx: %d\n", ctx->index);
345 CODEC_PARAM_INIT (params);
346 params.api_index = CODEC_PICTURE_COPY;
347 params.ctx_index = ctx->index;
348 params.mem_offset = dev->mem_info.offset;
349 CODEC_WRITE_TO_QEMU (fd, ¶ms, 1);
351 CODEC_LOG (DEBUG, "[copy_frame] after write.\n");
353 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
354 CODEC_LOG (DEBUG, "[copy_frame] read data from qemu.\n");
355 memcpy (pict, mmapbuf, pict_size);
358 ioctl (fd, CODEC_CMD_COPY_FROM_DEVICE_MEM, &usable);
360 CODEC_LOG (DEBUG, "[copy_frame] wait 2.\n");
364 CODEC_LOG (DEBUG, "[copy_frame] read data from qemu.\n");
365 memcpy (pict, mmapbuf, pict_size);
368 ioctl (fd, CODEC_CMD_REMOVE_TASK_QUEUE, ©back);
371 CODEC_LOG (DEBUG, "leave: %s\n", __func__);
375 emul_avcodec_decode_audio (CodecContext *ctx, int16_t *samples,
376 int *frame_size_ptr, uint8_t *in_buf, int in_size, CodecDevice *dev)
379 uint8_t *mmapbuf = NULL;
381 int copyback, usable;
382 CodecIOParams params;
384 CODEC_LOG (DEBUG, "enter: %s\n", __func__);
388 GST_ERROR("failed to get %s fd\n", CODEC_DEV);
392 mmapbuf = (uint8_t *)dev->buf;
394 GST_ERROR("failed to get mmaped memory address\n");
398 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
399 emul_avcodec_decode_audio_to (in_buf, in_size, mmapbuf);
401 copyback = CODEC_USER_FROM;
402 ioctl (fd, CODEC_CMD_ADD_TASK_QUEUE, ©back);
405 ioctl (fd, CODEC_CMD_COPY_TO_DEVICE_MEM, &usable);
407 CODEC_LOG (DEBUG, "[decode_audio][%d] wait 1.\n", __LINE__);
411 emul_avcodec_decode_audio_to (in_buf, in_size, mmapbuf);
414 memcpy (mmapbuf + size, &in_size, sizeof(in_size));
415 size += sizeof(in_size);
417 memcpy (mmapbuf + size, in_buf, in_size);
421 size -= sizeof(size);
422 memcpy (mmapbuf, &size, sizeof(size));
423 CODEC_LOG (DEBUG, "[decode_audio] write size: %d, inbuf_size: %d\n", size, in_size);
429 CODEC_PARAM_INIT (params);
430 params.api_index = CODEC_DECODE_AUDIO;
431 params.ctx_index = ctx->index;
432 params.mem_offset = dev->mem_info.offset;
433 CODEC_WRITE_TO_QEMU (fd, ¶ms, 1);
435 if (dev->mem_info.type == CODEC_FIXED_DEVICE_MEM) {
436 len = emul_avcodec_decode_audio_from (ctx, frame_size_ptr, samples, mmapbuf);
439 ioctl (fd, CODEC_CMD_COPY_FROM_DEVICE_MEM, &usable);
441 CODEC_LOG (DEBUG, "[decode_audio][%d] wait 2.\n", __LINE__);
445 len = emul_avcodec_decode_audio_from (ctx, frame_size_ptr, samples, mmapbuf);
447 CODEC_LOG (DEBUG, "[decode_audio] read data\n");
448 memcpy (&ctx->audio.channel_layout,
449 (uint8_t *)mmapbuf, sizeof(ctx->audio.channel_layout));
450 size = sizeof(ctx->audio.channel_layout);
451 memcpy (&len, (uint8_t *)mmapbuf + size, sizeof(len));
453 memcpy (frame_size_ptr, (uint8_t *)mmapbuf + size, sizeof(*frame_size_ptr));
454 size += sizeof(*frame_size_ptr);
455 CODEC_LOG (DEBUG, "[decode_audio] len: %d, channel_layout: %lld\n",
456 len, ctx->audio.channel_layout);
458 memcpy (samples, (uint8_t *)mmapbuf + size, FF_MAX_AUDIO_FRAME_SIZE);
463 ioctl (fd, CODEC_CMD_REMOVE_TASK_QUEUE, ©back);
466 CODEC_LOG (DEBUG, "leave: %s\n", __func__);
471 emul_avcodec_encode_video (CodecContext *ctx, uint8_t*out_buf, int out_size,
472 uint8_t *in_buf, int in_size, CodecDevice *dev)
476 int len = 0, outbuf_size, size = 0;
477 int copyback, usable;
478 CodecIOParams params;
480 CODEC_LOG (DEBUG, "enter: %s\n", __func__);
484 GST_ERROR ("failed to get %s fd.\n", CODEC_DEV);
490 GST_ERROR ("failed to get mmaped memory address.\n");
494 copyback = CODEC_USER_FROM;
495 ioctl (fd, CODEC_CMD_ADD_TASK_QUEUE, ©back);
498 ioctl (fd, CODEC_CMD_COPY_TO_DEVICE_MEM, &usable);
500 CODEC_LOG (DEBUG, "[init][%d] failure.\n", __LINE__);
505 CODEC_LOG (DEBUG, "[encode_video] write data to qemu\n");
506 memcpy ((uint8_t *)mmapbuf + size, &in_size, sizeof(guint));
507 size += sizeof(guint);
508 memcpy ((uint8_t *)mmapbuf + size, in_buf, in_size);
512 CODEC_PARAM_INIT (params);
513 params.api_index = CODEC_ENCODE_VIDEO;
514 params.ctx_index = ctx->index;
515 params.mem_offset = dev->mem_info.offset;
516 CODEC_WRITE_TO_QEMU (fd, ¶ms, 1);
520 copyback = CODEC_USER_TO;
521 ioctl (fd, CODEC_CMD_COPY_FROM_DEVICE_MEM, ©back);
525 memcpy (&out_size, (uint8_t *)mmapbuf + size, sizeof(uint));
526 size += sizeof(guint);
528 ret = gst_pad_alloc_buffer_and_set_caps (emulenc->srcpad,
529 GST_BUFFER_OFFSET_NONE, out_size,
530 GST_PAD_CAPS (emulenc->srcpad), out_buf);
532 gst_buffer_set_caps (*out_buf, GST_PAD_CAPS (emulenc->srcpad));
534 if (GST_BUFFER_DATA(*out_buf)) {
535 memcpy (GST_BUFFER_DATA(*out_buf), (uint8_t *)mmapbuf + size, out_size);
537 pritnf ("failed to allocate output buffer\n");
542 ioctl (fd, CODEC_CMD_REMOVE_TASK_QUEUE, ©back);
544 CODEC_LOG (DEBUG, "leave: %s\n", __func__);
550 emul_avcodec_encode_audio (CodecContext *ctx, uint8_t *outbuf, int outbuf_size,
551 const short *inbuf, int inbuf_size, CodecDevice *dev)
555 int len = 0, size = 0;
556 int copyback, usable;
557 CodecIOParams params;
559 CODEC_LOG (DEBUG, "enter: %s\n", __func__);
563 GST_ERROR ("failed to get %s fd.\n", CODEC_DEV);
569 GST_ERROR ("failed to get mmaped memory address.\n");
573 copyback = CODEC_USER_FROM;
574 ioctl (fd, CODEC_CMD_ADD_TASK_QUEUE, ©back);
577 ioctl (fd, CODEC_CMD_COPY_TO_DEVICE_MEM, &usable);
579 CODEC_LOG (DEBUG, "[decode_video] wait.\n");
584 CODEC_LOG (DEBUG, "[encode_audio] write data to qemu\n");
585 memcpy ((uint8_t *)mmapbuf + size, &inbuf_size, sizeof(inbuf_size));
586 size += sizeof(inbuf_size);
587 memcpy ((uint8_t *)mmapbuf + size, inbuf, inbuf_size);
591 CODEC_PARAM_INIT (params);
592 params.api_index = CODEC_ENCODE_AUDIO;
593 params.ctx_index = ctx->index;
594 params.mem_offset = dev->mem_info.offset;
595 CODEC_WRITE_TO_QEMU (fd, ¶ms, 1);
598 ioctl (fd, CODEC_CMD_COPY_FROM_DEVICE_MEM, &usable);
600 CODEC_LOG (DEBUG, "[decode_video] wait. 2\n");
605 CODEC_LOG (DEBUG, "[encode_audio] read data from qemu\n");
606 memcpy (outbuf, (uint8_t *)mmapbuf, outbuf_size);
609 ioctl (fd, CODEC_CMD_REMOVE_TASK_QUEUE, NULL);
611 CODEC_LOG (DEBUG, "leave: %s\n", __func__);