--- a/khronosfws/openmax_al/src/adaptation/xaadaptationcontextbase.c Mon May 03 12:59:52 2010 +0300
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,1924 +0,0 @@
-/*
-* Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
-* All rights reserved.
-* This component and the accompanying materials are made available
-* under the terms of "Eclipse Public License v1.0"
-* which accompanies this distribution, and is available
-* at the URL "http://www.eclipse.org/legal/epl-v10.html".
-*
-* Initial Contributors:
-* Nokia Corporation - initial contribution.
-*
-* Contributors:
-*
-* Description:
-*
-*/
-
-#include <assert.h>
-#include <string.h>
-#include "gst/gst.h"
-#include "gst/gstbuffer.h"
-#include "gst/app/gstappsrc.h"
-#include "XAAdaptationContextBase.h"
-#include "XAAdaptation.h"
-#include "XAObjectItf.h"
-#include "XACameraDevice.h"
-#include "XARadioDevice.h"
-#include "XAOutputMix.h"
-#include "XAStaticCapsAdaptation.h"
-#include "XAMediaPlayerAdaptCtx.h"
-
-extern XAboolean cameraRealized;
-extern XACameraAdaptationCtx_* cameraCtx;
-/*
- * XAAdaptationBaseCtx* XAAdaptationBase_Create()
- * 1st phase initialization function for Adaptation Base context structure.
- * Reserves memory for base context and initializes GStreamer FW.
- */
-XAresult XAAdaptationBase_Init( XAAdaptationBaseCtx* pSelf, XAuint32 ctxId )
-{
- DEBUG_API("->XAAdaptationBase_Init");
-
- if ( pSelf )
- {
- GError* gerror = 0;
- pSelf->pipeSrcThr = NULL;
- pSelf->pipeSinkThr = NULL;
-
- /* Set context id */
- pSelf->ctxId = ctxId;
- /* Add default handler for Gst-bus messages */
- pSelf->busCb = XAAdaptationBase_GstBusCb;
-
- // VASU MOD BEGINS
- pSelf->cond_mutx_inited = XA_BOOLEAN_FALSE;
- // VASU MOD ENDS
-
- pSelf->evtHdlrs = g_array_new (FALSE, FALSE, sizeof (XAAdaptEvtHdlr));
-
- sem_init(&(pSelf->semAsyncWait),0,0);
-
-
- if ( !gst_init_check( NULL, NULL, &gerror ) )
- {
- DEBUG_ERR("Gst Initalization failure.");
- return XA_RESULT_INTERNAL_ERROR;
- }
- }
- else
- {
- DEBUG_ERR("Invalid Adaptation Base Context.")
- return XA_RESULT_PARAMETER_INVALID;
- }
-
- DEBUG_API("<-XAAdaptationBase_Init");
- return XA_RESULT_SUCCESS;
-}
-
-/*
- * XAresult XAAdaptationBase_PostInit()
- * 2nd phase initialization for Adaptation Base.
- */
-XAresult XAAdaptationBase_PostInit( XAAdaptationBaseCtx* ctx )
-{
- XAresult ret = XA_RESULT_SUCCESS;
- DEBUG_API("->XAAdaptationBase_PostInit");
- // VASU MOD BEGINS
- ctx->thread_launched = XA_BOOLEAN_FALSE;
- pthread_mutex_init(&(ctx->ds_mutex), NULL);
- pthread_cond_init(&(ctx->ds_condition), NULL);
- ctx->cond_mutx_inited = XA_BOOLEAN_TRUE;
- // VASU MOD ENDS
- DEBUG_API("<-XAAdaptationBase_PostInit");
- return ret;
-}
-
-/*
- * void XAAdaptationBase_Free( XAAdaptationBaseCtx* ctx )
- * Frees all Base context variables .
- */
-void XAAdaptationBase_Free( XAAdaptationBaseCtx* ctx )
-{
- GstElement* fakesink = NULL;
- DEBUG_API("->XAAdaptationBase_Free");
-
- if ( ctx->bin )
- {
- fakesink = gst_bin_get_by_name(GST_BIN(ctx->bin), "fakesink");
- if ( fakesink )
- {
- gst_element_set_state( GST_ELEMENT(fakesink), GST_STATE_NULL);
- gst_object_unref(fakesink);
- }
-
- if ( gst_element_set_state(GST_ELEMENT(ctx->bin), GST_STATE_NULL )!=GST_STATE_CHANGE_SUCCESS )
- { /*not much we can do*/
- DEBUG_ERR("WARNING: Failed to change to NULL state before deletion!!")
- }
- }
-
- if(ctx->asynctimer)
- { /*cancel timer*/
- g_source_remove(ctx->asynctimer);
- }
- sem_post(&(ctx->semAsyncWait));
- sem_destroy(&(ctx->semAsyncWait));
-
- XAAdaptationBase_StopGstListener(ctx);
-
- if ( ctx->bin )
- {
- gst_object_unref(ctx->bin);
- }
-
- g_array_free(ctx->evtHdlrs, TRUE);
- // VASU MOD BEGINS
- if (ctx->cond_mutx_inited == XA_BOOLEAN_TRUE)
- {
- ctx->thread_launched = XA_BOOLEAN_FALSE;
- pthread_mutex_destroy(&(ctx->ds_mutex));
- pthread_cond_destroy(&(ctx->ds_condition));
- ctx->cond_mutx_inited = XA_BOOLEAN_FALSE;
- }
- // VASU MOD ENDS
-
- DEBUG_API("<-XAAdaptationBase_Free");
-}
-
-/*
- * XAresult XAAdaptationBase_AddEventHandler
- * Adds event handler for certain event types.
- */
-XAresult XAAdaptationBase_AddEventHandler( XAAdaptationBaseCtx* ctx, xaAdaptEventHandler evtHandler,
- XAuint32 evtTypes, void *pHandlerCtx )
-{
- XAuint32 i;
- XAAdaptEvtHdlr tmp;
- DEBUG_API("->XAAdaptationBase_AddEventHandler");
- if(!ctx)
- {
- DEBUG_ERR("no context");
- return XA_RESULT_PARAMETER_INVALID;
- }
- for(i=0; i<ctx->evtHdlrs->len; i++)
- {
- if( (g_array_index(ctx->evtHdlrs, XAAdaptEvtHdlr, i)).handlerfunc == evtHandler )
- {
- return XA_RESULT_PARAMETER_INVALID;
- }
- }
- tmp.handlerfunc = evtHandler;
- tmp.handlercontext = pHandlerCtx;
- tmp.eventtypes = evtTypes;
- g_array_append_val(ctx->evtHdlrs, tmp);
- DEBUG_API("<-XAAdaptationBase_AddEventHandler");
- return XA_RESULT_SUCCESS;
-}
-
-/*
- * XAresult XAAdaptationBase_RemoveEventHandler
- * Removes event handler for certain event types.
- */
-XAresult XAAdaptationBase_RemoveEventHandler( XAAdaptationBaseCtx* ctx, xaAdaptEventHandler evtHandler)
-{
- XAuint32 i;
- DEBUG_API("->XAAdaptationBase_RemoveEventHandler");
- if(!ctx)
- {
- DEBUG_ERR("no context");
- return XA_RESULT_PARAMETER_INVALID;
- }
- for(i=0; i<ctx->evtHdlrs->len; i++)
- {
- if( (g_array_index(ctx->evtHdlrs, XAAdaptEvtHdlr, i)).handlerfunc == evtHandler )
- {
- g_array_remove_index(ctx->evtHdlrs, i);
- return XA_RESULT_SUCCESS;
- }
- }
- DEBUG_API("<-XAAdaptationBase_RemoveEventHandler");
- /*did not find, return error*/
- return XA_RESULT_PARAMETER_INVALID;
-}
-
-/*
- * gboolean XAAdaptationBase_GstBusCb( GstBus *bus, GstMessage *message, gpointer data )
- * Default Gst-bus message handler (Callback)
- */
-gboolean XAAdaptationBase_GstBusCb( GstBus *bus, GstMessage *message, gpointer data )
-{
- GError *error;
- gchar *debug;
- DEBUG_API("->XAAdaptationBase_GstBusCb");
- DEBUG_INFO_A2("Received Gst callback \"%s\" from \"%s\"",
- GST_MESSAGE_TYPE_NAME(message),
- GST_OBJECT_NAME(GST_MESSAGE_SRC(message)));
-
- switch( GST_MESSAGE_TYPE(message))
- {
- case GST_MESSAGE_ERROR:
- gst_message_parse_error( message, &error, &debug );
- DEBUG_INFO_A1("%s", debug);
- break;
- case GST_MESSAGE_EOS:
- break;
- case GST_MESSAGE_UNKNOWN:
- break;
- case GST_MESSAGE_WARNING:
- break;
- case GST_MESSAGE_INFO:
- break;
- case GST_MESSAGE_TAG:
- break;
- case GST_MESSAGE_BUFFERING:
- break;
- case GST_MESSAGE_STATE_CHANGED:
- break;
- case GST_MESSAGE_STATE_DIRTY:
- break;
- case GST_MESSAGE_STEP_DONE:
- break;
- case GST_MESSAGE_CLOCK_PROVIDE:
- break;
- case GST_MESSAGE_CLOCK_LOST:
- break;
- case GST_MESSAGE_NEW_CLOCK:
- break;
- case GST_MESSAGE_STRUCTURE_CHANGE:
- break;
- case GST_MESSAGE_STREAM_STATUS:
- break;
- case GST_MESSAGE_APPLICATION:
- break;
- case GST_MESSAGE_ELEMENT:
- break;
- case GST_MESSAGE_SEGMENT_START:
- break;
- case GST_MESSAGE_SEGMENT_DONE:
- break;
- case GST_MESSAGE_DURATION:
- break;
- case GST_MESSAGE_LATENCY:
- break;
- case GST_MESSAGE_ASYNC_START:
- break;
- case GST_MESSAGE_ASYNC_DONE:
- break;
- case GST_MESSAGE_ANY:
- break;
- default:
- DEBUG_INFO("Unhandled Gst-Bus message");
- break;
- }
- DEBUG_API("<-XAAdaptationBase_GstBusCb");
- return TRUE;
-}
-
-XAresult XAAdaptationBase_InitGstListener(XAAdaptationBaseCtx* ctx)
-{
- int ret;
- DEBUG_API("->XAAdaptationBase_InitGstListener");
- if ( ctx->bin )
- {
- ctx->bus = gst_pipeline_get_bus( GST_PIPELINE( ctx->bin ));
- }
- if( !ctx->bus )
- {
- DEBUG_ERR("could not get gst bus!")
- return XA_RESULT_INTERNAL_ERROR;
- }
- ret = pthread_create(&(ctx->busloopThr), NULL, (XAAdaptationBase_LaunchGstListener),(void*)ctx);
- // VASU MOD BEGINS
- if ( ctx->thread_launched == XA_BOOLEAN_FALSE )
- {
- // Wait until the thread is created
- pthread_mutex_lock(&(ctx->ds_mutex));
- pthread_cond_wait(&(ctx->ds_condition), &(ctx->ds_mutex));
- pthread_mutex_unlock(&(ctx->ds_mutex));
- // VASU MOD ENDS
- }
- if(ret)
- {
- DEBUG_ERR_A1("could not create thread!! (%d)",ret)
- return XA_RESULT_INTERNAL_ERROR;
- }
- DEBUG_API("<-XAAdaptationBase_InitGstListener");
- return XA_RESULT_SUCCESS;
-}
-
-void * XAAdaptationBase_LaunchGstListener(void* args)
-{
- XAAdaptationBaseCtx* ctx = (XAAdaptationBaseCtx*)args;
- DEBUG_API("->XAAdaptationBase_LaunchGstListener");
- // VASU MOD BEGINS
- // Signal calling thread that this thread creation is completed
- ctx->thread_launched = XA_BOOLEAN_TRUE;
- pthread_mutex_lock(&(ctx->ds_mutex));
- pthread_cond_signal(&(ctx->ds_condition));
- pthread_mutex_unlock(&(ctx->ds_mutex));
- // VASU MOD ENDS
-
- ctx->busloop = g_main_loop_new( NULL, FALSE );
- if ( !ctx->busloop )
- {
- DEBUG_ERR("Glib main loop failure.")
- DEBUG_API("<-XAAdaptationBase_LaunchGstListener");
- assert(0);
- }
- else
- {
- DEBUG_INFO("Start Glib main loop")
- g_main_loop_run(ctx->busloop);
- DEBUG_INFO("Glib main loop stopped - exiting thread")
- DEBUG_API("<-XAAdaptationBase_LaunchGstListener");
- pthread_exit(NULL);
- }
-
-}
-
-void XAAdaptationBase_StopGstListener(XAAdaptationBaseCtx* ctx)
-{
- DEBUG_API("->XAAdaptationBase_StopGstListener");
- if(ctx->busloop)
- {
- g_main_loop_quit (ctx->busloop);
- g_main_loop_unref(ctx->busloop);
- }
- if(ctx->bus)
- {
- gst_object_unref(ctx->bus);
- ctx->bus = NULL;
- }
- DEBUG_API("<-XAAdaptationBase_StopGstListener");
-}
-
-void XAAdaptationBase_SendAdaptEvents(XAAdaptationBaseCtx* ctx, XAAdaptEvent* event)
-{
- XAuint32 i;
- XAAdaptEvtHdlr* tmp;
- for(i=0; i<ctx->evtHdlrs->len; i++)
- {
- tmp = &g_array_index(ctx->evtHdlrs, XAAdaptEvtHdlr, i);
- if( tmp->eventtypes & event->eventtype )
- {
- (tmp->handlerfunc)(tmp->handlercontext, event);
- }
- }
-}
-
-/*
- * ASynchronous operation managing
- **/
-
-/* NOTE: This should NOT be called from gst callbacks - danger of deadlock!!
- */
-void XAAdaptationBase_PrepareAsyncWait(XAAdaptationBaseCtx* ctx)
-{
- DEBUG_API("->XAAdaptationBase_PrepareAsyncWait");
-
- if( ctx->waitingasyncop )
- { /*wait previous async op*/
- DEBUG_INFO("::WARNING:: previous asynch still ongoing!!!");
- DEBUG_INFO(">>>> WAIT PREVIOUS");
- sem_wait(&(ctx->semAsyncWait));
- DEBUG_INFO("<<<< PREVIOUS COMPLETED");
- }
- sem_init(&(ctx->semAsyncWait),0,0);
-
- ctx->waitingasyncop = XA_BOOLEAN_TRUE;
- DEBUG_API("<-XAAdaptationBase_PrepareAsyncWait");
-}
-
-void XAAdaptationBase_StartAsyncWait(XAAdaptationBaseCtx* ctx)
-{
- DEBUG_API("->XAAdaptationBase_StartAsyncWait");
-
- /* timeout to try to avoid gst freeze in rollup */
- ctx->asynctimer = g_timeout_add(XA_ADAPT_ASYNC_TIMEOUT,
- XAAdaptationBase_CancelAsyncWait, ctx);
- /* check flag once again if callback already happened before wait */
- if(ctx->waitingasyncop)
- {
- DEBUG_INFO(">>>> ASYNC STARTS");
- sem_wait(&(ctx->semAsyncWait));
- DEBUG_INFO("<<<< ASYNC COMPLETED");
- }
- else
- {
- DEBUG_INFO("<> async completed already");
- }
- /*cancel timer*/
- if(ctx->asynctimer)
- {
- g_source_remove(ctx->asynctimer);
- }
- ctx->waitingasyncop = XA_BOOLEAN_FALSE;
-
- DEBUG_API("<-XAAdaptationBase_StartAsyncWait");
-}
-
-/* async operation timeout callback*/
-gboolean XAAdaptationBase_CancelAsyncWait(gpointer ctx)
-{
- XAAdaptationBaseCtx* bCtx = (XAAdaptationBaseCtx*)ctx;
- DEBUG_API("->XAAdaptationBase_CancelAsyncWait");
- if( bCtx->waitingasyncop )
- {
- DEBUG_ERR_A3("ASYNC TIMED OUT : current %d, gsttarget %d, wanted %d",
- GST_STATE(bCtx->bin), GST_STATE_TARGET(bCtx->bin), bCtx->binWantedState);
- bCtx->waitingasyncop = XA_BOOLEAN_FALSE;
- sem_post(&(bCtx->semAsyncWait));
- }
- DEBUG_API("<-XAAdaptationBase_CancelAsyncWait");
- /* return false to remove timer */
- return FALSE;
-}
-
-void XAAdaptationBase_CompleteAsyncWait(XAAdaptationBaseCtx* ctx)
-{
- DEBUG_API("->XAAdaptationBase_CompleteAsyncWait");
- if( ctx->waitingasyncop )
- {
- int i;
- ctx->waitingasyncop = XA_BOOLEAN_FALSE;
- sem_getvalue(&(ctx->semAsyncWait),&i);
- DEBUG_INFO_A1("Asynch operation succeeded, sem value %d",i);
- if(i<=0)
- { /* only post if locked */
- sem_post(&(ctx->semAsyncWait));
- }
- else if(i>0)
- { /* should not be, reset semaphore */
- sem_init(&(ctx->semAsyncWait),0,0);
- }
- }
- DEBUG_API("<-XAAdaptationBase_CompleteAsyncWait");
-}
-
-XAresult XAAdaptationBase_SetCPConfiguration(XAAdaptationBaseCtx* ctx, XAConfigExtensionCpKey configValue)
-{
- XAresult res = XA_RESULT_SUCCESS;
-
- DEBUG_API("-> XAAdaptationBase_SetConfiguration");
- if( ctx )
- {
- if ( configValue == XA_READ )
- {
- ctx->pipeSrcThrCtx.cpConfig = configValue;
- res = XA_RESULT_SUCCESS;
- }
- else if ( configValue == XA_READBUFFER )
- {
- ctx->pipeSrcThrCtx.cpConfig = configValue;
- res = XA_RESULT_SUCCESS;
- }
- else if ( configValue == XA_WRITE )
- {
- ctx->pipeSinkThrCtx.cpConfig = configValue;
- res = XA_RESULT_SUCCESS;
- }
- else if ( configValue == XA_WRITEBUFFER )
- {
- ctx->pipeSinkThrCtx.cpConfig = configValue;
- res = XA_RESULT_SUCCESS;
- }
- }
- else
- {
- res = XA_RESULT_PARAMETER_INVALID;
- }
- DEBUG_API("-> XAAdaptationBase_SetConfiguration");
- return res;
-}
-
-/**
- * GstElement* XAAdaptationBase_CreateGstSource( XADataSource* xaSrc, const XAchar *name )
- * @param XADataSource* xaSnk - XADataSource defining gst source to create
- * @param const XAchar *name - string for naming the gst element
- * @param XAboolean *isobj - (out param) is source another XA object?
- * @return GstElement* - return newly created gst source element
- * Description: Create gst source element corresponding to XA source structure
- */
-GstElement* XAAdaptationBase_CreateGstSource( XADataSource* xaSrc, const char *name, XAboolean *isobj, XAboolean *isPCM, XAboolean *isRawImage )
-{
- XAuint32 locType = 0;
- GstElement* gstSrc = NULL;
- char* fname=NULL;
- XADataLocator_URI* uri = NULL;
- XADataLocator_IODevice* ioDevice = NULL;
- XACameraDeviceImpl* cameraDevice = NULL;
- XARadioDeviceImpl* radioDevice = NULL;
- XAObjectItfImpl* pObj = NULL;
-
- DEBUG_API("->XAAdaptationBase_CreateGstSource");
- if( !xaSrc || !xaSrc->pLocator || !isobj )
- {
- return NULL;
- }
- *isobj = XA_BOOLEAN_FALSE;
- if( xaSrc && xaSrc->pFormat && *((XAuint32*)(xaSrc->pFormat))==XA_DATAFORMAT_PCM && isPCM )
- {
- *isPCM = XA_BOOLEAN_TRUE;
- }
- if( xaSrc && xaSrc->pFormat && *((XAuint32*)(xaSrc->pFormat))==XA_DATAFORMAT_RAWIMAGE && isRawImage )
- {
- *isRawImage = XA_BOOLEAN_TRUE;
- }
- locType = *((XAuint32*)(xaSrc->pLocator));
- switch ( locType )
- {
- case XA_DATALOCATOR_URI:
- DEBUG_INFO("XA_DATALOCATOR_URI");
- uri = (XADataLocator_URI*)xaSrc->pLocator;
- gstSrc = gst_element_factory_make("filesrc",name);
- if ( uri->URI != NULL )
- {
- DEBUG_INFO_A1("URI: %s", uri->URI);
- if(strncmp((char *)uri->URI, "file://", 7) == 0)
- {
- fname = (char *)&((uri->URI)[7]);
- }
- else
- {
- fname = (char *)uri->URI;
- }
- DEBUG_INFO_A1("->filesystem path %s", fname);
- g_object_set( G_OBJECT(gstSrc), "location", fname, NULL );
- /*check for pcm - decodebin does not know how to handle raw PCM files */
- if( isPCM && strstr(fname, ".pcm") )
- {
- DEBUG_INFO("PCM file detected");
- *isPCM=XA_BOOLEAN_TRUE;
- }
- }
- else
- {
- DEBUG_ERR("No uri specified.");
- return NULL;
- }
- break; /* XA_DATALOCATOR_URI */
-
-
- case XA_DATALOCATOR_IODEVICE:
- DEBUG_INFO("XA_DATALOCATOR_IODEVICE");
- ioDevice = (XADataLocator_IODevice*)(xaSrc->pLocator);
- switch ( ioDevice->deviceType )
- {
- case XA_IODEVICE_AUDIOINPUT:
- {
- DEBUG_INFO("XA_IODEVICE_AUDIOINPUT");
- DEBUG_INFO_A1("ioDevice->deviceID: %x", ioDevice->deviceID);
- switch (ioDevice->deviceID )
- {
- //case XA_ADAPTID_ALSASRC: //Krishna
- case XA_ADAPTID_DEVSOUNDSRC:
- //DEBUG_INFO("alsasrc"); //Krishna
- DEBUG_INFO("devsoundsrc");
- gstSrc = gst_element_factory_make("devsoundsrc",name); //Krishna - changed to devsoundsrc
- g_object_set (G_OBJECT (gstSrc), "num-buffers", 80, NULL);
- break;
- case XA_ADAPTID_AUDIOTESTSRC:
- /*fall through*/
- default:
- DEBUG_INFO("audiotestsrc");
- gstSrc = gst_element_factory_make("audiotestsrc",name);
- break;
- }
- break;
- }
- case XA_IODEVICE_CAMERA:
- {
- DEBUG_INFO("XA_IODEVICE_CAMERA");
- if ( ioDevice->device )
- { /*source is camera object*/
- DEBUG_INFO("Use camerabin as source.");
- /* Get camerabin from source object */
- pObj = (XAObjectItfImpl*)(*ioDevice->device);
- cameraDevice = (XACameraDeviceImpl*)(pObj);
- gstSrc = GST_ELEMENT(cameraDevice->adaptationCtx->bin);
- /* refcount increase is needed to keep this not being deleted after use */
- gst_object_ref(GST_OBJECT(gstSrc));
- *isobj = XA_BOOLEAN_TRUE;
- }
- else
- {
- DEBUG_INFO_A1("ioDevice->deviceID: %x", ioDevice->deviceID);
- switch (ioDevice->deviceID )
- {
- case XA_ADAPTID_V4L2SRC:
- DEBUG_INFO("Camera deviceID: v4l2src ");
-
- break;
- case XA_ADAPTID_VIDEOTESTSRC:
- DEBUG_INFO("Camera deviceID: videotestsrc");
-
- break;
- default:
- case XA_DEFAULTDEVICEID_CAMERA:
- DEBUG_INFO("Camera deviceID:Default");
-
- break;
- }
- if ( cameraCtx )
- {
- gstSrc = GST_ELEMENT(cameraCtx->baseObj.bin);
- gst_object_ref(GST_OBJECT(gstSrc));
- *isobj = XA_BOOLEAN_TRUE;
- }
- else
- {
- DEBUG_ERR("No camera object created!");
- return NULL;
- }
- }
- break;
- }
- case XA_IODEVICE_RADIO:
- DEBUG_INFO("XA_IODEVICE_RADIO");
- if ( ioDevice->device )
- {
- DEBUG_INFO("Use radio pipeline as source.");
- /* Get radio_pipeline and set it to base context */
- radioDevice = (XARadioDeviceImpl*)(*ioDevice->device);
- /* radio does not have actual bin, only source element*/
- gstSrc = GST_ELEMENT(radioDevice->adaptationCtx->bin);
- /* refcount increase is needed to keep this not being deleted after use */
- gst_object_ref(GST_OBJECT(gstSrc));
- /**isobj = XA_BOOLEAN_TRUE;*/
- }
- break;
- default:
- {
- DEBUG_ERR("Unsupported IODevice.");
- return NULL;
- break;
- }
- }
- break; /* XA_DATALOCATOR_IODEVICE */
-
- case XA_DATALOCATOR_CONTENTPIPE:
- {
- DEBUG_INFO("XA_DATALOCATOR_CONTENTPIPE");
- gstSrc = gst_element_factory_make("appsrc",name);
- break;
- }
- case XA_DATALOCATOR_ADDRESS:
- {
- XADataLocator_Address* address = (XADataLocator_Address*)(xaSrc->pLocator);
- gstSrc = gst_element_factory_make("appsrc", name);
- /* init gst buffer from datalocator */
- if( gstSrc )
- {
- /* init GST buffer from XADataLocator*/
- GstBuffer* userBuf = gst_buffer_new();
- if( userBuf )
- {
- userBuf->size = address->length;
- userBuf->data = address->pAddress;
- /* push the whole buffer to appsrc so it is ready for preroll */
- DEBUG_INFO("Pushing buffer");
- gst_app_src_push_buffer( GST_APP_SRC(gstSrc), userBuf );
- DEBUG_INFO_A1("Sent buffer at 0x%x to appsrc", userBuf );
- gst_app_src_end_of_stream( GST_APP_SRC(gstSrc) );
- }
- else
- {
- DEBUG_ERR("Failure allocating buffer!");
- }
- }
- else
- {
- DEBUG_ERR("Failure creating appsrc!");
- }
- }
- break;
-
- default:
- DEBUG_ERR("Incorrect data locator for source.")
- return NULL;
- break;
- }
-
- if ( gstSrc )
- {
- DEBUG_INFO_A1("Created gstreamer source element at %x", gstSrc);
- }
-
- DEBUG_API("<-XAAdaptationBase_CreateGstSource");
- return gstSrc;
-}
-
-
-/**
- * GstElement* XAAdaptationBase_CreateGstSink( XADataSink* xaSnk, const XAchar *name )
- * @param XADataSink* xaSnk - XADataSink defining gst sink to create
- * @param const XAchar *name - string for naming the gst element
- * @return GstElement* - return newly created gst sink element
- * Description: Create gst sink element corresponding to XA sink structure
- */
-GstElement* XAAdaptationBase_CreateGstSink( XADataSink* xaSnk, const char *name, XAboolean *isobj )
-{
- XAuint32 locType = 0;
- GstElement* gstSnk = NULL;
- XADataLocator_URI* uri = NULL;
- DEBUG_API("->XAAdaptationBase_CreateGstSink");
- if(!xaSnk || !xaSnk->pLocator)
- {
- DEBUG_INFO("Warning! No sink specified, use fakesink");
- gstSnk = gst_element_factory_make("fakesink",name);
- if(!gstSnk)
- {
- DEBUG_ERR("Cannot create sink!");
- return NULL;
- }
- g_object_set( G_OBJECT(gstSnk),"async", FALSE, NULL);
- }
- else
- {
- locType = *((XAuint32*)(xaSnk->pLocator));
- switch ( locType )
- {
- case XA_DATALOCATOR_URI:
- DEBUG_INFO("XA_DATALOCATOR_URI");
- uri = (XADataLocator_URI*)xaSnk->pLocator;
- gstSnk = gst_element_factory_make("filesink",name);
- if(!gstSnk)
- {
- DEBUG_ERR("Cannot create sink!");
- return NULL;
- }
- if ( uri->URI != NULL )
- {
- XAchar *fname;
- DEBUG_INFO_A1("URI: %s", uri->URI);
- if(strncmp((char *)uri->URI, "file://", 7) == 0)
- {
- fname = &((uri->URI)[7]);
- }
- else
- {
- fname = uri->URI;
- }
- DEBUG_INFO_A1("->filesystem path %s", fname);
- g_object_set( G_OBJECT(gstSnk),"location", fname,
- "async", FALSE,
- "qos", FALSE,
- "max-lateness", (gint64)(-1),
- NULL);
- }
- else
- {
- DEBUG_ERR("No recording output uri specified.");
- return NULL;
- }
- break;
- case XA_DATALOCATOR_NATIVEDISPLAY:
- DEBUG_INFO("Sink locator type - XA_DATALOCATOR_NATIVEDISPLAY");
-#ifdef USE_NGA_SURFACES
- gstSnk = gst_element_factory_make("devvideosink","devvideosink");
-#else
- gstSnk = gst_element_factory_make("ximagesink",name);
-#endif /*USE_NGA_SURFACES*/
- if(!gstSnk)
- {
- DEBUG_ERR("Cannot create sink!");
- return NULL;
- }
- g_object_set( G_OBJECT(gstSnk), "force-aspect-ratio", TRUE,
- "async", FALSE,
- "qos", FALSE,
- "handle-events", TRUE,
- "handle-expose", TRUE,
- "max-lateness", (gint64)(-1),
- NULL);
- break;
- case XA_DATALOCATOR_OUTPUTMIX:
- DEBUG_INFO("Sink locator type - XA_DATALOCATOR_OUTPUTMIX");
- {
- /* Get OutputMix adaptation from data locator */
- XADataLocator_OutputMix* omix = (XADataLocator_OutputMix*)(xaSnk->pLocator);
- if ( omix->outputMix )
- {
- XAOMixImpl* omixDevice = (XAOMixImpl*)(*omix->outputMix);
-
- if(omixDevice)
- {
- gstSnk = XAOutputMixAdapt_GetSink(omixDevice->adaptationCtx);
- if(!gstSnk)
- {
- DEBUG_ERR("Cannot create sink!");
- return NULL;
- }
- *isobj = XA_BOOLEAN_TRUE;
- }
- else
- {
- DEBUG_ERR("Warning - NULL outputmix object - default audio output used");
- gstSnk = gst_element_factory_make("alsasink",name);
- }
- }
- else
- {
- DEBUG_ERR("Warning - NULL outputmix object - default audio output used");
- gstSnk = gst_element_factory_make("alsasink",name);
- }
-
- }
- break;
- case XA_DATALOCATOR_CONTENTPIPE:
- DEBUG_INFO("XA_DATALOCATOR_CONTENTPIPE");
- gstSnk = gst_element_factory_make("appsink",name);
- break;
- case XA_DATALOCATOR_ADDRESS:
- {
- gstSnk = gst_element_factory_make("appsink", name);
- /* Not actually object sink, but attribute used to notify recorder
- * about appsink (no object sinks applicable in this use case)
- **/
- *isobj=TRUE;
- }
- break;
- case XA_DATALOCATOR_IODEVICE:
- /* when only valid IOdevice sinks vibra and LED sinks implemented
- * at adaptation level, add handling here (in this implementation,
- * no handling needed as only dummy implementations for those)
- **/
- default:
- DEBUG_ERR("Incorrect data locator for sink.")
- return NULL;
- break;
- }
- }
- if (gstSnk )
- {
- DEBUG_INFO_A1("Created gstreamer sink element at %x", gstSnk);
- }
- DEBUG_API("<-XAAdaptationBase_CreateGstSink");
- return gstSnk;
-}
-
-/**
- * GstElement* XAAdaptationBase_CreateVideoPP( )
- * @return GstElement* - return newly created gst pipeline element
- * Description: Create video processing pipeline
- */
-GstElement* XAAdaptationBase_CreateVideoPP( )
-{
- GstElement *vpp;
- DEBUG_API("->XAAdaptationBase_CreateVideoPP");
- vpp = gst_pipeline_new("videopp");
- if( vpp )
- {
- GstPad *ghostsink, *ghostsrc;
- GstElement *col1,
- *col2,
- *rotate,
- *mirror,
- *box,
- *crop,
- *gamma,
- *balance,
- *scale,
- *scale2,
-#ifdef USE_NGA_SURFACES
- *identity,
-#endif /*USE_NGA_SURFACES*/
- *queue;
-
-
- /* Crete ffmpegcolorspace to convert stream to correct format */
- col1 = gst_element_factory_make( "ffmpegcolorspace", "pp_colsp1");
- if(col1)
- {
- DEBUG_INFO("Created ffmpegcolorspace element");
- gst_bin_add(GST_BIN(vpp), col1);
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(col1,"sink");
- if(ghostsink)
- {
- gst_element_add_pad(vpp, gst_ghost_pad_new("videopp_sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
- }
-
- /* create video crop, this will be sink for videoPP pipeline */
- crop = gst_element_factory_make( "videocrop", "pp_crop");
- if(crop)
- {
- DEBUG_INFO("Created crop element");
- gst_bin_add(GST_BIN(vpp), crop);
- }
-
- /* create video rotate */
- rotate = gst_element_factory_make( "videoflip", "pp_rotate");
- if(rotate)
- {
- DEBUG_INFO("Created rotate element");
- g_object_set(G_OBJECT(rotate), "method", FLIP_NONE, NULL);
- gst_bin_add(GST_BIN(vpp), rotate);
- }
-
- /* create video mirror */
- mirror = gst_element_factory_make( "videoflip", "pp_mirror");
- if(mirror)
- {
- DEBUG_INFO("Created mirror element");
- g_object_set(G_OBJECT(mirror), "method", FLIP_NONE, NULL);
- gst_bin_add(GST_BIN(vpp), mirror);
- }
-
- /* create video box */
- box = gst_element_factory_make( "videobox", "pp_box");
- if(box)
- {
- DEBUG_INFO("Created videobox element");
- gst_bin_add(GST_BIN(vpp), box);
- }
-
- /* create video balance */
- balance = gst_element_factory_make( "videobalance", "pp_balance");
- if(balance)
- {
- DEBUG_INFO("Created balance element");
- gst_bin_add(GST_BIN(vpp), balance);
- }
-
- /* create video gamma */
- gamma = gst_element_factory_make( "gamma", "pp_gamma");
- if(gamma)
- {
- DEBUG_INFO("Created gamma element");
- gst_bin_add(GST_BIN(vpp), gamma);
- }
-
- /* Create videoscale element to scale postprocessed output to correct size */
- scale = gst_element_factory_make("videoscale", "pp_scale");
- if ( scale )
- {
- DEBUG_INFO("Created videoscale element");
- gst_bin_add(GST_BIN(vpp), scale);
- }
- scale2 = gst_element_factory_make("videoscale", "pp_scale2");
- if ( scale2 )
- {
- GstPad *pad = NULL;
- GstCaps *caps = NULL;
- DEBUG_INFO("Created videoscale element");
- pad = gst_element_get_static_pad(scale2,"src");
- caps = gst_caps_new_simple("video/x-raw-yuv",
- "width", G_TYPE_INT,0,
- "height", G_TYPE_INT,0,
- NULL);
- gst_pad_set_caps(pad, caps);
- gst_bin_add(GST_BIN(vpp), scale2);
- }
-
- /* create video queue */
- queue = gst_element_factory_make( "queue", "vpp_queue");
- if(queue)
- {
- DEBUG_INFO("Created queue element");
- gst_bin_add(GST_BIN(vpp), queue);
-#ifdef USE_NGA_SURFACES
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(queue,"sink");
- if(ghostsink)
- {
- gst_element_add_pad(vpp, gst_ghost_pad_new("videopp_src",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
-#endif /*USE_NGA_SURFACES*/
- }
-
-
- /* Crete ffmpegcolorspace to convert stream to correct format */
- col2 = gst_element_factory_make( "ffmpegcolorspace", "pp_colsp2");
- if(col2)
- {
- DEBUG_INFO("Created ffmpegcolorspace element");
- gst_bin_add(GST_BIN(vpp), col2);
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(col2,"src");
- if(ghostsrc)
- {
- gst_element_add_pad(vpp, gst_ghost_pad_new("videopp_src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- }
-
-#ifdef USE_NGA_SURFACES
- //shyward
- /* create identity element */
- identity = gst_element_factory_make( "identity", "identity" );
- if(identity)
- {
- DEBUG_INFO("Created identity element");
- gst_bin_add(GST_BIN(vpp), identity);
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(identity,"src");
- if(ghostsrc)
- {
- gst_element_add_pad(vpp, gst_ghost_pad_new("videopp_sink",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- }
- if( !(gst_element_link_many(queue,identity,NULL)) )
-#else
- //shyward - thins code assumes all the elements will have been created, which is not true
- if( !(gst_element_link_many(col1,
- scale,
- crop,
- rotate,
- mirror,
- box,
- balance,
- gamma,
- queue,
- scale2,
-#ifdef USE_NGA_SURFACES
- identity,
-#endif /*USE_NGA_SURFACES*/
- col2,
- NULL)
- ) )
-#endif /*USE_NGA_SURFACES*/
- {
- DEBUG_ERR("Could not link videopp elements!!");
- gst_object_unref(vpp);
- vpp = NULL;
- }
- }
- DEBUG_API("<-XAAdaptationBase_CreateVideoPP");
- return vpp;
-}
-
-/**
- * GstElement* XAAdaptationBase_CreateFixedSizeRecordVideoPP( )
- * @return GstElement* - return newly created gst pipeline element
- * Description: Create video processing pipeline with fixed output size to TEST_VIDEO_WIDTH x TEST_VIDEO_HEIGHT
- * experimental implementation for changing recorder output size
- */
-GstElement* XAAdaptationBase_CreateFixedSizeVideoPP( )
-{
- GstElement *vpp;
- DEBUG_API("->XAAdaptationBase_CreateFixedSizeVideoPP");
- vpp = gst_pipeline_new("videopp");
- if( vpp )
- {
- GstPad *ghostsink, *ghostsrc;
- GstElement *col1,
- *col2,
- *rotate,
- *mirror,
- *box,
- *crop,
- *gamma,
- *balance,
- *scale,
- *scale2,
- *filter,
- *queue;
-
-
- /* Crete ffmpegcolorspace to convert stream to correct format */
- col1 = gst_element_factory_make( "ffmpegcolorspace", "pp_colsp1");
- if(col1)
- {
- DEBUG_INFO("Created ffmpegcolorspace element");
- gst_bin_add(GST_BIN(vpp), col1);
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(col1,"sink");
- if(ghostsink)
- {
- gst_element_add_pad(vpp, gst_ghost_pad_new("videopp_sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
- }
-
- /* create video crop, this will be sink for videoPP pipeline */
- crop = gst_element_factory_make( "videocrop", "pp_crop");
- if(crop)
- {
- DEBUG_INFO("Created crop element");
- gst_bin_add(GST_BIN(vpp), crop);
- }
-
- /* create video rotate */
- rotate = gst_element_factory_make( "videoflip", "pp_rotate");
- if(rotate)
- {
- DEBUG_INFO("Created rotate element");
- g_object_set(G_OBJECT(rotate), "method", FLIP_NONE, NULL);
- gst_bin_add(GST_BIN(vpp), rotate);
- }
-
- /* create video mirror */
- mirror = gst_element_factory_make( "videoflip", "pp_mirror");
- if(mirror)
- {
- DEBUG_INFO("Created mirror element");
- g_object_set(G_OBJECT(mirror), "method", FLIP_NONE, NULL);
- gst_bin_add(GST_BIN(vpp), mirror);
- }
-
- /* create video box */
- box = gst_element_factory_make( "videobox", "pp_box");
- if(box)
- {
- DEBUG_INFO("Created videobox element");
- gst_bin_add(GST_BIN(vpp), box);
- }
-
- /* create video balance */
- balance = gst_element_factory_make( "videobalance", "pp_balance");
- if(balance)
- {
- DEBUG_INFO("Created balance element");
- gst_bin_add(GST_BIN(vpp), balance);
- }
-
- /* create video gamma */
- gamma = gst_element_factory_make( "gamma", "pp_gamma");
- if(gamma)
- {
- DEBUG_INFO("Created gamma element");
- gst_bin_add(GST_BIN(vpp), gamma);
- }
-
- /* Create videoscale element to scale postprocessed output to correct size */
- scale = gst_element_factory_make("videoscale", "pp_scale");
- if ( scale )
- {
- DEBUG_INFO("Created videoscale element");
- gst_bin_add(GST_BIN(vpp), scale);
- }
- scale2 = gst_element_factory_make("videoscale", "pp_scale2");
- if ( scale2 )
- {
- GstPad *pad = NULL;
- GstCaps *caps = NULL;
- DEBUG_INFO("Created videoscale element");
- pad = gst_element_get_static_pad(scale2,"src");
- caps = gst_caps_new_simple("video/x-raw-yuv",
- "width", G_TYPE_INT,0,
- "height", G_TYPE_INT,0,
- NULL);
- gst_pad_set_caps(pad, caps);
- gst_bin_add(GST_BIN(vpp), scale2);
- }
-
- /* create capsfilter for fixed video size */
- filter = gst_element_factory_make("capsfilter", "pp_filter");
- if ( filter )
- {
-
- g_object_set( G_OBJECT(filter), "caps",
- gst_caps_new_simple("video/x-raw-yuv",
- "width", G_TYPE_INT, TEST_VIDEO_WIDTH,
- "height", G_TYPE_INT, TEST_VIDEO_HEIGHT, NULL)
- ,NULL );
- gst_bin_add(GST_BIN(vpp), filter);
- }
-
- /* create video queue */
- queue = gst_element_factory_make( "queue", "vpp_queue");
- if(queue)
- {
- gst_bin_add(GST_BIN(vpp), queue);
- }
-
-
- /* Crete ffmpegcolorspace to convert stream to correct format */
- col2 = gst_element_factory_make( "ffmpegcolorspace", "pp_colsp2");
- if(col2)
- {
- DEBUG_INFO("Created ffmpegcolorspace element");
- gst_bin_add(GST_BIN(vpp), col2);
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(col2,"src");
- if(ghostsrc)
- {
- gst_element_add_pad(vpp, gst_ghost_pad_new("videopp_src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- }
- if( !(gst_element_link_many(col1,
- scale,
- crop,
- rotate,
- mirror,
- box,
- balance,
- gamma,
- queue,
- scale2,
- filter,
- col2,
- NULL)
- ) )
- {
- DEBUG_ERR("Could not link videopp elements!!");
- gst_object_unref(vpp);
- vpp = NULL;
- }
- }
- DEBUG_API("<-XAAdaptationBase_CreateFixedSizeVideoPP");
- return vpp;
-}
-
-
-
-/**
- * GstElement* XAAdaptationBase_CreateVideoPPBlackScr( )
- * @return GstElement* - return newly created gst pipeline element
- * Description: Create video processing pipeline for black screen
- */
-GstElement* XAAdaptationBase_CreateVideoPPBlackScr( )
-{
- GstElement *vppBScr;
- DEBUG_API("->XAAdaptationBase_CreateVideoPPBlackScr");
- vppBScr = gst_pipeline_new("videoppBScr");
- if( vppBScr )
- {
- GstPad *ghostsrc=NULL;
- GstElement *testVideo=NULL, *scale=NULL;
- GstElement *ffmpegcolorspace=NULL;
-
- testVideo = gst_element_factory_make( "videotestsrc", "videotest");
- if(testVideo)
- {
- DEBUG_INFO("Created videotestsrc element");
-
- g_object_set(G_OBJECT(testVideo), "pattern", (gint)2, "num-buffers", (gint)1, NULL);
- gst_bin_add(GST_BIN(vppBScr), testVideo);
- }
-
- scale = gst_element_factory_make("videoscale", "BSrc_scale");
- if(scale)
- {
- DEBUG_INFO("Created videoscale element");
- gst_bin_add(GST_BIN(vppBScr), scale);
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(scale,"src");
- if(ghostsrc)
- {
- gst_element_add_pad(vppBScr, gst_ghost_pad_new("videoppBSrc_src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- }
- ffmpegcolorspace = gst_element_factory_make("ffmpegcolorspace", "BlackScrFfmpeg");
- gst_bin_add(GST_BIN(vppBScr), ffmpegcolorspace);
- if( !(gst_element_link_many(testVideo, ffmpegcolorspace, scale, NULL)) )
- {
- DEBUG_ERR("Could not link videoppBSrc elements!!");
- gst_object_unref(vppBScr);
- vppBScr = NULL;
- }
- }
- DEBUG_API("<-XAAdaptationBase_CreateVideoPPBlackScr");
- return vppBScr;
-}
-
-/**
- * GstElement* XAAdaptationBase_CreateInputSelector( )
- * @return GstElement* - return newly created input selector
- * Description: Create input selector to processing between black screen and video screen
- */
-GstElement* XAAdaptationBase_CreateInputSelector( )
-{
- GstElement *inputSelector;
- DEBUG_API("->XAAdaptationBase_CreateInputSelector");
- inputSelector = gst_element_factory_make("input-selector", "input-selector");
- if( inputSelector )
- {
- g_object_set(G_OBJECT(inputSelector), "select-all", TRUE, NULL);
- }
- DEBUG_API("<-XAAdaptationBase_CreateInputSelector");
- return inputSelector;
-}
-
-/**
- * GstElement* XAAdaptationBase_CreateAudioPP( )
- * @return GstElement* - return newly created gst pipeline element
- * Description: Create video processing pipeline
- */
-GstElement* XAAdaptationBase_CreateAudioPP( )
-{
- GstElement *app;
- gboolean ok = TRUE;
- DEBUG_API("->XAAdaptationBase_CreateAudioPP");
- app = gst_pipeline_new("audiopp");
- if( app )
- {
- GstPad *ghostsink, *ghostsrc;
- GstElement *ac,*vol,*eq,*queue,*pan, *ac2;
-
- /* first and last elements should be audioconverts to match sink and encoder formats */
- ac = gst_element_factory_make( "audioconvert", "pp_ac");
- if (ac)
- {
- ok = gst_bin_add(GST_BIN(app), ac);
- /* make this bin link point*/
- if (ok)
- {
- ghostsink = gst_element_get_static_pad(ac,"sink");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
- }
- ac2 = gst_element_factory_make( "audioconvert", "pp_ac2");
- if (ac2 && ok)
- {
- ok = gst_bin_add(GST_BIN(app), ac2);
- /* make this bin link point*/
- if (ok)
- {
- ghostsrc = gst_element_get_static_pad(ac2,"src");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- }
-
- vol = gst_element_factory_make( "volume", "pp_vol");
- /* create volume controller */
- if (vol && ok)
- {
- ok = gst_bin_add(GST_BIN(app), vol);
- g_object_set( G_OBJECT(vol), "volume", (gdouble)1, NULL );
- }
- /* create 10-band equalizer */
- eq = gst_element_factory_make( "equalizer-10bands", "pp_equ");
- if (eq && ok)
- {
- ok = gst_bin_add(GST_BIN(app), eq);
- }
- /* create audio queue */
- queue = gst_element_factory_make( "queue", "app_queue");
- if(queue && ok)
- {
- ok = gst_bin_add(GST_BIN(app), queue);
- g_object_set (G_OBJECT (queue), "max-size-buffers", 2, NULL);
- }
- /* create audio pan effect */
- pan = gst_element_factory_make( "audiopanorama", "pp_pan");
- if (pan && ok)
- {
- ok = gst_bin_add(GST_BIN(app), pan);
- }
-
- if (ac && ok)
- {
- if (queue)
- {
- ok = gst_element_link(ac, queue);
- }
- else if (vol)
- {
- ok = gst_element_link(ac, vol);
- }
- else if (pan)
- {
- ok = gst_element_link(ac, pan);
- }
- else if (eq)
- {
- ok = gst_element_link(ac, eq);
- }
- else if (ac2)
- {
- ok = gst_element_link(ac, ac2);
- }
- }
- if (queue && ok)
- {
- if (vol)
- {
- ok = gst_element_link(queue, vol);
- }
- else if (pan)
- {
- ok = gst_element_link(queue, pan);
- }
- else if (eq)
- {
- ok = gst_element_link(queue, eq);
- }
- else if (ac2)
- {
- ok = gst_element_link(queue, ac2);
- }
- }
- if (vol && ok)
- {
- if (pan)
- {
- ok = gst_element_link(vol, pan);
- }
- else if (eq)
- {
- ok = gst_element_link(vol, eq);
- }
- else if (ac2)
- {
- ok = gst_element_link(vol, ac2);
- }
- }
- if (pan && ok)
- {
- if (eq)
- {
- ok = gst_element_link(pan, eq);
- }
- else if (ac2)
- {
- ok = gst_element_link(pan, ac2);
- }
- }
- if (eq && ok)
- {
- if (ac2)
- {
- ok = gst_element_link(eq, ac2);
- }
- }
-
- if (ac)
- {
- // ghost sink above
- }
- else if (queue && ok)
- {
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(queue,"sink");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
- else if (vol && ok)
- {
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(vol,"sink");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
- else if (pan && ok)
- {
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(pan,"sink");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
- else if (eq && ok)
- {
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(eq,"sink");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
- else if (ac2 && ok)
- {
- /* make this bin link point*/
- ghostsink = gst_element_get_static_pad(ac2,"sink");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("sink",ghostsink));
- gst_object_unref(GST_OBJECT(ghostsink));
- }
-
- if (ac2)
- {
- // ghost src above
- }
- else if (eq && ok)
- {
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(eq,"src");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- else if (pan && ok)
- {
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(pan,"src");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- else if (vol && ok)
- {
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(vol,"src");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- else if (queue && ok)
- {
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(queue,"src");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
- else if (ac && ok)
- {
- /* make this bin link point*/
- ghostsrc = gst_element_get_static_pad(ac,"src");
- ok = gst_element_add_pad(app, gst_ghost_pad_new("src",ghostsrc));
- gst_object_unref(GST_OBJECT(ghostsrc));
- }
-
-// if( !(gst_element_link_many(ac, queue, vol, ac2, NULL)) )
-// if( !(gst_element_link_many(ac, queue, vol, pan, eq, ac2, NULL)) )
- if (!ok)
- {
- DEBUG_ERR("Could not link audiopp elements!!");
- gst_object_unref(app);
- app = NULL;
- }
- }
-
- DEBUG_API("<-XAAdaptationBase_CreateAudioPP");
- return app;
-}
-
-/* called when pad is actually blocking/ gets unblocked*/
-void XAAdaptationBase_PadBlockCb(GstPad *pad, gboolean blocked, gpointer user_data)
-{
- DEBUG_API_A2("->XAAdaptationBase_PadBlockCb pad \"%s\" of \"%s\" ",
- GST_OBJECT_NAME(pad),
- GST_OBJECT_NAME(gst_pad_get_parent_element(pad)) );
- DEBUG_API_A1("<-XAAdaptationBase_PadBlockCb blocked:%d",blocked);
-}
-
-/* utility to set same fields for all media types in caps */
-void XAAdaptationBase_SetAllCaps (GstCaps * caps, char *field, ...)
-{
- GstStructure *structure;
- va_list var_args;
- int i;
-
- for (i = 0; i < gst_caps_get_size (caps); i++)
- {
- structure = gst_caps_get_structure (caps, i);
- va_start (var_args, field);
- gst_structure_set_valist (structure, field, var_args);
- va_end (var_args);
- }
-}
-
-/*
- * void* XAAdaptationBase_ContentPipeScrThrFunc( void* arg )
- */
-void* XAAdaptationBase_ContentPipeScrThrFunc( void* arg )
-{
- XAAdaptCpThrCtx* thrCtx = (XAAdaptCpThrCtx*)arg;
- XAresult ret;
- CPresult cpRet;
- XAuint32 requestedBytes = CONTENT_PIPE_BUFFER_SIZE;
- CP_CHECKBYTESRESULTTYPE eResult;
-
- DEBUG_API("->XAAdaptationBase_ContentPipeScrThrFunc");
-
-
- /* Wait until playstate is changed */
- ret = XAImpl_WaitSemaphore( thrCtx->stateSem );
- if ( ret != XA_RESULT_SUCCESS)
- {
- DEBUG_ERR("Could not start semaphore");
- }
-
- thrCtx->state = CPStateRunning;
-
- do
- {
- GstBuffer *buffer = NULL; /* Gstreamer buffer */
-
- if ( thrCtx->state == CPStatePaused )
- {
- /* Wait until playstate is changed */
- ret = XAImpl_WaitSemaphore( thrCtx->stateSem );
- if ( ret != XA_RESULT_SUCCESS)
- {
- DEBUG_ERR("Could not start semaphore");
- thrCtx->state = CPStateError;
- break;
- }
- }
-
- if ( thrCtx->state == CPStateWaitForData )
- {
- }
- /* Check do we have enough bytes in pipe */
- cpRet = thrCtx->pipe->pContentPipe->CheckAvailableBytes(&(thrCtx->dataHandle), requestedBytes, &eResult);
- if ( cpRet != EXIT_SUCCESS )
- {
- thrCtx->state = CPStateError;
- }
-
- if ( eResult == CP_CheckBytesOk)
- { /* We have enough bytes in content pipe */
- thrCtx->state = CPStateRunning;
- DEBUG_API("CP_CheckBytesOk");
-
- if ( thrCtx->cpConfig == XA_READ )
- { /* OMX-AL implementation allocates buffers */
-
- /* Pointer to OMX-AL RI allocated data */
- gpointer cpBuffer = NULL;
-
- /* Allocate new buffer with preferred size */
- cpBuffer = g_malloc0(requestedBytes );
- cpRet = thrCtx->pipe->pContentPipe->Read( &(thrCtx->dataHandle), (CPbyte*)cpBuffer, requestedBytes );
- if ( cpRet != EXIT_SUCCESS )
- {
- DEBUG_ERR("Could not read data from content pipe!");
- thrCtx->state = CPStateError;
- break;
- }
- else
- {
- DEBUG_INFO_A1("Readed %u bytes", requestedBytes );
- /* Create gstBuffer, GStreamer frees data */
- buffer = gst_app_buffer_new( (void*)cpBuffer, requestedBytes, g_free, cpBuffer );
- if ( !buffer )
- {
- DEBUG_ERR("Could not allocate buffer for content pipe source!");
- thrCtx->state = CPStateError;
- break;
- }
- }
- }
- else
- { /* Content pipe implementation allocates buffers */
- gpointer pipeBuffer = NULL;
- gpointer omxBuffer = NULL;
-
- cpRet = thrCtx->pipe->pContentPipe->ReadBuffer( &(thrCtx->dataHandle), (CPbyte**)&pipeBuffer, &requestedBytes, FALSE);
- if ( cpRet != EXIT_SUCCESS )
- {
- DEBUG_ERR("Could not read data from content pipe!");
- thrCtx->state = CPStateError;
- break;
- }
- else
- {
- DEBUG_INFO_A1("Readed %u bytes", requestedBytes );
- /* Copy pipe allocated data into own buffer */
- omxBuffer = g_malloc0(requestedBytes );
- memcpy( omxBuffer, pipeBuffer, requestedBytes );
-
- /* Create gstBuffer, GStreamer frees data */
- buffer = gst_app_buffer_new( omxBuffer, requestedBytes, g_free, omxBuffer );
- if ( !buffer )
- {
- DEBUG_ERR("Could not allocate buffer for content pipe source!");
- thrCtx->state = CPStateError;
- break;
- }
- /* Release readbuffer */
- cpRet = thrCtx->pipe->pContentPipe->ReleaseReadBuffer( &(thrCtx->dataHandle), (CPbyte*)pipeBuffer );
- if ( cpRet != EXIT_SUCCESS )
- {
- DEBUG_ERR("Could not release readbuffer!");
- thrCtx->state = CPStateError;
- break;
- }
- pipeBuffer = NULL;
-
- }
- }
- if ( cpRet == EXIT_SUCCESS )
- {
- if( buffer )
- {
- DEBUG_INFO("Pushing buffer");
- gst_app_src_push_buffer( GST_APP_SRC(thrCtx->appSrc), GST_BUFFER(buffer) );
- }
- }
- }
- else if ( eResult == CP_CheckBytesNotReady )
- {
- DEBUG_API("CP_CheckBytesNotReady");
- thrCtx->state = CPStateWaitForData;
- }
- else if ( eResult == CP_CheckBytesInsufficientBytes )
- {
- DEBUG_API("CP_CheckBytesInsufficientBytes");
- if ( requestedBytes > 0 )
- {
- requestedBytes = requestedBytes - 1 ;
- }
- else
- {
- thrCtx->state = CPStateError;
- }
- }
- else if ( eResult == CP_CheckBytesAtEndOfStream)
- {
- DEBUG_API("XAAdaptationBase_ContentPipeScrThrFunc-> CP_CheckBytesAtEndOfStream");
- thrCtx->state = CPStateEOS;
- }
- }while (thrCtx->state == CPStateRunning || thrCtx->state == CPStateWaitForData || thrCtx->state == CPStatePaused );
-
- if ( thrCtx->state == CPStateError )
- {
- /* If error goto beginning of content */
- cpRet = thrCtx->pipe->pContentPipe->SetPosition( &(thrCtx->dataHandle),0, CP_OriginBegin);
- }
- else if ( thrCtx->state == CPStateEOS )
- {
- /* Send EOS to appSrc */
- gst_app_src_end_of_stream( GST_APP_SRC(thrCtx->appSrc) );
- /* Set position to beginning */
- cpRet = thrCtx->pipe->pContentPipe->SetPosition( &(thrCtx->dataHandle),0, CP_OriginBegin);
- }
- else if ( thrCtx->state == CPStateStopped )
- {
- cpRet = thrCtx->pipe->pContentPipe->SetPosition( &(thrCtx->dataHandle),0, CP_OriginBegin);
- }
-
- thrCtx->state = CPStateInitialized;
-
- DEBUG_API("<-XAAdaptationBase_ContentPipeScrThrFunc");
- return NULL;
-}
-
-/*
- * void* XAAdaptationBase_ContentPipeSinkThrFunc( void* arg )
- */
-void* XAAdaptationBase_ContentPipeSinkThrFunc( void* arg )
-{
- XAAdaptCpThrCtx* thrCtx = (XAAdaptCpThrCtx*)arg;
- XAresult ret;
- CPresult cpRet;
- XAboolean paused;
- XAuint32 position = 0;
-
- DEBUG_API("->XAAdaptationBase_ContentPipeSinkThrFunc");
-
- thrCtx->state = CPStateStarted;
-
- /* Wait until recordstate is changed */
- ret = XAImpl_WaitSemaphore( thrCtx->stateSem );
- if ( ret != XA_RESULT_SUCCESS)
- {
- DEBUG_ERR("Could not start semaphore");
- }
- thrCtx->state = CPStateRunning;
-
- do
- {
- GstBuffer *buffer;
-
- if ( thrCtx->state == CPStatePaused )
- {
- /*If paused get position from end of the file*/
- paused = XA_BOOLEAN_TRUE;
- DEBUG_API("Get New position");
- cpRet = thrCtx->pipe->pContentPipe->GetPosition(&(thrCtx->dataHandle), &position);
- cpRet = thrCtx->pipe->pContentPipe->SetPosition(&(thrCtx->dataHandle), (CPint)position, CP_OriginEnd);
- /* Wait until playstate is changed */
- ret = XAImpl_WaitSemaphore( thrCtx->stateSem );
- if ( ret != XA_RESULT_SUCCESS)
- {
- DEBUG_ERR("Could not start waiting content pipe state semaphore");
- thrCtx->state = CPStateError;
- break;
- }
- }
-
- buffer = gst_app_sink_pull_buffer(GST_APP_SINK(thrCtx->appSink) );
- if ( !buffer )
- {
- DEBUG_INFO("No buffer in gstAppSink!")
- if ( gst_app_sink_is_eos( thrCtx->appSink) )
- {
- DEBUG_API("XAAdaptationBase_ContentPipeSinkThrFunc-> CPStateEOS")
- thrCtx->state = CPStateEOS;
- }
- continue;
- }
-
- if ( thrCtx->cpConfig == XA_WRITE )
- { /* OMX-AL implementation allocates buffers */
-
- /* Write data to content pipe */
- cpRet = thrCtx->pipe->pContentPipe->Write( &(thrCtx->dataHandle), (CPbyte *)GST_BUFFER_DATA(buffer), GST_BUFFER_SIZE(buffer) );
- if ( cpRet != EXIT_SUCCESS )
- {
- DEBUG_ERR("Could not write data to content pipe!");
- thrCtx->state = CPStateError;
- break;
- }
- }
- else
- { /* Use content pipe allocated buffers */
-
- gpointer cpBuffer = NULL;
-
- /* Request buffer from content pipe with gst-buffer size */
- cpRet = thrCtx->pipe->pContentPipe->GetWriteBuffer( &(thrCtx->dataHandle), (CPbyte**)&cpBuffer, GST_BUFFER_SIZE(buffer) );
- if ( cpRet != EXIT_SUCCESS )
- {
- DEBUG_ERR("Could not get write buffer from content pipe!");
- thrCtx->state = CPStateError;
- break;
- }
-
- /* Copy data from gst-buffer to content pipe buffer */
- memcpy( cpBuffer,GST_BUFFER_DATA(buffer),GST_BUFFER_SIZE(buffer));
-
- /* Write buffer to content pipe */
- cpRet = thrCtx->pipe->pContentPipe->WriteBuffer( &(thrCtx->dataHandle), cpBuffer, GST_BUFFER_SIZE(buffer) );
- if ( cpRet != EXIT_SUCCESS )
- {
- DEBUG_ERR("Could not write buffer to content pipe!");
- thrCtx->state = CPStateError;
- break;
- }
-
- g_free(cpBuffer);
- cpBuffer = NULL;
- }
-
- if ( gst_app_sink_is_eos( thrCtx->appSink) )
- {
- thrCtx->state = CPStateEOS;
- }
-
- }while (thrCtx->state == CPStateRunning || thrCtx->state == CPStatePaused );
-
- if ( thrCtx->state == CPStateError )
- {
- /* If error goto beginning of content */
- cpRet = thrCtx->pipe->pContentPipe->SetPosition( &(thrCtx->dataHandle),0, CP_OriginBegin);
- }
- else if ( thrCtx->state == CPStateStopped )
- {
- cpRet = thrCtx->pipe->pContentPipe->SetPosition( &(thrCtx->dataHandle),0, CP_OriginBegin);
- }
-
- DEBUG_API("<-XAAdaptationBase_ContentPipeSinkThrFunc");
- return NULL;
-}
-
-/*
- * CPresult XAAdaptationBase_ContentPipeSrcCb(CP_EVENTTYPE eEvent, CPuint iParam)
- * Description: Callback function for content pipe source
- * @param: CP_EVENTTYPE eEvent - Callback event
- * @param: CPuint iParam - Param related to event
- *
- * No actual functionality can be handled in callback, since current
- * Content Pipe specification lacks methods of supplying client context and/or
- * reference to context pipe handle with CP callback.
- * Khronos group is in progress on proposals for extending this functionality.
- *
- */
-CPresult XAAdaptationBase_ContentPipeSrcCb(CP_EVENTTYPE eEvent, CPuint iParam)
-{
- XAresult ret = XA_RESULT_SUCCESS;
- switch (eEvent )
- {
- case CP_BytesAvailable:
- /* Restart reading thread */
- break;
- case CP_Overflow:
- /* Handle error */
- break;
- case CP_PipeDisconnected:
- /* Reconnect pipe */
- case CP_EventMax:
- break;
- default:
- break;
- }
- return ret;
-}
-
-/*
- * CPresult XAAdaptationBase_ContentPipeSinkCb(CP_EVENTTYPE eEvent, CPuint iParam)
- * Description: Callback function for content pipe sink
- * @param: CP_EVENTTYPE eEvent - Callback event
- * @param: CPuint iParam - Param related to event
- *
- * No actual functionality can be handled in callback, since current
- * Content Pipe specification lacks methods of supplying client context and/or
- * reference to context pipe handle with CP callback.
- * Khronos group is in progress on proposals for extending this functionality.
- *
- */
-CPresult XAAdaptationBase_ContentPipeSinkCb(CP_EVENTTYPE eEvent, CPuint iParam)
-{
- XAresult ret = XA_RESULT_SUCCESS;
- switch (eEvent )
- {
- case CP_BytesAvailable:
- /*Restart write thread.*/
- break;
- case CP_Overflow:
- /*Handle error */
- break;
- case CP_PipeDisconnected:
- /*Reconnect pipe */
- default:
- break;
- }
- return ret;
-
-}