linux/drivers/media/tuners/it913x.c
<<
>>
Prefs
   1/*
   2 * ITE IT913X silicon tuner driver
   3 *
   4 *  Copyright (C) 2011 Malcolm Priestley (tvboxspy@gmail.com)
   5 *  IT9137 Copyright (C) ITE Tech Inc.
   6 *
   7 *  This program is free software; you can redistribute it and/or modify
   8 *  it under the terms of the GNU General Public License as published by
   9 *  the Free Software Foundation; either version 2 of the License, or
  10 *  (at your option) any later version.
  11 *
  12 *  This program is distributed in the hope that it will be useful,
  13 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  14 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  15 *
  16 *  GNU General Public License for more details.
  17 */
  18
  19#include "it913x.h"
  20#include <linux/platform_device.h>
  21#include <linux/regmap.h>
  22
  23struct it913x_dev {
  24        struct platform_device *pdev;
  25        struct regmap *regmap;
  26        struct dvb_frontend *fe;
  27        u8 chip_ver:2;
  28        u8 role:2;
  29        u16 xtal;
  30        u8 fdiv;
  31        u8 clk_mode;
  32        u32 fn_min;
  33        bool active;
  34};
  35
  36static int it913x_init(struct dvb_frontend *fe)
  37{
  38        struct it913x_dev *dev = fe->tuner_priv;
  39        struct platform_device *pdev = dev->pdev;
  40        int ret;
  41        unsigned int utmp;
  42        u8 iqik_m_cal, nv_val, buf[2];
  43        static const u8 nv[] = {48, 32, 24, 16, 12, 8, 6, 4, 2};
  44        unsigned long timeout;
  45
  46        dev_dbg(&pdev->dev, "role %u\n", dev->role);
  47
  48        ret = regmap_write(dev->regmap, 0x80ec4c, 0x68);
  49        if (ret)
  50                goto err;
  51
  52        usleep_range(10000, 100000);
  53
  54        ret = regmap_read(dev->regmap, 0x80ec86, &utmp);
  55        if (ret)
  56                goto err;
  57
  58        switch (utmp) {
  59        case 0:
  60                /* 12.000 MHz */
  61                dev->clk_mode = utmp;
  62                dev->xtal = 2000;
  63                dev->fdiv = 3;
  64                iqik_m_cal = 16;
  65                break;
  66        case 1:
  67                /* 20.480 MHz */
  68                dev->clk_mode = utmp;
  69                dev->xtal = 640;
  70                dev->fdiv = 1;
  71                iqik_m_cal = 6;
  72                break;
  73        default:
  74                dev_err(&pdev->dev, "unknown clock identifier %d\n", utmp);
  75                goto err;
  76        }
  77
  78        ret = regmap_read(dev->regmap, 0x80ed03,  &utmp);
  79        if (ret)
  80                goto err;
  81
  82        else if (utmp < ARRAY_SIZE(nv))
  83                nv_val = nv[utmp];
  84        else
  85                nv_val = 2;
  86
  87        #define TIMEOUT 50
  88        timeout = jiffies + msecs_to_jiffies(TIMEOUT);
  89        while (!time_after(jiffies, timeout)) {
  90                ret = regmap_bulk_read(dev->regmap, 0x80ed23, buf, 2);
  91                if (ret)
  92                        goto err;
  93
  94                utmp = (buf[1] << 8) | (buf[0] << 0);
  95                if (utmp)
  96                        break;
  97        }
  98
  99        dev_dbg(&pdev->dev, "r_fbc_m_bdry took %u ms, val %u\n",
 100                        jiffies_to_msecs(jiffies) -
 101                        (jiffies_to_msecs(timeout) - TIMEOUT), utmp);
 102
 103        dev->fn_min = dev->xtal * utmp;
 104        dev->fn_min /= (dev->fdiv * nv_val);
 105        dev->fn_min *= 1000;
 106        dev_dbg(&pdev->dev, "fn_min %u\n", dev->fn_min);
 107
 108        /*
 109         * Chip version BX never sets that flag so we just wait 50ms in that
 110         * case. It is possible poll BX similarly than AX and then timeout in
 111         * order to get 50ms delay, but that causes about 120 extra I2C
 112         * messages. As for now, we just wait and reduce IO.
 113         */
 114        if (dev->chip_ver == 1) {
 115                #define TIMEOUT 50
 116                timeout = jiffies + msecs_to_jiffies(TIMEOUT);
 117                while (!time_after(jiffies, timeout)) {
 118                        ret = regmap_read(dev->regmap, 0x80ec82, &utmp);
 119                        if (ret)
 120                                goto err;
 121
 122                        if (utmp)
 123                                break;
 124                }
 125
 126                dev_dbg(&pdev->dev, "p_tsm_init_mode took %u ms, val %u\n",
 127                                jiffies_to_msecs(jiffies) -
 128                                (jiffies_to_msecs(timeout) - TIMEOUT), utmp);
 129        } else {
 130                msleep(50);
 131        }
 132
 133        ret = regmap_write(dev->regmap, 0x80ed81, iqik_m_cal);
 134        if (ret)
 135                goto err;
 136
 137        ret = regmap_write(dev->regmap, 0x80ec57, 0x00);
 138        if (ret)
 139                goto err;
 140
 141        ret = regmap_write(dev->regmap, 0x80ec58, 0x00);
 142        if (ret)
 143                goto err;
 144
 145        ret = regmap_write(dev->regmap, 0x80ec40, 0x01);
 146        if (ret)
 147                goto err;
 148
 149        dev->active = true;
 150
 151        return 0;
 152err:
 153        dev_dbg(&pdev->dev, "failed %d\n", ret);
 154        return ret;
 155}
 156
 157static int it913x_sleep(struct dvb_frontend *fe)
 158{
 159        struct it913x_dev *dev = fe->tuner_priv;
 160        struct platform_device *pdev = dev->pdev;
 161        int ret, len;
 162
 163        dev_dbg(&pdev->dev, "role %u\n", dev->role);
 164
 165        dev->active = false;
 166
 167        ret  = regmap_bulk_write(dev->regmap, 0x80ec40, "\x00", 1);
 168        if (ret)
 169                goto err;
 170
 171        /*
 172         * Writing '0x00' to master tuner register '0x80ec08' causes slave tuner
 173         * communication lost. Due to that, we cannot put master full sleep.
 174         */
 175        if (dev->role == IT913X_ROLE_DUAL_MASTER)
 176                len = 4;
 177        else
 178                len = 15;
 179
 180        dev_dbg(&pdev->dev, "role %u, len %d\n", dev->role, len);
 181
 182        ret = regmap_bulk_write(dev->regmap, 0x80ec02,
 183                        "\x3f\x1f\x3f\x3e\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00",
 184                        len);
 185        if (ret)
 186                goto err;
 187
 188        ret = regmap_bulk_write(dev->regmap, 0x80ec12, "\x00\x00\x00\x00", 4);
 189        if (ret)
 190                goto err;
 191
 192        ret = regmap_bulk_write(dev->regmap, 0x80ec17,
 193                        "\x00\x00\x00\x00\x00\x00\x00\x00\x00", 9);
 194        if (ret)
 195                goto err;
 196
 197        ret = regmap_bulk_write(dev->regmap, 0x80ec22,
 198                        "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00", 10);
 199        if (ret)
 200                goto err;
 201
 202        ret = regmap_bulk_write(dev->regmap, 0x80ec20, "\x00", 1);
 203        if (ret)
 204                goto err;
 205
 206        ret = regmap_bulk_write(dev->regmap, 0x80ec3f, "\x01", 1);
 207        if (ret)
 208                goto err;
 209
 210        return 0;
 211err:
 212        dev_dbg(&pdev->dev, "failed %d\n", ret);
 213        return ret;
 214}
 215
 216static int it913x_set_params(struct dvb_frontend *fe)
 217{
 218        struct it913x_dev *dev = fe->tuner_priv;
 219        struct platform_device *pdev = dev->pdev;
 220        struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 221        int ret;
 222        unsigned int utmp;
 223        u32 pre_lo_freq, t_cal_freq;
 224        u16 iqik_m_cal, n_div;
 225        u8 u8tmp, n, l_band, lna_band;
 226
 227        dev_dbg(&pdev->dev, "role=%u, frequency %u, bandwidth_hz %u\n",
 228                        dev->role, c->frequency, c->bandwidth_hz);
 229
 230        if (!dev->active) {
 231                ret = -EINVAL;
 232                goto err;
 233        }
 234
 235        if (c->frequency <=         74000000) {
 236                n_div = 48;
 237                n = 0;
 238        } else if (c->frequency <= 111000000) {
 239                n_div = 32;
 240                n = 1;
 241        } else if (c->frequency <= 148000000) {
 242                n_div = 24;
 243                n = 2;
 244        } else if (c->frequency <= 222000000) {
 245                n_div = 16;
 246                n = 3;
 247        } else if (c->frequency <= 296000000) {
 248                n_div = 12;
 249                n = 4;
 250        } else if (c->frequency <= 445000000) {
 251                n_div = 8;
 252                n = 5;
 253        } else if (c->frequency <= dev->fn_min) {
 254                n_div = 6;
 255                n = 6;
 256        } else if (c->frequency <= 950000000) {
 257                n_div = 4;
 258                n = 7;
 259        } else {
 260                n_div = 2;
 261                n = 0;
 262        }
 263
 264        ret = regmap_read(dev->regmap, 0x80ed81, &utmp);
 265        if (ret)
 266                goto err;
 267
 268        iqik_m_cal = utmp * n_div;
 269
 270        if (utmp < 0x20) {
 271                if (dev->clk_mode == 0)
 272                        iqik_m_cal = (iqik_m_cal * 9) >> 5;
 273                else
 274                        iqik_m_cal >>= 1;
 275        } else {
 276                iqik_m_cal = 0x40 - iqik_m_cal;
 277                if (dev->clk_mode == 0)
 278                        iqik_m_cal = ~((iqik_m_cal * 9) >> 5);
 279                else
 280                        iqik_m_cal = ~(iqik_m_cal >> 1);
 281        }
 282
 283        t_cal_freq = (c->frequency / 1000) * n_div * dev->fdiv;
 284        pre_lo_freq = t_cal_freq / dev->xtal;
 285        utmp = pre_lo_freq * dev->xtal;
 286
 287        if ((t_cal_freq - utmp) >= (dev->xtal >> 1))
 288                pre_lo_freq++;
 289
 290        pre_lo_freq += (u32) n << 13;
 291        /* Frequency OMEGA_IQIK_M_CAL_MID*/
 292        t_cal_freq = pre_lo_freq + (u32)iqik_m_cal;
 293        dev_dbg(&pdev->dev, "t_cal_freq %u, pre_lo_freq %u\n",
 294                        t_cal_freq, pre_lo_freq);
 295
 296        if (c->frequency <=         440000000) {
 297                l_band = 0;
 298                lna_band = 0;
 299        } else if (c->frequency <=  484000000) {
 300                l_band = 1;
 301                lna_band = 1;
 302        } else if (c->frequency <=  533000000) {
 303                l_band = 1;
 304                lna_band = 2;
 305        } else if (c->frequency <=  587000000) {
 306                l_band = 1;
 307                lna_band = 3;
 308        } else if (c->frequency <=  645000000) {
 309                l_band = 1;
 310                lna_band = 4;
 311        } else if (c->frequency <=  710000000) {
 312                l_band = 1;
 313                lna_band = 5;
 314        } else if (c->frequency <=  782000000) {
 315                l_band = 1;
 316                lna_band = 6;
 317        } else if (c->frequency <=  860000000) {
 318                l_band = 1;
 319                lna_band = 7;
 320        } else if (c->frequency <= 1492000000) {
 321                l_band = 1;
 322                lna_band = 0;
 323        } else if (c->frequency <= 1685000000) {
 324                l_band = 1;
 325                lna_band = 1;
 326        } else {
 327                ret = -EINVAL;
 328                goto err;
 329        }
 330
 331        /* XXX: latest windows driver does not set that at all */
 332        ret = regmap_write(dev->regmap, 0x80ee06, lna_band);
 333        if (ret)
 334                goto err;
 335
 336        if (c->bandwidth_hz <=      5000000)
 337                u8tmp = 0;
 338        else if (c->bandwidth_hz <= 6000000)
 339                u8tmp = 2;
 340        else if (c->bandwidth_hz <= 7000000)
 341                u8tmp = 4;
 342        else
 343                u8tmp = 6;       /* 8000000 */
 344
 345        ret = regmap_write(dev->regmap, 0x80ec56, u8tmp);
 346        if (ret)
 347                goto err;
 348
 349        /* XXX: latest windows driver sets different value (a8 != 68) */
 350        ret = regmap_write(dev->regmap, 0x80ec4c, 0xa0 | (l_band << 3));
 351        if (ret)
 352                goto err;
 353
 354        ret = regmap_write(dev->regmap, 0x80ec4d, (t_cal_freq >> 0) & 0xff);
 355        if (ret)
 356                goto err;
 357
 358        ret = regmap_write(dev->regmap, 0x80ec4e, (t_cal_freq >> 8) & 0xff);
 359        if (ret)
 360                goto err;
 361
 362        ret = regmap_write(dev->regmap, 0x80011e, (pre_lo_freq >> 0) & 0xff);
 363        if (ret)
 364                goto err;
 365
 366        ret = regmap_write(dev->regmap, 0x80011f, (pre_lo_freq >> 8) & 0xff);
 367        if (ret)
 368                goto err;
 369
 370        return 0;
 371err:
 372        dev_dbg(&pdev->dev, "failed %d\n", ret);
 373        return ret;
 374}
 375
 376static const struct dvb_tuner_ops it913x_tuner_ops = {
 377        .info = {
 378                .name           = "ITE IT913X",
 379                .frequency_min  = 174000000,
 380                .frequency_max  = 862000000,
 381        },
 382
 383        .init = it913x_init,
 384        .sleep = it913x_sleep,
 385        .set_params = it913x_set_params,
 386};
 387
 388static int it913x_probe(struct platform_device *pdev)
 389{
 390        struct it913x_platform_data *pdata = pdev->dev.platform_data;
 391        struct dvb_frontend *fe = pdata->fe;
 392        struct it913x_dev *dev;
 393        const struct platform_device_id *id = platform_get_device_id(pdev);
 394        int ret;
 395        char *chip_ver_str;
 396
 397        dev = kzalloc(sizeof(struct it913x_dev), GFP_KERNEL);
 398        if (dev == NULL) {
 399                ret = -ENOMEM;
 400                dev_err(&pdev->dev, "kzalloc() failed\n");
 401                goto err;
 402        }
 403
 404        dev->pdev = pdev;
 405        dev->regmap = pdata->regmap;
 406        dev->fe = pdata->fe;
 407        dev->chip_ver = id->driver_data;
 408        dev->role = pdata->role;
 409
 410        fe->tuner_priv = dev;
 411        memcpy(&fe->ops.tuner_ops, &it913x_tuner_ops,
 412                        sizeof(struct dvb_tuner_ops));
 413        platform_set_drvdata(pdev, dev);
 414
 415        if (dev->chip_ver == 1)
 416                chip_ver_str = "AX";
 417        else if (dev->chip_ver == 2)
 418                chip_ver_str = "BX";
 419        else
 420                chip_ver_str = "??";
 421
 422        dev_info(&pdev->dev, "ITE IT913X %s successfully attached\n",
 423                 chip_ver_str);
 424        dev_dbg(&pdev->dev, "chip_ver %u, role %u\n", dev->chip_ver, dev->role);
 425        return 0;
 426err:
 427        dev_dbg(&pdev->dev, "failed %d\n", ret);
 428        return ret;
 429}
 430
 431static int it913x_remove(struct platform_device *pdev)
 432{
 433        struct it913x_dev *dev = platform_get_drvdata(pdev);
 434        struct dvb_frontend *fe = dev->fe;
 435
 436        dev_dbg(&pdev->dev, "\n");
 437
 438        memset(&fe->ops.tuner_ops, 0, sizeof(struct dvb_tuner_ops));
 439        fe->tuner_priv = NULL;
 440        kfree(dev);
 441
 442        return 0;
 443}
 444
 445static const struct platform_device_id it913x_id_table[] = {
 446        {"it9133ax-tuner", 1},
 447        {"it9133bx-tuner", 2},
 448        {},
 449};
 450MODULE_DEVICE_TABLE(platform, it913x_id_table);
 451
 452static struct platform_driver it913x_driver = {
 453        .driver = {
 454                .name   = "it913x",
 455                .suppress_bind_attrs    = true,
 456        },
 457        .probe          = it913x_probe,
 458        .remove         = it913x_remove,
 459        .id_table       = it913x_id_table,
 460};
 461
 462module_platform_driver(it913x_driver);
 463
 464MODULE_DESCRIPTION("ITE IT913X silicon tuner driver");
 465MODULE_AUTHOR("Antti Palosaari <crope@iki.fi>");
 466MODULE_LICENSE("GPL");
 467