19bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota/* DVB USB compliant Linux driver for the 2458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota * - GENPIX 8pks/qpsk/DCII USB2.0 DVB-S module 39bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * 4458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota * Copyright (C) 2006,2007 Alan Nisota (alannisota@gmail.com) 5458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota * Copyright (C) 2006,2007 Genpix Electronics (genpix@genpix-electronics.com) 69bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * 79bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * Thanks to GENPIX for the sample code used to implement this module. 89bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * 99bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * This module is based off the vp7045 and vp702x modules 109bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * 119bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * This program is free software; you can redistribute it and/or modify it 129bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * under the terms of the GNU General Public License as published by the Free 139bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * Software Foundation, version 2. 149bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * 159bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota * see Documentation/dvb/README.dvb-usb for more information 169bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota */ 179bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota#include "gp8psk.h" 189bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 199bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota/* debug */ 209bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotastatic char bcm4500_firmware[] = "dvb-usb-gp8psk-02.fw"; 219bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotaint dvb_usb_gp8psk_debug; 229bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotamodule_param_named(debug,dvb_usb_gp8psk_debug, int, 0644); 239bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan NisotaMODULE_PARM_DESC(debug, "set debugging level (1=info,xfer=2,rc=4 (or-able))." DVB_USB_DEBUG_STATUS); 249bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2578e92006f410a4044f8c1760c25ac9d11d259aa2Janne GrunauDVB_DEFINE_MOD_OPT_ADAPTER_NR(adapter_nr); 2678e92006f410a4044f8c1760c25ac9d11d259aa2Janne Grunau 279e21ccaa69674e1b0aa887722801258f7de842dbVDR Userstatic int gp8psk_get_fw_version(struct dvb_usb_device *d, u8 *fw_vers) 289e21ccaa69674e1b0aa887722801258f7de842dbVDR User{ 299e21ccaa69674e1b0aa887722801258f7de842dbVDR User return (gp8psk_usb_in_op(d, GET_FW_VERS, 0, 0, fw_vers, 6)); 309e21ccaa69674e1b0aa887722801258f7de842dbVDR User} 319e21ccaa69674e1b0aa887722801258f7de842dbVDR User 329e21ccaa69674e1b0aa887722801258f7de842dbVDR Userstatic int gp8psk_get_fpga_version(struct dvb_usb_device *d, u8 *fpga_vers) 339e21ccaa69674e1b0aa887722801258f7de842dbVDR User{ 349e21ccaa69674e1b0aa887722801258f7de842dbVDR User return (gp8psk_usb_in_op(d, GET_FPGA_VERS, 0, 0, fpga_vers, 1)); 359e21ccaa69674e1b0aa887722801258f7de842dbVDR User} 369e21ccaa69674e1b0aa887722801258f7de842dbVDR User 379e21ccaa69674e1b0aa887722801258f7de842dbVDR Userstatic void gp8psk_info(struct dvb_usb_device *d) 389e21ccaa69674e1b0aa887722801258f7de842dbVDR User{ 399e21ccaa69674e1b0aa887722801258f7de842dbVDR User u8 fpga_vers, fw_vers[6]; 409e21ccaa69674e1b0aa887722801258f7de842dbVDR User 419e21ccaa69674e1b0aa887722801258f7de842dbVDR User if (!gp8psk_get_fw_version(d, fw_vers)) 429e21ccaa69674e1b0aa887722801258f7de842dbVDR User info("FW Version = %i.%02i.%i (0x%x) Build %4i/%02i/%02i", 439e21ccaa69674e1b0aa887722801258f7de842dbVDR User fw_vers[2], fw_vers[1], fw_vers[0], GP8PSK_FW_VERS(fw_vers), 449e21ccaa69674e1b0aa887722801258f7de842dbVDR User 2000 + fw_vers[5], fw_vers[4], fw_vers[3]); 459e21ccaa69674e1b0aa887722801258f7de842dbVDR User else 469e21ccaa69674e1b0aa887722801258f7de842dbVDR User info("failed to get FW version"); 479e21ccaa69674e1b0aa887722801258f7de842dbVDR User 489e21ccaa69674e1b0aa887722801258f7de842dbVDR User if (!gp8psk_get_fpga_version(d, &fpga_vers)) 499e21ccaa69674e1b0aa887722801258f7de842dbVDR User info("FPGA Version = %i", fpga_vers); 509e21ccaa69674e1b0aa887722801258f7de842dbVDR User else 519e21ccaa69674e1b0aa887722801258f7de842dbVDR User info("failed to get FPGA version"); 529e21ccaa69674e1b0aa887722801258f7de842dbVDR User} 539e21ccaa69674e1b0aa887722801258f7de842dbVDR User 549bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotaint gp8psk_usb_in_op(struct dvb_usb_device *d, u8 req, u16 value, u16 index, u8 *b, int blen) 559bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota{ 569bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota int ret = 0,try = 0; 579bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 589bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if ((ret = mutex_lock_interruptible(&d->usb_mutex))) 599bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return ret; 609bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 619bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota while (ret >= 0 && ret != blen && try < 3) { 629bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota ret = usb_control_msg(d->udev, 639bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota usb_rcvctrlpipe(d->udev,0), 649bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota req, 659bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota USB_TYPE_VENDOR | USB_DIR_IN, 669bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota value,index,b,blen, 679bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2000); 689bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota deb_info("reading number %d (ret: %d)\n",try,ret); 699bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota try++; 709bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } 719bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 729bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (ret < 0 || ret != blen) { 73458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota warn("usb in %d operation failed.", req); 749bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota ret = -EIO; 759bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } else 769bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota ret = 0; 779bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 789bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota deb_xfer("in: req. %x, val: %x, ind: %x, buffer: ",req,value,index); 799bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota debug_dump(b,blen,deb_xfer); 809bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 819bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota mutex_unlock(&d->usb_mutex); 829bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 839bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return ret; 849bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota} 859bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 869bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotaint gp8psk_usb_out_op(struct dvb_usb_device *d, u8 req, u16 value, 879bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota u16 index, u8 *b, int blen) 889bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota{ 899bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota int ret; 909bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 919bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota deb_xfer("out: req. %x, val: %x, ind: %x, buffer: ",req,value,index); 929bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota debug_dump(b,blen,deb_xfer); 939bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 949bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if ((ret = mutex_lock_interruptible(&d->usb_mutex))) 959bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return ret; 969bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 979bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (usb_control_msg(d->udev, 989bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota usb_sndctrlpipe(d->udev,0), 999bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota req, 1009bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota USB_TYPE_VENDOR | USB_DIR_OUT, 1019bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota value,index,b,blen, 1029bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2000) != blen) { 1039bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota warn("usb out operation failed."); 1049bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota ret = -EIO; 1059bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } else 1069bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota ret = 0; 1079bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota mutex_unlock(&d->usb_mutex); 1089bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 1099bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return ret; 1109bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota} 1119bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 1129bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotastatic int gp8psk_load_bcm4500fw(struct dvb_usb_device *d) 1139bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota{ 1149bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota int ret; 1159bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota const struct firmware *fw = NULL; 1163a9282cacdb13466b9c745518237938434dbde0bDavid Woodhouse const u8 *ptr; 1173a9282cacdb13466b9c745518237938434dbde0bDavid Woodhouse u8 *buf; 1189bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if ((ret = request_firmware(&fw, bcm4500_firmware, 1199bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota &d->udev->dev)) != 0) { 1209bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota err("did not find the bcm4500 firmware file. (%s) " 1219bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota "Please see linux/Documentation/dvb/ for more details on firmware-problems. (%d)", 1229bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota bcm4500_firmware,ret); 1239bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return ret; 1249bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } 1259bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 126976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher ret = -EINVAL; 127976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher 128976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher if (gp8psk_usb_out_op(d, LOAD_BCM4500,1,0,NULL, 0)) 129976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher goto out_rel_fw; 1309bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 131458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota info("downloading bcm4500 firmware from file '%s'",bcm4500_firmware); 1329bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 1339bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota ptr = fw->data; 134458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota buf = kmalloc(64, GFP_KERNEL | GFP_DMA); 135205161ed03b53c467dd669a340ea704ce0fb6f9eJiri Slaby if (!buf) { 136205161ed03b53c467dd669a340ea704ce0fb6f9eJiri Slaby ret = -ENOMEM; 137205161ed03b53c467dd669a340ea704ce0fb6f9eJiri Slaby goto out_rel_fw; 138205161ed03b53c467dd669a340ea704ce0fb6f9eJiri Slaby } 1399bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 1409bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota while (ptr[0] != 0xff) { 1419bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota u16 buflen = ptr[0] + 4; 1429bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (ptr + buflen >= fw->data + fw->size) { 1439bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota err("failed to load bcm4500 firmware."); 144976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher goto out_free; 1459bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } 1469bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota memcpy(buf, ptr, buflen); 1479bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (dvb_usb_generic_write(d, buf, buflen)) { 1489bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota err("failed to load bcm4500 firmware."); 149976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher goto out_free; 1509bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } 1519bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota ptr += buflen; 1529bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } 153976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher 154976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher ret = 0; 155976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher 156976e3483799ce5f718753d67454378d46500f0daPatrick Boettcherout_free: 1579bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota kfree(buf); 158976e3483799ce5f718753d67454378d46500f0daPatrick Boettcherout_rel_fw: 159976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher release_firmware(fw); 160976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher 161976e3483799ce5f718753d67454378d46500f0daPatrick Boettcher return ret; 1629bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota} 1639bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 1649bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotastatic int gp8psk_power_ctrl(struct dvb_usb_device *d, int onoff) 1659bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota{ 1669bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota u8 status, buf; 167458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota int gp_product_id = le16_to_cpu(d->udev->descriptor.idProduct); 168458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota 1699bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (onoff) { 1709bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota gp8psk_usb_in_op(d, GET_8PSK_CONFIG,0,0,&status,1); 171458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (! (status & bm8pskStarted)) { /* started */ 172458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if(gp_product_id == USB_PID_GENPIX_SKYWALKER_CW3K) 173458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota gp8psk_usb_out_op(d, CW3K_INIT, 1, 0, NULL, 0); 1749bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (gp8psk_usb_in_op(d, BOOT_8PSK, 1, 0, &buf, 1)) 1759bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return -EINVAL; 1769e21ccaa69674e1b0aa887722801258f7de842dbVDR User gp8psk_info(d); 177458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota } 1789bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 179458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (gp_product_id == USB_PID_GENPIX_8PSK_REV_1_WARM) 180458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (! (status & bm8pskFW_Loaded)) /* BCM4500 firmware loaded */ 181458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if(gp8psk_load_bcm4500fw(d)) 1827fa7b8583f14889aaceebcd8dca3093987e289f7Marcin Slusarz return -EINVAL; 1839bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 184458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (! (status & bmIntersilOn)) /* LNB Power */ 1859bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (gp8psk_usb_in_op(d, START_INTERSIL, 1, 0, 1869bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota &buf, 1)) 1877fa7b8583f14889aaceebcd8dca3093987e289f7Marcin Slusarz return -EINVAL; 1889bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 189458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota /* Set DVB mode to 1 */ 190458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (gp_product_id == USB_PID_GENPIX_8PSK_REV_1_WARM) 191458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (gp8psk_usb_out_op(d, SET_DVB_MODE, 1, 0, NULL, 0)) 1927fa7b8583f14889aaceebcd8dca3093987e289f7Marcin Slusarz return -EINVAL; 193458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota /* Abort possible TS (if previous tune crashed) */ 194458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (gp8psk_usb_out_op(d, ARM_TRANSFER, 0, 0, NULL, 0)) 1957fa7b8583f14889aaceebcd8dca3093987e289f7Marcin Slusarz return -EINVAL; 1969bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } else { 1979bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota /* Turn off LNB power */ 1989bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (gp8psk_usb_in_op(d, START_INTERSIL, 0, 0, &buf, 1)) 1997fa7b8583f14889aaceebcd8dca3093987e289f7Marcin Slusarz return -EINVAL; 2009bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota /* Turn off 8psk power */ 2019bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota if (gp8psk_usb_in_op(d, BOOT_8PSK, 0, 0, &buf, 1)) 2029bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return -EINVAL; 203458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if(gp_product_id == USB_PID_GENPIX_SKYWALKER_CW3K) 204458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota gp8psk_usb_out_op(d, CW3K_INIT, 0, 0, NULL, 0); 2059bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } 2069bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return 0; 2079bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota} 2089bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 20902ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisotaint gp8psk_bcm4500_reload(struct dvb_usb_device *d) 21002ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota{ 21102ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota u8 buf; 21202ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota int gp_product_id = le16_to_cpu(d->udev->descriptor.idProduct); 21302ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota /* Turn off 8psk power */ 21402ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota if (gp8psk_usb_in_op(d, BOOT_8PSK, 0, 0, &buf, 1)) 21502ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota return -EINVAL; 21602ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota /* Turn On 8psk power */ 21702ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota if (gp8psk_usb_in_op(d, BOOT_8PSK, 1, 0, &buf, 1)) 21802ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota return -EINVAL; 21902ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota /* load BCM4500 firmware */ 22002ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota if (gp_product_id == USB_PID_GENPIX_8PSK_REV_1_WARM) 22102ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota if (gp8psk_load_bcm4500fw(d)) 222da1b5c95e49bb564ae8c61ed135d34ed09acbb66Hans Verkuil return -EINVAL; 22302ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota return 0; 22402ebf23bc20eee5d91d008a9e831e7768d963946Alan Nisota} 2259bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2264d43e13f723e12734257277cc38497fab1efc605Patrick Boettcherstatic int gp8psk_streaming_ctrl(struct dvb_usb_adapter *adap, int onoff) 2279bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota{ 2284d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher return gp8psk_usb_out_op(adap->dev, ARM_TRANSFER, onoff, 0 , NULL, 0); 2299bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota} 2309bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2314d43e13f723e12734257277cc38497fab1efc605Patrick Boettcherstatic int gp8psk_frontend_attach(struct dvb_usb_adapter *adap) 2329bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota{ 23377eed219fed5a913f59329cc846420fdeab0150fMichael Krufky adap->fe_adap[0].fe = gp8psk_fe_attach(adap->dev); 2349bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota return 0; 2359bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota} 2369bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2374d43e13f723e12734257277cc38497fab1efc605Patrick Boettcherstatic struct dvb_usb_device_properties gp8psk_properties; 2389bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2399bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotastatic int gp8psk_usb_probe(struct usb_interface *intf, 2409bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota const struct usb_device_id *id) 2419bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota{ 242458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota int ret; 243458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota struct usb_device *udev = interface_to_usbdev(intf); 24478e92006f410a4044f8c1760c25ac9d11d259aa2Janne Grunau ret = dvb_usb_device_init(intf, &gp8psk_properties, 24578e92006f410a4044f8c1760c25ac9d11d259aa2Janne Grunau THIS_MODULE, NULL, adapter_nr); 246458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota if (ret == 0) { 247458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota info("found Genpix USB device pID = %x (hex)", 248458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota le16_to_cpu(udev->descriptor.idProduct)); 249458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota } 250458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota return ret; 2519bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota} 2529bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2539bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotastatic struct usb_device_id gp8psk_usb_table [] = { 254458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota { USB_DEVICE(USB_VID_GENPIX, USB_PID_GENPIX_8PSK_REV_1_COLD) }, 255458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota { USB_DEVICE(USB_VID_GENPIX, USB_PID_GENPIX_8PSK_REV_1_WARM) }, 256458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota { USB_DEVICE(USB_VID_GENPIX, USB_PID_GENPIX_8PSK_REV_2) }, 257458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota { USB_DEVICE(USB_VID_GENPIX, USB_PID_GENPIX_SKYWALKER_1) }, 258bdd1751b49be2860cc8c6a61e8fadda0caf22e5aDerek Kelly { USB_DEVICE(USB_VID_GENPIX, USB_PID_GENPIX_SKYWALKER_2) }, 25986cf5f84e60fe32e3e665fdc69325f8993970189Alan Nisota/* { USB_DEVICE(USB_VID_GENPIX, USB_PID_GENPIX_SKYWALKER_CW3K) }, */ 2609bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota { 0 }, 2619bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota}; 2629bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan NisotaMODULE_DEVICE_TABLE(usb, gp8psk_usb_table); 2639bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2644d43e13f723e12734257277cc38497fab1efc605Patrick Boettcherstatic struct dvb_usb_device_properties gp8psk_properties = { 2659bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .usb_ctrl = CYPRESS_FX2, 2669bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .firmware = "dvb-usb-gp8psk-01.fw", 2679bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 2684d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher .num_adapters = 1, 2694d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher .adapter = { 2704d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher { 27177eed219fed5a913f59329cc846420fdeab0150fMichael Krufky .num_frontends = 1, 27277eed219fed5a913f59329cc846420fdeab0150fMichael Krufky .fe = {{ 27301451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher .streaming_ctrl = gp8psk_streaming_ctrl, 27401451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher .frontend_attach = gp8psk_frontend_attach, 27501451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher /* parameter for the MPEG2-data transfer */ 2764d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher .stream = { 2774d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher .type = USB_BULK, 27801451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher .count = 7, 27901451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher .endpoint = 0x82, 28001451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher .u = { 28101451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher .bulk = { 28201451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher .buffersize = 8192, 28301451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher } 28401451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher } 28501451e722793f191f6e13c5150dd8664f4439d17Patrick Boettcher }, 28677eed219fed5a913f59329cc846420fdeab0150fMichael Krufky }}, 2874d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher } 2884d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher }, 2894d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher .power_ctrl = gp8psk_power_ctrl, 2904d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher 2914d43e13f723e12734257277cc38497fab1efc605Patrick Boettcher .generic_bulk_ctrl_endpoint = 0x01, 2929bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 293bdd1751b49be2860cc8c6a61e8fadda0caf22e5aDerek Kelly .num_device_descs = 4, 2949bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .devices = { 295458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota { .name = "Genpix 8PSK-to-USB2 Rev.1 DVB-S receiver", 2969bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .cold_ids = { &gp8psk_usb_table[0], NULL }, 2979bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .warm_ids = { &gp8psk_usb_table[1], NULL }, 2989bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota }, 299458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota { .name = "Genpix 8PSK-to-USB2 Rev.2 DVB-S receiver", 300458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota .cold_ids = { NULL }, 301458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota .warm_ids = { &gp8psk_usb_table[2], NULL }, 302458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota }, 303458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota { .name = "Genpix SkyWalker-1 DVB-S receiver", 304458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota .cold_ids = { NULL }, 305458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota .warm_ids = { &gp8psk_usb_table[3], NULL }, 306458b634cd86968032171a4d6db5c89a772ff0348Alan Nisota }, 307bdd1751b49be2860cc8c6a61e8fadda0caf22e5aDerek Kelly { .name = "Genpix SkyWalker-2 DVB-S receiver", 308bdd1751b49be2860cc8c6a61e8fadda0caf22e5aDerek Kelly .cold_ids = { NULL }, 309bdd1751b49be2860cc8c6a61e8fadda0caf22e5aDerek Kelly .warm_ids = { &gp8psk_usb_table[4], NULL }, 310bdd1751b49be2860cc8c6a61e8fadda0caf22e5aDerek Kelly }, 311ab9caf9e221ee1b13186a9144da26ac358f2a6f4Randy Dunlap { NULL }, 3129bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota } 3139bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota}; 3149bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 3159bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota/* usb specific object needed to register this driver with the usb subsystem */ 3169bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisotastatic struct usb_driver gp8psk_usb_driver = { 3179bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .name = "dvb_usb_gp8psk", 3189bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .probe = gp8psk_usb_probe, 3199bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .disconnect = dvb_usb_device_exit, 3209bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota .id_table = gp8psk_usb_table, 3219bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota}; 3229bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 323ecb3b2b35db49778b6d89e3ffd0c400776c20735Greg Kroah-Hartmanmodule_usb_driver(gp8psk_usb_driver); 3249bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan Nisota 3259bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan NisotaMODULE_AUTHOR("Alan Nisota <alannisota@gamil.com>"); 326d12da8e9349667336753709915c5bf7d0de15700Derek KellyMODULE_DESCRIPTION("Driver for Genpix DVB-S"); 327458b634cd86968032171a4d6db5c89a772ff0348Alan NisotaMODULE_VERSION("1.1"); 3289bbe076f364aa7ba8c2e49e417a76d628ffb164cAlan NisotaMODULE_LICENSE("GPL"); 329