sound/pcmcia/pdaudiocf/pdaudiocf_irq.c

Source file repositories/reference/linux-study-clean/sound/pcmcia/pdaudiocf/pdaudiocf_irq.c

File Facts

System
Linux kernel
Corpus path
sound/pcmcia/pdaudiocf/pdaudiocf_irq.c
Extension
.c
Size
8506 bytes
Lines
313
Domain
Driver Families
Bucket
sound/pcmcia
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

if (chip->pcm_little) {
			if (chip->pcm_channels == 1) {
				pdacf_transfer_mono24le((char *)chip->pcm_area + (off * 3), xor, size, rdp_port);
			} else {
				pdacf_transfer_stereo24le((char *)chip->pcm_area + (off * 6), xor, size, rdp_port);
			}
		} else {
			if (chip->pcm_channels == 1) {
				pdacf_transfer_mono24be((char *)chip->pcm_area + (off * 3), xor, size, rdp_port);
			} else {
				pdacf_transfer_stereo24be((char *)chip->pcm_area + (off * 6), xor, size, rdp_port);
			}			
		}
		return;
	}
	if (chip->pcm_swab == 0) {
		if (chip->pcm_channels == 1) {
			if (chip->pcm_frame == 2) {
				pdacf_transfer_mono16((u16 *)chip->pcm_area + off, xor, size, rdp_port);
			} else {
				pdacf_transfer_mono32((u32 *)chip->pcm_area + off, xor, size, rdp_port);
			}
		} else {
			if (chip->pcm_frame == 2) {
				pdacf_transfer_stereo16((u16 *)chip->pcm_area + (off * 2), xor, size, rdp_port);
			} else {
				pdacf_transfer_stereo32((u32 *)chip->pcm_area + (off * 2), xor, size, rdp_port);
			}
		}
	} else {
		if (chip->pcm_channels == 1) {
			if (chip->pcm_frame == 2) {
				pdacf_transfer_mono16sw((u16 *)chip->pcm_area + off, xor, size, rdp_port);
			} else {
				pdacf_transfer_mono32sw((u32 *)chip->pcm_area + off, xor, size, rdp_port);
			}
		} else {
			if (chip->pcm_frame == 2) {
				pdacf_transfer_stereo16sw((u16 *)chip->pcm_area + (off * 2), xor, size, rdp_port);
			} else {
				pdacf_transfer_stereo32sw((u32 *)chip->pcm_area + (off * 2), xor, size, rdp_port);
			}
		}
	}
}

irqreturn_t pdacf_threaded_irq(int irq, void *dev)
{
	struct snd_pdacf *chip = dev;
	int size, off, cont, rdp, wdp;

	if ((chip->chip_status & (PDAUDIOCF_STAT_IS_STALE|PDAUDIOCF_STAT_IS_CONFIGURED)) != PDAUDIOCF_STAT_IS_CONFIGURED)
		return IRQ_HANDLED;
	
	if (chip->pcm_substream == NULL || chip->pcm_substream->runtime == NULL || !snd_pcm_running(chip->pcm_substream))
		return IRQ_HANDLED;

	rdp = inw(chip->port + PDAUDIOCF_REG_RDP);
	wdp = inw(chip->port + PDAUDIOCF_REG_WDP);
	size = wdp - rdp;
	if (size < 0)
		size += 0x10000;
	if (size == 0)
		size = 0x10000;
	size /= chip->pcm_frame;
	if (size > 64)
		size -= 32;

#if 0
	chip->pcm_hwptr += size;
	chip->pcm_hwptr %= chip->pcm_size;
	chip->pcm_tdone += size;
	if (chip->pcm_frame == 2) {
		unsigned long rdp_port = chip->port + PDAUDIOCF_REG_MD;
		while (size-- > 0) {
			inw(rdp_port);
			inw(rdp_port);
		}
	} else {
		unsigned long rdp_port = chip->port + PDAUDIOCF_REG_MD;
		while (size-- > 0) {
			inw(rdp_port);
			inw(rdp_port);
			inw(rdp_port);
		}
	}
#else
	off = chip->pcm_hwptr + chip->pcm_tdone;
	off %= chip->pcm_size;
	chip->pcm_tdone += size;

Annotation

Implementation Notes