⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 play_audio.c

📁 Sample code for use on smp 863x processor.
💻 C
📖 第 1 页 / 共 5 页
字号:
	SampleClock = 48000;	f.PLL = PLLGen_cd_6;	f.PLLOutput = PLLOut_1; // or _1 or _2	f.MaxM = 31;	f.Clock = ClockSignal_RClk2;	f.Frequency = SampleClock * 256;	RUASetProperty(dcc_info->pRUA, PLL, RMPLLPropertyID_Frequency, &f, sizeof(f), 0);	//printf("finish set RCLK2...\n");}#endif	// Query Memory needed for AudioCapture Module	dram_in.SerialInFIFOSize = AUDIO_FIFO_SIZE; 	dram_in.XferFIFOCount = XFER_FIFO_COUNT; 	err = RUAExchangeProperty(dcc_info->pRUA, audio_capture, RMAudioCapturePropertyID_DRAMSize, &dram_in, sizeof(dram_in), &dram_out, sizeof(dram_out));	if (RMFAILED(err)) {		RMDBGLOG((ENABLE, "No memory available for Audio RISC Processor! %s\n", RMstatusToString(err)));		return err;	} 	// construct open profile	memset(&capture_open, 0, sizeof(struct AudioCapture_Open_type));	capture_open.CaptureMode = capture_mode;	capture_open.Delay = ((audio_opt->CaptureDelay) ? audio_opt->CaptureDelay : 1824) / 2; // Delay is 45000 Hz based start PTS	if (audio_opt->CaptureSource == 0) {		// Capture from I2S, 32 bit frames		//capture_open.SI_CONF = 0x109;  // 16 bit I2S frames		capture_open.SI_CONF = 0x107 |  // SerialIn Configuration, 32 bit frames			(audio_opt->AudioInAlign << 3) | 			(audio_opt->AudioInLSBfirst ? 0x200 : 0x000);		capture_source = AudioCapture_Source_I2S;	} else {		// Capture from SPDIF, always 16 bit frames		if (audio_opt->CaptureSource == 1) {#if (EM86XX_CHIP >= EM86XX_CHIPID_TANGO15)  // in 8622/24 Tango 1.5 and 8634 Tango 2 spdif is dedicated line, use it with source=1			capture_open.SI_CONF = 0x900;  // capture from SI_SPDIF		} else if (audio_opt->CaptureSource == 2) {#endif			capture_open.SI_CONF = 0x100;  // capture from SI_DATA		} else {			fprintf(stderr, "Error, wrong audio source: %lu\n", audio_opt->CaptureSource);			return RM_ERROR;		}		capture_source = AudioCapture_Source_SPDIF;	}		capture_open.SI_CONF |= 0x80000000;  // extended info in unused bits of SI_CONF	if ((audio_opt->CaptureSource == 0) && (audio_opt->Codec == AudioDecoder_Codec_PCM)) {		RMuint32 BitsPerSample;		switch (audio_opt->SubCodec) {			default: BitsPerSample = audio_opt->PcmCdaParams.BitsPerSample; break;			case 1: BitsPerSample = audio_opt->LpcmVobParams.BitsPerSample; break;			case 2: BitsPerSample = audio_opt->LpcmAobParams.BitsPerSampleGroup1; break;			case 3: BitsPerSample = audio_opt->PcmCdaParams.BitsPerSample; break;		}		if (BitsPerSample >= 24) {			capture_open.SI_CONF |= 0x40000000;  // don't truncate 24 bit PCM samples to 16 bits		}	}		// allocate memory only when it is file mode	if(!capture_mode){		// memory allocation for capture module		capture_open.SerialInFIFOSize = dram_in.SerialInFIFOSize;		capture_open.XferFIFOCount = dram_in.XferFIFOCount;				// allocate cached memory		capture_open.CachedSize = dram_out.CachedSize;		if (capture_open.CachedSize > 0){			capture_open.CachedAddress = RUAMalloc(dcc_info->pRUA, 0, RUA_DRAM_CACHED, capture_open.CachedSize);			printf("audio capture cached addr: 0x%08lX, size 0x%08lX, end: 0x%08lX\n",			       capture_open.CachedAddress,			       capture_open.CachedSize,			       capture_open.CachedAddress + capture_open.CachedSize);			p_context->capture_cached_addr = (RMuint32)capture_open.CachedAddress;		}		else { capture_open.CachedAddress = 0; }				// allocate uncached memory		capture_open.UncachedSize = dram_out.UncachedSize;		if (capture_open.UncachedSize > 0){			capture_open.UncachedAddress = RUAMalloc(dcc_info->pRUA, 0, RUA_DRAM_UNCACHED, capture_open.UncachedSize);			printf("audio capture uncached addr: 0x%08lX, size 0x%08lX, end: 0x%08lX\n",			       capture_open.UncachedAddress,			       capture_open.UncachedSize,			       capture_open.UncachedAddress + capture_open.UncachedSize);			p_context->capture_uncached_addr = capture_open.UncachedAddress;		}		else { capture_open.UncachedAddress = 0; }	}	err = RUASetProperty(dcc_info->pRUA, audio_capture, 		RMAudioCapturePropertyID_Open, 		&capture_open, sizeof(capture_open), 0);	if (RMFAILED(err)) {		fprintf(stderr, "Error opening audio capture module!\n");		return err;	}		err = RUASetProperty(dcc_info->pRUA, audio_capture, 		RMAudioCapturePropertyID_Source, 		&capture_source, sizeof(capture_source), 0);	if (RMFAILED(err)) {		fprintf(stderr, "Error setting audio capture source!.\n");		return err;	}		capture_type = audio_opt->CaptureType;	err = RUASetProperty(dcc_info->pRUA, audio_capture, 		RMAudioCapturePropertyID_SpdifDataType, 		&capture_type, sizeof(capture_type), 0);	if (RMFAILED(err)) {		fprintf(stderr, "Error setting audio capture type!.\n");		return err;	}		err = RUASetProperty(dcc_info->pRUA, audio_capture,		RMAudioCapturePropertyID_Capture, 		&cmd, sizeof(cmd), 0);	if (RMFAILED(err)) 		fprintf(stderr, "Error sending capture ON command.\n");	// open buffer pool only when file capture mode	if(!capture_mode){		err = RUAOpenPool(dcc_info->pRUA, 				  audio_capture, 				  p_context->play_opt->dmapool_count, 				  p_context->play_opt->dmapool_log2size, 				  RUA_POOL_DIRECTION_RECEIVE, 				  &(p_context->pDMA));		if (RMFAILED(err)){			RMDBGLOG((ENABLE, "Error while creating DMA Pool for receiving! %s\n", RMstatusToString(err)));		}	}		return err;}static RMstatus StopAudioCapture(struct dcc_context *dcc_info, RMuint32 audio_capture, struct audio_context* p_context){	enum AudioCapture_Capture_type cmd = AudioCapture_Capture_Off;	RMuint32 temp = 0;	RMstatus err;	err = RUASetProperty(dcc_info->pRUA, audio_capture,			     RMAudioCapturePropertyID_Capture, &cmd, sizeof(cmd), 0);	if (RMFAILED(err)) 		fprintf(stderr, "Error sending capture OFF command.\n");	err = RUASetProperty(dcc_info->pRUA, audio_capture, RMAudioCapturePropertyID_Close, 			     &temp, sizeof(temp), 0);	if (RMFAILED(err)) {		fprintf(stderr, "Error closing capture module!\n");		return err;	}	if(p_context->capture_cached_addr){		RUAFree(dcc_info->pRUA, p_context->capture_cached_addr);		p_context->capture_cached_addr = 0;	}		if(p_context->capture_uncached_addr){		RUAFree(dcc_info->pRUA, p_context->capture_uncached_addr);		p_context->capture_uncached_addr = 0;	}	if(p_context->fp_capture){		fclose(p_context->fp_capture);		p_context->fp_capture = NULL;	}	return err;}static RMstatus Stop(struct audio_context *pSendContext, RMuint32 devices){	RMstatus err = RM_OK;	if (devices & RM_DEVICES_STC) {		RMDBGLOG((ENABLE, "STOP: stc\n"));		DCCSTCStop(pSendContext->dcc_info->pStcSource);	}	if (devices & RM_DEVICES_AUDIO) {		if (pSendContext->dcc_info->pMultipleAudioSource) {			if (pSendContext->play_opt->disk_ctrl_state != DISK_CONTROL_STATE_DISABLE) {				while (pSendContext->dmabuffer_index > 0) {					pSendContext->dmabuffer_index--;					if (pSendContext->dmabuffer_array[pSendContext->dmabuffer_index]) {						RMDBGLOG((ENABLE, "releasing buffer index %lu buffer %p\n", pSendContext->dmabuffer_index, pSendContext->dmabuffer_array[pSendContext->dmabuffer_index]));						RUAReleaseBuffer(pSendContext->pDMA, pSendContext->dmabuffer_array[pSendContext->dmabuffer_index]);					}				}			}			RMDBGLOG((ENABLE, "STOP: multiple audio decoders\n"));			err = DCCStopMultipleAudioSource(pSendContext->dcc_info->pMultipleAudioSource);			if (RMFAILED(err)){				RMDBGLOG((ENABLE, "Error stopping audio source %d\n", err));				return err;			}			pSendContext->audio_decoder_initialized = FALSE;			pSendContext->FirstSystemTimeStamp = TRUE;			pSendContext->FirstPTS = 0;			/* because DMAPool and BitstreamFIFO are the same in standalone when using elementary streams			   we need to reset the pool */			err = RUAResetPool(pSendContext->pDMA);	// needed for no dram copy version on standalone			if (RMFAILED(err)) {				RMDBGLOG((ENABLE, "Error cannot reset dmapool\n"));				return err;			}		}	}	return err;}static RMstatus Play(struct audio_context * pSendContext, RMuint32 devices){	RMstatus err = RM_OK;	if (devices & RM_DEVICES_STC) {		RMDBGLOG((ENABLE, "PLAY: stc\n"));		DCCSTCPlay(pSendContext->dcc_info->pStcSource);	}	if (devices & RM_DEVICES_AUDIO) {		if (pSendContext->dcc_info->pMultipleAudioSource) {			if (!pSendContext->audio_decoder_initialized) {						pSendContext->audio_decoder_initialized = TRUE;			}			RMDBGLOG((ENABLE, "PLAY: multiple audio decoders\n"));			err = DCCPlayMultipleAudioSource(pSendContext->dcc_info->pMultipleAudioSource);			if (RMFAILED(err)) {				RMDBGLOG((ENABLE, "Cannot play audio decoder %d\n", err));				return err;			}		}	}	return err;}// used for prebufferingstatic RMstatus Pause(struct audio_context * pSendContext, RMuint32 devices){	RMstatus err = RM_OK;		if (devices & RM_DEVICES_STC) {		RMDBGLOG((ENABLE, "PAUSE: stc\n"));		DCCSTCStop(pSendContext->dcc_info->pStcSource);	}	if (devices & RM_DEVICES_AUDIO) {		if (pSendContext->dcc_info->pMultipleAudioSource) {			RMDBGLOG((ENABLE, "PAUSE: multiple audio decoders\n"));			err = DCCPauseMultipleAudioSource(pSendContext->dcc_info->pMultipleAudioSource);			if (RMFAILED(err)) {				RMDBGLOG((ENABLE, "Cannot play audio decoder %d\n", err));				return err;			}		}	}	return err;}static RMstatus seek(struct audio_context *pSendContext, RMuint32 time_sec){	RMuint64 bytesSec = pSendContext->fileSize / pSendContext->Duration;	RMuint32 timeSec = 0;	RMuint64 seekPos;	RMuint32 audioPTS;	RMstatus err;	struct DCCAudioSourceHandle audioHandle;	timeSec = time_sec;			seekPos = timeSec * bytesSec;	RMDBGLOG((ENABLE, "seek to %lu s\n", timeSec));	// we assume multiple decoders are in sync	DCCMultipleAudioSourceGetSingleDecoderHandleForInstance(pSendContext->dcc_info->pMultipleAudioSource, 0, &audioHandle);	err = RUAGetProperty(pSendContext->dcc_info->pRUA, audioHandle.moduleID, RMAudioDecoderPropertyID_CurrentPTS, &audioPTS, sizeof(audioPTS));	if (err != RM_OK) {		RMDBGLOG((ENABLE, "error getting current pts property for audio, error %lu\n", (RMuint32)err));		return RM_ERROR;	}	RMDBGLOG((ENABLE, "current audio pts %lu(0x%08lx)\n", audioPTS, audioPTS));	Stop(pSendContext, RM_DEVICES_AUDIO);	RMDBGLOG((ENABLE, ">> %llu bytes/sec, seekto %lu sec => pos %llu\n", bytesSec, timeSec, seekPos));	// pcm should start at the correct sample position	if (pSendContext->audio_opt[0].Codec == AudioDecoder_Codec_PCM) {				seekPos -= seekPos % pSendContext->PCMblockSize;				RMDBGLOG((ENABLE, "PCM audio blockSize %lu, new seekPos %lld\n", pSendContext->PCMblockSize, seekPos));	}	if (pSendContext->skipFirstNBytes) {		RMDBGLOG((ENABLE, "adjust seek pos due to skipping of %lu bytes\n", pSendContext->skipFirstNBytes));		seekPos += pSendContext->skipFirstNBytes;	}		RMSeekFile(pSendContext->f_bitstream, seekPos, RM_FILE_SEEK_START);	DCCSTCSetTime(pSendContext->dcc_info->pStcSource, timeSec*pSendContext->audio_vop_tir, pSendContext->audio_vop_tir);	pSendContext->FirstSystemTimeStamp = TRUE;	pSendContext->FirstPTS = timeSec*pSendContext->audio_vop_tir;	Play(pSendContext, RM_DEVICES_AUDIO);	RM_PSM_SetState(pSendContext->PSMcontext, &(pSendContext->dcc_info), RM_PSM_Playing);	return RM_OK;}static RMstatus resumeFromTrick(struct audio_context *pSendContext){	RMuint64 stc;	RMuint32 timeSec;		DCCSTCGetTime(pSendContext->dcc_info->pStcSource, &stc, pSendContext->audio_vop_tir);				RMDBGLOG((ENABLE, "resume from trick at %llu s\n", stc/pSendContext->audio_vop_tir));	timeSec = (RMuint32) (stc / pSendContext->audio_vop_tir);       	seek(pSendContext, timeSec);		return RM_OK;}static void check_prebuf_state(struct audio_context *pSendContext, RMuint32 buffersize){	RMbool quit_prebuf;	enum RM_PSM_State PlaybackStatus = RM_PSM_GetState(pSendContext->PSMcontext, &(pSendContext->dcc_info));		if (PlaybackStatus != RM_PSM_Prebuffering)		return;	/* if fail in getbuffer/senddata force quitting prebuffering state */	quit_prebuf = ((buffersize == 0) || ((pSendContext->play_opt->prebuf_max > 0) && (pSendContext->prebufferedBytes >= pSendContext->play_opt->prebuf_max))) ? TRUE : FALSE;	pSendContext->prebufferedBytes += buffersize;			if (quit_prebuf) {		RMDBGLOG((ENABLE, "exit prebuffering state, enter play state (bufsize %lu, prebuffered %lu)\n", buffersize, pSendContext->prebufferedBytes));		fprintf(stderr, "now playing\n");		RM_PSM_SetState(pSendContext->PSMcontext, &(pSendContext->dcc_info), RM_PSM_Playing);		Play(pSendContext, RM_DEVICES_STC | RM_DEVICES_AUDIO);		pSendContext->prebufferedBytes = 0;	}}#ifdef WITH_MONOint main_audio(struct mono_info *mono){#elseint main(int argc, char *argv[]){	/*for MONO compatibility, always access these variables through the global pointers*/	struct playback_cmdline playback_options; /*access through play_opt*/	struct audio_cmdline audio_options[MAX_AUDIO_DECODER_INSTANCES]; /*access through audio_opt*/	struct dh_context dh_info = {0,};#endif	RMstatus err = RM_ERROR;	RMfile file = NULL; // Error code for open	struct dcc_context dcc_info = {0,};	RMuint32 file_offset = 0;	RMuint32 audio_capture;	struct audio_context context = {0,};	struct RM_PSM_Context PSMContext;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -