2 * drivers/staging/media/radio-bcm2048.c
4 * Driver for I2C Broadcom BCM2048 FM Radio Receiver:
6 * Copyright (C) Nokia Corporation
7 * Contact: Eero Nurkkala <ext-eero.nurkkala@nokia.com>
9 * Copyright (C) Nils Faerber <nils.faerber@kernelconcepts.de>
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.
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.
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
28 * Eero Nurkkala <ext-eero.nurkkala@nokia.com>
30 * - Initial implementation
31 * 2010-02-21 Nils Faerber <nils.faerber@kernelconcepts.de>
33 * - Add support for interrupt driven rds data reading
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"
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"
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
96 /* BCM2048_I2C_FM_RDS_SYSTEM */
97 #define BCM2048_FM_ON 0x01
98 #define BCM2048_RDS_ON 0x02
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
107 /* BCM2048_I2C_RDS_CTRL0 */
108 #define BCM2048_RBDS_RDS_SELECT 0x01
109 #define BCM2048_FLUSH_FIFO 0x02
111 /* BCM2048_I2C_FM_AUDIO_PAUSE */
112 #define BCM2048_AUDIO_PAUSE_RSSI_TRESH 0x0f
113 #define BCM2048_AUDIO_PAUSE_DURATION 0xf0
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
125 /* BCM2048_I2C_FM_SEARCH_CTRL0 */
126 #define BCM2048_SEARCH_RSSI_THRESHOLD 0x7f
127 #define BCM2048_SEARCH_DIRECTION 0x80
129 /* BCM2048_I2C_FM_SEARCH_TUNE_MODE */
130 #define BCM2048_FM_AUTO_SEARCH 0x03
132 /* BCM2048_I2C_FM_RSSI */
133 #define BCM2048_RSSI_VALUE 0xff
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
145 /* BCM2048_I2C_RDS_DATA */
146 #define BCM2048_SLAVE_ADDRESS 0x3f
147 #define BCM2048_SLAVE_ENABLE 0x80
149 /* BCM2048_I2C_FM_BEST_TUNE_MODE */
150 #define BCM2048_BEST_TUNE_MODE 0x80
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
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
165 #define BCM2048_RDS_MARK_END_BYTE0 0x7C
166 #define BCM2048_RDS_MARK_END_BYTEN 0xFF
168 #define BCM2048_FM_FLAGS_ALL (FM_FLAG_SEARCH_TUNE_FINISHED | \
169 FM_FLAG_SEARCH_TUNE_FAIL | \
171 FM_FLAG_CARRIER_ERROR_HIGH | \
172 FM_FLAG_AUDIO_PAUSE_INDICATION | \
173 FLAG_STEREO_DETECTED | FLAG_STEREO_ACTIVE)
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)
179 #define BCM2048_DEFAULT_TIMEOUT 1500
180 #define BCM2048_AUTO_SEARCH_TIMEOUT 3000
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)
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)
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
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
202 #define BCM2048_FREQUENCY_BASE 64000
204 #define BCM2048_POWER_ON 0x01
205 #define BCM2048_POWER_OFF 0x00
207 #define BCM2048_ITEM_ENABLED 0x01
208 #define BCM2048_SEARCH_DIRECTION_UP 0x01
210 #define BCM2048_DE_EMPHASIS_75us 75
211 #define BCM2048_DE_EMPHASIS_50us 50
213 #define BCM2048_SCAN_FAIL 0x00
214 #define BCM2048_SCAN_OK 0x01
216 #define BCM2048_FREQ_ERROR_FLOOR -20
217 #define BCM2048_FREQ_ERROR_ROOF 20
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))
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
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
242 #define BCM2048_RDS_RT 0x20
243 #define BCM2048_RDS_PS 0x00
245 #define BCM2048_RDS_GROUP_AB_MASK 0x08
246 #define BCM2048_RDS_GROUP_A 0x00
247 #define BCM2048_RDS_GROUP_B 0x08
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
254 #define BCM2048_RDS_PS_INDEX 0x03
258 #define BCM2048_MAX_RDS_RT (64 + 1)
259 u8 rds_rt[BCM2048_MAX_RDS_RT];
262 #define BCM2048_MAX_RDS_PS (8 + 1)
263 u8 rds_ps[BCM2048_MAX_RDS_PS];
266 #define BCM2048_MAX_RDS_RADIO_TEXT 255
267 u8 radio_text[BCM2048_MAX_RDS_RADIO_TEXT + 3];
272 u32 bottom_frequency;
279 struct bcm2048_device {
280 struct i2c_client *client;
281 struct video_device videodev;
282 struct work_struct work;
283 struct completion compl;
285 struct bcm2048_platform_data *platform_data;
286 struct rds_info rds_info;
287 struct region_info region_info;
289 u8 cache_fm_rds_system;
291 u8 cache_fm_audio_ctrl0;
292 u8 cache_fm_search_ctrl0;
299 /* for rds data device read */
300 wait_queue_head_t read_queue;
302 unsigned char rds_data_available;
303 unsigned int rd_index;
306 static int radio_nr = -1; /* radio device minor (-1 ==> auto assign) */
307 module_param(radio_nr, int, 0);
308 MODULE_PARM_DESC(radio_nr,
309 "Minor number for radio device (-1 ==> auto assign)");
311 static const struct region_info region_configs[] = {
314 .channel_spacing = 20,
315 .bottom_frequency = 87500,
316 .top_frequency = 108000,
322 .channel_spacing = 20,
323 .bottom_frequency = 87500,
324 .top_frequency = 108000,
330 .channel_spacing = 10,
331 .bottom_frequency = 87500,
332 .top_frequency = 108000,
338 .channel_spacing = 10,
339 .bottom_frequency = 76000,
340 .top_frequency = 90000,
347 * I2C Interface read / write
349 static int bcm2048_send_command(struct bcm2048_device *bdev, unsigned int reg,
352 struct i2c_client *client = bdev->client;
355 if (!bdev->power_state) {
356 dev_err(&bdev->client->dev, "bcm2048: chip not powered!\n");
360 data[0] = reg & 0xff;
361 data[1] = value & 0xff;
363 if (i2c_master_send(client, data, 2) == 2)
366 dev_err(&bdev->client->dev, "BCM I2C error!\n");
367 dev_err(&bdev->client->dev, "Is Bluetooth up and running?\n");
371 static int bcm2048_recv_command(struct bcm2048_device *bdev, unsigned int reg,
374 struct i2c_client *client = bdev->client;
376 if (!bdev->power_state) {
377 dev_err(&bdev->client->dev, "bcm2048: chip not powered!\n");
381 value[0] = i2c_smbus_read_byte_data(client, reg & 0xff);
386 static int bcm2048_recv_duples(struct bcm2048_device *bdev, unsigned int reg,
387 u8 *value, u8 duples)
389 struct i2c_client *client = bdev->client;
390 struct i2c_adapter *adap = client->adapter;
391 struct i2c_msg msg[2];
394 if (!bdev->power_state) {
395 dev_err(&bdev->client->dev, "bcm2048: chip not powered!\n");
401 msg[0].addr = client->addr;
402 msg[0].flags = client->flags & I2C_M_TEN;
406 msg[1].addr = client->addr;
407 msg[1].flags = client->flags & I2C_M_TEN;
408 msg[1].flags |= I2C_M_RD;
412 return i2c_transfer(adap, msg, 2);
416 * BCM2048 - I2C register programming helpers
418 static int bcm2048_set_power_state(struct bcm2048_device *bdev, u8 power)
422 mutex_lock(&bdev->mutex);
425 bdev->power_state = BCM2048_POWER_ON;
426 bdev->cache_fm_rds_system |= BCM2048_FM_ON;
428 bdev->cache_fm_rds_system &= ~BCM2048_FM_ON;
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!
437 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM,
438 bdev->cache_fm_rds_system);
439 msleep(BCM2048_DEFAULT_POWERING_DELAY);
442 bdev->power_state = BCM2048_POWER_OFF;
444 mutex_unlock(&bdev->mutex);
448 static int bcm2048_get_power_state(struct bcm2048_device *bdev)
453 mutex_lock(&bdev->mutex);
455 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM, &value);
457 mutex_unlock(&bdev->mutex);
459 if (!err && (value & BCM2048_FM_ON))
460 return BCM2048_POWER_ON;
465 static int bcm2048_set_rds_no_lock(struct bcm2048_device *bdev, u8 rds_on)
470 bdev->cache_fm_rds_system &= ~BCM2048_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,
481 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK1,
483 memset(&bdev->rds_info, 0, sizeof(bdev->rds_info));
488 return bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM,
489 bdev->cache_fm_rds_system);
492 static int bcm2048_get_rds_no_lock(struct bcm2048_device *bdev)
497 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_SYSTEM, &value);
499 if (!err && (value & BCM2048_RDS_ON))
500 return BCM2048_ITEM_ENABLED;
505 static int bcm2048_set_rds(struct bcm2048_device *bdev, u8 rds_on)
509 mutex_lock(&bdev->mutex);
511 err = bcm2048_set_rds_no_lock(bdev, rds_on);
513 mutex_unlock(&bdev->mutex);
517 static int bcm2048_get_rds(struct bcm2048_device *bdev)
521 mutex_lock(&bdev->mutex);
523 err = bcm2048_get_rds_no_lock(bdev);
525 mutex_unlock(&bdev->mutex);
529 static int bcm2048_get_rds_pi(struct bcm2048_device *bdev)
531 return bdev->rds_info.rds_pi;
534 static int bcm2048_set_fm_automatic_stereo_mono(struct bcm2048_device *bdev,
539 mutex_lock(&bdev->mutex);
541 bdev->cache_fm_ctrl &= ~BCM2048_STEREO_MONO_AUTO_SELECT;
544 bdev->cache_fm_ctrl |= BCM2048_STEREO_MONO_AUTO_SELECT;
546 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_CTRL,
547 bdev->cache_fm_ctrl);
549 mutex_unlock(&bdev->mutex);
553 static int bcm2048_set_fm_hi_lo_injection(struct bcm2048_device *bdev,
558 mutex_lock(&bdev->mutex);
560 bdev->cache_fm_ctrl &= ~BCM2048_HI_LO_INJECTION;
563 bdev->cache_fm_ctrl |= BCM2048_HI_LO_INJECTION;
565 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_CTRL,
566 bdev->cache_fm_ctrl);
568 mutex_unlock(&bdev->mutex);
572 static int bcm2048_get_fm_hi_lo_injection(struct bcm2048_device *bdev)
577 mutex_lock(&bdev->mutex);
579 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_CTRL, &value);
581 mutex_unlock(&bdev->mutex);
583 if (!err && (value & BCM2048_HI_LO_INJECTION))
584 return BCM2048_ITEM_ENABLED;
589 static int bcm2048_set_fm_frequency(struct bcm2048_device *bdev, u32 frequency)
593 if (frequency < bdev->region_info.bottom_frequency ||
594 frequency > bdev->region_info.top_frequency)
597 frequency -= BCM2048_FREQUENCY_BASE;
599 mutex_lock(&bdev->mutex);
601 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_FREQ0, lsb(frequency));
602 err |= bcm2048_send_command(bdev, BCM2048_I2C_FM_FREQ1,
606 bdev->frequency = frequency;
608 mutex_unlock(&bdev->mutex);
612 static int bcm2048_get_fm_frequency(struct bcm2048_device *bdev)
617 mutex_lock(&bdev->mutex);
619 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_FREQ0, &lsb);
620 err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_FREQ1, &msb);
622 mutex_unlock(&bdev->mutex);
627 err = compose_u16(msb, lsb);
628 err += BCM2048_FREQUENCY_BASE;
633 static int bcm2048_set_fm_af_frequency(struct bcm2048_device *bdev,
638 if (frequency < bdev->region_info.bottom_frequency ||
639 frequency > bdev->region_info.top_frequency)
642 frequency -= BCM2048_FREQUENCY_BASE;
644 mutex_lock(&bdev->mutex);
646 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AF_FREQ0,
648 err |= bcm2048_send_command(bdev, BCM2048_I2C_FM_AF_FREQ1,
651 bdev->frequency = frequency;
653 mutex_unlock(&bdev->mutex);
657 static int bcm2048_get_fm_af_frequency(struct bcm2048_device *bdev)
662 mutex_lock(&bdev->mutex);
664 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AF_FREQ0, &lsb);
665 err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_AF_FREQ1, &msb);
667 mutex_unlock(&bdev->mutex);
672 err = compose_u16(msb, lsb);
673 err += BCM2048_FREQUENCY_BASE;
678 static int bcm2048_set_fm_deemphasis(struct bcm2048_device *bdev, int d)
683 if (d == BCM2048_DE_EMPHASIS_75us)
684 deemphasis = BCM2048_DE_EMPHASIS_SELECT;
688 mutex_lock(&bdev->mutex);
690 bdev->cache_fm_audio_ctrl0 &= ~BCM2048_DE_EMPHASIS_SELECT;
691 bdev->cache_fm_audio_ctrl0 |= deemphasis;
693 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
694 bdev->cache_fm_audio_ctrl0);
697 bdev->region_info.deemphasis = d;
699 mutex_unlock(&bdev->mutex);
704 static int bcm2048_get_fm_deemphasis(struct bcm2048_device *bdev)
709 mutex_lock(&bdev->mutex);
711 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0, &value);
713 mutex_unlock(&bdev->mutex);
716 if (value & BCM2048_DE_EMPHASIS_SELECT)
717 return BCM2048_DE_EMPHASIS_75us;
719 return BCM2048_DE_EMPHASIS_50us;
725 static int bcm2048_set_region(struct bcm2048_device *bdev, u8 region)
728 u32 new_frequency = 0;
730 if (region >= ARRAY_SIZE(region_configs))
733 mutex_lock(&bdev->mutex);
734 bdev->region_info = region_configs[region];
736 if (region_configs[region].bottom_frequency < 87500)
737 bdev->cache_fm_ctrl |= BCM2048_BAND_SELECT;
739 bdev->cache_fm_ctrl &= ~BCM2048_BAND_SELECT;
741 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_CTRL,
742 bdev->cache_fm_ctrl);
744 mutex_unlock(&bdev->mutex);
747 mutex_unlock(&bdev->mutex);
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;
753 if (new_frequency > 0) {
754 err = bcm2048_set_fm_frequency(bdev, new_frequency);
760 err = bcm2048_set_fm_deemphasis(bdev,
761 region_configs[region].deemphasis);
767 static int bcm2048_get_region(struct bcm2048_device *bdev)
771 mutex_lock(&bdev->mutex);
772 err = bdev->region_info.region;
773 mutex_unlock(&bdev->mutex);
778 static int bcm2048_set_mute(struct bcm2048_device *bdev, u16 mute)
782 mutex_lock(&bdev->mutex);
784 bdev->cache_fm_audio_ctrl0 &= ~(BCM2048_RF_MUTE | BCM2048_MANUAL_MUTE);
787 bdev->cache_fm_audio_ctrl0 |= (BCM2048_RF_MUTE |
788 BCM2048_MANUAL_MUTE);
790 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
791 bdev->cache_fm_audio_ctrl0);
794 bdev->mute_state = mute;
796 mutex_unlock(&bdev->mutex);
800 static int bcm2048_get_mute(struct bcm2048_device *bdev)
805 mutex_lock(&bdev->mutex);
807 if (bdev->power_state) {
808 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
811 err = value & (BCM2048_RF_MUTE | BCM2048_MANUAL_MUTE);
813 err = bdev->mute_state;
816 mutex_unlock(&bdev->mutex);
820 static int bcm2048_set_audio_route(struct bcm2048_device *bdev, u8 route)
824 mutex_lock(&bdev->mutex);
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;
831 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
832 bdev->cache_fm_audio_ctrl0);
834 mutex_unlock(&bdev->mutex);
838 static int bcm2048_get_audio_route(struct bcm2048_device *bdev)
843 mutex_lock(&bdev->mutex);
845 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0, &value);
847 mutex_unlock(&bdev->mutex);
850 return value & (BCM2048_AUDIO_ROUTE_DAC |
851 BCM2048_AUDIO_ROUTE_I2S);
856 static int bcm2048_set_dac_output(struct bcm2048_device *bdev, u8 channels)
860 mutex_lock(&bdev->mutex);
862 bdev->cache_fm_audio_ctrl0 &= ~(BCM2048_DAC_OUTPUT_LEFT |
863 BCM2048_DAC_OUTPUT_RIGHT);
864 bdev->cache_fm_audio_ctrl0 |= channels;
866 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0,
867 bdev->cache_fm_audio_ctrl0);
869 mutex_unlock(&bdev->mutex);
873 static int bcm2048_get_dac_output(struct bcm2048_device *bdev)
878 mutex_lock(&bdev->mutex);
880 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_AUDIO_CTRL0, &value);
882 mutex_unlock(&bdev->mutex);
885 return value & (BCM2048_DAC_OUTPUT_LEFT |
886 BCM2048_DAC_OUTPUT_RIGHT);
891 static int bcm2048_set_fm_search_rssi_threshold(struct bcm2048_device *bdev,
896 mutex_lock(&bdev->mutex);
898 threshold &= BCM2048_SEARCH_RSSI_THRESHOLD;
899 bdev->cache_fm_search_ctrl0 &= ~BCM2048_SEARCH_RSSI_THRESHOLD;
900 bdev->cache_fm_search_ctrl0 |= threshold;
902 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0,
903 bdev->cache_fm_search_ctrl0);
905 mutex_unlock(&bdev->mutex);
909 static int bcm2048_get_fm_search_rssi_threshold(struct bcm2048_device *bdev)
914 mutex_lock(&bdev->mutex);
916 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0, &value);
918 mutex_unlock(&bdev->mutex);
921 return value & BCM2048_SEARCH_RSSI_THRESHOLD;
926 static int bcm2048_set_fm_search_mode_direction(struct bcm2048_device *bdev,
931 mutex_lock(&bdev->mutex);
933 bdev->cache_fm_search_ctrl0 &= ~BCM2048_SEARCH_DIRECTION;
936 bdev->cache_fm_search_ctrl0 |= BCM2048_SEARCH_DIRECTION;
938 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0,
939 bdev->cache_fm_search_ctrl0);
941 mutex_unlock(&bdev->mutex);
945 static int bcm2048_get_fm_search_mode_direction(struct bcm2048_device *bdev)
950 mutex_lock(&bdev->mutex);
952 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_SEARCH_CTRL0, &value);
954 mutex_unlock(&bdev->mutex);
956 if (!err && (value & BCM2048_SEARCH_DIRECTION))
957 return BCM2048_SEARCH_DIRECTION_UP;
962 static int bcm2048_set_fm_search_tune_mode(struct bcm2048_device *bdev,
965 int err, timeout, restart_rds = 0;
968 value = mode & BCM2048_FM_AUTO_SEARCH;
970 flags = BCM2048_FM_FLAG_SEARCH_TUNE_FINISHED |
971 BCM2048_FM_FLAG_SEARCH_TUNE_FAIL;
973 mutex_lock(&bdev->mutex);
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.
982 if (bcm2048_get_rds_no_lock(bdev)) {
983 err = bcm2048_set_rds_no_lock(bdev, 0);
989 err = bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK0, flags);
994 bcm2048_send_command(bdev, BCM2048_I2C_FM_SEARCH_TUNE_MODE, value);
996 if (mode != BCM2048_FM_AUTO_SEARCH_MODE)
997 timeout = BCM2048_DEFAULT_TIMEOUT;
999 timeout = BCM2048_AUTO_SEARCH_TIMEOUT;
1001 if (!wait_for_completion_timeout(&bdev->compl,
1002 msecs_to_jiffies(timeout)))
1003 dev_err(&bdev->client->dev, "IRQ timeout.\n");
1006 if (!bdev->scan_state)
1011 err |= bcm2048_set_rds_no_lock(bdev, 1);
1013 mutex_unlock(&bdev->mutex);
1018 static int bcm2048_get_fm_search_tune_mode(struct bcm2048_device *bdev)
1023 mutex_lock(&bdev->mutex);
1025 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_SEARCH_TUNE_MODE,
1028 mutex_unlock(&bdev->mutex);
1031 return value & BCM2048_FM_AUTO_SEARCH;
1036 static int bcm2048_set_rds_b_block_mask(struct bcm2048_device *bdev, u16 mask)
1040 mutex_lock(&bdev->mutex);
1042 err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MASK0,
1044 err |= bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MASK1,
1047 mutex_unlock(&bdev->mutex);
1051 static int bcm2048_get_rds_b_block_mask(struct bcm2048_device *bdev)
1054 u8 lsb = 0, msb = 0;
1056 mutex_lock(&bdev->mutex);
1058 err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MASK0, &lsb);
1059 err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MASK1, &msb);
1061 mutex_unlock(&bdev->mutex);
1064 return compose_u16(msb, lsb);
1069 static int bcm2048_set_rds_b_block_match(struct bcm2048_device *bdev,
1074 mutex_lock(&bdev->mutex);
1076 err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH0,
1078 err |= bcm2048_send_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH1,
1081 mutex_unlock(&bdev->mutex);
1085 static int bcm2048_get_rds_b_block_match(struct bcm2048_device *bdev)
1088 u8 lsb = 0, msb = 0;
1090 mutex_lock(&bdev->mutex);
1092 err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH0, &lsb);
1093 err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_BLKB_MATCH1, &msb);
1095 mutex_unlock(&bdev->mutex);
1098 return compose_u16(msb, lsb);
1103 static int bcm2048_set_rds_pi_mask(struct bcm2048_device *bdev, u16 mask)
1107 mutex_lock(&bdev->mutex);
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));
1112 mutex_unlock(&bdev->mutex);
1116 static int bcm2048_get_rds_pi_mask(struct bcm2048_device *bdev)
1119 u8 lsb = 0, msb = 0;
1121 mutex_lock(&bdev->mutex);
1123 err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MASK0, &lsb);
1124 err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MASK1, &msb);
1126 mutex_unlock(&bdev->mutex);
1129 return compose_u16(msb, lsb);
1134 static int bcm2048_set_rds_pi_match(struct bcm2048_device *bdev, u16 match)
1138 mutex_lock(&bdev->mutex);
1140 err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_PI_MATCH0,
1142 err |= bcm2048_send_command(bdev, BCM2048_I2C_RDS_PI_MATCH1,
1145 mutex_unlock(&bdev->mutex);
1149 static int bcm2048_get_rds_pi_match(struct bcm2048_device *bdev)
1152 u8 lsb = 0, msb = 0;
1154 mutex_lock(&bdev->mutex);
1156 err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MATCH0, &lsb);
1157 err |= bcm2048_recv_command(bdev, BCM2048_I2C_RDS_PI_MATCH1, &msb);
1159 mutex_unlock(&bdev->mutex);
1162 return compose_u16(msb, lsb);
1167 static int bcm2048_set_fm_rds_mask(struct bcm2048_device *bdev, u16 mask)
1171 mutex_lock(&bdev->mutex);
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));
1176 mutex_unlock(&bdev->mutex);
1180 static int bcm2048_get_fm_rds_mask(struct bcm2048_device *bdev)
1183 u8 value0 = 0, value1 = 0;
1185 mutex_lock(&bdev->mutex);
1187 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_MASK0, &value0);
1188 err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_MASK1, &value1);
1190 mutex_unlock(&bdev->mutex);
1193 return compose_u16(value1, value0);
1198 static int bcm2048_get_fm_rds_flags(struct bcm2048_device *bdev)
1201 u8 value0 = 0, value1 = 0;
1203 mutex_lock(&bdev->mutex);
1205 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG0, &value0);
1206 err |= bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG1, &value1);
1208 mutex_unlock(&bdev->mutex);
1211 return compose_u16(value1, value0);
1216 static int bcm2048_get_region_bottom_frequency(struct bcm2048_device *bdev)
1218 return bdev->region_info.bottom_frequency;
1221 static int bcm2048_get_region_top_frequency(struct bcm2048_device *bdev)
1223 return bdev->region_info.top_frequency;
1226 static int bcm2048_set_fm_best_tune_mode(struct bcm2048_device *bdev, u8 mode)
1231 mutex_lock(&bdev->mutex);
1233 /* Perform read as the manual indicates */
1234 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_BEST_TUNE_MODE,
1236 value &= ~BCM2048_BEST_TUNE_MODE;
1239 value |= BCM2048_BEST_TUNE_MODE;
1240 err |= bcm2048_send_command(bdev, BCM2048_I2C_FM_BEST_TUNE_MODE,
1243 mutex_unlock(&bdev->mutex);
1247 static int bcm2048_get_fm_best_tune_mode(struct bcm2048_device *bdev)
1252 mutex_lock(&bdev->mutex);
1254 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_BEST_TUNE_MODE,
1257 mutex_unlock(&bdev->mutex);
1259 if (!err && (value & BCM2048_BEST_TUNE_MODE))
1260 return BCM2048_ITEM_ENABLED;
1265 static int bcm2048_get_fm_carrier_error(struct bcm2048_device *bdev)
1270 mutex_lock(&bdev->mutex);
1271 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_CARRIER, &value);
1272 mutex_unlock(&bdev->mutex);
1280 static int bcm2048_get_fm_rssi(struct bcm2048_device *bdev)
1285 mutex_lock(&bdev->mutex);
1286 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RSSI, &value);
1287 mutex_unlock(&bdev->mutex);
1295 static int bcm2048_set_rds_wline(struct bcm2048_device *bdev, u8 wline)
1299 mutex_lock(&bdev->mutex);
1301 err = bcm2048_send_command(bdev, BCM2048_I2C_RDS_WLINE, wline);
1304 bdev->fifo_size = wline;
1306 mutex_unlock(&bdev->mutex);
1310 static int bcm2048_get_rds_wline(struct bcm2048_device *bdev)
1315 mutex_lock(&bdev->mutex);
1317 err = bcm2048_recv_command(bdev, BCM2048_I2C_RDS_WLINE, &value);
1319 mutex_unlock(&bdev->mutex);
1322 bdev->fifo_size = value;
1329 static int bcm2048_checkrev(struct bcm2048_device *bdev)
1334 mutex_lock(&bdev->mutex);
1336 err = bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_REV, &version);
1338 mutex_unlock(&bdev->mutex);
1341 dev_info(&bdev->client->dev, "BCM2048 Version 0x%x\n",
1349 static int bcm2048_get_rds_rt(struct bcm2048_device *bdev, char *data)
1351 int err = 0, i, j = 0, ce = 0, cr = 0;
1352 char data_buffer[BCM2048_MAX_RDS_RT + 1];
1354 mutex_lock(&bdev->mutex);
1356 if (!bdev->rds_info.text_len) {
1361 for (i = 0; i < BCM2048_MAX_RDS_RT; i++) {
1362 if (bdev->rds_info.rds_rt[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];
1374 if (j <= BCM2048_MAX_RDS_RT)
1377 for (i = 0; i < BCM2048_MAX_RDS_RT; i++) {
1378 if (!bdev->rds_info.rds_rt[i]) {
1379 if (cr && (i < cr)) {
1384 if (cr && (i >= cr))
1392 memcpy(data, data_buffer, sizeof(data_buffer));
1395 mutex_unlock(&bdev->mutex);
1399 static int bcm2048_get_rds_ps(struct bcm2048_device *bdev, char *data)
1401 int err = 0, i, j = 0;
1402 char data_buffer[BCM2048_MAX_RDS_PS + 1];
1404 mutex_lock(&bdev->mutex);
1406 if (!bdev->rds_info.text_len) {
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];
1415 if (i < (BCM2048_MAX_RDS_PS - 1)) {
1422 if (j <= BCM2048_MAX_RDS_PS)
1425 memcpy(data, data_buffer, sizeof(data_buffer));
1428 mutex_unlock(&bdev->mutex);
1432 static void bcm2048_parse_rds_pi(struct bcm2048_device *bdev)
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];
1443 if (!bdev->rds_info.rds_pi) {
1444 bdev->rds_info.rds_pi = pi;
1447 if (pi != bdev->rds_info.rds_pi) {
1450 bdev->rds_info.rds_pi = pi;
1460 static int bcm2048_rds_block_crc(struct bcm2048_device *bdev, int i)
1462 return bdev->rds_info.radio_text[i] & BCM2048_RDS_CRC_MASK;
1465 static void bcm2048_parse_rds_rt_block(struct bcm2048_device *bdev, int i,
1468 /* Good data will overwrite poor data */
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];
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];
1484 static int bcm2048_parse_rt_match_b(struct bcm2048_device *bdev, int i)
1486 int crc, rt_id, rt_group_b, rt_ab, index = 0;
1488 crc = bcm2048_rds_block_crc(bdev, i);
1490 if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
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;
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;
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;
1516 index = bdev->rds_info.radio_text[i + 2] &
1517 BCM2048_RDS_RT_INDEX;
1519 if (bdev->rds_info.rds_rt_group_b)
1531 static int bcm2048_parse_rt_match_c(struct bcm2048_device *bdev, int i,
1536 crc = bcm2048_rds_block_crc(bdev, i);
1538 if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1541 BUG_ON((index+2) >= BCM2048_MAX_RDS_RT);
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)
1547 bcm2048_parse_rds_rt_block(bdev, i, index, crc);
1554 static void bcm2048_parse_rt_match_d(struct bcm2048_device *bdev, int i,
1559 crc = bcm2048_rds_block_crc(bdev, i);
1561 if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1564 BUG_ON((index+4) >= BCM2048_MAX_RDS_RT);
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);
1571 static void bcm2048_parse_rds_rt(struct bcm2048_device *bdev)
1573 int i, index = 0, crc, match_b = 0, match_c = 0, match_d = 0;
1575 for (i = 0; i < bdev->fifo_size; i += BCM2048_RDS_FIFO_DUPLE_SIZE) {
1578 index = bcm2048_parse_rt_match_b(bdev, i);
1579 if (index >= 0 && index <= (BCM2048_MAX_RDS_RT - 5))
1582 } else if (match_c) {
1584 if (bcm2048_parse_rt_match_c(bdev, i, index))
1587 } else if (match_d) {
1589 bcm2048_parse_rt_match_d(bdev, i, index);
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)
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)
1608 static void bcm2048_parse_rds_ps_block(struct bcm2048_device *bdev, int i,
1611 /* Good data will overwrite poor data */
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];
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];
1627 static int bcm2048_parse_ps_match_c(struct bcm2048_device *bdev, int i,
1632 crc = bcm2048_rds_block_crc(bdev, i);
1634 if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
1637 if ((bdev->rds_info.radio_text[i] & BCM2048_RDS_BLOCK_MASK) ==
1638 BCM2048_RDS_BLOCK_C)
1644 static void bcm2048_parse_ps_match_d(struct bcm2048_device *bdev, int i,
1649 crc = bcm2048_rds_block_crc(bdev, i);
1651 if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
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);
1659 static int bcm2048_parse_ps_match_b(struct bcm2048_device *bdev, int i)
1661 int crc, index, ps_id, ps_group;
1663 crc = bcm2048_rds_block_crc(bdev, i);
1665 if (crc == BCM2048_RDS_CRC_UNRECOVARABLE)
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;
1677 * Poor RSSI will lead to RDS data corruption
1678 * So using 3 (same) sequential values to justify major changes
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");
1692 bdev->rds_info.rds_ps_group_cnt = 0;
1696 if (ps_id == BCM2048_RDS_PS) {
1697 index = bdev->rds_info.radio_text[i + 2] &
1698 BCM2048_RDS_PS_INDEX;
1707 static void bcm2048_parse_rds_ps(struct bcm2048_device *bdev)
1709 int i, index = 0, crc, match_b = 0, match_c = 0, match_d = 0;
1711 for (i = 0; i < bdev->fifo_size; i += BCM2048_RDS_FIFO_DUPLE_SIZE) {
1714 index = bcm2048_parse_ps_match_b(bdev, i);
1715 if (index >= 0 && index < (BCM2048_MAX_RDS_PS - 1))
1718 } else if (match_c) {
1720 if (bcm2048_parse_ps_match_c(bdev, i, index))
1723 } else if (match_d) {
1725 bcm2048_parse_ps_match_d(bdev, i, index);
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)
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)
1744 static void bcm2048_rds_fifo_receive(struct bcm2048_device *bdev)
1748 mutex_lock(&bdev->mutex);
1750 err = bcm2048_recv_duples(bdev, BCM2048_I2C_RDS_DATA,
1751 bdev->rds_info.radio_text, bdev->fifo_size);
1753 dev_err(&bdev->client->dev, "RDS Read problem\n");
1754 mutex_unlock(&bdev->mutex);
1758 bdev->rds_info.text_len = bdev->fifo_size;
1760 bcm2048_parse_rds_pi(bdev);
1761 bcm2048_parse_rds_rt(bdev);
1762 bcm2048_parse_rds_ps(bdev);
1764 mutex_unlock(&bdev->mutex);
1766 wake_up_interruptible(&bdev->read_queue);
1769 static int bcm2048_get_rds_data(struct bcm2048_device *bdev, char *data)
1771 int err = 0, i, p = 0;
1774 mutex_lock(&bdev->mutex);
1776 if (!bdev->rds_info.text_len) {
1781 data_buffer = kcalloc(BCM2048_MAX_RDS_RADIO_TEXT, 5, GFP_KERNEL);
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]);
1792 memcpy(data, data_buffer, p);
1796 mutex_unlock(&bdev->mutex);
1801 * BCM2048 default initialization sequence
1803 static int bcm2048_init(struct bcm2048_device *bdev)
1807 err = bcm2048_set_power_state(bdev, BCM2048_POWER_ON);
1811 err = bcm2048_set_audio_route(bdev, BCM2048_AUDIO_ROUTE_DAC);
1815 err = bcm2048_set_dac_output(bdev, BCM2048_DAC_OUTPUT_LEFT |
1816 BCM2048_DAC_OUTPUT_RIGHT);
1823 * BCM2048 default deinitialization sequence
1825 static int bcm2048_deinit(struct bcm2048_device *bdev)
1829 err = bcm2048_set_audio_route(bdev, 0);
1833 err = bcm2048_set_dac_output(bdev, 0);
1837 return bcm2048_set_power_state(bdev, BCM2048_POWER_OFF);
1841 * BCM2048 probe sequence
1843 static int bcm2048_probe(struct bcm2048_device *bdev)
1847 err = bcm2048_set_power_state(bdev, BCM2048_POWER_ON);
1851 err = bcm2048_checkrev(bdev);
1855 err = bcm2048_set_mute(bdev, BCM2048_DEFAULT_MUTE);
1859 err = bcm2048_set_region(bdev, BCM2048_DEFAULT_REGION);
1863 err = bcm2048_set_fm_search_rssi_threshold(bdev,
1864 BCM2048_DEFAULT_RSSI_THRESHOLD);
1868 err = bcm2048_set_fm_automatic_stereo_mono(bdev, BCM2048_ITEM_ENABLED);
1872 err = bcm2048_get_rds_wline(bdev);
1873 if (err < BCM2048_DEFAULT_RDS_WLINE)
1874 err = bcm2048_set_rds_wline(bdev, BCM2048_DEFAULT_RDS_WLINE);
1878 err = bcm2048_set_power_state(bdev, BCM2048_POWER_OFF);
1880 init_waitqueue_head(&bdev->read_queue);
1881 bdev->rds_data_available = 0;
1890 * BCM2048 workqueue handler
1892 static void bcm2048_work(struct work_struct *work)
1894 struct bcm2048_device *bdev;
1895 u8 flag_lsb = 0, flag_msb = 0, flags;
1897 bdev = container_of(work, struct bcm2048_device, work);
1898 bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG0, &flag_lsb);
1899 bcm2048_recv_command(bdev, BCM2048_I2C_FM_RDS_FLAG1, &flag_msb);
1901 if (flag_lsb & (BCM2048_FM_FLAG_SEARCH_TUNE_FINISHED |
1902 BCM2048_FM_FLAG_SEARCH_TUNE_FAIL)) {
1903 if (flag_lsb & BCM2048_FM_FLAG_SEARCH_TUNE_FAIL)
1904 bdev->scan_state = BCM2048_SCAN_FAIL;
1906 bdev->scan_state = BCM2048_SCAN_OK;
1908 complete(&bdev->compl);
1911 if (flag_msb & BCM2048_RDS_FLAG_FIFO_WLINE) {
1912 bcm2048_rds_fifo_receive(bdev);
1913 if (bdev->rds_state) {
1914 flags = BCM2048_RDS_FLAG_FIFO_WLINE;
1915 bcm2048_send_command(bdev, BCM2048_I2C_FM_RDS_MASK1,
1918 bdev->rds_data_available = 1;
1919 bdev->rd_index = 0; /* new data, new start */
1924 * BCM2048 interrupt handler
1926 static irqreturn_t bcm2048_handler(int irq, void *dev)
1928 struct bcm2048_device *bdev = dev;
1930 dev_dbg(&bdev->client->dev, "IRQ called, queuing work\n");
1931 if (bdev->power_state)
1932 schedule_work(&bdev->work);
1938 * BCM2048 sysfs interface definitions
1940 #define property_write(prop, type, mask, check) \
1941 static ssize_t bcm2048_##prop##_write(struct device *dev, \
1942 struct device_attribute *attr, \
1946 struct bcm2048_device *bdev = dev_get_drvdata(dev); \
1953 if (sscanf(buf, mask, &value) != 1) \
1959 err = bcm2048_set_##prop(bdev, value); \
1961 return err < 0 ? err : count; \
1964 #define property_read(prop, size, mask) \
1965 static ssize_t bcm2048_##prop##_read(struct device *dev, \
1966 struct device_attribute *attr, \
1969 struct bcm2048_device *bdev = dev_get_drvdata(dev); \
1975 value = bcm2048_get_##prop(bdev); \
1978 value = sprintf(buf, mask "\n", value); \
1983 #define property_signed_read(prop, size, mask) \
1984 static ssize_t bcm2048_##prop##_read(struct device *dev, \
1985 struct device_attribute *attr, \
1988 struct bcm2048_device *bdev = dev_get_drvdata(dev); \
1994 value = bcm2048_get_##prop(bdev); \
1996 return sprintf(buf, mask "\n", value); \
1999 #define DEFINE_SYSFS_PROPERTY(prop, signal, size, mask, check) \
2000 property_write(prop, signal size, mask, check) \
2001 property_read(prop, size, mask)
2003 #define property_str_read(prop, size) \
2004 static ssize_t bcm2048_##prop##_read(struct device *dev, \
2005 struct device_attribute *attr, \
2008 struct bcm2048_device *bdev = dev_get_drvdata(dev); \
2015 out = kzalloc(size + 1, GFP_KERNEL); \
2019 bcm2048_get_##prop(bdev, out); \
2020 count = sprintf(buf, "%s\n", out); \
2027 DEFINE_SYSFS_PROPERTY(power_state, unsigned, int, "%u", 0)
2028 DEFINE_SYSFS_PROPERTY(mute, unsigned, int, "%u", 0)
2029 DEFINE_SYSFS_PROPERTY(audio_route, unsigned, int, "%u", 0)
2030 DEFINE_SYSFS_PROPERTY(dac_output, unsigned, int, "%u", 0)
2032 DEFINE_SYSFS_PROPERTY(fm_hi_lo_injection, unsigned, int, "%u", 0)
2033 DEFINE_SYSFS_PROPERTY(fm_frequency, unsigned, int, "%u", 0)
2034 DEFINE_SYSFS_PROPERTY(fm_af_frequency, unsigned, int, "%u", 0)
2035 DEFINE_SYSFS_PROPERTY(fm_deemphasis, unsigned, int, "%u", 0)
2036 DEFINE_SYSFS_PROPERTY(fm_rds_mask, unsigned, int, "%u", 0)
2037 DEFINE_SYSFS_PROPERTY(fm_best_tune_mode, unsigned, int, "%u", 0)
2038 DEFINE_SYSFS_PROPERTY(fm_search_rssi_threshold, unsigned, int, "%u", 0)
2039 DEFINE_SYSFS_PROPERTY(fm_search_mode_direction, unsigned, int, "%u", 0)
2040 DEFINE_SYSFS_PROPERTY(fm_search_tune_mode, unsigned, int, "%u", value > 3)
2042 DEFINE_SYSFS_PROPERTY(rds, unsigned, int, "%u", 0)
2043 DEFINE_SYSFS_PROPERTY(rds_b_block_mask, unsigned, int, "%u", 0)
2044 DEFINE_SYSFS_PROPERTY(rds_b_block_match, unsigned, int, "%u", 0)
2045 DEFINE_SYSFS_PROPERTY(rds_pi_mask, unsigned, int, "%u", 0)
2046 DEFINE_SYSFS_PROPERTY(rds_pi_match, unsigned, int, "%u", 0)
2047 DEFINE_SYSFS_PROPERTY(rds_wline, unsigned, int, "%u", 0)
2048 property_read(rds_pi, unsigned int, "%x")
2049 property_str_read(rds_rt, (BCM2048_MAX_RDS_RT + 1))
2050 property_str_read(rds_ps, (BCM2048_MAX_RDS_PS + 1))
2052 property_read(fm_rds_flags, unsigned int, "%u")
2053 property_str_read(rds_data, BCM2048_MAX_RDS_RADIO_TEXT * 5)
2055 property_read(region_bottom_frequency, unsigned int, "%u")
2056 property_read(region_top_frequency, unsigned int, "%u")
2057 property_signed_read(fm_carrier_error, int, "%d")
2058 property_signed_read(fm_rssi, int, "%d")
2059 DEFINE_SYSFS_PROPERTY(region, unsigned, int, "%u", 0)
2061 static struct device_attribute attrs[] = {
2062 __ATTR(power_state, S_IRUGO | S_IWUSR, bcm2048_power_state_read,
2063 bcm2048_power_state_write),
2064 __ATTR(mute, S_IRUGO | S_IWUSR, bcm2048_mute_read,
2065 bcm2048_mute_write),
2066 __ATTR(audio_route, S_IRUGO | S_IWUSR, bcm2048_audio_route_read,
2067 bcm2048_audio_route_write),
2068 __ATTR(dac_output, S_IRUGO | S_IWUSR, bcm2048_dac_output_read,
2069 bcm2048_dac_output_write),
2070 __ATTR(fm_hi_lo_injection, S_IRUGO | S_IWUSR,
2071 bcm2048_fm_hi_lo_injection_read,
2072 bcm2048_fm_hi_lo_injection_write),
2073 __ATTR(fm_frequency, S_IRUGO | S_IWUSR, bcm2048_fm_frequency_read,
2074 bcm2048_fm_frequency_write),
2075 __ATTR(fm_af_frequency, S_IRUGO | S_IWUSR,
2076 bcm2048_fm_af_frequency_read,
2077 bcm2048_fm_af_frequency_write),
2078 __ATTR(fm_deemphasis, S_IRUGO | S_IWUSR, bcm2048_fm_deemphasis_read,
2079 bcm2048_fm_deemphasis_write),
2080 __ATTR(fm_rds_mask, S_IRUGO | S_IWUSR, bcm2048_fm_rds_mask_read,
2081 bcm2048_fm_rds_mask_write),
2082 __ATTR(fm_best_tune_mode, S_IRUGO | S_IWUSR,
2083 bcm2048_fm_best_tune_mode_read,
2084 bcm2048_fm_best_tune_mode_write),
2085 __ATTR(fm_search_rssi_threshold, S_IRUGO | S_IWUSR,
2086 bcm2048_fm_search_rssi_threshold_read,
2087 bcm2048_fm_search_rssi_threshold_write),
2088 __ATTR(fm_search_mode_direction, S_IRUGO | S_IWUSR,
2089 bcm2048_fm_search_mode_direction_read,
2090 bcm2048_fm_search_mode_direction_write),
2091 __ATTR(fm_search_tune_mode, S_IRUGO | S_IWUSR,
2092 bcm2048_fm_search_tune_mode_read,
2093 bcm2048_fm_search_tune_mode_write),
2094 __ATTR(rds, S_IRUGO | S_IWUSR, bcm2048_rds_read,
2096 __ATTR(rds_b_block_mask, S_IRUGO | S_IWUSR,
2097 bcm2048_rds_b_block_mask_read,
2098 bcm2048_rds_b_block_mask_write),
2099 __ATTR(rds_b_block_match, S_IRUGO | S_IWUSR,
2100 bcm2048_rds_b_block_match_read,
2101 bcm2048_rds_b_block_match_write),
2102 __ATTR(rds_pi_mask, S_IRUGO | S_IWUSR, bcm2048_rds_pi_mask_read,
2103 bcm2048_rds_pi_mask_write),
2104 __ATTR(rds_pi_match, S_IRUGO | S_IWUSR, bcm2048_rds_pi_match_read,
2105 bcm2048_rds_pi_match_write),
2106 __ATTR(rds_wline, S_IRUGO | S_IWUSR, bcm2048_rds_wline_read,
2107 bcm2048_rds_wline_write),
2108 __ATTR(rds_pi, S_IRUGO, bcm2048_rds_pi_read, NULL),
2109 __ATTR(rds_rt, S_IRUGO, bcm2048_rds_rt_read, NULL),
2110 __ATTR(rds_ps, S_IRUGO, bcm2048_rds_ps_read, NULL),
2111 __ATTR(fm_rds_flags, S_IRUGO, bcm2048_fm_rds_flags_read, NULL),
2112 __ATTR(region_bottom_frequency, S_IRUGO,
2113 bcm2048_region_bottom_frequency_read, NULL),
2114 __ATTR(region_top_frequency, S_IRUGO,
2115 bcm2048_region_top_frequency_read, NULL),
2116 __ATTR(fm_carrier_error, S_IRUGO,
2117 bcm2048_fm_carrier_error_read, NULL),
2118 __ATTR(fm_rssi, S_IRUGO,
2119 bcm2048_fm_rssi_read, NULL),
2120 __ATTR(region, S_IRUGO | S_IWUSR, bcm2048_region_read,
2121 bcm2048_region_write),
2122 __ATTR(rds_data, S_IRUGO, bcm2048_rds_data_read, NULL),
2125 static int bcm2048_sysfs_unregister_properties(struct bcm2048_device *bdev,
2130 for (i = 0; i < size; i++)
2131 device_remove_file(&bdev->client->dev, &attrs[i]);
2136 static int bcm2048_sysfs_register_properties(struct bcm2048_device *bdev)
2141 for (i = 0; i < ARRAY_SIZE(attrs); i++) {
2142 if (device_create_file(&bdev->client->dev, &attrs[i]) != 0) {
2143 dev_err(&bdev->client->dev,
2144 "could not register sysfs entry\n");
2146 bcm2048_sysfs_unregister_properties(bdev, i);
2154 static int bcm2048_fops_open(struct file *file)
2156 struct bcm2048_device *bdev = video_drvdata(file);
2160 bdev->rds_data_available = 0;
2165 static int bcm2048_fops_release(struct file *file)
2167 struct bcm2048_device *bdev = video_drvdata(file);
2174 static unsigned int bcm2048_fops_poll(struct file *file,
2175 struct poll_table_struct *pts)
2177 struct bcm2048_device *bdev = video_drvdata(file);
2180 poll_wait(file, &bdev->read_queue, pts);
2182 if (bdev->rds_data_available)
2183 retval = POLLIN | POLLRDNORM;
2188 static ssize_t bcm2048_fops_read(struct file *file, char __user *buf,
2189 size_t count, loff_t *ppos)
2191 struct bcm2048_device *bdev = video_drvdata(file);
2195 /* we return at least 3 bytes, one block */
2196 count = (count / 3) * 3; /* only multiples of 3 */
2200 while (!bdev->rds_data_available) {
2201 if (file->f_flags & O_NONBLOCK) {
2202 retval = -EWOULDBLOCK;
2205 /* interruptible_sleep_on(&bdev->read_queue); */
2206 if (wait_event_interruptible(bdev->read_queue,
2207 bdev->rds_data_available) < 0) {
2213 mutex_lock(&bdev->mutex);
2214 /* copy data to userspace */
2215 i = bdev->fifo_size - bdev->rd_index;
2217 count = (i / 3) * 3;
2221 unsigned char tmpbuf[3];
2223 tmpbuf[i] = bdev->rds_info.radio_text[bdev->rd_index + i + 2];
2225 bdev->rds_info.radio_text[bdev->rd_index + i + 1];
2227 (bdev->rds_info.radio_text[bdev->rd_index + i] &
2229 if ((bdev->rds_info.radio_text[bdev->rd_index + i] &
2230 BCM2048_RDS_CRC_MASK) == BCM2048_RDS_CRC_UNRECOVARABLE)
2231 tmpbuf[i + 2] |= 0x80;
2232 if (copy_to_user(buf + i, tmpbuf, 3)) {
2239 bdev->rd_index += i;
2240 if (bdev->rd_index >= bdev->fifo_size)
2241 bdev->rds_data_available = 0;
2243 mutex_unlock(&bdev->mutex);
2252 * bcm2048_fops - file operations interface
2254 static const struct v4l2_file_operations bcm2048_fops = {
2255 .owner = THIS_MODULE,
2256 .unlocked_ioctl = video_ioctl2,
2257 /* for RDS read support */
2258 .open = bcm2048_fops_open,
2259 .release = bcm2048_fops_release,
2260 .read = bcm2048_fops_read,
2261 .poll = bcm2048_fops_poll
2265 * Video4Linux Interface
2267 static struct v4l2_queryctrl bcm2048_v4l2_queryctrl[] = {
2269 .id = V4L2_CID_AUDIO_VOLUME,
2270 .flags = V4L2_CTRL_FLAG_DISABLED,
2273 .id = V4L2_CID_AUDIO_BALANCE,
2274 .flags = V4L2_CTRL_FLAG_DISABLED,
2277 .id = V4L2_CID_AUDIO_BASS,
2278 .flags = V4L2_CTRL_FLAG_DISABLED,
2281 .id = V4L2_CID_AUDIO_TREBLE,
2282 .flags = V4L2_CTRL_FLAG_DISABLED,
2285 .id = V4L2_CID_AUDIO_MUTE,
2286 .type = V4L2_CTRL_TYPE_BOOLEAN,
2294 .id = V4L2_CID_AUDIO_LOUDNESS,
2295 .flags = V4L2_CTRL_FLAG_DISABLED,
2299 static int bcm2048_vidioc_querycap(struct file *file, void *priv,
2300 struct v4l2_capability *capability)
2302 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2304 strlcpy(capability->driver, BCM2048_DRIVER_NAME,
2305 sizeof(capability->driver));
2306 strlcpy(capability->card, BCM2048_DRIVER_CARD,
2307 sizeof(capability->card));
2308 snprintf(capability->bus_info, 32, "I2C: 0x%X", bdev->client->addr);
2309 capability->device_caps = V4L2_CAP_TUNER | V4L2_CAP_RADIO |
2310 V4L2_CAP_HW_FREQ_SEEK;
2311 capability->capabilities = capability->device_caps |
2312 V4L2_CAP_DEVICE_CAPS;
2317 static int bcm2048_vidioc_g_input(struct file *filp, void *priv,
2325 static int bcm2048_vidioc_s_input(struct file *filp, void *priv,
2334 static int bcm2048_vidioc_queryctrl(struct file *file, void *priv,
2335 struct v4l2_queryctrl *qc)
2339 for (i = 0; i < ARRAY_SIZE(bcm2048_v4l2_queryctrl); i++) {
2340 if (qc->id && qc->id == bcm2048_v4l2_queryctrl[i].id) {
2341 *qc = bcm2048_v4l2_queryctrl[i];
2349 static int bcm2048_vidioc_g_ctrl(struct file *file, void *priv,
2350 struct v4l2_control *ctrl)
2352 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2359 case V4L2_CID_AUDIO_MUTE:
2360 err = bcm2048_get_mute(bdev);
2369 static int bcm2048_vidioc_s_ctrl(struct file *file, void *priv,
2370 struct v4l2_control *ctrl)
2372 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2379 case V4L2_CID_AUDIO_MUTE:
2381 if (bdev->power_state) {
2382 err = bcm2048_set_mute(bdev, ctrl->value);
2383 err |= bcm2048_deinit(bdev);
2386 if (!bdev->power_state) {
2387 err = bcm2048_init(bdev);
2388 err |= bcm2048_set_mute(bdev, ctrl->value);
2397 static int bcm2048_vidioc_g_audio(struct file *file, void *priv,
2398 struct v4l2_audio *audio)
2400 if (audio->index > 1)
2403 strncpy(audio->name, "Radio", 32);
2404 audio->capability = V4L2_AUDCAP_STEREO;
2409 static int bcm2048_vidioc_s_audio(struct file *file, void *priv,
2410 const struct v4l2_audio *audio)
2412 if (audio->index != 0)
2418 static int bcm2048_vidioc_g_tuner(struct file *file, void *priv,
2419 struct v4l2_tuner *tuner)
2421 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2428 if (tuner->index > 0)
2431 strncpy(tuner->name, "FM Receiver", 32);
2432 tuner->type = V4L2_TUNER_RADIO;
2434 dev_to_v4l2(bcm2048_get_region_bottom_frequency(bdev));
2436 dev_to_v4l2(bcm2048_get_region_top_frequency(bdev));
2437 tuner->rxsubchans = V4L2_TUNER_SUB_STEREO;
2438 tuner->capability = V4L2_TUNER_CAP_STEREO | V4L2_TUNER_CAP_LOW;
2439 tuner->audmode = V4L2_TUNER_MODE_STEREO;
2441 if (bdev->power_state) {
2443 * Report frequencies with high carrier errors to have zero
2446 f_error = bcm2048_get_fm_carrier_error(bdev);
2447 if (f_error < BCM2048_FREQ_ERROR_FLOOR ||
2448 f_error > BCM2048_FREQ_ERROR_ROOF) {
2452 * RSSI level -60 dB is defined to report full
2455 rssi = bcm2048_get_fm_rssi(bdev);
2456 if (rssi >= BCM2048_RSSI_LEVEL_BASE) {
2457 tuner->signal = 0xFFFF;
2458 } else if (rssi > BCM2048_RSSI_LEVEL_ROOF) {
2459 tuner->signal = (rssi +
2460 BCM2048_RSSI_LEVEL_ROOF_NEG)
2461 * BCM2048_SIGNAL_MULTIPLIER;
2473 static int bcm2048_vidioc_s_tuner(struct file *file, void *priv,
2474 const struct v4l2_tuner *tuner)
2476 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2481 if (tuner->index > 0)
2487 static int bcm2048_vidioc_g_frequency(struct file *file, void *priv,
2488 struct v4l2_frequency *freq)
2490 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2494 if (!bdev->power_state)
2497 freq->type = V4L2_TUNER_RADIO;
2498 f = bcm2048_get_fm_frequency(bdev);
2503 freq->frequency = dev_to_v4l2(f);
2508 static int bcm2048_vidioc_s_frequency(struct file *file, void *priv,
2509 const struct v4l2_frequency *freq)
2511 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2514 if (freq->type != V4L2_TUNER_RADIO)
2517 if (!bdev->power_state)
2520 err = bcm2048_set_fm_frequency(bdev, v4l2_to_dev(freq->frequency));
2521 err |= bcm2048_set_fm_search_tune_mode(bdev, BCM2048_FM_PRE_SET_MODE);
2526 static int bcm2048_vidioc_s_hw_freq_seek(struct file *file, void *priv,
2527 const struct v4l2_hw_freq_seek *seek)
2529 struct bcm2048_device *bdev = video_get_drvdata(video_devdata(file));
2532 if (!bdev->power_state)
2535 if ((seek->tuner != 0) || (seek->type != V4L2_TUNER_RADIO))
2538 err = bcm2048_set_fm_search_mode_direction(bdev, seek->seek_upward);
2539 err |= bcm2048_set_fm_search_tune_mode(bdev,
2540 BCM2048_FM_AUTO_SEARCH_MODE);
2545 static struct v4l2_ioctl_ops bcm2048_ioctl_ops = {
2546 .vidioc_querycap = bcm2048_vidioc_querycap,
2547 .vidioc_g_input = bcm2048_vidioc_g_input,
2548 .vidioc_s_input = bcm2048_vidioc_s_input,
2549 .vidioc_queryctrl = bcm2048_vidioc_queryctrl,
2550 .vidioc_g_ctrl = bcm2048_vidioc_g_ctrl,
2551 .vidioc_s_ctrl = bcm2048_vidioc_s_ctrl,
2552 .vidioc_g_audio = bcm2048_vidioc_g_audio,
2553 .vidioc_s_audio = bcm2048_vidioc_s_audio,
2554 .vidioc_g_tuner = bcm2048_vidioc_g_tuner,
2555 .vidioc_s_tuner = bcm2048_vidioc_s_tuner,
2556 .vidioc_g_frequency = bcm2048_vidioc_g_frequency,
2557 .vidioc_s_frequency = bcm2048_vidioc_s_frequency,
2558 .vidioc_s_hw_freq_seek = bcm2048_vidioc_s_hw_freq_seek,
2562 * bcm2048_viddev_template - video device interface
2564 static struct video_device bcm2048_viddev_template = {
2565 .fops = &bcm2048_fops,
2566 .name = BCM2048_DRIVER_NAME,
2567 .release = video_device_release_empty,
2568 .ioctl_ops = &bcm2048_ioctl_ops,
2572 * I2C driver interface
2574 static int bcm2048_i2c_driver_probe(struct i2c_client *client,
2575 const struct i2c_device_id *id)
2577 struct bcm2048_device *bdev;
2580 bdev = kzalloc(sizeof(*bdev), GFP_KERNEL);
2586 bdev->client = client;
2587 i2c_set_clientdata(client, bdev);
2588 mutex_init(&bdev->mutex);
2589 init_completion(&bdev->compl);
2590 INIT_WORK(&bdev->work, bcm2048_work);
2593 err = request_irq(client->irq,
2594 bcm2048_handler, IRQF_TRIGGER_FALLING,
2595 client->name, bdev);
2597 dev_err(&client->dev, "Could not request IRQ\n");
2600 dev_dbg(&client->dev, "IRQ requested.\n");
2602 dev_dbg(&client->dev, "IRQ not configured. Using timeouts.\n");
2605 bdev->videodev = bcm2048_viddev_template;
2606 video_set_drvdata(&bdev->videodev, bdev);
2607 if (video_register_device(&bdev->videodev, VFL_TYPE_RADIO, radio_nr)) {
2608 dev_dbg(&client->dev, "Could not register video device.\n");
2613 err = bcm2048_sysfs_register_properties(bdev);
2615 dev_dbg(&client->dev, "Could not register sysfs interface.\n");
2616 goto free_registration;
2619 err = bcm2048_probe(bdev);
2621 dev_dbg(&client->dev, "Failed to probe device information.\n");
2628 bcm2048_sysfs_unregister_properties(bdev, ARRAY_SIZE(attrs));
2630 video_unregister_device(&bdev->videodev);
2633 free_irq(client->irq, bdev);
2635 i2c_set_clientdata(client, NULL);
2641 static int __exit bcm2048_i2c_driver_remove(struct i2c_client *client)
2643 struct bcm2048_device *bdev = i2c_get_clientdata(client);
2645 if (!client->adapter)
2649 bcm2048_sysfs_unregister_properties(bdev, ARRAY_SIZE(attrs));
2650 video_unregister_device(&bdev->videodev);
2652 if (bdev->power_state)
2653 bcm2048_set_power_state(bdev, BCM2048_POWER_OFF);
2655 if (client->irq > 0)
2656 free_irq(client->irq, bdev);
2658 cancel_work_sync(&bdev->work);
2667 * bcm2048_i2c_driver - i2c driver interface
2669 static const struct i2c_device_id bcm2048_id[] = {
2673 MODULE_DEVICE_TABLE(i2c, bcm2048_id);
2675 static struct i2c_driver bcm2048_i2c_driver = {
2677 .name = BCM2048_DRIVER_NAME,
2679 .probe = bcm2048_i2c_driver_probe,
2680 .remove = __exit_p(bcm2048_i2c_driver_remove),
2681 .id_table = bcm2048_id,
2684 module_i2c_driver(bcm2048_i2c_driver);
2686 MODULE_LICENSE("GPL");
2687 MODULE_AUTHOR(BCM2048_DRIVER_AUTHOR);
2688 MODULE_DESCRIPTION(BCM2048_DRIVER_DESC);
2689 MODULE_VERSION("0.0.2");