/*
 * Line 6 Linux USB driver
 *
 * Copyright (C) 2004-2010 Markus Grabner (grabner@icg.tugraz.at)
 *
 *	This program is free software; you can redistribute it and/or
 *	modify it under the terms of the GNU General Public License as
 *	published by the Free Software Foundation, version 2.
 *
 */

#include <linux/slab.h>
#include <sound/core.h>
#include <sound/pcm.h>
#include <sound/pcm_params.h>

#include "capture.h"
#include "driver.h"
#include "pcm.h"
#include "playback.h"

/*
	Software stereo volume control.
*/
static void change_volume(struct urb *urb_out, int volume[],
			  int bytes_per_frame)
{
	int chn = 0;

	if (volume[0] == 256 && volume[1] == 256)
		return;		/* maximum volume - no change */

	if (bytes_per_frame == 4) {
		short *p, *buf_end;

		p = (short *)urb_out->transfer_buffer;
		buf_end = p + urb_out->transfer_buffer_length / sizeof(*p);

		for (; p < buf_end; ++p) {
			int val = (*p * volume[chn & 1]) >> 8;
			*p = clamp(val, 0x7fff, -0x8000);
			++chn;
		}
	} else if (bytes_per_frame == 6) {
		unsigned char *p, *buf_end;

		p = (unsigned char *)urb_out->transfer_buffer;
		buf_end = p + urb_out->transfer_buffer_length;

		for (; p < buf_end; p += 3) {
			int val;

			val = p[0] + (p[1] << 8) + ((signed char)p[2] << 16);
			val = (val * volume[chn & 1]) >> 8;
			val = clamp(val, 0x7fffff, -0x800000);
			p[0] = val;
			p[1] = val >> 8;
			p[2] = val >> 16;
			++chn;
		}
	}
}

/*
	Create signal for impulse response test.
*/
static void create_impulse_test_signal(struct snd_line6_pcm *line6pcm,
				       struct urb *urb_out, int bytes_per_frame)
{
	int frames = urb_out->transfer_buffer_length / bytes_per_frame;

	if (bytes_per_frame == 4) {
		int i;
		short *pi = (short *)line6pcm->prev_fbuf;
		short *po = (short *)urb_out->transfer_buffer;

		for (i = 0; i < frames; ++i) {
			po[0] = pi[0];
			po[1] = 0;
			pi += 2;
			po += 2;
		}
	} else if (bytes_per_frame == 6) {
		int i, j;
		unsigned char *pi = line6pcm->prev_fbuf;
		unsigned char *po = urb_out->transfer_buffer;

		for (i = 0; i < frames; ++i) {
			for (j = 0; j < bytes_per_frame / 2; ++j)
				po[j] = pi[j];

			for (; j < bytes_per_frame; ++j)
				po[j] = 0;

			pi += bytes_per_frame;
			po += bytes_per_frame;
		}
	}
	if (--line6pcm->impulse_count <= 0) {
		((unsigned char *)(urb_out->transfer_buffer))[bytes_per_frame -
							      1] =
		    line6pcm->impulse_volume;
		line6pcm->impulse_count = line6pcm->impulse_period;
	}
}

/*
	Add signal to buffer for software monitoring.
*/
static void add_monitor_signal(struct urb *urb_out, unsigned char *signal,
			       int volume, int bytes_per_frame)
{
	if (volume == 0)
		return;		/* zero volume - no change */

	if (bytes_per_frame == 4) {
		short *pi, *po, *buf_end;

		pi = (short *)signal;
		po = (short *)urb_out->transfer_buffer;
		buf_end = po + urb_out->transfer_buffer_length / sizeof(*po);

		for (; po < buf_end; ++pi, ++po) {
			int val = *po + ((*pi * volume) >> 8);
			*po = clamp(val, 0x7fff, -0x8000);
		}
	}

	/*
	   We don't need to handle devices with 6 bytes per frame here
	   since they all support hardware monitoring.
	 */
}

