📄 hdsp.c
字号:
spinlock_t lock; struct snd_pcm_substream *capture_substream; struct snd_pcm_substream *playback_substream; struct hdsp_midi midi[2]; struct tasklet_struct midi_tasklet; int use_midi_tasklet; int precise_ptr; u32 control_register; /* cached value */ u32 control2_register; /* cached value */ u32 creg_spdif; u32 creg_spdif_stream; int clock_source_locked; char *card_name; /* digiface/multiface */ enum HDSP_IO_Type io_type; /* ditto, but for code use */ unsigned short firmware_rev; unsigned short state; /* stores state bits */ u32 firmware_cache[24413]; /* this helps recover from accidental iobox power failure */ size_t period_bytes; /* guess what this is */ unsigned char max_channels; unsigned char qs_in_channels; /* quad speed mode for H9632 */ unsigned char ds_in_channels; unsigned char ss_in_channels; /* different for multiface/digiface */ unsigned char qs_out_channels; unsigned char ds_out_channels; unsigned char ss_out_channels; struct snd_dma_buffer capture_dma_buf; struct snd_dma_buffer playback_dma_buf; unsigned char *capture_buffer; /* suitably aligned address */ unsigned char *playback_buffer; /* suitably aligned address */ pid_t capture_pid; pid_t playback_pid; int running; int system_sample_rate; char *channel_map; int dev; int irq; unsigned long port; void __iomem *iobase; struct snd_card *card; struct snd_pcm *pcm; struct snd_hwdep *hwdep; struct pci_dev *pci; struct snd_kcontrol *spdif_ctl; unsigned short mixer_matrix[HDSP_MATRIX_MIXER_SIZE]; unsigned int dds_value; /* last value written to freq register */};/* These tables map the ALSA channels 1..N to the channels that we need to use in order to find the relevant channel buffer. RME refer to this kind of mapping as between "the ADAT channel and the DMA channel." We index it using the logical audio channel, and the value is the DMA channel (i.e. channel buffer number) where the data for that channel can be read/written from/to.*/static char channel_map_df_ss[HDSP_MAX_CHANNELS] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25};static char channel_map_mf_ss[HDSP_MAX_CHANNELS] = { /* Multiface */ /* Analog */ 0, 1, 2, 3, 4, 5, 6, 7, /* ADAT 2 */ 16, 17, 18, 19, 20, 21, 22, 23, /* SPDIF */ 24, 25, -1, -1, -1, -1, -1, -1, -1, -1};static char channel_map_ds[HDSP_MAX_CHANNELS] = { /* ADAT channels are remapped */ 1, 3, 5, 7, 9, 11, 13, 15, 17, 19, 21, 23, /* channels 12 and 13 are S/PDIF */ 24, 25, /* others don't exist */ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};static char channel_map_H9632_ss[HDSP_MAX_CHANNELS] = { /* ADAT channels */ 0, 1, 2, 3, 4, 5, 6, 7, /* SPDIF */ 8, 9, /* Analog */ 10, 11, /* AO4S-192 and AI4S-192 extension boards */ 12, 13, 14, 15, /* others don't exist */ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};static char channel_map_H9632_ds[HDSP_MAX_CHANNELS] = { /* ADAT */ 1, 3, 5, 7, /* SPDIF */ 8, 9, /* Analog */ 10, 11, /* AO4S-192 and AI4S-192 extension boards */ 12, 13, 14, 15, /* others don't exist */ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};static char channel_map_H9632_qs[HDSP_MAX_CHANNELS] = { /* ADAT is disabled in this mode */ /* SPDIF */ 8, 9, /* Analog */ 10, 11, /* AO4S-192 and AI4S-192 extension boards */ 12, 13, 14, 15, /* others don't exist */ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1};static int snd_hammerfall_get_buffer(struct pci_dev *pci, struct snd_dma_buffer *dmab, size_t size){ dmab->dev.type = SNDRV_DMA_TYPE_DEV; dmab->dev.dev = snd_dma_pci_data(pci); if (snd_dma_get_reserved_buf(dmab, snd_dma_pci_buf_id(pci))) { if (dmab->bytes >= size) return 0; } if (snd_dma_alloc_pages(SNDRV_DMA_TYPE_DEV, snd_dma_pci_data(pci), size, dmab) < 0) return -ENOMEM; return 0;}static void snd_hammerfall_free_buffer(struct snd_dma_buffer *dmab, struct pci_dev *pci){ if (dmab->area) { dmab->dev.dev = NULL; /* make it anonymous */ snd_dma_reserve_buf(dmab, snd_dma_pci_buf_id(pci)); }}static struct pci_device_id snd_hdsp_ids[] = { { .vendor = PCI_VENDOR_ID_XILINX, .device = PCI_DEVICE_ID_XILINX_HAMMERFALL_DSP, .subvendor = PCI_ANY_ID, .subdevice = PCI_ANY_ID, }, /* RME Hammerfall-DSP */ { 0, },};MODULE_DEVICE_TABLE(pci, snd_hdsp_ids);/* prototypes */static int snd_hdsp_create_alsa_devices(struct snd_card *card, struct hdsp *hdsp);static int snd_hdsp_create_pcm(struct snd_card *card, struct hdsp *hdsp);static int snd_hdsp_enable_io (struct hdsp *hdsp);static void snd_hdsp_initialize_midi_flush (struct hdsp *hdsp);static void snd_hdsp_initialize_channels (struct hdsp *hdsp);static int hdsp_fifo_wait(struct hdsp *hdsp, int count, int timeout);static int hdsp_autosync_ref(struct hdsp *hdsp);static int snd_hdsp_set_defaults(struct hdsp *hdsp);static void snd_hdsp_9652_enable_mixer (struct hdsp *hdsp);static int hdsp_playback_to_output_key (struct hdsp *hdsp, int in, int out){ switch (hdsp->io_type) { case Multiface: case Digiface: default: return (64 * out) + (32 + (in)); case H9632: return (32 * out) + (16 + (in)); case H9652: return (52 * out) + (26 + (in)); }}static int hdsp_input_to_output_key (struct hdsp *hdsp, int in, int out){ switch (hdsp->io_type) { case Multiface: case Digiface: default: return (64 * out) + in; case H9632: return (32 * out) + in; case H9652: return (52 * out) + in; }}static void hdsp_write(struct hdsp *hdsp, int reg, int val){ writel(val, hdsp->iobase + reg);}static unsigned int hdsp_read(struct hdsp *hdsp, int reg){ return readl (hdsp->iobase + reg);}static int hdsp_check_for_iobox (struct hdsp *hdsp){ if (hdsp->io_type == H9652 || hdsp->io_type == H9632) return 0; if (hdsp_read (hdsp, HDSP_statusRegister) & HDSP_ConfigError) { snd_printk ("Hammerfall-DSP: no Digiface or Multiface connected!\n"); hdsp->state &= ~HDSP_FirmwareLoaded; return -EIO; } return 0;}static int snd_hdsp_load_firmware_from_cache(struct hdsp *hdsp) { int i; unsigned long flags; if ((hdsp_read (hdsp, HDSP_statusRegister) & HDSP_DllError) != 0) { snd_printk ("Hammerfall-DSP: loading firmware\n"); hdsp_write (hdsp, HDSP_control2Reg, HDSP_S_PROGRAM); hdsp_write (hdsp, HDSP_fifoData, 0); if (hdsp_fifo_wait (hdsp, 0, HDSP_LONG_WAIT)) { snd_printk ("Hammerfall-DSP: timeout waiting for download preparation\n"); return -EIO; } hdsp_write (hdsp, HDSP_control2Reg, HDSP_S_LOAD); for (i = 0; i < 24413; ++i) { hdsp_write(hdsp, HDSP_fifoData, hdsp->firmware_cache[i]); if (hdsp_fifo_wait (hdsp, 127, HDSP_LONG_WAIT)) { snd_printk ("Hammerfall-DSP: timeout during firmware loading\n"); return -EIO; } } ssleep(3); if (hdsp_fifo_wait (hdsp, 0, HDSP_LONG_WAIT)) { snd_printk ("Hammerfall-DSP: timeout at end of firmware loading\n"); return -EIO; }#ifdef SNDRV_BIG_ENDIAN hdsp->control2_register = HDSP_BIGENDIAN_MODE;#else hdsp->control2_register = 0;#endif hdsp_write (hdsp, HDSP_control2Reg, hdsp->control2_register); snd_printk ("Hammerfall-DSP: finished firmware loading\n"); } if (hdsp->state & HDSP_InitializationComplete) { snd_printk(KERN_INFO "Hammerfall-DSP: firmware loaded from cache, restoring defaults\n"); spin_lock_irqsave(&hdsp->lock, flags); snd_hdsp_set_defaults(hdsp); spin_unlock_irqrestore(&hdsp->lock, flags); } hdsp->state |= HDSP_FirmwareLoaded; return 0;}static int hdsp_get_iobox_version (struct hdsp *hdsp){ if ((hdsp_read (hdsp, HDSP_statusRegister) & HDSP_DllError) != 0) { hdsp_write (hdsp, HDSP_control2Reg, HDSP_PROGRAM); hdsp_write (hdsp, HDSP_fifoData, 0); if (hdsp_fifo_wait (hdsp, 0, HDSP_SHORT_WAIT) < 0) return -EIO; hdsp_write (hdsp, HDSP_control2Reg, HDSP_S_LOAD); hdsp_write (hdsp, HDSP_fifoData, 0); if (hdsp_fifo_wait (hdsp, 0, HDSP_SHORT_WAIT)) { hdsp->io_type = Multiface; hdsp_write (hdsp, HDSP_control2Reg, HDSP_VERSION_BIT); hdsp_write (hdsp, HDSP_control2Reg, HDSP_S_LOAD); hdsp_fifo_wait (hdsp, 0, HDSP_SHORT_WAIT); } else { hdsp->io_type = Digiface; } } else { /* firmware was already loaded, get iobox type */ if (hdsp_read(hdsp, HDSP_status2Register) & HDSP_version1) hdsp->io_type = Multiface; else hdsp->io_type = Digiface; } return 0;}#ifdef HDSP_FW_LOADERstatic int __devinit hdsp_request_fw_loader(struct hdsp *hdsp);#endifstatic int hdsp_check_for_firmware (struct hdsp *hdsp, int load_on_demand){ if (hdsp->io_type == H9652 || hdsp->io_type == H9632) return 0; if ((hdsp_read (hdsp, HDSP_statusRegister) & HDSP_DllError) != 0) { hdsp->state &= ~HDSP_FirmwareLoaded; if (! load_on_demand) return -EIO; snd_printk(KERN_ERR "Hammerfall-DSP: firmware not present.\n"); /* try to load firmware */ if (! (hdsp->state & HDSP_FirmwareCached)) {#ifdef HDSP_FW_LOADER if (! hdsp_request_fw_loader(hdsp)) return 0;#endif snd_printk(KERN_ERR "Hammerfall-DSP: No firmware loaded nor " "cached, please upload firmware.\n"); return -EIO; } if (snd_hdsp_load_firmware_from_cache(hdsp) != 0) { snd_printk(KERN_ERR "Hammerfall-DSP: Firmware loading from " "cache failed, please upload manually.\n"); return -EIO; } } return 0;}static int hdsp_fifo_wait(struct hdsp *hdsp, int count, int timeout){ int i; /* the fifoStatus registers reports on how many words are available in the command FIFO. */ for (i = 0; i < timeout; i++) { if ((int)(hdsp_read (hdsp, HDSP_fifoStatus) & 0xff) <= count) return 0; /* not very friendly, but we only do this during a firmware load and changing the mixer, so we just put up with it. */ udelay (100); } snd_printk ("Hammerfall-DSP: wait for FIFO status <= %d failed after %d iterations\n", count, timeout); return -1;}static int hdsp_read_gain (struct hdsp *hdsp, unsigned int addr){ if (addr >= HDSP_MATRIX_MIXER_SIZE) return 0; return hdsp->mixer_matrix[addr];}static int hdsp_write_gain(struct hdsp *hdsp, unsigned int addr, unsigned short data){ unsigned int ad; if (addr >= HDSP_MATRIX_MIXER_SIZE) return -1; if (hdsp->io_type == H9652 || hdsp->io_type == H9632) { /* from martin bjornsen: "You can only write dwords to the mixer memory which contain two mixer values in the low and high word. So if you want to change value 0 you have to read value 1 from the cache and write both to the first dword in the mixer memory." */ if (hdsp->io_type == H9632 && addr >= 512) return 0; if (hdsp->io_type == H9652 && addr >= 1352) return 0; hdsp->mixer_matrix[addr] = data; /* `addr' addresses a 16-bit wide address, but the address space accessed via hdsp_write uses byte offsets. put another way, addr varies from 0 to 1351, but to access the corresponding memory location, we need to access 0 to 2703 ... */ ad = addr/2; hdsp_write (hdsp, 4096 + (ad*4), (hdsp->mixer_matrix[(addr&0x7fe)+1] << 16) + hdsp->mixer_matrix[addr&0x7fe]); return 0; } else { ad = (addr << 16) + data; if (hdsp_fifo_wait(hdsp, 127, HDSP_LONG_WAIT)) return -1; hdsp_write (hdsp, HDSP_fifoData, ad); hdsp->mixer_matrix[addr] = data; } return 0;}static int snd_hdsp_use_is_exclusive(struct hdsp *hdsp){ unsigned long flags;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -