dst.c 33 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405
  1. /*
  2. Frontend/Card driver for TwinHan DST Frontend
  3. Copyright (C) 2003 Jamie Honan
  4. Copyright (C) 2004, 2005 Manu Abraham (manu@kromtek.com)
  5. This program is free software; you can redistribute it and/or modify
  6. it under the terms of the GNU General Public License as published by
  7. the Free Software Foundation; either version 2 of the License, or
  8. (at your option) any later version.
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. GNU General Public License for more details.
  13. You should have received a copy of the GNU General Public License
  14. along with this program; if not, write to the Free Software
  15. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  16. */
  17. #include <linux/kernel.h>
  18. #include <linux/module.h>
  19. #include <linux/init.h>
  20. #include <linux/string.h>
  21. #include <linux/slab.h>
  22. #include <linux/vmalloc.h>
  23. #include <linux/delay.h>
  24. #include <asm/div64.h>
  25. #include "dvb_frontend.h"
  26. #include "dst_priv.h"
  27. #include "dst_common.h"
  28. static unsigned int verbose = 1;
  29. module_param(verbose, int, 0644);
  30. MODULE_PARM_DESC(verbose, "verbose startup messages, default is 1 (yes)");
  31. static unsigned int debug = 1;
  32. module_param(debug, int, 0644);
  33. MODULE_PARM_DESC(debug, "debug messages, default is 0 (yes)");
  34. static unsigned int dst_addons;
  35. module_param(dst_addons, int, 0644);
  36. MODULE_PARM_DESC(dst_addons, "CA daughterboard, default is 0 (No addons)");
  37. #define dprintk if (debug) printk
  38. #define HAS_LOCK 1
  39. #define ATTEMPT_TUNE 2
  40. #define HAS_POWER 4
  41. static void dst_packsize(struct dst_state* state, int psize)
  42. {
  43. union dst_gpio_packet bits;
  44. bits.psize = psize;
  45. bt878_device_control(state->bt, DST_IG_TS, &bits);
  46. }
  47. int dst_gpio_outb(struct dst_state* state, u32 mask, u32 enbb, u32 outhigh, int delay)
  48. {
  49. union dst_gpio_packet enb;
  50. union dst_gpio_packet bits;
  51. int err;
  52. enb.enb.mask = mask;
  53. enb.enb.enable = enbb;
  54. if (verbose > 4)
  55. dprintk("%s: mask=[%04x], enbb=[%04x], outhigh=[%04x]\n", __FUNCTION__, mask, enbb, outhigh);
  56. if ((err = bt878_device_control(state->bt, DST_IG_ENABLE, &enb)) < 0) {
  57. dprintk("%s: dst_gpio_enb error (err == %i, mask == %02x, enb == %02x)\n", __FUNCTION__, err, mask, enbb);
  58. return -EREMOTEIO;
  59. }
  60. udelay(1000);
  61. /* because complete disabling means no output, no need to do output packet */
  62. if (enbb == 0)
  63. return 0;
  64. if (delay)
  65. msleep(10);
  66. bits.outp.mask = enbb;
  67. bits.outp.highvals = outhigh;
  68. if ((err = bt878_device_control(state->bt, DST_IG_WRITE, &bits)) < 0) {
  69. dprintk("%s: dst_gpio_outb error (err == %i, enbb == %02x, outhigh == %02x)\n", __FUNCTION__, err, enbb, outhigh);
  70. return -EREMOTEIO;
  71. }
  72. return 0;
  73. }
  74. EXPORT_SYMBOL(dst_gpio_outb);
  75. int dst_gpio_inb(struct dst_state *state, u8 * result)
  76. {
  77. union dst_gpio_packet rd_packet;
  78. int err;
  79. *result = 0;
  80. if ((err = bt878_device_control(state->bt, DST_IG_READ, &rd_packet)) < 0) {
  81. dprintk("%s: dst_gpio_inb error (err == %i)\n", __FUNCTION__, err);
  82. return -EREMOTEIO;
  83. }
  84. *result = (u8) rd_packet.rd.value;
  85. return 0;
  86. }
  87. EXPORT_SYMBOL(dst_gpio_inb);
  88. int rdc_reset_state(struct dst_state *state)
  89. {
  90. if (verbose > 1)
  91. dprintk("%s: Resetting state machine\n", __FUNCTION__);
  92. if (dst_gpio_outb(state, RDC_8820_INT, RDC_8820_INT, 0, NO_DELAY) < 0) {
  93. dprintk("%s: dst_gpio_outb ERROR !\n", __FUNCTION__);
  94. return -1;
  95. }
  96. msleep(10);
  97. if (dst_gpio_outb(state, RDC_8820_INT, RDC_8820_INT, RDC_8820_INT, NO_DELAY) < 0) {
  98. dprintk("%s: dst_gpio_outb ERROR !\n", __FUNCTION__);
  99. msleep(10);
  100. return -1;
  101. }
  102. return 0;
  103. }
  104. EXPORT_SYMBOL(rdc_reset_state);
  105. int rdc_8820_reset(struct dst_state *state)
  106. {
  107. if (verbose > 1)
  108. dprintk("%s: Resetting DST\n", __FUNCTION__);
  109. if (dst_gpio_outb(state, RDC_8820_RESET, RDC_8820_RESET, 0, NO_DELAY) < 0) {
  110. dprintk("%s: dst_gpio_outb ERROR !\n", __FUNCTION__);
  111. return -1;
  112. }
  113. udelay(1000);
  114. if (dst_gpio_outb(state, RDC_8820_RESET, RDC_8820_RESET, RDC_8820_RESET, DELAY) < 0) {
  115. dprintk("%s: dst_gpio_outb ERROR !\n", __FUNCTION__);
  116. return -1;
  117. }
  118. return 0;
  119. }
  120. EXPORT_SYMBOL(rdc_8820_reset);
  121. int dst_pio_enable(struct dst_state *state)
  122. {
  123. if (dst_gpio_outb(state, ~0, RDC_8820_PIO_0_ENABLE, 0, NO_DELAY) < 0) {
  124. dprintk("%s: dst_gpio_outb ERROR !\n", __FUNCTION__);
  125. return -1;
  126. }
  127. udelay(1000);
  128. return 0;
  129. }
  130. EXPORT_SYMBOL(dst_pio_enable);
  131. int dst_pio_disable(struct dst_state *state)
  132. {
  133. if (dst_gpio_outb(state, ~0, RDC_8820_PIO_0_DISABLE, RDC_8820_PIO_0_DISABLE, NO_DELAY) < 0) {
  134. dprintk("%s: dst_gpio_outb ERROR !\n", __FUNCTION__);
  135. return -1;
  136. }
  137. if (state->type_flags & DST_TYPE_HAS_FW_1)
  138. udelay(1000);
  139. return 0;
  140. }
  141. EXPORT_SYMBOL(dst_pio_disable);
  142. int dst_wait_dst_ready(struct dst_state *state, u8 delay_mode)
  143. {
  144. u8 reply;
  145. int i;
  146. for (i = 0; i < 200; i++) {
  147. if (dst_gpio_inb(state, &reply) < 0) {
  148. dprintk("%s: dst_gpio_inb ERROR !\n", __FUNCTION__);
  149. return -1;
  150. }
  151. if ((reply & RDC_8820_PIO_0_ENABLE) == 0) {
  152. if (verbose > 4)
  153. dprintk("%s: dst wait ready after %d\n", __FUNCTION__, i);
  154. return 1;
  155. }
  156. msleep(10);
  157. }
  158. if (verbose > 1)
  159. dprintk("%s: dst wait NOT ready after %d\n", __FUNCTION__, i);
  160. return 0;
  161. }
  162. EXPORT_SYMBOL(dst_wait_dst_ready);
  163. int dst_error_recovery(struct dst_state *state)
  164. {
  165. dprintk("%s: Trying to return from previous errors...\n", __FUNCTION__);
  166. dst_pio_disable(state);
  167. msleep(10);
  168. dst_pio_enable(state);
  169. msleep(10);
  170. return 0;
  171. }
  172. EXPORT_SYMBOL(dst_error_recovery);
  173. int dst_error_bailout(struct dst_state *state)
  174. {
  175. dprintk("%s: Trying to bailout from previous error...\n", __FUNCTION__);
  176. rdc_8820_reset(state);
  177. dst_pio_disable(state);
  178. msleep(10);
  179. return 0;
  180. }
  181. EXPORT_SYMBOL(dst_error_bailout);
  182. int dst_comm_init(struct dst_state* state)
  183. {
  184. if (verbose > 1)
  185. dprintk ("%s: Initializing DST..\n", __FUNCTION__);
  186. if ((dst_pio_enable(state)) < 0) {
  187. dprintk("%s: PIO Enable Failed.\n", __FUNCTION__);
  188. return -1;
  189. }
  190. if ((rdc_reset_state(state)) < 0) {
  191. dprintk("%s: RDC 8820 State RESET Failed.\n", __FUNCTION__);
  192. return -1;
  193. }
  194. if (state->type_flags & DST_TYPE_HAS_FW_1)
  195. msleep(100);
  196. else
  197. msleep(5);
  198. return 0;
  199. }
  200. EXPORT_SYMBOL(dst_comm_init);
  201. int write_dst(struct dst_state *state, u8 *data, u8 len)
  202. {
  203. struct i2c_msg msg = {
  204. .addr = state->config->demod_address,.flags = 0,.buf = data,.len = len
  205. };
  206. int err;
  207. int cnt;
  208. if (debug && (verbose > 4)) {
  209. u8 i;
  210. if (verbose > 4) {
  211. dprintk("%s writing", __FUNCTION__);
  212. for (i = 0; i < len; i++)
  213. dprintk(" %02x", data[i]);
  214. dprintk("\n");
  215. }
  216. }
  217. for (cnt = 0; cnt < 2; cnt++) {
  218. if ((err = i2c_transfer(state->i2c, &msg, 1)) < 0) {
  219. dprintk("%s: _write_dst error (err == %i, len == 0x%02x, b0 == 0x%02x)\n", __FUNCTION__, err, len, data[0]);
  220. dst_error_recovery(state);
  221. continue;
  222. } else
  223. break;
  224. }
  225. if (cnt >= 2) {
  226. if (verbose > 1)
  227. printk("%s: RDC 8820 RESET...\n", __FUNCTION__);
  228. dst_error_bailout(state);
  229. return -1;
  230. }
  231. return 0;
  232. }
  233. EXPORT_SYMBOL(write_dst);
  234. int read_dst(struct dst_state *state, u8 * ret, u8 len)
  235. {
  236. struct i2c_msg msg = {.addr = state->config->demod_address,.flags = I2C_M_RD,.buf = ret,.len = len };
  237. int err;
  238. int cnt;
  239. for (cnt = 0; cnt < 2; cnt++) {
  240. if ((err = i2c_transfer(state->i2c, &msg, 1)) < 0) {
  241. dprintk("%s: read_dst error (err == %i, len == 0x%02x, b0 == 0x%02x)\n", __FUNCTION__, err, len, ret[0]);
  242. dst_error_recovery(state);
  243. continue;
  244. } else
  245. break;
  246. }
  247. if (cnt >= 2) {
  248. if (verbose > 1)
  249. printk("%s: RDC 8820 RESET...\n", __FUNCTION__);
  250. dst_error_bailout(state);
  251. return -1;
  252. }
  253. if (debug && (verbose > 4)) {
  254. dprintk("%s reply is 0x%x\n", __FUNCTION__, ret[0]);
  255. for (err = 1; err < len; err++)
  256. dprintk(" 0x%x", ret[err]);
  257. if (err > 1)
  258. dprintk("\n");
  259. }
  260. return 0;
  261. }
  262. EXPORT_SYMBOL(read_dst);
  263. static int dst_set_freq(struct dst_state *state, u32 freq)
  264. {
  265. u8 *val;
  266. state->frequency = freq;
  267. if (debug > 4)
  268. dprintk("%s: set Frequency %u\n", __FUNCTION__, freq);
  269. if (state->dst_type == DST_TYPE_IS_SAT) {
  270. freq = freq / 1000;
  271. if (freq < 950 || freq > 2150)
  272. return -EINVAL;
  273. val = &state->tx_tuna[0];
  274. val[2] = (freq >> 8) & 0x7f;
  275. val[3] = (u8) freq;
  276. val[4] = 1;
  277. val[8] &= ~4;
  278. if (freq < 1531)
  279. val[8] |= 4;
  280. } else if (state->dst_type == DST_TYPE_IS_TERR) {
  281. freq = freq / 1000;
  282. if (freq < 137000 || freq > 858000)
  283. return -EINVAL;
  284. val = &state->tx_tuna[0];
  285. val[2] = (freq >> 16) & 0xff;
  286. val[3] = (freq >> 8) & 0xff;
  287. val[4] = (u8) freq;
  288. val[5] = 0;
  289. switch (state->bandwidth) {
  290. case BANDWIDTH_6_MHZ:
  291. val[6] = 6;
  292. break;
  293. case BANDWIDTH_7_MHZ:
  294. case BANDWIDTH_AUTO:
  295. val[6] = 7;
  296. break;
  297. case BANDWIDTH_8_MHZ:
  298. val[6] = 8;
  299. break;
  300. }
  301. val[7] = 0;
  302. val[8] = 0;
  303. } else if (state->dst_type == DST_TYPE_IS_CABLE) {
  304. /* guess till will get one */
  305. freq = freq / 1000;
  306. val = &state->tx_tuna[0];
  307. val[2] = (freq >> 16) & 0xff;
  308. val[3] = (freq >> 8) & 0xff;
  309. val[4] = (u8) freq;
  310. } else
  311. return -EINVAL;
  312. return 0;
  313. }
  314. static int dst_set_bandwidth(struct dst_state* state, fe_bandwidth_t bandwidth)
  315. {
  316. u8 *val;
  317. state->bandwidth = bandwidth;
  318. if (state->dst_type != DST_TYPE_IS_TERR)
  319. return 0;
  320. val = &state->tx_tuna[0];
  321. switch (bandwidth) {
  322. case BANDWIDTH_6_MHZ:
  323. val[6] = 6;
  324. break;
  325. case BANDWIDTH_7_MHZ:
  326. val[6] = 7;
  327. break;
  328. case BANDWIDTH_8_MHZ:
  329. val[6] = 8;
  330. break;
  331. default:
  332. return -EINVAL;
  333. }
  334. return 0;
  335. }
  336. static int dst_set_inversion(struct dst_state* state, fe_spectral_inversion_t inversion)
  337. {
  338. u8 *val;
  339. state->inversion = inversion;
  340. val = &state->tx_tuna[0];
  341. val[8] &= ~0x80;
  342. switch (inversion) {
  343. case INVERSION_OFF:
  344. break;
  345. case INVERSION_ON:
  346. val[8] |= 0x80;
  347. break;
  348. default:
  349. return -EINVAL;
  350. }
  351. return 0;
  352. }
  353. static int dst_set_fec(struct dst_state* state, fe_code_rate_t fec)
  354. {
  355. state->fec = fec;
  356. return 0;
  357. }
  358. static fe_code_rate_t dst_get_fec(struct dst_state* state)
  359. {
  360. return state->fec;
  361. }
  362. static int dst_set_symbolrate(struct dst_state* state, u32 srate)
  363. {
  364. u8 *val;
  365. u32 symcalc;
  366. u64 sval;
  367. state->symbol_rate = srate;
  368. if (state->dst_type == DST_TYPE_IS_TERR) {
  369. return 0;
  370. }
  371. if (debug > 4)
  372. dprintk("%s: set symrate %u\n", __FUNCTION__, srate);
  373. srate /= 1000;
  374. val = &state->tx_tuna[0];
  375. if (state->type_flags & DST_TYPE_HAS_SYMDIV) {
  376. sval = srate;
  377. sval <<= 20;
  378. do_div(sval, 88000);
  379. symcalc = (u32) sval;
  380. if (debug > 4)
  381. dprintk("%s: set symcalc %u\n", __FUNCTION__, symcalc);
  382. val[5] = (u8) (symcalc >> 12);
  383. val[6] = (u8) (symcalc >> 4);
  384. val[7] = (u8) (symcalc << 4);
  385. } else {
  386. val[5] = (u8) (srate >> 16) & 0x7f;
  387. val[6] = (u8) (srate >> 8);
  388. val[7] = (u8) srate;
  389. }
  390. val[8] &= ~0x20;
  391. if (srate > 8000)
  392. val[8] |= 0x20;
  393. return 0;
  394. }
  395. u8 dst_check_sum(u8 * buf, u32 len)
  396. {
  397. u32 i;
  398. u8 val = 0;
  399. if (!len)
  400. return 0;
  401. for (i = 0; i < len; i++) {
  402. val += buf[i];
  403. }
  404. return ((~val) + 1);
  405. }
  406. EXPORT_SYMBOL(dst_check_sum);
  407. static void dst_type_flags_print(u32 type_flags)
  408. {
  409. printk("DST type flags :");
  410. if (type_flags & DST_TYPE_HAS_NEWTUNE)
  411. printk(" 0x%x newtuner", DST_TYPE_HAS_NEWTUNE);
  412. if (type_flags & DST_TYPE_HAS_TS204)
  413. printk(" 0x%x ts204", DST_TYPE_HAS_TS204);
  414. if (type_flags & DST_TYPE_HAS_SYMDIV)
  415. printk(" 0x%x symdiv", DST_TYPE_HAS_SYMDIV);
  416. if (type_flags & DST_TYPE_HAS_FW_1)
  417. printk(" 0x%x firmware version = 1", DST_TYPE_HAS_FW_1);
  418. if (type_flags & DST_TYPE_HAS_FW_2)
  419. printk(" 0x%x firmware version = 2", DST_TYPE_HAS_FW_2);
  420. if (type_flags & DST_TYPE_HAS_FW_3)
  421. printk(" 0x%x firmware version = 3", DST_TYPE_HAS_FW_3);
  422. // if ((type_flags & DST_TYPE_HAS_FW_BUILD) && new_fw)
  423. printk("\n");
  424. }
  425. static int dst_type_print (u8 type)
  426. {
  427. char *otype;
  428. switch (type) {
  429. case DST_TYPE_IS_SAT:
  430. otype = "satellite";
  431. break;
  432. case DST_TYPE_IS_TERR:
  433. otype = "terrestrial";
  434. break;
  435. case DST_TYPE_IS_CABLE:
  436. otype = "cable";
  437. break;
  438. default:
  439. printk("%s: invalid dst type %d\n", __FUNCTION__, type);
  440. return -EINVAL;
  441. }
  442. printk("DST type : %s\n", otype);
  443. return 0;
  444. }
  445. /*
  446. Known cards list
  447. Satellite
  448. -------------------
  449. 200103A
  450. VP-1020 DST-MOT LG(old), TS=188
  451. VP-1020 DST-03T LG(new), TS=204
  452. VP-1022 DST-03T LG(new), TS=204
  453. VP-1025 DST-03T LG(new), TS=204
  454. VP-1030 DSTMCI, LG(new), TS=188
  455. VP-1032 DSTMCI, LG(new), TS=188
  456. Cable
  457. -------------------
  458. VP-2030 DCT-CI, Samsung, TS=204
  459. VP-2021 DCT-CI, Unknown, TS=204
  460. VP-2031 DCT-CI, Philips, TS=188
  461. VP-2040 DCT-CI, Philips, TS=188, with CA daughter board
  462. VP-2040 DCT-CI, Philips, TS=204, without CA daughter board
  463. Terrestrial
  464. -------------------
  465. VP-3050 DTTNXT TS=188
  466. VP-3040 DTT-CI, Philips, TS=188
  467. VP-3040 DTT-CI, Philips, TS=204
  468. ATSC
  469. -------------------
  470. VP-3220 ATSCDI, TS=188
  471. VP-3250 ATSCAD, TS=188
  472. */
  473. struct dst_types dst_tlist[] = {
  474. {
  475. .device_id = "200103A",
  476. .offset = 0,
  477. .dst_type = DST_TYPE_IS_SAT,
  478. .type_flags = DST_TYPE_HAS_SYMDIV | DST_TYPE_HAS_FW_1,
  479. .dst_feature = 0
  480. }, /* obsolete */
  481. {
  482. .device_id = "DST-020",
  483. .offset = 0,
  484. .dst_type = DST_TYPE_IS_SAT,
  485. .type_flags = DST_TYPE_HAS_SYMDIV | DST_TYPE_HAS_FW_1,
  486. .dst_feature = 0
  487. }, /* obsolete */
  488. {
  489. .device_id = "DST-030",
  490. .offset = 0,
  491. .dst_type = DST_TYPE_IS_SAT,
  492. .type_flags = DST_TYPE_HAS_TS204 | DST_TYPE_HAS_NEWTUNE | DST_TYPE_HAS_FW_1,
  493. .dst_feature = 0
  494. }, /* obsolete */
  495. {
  496. .device_id = "DST-03T",
  497. .offset = 0,
  498. .dst_type = DST_TYPE_IS_SAT,
  499. .type_flags = DST_TYPE_HAS_SYMDIV | DST_TYPE_HAS_TS204 | DST_TYPE_HAS_FW_2,
  500. .dst_feature = DST_TYPE_HAS_DISEQC3 | DST_TYPE_HAS_DISEQC4 | DST_TYPE_HAS_DISEQC5
  501. | DST_TYPE_HAS_MAC | DST_TYPE_HAS_MOTO
  502. },
  503. {
  504. .device_id = "DST-MOT",
  505. .offset = 0,
  506. .dst_type = DST_TYPE_IS_SAT,
  507. .type_flags = DST_TYPE_HAS_SYMDIV | DST_TYPE_HAS_FW_1,
  508. .dst_feature = 0
  509. }, /* obsolete */
  510. {
  511. .device_id = "DST-CI",
  512. .offset = 1,
  513. .dst_type = DST_TYPE_IS_SAT,
  514. .type_flags = DST_TYPE_HAS_TS204 | DST_TYPE_HAS_NEWTUNE | DST_TYPE_HAS_FW_1,
  515. .dst_feature = DST_TYPE_HAS_CA
  516. }, /* An OEM board */
  517. {
  518. .device_id = "DSTMCI",
  519. .offset = 1,
  520. .dst_type = DST_TYPE_IS_SAT,
  521. .type_flags = DST_TYPE_HAS_NEWTUNE | DST_TYPE_HAS_FW_2 | DST_TYPE_HAS_FW_BUILD,
  522. .dst_feature = DST_TYPE_HAS_CA | DST_TYPE_HAS_DISEQC3 | DST_TYPE_HAS_DISEQC4
  523. | DST_TYPE_HAS_MOTO | DST_TYPE_HAS_MAC
  524. },
  525. {
  526. .device_id = "DSTFCI",
  527. .offset = 1,
  528. .dst_type = DST_TYPE_IS_SAT,
  529. .type_flags = DST_TYPE_HAS_NEWTUNE | DST_TYPE_HAS_FW_1,
  530. .dst_feature = 0
  531. }, /* unknown to vendor */
  532. {
  533. .device_id = "DCT-CI",
  534. .offset = 1,
  535. .dst_type = DST_TYPE_IS_CABLE,
  536. .type_flags = DST_TYPE_HAS_TS204 | DST_TYPE_HAS_NEWTUNE | DST_TYPE_HAS_FW_1
  537. | DST_TYPE_HAS_FW_2 | DST_TYPE_HAS_FW_BUILD,
  538. .dst_feature = DST_TYPE_HAS_CA
  539. },
  540. {
  541. .device_id = "DCTNEW",
  542. .offset = 1,
  543. .dst_type = DST_TYPE_IS_CABLE,
  544. .type_flags = DST_TYPE_HAS_NEWTUNE | DST_TYPE_HAS_FW_3,
  545. .dst_feature = 0
  546. },
  547. {
  548. .device_id = "DTT-CI",
  549. .offset = 1,
  550. .dst_type = DST_TYPE_IS_TERR,
  551. .type_flags = DST_TYPE_HAS_TS204 | DST_TYPE_HAS_FW_2 | DST_TYPE_HAS_FW_BUILD,
  552. .dst_feature = 0
  553. },
  554. {
  555. .device_id = "DTTDIG",
  556. .offset = 1,
  557. .dst_type = DST_TYPE_IS_TERR,
  558. .type_flags = DST_TYPE_HAS_FW_2,
  559. .dst_feature = 0
  560. },
  561. {
  562. .device_id = "DTTNXT",
  563. .offset = 1,
  564. .dst_type = DST_TYPE_IS_TERR,
  565. .type_flags = DST_TYPE_HAS_FW_2,
  566. .dst_feature = DST_TYPE_HAS_ANALOG
  567. },
  568. {
  569. .device_id = "ATSCDI",
  570. .offset = 1,
  571. .dst_type = DST_TYPE_IS_ATSC,
  572. .type_flags = DST_TYPE_HAS_FW_2,
  573. .dst_feature = 0
  574. },
  575. {
  576. .device_id = "ATSCAD",
  577. .offset = 1,
  578. .dst_type = DST_TYPE_IS_ATSC,
  579. .type_flags = DST_TYPE_HAS_FW_2,
  580. .dst_feature = 0
  581. },
  582. { }
  583. };
  584. static int dst_get_device_id(struct dst_state *state)
  585. {
  586. u8 reply;
  587. int i;
  588. struct dst_types *p_dst_type;
  589. u8 use_dst_type = 0;
  590. u32 use_type_flags = 0;
  591. static u8 device_type[8] = {0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff};
  592. device_type[7] = dst_check_sum(device_type, 7);
  593. if (write_dst(state, device_type, FIXED_COMM))
  594. return -1; /* Write failed */
  595. if ((dst_pio_disable(state)) < 0)
  596. return -1;
  597. if (read_dst(state, &reply, GET_ACK))
  598. return -1; /* Read failure */
  599. if (reply != ACK) {
  600. dprintk("%s: Write not Acknowledged! [Reply=0x%02x]\n", __FUNCTION__, reply);
  601. return -1; /* Unack'd write */
  602. }
  603. if (!dst_wait_dst_ready(state, DEVICE_INIT))
  604. return -1; /* DST not ready yet */
  605. if (read_dst(state, state->rxbuffer, FIXED_COMM))
  606. return -1;
  607. dst_pio_disable(state);
  608. if (state->rxbuffer[7] != dst_check_sum(state->rxbuffer, 7)) {
  609. dprintk("%s: Checksum failure! \n", __FUNCTION__);
  610. return -1; /* Checksum failure */
  611. }
  612. state->rxbuffer[7] = '\0';
  613. for (i = 0, p_dst_type = dst_tlist; i < ARRAY_SIZE (dst_tlist); i++, p_dst_type++) {
  614. if (!strncmp (&state->rxbuffer[p_dst_type->offset], p_dst_type->device_id, strlen (p_dst_type->device_id))) {
  615. use_type_flags = p_dst_type->type_flags;
  616. use_dst_type = p_dst_type->dst_type;
  617. /* Card capabilities */
  618. state->dst_hw_cap = p_dst_type->dst_feature;
  619. printk ("%s: Recognise [%s]\n", __FUNCTION__, p_dst_type->device_id);
  620. break;
  621. }
  622. }
  623. if (i >= sizeof (dst_tlist) / sizeof (dst_tlist [0])) {
  624. printk("%s: Unable to recognize %s or %s\n", __FUNCTION__, &state->rxbuffer[0], &state->rxbuffer[1]);
  625. printk("%s: please email linux-dvb@linuxtv.org with this type in\n", __FUNCTION__);
  626. use_dst_type = DST_TYPE_IS_SAT;
  627. use_type_flags = DST_TYPE_HAS_SYMDIV;
  628. }
  629. dst_type_print(use_dst_type);
  630. state->type_flags = use_type_flags;
  631. state->dst_type = use_dst_type;
  632. dst_type_flags_print(state->type_flags);
  633. if (state->type_flags & DST_TYPE_HAS_TS204) {
  634. dst_packsize(state, 204);
  635. }
  636. return 0;
  637. }
  638. static int dst_probe(struct dst_state *state)
  639. {
  640. if ((rdc_8820_reset(state)) < 0) {
  641. dprintk("%s: RDC 8820 RESET Failed.\n", __FUNCTION__);
  642. return -1;
  643. }
  644. if (dst_addons & DST_TYPE_HAS_CA)
  645. msleep(4000);
  646. else
  647. msleep(100);
  648. if ((dst_comm_init(state)) < 0) {
  649. dprintk("%s: DST Initialization Failed.\n", __FUNCTION__);
  650. return -1;
  651. }
  652. msleep(100);
  653. if (dst_get_device_id(state) < 0) {
  654. dprintk("%s: unknown device.\n", __FUNCTION__);
  655. return -1;
  656. }
  657. return 0;
  658. }
  659. int dst_command(struct dst_state* state, u8 * data, u8 len)
  660. {
  661. u8 reply;
  662. if ((dst_comm_init(state)) < 0) {
  663. dprintk("%s: DST Communication Initialization Failed.\n", __FUNCTION__);
  664. return -1;
  665. }
  666. if (write_dst(state, data, len)) {
  667. if (verbose > 1)
  668. dprintk("%s: Tring to recover.. \n", __FUNCTION__);
  669. if ((dst_error_recovery(state)) < 0) {
  670. dprintk("%s: Recovery Failed.\n", __FUNCTION__);
  671. return -1;
  672. }
  673. return -1;
  674. }
  675. if ((dst_pio_disable(state)) < 0) {
  676. dprintk("%s: PIO Disable Failed.\n", __FUNCTION__);
  677. return -1;
  678. }
  679. if (state->type_flags & DST_TYPE_HAS_FW_1)
  680. udelay(3000);
  681. if (read_dst(state, &reply, GET_ACK)) {
  682. if (verbose > 1)
  683. dprintk("%s: Trying to recover.. \n", __FUNCTION__);
  684. if ((dst_error_recovery(state)) < 0) {
  685. dprintk("%s: Recovery Failed.\n", __FUNCTION__);
  686. return -1;
  687. }
  688. return -1;
  689. }
  690. if (reply != ACK) {
  691. dprintk("%s: write not acknowledged 0x%02x \n", __FUNCTION__, reply);
  692. return -1;
  693. }
  694. if (len >= 2 && data[0] == 0 && (data[1] == 1 || data[1] == 3))
  695. return 0;
  696. // udelay(3000);
  697. if (state->type_flags & DST_TYPE_HAS_FW_1)
  698. udelay(3000);
  699. else
  700. udelay(2000);
  701. if (!dst_wait_dst_ready(state, NO_DELAY))
  702. return -1;
  703. if (read_dst(state, state->rxbuffer, FIXED_COMM)) {
  704. if (verbose > 1)
  705. dprintk("%s: Trying to recover.. \n", __FUNCTION__);
  706. if ((dst_error_recovery(state)) < 0) {
  707. dprintk("%s: Recovery failed.\n", __FUNCTION__);
  708. return -1;
  709. }
  710. return -1;
  711. }
  712. if (state->rxbuffer[7] != dst_check_sum(state->rxbuffer, 7)) {
  713. dprintk("%s: checksum failure\n", __FUNCTION__);
  714. return -1;
  715. }
  716. return 0;
  717. }
  718. EXPORT_SYMBOL(dst_command);
  719. static int dst_get_signal(struct dst_state* state)
  720. {
  721. int retval;
  722. u8 get_signal[] = { 0x00, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfb };
  723. if ((state->diseq_flags & ATTEMPT_TUNE) == 0) {
  724. state->decode_lock = state->decode_strength = state->decode_snr = 0;
  725. return 0;
  726. }
  727. if (0 == (state->diseq_flags & HAS_LOCK)) {
  728. state->decode_lock = state->decode_strength = state->decode_snr = 0;
  729. return 0;
  730. }
  731. if (time_after_eq(jiffies, state->cur_jiff + (HZ / 5))) {
  732. retval = dst_command(state, get_signal, 8);
  733. if (retval < 0)
  734. return retval;
  735. if (state->dst_type == DST_TYPE_IS_SAT) {
  736. state->decode_lock = ((state->rxbuffer[6] & 0x10) == 0) ? 1 : 0;
  737. state->decode_strength = state->rxbuffer[5] << 8;
  738. state->decode_snr = state->rxbuffer[2] << 8 | state->rxbuffer[3];
  739. } else if ((state->dst_type == DST_TYPE_IS_TERR) || (state->dst_type == DST_TYPE_IS_CABLE)) {
  740. state->decode_lock = (state->rxbuffer[1]) ? 1 : 0;
  741. state->decode_strength = state->rxbuffer[4] << 8;
  742. state->decode_snr = state->rxbuffer[3] << 8;
  743. }
  744. state->cur_jiff = jiffies;
  745. }
  746. return 0;
  747. }
  748. static int dst_tone_power_cmd(struct dst_state* state)
  749. {
  750. u8 paket[8] = { 0x00, 0x09, 0xff, 0xff, 0x01, 0x00, 0x00, 0x00 };
  751. if (state->dst_type == DST_TYPE_IS_TERR)
  752. return 0;
  753. if (state->voltage == SEC_VOLTAGE_OFF)
  754. paket[4] = 0;
  755. else
  756. paket[4] = 1;
  757. if (state->tone == SEC_TONE_ON)
  758. paket[2] = 0x02;
  759. else
  760. paket[2] = 0;
  761. paket[3] = state->tx_tuna[3];
  762. paket[7] = dst_check_sum (paket, 7);
  763. dst_command(state, paket, 8);
  764. return 0;
  765. }
  766. static int dst_get_tuna(struct dst_state* state)
  767. {
  768. int retval;
  769. if ((state->diseq_flags & ATTEMPT_TUNE) == 0)
  770. return 0;
  771. state->diseq_flags &= ~(HAS_LOCK);
  772. if (!dst_wait_dst_ready(state, NO_DELAY))
  773. return 0;
  774. if (state->type_flags & DST_TYPE_HAS_NEWTUNE) {
  775. /* how to get variable length reply ???? */
  776. retval = read_dst(state, state->rx_tuna, 10);
  777. } else {
  778. retval = read_dst(state, &state->rx_tuna[2], FIXED_COMM);
  779. }
  780. if (retval < 0) {
  781. dprintk("%s: read not successful\n", __FUNCTION__);
  782. return 0;
  783. }
  784. if (state->type_flags & DST_TYPE_HAS_NEWTUNE) {
  785. if (state->rx_tuna[9] != dst_check_sum(&state->rx_tuna[0], 9)) {
  786. dprintk("%s: checksum failure?\n", __FUNCTION__);
  787. return 0;
  788. }
  789. } else {
  790. if (state->rx_tuna[9] != dst_check_sum(&state->rx_tuna[2], 7)) {
  791. dprintk("%s: checksum failure?\n", __FUNCTION__);
  792. return 0;
  793. }
  794. }
  795. if (state->rx_tuna[2] == 0 && state->rx_tuna[3] == 0)
  796. return 0;
  797. state->decode_freq = ((state->rx_tuna[2] & 0x7f) << 8) + state->rx_tuna[3];
  798. state->decode_lock = 1;
  799. /*
  800. dst->decode_n1 = (dst->rx_tuna[4] << 8) +
  801. (dst->rx_tuna[5]);
  802. dst->decode_n2 = (dst->rx_tuna[8] << 8) +
  803. (dst->rx_tuna[7]);
  804. */
  805. state->diseq_flags |= HAS_LOCK;
  806. /* dst->cur_jiff = jiffies; */
  807. return 1;
  808. }
  809. static int dst_set_voltage(struct dvb_frontend* fe, fe_sec_voltage_t voltage);
  810. static int dst_write_tuna(struct dvb_frontend* fe)
  811. {
  812. struct dst_state* state = fe->demodulator_priv;
  813. int retval;
  814. u8 reply;
  815. if (debug > 4)
  816. dprintk("%s: type_flags 0x%x \n", __FUNCTION__, state->type_flags);
  817. state->decode_freq = 0;
  818. state->decode_lock = state->decode_strength = state->decode_snr = 0;
  819. if (state->dst_type == DST_TYPE_IS_SAT) {
  820. if (!(state->diseq_flags & HAS_POWER))
  821. dst_set_voltage(fe, SEC_VOLTAGE_13);
  822. }
  823. state->diseq_flags &= ~(HAS_LOCK | ATTEMPT_TUNE);
  824. if ((dst_comm_init(state)) < 0) {
  825. dprintk("%s: DST Communication initialization failed.\n", __FUNCTION__);
  826. return -1;
  827. }
  828. if (state->type_flags & DST_TYPE_HAS_NEWTUNE) {
  829. state->tx_tuna[9] = dst_check_sum(&state->tx_tuna[0], 9);
  830. retval = write_dst(state, &state->tx_tuna[0], 10);
  831. } else {
  832. state->tx_tuna[9] = dst_check_sum(&state->tx_tuna[2], 7);
  833. retval = write_dst(state, &state->tx_tuna[2], FIXED_COMM);
  834. }
  835. if (retval < 0) {
  836. dst_pio_disable(state);
  837. dprintk("%s: write not successful\n", __FUNCTION__);
  838. return retval;
  839. }
  840. if ((dst_pio_disable(state)) < 0) {
  841. dprintk("%s: DST PIO disable failed !\n", __FUNCTION__);
  842. return -1;
  843. }
  844. if ((read_dst(state, &reply, GET_ACK) < 0)) {
  845. dprintk("%s: read verify not successful.\n", __FUNCTION__);
  846. return -1;
  847. }
  848. if (reply != ACK) {
  849. dprintk("%s: write not acknowledged 0x%02x \n", __FUNCTION__, reply);
  850. return 0;
  851. }
  852. state->diseq_flags |= ATTEMPT_TUNE;
  853. return dst_get_tuna(state);
  854. }
  855. /*
  856. * line22k0 0x00, 0x09, 0x00, 0xff, 0x01, 0x00, 0x00, 0x00
  857. * line22k1 0x00, 0x09, 0x01, 0xff, 0x01, 0x00, 0x00, 0x00
  858. * line22k2 0x00, 0x09, 0x02, 0xff, 0x01, 0x00, 0x00, 0x00
  859. * tone 0x00, 0x09, 0xff, 0x00, 0x01, 0x00, 0x00, 0x00
  860. * data 0x00, 0x09, 0xff, 0x01, 0x01, 0x00, 0x00, 0x00
  861. * power_off 0x00, 0x09, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00
  862. * power_on 0x00, 0x09, 0xff, 0xff, 0x01, 0x00, 0x00, 0x00
  863. * Diseqc 1 0x00, 0x08, 0x04, 0xe0, 0x10, 0x38, 0xf0, 0xec
  864. * Diseqc 2 0x00, 0x08, 0x04, 0xe0, 0x10, 0x38, 0xf4, 0xe8
  865. * Diseqc 3 0x00, 0x08, 0x04, 0xe0, 0x10, 0x38, 0xf8, 0xe4
  866. * Diseqc 4 0x00, 0x08, 0x04, 0xe0, 0x10, 0x38, 0xfc, 0xe0
  867. */
  868. static int dst_set_diseqc(struct dvb_frontend* fe, struct dvb_diseqc_master_cmd* cmd)
  869. {
  870. struct dst_state* state = fe->demodulator_priv;
  871. u8 paket[8] = { 0x00, 0x08, 0x04, 0xe0, 0x10, 0x38, 0xf0, 0xec };
  872. if (state->dst_type == DST_TYPE_IS_TERR)
  873. return 0;
  874. if (cmd->msg_len == 0 || cmd->msg_len > 4)
  875. return -EINVAL;
  876. memcpy(&paket[3], cmd->msg, cmd->msg_len);
  877. paket[7] = dst_check_sum(&paket[0], 7);
  878. dst_command(state, paket, 8);
  879. return 0;
  880. }
  881. static int dst_set_voltage(struct dvb_frontend* fe, fe_sec_voltage_t voltage)
  882. {
  883. u8 *val;
  884. int need_cmd;
  885. struct dst_state* state = fe->demodulator_priv;
  886. state->voltage = voltage;
  887. if (state->dst_type == DST_TYPE_IS_TERR)
  888. return 0;
  889. need_cmd = 0;
  890. val = &state->tx_tuna[0];
  891. val[8] &= ~0x40;
  892. switch (voltage) {
  893. case SEC_VOLTAGE_13:
  894. if ((state->diseq_flags & HAS_POWER) == 0)
  895. need_cmd = 1;
  896. state->diseq_flags |= HAS_POWER;
  897. break;
  898. case SEC_VOLTAGE_18:
  899. if ((state->diseq_flags & HAS_POWER) == 0)
  900. need_cmd = 1;
  901. state->diseq_flags |= HAS_POWER;
  902. val[8] |= 0x40;
  903. break;
  904. case SEC_VOLTAGE_OFF:
  905. need_cmd = 1;
  906. state->diseq_flags &= ~(HAS_POWER | HAS_LOCK | ATTEMPT_TUNE);
  907. break;
  908. default:
  909. return -EINVAL;
  910. }
  911. if (need_cmd)
  912. dst_tone_power_cmd(state);
  913. return 0;
  914. }
  915. static int dst_set_tone(struct dvb_frontend* fe, fe_sec_tone_mode_t tone)
  916. {
  917. u8 *val;
  918. struct dst_state* state = fe->demodulator_priv;
  919. state->tone = tone;
  920. if (state->dst_type == DST_TYPE_IS_TERR)
  921. return 0;
  922. val = &state->tx_tuna[0];
  923. val[8] &= ~0x1;
  924. switch (tone) {
  925. case SEC_TONE_OFF:
  926. break;
  927. case SEC_TONE_ON:
  928. val[8] |= 1;
  929. break;
  930. default:
  931. return -EINVAL;
  932. }
  933. dst_tone_power_cmd(state);
  934. return 0;
  935. }
  936. static int dst_send_burst(struct dvb_frontend *fe, fe_sec_mini_cmd_t minicmd)
  937. {
  938. struct dst_state *state = fe->demodulator_priv;
  939. if ((state->dst_type == DST_TYPE_IS_TERR) || (state->dst_type == DST_TYPE_IS_CABLE))
  940. return 0;
  941. state->minicmd = minicmd;
  942. switch (minicmd) {
  943. case SEC_MINI_A:
  944. state->tx_tuna[3] = 0x02;
  945. break;
  946. case SEC_MINI_B:
  947. state->tx_tuna[3] = 0xff;
  948. break;
  949. }
  950. dst_tone_power_cmd(state);
  951. return 0;
  952. }
  953. static int dst_init(struct dvb_frontend* fe)
  954. {
  955. struct dst_state* state = fe->demodulator_priv;
  956. static u8 ini_satci_tuna[] = { 9, 0, 3, 0xb6, 1, 0, 0x73, 0x21, 0, 0 };
  957. static u8 ini_satfta_tuna[] = { 0, 0, 3, 0xb6, 1, 0x55, 0xbd, 0x50, 0, 0 };
  958. static u8 ini_tvfta_tuna[] = { 0, 0, 3, 0xb6, 1, 7, 0x0, 0x0, 0, 0 };
  959. static u8 ini_tvci_tuna[] = { 9, 0, 3, 0xb6, 1, 7, 0x0, 0x0, 0, 0 };
  960. static u8 ini_cabfta_tuna[] = { 0, 0, 3, 0xb6, 1, 7, 0x0, 0x0, 0, 0 };
  961. static u8 ini_cabci_tuna[] = { 9, 0, 3, 0xb6, 1, 7, 0x0, 0x0, 0, 0 };
  962. state->inversion = INVERSION_ON;
  963. state->voltage = SEC_VOLTAGE_13;
  964. state->tone = SEC_TONE_OFF;
  965. state->symbol_rate = 29473000;
  966. state->fec = FEC_AUTO;
  967. state->diseq_flags = 0;
  968. state->k22 = 0x02;
  969. state->bandwidth = BANDWIDTH_7_MHZ;
  970. state->cur_jiff = jiffies;
  971. if (state->dst_type == DST_TYPE_IS_SAT) {
  972. state->frequency = 950000;
  973. memcpy(state->tx_tuna, ((state->type_flags & DST_TYPE_HAS_NEWTUNE) ? ini_satci_tuna : ini_satfta_tuna), sizeof(ini_satfta_tuna));
  974. } else if (state->dst_type == DST_TYPE_IS_TERR) {
  975. state->frequency = 137000000;
  976. memcpy(state->tx_tuna, ((state->type_flags & DST_TYPE_HAS_NEWTUNE) ? ini_tvci_tuna : ini_tvfta_tuna), sizeof(ini_tvfta_tuna));
  977. } else if (state->dst_type == DST_TYPE_IS_CABLE) {
  978. state->frequency = 51000000;
  979. memcpy(state->tx_tuna, ((state->type_flags & DST_TYPE_HAS_NEWTUNE) ? ini_cabci_tuna : ini_cabfta_tuna), sizeof(ini_cabfta_tuna));
  980. }
  981. return 0;
  982. }
  983. static int dst_read_status(struct dvb_frontend* fe, fe_status_t* status)
  984. {
  985. struct dst_state* state = fe->demodulator_priv;
  986. *status = 0;
  987. if (state->diseq_flags & HAS_LOCK) {
  988. dst_get_signal(state);
  989. if (state->decode_lock)
  990. *status |= FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER | FE_HAS_SYNC | FE_HAS_VITERBI;
  991. }
  992. return 0;
  993. }
  994. static int dst_read_signal_strength(struct dvb_frontend* fe, u16* strength)
  995. {
  996. struct dst_state* state = fe->demodulator_priv;
  997. dst_get_signal(state);
  998. *strength = state->decode_strength;
  999. return 0;
  1000. }
  1001. static int dst_read_snr(struct dvb_frontend* fe, u16* snr)
  1002. {
  1003. struct dst_state* state = fe->demodulator_priv;
  1004. dst_get_signal(state);
  1005. *snr = state->decode_snr;
  1006. return 0;
  1007. }
  1008. static int dst_set_frontend(struct dvb_frontend* fe, struct dvb_frontend_parameters *p)
  1009. {
  1010. struct dst_state* state = fe->demodulator_priv;
  1011. dst_set_freq(state, p->frequency);
  1012. if (verbose > 4)
  1013. dprintk("Set Frequency = [%d]\n", p->frequency);
  1014. dst_set_inversion(state, p->inversion);
  1015. if (state->dst_type == DST_TYPE_IS_SAT) {
  1016. dst_set_fec(state, p->u.qpsk.fec_inner);
  1017. dst_set_symbolrate(state, p->u.qpsk.symbol_rate);
  1018. if (verbose > 4)
  1019. dprintk("Set Symbolrate = [%d]\n", p->u.qpsk.symbol_rate);
  1020. } else if (state->dst_type == DST_TYPE_IS_TERR) {
  1021. dst_set_bandwidth(state, p->u.ofdm.bandwidth);
  1022. } else if (state->dst_type == DST_TYPE_IS_CABLE) {
  1023. dst_set_fec(state, p->u.qam.fec_inner);
  1024. dst_set_symbolrate(state, p->u.qam.symbol_rate);
  1025. }
  1026. dst_write_tuna(fe);
  1027. return 0;
  1028. }
  1029. static int dst_get_frontend(struct dvb_frontend* fe, struct dvb_frontend_parameters *p)
  1030. {
  1031. struct dst_state* state = fe->demodulator_priv;
  1032. p->frequency = state->decode_freq;
  1033. p->inversion = state->inversion;
  1034. if (state->dst_type == DST_TYPE_IS_SAT) {
  1035. p->u.qpsk.symbol_rate = state->symbol_rate;
  1036. p->u.qpsk.fec_inner = dst_get_fec(state);
  1037. } else if (state->dst_type == DST_TYPE_IS_TERR) {
  1038. p->u.ofdm.bandwidth = state->bandwidth;
  1039. } else if (state->dst_type == DST_TYPE_IS_CABLE) {
  1040. p->u.qam.symbol_rate = state->symbol_rate;
  1041. p->u.qam.fec_inner = dst_get_fec(state);
  1042. p->u.qam.modulation = QAM_AUTO;
  1043. }
  1044. return 0;
  1045. }
  1046. static void dst_release(struct dvb_frontend* fe)
  1047. {
  1048. struct dst_state* state = fe->demodulator_priv;
  1049. kfree(state);
  1050. }
  1051. static struct dvb_frontend_ops dst_dvbt_ops;
  1052. static struct dvb_frontend_ops dst_dvbs_ops;
  1053. static struct dvb_frontend_ops dst_dvbc_ops;
  1054. struct dst_state* dst_attach(struct dst_state *state, struct dvb_adapter *dvb_adapter)
  1055. {
  1056. /* check if the ASIC is there */
  1057. if (dst_probe(state) < 0) {
  1058. if (state)
  1059. kfree(state);
  1060. return NULL;
  1061. }
  1062. /* determine settings based on type */
  1063. switch (state->dst_type) {
  1064. case DST_TYPE_IS_TERR:
  1065. memcpy(&state->ops, &dst_dvbt_ops, sizeof(struct dvb_frontend_ops));
  1066. break;
  1067. case DST_TYPE_IS_CABLE:
  1068. memcpy(&state->ops, &dst_dvbc_ops, sizeof(struct dvb_frontend_ops));
  1069. break;
  1070. case DST_TYPE_IS_SAT:
  1071. memcpy(&state->ops, &dst_dvbs_ops, sizeof(struct dvb_frontend_ops));
  1072. break;
  1073. default:
  1074. printk("%s: unknown DST type. please report to the LinuxTV.org DVB mailinglist.\n", __FUNCTION__);
  1075. if (state)
  1076. kfree(state);
  1077. return NULL;
  1078. }
  1079. /* create dvb_frontend */
  1080. state->frontend.ops = &state->ops;
  1081. state->frontend.demodulator_priv = state;
  1082. return state; /* Manu (DST is a card not a frontend) */
  1083. }
  1084. EXPORT_SYMBOL(dst_attach);
  1085. static struct dvb_frontend_ops dst_dvbt_ops = {
  1086. .info = {
  1087. .name = "DST DVB-T",
  1088. .type = FE_OFDM,
  1089. .frequency_min = 137000000,
  1090. .frequency_max = 858000000,
  1091. .frequency_stepsize = 166667,
  1092. .caps = FE_CAN_FEC_AUTO | FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO
  1093. },
  1094. .release = dst_release,
  1095. .init = dst_init,
  1096. .set_frontend = dst_set_frontend,
  1097. .get_frontend = dst_get_frontend,
  1098. .read_status = dst_read_status,
  1099. .read_signal_strength = dst_read_signal_strength,
  1100. .read_snr = dst_read_snr,
  1101. };
  1102. static struct dvb_frontend_ops dst_dvbs_ops = {
  1103. .info = {
  1104. .name = "DST DVB-S",
  1105. .type = FE_QPSK,
  1106. .frequency_min = 950000,
  1107. .frequency_max = 2150000,
  1108. .frequency_stepsize = 1000, /* kHz for QPSK frontends */
  1109. .frequency_tolerance = 29500,
  1110. .symbol_rate_min = 1000000,
  1111. .symbol_rate_max = 45000000,
  1112. /* . symbol_rate_tolerance = ???,*/
  1113. .caps = FE_CAN_FEC_AUTO | FE_CAN_QPSK
  1114. },
  1115. .release = dst_release,
  1116. .init = dst_init,
  1117. .set_frontend = dst_set_frontend,
  1118. .get_frontend = dst_get_frontend,
  1119. .read_status = dst_read_status,
  1120. .read_signal_strength = dst_read_signal_strength,
  1121. .read_snr = dst_read_snr,
  1122. .diseqc_send_burst = dst_send_burst,
  1123. .diseqc_send_master_cmd = dst_set_diseqc,
  1124. .set_voltage = dst_set_voltage,
  1125. .set_tone = dst_set_tone,
  1126. };
  1127. static struct dvb_frontend_ops dst_dvbc_ops = {
  1128. .info = {
  1129. .name = "DST DVB-C",
  1130. .type = FE_QAM,
  1131. .frequency_stepsize = 62500,
  1132. .frequency_min = 51000000,
  1133. .frequency_max = 858000000,
  1134. .symbol_rate_min = 1000000,
  1135. .symbol_rate_max = 45000000,
  1136. /* . symbol_rate_tolerance = ???,*/
  1137. .caps = FE_CAN_FEC_AUTO | FE_CAN_QAM_AUTO
  1138. },
  1139. .release = dst_release,
  1140. .init = dst_init,
  1141. .set_frontend = dst_set_frontend,
  1142. .get_frontend = dst_get_frontend,
  1143. .read_status = dst_read_status,
  1144. .read_signal_strength = dst_read_signal_strength,
  1145. .read_snr = dst_read_snr,
  1146. };
  1147. MODULE_DESCRIPTION("DST DVB-S/T/C Combo Frontend driver");
  1148. MODULE_AUTHOR("Jamie Honan, Manu Abraham");
  1149. MODULE_LICENSE("GPL");