root/sound/core/isadma.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. snd_dma_program
  2. snd_dma_disable
  3. snd_dma_pointer

   1 // SPDX-License-Identifier: GPL-2.0-or-later
   2 /*
   3  *  ISA DMA support functions
   4  *  Copyright (c) by Jaroslav Kysela <perex@perex.cz>
   5  */
   6 
   7 /*
   8  * Defining following add some delay. Maybe this helps for some broken
   9  * ISA DMA controllers.
  10  */
  11 
  12 #undef HAVE_REALLY_SLOW_DMA_CONTROLLER
  13 
  14 #include <linux/export.h>
  15 #include <sound/core.h>
  16 #include <asm/dma.h>
  17 
  18 /**
  19  * snd_dma_program - program an ISA DMA transfer
  20  * @dma: the dma number
  21  * @addr: the physical address of the buffer
  22  * @size: the DMA transfer size
  23  * @mode: the DMA transfer mode, DMA_MODE_XXX
  24  *
  25  * Programs an ISA DMA transfer for the given buffer.
  26  */
  27 void snd_dma_program(unsigned long dma,
  28                      unsigned long addr, unsigned int size,
  29                      unsigned short mode)
  30 {
  31         unsigned long flags;
  32 
  33         flags = claim_dma_lock();
  34         disable_dma(dma);
  35         clear_dma_ff(dma);
  36         set_dma_mode(dma, mode);
  37         set_dma_addr(dma, addr);
  38         set_dma_count(dma, size);
  39         if (!(mode & DMA_MODE_NO_ENABLE))
  40                 enable_dma(dma);
  41         release_dma_lock(flags);
  42 }
  43 EXPORT_SYMBOL(snd_dma_program);
  44 
  45 /**
  46  * snd_dma_disable - stop the ISA DMA transfer
  47  * @dma: the dma number
  48  *
  49  * Stops the ISA DMA transfer.
  50  */
  51 void snd_dma_disable(unsigned long dma)
  52 {
  53         unsigned long flags;
  54 
  55         flags = claim_dma_lock();
  56         clear_dma_ff(dma);
  57         disable_dma(dma);
  58         release_dma_lock(flags);
  59 }
  60 EXPORT_SYMBOL(snd_dma_disable);
  61 
  62 /**
  63  * snd_dma_pointer - return the current pointer to DMA transfer buffer in bytes
  64  * @dma: the dma number
  65  * @size: the dma transfer size
  66  *
  67  * Return: The current pointer in DMA transfer buffer in bytes.
  68  */
  69 unsigned int snd_dma_pointer(unsigned long dma, unsigned int size)
  70 {
  71         unsigned long flags;
  72         unsigned int result, result1;
  73 
  74         flags = claim_dma_lock();
  75         clear_dma_ff(dma);
  76         if (!isa_dma_bridge_buggy)
  77                 disable_dma(dma);
  78         result = get_dma_residue(dma);
  79         /*
  80          * HACK - read the counter again and choose higher value in order to
  81          * avoid reading during counter lower byte roll over if the
  82          * isa_dma_bridge_buggy is set.
  83          */
  84         result1 = get_dma_residue(dma);
  85         if (!isa_dma_bridge_buggy)
  86                 enable_dma(dma);
  87         release_dma_lock(flags);
  88         if (unlikely(result < result1))
  89                 result = result1;
  90 #ifdef CONFIG_SND_DEBUG
  91         if (result > size)
  92                 pr_err("ALSA: pointer (0x%x) for DMA #%ld is greater than transfer size (0x%x)\n", result, dma, size);
  93 #endif
  94         if (result >= size || result == 0)
  95                 return 0;
  96         else
  97                 return size - result;
  98 }
  99 EXPORT_SYMBOL(snd_dma_pointer);

/* [<][>][^][v][top][bottom][index][help] */