1 /* 2 * Emagic EMI 2|6 usb audio interface firmware loader. 3 * Copyright (C) 2002 4 * Tapio Laxstr�m (tapio.laxstrom@iptime.fi) 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License, as published by 8 * the Free Software Foundation, version 2. 9 * 10 * $Id: emi62.c,v 1.15 2002/04/23 06:13:59 tapio Exp $ 11 */ 12 #include <linux/kernel.h> 13 #include <linux/errno.h> 14 #include <linux/slab.h> 15 #include <linux/init.h> 16 #include <linux/module.h> 17 #include <linux/usb.h> 18 #include <linux/delay.h> 19 20 #define MAX_INTEL_HEX_RECORD_LENGTH 16 21 typedef struct _INTEL_HEX_RECORD 22 { 23 __u32 length; 24 __u32 address; 25 __u32 type; 26 __u8 data[MAX_INTEL_HEX_RECORD_LENGTH]; 27 } INTEL_HEX_RECORD, *PINTEL_HEX_RECORD; 28 29 /* include firmware (variables)*/ 30 31 /* FIXME: This is quick and dirty solution! */ 32 #define SPDIF /* if you want SPDIF comment next line */ 33 //#undef SPDIF /* if you want MIDI uncomment this line */ 34 35 #ifdef SPDIF 36 # include "emi62_fw_s.h" /* spdif fw */ 37 #else 38 # include "emi62_fw_m.h" /* midi fw */ 39 #endif 40 41 #define EMI62_VENDOR_ID 0x086a /* Emagic Soft-und Hardware GmBH */ 42 #define EMI62_PRODUCT_ID 0x0110 /* EMI 6|2m without firmware */ 43 44 #define ANCHOR_LOAD_INTERNAL 0xA0 /* Vendor specific request code for Anchor Upload/Download (This one is implemented in the core) */ 45 #define ANCHOR_LOAD_EXTERNAL 0xA3 /* This command is not implemented in the core. Requires firmware */ 46 #define ANCHOR_LOAD_FPGA 0xA5 /* This command is not implemented in the core. Requires firmware. Emagic extension */ 47 #define MAX_INTERNAL_ADDRESS 0x1B3F /* This is the highest internal RAM address for the AN2131Q */ 48 #define CPUCS_REG 0x7F92 /* EZ-USB Control and Status Register. Bit 0 controls 8051 reset */ 49 #define INTERNAL_RAM(address) (address <= MAX_INTERNAL_ADDRESS) 50 51 static int emi62_writememory( struct usb_device *dev, int address, unsigned char *data, int length, __u8 bRequest); 52 static int emi62_set_reset(struct usb_device *dev, unsigned char reset_bit); 53 static int emi62_load_firmware (struct usb_device *dev); 54 static int emi62_probe(struct usb_interface *intf, const struct usb_device_id *id); 55 static void emi62_disconnect(struct usb_interface *intf); 56 static int __init emi62_init (void); 57 static void __exit emi62_exit (void); 58 59 60 /* thanks to drivers/usb/serial/keyspan_pda.c code */ 61 static int emi62_writememory (struct usb_device *dev, int address, unsigned char *data, int length, __u8 request) 62 { 63 int result; 64 unsigned char *buffer = kmalloc (length, GFP_KERNEL); 65 66 if (!buffer) { 67 err("emi62: kmalloc(%d) failed.", length); 68 return -ENOMEM; 69 } 70 memcpy (buffer, data, length); 71 /* Note: usb_control_msg returns negative value on error or length of the 72 * data that was written! */ 73 result = usb_control_msg (dev, usb_sndctrlpipe(dev, 0), request, 0x40, address, 0, buffer, length, 300); 74 kfree (buffer); 75 return result; 76 } 77 78 /* thanks to drivers/usb/serial/keyspan_pda.c code */ 79 static int emi62_set_reset (struct usb_device *dev, unsigned char reset_bit) 80 { 81 int response; 82 info("%s - %d", __FUNCTION__, reset_bit); 83 84 response = emi62_writememory (dev, CPUCS_REG, &reset_bit, 1, 0xa0); 85 if (response < 0) { 86 err("emi62: set_reset (%d) failed", reset_bit); 87 } 88 return response; 89 } 90 91 #define FW_LOAD_SIZE 1023 92 93 static int emi62_load_firmware (struct usb_device *dev) 94 { 95 int err; 96 int i; 97 int pos = 0; /* Position in hex record */ 98 __u32 addr; /* Address to write */ 99 __u8 *buf; 100 101 dev_dbg(&dev->dev, "load_firmware\n"); 102 buf = kmalloc(FW_LOAD_SIZE, GFP_KERNEL); 103 if (!buf) { 104 err( "%s - error loading firmware: error = %d", __FUNCTION__, -ENOMEM); 105 err = -ENOMEM; 106 goto wraperr; 107 } 108 109 /* Assert reset (stop the CPU in the EMI) */ 110 err = emi62_set_reset(dev,1); 111 if (err < 0) { 112 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 113 goto wraperr; 114 } 115 116 /* 1. We need to put the loader for the FPGA into the EZ-USB */ 117 for (i=0; g_emi62_loader[i].type == 0; i++) { 118 err = emi62_writememory(dev, g_emi62_loader[i].address, g_emi62_loader[i].data, g_emi62_loader[i].length, ANCHOR_LOAD_INTERNAL); 119 if (err < 0) { 120 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 121 goto wraperr; 122 } 123 } 124 125 /* De-assert reset (let the CPU run) */ 126 err = emi62_set_reset(dev,0); 127 msleep(250); /* let device settle */ 128 129 /* 2. We upload the FPGA firmware into the EMI 130 * Note: collect up to 1023 (yes!) bytes and send them with 131 * a single request. This is _much_ faster! */ 132 do { 133 i = 0; 134 addr = g_emi62bs[pos].address; 135 136 /* intel hex records are terminated with type 0 element */ 137 while ((g_emi62bs[pos].type == 0) && (i + g_emi62bs[pos].length < FW_LOAD_SIZE)) { 138 memcpy(buf + i, g_emi62bs[pos].data, g_emi62bs[pos].length); 139 i += g_emi62bs[pos].length; 140 pos++; 141 } 142 err = emi62_writememory(dev, addr, buf, i, ANCHOR_LOAD_FPGA); 143 if (err < 0) { 144 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 145 goto wraperr; 146 } 147 } while (i > 0); 148 149 /* Assert reset (stop the CPU in the EMI) */ 150 err = emi62_set_reset(dev,1); 151 if (err < 0) { 152 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 153 goto wraperr; 154 } 155 156 /* 3. We need to put the loader for the firmware into the EZ-USB (again...) */ 157 for (i=0; g_emi62_loader[i].type == 0; i++) { 158 err = emi62_writememory(dev, g_emi62_loader[i].address, g_emi62_loader[i].data, g_emi62_loader[i].length, ANCHOR_LOAD_INTERNAL); 159 if (err < 0) { 160 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 161 goto wraperr; 162 } 163 } 164 165 /* De-assert reset (let the CPU run) */ 166 err = emi62_set_reset(dev,0); 167 if (err < 0) { 168 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 169 goto wraperr; 170 } 171 msleep(250); /* let device settle */ 172 173 /* 4. We put the part of the firmware that lies in the external RAM into the EZ-USB */ 174 175 /* FIXME: quick and dirty ifdefs */ 176 #ifdef SPDIF 177 for (i=0; g_HexSpdifFw62[i].type == 0; i++) { 178 if (!INTERNAL_RAM(g_HexSpdifFw62[i].address)) { 179 err = emi62_writememory(dev, g_HexSpdifFw62[i].address, g_HexSpdifFw62[i].data, g_HexSpdifFw62[i].length, ANCHOR_LOAD_EXTERNAL); 180 if (err < 0) { 181 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 182 goto wraperr; 183 } 184 } 185 } 186 #else /* MIDI */ 187 for (i=0; g_HexMidiFw62[i].type == 0; i++) { 188 if (!INTERNAL_RAM(g_HexMidiFw62[i].address)) { 189 err = emi62_writememory(dev, g_HexMidiFw62[i].address, g_HexMidiFw62[i].data, g_HexMidiFw62[i].length, ANCHOR_LOAD_EXTERNAL); 190 if (err < 0) { 191 err("%s - error loading firmware: error = %d\n", __FUNCTION__, err); 192 goto wraperr; 193 return err; 194 } 195 } 196 } 197 #endif 198 /* Assert reset (stop the CPU in the EMI) */ 199 err = emi62_set_reset(dev,1); 200 if (err < 0) { 201 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 202 goto wraperr; 203 } 204 205 /* FIXME: quick and dirty ifdefs */ 206 #ifdef SPDIF 207 for (i=0; g_HexSpdifFw62[i].type == 0; i++) { 208 if (INTERNAL_RAM(g_HexSpdifFw62[i].address)) { 209 err = emi62_writememory(dev, g_HexSpdifFw62[i].address, g_HexSpdifFw62[i].data, g_HexSpdifFw62[i].length, ANCHOR_LOAD_INTERNAL); 210 if (err < 0) { 211 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 212 goto wraperr; 213 } 214 } 215 } 216 #else /* MIDI */ 217 for (i=0; g_HexMidiFw62[i].type == 0; i++) { 218 if (INTERNAL_RAM(g_HexMidiFw62[i].address)) { 219 err = emi62_writememory(dev, g_HexMidiFw62[i].address, g_HexMidiFw62[i].data, g_HexMidiFw62[i].length, ANCHOR_LOAD_INTERNAL); 220 if (err < 0) { 221 err("%s - error loading firmware: error = %d\n", __FUNCTION__, err); 222 goto wraperr; 223 } 224 } 225 } 226 #endif 227 228 /* De-assert reset (let the CPU run) */ 229 err = emi62_set_reset(dev,0); 230 if (err < 0) { 231 err("%s - error loading firmware: error = %d", __FUNCTION__, err); 232 goto wraperr; 233 } 234 msleep(250); /* let device settle */ 235 236 kfree(buf); 237 238 /* return 1 to fail the driver inialization 239 * and give real driver change to load */ 240 return 1; 241 242 wraperr: 243 kfree(buf); 244 dev_err(&dev->dev, "Error\n"); 245 return err; 246 } 247 248 static __devinitdata struct usb_device_id id_table [] = { 249 { USB_DEVICE(EMI62_VENDOR_ID, EMI62_PRODUCT_ID) }, 250 { } /* Terminating entry */ 251 }; 252 253 MODULE_DEVICE_TABLE (usb, id_table); 254 255 static int emi62_probe(struct usb_interface *intf, const struct usb_device_id *id) 256 { 257 struct usb_device *dev = interface_to_usbdev(intf); 258 dev_dbg(&intf->dev, "emi62_probe\n"); 259 260 info("%s start", __FUNCTION__); 261 262 emi62_load_firmware(dev); 263 264 /* do not return the driver context, let real audio driver do that */ 265 return -EIO; 266 } 267 268 static void emi62_disconnect(struct usb_interface *intf) 269 { 270 } 271 272 static struct usb_driver emi62_driver = { 273 .name = "emi62 - firmware loader", 274 .probe = emi62_probe, 275 .disconnect = emi62_disconnect, 276 .id_table = id_table, 277 }; 278 279 static int __init emi62_init (void) 280 { 281 int retval; 282 retval = usb_register (&emi62_driver); 283 if (retval) 284 printk(KERN_ERR "adi-emi: registration failed\n"); 285 return retval; 286 } 287 288 static void __exit emi62_exit (void) 289 { 290 usb_deregister (&emi62_driver); 291 } 292 293 module_init(emi62_init); 294 module_exit(emi62_exit); 295 296 MODULE_AUTHOR("tapio laxstr�m"); 297 MODULE_DESCRIPTION("Emagic EMI 6|2m firmware loader."); 298 MODULE_LICENSE("GPL"); 299 300 /* vi:ai:syntax=c:sw=8:ts=8:tw=80 301 */ 302