/*
	Find a free URB, prepare audio data, and submit URB.
	must be called in line6pcm->out.lock context
*/
static int submit_audio_out_urb(struct snd_line6_pcm *line6pcm)
{
	int index;
	int i, urb_size, urb_frames;
	int ret;
	const int bytes_per_frame = line6pcm->properties->bytes_per_frame;
	const int frame_increment =
	    line6pcm->properties->snd_line6_rates.rats[0].num_min;
	const int frame_factor =
	    line6pcm->properties->snd_line6_rates.rats[0].den *
	    (USB_INTERVALS_PER_SECOND / LINE6_ISO_INTERVAL);
	struct urb *urb_out;

	index =
	    find_first_zero_bit(&line6pcm->out.active_urbs, LINE6_ISO_BUFFERS);

	if (index < 0 || index >= LINE6_ISO_BUFFERS) {
		dev_err(line6pcm->line6->ifcdev, "no free URB found\n");
		return -EINVAL;
	}

	urb_out = line6pcm->out.urbs[index];
	urb_size = 0;

	for (i = 0; i < LINE6_ISO_PACKETS; ++i) {
		/* compute frame size for given sampling rate */
		int fsize = 0;
		struct usb_iso_packet_descriptor *fout =
		    &urb_out->iso_frame_desc[i];

		fsize = line6pcm->prev_fsize;
		if (fsize == 0) {
			int n;

			line6pcm->out.count += frame_increment;
			n = line6pcm->out.count / frame_factor;
			line6pcm->out.count -= n * frame_factor;
			fsize = n * bytes_per_frame;
		}

		fout->offset = urb_size;
		fout->length = fsize;
		urb_size += fsize;
	}

	if (urb_size == 0) {
		/* can't determine URB size */
		dev_err(line6pcm->line6->ifcdev, "driver bug: urb_size = 0\n");
		return -EINVAL;
	}

	urb_frames = urb_size / bytes_per_frame;
	urb_out->transfer_buffer =
	    line6pcm->out.buffer +
	    index * LINE6_ISO_PACKETS * line6pcm->max_packet_size;
	urb_out->transfer_buffer_length = urb_size;
	urb_out->context = line6pcm;

	if (test_bit(LINE6_INDEX_PCM_ALSA_PLAYBACK_STREAM, &line6pcm->flags) &&
	    !test_bit(LINE6_INDEX_PAUSE_PLAYBACK, &line6pcm->flags)) {
		struct snd_pcm_runtime *runtime =
		    get_substream(line6pcm, SNDRV_PCM_STREAM_PLAYBACK)->runtime;

		if (line6pcm->out.pos + urb_frames > runtime->buffer_size) {
			/*
			   The transferred area goes over buffer boundary,
			   copy the data to the temp buffer.
			 */
			int len;

			len = runtime->buffer_size - line6pcm->out.pos;

			if (len > 0) {
				memcpy(urb_out->transfer_buffer,
				       runtime->dma_area +
				       line6pcm->out.pos * bytes_per_frame,
				       len * bytes_per_frame);
				memcpy(urb_out->transfer_buffer +
				       len * bytes_per_frame, runtime->dma_area,
				       (urb_frames - len) * bytes_per_frame);
			} else
				dev_err(line6pcm->line6->ifcdev, "driver bug: len = %d\n",
					len);
		} else {
			memcpy(urb_out->transfer_buffer,
			       runtime->dma_area +
			       line6pcm->out.pos * bytes_per_frame,
			       urb_out->transfer_buffer_length);
		}

		line6pcm->out.pos += urb_frames;
		if (line6pcm->out.pos >= runtime->buffer_size)
			line6pcm->out.pos -= runtime->buffer_size;

		change_volume(urb_out, line6pcm->volume_playback,
			      bytes_per_frame);
	} else {
		memset(urb_out->transfer_buffer, 0,
		       urb_out->transfer_buffer_length);
	}

	spin_lock_nested(&line6pcm->in.lock, SINGLE_DEPTH_NESTING);
	if (line6pcm->prev_fbuf) {
		if (line6pcm->flags & LINE6_BITS_PCM_IMPULSE) {
			create_impulse_test_signal(line6pcm, urb_out,
						   bytes_per_frame);
			if (line6pcm->flags &
			    LINE6_BIT_PCM_ALSA_CAPTURE_STREAM) {
				line6_capture_copy(line6pcm,
						   urb_out->transfer_buffer,
						   urb_out->
						   transfer_buffer_length);
				line6_capture_check_period(line6pcm,
					urb_out->transfer_buffer_length);
			}
		} else {
			if (!
			    (line6pcm->line6->
			     properties->capabilities & LINE6_CAP_HWMON)
			    && (line6pcm->flags & LINE6_BITS_PLAYBACK_STREAM)
			    && (line6pcm->flags & LINE6_BITS_CAPTURE_STREAM))
				add_monitor_signal(urb_out, line6pcm->prev_fbuf,
						   line6pcm->volume_monitor,
						   bytes_per_frame);
		}
		line6pcm->prev_fbuf = NULL;
		line6pcm->prev_fsize = 0;
	}
	spin_unlock(&line6pcm->in.lock);

	ret = usb_submit_urb(urb_out, GFP_ATOMIC);

	if (ret == 0)
		set_bit(index, &line6pcm->out.active_urbs);
	else
		dev_err(line6pcm->line6->ifcdev,
			"URB out #%d submission failed (%d)\n", index, ret);

	return 0;
}

