void A2dpStartKalimbaStreaming(const A2DP *a2dp, uint16 media_sink) { FILE_INDEX index = FILE_NONE; #ifdef BUILD_FOR_23FW Transform t; #else Transform t, l_t, r_t; Source l_src = StreamAudioSource(AUDIO_HARDWARE_CODEC, AUDIO_INSTANCE_0, AUDIO_CHANNEL_A); Source r_src = StreamAudioSource(AUDIO_HARDWARE_CODEC, AUDIO_INSTANCE_1, AUDIO_CHANNEL_B); Sink l_snk = StreamAudioSink(AUDIO_HARDWARE_CODEC, AUDIO_INSTANCE_0, AUDIO_CHANNEL_A); Sink r_snk = StreamAudioSink(AUDIO_HARDWARE_CODEC, AUDIO_INSTANCE_1, AUDIO_CHANNEL_B); #endif /* load SBC codec */ index = FileFind(FILE_ROOT, sbc_encoder, sizeof(sbc_encoder)-1); if (!KalimbaLoad(index)) /* codec load failure, Panic as the test isn't going to work now */ Panic(); /* Init and configure RTP */ t = TransformRtpSbcEncode(StreamKalimbaSource(0), (Sink)media_sink); TransformConfigure(t, VM_TRANSFORM_RTP_SBC_ENCODE_PACKET_SIZE, 668); TransformConfigure(t, VM_TRANSFORM_RTP_SBC_ENCODE_MANAGE_TIMING, FALSE); (void)TransformStart(t); /* Configure SBC encoding format */ (void)PanicFalse(KalimbaSendMessage(KALIMBA_MSG_SBCENC_SET_PARAMS, 0x00bd, 0, 0, 0)); (void)PanicFalse(KalimbaSendMessage(KALIMBA_MSG_SBCENC_SET_BITPOOL, 0x0030, 0, 0, 0)); #ifdef BUILD_FOR_23FW StreamDisconnect(StreamPcmSource(0), StreamPcmSink(0)); StreamDisconnect(StreamPcmSource(1), StreamPcmSink(1)); /* set up ADCs */ (void)PcmClearAllRouting(); (void)PanicFalse(PcmRateAndRoute(0, PCM_NO_SYNC, 44100, 44100, VM_PCM_INTERNAL_A)); (void)PanicFalse(PcmRateAndRoute(1, 0, 44100, 44100, VM_PCM_INTERNAL_B)); (void)PanicFalse(StreamConnect(StreamPcmSource(0),StreamKalimbaSink(0))); (void)PanicFalse(StreamConnect(StreamPcmSource(1),StreamKalimbaSink(1))); #else SourceClose(l_src); SourceClose(r_src); SinkClose(l_snk); SinkClose(r_snk); (void) SourceConfigure(l_src, STREAM_CODEC_INPUT_RATE, 44100); (void) SourceConfigure(r_src, STREAM_CODEC_INPUT_RATE, 44100); (void) SourceSynchronise(l_src, r_src); /* set up ADCs */ l_t = StreamConnect(l_src, StreamKalimbaSink(0)); r_t = StreamConnect(r_src, StreamKalimbaSink(1)); (void)TransformStart(l_t); (void)TransformStart(r_t); #endif /* Start decode */ (void) PanicFalse(KalimbaSendMessage(KALIMBA_MSG_GO,0,0,0,0)); }
/**************************************************************************** DESCRIPTION Plays back a voice prompt once DSP has loaded */ static Source csrVoicePresencesGetPrompt(voice_prompt* prompt, koovox_phrase_data_T * pData) { const uint8* rx_array; Source lSource = NULL; uint16 index; char file_name[17]; PRINT(("***check_the_source***\n")); if(!pData) return NULL; /* Must be a prompt, work out the index of the prompt */ index = pData->prompt_id; /* Adjust for language */ index += (pData->language * present_header.no_prompts_per_lang); PRINT(("***check prompt id***\n")); /* Sanity checking */ if(index >= present_header.no_prompts || !prompt ) return NULL; PRINT(("PRESENT: Play prompt %d of %d\n", index+1, present_header.no_prompts)); /* Get the header file name */ sprintf(file_name, "headers/%d.idx", index); lSource = StreamFileSource(FileFind(FILE_ROOT, file_name, strlen(file_name))); /* Check source created successfully */ if(SourceSize(lSource) < SIZE_PROMPT_DATA) { /* Finished with header source, close it */ SourceClose(lSource); return NULL; } /* Map in header */ rx_array = SourceMap(lSource); /* Pack data into result */ /* rx_array[0] not used*/ /* rx_array[1] index, not used */ prompt->stereo = rx_array[4]; prompt->size = ((uint32)rx_array[5] << 24) | ((uint32)rx_array[6] << 16) | ((uint16)rx_array[7] << 8) | (rx_array[8]); prompt->decompression = rx_array[9]; prompt->playback_rate = ((uint16)rx_array[10] << 8) | (rx_array[11]); /* The size of the prompt must be limited to 16 bits for I2C and SPI as the firmware traps only support a 16 bit size */ if (prompt->size > PRESENT_MAX_SIZE) { prompt->size = PRESENT_MAX_SIZE; PRINT(("Prompt size adjusted to 16 bit maximum\n")); } /* Get the prompt file name */ sprintf(file_name, "prompts/%d.prm", index); PRINT(("File Prompt: %s dec %X rate 0x%x stereo %u size 0x%lx \n", file_name, prompt->decompression,prompt->playback_rate,prompt->stereo,prompt->size)); /* Finished with header source, close it */ if(!SourceClose(lSource)) Panic(); return StreamFileSource(FileFind(FILE_ROOT, file_name, strlen(file_name))); }
/**************************************************************************** DESCRIPTION This function connects a synchronous audio stream to the pcm subsystem */ void CsrSbcEncoderPluginConnect( Sink audio_sink , Task codec_task , uint16 volume , uint32 rate , bool stereo , AUDIO_MODE_T mode , const void * params ) { /* DSP Application loading and Transform starting is handled by a call to A2dpAudioCodecEnable in the application, so should not be done here. */ const char sbc_encoder[] = "sbc_encoder/sbc_encoder.kap"; FILE_INDEX index = FILE_NONE; typedef struct { uint8 content_protection; uint32 voice_rate; unsigned bitpool:8; unsigned format:8; uint16 packet_size; uint16 clock_mismatch; } sbc_codec_data_type; sbc_codec_data_type *sbc_codecData = (sbc_codec_data_type *) params; if (!sbc_codecData) Panic(); index = FileFind(FILE_ROOT, sbc_encoder, sizeof(sbc_encoder)-1); if (index == FILE_NONE) Panic(); if (!KalimbaLoad(index)) Panic(); if (!KalimbaSendMessage(KALIMBA_CODEC_TYPE_MESSAGE, 0,0,0,0)) Panic(); CodecSetInputGainNow(codec_task,volume,left_and_right_ch); SBC = (SBC_t*)PanicUnlessMalloc (sizeof (SBC_t) ) ; SBC->media_sink[0] = audio_sink ; SBC->codec_task = codec_task ; SBC->packet_size = sbc_codecData->packet_size; StreamDisconnect(StreamKalimbaSource(2), 0); /* Initialise the RTP SBC encoder */ SBC->t[0] = TransformRtpSbcEncode(StreamKalimbaSource(2), audio_sink); /* Configure the RTP transform to generate the selected packet size */ TransformConfigure(SBC->t[0], VM_TRANSFORM_RTP_SBC_ENCODE_PACKET_SIZE, sbc_codecData->packet_size); /* Transform should not manage timings. */ TransformConfigure(SBC->t[0], VM_TRANSFORM_RTP_SBC_ENCODE_MANAGE_TIMING, FALSE); /* Start the transform */ (void) TransformStart(SBC->t[0]); PRINT(("Audio Plugin: TransformStart sink:0x%x\n",(uint16)audio_sink)); if (SBC->media_sink[1]) { /* There is a 2nd audio stream so initialise this transform */ StreamDisconnect(StreamKalimbaSource(3), 0); /* Initialise the RTP SBC encoder */ SBC->t[1] = TransformRtpSbcEncode(StreamKalimbaSource(3), SBC->media_sink[1]); /* Configure the RTP transform to generate the selected packet size */ TransformConfigure(SBC->t[1], VM_TRANSFORM_RTP_SBC_ENCODE_PACKET_SIZE, sbc_codecData->packet_size); /* Transform should not manage timings. */ TransformConfigure(SBC->t[1], VM_TRANSFORM_RTP_SBC_ENCODE_MANAGE_TIMING, FALSE); /* Start the transform */ (void) TransformStart(SBC->t[1]); PRINT(("Audio Plugin: TransformStart sink:0x%x\n",(uint16)SBC->media_sink[1])); } /* Configure SBC encoding format */ if (!KalimbaSendMessage(KALIMBA_MSG_SBCENC_SET_PARAMS, sbc_codecData->format, 0, 0, 0)) /* If message fails to get through, abort */ Panic(); /* Pass bit pool value to DSP */ if (!KalimbaSendMessage(KALIMBA_MSG_SBCENC_SET_BITPOOL, sbc_codecData->bitpool, 0, 0, 0)) /* If message fails to get through, abort */ Panic(); /* disard any data sent by the SNK */ StreamConnectDispose(StreamSourceFromSink(audio_sink)); if (SBC->media_sink[1]) { /* disard any data sent by the 2nd SNK */ StreamConnectDispose(StreamSourceFromSink(SBC->media_sink[1])); } /* select the source type */ { PRINT(("Audio Plugin: SourceAnalog\n")); /* For analogue input source */ StreamDisconnect(StreamPcmSource(0), StreamPcmSink(0)); StreamDisconnect(StreamPcmSource(1), StreamPcmSink(1)); (void)PcmClearAllRouting(); { PRINT(("Audio Plugin: codec_internal\n")); /* configure slot 0 and 1 to be left and right channel and synchronise the offsets for stereo playback */ (void)PcmRateAndRoute(0, PCM_NO_SYNC, (uint32) rate, (uint32) rate, VM_PCM_INTERNAL_A); (void)PcmRateAndRoute(1, 0, (uint32) rate, (uint32) rate, VM_PCM_INTERNAL_B); } /* plug Left ADC into port 0 */ (void)StreamConnect(StreamPcmSource(0),StreamKalimbaSink(0)); /* plug Right ADC into port 1 */ (void)StreamConnect(StreamPcmSource(1),StreamKalimbaSink(1)); /* Select the source type */ PanicFalse(KalimbaSendMessage(KALIMBA_ENCODER_SELECT, 0x0002, 0, 0, 0)); if(!KalimbaSendMessage(KALIMBA_MSG_GO,0,0,0,0)) { PRINT(("SBC: Message KALIMBA_MSG_GO failed!\n")); Panic(); } } /* Select the source type */ /*PanicFalse(KalimbaSendMessage(KALIMBA_SOURCE_SELECT, SOURCE_USB, 0, 0, 0)); */ /*CsrSbcEncoderUsbPluginSetVolume(volume) ;*/ /*(void) StreamConnect(PanicNull(StreamUsbEndPointSource(end_point_iso_in)), StreamKalimbaSink(0)); */ /* Start decode */ /* if(!KalimbaSendMessage(KALIMBA_MSG_GO,0,0,0,0)) { PRINT(("SBC: Message KALIMBA_MSG_GO failed!\n")); Panic(); } */ }
/**************************************************************************** DESCRIPTION This function connects a synchronous audio stream to the pcm subsystem */ void CsrA2dpDecoderPluginConnect( A2dpPluginTaskdata *task, Sink audio_sink , Task codec_task , uint16 volume , uint32 rate , bool stereo , AUDIO_MODE_T mode , const void * params , Task app_task ) { FILE_INDEX index = FILE_NONE; char* kap_file = NULL ; /* Only need to read the PS Key value once */ if (!pskey_read) { if (PsFullRetrieve(PSKEY_MAX_CLOCK_MISMATCH, &val_pskey_max_mismatch, sizeof(uint16)) == 0) val_pskey_max_mismatch = 0; pskey_read = TRUE; } switch ((A2DP_DECODER_PLUGIN_TYPE_T)task->a2dp_plugin_variant) { case SBC_DECODER: kap_file = "sbc_decoder/sbc_decoder.kap"; break; case MP3_DECODER: kap_file = "mp3_decoder/mp3_decoder.kap"; break; case AAC_DECODER: kap_file = "aac_decoder/aac_decoder.kap"; break; case FASTSTREAM_SINK: kap_file = "faststream_sink/faststream_sink.kap"; break; default: Panic(); break; } /*ensure that the messages received are from the correct kap file*/ (void) MessageCancelAll( (TaskData*) task, MESSAGE_FROM_KALIMBA); MessageKalimbaTask( (TaskData*) task ); index = FileFind(FILE_ROOT,(const char *) kap_file ,strlen(kap_file)); if (index == FILE_NONE) Panic(); if (!KalimbaLoad(index)) Panic(); DECODER = (DECODER_t*)PanicUnlessMalloc (sizeof (DECODER_t) ) ; DECODER->media_sink = audio_sink ; DECODER->codec_task = codec_task ; DECODER->volume = volume; DECODER->mode = mode; DECODER->stereo = stereo; DECODER->params = (uint16) params; DECODER->rate = rate; DECODER->app_task = app_task; if ((A2DP_DECODER_PLUGIN_TYPE_T)task->a2dp_plugin_variant == AAC_DECODER) { /* Workaround for AAC+ sources that negotiate sampling frequency at half the actual value */ if (rate < 32000) DECODER->rate = rate * 2; } CodecSetOutputGainNow(DECODER->codec_task, 0, left_and_right_ch); StreamDisconnect(StreamPcmSource(0), StreamPcmSink(0)); StreamDisconnect(StreamPcmSource(1), StreamPcmSink(1)); PanicFalse(PcmClearRouting(0)); PanicFalse(PcmClearRouting(1)); /* For sinks disconnect the source in case its currently being disposed. */ StreamDisconnect(StreamSourceFromSink(audio_sink), 0); PRINT(("DECODER: CsrA2dpDecoderPluginConnect completed\n")); }