Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 302e4c2f authored by Takashi Iwai's avatar Takashi Iwai Committed by Jaroslav Kysela
Browse files

[ALSA] Change an arugment of snd_mpu401_uart_new() to bit flags



Change the 5th argument of snd_mpu401_uart_new() to bit flags
instead of a boolean.  The argument takes bits that consist of
MPU401_INFO_XXX flags.
The callers that used the value 1 there are replaced with
MPU401_INFO_INTEGRATED.

Signed-off-by: default avatarTakashi Iwai <tiwai@suse.de>
parent 140432fd
Loading
Loading
Loading
Loading
+25 −4
Original line number Diff line number Diff line
@@ -4215,7 +4215,7 @@ struct _snd_pcm_runtime {
          <programlisting>
<![CDATA[
  struct snd_rawmidi *rmidi;
  snd_mpu401_uart_new(card, 0, MPU401_HW_MPU401, port, integrated,
  snd_mpu401_uart_new(card, 0, MPU401_HW_MPU401, port, info_flags,
                      irq, irq_flags, &rmidi);
]]>
          </programlisting>
@@ -4242,15 +4242,36 @@ struct _snd_pcm_runtime {
      </para>

      <para>
	The 5th argument is bitflags for additional information.
        When the i/o port address above is a part of the PCI i/o
      region, the MPU401 i/o port might have been already allocated
      (reserved) by the driver itself. In such a case, pass non-zero
      to the 5th argument
      (<parameter>integrated</parameter>). Otherwise, pass 0 to it,
      (reserved) by the driver itself. In such a case, pass a bit flag
      <constant>MPU401_INFO_INTEGRATED</constant>,
      and 
      the mpu401-uart layer will allocate the i/o ports by itself. 
      </para>

	<para>
	When the controller supports only the input or output MIDI stream,
	pass <constant>MPU401_INFO_INPUT</constant> or
	<constant>MPU401_INFO_OUTPUT</constant> bitflag, respectively.
	Then the rawmidi instance is created as a single stream.
	</para>

	<para>
	<constant>MPU401_INFO_MMIO</constant> bitflag is used to change
	the access method to MMIO (via readb and writeb) instead of
	iob and outb.  In this case, you have to pass the iomapped address
	to <function>snd_mpu401_uart_new()</function>.
	</para>

	<para>
	When <constant>MPU401_INFO_TX_IRQ</constant> is set, the output
	stream isn't checked in the default interrupt handler.  The driver
	needs to call <function>snd_mpu401_uart_interrupt_tx()</function>
	by itself to start processing the output stream in irq handler.
	</para>

      <para>
        Usually, the port address corresponds to the command port and
        port + 1 corresponds to the data port. If not, you may change
+12 −2
Original line number Diff line number Diff line
@@ -45,6 +45,12 @@
#define MPU401_HW_PC98II		18	/* Roland PC98II */
#define MPU401_HW_AUREAL		19	/* Aureal Vortex */

#define MPU401_INFO_INPUT	(1 << 0)	/* input stream */
#define MPU401_INFO_OUTPUT	(1 << 1)	/* output stream */
#define MPU401_INFO_INTEGRATED	(1 << 2)	/* integrated h/w port */
#define MPU401_INFO_MMIO	(1 << 3)	/* MMIO access */
#define MPU401_INFO_TX_IRQ	(1 << 4)	/* independent TX irq */

#define MPU401_MODE_BIT_INPUT		0
#define MPU401_MODE_BIT_OUTPUT		1
#define MPU401_MODE_BIT_INPUT_TRIGGER	2
@@ -62,6 +68,7 @@ struct snd_mpu401 {
	struct snd_rawmidi *rmidi;

	unsigned short hardware;	/* MPU401_HW_XXXX */
	unsigned int info_flags;	/* MPU401_INFO_XXX */
	unsigned long port;		/* base port of MPU-401 chip */
	unsigned long cport;		/* port + 1 (usually) */
	struct resource *res;		/* port resource */
@@ -99,13 +106,16 @@ struct snd_mpu401 {

 */

irqreturn_t snd_mpu401_uart_interrupt(int irq, void *dev_id, struct pt_regs *regs);
irqreturn_t snd_mpu401_uart_interrupt(int irq, void *dev_id,
				      struct pt_regs *regs);
irqreturn_t snd_mpu401_uart_interrupt_tx(int irq, void *dev_id,
					 struct pt_regs *regs);

int snd_mpu401_uart_new(struct snd_card *card,
			int device,
			unsigned short hardware,
			unsigned long port,
			int integrated,
			unsigned int info_flags,
			int irq,
			int irq_flags,
			struct snd_rawmidi ** rrawmidi);
+68 −28
Original line number Diff line number Diff line
@@ -95,23 +95,30 @@ static void snd_mpu401_uart_clear_rx(struct snd_mpu401 *mpu)
#endif
}

static void uart_interrupt_tx(struct snd_mpu401 *mpu)
{
	if (test_bit(MPU401_MODE_BIT_OUTPUT, &mpu->mode) &&
	    test_bit(MPU401_MODE_BIT_OUTPUT_TRIGGER, &mpu->mode)) {
		spin_lock(&mpu->output_lock);
		snd_mpu401_uart_output_write(mpu);
		spin_unlock(&mpu->output_lock);
	}
}

static void _snd_mpu401_uart_interrupt(struct snd_mpu401 *mpu)
{
	if (mpu->info_flags & MPU401_INFO_INPUT) {
		spin_lock(&mpu->input_lock);
		if (test_bit(MPU401_MODE_BIT_INPUT, &mpu->mode))
			snd_mpu401_uart_input_read(mpu);
		else
			snd_mpu401_uart_clear_rx(mpu);
		spin_unlock(&mpu->input_lock);
 	/* ok. for better Tx performance try do some output when
	 * input is done
	 */
	if (test_bit(MPU401_MODE_BIT_OUTPUT, &mpu->mode) &&
	    test_bit(MPU401_MODE_BIT_OUTPUT_TRIGGER, &mpu->mode)) {
		spin_lock(&mpu->output_lock);
		snd_mpu401_uart_output_write(mpu);
		spin_unlock(&mpu->output_lock);
	}
	if (! (mpu->info_flags & MPU401_INFO_TX_IRQ))
		/* ok. for better Tx performance try do some output
		   when input is done */
		uart_interrupt_tx(mpu);
}

/**
@@ -135,6 +142,27 @@ irqreturn_t snd_mpu401_uart_interrupt(int irq, void *dev_id,

EXPORT_SYMBOL(snd_mpu401_uart_interrupt);

/**
 * snd_mpu401_uart_interrupt_tx - generic MPU401-UART transmit irq handler
 * @irq: the irq number
 * @dev_id: mpu401 instance
 * @regs: the reigster
 *
 * Processes the interrupt for MPU401-UART output.
 */
irqreturn_t snd_mpu401_uart_interrupt_tx(int irq, void *dev_id,
					 struct pt_regs *regs)
{
	struct snd_mpu401 *mpu = dev_id;
	
	if (mpu == NULL)
		return IRQ_NONE;
	uart_interrupt_tx(mpu);
	return IRQ_HANDLED;
}

EXPORT_SYMBOL(snd_mpu401_uart_interrupt_tx);

/*
 * timer callback
 * reprogram the timer and call the interrupt job
@@ -430,6 +458,7 @@ snd_mpu401_uart_output_trigger(struct snd_rawmidi_substream *substream, int up)
		 * since the output timer might have been removed in
		 * snd_mpu401_uart_output_write().
		 */
		if (! (mpu->info_flags & MPU401_INFO_TX_IRQ))
			snd_mpu401_uart_add_timer(mpu, 0);

		/* output pending data */
@@ -437,6 +466,7 @@ snd_mpu401_uart_output_trigger(struct snd_rawmidi_substream *substream, int up)
		snd_mpu401_uart_output_write(mpu);
		spin_unlock_irqrestore(&mpu->output_lock, flags);
	} else {
		if (! (mpu->info_flags & MPU401_INFO_TX_IRQ))
			snd_mpu401_uart_remove_timer(mpu, 0);
		clear_bit(MPU401_MODE_BIT_OUTPUT_TRIGGER, &mpu->mode);
	}
@@ -475,7 +505,7 @@ static void snd_mpu401_uart_free(struct snd_rawmidi *rmidi)
 * @device: the device index, zero-based
 * @hardware: the hardware type, MPU401_HW_XXXX
 * @port: the base address of MPU401 port
 * @integrated: non-zero if the port was already reserved by the chip
 * @info_flags: bitflags MPU401_INFO_XXX
 * @irq: the irq number, -1 if no interrupt for mpu
 * @irq_flags: the irq request flags (SA_XXX), 0 if irq was already reserved.
 * @rrawmidi: the pointer to store the new rawmidi instance
@@ -490,17 +520,24 @@ static void snd_mpu401_uart_free(struct snd_rawmidi *rmidi)
 */
int snd_mpu401_uart_new(struct snd_card *card, int device,
			unsigned short hardware,
			unsigned long port, int integrated,
			unsigned long port,
			unsigned int info_flags,
			int irq, int irq_flags,
			struct snd_rawmidi ** rrawmidi)
{
	struct snd_mpu401 *mpu;
	struct snd_rawmidi *rmidi;
	int in_enable, out_enable;
	int err;

	if (rrawmidi)
		*rrawmidi = NULL;
	if ((err = snd_rawmidi_new(card, "MPU-401U", device, 1, 1, &rmidi)) < 0)
	if (! (info_flags & (MPU401_INFO_INPUT | MPU401_INFO_OUTPUT)))
		info_flags |= MPU401_INFO_INPUT | MPU401_INFO_OUTPUT;
	in_enable = (info_flags & MPU401_INFO_INPUT) ? 1 : 0;
	out_enable = (info_flags & MPU401_INFO_OUTPUT) ? 1 : 0;
	if ((err = snd_rawmidi_new(card, "MPU-401U", device,
				   out_enable, in_enable, &rmidi)) < 0)
		return err;
	mpu = kzalloc(sizeof(*mpu), GFP_KERNEL);
	if (mpu == NULL) {
@@ -514,7 +551,7 @@ int snd_mpu401_uart_new(struct snd_card *card, int device,
	spin_lock_init(&mpu->output_lock);
	spin_lock_init(&mpu->timer_lock);
	mpu->hardware = hardware;
	if (!integrated) {
	if (! (info_flags & MPU401_INFO_INTEGRATED)) {
		int res_size = hardware == MPU401_HW_PC98II ? 4 : 2;
		mpu->res = request_region(port, res_size, "MPU401 UART");
		if (mpu->res == NULL) {
@@ -525,15 +562,12 @@ int snd_mpu401_uart_new(struct snd_card *card, int device,
			return -EBUSY;
		}
	}
	switch (hardware) {
	case MPU401_HW_AUREAL:
	if (info_flags & MPU401_INFO_MMIO) {
		mpu->write = mpu401_write_mmio;
		mpu->read = mpu401_read_mmio;
		break;
	default:
	} else {
		mpu->write = mpu401_write_port;
		mpu->read = mpu401_read_port;
		break;
	}
	mpu->port = port;
	if (hardware == MPU401_HW_PC98II)
@@ -549,6 +583,7 @@ int snd_mpu401_uart_new(struct snd_card *card, int device,
			return -EBUSY;
		}
	}
	mpu->info_flags = info_flags;
	mpu->irq = irq;
	mpu->irq_flags = irq_flags;
	if (card->shortname[0])
@@ -556,13 +591,18 @@ int snd_mpu401_uart_new(struct snd_card *card, int device,
			 card->shortname);
	else
		sprintf(rmidi->name, "MPU-401 MIDI %d-%d",card->number, device);
	if (out_enable) {
		snd_rawmidi_set_ops(rmidi, SNDRV_RAWMIDI_STREAM_OUTPUT,
				    &snd_mpu401_uart_output);
		rmidi->info_flags |= SNDRV_RAWMIDI_INFO_OUTPUT;
	}
	if (in_enable) {
		snd_rawmidi_set_ops(rmidi, SNDRV_RAWMIDI_STREAM_INPUT,
				    &snd_mpu401_uart_input);
	rmidi->info_flags |= SNDRV_RAWMIDI_INFO_OUTPUT |
	                     SNDRV_RAWMIDI_INFO_INPUT |
	                     SNDRV_RAWMIDI_INFO_DUPLEX;
		rmidi->info_flags |= SNDRV_RAWMIDI_INFO_INPUT;
		if (out_enable)
			rmidi->info_flags |= SNDRV_RAWMIDI_INFO_DUPLEX;
	}
	mpu->rmidi = rmidi;
	if (rrawmidi)
		*rrawmidi = rmidi;
+1 −2
Original line number Diff line number Diff line
@@ -897,10 +897,9 @@ static int __devinit create_mpu401(struct snd_card *card, int devnum, unsigned l
	struct snd_rawmidi *rawmidi;
	int err;

#define MPU401_SHARE_HARDWARE  1
	if ((err = snd_mpu401_uart_new(card, devnum,
	                               MPU401_HW_MPU401,
	                               port, MPU401_SHARE_HARDWARE,
	                               port, MPU401_INFO_INTEGRATED,
	                               irq, SA_INTERRUPT,
	                               &rawmidi)) == 0) {
		struct snd_mpu401 *mpu = (struct snd_mpu401 *) rawmidi->private_data;
+2 −2
Original line number Diff line number Diff line
@@ -746,8 +746,8 @@ static int __devinit snd_card_als4000_probe(struct pci_dev *pci,
		card->shortname, chip->alt_port, chip->irq);

	if ((err = snd_mpu401_uart_new( card, 0, MPU401_HW_ALS4000,
				        gcr+0x30, 1, pci->irq, 0,
				        &chip->rmidi)) < 0) {
				        gcr+0x30, MPU401_INFO_INTEGRATED,
					pci->irq, 0, &chip->rmidi)) < 0) {
		printk(KERN_ERR "als4000: no MPU-401 device at 0x%lx?\n", gcr+0x30);
		goto out_err;
	}
Loading