/*
	Submit all currently available playback URBs.
*/
int line6_submit_audio_out_all_urbs(struct snd_line6_pcm *line6pcm)
{
	unsigned long flags;
	int ret = 0, i;

	spin_lock_irqsave(&line6pcm->out.lock, flags);
	for (i = 0; i < LINE6_ISO_BUFFERS; ++i) {
		ret = submit_audio_out_urb(line6pcm);
		if (ret < 0)
			break;
	}

	spin_unlock_irqrestore(&line6pcm->out.lock, flags);
	return ret;
}

/*
	Callback for completed playback URB.
*/
static void audio_out_callback(struct urb *urb)
{
	int i, index, length = 0, shutdown = 0;
	unsigned long flags;
	struct snd_line6_pcm *line6pcm = (struct snd_line6_pcm *)urb->context;
	struct snd_pcm_substream *substream =
	    get_substream(line6pcm, SNDRV_PCM_STREAM_PLAYBACK);

#if USE_CLEAR_BUFFER_WORKAROUND
	memset(urb->transfer_buffer, 0, urb->transfer_buffer_length);
#endif

	line6pcm->out.last_frame = urb->start_frame;

	/* find index of URB */
	for (index = 0; index < LINE6_ISO_BUFFERS; index++)
		if (urb == line6pcm->out.urbs[index])
			break;

	if (index >= LINE6_ISO_BUFFERS)
		return;		/* URB has been unlinked asynchronously */

	for (i = 0; i < LINE6_ISO_PACKETS; i++)
		length += urb->iso_frame_desc[i].length;

	spin_lock_irqsave(&line6pcm->out.lock, flags);

	if (test_bit(LINE6_INDEX_PCM_ALSA_PLAYBACK_STREAM, &line6pcm->flags)) {
		struct snd_pcm_runtime *runtime = substream->runtime;

		line6pcm->out.pos_done +=
		    length / line6pcm->properties->bytes_per_frame;

		if (line6pcm->out.pos_done >= runtime->buffer_size)
			line6pcm->out.pos_done -= runtime->buffer_size;
	}

	clear_bit(index, &line6pcm->out.active_urbs);

	for (i = 0; i < LINE6_ISO_PACKETS; i++)
		if (urb->iso_frame_desc[i].status == -EXDEV) {
			shutdown = 1;
			break;
		}

	if (test_and_clear_bit(index, &line6pcm->out.unlink_urbs))
		shutdown = 1;

	if (!shutdown) {
		submit_audio_out_urb(line6pcm);

		if (test_bit(LINE6_INDEX_PCM_ALSA_PLAYBACK_STREAM,
			     &line6pcm->flags)) {
			line6pcm->out.bytes += length;
			if (line6pcm->out.bytes >= line6pcm->out.period) {
				line6pcm->out.bytes %= line6pcm->out.period;
				spin_unlock(&line6pcm->out.lock);
				snd_pcm_period_elapsed(substream);
				spin_lock(&line6pcm->out.lock);
			}
		}
	}
	spin_unlock_irqrestore(&line6pcm->out.lock, flags);
}

/* open playback callback */
static int snd_line6_playback_open(struct snd_pcm_substream *substream)
{
	int err;
	struct snd_pcm_runtime *runtime = substream->runtime;
	struct snd_line6_pcm *line6pcm = snd_pcm_substream_chip(substream);

	err = snd_pcm_hw_constraint_ratdens(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
					    (&line6pcm->
					     properties->snd_line6_rates));
	if (err < 0)
		return err;

	runtime->hw = line6pcm->properties->snd_line6_playback_hw;
	return 0;
}

