linux/drivers/staging/media/bcm2048/radio-bcm2048.c
<<
>>
Prefs
   1/*
   2 * drivers/staging/media/radio-bcm2048.c
   3 *
   4 * Driver for I2C Broadcom BCM2048 FM Radio Receiver:
   5 *
   6 * Copyright (C) Nokia Corporation
   7 * Contact: Eero Nurkkala <ext-eero.nurkkala@nokia.com>
   8 *
   9 * Copyright (C) Nils Faerber <nils.faerber@kernelconcepts.de>
  10 *
  11 * This program is free software; you can redistribute it and/or
  12 * modify it under the terms of the GNU General Public License
  13 * version 2 as published by the Free Software Foundation.
  14 *
  15 * This program is distributed in the hope that it will be useful, but
  16 * WITHOUT ANY WARRANTY; without even the implied warranty of
  17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  18 * General Public License for more details.
  19 *
  20 * You should have received a copy of the GNU General Public License
  21 * along with this program; if not, write to the Free Software
  22 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
  23 * 02110-1301 USA
  24 */
  25
  26/*
  27 * History:
  28 *              Eero Nurkkala <ext-eero.nurkkala@nokia.com>
  29 *              Version 0.0.1
  30 *              - Initial implementation
  31 * 2010-02-21   Nils Faerber <nils.faerber@kernelconcepts.de>
  32 *              Version 0.0.2
  33 *              - Add support for interrupt driven rds data reading
  34 */
  35
  36#include <linux/kernel.h>
  37#include <linux/module.h>
  38#include <linux/init.h>
  39#include <linux/version.h>
  40#include <linux/interrupt.h>
  41#include <linux/sysfs.h>
  42#include <linux/completion.h>
  43#include <linux/delay.h>
  44#include <linux/i2c.h>
  45#include <linux/videodev2.h>
  46#include <linux/mutex.h>
  47#include <linux/slab.h>
  48#include <media/v4l2-common.h>
  49#include <media/v4l2-ioctl.h>
  50#include "radio-bcm2048.h"
  51
  52/* driver definitions */
  53#define BCM2048_DRIVER_AUTHOR   "Eero Nurkkala <ext-eero.nurkkala@nokia.com>"
  54#define BCM2048_DRIVER_NAME     BCM2048_NAME
  55#define BCM2048_DRIVER_VERSION  KERNEL_VERSION(0, 0, 1)
  56#define BCM2048_DRIVER_CARD     "Broadcom bcm2048 FM Radio Receiver"
  57#define BCM2048_DRIVER_DESC     "I2C driver for BCM2048 FM Radio Receiver"
  58
  59/* I2C Control Registers */
  60#define BCM2048_I2C_FM_RDS_SYSTEM       0x00
  61#define BCM2048_I2C_FM_CTRL             0x01
  62#define BCM2048_I2C_RDS_CTRL0           0x02
  63#define BCM2048_I2C_RDS_CTRL1           0x03
  64#define BCM2048_I2C_FM_AUDIO_PAUSE      0x04
  65#define BCM2048_I2C_FM_AUDIO_CTRL0      0x05
  66#define BCM2048_I2C_FM_AUDIO_CTRL1      0x06
  67#define BCM2048_I2C_FM_SEARCH_CTRL0     0x07
  68#define BCM2048_I2C_FM_SEARCH_CTRL1     0x08
  69#define BCM2048_I2C_FM_SEARCH_TUNE_MODE 0x09
  70#define BCM2048_I2C_FM_FREQ0            0x0a
  71#define BCM2048_I2C_FM_FREQ1            0x0b
  72#define BCM2048_I2C_FM_AF_FREQ0         0x0c
  73#define BCM2048_I2C_FM_AF_FREQ1         0x0d
  74#define BCM2048_I2C_FM_CARRIER          0x0e
  75#define BCM2048_I2C_FM_RSSI             0x0f
  76#define BCM2048_I2C_FM_RDS_MASK0        0x10
  77#define BCM2048_I2C_FM_RDS_MASK1        0x11
  78#define BCM2048_I2C_FM_RDS_FLAG0        0x12
  79#define BCM2048_I2C_FM_RDS_FLAG1        0x13
  80#define BCM2048_I2C_RDS_WLINE           0x14
  81#define BCM2048_I2C_RDS_BLKB_MATCH0     0x16
  82#define BCM2048_I2C_RDS_BLKB_MATCH1     0x17
  83#define BCM2048_I2C_RDS_BLKB_MASK0      0x18
  84#define BCM2048_I2C_RDS_BLKB_MASK1      0x19
  85#define BCM2048_I2C_RDS_PI_MATCH0       0x1a
  86#define BCM2048_I2C_RDS_PI_MATCH1       0x1b
  87#define BCM2048_I2C_RDS_PI_MASK0        0x1c
  88#define BCM2048_I2C_RDS_PI_MASK1        0x1d
  89#define BCM2048_I2C_SPARE1              0x20
  90#define BCM2048_I2C_SPARE2              0x21
  91#define BCM2048_I2C_FM_RDS_REV          0x28
  92#define BCM2048_I2C_SLAVE_CONFIGURATION 0x29
  93#define BCM2048_I2C_RDS_DATA            0x80
  94#define BCM2048_I2C_FM_BEST_TUNE_MODE   0x90
  95
  96/* BCM2048_I2C_FM_RDS_SYSTEM */
  97#define BCM2048_FM_ON                   0x01
  98#define BCM2048_RDS_ON                  0x02
  99
 100/* BCM2048_I2C_FM_CTRL */
 101#define BCM2048_BAND_SELECT                     0x01
 102#define BCM2048_STEREO_MONO_AUTO_SELECT         0x02
 103#define BCM2048_STEREO_MONO_MANUAL_SELECT       0x04
 104#define BCM2048_STEREO_MONO_BLEND_SWITCH        0x08
 105#define BCM2048_HI_LO_INJECTION                 0x10
 106
 107/* BCM2048_I2C_RDS_CTRL0 */
 108#define BCM2048_RBDS_RDS_SELECT         0x01
 109#define BCM2048_FLUSH_FIFO              0x02
 110
 111/* BCM2048_I2C_FM_AUDIO_PAUSE */
 112#define BCM2048_AUDIO_PAUSE_RSSI_TRESH  0x0f
 113#define BCM2048_AUDIO_PAUSE_DURATION    0xf0
 114
 115/* BCM2048_I2C_FM_AUDIO_CTRL0 */
 116#define BCM2048_RF_MUTE                 0x01
 117#define BCM2048_MANUAL_MUTE             0x02
 118#define BCM2048_DAC_OUTPUT_LEFT         0x04
 119#define BCM2048_DAC_OUTPUT_RIGHT        0x08
 120#define BCM2048_AUDIO_ROUTE_DAC         0x10
 121#define BCM2048_AUDIO_ROUTE_I2S         0x20
 122#define BCM2048_DE_EMPHASIS_SELECT      0x40
 123#define BCM2048_AUDIO_BANDWIDTH_SELECT  0x80
 124
 125/* BCM2048_I2C_FM_SEARCH_CTRL0 */
 126#define BCM2048_SEARCH_RSSI_THRESHOLD   0x7f
 127#define BCM2048_SEARCH_DIRECTION        0x80
 128
 129/* BCM2048_I2C_FM_SEARCH_TUNE_MODE */
 130#define BCM2048_FM_AUTO_SEARCH          0x03
 131
 132/* BCM2048_I2C_FM_RSSI */
 133#define BCM2048_RSSI_VALUE              0xff
 134
 135/* BCM2048_I2C_FM_RDS_MASK0 */
 136/* BCM2048_I2C_FM_RDS_MASK1 */
 137#define BCM2048_FM_FLAG_SEARCH_TUNE_FINISHED    0x01
 138#define BCM2048_FM_FLAG_SEARCH_TUNE_FAIL        0x02
 139#define BCM2048_FM_FLAG_RSSI_LOW                0x04
 140#define BCM2048_FM_FLAG_CARRIER_ERROR_HIGH      0x08
 141#define BCM2048_FM_FLAG_AUDIO_PAUSE_INDICATION  0x10
 142#define BCM2048_FLAG_STEREO_DETECTED            0x20
 143#define BCM2048_FLAG_STEREO_ACTIVE              0x40
 144
 145/* BCM2048_I2C_RDS_DATA */
 146#define BCM2048_SLAVE_ADDRESS                   0x3f
 147#define BCM2048_SLAVE_ENABLE                    0x80
 148
 149/* BCM2048_I2C_FM_BEST_TUNE_MODE */
 150#define BCM2048_BEST_TUNE_MODE                  0x80
 151
 152#define BCM2048_FM_FLAG_SEARCH_TUNE_FINISHED    0x01
 153#define BCM2048_FM_FLAG_SEARCH_TUNE_FAIL        0x02
 154#define BCM2048_FM_FLAG_RSSI_LOW                0x04
 155#define BCM2048_FM_FLAG_CARRIER_ERROR_HIGH      0x08
 156#define BCM2048_FM_FLAG_AUDIO_PAUSE_INDICATION  0x10
 157#define BCM2048_FLAG_STEREO_DETECTED            0x20
 158#define BCM2048_FLAG_STEREO_ACTIVE              0x40
 159
 160#define BCM2048_RDS_FLAG_FIFO_WLINE             0x02
 161#define BCM2048_RDS_FLAG_B_BLOCK_MATCH          0x08
 162#define BCM2048_RDS_FLAG_SYNC_LOST              0x10
 163#define BCM2048_RDS_FLAG_PI_MATCH               0x20
 164
 165#define BCM2048_RDS_MARK_END_BYTE0              0x7C
 166#define BCM2048_RDS_MARK_END_BYTEN              0xFF
 167
 168#define BCM2048_FM_FLAGS_ALL    (FM_FLAG_SEARCH_TUNE_FINISHED | \
 169                                 FM_FLAG_SEARCH_TUNE_FAIL | \
 170                                 FM_FLAG_RSSI_LOW | \
 171                                 FM_FLAG_CARRIER_ERROR_HIGH | \
 172                                 FM_FLAG_AUDIO_PAUSE_INDICATION | \
 173                                 FLAG_STEREO_DETECTED | FLAG_STEREO_ACTIVE)
 174
 175#define BCM2048_RDS_FLAGS_ALL   (RDS_FLAG_FIFO_WLINE | \
 176                                 RDS_FLAG_B_BLOCK_MATCH | \
 177                                 RDS_FLAG_SYNC_LOST | RDS_FLAG_PI_MATCH)
 178
 179#define BCM2048_DEFAULT_TIMEOUT         1500
 180#define BCM2048_AUTO_SEARCH_TIMEOUT     3000
 181
 182#define BCM2048_FREQDEV_UNIT            10000
 183#define BCM2048_FREQV4L2_MULTI          625
 184#define dev_to_v4l2(f)  ((f * BCM2048_FREQDEV_UNIT) / BCM2048_FREQV4L2_MULTI)
 185#define v4l2_to_dev(f)  ((f * BCM2048_FREQV4L2_MULTI) / BCM2048_FREQDEV_UNIT)
 186
 187#define msb(x)                  ((u8)((u16)x >> 8))
 188#define lsb(x)                  ((u8)((u16)x &  0x00FF))
 189#define compose_u16(msb, lsb)   (((u16)msb << 8) | lsb)
 190
 191#define BCM2048_DEFAULT_POWERING_DELAY  20
 192#define BCM2048_DEFAULT_REGION          0x02
 193#define BCM2048_DEFAULT_MUTE            0x01
 194#define BCM2048_DEFAULT_RSSI_THRESHOLD  0x64
 195#define BCM2048_DEFAULT_RDS_WLINE       0x7E
 196
 197#define BCM2048_FM_SEARCH_INACTIVE      0x00
 198#define BCM2048_FM_PRE_SET_MODE         0x01
 199#define BCM2048_FM_AUTO_SEARCH_MODE     0x02
 200#define BCM2048_FM_AF_JUMP_MODE         0x03
 201
 202#define BCM2048_FREQUENCY_BASE          64000
 203
 204#define BCM2048_POWER_ON                0x01
 205#define BCM2048_POWER_OFF               0x00
 206
 207#define BCM2048_ITEM_ENABLED            0x01
 208#define BCM2048_SEARCH_DIRECTION_UP     0x01
 209
 210#define BCM2048_DE_EMPHASIS_75us        75
 211#define BCM2048_DE_EMPHASIS_50us        50
 212
 213#define BCM2048_SCAN_FAIL               0x00
 214#define BCM2048_SCAN_OK                 0x01
 215
 216#define BCM2048_FREQ_ERROR_FLOOR        -20
 217#define BCM2048_FREQ_ERROR_ROOF         20
 218
 219/* -60 dB is reported as full signal strength */
 220#define BCM2048_RSSI_LEVEL_BASE         -60
 221#define BCM2048_RSSI_LEVEL_ROOF         -100
 222#define BCM2048_RSSI_LEVEL_ROOF_NEG     100
 223#define BCM2048_SIGNAL_MULTIPLIER       (0xFFFF / \
 224                                         (BCM2048_RSSI_LEVEL_ROOF_NEG + \
 225                                          BCM2048_RSSI_LEVEL_BASE))
 226
 227#define BCM2048_RDS_FIFO_DUPLE_SIZE     0x03
 228#define BCM2048_RDS_CRC_MASK            0x0F
 229#define BCM2048_RDS_CRC_NONE            0x00
 230#define BCM2048_RDS_CRC_MAX_2BITS       0x04
 231#define BCM2048_RDS_CRC_LEAST_2BITS     0x08
 232#define BCM2048_RDS_CRC_UNRECOVARABLE   0x0C
 233
 234#define BCM2048_RDS_BLOCK_MASK          0xF0
 235#define BCM2048_RDS_BLOCK_A             0x00
 236#define BCM2048_RDS_BLOCK_B             0x10
 237#define BCM2048_RDS_BLOCK_C             0x20
 238#define BCM2048_RDS_BLOCK_D             0x30
 239#define BCM2048_RDS_BLOCK_C_SCORED      0x40
 240#define BCM2048_RDS_BLOCK_E             0x60
 241
 242#define BCM2048_RDS_RT                  0x20
 243#define BCM2048_RDS_PS                  0x00
 244
 245#define BCM2048_RDS_GROUP_AB_MASK       0x08
 246#define BCM2048_RDS_GROUP_A             0x00
 247#define BCM2048_RDS_GROUP_B             0x08
 248
 249#define BCM2048_RDS_RT_AB_MASK          0x10
 250#define BCM2048_RDS_RT_A                0x00
 251#define BCM2048_RDS_RT_B                0x10
 252#define BCM2048_RDS_RT_INDEX            0x0F
 253
 254#define BCM2048_RDS_PS_INDEX            0x03
 255
 256struct rds_info {
 257        u16 rds_pi;
 258#define BCM2048_MAX_RDS_RT (64 + 1)
 259        u8 rds_rt[BCM2048_MAX_RDS_RT];
 260        u8 rds_rt_group_b;
 261        u8 rds_rt_ab;
 262#define BCM2048_MAX_RDS_PS (8 + 1)
 263        u8 rds_ps[BCM2048_MAX_RDS_PS];
 264        u8 rds_ps_group;
 265        u8 rds_ps_group_cnt;
 266#define BCM2048_MAX_RDS_RADIO_TEXT 255
 267        u8 radio_text[BCM2048_MAX_RDS_RADIO_TEXT + 3];
 268        u8 text_len;
 269};
 270
 271struct region_info {
 272        u32 bottom_frequency;
 273        u32 top_frequency;
 274        u8 deemphasis;
 275        u8 channel_spacing;
 276        u8 region;
 277};
 278
 279struct bcm2048_device {
 280        struct i2c_client *client;
 281        struct video_device videodev;
 282        struct work_struct work;
 283        struct completion compl;
 284        struct mutex mutex;
 285        struct bcm2048_platform_data *platform_data;
 286        struct rds_info rds_info;
 287        struct region_info region_info;
 288        u16 frequency;
 289        u8 cache_fm_rds_system;
 290        u8 cache_fm_ctrl;
 291        u8 cache_fm_audio_ctrl0;
 292        u8 cache_fm_search_ctrl0;
 293        u8 power_state;
 294        u8 rds_state;
 295        u8 fifo_size;
 296        u8 scan_state;
 297        u8 mute_state;
 298
 299        /* for rds data device read */
 300        wait_queue_head_t read_queue;
 301        unsigned int users;
 302        unsigned char rds_data_available;
 303        unsigned int rd_index;
 304};
 305
 306static int radio_nr = -1;       /* radio device minor (-1 ==> auto assign) */
 307module_param(radio_nr, int, 0);
 308MODULE_PARM_DESC(radio_nr,
 309                 "Minor number for radio device (-1 ==> auto assign)");
 310
 311static struct region_info region_configs[] = {
 312        /* USA */
 313        {
 314                .channel_spacing        = 20,
 315                .bottom_frequency       = 87500,
 316                .top_frequency          = 108000,
 317                .deemphasis             = 75,
 318                .region                 = 0,
 319        },
 320        /* Australia */
 321        {
 322                .channel_spacing        = 20,
 323                .bottom_frequency       = 87500,
 324                .top_frequency          = 108000,
 325                .deemphasis             = 50,
 326                .region                 = 1,
 327        },
 328        /* Europe */
 329        {
 330                .channel_spacing        = 10,
 331                .bottom_frequency       = 87500,
 332                .top_frequency          = 108000,
 333                .deemphasis             = 50,
 334                .region                 = 2,
 335        },
 336        /* Japan */
 337        {
 338                .channel_spacing        = 10,
 339                .bottom_frequency       = 76000,
 340                .top_frequency          = 90000,
 341                .deemphasis             = 50,
 342                .region                 = 3,
 343        },
 344};
 345
 346/*
 347 *      I2C Interface read / write
 348 */
 349static int bcm2048_send_command(struct bcm2048_device *bdev, unsigned int reg,
 350                                unsigned int value)
 351{
 352        struct i2c_client *client = bdev->client;
 353        u8 data[2];
 354
 355        if (!bdev->power_state) {
 356                dev_err(&bdev->client->dev, "bcm2048: chip not powered!\n");
 357                return -EIO;
 358        }
 359
 360        data[0] = reg & 0xff;
 361        data[1] = value & 0xff;
 362
 363        if (i2c_master_send(client, data, 2) == 2)
 364                return 0;
 365
 366        dev_err(&bdev->client->dev, "BCM I2C error!\n");
 367        dev_err(&bdev->client->dev, "Is Bluetooth up and running?\n");
 368        return -EIO;
 369}
 370
 371static int bcm2048_recv_command(struct bcm2048_device *bdev, unsigned int reg,
 372                                u8 *value)
 373{
 374        struct i2c_client *client = bdev->client;
 375
 376        if (!bdev->power_state) {
 377                dev_err(&bdev->client->dev, "bcm2048: chip not powered!\n");
 378                return -EIO;
 379        }
 380
 381        value[0] = i2c_smbus_read_byte_data(client, reg & 0xff);
 382
 383        return 0;
 384}
 385
 386static int bcm2048_recv_duples(struct bcm2048_device *bdev, unsigned int reg,
 387                               u8 *value, u8 duples)
 388{
 389        struct i2c_client *client = bdev->client;
 390        struct i2c_adapter *adap = client->adapter;
 391        struct i2c_msg msg[2];
 392        u8 buf;
 393
 394        if (!bdev->power_state) {
 395                dev_err(&bdev->client->dev, "bcm2048: chip not powered!\n");
 396                return -EIO;
 397        }
 398
 399        buf = reg & 0xff;
 400
 401        msg[0].addr = client->addr;
 402        msg[0].flags = client->flags & I2C_M_TEN;
 403        msg[0].len = 1;
 404        msg[0].buf = &buf;
 405
 406        msg[1].addr = client->addr;
 407        msg[1].flags = client->flags & I2C_M_TEN;
 408        msg[1].flags |= I2C_M_RD;
 409        msg[1].len = duples;
 410        msg[1].buf = value;
 411
 412        return i2c_transfer(adap, msg, 2);
 413}
 414
 415/*
 416 *      BCM2048 - I2C register programming helpers
 417 */
 418static int bcm2048_set_power_state(struct bcm2048_device *bdev, u8 power)
 419{
 420        int err = 0;
 421
 422        mutex_lock(&bdev->mutex);
 423
 424        if (power) {
 425                bdev->power_state = BCM2048_POWER_ON;
 426                bdev->cache_fm_rds_system |= BCM2048_FM_ON;
 427        } else {
 428                bdev->cache_fm_rds_system &= ~BCM2048_FM_ON;
 429        }
 430
 431        /*
 432         * Warning! FM cannot be turned off because then
 433         * the I2C communications get ruined!
 434         * Comment off the "if (power)" when the chip works!
 435         */
 436        if (power)
 437                err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM,
 438                                           bdev->cache_fm_rds_system);
 439        msleep(BCM2048_DEFAULT_POWERING_DELAY);
 440
 441        if (!power)
 442                bdev->power_state = BCM2048_POWER_OFF;
 443
 444        mutex_unlock(&bdev->mutex);
 445        return err;
 446}
 447
 448static int bcm2048_get_power_state(struct bcm2048_device *bdev)
 449{
 450        int err;
 451        u8 value;
 452
 453        mutex_lock(&bdev->mutex);
 454
 455        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM, &value);
 456
 457        mutex_unlock(&bdev->mutex);
 458
 459        if (!err && (value & BCM2048_FM_ON))
 460                return BCM2048_POWER_ON;
 461
 462        return err;
 463}
 464
 465static int bcm2048_set_rds_no_lock(struct bcm2048_device *bdev, u8 rds_on)
 466{
 467        int err;
 468        u8 flags;
 469
 470        bdev->cache_fm_rds_system &= ~BCM2048_RDS_ON;
 471
 472        if (rds_on) {
 473                bdev->cache_fm_rds_system |= BCM2048_RDS_ON;
 474                bdev->rds_state = BCM2048_RDS_ON;
 475                flags = BCM2048_RDS_FLAG_FIFO_WLINE;
 476                err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK1,
 477                                           flags);
 478        } else {
 479                flags = 0;
 480                bdev->rds_state = 0;
 481                err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK1,
 482                                           flags);
 483                memset(&bdev->rds_info, 0, sizeof(bdev->rds_info));
 484        }
 485
 486        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM,
 487                                   bdev->cache_fm_rds_system);
 488
 489        return err;
 490}
 491
 492static int bcm2048_get_rds_no_lock(struct bcm2048_device *bdev)
 493{
 494        int err;
 495        u8 value;
 496
 497        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM, &value);
 498
 499        if (!err && (value & BCM2048_RDS_ON))
 500                return BCM2048_ITEM_ENABLED;
 501
 502        return err;
 503}
 504
 505static int bcm2048_set_rds(struct bcm2048_device *bdev, u8 rds_on)
 506{
 507        int err;
 508
 509        mutex_lock(&bdev->mutex);
 510
 511        err = bcm2048_set_rds_no_lock(bdev, rds_on);
 512
 513        mutex_unlock(&bdev->mutex);
 514        return err;
 515}
 516
 517static int bcm2048_get_rds(struct bcm2048_device *bdev)
 518{
 519        int err;
 520
 521        mutex_lock(&bdev->mutex);
 522
 523        err = bcm2048_get_rds_no_lock(bdev);
 524
 525        mutex_unlock(&bdev->mutex);
 526        return err;
 527}
 528
 529static int bcm2048_get_rds_pi(struct bcm2048_device *bdev)
 530{
 531        return bdev->rds_info.rds_pi;
 532}
 533
 534static int bcm2048_set_fm_automatic_stereo_mono(struct bcm2048_device *bdev,
 535                                                u8 enabled)
 536{
 537        int err;
 538
 539        mutex_lock(&bdev->mutex);
 540
 541        bdev->cache_fm_ctrl &= ~BCM2048_STEREO_MONO_AUTO_SELECT;
 542
 543        if (enabled)
 544                bdev->cache_fm_ctrl |= BCM2048_STEREO_MONO_AUTO_SELECT;
 545
 546        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_CTRL,
 547                                   bdev->cache_fm_ctrl);
 548
 549        mutex_unlock(&bdev->mutex);
 550        return err;
 551}
 552
 553static int bcm2048_set_fm_hi_lo_injection(struct bcm2048_device *bdev,
 554                                          u8 hi_lo)
 555{
 556        int err;
 557
 558        mutex_lock(&bdev->mutex);
 559
 560        bdev->cache_fm_ctrl &= ~BCM2048_HI_LO_INJECTION;
 561
 562        if (hi_lo)
 563                bdev->cache_fm_ctrl |= BCM2048_HI_LO_INJECTION;
 564
 565        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_CTRL,
 566                                   bdev->cache_fm_ctrl);
 567
 568        mutex_unlock(&bdev->mutex);
 569        return err;
 570}
 571
 572static int bcm2048_get_fm_hi_lo_injection(struct bcm2048_device *bdev)
 573{
 574        int err;
 575        u8 value;
 576
 577        mutex_lock(&bdev->mutex);
 578
 579        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_CTRL, &value);
 580
 581        mutex_unlock(&bdev->mutex);
 582
 583        if (!err && (value & BCM2048_HI_LO_INJECTION))
 584                return BCM2048_ITEM_ENABLED;
 585
 586        return err;
 587}
 588
 589static int bcm2048_set_fm_frequency(struct bcm2048_device *bdev, u32 frequency)
 590{
 591        int err;
 592
 593        if (frequency < bdev->region_info.bottom_frequency ||
 594            frequency > bdev->region_info.top_frequency)
 595                return -EDOM;
 596
 597        frequency -= BCM2048_FREQUENCY_BASE;
 598
 599        mutex_lock(&bdev->mutex);
 600
 601        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_FREQ0, lsb(frequency));
 602        err |= bcm2048_send_command(bdev, BCM2048_I2C_FM_FREQ1,
 603                                    msb(frequency));
 604
 605        if (!err)
 606                bdev->frequency = frequency;
 607
 608        mutex_unlock(&bdev->mutex);
 609        return err;
 610}
 611
 612static int bcm2048_get_fm_frequency(struct bcm2048_device *bdev)
 613{
 614        int err;
 615        u8 lsb = 0, msb = 0;
 616
 617        mutex_lock(&bdev->mutex);
 618
 619        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_FREQ0, &lsb);
 620        err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_FREQ1, &msb);
 621
 622        mutex_unlock(&bdev->mutex);
 623
 624        if (err)
 625                return err;
 626
 627        err = compose_u16(msb, lsb);
 628        err += BCM2048_FREQUENCY_BASE;
 629
 630        return err;
 631}
 632
 633static int bcm2048_set_fm_af_frequency(struct bcm2048_device *bdev,
 634                                       u32 frequency)
 635{
 636        int err;
 637
 638        if (frequency < bdev->region_info.bottom_frequency ||
 639            frequency > bdev->region_info.top_frequency)
 640                return -EDOM;
 641
 642        frequency -= BCM2048_FREQUENCY_BASE;
 643
 644        mutex_lock(&bdev->mutex);
 645
 646        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AF_FREQ0,
 647                                   lsb(frequency));
 648        err |= bcm2048_send_command(bdev, BCM2048_I2C_FM_AF_FREQ1,
 649                                    msb(frequency));
 650        if (!err)
 651                bdev->frequency = frequency;
 652
 653        mutex_unlock(&bdev->mutex);
 654        return err;
 655}
 656
 657static int bcm2048_get_fm_af_frequency(struct bcm2048_device *bdev)
 658{
 659        int err;
 660        u8 lsb = 0, msb = 0;
 661
 662        mutex_lock(&bdev->mutex);
 663
 664        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AF_FREQ0, &lsb);
 665        err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_AF_FREQ1, &msb);
 666
 667        mutex_unlock(&bdev->mutex);
 668
 669        if (err)
 670                return err;
 671
 672        err = compose_u16(msb, lsb);
 673        err += BCM2048_FREQUENCY_BASE;
 674
 675        return err;
 676}
 677
 678static int bcm2048_set_fm_deemphasis(struct bcm2048_device *bdev, int d)
 679{
 680        int err;
 681        u8 deemphasis;
 682
 683        if (d == BCM2048_DE_EMPHASIS_75us)
 684                deemphasis = BCM2048_DE_EMPHASIS_SELECT;
 685        else
 686                deemphasis = 0;
 687
 688        mutex_lock(&bdev->mutex);
 689
 690        bdev->cache_fm_audio_ctrl0 &= ~BCM2048_DE_EMPHASIS_SELECT;
 691        bdev->cache_fm_audio_ctrl0 |= deemphasis;
 692
 693        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
 694                                   bdev->cache_fm_audio_ctrl0);
 695
 696        if (!err)
 697                bdev->region_info.deemphasis = d;
 698
 699        mutex_unlock(&bdev->mutex);
 700
 701        return err;
 702}
 703
 704static int bcm2048_get_fm_deemphasis(struct bcm2048_device *bdev)
 705{
 706        int err;
 707        u8 value;
 708
 709        mutex_lock(&bdev->mutex);
 710
 711        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0, &value);
 712
 713        mutex_unlock(&bdev->mutex);
 714
 715        if (!err) {
 716                if (value & BCM2048_DE_EMPHASIS_SELECT)
 717                        return BCM2048_DE_EMPHASIS_75us;
 718
 719                return BCM2048_DE_EMPHASIS_50us;
 720        }
 721
 722        return err;
 723}
 724
 725static int bcm2048_set_region(struct bcm2048_device *bdev, u8 region)
 726{
 727        int err;
 728        u32 new_frequency = 0;
 729
 730        if (region >= ARRAY_SIZE(region_configs))
 731                return -EINVAL;
 732
 733        mutex_lock(&bdev->mutex);
 734        bdev->region_info = region_configs[region];
 735
 736        if (region_configs[region].bottom_frequency < 87500)
 737                bdev->cache_fm_ctrl |= BCM2048_BAND_SELECT;
 738        else
 739                bdev->cache_fm_ctrl &= ~BCM2048_BAND_SELECT;
 740
 741        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_CTRL,
 742                                   bdev->cache_fm_ctrl);
 743        if (err) {
 744                mutex_unlock(&bdev->mutex);
 745                goto done;
 746        }
 747        mutex_unlock(&bdev->mutex);
 748
 749        if (bdev->frequency < region_configs[region].bottom_frequency ||
 750            bdev->frequency > region_configs[region].top_frequency)
 751                new_frequency = region_configs[region].bottom_frequency;
 752
 753        if (new_frequency > 0) {
 754                err = bcm2048_set_fm_frequency(bdev, new_frequency);
 755
 756                if (err)
 757                        goto done;
 758        }
 759
 760        err = bcm2048_set_fm_deemphasis(bdev,
 761                                        region_configs[region].deemphasis);
 762
 763done:
 764        return err;
 765}
 766
 767static int bcm2048_get_region(struct bcm2048_device *bdev)
 768{
 769        int err;
 770
 771        mutex_lock(&bdev->mutex);
 772        err = bdev->region_info.region;
 773        mutex_unlock(&bdev->mutex);
 774
 775        return err;
 776}
 777
 778static int bcm2048_set_mute(struct bcm2048_device *bdev, u16 mute)
 779{
 780        int err;
 781
 782        mutex_lock(&bdev->mutex);
 783
 784        bdev->cache_fm_audio_ctrl0 &= ~(BCM2048_RF_MUTE | BCM2048_MANUAL_MUTE);
 785
 786        if (mute)
 787                bdev->cache_fm_audio_ctrl0 |= (BCM2048_RF_MUTE |
 788                                               BCM2048_MANUAL_MUTE);
 789
 790        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
 791                                   bdev->cache_fm_audio_ctrl0);
 792
 793        if (!err)
 794                bdev->mute_state = mute;
 795
 796        mutex_unlock(&bdev->mutex);
 797        return err;
 798}
 799
 800static int bcm2048_get_mute(struct bcm2048_device *bdev)
 801{
 802        int err;
 803        u8 value;
 804
 805        mutex_lock(&bdev->mutex);
 806
 807        if (bdev->power_state) {
 808                err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
 809                                           &value);
 810                if (!err)
 811                        err = value & (BCM2048_RF_MUTE | BCM2048_MANUAL_MUTE);
 812        } else {
 813                err = bdev->mute_state;
 814        }
 815
 816        mutex_unlock(&bdev->mutex);
 817        return err;
 818}
 819
 820static int bcm2048_set_audio_route(struct bcm2048_device *bdev, u8 route)
 821{
 822        int err;
 823
 824        mutex_lock(&bdev->mutex);
 825
 826        route &= (BCM2048_AUDIO_ROUTE_DAC | BCM2048_AUDIO_ROUTE_I2S);
 827        bdev->cache_fm_audio_ctrl0 &= ~(BCM2048_AUDIO_ROUTE_DAC |
 828                                        BCM2048_AUDIO_ROUTE_I2S);
 829        bdev->cache_fm_audio_ctrl0 |= route;
 830
 831        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
 832                                   bdev->cache_fm_audio_ctrl0);
 833
 834        mutex_unlock(&bdev->mutex);
 835        return err;
 836}
 837
 838static int bcm2048_get_audio_route(struct bcm2048_device *bdev)
 839{
 840        int err;
 841        u8 value;
 842
 843        mutex_lock(&bdev->mutex);
 844
 845        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0, &value);
 846
 847        mutex_unlock(&bdev->mutex);
 848
 849        if (!err)
 850                return value & (BCM2048_AUDIO_ROUTE_DAC |
 851                                BCM2048_AUDIO_ROUTE_I2S);
 852
 853        return err;
 854}
 855
 856static int bcm2048_set_dac_output(struct bcm2048_device *bdev, u8 channels)
 857{
 858        int err;
 859
 860        mutex_lock(&bdev->mutex);
 861
 862        bdev->cache_fm_audio_ctrl0 &= ~(BCM2048_DAC_OUTPUT_LEFT |
 863                                        BCM2048_DAC_OUTPUT_RIGHT);
 864        bdev->cache_fm_audio_ctrl0 |= channels;
 865
 866        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
 867                                   bdev->cache_fm_audio_ctrl0);
 868
 869        mutex_unlock(&bdev->mutex);
 870        return err;
 871}
 872
 873static int bcm2048_get_dac_output(struct bcm2048_device *bdev)
 874{
 875        int err;
 876        u8 value;
 877
 878        mutex_lock(&bdev->mutex);
 879
 880        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0, &value);
 881
 882        mutex_unlock(&bdev->mutex);
 883
 884        if (!err)
 885                return value & (BCM2048_DAC_OUTPUT_LEFT |
 886                                BCM2048_DAC_OUTPUT_RIGHT);
 887
 888        return err;
 889}
 890
 891static int bcm2048_set_fm_search_rssi_threshold(struct bcm2048_device *bdev,
 892                                                u8 threshold)
 893{
 894        int err;
 895
 896        mutex_lock(&bdev->mutex);
 897
 898        threshold &= BCM2048_SEARCH_RSSI_THRESHOLD;
 899        bdev->cache_fm_search_ctrl0 &= ~BCM2048_SEARCH_RSSI_THRESHOLD;
 900        bdev->cache_fm_search_ctrl0 |= threshold;
 901
 902        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0,
 903                                   bdev->cache_fm_search_ctrl0);
 904
 905        mutex_unlock(&bdev->mutex);
 906        return err;
 907}
 908
 909static int bcm2048_get_fm_search_rssi_threshold(struct bcm2048_device *bdev)
 910{
 911        int err;
 912        u8 value;
 913
 914        mutex_lock(&bdev->mutex);
 915
 916        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0, &value);
 917
 918        mutex_unlock(&bdev->mutex);
 919
 920        if (!err)
 921                return value & BCM2048_SEARCH_RSSI_THRESHOLD;
 922
 923        return err;
 924}
 925
 926static int bcm2048_set_fm_search_mode_direction(struct bcm2048_device *bdev,
 927                                                u8 direction)
 928{
 929        int err;
 930
 931        mutex_lock(&bdev->mutex);
 932
 933        bdev->cache_fm_search_ctrl0 &= ~BCM2048_SEARCH_DIRECTION;
 934
 935        if (direction)
 936                bdev->cache_fm_search_ctrl0 |= BCM2048_SEARCH_DIRECTION;
 937
 938        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0,
 939                                   bdev->cache_fm_search_ctrl0);
 940
 941        mutex_unlock(&bdev->mutex);
 942        return err;
 943}
 944
 945static int bcm2048_get_fm_search_mode_direction(struct bcm2048_device *bdev)
 946{
 947        int err;
 948        u8 value;
 949
 950        mutex_lock(&bdev->mutex);
 951
 952        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0, &value);
 953
 954        mutex_unlock(&bdev->mutex);
 955
 956        if (!err && (value & BCM2048_SEARCH_DIRECTION))
 957                return BCM2048_SEARCH_DIRECTION_UP;
 958
 959        return err;
 960}
 961
 962static int bcm2048_set_fm_search_tune_mode(struct bcm2048_device *bdev,
 963                                           u8 mode)
 964{
 965        int err, timeout, restart_rds = 0;
 966        u8 value, flags;
 967
 968        value = mode & BCM2048_FM_AUTO_SEARCH;
 969
 970        flags = BCM2048_FM_FLAG_SEARCH_TUNE_FINISHED |
 971                BCM2048_FM_FLAG_SEARCH_TUNE_FAIL;
 972
 973        mutex_lock(&bdev->mutex);
 974
 975        /*
 976         * If RDS is enabled, and frequency is changed, RDS quits working.
 977         * Thus, always restart RDS if it's enabled. Moreover, RDS must
 978         * not be enabled while changing the frequency because it can
 979         * provide a race to the mutex from the workqueue handler if RDS
 980         * IRQ occurs while waiting for frequency changed IRQ.
 981         */
 982        if (bcm2048_get_rds_no_lock(bdev)) {
 983                err = bcm2048_set_rds_no_lock(bdev, 0);
 984                if (err)
 985                        goto unlock;
 986                restart_rds = 1;
 987        }
 988
 989        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK0, flags);
 990
 991        if (err)
 992                goto unlock;
 993
 994        bcm2048_send_command(bdev, BCM2048_I2C_FM_SEARCH_TUNE_MODE, value);
 995
 996        if (mode != BCM2048_FM_AUTO_SEARCH_MODE)
 997                timeout = BCM2048_DEFAULT_TIMEOUT;
 998        else
 999                timeout = BCM2048_AUTO_SEARCH_TIMEOUT;
