// SPDX-License-Identifier: GPL-2.0-or-later
/*
 *  HID driver for the Prodikeys PC-MIDI Keyboard
 *  providing midi & extra multimedia keys functionality
 *
 *  Copyright (c) 2009 Don Prince <dhprince.devel@yahoo.co.uk>
 *
 *  Controls for Octave Shift Up/Down, Channel, and
 *  Sustain Duration available via sysfs.
 */

/*
 */

#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

#include <linux/device.h>
#include <linux/module.h>
#include <linux/usb.h>
#include <linux/mutex.h>
#include <linux/hid.h>
#include <sound/core.h>
#include <sound/initval.h>
#include <sound/rawmidi.h>
#include "hid-ids.h"


#define pk_debug(format, arg...) \
	pr_debug("hid-prodikeys: " format "\n" , ## arg)
#define pk_error(format, arg...) \
	pr_err("hid-prodikeys: " format "\n" , ## arg)

struct pcmidi_snd;

struct pcmidi_sustain {
	unsigned long		in_use;
	struct pcmidi_snd	*pm;
	struct timer_list	timer;
	unsigned char		status;
	unsigned char		note;
	unsigned char		velocity;
};

#define PCMIDI_SUSTAINED_MAX	32
struct pcmidi_snd {
	struct hid_device		*hdev;
	unsigned short			ifnum;
	struct hid_report		*pcmidi_report6;
	struct input_dev		*input_ep82;
	unsigned short			midi_mode;
	unsigned short			midi_sustain_mode;
	unsigned short			midi_sustain;
	unsigned short			midi_channel;
	short				midi_octave;
	struct pcmidi_sustain		sustained_notes[PCMIDI_SUSTAINED_MAX];
	unsigned short			fn_state;
	unsigned short			last_key[24];
	spinlock_t			rawmidi_in_lock;
	struct snd_card			*card;
	struct snd_rawmidi		*rwmidi;
	struct snd_rawmidi_substream	*in_substream;
	unsigned long			in_triggered;
};

#define PK_QUIRK_NOGET	0x00010000
#define PCMIDI_MIDDLE_C 60
#define PCMIDI_CHANNEL_MIN 0
#define PCMIDI_CHANNEL_MAX 15
#define PCMIDI_OCTAVE_MIN (-2)
#define PCMIDI_OCTAVE_MAX 2
#define PCMIDI_SUSTAIN_MIN 0
#define PCMIDI_SUSTAIN_MAX 5000

static const char shortname[] = "PC-MIDI";
static const char longname[] = "Prodikeys PC-MIDI Keyboard";

static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX;
static char *id[SNDRV_CARDS] = SNDRV_DEFAULT_STR;
static bool enable[SNDRV_CARDS] = SNDRV_DEFAULT_ENABLE_PNP;

module_param_array(index, int, NULL, 0444);
module_param_array(id, charp, NULL, 0444);
module_param_array(enable, bool, NULL, 0444);
MODULE_PARM_DESC(index, "Index value for the PC-MIDI virtual audio driver");
MODULE_PARM_DESC(id, "ID string for the PC-MIDI virtual audio driver");
MODULE_PARM_DESC(enable, "Enable for the PC-MIDI virtual audio driver");


/* Output routine for the sysfs channel file */
static ssize_t show_channel(struct device *dev,
	struct device_attribute *attr, char *buf)
{
	struct hid_device *hdev = to_hid_device(dev);
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	dbg_hid("pcmidi sysfs read channel=%u\n", pm->midi_channel);

	return sprintf(buf, "%u (min:%u, max:%u)\n", pm->midi_channel,
		PCMIDI_CHANNEL_MIN, PCMIDI_CHANNEL_MAX);
}

/* Input routine for the sysfs channel file */
static ssize_t store_channel(struct device *dev,
	struct device_attribute *attr, const char *buf, size_t count)
{
	struct hid_device *hdev = to_hid_device(dev);
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	unsigned channel = 0;

	if (sscanf(buf, "%u", &channel) > 0 && channel <= PCMIDI_CHANNEL_MAX) {
		dbg_hid("pcmidi sysfs write channel=%u\n", channel);
		pm->midi_channel = channel;
		return strlen(buf);
	}
	return -EINVAL;
}

static DEVICE_ATTR(channel, S_IRUGO | S_IWUSR | S_IWGRP , show_channel,
		store_channel);

static struct device_attribute *sysfs_device_attr_channel = {
		&dev_attr_channel,
		};

/* Output routine for the sysfs sustain file */
static ssize_t show_sustain(struct device *dev,
 struct device_attribute *attr, char *buf)
{
	struct hid_device *hdev = to_hid_device(dev);
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	dbg_hid("pcmidi sysfs read sustain=%u\n", pm->midi_sustain);

	return sprintf(buf, "%u (off:%u, max:%u (ms))\n", pm->midi_sustain,
		PCMIDI_SUSTAIN_MIN, PCMIDI_SUSTAIN_MAX);
}

/* Input routine for the sysfs sustain file */
static ssize_t store_sustain(struct device *dev,
	struct device_attribute *attr, const char *buf, size_t count)
{
	struct hid_device *hdev = to_hid_device(dev);
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	unsigned sustain = 0;

	if (sscanf(buf, "%u", &sustain) > 0 && sustain <= PCMIDI_SUSTAIN_MAX) {
		dbg_hid("pcmidi sysfs write sustain=%u\n", sustain);
		pm->midi_sustain = sustain;
		pm->midi_sustain_mode = (0 == sustain || !pm->midi_mode) ? 0 : 1;
		return strlen(buf);
	}
	return -EINVAL;
}

static DEVICE_ATTR(sustain, S_IRUGO | S_IWUSR | S_IWGRP, show_sustain,
		store_sustain);

static struct device_attribute *sysfs_device_attr_sustain = {
		&dev_attr_sustain,
		};

/* Output routine for the sysfs octave file */
static ssize_t show_octave(struct device *dev,
	struct device_attribute *attr, char *buf)
{
	struct hid_device *hdev = to_hid_device(dev);
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	dbg_hid("pcmidi sysfs read octave=%d\n", pm->midi_octave);

	return sprintf(buf, "%d (min:%d, max:%d)\n", pm->midi_octave,
		PCMIDI_OCTAVE_MIN, PCMIDI_OCTAVE_MAX);
}

/* Input routine for the sysfs octave file */
static ssize_t store_octave(struct device *dev,
	struct device_attribute *attr, const char *buf, size_t count)
{
	struct hid_device *hdev = to_hid_device(dev);
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	int octave = 0;

	if (sscanf(buf, "%d", &octave) > 0 &&
		octave >= PCMIDI_OCTAVE_MIN && octave <= PCMIDI_OCTAVE_MAX) {
		dbg_hid("pcmidi sysfs write octave=%d\n", octave);
		pm->midi_octave = octave;
		return strlen(buf);
	}
	return -EINVAL;
}

static DEVICE_ATTR(octave, S_IRUGO | S_IWUSR | S_IWGRP, show_octave,
		store_octave);

static struct device_attribute *sysfs_device_attr_octave = {
		&dev_attr_octave,
		};


static void pcmidi_send_note(struct pcmidi_snd *pm,
	unsigned char status, unsigned char note, unsigned char velocity)
{
	unsigned long flags;
	unsigned char buffer[3];

	buffer[0] = status;
	buffer[1] = note;
	buffer[2] = velocity;

	spin_lock_irqsave(&pm->rawmidi_in_lock, flags);

	if (!pm->in_substream)
		goto drop_note;
	if (!test_bit(pm->in_substream->number, &pm->in_triggered))
		goto drop_note;

	snd_rawmidi_receive(pm->in_substream, buffer, 3);

drop_note:
	spin_unlock_irqrestore(&pm->rawmidi_in_lock, flags);

	return;
}

static void pcmidi_sustained_note_release(struct timer_list *t)
{
	struct pcmidi_sustain *pms = from_timer(pms, t, timer);

	pcmidi_send_note(pms->pm, pms->status, pms->note, pms->velocity);
	pms->in_use = 0;
}

static void init_sustain_timers(struct pcmidi_snd *pm)
{
	struct pcmidi_sustain *pms;
	unsigned i;

	for (i = 0; i < PCMIDI_SUSTAINED_MAX; i++) {
		pms = &pm->sustained_notes[i];
		pms->in_use = 0;
		pms->pm = pm;
		timer_setup(&pms->timer, pcmidi_sustained_note_release, 0);
	}
}

static void stop_sustain_timers(struct pcmidi_snd *pm)
{
	struct pcmidi_sustain *pms;
	unsigned i;

	for (i = 0; i < PCMIDI_SUSTAINED_MAX; i++) {
		pms = &pm->sustained_notes[i];
		pms->in_use = 1;
		del_timer_sync(&pms->timer);
	}
}

static int pcmidi_get_output_report(struct pcmidi_snd *pm)
{
	struct hid_device *hdev = pm->hdev;
	struct hid_report *report;

	list_for_each_entry(report,
		&hdev->report_enum[HID_OUTPUT_REPORT].report_list, list) {
		if (!(6 == report->id))
			continue;

		if (report->maxfield < 1) {
			hid_err(hdev, "output report is empty\n");
			break;
		}
		if (report->field[0]->report_count != 2) {
			hid_err(hdev, "field count too low\n");
			break;
		}
		pm->pcmidi_report6 = report;
		return 0;
	}
	/* should never get here */
	return -ENODEV;
}

static void pcmidi_submit_output_report(struct pcmidi_snd *pm, int state)
{
	struct hid_device *hdev = pm->hdev;
	struct hid_report *report = pm->pcmidi_report6;
	report->field[0]->value[0] = 0x01;
	report->field[0]->value[1] = state;

	hid_hw_request(hdev, report, HID_REQ_SET_REPORT);
}

static int pcmidi_handle_report1(struct pcmidi_snd *pm, u8 *data)
{
	u32 bit_mask;

	bit_mask = data[1];
	bit_mask = (bit_mask << 8) | data[2];
	bit_mask = (bit_mask << 8) | data[3];

	dbg_hid("pcmidi mode: %d\n", pm->midi_mode);

	/*KEY_MAIL or octave down*/
	if (pm->midi_mode && bit_mask == 0x004000) {
		/* octave down */
		pm->midi_octave--;
		if (pm->midi_octave < -2)
			pm->midi_octave = -2;
		dbg_hid("pcmidi mode: %d octave: %d\n",
			pm->midi_mode, pm->midi_octave);
		return 1;
	}
	/*KEY_WWW or sustain*/
	else if (pm->midi_mode && bit_mask == 0x000004) {
		/* sustain on/off*/
		pm->midi_sustain_mode ^= 0x1;
		return 1;
	}

	return 0; /* continue key processing */
}

static int pcmidi_handle_report3(struct pcmidi_snd *pm, u8 *data, int size)
{
	struct pcmidi_sustain *pms;
	unsigned i, j;
	unsigned char status, note, velocity;

	unsigned num_notes = (size-1)/2;
	for (j = 0; j < num_notes; j++)	{
		note = data[j*2+1];
		velocity = data[j*2+2];

		if (note < 0x81) { /* note on */
			status = 128 + 16 + pm->midi_channel; /* 1001nnnn */
			note = note - 0x54 + PCMIDI_MIDDLE_C +
				(pm->midi_octave * 12);
			if (0 == velocity)
				velocity = 1; /* force note on */
		} else { /* note off */
			status = 128 + pm->midi_channel; /* 1000nnnn */
			note = note - 0x94 + PCMIDI_MIDDLE_C +
				(pm->midi_octave*12);

			if (pm->midi_sustain_mode) {
				for (i = 0; i < PCMIDI_SUSTAINED_MAX; i++) {
					pms = &pm->sustained_notes[i];
					if (!pms->in_use) {
						pms->status = status;
						pms->note = note;
						pms->velocity = velocity;
						pms->in_use = 1;

						mod_timer(&pms->timer,
							jiffies +
					msecs_to_jiffies(pm->midi_sustain));
						return 1;
					}
				}
			}
		}
		pcmidi_send_note(pm, status, note, velocity);
	}

	return 1;
}

static int pcmidi_handle_report4(struct pcmidi_snd *pm, u8 *data)
{
	unsigned	key;
	u32		bit_mask;
	u32		bit_index;

	bit_mask = data[1];
	bit_mask = (bit_mask << 8) | data[2];
	bit_mask = (bit_mask << 8) | data[3];

	/* break keys */
	for (bit_index = 0; bit_index < 24; bit_index++) {
		if (!((0x01 << bit_index) & bit_mask)) {
			input_event(pm->input_ep82, EV_KEY,
				pm->last_key[bit_index], 0);
			pm->last_key[bit_index] = 0;
		}
	}

	/* make keys */
	for (bit_index = 0; bit_index < 24; bit_index++) {
		key = 0;
		switch ((0x01 << bit_index) & bit_mask) {
		case 0x000010: /* Fn lock*/
			pm->fn_state ^= 0x000010;
			if (pm->fn_state)
				pcmidi_submit_output_report(pm, 0xc5);
			else
				pcmidi_submit_output_report(pm, 0xc6);
			continue;
		case 0x020000: /* midi launcher..send a key (qwerty) or not? */
			pcmidi_submit_output_report(pm, 0xc1);
			pm->midi_mode ^= 0x01;

			dbg_hid("pcmidi mode: %d\n", pm->midi_mode);
			continue;
		case 0x100000: /* KEY_MESSENGER or octave up */
			dbg_hid("pcmidi mode: %d\n", pm->midi_mode);
			if (pm->midi_mode) {
				pm->midi_octave++;
				if (pm->midi_octave > 2)
					pm->midi_octave = 2;
				dbg_hid("pcmidi mode: %d octave: %d\n",
					pm->midi_mode, pm->midi_octave);
				continue;
			} else
				key = KEY_MESSENGER;
			break;
		case 0x400000:
			key = KEY_CALENDAR;
			break;
		case 0x080000:
			key = KEY_ADDRESSBOOK;
			break;
		case 0x040000:
			key = KEY_DOCUMENTS;
			break;
		case 0x800000:
			key = KEY_WORDPROCESSOR;
			break;
		case 0x200000:
			key = KEY_SPREADSHEET;
			break;
		case 0x010000:
			key = KEY_COFFEE;
			break;
		case 0x000100:
			key = KEY_HELP;
			break;
		case 0x000200:
			key = KEY_SEND;
			break;
		case 0x000400:
			key = KEY_REPLY;
			break;
		case 0x000800:
			key = KEY_FORWARDMAIL;
			break;
		case 0x001000:
			key = KEY_NEW;
			break;
		case 0x002000:
			key = KEY_OPEN;
			break;
		case 0x004000:
			key = KEY_CLOSE;
			break;
		case 0x008000:
			key = KEY_SAVE;
			break;
		case 0x000001:
			key = KEY_UNDO;
			break;
		case 0x000002:
			key = KEY_REDO;
			break;
		case 0x000004:
			key = KEY_SPELLCHECK;
			break;
		case 0x000008:
			key = KEY_PRINT;
			break;
		}
		if (key) {
			input_event(pm->input_ep82, EV_KEY, key, 1);
			pm->last_key[bit_index] = key;
		}
	}

	return 1;
}

static int pcmidi_handle_report(
	struct pcmidi_snd *pm, unsigned report_id, u8 *data, int size)
{
	int ret = 0;

	switch (report_id) {
	case 0x01: /* midi keys (qwerty)*/
		ret = pcmidi_handle_report1(pm, data);
		break;
	case 0x03: /* midi keyboard (musical)*/
		ret = pcmidi_handle_report3(pm, data, size);
		break;
	case 0x04: /* multimedia/midi keys (qwerty)*/
		ret = pcmidi_handle_report4(pm, data);
		break;
	}
	return ret;
}

static void pcmidi_setup_extra_keys(
	struct pcmidi_snd *pm, struct input_dev *input)
{
	/* reassigned functionality for N/A keys
		MY PICTURES =>	KEY_WORDPROCESSOR
		MY MUSIC=>	KEY_SPREADSHEET
	*/
	static const unsigned int keys[] = {
		KEY_FN,
		KEY_MESSENGER, KEY_CALENDAR,
		KEY_ADDRESSBOOK, KEY_DOCUMENTS,
		KEY_WORDPROCESSOR,
		KEY_SPREADSHEET,
		KEY_COFFEE,
		KEY_HELP, KEY_SEND,
		KEY_REPLY, KEY_FORWARDMAIL,
		KEY_NEW, KEY_OPEN,
		KEY_CLOSE, KEY_SAVE,
		KEY_UNDO, KEY_REDO,
		KEY_SPELLCHECK,	KEY_PRINT,
		0
	};

	const unsigned int *pkeys = &keys[0];
	unsigned short i;

	if (pm->ifnum != 1)  /* only set up ONCE for interace 1 */
		return;

	pm->input_ep82 = input;

	for (i = 0; i < 24; i++)
		pm->last_key[i] = 0;

	while (*pkeys != 0) {
		set_bit(*pkeys, pm->input_ep82->keybit);
		++pkeys;
	}
}

static int pcmidi_set_operational(struct pcmidi_snd *pm)
{
	int rc;

	if (pm->ifnum != 1)
		return 0; /* only set up ONCE for interace 1 */

	rc = pcmidi_get_output_report(pm);
	if (rc < 0)
		return rc;
	pcmidi_submit_output_report(pm, 0xc1);
	return 0;
}

static int pcmidi_snd_free(struct snd_device *dev)
{
	return 0;
}

static int pcmidi_in_open(struct snd_rawmidi_substream *substream)
{
	struct pcmidi_snd *pm = substream->rmidi->private_data;

	dbg_hid("pcmidi in open\n");
	pm->in_substream = substream;
	return 0;
}

static int pcmidi_in_close(struct snd_rawmidi_substream *substream)
{
	dbg_hid("pcmidi in close\n");
	return 0;
}

static void pcmidi_in_trigger(struct snd_rawmidi_substream *substream, int up)
{
	struct pcmidi_snd *pm = substream->rmidi->private_data;

	dbg_hid("pcmidi in trigger %d\n", up);

	pm->in_triggered = up;
}

static const struct snd_rawmidi_ops pcmidi_in_ops = {
	.open = pcmidi_in_open,
	.close = pcmidi_in_close,
	.trigger = pcmidi_in_trigger
};

static int pcmidi_snd_initialise(struct pcmidi_snd *pm)
{
	static int dev;
	struct snd_card *card;
	struct snd_rawmidi *rwmidi;
	int err;

	static struct snd_device_ops ops = {
		.dev_free = pcmidi_snd_free,
	};

	if (pm->ifnum != 1)
		return 0; /* only set up midi device ONCE for interace 1 */

	if (dev >= SNDRV_CARDS)
		return -ENODEV;

	if (!enable[dev]) {
		dev++;
		return -ENOENT;
	}

	/* Setup sound card */

	err = snd_card_new(&pm->hdev->dev, index[dev], id[dev],
			   THIS_MODULE, 0, &card);
	if (err < 0) {
		pk_error("failed to create pc-midi sound card\n");
		err = -ENOMEM;
		goto fail;
	}
	pm->card = card;

	/* Setup sound device */
	err = snd_device_new(card, SNDRV_DEV_LOWLEVEL, pm, &ops);
	if (err < 0) {
		pk_error("failed to create pc-midi sound device: error %d\n",
			err);
		goto fail;
	}

	strscpy(card->driver, shortname, sizeof(card->driver));
	strscpy(card->shortname, shortname, sizeof(card->shortname));
	strscpy(card->longname, longname, sizeof(card->longname));

	/* Set up rawmidi */
	err = snd_rawmidi_new(card, card->shortname, 0,
			      0, 1, &rwmidi);
	if (err < 0) {
		pk_error("failed to create pc-midi rawmidi device: error %d\n",
			err);
		goto fail;
	}
	pm->rwmidi = rwmidi;
	strscpy(rwmidi->name, card->shortname, sizeof(rwmidi->name));
	rwmidi->info_flags = SNDRV_RAWMIDI_INFO_INPUT;
	rwmidi->private_data = pm;

	snd_rawmidi_set_ops(rwmidi, SNDRV_RAWMIDI_STREAM_INPUT,
		&pcmidi_in_ops);

	/* create sysfs variables */
	err = device_create_file(&pm->hdev->dev,
				 sysfs_device_attr_channel);
	if (err < 0) {
		pk_error("failed to create sysfs attribute channel: error %d\n",
			err);
		goto fail;
	}

	err = device_create_file(&pm->hdev->dev,
				sysfs_device_attr_sustain);
	if (err < 0) {
		pk_error("failed to create sysfs attribute sustain: error %d\n",
			err);
		goto fail_attr_sustain;
	}

	err = device_create_file(&pm->hdev->dev,
			 sysfs_device_attr_octave);
	if (err < 0) {
		pk_error("failed to create sysfs attribute octave: error %d\n",
			err);
		goto fail_attr_octave;
	}

	spin_lock_init(&pm->rawmidi_in_lock);

	init_sustain_timers(pm);
	err = pcmidi_set_operational(pm);
	if (err < 0) {
		pk_error("failed to find output report\n");
		goto fail_register;
	}

	/* register it */
	err = snd_card_register(card);
	if (err < 0) {
		pk_error("failed to register pc-midi sound card: error %d\n",
			 err);
		goto fail_register;
	}

	dbg_hid("pcmidi_snd_initialise finished ok\n");
	return 0;

fail_register:
	stop_sustain_timers(pm);
	device_remove_file(&pm->hdev->dev, sysfs_device_attr_octave);
fail_attr_octave:
	device_remove_file(&pm->hdev->dev, sysfs_device_attr_sustain);
fail_attr_sustain:
	device_remove_file(&pm->hdev->dev, sysfs_device_attr_channel);
fail:
	if (pm->card) {
		snd_card_free(pm->card);
		pm->card = NULL;
	}
	return err;
}

static int pcmidi_snd_terminate(struct pcmidi_snd *pm)
{
	if (pm->card) {
		stop_sustain_timers(pm);

		device_remove_file(&pm->hdev->dev, sysfs_device_attr_channel);
		device_remove_file(&pm->hdev->dev, sysfs_device_attr_sustain);
		device_remove_file(&pm->hdev->dev, sysfs_device_attr_octave);

		snd_card_disconnect(pm->card);
		snd_card_free_when_closed(pm->card);
	}

	return 0;
}

/*
 * PC-MIDI report descriptor for report id is wrong.
 */
static const __u8 *pk_report_fixup(struct hid_device *hdev, __u8 *rdesc,
		unsigned int *rsize)
{
	if (*rsize == 178 &&
	      rdesc[111] == 0x06 && rdesc[112] == 0x00 &&
	      rdesc[113] == 0xff) {
		hid_info(hdev,
			 "fixing up pc-midi keyboard report descriptor\n");

		rdesc[144] = 0x18; /* report 4: was 0x10 report count */
	}
	return rdesc;
}

static int pk_input_mapping(struct hid_device *hdev, struct hid_input *hi,
		struct hid_field *field, struct hid_usage *usage,
		unsigned long **bit, int *max)
{
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	if (HID_UP_MSVENDOR == (usage->hid & HID_USAGE_PAGE) &&
		1 == pm->ifnum) {
		pcmidi_setup_extra_keys(pm, hi->input);
		return 0;
	}

	return 0;
}


static int pk_raw_event(struct hid_device *hdev, struct hid_report *report,
	u8 *data, int size)
{
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);
	int ret = 0;

	if (1 == pm->ifnum) {
		if (report->id == data[0])
			switch (report->id) {
			case 0x01: /* midi keys (qwerty)*/
			case 0x03: /* midi keyboard (musical)*/
			case 0x04: /* extra/midi keys (qwerty)*/
				ret = pcmidi_handle_report(pm,
						report->id, data, size);
				break;
			}
	}

	return ret;
}

static int pk_probe(struct hid_device *hdev, const struct hid_device_id *id)
{
	int ret;
	struct usb_interface *intf;
	unsigned short ifnum;
	unsigned long quirks = id->driver_data;
	struct pcmidi_snd *pm;

	if (!hid_is_usb(hdev))
		return -EINVAL;

	intf = to_usb_interface(hdev->dev.parent);
	ifnum = intf->cur_altsetting->desc.bInterfaceNumber;

	pm = kzalloc(sizeof(*pm), GFP_KERNEL);
	if (pm == NULL) {
		hid_err(hdev, "can't alloc descriptor\n");
		return -ENOMEM;
	}

	pm->hdev = hdev;
	pm->ifnum = ifnum;

	hid_set_drvdata(hdev, pm);

	ret = hid_parse(hdev);
	if (ret) {
		hid_err(hdev, "hid parse failed\n");
		goto err_free;
	}

	if (quirks & PK_QUIRK_NOGET) { /* hid_parse cleared all the quirks */
		hdev->quirks |= HID_QUIRK_NOGET;
	}

	ret = hid_hw_start(hdev, HID_CONNECT_DEFAULT);
	if (ret) {
		hid_err(hdev, "hw start failed\n");
		goto err_free;
	}

	ret = pcmidi_snd_initialise(pm);
	if (ret < 0)
		goto err_stop;

	return 0;
err_stop:
	hid_hw_stop(hdev);
err_free:
	kfree(pm);

	return ret;
}

static void pk_remove(struct hid_device *hdev)
{
	struct pcmidi_snd *pm = hid_get_drvdata(hdev);

	pcmidi_snd_terminate(pm);
	hid_hw_stop(hdev);

	kfree(pm);
}

static const struct hid_device_id pk_devices[] = {
	{HID_USB_DEVICE(USB_VENDOR_ID_CREATIVELABS,
		USB_DEVICE_ID_PRODIKEYS_PCMIDI),
	    .driver_data = PK_QUIRK_NOGET},
	{ }
};
MODULE_DEVICE_TABLE(hid, pk_devices);

static struct hid_driver pk_driver = {
	.name = "prodikeys",
	.id_table = pk_devices,
	.report_fixup = pk_report_fixup,
	.input_mapping = pk_input_mapping,
	.raw_event = pk_raw_event,
	.probe = pk_probe,
	.remove = pk_remove,
};
module_hid_driver(pk_driver);

MODULE_DESCRIPTION("HID driver for the Prodikeys PC-MIDI Keyboard");
MODULE_LICENSE("GPL");
