^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-or-later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Linux driver for TerraTec DMX 6Fire USB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * Device communications
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) * Author: Torsten Schenk <torsten.schenk@zoho.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * Created: Jan 01, 2011
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * Copyright: (C) Torsten Schenk
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include "comm.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include "chip.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include "midi.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) COMM_EP = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) COMM_FPGA_EP = 2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) static void usb6fire_comm_init_urb(struct comm_runtime *rt, struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) u8 *buffer, void *context, void(*handler)(struct urb *urb))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) usb_init_urb(urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) urb->transfer_buffer = buffer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) urb->pipe = usb_sndintpipe(rt->chip->dev, COMM_EP);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) urb->complete = handler;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) urb->context = context;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) urb->interval = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) urb->dev = rt->chip->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) static void usb6fire_comm_receiver_handler(struct urb *urb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) struct comm_runtime *rt = urb->context;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) struct midi_runtime *midi_rt = rt->chip->midi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) if (!urb->status) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) if (rt->receiver_buffer[0] == 0x10) /* midi in event */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) if (midi_rt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) midi_rt->in_received(midi_rt,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) rt->receiver_buffer + 2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) rt->receiver_buffer[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) if (!rt->chip->shutdown) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) urb->status = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) urb->actual_length = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) if (usb_submit_urb(urb, GFP_ATOMIC) < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) dev_warn(&urb->dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) "comm data receiver aborted.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) static void usb6fire_comm_init_buffer(u8 *buffer, u8 id, u8 request,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) u8 reg, u8 vl, u8 vh)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) buffer[0] = 0x01;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) buffer[2] = request;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) buffer[3] = id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) switch (request) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) case 0x02:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) buffer[1] = 0x05; /* length (starting at buffer[2]) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) buffer[4] = reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) buffer[5] = vl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) buffer[6] = vh;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) case 0x12:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) buffer[1] = 0x0b; /* length (starting at buffer[2]) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) buffer[4] = 0x00;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) buffer[5] = 0x18;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) buffer[6] = 0x05;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) buffer[7] = 0x00;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) buffer[8] = 0x01;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) buffer[9] = 0x00;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) buffer[10] = 0x9e;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) buffer[11] = reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) buffer[12] = vl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) case 0x20:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) case 0x21:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) case 0x22:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) buffer[1] = 0x04;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) buffer[4] = reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) buffer[5] = vl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) static int usb6fire_comm_send_buffer(u8 *buffer, struct usb_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) int actual_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) ret = usb_interrupt_msg(dev, usb_sndintpipe(dev, COMM_EP),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) buffer, buffer[1] + 2, &actual_len, 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) else if (actual_len != buffer[1] + 2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) return -EIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) static int usb6fire_comm_write8(struct comm_runtime *rt, u8 request,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) u8 reg, u8 value)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) u8 *buffer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) /* 13: maximum length of message */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) buffer = kmalloc(13, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) if (!buffer)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) usb6fire_comm_init_buffer(buffer, 0x00, request, reg, value, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) ret = usb6fire_comm_send_buffer(buffer, rt->chip->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) kfree(buffer);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) static int usb6fire_comm_write16(struct comm_runtime *rt, u8 request,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) u8 reg, u8 vl, u8 vh)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) u8 *buffer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) /* 13: maximum length of message */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) buffer = kmalloc(13, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) if (!buffer)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) usb6fire_comm_init_buffer(buffer, 0x00, request, reg, vl, vh);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) ret = usb6fire_comm_send_buffer(buffer, rt->chip->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) kfree(buffer);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) int usb6fire_comm_init(struct sfire_chip *chip)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) struct comm_runtime *rt = kzalloc(sizeof(struct comm_runtime),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) struct urb *urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) if (!rt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) rt->receiver_buffer = kzalloc(COMM_RECEIVER_BUFSIZE, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) if (!rt->receiver_buffer) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) kfree(rt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) urb = &rt->receiver;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) rt->serial = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) rt->chip = chip;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) usb_init_urb(urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) rt->init_urb = usb6fire_comm_init_urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) rt->write8 = usb6fire_comm_write8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) rt->write16 = usb6fire_comm_write16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) /* submit an urb that receives communication data from device */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) urb->transfer_buffer = rt->receiver_buffer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) urb->transfer_buffer_length = COMM_RECEIVER_BUFSIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) urb->pipe = usb_rcvintpipe(chip->dev, COMM_EP);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) urb->dev = chip->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) urb->complete = usb6fire_comm_receiver_handler;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) urb->context = rt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) urb->interval = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) ret = usb_submit_urb(urb, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) kfree(rt->receiver_buffer);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) kfree(rt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) dev_err(&chip->dev->dev, "cannot create comm data receiver.");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) chip->comm = rt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) void usb6fire_comm_abort(struct sfire_chip *chip)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) struct comm_runtime *rt = chip->comm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) if (rt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) usb_poison_urb(&rt->receiver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) void usb6fire_comm_destroy(struct sfire_chip *chip)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) struct comm_runtime *rt = chip->comm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) kfree(rt->receiver_buffer);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) kfree(rt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) chip->comm = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) }