/* close playback callback */
static int snd_line6_playback_close(struct snd_pcm_substream *substream)
{
	return 0;
}

/* hw_params playback callback */
static int snd_line6_playback_hw_params(struct snd_pcm_substream *substream,
					struct snd_pcm_hw_params *hw_params)
{
	int ret;
	struct snd_line6_pcm *line6pcm = snd_pcm_substream_chip(substream);

	ret = line6_pcm_acquire(line6pcm, LINE6_BIT_PCM_ALSA_PLAYBACK_BUFFER);

	if (ret < 0)
		return ret;

	ret = snd_pcm_lib_malloc_pages(substream,
				       params_buffer_bytes(hw_params));
	if (ret < 0) {
		line6_pcm_release(line6pcm, LINE6_BIT_PCM_ALSA_PLAYBACK_BUFFER);
		return ret;
	}

	line6pcm->out.period = params_period_bytes(hw_params);
	return 0;
}

/* hw_free playback callback */
static int snd_line6_playback_hw_free(struct snd_pcm_substream *substream)
{
	struct snd_line6_pcm *line6pcm = snd_pcm_substream_chip(substream);

	line6_pcm_release(line6pcm, LINE6_BIT_PCM_ALSA_PLAYBACK_BUFFER);
	return snd_pcm_lib_free_pages(substream);
}

/* trigger playback callback */
int snd_line6_playback_trigger(struct snd_line6_pcm *line6pcm, int cmd)
{
	int err;

	switch (cmd) {
	case SNDRV_PCM_TRIGGER_START:
	case SNDRV_PCM_TRIGGER_RESUME:
		err = line6_pcm_acquire(line6pcm,
					LINE6_BIT_PCM_ALSA_PLAYBACK_STREAM);

		if (err < 0)
			return err;

		break;

	case SNDRV_PCM_TRIGGER_STOP:
	case SNDRV_PCM_TRIGGER_SUSPEND:
		err = line6_pcm_release(line6pcm,
					LINE6_BIT_PCM_ALSA_PLAYBACK_STREAM);

		if (err < 0)
			return err;

		break;

	case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
		set_bit(LINE6_INDEX_PAUSE_PLAYBACK, &line6pcm->flags);
		break;

	case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
		clear_bit(LINE6_INDEX_PAUSE_PLAYBACK, &line6pcm->flags);
		break;

	default:
		return -EINVAL;
	}

	return 0;
}

/* playback pointer callback */
static snd_pcm_uframes_t
snd_line6_playback_pointer(struct snd_pcm_substream *substream)
{
	struct snd_line6_pcm *line6pcm = snd_pcm_substream_chip(substream);

	return line6pcm->out.pos_done;
}

/* playback operators */
struct snd_pcm_ops snd_line6_playback_ops = {
	.open = snd_line6_playback_open,
	.close = snd_line6_playback_close,
	.ioctl = snd_pcm_lib_ioctl,
	.hw_params = snd_line6_playback_hw_params,
	.hw_free = snd_line6_playback_hw_free,
	.prepare = snd_line6_prepare,
	.trigger = snd_line6_trigger,
	.pointer = snd_line6_playback_pointer,
};

int line6_create_audio_out_urbs(struct snd_line6_pcm *line6pcm)
{
	struct usb_line6 *line6 = line6pcm->line6;
	int i;

	/* create audio URBs and fill in constant values: */
	for (i = 0; i < LINE6_ISO_BUFFERS; ++i) {
		struct urb *urb;

		/* URB for audio out: */
		urb = line6pcm->out.urbs[i] =
		    usb_alloc_urb(LINE6_ISO_PACKETS, GFP_KERNEL);

		if (urb == NULL)
			return -ENOMEM;

		urb->dev = line6->usbdev;
		urb->pipe =
		    usb_sndisocpipe(line6->usbdev,
				    line6->properties->ep_audio_w &
				    USB_ENDPOINT_NUMBER_MASK);
		urb->transfer_flags = URB_ISO_ASAP;
		urb->start_frame = -1;
		urb->number_of_packets = LINE6_ISO_PACKETS;
		urb->interval = LINE6_ISO_INTERVAL;
		urb->error_count = 0;
		urb->complete = audio_out_callback;
	}

	return 0;
}
