海思平台播放AAC音频
来源:互联网 发布:知乎 蓝洞 韩国 编辑:程序博客网 时间:2024/05/16 04:47
利用海思sdk的sample修改了一个播AAC的小程序
代码
主程序voice_player.c:
/****************************************************************************** A simple program of Hisilicon HI3516 audio input/output/encoder/decoder implementation. Copyright (C), 2010-2011, Hisilicon Tech. Co., Ltd. ****************************************************************************** Modification: 2011-2 Created******************************************************************************/#include <stdlib.h>#include <stdio.h>#include <string.h>#include <unistd.h>#include <sys/types.h>#include <sys/stat.h>#include <sys/ioctl.h>#include <fcntl.h>#include <pthread.h>#include <errno.h>#include <signal.h>//#include "hi_comm_vb.h"#include "audio_aac_adp.h"#define TEST_AIO_ID 0#define AIO_WORK_MODE AIO_MODE_I2S_MASTERstatic PAYLOAD_TYPE_E gs_enPayloadType = PT_AAC;static AAC_TYPE_E gs_enAacType = AAC_TYPE_AACLC;static AAC_BPS_E gs_enAacBps = AAC_BPS_24K;static HI_BOOL gs_bUserGetMode = HI_FALSE;//static HI_BOOL gs_bMicIn = HI_FALSE;//static HI_U32 g_InnerCodecInput = 1; /*0-micin 1-linein 2-micind 3-lineind*///static HI_U32 g_InnerCodecOutput = 0; /*0-lineout 1-leftd 2-rightd*/#define SAMPLE_DBG(s32Ret)\do{\ printf("s32Ret=%#x,fuc:%s,line:%d\n", s32Ret, __FUNCTION__, __LINE__);\}while(0)/******************************************************************************* function : PT Number to String******************************************************************************/static char* SAMPLE_AUDIO_Pt2Str(PAYLOAD_TYPE_E enType){ if (PT_AAC == enType) return "aac"; else return "data";}/******************************************************************************* function : Open Aenc File******************************************************************************/static FILE * SAMPLE_AUDIO_OpenAencFile(AENC_CHN AeChn, PAYLOAD_TYPE_E enType){ FILE *pfd; HI_CHAR aszFileName[128]; /* create file for save stream*/ snprintf(aszFileName, sizeof(aszFileName), "audio_chn%d.%s", AeChn, SAMPLE_AUDIO_Pt2Str(enType)); pfd = fopen(aszFileName, "w+"); if (NULL == pfd) { printf("%s: open file %s failed\n", __FUNCTION__, aszFileName); return NULL; } printf("open stream file:\"%s\" for aenc ok\n", aszFileName); return pfd;}/******************************************************************************* function : Open Adec File******************************************************************************/static FILE *SAMPLE_AUDIO_OpenAdecFile(char *filename){ FILE *pfd; pfd = fopen(filename, "rb"); if (NULL == pfd) { printf("%s: open file %s failed\n", __FUNCTION__, filename); return NULL; } printf("open stream file:\"%s\" for adec ok\n", filename); return pfd;}/******************************************************************************* function : Start Aenc******************************************************************************/HI_S32 SAMPLE_AUDIO_StartAenc(HI_S32 s32AencChnCnt, AIO_ATTR_S *pstAioAttr, PAYLOAD_TYPE_E enType){ AENC_CHN AeChn; HI_S32 s32Ret, i; AENC_CHN_ATTR_S stAencAttr; AENC_ATTR_AAC_S stAencAac; /* set AENC chn attr */ stAencAttr.enType = enType; stAencAttr.u32BufSize = 30;stAencAttr.u32PtNumPerFrm = pstAioAttr->u32PtNumPerFrm; if (PT_AAC == stAencAttr.enType) { stAencAttr.pValue = &stAencAac; stAencAac.enAACType = gs_enAacType; stAencAac.enBitRate = gs_enAacBps; stAencAac.enBitWidth = AUDIO_BIT_WIDTH_16; stAencAac.enSmpRate = pstAioAttr->enSamplerate; stAencAac.enSoundMode = pstAioAttr->enSoundmode; stAencAac.enTransType = AAC_TRANS_TYPE_ADTS; stAencAac.s16BandWidth = 0; } else { printf("%s: invalid aenc payload type:%d\n", __FUNCTION__, stAencAttr.enType); return HI_FAILURE; } for (i=0; i<s32AencChnCnt; i++) { AeChn = i; /* create aenc chn*/ s32Ret = HI_MPI_AENC_CreateChn(AeChn, &stAencAttr); if (s32Ret != HI_SUCCESS) { printf("%s: HI_MPI_AENC_CreateChn(%d) failed with %#x!\n", __FUNCTION__, AeChn, s32Ret); return HI_FAILURE; } } return HI_SUCCESS;}/******************************************************************************* function : Start Adec******************************************************************************/HI_S32 SAMPLE_AUDIO_StartAdec(ADEC_CHN AdChn, PAYLOAD_TYPE_E enType){ HI_S32 s32Ret; ADEC_CHN_ATTR_S stAdecAttr; ADEC_ATTR_AAC_S stAdecAac; stAdecAttr.enType = enType; stAdecAttr.u32BufSize = 20; stAdecAttr.enMode = ADEC_MODE_STREAM;/* propose use pack mode in your app */if (PT_AAC == stAdecAttr.enType) { stAdecAttr.pValue = &stAdecAac; stAdecAttr.enMode = ADEC_MODE_STREAM; /* aac should be stream mode */ stAdecAac.enTransType = AAC_TRANS_TYPE_ADTS; } else { printf("%s: invalid aenc payload type:%d\n", __FUNCTION__, stAdecAttr.enType); return HI_FAILURE; } /* create adec chn*/ s32Ret = HI_MPI_ADEC_CreateChn(AdChn, &stAdecAttr); if (s32Ret) { printf("%s: HI_MPI_ADEC_CreateChn(%d) failed with %#x!\n", __FUNCTION__,\ AdChn,s32Ret); return s32Ret; } return 0;}/******************************************************************************* function : file -> ADec -> Ao******************************************************************************/HI_S32 SAMPLE_AUDIO_AdecAo(char *filename, AIO_ATTR_S *pstAioAttr){ HI_S32 s32Ret;#ifdef AO_DEV AUDIO_DEV AoDev = AO_DEV;#elseAUDIO_DEV AoDev = TEST_AIO_ID;#endif AO_CHN AoChn = 0; ADEC_CHN AdChn = 0;HI_S32 s32AoChnCnt; FILE *pfd = NULL; if (NULL == pstAioAttr) { printf("%s: input piont is invalid!\n", __FUNCTION__); return HI_FAILURE; } s32Ret = SAMPLE_COMM_AUDIO_CfgAcodec(pstAioAttr); if (HI_SUCCESS != s32Ret) { SAMPLE_DBG(s32Ret); goto ADECAO_ERR3; } s32Ret = SAMPLE_AUDIO_StartAdec(AdChn, gs_enPayloadType); if (s32Ret != HI_SUCCESS) { SAMPLE_DBG(s32Ret); goto ADECAO_ERR3; }s32AoChnCnt = pstAioAttr->u32ChnCnt; s32Ret = SAMPLE_COMM_AUDIO_StartAo(AoDev, s32AoChnCnt, pstAioAttr, AUDIO_SAMPLE_RATE_BUTT, HI_FALSE, NULL, 0); if (s32Ret != HI_SUCCESS) { SAMPLE_DBG(s32Ret); goto ADECAO_ERR2; } s32Ret = SAMPLE_COMM_AUDIO_AoBindAdec(AoDev, AoChn, AdChn); if (s32Ret != HI_SUCCESS) { SAMPLE_DBG(s32Ret); goto ADECAO_ERR1; } pfd = SAMPLE_AUDIO_OpenAdecFile(filename); if (!pfd) { SAMPLE_DBG(HI_FAILURE); goto ADECAO_ERR0; } s32Ret = SAMPLE_COMM_AUDIO_CreatTrdFileAdec(AdChn, pfd); if (s32Ret != HI_SUCCESS) { SAMPLE_DBG(s32Ret); goto ADECAO_ERR0; } printf("bind adec:%d to ao(%d,%d) ok \n", AdChn, AoDev, AoChn); //SAMPLE_COMM_AUDIO_DestoryTrdFileAdec(AdChn);ADECAO_ERR0: s32Ret |= SAMPLE_COMM_AUDIO_AoUnbindAdec(AoDev, AoChn, AdChn);ADECAO_ERR1: s32Ret |= SAMPLE_COMM_AUDIO_StopAo(AoDev, s32AoChnCnt, HI_FALSE, HI_FALSE);ADECAO_ERR2: s32Ret |= SAMPLE_COMM_AUDIO_StopAdec(AdChn);ADECAO_ERR3: return s32Ret;}/******************************************************************************* function : to process abnormal case******************************************************************************/void SAMPLE_AUDIO_HandleSig(HI_S32 signo){ if (SIGINT == signo || SIGTSTP == signo) { SAMPLE_COMM_AUDIO_DestoryAllTrd(); SAMPLE_COMM_SYS_Exit(); printf("\033[0;31mprogram exit abnormally!\033[0;39m\n"); } exit(0);}/******************************************************************************* function : main******************************************************************************/HI_S32 main(int argc, char *argv[]){ char ch; HI_S32 s32Ret= HI_SUCCESS; AIO_ATTR_S stAioAttr; /* init stAio. all of cases will use it */ memset(&stAioAttr, 0, sizeof(AIO_ATTR_S)); stAioAttr.enBitwidth = AUDIO_BIT_WIDTH_16; stAioAttr.enWorkmode = AIO_WORK_MODE; stAioAttr.enSoundmode = AUDIO_SOUND_MODE_MONO; stAioAttr.u32EXFlag = 0; stAioAttr.u32FrmNum = 30; stAioAttr.u32ChnCnt = 1; #ifdef HI_ACODEC_TYPE_TLV320AIC31 stAioAttr.u32ClkSel = 1; #else stAioAttr.u32ClkSel = 0; #endifstAioAttr.enSamplerate = AUDIO_SAMPLE_RATE_8000;stAioAttr.u32PtNumPerFrm = (AAC_TYPE_AACLC == gs_enAacType) ? 1024 : 2048; //signal(SIGINT, SAMPLE_AUDIO_HandleSig); //signal(SIGTERM, SAMPLE_AUDIO_HandleSig); s32Ret = SAMPLE_COMM_SYS_Init(); if (HI_SUCCESS != s32Ret) { printf("%s: system init failed with %d!\n", __FUNCTION__, s32Ret); return HI_FAILURE; } /* register aac encoder and decoder */ HI_MPI_ADEC_AacInit(); s32Ret = SAMPLE_AUDIO_AdecAo(argv[1],&stAioAttr);/* read audio stream from file,decode and send AO*/ if (s32Ret != HI_SUCCESS) { } SAMPLE_COMM_SYS_Exit(); return HI_SUCCESS;}什么标注了几个关键的点。
sample_comm_audio.c部分代码:
/******************************************************************************* function : Create the thread to get stream from file and send to adec******************************************************************************/HI_S32 SAMPLE_COMM_AUDIO_CreatTrdFileAdec(ADEC_CHN AdChn, FILE *pAdcFd){ SAMPLE_ADEC_S *pstAdec = NULL; if (NULL == pAdcFd) { return HI_FAILURE; } pstAdec = &gs_stSampleAdec[AdChn]; pstAdec->AdChn = AdChn; pstAdec->pfd = pAdcFd; pstAdec->bStart = HI_TRUE; //pthread_create(&pstAdec->stAdPid, 0, SAMPLE_COMM_AUDIO_AdecProc, pstAdec); SAMPLE_COMM_AUDIO_AdecProc(pstAdec); return HI_SUCCESS;}
/******************************************************************************* function : get stream from file, and send it to Adec******************************************************************************/void *SAMPLE_COMM_AUDIO_AdecProc(SAMPLE_ADEC_S *pstAdec){ HI_S32 s32Ret; AUDIO_STREAM_S stAudioStream; HI_U32 u32Len = 2048; HI_U32 u32ReadLen; HI_S32 s32AdecChn; HI_U8 *pu8AudioStream = NULL; SAMPLE_ADEC_S *pstAdecCtl = (SAMPLE_ADEC_S *)pstAdec; AO_CHN_STATE_S pstStatus; FILE *pfd = pstAdecCtl->pfd; s32AdecChn = pstAdecCtl->AdChn; pu8AudioStream = (HI_U8*)malloc(sizeof(HI_U8)*MAX_AUDIO_STREAM_LEN); if (NULL == pu8AudioStream) { printf("%s: malloc failed!\n", __FUNCTION__); return NULL; } while (HI_TRUE == pstAdecCtl->bStart) { /* read from file */ stAudioStream.pStream = pu8AudioStream; u32ReadLen = fread(stAudioStream.pStream, 1, u32Len, pfd); if (u32ReadLen <= 0) { /* s32Ret = HI_MPI_ADEC_SendEndOfStream(s32AdecChn, HI_FALSE); if (HI_SUCCESS != s32Ret) { printf("%s: HI_MPI_ADEC_SendEndOfStream failed!\n", __FUNCTION__); } fseek(pfd, 0, SEEK_SET); */ printf("u32ReadLen <= 0 break! s32Ret:%d \n",s32Ret); break; } /* here only demo adec streaming sending mode, but pack sending mode is commended */ stAudioStream.u32Len = u32ReadLen; s32Ret = HI_MPI_ADEC_SendStream(s32AdecChn, &stAudioStream, HI_TRUE); if(HI_SUCCESS != s32Ret) { printf("%s: HI_MPI_ADEC_SendStream(%d) failed with %#x!\n",\ __FUNCTION__, s32AdecChn, s32Ret); //break; } usleep(1000*10); } while (HI_TRUE == pstAdecCtl->bStart) { s32Ret = HI_MPI_AO_QueryChnStat(0, 0,&pstStatus); //printf("pstStatus.u32ChnBusyNum: %d\n",pstStatus.u32ChnBusyNum); if(pstStatus.u32ChnBusyNum < 1) { s32Ret = HI_MPI_ADEC_SendEndOfStream(s32AdecChn, HI_FALSE); if (HI_SUCCESS != s32Ret) { printf("%s: HI_MPI_ADEC_SendEndOfStream failed!\n", __FUNCTION__); } break; } sleep(1); } free(pu8AudioStream); pu8AudioStream = NULL; fclose(pfd); pstAdecCtl->bStart = HI_FALSE; return NULL;}注意播放时要查询AO 通道中当前的音频数据缓存状态,等到缓存为空时再停止播放,不然只能播一部分,不能播完。
编译
上makefile
include config.mkLOCAL_SRC_CFILES := \voice_player.c \src/audio_aac_adp.c \src/sample_comm_audio.c \src/sample_comm_sys.cLOCAL_MODULE := voice_playerLOCAL_CFLAGS := -D__LINUX__PREFIX := arm-hisiv300-linux-LOCAL_SHARED_LIBRARIES := pthread \LOCAL_C_INCLUDES :=./include \./ \LOCAL_LDFLAGS := lib/libaacdec.so \ lib/libmpi.so \ lib/libisp.so \ lib/libive.so\ lib/libVoiceEngine.so \ lib/libupvqe.so \ lib/libdnvqe.so \ lib/lib_hidefog.so \ lib/libaacenc.so \include exec_rules.mk只看makefile的话应该就能看出我的目录结构吧!
水一波@_@~
阅读全文
0 0
- 海思平台播放AAC音频
- suse amarok播放aac音频
- 用QMediaPlayerControl播放AAC格式音频
- [推荐] 基于ARM平台优化的 AAC, HE-AAC, HE-AAC V2 音频编码器解码器
- AAC 音频
- AAC 音频
- AAC 音频
- android aac文件格式音频的录制和播放
- 基于Windows平台的AAC音频编码器和解码器
- 【hi3516a 调试笔记】 海思hi3516a平台音频aac编码测试
- Android MediaCodec硬解码AAC音频文件(实时AAC音频帧)并播放
- Android MediaCodec硬解码AAC音频文件(实时AAC音频帧)并播放
- 多平台下音频原始播放接口
- AAC音频编码格式
- AAC音频编码规格
- android AAC音频编码
- AAC音频介绍
- IOS录制AAC音频
- eclipse部署maven web项目到tomcat服务器时,没有将lib、web.xml复制过去的解决办法
- 平常的资源图转Bitmap(太大的资源图不能用这个转)
- 关于儿时的记忆
- 正则表达式 在安卓editText的用法
- jq+css
- 海思平台播放AAC音频
- 八数码 HDU
- 安装python爬虫scrapy踩过的那些坑和编程外的思考
- 备份下ionic升级
- Use of @OneToMany or @ManyToMany targeting an unmapped class
- jenkins跑在docker
- Codeforces Round #440 (Div. 2, based on Technocup 2018 Elimination) A. Search for Pretty Integers
- thinkphp phpmailer发送邮件
- android模块化