00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046 #include <sys/atom.h>
00047 #include <sys/event.h>
00048 #include <sys/timer.h>
00049 #include <sys/heap.h>
00050
00051 #include <cfg/arch/gpio.h>
00052 #include <cfg/audio.h>
00053 #include <dev/irqreg.h>
00054
00055 #include <contrib/hxmp3/mp3dec.h>
00056 #include <contrib/hxmp3/hermite.h>
00057 #include <dev/hxcodec.h>
00058 #include <dev/tlv320dac.h>
00059
00060 #include <sys/bankmem.h>
00061
00062 #include <stdlib.h>
00063 #include <stddef.h>
00064 #include <string.h>
00065
00066 #if 0
00067
00068 #define NUTDEBUG
00069 #include <stdio.h>
00070 #endif
00071
00072 #ifndef DAC_OUTPUT_RATE
00073 #if defined (AT91SAM9260_EK)
00074 #define DAC_OUTPUT_RATE 44100
00075 #else
00076 #define DAC_OUTPUT_RATE 8000
00077 #endif
00078 #endif
00079
00080 #ifndef MP3_BUFSIZ
00081 #if defined (AT91SAM9260_EK)
00082 #define MP3_BUFSIZ 1048576
00083 #else
00084 #define MP3_BUFSIZ (4 * MAINBUF_SIZE)
00085 #endif
00086 #endif
00087
00088 #ifndef ENABLE_RESAMPLER
00089 #if defined (AT91SAM9260_EK)
00090 #define ENABLE_RESAMPLER
00091 #endif
00092 #endif
00093
00094 #ifdef ENABLE_RESAMPLER
00095 static int rs_maxout;
00096 static short *rs_pcmbuf;
00097 #endif
00098
00103
00104 typedef struct _HXDCB {
00105 int dcb_pbstat;
00106 uint32_t dcb_scmd;
00107 int dcb_crvol;
00108 int dcb_srvol;
00109 int dcb_clvol;
00110 int dcb_slvol;
00111 uint32_t dcb_pbwlo;
00112 uint32_t dcb_pbwhi;
00113 } HXDCB;
00114
00115 static HXDCB dcb;
00116 static void *hres;
00117
00118 typedef struct _MP3PLAYERINFO {
00119 HMP3Decoder mpi_mp3dec;
00120 MP3FrameInfo mpi_frameinfo;
00121 } MP3PLAYERINFO;
00122
00123 static MP3PLAYERINFO mpi;
00124
00125 static short pi_pcmbuf[MAX_NCHAN * MAX_NGRAN * MAX_NSAMP];
00126
00131 static u_char ri_buff[MP3_BUFSIZ + 2 * MAINBUF_SIZE];
00132
00135 static u_int ri_avail;
00136
00137 static int first_frame;
00138 static int samprate;
00139
00140 static int HelixPlayerFlush(void)
00141 {
00142 int tmo = 1000;
00143
00144
00145 while(dcb.dcb_pbstat == CODEC_STATUS_PLAYING) {
00146 NutSleep(1);
00147 if (tmo-- <= 0) {
00148 return -1;
00149 }
00150 }
00151 return 0;
00152 }
00153
00162 static int HelixWrite(NUTFILE * fp, CONST void *data, int len)
00163 {
00164 int ec;
00165 int rbytes;
00166 int skip;
00167 u_char *bufptr;
00168
00169
00170 if (data == NULL || len == 0) {
00171 return HelixPlayerFlush();
00172 }
00173
00174 if (len) {
00175 memcpy(&ri_buff[ri_avail], data, len);
00176 ri_avail += len;
00177 }
00178
00179 if (ri_avail >= 4 * MAINBUF_SIZE) {
00180 rbytes = ri_avail;
00181 bufptr = ri_buff;
00182 while (rbytes > 2 * MAINBUF_SIZE) {
00183 if ((skip = MP3FindSyncWord(bufptr, rbytes)) < 0) {
00184 break;
00185 } else if (skip) {
00186 rbytes -= skip;
00187 bufptr += skip;
00188 } else {
00189 ec = MP3Decode(mpi.mpi_mp3dec, &bufptr, &rbytes, pi_pcmbuf, 0);
00190 if (ec) {
00191 break;
00192 }
00193 if (first_frame) {
00194 MP3GetLastFrameInfo(mpi.mpi_mp3dec, &mpi.mpi_frameinfo);
00195 if (mpi.mpi_frameinfo.nChans == 1) {
00196 samprate = mpi.mpi_frameinfo.samprate / 2;
00197 }
00198 else if (mpi.mpi_frameinfo.nChans == 2) {
00199 samprate = mpi.mpi_frameinfo.samprate;
00200 }
00201 else {
00202 samprate = 0;
00203 ec = -1;
00204 }
00205 if (mpi.mpi_frameinfo.samprate < 8000 || samprate > DAC_OUTPUT_RATE) {
00206 ec = -1;
00207 }
00208 if (mpi.mpi_frameinfo.bitsPerSample != 16) {
00209 ec = -1;
00210 }
00211 #ifdef ENABLE_RESAMPLER
00212
00213 if (ec == 0 && samprate != DAC_OUTPUT_RATE) {
00214 if ((hres = RAInitResamplerHermite(samprate, DAC_OUTPUT_RATE, mpi.mpi_frameinfo.nChans)) == NULL) {
00215 ec = -1;
00216 }
00217 rs_maxout = RAGetMaxOutputHermite(mpi.mpi_frameinfo.outputSamps, hres);
00218 if ((rs_pcmbuf = malloc(rs_maxout * 2)) == NULL) {
00219 ec = -1;
00220 }
00221 }
00222 #endif
00223 if (ec == 0) {
00224 first_frame = 0;
00225 }
00226 }
00227 if (ec == 0) {
00228 if (Tlv320DacWrite(pi_pcmbuf, mpi.mpi_frameinfo.outputSamps)) {
00229 return -1;
00230 }
00231 }
00232 }
00233 }
00234 if (rbytes > 0) {
00235 memcpy(ri_buff, &ri_buff[ri_avail - rbytes], rbytes);
00236 ri_avail = rbytes;
00237 } else {
00238 ri_avail = 0;
00239 }
00240 }
00241 return len;
00242 }
00243
00244 #ifdef __HARVARD_ARCH__
00245
00267 static int HelixWrite_P(NUTFILE * nfp, PGM_P buffer, int len)
00268 {
00269 return -1;
00270 }
00271 #endif
00272
00278 static NUTFILE *HelixOpen(NUTDEVICE * dev, CONST char *name, int mode, int acc)
00279 {
00280 NUTFILE *nfp;
00281
00282 ri_avail = 0;
00283
00284 if ((mpi.mpi_mp3dec = MP3InitDecoder()) == NULL) {
00285 return NUTFILE_EOF;
00286 }
00287
00288 first_frame = 1;
00289
00290 NutSleep(2);
00291
00292 nfp = malloc(sizeof(NUTFILE));
00293 nfp->nf_next = NULL;
00294 nfp->nf_dev = dev;
00295 nfp->nf_fcb = NULL;
00296
00297 return nfp;
00298 }
00299
00303 static int HelixClose(NUTFILE * nfp)
00304 {
00305 int rc = HelixPlayerFlush();
00306
00307 if (nfp) {
00308 if (mpi.mpi_mp3dec) {
00309 MP3FreeDecoder(mpi.mpi_mp3dec);
00310 mpi.mpi_mp3dec = NULL;
00311 }
00312 free(nfp);
00313 }
00314 return rc;
00315 }
00316
00336 static int HelixIOCtl(NUTDEVICE * dev, int req, void *conf)
00337 {
00338 int rc = 0;
00339 int *ivp = (int *) conf;
00340 int iv = *ivp;
00341
00342 switch (req) {
00343 case AUDIO_PLAY:
00344
00345 break;
00346 case AUDIO_CANCEL:
00347
00348 break;
00349 case AUDIO_GET_STATUS:
00350 break;
00351 case AUDIO_GET_PLAYGAIN:
00352 break;
00353 case AUDIO_SET_PLAYGAIN:
00354 if (iv > AUDIO_DAC_MAX_GAIN) {
00355 iv = AUDIO_DAC_MAX_GAIN;
00356 }
00357 if (iv < AUDIO_DAC_MIN_GAIN) {
00358 iv = AUDIO_DAC_MIN_GAIN;
00359 }
00360 dcb.dcb_slvol = dcb.dcb_srvol = iv;
00361 Tlv320DacSetVolume(dcb.dcb_slvol, dcb.dcb_srvol);
00362 break;
00363 default:
00364 rc = -1;
00365 break;
00366 }
00367 return rc;
00368 }
00369
00370
00371
00372
00373 static int HelixInit(NUTDEVICE * dev)
00374 {
00375 Tlv320DacInit(DAC_OUTPUT_RATE);
00376
00377 dcb.dcb_srvol = -32;
00378 dcb.dcb_slvol = -32;
00379 Tlv320DacSetVolume(dcb.dcb_srvol, dcb.dcb_slvol);
00380
00381 return 0;
00382 }
00383
00394 NUTDEVICE devHelixCodec = {
00395 0,
00396 {'a', 'u', 'd', 'i', 'o', '0', 0, 0, 0},
00397 IFTYP_CHAR,
00398 0,
00399 0,
00400 0,
00401 &dcb,
00402 HelixInit,
00403 HelixIOCtl,
00404 NULL,
00405 HelixWrite,
00406 #ifdef __HARVARD_ARCH__
00407 HelixWrite_P,
00408 #endif
00409 HelixOpen,
00410 HelixClose,
00411 NULL
00412 };
00413