1 /* 2 * Copyright (c) by Jaroslav Kysela <perex@perex.cz> 3 * Takashi Iwai <tiwai@suse.de> 4 * 5 * Generic memory allocators 6 * 7 * 8 * This program is free software; you can redistribute it and/or modify 9 * it under the terms of the GNU General Public License as published by 10 * the Free Software Foundation; either version 2 of the License, or 11 * (at your option) any later version. 12 * 13 * This program is distributed in the hope that it will be useful, 14 * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 * GNU General Public License for more details. 17 * 18 * You should have received a copy of the GNU General Public License 19 * along with this program; if not, write to the Free Software 20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 21 * 22 */ 23 24 #include <linux/slab.h> 25 #include <linux/mm.h> 26 #include <linux/dma-mapping.h> 27 #include <linux/genalloc.h> 28 #ifdef CONFIG_X86 29 #include <asm/set_memory.h> 30 #endif 31 #include <sound/memalloc.h> 32 33 /* 34 * 35 * Generic memory allocators 36 * 37 */ 38 39 /** 40 * snd_malloc_pages - allocate pages with the given size 41 * @size: the size to allocate in bytes 42 * @gfp_flags: the allocation conditions, GFP_XXX 43 * 44 * Allocates the physically contiguous pages with the given size. 45 * 46 * Return: The pointer of the buffer, or %NULL if no enough memory. 47 */ 48 void *snd_malloc_pages(size_t size, gfp_t gfp_flags) 49 { 50 int pg; 51 52 if (WARN_ON(!size)) 53 return NULL; 54 if (WARN_ON(!gfp_flags)) 55 return NULL; 56 gfp_flags |= __GFP_COMP; /* compound page lets parts be mapped */ 57 pg = get_order(size); 58 return (void *) __get_free_pages(gfp_flags, pg); 59 } 60 EXPORT_SYMBOL(snd_malloc_pages); 61 62 /** 63 * snd_free_pages - release the pages 64 * @ptr: the buffer pointer to release 65 * @size: the allocated buffer size 66 * 67 * Releases the buffer allocated via snd_malloc_pages(). 68 */ 69 void snd_free_pages(void *ptr, size_t size) 70 { 71 int pg; 72 73 if (ptr == NULL) 74 return; 75 pg = get_order(size); 76 free_pages((unsigned long) ptr, pg); 77 } 78 EXPORT_SYMBOL(snd_free_pages); 79 80 /* 81 * 82 * Bus-specific memory allocators 83 * 84 */ 85 86 #ifdef CONFIG_HAS_DMA 87 /* allocate the coherent DMA pages */ 88 static void snd_malloc_dev_pages(struct snd_dma_buffer *dmab, size_t size) 89 { 90 gfp_t gfp_flags; 91 92 gfp_flags = GFP_KERNEL 93 | __GFP_COMP /* compound page lets parts be mapped */ 94 | __GFP_NORETRY /* don't trigger OOM-killer */ 95 | __GFP_NOWARN; /* no stack trace print - this call is non-critical */ 96 dmab->area = dma_alloc_coherent(dmab->dev.dev, size, &dmab->addr, 97 gfp_flags); 98 #ifdef CONFIG_X86 99 if (dmab->area && dmab->dev.type == SNDRV_DMA_TYPE_DEV_UC) 100 set_memory_wc((unsigned long)dmab->area, 101 PAGE_ALIGN(size) >> PAGE_SHIFT); 102 #endif 103 } 104 105 /* free the coherent DMA pages */ 106 static void snd_free_dev_pages(struct snd_dma_buffer *dmab) 107 { 108 #ifdef CONFIG_X86 109 if (dmab->dev.type == SNDRV_DMA_TYPE_DEV_UC) 110 set_memory_wb((unsigned long)dmab->area, 111 PAGE_ALIGN(dmab->bytes) >> PAGE_SHIFT); 112 #endif 113 dma_free_coherent(dmab->dev.dev, dmab->bytes, dmab->area, dmab->addr); 114 } 115 116 #ifdef CONFIG_GENERIC_ALLOCATOR 117 /** 118 * snd_malloc_dev_iram - allocate memory from on-chip internal ram 119 * @dmab: buffer allocation record to store the allocated data 120 * @size: number of bytes to allocate from the iram 121 * 122 * This function requires iram phandle provided via of_node 123 */ 124 static void snd_malloc_dev_iram(struct snd_dma_buffer *dmab, size_t size) 125 { 126 struct device *dev = dmab->dev.dev; 127 struct gen_pool *pool = NULL; 128 129 dmab->area = NULL; 130 dmab->addr = 0; 131 132 if (dev->of_node) 133 pool = of_gen_pool_get(dev->of_node, "iram", 0); 134 135 if (!pool) 136 return; 137 138 /* Assign the pool into private_data field */ 139 dmab->private_data = pool; 140 141 dmab->area = gen_pool_dma_alloc(pool, size, &dmab->addr); 142 } 143 144 /** 145 * snd_free_dev_iram - free allocated specific memory from on-chip internal ram 146 * @dmab: buffer allocation record to store the allocated data 147 */ 148 static void snd_free_dev_iram(struct snd_dma_buffer *dmab) 149 { 150 struct gen_pool *pool = dmab->private_data; 151 152 if (pool && dmab->area) 153 gen_pool_free(pool, (unsigned long)dmab->area, dmab->bytes); 154 } 155 #endif /* CONFIG_GENERIC_ALLOCATOR */ 156 #endif /* CONFIG_HAS_DMA */ 157 158 /* 159 * 160 * ALSA generic memory management 161 * 162 */ 163 164 165 /** 166 * snd_dma_alloc_pages - allocate the buffer area according to the given type 167 * @type: the DMA buffer type 168 * @device: the device pointer 169 * @size: the buffer size to allocate 170 * @dmab: buffer allocation record to store the allocated data 171 * 172 * Calls the memory-allocator function for the corresponding 173 * buffer type. 174 * 175 * Return: Zero if the buffer with the given size is allocated successfully, 176 * otherwise a negative value on error. 177 */ 178 int snd_dma_alloc_pages(int type, struct device *device, size_t size, 179 struct snd_dma_buffer *dmab) 180 { 181 if (WARN_ON(!size)) 182 return -ENXIO; 183 if (WARN_ON(!dmab)) 184 return -ENXIO; 185 186 dmab->dev.type = type; 187 dmab->dev.dev = device; 188 dmab->bytes = 0; 189 switch (type) { 190 case SNDRV_DMA_TYPE_CONTINUOUS: 191 dmab->area = snd_malloc_pages(size, 192 (__force gfp_t)(unsigned long)device); 193 dmab->addr = 0; 194 break; 195 #ifdef CONFIG_HAS_DMA 196 #ifdef CONFIG_GENERIC_ALLOCATOR 197 case SNDRV_DMA_TYPE_DEV_IRAM: 198 snd_malloc_dev_iram(dmab, size); 199 if (dmab->area) 200 break; 201 /* Internal memory might have limited size and no enough space, 202 * so if we fail to malloc, try to fetch memory traditionally. 203 */ 204 dmab->dev.type = SNDRV_DMA_TYPE_DEV; 205 #endif /* CONFIG_GENERIC_ALLOCATOR */ 206 case SNDRV_DMA_TYPE_DEV: 207 case SNDRV_DMA_TYPE_DEV_UC: 208 snd_malloc_dev_pages(dmab, size); 209 break; 210 #endif 211 #ifdef CONFIG_SND_DMA_SGBUF 212 case SNDRV_DMA_TYPE_DEV_SG: 213 case SNDRV_DMA_TYPE_DEV_UC_SG: 214 snd_malloc_sgbuf_pages(device, size, dmab, NULL); 215 break; 216 #endif 217 default: 218 pr_err("snd-malloc: invalid device type %d\n", type); 219 dmab->area = NULL; 220 dmab->addr = 0; 221 return -ENXIO; 222 } 223 if (! dmab->area) 224 return -ENOMEM; 225 dmab->bytes = size; 226 return 0; 227 } 228 EXPORT_SYMBOL(snd_dma_alloc_pages); 229 230 /** 231 * snd_dma_alloc_pages_fallback - allocate the buffer area according to the given type with fallback 232 * @type: the DMA buffer type 233 * @device: the device pointer 234 * @size: the buffer size to allocate 235 * @dmab: buffer allocation record to store the allocated data 236 * 237 * Calls the memory-allocator function for the corresponding 238 * buffer type. When no space is left, this function reduces the size and 239 * tries to allocate again. The size actually allocated is stored in 240 * res_size argument. 241 * 242 * Return: Zero if the buffer with the given size is allocated successfully, 243 * otherwise a negative value on error. 244 */ 245 int snd_dma_alloc_pages_fallback(int type, struct device *device, size_t size, 246 struct snd_dma_buffer *dmab) 247 { 248 int err; 249 250 while ((err = snd_dma_alloc_pages(type, device, size, dmab)) < 0) { 251 if (err != -ENOMEM) 252 return err; 253 if (size <= PAGE_SIZE) 254 return -ENOMEM; 255 size >>= 1; 256 size = PAGE_SIZE << get_order(size); 257 } 258 if (! dmab->area) 259 return -ENOMEM; 260 return 0; 261 } 262 EXPORT_SYMBOL(snd_dma_alloc_pages_fallback); 263 264 265 /** 266 * snd_dma_free_pages - release the allocated buffer 267 * @dmab: the buffer allocation record to release 268 * 269 * Releases the allocated buffer via snd_dma_alloc_pages(). 270 */ 271 void snd_dma_free_pages(struct snd_dma_buffer *dmab) 272 { 273 switch (dmab->dev.type) { 274 case SNDRV_DMA_TYPE_CONTINUOUS: 275 snd_free_pages(dmab->area, dmab->bytes); 276 break; 277 #ifdef CONFIG_HAS_DMA 278 #ifdef CONFIG_GENERIC_ALLOCATOR 279 case SNDRV_DMA_TYPE_DEV_IRAM: 280 snd_free_dev_iram(dmab); 281 break; 282 #endif /* CONFIG_GENERIC_ALLOCATOR */ 283 case SNDRV_DMA_TYPE_DEV: 284 case SNDRV_DMA_TYPE_DEV_UC: 285 snd_free_dev_pages(dmab); 286 break; 287 #endif 288 #ifdef CONFIG_SND_DMA_SGBUF 289 case SNDRV_DMA_TYPE_DEV_SG: 290 case SNDRV_DMA_TYPE_DEV_UC_SG: 291 snd_free_sgbuf_pages(dmab); 292 break; 293 #endif 294 default: 295 pr_err("snd-malloc: invalid device type %d\n", dmab->dev.type); 296 } 297 } 298 EXPORT_SYMBOL(snd_dma_free_pages); 299