2 * Plugin Name : adecoder
3 * Description : A Generic (ARM/DSP based) Audio Decoder for for TI
6 * Copyright (C) 2007 Texas Instruments, Inc.
8 * This program is free software; you can redistribute it and/or modify it
9 * under the terms of the GNU Lesser General Public License as published
10 * by the Free Software Foundation version 2.1 of the License.
12 * This program is distributed "as is" WITHOUT ANY WARRANTY of any kind,
13 * whether express or implied; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
26 #include "gstadecoder.h"
43 PROP_0
, //prop_id should be greater than 0.
49 ARG_ENABLE_PROCESSING
,
66 GST_DEBUG_CATEGORY_STATIC(gstadecoder_debug
);
67 #define GST_CAT_DEFAULT (gstadecoder_debug)
69 #define translate_DspCommError(x) AVPLAYER_APP_DSPCOMM
71 /* elementfactory information */
73 static GstElementDetails adecoder_details
=
75 "A Generic Audio Decoder",
77 "Codec/Decoder/Audio",
79 "Decodes Various Audio Formats using the Codec Engine",
81 "Yashwant Vijayakumar"
84 static GstStaticPadTemplate sink_template
= GST_STATIC_PAD_TEMPLATE("sink",
94 "mpegversion = (int) { 1, 2, 4 }, "
96 "layer = (int) { 1, 2, 3 }; "
100 "wmaversion = (int) { 1, 2, 3 }, "
102 "rate = (int) { 8000, 11025, 12000, 16000, 22050, 24000, 32000, 44100, 48000 }, "
104 "channels = (int) [ 1, 2 ]"));
107 static GstStaticPadTemplate src_template
= GST_STATIC_PAD_TEMPLATE("src",
117 "endianness = (int) " G_STRINGIFY (G_BYTE_ORDER
) ", "
119 "signed = (boolean)true, "
121 "width = (int) 16, depth = (int) 16, "
123 "rate = (int) {8000, 11025, 12000, 16000, 22050, 24000, 32000, 44100, 48000 }, "
125 "channels = (int) [ 1, 2 ]"));
129 GType
gst_adecoder_get_type(void)
133 static GType adecoder_type
= 0;
137 static const GTypeInfo adecoder_info
=
139 sizeof(GstADecoderClass
),
141 (GBaseInitFunc
) gst_adecoder_base_init
,
145 (GClassInitFunc
) gst_adecoder_class_init
,
155 (GInstanceInitFunc
) gst_adecoder_init
,
158 adecoder_type
= g_type_register_static(GST_TYPE_ELEMENT
, "GstADecoder",&adecoder_info
, 0);
160 GST_DEBUG_CATEGORY_INIT(gstadecoder_debug
,"adecoder",0,"Generic Audio Decoder Element for the ARM");
164 return adecoder_type
;
169 static GType
gst_adecoder_get_engine_type(void)
172 static GType adecoder_engine_type
= 0;
174 if(!adecoder_engine_type
)
176 static GEnumValue engine_types
[] =
179 { H264ENGINE
, "H264Engine","When running H264 or standalone AAC"},
181 { MPEG4ENGINE
,"MPEG4Engine","When running MPEG4"},
183 { WMENGINE
,"WMEngine","When running WMV or standalone WMA"},
185 { MP3ENGINE
,"MP3Engine","When running standalone MP3"},
191 adecoder_engine_type
= g_enum_register_static("AdecoderEngineName",engine_types
);
194 return adecoder_engine_type
;
199 static GType
gst_adecoder_get_codec_type(void)
202 static GType adecoder_codec_type
= 0;
204 if(!adecoder_codec_type
)
206 static GEnumValue codec_types
[] =
208 { ST_AUDIO_ARM_MP3
, "MP3","When running MP3 Decoder"},
210 { ST_AUDIO_WMA
,"WMA","When running WMA Decoder"},
212 { ST_AUDIO_AAC
,"AAC","When running AAC Decoder"},
214 { ST_AUDIO_DSP_MP3
, "MP3","When running MP3 Decoder"},
220 adecoder_codec_type
= g_enum_register_static("AdecoderCodecName",codec_types
);
223 return adecoder_codec_type
;
227 static GstCaps
*gst_adecoder_sink_getcaps(GstPad
* pad
)
232 printf("Sink getcaps invoked\n");
236 return gst_caps_copy(gst_pad_get_pad_template_caps(pad
));
241 static GstCaps
*gst_adecoder_src_getcaps(GstPad
* pad
)
246 printf("Src getcaps invoked\n");
250 return gst_caps_copy(gst_pad_get_pad_template_caps(pad
));
255 static gboolean
gst_adecoder_sink_setcaps(GstPad
* pad
, GstCaps
* caps
)
258 GstADecoder
*adecoder
;
260 GstStructure
*structure
;
262 GstCaps
*intersection
;
268 printf("Inside set caps...\n");
272 adecoder
= GST_ADECODER(GST_PAD_PARENT(pad
));
274 intersection
= gst_caps_intersect(gst_pad_get_pad_template_caps(pad
), caps
);
276 if (gst_caps_is_empty(intersection
))
280 printf(" Caps empty...\n");
287 gst_caps_unref(intersection
);
289 structure
= gst_caps_get_structure(caps
, 0);
291 mime
= gst_structure_get_name(structure
);
293 if (!strcmp("audio/mpeg", mime
))
297 gst_structure_get_int(structure
, "mpegversion", &version
);
303 if (version
== 1){ //version 1 -> mp3
304 adecoder
->codec
= ST_AUDIO_DSP_MP3
;
305 printf("Audio is MP3\n");
307 else{ //version 2 or 4 -> aac
308 adecoder
->codec
= ST_AUDIO_AAC
;
309 printf("Audio is AAC\n");
311 }else if (!strcmp("audio/x-wma",mime
)){
312 adecoder
->codec
= ST_AUDIO_WMA
;
313 printf("Audio is WMA\n");
315 printf(" Unknown mime type...\n");
319 adecoder
->isCodecPropSet
= TRUE
;
324 static void gst_adecoder_base_init(GstADecoderClass
* klass
)
327 GstElementClass
*element_class
= GST_ELEMENT_CLASS(klass
);
329 klass
->sink_template
= gst_static_pad_template_get(&sink_template
);
331 klass
->src_template
= gst_static_pad_template_get(&src_template
);
333 gst_element_class_add_pad_template(element_class
, klass
->src_template
);
335 gst_element_class_add_pad_template(element_class
,klass
->sink_template
);
337 gst_element_class_set_details(element_class
, &adecoder_details
);
341 static void gst_adecoder_class_init(GstADecoderClass
* klass
)
344 GstElementClass
*gstelement_class
= (GstElementClass
*) klass
;
346 GObjectClass
*object_class
= (GObjectClass
*)(klass
);
348 parent_class
= g_type_class_ref(GST_TYPE_ELEMENT
);
350 gstelement_class
->change_state
= gst_adecoder_change_state
;
352 object_class
->set_property
= gst_adecoder_set_property
;
354 g_object_class_install_property(object_class
,ARG_ENGINE_NAME
,g_param_spec_enum ("Engine","Engine","Name of Engine to open"
356 ,GST_TYPE_ADECODER_ENGINE
,0,G_PARAM_WRITABLE
));
358 g_object_class_install_property(object_class
,ARG_CODEC_NAME
,g_param_spec_enum ("Codec","Codec","Name of Codec to run"
360 ,GST_TYPE_ADECODER_CODEC
,0,G_PARAM_WRITABLE
));
362 g_object_class_install_property(object_class
,ARG_ENABLE_PROCESSING
,g_param_spec_boolean ("Enable_Processing","Enable_Processing","Used during dsp on/off"
364 ,TRUE
,G_PARAM_WRITABLE
));
368 static void gst_adecoder_set_property (GObject
* object
, guint prop_id
, const GValue
* value
, GParamSpec
* pspec
)
370 GstADecoder
*adecoder
= GST_ADECODER(object
);
374 case ARG_ENGINE_NAME
:
376 adecoder
->engine
= g_value_get_enum(value
);
378 adecoder
->isEnginePropSet
= TRUE
;
382 printf("Engine handle set to value %x\n",adecoder
->ce
);
390 adecoder
->codec
= g_value_get_enum(value
);
392 adecoder
->isCodecPropSet
= TRUE
;
396 printf("Codec set to enum value %d\n",adecoder
->codec
);
402 case ARG_ENABLE_PROCESSING
:
404 if(adecoder
->enable_processing
!= g_value_get_boolean(value
))
407 adecoder
->enable_processing
= g_value_get_boolean(value
);
409 if(adecoder
->enable_processing
== TRUE
)
413 printf("Enable_processing\n");
417 pthread_mutex_unlock(adecoder
->start_decode
);
424 printf("Disable_processing\n");
428 //pthread_mutex_lock(adecoder->start_decode);
437 G_OBJECT_WARN_INVALID_PROPERTY_ID (object
, prop_id
, pspec
);
443 //gst_object_unref(adecoder); //getting seg.fault when unref is done.
448 static void gst_adecoder_init(GstADecoder
* adecoder
)
451 GstADecoderClass
*klass
= GST_ADECODER_GET_CLASS(adecoder
);
453 GstElementClass
*element_class
= GST_ELEMENT_CLASS(klass
);
455 adecoder
->sinkpad
= gst_pad_new_from_template(klass
->sink_template
, "sink");
457 gst_pad_set_activate_function(adecoder
->sinkpad
,GST_DEBUG_FUNCPTR(gst_adecoder_sink_activate
));
459 gst_pad_set_activatepull_function(adecoder
->sinkpad
,GST_DEBUG_FUNCPTR(gst_adecoder_sink_activate_pull
));
461 gst_pad_set_event_function(adecoder
->sinkpad
,GST_DEBUG_FUNCPTR(gst_adecoder_sink_event
));
463 gst_pad_set_chain_function(adecoder
->sinkpad
, gst_adecoder_chain
);
465 gst_pad_set_getcaps_function(adecoder
->sinkpad
,gst_adecoder_sink_getcaps
);
467 gst_pad_set_setcaps_function(adecoder
->sinkpad
,gst_adecoder_sink_setcaps
);
469 gst_element_add_pad(GST_ELEMENT(adecoder
), adecoder
->sinkpad
);
471 adecoder
->srcpad
= gst_pad_new_from_template(klass
->src_template
, "src");
473 gst_pad_set_event_function(adecoder
->srcpad
,GST_DEBUG_FUNCPTR(gst_adecoder_src_event
));
475 gst_pad_set_getcaps_function(adecoder
->srcpad
,gst_adecoder_src_getcaps
);
477 gst_element_add_pad(GST_ELEMENT(adecoder
), adecoder
->srcpad
);
479 element_class
->query
= gst_adecoder_query
;
481 gst_adecoder_initialize_handle(adecoder
);
486 static gboolean
gst_adecoder_query(GstElement
*element
, GstQuery
*query
)
488 GstStructure
*query_struct
;
490 GValue bitRate
= {0};
492 GValue dspLoad
= { 0, };
494 GstADecoder
*adecoder
= GST_ADECODER(element
);
496 g_value_init(&bitRate
,G_TYPE_UINT
);
498 g_value_set_uint(&bitRate
,adecoder
->Status
->bitRate
);
500 g_value_init(&dspLoad
, G_TYPE_INT
);
502 g_value_set_int(&dspLoad
, Engine_getCpuLoad(adecoder
->ce
));
504 query_struct
= gst_query_get_structure(query
);
506 gst_structure_set_value(query_struct
,"bitRate",&bitRate
);
508 gst_structure_set_value(query_struct
, "dspCpuLoad", &dspLoad
);
509 g_value_unset(&bitRate
);
511 g_value_unset(&dspLoad
);
513 gst_object_unref(adecoder
);
518 static void gst_adecoder_initialize_handle(GstADecoder
* adecoder
)
521 adecoder
->firstFrame
= TRUE
;
523 adecoder
->inbuf
= adecoder
->inbuf_start_addr
= NULL
;
525 adecoder
->outbuf
[0] = NULL
;
527 adecoder
->outbuf
[1] = NULL
;
529 adecoder
->readOffset
= 0;
531 adecoder
->codec_handle
= NULL
;
535 adecoder
->bytes_not_decoded
= 0;
537 adecoder
->bytesConsumed
= 0;
539 adecoder
->frameCount
= 0;
541 adecoder
->isEof
= FALSE
;
543 adecoder
->isEos
= FALSE
;
547 adecoder
->engine
= 0;
549 adecoder
->isEnginePropSet
= FALSE
;
551 adecoder
->isCodecPropSet
= FALSE
;
553 adecoder
->isPaused
= FALSE
;
555 adecoder
->isStopped
= FALSE
;
557 adecoder
->frame_time
= 0;
559 adecoder
->enable_processing
= TRUE
;
561 adecoder
->start_decode
= malloc(sizeof(pthread_mutex_t
));
563 pthread_mutex_init(adecoder
->start_decode
, NULL
);
565 pthread_mutex_lock(adecoder
->start_decode
);
569 static gboolean
gst_adecoder_sink_activate(GstPad
* sinkpad
)
572 GstADecoder
*adecoder
= GST_ADECODER(gst_pad_get_parent(sinkpad
));
576 printf("Sink Activate invoked\n");
580 if (gst_pad_check_pull_range(sinkpad
))
582 adecoder
->isInPushMode
= FALSE
;
584 gst_object_unref(adecoder
);
586 return gst_pad_activate_pull(sinkpad
, TRUE
);
593 printf("pull_range not supported on sinkpad\n");
595 printf("Running In Push Mode\n");
599 adecoder
->isInPushMode
= TRUE
;
601 gst_object_unref(adecoder
);
603 return gst_pad_activate_push(sinkpad
, TRUE
);
609 static gboolean
gst_adecoder_sink_activate_pull(GstPad
* sinkpad
, gboolean active
)
612 GstADecoder
*adecoder
= GST_ADECODER(gst_pad_get_parent(sinkpad
));
616 printf("Activate pull invoked\n");
622 gst_pad_start_task(sinkpad
, (GstTaskFunction
) gst_adecoder_loop
,sinkpad
);/* if we have a scheduler we can start the task */
626 gst_pad_stop_task(sinkpad
);
628 gst_object_unref(adecoder
);
634 static void gst_adecoder_loop(GstPad
* pad
)
636 GstADecoder
*adecoder
= GST_ADECODER(gst_pad_get_parent(pad
));
638 if(adecoder
->isEos
== FALSE
&& adecoder
->isStopped
== FALSE
)
641 if(adecoder
->initialized
== FALSE
)
643 if((adecoder
->initialized
= gst_adecoder_decoder_initialize(adecoder
,NULL
)) == FALSE
)
647 printf("Could not initialize\n");
651 gst_object_unref(adecoder
);
657 if(gst_adecoder_loop_get_data(adecoder
) == FALSE
)
659 gst_object_unref(adecoder
);
664 if (adecoder
->enable_processing
== FALSE
)
668 printf("Waiting on lock\n");
672 pthread_mutex_lock(adecoder
->start_decode
);
676 printf("Lock succeeded\n");
682 if (adecoder
->isPaused
== TRUE
)
684 gst_object_unref(adecoder
);
689 if(gst_adecoder_process_data(adecoder
) == FALSE
)
691 gst_object_unref(adecoder
);
696 if(adecoder
->firstFrame
== TRUE
)
698 gst_adecoder_initialize_osssink(adecoder
);
700 gst_adecoder_output_data(adecoder
);
704 gst_object_unref(adecoder
);
708 static gboolean
gst_adecoder_loop_get_data(GstADecoder
*adecoder
)
710 GstBuffer
*buf
= NULL
;
712 if(adecoder
->bytes_not_decoded
< adecoder
->inBufSize
&& adecoder
->isEof
== FALSE
)
715 if (gst_pad_pull_range(adecoder
->sinkpad
,adecoder
->readOffset
,INPUT_BUFFER_SIZE
- adecoder
->bytes_not_decoded
,&buf
) != GST_FLOW_OK
)
719 printf("Pad pull range failed\n");
723 gst_pad_push_event(adecoder
->srcpad
, gst_event_new_eos());
729 if(GST_BUFFER_SIZE(buf
) < INPUT_BUFFER_SIZE
- adecoder
->bytes_not_decoded
)
731 adecoder
->isEof
= TRUE
;
733 memmove(adecoder
->inbuf_start_addr
,adecoder
->inbuf
,adecoder
->bytes_not_decoded
);
735 adecoder
->inbuf
= adecoder
->inbuf_start_addr
;
737 memcpy((guint8
*) ((guint32
) adecoder
->inbuf
+ adecoder
->bytes_not_decoded
),GST_BUFFER_DATA(buf
), GST_BUFFER_SIZE(buf
));
739 adecoder
->bytes_not_decoded
+= GST_BUFFER_SIZE(buf
);
741 adecoder
->readOffset
+= GST_BUFFER_SIZE(buf
);
743 gst_buffer_unref(buf
);
747 if(adecoder
->bytes_not_decoded
<= 10)
751 printf("No more data to decode....Sending EOS event to terminate...\n");
753 printf("Bytes not decoded:%d\n",adecoder
->bytes_not_decoded
);
757 gst_pad_push_event(adecoder
->srcpad
, gst_event_new_eos());
759 adecoder
->isEos
= TRUE
;
769 static GstFlowReturn
gst_adecoder_chain(GstPad
* pad
,GstBuffer
* input_buffer
)
772 GstADecoder
*adecoder
= GST_ADECODER(gst_pad_get_parent(pad
));
774 if(adecoder
->initialized
== FALSE
)
777 if((adecoder
->initialized
= gst_adecoder_decoder_initialize(adecoder
,input_buffer
)) == FALSE
)
781 printf("Could not initialize\n");
785 gst_object_unref(adecoder
);
787 gst_buffer_unref(input_buffer
);
789 return GST_FLOW_ERROR
;
792 adecoder
->initTimeStamp
= GST_BUFFER_TIMESTAMP(input_buffer
);
798 printf("Buffer size from Demuxer:%d\n",GST_BUFFER_SIZE(input_buffer
));
802 if(gst_adecoder_chain_get_data(adecoder
,input_buffer
) == FALSE
)
805 gst_object_unref(adecoder
);
810 while(adecoder
->bytes_not_decoded
> adecoder
->inBufSize
&& adecoder
->isStopped
== FALSE
)
812 if (adecoder
->enable_processing
== FALSE
)
816 printf("Waiting on lock\n");
820 pthread_mutex_lock(adecoder
->start_decode
);
824 printf("Lock succeeded\n");
830 if( gst_adecoder_process_data(adecoder
) == FALSE
)
832 gst_object_unref(adecoder
);
837 if(adecoder
->firstFrame
== TRUE
)
839 gst_adecoder_initialize_osssink(adecoder
);
842 if(gst_adecoder_output_data(adecoder
) == FALSE
)
844 gst_object_unref(adecoder
);
846 return GST_FLOW_ERROR
;
850 gst_object_unref(adecoder
);
857 static gboolean
gst_adecoder_chain_get_data(GstADecoder
*adecoder
,GstBuffer
* buffer
)
859 guint32 buf_size
= GST_BUFFER_SIZE(buffer
);
861 if(adecoder
->inbuf
!= adecoder
->inbuf_start_addr
)
864 memmove(adecoder
->inbuf_start_addr
,adecoder
->inbuf
,adecoder
->bytes_not_decoded
);
866 adecoder
->inbuf
= adecoder
->inbuf_start_addr
;
869 if(adecoder
->bytes_not_decoded
+ buf_size
>= INPUT_BUFFER_SIZE
)
873 printf("Push mode:Not enough memory to save the buffer....current size:%d\n",adecoder
->bytes_not_decoded
);
877 gst_buffer_unref(buffer
);
882 memcpy((guint8
*) ((guint32
) adecoder
->inbuf
+ adecoder
->bytes_not_decoded
),(char *)(GST_BUFFER_DATA(buffer
)),buf_size
);
884 gst_buffer_unref(buffer
);
886 adecoder
->bytes_not_decoded
+= buf_size
;
888 if(adecoder
->bytes_not_decoded
< adecoder
->inBufSize
)
897 static gboolean
gst_adecoder_process_data(GstADecoder
*adecoder
)
902 printf("Before calling AUDDEC_process\n");
906 if(AUDDEC_process(adecoder
->codec_handle
,&(adecoder
->inBufDesc
),&(adecoder
->outBufDesc
),adecoder
->InArgs
,adecoder
->OutArgs
) == AUDDEC_EOK
)
911 printf("AUDDEC_process returned successfully,bytesConsumed:%d\n",adecoder
->OutArgs
->bytesConsumed
);
915 adecoder
->inbuf
+= adecoder
->OutArgs
->bytesConsumed
;
917 adecoder
->bytes_not_decoded
-= adecoder
->OutArgs
->bytesConsumed
;
919 AUDDEC_control(adecoder
->codec_handle
,XDM_GETSTATUS
,adecoder
->DyParams
,adecoder
->Status
);
921 adecoder
->frameCount
++;
925 printf("FrameCount:%u FrameLen:%d SampleRate:%d BitsPerSample:%d BitRate:%d ",adecoder
->frameCount
,
927 adecoder
->Status
->frameLen
,adecoder
->Status
->sampleRate
,adecoder
->Status
->outputBitsPerSample
,adecoder
->Status
->bitRate
);
929 if(adecoder
->Status
->numChannels
== IAUDIO_MONO
)
931 printf("IAUDIO_MONO\n");
935 printf("IAUDIO_STEREO\n");
937 printf("bytes_not_decoded:%d\n",adecoder
->bytes_not_decoded
);
950 printf("AUDDEC_process returned with failure\n");
959 static void gst_adecoder_initialize_osssink(GstADecoder
*adecoder
)
961 GstCaps
*othercaps
, *getcaps
;
963 GstStructure
*structure
;
967 othercaps
= gst_caps_new_simple ("audio/x-raw-int",
969 "endianness", G_TYPE_INT
, G_BYTE_ORDER
,
971 "signed", G_TYPE_BOOLEAN
, TRUE
,
973 "width", G_TYPE_INT
, 16,
975 "depth", G_TYPE_INT
, 16,
977 "rate", G_TYPE_INT
,adecoder
->Status
->sampleRate
,
979 "channels", G_TYPE_INT
,DEFAULT_NO_OF_OUTPUT_CHANNELS
, NULL
);
981 if(gst_pad_set_caps(adecoder
->srcpad
, othercaps
) == FALSE
)
986 printf("Initialize osssink failed\n");
992 gst_pad_use_fixed_caps(adecoder
->srcpad
);
994 getcaps
= gst_pad_get_caps(adecoder
->srcpad
);
996 structure
= gst_caps_get_structure(getcaps
, 0);
998 gst_structure_get_int(structure
,"rate",&rate
);
1002 printf("Sampling Rate:%d\n",rate
);
1006 gst_caps_unref(othercaps
);
1008 if(adecoder
->isInPushMode
== FALSE
)
1010 gst_pad_push_event(adecoder
->srcpad
,
1012 gst_event_new_new_segment( FALSE
,
1014 adecoder
->segment
.rate
,
1016 adecoder
->segment
.format
,
1018 adecoder
->segment
.start
,
1020 adecoder
->segment
.duration
,
1022 adecoder
->segment
.start
));
1025 if(adecoder
->firstFrame
== TRUE
)
1027 adecoder
->firstFrame
= FALSE
;
1032 static gboolean
gst_adecoder_output_data(GstADecoder
*adecoder
)
1036 GstBuffer
*outbuf
[2];
1038 guint32 frameLen
= adecoder
->Status
->frameLen
;
1040 guint32 bitsPerSample
= adecoder
->Status
->outputBitsPerSample
;
1042 guint8 numChannels
= adecoder
->Status
->numChannels
;
1048 for( i
= 0; (i
< adecoder
->outBufDesc
.numBufs
);i
++)
1050 ret
= gst_pad_alloc_buffer(adecoder
->srcpad
, GST_BUFFER_OFFSET_NONE
,frameLen
* DEFAULT_NO_OF_OUTPUT_CHANNELS
* bitsPerSample
/ 8
1052 ,GST_PAD_CAPS(adecoder
->srcpad
),&(outbuf
[i
]));
1055 if (ret
!= GST_FLOW_OK
)
1059 printf("failed when allocating a %ld bytes buffer\n",frameLen
* DEFAULT_NO_OF_OUTPUT_CHANNELS
* bitsPerSample
/ 8);
1063 if ( (adecoder
->isInPushMode
== FALSE
) && (adecoder
->isPaused
== FALSE
) )
1065 gst_pad_pause_task(adecoder
->sinkpad
);
1072 for( i
= 0;(i
< adecoder
->outBufDesc
.numBufs
);i
++)
1075 if(adecoder
->codec
== ST_AUDIO_WMA
&& numChannels
== IAUDIO_MONO
) //WMA Decoder is not replicating data in case of MONO.
1078 memcpy((char *)((unsigned)(adecoder
->outbuf
[i
]) + frameLen
* bitsPerSample
/ 8),
1080 (char *)(adecoder
->outbuf
[i
]),frameLen
* bitsPerSample
/ 8);
1082 block_to_interleaved((XDAS_Int16
*)(adecoder
->outbuf
[i
]),(XDAS_Int8
*)GST_BUFFER_DATA(outbuf
[i
]),frameLen
);
1091 block_to_interleaved((XDAS_Int16
*)(adecoder
->outbuf
[i
]),(XDAS_Int8
*)GST_BUFFER_DATA(outbuf
[i
]),frameLen
);
1095 memcpy((char *)GST_BUFFER_DATA(outbuf
[i
]),(char *)adecoder
->outbuf
[i
],
1097 frameLen
* DEFAULT_NO_OF_OUTPUT_CHANNELS
* bitsPerSample
/ 8);
1101 if (gst_adecoder_send_data(adecoder
,outbuf
[i
]) != GST_FLOW_OK
)
1106 printf("Send data to osssink failed\n");
1123 static gboolean
gst_adecoder_decoder_initialize(GstADecoder
* adecoder
,GstBuffer
* input_buffer
)
1127 printf ("Entering gst_adecoder_decoder_initialize...\n");
1131 if(gst_adecoder_open_engine(adecoder
) == FALSE
)
1135 if(gst_adecoder_create_codec(adecoder
,input_buffer
) == FALSE
)
1139 if(gst_adecoder_initialize_codec(adecoder
) == FALSE
)
1143 if(adecoder
->isInPushMode
== FALSE
)
1145 gst_segment_init(&adecoder
->segment
, GST_FORMAT_TIME
);
1149 printf ("Exiting gst_adecoder_decoder_initialize...\n");
1157 static gboolean
gst_adecoder_open_engine(GstADecoder
* adecoder
)
1162 //GT_set("*=01234567,CE-1");
1164 if(adecoder
->isEnginePropSet
== TRUE
)
1166 switch (adecoder
->engine
)
1173 printf ("Opening H264 Engine...\n");
1177 adecoder
->ce
= Engine_open("H264Engine", NULL
, NULL
);
1185 printf ("Opening MPEG4 Engine...\n");
1189 adecoder
->ce
= Engine_open("MPEG4Engine", NULL
, NULL
);
1197 printf ("Opening WM Engine...\n");
1201 adecoder
->ce
= Engine_open("WMEngine", NULL
, NULL
);
1209 printf ("Opening MP3 Engine...\n");
1213 adecoder
->ce
= Engine_open("MP3Engine", NULL
, NULL
);
1221 else if(adecoder
->isCodecPropSet
== TRUE
) //standalone case
1223 switch (adecoder
->codec
)
1230 printf ("Opening MPEG4 Engine...\n");
1234 adecoder
->ce
= Engine_open("MPEG4Engine", NULL
, NULL
);
1242 printf ("Opening WM Engine...\n");
1246 adecoder
->ce
= Engine_open("WMEngine", NULL
, NULL
);
1250 case ST_AUDIO_DSP_MP3
:
1254 printf ("Opening MP3 Engine...\n");
1258 adecoder
->ce
= Engine_open("MP3Engine", NULL
, NULL
);
1270 printf ("Both properties not Set.....Opening H264 Engine by default..\n");
1274 adecoder
->ce
= Engine_open("H264Engine", NULL
, NULL
);
1278 if( adecoder
->ce
== NULL
)
1282 printf("Engine_open failed\n");
1294 static gboolean
gst_adecoder_create_codec(GstADecoder
* adecoder
,GstBuffer
* input_buffer
)
1297 IAUDDEC_Params audParams
;
1298 AUDDEC_Handle audDec
;
1301 switch (adecoder
->codec
)
1306 printf ("Creating WMA Codec...\n");
1309 audParams
.size
= sizeof(IAUDDEC_Params
);
1310 audParams
.maxSampleRate
= 48000;
1311 audParams
.maxBitrate
= 384000;
1312 audParams
.maxNoOfCh
= IAUDIO_STEREO
;
1313 audParams
.dataEndianness
= XDM_BYTE
;
1315 audDec
= AUDDEC_create(adecoder
->ce
, "wma9dec", &audParams
);
1320 printf("Engine handle:%x\n",adecoder
->ce
);
1321 printf("AUDDEC_create failed\n");
1331 printf ("Creating AAC Codec...\n");
1334 audParams
.size
= sizeof(IAUDDEC_Params
);
1335 audParams
.maxSampleRate
= 48000;
1336 audParams
.maxBitrate
= 448000;
1337 audParams
.maxNoOfCh
= IAUDIO_STEREO
;
1338 audParams
.dataEndianness
= XDM_BYTE
;
1340 audDec
= AUDDEC_create(adecoder
->ce
, "aachedec", &audParams
);
1345 printf("AUDDEC_create failed\n");
1352 case ST_AUDIO_DSP_MP3
:
1355 printf ("Creating DSP MP3 Codec...\n");
1358 audParams
.size
= sizeof(IAUDDEC_Params
);
1359 audParams
.maxSampleRate
= 48000;
1360 audParams
.maxBitrate
= 448000;
1361 audParams
.maxNoOfCh
= IAUDIO_STEREO
;
1362 audParams
.dataEndianness
= XDM_BYTE
;
1364 audDec
= AUDDEC_create(adecoder
->ce
, "mp3dec", &audParams
);
1369 printf("AUDDEC_create failed\n");
1379 adecoder
->codec_handle
= audDec
;
1382 printf ("Exiting Create Codec...\n");
1387 static gboolean
gst_adecoder_initialize_codec(GstADecoder
* adecoder
)
1390 IAUDDEC_DynamicParams
*audDynamicParams
= NULL
;
1391 IAUDDEC_Status
*audStatus
= NULL
;
1392 IAUDDEC_InArgs
*InArgs
= NULL
;
1393 IAUDDEC_OutArgs
*OutArgs
= NULL
;
1394 XDAS_Int32 ret1
,ret2
,ret3
,ret4
;
1398 printf ("Entering gst_adecoder_initialize_codec...\n");
1401 switch(adecoder
->codec
)
1405 InArgs
= (IAUDDEC_InArgs
*)malloc(sizeof(IAUDDEC_InArgs
));
1406 InArgs
->size
= sizeof(IAUDDEC_InArgs
);
1408 OutArgs
= (IAUDDEC_OutArgs
*)malloc(sizeof(IAUDDEC_OutArgs
));
1409 OutArgs
->size
= sizeof(IAUDDEC_OutArgs
);
1411 audStatus
= (IAUDDEC_Status
*)malloc(sizeof(IAUDDEC_Status
));
1412 audStatus
->size
= sizeof(IAUDDEC_Status
);
1414 audDynamicParams
= (IAUDDEC_DynamicParams
*)malloc(sizeof(IAUDDEC_DynamicParams
));
1415 audDynamicParams
->size
= sizeof(IAUDDEC_DynamicParams
);
1422 audStatus
= (IAUDDEC_Status
*)malloc(sizeof(IAUDDEC_Status
));
1423 audStatus
->size
= sizeof(IAUDDEC_Status
);
1430 InArgs
= (IAUDDEC_InArgs
*)malloc(sizeof(IAUDDEC_InArgs
));
1431 InArgs
->size
= sizeof(IAUDDEC_InArgs
);
1434 if(audDynamicParams
== NULL
)
1436 audDynamicParams
= (IAUDDEC_DynamicParams
*)malloc(sizeof(IAUDDEC_DynamicParams
));
1437 audDynamicParams
->size
= sizeof(IAUDDEC_DynamicParams
);
1442 OutArgs
= (IAUDDEC_OutArgs
*)malloc(sizeof(IAUDDEC_OutArgs
));
1443 OutArgs
->size
= sizeof(IAUDDEC_OutArgs
);
1446 if(audStatus
== NULL
)
1448 audStatus
= (IAUDDEC_Status
*)malloc(sizeof(IAUDDEC_Status
));
1449 audStatus
->size
= sizeof(IAUDDEC_Status
);
1454 printf("handle:%x audDynamicParams:%x Status:%x\n",adecoder
->codec_handle
,audDynamicParams
,audStatus
);
1458 // ret1 = AUDDEC_control(adecoder->codec_handle,XDM_RESET,audDynamicParams,audStatus);
1460 // if (ret1 != AUDDEC_EOK)
1463 // printf("AUDDEC_control() 1 returned failure in gst_adecoder_initialize_codec()\n");
1469 ret2
= AUDDEC_control(adecoder
->codec_handle
,XDM_SETDEFAULT
,audDynamicParams
,audStatus
);
1473 audDynamicParams
->outputFormat
= IAUDIO_INTERLEAVED
;
1475 audDynamicParams
->outputFormat
= IAUDIO_BLOCK
;
1478 ret3
= AUDDEC_control(adecoder
->codec_handle
,XDM_SETPARAMS
, audDynamicParams
,audStatus
);
1479 ret4
= AUDDEC_control(adecoder
->codec_handle
,XDM_GETBUFINFO
, audDynamicParams
, audStatus
);
1481 if (ret2
!= AUDDEC_EOK
)
1485 printf("AUDDEC_control() 2 returned failure in gst_adecoder_initialize_codec()\n");
1492 // if (ret1 != AUDDEC_EOK || ret2!= AUDDEC_EOK || ret3 != AUDDEC_EOK || ret4 != AUDDEC_EOK)
1493 if (ret3
!= AUDDEC_EOK
)
1497 printf("AUDDEC_control() 3 returned failure in gst_adecoder_initialize_codec()\n");
1504 if (ret4
!= AUDDEC_EOK
)
1508 printf("AUDDEC_control() 4 returned failure in gst_adecoder_initialize_codec()\n");
1517 adecoder
->inBufSize
= audStatus
->bufInfo
.minInBufSize
[0];
1521 printf("Input buffer size = %ld\n",audStatus
->bufInfo
.minInBufSize
[0]);
1525 adecoder
->inbuf_start_addr
= adecoder
->inbuf
= (XDAS_Int8
*) Memory_contigAlloc(INPUT_BUFFER_SIZE
,Memory_DEFAULTALIGNMENT
);
1527 if (adecoder
->inbuf
== NULL
)
1531 printf("Failed to allocate input buffer using CMEM\n");
1541 for(i
= 0;i
< audStatus
->bufInfo
.minNumOutBufs
;i
++)
1543 adecoder
->outBufSize
[i
] = audStatus
->bufInfo
.minOutBufSize
[i
];
1545 adecoder
->outbuf
[i
] = (XDAS_Int8
*) Memory_contigAlloc(adecoder
->outBufSize
[i
],Memory_DEFAULTALIGNMENT
);
1547 if(adecoder
->outbuf
[i
] == NULL
)
1551 printf("Failed to allocate output buffer using CMEM\n");
1561 adecoder
->outBufDesc
.bufSizes
= adecoder
->outBufSize
;
1563 adecoder
->outBufDesc
.numBufs
= audStatus
->bufInfo
.minNumOutBufs
;
1565 adecoder
->inBufDesc
.bufSizes
= &adecoder
->inBufSize
;
1567 adecoder
->inBufDesc
.numBufs
= 1;
1569 adecoder
->outBufDesc
.bufs
= adecoder
->outbuf
;
1571 adecoder
->inBufDesc
.bufs
= &(adecoder
->inbuf
);
1573 InArgs
->numBytes
= adecoder
->inBufSize
;
1575 adecoder
->DyParams
= audDynamicParams
;
1577 adecoder
->Status
= audStatus
;
1579 adecoder
->InArgs
= InArgs
;
1581 adecoder
->OutArgs
= OutArgs
;
1585 printf ("Exiting gst_adecoder_initialize_codec...\n");
1594 static void block_to_interleaved(XDAS_Int16
*src
,XDAS_Int8
*dest
,guint32 frameLen
)
1598 unsigned short c
,c1
,c2
;
1600 for(i
= 0,j
= 0;i
< frameLen
;i
++,j
+= 4)
1606 c1
= (c
>> 8) & 0xff;
1616 c
= src
[i
+frameLen
];
1618 c1
= (c
>> 8) & 0xff;
1631 static unsigned long timeDiffMs(struct timespec
*pTs1
, struct timespec
*pTs2
)
1633 unsigned long delta
= 0;
1635 pTs1
->tv_nsec
/= 1000;
1637 pTs2
->tv_nsec
/= 1000;
1639 delta
= pTs2
->tv_nsec
> pTs1
->tv_nsec
?
1641 (pTs2
->tv_sec
- pTs1
->tv_sec
) * 1000000 + (pTs2
->tv_nsec
- pTs1
->tv_nsec
) :
1643 (pTs2
->tv_sec
- pTs1
->tv_sec
- 1) * 1000000 + (1000000 - pTs1
->tv_nsec
+ pTs2
->tv_nsec
);
1650 static GstFlowReturn
gst_adecoder_send_data(GstADecoder
* adecoder
,GstBuffer
* buffer
)
1652 #ifdef TIMESTAMP_ENABLE
1654 if(adecoder
->isInPushMode
== TRUE
) //No timestamps in case of Pull mode / Standalone playback.
1657 if(adecoder
->frame_time
== 0 && adecoder
->initTimeStamp
!= 0)
1659 adecoder
->frame_time
= adecoder
->initTimeStamp
;
1663 adecoder
->frame_time
+= adecoder
->Status
->frameLen
* NANO_SEC_PER_SEC
/ adecoder
->Status
->sampleRate
;
1665 GST_BUFFER_TIMESTAMP(buffer
) = adecoder
->frame_time
;
1669 printf("Timestamp value:%llu\n",GST_BUFFER_TIMESTAMP(buffer
));
1676 return gst_pad_push(adecoder
->srcpad
, buffer
);
1679 static gboolean
gst_adecoder_sink_event(GstPad
* pad
, GstEvent
* event
)
1682 GstADecoder
*adecoder
= GST_ADECODER(GST_PAD_PARENT(pad
));
1684 gboolean ret
= TRUE
;
1688 printf("Got %s event on sink pad\n", GST_EVENT_TYPE_NAME(event
));
1692 switch (GST_EVENT_TYPE(event
))
1694 case GST_EVENT_NEWSEGMENT
:
1696 ret
= gst_pad_event_default(pad
, event
);
1700 case GST_EVENT_FLUSH_START
:
1702 ret
= gst_pad_event_default(pad
, event
);
1706 case GST_EVENT_FLUSH_STOP
:
1708 ret
= gst_pad_event_default(pad
, event
);
1714 gst_adecoder_decode_remaining(adecoder
);
1716 ret
= gst_pad_event_default(pad
, event
);
1722 ret
= gst_pad_event_default(pad
, event
);
1730 static void gst_adecoder_decode_remaining(GstADecoder
* adecoder
)
1733 while(adecoder
->bytes_not_decoded
> 10 && adecoder
->isStopped
== FALSE
)
1735 if(adecoder
->enable_processing
== FALSE
)
1737 pthread_mutex_lock(adecoder
->start_decode
);
1739 gst_adecoder_process_data(adecoder
);
1741 if(gst_adecoder_output_data(adecoder
) == FALSE
)
1749 printf("bytes_not_decoded:%d\n",adecoder
->bytes_not_decoded
);
1755 static gboolean
gst_adecoder_src_event(GstPad
* pad
, GstEvent
* event
)
1759 GstADecoder
*adecoder
;
1761 adecoder
= GST_ADECODER(GST_PAD_PARENT(pad
));
1763 if (adecoder
->codec_handle
== NULL
)
1767 res
= gst_pad_push_event(adecoder
->sinkpad
, event
);
1773 GST_DEBUG_OBJECT(adecoder
, "no decoder, cannot handle event");
1775 gst_event_unref(event
);
1781 static GstStateChangeReturn
gst_adecoder_change_state(GstElement
* element
, GstStateChange transition
)
1783 GstStateChangeReturn result
;
1785 GstADecoder
*adecoder
= GST_ADECODER(element
);
1789 case GST_STATE_CHANGE_NULL_TO_READY
:
1791 GST_DEBUG_OBJECT(adecoder
, "State Changed from NULL_TO_READY\n");
1796 case GST_STATE_CHANGE_READY_TO_PAUSED
:
1798 GST_DEBUG_OBJECT(adecoder
, "State Changed from READY_TO_PAUSED\n");
1802 case GST_STATE_CHANGE_PAUSED_TO_PLAYING
:
1804 adecoder
->isPaused
= FALSE
;
1813 result
= GST_ELEMENT_CLASS(parent_class
)->change_state(element
, transition
);
1817 case GST_STATE_CHANGE_PLAYING_TO_PAUSED
:
1819 adecoder
->isPaused
= TRUE
;
1823 printf("playing to paused\n");
1829 case GST_STATE_CHANGE_PAUSED_TO_READY
:
1831 adecoder
->isStopped
= TRUE
;
1835 printf("paused to ready\n");
1841 case GST_STATE_CHANGE_READY_TO_NULL
:
1845 printf("Ready to Null\n");
1849 free(adecoder
->DyParams
);
1851 free(adecoder
->Status
);
1853 free(adecoder
->InArgs
);
1855 free(adecoder
->OutArgs
);
1857 pthread_mutex_unlock(adecoder
->start_decode
);
1859 free(adecoder
->start_decode
);
1861 if (adecoder
->inbuf
!= NULL
)
1863 Memory_contigFree((XDAS_Int8
*) (adecoder
->inbuf_start_addr
),INPUT_BUFFER_SIZE
);
1865 if (adecoder
->outbuf
[0] != NULL
)
1867 Memory_contigFree((XDAS_Int8
*) (adecoder
->outbuf
[0]),adecoder
->outBufSize
[0]);
1869 if (adecoder
->outbuf
[1] != NULL
)
1871 Memory_contigFree((XDAS_Int8
*) (adecoder
->outbuf
[1]),adecoder
->outBufSize
[1]);
1873 AUDDEC_delete(adecoder
->codec_handle
);
1875 Engine_close(adecoder
->ce
);
1877 gst_adecoder_initialize_handle(adecoder
);