aboutsummaryrefslogtreecommitdiffstats
path: root/include/sound
diff options
context:
space:
mode:
authorTakashi Iwai <tiwai@suse.de>2008-07-30 09:13:33 -0400
committerJaroslav Kysela <perex@perex.cz>2008-08-25 03:57:38 -0400
commit51e9f2e665bf2b6a01be275d64c336d942c59a66 (patch)
tree75b79c23288a820eea6959e79060e3e4fb9d0eae /include/sound
parent4e184f8fc06411f35fdcf4b9bc6187c857bf7214 (diff)
ALSA: Allocate larger pages in sgbuf
Most hardwares have limited buffer-descriptor table length. This also restricts the max buffer size of the sound driver. For example, snd-hda-intel has 1MB buffer size limit, and this is because it can have at most 256 BDL entries. For supporting larger buffers, we need to allocate larger pages even for sg-buffers. This patch changes the sgbuf allocation code to try to allocate larger pages first. At each head of the allocated pages, the number of allocated pages is stored in the lowest bits of the corresponding entry of the table addr field. This change isn't visible as long as the driver uses snd_sgbuf_get_addr() helper. Also, the patch adds a new function, snd_pcm_sgbuf_get_chunk_size(). This returns the size of the chunk on continuous pages starting at the given position offset. If the chunk reaches to a non-continuous page, it returns the size to the boundary. Signed-off-by: Takashi Iwai <tiwai@suse.de> Signed-off-by: Jaroslav Kysela <perex@perex.cz>
Diffstat (limited to 'include/sound')
-rw-r--r--include/sound/memalloc.h4
-rw-r--r--include/sound/pcm.h3
2 files changed, 5 insertions, 2 deletions
diff --git a/include/sound/memalloc.h b/include/sound/memalloc.h
index 96d0dc171459..d787a6b4a101 100644
--- a/include/sound/memalloc.h
+++ b/include/sound/memalloc.h
@@ -97,7 +97,9 @@ static inline unsigned int snd_sgbuf_aligned_pages(size_t size)
97 */ 97 */
98static inline dma_addr_t snd_sgbuf_get_addr(struct snd_sg_buf *sgbuf, size_t offset) 98static inline dma_addr_t snd_sgbuf_get_addr(struct snd_sg_buf *sgbuf, size_t offset)
99{ 99{
100 return sgbuf->table[offset >> PAGE_SHIFT].addr + offset % PAGE_SIZE; 100 dma_addr_t addr = sgbuf->table[offset >> PAGE_SHIFT].addr;
101 addr &= PAGE_MASK;
102 return addr + offset % PAGE_SIZE;
101} 103}
102 104
103/* 105/*
diff --git a/include/sound/pcm.h b/include/sound/pcm.h
index 8db89630c821..40c5a6fa6bcd 100644
--- a/include/sound/pcm.h
+++ b/include/sound/pcm.h
@@ -996,7 +996,8 @@ snd_pcm_sgbuf_get_ptr(struct snd_pcm_substream *substream, unsigned int ofs)
996 996
997struct page *snd_pcm_sgbuf_ops_page(struct snd_pcm_substream *substream, 997struct page *snd_pcm_sgbuf_ops_page(struct snd_pcm_substream *substream,
998 unsigned long offset); 998 unsigned long offset);
999 999unsigned int snd_pcm_sgbuf_get_chunk_size(struct snd_pcm_substream *substream,
1000 unsigned int ofs, unsigned int size);
1000 1001
1001/* handle mmap counter - PCM mmap callback should handle this counter properly */ 1002/* handle mmap counter - PCM mmap callback should handle this counter properly */
1002static inline void snd_pcm_mmap_data_open(struct vm_area_struct *area) 1003static inline void snd_pcm_mmap_data_open(struct vm_area_struct *area)