1000
1001        if (!wait_for_completion_timeout(&bdev->compl,
1002                msecs_to_jiffies(timeout)))
1003                dev_err(&bdev->client->dev, "IRQ timeout.\n");
1004
1005        if (value)
1006                if (!bdev->scan_state)
1007                        err = -EIO;
1008
1009unlock:
1010        if (restart_rds)
1011                err |= bcm2048_set_rds_no_lock(bdev, 1);
1012
1013        mutex_unlock(&bdev->mutex);
1014
1015        return err;
1016}
1017
1018static int bcm2048_get_fm_search_tune_mode(struct bcm2048_device *bdev)
1019{
1020        int err;
1021        u8 value;
1022
1023        mutex_lock(&bdev->mutex);
1024
1025        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_SEARCH_TUNE_MODE,
1026                                   &value);
1027
1028        mutex_unlock(&bdev->mutex);
1029
1030        if (!err)
1031                return value & BCM2048_FM_AUTO_SEARCH;
1032
1033        return err;
1034}
1035
1036static int bcm2048_set_rds_b_block_mask(struct bcm2048_device *bdev, u16 mask)
1037{
1038        int err;
1039
1040        mutex_lock(&bdev->mutex);
1041
1042        err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MASK0,
1043                                   lsb(mask));
1044        err |= bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MASK1,
1045                                    msb(mask));
1046
1047        mutex_unlock(&bdev->mutex);
1048        return err;
1049}
1050
1051static int bcm2048_get_rds_b_block_mask(struct bcm2048_device *bdev)
1052{
1053        int err;
1054        u8 lsb = 0, msb = 0;
1055
1056        mutex_lock(&bdev->mutex);
1057
1058        err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MASK0, &lsb);
1059        err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MASK1, &msb);
1060
1061        mutex_unlock(&bdev->mutex);
1062
1063        if (!err)
1064                return compose_u16(msb, lsb);
1065
1066        return err;
1067}
1068
1069static int bcm2048_set_rds_b_block_match(struct bcm2048_device *bdev,
1070                                         u16 match)
1071{
1072        int err;
1073
1074        mutex_lock(&bdev->mutex);
1075
1076        err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH0,
1077                                   lsb(match));
1078        err |= bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH1,
1079                                    msb(match));
1080
1081        mutex_unlock(&bdev->mutex);
1082        return err;
1083}
1084
1085static int bcm2048_get_rds_b_block_match(struct bcm2048_device *bdev)
1086{
1087        int err;
1088        u8 lsb = 0, msb = 0;
1089
1090        mutex_lock(&bdev->mutex);
1091
1092        err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH0, &lsb);
1093        err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH1, &msb);
1094
1095        mutex_unlock(&bdev->mutex);
1096
1097        if (!err)
1098                return compose_u16(msb, lsb);
1099
1100        return err;
1101}
1102
1103static int bcm2048_set_rds_pi_mask(struct bcm2048_device *bdev, u16 mask)
1104{
1105        int err;
1106
1107        mutex_lock(&bdev->mutex);
1108
1109        err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_PI_MASK0, lsb(mask));
1110        err |= bcm2048_send_command(bdev, BCM2048_I2C_RDS_PI_MASK1, msb(mask));
1111
1112        mutex_unlock(&bdev->mutex);
1113        return err;
1114}
1115
1116static int bcm2048_get_rds_pi_mask(struct bcm2048_device *bdev)
1117{
1118        int err;
1119        u8 lsb = 0, msb = 0;
1120
1121        mutex_lock(&bdev->mutex);
1122
1123        err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MASK0, &lsb);
1124        err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MASK1, &msb);
1125
1126        mutex_unlock(&bdev->mutex);
1127
1128        if (!err)
1129                return compose_u16(msb, lsb);
1130
1131        return err;
1132}
1133
1134static int bcm2048_set_rds_pi_match(struct bcm2048_device *bdev, u16 match)
1135{
1136        int err;
1137
1138        mutex_lock(&bdev->mutex);
1139
1140        err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_PI_MATCH0,
1141                                   lsb(match));
1142        err |= bcm2048_send_command(bdev, BCM2048_I2C_RDS_PI_MATCH1,
1143                                    msb(match));
1144
1145        mutex_unlock(&bdev->mutex);
1146        return err;
1147}
1148
1149static int bcm2048_get_rds_pi_match(struct bcm2048_device *bdev)
1150{
1151        int err;
1152        u8 lsb = 0, msb = 0;
1153
1154        mutex_lock(&bdev->mutex);
1155
1156        err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MATCH0, &lsb);
1157        err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MATCH1, &msb);
1158
1159        mutex_unlock(&bdev->mutex);
1160
1161        if (!err)
1162                return compose_u16(msb, lsb);
1163
1164        return err;
1165}
1166
1167static int bcm2048_set_fm_rds_mask(struct bcm2048_device *bdev, u16 mask)
1168{
1169        int err;
1170
1171        mutex_lock(&bdev->mutex);
1172
1173        err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK0, lsb(mask));
1174        err |= bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK1, msb(mask));
1175
1176        mutex_unlock(&bdev->mutex);
1177        return err;
1178}
1179
1180static int bcm2048_get_fm_rds_mask(struct bcm2048_device *bdev)
1181{
1182        int err;
1183        u8 value0 = 0, value1 = 0;
1184
1185        mutex_lock(&bdev->mutex);
1186
1187        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_MASK0, &value0);
1188        err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_MASK1, &value1);
1189
1190        mutex_unlock(&bdev->mutex);
1191
1192        if (!err)
1193                return compose_u16(value1, value0);
1194
1195        return err;
1196}
1197
1198static int bcm2048_get_fm_rds_flags(struct bcm2048_device *bdev)
1199{
1200        int err;
1201        u8 value0 = 0, value1 = 0;
1202
1203        mutex_lock(&bdev->mutex);
1204
1205        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG0, &value0);
1206        err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG1, &value1);
1207
1208        mutex_unlock(&bdev->mutex);
1209
1210        if (!err)
1211                return compose_u16(value1, value0);
1212
1213        return err;
1214}
1215
1216static int bcm2048_get_region_bottom_frequency(struct bcm2048_device *bdev)
1217{
1218        return bdev->region_info.bottom_frequency;
1219}
1220
1221static int bcm2048_get_region_top_frequency(struct bcm2048_device *bdev)
1222{
1223        return bdev->region_info.top_frequency;
1224}
1225
1226static int bcm2048_set_fm_best_tune_mode(struct bcm2048_device *bdev, u8 mode)
1227{
1228        int err;
1229        u8 value = 0;
1230
1231        mutex_lock(&bdev->mutex);
1232
1233        /* Perform read as the manual indicates */
1234        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_BEST_TUNE_MODE,
1235                                   &value);
1236        value &= ~BCM2048_BEST_TUNE_MODE;
1237
1238        if (mode)
1239                value |= BCM2048_BEST_TUNE_MODE;
1240        err |= bcm2048_send_command(bdev, BCM2048_I2C_FM_BEST_TUNE_MODE,
1241                                    value);
1242
1243        mutex_unlock(&bdev->mutex);
1244        return err;
1245}
1246
1247static int bcm2048_get_fm_best_tune_mode(struct bcm2048_device *bdev)
1248{
1249        int err;
1250        u8 value;
1251
1252        mutex_lock(&bdev->mutex);
1253
1254        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_BEST_TUNE_MODE,
1255                                   &value);
1256
1257        mutex_unlock(&bdev->mutex);
1258
1259        if (!err && (value & BCM2048_BEST_TUNE_MODE))
1260                return BCM2048_ITEM_ENABLED;
1261
1262        return err;
1263}
1264
1265static int bcm2048_get_fm_carrier_error(struct bcm2048_device *bdev)
1266{
1267        int err = 0;
1268        s8 value;
1269
1270        mutex_lock(&bdev->mutex);
1271        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_CARRIER, &value);
1272        mutex_unlock(&bdev->mutex);
1273
1274        if (!err)
1275                return value;
1276
1277        return err;
1278}
1279
1280static int bcm2048_get_fm_rssi(struct bcm2048_device *bdev)
1281{
1282        int err;
1283        s8 value;
1284
1285        mutex_lock(&bdev->mutex);
1286        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RSSI, &value);
1287        mutex_unlock(&bdev->mutex);
1288
1289        if (!err)
1290                return value;
1291
1292        return err;
1293}
1294
1295static int bcm2048_set_rds_wline(struct bcm2048_device *bdev, u8 wline)
1296{
1297        int err;
1298
1299        mutex_lock(&bdev->mutex);
1300
1301        err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_WLINE, wline);
1302
1303        if (!err)
1304                bdev->fifo_size = wline;
1305
1306        mutex_unlock(&bdev->mutex);
1307        return err;
1308}
1309
1310static int bcm2048_get_rds_wline(struct bcm2048_device *bdev)
1311{
1312        int err;
1313        u8 value;
1314
1315        mutex_lock(&bdev->mutex);
1316
1317        err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_WLINE, &value);
1318
1319        mutex_unlock(&bdev->mutex);
1320
1321        if (!err) {
1322                bdev->fifo_size = value;
1323                return value;
1324        }
1325
1326        return err;
1327}
1328
1329static int bcm2048_checkrev(struct bcm2048_device *bdev)
1330{
1331        int err;
1332        u8 version;
1333
1334        mutex_lock(&bdev->mutex);
1335
1336        err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_REV, &version);
1337
1338        mutex_unlock(&bdev->mutex);
1339
1340        if (!err) {
1341                dev_info(&bdev->client->dev, "BCM2048 Version 0x%x\n",
1342                         version);
1343                return version;
1344        }
1345
1346        return err;
1347}
1348
1349static int bcm2048_get_rds_rt(struct bcm2048_device *bdev, char *data)
1350{
1351        int err = 0, i, j = 0, ce = 0, cr = 0;
1352        char data_buffer[BCM2048_MAX_RDS_RT + 1];
1353
1354        mutex_lock(&bdev->mutex);
1355
1356        if (!bdev->rds_info.text_len) {
1357                err = -EINVAL;
1358                goto unlock;
1359        }
1360
1361        for (i = 0; i < BCM2048_MAX_RDS_RT; i++) {
1362                if (bdev->rds_info.rds_rt[i]) {
1363                        ce = i;
1364                        /* Skip the carriage return */
1365                        if (bdev->rds_info.rds_rt[i] != 0x0d) {
1366                                data_buffer[j++] = bdev->rds_info.rds_rt[i];
1367                        } else {
1368                                cr = i;
1369                                break;
1370                        }
1371                }
1372        }
1373
1374        if (j <= BCM2048_MAX_RDS_RT)
1375                data_buffer[j] = 0;
1376
1377        for (i = 0; i < BCM2048_MAX_RDS_RT; i++) {
1378                if (!bdev->rds_info.rds_rt[i]) {
1379                        if (cr && (i < cr)) {
1380                                err = -EBUSY;
1381                                goto unlock;
1382                        }
1383                        if (i < ce) {
1384                                if (cr && (i >= cr))
1385                                        break;
1386                                err = -EBUSY;
1387                                goto unlock;
1388                        }
1389                }
1390        }
1391
1392        memcpy(data, data_buffer, sizeof(data_buffer));
1393
1394unlock:
1395        mutex_unlock(&bdev->mutex);
1396        return err;
1397}
1398
1399static int bcm2048_get_rds_ps(struct bcm2048_device *bdev, char *data)
1400{
1401        int err = 0, i, j = 0;
1402        char data_buffer[BCM2048_MAX_RDS_PS + 1];
1403
1404        mutex_lock(&bdev->mutex);
1405
1406        if (!bdev->rds_info.text_len) {
1407                err = -EINVAL;
1408                goto unlock;
1409        }
1410
1411        for (i = 0; i < BCM2048_MAX_RDS_PS; i++) {
1412                if (bdev->rds_info.rds_ps[i]) {
1413                        data_buffer[j++] = bdev->rds_info.rds_ps[i];
1414                } else {
1415                        if (i < (BCM2048_MAX_RDS_PS - 1)) {
1416                                err = -EBUSY;
1417                                goto unlock;
1418                        }
1419                }
1420        }
1421
1422        if (j <= BCM2048_MAX_RDS_PS)
1423                data_buffer[j] = 0;
1424
1425        memcpy(data, data_buffer, sizeof(data_buffer));
1426
1427unlock:
1428        mutex_unlock(&bdev->mutex);
1429        return err;
1430}
1431
1432static void bcm2048_parse_rds_pi(struct bcm2048_device *bdev)
1433{
1434        int i, cnt = 0;
1435        u16 pi;
1436
1437        for (i = 0; i < bdev->fifo_size; i += BCM2048_RDS_FIFO_DUPLE_SIZE) {
1438                /* Block A match, only data without crc errors taken */
1439                if (bdev->rds_info.radio_text[i] == BCM2048_RDS_BLOCK_A) {
1440                        pi = (bdev->rds_info.radio_text[i + 1] << 8) +
1441                                bdev->rds_info.radio_text[i + 2];
1442
1443                        if (!bdev->rds_info.rds_pi) {
1444                                bdev->rds_info.rds_pi = pi;
1445                                return;
1446                        }
1447                        if (pi != bdev->rds_info.rds_pi) {
1448                                cnt++;
1449                                if (cnt > 3) {
1450                                        bdev->rds_info.rds_pi = pi;
1451                                        cnt = 0;
1452                                }
1453                        } else {
1454                                cnt = 0;
1455                        }
1456                }
1457        }
1458}
1459
1460static int bcm2048_rds_block_crc(struct bcm2048_device *bdev, int i)
1461{
1462        return bdev->rds_info.radio_text[i] & BCM2048_RDS_CRC_MASK;
1463}
1464
1465static void bcm2048_parse_rds_rt_block(struct bcm2048_device *bdev, int i,
1466                                       int index, int crc)
1467{
1468        /* Good data will overwrite poor data */
1469        if (crc) {
1470                if (!bdev->rds_info.rds_rt[index])
1471                        bdev->rds_info.rds_rt[index] =
1472                                bdev->rds_info.radio_text[i + 1];
1473                if (!bdev->rds_info.rds_rt[index + 1])
1474                        bdev->rds_info.rds_rt[index + 1] =
1475                                bdev->rds_info.radio_text[i + 2];
1476        } else {
1477                bdev->rds_info.rds_rt[index] =
1478                        bdev->rds_info.radio_text[i + 1];
1479                bdev->rds_info.rds_rt[index + 1] =
1480                        bdev->rds_info.radio_text[i + 2];
1481        }
1482}
1483
1484static int bcm2048_parse_rt_match_b(struct bcm2048_device *bdev, int i)
1485{
1486        int crc, rt_id, rt_group_b, rt_ab, index = 0;
1487
1488        crc = bcm2048_rds_block_crc(bdev, i);
1489
1490        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1491                return -EIO;
1492
1493        if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1494            BCM2048_RDS_BLOCK_B) {
1495                rt_id = bdev->rds_info.radio_text[i + 1] &
1496                        BCM2048_RDS_BLOCK_MASK;
1497                rt_group_b = bdev->rds_info.radio_text[i + 1] &
1498                        BCM2048_RDS_GROUP_AB_MASK;
1499                rt_ab = bdev->rds_info.radio_text[i + 2] &
1500                                BCM2048_RDS_RT_AB_MASK;
1501
1502                if (rt_group_b != bdev->rds_info.rds_rt_group_b) {
1503                        memset(bdev->rds_info.rds_rt, 0,
1504                               sizeof(bdev->rds_info.rds_rt));
1505                        bdev->rds_info.rds_rt_group_b = rt_group_b;
1506                }
1507
1508                if (rt_id == BCM2048_RDS_RT) {
1509                        /* A to B or (vice versa), means: clear screen */
1510                        if (rt_ab != bdev->rds_info.rds_rt_ab) {
1511                                memset(bdev->rds_info.rds_rt, 0,
1512                                       sizeof(bdev->rds_info.rds_rt));
1513                                bdev->rds_info.rds_rt_ab = rt_ab;
1514                        }
1515
1516                        index = bdev->rds_info.radio_text[i + 2] &
1517                                        BCM2048_RDS_RT_INDEX;
1518
1519                        if (bdev->rds_info.rds_rt_group_b)
1520                                index <<= 1;
1521                        else
1522                                index <<= 2;
1523
1524                        return index;
1525                }
1526        }
1527
1528        return -EIO;
1529}
1530
1531static int bcm2048_parse_rt_match_c(struct bcm2048_device *bdev, int i,
1532                                    int index)
1533{
1534        int crc;
1535
1536        crc = bcm2048_rds_block_crc(bdev, i);
1537
1538        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1539                return 0;
1540
1541        BUG_ON((index+2) >= BCM2048_MAX_RDS_RT);
1542
1543        if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1544                BCM2048_RDS_BLOCK_C) {
1545                if (bdev->rds_info.rds_rt_group_b)
1546                        return 1;
1547                bcm2048_parse_rds_rt_block(bdev, i, index, crc);
1548                return 1;
1549        }
1550
1551        return 0;
1552}
1553
1554static void bcm2048_parse_rt_match_d(struct bcm2048_device *bdev, int i,
1555                                     int index)
1556{
1557        int crc;
1558
1559        crc = bcm2048_rds_block_crc(bdev, i);
1560
1561        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1562                return;
1563
1564        BUG_ON((index+4) >= BCM2048_MAX_RDS_RT);
1565
1566        if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1567            BCM2048_RDS_BLOCK_D)
1568                bcm2048_parse_rds_rt_block(bdev, i, index + 2, crc);
1569}
1570
1571static void bcm2048_parse_rds_rt(struct bcm2048_device *bdev)
1572{
1573        int i, index = 0, crc, match_b = 0, match_c = 0, match_d = 0;
1574
1575        for (i = 0; i < bdev->fifo_size; i += BCM2048_RDS_FIFO_DUPLE_SIZE) {
1576                if (match_b) {
1577                        match_b = 0;
1578                        index = bcm2048_parse_rt_match_b(bdev, i);
1579                        if (index >= 0 && index <= (BCM2048_MAX_RDS_RT - 5))
1580                                match_c = 1;
1581                        continue;
1582                } else if (match_c) {
1583                        match_c = 0;
1584                        if (bcm2048_parse_rt_match_c(bdev, i, index))
1585                                match_d = 1;
1586                        continue;
1587                } else if (match_d) {
1588                        match_d = 0;
1589                        bcm2048_parse_rt_match_d(bdev, i, index);
1590                        continue;
1591                }
1592
1593                /* Skip erroneous blocks due to messed up A block altogether */
1594                if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1595                    BCM2048_RDS_BLOCK_A) {
1596                        crc = bcm2048_rds_block_crc(bdev, i);
1597                        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1598                                continue;
1599                        /* Synchronize to a good RDS PI */
1600                        if (((bdev->rds_info.radio_text[i + 1] << 8) +
1601                            bdev->rds_info.radio_text[i + 2]) ==
1602                            bdev->rds_info.rds_pi)
1603                                match_b = 1;
1604                }
1605        }
1606}
1607
1608static void bcm2048_parse_rds_ps_block(struct bcm2048_device *bdev, int i,
1609                                       int index, int crc)
1610{
1611        /* Good data will overwrite poor data */
1612        if (crc) {
1613                if (!bdev->rds_info.rds_ps[index])
1614                        bdev->rds_info.rds_ps[index] =
1615                                bdev->rds_info.radio_text[i + 1];
1616                if (!bdev->rds_info.rds_ps[index + 1])
1617                        bdev->rds_info.rds_ps[index + 1] =
1618                                bdev->rds_info.radio_text[i + 2];
1619        } else {
1620                bdev->rds_info.rds_ps[index] =
1621                        bdev->rds_info.radio_text[i + 1];
1622                bdev->rds_info.rds_ps[index + 1] =
1623                        bdev->rds_info.radio_text[i + 2];
1624        }
1625}
1626
1627static int bcm2048_parse_ps_match_c(struct bcm2048_device *bdev, int i,
1628                                    int index)
1629{
1630        int crc;
1631
1632        crc = bcm2048_rds_block_crc(bdev, i);
1633
1634        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1635                return 0;
1636
1637        if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1638            BCM2048_RDS_BLOCK_C)
1639                return 1;
1640
1641        return 0;
1642}
1643
1644static void bcm2048_parse_ps_match_d(struct bcm2048_device *bdev, int i,
1645                                     int index)
1646{
1647        int crc;
1648
1649        crc = bcm2048_rds_block_crc(bdev, i);
1650
1651        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1652                return;
1653
1654        if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1655            BCM2048_RDS_BLOCK_D)
1656                bcm2048_parse_rds_ps_block(bdev, i, index, crc);
1657}
1658
1659static int bcm2048_parse_ps_match_b(struct bcm2048_device *bdev, int i)
1660{
1661        int crc, index, ps_id, ps_group;
1662
1663        crc = bcm2048_rds_block_crc(bdev, i);
1664
1665        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1666                return -EIO;
1667
1668        /* Block B Radio PS match */
1669        if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1670            BCM2048_RDS_BLOCK_B) {
1671                ps_id = bdev->rds_info.radio_text[i + 1] &
1672                        BCM2048_RDS_BLOCK_MASK;
1673                ps_group = bdev->rds_info.radio_text[i + 1] &
1674                        BCM2048_RDS_GROUP_AB_MASK;
1675
1676                /*
1677                 * Poor RSSI will lead to RDS data corruption
1678                 * So using 3 (same) sequential values to justify major changes
1679                 */
1680                if (ps_group != bdev->rds_info.rds_ps_group) {
1681                        if (crc == BCM2048_RDS_CRC_NONE) {
1682                                bdev->rds_info.rds_ps_group_cnt++;
1683                                if (bdev->rds_info.rds_ps_group_cnt > 2) {
1684                                        bdev->rds_info.rds_ps_group = ps_group;
1685                                        bdev->rds_info.rds_ps_group_cnt = 0;
1686                                        dev_err(&bdev->client->dev,
1687                                                "RDS PS Group change!\n");
1688                                } else {
1689                                        return -EIO;
1690                                }
1691                        } else {
1692                                bdev->rds_info.rds_ps_group_cnt = 0;
1693                        }
1694                }
1695
1696                if (ps_id == BCM2048_RDS_PS) {
1697                        index = bdev->rds_info.radio_text[i + 2] &
1698                                BCM2048_RDS_PS_INDEX;
1699                        index <<= 1;
1700                        return index;
1701                }
1702        }
1703
1704        return -EIO;
1705}
1706
1707static void bcm2048_parse_rds_ps(struct bcm2048_device *bdev)
1708{
1709        int i, index = 0, crc, match_b = 0, match_c = 0, match_d = 0;
1710
1711        for (i = 0; i < bdev->fifo_size; i += BCM2048_RDS_FIFO_DUPLE_SIZE) {
1712                if (match_b) {
1713                        match_b = 0;
1714                        index = bcm2048_parse_ps_match_b(bdev, i);
1715                        if (index >= 0 && index < (BCM2048_MAX_RDS_PS - 1))
1716                                match_c = 1;
1717                        continue;
1718                } else if (match_c) {
1719                        match_c = 0;
1720                        if (bcm2048_parse_ps_match_c(bdev, i, index))
1721                                match_d = 1;
1722                        continue;
1723                } else if (match_d) {
1724                        match_d = 0;
1725                        bcm2048_parse_ps_match_d(bdev, i, index);
1726                        continue;
1727                }
1728
1729                /* Skip erroneous blocks due to messed up A block altogether */
1730                if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1731                    BCM2048_RDS_BLOCK_A) {
1732                        crc = bcm2048_rds_block_crc(bdev, i);
1733                        if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1734                                continue;
1735                        /* Synchronize to a good RDS PI */
1736                        if (((bdev->rds_info.radio_text[i + 1] << 8) +
1737                            bdev->rds_info.radio_text[i + 2]) ==
1738                            bdev->rds_info.rds_pi)
1739                                match_b = 1;
1740                }
1741        }
1742}
1743
1744static void bcm2048_rds_fifo_receive(struct bcm2048_device *bdev)
1745{
1746        int err;
1747
1748        mutex_lock(&bdev->mutex);
1749
1750        err = bcm2048_recv_duples(bdev, BCM2048_I2C_RDS_DATA,
1751                                  bdev->rds_info.radio_text, bdev->fifo_size);
1752        if (err != 2) {
1753                dev_err(&bdev->client->dev, "RDS Read problem\n");
1754                mutex_unlock(&bdev->mutex);
1755                return;
1756        }
1757
1758        bdev->rds_info.text_len = bdev->fifo_size;
1759
1760        bcm2048_parse_rds_pi(bdev);
1761        bcm2048_parse_rds_rt(bdev);
1762        bcm2048_parse_rds_ps(bdev);
1763
1764        mutex_unlock(&bdev->mutex);
1765
1766        wake_up_interruptible(&bdev->read_queue);
1767}
1768
1769static int bcm2048_get_rds_data(struct bcm2048_device *bdev, char *data)
1770{
1771        int err = 0, i, p = 0;
1772        char *data_buffer;
1773
1774        mutex_lock(&bdev->mutex);
1775
1776        if (!bdev->rds_info.text_len) {
1777                err = -EINVAL;
1778                goto unlock;
1779        }
1780
1781        data_buffer = kcalloc(BCM2048_MAX_RDS_RADIO_TEXT, 5, GFP_KERNEL);
1782        if (!data_buffer) {
1783                err = -ENOMEM;
1784                goto unlock;
1785        }
1786
1787        for (i = 0; i < bdev->rds_info.text_len; i++) {
1788                p += sprintf(data_buffer + p, "%x ",
1789                             bdev->rds_info.radio_text[i]);
1790        }
1791
1792        memcpy(data, data_buffer, p);
1793        kfree(data_buffer);
1794
1795unlock:
1796        mutex_unlock(&bdev->mutex);
1797        return err;
1798}
1799
1800/*
1801 *      BCM2048 default initialization sequence
1802 */
1803static int bcm2048_init(struct bcm2048_device *bdev)
1804{
1805        int err;
1806
1807        err = bcm2048_set_power_state(bdev, BCM2048_POWER_ON);
1808        if (err < 0)
1809                goto exit;
1810
1811        err = bcm2048_set_audio_route(bdev, BCM2048_AUDIO_ROUTE_DAC);
1812        if (err < 0)
1813                goto exit;
1814
1815        err = bcm2048_set_dac_output(bdev, BCM2048_DAC_OUTPUT_LEFT |
1816                                     BCM2048_DAC_OUTPUT_RIGHT);
1817
1818exit:
1819        return err;
1820}
1821
1822/*
1823 *      BCM2048 default deinitialization sequence
1824 */
1825static int bcm2048_deinit(struct bcm2048_device *bdev)
1826{
1827        int err;
1828
1829        err = bcm2048_set_audio_route(bdev, 0);
1830        if (err < 0)
1831                goto exit;
1832
1833        err = bcm2048_set_dac_output(bdev, 0);
1834        if (err < 0)
1835                goto exit;
1836
1837        err = bcm2048_set_power_state(bdev, BCM2048_POWER_OFF);
1838        if (err < 0)
1839                goto exit;
1840
1841exit:
1842        return err;
1843}
1844
1845/*
1846 *      BCM2048 probe sequence
1847 */
1848static int bcm2048_probe(struct bcm2048_device *bdev)
1849{
1850        int err;
1851
1852        err = bcm2048_set_power_state(bdev, BCM2048_POWER_ON);
1853        if (err < 0)
1854                goto unlock;
1855
1856        err = bcm2048_checkrev(bdev);
1857        if (err < 0)
1858                goto unlock;
1859
1860        err = bcm2048_set_mute(bdev, BCM2048_DEFAULT_MUTE);
1861        if (err < 0)
1862                goto unlock;
1863
1864        err = bcm2048_set_region(bdev, BCM2048_DEFAULT_REGION);
1865        if (err < 0)
1866                goto unlock;
1867
1868        err = bcm2048_set_fm_search_rssi_threshold(bdev,
1869                                        BCM2048_DEFAULT_RSSI_THRESHOLD);
1870        if (err < 0)
1871                goto unlock;
1872
1873        err = bcm2048_set_fm_automatic_stereo_mono(bdev, BCM2048_ITEM_ENABLED);
1874        if (err < 0)
1875                goto unlock;
1876
1877        err = bcm2048_get_rds_wline(bdev);
1878        if (err < BCM2048_DEFAULT_RDS_WLINE)
1879                err = bcm2048_set_rds_wline(bdev, BCM2048_DEFAULT_RDS_WLINE);
1880        if (err < 0)
1881                goto unlock;
1882
1883        err = bcm2048_set_power_state(bdev, BCM2048_POWER_OFF);
1884
1885        init_waitqueue_head(&bdev->read_queue);
1886        bdev->rds_data_available = 0;
1887        bdev->rd_index = 0;
1888        bdev->users = 0;
1889
1890unlock:
1891        return err;
1892}
1893
1894/*
1895 *      BCM2048 workqueue handler
1896 */
1897static void bcm2048_work(struct work_struct *work)
1898{
1899        struct bcm2048_device *bdev;
1900        u8 flag_lsb = 0, flag_msb = 0, flags;
1901
1902        bdev = container_of(work, struct bcm2048_device, work);
1903        bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG0, &flag_lsb);
1904        bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG1, &flag_msb);
1905
1906        if (flag_lsb & (BCM2048_FM_FLAG_SEARCH_TUNE_FINISHED |
1907                        BCM2048_FM_FLAG_SEARCH_TUNE_FAIL)) {
1908                if (flag_lsb & BCM2048_FM_FLAG_SEARCH_TUNE_FAIL)
1909                        bdev->scan_state = BCM2048_SCAN_FAIL;
1910                else
1911                        bdev->scan_state = BCM2048_SCAN_OK;
1912
1913                complete(&bdev->compl);
1914        }
1915
1916        if (flag_msb & BCM2048_RDS_FLAG_FIFO_WLINE) {
1917                bcm2048_rds_fifo_receive(bdev);
1918                if (bdev->rds_state) {
1919                        flags = BCM2048_RDS_FLAG_FIFO_WLINE;
1920                        bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK1,
1921                                             flags);
1922                }
1923                bdev->rds_data_available = 1;
1924                bdev->rd_index = 0; /* new data, new start */
1925        }
1926}
1927
1928/*
1929 *      BCM2048 interrupt handler
1930 */
1931static irqreturn_t bcm2048_handler(int irq, void *dev)
1932{
1933        struct bcm2048_device *bdev = dev;
1934
1935        dev_dbg(&bdev->client->dev, "IRQ called, queuing work\n");
1936        if (bdev->power_state)
1937                schedule_work(&bdev->work);
1938
1939        return IRQ_HANDLED;
1940}
1941
1942/*
1943 *      BCM2048 sysfs interface definitions
1944 */
1945#define property_write(prop, type, mask, check)                         \
1946static ssize_t bcm2048_##prop##_write(struct device *dev,               \
1947                                        struct device_attribute *attr,  \
1948                                        const char *buf,                \
1949                                        size_t count)                   \
1950{                                                                       \
1951        struct bcm2048_device *bdev = dev_get_drvdata(dev);             \
1952        type value;                                                     \
1953        int err;                                                        \
1954                                                                        \
1955        if (!bdev)                                                      \
1956                return -ENODEV;                                         \
1957                                                                        \
1958        if (sscanf(buf, mask, &value) != 1)                             \
1959                return -EINVAL;                                         \
1960                                                                        \
1961        if (check)                                                      \
1962                return -EDOM;                                           \
1963                                                                        \
1964        err = bcm2048_set_##prop(bdev, value);                          \
1965                                                                        \
1966        return err < 0 ? err : count;                                   \
1967}
1968
1969#define property_read(prop, size, mask)                                 \
1970static ssize_t bcm2048_##prop##_read(struct device *dev,                \
1971                                        struct device_attribute *attr,  \
1972                                        char *buf)                      \
1973{                                                                       \
1974        struct bcm2048_device *bdev = dev_get_drvdata(dev);             \
1975        int value;                                                      \
1976                                                                        \
1977        if (!bdev)                                                      \
1978                return -ENODEV;                                         \
1979                                                                        \
1980        value = bcm2048_get_##prop(bdev);                               \
1981                                                                        \
1982        if (value >= 0)                                                 \
1983                value = sprintf(buf, mask "\n", value);                 \
1984                                                                        \
1985        return value;                                                   \
1986}
1987
1988#define property_signed_read(prop, size, mask)                          \
1989static ssize_t bcm2048_##prop##_read(struct device *dev,                \
1990                                        struct device_attribute *attr,  \
1991                                        char *buf)                      \
1992{                                                                       \
1993        struct bcm2048_device *bdev = dev_get_drvdata(dev);             \
1994        size value;                                                     \
1995                                                                        \
1996        if (!bdev)                                                      \
1997                return -ENODEV;                                         \
1998                                                                        \
1999        value = bcm2048_get_##prop(bdev);                               \
2000                                                                        \
2001        value = sprintf(buf, mask "\n", value);                         \
2002                                                                        \
2003        return value;                                                   \
2004}
2005
2006#define DEFINE_SYSFS_PROPERTY(prop, signal, size, mask, check)          \
2007property_write(prop, signal size, mask, check)                          \
2008property_read(prop, size, mask)
2009
2010#define property_str_read(prop, size)                                   \
2011static ssize_t bcm2048_##prop##_read(struct device *dev,                \
2012                                        struct device_attribute *attr,  \
2013                                        char *buf)                      \
2014{                                                                       \
2015        struct bcm2048_device *bdev = dev_get_drvdata(dev);             \
2016        int count;                                                      \
2017        u8 *out;                                                        \
2018                                                                        \
2019        if (!bdev)                                                      \
2020                return -ENODEV;                                         \
2021                                                                        \
2022        out = kzalloc(size + 1, GFP_KERNEL);                            \
2023        if (!out)                                                       \
2024                return -ENOMEM;                                         \
2025                                                                        \
2026        bcm2048_get_##prop(bdev, out);                                  \
2027        count = sprintf(buf, "%s\n", out);                              \
2028                                                                        \
2029        kfree(out);                                                     \
2030                                                                        \
2031        return count;                                                   \
2032}
2033
2034DEFINE_SYSFS_PROPERTY(power_state, unsigned, int, "%u", 0)
2035DEFINE_SYSFS_PROPERTY(mute, unsigned, int, "%u", 0)
2036DEFINE_SYSFS_PROPERTY(audio_route, unsigned, int, "%u", 0)
2037DEFINE_SYSFS_PROPERTY(dac_output, unsigned, int, "%u", 0)
2038
2039DEFINE_SYSFS_PROPERTY(fm_hi_lo_injection, unsigned, int, "%u", 0)
2040DEFINE_SYSFS_PROPERTY(fm_frequency, unsigned, int, "%u", 0)
2041DEFINE_SYSFS_PROPERTY(fm_af_frequency, unsigned, int, "%u", 0)
2042DEFINE_SYSFS_PROPERTY(fm_deemphasis, unsigned, int, "%u", 0)
2043DEFINE_SYSFS_PROPERTY(fm_rds_mask, unsigned, int, "%u", 0)
2044DEFINE_SYSFS_PROPERTY(fm_best_tune_mode, unsigned, int, "%u", 0)
2045DEFINE_SYSFS_PROPERTY(fm_search_rssi_threshold, unsigned, int, "%u", 0)
2046DEFINE_SYSFS_PROPERTY(fm_search_mode_direction, unsigned, int, "%u", 0)
2047DEFINE_SYSFS_PROPERTY(fm_search_tune_mode, unsigned, int, "%u", value > 3)
2048
2049DEFINE_SYSFS_PROPERTY(rds, unsigned, int, "%u", 0)
2050DEFINE_SYSFS_PROPERTY(rds_b_block_mask, unsigned, int, "%u", 0)
2051DEFINE_SYSFS_PROPERTY(rds_b_block_match, unsigned, int, "%u", 0)
2052DEFINE_SYSFS_PROPERTY(rds_pi_mask, unsigned, int, "%u", 0)
2053DEFINE_SYSFS_PROPERTY(rds_pi_match, unsigned, int, "%u", 0)
2054DEFINE_SYSFS_PROPERTY(rds_wline, unsigned, int, "%u", 0)
2055property_read(rds_pi, unsigned int, "%x")
2056property_str_read(rds_rt, (BCM2048_MAX_RDS_RT + 1))
2057property_str_read(rds_ps, (BCM2048_MAX_RDS_PS + 1))
2058
2059property_read(fm_rds_flags, unsigned int, "%u")
2060property_str_read(rds_data, BCM2048_MAX_RDS_RADIO_TEXT * 5)
2061
2062property_read(region_bottom_frequency, unsigned int, "%u")
2063property_read(region_top_frequency, unsigned int, "%u")
2064property_signed_read(fm_carrier_error, int, "%d")
2065property_signed_read(fm_rssi, int, "%d")
2066DEFINE_SYSFS_PROPERTY(region, unsigned, int, "%u", 0)
2067
2068static struct device_attribute attrs[] = {
2069        __ATTR(power_state, S_IRUGO | S_IWUSR, bcm2048_power_state_read,
2070               bcm2048_power_state_write),
2071        __ATTR(mute, S_IRUGO | S_IWUSR, bcm2048_mute_read,
2072               bcm2048_mute_write),
2073        __ATTR(audio_route, S_IRUGO | S_IWUSR, bcm2048_audio_route_read,
2074               bcm2048_audio_route_write),
2075        __ATTR(dac_output, S_IRUGO | S_IWUSR, bcm2048_dac_output_read,
2076               bcm2048_dac_output_write),
2077        __ATTR(fm_hi_lo_injection, S_IRUGO | S_IWUSR,
2078               bcm2048_fm_hi_lo_injection_read,
2079               bcm2048_fm_hi_lo_injection_write),
2080        __ATTR(fm_frequency, S_IRUGO | S_IWUSR, bcm2048_fm_frequency_read,
2081               bcm2048_fm_frequency_write),
2082        __ATTR(fm_af_frequency, S_IRUGO | S_IWUSR,
2083               bcm2048_fm_af_frequency_read,
2084               bcm2048_fm_af_frequency_write),
2085        __ATTR(fm_deemphasis, S_IRUGO | S_IWUSR, bcm2048_fm_deemphasis_read,
2086               bcm2048_fm_deemphasis_write),
2087        __ATTR(fm_rds_mask, S_IRUGO | S_IWUSR, bcm2048_fm_rds_mask_read,
2088               bcm2048_fm_rds_mask_write),
2089        __ATTR(fm_best_tune_mode, S_IRUGO | S_IWUSR,
2090               bcm2048_fm_best_tune_mode_read,
2091               bcm2048_fm_best_tune_mode_write),
2092        __ATTR(fm_search_rssi_threshold, S_IRUGO | S_IWUSR,
2093               bcm2048_fm_search_rssi_threshold_read,
2094               bcm2048_fm_search_rssi_threshold_write),
2095        __ATTR(fm_search_mode_direction, S_IRUGO | S_IWUSR,
2096               bcm2048_fm_search_mode_direction_read,
2097               bcm2048_fm_search_mode_direction_write),
2098        __ATTR(fm_search_tune_mode, S_IRUGO | S_IWUSR,
2099               bcm2048_fm_search_tune_mode_read,
2100               bcm2048_fm_search_tune_mode_write),
2101        __ATTR(rds, S_IRUGO | S_IWUSR, bcm2048_rds_read,
2102               bcm2048_rds_write),
2103        __ATTR(rds_b_block_mask, S_IRUGO | S_IWUSR,
2104               bcm2048_rds_b_block_mask_read,
2105               bcm2048_rds_b_block_mask_write),
2106        __ATTR(rds_b_block_match, S_IRUGO | S_IWUSR,
2107               bcm2048_rds_b_block_match_read,
2108               bcm2048_rds_b_block_match_write),
2109        __ATTR(rds_pi_mask, S_IRUGO | S_IWUSR, bcm2048_rds_pi_mask_read,
2110               bcm2048_rds_pi_mask_write),
2111        __ATTR(rds_pi_match, S_IRUGO | S_IWUSR, bcm2048_rds_pi_match_read,
2112               bcm2048_rds_pi_match_write),
2113        __ATTR(rds_wline, S_IRUGO | S_IWUSR, bcm2048_rds_wline_read,
2114               bcm2048_rds_wline_write),
2115        __ATTR(rds_pi, S_IRUGO, bcm2048_rds_pi_read, NULL),
2116        __ATTR(rds_rt, S_IRUGO, bcm2048_rds_rt_read, NULL),
2117        __ATTR(rds_ps, S_IRUGO, bcm2048_rds_ps_read, NULL),
2118        __ATTR(fm_rds_flags, S_IRUGO, bcm2048_fm_rds_flags_read, NULL),
2119        __ATTR(region_bottom_frequency, S_IRUGO,
2120               bcm2048_region_bottom_frequency_read, NULL),
2121        __ATTR(region_top_frequency, S_IRUGO,
2122               bcm2048_region_top_frequency_read, NULL),
2123        __ATTR(fm_carrier_error, S_IRUGO,
2124               bcm2048_fm_carrier_error_read, NULL),
2125        __ATTR(fm_rssi, S_IRUGO,
2126               bcm2048_fm_rssi_read, NULL),
2127        __ATTR(region, S_IRUGO | S_IWUSR, bcm2048_region_read,
2128               bcm2048_region_write),
2129        __ATTR(rds_data, S_IRUGO, bcm2048_rds_data_read, NULL),
2130};
2131
2132static int bcm2048_sysfs_unregister_properties(struct bcm2048_device *bdev,
2133                                               int size)
2134{
2135        int i;
2136
2137        for (i = 0; i < size; i++)
2138                device_remove_file(&bdev->client->dev, &attrs[i]);
2139
2140        return 0;
2141}
2142
2143static int bcm2048_sysfs_register_properties(struct bcm2048_device *bdev)
2144{
2145        int err = 0;
2146        int i;
2147
2148        for (i = 0; i < ARRAY_SIZE(attrs); i++) {
2149                if (device_create_file(&bdev->client->dev, &attrs[i]) != 0) {
2150                        dev_err(&bdev->client->dev,
2151                                "could not register sysfs entry\n");
2152                        err = -EBUSY;
2153                        bcm2048_sysfs_unregister_properties(bdev, i);
2154                        break;
2155                }
2156        }
2157
2158        return err;
2159}
2160
2161static int bcm2048_fops_open(struct file *file)
2162{
2163        struct bcm2048_device *bdev = video_drvdata(file);
2164
2165        bdev->users++;
2166        bdev->rd_index = 0;
2167        bdev->rds_data_available = 0;
2168
2169        return 0;
2170}
2171
2172static int bcm2048_fops_release(struct file *file)
2173{
2174        struct bcm2048_device *bdev = video_drvdata(file);
2175
2176        bdev->users--;
2177
2178        return 0;
2179}
2180
2181static unsigned int bcm2048_fops_poll(struct file *file,
2182                                      struct poll_table_struct *pts)
2183{
2184        struct bcm2048_device *bdev = video_drvdata(file);
2185        int retval = 0;
2186
2187        poll_wait(file, &bdev->read_queue, pts);
2188
2189        if (bdev->rds_data_available)
2190                retval = POLLIN | POLLRDNORM;
2191
2192        return retval;
2193}
2194
2195static ssize_t bcm2048_fops_read(struct file *file, char __user *buf,
2196                                 size_t count, loff_t *ppos)
2197{
2198        struct bcm2048_device *bdev = video_drvdata(file);
2199        int i;
2200        int retval = 0;
2201
2202        /* we return at least 3 bytes, one block */
2203        count = (count / 3) * 3; /* only multiples of 3 */
2204        if (count < 3)
2205                return -ENOBUFS;
2206
2207        while (!bdev->rds_data_available) {
2208                if (file->f_flags & O_NONBLOCK) {
2209                        retval = -EWOULDBLOCK;
2210                        goto done;
2211                }
2212                /* interruptible_sleep_on(&bdev->read_queue); */
2213                if (wait_event_interruptible(bdev->read_queue,
2214                    bdev->rds_data_available) < 0) {
2215                        retval = -EINTR;
2216                        goto done;
2217                }
2218        }
2219
2220        mutex_lock(&bdev->mutex);
2221        /* copy data to userspace */
2222        i = bdev->fifo_size - bdev->rd_index;
2223        if (count > i)
2224                count = (i / 3) * 3;
2225
2226        i = 0;
2227        while (i < count) {
2228                unsigned char tmpbuf[3];
2229
2230                tmpbuf[i] = bdev->rds_info.radio_text[bdev->rd_index + i + 2];
2231                tmpbuf[i + 1] =
2232                        bdev->rds_info.radio_text[bdev->rd_index + i + 1];
2233                tmpbuf[i + 2] =
2234                        (bdev->rds_info.radio_text[bdev->rd_index + i] &
2235                         0xf0) >> 4;
2236                if ((bdev->rds_info.radio_text[bdev->rd_index + i] &
2237                    BCM2048_RDS_CRC_MASK) == BCM2048_RDS_CRC_UNRECOVARABLE)
2238                        tmpbuf[i + 2] |= 0x80;
2239                if (copy_to_user(buf + i, tmpbuf, 3)) {
2240                        retval = -EFAULT;
2241                        break;
2242                }
2243                i += 3;
2244        }
2245
2246        bdev->rd_index += i;
2247        if (bdev->rd_index >= bdev->fifo_size)
2248                bdev->rds_data_available = 0;
2249
2250        mutex_unlock(&bdev->mutex);
2251        if (retval == 0)
2252                retval = i;
2253
2254done:
2255        return retval;
2256}
2257
2258/*
2259 *      bcm2048_fops - file operations interface
2260 */
2261static const struct v4l2_file_operations bcm2048_fops = {
2262        .owner          = THIS_MODULE,
2263        .unlocked_ioctl = video_ioctl2,
2264        /* for RDS read support */
2265        .open           = bcm2048_fops_open,
2266        .release        = bcm2048_fops_release,
2267        .read           = bcm2048_fops_read,
2268        .poll           = bcm2048_fops_poll
2269};
2270
2271/*
2272 *      Video4Linux Interface
2273 */
2274static struct v4l2_queryctrl bcm2048_v4l2_queryctrl[] = {
2275        {
2276                .id             = V4L2_CID_AUDIO_VOLUME,
2277                .flags          = V4L2_CTRL_FLAG_DISABLED,
2278        },
2279        {
2280                .id             = V4L2_CID_AUDIO_BALANCE,
2281                .flags          = V4L2_CTRL_FLAG_DISABLED,
2282        },
2283        {
2284                .id             = V4L2_CID_AUDIO_BASS,
2285                .flags          = V4L2_CTRL_FLAG_DISABLED,
2286        },
2287        {
2288                .id             = V4L2_CID_AUDIO_TREBLE,
2289                .flags          = V4L2_CTRL_FLAG_DISABLED,
2290        },
2291        {
2292                .id             = V4L2_CID_AUDIO_MUTE,
2293                .type           = V4L2_CTRL_TYPE_BOOLEAN,
2294                .name           = "Mute",
2295                .minimum        = 0,
2296                .maximum        = 1,
2297                .step           = 1,
2298                .default_value  = 1,
2299        },
2300        {
2301                .id             = V4L2_CID_AUDIO_LOUDNESS,
2302                .flags          = V4L2_CTRL_FLAG_DISABLED,
2303        },
2304};
2305
2306static int bcm2048_vidioc_querycap(struct file *file, void *priv,
2307                                   struct v4l2_capability *capability)
2308{
2309        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2310
2311        strlcpy(capability->driver, BCM2048_DRIVER_NAME,
2312                sizeof(capability->driver));
2313        strlcpy(capability->card, BCM2048_DRIVER_CARD,
2314                sizeof(capability->card));
2315        snprintf(capability->bus_info, 32, "I2C: 0x%X", bdev->client->addr);
2316        capability->device_caps = V4L2_CAP_TUNER | V4L2_CAP_RADIO |
2317                                        V4L2_CAP_HW_FREQ_SEEK;
2318        capability->capabilities = capability->device_caps |
2319                V4L2_CAP_DEVICE_CAPS;
2320
2321        return 0;
2322}
2323
2324static int bcm2048_vidioc_g_input(struct file *filp, void *priv,
2325                                  unsigned int *i)
2326{
2327        *i = 0;
2328
2329        return 0;
2330}
2331
2332static int bcm2048_vidioc_s_input(struct file *filp, void *priv,
2333                                  unsigned int i)
2334{
2335        if (i)
2336                return -EINVAL;
2337
2338        return 0;
2339}
2340
2341static int bcm2048_vidioc_queryctrl(struct file *file, void *priv,
2342                                    struct v4l2_queryctrl *qc)
2343{
2344        int i;
2345
2346        for (i = 0; i < ARRAY_SIZE(bcm2048_v4l2_queryctrl); i++) {
2347                if (qc->id && qc->id == bcm2048_v4l2_queryctrl[i].id) {
2348                        *qc = bcm2048_v4l2_queryctrl[i];
2349                        return 0;
2350                }
2351        }
2352
2353        return -EINVAL;
2354}
2355
2356static int bcm2048_vidioc_g_ctrl(struct file *file, void *priv,
2357                                 struct v4l2_control *ctrl)
2358{
2359        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2360        int err = 0;
2361
2362        if (!bdev)
2363                return -ENODEV;
2364
2365        switch (ctrl->id) {
2366        case V4L2_CID_AUDIO_MUTE:
2367                err = bcm2048_get_mute(bdev);
2368                if (err >= 0)
2369                        ctrl->value = err;
2370                break;
2371        }
2372
2373        return err;
2374}
2375
2376static int bcm2048_vidioc_s_ctrl(struct file *file, void *priv,
2377                                 struct v4l2_control *ctrl)
2378{
2379        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2380        int err = 0;
2381
2382        if (!bdev)
2383                return -ENODEV;
2384
2385        switch (ctrl->id) {
2386        case V4L2_CID_AUDIO_MUTE:
2387                if (ctrl->value) {
2388                        if (bdev->power_state) {
2389                                err = bcm2048_set_mute(bdev, ctrl->value);
2390                                err |= bcm2048_deinit(bdev);
2391                        }
2392                } else {
2393                        if (!bdev->power_state) {
2394                                err = bcm2048_init(bdev);
2395                                err |= bcm2048_set_mute(bdev, ctrl->value);
2396                        }
2397                }
2398                break;
2399        }
2400
2401        return err;
2402}
2403
2404static int bcm2048_vidioc_g_audio(struct file *file, void *priv,
2405                                  struct v4l2_audio *audio)
2406{
2407        if (audio->index > 1)
2408                return -EINVAL;
2409
2410        strncpy(audio->name, "Radio", 32);
2411        audio->capability = V4L2_AUDCAP_STEREO;
2412
2413        return 0;
2414}
2415
2416static int bcm2048_vidioc_s_audio(struct file *file, void *priv,
2417                                  const struct v4l2_audio *audio)
2418{
2419        if (audio->index != 0)
2420                return -EINVAL;
2421
2422        return 0;
2423}
2424
2425static int bcm2048_vidioc_g_tuner(struct file *file, void *priv,
2426                                  struct v4l2_tuner *tuner)
2427{
2428        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2429        s8 f_error;
2430        s8 rssi;
2431
2432        if (!bdev)
2433                return -ENODEV;
2434
2435        if (tuner->index > 0)
2436                return -EINVAL;
2437
2438        strncpy(tuner->name, "FM Receiver", 32);
2439        tuner->type = V4L2_TUNER_RADIO;
2440        tuner->rangelow =
2441                dev_to_v4l2(bcm2048_get_region_bottom_frequency(bdev));
2442        tuner->rangehigh =
2443                dev_to_v4l2(bcm2048_get_region_top_frequency(bdev));
2444        tuner->rxsubchans = V4L2_TUNER_SUB_STEREO;
2445        tuner->capability = V4L2_TUNER_CAP_STEREO | V4L2_TUNER_CAP_LOW;
2446        tuner->audmode = V4L2_TUNER_MODE_STEREO;
2447        tuner->afc = 0;
2448        if (bdev->power_state) {
2449                /*
2450                 * Report frequencies with high carrier errors to have zero
2451                 * signal level
2452                 */
2453                f_error = bcm2048_get_fm_carrier_error(bdev);
2454                if (f_error < BCM2048_FREQ_ERROR_FLOOR ||
2455                    f_error > BCM2048_FREQ_ERROR_ROOF) {
2456                        tuner->signal = 0;
2457                } else {
2458                        /*
2459                         * RSSI level -60 dB is defined to report full
2460                         * signal strength
2461                         */
2462                        rssi = bcm2048_get_fm_rssi(bdev);
2463                        if (rssi >= BCM2048_RSSI_LEVEL_BASE) {
2464                                tuner->signal = 0xFFFF;
2465                        } else if (rssi > BCM2048_RSSI_LEVEL_ROOF) {
2466                                tuner->signal = (rssi +
2467                                                 BCM2048_RSSI_LEVEL_ROOF_NEG)
2468                                                 * BCM2048_SIGNAL_MULTIPLIER;
2469                        } else {
2470                                tuner->signal = 0;
2471                        }
2472                }
2473        } else {
2474                tuner->signal = 0;
2475        }
2476
2477        return 0;
2478}
2479
2480static int bcm2048_vidioc_s_tuner(struct file *file, void *priv,
2481                                  const struct v4l2_tuner *tuner)
2482{
2483        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2484
2485        if (!bdev)
2486                return -ENODEV;
2487
2488        if (tuner->index > 0)
2489                return -EINVAL;
2490
2491        return 0;
2492}
2493
2494static int bcm2048_vidioc_g_frequency(struct file *file, void *priv,
2495                                      struct v4l2_frequency *freq)
2496{
2497        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2498        int err = 0;
2499        int f;
2500
2501        if (!bdev->power_state)
2502                return -ENODEV;
2503
2504        freq->type = V4L2_TUNER_RADIO;
2505        f = bcm2048_get_fm_frequency(bdev);
2506
2507        if (f < 0)
2508                err = f;
2509        else
2510                freq->frequency = dev_to_v4l2(f);
2511
2512        return err;
2513}
2514
2515static int bcm2048_vidioc_s_frequency(struct file *file, void *priv,
2516                                      const struct v4l2_frequency *freq)
2517{
2518        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2519        int err;
2520
2521        if (freq->type != V4L2_TUNER_RADIO)
2522                return -EINVAL;
2523
2524        if (!bdev->power_state)
2525                return -ENODEV;
2526
2527        err = bcm2048_set_fm_frequency(bdev, v4l2_to_dev(freq->frequency));
2528        err |= bcm2048_set_fm_search_tune_mode(bdev, BCM2048_FM_PRE_SET_MODE);
2529
2530        return err;
2531}
2532
2533static int bcm2048_vidioc_s_hw_freq_seek(struct file *file, void *priv,
2534                                         const struct v4l2_hw_freq_seek *seek)
2535{
2536        struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2537        int err;
2538
2539        if (!bdev->power_state)
2540                return -ENODEV;
2541
2542        if ((seek->tuner != 0) || (seek->type != V4L2_TUNER_RADIO))
2543                return -EINVAL;
2544
2545        err = bcm2048_set_fm_search_mode_direction(bdev, seek->seek_upward);
2546        err |= bcm2048_set_fm_search_tune_mode(bdev,
2547                                               BCM2048_FM_AUTO_SEARCH_MODE);
2548
2549        return err;
2550}
2551
2552static struct v4l2_ioctl_ops bcm2048_ioctl_ops = {
2553        .vidioc_querycap        = bcm2048_vidioc_querycap,
2554        .vidioc_g_input         = bcm2048_vidioc_g_input,
2555        .vidioc_s_input         = bcm2048_vidioc_s_input,
2556        .vidioc_queryctrl       = bcm2048_vidioc_queryctrl,
2557        .vidioc_g_ctrl          = bcm2048_vidioc_g_ctrl,
2558        .vidioc_s_ctrl          = bcm2048_vidioc_s_ctrl,
2559        .vidioc_g_audio         = bcm2048_vidioc_g_audio,
2560        .vidioc_s_audio         = bcm2048_vidioc_s_audio,
2561        .vidioc_g_tuner         = bcm2048_vidioc_g_tuner,
2562        .vidioc_s_tuner         = bcm2048_vidioc_s_tuner,
2563        .vidioc_g_frequency     = bcm2048_vidioc_g_frequency,
2564        .vidioc_s_frequency     = bcm2048_vidioc_s_frequency,
2565        .vidioc_s_hw_freq_seek  = bcm2048_vidioc_s_hw_freq_seek,
2566};
2567
2568/*
2569 * bcm2048_viddev_template - video device interface
2570 */
2571static struct video_device bcm2048_viddev_template = {
2572        .fops                   = &bcm2048_fops,
2573        .name                   = BCM2048_DRIVER_NAME,
2574        .release                = video_device_release_empty,
2575        .ioctl_ops              = &bcm2048_ioctl_ops,
2576};
2577
2578/*
2579 *      I2C driver interface
2580 */
2581static int bcm2048_i2c_driver_probe(struct i2c_client *client,
2582                                    const struct i2c_device_id *id)
2583{
2584        struct bcm2048_device *bdev;
2585        int err;
2586
2587        bdev = kzalloc(sizeof(*bdev), GFP_KERNEL);
2588        if (!bdev) {
2589                err = -ENOMEM;
2590                goto exit;
2591        }
2592
2593        bdev->client = client;
2594        i2c_set_clientdata(client, bdev);
2595        mutex_init(&bdev->mutex);
2596        init_completion(&bdev->compl);
2597        INIT_WORK(&bdev->work, bcm2048_work);
2598
2599        if (client->irq) {
2600                err = request_irq(client->irq,
2601                                  bcm2048_handler, IRQF_TRIGGER_FALLING,
2602                                  client->name, bdev);
2603                if (err < 0) {
2604                        dev_err(&client->dev, "Could not request IRQ\n");
2605                        goto free_bdev;
2606                }
2607                dev_dbg(&client->dev, "IRQ requested.\n");
2608        } else {
2609                dev_dbg(&client->dev, "IRQ not configured. Using timeouts.\n");
2610        }
2611
2612        bdev->videodev = bcm2048_viddev_template;
2613        video_set_drvdata(&bdev->videodev, bdev);
2614        if (video_register_device(&bdev->videodev, VFL_TYPE_RADIO, radio_nr)) {
2615                dev_dbg(&client->dev, "Could not register video device.\n");
2616                err = -EIO;
2617                goto free_irq;
2618        }
2619
2620        err = bcm2048_sysfs_register_properties(bdev);
2621        if (err < 0) {
2622                dev_dbg(&client->dev, "Could not register sysfs interface.\n");
2623                goto free_registration;
2624        }
2625
2626        err = bcm2048_probe(bdev);
2627        if (err < 0) {
2628                dev_dbg(&client->dev, "Failed to probe device information.\n");
2629                goto free_sysfs;
2630        }
2631
2632        return 0;
2633
2634free_sysfs:
2635        bcm2048_sysfs_unregister_properties(bdev, ARRAY_SIZE(attrs));
2636free_registration:
2637        video_unregister_device(&bdev->videodev);
2638free_irq:
2639        if (client->irq)
2640                free_irq(client->irq, bdev);
2641free_bdev:
2642        i2c_set_clientdata(client, NULL);
2643        kfree(bdev);
2644exit:
2645        return err;
2646}
2647
2648static int __exit bcm2048_i2c_driver_remove(struct i2c_client *client)
2649{
2650        struct bcm2048_device *bdev = i2c_get_clientdata(client);
2651
2652        if (!client->adapter)
2653                return -ENODEV;
2654
2655        if (bdev) {
2656                bcm2048_sysfs_unregister_properties(bdev, ARRAY_SIZE(attrs));
2657                video_unregister_device(&bdev->videodev);
2658
2659                if (bdev->power_state)
2660                        bcm2048_set_power_state(bdev, BCM2048_POWER_OFF);
2661
2662                if (client->irq > 0)
2663                        free_irq(client->irq, bdev);
2664
2665                cancel_work_sync(&bdev->work);
2666
2667                kfree(bdev);
2668        }
2669
2670        return 0;
2671}
2672
2673/*
2674 *      bcm2048_i2c_driver - i2c driver interface
2675 */
2676static const struct i2c_device_id bcm2048_id[] = {
2677        { "bcm2048", 0 },
2678        { },
2679};
2680MODULE_DEVICE_TABLE(i2c, bcm2048_id);
2681
2682static struct i2c_driver bcm2048_i2c_driver = {
2683        .driver         = {
2684                .name   = BCM2048_DRIVER_NAME,
2685        },
2686        .probe          = bcm2048_i2c_driver_probe,
2687        .remove         = __exit_p(bcm2048_i2c_driver_remove),
2688        .id_table       = bcm2048_id,
2689};
2690
2691module_i2c_driver(bcm2048_i2c_driver);
2692
2693MODULE_LICENSE("GPL");
2694MODULE_AUTHOR(BCM2048_DRIVER_AUTHOR);
2695MODULE_DESCRIPTION(BCM2048_DRIVER_DESC);
2696MODULE_VERSION("0.0.2");
2697