On Tue, Nov 9, 2010 at 8:04 PM, Jaroslav Kysela <perex@xxxxxxxx> wrote: > On Tue, 9 Nov 2010, Manu Abraham wrote: > >> On Tue, Nov 9, 2010 at 6:21 PM, Jaroslav Kysela <perex@xxxxxxxx> wrote: >>> >>> On Tue, 9 Nov 2010, Manu Abraham wrote: >>> >>>> On Tue, Nov 9, 2010 at 5:31 PM, Jaroslav Kysela <perex@xxxxxxxx> wrote: >>>>> >>>>> On Tue, 9 Nov 2010, Manu Abraham wrote: >>>>> >>>>>> testbox ~ # arecord -Dhw:2,0 >>>>>> Recording WAVE 'stdin' : Unsigned 8 bit, Rate 8000 Hz, Mono >>>>> >>>>>> Any idea, why saa7231_hw_params is not getting invoked ? >>>>> >>>>> Your hw probably does not support directly 8-bit sample at 8000Hz, one >>>>> channel. Use 'plughw:2,0' device instead 'hw:2,0' to let alsa-lib do >>>>> all >>>>> stream format conversions. >>>> >>>> That didn't make any difference at all. >>> >>> Check your code. You probably created wrong hw_ops, looking to your code: >>> >>> .buffer_bytes_max = 512 * 4096, >>> .period_bytes_min = 8192, >>> .period_bytes_max = 8192, >>> .periods_min = 8192, >>> .periods_max = 8192, >>> >>> It's definitely an empty configuration space. >>> >>> You have buffer_bytes_max 2097152, but restricted number of periods to >>> 8192 >>> and period_bytes to 8192. >>> >>> 8192 * 8192 = 67108864 which is not less than 2097152 (and I'm not >>> counting >>> the bytes for channels and formats). Bingo, the ALSA PCM code does not >>> know >>> what to configure. >>> >>> Decrease periods_min and probably also periods_max. >>> >> >> oh ! The error message was really a weird one. I can say that the >> hardware can do 192 audio frames in an interrupt, whatever the frame >> size is. So, what periods and period_bytes should I describe in the >> configuration ? > > You cannot describe this using hw_ops. Leave period bytes in good range (192 > - 1536?), periods (2-1024?) and add something like this to the open > callback: > > err = snd_pcm_hw_constraint_minmax(runtime, > SNDRV_PCM_HW_PARAM_PERIOD_SIZE, > 192, 192); > > Note the difference between SNDRV_PCM_HW_PARAM_PERIOD_SIZE and > SNDRV_PCM_HW_PARAM_PERIOD_BYTES. > Ok, thanks. I modified it to look thus ... static struct snd_pcm_hardware saa7231_capture_info = { .info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER | SNDRV_PCM_INFO_MMAP_VALID), .formats = (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S16_BE | SNDRV_PCM_FMTBIT_S8 | SNDRV_PCM_FMTBIT_U8 | SNDRV_PCM_FMTBIT_U16_LE | SNDRV_PCM_FMTBIT_U16_BE), .rates = SNDRV_PCM_RATE_32000, .rate_min = 32000, .rate_max = 48000, .channels_min = 2, .channels_max = 2, .buffer_bytes_max = 512 * 4096, .period_bytes_min = 192, .period_bytes_max = 1536, .periods_min = 2, .periods_max = 1024, }; static int saa7231_capture_open(struct snd_pcm_substream *pcm) { struct saa7231_audio *audio = snd_pcm_substream_chip(pcm); struct snd_pcm_runtime *rt = pcm->runtime; struct saa7231_dev *saa7231 = audio->saa7231; int err; dprintk(SAA7231_DEBUG, 1, "()"); rt->hw = saa7231_capture_info; snd_pcm_hw_constraint_list(rt, 0, SNDRV_PCM_HW_PARAM_RATE, &hw_constraint_rates); err = snd_pcm_hw_constraint_integer(rt, SNDRV_PCM_HW_PARAM_PERIODS); if (err < 0) { dprintk(SAA7231_ERROR, 1, "snd_pcm_hw_constraint_integer() failed. ret=%d", err); return err; } err = snd_pcm_hw_constraint_minmax(rt, SNDRV_PCM_HW_PARAM_PERIOD_SIZE, 192, 192); if (err < 0) { dprintk(SAA7231_ERROR, 1, "snd_pcm_hw_constraint_minmax() failed. ret=%d", err); return err; } return 0; } static int saa7231_hw_params(struct snd_pcm_substream *pcm, struct snd_pcm_hw_params *params) { struct saa7231_audio *audio = snd_pcm_substream_chip(pcm); struct saa7231_dev *saa7231 = audio->saa7231; struct saa7231_dmabuf *buffer; struct saa7231_stream *stream; struct saa7231_dmabuf *dmabuf; struct page **ptable; void *vma; void *dma_area; int i, j, pages, bytes, periods, bufsiz; dprintk(SAA7231_DEBUG, 1, "DEBUG: ()"); periods = params_periods(params); bytes = params_period_bytes(params); bufsiz = periods * bytes; dprintk(SAA7231_DEBUG, 1, "bufsiz=%d periods=%d bytes=%d", bufsiz, periods, bytes); pages = bufsiz / PAGE_SIZE; /* enable stream */ stream = saa7231_stream_init(saa7231, AUDIO_CAPTURE, ADAPTER_INT, 0, 512); if (!stream) { dprintk(SAA7231_ERROR, 1, "ERROR: Registering stream"); return -ENOMEM; } audio->stream = stream; buffer = stream->dmabuf; saa7231_add_irqevent(saa7231, 43, SAA7231_EDGE_RISING, saa7231_audio_evhandler, "AS2D_AVIS"); dprintk(SAA7231_DEBUG, 1, "Mapping %d buffers with %d pages each", XS2D_BUFFERS, pages); return 0; } testbox ~ # arecord -Dplughw:2,0 Recording WAVE 'stdin' : Unsigned 8 bit, Rate 8000 Hz, Mono ALSA lib pcm_mmap.c:369:(snd_pcm_mmap) mmap failed: Invalid argument arecord: set_params:1041: Unable to install hw params: ACCESS: RW_INTERLEAVED FORMAT: U8 SUBFORMAT: STD SAMPLE_BITS: 8 FRAME_BITS: 8 CHANNELS: 1 RATE: 8000 PERIOD_TIME: 6000 PERIOD_SIZE: 48 PERIOD_BYTES: 48 PERIODS: 83 BUFFER_TIME: 498000 BUFFER_SIZE: 3984 BUFFER_BYTES: 3984 TICK_TIME: 0 [ 819.928438] saa7231_capture_open (0): () [ 819.945466] saa7231_hw_params (0): DEBUG: () [ 819.945470] saa7231_hw_params (0): bufsiz=31872 periods=83 bytes=384 [ 819.945472] saa7231_stream_init (0): DEBUG: Initializing Stream with MODE=0x01 [ 819.945475] saa7231_xs2dtl_init (0): XS2DTL engine Initializing ..... [ 819.945477] saa7231_xs2dtl_init (0): Allocated 8 XS2DTL Buffer @0xf47b6000 [ 819.945479] saa7231_xs2dtl_init (0): Allocating DMA Buffers ... [ 819.945481] saa7231_xs2dtl_init (0): Allocating DMA buffer:0 @0xf47b6000.. [ 819.945492] saa7231_allocate_ptable (0): Virtual 0xf3bb7000 to Phys 0x33bb7000 mapped page [ 819.945598] saa7231_dmabuf_sgalloc (0): Virtual contiguous 2097152 byte region with 512 4k pages ... ... bufsiz=31872 periods=83 bytes=384 Now, I wonder what a period really is. I guess I lack the basics here .. A basic explanation to the context, would be quite helpful. Best Regards, Manu _______________________________________________ Alsa-devel mailing list Alsa-devel@xxxxxxxxxxxxxxxx http://mailman.alsa-project.org/mailman/listinfo/alsa-devel